Struct yubirs::piv::handle::Handle

source ·
pub struct Handle<T: PcscHal> { /* private fields */ }
Expand description

A Handle representing a connection to an underlying PC/SC device. This struct is parameterized on a PcscHal implementation, so the underlying hardware implementation can be swapped out as long as it is “compatible” with the PC/SC library, in some sense.

Users of this struct must connect before calling most API functions.

Many API functions also require authentication. The authentication secrets can either be passed in, or alternatively will be prompted for on stdin. The following table denotes which functions require which kind of authentication:

FunctionMGM KeyPINPUKNotes
list_readers
connect
disconnect
get_version
get_serial
change_pinX
unblock_pinX
change_pukX
resetPIN + PUK must be blocked.
set_retriesXX
set_management_keyX
set_chuidX
set_cccX
read_object
write_objectX
generateX
import_keyX
attest
read_certificate
encrypt
decryptX

Implementations§

source§

impl<T: PcscHal> Handle<T>

source

pub fn new() -> Result<Self>

source

pub fn new_with_hal(hal: T) -> Self

source

pub fn get_hal(&self) -> &T

source

pub fn get_hal_mut(&mut self) -> &mut T

source

pub fn list_readers(&self) -> Result<Vec<String>>

This function returns the list of valid reader strings which can be passed to State::new.

source

pub fn connect(&mut self, reader: Option<&str>) -> Result<()>

Connect to the PC/SC reader which matches the given reader string (or DEFAULT_READER, if one was not provided). The first reader which includes the given string as a substring will be used.

source

pub fn disconnect(&mut self)

Disconnect from the currently connected PC/SC reader. This is only necessary if you want to re-use this State to interact with a different reader.

source

pub fn get_version(&self) -> Result<Version>

This function returns the version number the connected reader reports. Note that connect() must be called before this function, or an error will be returned.

source

pub fn get_serial(&self) -> Result<Serial>

This function returns the serial number of the connected reader. This is a number which uniquely identifes this device from others of the same model. Note that connect() must be called before this function, or an error will be returned.

source

pub fn change_pin( &mut self, old_pin: Option<&str>, new_pin: Option<&str> ) -> Result<()>

This function allows the user to change the Yubikey’s PIN, given that the user knows the existing PIN. The old and new PINs can be provided as function arguments. If they are not provided, this function will prompt for them on stdin.

When prompting for a PIN, this function will automatically retry if PIN verification fails, until there are no more available retries. At that point, the PIN can be unblocked using the PUK.

source

pub fn unblock_pin( &mut self, puk: Option<&str>, new_pin: Option<&str> ) -> Result<()>

This function allows the user to reset the Yubikey’s PIN using the PUK, after the user has exhausted their allotted tries to enter the PIN correctly. The PUK and new PIN can be provided as function arguments. If they are not provided, this function will prompt for them on stdin.

When prompting for a PUK, this function will automatically retry if PUK verification fails, until there are no more available retries. At that point, the Yubiey can be reset to factory defaults using the reset function.

source

pub fn change_puk( &mut self, old_puk: Option<&str>, new_puk: Option<&str> ) -> Result<()>

This function allows the user to change the Yubikey’s PUK, given that the user knows the existing PUK. The old and new PUKs can be provided as function arguments. If they are not provided, this function will prompt for them on stdin.

When prompting for a PUK, this function will automatically retry if PUK verification fails, until there are no more available retries. At that point, the PIN and PUK can both be unblocked using the reset function.

source

pub fn reset(&mut self) -> Result<()>

This function resets the PIN, PUK, and management key to their factory default values, as well as delete any stored certificates and keys. The default values for the PIN and PUK are 123456 and 12345678, respectively.

Note that this function will return an error unless the tries to verify the PIN and PUK have both been fully exhausted (e.g., the Yubikey is now unusable). Otherwise, the change_pin, unblock_pin, and change_puk functions should be used instead of this function.

source

pub fn force_reset(&mut self) -> Result<()>

This function is similar to reset, except it first ensures that all of the PIN and PUK retries have been exhausted first (by intentionally exhausting them with known-bad values).

source

pub fn set_retries( &mut self, mgm_key: Option<&str>, pin: Option<&str>, pin_retries: u8, puk_retries: u8 ) -> Result<()>

This function sets the number of retries available for PIN or PUK verification. This also resets the PIN and PUK back to their factory default values, 123456 and 12345678, respectively.

Note that this function is slightly strange compared to the rest of the API, in that both the management key and the current PIN are required.

source

pub fn set_management_key( &mut self, old_mgm_key: Option<&str>, new_mgm_key: Option<&str>, touch: bool ) -> Result<()>

This function changes the management key stored on the device. This is the key used to authenticate() for administrative / management access.

source

pub fn set_chuid(&mut self, mgm_key: Option<&str>) -> Result<()>

This function writes a new, randomly-generated Card Holder Unique Identifier (CHUID) to the device. Some systems (Windows) require a CHUID to be present before they will recognize the Yubikey. This data object is not present on Yubikeys by default (from the factory).

Also note that, according to the Yubikey docs, the card contents are aggressively cached on Windows. In order to invalidate the cached data, e.g. after changing stored certificates, the CHUID must also be changed.

source

pub fn set_ccc(&mut self, mgm_key: Option<&str>) -> Result<()>

This function writes a new, randomly-generated Card Capability Container (CCC) to the device. Some systems (MacOS) require a CCC to be present before they will recognize the Yubikey. This data object is not present on Yubikeys by default (from the factory).

source

pub fn read_object(&self, id: Object) -> Result<Vec<u8>>

Read a data object from the Yubikey, returning the byte contents.

source

pub fn write_object( &mut self, mgm_key: Option<&str>, id: Object, buffer: Vec<u8> ) -> Result<()>

Write a data object to the Yubikey. This function takes ownership of the data, because upstream’s API requires a mutable data buffer.

source

pub fn generate( &mut self, mgm_key: Option<&str>, slot: Key, algorithm: Algorithm, pin_policy: PinPolicy, touch_policy: TouchPolicy ) -> Result<PublicKey>

Generate a new private / public key pair, using the underlying hardware’s generation capability. Store the private key in the given key slot, and return the public key. The specified PIN and touch policies will be enforced whenever this key is used in the future.

source

pub fn import_key<P: AsRef<Path>>( &mut self, mgm_key: Option<&str>, input: P, slot: Key, encrypted: bool, passphrase: Option<&str>, pin_policy: PinPolicy, touch_policy: TouchPolicy ) -> Result<PublicKey>

Import an RSA or EC private key into the given key slot. The provided input key must be a PEM-encoded private key file. The caller must indicate if the private key is encrypted or not. If the key is encrypted, and no passphrase is provided, one will be prompted for. The specified PIN and touch policies will be enforced whenever this key is used in the future.

source

pub fn attest(&self, slot: Key) -> Result<PublicKeyCertificate>

Attest returns an X.509 certificate signed with the private key in the given slot if and only if the private key was generated on the device rather than imported. Note that this feature is only supported by some newer hardware devices. For details, see: https://developers.yubico.com/yubico-piv-tool/Attestation.html

source

pub fn read_certificate(&self, slot: Key) -> Result<PublicKeyCertificate>

source

pub fn encrypt( &self, public_key: &PublicKey, plaintext: &[u8] ) -> Result<(Algorithm, Vec<u8>)>

Encrypts the given data with the given public key. It is assumed that the matching private key is stored on the device, in which case the returned encrypted data can later be deciphered using the hardware device.

Note that the given input key must be an RSA key in PEM format.

Refer to piv::pkey::PublicKey::encrypt for more details.

source

pub fn decrypt( &mut self, pin: Option<&str>, ciphertext: &[u8], slot: Key, algorithm: Algorithm ) -> Result<Vec<u8>>

Decrypts the given ciphertext with the private key in the given key slot. The specified key must be an RSA key, and the cipertext must have been encrypted with padding as per the encrypt function.

Trait Implementations§

source§

impl<T: PcscHal> Drop for Handle<T>

source§

fn drop(&mut self)

Executes the destructor for this type. Read more

Auto Trait Implementations§

§

impl<T> RefUnwindSafe for Handle<T>
where T: RefUnwindSafe,

§

impl<T> Send for Handle<T>
where T: Send,

§

impl<T> Sync for Handle<T>
where T: Sync,

§

impl<T> Unpin for Handle<T>
where T: Unpin,

§

impl<T> UnwindSafe for Handle<T>
where T: UnwindSafe,

Blanket Implementations§

source§

impl<T> Any for T
where T: 'static + ?Sized,

source§

fn type_id(&self) -> TypeId

Gets the TypeId of self. Read more
source§

impl<T> Borrow<T> for T
where T: ?Sized,

source§

fn borrow(&self) -> &T

Immutably borrows from an owned value. Read more
source§

impl<T> BorrowMut<T> for T
where T: ?Sized,

source§

fn borrow_mut(&mut self) -> &mut T

Mutably borrows from an owned value. Read more
source§

impl<T> From<T> for T

source§

fn from(t: T) -> T

Returns the argument unchanged.

§

impl<T> Instrument for T

§

fn instrument(self, span: Span) -> Instrumented<Self>

Instruments this type with the provided [Span], returning an Instrumented wrapper. Read more
§

fn in_current_span(self) -> Instrumented<Self>

Instruments this type with the current Span, returning an Instrumented wrapper. Read more
source§

impl<T, U> Into<U> for T
where U: From<T>,

source§

fn into(self) -> U

Calls U::from(self).

That is, this conversion is whatever the implementation of From<T> for U chooses to do.

source§

impl<T, U> TryFrom<U> for T
where U: Into<T>,

§

type Error = Infallible

The type returned in the event of a conversion error.
source§

fn try_from(value: U) -> Result<T, <T as TryFrom<U>>::Error>

Performs the conversion.
source§

impl<T, U> TryInto<U> for T
where U: TryFrom<T>,

§

type Error = <U as TryFrom<T>>::Error

The type returned in the event of a conversion error.
source§

fn try_into(self) -> Result<U, <U as TryFrom<T>>::Error>

Performs the conversion.
§

impl<V, T> VZip<V> for T
where V: MultiLane<T>,

§

fn vzip(self) -> V

§

impl<T> WithSubscriber for T

§

fn with_subscriber<S>(self, subscriber: S) -> WithDispatch<Self>
where S: Into<Dispatch>,

Attaches the provided Subscriber to this type, returning a [WithDispatch] wrapper. Read more
§

fn with_current_subscriber(self) -> WithDispatch<Self>

Attaches the current default Subscriber to this type, returning a [WithDispatch] wrapper. Read more