Function blake2b_simd::update4
source · pub fn update4(
state0: &mut State,
state1: &mut State,
state2: &mut State,
state3: &mut State,
input0: &[u8],
input1: &[u8],
input2: &[u8],
input3: &[u8]
)Expand description
Update four State objects at the same time.
Without SIMD, this is no different from making four separate calls to update. However, with
SIMD, it can be implemented more efficiently. AVX2 is very good at doing four things in
parallel, and the regular BLAKE2b implementation is able to take advantage of that somewhat,
but actually hashing four separate inputs at once is a more natural fit for the instruction
set. This parallel implementation shares its underlying machinery with BLAKE2bp, and like
BLAKE2bp is has about double the throughput of serial BLAKE2b.
update4 can only operate in parallel as long as all four inputs still have bytes left. Once
one or more of the inputs are exhausted, it falls back to regular serial hashing for the rest.
To get the best throughput, try make your inputs roughly the same length.
Note that unlike BLAKE2bp, which is specifically designed to have four lanes, parallel BLAKE2b
isn’t tied to any particular number of lanes. When the AVX-512 instruction set becomes more
widespread, for example, we could add an update8 implementation to take full advantage of it.
Example
use blake2b_simd::{blake2b, finalize4, update4, State};
let mut state0 = State::new();
let mut state1 = State::new();
let mut state2 = State::new();
let mut state3 = State::new();
update4(
&mut state0,
&mut state1,
&mut state2,
&mut state3,
b"foo",
b"bar",
b"baz",
b"bing",
);
let parallel_hashes = finalize4(&mut state0, &mut state1, &mut state2, &mut state3);
let serial_hashes = [
blake2b(b"foo"),
blake2b(b"bar"),
blake2b(b"baz"),
blake2b(b"bing"),
];
assert_eq!(serial_hashes, parallel_hashes);