diff options
author | Daniel Schadt <kingdread@gmx.de> | 2025-04-11 10:13:11 +0200 |
---|---|---|
committer | Daniel Schadt <kingdread@gmx.de> | 2025-04-11 10:13:11 +0200 |
commit | 170d9413b4d5d4b2c43f53343be4e43350e3e83f (patch) | |
tree | bea54572f654cc639d2bd2bd12a80355243ecf7b /src | |
parent | eecd8fb23edb86223f8e3c6ac18df7c1dc596151 (diff) | |
download | zears-170d9413b4d5d4b2c43f53343be4e43350e3e83f.tar.gz zears-170d9413b4d5d4b2c43f53343be4e43350e3e83f.tar.bz2 zears-170d9413b4d5d4b2c43f53343be4e43350e3e83f.zip |
move hot comparison out of E::eval
Most of the time, especially in the hot loop, we're falling into the
lower branch with j != -1. Doing this check in advance gives around 10%
speedup.
Now, the code for j == -1 is directly in e(), as we never use E::new(-1,
...) anyway.
Diffstat (limited to 'src')
-rw-r--r-- | src/lib.rs | 72 |
1 files changed, 22 insertions, 50 deletions
@@ -717,79 +717,51 @@ fn aez_prf(aez: &Aez, tweaks: Tweak, buffer: &mut [u8]) { /// temporary values and makes it much faster to compute E_K^{j, i+1}, E_K^{j, i+2}, ... struct E<'a> { aez: &'a Aez, - state: Estate, -} - -#[derive(Clone, Debug)] -enum Estate { - Neg { - i: u32, - }, - Pos { - i: u32, - kj_t_j: Block, - ki_p_i: Block, - }, + i: u32, + kj_t_j: Block, + ki_p_i: Block, } impl<'a> E<'a> { /// Create a new "suspended" computation of E_K^{j,i}. fn new(j: i32, i: u32, aez: &'a Aez) -> Self { - let state = if j == -1 { - Estate::Neg { i } - } else { - let j: u32 = j.try_into().expect("j was negative"); - let exponent = if i % 8 == 0 { i / 8 } else { i / 8 + 1 }; - Estate::Pos { - i, - kj_t_j: aez.key_j * j, - ki_p_i: aez.key_i.exp(exponent), - } - }; + assert!(j >= 0); + let j: u32 = j.try_into().expect("j was negative"); + let exponent = if i % 8 == 0 { i / 8 } else { i / 8 + 1 }; E { aez, - state, + i, + kj_t_j: aez.key_j * j, + ki_p_i: aez.key_i.exp(exponent), } } /// Complete this computation to evaluate E_K^{j,i}(block). fn eval(&self, block: Block) -> Block { - match self.state { - Estate::Neg { i } => { - let delta = self.aez.key_l * i; - self.aez.aes.aes10(block ^ delta) - } - Estate::Pos { i, kj_t_j, ki_p_i } => { - let delta = kj_t_j ^ ki_p_i ^ self.aez.key_l_multiples[i as usize % 8]; - self.aez.aes.aes4(block ^ delta) - } - } + let delta = self.kj_t_j ^ self.ki_p_i ^ self.aez.key_l_multiples[self.i as usize % 8]; + self.aez.aes.aes4(block ^ delta) } /// Advance this computation by going from i to i+1. /// /// Afterwards, this computation will represent E_K^{j, i+1} fn advance(&mut self) { - self.state = match self.state { - Estate::Neg { i } => Estate::Neg { i: i + 1 }, - Estate::Pos { i, kj_t_j, ki_p_i } => { - // We need to advance ki_p_i if exponent = old_exponent + 1 - // This happens exactly when the old exponent was just a multiple of 8, because the - // next exponent is then not a multiple anymore and will be rounded *up*. - let ki_p_i = if i % 8 == 0 { ki_p_i * 2 } else { ki_p_i }; - Estate::Pos { - i: i + 1, - kj_t_j, - ki_p_i, - } - } - } + // We need to advance ki_p_i if exponent = old_exponent + 1 + // This happens exactly when the old exponent was just a multiple of 8, because the + // next exponent is then not a multiple anymore and will be rounded *up*. + if self.i % 8 == 0 { self.ki_p_i = self.ki_p_i * 2 }; + self.i += 1; } } /// Shorthand to get E_K^{j,i}(block) fn e(j: i32, i: u32, aez: &Aez, block: Block) -> Block { - E::new(j, i, aez).eval(block) + if j == -1 { + let delta = aez.key_l * i; + aez.aes.aes10(block ^ delta) + } else { + E::new(j, i, aez).eval(block) + } } fn split_key(key: &Key) -> (Block, Block, Block) { |