ovunto_security/crypto/
hmac.rs

1use aes_gcm::aes::cipher::BlockSizeUser;
2use hmac::Mac;
3use sha1::{
4    digest::{
5        block_buffer::Eager,
6        consts::U256,
7        core_api::{BufferKindUser, CoreProxy, FixedOutputCore, UpdateCore},
8        typenum::{IsLess, Le, NonZero},
9        HashMarker,
10    },
11    Sha1,
12};
13use sha2::{Sha256, Sha512};
14
15use crate::{Algorithm, Key};
16
17pub trait Hmac {
18    fn hmac(&self, secret: Key, bytes: &[u8]) -> Vec<u8>;
19
20    fn hmac_oid<D>(secret: Key, bytes: &[u8]) -> Vec<u8>
21    where
22        D: CoreProxy,
23        D::Core: HashMarker
24            + UpdateCore
25            + FixedOutputCore
26            + BufferKindUser<BufferKind = Eager>
27            + Default
28            + Clone,
29        <D::Core as BlockSizeUser>::BlockSize: IsLess<U256>,
30        Le<<D::Core as BlockSizeUser>::BlockSize, U256>: NonZero,
31    {
32        let mut mac =
33            hmac::Hmac::<D>::new_from_slice(&secret.0).expect("HMAC can take key of any size");
34        mac.update(bytes);
35        mac.finalize().into_bytes().to_vec()
36    }
37}
38
39impl Hmac for Algorithm {
40    fn hmac(&self, secret: Key, bytes: &[u8]) -> Vec<u8> {
41        match self {
42            Algorithm::Sha1 => Self::hmac_oid::<Sha1>(secret, bytes),
43            Algorithm::Sha256 => Self::hmac_oid::<Sha256>(secret, bytes),
44            Algorithm::Sha512 => Self::hmac_oid::<Sha512>(secret, bytes),
45        }
46    }
47}