Skip to content

Commit

Permalink
digest: add FixedOutputDirty trait + finalize_into*
Browse files Browse the repository at this point in the history
Adds a `FixedOutputDirty` trait which writes the digest output to a
provided byte array, but does not reset the internal state. This is
intended for implementations to use in order to ensure that they are
not reset in the event the instance is consumed.

Also adds a set of `finalize_into` and `finalize_into_reset` methods to
`FixedOutput` whhich also write their input into a provided byte array,
and changes the existing `finalize_fixed` (and newly added
`finalize_fixed_reset`) methods to have a default implementation which
returns a byte array allocated on the stack.

Finally, adds a blanket impl of `FixedOutput` for `FixedOutputDirty` +
`Reset` types which handles safely invoking the underlying
implementation by either consuming the instance (avoiding a reset)
or borrowing the hasher, obtaining the output, and resetting.
  • Loading branch information
tarcieri committed Jun 9, 2020
1 parent e312a03 commit daf6cfb
Showing 1 changed file with 53 additions and 2 deletions.
55 changes: 53 additions & 2 deletions digest/src/lib.rs
Expand Up @@ -79,8 +79,59 @@ pub trait FixedOutput {
/// Output size for fixed output digest
type OutputSize: ArrayLength<u8>;

/// Retrieve result and consume hasher instance.
fn finalize_fixed(self) -> GenericArray<u8, Self::OutputSize>;
/// Write result into provided array and consume the hasher instance.
fn finalize_into(self, out: &mut GenericArray<u8, Self::OutputSize>);

/// Write result into provided array and reset the hasher instance.
fn finalize_into_reset(&mut self, out: &mut GenericArray<u8, Self::OutputSize>);

/// Retrieve result and consume the hasher instance.
#[inline]
fn finalize_fixed(self) -> GenericArray<u8, Self::OutputSize>
where
Self: Sized,
{
let mut out = Default::default();
self.finalize_into(&mut out);
out
}

/// Retrieve result and reset the hasher instance.
#[inline]
fn finalize_fixed_reset(&mut self) -> GenericArray<u8, Self::OutputSize> {
let mut out = Default::default();
self.finalize_into_reset(&mut out);
out
}
}

/// Trait for fixed-output digest implementations to use to retrieve the
/// hash output.
pub trait FixedOutputDirty {
/// Output size for fixed output digest
type OutputSize: ArrayLength<u8>;

/// Retrieve result into provided buffer and leave hasher in a dirty state.
/// Usage of this method in user code is discouraged, prefer `finalize_fixed`
/// or `finalize_fixed_reset`.
///
/// Implementations should panic if this is called twice without resetting.
fn finalize_into_dirty(&mut self, out: &mut GenericArray<u8, Self::OutputSize>);
}

impl<D: FixedOutputDirty + Reset> FixedOutput for D {
type OutputSize = D::OutputSize;

#[inline]
fn finalize_into(mut self, out: &mut GenericArray<u8, Self::OutputSize>) {
self.finalize_into_dirty(out);
}

#[inline]
fn finalize_into_reset(&mut self, out: &mut GenericArray<u8, Self::OutputSize>) {
self.finalize_into_dirty(out);
self.reset();
}
}

/// Trait for returning digest result with the variable size
Expand Down

0 comments on commit daf6cfb

Please sign in to comment.