tor_keymgr/keystore/arti/
err.rs

1//! An error type for [`ArtiNativeKeystore`](crate::ArtiNativeKeystore).
2
3use crate::keystore::fs_utils::FilesystemError;
4use crate::{ArtiPathSyntaxError, KeystoreError, UnknownKeyTypeError};
5use tor_error::{ErrorKind, HasKind};
6use tor_key_forge::{CertType, KeyType, SshKeyAlgorithm};
7
8use std::path::PathBuf;
9use std::sync::Arc;
10
11/// An error returned by [`ArtiNativeKeystore`](crate::ArtiNativeKeystore)'s
12/// [`Keystore`](crate::Keystore) implementation.
13#[derive(thiserror::Error, Debug, Clone)]
14pub(crate) enum ArtiNativeKeystoreError {
15    /// An error that occurred while accessing the filesystem.
16    #[error("{0}")]
17    Filesystem(#[from] FilesystemError),
18
19    /// Found a key with an invalid path.
20    #[error("Key has invalid path: {path}")]
21    MalformedPath {
22        /// The path of the key.
23        path: PathBuf,
24        /// The underlying error.
25        #[source]
26        err: MalformedPathError,
27    },
28
29    /// An error due to encountering an unsupported [`KeyType`].
30    #[error("{0}")]
31    UnknownKeyType(#[from] UnknownKeyTypeError),
32
33    /// Failed to parse an OpenSSH key
34    #[error("Failed to parse OpenSSH with type {key_type:?}")]
35    SshKeyParse {
36        /// The path of the malformed key.
37        path: PathBuf,
38        /// The type of key we were trying to fetch.
39        key_type: KeyType,
40        /// The underlying error.
41        #[source]
42        err: Arc<ssh_key::Error>,
43    },
44
45    /// The OpenSSH key we retrieved is of the wrong type.
46    #[error("Unexpected OpenSSH key type: wanted {wanted_key_algo}, found {found_key_algo}")]
47    UnexpectedSshKeyType {
48        /// The path of the malformed key.
49        path: PathBuf,
50        /// The algorithm we expected the key to use.
51        wanted_key_algo: SshKeyAlgorithm,
52        /// The algorithm of the key we got.
53        found_key_algo: SshKeyAlgorithm,
54    },
55
56    /// Failed to parse an OpenSSH key
57    #[error("Failed to parse cert with type {cert_type:?}")]
58    CertParse {
59        /// The path of the malformed key.
60        path: PathBuf,
61        /// The type of cert we were trying to fetch.
62        cert_type: CertType,
63        /// The underlying error.
64        #[source]
65        err: tor_bytes::Error,
66    },
67
68    /// An internal error.
69    #[error("Internal error")]
70    Bug(#[from] tor_error::Bug),
71}
72
73/// The keystore contained a file whose name syntactically improper
74///
75/// Keys are supposed to have pathnames consisting of an `ArtiPath`
76/// followed by a file extension.
77///
78/// See also [`KeyPathError`](crate::KeyPathError), which occurs at a higher level.
79#[derive(thiserror::Error, Debug, Clone)]
80pub(crate) enum MalformedPathError {
81    /// Found a key with a non-UTF-8 path.
82    #[error("the path is not valid UTF-8")]
83    Utf8,
84
85    /// Found a key with no extension.
86    #[error("no extension")]
87    NoExtension,
88
89    /// The file path is not a valid [`ArtiPath`](crate::ArtiPath).
90    #[error("not a valid ArtiPath")]
91    InvalidArtiPath(ArtiPathSyntaxError),
92}
93
94impl KeystoreError for ArtiNativeKeystoreError {}
95
96impl HasKind for ArtiNativeKeystoreError {
97    fn kind(&self) -> ErrorKind {
98        use ArtiNativeKeystoreError as KE;
99
100        match self {
101            KE::Filesystem(e) => e.kind(),
102            KE::MalformedPath { .. } => ErrorKind::KeystoreAccessFailed,
103            KE::UnknownKeyType(_) => ErrorKind::KeystoreAccessFailed,
104            KE::SshKeyParse { .. } | KE::UnexpectedSshKeyType { .. } | KE::CertParse { .. } => {
105                ErrorKind::KeystoreCorrupted
106            }
107            KE::Bug(e) => e.kind(),
108        }
109    }
110}
111
112impl From<ArtiNativeKeystoreError> for crate::Error {
113    fn from(e: ArtiNativeKeystoreError) -> Self {
114        crate::Error::Keystore(Arc::new(e))
115    }
116}