mirror of
https://github.com/trussed-dev/usbd-ccid.git
synced 2026-06-20 04:16:20 -07:00
Small CCID improvements
This commit is contained in:
+12
-3
@@ -40,10 +40,13 @@ pub const CLOCK_FREQUENCY_KHZ: [u8; 4] = [0xfc, 0x0d, 0x00, 0x00];
|
||||
// (not relevant, fixed fixed for legacy reasonse
|
||||
// Yubico: 307200 bps, gnuk: 9600
|
||||
// pub const DATA_RATE_BPS: [u8; 4] = [0x00, 0xb0, 0x04, 0x00];
|
||||
// pub const DATA_RATE_BPS: [u8; 4] = [0x80, 0x25, 0x00, 0x00];
|
||||
// ICCD spec: "9600bps, not relevant, fixed for legacy reason"
|
||||
pub const DATA_RATE_BPS: [u8; 4] = [0x80, 0x25, 0x00, 0x00];
|
||||
// 254 (as per ICCD spec)
|
||||
// Yubico: 2038, gnuk: 254
|
||||
// pub const MAX_IFSD: [u8; 4] = [0xf6, 0x07, 0x00, 0x00];
|
||||
// ICCD spec: "For T = 1: 000000FEh"
|
||||
pub const MAX_IFSD: [u8; 4] = [0xfe, 0x00, 0x00, 0x00];
|
||||
|
||||
// "The value shall be between 261 + 10 and 65544 + 10
|
||||
@@ -62,9 +65,11 @@ pub const FUNCTIONAL_INTERFACE_DESCRIPTOR: [u8; 52] = [
|
||||
// bcdCCID rev1.10
|
||||
0x10, 0x01,
|
||||
// bMaxSlotIndex
|
||||
NUM_SLOTS - 1,
|
||||
// NUM_SLOTS - 1,
|
||||
// "An USB-ICC is regarded as a single slot CCID."
|
||||
0x00,
|
||||
// bVoltageSupport (5.0V + 3.0V + 1.8V)
|
||||
0x07,
|
||||
0x01,
|
||||
// dwProtocols: T=1 only (0 = T=0, 3 = T0+T1)
|
||||
0x02, 0x00, 0x00, 0x00,
|
||||
|
||||
@@ -112,7 +117,10 @@ pub const FUNCTIONAL_INTERFACE_DESCRIPTOR: [u8; 52] = [
|
||||
// Auto baud rate change
|
||||
// Auto parameter negotiation made by CCID
|
||||
// Short and extended APDU level exchange
|
||||
0xFE, 0x00, 0x04, 0x00,
|
||||
// 0xFE, 0x00, 0x04, 0x00,
|
||||
// ICCD: lower word (=0840): only requests valid for USB-ICC
|
||||
// upper word: 0000 = char level, 0002 = short APDU, 0004 = short+exteded APDU
|
||||
0x40, 0x08, 0x04, 0x00,
|
||||
|
||||
// dwMaxCCIDMsgLen (3072)
|
||||
// gnuk: 271
|
||||
@@ -128,6 +136,7 @@ pub const FUNCTIONAL_INTERFACE_DESCRIPTOR: [u8; 52] = [
|
||||
// wlcdLayout (none)
|
||||
0x00, 0x00,
|
||||
// bPinSupport
|
||||
// ICCD: "No PIN pad, not relevant, fixed for legacy reasons"
|
||||
PIN_SUPPORT,
|
||||
// bMaxCCIDBusySlots
|
||||
MAX_BUSY_SLOTS,
|
||||
|
||||
@@ -118,6 +118,14 @@ impl<N: ArrayLength<u8>> Der<N> {
|
||||
self.extend_from_slice(value)
|
||||
}
|
||||
|
||||
/// Write an arbitrary tag-length-value with 2-byte tag
|
||||
/// NB: everything in ISO 7816 is big-endian
|
||||
pub fn raw_tlv2(&mut self, tag: u16, value: &[u8]) -> Result {
|
||||
self.extend_from_slice(&tag.to_be_bytes())?;
|
||||
self.write_length_field(value.len())?;
|
||||
self.extend_from_slice(value)
|
||||
}
|
||||
|
||||
///// Write the given input as integer.
|
||||
/////
|
||||
///// Assumes `input` is the big-endian representation of a non-negative `Integer`
|
||||
|
||||
+45
-27
@@ -380,6 +380,24 @@ where
|
||||
let packet = DataBlock::new(
|
||||
self.seq,
|
||||
Chain::BeginsAndEnds,
|
||||
|
||||
// PivApplet just uses:
|
||||
// 3B 80 80 01 01
|
||||
//
|
||||
// 3B 88 80 01 80 57 53 6F 6C 6F 20 42 83
|
||||
// T=0, T=1, card issuer's data "Solo B"
|
||||
// https://smartcard-atr.apdu.fr/parse?ATR=3B+88+80+01+80+57+53+6F+6C+6F+20+42+83
|
||||
//
|
||||
// T=0, T=1, command chaining/extended Lc+Le/no logical channels, card issuer's data "Solo B"
|
||||
// 3B 8C 80 01 80 73 C0 21 C0 56 53 6F 6C 6F 20 42 D4
|
||||
// https://smartcard-atr.apdu.fr/parse?ATR=3B+8C+80+01+80+73+C0+21+C0+56+53+6F+6C+6F+20+42+D4
|
||||
b";\x8c\x80\x01\x80s\xc0!\xc0VSolo B\xd4"
|
||||
//
|
||||
// Not sure if we also need some TA/TB/TC data as in
|
||||
// https://smartcard-atr.apdu.fr/parse?ATR=3B+F8+13+00+00+81+31+FE+15+59+75+62+69+6B+65+79+34+D4
|
||||
// At least TB(1) is deprecated, so it makes no sense
|
||||
// Also, there TD(1) = 0x81 and TD(2) = 0x31 both refer to protocol T=1 which seems wrong
|
||||
|
||||
// don't remember where i got this from
|
||||
// &[0x3b, 0x8c,0x80,0x01],
|
||||
// "corrected"?
|
||||
@@ -400,37 +418,37 @@ where
|
||||
// ],
|
||||
// Yubikey FIDO+CCID
|
||||
// 3b:f8:13:00:00:81:31:fe:15:59:75:62:69:6b:65:79:34:d4
|
||||
&[
|
||||
// TS
|
||||
0x3b,
|
||||
// TO = TA1, TB1, TB2, TB3 follow, 8 historical bytes
|
||||
0xf8,
|
||||
// &[
|
||||
// // TS
|
||||
// 0x3b,
|
||||
// // TO = TA1, TB1, TB2, TB3 follow, 8 historical bytes
|
||||
// 0xf8,
|
||||
|
||||
// TA1 = default clock (5MHz), default clock rate conversion (372)o
|
||||
// But sets Di to 3 instead of default of 1
|
||||
0x13,
|
||||
// TB1 deprecated, should not transmit
|
||||
0x00,
|
||||
// TC1 = "extra guard time", default of 0
|
||||
0x00,
|
||||
// // TA1 = default clock (5MHz), default clock rate conversion (372)o
|
||||
// // But sets Di to 3 instead of default of 1
|
||||
// 0x13,
|
||||
// // TB1 deprecated, should not transmit
|
||||
// 0x00,
|
||||
// // TC1 = "extra guard time", default of 0
|
||||
// 0x00,
|
||||
|
||||
// TD1 = (Y2, T) -> follows D2, T = 1
|
||||
0x81,
|
||||
// TD2 = (Y2, T)
|
||||
0x31,
|
||||
// TA2
|
||||
0xfe,
|
||||
// TB2
|
||||
0x15,
|
||||
// T1 = first historical byte
|
||||
0x59,
|
||||
// // TD1 = (Y2, T) -> follows D2, T = 1
|
||||
// 0x81,
|
||||
// // TD2 = (Y2, T)
|
||||
// 0x31,
|
||||
// // TA2
|
||||
// 0xfe,
|
||||
// // TB2
|
||||
// 0x15,
|
||||
// // T1 = first historical byte
|
||||
// 0x59,
|
||||
|
||||
// "SoloBee"
|
||||
0x53, 0x6F, 0x6C, 0x6F, 0x42, 0x65 ,0x65,
|
||||
// // "SoloBee"
|
||||
// 0x53, 0x6F, 0x6C, 0x6F, 0x42, 0x65 ,0x65,
|
||||
|
||||
// Checksum
|
||||
0x94,
|
||||
],
|
||||
// // Checksum
|
||||
// 0x94,
|
||||
// ],
|
||||
// Yubikey NEO OTP+U2F+CCID
|
||||
// 3b:fc:13:00:00:81:31:fe:15:59:75:62:69:6b:65:79:4e:45:4f:72:33:e1
|
||||
);
|
||||
|
||||
Reference in New Issue
Block a user