chanmgr: Add an error case if a final_attempt neither succeeds or fails

This can happen in weird corner cases, so it's probably best to
report it rather than having an "internal error."
This commit is contained in:
Nick Mathewson 2022-10-18 11:30:51 -04:00
parent 4b0c28014d
commit 06132d9f35
2 changed files with 11 additions and 1 deletions

View File

@ -96,6 +96,11 @@ pub enum Error {
#[error("No plugin available for the transport {0}")]
NoSuchTransport(tor_linkspec::TransportId),
/// An attempt to open a channel failed because it was cancelled or
/// superseded by another request or configuration change.
#[error("Channel request cancelled or superseded")]
RequestCancelled,
/// An internal error of some kind that should never occur.
#[error("Internal error")]
Internal(#[from] tor_error::Bug),
@ -132,7 +137,8 @@ impl tor_error::HasKind for Error {
E::UnusableTarget(_) | E::Internal(_) => EK::Internal,
E::MissingId => EK::BadApiUsage,
E::IdentityConflict => EK::TorAccessFailed,
Error::ChannelBuild { .. } => EK::TorAccessFailed,
E::ChannelBuild { .. } => EK::TorAccessFailed,
E::RequestCancelled => EK::TransientFailure,
}
}
}
@ -169,6 +175,8 @@ impl tor_error::HasRetryTime for Error {
// transports, is reconfigured.
E::NoSuchTransport(_) => RT::Never,
E::RequestCancelled => RT::Never,
// These aren't recoverable at all.
E::Spawn { .. } | E::MissingId | E::Internal(_) => RT::Never,
}

View File

@ -203,6 +203,7 @@ impl<CF: AbstractChannelFactory> AbstractChanMgr<CF> {
// identities we want. Check for this.
final_attempt = true;
provenance = ChanProvenance::NewlyCreated;
last_err.get_or_insert(Error::RequestCancelled);
}
Ok(Err(e)) => {
last_err = Some(e);
@ -229,6 +230,7 @@ impl<CF: AbstractChannelFactory> AbstractChanMgr<CF> {
Ok(None) => {
final_attempt = true;
provenance = ChanProvenance::NewlyCreated;
last_err.get_or_insert(Error::RequestCancelled);
}
Err(e) => last_err = Some(e),
}