Skip to content

Commit 5edffca

Browse files
authored
Migrate to const blobby parsing (#710)
1 parent b75762d commit 5edffca

File tree

6 files changed

+106
-65
lines changed

6 files changed

+106
-65
lines changed

Cargo.lock

Lines changed: 14 additions & 18 deletions
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

Cargo.toml

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -33,3 +33,9 @@ opt-level = 2
3333
sha1 = { path = "sha1" }
3434
sha3 = { path = "sha3" }
3535
whirlpool = { path = "whirlpool" }
36+
37+
# https://github.com/RustCrypto/utils/pull/1187
38+
blobby = { git = "https://github.com/RustCrypto/utils" }
39+
# https://github.com/RustCrypto/traits/pull/1916
40+
digest = { git = "https://github.com/RustCrypto/traits" }
41+
block-buffer = { git = "https://github.com/RustCrypto/utils" }

ascon-hash/src/lib.rs

Lines changed: 24 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -73,6 +73,18 @@ struct HashCore<P: HashParameters> {
7373
phantom: PhantomData<P>,
7474
}
7575

76+
#[cfg(feature = "zeroize")]
77+
impl<P: HashParameters> digest::zeroize::ZeroizeOnDrop for HashCore<P> {}
78+
79+
#[allow(dead_code)]
80+
#[cfg(feature = "zeroize")]
81+
const _: () = {
82+
// State is the only field in AsconCore
83+
fn check_core(v: &State) {
84+
let _ = v as &dyn digest::zeroize::ZeroizeOnDrop;
85+
}
86+
};
87+
7688
impl<P: HashParameters> HashCore<P> {
7789
fn absorb_block(&mut self, block: &[u8; 8]) {
7890
self.state[0] ^= u64::from_le_bytes(*block);
@@ -195,6 +207,18 @@ impl SerializableState for AsconCore {
195207
}
196208
}
197209

210+
#[cfg(feature = "zeroize")]
211+
impl digest::zeroize::ZeroizeOnDrop for AsconCore {}
212+
213+
#[allow(dead_code)]
214+
#[cfg(feature = "zeroize")]
215+
const _: () = {
216+
// HashCore is the only field in AsconCore
217+
fn check_core(v: &HashCore<Parameters>) {
218+
let _ = v as &dyn digest::zeroize::ZeroizeOnDrop;
219+
}
220+
};
221+
198222
/// Ascon XOF
199223
#[derive(Clone, Debug, Default)]
200224
pub struct AsconXofCore {

blake2/tests/mac.rs

Lines changed: 6 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -1,10 +1,12 @@
11
#[cfg(not(feature = "reset"))]
2-
use digest::new_mac_test as new_test;
2+
use digest::dev::mac_test as test_fn;
33
#[cfg(feature = "reset")]
4-
use digest::new_resettable_mac_test as new_test;
4+
use digest::dev::reset_mac_test as test_fn;
55

6-
new_test!(blake2b_mac, "blake2b/mac", blake2::Blake2bMac512);
7-
new_test!(blake2s_mac, "blake2s/mac", blake2::Blake2sMac256);
6+
use digest::new_mac_test;
7+
8+
new_mac_test!(blake2b_mac, "blake2b/mac", blake2::Blake2bMac512, test_fn);
9+
new_mac_test!(blake2s_mac, "blake2s/mac", blake2::Blake2sMac256, test_fn);
810

911
#[test]
1012
fn blake2b_new_test() {

sha3/tests/cshake.rs

Lines changed: 35 additions & 34 deletions
Original file line numberDiff line numberDiff line change
@@ -1,20 +1,31 @@
1-
use core::fmt::Debug;
21
use digest::{CustomizedInit, ExtendableOutputReset};
32

4-
pub(crate) fn cshake_reset_test<D, F>(input: &[u8], output: &[u8], new: F) -> Option<&'static str>
3+
#[derive(Debug, Clone, Copy)]
4+
pub struct TestVector {
5+
pub customization: &'static [u8],
6+
pub input: &'static [u8],
7+
pub output: &'static [u8],
8+
}
9+
10+
pub(crate) fn cshake_reset_test<D>(
11+
&TestVector {
12+
customization,
13+
input,
14+
output,
15+
}: &TestVector,
16+
) -> Result<(), &'static str>
517
where
6-
D: ExtendableOutputReset + Debug + Clone,
7-
F: Fn() -> D,
18+
D: CustomizedInit + ExtendableOutputReset + Clone,
819
{
9-
let mut hasher = new();
20+
let mut hasher = D::new_customized(customization);
1021
let mut buf = [0u8; 1024];
1122
let buf = &mut buf[..output.len()];
1223
// Test that it works when accepting the message all at once
1324
hasher.update(input);
1425
let mut hasher2 = hasher.clone();
1526
hasher.finalize_xof_into(buf);
1627
if buf != output {
17-
return Some("whole message");
28+
return Err("whole message");
1829
}
1930
buf.iter_mut().for_each(|b| *b = 0);
2031

@@ -23,67 +34,57 @@ where
2334
hasher2.update(input);
2435
hasher2.finalize_xof_reset_into(buf);
2536
if buf != output {
26-
return Some("whole message after reset");
37+
return Err("whole message after reset");
2738
}
2839
buf.iter_mut().for_each(|b| *b = 0);
2940

3041
// Test that it works when accepting the message in chunks
3142
for n in 1..core::cmp::min(17, input.len()) {
32-
let mut hasher = new();
43+
let mut hasher = D::new_customized(customization);
3344
for chunk in input.chunks(n) {
3445
hasher.update(chunk);
3546
hasher2.update(chunk);
3647
}
3748
hasher.finalize_xof_into(buf);
3849
if buf != output {
39-
return Some("message in chunks");
50+
return Err("message in chunks");
4051
}
4152
buf.iter_mut().for_each(|b| *b = 0);
4253

4354
hasher2.finalize_xof_reset_into(buf);
4455
if buf != output {
45-
return Some("message in chunks");
56+
return Err("message in chunks");
4657
}
4758
buf.iter_mut().for_each(|b| *b = 0);
4859
}
4960

50-
None
61+
Ok(())
5162
}
5263

5364
macro_rules! new_cshake_test {
54-
($name:ident, $test_name:expr, $hasher:ty, $test_func:ident $(,)?) => {
65+
($name:ident, $test_name:expr, $hasher:ty $(,)?) => {
5566
#[test]
5667
fn $name() {
57-
use digest::dev::blobby::Blob3Iterator;
58-
let data = include_bytes!(concat!("data/", $test_name, ".blb"));
68+
digest::dev::blobby::parse_into_structs!(
69+
include_bytes!(concat!("data/", $test_name, ".blb"));
70+
static TEST_VECTORS: &[TestVector { customization, input, output }];
71+
);
5972

60-
for (i, row) in Blob3Iterator::new(data).unwrap().enumerate() {
61-
let [customization, input, output] = row.unwrap();
62-
if let Some(desc) =
63-
$test_func(input, output, || <$hasher>::new_customized(customization))
73+
for (i, tv) in TEST_VECTORS.iter().enumerate() {
74+
if let Err(reason) =
75+
cshake_reset_test::<$hasher>(tv)
6476
{
6577
panic!(
6678
"\n\
67-
Failed test №{}: {}\n\
68-
input:\t{:?}\n\
69-
output:\t{:?}\n",
70-
i, desc, input, output,
79+
Failed test #{i}\n\
80+
reason:\t{reason}
81+
test vector:\t{tv:?}\n"
7182
);
7283
}
7384
}
7485
}
7586
};
7687
}
7788

78-
new_cshake_test!(
79-
cshake128_reset,
80-
"cshake128",
81-
sha3::CShake128,
82-
cshake_reset_test
83-
);
84-
new_cshake_test!(
85-
cshake256_reset,
86-
"cshake256",
87-
sha3::CShake256,
88-
cshake_reset_test
89-
);
89+
new_cshake_test!(cshake128_reset, "cshake128", sha3::CShake128);
90+
new_cshake_test!(cshake256_reset, "cshake256", sha3::CShake256);

sha3/tests/turboshake.rs

Lines changed: 21 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -1,11 +1,19 @@
11
use core::fmt::Debug;
22
use digest::ExtendableOutput;
33

4+
#[derive(Debug, Clone, Copy)]
5+
pub struct TestVector {
6+
pub input: &'static [u8],
7+
pub input_pattern_length: &'static [u8],
8+
pub output: &'static [u8],
9+
pub truncate_output: &'static [u8],
10+
}
11+
412
pub(crate) fn turbo_shake_test<D>(
513
input: &[u8],
614
output: &[u8],
715
truncate_output: usize,
8-
) -> Option<&'static str>
16+
) -> Result<(), &'static str>
917
where
1018
D: ExtendableOutput + Default + Debug + Clone,
1119
{
@@ -17,7 +25,7 @@ where
1725
let mut hasher2 = hasher.clone();
1826
hasher.finalize_xof_into(buf);
1927
if &buf[truncate_output..] != output {
20-
return Some("whole message");
28+
return Err("whole message");
2129
}
2230
buf.iter_mut().for_each(|b| *b = 0);
2331

@@ -30,23 +38,27 @@ where
3038
}
3139
hasher.finalize_xof_into(buf);
3240
if &buf[truncate_output..] != output {
33-
return Some("message in chunks");
41+
return Err("message in chunks");
3442
}
3543
buf.iter_mut().for_each(|b| *b = 0);
3644
}
3745

38-
None
46+
Ok(())
3947
}
4048

4149
macro_rules! new_turbo_shake_test {
4250
($name:ident, $test_name:expr, $hasher:ty, $test_func:ident $(,)?) => {
4351
#[test]
4452
fn $name() {
45-
use digest::dev::blobby::Blob4Iterator;
46-
let data = include_bytes!(concat!("data/", $test_name, ".blb"));
53+
digest::dev::blobby::parse_into_structs!(
54+
include_bytes!(concat!("data/", $test_name, ".blb"));
55+
static TEST_VECTORS: &[TestVector {
56+
input, input_pattern_length, output, truncate_output
57+
}];
58+
);
4759

48-
for (i, row) in Blob4Iterator::new(data).unwrap().enumerate() {
49-
let [input, input_pattern_length, output, truncate_output] = row.unwrap();
60+
for (i, tv) in TEST_VECTORS.iter().enumerate() {
61+
let &TestVector { input, input_pattern_length, output, truncate_output } = tv;
5062

5163
let input = if (input_pattern_length.len() == 0) {
5264
input.to_vec()
@@ -70,7 +82,7 @@ macro_rules! new_turbo_shake_test {
7082

7183
println!("before func: {:?}", truncate_output.len());
7284

73-
if let Some(desc) = $test_func::<$hasher>(
85+
if let Err(desc) = $test_func::<$hasher>(
7486
&input,
7587
output,
7688
u64::from_be_bytes(truncate_output.try_into().unwrap())

0 commit comments

Comments
 (0)