1 //! This crate provides traits which describe functionality of cryptographic hash 2 //! functions. 3 //! 4 //! Traits in this repository are organized into high-level convenience traits, 5 //! mid-level traits which expose more fine-grained functionality, and 6 //! low-level traits intended to only be used by algorithm implementations: 7 //! 8 //! - **High-level convenience traits**: [`Digest`], [`DynDigest`]. They are wrappers 9 //! around lower-level traits for most common hash-function use-cases. 10 //! - **Mid-level traits**: [`Update`], [`BlockInput`], [`Reset`], [`FixedOutput`], 11 //! [`VariableOutput`], [`ExtendableOutput`]. These traits atomically describe 12 //! available functionality of hash function implementations. 13 //! - **Low-level traits**: [`FixedOutputDirty`], [`VariableOutputDirty`], 14 //! [`ExtendableOutputDirty`]. These traits are intended to be implemented by 15 //! low-level algorithm providers only and simplify the amount of work 16 //! implementers need to do and therefore shouldn't be used in 17 //! application-level code. 18 //! 19 //! Additionally hash functions implement traits from the standard library: 20 //! `Default`, `Clone`, `Write`. The latter is feature-gated behind `std` feature, 21 //! which is usually enabled by default by hash implementation crates. 22 //! 23 //! The [`Digest`] trait is the most commonly used trait. 24 25 #![no_std] 26 #![cfg_attr(docsrs, feature(doc_cfg))] 27 #![forbid(unsafe_code)] 28 #![doc(html_logo_url = "https://raw.githubusercontent.com/RustCrypto/meta/master/logo_small.png")] 29 #![warn(missing_docs, rust_2018_idioms)] 30 31 #[cfg(feature = "alloc")] 32 #[macro_use] 33 extern crate alloc; 34 35 #[cfg(feature = "std")] 36 extern crate std; 37 38 #[cfg(feature = "dev")] 39 #[cfg_attr(docsrs, doc(cfg(feature = "dev")))] 40 pub mod dev; 41 42 mod digest; 43 mod dyn_digest; 44 mod errors; 45 mod fixed; 46 mod variable; 47 mod xof; 48 49 pub use crate::digest::{Digest, Output}; 50 pub use crate::errors::InvalidOutputSize; 51 pub use crate::fixed::{FixedOutput, FixedOutputDirty}; 52 pub use crate::variable::{VariableOutput, VariableOutputDirty}; 53 pub use crate::xof::{ExtendableOutput, ExtendableOutputDirty, XofReader}; 54 pub use generic_array::{self, typenum::consts}; 55 56 #[cfg(feature = "alloc")] 57 pub use dyn_digest::DynDigest; 58 59 use generic_array::ArrayLength; 60 61 /// Trait for updating digest state with input data. 62 pub trait Update { 63 /// Digest input data. 64 /// 65 /// This method can be called repeatedly, e.g. for processing streaming 66 /// messages. update(&mut self, data: impl AsRef<[u8]>)67 fn update(&mut self, data: impl AsRef<[u8]>); 68 69 /// Digest input data in a chained manner. chain(mut self, data: impl AsRef<[u8]>) -> Self where Self: Sized,70 fn chain(mut self, data: impl AsRef<[u8]>) -> Self 71 where 72 Self: Sized, 73 { 74 self.update(data); 75 self 76 } 77 } 78 79 /// Trait to indicate that digest function processes data in blocks of size 80 /// `BlockSize`. 81 /// 82 /// The main usage of this trait is for implementing HMAC generically. 83 pub trait BlockInput { 84 /// Block size 85 type BlockSize: ArrayLength<u8>; 86 } 87 88 /// Trait for resetting hash instances 89 pub trait Reset { 90 /// Reset hasher instance to its initial state and return current state. reset(&mut self)91 fn reset(&mut self); 92 } 93 94 #[macro_export] 95 /// Implements `std::io::Write` trait for implementer of [`Update`] 96 macro_rules! impl_write { 97 ($hasher:ident) => { 98 #[cfg(feature = "std")] 99 impl std::io::Write for $hasher { 100 fn write(&mut self, buf: &[u8]) -> std::io::Result<usize> { 101 Update::update(self, buf); 102 Ok(buf.len()) 103 } 104 105 fn flush(&mut self) -> std::io::Result<()> { 106 Ok(()) 107 } 108 } 109 }; 110 } 111