consts: Whittle down to the essentials

This factors the junk drawer of constants into the relevant files.

There are still a few "global" ones left but they can be addressed in a
followup commit.
This commit is contained in:
Tony Arcieri
2019-12-08 08:39:21 -08:00
parent 4dfac56753
commit 104020d518
12 changed files with 102 additions and 111 deletions
+6 -1
View File
@@ -55,6 +55,11 @@ const OID_EC_PUBLIC_KEY: &str = "1.2.840.10045.2.1";
const OID_NIST_P256: &str = "1.2.840.10045.3.1.7"; const OID_NIST_P256: &str = "1.2.840.10045.3.1.7";
const OID_NIST_P384: &str = "1.3.132.0.34"; const OID_NIST_P384: &str = "1.3.132.0.34";
#[allow(dead_code)]
const CERTINFO_UNCOMPRESSED: u8 = 0;
#[cfg(feature = "untested")]
const CERTINFO_GZIP: u8 = 1;
/// Information about a public key within a [`Certificate`]. /// Information about a public key within a [`Certificate`].
#[derive(Clone, Eq, PartialEq)] #[derive(Clone, Eq, PartialEq)]
pub enum PublicKeyInfo { pub enum PublicKeyInfo {
@@ -273,7 +278,7 @@ pub(crate) fn write_certificate(
// write compression info and LRC trailer // write compression info and LRC trailer
buf[offset] = TAG_CERT_COMPRESS; buf[offset] = TAG_CERT_COMPRESS;
buf[offset + 1] = 0x01; buf[offset + 1] = 0x01;
buf[offset + 2] = if certinfo == YKPIV_CERTINFO_GZIP { buf[offset + 2] = if certinfo == CERTINFO_GZIP {
0x01 0x01
} else { } else {
0x00 0x00
+3
View File
@@ -37,6 +37,9 @@ use std::{
time::{Duration, SystemTime, UNIX_EPOCH}, time::{Duration, SystemTime, UNIX_EPOCH},
}; };
const CB_ADMIN_TIMESTAMP: usize = 0x04;
const PROTECTED_FLAGS_1_PUK_NOBLOCK: u8 = 0x01;
/// Config /// Config
#[derive(Copy, Clone, Debug)] #[derive(Copy, Clone, Debug)]
pub struct Config { pub struct Config {
+1 -84
View File
@@ -33,75 +33,17 @@
// TODO(tarcieri): document these! // TODO(tarcieri): document these!
#![allow(missing_docs, non_upper_case_globals)] #![allow(missing_docs, non_upper_case_globals)]
#![cfg_attr(not(feature = "untested"), allow(dead_code))]
pub const szLOG_SOURCE: &str = "yubikey-piv.rs";
pub const ADMIN_FLAGS_1_PUK_BLOCKED: u8 = 0x01; pub const ADMIN_FLAGS_1_PUK_BLOCKED: u8 = 0x01;
pub const ADMIN_FLAGS_1_PROTECTED_MGM: u8 = 0x02; pub const ADMIN_FLAGS_1_PROTECTED_MGM: u8 = 0x02;
/// PIV Applet ID
pub const PIV_AID: [u8; 5] = [0xa0, 0x00, 0x00, 0x03, 0x08];
/// MGMT Applet ID.
/// <https://developers.yubico.com/PIV/Introduction/Admin_access.html>
pub const MGMT_AID: [u8; 8] = [0xa0, 0x00, 0x00, 0x05, 0x27, 0x47, 0x11, 0x17];
/// YubiKey OTP Applet ID. Needed to query serial on YK4.
pub const YK_AID: [u8; 8] = [0xa0, 0x00, 0x00, 0x05, 0x27, 0x20, 0x01, 0x01];
pub const CB_ADMIN_TIMESTAMP: usize = 0x04;
pub const CB_ADMIN_SALT: usize = 16;
pub const CB_ATR_MAX: usize = 33;
pub const CB_BUF_MAX: usize = 3072; pub const CB_BUF_MAX: usize = 3072;
pub const CB_ECC_POINTP256: usize = 65;
pub const CB_ECC_POINTP384: usize = 97;
pub const CB_OBJ_MAX: usize = CB_BUF_MAX - 9; pub const CB_OBJ_MAX: usize = CB_BUF_MAX - 9;
pub const CB_OBJ_TAG_MIN: usize = 2; // 1 byte tag + 1 byte len pub const CB_OBJ_TAG_MIN: usize = 2; // 1 byte tag + 1 byte len
pub const CB_OBJ_TAG_MAX: usize = (CB_OBJ_TAG_MIN + 2); // 1 byte tag + 3 bytes len pub const CB_OBJ_TAG_MAX: usize = (CB_OBJ_TAG_MIN + 2); // 1 byte tag + 3 bytes len
pub const CB_PAGE: usize = 4096;
pub const CB_PIN_MAX: usize = 8;
pub const CHREF_ACT_CHANGE_PIN: i32 = 0;
pub const CHREF_ACT_UNBLOCK_PIN: i32 = 1;
pub const CHREF_ACT_CHANGE_PUK: i32 = 2;
pub const CONTAINER_NAME_LEN: usize = 40;
pub const CONTAINER_REC_LEN: usize = (2 * CONTAINER_NAME_LEN) + 27; // 80 + 1 + 1 + 2 + 1 + 1 + 1 + 20
pub const DES_TYPE_3DES: u8 = 1;
pub const DES_LEN_DES: usize = 8;
pub const DES_LEN_3DES: usize = DES_LEN_DES * 3;
// device types
pub const DEVTYPE_UNKNOWN: u32 = 0x0000_0000;
pub const DEVTYPE_YK: u32 = 0x594B_0000; //"YK"
pub const DEVTYPE_YK4: u32 = (DEVTYPE_YK | 0x0000_0034); // "4"
pub const DEVYTPE_YK5: u32 = (DEVTYPE_YK | 0x0000_0035); // "5"
pub const ITER_MGM_PBKDF2: usize = 10000;
pub const PROTECTED_FLAGS_1_PUK_NOBLOCK: u8 = 0x01;
// sw is status words, see NIST special publication 800-73-4, section 5.6
pub const SW_SUCCESS: i32 = 0x9000;
pub const SW_ERR_SECURITY_STATUS: i32 = 0x6982;
pub const SW_ERR_AUTH_BLOCKED: i32 = 0x6983;
pub const SW_ERR_INCORRECT_PARAM: i32 = 0x6a80;
// this is a custom sw for yubikey
pub const SW_ERR_INCORRECT_SLOT: i32 = 0x6b00;
pub const SW_ERR_NOT_SUPPORTED: i32 = 0x6d00;
pub const TAG_CERT: u8 = 0x70; pub const TAG_CERT: u8 = 0x70;
pub const TAG_CERT_COMPRESS: u8 = 0x71; pub const TAG_CERT_COMPRESS: u8 = 0x71;
pub const TAG_CERT_LRC: u8 = 0xFE; pub const TAG_CERT_LRC: u8 = 0xFE;
@@ -119,28 +61,3 @@ pub const TAG_MSROOTS_MID: u8 = 0x83;
pub const TAG_RSA_MODULUS: u8 = 0x81; pub const TAG_RSA_MODULUS: u8 = 0x81;
pub const TAG_RSA_EXP: u8 = 0x82; pub const TAG_RSA_EXP: u8 = 0x82;
pub const TAG_ECC_POINT: u8 = 0x86; pub const TAG_ECC_POINT: u8 = 0x86;
pub const YKPIV_ALGO_3DES: u8 = 0x03;
pub const YKPIV_CERTINFO_UNCOMPRESSED: u8 = 0;
pub const YKPIV_CERTINFO_GZIP: u8 = 1;
pub const YKPIV_KEY_CARDMGM: u8 = 0x9b;
pub const YKPIV_OBJ_FINGERPRINTS: u32 = 0x005f_c103;
pub const YKPIV_OBJ_SECURITY: u32 = 0x005f_c106;
pub const YKPIV_OBJ_FACIAL: u32 = 0x005f_c108;
pub const YKPIV_OBJ_PRINTED: u32 = 0x005f_c109;
pub const YKPIV_OBJ_DISCOVERY: u32 = 0x7e;
pub const YKPIV_OBJ_KEY_HISTORY: u32 = 0x005f_c10c;
pub const YKPIV_OBJ_IRIS: u32 = 0x005f_c121;
// Internal object IDs
pub const YKPIV_OBJ_ADMIN_DATA: u32 = 0x005f_ff00;
pub const YKPIV_OBJ_MSCMAP: u32 = 0x005f_ff10;
pub const YKPIV_OBJ_MSROOTS1: u32 = 0x005f_ff11;
pub const YKPIV_OBJ_MSROOTS2: u32 = 0x005f_ff12;
pub const YKPIV_OBJ_MSROOTS3: u32 = 0x005f_ff13;
pub const YKPIV_OBJ_MSROOTS4: u32 = 0x005f_ff14;
pub const YKPIV_OBJ_MSROOTS5: u32 = 0x005f_ff15;
+11 -3
View File
@@ -40,6 +40,14 @@ use std::{
fmt::{self, Debug}, fmt::{self, Debug},
}; };
/// Container name length
const CONTAINER_NAME_LEN: usize = 40;
/// Container record length: 27 = 80 + 1 + 1 + 2 + 1 + 1 + 1 + 20
const CONTAINER_REC_LEN: usize = (2 * CONTAINER_NAME_LEN) + 27;
const OBJ_MSCMAP: u32 = 0x005f_ff10;
/// MS Container Map(?) Records /// MS Container Map(?) Records
#[derive(Copy, Clone)] #[derive(Copy, Clone)]
pub struct Container { pub struct Container {
@@ -72,7 +80,7 @@ impl Container {
/// Read MS Container Map records /// Read MS Container Map records
pub fn read_mscmap(yubikey: &mut YubiKey) -> Result<Vec<Self>, Error> { pub fn read_mscmap(yubikey: &mut YubiKey) -> Result<Vec<Self>, Error> {
let txn = yubikey.begin_transaction()?; let txn = yubikey.begin_transaction()?;
let response = txn.fetch_object(YKPIV_OBJ_MSCMAP)?; let response = txn.fetch_object(OBJ_MSCMAP)?;
let mut containers = vec![]; let mut containers = vec![];
if response.len() < CB_OBJ_TAG_MIN { if response.len() < CB_OBJ_TAG_MIN {
@@ -110,7 +118,7 @@ impl Container {
let txn = yubikey.begin_transaction()?; let txn = yubikey.begin_transaction()?;
if n_containers == 0 { if n_containers == 0 {
return txn.save_object(YKPIV_OBJ_MSCMAP, &[]); return txn.save_object(OBJ_MSCMAP, &[]);
} }
let req_len = 1 + set_length(&mut buf, data_len) + data_len; let req_len = 1 + set_length(&mut buf, data_len) + data_len;
@@ -131,7 +139,7 @@ impl Container {
} }
offset += data_len; offset += data_len;
txn.save_object(YKPIV_OBJ_MSCMAP, &buf[..offset]) txn.save_object(OBJ_MSCMAP, &buf[..offset])
} }
/// Parse a container record from a byte slice /// Parse a container record from a byte slice
+5
View File
@@ -59,6 +59,11 @@ use log::{error, warn};
#[cfg(feature = "untested")] #[cfg(feature = "untested")]
use zeroize::Zeroizing; use zeroize::Zeroizing;
#[cfg(feature = "untested")]
const CB_ECC_POINTP256: usize = 65;
#[cfg(feature = "untested")]
const CB_ECC_POINTP384: usize = 97;
/// Slot identifiers. /// Slot identifiers.
/// <https://developers.yubico.com/PIV/Introduction/Certificate_slots.html> /// <https://developers.yubico.com/PIV/Introduction/Certificate_slots.html>
#[derive(Clone, Copy, Debug, PartialEq)] #[derive(Clone, Copy, Debug, PartialEq)]
+1 -1
View File
@@ -140,7 +140,7 @@ pub mod cccid;
pub mod certificate; pub mod certificate;
pub mod chuid; pub mod chuid;
pub mod config; pub mod config;
pub mod consts; mod consts;
#[cfg(feature = "untested")] #[cfg(feature = "untested")]
pub mod container; pub mod container;
pub mod error; pub mod error;
+7 -4
View File
@@ -35,6 +35,9 @@ use crate::{consts::*, error::Error, serialization::*, transaction::Transaction,
#[cfg(feature = "untested")] #[cfg(feature = "untested")]
use zeroize::Zeroizing; use zeroize::Zeroizing;
pub const OBJ_ADMIN_DATA: u32 = 0x005f_ff00;
pub const OBJ_PRINTED: u32 = 0x005f_c109;
/// Get metadata item /// Get metadata item
pub(crate) fn get_item(data: &[u8], tag: u8) -> Result<&[u8], Error> { pub(crate) fn get_item(data: &[u8], tag: u8) -> Result<&[u8], Error> {
let mut cb_temp: usize = 0; let mut cb_temp: usize = 0;
@@ -166,8 +169,8 @@ pub(crate) fn set_item(
/// Read metadata /// Read metadata
pub(crate) fn read(txn: &Transaction<'_>, tag: u8) -> Result<Buffer, Error> { pub(crate) fn read(txn: &Transaction<'_>, tag: u8) -> Result<Buffer, Error> {
let obj_id = match tag { let obj_id = match tag {
TAG_ADMIN => YKPIV_OBJ_ADMIN_DATA, TAG_ADMIN => OBJ_ADMIN_DATA,
TAG_PROTECTED => YKPIV_OBJ_PRINTED, TAG_PROTECTED => OBJ_PRINTED,
_ => return Err(Error::InvalidObject), _ => return Err(Error::InvalidObject),
}; };
@@ -203,8 +206,8 @@ pub(crate) fn write(txn: &Transaction<'_>, tag: u8, data: &[u8]) -> Result<(), E
} }
let obj_id = match tag { let obj_id = match tag {
TAG_ADMIN => YKPIV_OBJ_ADMIN_DATA, TAG_ADMIN => OBJ_ADMIN_DATA,
TAG_PROTECTED => YKPIV_OBJ_PRINTED, TAG_PROTECTED => OBJ_PRINTED,
_ => return Err(Error::InvalidObject), _ => return Err(Error::InvalidObject),
}; };
+15 -2
View File
@@ -30,14 +30,14 @@
// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE // (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. // OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
use crate::{consts::*, error::Error}; use crate::error::Error;
use getrandom::getrandom; use getrandom::getrandom;
use log::error; use log::error;
use std::convert::{TryFrom, TryInto}; use std::convert::{TryFrom, TryInto};
use zeroize::{Zeroize, Zeroizing}; use zeroize::{Zeroize, Zeroizing};
#[cfg(feature = "untested")] #[cfg(feature = "untested")]
use crate::{metadata, yubikey::YubiKey}; use crate::{consts::*, metadata, yubikey::YubiKey};
#[cfg(feature = "untested")] #[cfg(feature = "untested")]
use des::{ use des::{
block_cipher_trait::{generic_array::GenericArray, BlockCipher}, block_cipher_trait::{generic_array::GenericArray, BlockCipher},
@@ -50,11 +50,24 @@ use pbkdf2::pbkdf2;
#[cfg(feature = "untested")] #[cfg(feature = "untested")]
use sha1::Sha1; use sha1::Sha1;
#[cfg(feature = "untested")]
const CB_ADMIN_SALT: usize = 16;
/// Default MGM key configured on all YubiKeys /// Default MGM key configured on all YubiKeys
const DEFAULT_MGM_KEY: [u8; DES_LEN_3DES] = [ const DEFAULT_MGM_KEY: [u8; DES_LEN_3DES] = [
1, 2, 3, 4, 5, 6, 7, 8, 1, 2, 3, 4, 5, 6, 7, 8, 1, 2, 3, 4, 5, 6, 7, 8, 1, 2, 3, 4, 5, 6, 7, 8, 1, 2, 3, 4, 5, 6, 7, 8, 1, 2, 3, 4, 5, 6, 7, 8,
]; ];
/// Size of a DES key
const DES_LEN_DES: usize = 8;
/// Size of a 3DES key
pub(crate) const DES_LEN_3DES: usize = DES_LEN_DES * 3;
/// Number of PBKDF2 iterations to use when deriving from a password
#[cfg(feature = "untested")]
const ITER_MGM_PBKDF2: usize = 10000;
/// Management Key (MGM) key types (manual/derived/protected) /// Management Key (MGM) key types (manual/derived/protected)
#[derive(Copy, Clone, Debug, Eq, PartialEq)] #[derive(Copy, Clone, Debug, Eq, PartialEq)]
pub enum MgmType { pub enum MgmType {
+13 -6
View File
@@ -40,6 +40,15 @@
use crate::{consts::*, error::Error, serialization::*, yubikey::YubiKey}; use crate::{consts::*, error::Error, serialization::*, yubikey::YubiKey};
use log::error; use log::error;
const OBJ_MSROOTS1: u32 = 0x005f_ff11;
#[allow(dead_code)]
const OBJ_MSROOTS2: u32 = 0x005f_ff12;
#[allow(dead_code)]
const OBJ_MSROOTS3: u32 = 0x005f_ff13;
#[allow(dead_code)]
const OBJ_MSROOTS4: u32 = 0x005f_ff14;
const OBJ_MSROOTS5: u32 = 0x005f_ff15;
/// `msroots` file: PKCS#7-formatted certificate store for enterprise trust roots /// `msroots` file: PKCS#7-formatted certificate store for enterprise trust roots
pub struct MsRoots(Vec<u8>); pub struct MsRoots(Vec<u8>);
@@ -56,7 +65,7 @@ impl MsRoots {
// allocate first page // allocate first page
let mut data = Vec::with_capacity(CB_OBJ_MAX); let mut data = Vec::with_capacity(CB_OBJ_MAX);
for object_id in YKPIV_OBJ_MSROOTS1..YKPIV_OBJ_MSROOTS5 { for object_id in OBJ_MSROOTS1..OBJ_MSROOTS5 {
let buf = txn.fetch_object(object_id)?; let buf = txn.fetch_object(object_id)?;
let cb_buf = buf.len(); let cb_buf = buf.len();
@@ -66,9 +75,7 @@ impl MsRoots {
let tag = buf[0]; let tag = buf[0];
if (TAG_MSROOTS_MID != tag || YKPIV_OBJ_MSROOTS5 == object_id) if (TAG_MSROOTS_MID != tag || OBJ_MSROOTS5 == object_id) && (TAG_MSROOTS_END != tag) {
&& (TAG_MSROOTS_END != tag)
{
// the current object doesn't contain a valid part of a msroots file // the current object doesn't contain a valid part of a msroots file
// treat condition as object isn't found // treat condition as object isn't found
@@ -108,7 +115,7 @@ impl MsRoots {
let txn = yubikey.begin_transaction()?; let txn = yubikey.begin_transaction()?;
if data_len == 0 { if data_len == 0 {
return txn.save_object(YKPIV_OBJ_MSROOTS1, &[]); return txn.save_object(OBJ_MSROOTS1, &[]);
} }
// Calculate number of objects required to store blob // Calculate number of objects required to store blob
@@ -138,7 +145,7 @@ impl MsRoots {
buf[offset..].copy_from_slice(&data[data_offset..(data_offset + data_chunk)]); buf[offset..].copy_from_slice(&data[data_offset..(data_offset + data_chunk)]);
offset += data_chunk; offset += data_chunk;
txn.save_object(YKPIV_OBJ_MSROOTS1 + i as u32, &buf[..offset])?; txn.save_object(OBJ_MSROOTS1 + i as u32, &buf[..offset])?;
data_offset += data_chunk; data_offset += data_chunk;
} }
+5 -3
View File
@@ -30,7 +30,9 @@
// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE // (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. // OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
use crate::{consts::*, ObjectId}; use crate::ObjectId;
pub const OBJ_DISCOVERY: u32 = 0x7e;
// TODO(tarcieri): refactor these into better serializers/message builders // TODO(tarcieri): refactor these into better serializers/message builders
@@ -84,9 +86,9 @@ pub(crate) fn has_valid_length(buffer: &[u8], len: usize) -> bool {
pub(crate) fn set_object(object_id: ObjectId, mut buffer: &mut [u8]) -> &mut [u8] { pub(crate) fn set_object(object_id: ObjectId, mut buffer: &mut [u8]) -> &mut [u8] {
buffer[0] = 0x5c; buffer[0] = 0x5c;
if object_id == YKPIV_OBJ_DISCOVERY { if object_id == OBJ_DISCOVERY {
buffer[1] = 1; buffer[1] = 1;
buffer[2] = YKPIV_OBJ_DISCOVERY as u8; buffer[2] = OBJ_DISCOVERY as u8;
buffer = &mut buffer[3..]; buffer = &mut buffer[3..];
} else if object_id > 0xffff && object_id <= 0x00ff_ffff { } else if object_id > 0xffff && object_id <= 0x00ff_ffff {
buffer[1] = 3; buffer[1] = 3;
+5 -3
View File
@@ -16,9 +16,11 @@ use zeroize::Zeroizing;
#[cfg(feature = "untested")] #[cfg(feature = "untested")]
use crate::{ use crate::{
key::{AlgorithmId, SlotId}, key::{AlgorithmId, SlotId},
mgm::MgmKey, mgm::{MgmKey, DES_LEN_3DES},
}; };
const CB_PIN_MAX: usize = 8;
/// Exclusive transaction with the YubiKey's PC/SC card. /// Exclusive transaction with the YubiKey's PC/SC card.
pub(crate) struct Transaction<'tx> { pub(crate) struct Transaction<'tx> {
inner: pcsc::Transaction<'tx>, inner: pcsc::Transaction<'tx>,
@@ -227,8 +229,8 @@ impl<'tx> Transaction<'tx> {
}; };
let mut data = [0u8; DES_LEN_3DES + 3]; let mut data = [0u8; DES_LEN_3DES + 3];
data[0] = YKPIV_ALGO_3DES; data[0] = ALGO_3DES;
data[1] = YKPIV_KEY_CARDMGM; data[1] = KEY_CARDMGM;
data[2] = DES_LEN_3DES as u8; data[2] = DES_LEN_3DES as u8;
data[3..3 + DES_LEN_3DES].copy_from_slice(new_key.as_ref()); data[3..3 + DES_LEN_3DES].copy_from_slice(new_key.as_ref());
+30 -4
View File
@@ -63,6 +63,32 @@ use std::{
time::{SystemTime, UNIX_EPOCH}, time::{SystemTime, UNIX_EPOCH},
}; };
/// 3DES authentication
#[cfg(feature = "untested")]
pub(crate) const ALGO_3DES: u8 = 0x03;
/// Card management key
#[cfg(feature = "untested")]
pub(crate) const KEY_CARDMGM: u8 = 0x9b;
#[cfg(feature = "untested")]
pub(crate) const CHREF_ACT_CHANGE_PIN: i32 = 0;
#[cfg(feature = "untested")]
pub(crate) const CHREF_ACT_UNBLOCK_PIN: i32 = 1;
#[cfg(feature = "untested")]
pub(crate) const CHREF_ACT_CHANGE_PUK: i32 = 2;
/// PIV Applet ID
pub(crate) const PIV_AID: [u8; 5] = [0xa0, 0x00, 0x00, 0x03, 0x08];
/// MGMT Applet ID.
/// <https://developers.yubico.com/PIV/Introduction/Admin_access.html>
#[cfg(feature = "untested")]
pub(crate) const MGMT_AID: [u8; 8] = [0xa0, 0x00, 0x00, 0x05, 0x27, 0x47, 0x11, 0x17];
/// YubiKey OTP Applet ID. Needed to query serial on YK4.
pub(crate) const YK_AID: [u8; 8] = [0xa0, 0x00, 0x00, 0x05, 0x27, 0x20, 0x01, 0x01];
/// Cached YubiKey PIN /// Cached YubiKey PIN
pub type CachedPin = secrecy::SecretVec<u8>; pub type CachedPin = secrecy::SecretVec<u8>;
@@ -227,7 +253,7 @@ impl YubiKey {
// get a challenge from the card // get a challenge from the card
let challenge = APDU::new(Ins::Authenticate) let challenge = APDU::new(Ins::Authenticate)
.params(YKPIV_ALGO_3DES, YKPIV_KEY_CARDMGM) .params(ALGO_3DES, KEY_CARDMGM)
.data(&[TAG_DYN_AUTH, 0x02, 0x80, 0x00]) .data(&[TAG_DYN_AUTH, 0x02, 0x80, 0x00])
.transmit(&txn, 261)?; .transmit(&txn, 261)?;
@@ -256,7 +282,7 @@ impl YubiKey {
challenge.copy_from_slice(&data[14..22]); challenge.copy_from_slice(&data[14..22]);
let authentication = APDU::new(Ins::Authenticate) let authentication = APDU::new(Ins::Authenticate)
.params(YKPIV_ALGO_3DES, YKPIV_KEY_CARDMGM) .params(ALGO_3DES, KEY_CARDMGM)
.data(&data) .data(&data)
.transmit(&txn, 261)?; .transmit(&txn, 261)?;
@@ -513,7 +539,7 @@ impl YubiKey {
let txn = self.begin_transaction()?; let txn = self.begin_transaction()?;
let response = APDU::new(Ins::Authenticate) let response = APDU::new(Ins::Authenticate)
.params(YKPIV_ALGO_3DES, YKPIV_KEY_CARDMGM) .params(ALGO_3DES, KEY_CARDMGM)
.data(&[0x7c, 0x02, 0x81, 0x00]) .data(&[0x7c, 0x02, 0x81, 0x00])
.transmit(&txn, 261)?; .transmit(&txn, 261)?;
@@ -538,7 +564,7 @@ impl YubiKey {
// send the response to the card and a challenge of our own. // send the response to the card and a challenge of our own.
let status_words = APDU::new(Ins::Authenticate) let status_words = APDU::new(Ins::Authenticate)
.params(YKPIV_ALGO_3DES, YKPIV_KEY_CARDMGM) .params(ALGO_3DES, KEY_CARDMGM)
.data(&data) .data(&data)
.transmit(&txn, 261)? .transmit(&txn, 261)?
.status_words(); .status_words();