Struct KeyMgr
pub(crate) struct KeyMgr {
primary_store: Box<dyn Keystore>,
secondary_stores: Vec<Box<dyn Keystore>>,
key_info_extractors: Vec<&'static dyn KeyPathInfoExtractor>,
}
Expand description
A key manager that acts as a frontend to a primary Keystore
and
any number of secondary Keystore
s.
Note: KeyMgr
is a low-level utility and does not implement caching (the key stores are
accessed for every read/write).
The KeyMgr
accessors - currently just get()
-
search the configured key stores in order: first the primary key store,
and then the secondary stores, in order.
§Concurrent key store access
The key stores will allow concurrent modification by different processes. In order to implement this safely without locking, the key store operations (get, insert, remove) will need to be atomic.
Note: KeyMgr::generate
and KeyMgr::get_or_generate
should not be used
concurrently with any other KeyMgr
operation that mutates the same key
(i.e. a key with the same ArtiPath
), because
their outcome depends on whether the selected key store
[contains
][crate::Keystore::contains]
the specified key (and thus suffers from a TOCTOU race).
Fields§
§primary_store: Box<dyn Keystore>
§secondary_stores: Vec<Box<dyn Keystore>>
§key_info_extractors: Vec<&'static dyn KeyPathInfoExtractor>
Implementations§
§impl KeyMgr
impl KeyMgr
pub fn get<K>(&self, key_spec: &dyn KeySpecifier) -> Result<Option<K>, Error>where
K: ToEncodableKey,
pub fn get<K>(&self, key_spec: &dyn KeySpecifier) -> Result<Option<K>, Error>where
K: ToEncodableKey,
Read a key from one of the key stores, and try to deserialize it as K::Key
.
The key returned is retrieved from the first key store that contains an entry for the given specifier.
Returns Ok(None)
if none of the key stores have the requested key.
pub fn get_entry<K>(
&self,
entry: &KeystoreEntry<'_>,
) -> Result<Option<K>, Error>where
K: ToEncodableKey,
pub fn get_entry<K>(
&self,
entry: &KeystoreEntry<'_>,
) -> Result<Option<K>, Error>where
K: ToEncodableKey,
Retrieve the specified keystore entry, and try to deserialize it as K::Key
.
The key returned is retrieved from the key store specified in the [KeystoreEntry
].
Returns Ok(None)
if the key store does not contain the requested entry.
Returns an error if the specified key_type
does not match K::Key::item_type()
.
pub fn get_or_generate<K>(
&self,
key_spec: &dyn KeySpecifier,
selector: KeystoreSelector<'_>,
rng: &mut dyn KeygenRng,
) -> Result<K, Error>where
K: ToEncodableKey,
<K as ToEncodableKey>::Key: Keygen,
pub fn get_or_generate<K>(
&self,
key_spec: &dyn KeySpecifier,
selector: KeystoreSelector<'_>,
rng: &mut dyn KeygenRng,
) -> Result<K, Error>where
K: ToEncodableKey,
<K as ToEncodableKey>::Key: Keygen,
Read the key identified by key_spec
.
The key returned is retrieved from the first key store that contains an entry for the given specifier.
If the requested key does not exist in any of the key stores, this generates a new key of
type K
from the key created using using K::Key
’s [Keygen
] implementation, and inserts
it into the specified keystore, returning the newly inserted value.
This is a convenience wrapper around get()
and
generate()
.
pub fn generate<K>(
&self,
key_spec: &dyn KeySpecifier,
selector: KeystoreSelector<'_>,
rng: &mut dyn KeygenRng,
overwrite: bool,
) -> Result<K, Error>where
K: ToEncodableKey,
<K as ToEncodableKey>::Key: Keygen,
pub fn generate<K>(
&self,
key_spec: &dyn KeySpecifier,
selector: KeystoreSelector<'_>,
rng: &mut dyn KeygenRng,
overwrite: bool,
) -> Result<K, Error>where
K: ToEncodableKey,
<K as ToEncodableKey>::Key: Keygen,
Generate a new key of type K
, and insert it into the key store specified by selector
.
If the key already exists in the specified key store, the overwrite
flag is used to
decide whether to overwrite it with a newly generated key.
On success, this function returns the newly generated key.
Returns Error::KeyAlreadyExists
if the key already exists in the specified key store and overwrite
is false
.
IMPORTANT: using this function concurrently with any other KeyMgr
operation that
mutates the key store state is not recommended, as it can yield surprising results! The
outcome of KeyMgr::generate
depends on whether the selected key store
[contains
][crate::Keystore::contains] the specified key, and thus suffers from a TOCTOU race.
pub fn insert<K>(
&self,
key: K,
key_spec: &dyn KeySpecifier,
selector: KeystoreSelector<'_>,
overwrite: bool,
) -> Result<Option<K>, Error>where
K: ToEncodableKey,
pub fn insert<K>(
&self,
key: K,
key_spec: &dyn KeySpecifier,
selector: KeystoreSelector<'_>,
overwrite: bool,
) -> Result<Option<K>, Error>where
K: ToEncodableKey,
Insert key
into the Keystore
specified by selector
.
If the key already exists in the specified key store, the overwrite
flag is used to
decide whether to overwrite it with the provided key.
If this key is not already in the keystore, None
is returned.
If this key already exists in the keystore, its value is updated and the old value is returned.
Returns an error if the selected keystore is not the primary keystore or one of the configured secondary stores.
pub fn remove<K>(
&self,
key_spec: &dyn KeySpecifier,
selector: KeystoreSelector<'_>,
) -> Result<Option<K>, Error>where
K: ToEncodableKey,
pub fn remove<K>(
&self,
key_spec: &dyn KeySpecifier,
selector: KeystoreSelector<'_>,
) -> Result<Option<K>, Error>where
K: ToEncodableKey,
Remove the key identified by key_spec
from the Keystore
specified by selector
.
Returns an error if the selected keystore is not the primary keystore or one of the configured secondary stores.
Returns the value of the removed key,
or Ok(None)
if the key does not exist in the requested keystore.
Returns Err
if an error occurred while trying to remove the key.
pub fn remove_entry(
&self,
entry: &KeystoreEntry<'_>,
) -> Result<Option<()>, Error>
pub fn remove_entry( &self, entry: &KeystoreEntry<'_>, ) -> Result<Option<()>, Error>
Remove the specified keystore entry.
Like KeyMgr::remove
, except this function does not return the value of the removed key.
A return value of Ok(None)
indicates the key was not found in the specified key store,
whereas Ok(Some(())
means the key was successfully removed.
pub fn list_matching(
&self,
pat: &KeyPathPattern,
) -> Result<Vec<KeystoreEntry<'_>>, Error>
pub fn list_matching( &self, pat: &KeyPathPattern, ) -> Result<Vec<KeystoreEntry<'_>>, Error>
Return the keystore entry descriptors of the keys matching the specified [KeyPathPattern
].
NOTE: This searches for matching keys in all keystores.
pub fn describe(&self, path: &KeyPath) -> Result<KeyPathInfo, KeyPathError>
pub fn describe(&self, path: &KeyPath) -> Result<KeyPathInfo, KeyPathError>
Describe the specified key.
Returns [KeyPathError::Unrecognized
] if none of the registered
[KeyPathInfoExtractor
]s is able to parse the specified [KeyPath
].
This function uses the [KeyPathInfoExtractor
]s registered using
register_key_info_extractor
,
or by DefaultKeySpecifier
.
pub fn get_key_and_cert<K, C>(
&self,
spec: &dyn KeyCertificateSpecifier,
) -> Result<Option<(K, C)>, Error>where
K: ToEncodableKey,
C: ToEncodableCert<K>,
pub fn get_key_and_cert<K, C>(
&self,
spec: &dyn KeyCertificateSpecifier,
) -> Result<Option<(K, C)>, Error>where
K: ToEncodableKey,
C: ToEncodableCert<K>,
Read the specified key and certificate from one of the key stores,
deserializing the subject key as K::Key
, the cert as C::Cert
,
and the signing key as C::SigningKey
.
Returns Ok(None)
if none of the key stores have the requested key.
This function validates the certificate using [ToEncodableCert::validate
],
returning an error if it is invalid or missing.
pub fn get_or_generate_key_and_cert<K, C>(
&self,
spec: &dyn KeyCertificateSpecifier,
make_certificate: impl FnOnce(&K, &<C as ToEncodableCert<K>>::SigningKey) -> C,
selector: KeystoreSelector<'_>,
rng: &mut dyn KeygenRng,
) -> Result<(K, C), Error>where
K: ToEncodableKey,
<K as ToEncodableKey>::Key: Keygen,
C: ToEncodableCert<K>,
pub fn get_or_generate_key_and_cert<K, C>(
&self,
spec: &dyn KeyCertificateSpecifier,
make_certificate: impl FnOnce(&K, &<C as ToEncodableCert<K>>::SigningKey) -> C,
selector: KeystoreSelector<'_>,
rng: &mut dyn KeygenRng,
) -> Result<(K, C), Error>where
K: ToEncodableKey,
<K as ToEncodableKey>::Key: Keygen,
C: ToEncodableCert<K>,
Like KeyMgr::get_key_and_cert
, except this function also generates the subject key
and its corresponding certificate if they don’t already exist.
If the key certificate is missing, it will be generated
from the subject key and signing key using the provided make_certificate
callback.
Generates the missing key and/or certificate as follows:
| Subject Key exists | Signing Key exists | Cert exists | Action |
|--------------------|--------------------|-------------|----------------------------------------|
| Y | Y | Y | Validate cert, return key and cert |
| | | | if valid, error otherwise |
|--------------------|--------------------|-------------|----------------------------------------|
| N | Y | N | Generate subject key and |
| | | | a new cert signed with signing key |
|--------------------|--------------------|-------------|----------------------------------------|
| Y | Y | N | Generate cert signed with signing key |
|--------------------|--------------------|-------------|----------------------------------------|
| Y | N | N | Error - cannot validate cert |
| | | | if signing key is not available |
|--------------------|--------------------|-------------|----------------------------------------|
| Y/N | N | N | Error - cannot generate cert |
| | | | if signing key is not available |
|--------------------|--------------------|-------------|----------------------------------------|
| N | Y/N | Y | Error - subject key was removed? |
| | | | (we found the cert, |
| | | | but the subject key is missing) |
Auto Trait Implementations§
impl Freeze for KeyMgr
impl !RefUnwindSafe for KeyMgr
impl Send for KeyMgr
impl Sync for KeyMgr
impl Unpin for KeyMgr
impl !UnwindSafe for KeyMgr
Blanket Implementations§
§impl<'a, T, E> AsTaggedExplicit<'a, E> for Twhere
T: 'a,
impl<'a, T, E> AsTaggedExplicit<'a, E> for Twhere
T: 'a,
§impl<'a, T, E> AsTaggedImplicit<'a, E> for Twhere
T: 'a,
impl<'a, T, E> AsTaggedImplicit<'a, E> for Twhere
T: 'a,
Source§impl<T> BorrowMut<T> for Twhere
T: ?Sized,
impl<T> BorrowMut<T> for Twhere
T: ?Sized,
Source§fn borrow_mut(&mut self) -> &mut T
fn borrow_mut(&mut self) -> &mut T
§impl<T> Conv for T
impl<T> Conv for T
§impl<T> Downcast for Twhere
T: Any,
impl<T> Downcast for Twhere
T: Any,
§fn into_any(self: Box<T>) -> Box<dyn Any>
fn into_any(self: Box<T>) -> Box<dyn Any>
Box<dyn Trait>
(where Trait: Downcast
) to Box<dyn Any>
, which can then be
downcast
into Box<dyn ConcreteType>
where ConcreteType
implements Trait
.§fn into_any_rc(self: Rc<T>) -> Rc<dyn Any>
fn into_any_rc(self: Rc<T>) -> Rc<dyn Any>
Rc<Trait>
(where Trait: Downcast
) to Rc<Any>
, which can then be further
downcast
into Rc<ConcreteType>
where ConcreteType
implements Trait
.§fn as_any(&self) -> &(dyn Any + 'static)
fn as_any(&self) -> &(dyn Any + 'static)
&Trait
(where Trait: Downcast
) to &Any
. This is needed since Rust cannot
generate &Any
’s vtable from &Trait
’s.§fn as_any_mut(&mut self) -> &mut (dyn Any + 'static)
fn as_any_mut(&mut self) -> &mut (dyn Any + 'static)
&mut Trait
(where Trait: Downcast
) to &Any
. This is needed since Rust cannot
generate &mut Any
’s vtable from &mut Trait
’s.§impl<T> DowncastSend for T
impl<T> DowncastSend for T
§impl<T> DowncastSync for T
impl<T> DowncastSync for T
§impl<T> FmtForward for T
impl<T> FmtForward for T
§fn fmt_binary(self) -> FmtBinary<Self>where
Self: Binary,
fn fmt_binary(self) -> FmtBinary<Self>where
Self: Binary,
self
to use its Binary
implementation when Debug
-formatted.§fn fmt_display(self) -> FmtDisplay<Self>where
Self: Display,
fn fmt_display(self) -> FmtDisplay<Self>where
Self: Display,
self
to use its Display
implementation when
Debug
-formatted.§fn fmt_lower_exp(self) -> FmtLowerExp<Self>where
Self: LowerExp,
fn fmt_lower_exp(self) -> FmtLowerExp<Self>where
Self: LowerExp,
self
to use its LowerExp
implementation when
Debug
-formatted.§fn fmt_lower_hex(self) -> FmtLowerHex<Self>where
Self: LowerHex,
fn fmt_lower_hex(self) -> FmtLowerHex<Self>where
Self: LowerHex,
self
to use its LowerHex
implementation when
Debug
-formatted.§fn fmt_octal(self) -> FmtOctal<Self>where
Self: Octal,
fn fmt_octal(self) -> FmtOctal<Self>where
Self: Octal,
self
to use its Octal
implementation when Debug
-formatted.§fn fmt_pointer(self) -> FmtPointer<Self>where
Self: Pointer,
fn fmt_pointer(self) -> FmtPointer<Self>where
Self: Pointer,
self
to use its Pointer
implementation when
Debug
-formatted.§fn fmt_upper_exp(self) -> FmtUpperExp<Self>where
Self: UpperExp,
fn fmt_upper_exp(self) -> FmtUpperExp<Self>where
Self: UpperExp,
self
to use its UpperExp
implementation when
Debug
-formatted.§fn fmt_upper_hex(self) -> FmtUpperHex<Self>where
Self: UpperHex,
fn fmt_upper_hex(self) -> FmtUpperHex<Self>where
Self: UpperHex,
self
to use its UpperHex
implementation when
Debug
-formatted.§fn fmt_list(self) -> FmtList<Self>where
&'a Self: for<'a> IntoIterator,
fn fmt_list(self) -> FmtList<Self>where
&'a Self: for<'a> IntoIterator,
§impl<T> Instrument for T
impl<T> Instrument for T
§fn instrument(self, span: Span) -> Instrumented<Self> ⓘ
fn instrument(self, span: Span) -> Instrumented<Self> ⓘ
Source§impl<T> IntoEither for T
impl<T> IntoEither for T
Source§fn into_either(self, into_left: bool) -> Either<Self, Self> ⓘ
fn into_either(self, into_left: bool) -> Either<Self, Self> ⓘ
self
into a Left
variant of Either<Self, Self>
if into_left
is true
.
Converts self
into a Right
variant of Either<Self, Self>
otherwise. Read moreSource§fn into_either_with<F>(self, into_left: F) -> Either<Self, Self> ⓘ
fn into_either_with<F>(self, into_left: F) -> Either<Self, Self> ⓘ
self
into a Left
variant of Either<Self, Self>
if into_left(&self)
returns true
.
Converts self
into a Right
variant of Either<Self, Self>
otherwise. Read more§impl<T> Pipe for Twhere
T: ?Sized,
impl<T> Pipe for Twhere
T: ?Sized,
§fn pipe<R>(self, func: impl FnOnce(Self) -> R) -> Rwhere
Self: Sized,
fn pipe<R>(self, func: impl FnOnce(Self) -> R) -> Rwhere
Self: Sized,
§fn pipe_ref<'a, R>(&'a self, func: impl FnOnce(&'a Self) -> R) -> Rwhere
R: 'a,
fn pipe_ref<'a, R>(&'a self, func: impl FnOnce(&'a Self) -> R) -> Rwhere
R: 'a,
self
and passes that borrow into the pipe function. Read more§fn pipe_ref_mut<'a, R>(&'a mut self, func: impl FnOnce(&'a mut Self) -> R) -> Rwhere
R: 'a,
fn pipe_ref_mut<'a, R>(&'a mut self, func: impl FnOnce(&'a mut Self) -> R) -> Rwhere
R: 'a,
self
and passes that borrow into the pipe function. Read more§fn pipe_borrow<'a, B, R>(&'a self, func: impl FnOnce(&'a B) -> R) -> R
fn pipe_borrow<'a, B, R>(&'a self, func: impl FnOnce(&'a B) -> R) -> R
§fn pipe_borrow_mut<'a, B, R>(
&'a mut self,
func: impl FnOnce(&'a mut B) -> R,
) -> R
fn pipe_borrow_mut<'a, B, R>( &'a mut self, func: impl FnOnce(&'a mut B) -> R, ) -> R
§fn pipe_as_ref<'a, U, R>(&'a self, func: impl FnOnce(&'a U) -> R) -> R
fn pipe_as_ref<'a, U, R>(&'a self, func: impl FnOnce(&'a U) -> R) -> R
self
, then passes self.as_ref()
into the pipe function.§fn pipe_as_mut<'a, U, R>(&'a mut self, func: impl FnOnce(&'a mut U) -> R) -> R
fn pipe_as_mut<'a, U, R>(&'a mut self, func: impl FnOnce(&'a mut U) -> R) -> R
self
, then passes self.as_mut()
into the pipe
function.§fn pipe_deref<'a, T, R>(&'a self, func: impl FnOnce(&'a T) -> R) -> R
fn pipe_deref<'a, T, R>(&'a self, func: impl FnOnce(&'a T) -> R) -> R
self
, then passes self.deref()
into the pipe function.§impl<T> Tap for T
impl<T> Tap for T
§fn tap_borrow<B>(self, func: impl FnOnce(&B)) -> Self
fn tap_borrow<B>(self, func: impl FnOnce(&B)) -> Self
Borrow<B>
of a value. Read more§fn tap_borrow_mut<B>(self, func: impl FnOnce(&mut B)) -> Self
fn tap_borrow_mut<B>(self, func: impl FnOnce(&mut B)) -> Self
BorrowMut<B>
of a value. Read more§fn tap_ref<R>(self, func: impl FnOnce(&R)) -> Self
fn tap_ref<R>(self, func: impl FnOnce(&R)) -> Self
AsRef<R>
view of a value. Read more§fn tap_ref_mut<R>(self, func: impl FnOnce(&mut R)) -> Self
fn tap_ref_mut<R>(self, func: impl FnOnce(&mut R)) -> Self
AsMut<R>
view of a value. Read more§fn tap_deref<T>(self, func: impl FnOnce(&T)) -> Self
fn tap_deref<T>(self, func: impl FnOnce(&T)) -> Self
Deref::Target
of a value. Read more§fn tap_deref_mut<T>(self, func: impl FnOnce(&mut T)) -> Self
fn tap_deref_mut<T>(self, func: impl FnOnce(&mut T)) -> Self
Deref::Target
of a value. Read more§fn tap_dbg(self, func: impl FnOnce(&Self)) -> Self
fn tap_dbg(self, func: impl FnOnce(&Self)) -> Self
.tap()
only in debug builds, and is erased in release builds.§fn tap_mut_dbg(self, func: impl FnOnce(&mut Self)) -> Self
fn tap_mut_dbg(self, func: impl FnOnce(&mut Self)) -> Self
.tap_mut()
only in debug builds, and is erased in release
builds.§fn tap_borrow_dbg<B>(self, func: impl FnOnce(&B)) -> Self
fn tap_borrow_dbg<B>(self, func: impl FnOnce(&B)) -> Self
.tap_borrow()
only in debug builds, and is erased in release
builds.§fn tap_borrow_mut_dbg<B>(self, func: impl FnOnce(&mut B)) -> Self
fn tap_borrow_mut_dbg<B>(self, func: impl FnOnce(&mut B)) -> Self
.tap_borrow_mut()
only in debug builds, and is erased in release
builds.§fn tap_ref_dbg<R>(self, func: impl FnOnce(&R)) -> Self
fn tap_ref_dbg<R>(self, func: impl FnOnce(&R)) -> Self
.tap_ref()
only in debug builds, and is erased in release
builds.§fn tap_ref_mut_dbg<R>(self, func: impl FnOnce(&mut R)) -> Self
fn tap_ref_mut_dbg<R>(self, func: impl FnOnce(&mut R)) -> Self
.tap_ref_mut()
only in debug builds, and is erased in release
builds.§fn tap_deref_dbg<T>(self, func: impl FnOnce(&T)) -> Self
fn tap_deref_dbg<T>(self, func: impl FnOnce(&T)) -> Self
.tap_deref()
only in debug builds, and is erased in release
builds.