Skip to content

Commit

Permalink
aes: tweak weak key test
Browse files Browse the repository at this point in the history
  • Loading branch information
newpavlov committed Feb 14, 2025
1 parent 717c382 commit 8e12849
Show file tree
Hide file tree
Showing 9 changed files with 72 additions and 47 deletions.
7 changes: 0 additions & 7 deletions Cargo.lock

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

1 change: 0 additions & 1 deletion aes/Cargo.toml
Original file line number Diff line number Diff line change
Expand Up @@ -15,7 +15,6 @@ categories = ["cryptography", "no-std"]
[dependencies]
cfg-if = "1"
cipher = "=0.5.0-pre.7"
subtle = { version = "2.6", default-features = false }
zeroize = { version = "1.5.6", optional = true, default-features = false, features = [
"aarch64",
] }
Expand Down
9 changes: 6 additions & 3 deletions aes/src/armv8.rs
Original file line number Diff line number Diff line change
Expand Up @@ -110,8 +110,9 @@ macro_rules! define_aes_impl {
Self { encrypt, decrypt }
}

#[inline]
fn weak_key_test(key: &Key<Self>) -> Result<(), WeakKeyError> {
weak_key_test!(key, Self)
crate::weak_key_test(&key.0)
}
}

Expand Down Expand Up @@ -199,8 +200,9 @@ macro_rules! define_aes_impl {
Self { backend }
}

#[inline]
fn weak_key_test(key: &Key<Self>) -> Result<(), WeakKeyError> {
weak_key_test!(key, Self)
crate::weak_key_test(&key.0)
}
}

Expand Down Expand Up @@ -265,8 +267,9 @@ macro_rules! define_aes_impl {
Self { backend }
}

#[inline]
fn weak_key_test(key: &Key<Self>) -> Result<(), WeakKeyError> {
weak_key_test!(key, Self)
crate::weak_key_test(&key.0)
}
}

Expand Down
9 changes: 6 additions & 3 deletions aes/src/autodetect.rs
Original file line number Diff line number Diff line change
Expand Up @@ -105,8 +105,9 @@ macro_rules! define_aes_impl {
Self { inner, token }
}

#[inline]
fn weak_key_test(key: &Key<Self>) -> Result<(), WeakKeyError> {
weak_key_test!(key, Self)
crate::weak_key_test(&key.0)
}
}

Expand Down Expand Up @@ -226,8 +227,9 @@ macro_rules! define_aes_impl {
Self { inner, token }
}

#[inline]
fn weak_key_test(key: &Key<Self>) -> Result<(), WeakKeyError> {
weak_key_test!(key, Self)
crate::weak_key_test(&key.0)
}
}

Expand Down Expand Up @@ -357,8 +359,9 @@ macro_rules! define_aes_impl {
Self { inner, token }
}

#[inline]
fn weak_key_test(key: &Key<Self>) -> Result<(), WeakKeyError> {
weak_key_test!(key, Self)
crate::weak_key_test(&key.0)
}
}

Expand Down
32 changes: 31 additions & 1 deletion aes/src/lib.rs
Original file line number Diff line number Diff line change
Expand Up @@ -143,11 +143,41 @@ cfg_if! {
}

pub use cipher;
use cipher::{array::Array, consts::U16};
use cipher::{array::Array, consts::U16, crypto_common::WeakKeyError};

/// 128-bit AES block
pub type Block = Array<u8, U16>;

/// Check if any bit of the upper half of the key is set.
///
/// This follows the interpretation laid out in section `11.4.10.4 Reject of weak keys`
/// from the [TPM specification][0]:
/// ```text
/// In the case of AES, at least one bit in the upper half of the key must be set
/// ```
///
/// [0]: https://trustedcomputinggroup.org/wp-content/uploads/TPM-2.0-1.83-Part-1-Architecture.pdf#page=82
pub(crate) fn weak_key_test<const N: usize>(key: &[u8; N]) -> Result<(), WeakKeyError> {
let t = match N {
16 => u64::from_ne_bytes(key[..8].try_into().unwrap()),
24 => {
let t1 = u64::from_ne_bytes(key[..8].try_into().unwrap());
let t2 = u32::from_ne_bytes(key[8..12].try_into().unwrap());
t1 | u64::from(t2)
}
32 => {
let t1 = u64::from_ne_bytes(key[..8].try_into().unwrap());
let t2 = u64::from_ne_bytes(key[8..16].try_into().unwrap());
t1 | t2
}
_ => unreachable!(),
};
match t {
0 => Err(WeakKeyError),
_ => Ok(()),
}
}

#[cfg(test)]
mod tests {
#[cfg(feature = "zeroize")]
Expand Down
26 changes: 0 additions & 26 deletions aes/src/macros.rs
Original file line number Diff line number Diff line change
Expand Up @@ -103,29 +103,3 @@ macro_rules! impl_backends {
}
};
}

macro_rules! weak_key_test {
($key: expr, $k: ty) => {{
// Check if any bit of the upper half of the key is set
//
// This follows the interpretation laid out in section `11.4.10.4 Reject of weak keys`
// from the TPM specification:
// ```
// In the case of AES, at least one bit in the upper half of the key must be set
// ```
// See: https://trustedcomputinggroup.org/wp-content/uploads/TPM-2.0-1.83-Part-1-Architecture.pdf#page=82
let mut weak = subtle::Choice::from(0);

for v in &$key
[..(<<$k as cipher::KeySizeUser>::KeySize as cipher::typenum::Unsigned>::USIZE / 2)]
{
weak |= <_ as subtle::ConstantTimeGreater>::ct_gt(v, &0);
}

if weak.unwrap_u8() == 0 {
Err(cipher::crypto_common::WeakKeyError)
} else {
Ok(())
}
}};
}
9 changes: 6 additions & 3 deletions aes/src/ni.rs
Original file line number Diff line number Diff line change
Expand Up @@ -120,8 +120,9 @@ macro_rules! define_aes_impl {
Self { encrypt, decrypt }
}

#[inline]
fn weak_key_test(key: &Key<Self>) -> Result<(), WeakKeyError> {
weak_key_test!(key, Self)
crate::weak_key_test(&key.0)
}
}

Expand Down Expand Up @@ -199,8 +200,9 @@ macro_rules! define_aes_impl {
}
}

#[inline]
fn weak_key_test(key: &Key<Self>) -> Result<(), WeakKeyError> {
weak_key_test!(key, Self)
crate::weak_key_test(&key.0)
}
}

Expand Down Expand Up @@ -263,8 +265,9 @@ macro_rules! define_aes_impl {
$name_enc::new(key).into()
}

#[inline]
fn weak_key_test(key: &Key<Self>) -> Result<(), WeakKeyError> {
weak_key_test!(key, Self)
crate::weak_key_test(&key.0)
}
}

Expand Down
9 changes: 6 additions & 3 deletions aes/src/soft.rs
Original file line number Diff line number Diff line change
Expand Up @@ -69,8 +69,9 @@ macro_rules! define_aes_impl {
}
}

#[inline]
fn weak_key_test(key: &Key<Self>) -> Result<(), WeakKeyError> {
weak_key_test!(key, Self)
crate::weak_key_test(&key.0)
}
}

Expand Down Expand Up @@ -152,8 +153,9 @@ macro_rules! define_aes_impl {
Self { inner }
}

#[inline]
fn weak_key_test(key: &Key<Self>) -> Result<(), WeakKeyError> {
weak_key_test!(key, Self)
crate::weak_key_test(&key.0)
}
}

Expand Down Expand Up @@ -207,8 +209,9 @@ macro_rules! define_aes_impl {
Self { inner }
}

#[inline]
fn weak_key_test(key: &Key<Self>) -> Result<(), WeakKeyError> {
weak_key_test!(key, Self)
crate::weak_key_test(&key.0)
}
}

Expand Down
17 changes: 17 additions & 0 deletions aes/src/weak_key.rs
Original file line number Diff line number Diff line change
@@ -0,0 +1,17 @@
pub(crate) fn test192(key: &[u8; 24]) -> Result<(), WeakKeyError> {
let t1 = u32::from_ne_bytes(key[..4].try_into().unwrap());
let t2 = u32::from_ne_bytes(key[4..8].try_into().unwrap());
let t3 = u32::from_ne_bytes(key[8..12].try_into().unwrap());
match t1 | t2 | t3 {
0 => Err(WeakKeyError),
_ => Ok(()),
}
}

pub(crate) fn test256(key: &[u8; 32]) -> Result<(), WeakKeyError> {
let t = u128::from_ne_bytes(key[..16].try_into().unwrap());
match t {
0 => Err(WeakKeyError),
_ => Ok(()),
}
}

0 comments on commit 8e12849

Please sign in to comment.