Skip to content

Commit

Permalink
hmac: 2018 edition and crypto-mac crate upgrade
Browse files Browse the repository at this point in the history
Upgrades to Rust 2018 edition and the (now 2018 edition)
`crypto-mac` v0.8.0-pre crate.
  • Loading branch information
tarcieri committed May 31, 2020
1 parent d9a55bb commit 59dc87d
Show file tree
Hide file tree
Showing 5 changed files with 68 additions and 96 deletions.
66 changes: 18 additions & 48 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 @@ -8,7 +8,11 @@ members = [

[patch.crates-io]
aes = { git = "https://github.com/RustCrypto/block-ciphers" }
block-buffer = { git = "https://github.com/RustCrypto/utils" }
block-cipher = { git = "https://github.com/RustCrypto/traits" }
crypto-mac = { git = "https://github.com/RustCrypto/traits" }
digest = { git = "https://github.com/RustCrypto/traits" }
dbl = { git = "https://github.com/RustCrypto/utils" }
des = { git = "https://github.com/RustCrypto/block-ciphers" }
md-5 = { git = "https://github.com/RustCrypto/hashes" }
sha2 = { git = "https://github.com/RustCrypto/hashes" }
11 changes: 6 additions & 5 deletions hmac/Cargo.toml
Original file line number Diff line number Diff line change
Expand Up @@ -9,12 +9,13 @@ repository = "https://github.com/RustCrypto/MACs"
keywords = ["crypto", "mac", "hmac", "digest"]
categories = ["cryptography", "no-std"]
readme = "README.md"
edition = "2018"

[dependencies]
crypto-mac = "0.7"
digest = "0.8"
crypto-mac = "= 0.8.0-pre"
digest = "= 0.9.0-pre"

[dev-dependencies]
crypto-mac = { version = "0.7", features = ["dev"] }
md-5 = { version = "0.8", default-features = false }
sha2 = { version = "0.8", default-features = false }
crypto-mac = { version = "0.8.0-pre", features = ["dev"] }
md-5 = { version = "0.9.0-pre", default-features = false }
sha2 = { version = "0.9.0-pre", default-features = false }
76 changes: 38 additions & 38 deletions hmac/src/lib.rs
Original file line number Diff line number Diff line change
Expand Up @@ -10,76 +10,68 @@
//! To get the authentication code:
//!
//! ```rust
//! extern crate hmac;
//! extern crate sha2;
//!
//! use sha2::Sha256;
//! use hmac::{Hmac, Mac};
//! use hmac::{Hmac, Mac, NewMac};
//!
//! // Create alias for HMAC-SHA256
//! type HmacSha256 = Hmac<Sha256>;
//!
//! # fn main() {
//! // Create HMAC-SHA256 instance which implements `Mac` trait
//! let mut mac = HmacSha256::new_varkey(b"my secret and secure key")
//! .expect("HMAC can take key of any size");
//! mac.input(b"input message");
//! mac.update(b"input message");
//!
//! // `result` has type `MacResult` which is a thin wrapper around array of
//! // `result` has type `Output` which is a thin wrapper around array of
//! // bytes for providing constant time equality check
//! let result = mac.result();
//! // To get underlying array use `code` method, but be careful, since
//! // incorrect use of the code value may permit timing attacks which defeat
//! // the security provided by the `MacResult`
//! let code_bytes = result.code();
//! # }
//! // the security provided by the `Output`
//! let code_bytes = result.into_bytes();
//! ```
//!
//! To verify the message:
//!
//! ```rust
//! # extern crate hmac;
//! # extern crate sha2;
//! # use sha2::Sha256;
//! # use hmac::{Hmac, Mac};
//! # fn main() {
//! # use hmac::{Hmac, Mac, NewMac};
//! # type HmacSha256 = Hmac<Sha256>;
//! let mut mac = HmacSha256::new_varkey(b"my secret and secure key")
//! .expect("HMAC can take key of any size");
//!
//! mac.input(b"input message");
//! mac.update(b"input message");
//!
//! # let code_bytes = mac.clone().result().code();
//! # let code_bytes = mac.clone().result().into_bytes();
//! // `verify` will return `Ok(())` if code is correct, `Err(MacError)` otherwise
//! mac.verify(&code_bytes).unwrap();
//! # }
//! ```
//!
//! # Block and input sizes
//! Usually it is assumed that block size is larger than output size, due to the
//! generic nature of the implementation this edge case must be handled as well
//! to remove potential panic scenario. This is done by truncating hash output
//! to the hash block size if needed.

#![no_std]
#![doc(html_logo_url = "https://raw.githubusercontent.com/RustCrypto/meta/master/logo_small.png")]
pub extern crate crypto_mac;
pub extern crate digest;

pub use crypto_mac::{self, Mac, NewMac};
pub use digest;

use core::cmp::min;
use core::fmt;
pub use crypto_mac::Mac;
use crypto_mac::{InvalidKeyLength, MacResult};
use crypto_mac::{InvalidKeyLength, Output};
use digest::generic_array::sequence::GenericSequence;
use digest::generic_array::{ArrayLength, GenericArray};
use digest::{BlockInput, FixedOutput, Input, Reset};
use digest::{BlockInput, FixedOutput, Update, Reset};

const IPAD: u8 = 0x36;
const OPAD: u8 = 0x5C;

/// The `Hmac` struct represents an HMAC using a given hash function `D`.
pub struct Hmac<D>
where
D: Input + BlockInput + FixedOutput + Reset + Default + Clone,
D: Update + BlockInput + FixedOutput + Reset + Default + Clone,
D::BlockSize: ArrayLength<u8>,
{
digest: D,
Expand All @@ -89,7 +81,7 @@ where

impl<D> Clone for Hmac<D>
where
D: Input + BlockInput + FixedOutput + Reset + Default + Clone,
D: Update + BlockInput + FixedOutput + Reset + Default + Clone,
D::BlockSize: ArrayLength<u8>,
{
fn clone(&self) -> Hmac<D> {
Expand All @@ -103,10 +95,10 @@ where

impl<D> fmt::Debug for Hmac<D>
where
D: Input + BlockInput + FixedOutput + Reset + Default + Clone + fmt::Debug,
D: Update + BlockInput + FixedOutput + Reset + Default + Clone + fmt::Debug,
D::BlockSize: ArrayLength<u8>,
{
fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
f.debug_struct("Hmac")
.field("digest", &self.digest)
.field("i_key_pad", &self.i_key_pad)
Expand All @@ -115,13 +107,12 @@ where
}
}

impl<D> Mac for Hmac<D>
impl<D> NewMac for Hmac<D>
where
D: Input + BlockInput + FixedOutput + Reset + Default + Clone,
D: Update + BlockInput + FixedOutput + Reset + Default + Clone,
D::BlockSize: ArrayLength<u8>,
D::OutputSize: ArrayLength<u8>,
{
type OutputSize = D::OutputSize;
type KeySize = D::BlockSize;

fn new(key: &GenericArray<u8, Self::KeySize>) -> Self {
Expand Down Expand Up @@ -150,7 +141,7 @@ where
}
} else {
let mut digest = D::default();
digest.input(key);
digest.update(key);
let output = digest.fixed_result();
// `n` is calculated at compile time and will equal
// D::OutputSize. This is used to ensure panic-free code
Expand All @@ -161,28 +152,37 @@ where
}
}

hmac.digest.input(&hmac.i_key_pad);
hmac.opad_digest.input(&opad);
hmac.digest.update(&hmac.i_key_pad);
hmac.opad_digest.update(&opad);

Ok(hmac)
}
}

impl<D> Mac for Hmac<D>
where
D: Update + BlockInput + FixedOutput + Reset + Default + Clone,
D::BlockSize: ArrayLength<u8>,
D::OutputSize: ArrayLength<u8>,
{
type OutputSize = D::OutputSize;

#[inline]
fn input(&mut self, data: &[u8]) {
self.digest.input(data);
fn update(&mut self, data: &[u8]) {
self.digest.update(data);
}

#[inline]
fn result(self) -> MacResult<D::OutputSize> {
fn result(self) -> Output<Self> {
let mut opad_digest = self.opad_digest.clone();
let hash = self.digest.fixed_result();
opad_digest.input(&hash);
MacResult::new(opad_digest.fixed_result())
opad_digest.update(&hash);
Output::new(opad_digest.fixed_result())
}

#[inline]
fn reset(&mut self) {
self.digest.reset();
self.digest.input(&self.i_key_pad);
self.digest.update(&self.i_key_pad);
}
}
7 changes: 2 additions & 5 deletions hmac/tests/lib.rs
Original file line number Diff line number Diff line change
@@ -1,13 +1,10 @@
//! Test vectors from:
//! - md5: RFC 2104, plus wiki test
//! - sha2: RFC 4231

#![no_std]
#[macro_use]
extern crate crypto_mac;
extern crate hmac;
extern crate md5;
extern crate sha2;

use crypto_mac::new_test;
use hmac::Hmac;

new_test!(hmac_md5, "md5", Hmac<md5::Md5>);
Expand Down

0 comments on commit 59dc87d

Please sign in to comment.