1use std::cell::{RefCell, RefMut};
6use std::cmp::min;
7use std::collections::HashMap;
8use std::iter;
9use std::marker::PhantomData;
10use std::rc::Rc;
11
12use aes::{Aes128, Aes192, Aes256};
13use cbc::{Decryptor as CbcDecryptor, Encryptor as CbcEncryptor};
14use cmac::Cmac;
15use crypto_common::{KeyInit, KeyIvInit};
16use digest::DynDigest as Digest;
17use ecb::{Decryptor as EcbDecryptor, Encryptor as EcbEncryptor};
18use hmac::Hmac;
19use rand_core::{CryptoRng, RngCore};
20use rsa::traits::{
21 PaddingScheme as RsaPaddingScheme, PublicKeyParts as _, SignatureScheme as RsaSignatureScheme,
22};
23use rsa::{Oaep, Pss, RsaPrivateKey};
24use sha1::Sha1;
25use sha2::{Sha224, Sha256, Sha384, Sha512};
26use tee_internal::{
27 Algorithm, Attribute, EccCurve, Error, Mode, OperationHandle, Result as TeeResult, Usage,
28};
29
30use crate::storage::{
31 AesKey, HmacSha1Key, HmacSha224Key, HmacSha256Key, HmacSha384Key, HmacSha512Key, Key,
32 KeyType as _, NoKey, Object, RsaKeypair,
33};
34use crate::ErrorWithSize;
35
36type AesCmac128 = Cmac<Aes128>;
37type AesCmac192 = Cmac<Aes192>;
38type AesCmac256 = Cmac<Aes256>;
39type HmacSha1 = Hmac<Sha1>;
40type HmacSha224 = Hmac<Sha224>;
41type HmacSha256 = Hmac<Sha256>;
42type HmacSha384 = Hmac<Sha384>;
43type HmacSha512 = Hmac<Sha512>;
44
45pub fn is_algorithm_supported(alg: Algorithm, element: EccCurve) -> bool {
46 if element != EccCurve::None {
47 return false;
48 }
49 match alg {
50 Algorithm::Sha1
51 | Algorithm::Sha224
52 | Algorithm::Sha256
53 | Algorithm::Sha384
54 | Algorithm::Sha512
55 | Algorithm::AesCbcNopad
56 | Algorithm::AesEcbNopad
57 | Algorithm::AesCmac
58 | Algorithm::HmacSha1
59 | Algorithm::HmacSha224
60 | Algorithm::HmacSha256
61 | Algorithm::HmacSha384
62 | Algorithm::HmacSha512
63 | Algorithm::RsaesPkcs1OaepMgf1Sha1 => true,
64 _ => false,
65 }
66}
67
68pub(crate) struct Rng {}
70
71impl RngCore for Rng {
72 fn next_u32(&mut self) -> u32 {
73 let val = 0u32;
74 self.fill_bytes(&mut val.to_le_bytes());
75 val
76 }
77
78 fn next_u64(&mut self) -> u64 {
79 let val = 0u64;
80 self.fill_bytes(&mut val.to_le_bytes());
81 val
82 }
83
84 fn fill_bytes(&mut self, dest: &mut [u8]) {
85 zx::cprng_draw(dest)
86 }
87
88 fn try_fill_bytes(&mut self, dest: &mut [u8]) -> Result<(), rand_core::Error> {
89 self.fill_bytes(dest);
90 Ok(())
91 }
92}
93
94impl CryptoRng for Rng {}
95
96trait Mac {
98 fn output_size(&self) -> usize;
99
100 fn update(&mut self, data: &[u8]);
101
102 fn reset(&mut self);
103
104 fn finalize_into_reset(&mut self, out: &mut [u8]);
105
106 fn verify_reset(&mut self, expected: &[u8]) -> TeeResult;
108}
109
110impl<M> Mac for M
112where
113 M: digest::FixedOutputReset + digest::MacMarker + digest::Update,
114{
115 fn output_size(&self) -> usize {
116 <Self as digest::OutputSizeUser>::output_size()
118 }
119
120 fn update(&mut self, data: &[u8]) {
121 <Self as digest::Update>::update(self, data)
122 }
123
124 fn reset(&mut self) {
125 <Self as digest::Reset>::reset(self)
127 }
128
129 fn finalize_into_reset(&mut self, out: &mut [u8]) {
130 <Self as digest::FixedOutputReset>::finalize_into_reset(self, out.into())
131 }
132
133 fn verify_reset(&mut self, expected: &[u8]) -> TeeResult {
134 let finalized = <Self as digest::FixedOutputReset>::finalize_fixed_reset(self);
135 if finalized.as_slice() == expected {
136 Ok(())
137 } else {
138 Err(Error::MacInvalid)
139 }
140 }
141}
142
143enum MacType {
145 AesCmac,
146 HmacSha1,
147 HmacSha224,
148 HmacSha256,
149 HmacSha384,
150 HmacSha512,
151}
152
153trait Cipher {
155 fn block_size(&self) -> usize;
156 fn set_iv(&mut self, iv: &[u8]);
157 fn reset(&mut self);
158 fn encrypt(&self, input: &[u8], output: &mut [u8]);
159 fn encrypt_in_place(&self, inout: &mut [u8]);
160 fn decrypt(&self, input: &[u8], output: &mut [u8]);
161 fn decrypt_in_place(&self, inout: &mut [u8]);
162}
163
164impl<C: PreCipher> Cipher for C {
165 fn set_iv(&mut self, iv: &[u8]) {
166 self.set_iv(iv)
167 }
168
169 fn reset(&mut self) {
170 self.reset()
171 }
172
173 fn block_size(&self) -> usize {
174 debug_assert_eq!(C::Encryptor::block_size(), C::Decryptor::block_size());
175 C::Encryptor::block_size()
176 }
177
178 fn encrypt(&self, input: &[u8], output: &mut [u8]) {
179 self.new_encryptor().encrypt(input, output);
180 }
181
182 fn encrypt_in_place(&self, inout: &mut [u8]) {
183 self.new_encryptor().encrypt_in_place(inout)
184 }
185
186 fn decrypt(&self, input: &[u8], output: &mut [u8]) {
187 self.new_decryptor().decrypt(input, output)
188 }
189
190 fn decrypt_in_place(&self, inout: &mut [u8]) {
191 self.new_decryptor().decrypt_in_place(inout)
192 }
193}
194
195trait PreCipher {
198 type Encryptor: Encryptor;
199 type Decryptor: Decryptor;
200
201 fn set_iv(&mut self, iv: &[u8]);
202 fn reset(&mut self);
203
204 fn new_encryptor(&self) -> Self::Encryptor;
207 fn new_decryptor(&self) -> Self::Decryptor;
208}
209
210trait Encryptor {
211 fn block_size() -> usize;
212 fn encrypt(&mut self, input: &[u8], output: &mut [u8]);
213 fn encrypt_in_place(&mut self, inout: &mut [u8]);
214}
215
216trait Decryptor {
217 fn block_size() -> usize;
218 fn decrypt(&mut self, input: &[u8], output: &mut [u8]);
219 fn decrypt_in_place(&mut self, inout: &mut [u8]);
220}
221
222struct CipherWithIv<E, D>
224where
225 E: Encryptor + KeyIvInit,
226 D: Decryptor + KeyIvInit,
227{
228 key: Vec<u8>,
229 iv: Vec<u8>,
230 phantom: PhantomData<(E, D)>,
231}
232
233impl<E, D> CipherWithIv<E, D>
234where
235 E: Encryptor + KeyIvInit,
236 D: Decryptor + KeyIvInit,
237{
238 fn new(key: &[u8]) -> Self {
239 Self { key: key.to_vec(), iv: Vec::new(), phantom: PhantomData::default() }
240 }
241}
242
243impl<E, D> PreCipher for CipherWithIv<E, D>
244where
245 E: Encryptor + KeyIvInit,
246 D: Decryptor + KeyIvInit,
247{
248 type Encryptor = E;
249 type Decryptor = D;
250
251 fn set_iv(&mut self, iv: &[u8]) {
252 self.iv = iv.to_vec()
253 }
254
255 fn reset(&mut self) {
256 self.iv.clear()
257 }
258
259 fn new_encryptor(&self) -> E {
260 E::new_from_slices(&self.key, &self.iv).unwrap()
261 }
262
263 fn new_decryptor(&self) -> D {
264 D::new_from_slices(&self.key, &self.iv).unwrap()
265 }
266}
267
268struct CipherWithoutIv<E, D>
270where
271 E: Encryptor + KeyInit,
272 D: Decryptor + KeyInit,
273{
274 key: Vec<u8>,
275 phantom: PhantomData<(E, D)>,
276}
277
278impl<E, D> CipherWithoutIv<E, D>
279where
280 E: Encryptor + KeyInit,
281 D: Decryptor + KeyInit,
282{
283 fn new(key: &[u8]) -> Self {
284 Self { key: key.to_vec(), phantom: PhantomData::default() }
285 }
286}
287
288impl<E, D> PreCipher for CipherWithoutIv<E, D>
289where
290 E: Encryptor + KeyInit,
291 D: Decryptor + KeyInit,
292{
293 type Encryptor = E;
294 type Decryptor = D;
295
296 fn set_iv(&mut self, _iv: &[u8]) {}
304
305 fn reset(&mut self) {}
306
307 fn new_encryptor(&self) -> E {
308 E::new_from_slice(&self.key).unwrap()
309 }
310 fn new_decryptor(&self) -> D {
311 D::new_from_slice(&self.key).unwrap()
312 }
313}
314
315macro_rules! rustcrypto_encryptor_and_decryptor {
323 ($encryptor:tt, $decryptor:tt) => {
324 impl<C> Encryptor for $encryptor<C>
325 where
326 C: cipher::BlockCipher + cipher::BlockEncryptMut,
327 {
328 fn block_size() -> usize {
329 C::block_size()
330 }
331
332 fn encrypt(&mut self, input: &[u8], output: &mut [u8]) {
333 use cipher::BlockEncryptMut;
334
335 assert!(output.len() >= input.len());
336 let block_size = C::block_size();
337 let chunks =
338 iter::zip(input.chunks_exact(block_size), output.chunks_exact_mut(block_size));
339 for (in_block, out_block) in chunks {
340 self.encrypt_block_b2b_mut(in_block.into(), out_block.into());
341 }
342 }
343
344 fn encrypt_in_place(&mut self, inout: &mut [u8]) {
345 use cipher::BlockEncryptMut;
346
347 for block in inout.chunks_exact_mut(C::block_size()) {
348 self.encrypt_block_mut(block.into())
349 }
350 }
351 }
352
353 impl<C> Decryptor for $decryptor<C>
354 where
355 C: cipher::BlockCipher + cipher::BlockDecryptMut,
356 {
357 fn block_size() -> usize {
358 C::block_size()
359 }
360
361 fn decrypt(&mut self, input: &[u8], output: &mut [u8]) {
362 use cipher::BlockDecryptMut;
363
364 assert!(output.len() >= input.len());
365 let block_size = C::block_size();
366 let chunks =
367 iter::zip(input.chunks_exact(block_size), output.chunks_exact_mut(block_size));
368 for (in_block, out_block) in chunks {
369 self.decrypt_block_b2b_mut(in_block.into(), out_block.into());
370 }
371 }
372
373 fn decrypt_in_place(&mut self, inout: &mut [u8]) {
374 use cipher::BlockDecryptMut;
375
376 for block in inout.chunks_exact_mut(C::block_size()) {
377 self.decrypt_block_mut(block.into())
378 }
379 }
380 }
381 };
382}
383
384rustcrypto_encryptor_and_decryptor!(CbcEncryptor, CbcDecryptor);
385rustcrypto_encryptor_and_decryptor!(EcbEncryptor, EcbDecryptor);
386
387type AesCbcNopad<C> = CipherWithIv<cbc::Encryptor<C>, cbc::Decryptor<C>>;
388type Aes128CbcNopad = AesCbcNopad<Aes128>;
389type Aes192CbcNopad = AesCbcNopad<Aes192>;
390type Aes256CbcNopad = AesCbcNopad<Aes256>;
391
392type AesEcbNopad<C> = CipherWithoutIv<ecb::Encryptor<C>, ecb::Decryptor<C>>;
393type Aes128EcbNopad = AesEcbNopad<Aes128>;
394type Aes192EcbNopad = AesEcbNopad<Aes192>;
395type Aes256EcbNopad = AesEcbNopad<Aes256>;
396
397enum CipherType {
398 AesCbcNopad,
399 AesEcbNopad,
400}
401
402trait AsymmetricEncryptionKey {
403 fn decrypt(
404 &self,
405 params: &[Attribute],
406 input: &[u8],
407 output: &mut [u8],
408 ) -> Result<usize, ErrorWithSize>;
409}
410
411trait RsaPadding<D>: RsaPaddingScheme
412where
413 D: 'static + Digest + digest::Digest + Send + Sync,
414{
415 fn new() -> Self;
416}
417
418impl<D> RsaPadding<D> for Oaep
419where
420 D: 'static + Digest + digest::Digest + Send + Sync,
421{
422 fn new() -> Self {
423 Oaep::new::<D>()
424 }
425}
426
427struct RsaEncryptionKey<D, Padding>
428where
429 D: 'static + Digest + digest::Digest + Send + Sync,
430 Padding: RsaPadding<D>,
431{
432 private: Rc<RsaPrivateKey>,
433 phantom: PhantomData<(D, Padding)>,
434}
435
436impl<D, Padding> RsaEncryptionKey<D, Padding>
437where
438 D: 'static + Digest + digest::Digest + Send + Sync,
439 Padding: RsaPadding<D>,
440{
441 fn new(private: Rc<RsaPrivateKey>) -> Self {
442 Self { private, phantom: PhantomData::default() }
443 }
444}
445
446impl<D, Padding> AsymmetricEncryptionKey for RsaEncryptionKey<D, Padding>
447where
448 D: 'static + Digest + digest::Digest + Send + Sync,
449 Padding: RsaPadding<D>,
450{
451 fn decrypt(
452 &self,
453 params: &[Attribute],
454 input: &[u8],
455 output: &mut [u8],
456 ) -> Result<usize, ErrorWithSize> {
457 if !params.is_empty() {
458 unimplemented!();
459 }
460 let output_size = self.private.size() as usize;
461 if input.len() != output_size {
462 return Err(ErrorWithSize::new(Error::BadParameters));
463 }
464 if output.len() < output_size {
465 return Err(ErrorWithSize::short_buffer(output_size));
466 }
467
468 let decrypted = self.private.decrypt(Padding::new(), input).expect("Failed to decrypt");
469 let written = &mut output[..decrypted.len()];
470 written.copy_from_slice(&decrypted);
471 Ok(written.len())
472 }
473}
474
475enum AsymmetricEncryptionKeyType {
476 RsaOaepSha1,
477}
478
479trait AsymmetricSigningKey {
480 fn sign(
481 &self,
482 params: &[Attribute],
483 input: &[u8],
484 output: &mut [u8],
485 ) -> Result<usize, ErrorWithSize>;
486}
487
488trait RsaSignature<D>: RsaSignatureScheme
489where
490 D: 'static + Digest + digest::Digest + Send + Sync,
491{
492 fn new() -> Self;
493}
494
495impl<D> RsaSignature<D> for Pss
496where
497 D: 'static + Digest + digest::Digest + Send + Sync,
498{
499 fn new() -> Self {
500 Pss::new::<D>()
501 }
502}
503
504struct RsaSigningKey<D, Signature>
505where
506 D: 'static + Digest + digest::Digest + Send + Sync,
507 Signature: RsaSignature<D>,
508{
509 private: Rc<RsaPrivateKey>,
510 phantom: PhantomData<(D, Signature)>,
511}
512
513impl<D, Signature> RsaSigningKey<D, Signature>
514where
515 D: 'static + Digest + digest::Digest + Send + Sync,
516 Signature: RsaSignature<D>,
517{
518 fn new(private: Rc<RsaPrivateKey>) -> Self {
519 Self { private, phantom: PhantomData::default() }
520 }
521}
522
523impl<D, Signature> AsymmetricSigningKey for RsaSigningKey<D, Signature>
524where
525 D: 'static + Digest + digest::Digest + Send + Sync,
526 Signature: RsaSignature<D>,
527{
528 fn sign(
529 &self,
530 params: &[Attribute],
531 input: &[u8],
532 output: &mut [u8],
533 ) -> Result<usize, ErrorWithSize> {
534 assert!(params.is_empty());
535 let output_size = self.private.size() as usize;
536 if output.len() < output_size {
537 return Err(ErrorWithSize::short_buffer(output_size));
538 }
539
540 let signed = self
541 .private
542 .sign_with_rng(&mut Rng {}, Signature::new(), input)
543 .expect("Failed to sign");
544 let written = &mut output[..signed.len()];
545 written.copy_from_slice(&signed);
546 Ok(written.len())
547 }
548}
549
550enum AsymmetricSigningKeyType {
551 RsaPssSha1,
552}
553
554enum Helper {
557 Digest(Box<dyn Digest>),
558 Cipher(Option<Box<dyn Cipher>>, CipherType),
559 Mac(Option<Box<dyn Mac>>, MacType),
560 AsymmetricEncryptionKey(Option<Box<dyn AsymmetricEncryptionKey>>, AsymmetricEncryptionKeyType),
561 AsymmetricSigningKey(Option<Box<dyn AsymmetricSigningKey>>, AsymmetricSigningKeyType),
562}
563
564impl Helper {
565 fn new(algorithm: Algorithm) -> TeeResult<Self> {
566 match algorithm {
567 Algorithm::Sha1 => Ok(Helper::Digest(Box::new(Sha1::default()))),
568 Algorithm::Sha224 => Ok(Helper::Digest(Box::new(Sha224::default()))),
569 Algorithm::Sha256 => Ok(Helper::Digest(Box::new(Sha256::default()))),
570 Algorithm::Sha384 => Ok(Helper::Digest(Box::new(Sha384::default()))),
571 Algorithm::Sha512 => Ok(Helper::Digest(Box::new(Sha512::default()))),
572 Algorithm::AesCbcNopad => Ok(Helper::Cipher(None, CipherType::AesCbcNopad)),
573 Algorithm::AesEcbNopad => Ok(Helper::Cipher(None, CipherType::AesEcbNopad)),
574 Algorithm::AesCmac => Ok(Helper::Mac(None, MacType::AesCmac)),
575 Algorithm::HmacSha1 => Ok(Helper::Mac(None, MacType::HmacSha1)),
576 Algorithm::HmacSha224 => Ok(Helper::Mac(None, MacType::HmacSha224)),
577 Algorithm::HmacSha256 => Ok(Helper::Mac(None, MacType::HmacSha256)),
578 Algorithm::HmacSha384 => Ok(Helper::Mac(None, MacType::HmacSha384)),
579 Algorithm::HmacSha512 => Ok(Helper::Mac(None, MacType::HmacSha512)),
580 Algorithm::RsaesPkcs1OaepMgf1Sha1 => {
581 Ok(Helper::AsymmetricEncryptionKey(None, AsymmetricEncryptionKeyType::RsaOaepSha1))
582 }
583 Algorithm::RsassaPkcs1PssMgf1Sha1 => {
584 Ok(Helper::AsymmetricSigningKey(None, AsymmetricSigningKeyType::RsaPssSha1))
585 }
586 _ => Err(Error::NotSupported),
587 }
588 }
589
590 fn initialize(&mut self, key: &Key) {
591 match self {
592 Helper::Digest(digest) => {
593 assert!(matches!(key, Key::Data(NoKey {})));
595 digest.reset()
596 }
597 Helper::Cipher(cipher, cipher_type) => {
598 let Key::Aes(AesKey { secret }) = key else {
599 panic!("Wrong key type ({:?}) - expected AES", key.get_type());
600 };
601
602 match cipher_type {
603 CipherType::AesCbcNopad => {
604 let cbc: Box<dyn Cipher> = match secret.len() {
605 16 => Box::new(Aes128CbcNopad::new(&secret)),
606 24 => Box::new(Aes192CbcNopad::new(&secret)),
607 32 => Box::new(Aes256CbcNopad::new(&secret)),
608 len => panic!("Invalid AES key length: {len}"),
609 };
610 *cipher = Some(cbc);
611 }
612 CipherType::AesEcbNopad => {
613 let ecb: Box<dyn Cipher> = match secret.len() {
614 16 => Box::new(Aes128EcbNopad::new(&secret)),
615 24 => Box::new(Aes192EcbNopad::new(&secret)),
616 32 => Box::new(Aes256EcbNopad::new(&secret)),
617 len => panic!("Invalid AES key length: {len}"),
618 };
619 *cipher = Some(ecb);
620 }
621 }
622 }
623 Helper::Mac(mac, mac_type) => match mac_type {
624 MacType::AesCmac => {
625 let Key::Aes(AesKey { secret }) = key else {
626 panic!("Wrong key type ({:?}) - expected AES", key.get_type());
627 };
628 let cmac: Box<dyn Mac> = match secret.len() {
629 16 => Box::new(AesCmac128::new_from_slice(&secret).unwrap()),
630 24 => Box::new(AesCmac192::new_from_slice(&secret).unwrap()),
631 32 => Box::new(AesCmac256::new_from_slice(&secret).unwrap()),
632 len => panic!("Invalid AES key length: {len}"),
633 };
634 *mac = Some(cmac);
635 }
636 MacType::HmacSha1 => {
637 let Key::HmacSha1(HmacSha1Key { secret }) = key else {
638 panic!("Wrong key type ({:?}) - expected HMAC SHA1", key.get_type());
639 };
640 *mac = Some(Box::new(HmacSha1::new_from_slice(&secret).unwrap()))
641 }
642 MacType::HmacSha224 => {
643 let Key::HmacSha224(HmacSha224Key { secret }) = key else {
644 panic!("Wrong key type ({:?}) - expected HMAC SHA224", key.get_type());
645 };
646 *mac = Some(Box::new(HmacSha224::new_from_slice(&secret).unwrap()))
647 }
648 MacType::HmacSha256 => {
649 let Key::HmacSha256(HmacSha256Key { secret }) = key else {
650 panic!("Wrong key type ({:?}) - expected HMAC SHA256", key.get_type());
651 };
652 *mac = Some(Box::new(HmacSha256::new_from_slice(&secret).unwrap()))
653 }
654 MacType::HmacSha384 => {
655 let Key::HmacSha384(HmacSha384Key { secret }) = key else {
656 panic!("Wrong key type ({:?}) - expected HMAC SHA384", key.get_type());
657 };
658 *mac = Some(Box::new(HmacSha384::new_from_slice(&secret).unwrap()))
659 }
660 MacType::HmacSha512 => {
661 let Key::HmacSha512(HmacSha512Key { secret }) = key else {
662 panic!("Wrong key type ({:?}) - expected HMAC SHA512", key.get_type());
663 };
664 *mac = Some(Box::new(HmacSha512::new_from_slice(&secret).unwrap()))
665 }
666 },
667 Helper::AsymmetricEncryptionKey(aenc, aenc_type) => match aenc_type {
668 AsymmetricEncryptionKeyType::RsaOaepSha1 => {
669 let Key::RsaKeypair(rsa) = key else {
670 panic!("Wrong key type ({:?}) - expected RSA keypair", key.get_type());
671 };
672 *aenc = Some(Box::new(RsaEncryptionKey::<Sha1, Oaep>::new(rsa.private_key())));
673 }
674 },
675 Helper::AsymmetricSigningKey(asign, asign_type) => match asign_type {
676 AsymmetricSigningKeyType::RsaPssSha1 => {
677 let Key::RsaKeypair(rsa) = key else {
678 panic!("Wrong key type ({:?}) - expected RSA keypair", key.get_type());
679 };
680 *asign = Some(Box::new(RsaSigningKey::<Sha1, Pss>::new(rsa.private_key())));
681 }
682 },
683 }
684 }
685
686 fn reset(&mut self) {
687 match self {
688 Helper::Digest(digest) => digest.reset(),
689 Helper::Cipher(cipher, _) => {
690 if let Some(cipher) = cipher {
691 cipher.reset()
692 }
693 }
694 Helper::Mac(mac, _) => {
695 if let Some(mac) = mac {
696 mac.reset()
697 }
698 }
699 Helper::AsymmetricEncryptionKey(_, _) => {}
700 Helper::AsymmetricSigningKey(_, _) => {}
701 }
702 }
703}
704
705#[derive(Debug, Eq, PartialEq)]
706enum OpState {
707 Initial,
708 Active,
709 Extracting((Vec<u8>, usize)),
712}
713
714pub struct Operation {
715 algorithm: Algorithm,
716 mode: Mode,
717 key: Key,
718 max_key_size: u32, state: OpState,
720 helper: Helper,
721}
722
723impl Operation {
724 fn new(algorithm: Algorithm, mode: Mode, max_key_size: u32) -> TeeResult<Self> {
725 Ok(Self {
726 algorithm,
727 mode,
728 key: Key::Data(NoKey {}),
729 max_key_size,
730 state: OpState::Initial,
731 helper: Helper::new(algorithm)?,
732 })
733 }
734
735 fn as_digest(&mut self) -> &mut Box<dyn Digest> {
736 if let Helper::Digest(digest) = &mut self.helper {
737 digest
738 } else {
739 panic!("{:?} is not a digest algorithm", self.algorithm)
740 }
741 }
742
743 fn as_cipher(&mut self) -> &mut Box<dyn Cipher> {
744 if let Helper::Cipher(cipher, _) = &mut self.helper {
745 cipher.as_mut().expect("TEE_OperationSetKey() has not yet been called")
746 } else {
747 panic!("{:?} is not a cipher algorithm", self.algorithm)
748 }
749 }
750
751 fn as_mac(&mut self) -> &mut Box<dyn Mac> {
752 if let Helper::Mac(mac, _) = &mut self.helper {
753 mac.as_mut().expect("TEE_OperationSetKey() has not yet been called")
754 } else {
755 panic!("{:?} is not a MAC algorithm", self.algorithm)
756 }
757 }
758
759 fn as_asymmetric_encryption_key(&mut self) -> &mut Box<dyn AsymmetricEncryptionKey> {
760 if let Helper::AsymmetricEncryptionKey(aenc, _) = &mut self.helper {
761 aenc.as_mut().expect("TEE_OperationSetKey() has not yet been called")
762 } else {
763 panic!("{:?} is not a asymmetric encryption key algorithm", self.algorithm)
764 }
765 }
766
767 fn as_asymmetric_signing_key(&mut self) -> &mut Box<dyn AsymmetricSigningKey> {
768 if let Helper::AsymmetricSigningKey(aenc, _) = &mut self.helper {
769 aenc.as_mut().expect("TEE_OperationSetKey() has not yet been called")
770 } else {
771 panic!("{:?} is not a asymmetric signing key algorithm", self.algorithm)
772 }
773 }
774
775 fn is_extracting(&self) -> (bool, usize) {
778 if let OpState::Extracting((ref data, ref pos)) = self.state {
779 (true, data.len() - pos)
780 } else {
781 (false, 0)
782 }
783 }
784
785 fn reset(&mut self) {
786 self.helper.reset();
787 self.state = OpState::Initial;
788 }
789
790 fn set_key(&mut self, obj: Rc<RefCell<dyn Object>>) -> TeeResult {
791 let obj = obj.borrow();
792 let key = obj.key();
793
794 assert!(
795 key.max_size() <= self.max_key_size,
796 "Provided key size ({}) exceeds configured max ({})",
797 key.max_size(),
798 self.max_key_size
799 );
800
801 assert_eq!(
802 self.state,
803 OpState::Initial,
804 "Operation must be in the initial state (not {:?})",
805 self.state
806 );
807
808 match self.algorithm {
809 Algorithm::AesCbcNopad | Algorithm::AesEcbNopad => match self.mode {
810 Mode::Encrypt | Mode::Decrypt => {
811 let usage = obj.usage();
812 if self.mode == Mode::Encrypt {
813 assert!(usage.contains(Usage::ENCRYPT | Usage::VERIFY));
814 } else {
815 assert!(usage.contains(Usage::DECRYPT | Usage::SIGN));
816 }
817 }
818 _ => return Err(Error::NotImplemented),
819 },
820 Algorithm::Md5
821 | Algorithm::Sha1
822 | Algorithm::Sha224
823 | Algorithm::Sha256
824 | Algorithm::Sha384
825 | Algorithm::Sha512
826 | Algorithm::Sha3_224
827 | Algorithm::Sha3_256
828 | Algorithm::Sha3_384
829 | Algorithm::Sha3_512
830 | Algorithm::Shake128
831 | Algorithm::Shake256 => {
832 panic!("Algorithm {:?} has no associated object type", self.algorithm);
833 }
834 Algorithm::AesCmac
835 | Algorithm::HmacSha1
836 | Algorithm::HmacSha224
837 | Algorithm::HmacSha256
838 | Algorithm::HmacSha384
839 | Algorithm::HmacSha512 => {}
840 Algorithm::RsaesPkcs1OaepMgf1Sha1 => {}
841 Algorithm::RsassaPkcs1PssMgf1Sha1 => {}
842 _ => return Err(Error::NotImplemented),
843 };
844 self.key = key.clone();
845 self.helper.initialize(&self.key);
846 Ok(())
847 }
848
849 fn clear_key(&mut self) -> TeeResult {
850 self.key = Key::Data(NoKey {});
851 self.state = OpState::Initial;
852 Ok(())
853 }
854
855 fn extract_finalized(&mut self, buf: &mut [u8]) -> usize {
859 let OpState::Extracting((ref data, ref mut pos)) = self.state else {
860 panic!("Operation is not in the extracting state: {:?}", self.state);
861 };
862 if buf.is_empty() || *pos >= data.len() {
863 return 0;
864 }
865 let read_size = min(data.len() - *pos, buf.len());
866 let in_chunk = &data.as_slice()[*pos..(*pos + read_size)];
867 let out_chunk = &mut buf[..read_size];
868 out_chunk.copy_from_slice(in_chunk);
869 *pos += read_size;
870 read_size
871 }
872
873 fn update_digest(&mut self, chunk: &[u8]) {
875 assert_eq!(self.mode, Mode::Digest);
876 assert!(self.state == OpState::Initial || self.state == OpState::Active);
877 self.as_digest().update(chunk);
878 self.state = OpState::Active;
879 }
880
881 fn update_and_finalize_digest_into(
888 &mut self,
889 last_chunk: &[u8],
890 buf: &mut [u8],
891 ) -> Result<(), ErrorWithSize> {
892 assert_eq!(self.mode, Mode::Digest);
893
894 if let (true, left_to_extract) = self.is_extracting() {
895 assert!(last_chunk.is_empty());
896
897 if left_to_extract > buf.len() {
898 return Err(ErrorWithSize::short_buffer(left_to_extract));
899 }
900
901 let written = self.extract_digest(buf);
902 debug_assert_eq!(written, left_to_extract);
903 self.state = OpState::Initial;
904 return Ok(());
905 }
906
907 let buf = {
908 let digest = self.as_digest();
909 let output_size = digest.output_size();
910 if output_size > buf.len() {
911 return Err(ErrorWithSize::short_buffer(output_size));
912 }
913
914 if !last_chunk.is_empty() {
915 digest.update(last_chunk);
916 }
917 &mut buf[..output_size]
918 };
919
920 self.as_digest().finalize_into_reset(buf).unwrap();
921 self.state = OpState::Initial;
922 Ok(())
923 }
924
925 fn finalize_digest(&mut self) {
928 assert_eq!(self.mode, Mode::Digest);
929 let (extracting, _) = self.is_extracting();
930 if extracting {
931 return;
932 }
933
934 let bytes = self.as_digest().finalize_reset();
935 self.state = OpState::Extracting((Vec::from(bytes), 0));
936 }
937
938 fn extract_digest(&mut self, buf: &mut [u8]) -> usize {
940 self.finalize_digest();
941 self.extract_finalized(buf)
942 }
943
944 fn init_cipher(&mut self, iv: &[u8]) {
946 if self.state == OpState::Active {
947 self.as_cipher().reset();
948 } else {
949 assert_eq!(self.state, OpState::Initial);
950 }
951
952 self.as_cipher().set_iv(iv);
953
954 self.state = OpState::Active;
956 }
957
958 fn update_cipher(&mut self, src: &[u8], dest: &mut [u8]) -> Result<(), ErrorWithSize> {
961 assert_eq!(self.state, OpState::Active);
962
963 let block_size = self.as_cipher().block_size();
964 let num_blocks_in = src.len() / block_size;
965 let num_blocks_out = dest.len() / block_size;
966
967 if num_blocks_in > num_blocks_out {
970 return Err(ErrorWithSize::short_buffer(num_blocks_in * block_size));
971 }
972
973 if self.mode == Mode::Encrypt {
974 self.as_cipher().encrypt(src, dest);
975 } else {
976 assert_eq!(self.mode, Mode::Decrypt);
977 self.as_cipher().decrypt(src, dest);
978 }
979 Ok(())
980 }
981
982 fn update_cipher_in_place(&mut self, inout: &mut [u8]) {
983 assert_eq!(self.state, OpState::Active);
984
985 if self.mode == Mode::Encrypt {
986 self.as_cipher().encrypt_in_place(inout);
987 } else {
988 assert_eq!(self.mode, Mode::Decrypt);
989 self.as_cipher().decrypt_in_place(inout);
990 }
991 }
992
993 fn finalize_cipher(&mut self, src: &[u8], dest: &mut [u8]) -> Result<(), ErrorWithSize> {
997 let block_size = self.as_cipher().block_size();
998 assert_eq!(src.len() % block_size, 0);
999 assert!(dest.len() >= src.len());
1000 self.update_cipher(src, dest)?;
1001 self.state = OpState::Initial;
1002 Ok(())
1003 }
1004
1005 fn finalize_cipher_in_place(&mut self, inout: &mut [u8]) {
1006 let block_size = self.as_cipher().block_size();
1007 assert_eq!(inout.len() % block_size, 0);
1008 self.update_cipher_in_place(inout);
1009 self.state = OpState::Initial;
1010 }
1011
1012 fn init_mac(&mut self, _iv: &[u8]) {
1014 assert_eq!(self.mode, Mode::Mac);
1015 assert!(self.state == OpState::Initial || self.state == OpState::Active);
1016
1017 if self.state == OpState::Active {
1018 self.as_mac().reset();
1019 }
1020
1021 self.state = OpState::Active;
1025 }
1026
1027 fn update_mac(&mut self, chunk: &[u8]) {
1029 assert_eq!(self.mode, Mode::Mac);
1030 assert_eq!(self.state, OpState::Active);
1031
1032 let mac = self.as_mac();
1033 if !chunk.is_empty() {
1034 mac.update(chunk);
1035 }
1036 }
1037
1038 fn compute_final_mac(
1040 &mut self,
1041 message: &[u8],
1042 output: &mut [u8],
1043 ) -> Result<(), ErrorWithSize> {
1044 assert_eq!(self.mode, Mode::Mac);
1045 assert_eq!(self.state, OpState::Active);
1046
1047 let output_size = self.as_mac().output_size();
1048 if output.len() < output_size {
1049 return Err(ErrorWithSize::short_buffer(output_size));
1050 }
1051
1052 let mac = self.as_mac();
1055 if !message.is_empty() {
1056 mac.update(message);
1057 }
1058 mac.finalize_into_reset(&mut output[..output_size]);
1059 self.state = OpState::Initial;
1060 Ok(())
1061 }
1062
1063 fn compare_final_mac(&mut self, message: &[u8], expected: &[u8]) -> TeeResult {
1065 self.update_mac(message);
1066 let result = self.as_mac().verify_reset(expected);
1067 self.state = OpState::Initial;
1068 result
1069 }
1070
1071 fn asymmetric_decrypt(
1073 &mut self,
1074 params: &[Attribute],
1075 src: &[u8],
1076 dest: &mut [u8],
1077 ) -> Result<usize, ErrorWithSize> {
1078 assert_eq!(self.mode, Mode::Decrypt);
1079 self.as_asymmetric_encryption_key().decrypt(params, src, dest)
1080 }
1081
1082 fn asymmetric_sign_digest(
1084 &mut self,
1085 params: &[Attribute],
1086 digest: &[u8],
1087 signature: &mut [u8],
1088 ) -> Result<usize, ErrorWithSize> {
1089 assert_eq!(self.mode, Mode::Sign);
1090 self.as_asymmetric_signing_key().sign(params, digest, signature)
1091 }
1092}
1093
1094pub struct Operations {
1095 operations: HashMap<OperationHandle, RefCell<Operation>>,
1096 next_operation_handle_value: OperationHandle,
1097}
1098
1099impl Operations {
1100 pub fn new() -> Self {
1101 Self {
1102 operations: HashMap::new(),
1103 next_operation_handle_value: OperationHandle::from_value(1),
1104 }
1105 }
1106
1107 pub fn allocate(
1108 &mut self,
1109 algorithm: Algorithm,
1110 mode: Mode,
1111 max_key_size: u32,
1112 ) -> TeeResult<OperationHandle> {
1113 let is_valid_key_size = match algorithm {
1119 Algorithm::AesCbcNopad | Algorithm::AesEcbNopad => {
1120 match mode {
1121 Mode::Encrypt | Mode::Decrypt => {}
1122 _ => {
1123 return Err(Error::NotSupported);
1124 }
1125 };
1126 AesKey::is_valid_size
1127 }
1128 Algorithm::Md5
1129 | Algorithm::Sha1
1130 | Algorithm::Sha224
1131 | Algorithm::Sha256
1132 | Algorithm::Sha384
1133 | Algorithm::Sha512
1134 | Algorithm::Sha3_224
1135 | Algorithm::Sha3_256
1136 | Algorithm::Sha3_384
1137 | Algorithm::Sha3_512
1138 | Algorithm::Shake128
1139 | Algorithm::Shake256 => {
1140 if mode != Mode::Digest {
1141 return Err(Error::NotSupported);
1142 }
1143 NoKey::is_valid_size
1144 }
1145 Algorithm::AesCmac => {
1146 if mode != Mode::Mac {
1147 return Err(Error::NotSupported);
1148 }
1149 AesKey::is_valid_size
1150 }
1151 Algorithm::HmacSha1 => {
1152 if mode != Mode::Mac {
1153 return Err(Error::NotSupported);
1154 }
1155 HmacSha1Key::is_valid_size
1156 }
1157 Algorithm::HmacSha224 => {
1158 if mode != Mode::Mac {
1159 return Err(Error::NotSupported);
1160 }
1161 HmacSha224Key::is_valid_size
1162 }
1163 Algorithm::HmacSha256 => {
1164 if mode != Mode::Mac {
1165 return Err(Error::NotSupported);
1166 }
1167 HmacSha256Key::is_valid_size
1168 }
1169 Algorithm::HmacSha384 => {
1170 if mode != Mode::Mac {
1171 return Err(Error::NotSupported);
1172 }
1173 HmacSha384Key::is_valid_size
1174 }
1175 Algorithm::HmacSha512 => {
1176 if mode != Mode::Mac {
1177 return Err(Error::NotSupported);
1178 }
1179 HmacSha512Key::is_valid_size
1180 }
1181 Algorithm::RsaesPkcs1OaepMgf1Sha1 => {
1182 if mode != Mode::Encrypt && mode != Mode::Decrypt {
1183 return Err(Error::NotSupported);
1184 }
1185 RsaKeypair::is_valid_size
1186 }
1187 Algorithm::RsassaPkcs1PssMgf1Sha1 => {
1188 if mode != Mode::Sign && mode != Mode::Verify {
1189 return Err(Error::NotSupported);
1190 }
1191 RsaKeypair::is_valid_size
1192 }
1193 _ => {
1194 inspect_stubs::track_stub!(
1195 TODO("https://fxbug.dev/360942581"),
1196 "unsupported algorithm",
1197 );
1198 return Err(Error::NotImplemented);
1199 }
1200 };
1201 if !is_valid_key_size(max_key_size) {
1202 return Err(Error::NotSupported);
1203 }
1204 let operation = Operation::new(algorithm, mode, max_key_size)?;
1205 let handle = self.allocate_operation_handle();
1206 let prev = self.operations.insert(handle, RefCell::new(operation));
1207 debug_assert!(prev.is_none());
1208 Ok(handle)
1209 }
1210
1211 fn allocate_operation_handle(&mut self) -> OperationHandle {
1212 let handle = self.next_operation_handle_value;
1213 self.next_operation_handle_value = OperationHandle::from_value(*handle + 1);
1214 handle
1215 }
1216
1217 fn get_mut(&self, operation: OperationHandle) -> RefMut<'_, Operation> {
1218 self.operations.get(&operation).unwrap().borrow_mut()
1219 }
1220
1221 pub fn free(&mut self, operation: OperationHandle) {
1222 if operation.is_null() {
1223 return;
1224 }
1225 let _ = self.operations.remove(&operation).unwrap();
1226 }
1227
1228 pub fn reset(&mut self, operation: OperationHandle) {
1229 self.get_mut(operation).reset()
1230 }
1231
1232 pub fn set_key(
1233 &mut self,
1234 operation: OperationHandle,
1235 key: Rc<RefCell<dyn Object>>,
1236 ) -> TeeResult {
1237 self.get_mut(operation).set_key(key)
1238 }
1239
1240 pub fn clear_key(&mut self, operation: OperationHandle) -> TeeResult {
1241 self.get_mut(operation).clear_key()
1242 }
1243
1244 pub fn update_digest(&mut self, operation: OperationHandle, chunk: &[u8]) {
1245 self.get_mut(operation).update_digest(chunk);
1246 }
1247
1248 pub fn update_and_finalize_digest_into(
1249 &mut self,
1250 operation: OperationHandle,
1251 last_chunk: &[u8],
1252 buf: &mut [u8],
1253 ) -> Result<(), ErrorWithSize> {
1254 self.get_mut(operation).update_and_finalize_digest_into(last_chunk, buf)
1255 }
1256
1257 pub fn extract_digest<'a>(&mut self, operation: OperationHandle, buf: &'a mut [u8]) -> usize {
1258 self.get_mut(operation).extract_digest(buf)
1259 }
1260
1261 pub fn init_cipher(&mut self, operation: OperationHandle, iv: &[u8]) {
1262 self.get_mut(operation).init_cipher(iv)
1263 }
1264
1265 pub fn update_cipher(
1266 &mut self,
1267 operation: OperationHandle,
1268 input: &[u8],
1269 output: &mut [u8],
1270 ) -> Result<(), ErrorWithSize> {
1271 self.get_mut(operation).update_cipher(input, output)
1272 }
1273
1274 pub fn update_cipher_in_place(&mut self, operation: OperationHandle, inout: &mut [u8]) {
1275 self.get_mut(operation).update_cipher_in_place(inout)
1276 }
1277
1278 pub fn finalize_cipher(
1279 &mut self,
1280 operation: OperationHandle,
1281 input: &[u8],
1282 output: &mut [u8],
1283 ) -> Result<(), ErrorWithSize> {
1284 self.get_mut(operation).finalize_cipher(input, output)
1285 }
1286
1287 pub fn finalize_cipher_in_place(&mut self, operation: OperationHandle, inout: &mut [u8]) {
1288 self.get_mut(operation).finalize_cipher_in_place(inout)
1289 }
1290
1291 pub fn init_mac(&mut self, operation: OperationHandle, iv: &[u8]) {
1292 self.get_mut(operation).init_mac(iv)
1293 }
1294
1295 pub fn update_mac(&mut self, operation: OperationHandle, chunk: &[u8]) {
1296 self.get_mut(operation).update_mac(chunk)
1297 }
1298
1299 pub fn compute_final_mac(
1300 &mut self,
1301 operation: OperationHandle,
1302 message: &[u8],
1303 mac: &mut [u8],
1304 ) -> Result<(), ErrorWithSize> {
1305 self.get_mut(operation).compute_final_mac(message, mac)
1306 }
1307
1308 pub fn compare_final_mac(
1309 &mut self,
1310 operation: OperationHandle,
1311 message: &[u8],
1312 mac: &[u8],
1313 ) -> TeeResult {
1314 self.get_mut(operation).compare_final_mac(message, mac)
1315 }
1316
1317 pub fn asymmetric_decrypt(
1318 &mut self,
1319 operation: OperationHandle,
1320 params: &[Attribute],
1321 src: &[u8],
1322 dest: &mut [u8],
1323 ) -> Result<usize, ErrorWithSize> {
1324 self.get_mut(operation).asymmetric_decrypt(params, src, dest)
1325 }
1326
1327 pub fn asymmetric_sign_digest(
1328 &mut self,
1329 operation: OperationHandle,
1330 params: &[Attribute],
1331 digest: &[u8],
1332 signature: &mut [u8],
1333 ) -> Result<usize, ErrorWithSize> {
1334 self.get_mut(operation).asymmetric_sign_digest(params, digest, signature)
1335 }
1336}
1337
1338#[cfg(test)]
1339mod tests {
1340 use super::*;
1341
1342 #[fuchsia::test]
1343 fn operation_lifecycle() -> Result<(), Error> {
1344 let mut operations = Operations::new();
1345
1346 let operation = operations.allocate(Algorithm::Sha256, Mode::Digest, 0).unwrap();
1347
1348 operations.free(operation);
1349
1350 Ok(())
1351 }
1352}