1use crate::native::types::{
2 DeviceInfo, ECCCipherBlob, ECCPrivateKeyBlob, ECCPublicKeyBlob, ECCSignatureBlob, Version, BYTE,
3};
4
5impl Default for DeviceInfo {
6 fn default() -> Self {
7 Self {
8 version: Version::default(),
9 manufacturer: [0; 64],
10 issuer: [0; 64],
11 label: [0; 32],
12 serial_number: [0; 32],
13 hw_version: Version::default(),
14 firmware_version: Version::default(),
15 alg_sym_cap: 0,
16 alg_asym_cap: 0,
17 alg_hash_cap: 0,
18 dev_auth_alg_id: 0,
19 total_space: 0,
20 free_space: 0,
21 max_ecc_buffer_size: 0,
22 max_buffer_size: 0,
23 reserved: [0; 64],
24 }
25 }
26}
27
28impl ECCPublicKeyBlob {
29 pub fn new_256(x: &[u8], y: &[u8]) -> Self {
33 if x.len() != 32 || y.len() != 32 {
34 panic!("x.len() != 32 || y.len() != 32");
35 }
36 let mut xc = vec![0u8 as BYTE; 32];
37 xc.extend(x);
38 let mut yc = vec![0u8 as BYTE; 32];
39 yc.extend(y);
40 Self {
41 bit_len: 256,
42 x_coordinate: xc.try_into().unwrap(),
43 y_coordinate: yc.try_into().unwrap(),
44 }
45 }
46 pub fn x_value(&self) -> &[u8] {
47 &self.x_coordinate[self.bit_len as usize / 8..]
48 }
49 pub fn y_value(&self) -> &[u8] {
50 &self.y_coordinate[self.bit_len as usize / 8..]
51 }
52}
53impl Default for ECCPublicKeyBlob {
54 fn default() -> Self {
55 Self::new_256(&[0u8; 32], &[0u8; 32])
56 }
57}
58impl ECCPrivateKeyBlob {
59 pub fn new_256(key: &[u8]) -> Self {
63 if key.len() != 32 {
64 panic!("key.len() != 32");
65 }
66 let mut k = vec![0u8 as BYTE; 32];
67 k.extend(key);
68 Self {
69 bit_len: 256,
70 private_key: k.try_into().unwrap(),
71 }
72 }
73}
74impl Default for ECCPrivateKeyBlob {
75 fn default() -> Self {
76 Self::new_256(&[0u8; 32])
77 }
78}
79impl ECCCipherBlob {
80 pub const CIPHER_INDEX: usize = std::mem::size_of::<Self>() - 1;
82
83 pub fn size_of(cipher_len: usize) -> usize {
85 Self::CIPHER_INDEX + cipher_len
86 }
87
88 #[inline]
90 pub fn dst_size(&self) -> usize {
91 Self::CIPHER_INDEX + self.cipher_len as usize
92 }
93
94 pub fn cipher_ptr(&self) -> *const BYTE {
96 self.cipher.as_ptr() as *const BYTE
97 }
98
99 pub unsafe fn raw_bytes(&self) -> Vec<u8> {
105 let mut v: Vec<u8> = Vec::with_capacity(self.dst_size());
106 unsafe {
107 std::ptr::copy(
108 self.x_coordinate.as_ptr(),
109 v.as_mut_ptr(),
110 Self::CIPHER_INDEX,
111 );
112 std::ptr::copy(
113 self.cipher.as_ptr(),
114 v.as_mut_ptr().add(Self::CIPHER_INDEX),
115 self.cipher_len as usize,
116 );
117 v.set_len(self.dst_size());
118 }
119 v
120 }
121}
122
123impl Default for ECCSignatureBlob {
124 fn default() -> Self {
125 Self {
126 r: [0u8; 64],
127 s: [0u8; 64],
128 }
129 }
130}
131#[cfg(test)]
132mod test {
133 use crate::native::types::{
134 ECCCipherBlob, BYTE, ECC_MAX_X_COORDINATE_BITS_LEN, ECC_MAX_Y_COORDINATE_BITS_LEN, ULONG,
135 };
136
137 #[test]
138 fn cipher_blob_layout_test() {
139 #[derive(Debug, Copy, Clone)]
140 #[repr(C, packed(1))]
141 struct SizedBlob<const SIZE: usize> {
142 pub x_coordinate: [BYTE; ECC_MAX_X_COORDINATE_BITS_LEN / 8],
143 pub y_coordinate: [BYTE; ECC_MAX_Y_COORDINATE_BITS_LEN / 8],
144 pub hash: [BYTE; 32],
145 pub cipher_len: ULONG,
146 pub cipher: [BYTE; SIZE],
147 }
148
149 let x = SizedBlob::<100> {
150 x_coordinate: [1u8; 64],
151 y_coordinate: [2u8; 64],
152 hash: [3u8; 32],
153 cipher_len: 100,
154 cipher: [4u8; 100],
155 };
156 let blob: *const SizedBlob<100> = &x;
157 let blob = unsafe { &*(blob as *const ECCCipherBlob) };
158
159 assert_eq!(blob.x_coordinate, [1u8; 64]);
160 assert_eq!(blob.y_coordinate, [2u8; 64]);
161 assert_eq!(blob.hash, [3u8; 32]);
162 assert_eq!(
163 unsafe { std::ptr::addr_of!(blob.cipher_len).read_unaligned() },
164 100
165 );
166 assert_eq!(blob.cipher, [4u8; 1]);
167
168 let bytes = unsafe { blob.raw_bytes() };
169 assert_eq!(bytes.len(), blob.dst_size());
170 println!("raw bytes of ECCCipherBlob = {:?}", bytes);
171 }
172}