version bumps, MAX_RECV_SEEN patch, FIPS interop, doc updates
Some checks failed
CI / lint (push) Failing after 52s
CI / test-python (push) Successful in 1m40s
CI / test (push) Has been cancelled
CI / test-wasm (push) Has been cancelled
CI / publish-wasm (push) Has been cancelled
CI / miri (push) Has been cancelled
CI / fuzz-regression (push) Has been cancelled
CI / build (push) Has been cancelled
CI / publish (push) Has been cancelled
CI / publish-python (push) Has been cancelled
CI / test-zig (push) Has been cancelled

This commit is contained in:
Kamal Tufekcic 2026-09-09 00:49:53 +03:00
commit 6853b30036
No known key found for this signature in database
16 changed files with 582 additions and 435 deletions

View file

@ -16,10 +16,19 @@ use sha3::Sha3_256;
/// # Security
///
/// The caller is responsible for zeroizing the `out` buffer when the derived
/// key material is no longer needed. The `hkdf` crate's internal PRK is
/// **not** zeroized on drop (`hkdf 0.13.0-rc.5` has no `zeroize` feature).
/// Mitigation: `Hkdf` is a short-lived local — PRK lifetime is bounded to
/// this function scope, and `panic = "abort"` prevents unwinding.
/// key material is no longer needed.
///
/// What the dependencies zeroize, verified against the pinned sources
/// (`hkdf 0.13.0-rc.5`, `hmac 0.13.0-rc.5`, `sha3 0.11.0-rc.7`,
/// `digest 0.11.0-rc.11`, `block-buffer 0.11.0`, all with their `zeroize`
/// features resolved on): dropping the `Hkdf` zeroizes the PRK-keyed HMAC
/// state — both SHA3 cores through `sha3`'s `Drop` and the wrapper's block
/// buffer through `block-buffer`'s. `hkdf` itself has no `zeroize` feature
/// and leaves three plain stack copies behind: the raw 32-byte PRK that
/// `Hkdf::new` extracts and discards, the `key ^ OPAD` block that
/// `HmacCore::new_from_slice` builds in a local, and the last output block
/// that `expand` keeps in a local. All three are bounded to this function's
/// frame, and `panic = "abort"` prevents unwinding past it.
pub fn hkdf_sha3_256(salt: &[u8], ikm: &[u8], info: &[u8], out: &mut [u8]) -> Result<()> {
if out.is_empty() {
return Err(Error::InvalidLength {