1 // Copyright 2023 Google LLC 2 // 3 // Licensed under the Apache License, Version 2.0 (the "License"); 4 // you may not use this file except in compliance with the License. 5 // You may obtain a copy of the License at 6 // 7 // http://www.apache.org/licenses/LICENSE-2.0 8 // 9 // Unless required by applicable law or agreed to in writing, software 10 // distributed under the License is distributed on an "AS IS" BASIS, 11 // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 12 // See the License for the specific language governing permissions and 13 // limitations under the License.' 14 15 //! Crypto abstraction trait only crate, which provides traits for cryptographic primitives 16 17 #![no_std] 18 19 use core::fmt::Debug; 20 21 use crate::aes::{Aes128Key, Aes256Key}; 22 23 /// mod containing hmac trait 24 pub mod hkdf; 25 26 /// mod containing hkdf trait 27 pub mod hmac; 28 29 /// mod containing X25519 trait 30 pub mod x25519; 31 32 /// mod containing traits for NIST-P256 elliptic curve implementation. 33 pub mod p256; 34 35 /// mod containing traits for elliptic curve cryptography. 36 pub mod elliptic_curve; 37 38 /// mod containing SHA256 trait. 39 pub mod sha2; 40 41 /// mod containing aes trait. 42 pub mod aes; 43 44 /// mod containing aead trait. 45 pub mod aead; 46 47 /// mod containing traits for ed25519 key generation, signing, and verification 48 pub mod ed25519; 49 50 pub use tinyvec; 51 52 /// Uber crypto trait which defines the traits for all crypto primitives as associated types 53 pub trait CryptoProvider: Clone + Debug + PartialEq + Eq + Send { 54 /// The Hkdf type which implements the hkdf trait 55 type HkdfSha256: hkdf::Hkdf; 56 /// The Hmac type which implements the hmac trait 57 type HmacSha256: hmac::Hmac<32>; 58 /// The Hkdf type which implements the hkdf trait 59 type HkdfSha512: hkdf::Hkdf; 60 /// The Hmac type which implements the hmac trait 61 type HmacSha512: hmac::Hmac<64>; 62 /// The AES-CBC-PKCS7 implementation to use 63 type AesCbcPkcs7Padded: aes::cbc::AesCbcPkcs7Padded; 64 /// The X25519 implementation to use for ECDH. 65 type X25519: elliptic_curve::EcdhProvider<x25519::X25519>; 66 /// The P256 implementation to use for ECDH. 67 type P256: p256::P256EcdhProvider; 68 /// The SHA256 hash implementation. 69 type Sha256: sha2::Sha256; 70 /// The SHA512 hash implementation. 71 type Sha512: sha2::Sha512; 72 /// Plain AES-128 implementation (without block cipher mode). 73 type Aes128: aes::Aes<Key = Aes128Key>; 74 /// Plain AES-256 implementation (without block cipher mode). 75 type Aes256: aes::Aes<Key = Aes256Key>; 76 /// AES-128 with CTR block mode 77 type AesCtr128: aes::ctr::AesCtr<Key = aes::Aes128Key>; 78 /// AES-256 with CTR block mode 79 type AesCtr256: aes::ctr::AesCtr<Key = aes::Aes256Key>; 80 /// The trait defining ed25519, a Edwards-curve Digital Signature Algorithm signature scheme 81 /// using SHA-512 (SHA-2) and Curve25519 82 type Ed25519: ed25519::Ed25519Provider; 83 /// The trait defining AES-128-GCM-SIV, a nonce-misuse resistant AEAD with a key size of 16 bytes. 84 type Aes128GcmSiv: aead::AesGcmSiv + aead::AeadInit<Aes128Key>; 85 /// The trait defining AES-256-GCM-SIV, a nonce-misuse resistant AEAD with a key size of 32 bytes. 86 type Aes256GcmSiv: aead::AesGcmSiv + aead::AeadInit<Aes256Key>; 87 /// The trait defining AES-128-GCM, an AEAD with a key size of 16 bytes. 88 type Aes128Gcm: aead::AesGcm + aead::AeadInit<Aes128Key>; 89 /// The trait defining AES-256-GCM, an AEAD with a key size of 32 bytes. 90 type Aes256Gcm: aead::AesGcm + aead::AeadInit<Aes256Key>; 91 /// The cryptographically secure random number generator 92 type CryptoRng: CryptoRng; 93 94 /// Compares the two given slices, in constant time, and returns true if they are equal. constant_time_eq(a: &[u8], b: &[u8]) -> bool95 fn constant_time_eq(a: &[u8], b: &[u8]) -> bool; 96 } 97 98 /// Wrapper to a cryptographically secure pseudo random number generator 99 pub trait CryptoRng { 100 /// Returns an instance of the rng new() -> Self101 fn new() -> Self; 102 103 /// Return the next random u64 next_u64(&mut self) -> u64104 fn next_u64(&mut self) -> u64; 105 106 /// Fill dest with random data fill(&mut self, dest: &mut [u8])107 fn fill(&mut self, dest: &mut [u8]); 108 109 /// Generate a random entity gen<F: FromCryptoRng>(&mut self) -> F where Self: Sized,110 fn gen<F: FromCryptoRng>(&mut self) -> F 111 where 112 Self: Sized, 113 { 114 F::new_random::<Self>(self) 115 } 116 } 117 118 /// If impls want to opt out of passing a Rng they can simply use `()` for the Rng associated type 119 impl CryptoRng for () { new() -> Self120 fn new() -> Self {} 121 next_u64(&mut self) -> u64122 fn next_u64(&mut self) -> u64 { 123 unimplemented!() 124 } 125 fill(&mut self, _dest: &mut [u8])126 fn fill(&mut self, _dest: &mut [u8]) { 127 unimplemented!() 128 } 129 } 130 131 /// For types that can be created from a `CryptoRng` 132 pub trait FromCryptoRng { 133 /// Construct a new `Self` with random data from `rng` new_random<R: CryptoRng>(rng: &mut R) -> Self134 fn new_random<R: CryptoRng>(rng: &mut R) -> Self; 135 } 136 137 impl<const N: usize> FromCryptoRng for [u8; N] { new_random<R: CryptoRng>(rng: &mut R) -> Self138 fn new_random<R: CryptoRng>(rng: &mut R) -> Self { 139 let mut arr = [0; N]; 140 rng.fill(&mut arr); 141 arr 142 } 143 } 144 145 impl FromCryptoRng for u8 { new_random<R: CryptoRng>(rng: &mut R) -> Self146 fn new_random<R: CryptoRng>(rng: &mut R) -> Self { 147 let arr: [u8; 1] = rng.gen(); 148 arr[0] 149 } 150 } 151