Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Implement SerializableState for hashes #574

Merged
merged 19 commits into from
Mar 19, 2024
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
7 changes: 3 additions & 4 deletions Cargo.lock

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

4 changes: 4 additions & 0 deletions Cargo.toml
Original file line number Diff line number Diff line change
Expand Up @@ -26,3 +26,7 @@ members = [

[profile.dev]
opt-level = 2

[patch.crates-io]
# https://github.com/RustCrypto/traits/pull/1537 - Unreleased
digest = { git = "https://github.com/RustCrypto/traits.git" }
2 changes: 1 addition & 1 deletion blake2/tests/mac.rs
Original file line number Diff line number Diff line change
Expand Up @@ -12,7 +12,7 @@ fn blake2b_new_test() {

fn run<T: Mac + KeyInit>(key: &[u8]) {
const DATA: &[u8] = &[42; 300];
let res1 = T::new(Array::from_slice(key))
let res1 = T::new(&Array::try_from(key).unwrap())
.chain_update(DATA)
.finalize()
.into_bytes();
Expand Down
10 changes: 8 additions & 2 deletions fsb/src/lib.rs
Original file line number Diff line number Diff line change
Expand Up @@ -12,7 +12,7 @@
#[macro_use]
mod macros;

use core::fmt;
use core::{fmt, ops::Add};
pub use digest::{self, Digest};

// Double check this contains all values in the reference implementation
Expand All @@ -24,7 +24,8 @@ use digest::{
AlgorithmName, Block, BlockSizeUser, Buffer, BufferKindUser, CoreWrapper, FixedOutputCore,
OutputSizeUser, Reset, UpdateCore,
},
typenum::Unsigned,
crypto_common::hazmat::{DeserializeStateError, SerializableState, SerializedState},
typenum::{Unsigned, U8},
HashMarker, Output,
};

Expand All @@ -38,6 +39,7 @@ fsb_impl!(
160,
U60,
U20,
U80,
5 << 18,
80,
640,
Expand All @@ -54,6 +56,7 @@ fsb_impl!(
224,
U84,
U28,
U112,
7 << 18,
112,
896,
Expand All @@ -70,6 +73,7 @@ fsb_impl!(
256,
U96,
U32,
U128,
1 << 21,
128,
1024,
Expand All @@ -86,6 +90,7 @@ fsb_impl!(
384,
U115,
U48,
U184,
23 << 16,
184,
1472,
Expand All @@ -102,6 +107,7 @@ fsb_impl!(
512,
U155,
U64,
U248,
31 << 16,
248,
1984,
Expand Down
33 changes: 30 additions & 3 deletions fsb/src/macros.rs
Original file line number Diff line number Diff line change
@@ -1,9 +1,9 @@
macro_rules! fsb_impl {
(
$full_state:ident, $state:ident, $state_num:expr, $blocksize:ident, $outputsize:ident, $n:expr, $w:expr,
$r:expr, $p:expr, $s:expr, $full_doc:expr, $doc:expr,
$full_state:ident, $state:ident, $state_num:expr, $blocksize:ident, $outputsize:ident, $statesize:ident,
$n:expr, $w:expr, $r:expr, $p:expr, $s:expr, $full_doc:expr, $doc:expr,
) => {
use digest::consts::{$blocksize, $outputsize};
use digest::consts::{$blocksize, $outputsize, $statesize};

#[derive(Clone)]
#[doc=$doc]
Expand Down Expand Up @@ -95,6 +95,33 @@ macro_rules! fsb_impl {
#[cfg(feature = "zeroize")]
impl ZeroizeOnDrop for $state {}

impl SerializableState for $state {
type SerializedStateSize = <$statesize as Add<U8>>::Output;

fn serialize(&self) -> SerializedState<Self> {
let mut serialized_state = SerializedState::<Self>::default();

serialized_state[..self.state.len()].copy_from_slice(&self.state[..]);
serialized_state[self.state.len()..]
.copy_from_slice(&self.blocks_len.to_le_bytes());

serialized_state
}

fn deserialize(
serialized_state: &SerializedState<Self>,
) -> Result<Self, DeserializeStateError> {
let (serialized_state, serialized_block_len) =
serialized_state.split::<$statesize>();

let mut state = [0; $r / 8];
state.copy_from_slice(serialized_state.as_ref());

let blocks_len = u64::from_le_bytes(*serialized_block_len.as_ref());
Ok(Self { state, blocks_len })
}
}

impl $state {
const SIZE_OUTPUT_COMPRESS: usize = $r / 8;
const SIZE_INPUT_COMPRESS: usize = $s / 8;
Expand Down
129 changes: 127 additions & 2 deletions fsb/tests/mod.rs
Original file line number Diff line number Diff line change
@@ -1,5 +1,7 @@
use digest::dev::{feed_rand_16mib, fixed_reset_test};
use digest::new_test;
use digest::{
dev::{feed_rand_16mib, fixed_reset_test},
hash_serialization_test, new_test,
};
use fsb::{Digest, Fsb160, Fsb224, Fsb256, Fsb384, Fsb512};
use hex_literal::hex;

Expand All @@ -9,6 +11,129 @@ new_test!(fsb256_main, "fsb256", Fsb256, fixed_reset_test);
new_test!(fsb384_main, "fsb384", Fsb384, fixed_reset_test);
new_test!(fsb512_main, "fsb512", Fsb512, fixed_reset_test);

#[rustfmt::skip]
hash_serialization_test!(
fsb160_serialization,
Fsb160,
hex!("
e269a086505e9493fa92ed509f6cdce8
51dd58654160a8c8a499a953a479c169
d46c0576d8e7b262341087f58eb3dc9d
3002451f8f0d484cbdc8b342afef13e5
4f2fce12e400eca0a6bc0b8837f999c3
01000000000000000113000000000000
00000000000000000000000000000000
00000000000000000000000000000000
00000000000000000000000000000000
0000000000
")
);
#[rustfmt::skip]
hash_serialization_test!(
fsb224_serialization,
Fsb224,
hex!("
bfba3bbd79050b4428d239ec4eb25277
b228898bd26c04ccf11e052944e72b61
aae3f1a0a6cdb862d87fac21fefb1dc1
4074cfc45d8994087dc70d1d5308b6b1
f68f6eea5d886904dfcab198e62f6c97
67ae365fc648b1bb7d00f65ff276373a
7a1b4d80efdd7af5fce3b0e93371172a
01000000000000000113000000000000
00000000000000000000000000000000
00000000000000000000000000000000
00000000000000000000000000000000
00000000000000000000000000000000
00000000000000000000000000
")
);

#[rustfmt::skip]
hash_serialization_test!(
fsb256_serialization,
Fsb256,
hex!("
6c4fef5401baa1825e74fe2a150dd746
55ba10d8fa2db4ee3e6925de2cf4a83a
5121e2ded528f92613ec858045c1bdd1
5a11ce8bd4df1a3f409dfc9d1025d333
360f30a342f417018fcf0ff1c5dddb04
2a18453d707d27721e57fd182d932945
89a1c3ef007e6bb3b59f2a361094e21d
6c72d213545a6612a2adc547968a03e9
01000000000000000113000000000000
00000000000000000000000000000000
00000000000000000000000000000000
00000000000000000000000000000000
00000000000000000000000000000000
00000000000000000000000000000000
000000000000000000
")
);

#[rustfmt::skip]
hash_serialization_test!(
fsb384_serialization,
Fsb384,
hex!("
41825b73ae6b5cdc91b8b70723dc1f92
97fec62f09c17c75a2326e3d7664efb5
df1104db5c711016d161187f3174ef77
f5e0545c917d01375537d15cf90c838d
2f5fd5a294c7012d80a0f6a6240f90f9
a6976812ec60fdd35bbc1a064287308e
1d916cb4d59c02b19ab2d20e1b9b2acb
e826c4d0022db322e3314fe0cf232cdd
75b61c653bf30569ca76dd11bd032d03
bc83a0e59964eb5dd77a22d0a459de63
ab5ff6ce1207a9daed690c36399f7306
43a1628e0f33650a0100000000000000
01130000000000000000000000000000
00000000000000000000000000000000
00000000000000000000000000000000
00000000000000000000000000000000
00000000000000000000000000000000
00000000000000000000000000000000
00000000000000000000000000000000
00000000
")
);

#[rustfmt::skip]
hash_serialization_test!(
fsb512_serialization,
Fsb512,
hex!("
4feff733b532b0767d0bbe8804f60ebc
bbf33aa6796e608d37e6e24dcf216636
31312286c6efa794b237f05df2838526
cb5120291a53566bb784ff32d2ea5464
693cd68fc52a37375160c0a4f4b8dae8
06703a98720180c4abaa2c195a6ede59
ed68fc5caae6172003ad9195d7ae7747
10d7a0c46772a7216e553a39dbeac282
fa2848e7038eec7c78f7da35db4cf8ea
d35f2f140ec49203f1d3afe24fe4100a
9d0cc5fdb1e964ed48fe786e2bfdabe4
70c148f65c67c21cc6794b8e1eb90e6a
39800334a2016e2081f5a458fcd348d8
778dc4090066f3906b835a1283c97569
4e1dc38fef18dd35d2d4f283d0bc1502
db72a91871a23bc40100000000000000
01130000000000000000000000000000
00000000000000000000000000000000
00000000000000000000000000000000
00000000000000000000000000000000
00000000000000000000000000000000
00000000000000000000000000000000
00000000000000000000000000000000
00000000000000000000000000000000
00000000000000000000000000000000
000000000000000000000000
")
);

#[test]
fn fsb160_rand() {
let mut h = Fsb160::new();
Expand Down
48 changes: 47 additions & 1 deletion gost94/src/gost94_core.rs
Original file line number Diff line number Diff line change
@@ -1,12 +1,14 @@
#![allow(clippy::many_single_char_names)]
use core::fmt;
use digest::{
array::Array,
block_buffer::Eager,
core_api::{
AlgorithmName, Block as TBlock, BlockSizeUser, Buffer, BufferKindUser, FixedOutputCore,
OutputSizeUser, Reset, UpdateCore,
},
typenum::{Unsigned, U32},
crypto_common::hazmat::{DeserializeStateError, SerializableState, SerializedState},
typenum::{Unsigned, U32, U96},
HashMarker, Output,
};

Expand Down Expand Up @@ -290,3 +292,47 @@ impl<P: Gost94Params> Drop for Gost94Core<P> {

#[cfg(feature = "zeroize")]
impl<P: Gost94Params> ZeroizeOnDrop for Gost94Core<P> {}

impl<P: Gost94Params> SerializableState for Gost94Core<P> {
type SerializedStateSize = U96;

fn serialize(&self) -> SerializedState<Self> {
let serialized_h = Array::<_, U32>::from(self.h);

let mut serialized_n = Array::<_, U32>::default();
for (val, chunk) in self.n.iter().zip(serialized_n.chunks_exact_mut(8)) {
chunk.copy_from_slice(&val.to_le_bytes());
}

let mut serialized_sigma = Array::<_, U32>::default();
for (val, chunk) in self.sigma.iter().zip(serialized_sigma.chunks_exact_mut(8)) {
chunk.copy_from_slice(&val.to_le_bytes());
}

serialized_h.concat(serialized_n).concat(serialized_sigma)
}

fn deserialize(
serialized_state: &SerializedState<Self>,
) -> Result<Self, DeserializeStateError> {
let (serialized_h, remaining_buffer) = serialized_state.split::<U32>();

let (serialized_n, serialized_sigma) = remaining_buffer.split::<U32>();
let mut n = [0; 4];
for (val, chunk) in n.iter_mut().zip(serialized_n.chunks_exact(8)) {
*val = u64::from_le_bytes(chunk.try_into().unwrap());
}

let mut sigma = [0; 4];
for (val, chunk) in sigma.iter_mut().zip(serialized_sigma.chunks_exact(8)) {
*val = u64::from_le_bytes(chunk.try_into().unwrap());
}

Ok(Self {
h: serialized_h.into(),
n,
sigma,
_m: core::marker::PhantomData,
})
}
}
Loading
Loading