From f0c9e1c27f2604594b5e2e8ea4262e6bf89557a3 Mon Sep 17 00:00:00 2001 From: silverstillisntgold Date: Sun, 16 Feb 2025 21:49:02 -0500 Subject: [PATCH 1/6] Improve quality of StreamId impls ...and improve consistency of some documentation --- chacha20/src/rng.rs | 67 ++++++++++++++++++++++++++------------------- 1 file changed, 39 insertions(+), 28 deletions(-) diff --git a/chacha20/src/rng.rs b/chacha20/src/rng.rs index b9a4b9e9..f28ebe11 100644 --- a/chacha20/src/rng.rs +++ b/chacha20/src/rng.rs @@ -27,7 +27,7 @@ use crate::{ use cfg_if::cfg_if; -// number of 32-bit words per ChaCha block (fixed by algorithm definition) +/// Number of 32-bit words per ChaCha block (fixed by algorithm definition). const BLOCK_WORDS: u8 = 16; /// The seed for ChaCha20. Implements ZeroizeOnDrop when the @@ -108,22 +108,35 @@ impl From for WordPosInput { } } -/// A wrapper for the `stream_id`. It can be used with a: -/// * `[u32; 3]` -/// * `[u8; 12]` or -/// * a `u128` -pub struct StreamId([u32; 3]); +/// Amount of raw bytes backing a `StreamId` instance. +const STREAM_ID_BYTES: usize = size_of::(); +/// The length of the array contained within `StreamId`. +const STREAM_ID_LEN: usize = 3; -impl From<[u32; 3]> for StreamId { - fn from(value: [u32; 3]) -> Self { - Self([value[0].to_le(), value[1].to_le(), value[2].to_le()]) +/// A wrapper for the `stream_id`. +/// Can be constructed from any of the following: +/// * `[u32; 3]` +/// * `[u8; 12]` +/// * `u128` +pub struct StreamId([u32; STREAM_ID_LEN]); + +impl From<[u32; STREAM_ID_LEN]> for StreamId { + #[inline] + fn from(value: [u32; STREAM_ID_LEN]) -> Self { + let result = value.map(|v| v.to_le()); + Self(result) } } -impl From<[u8; 12]> for StreamId { - fn from(value: [u8; 12]) -> Self { - let mut result = Self([0u32; 3]); - for (n, chunk) in result.0.iter_mut().zip(value.chunks_exact(4)) { +impl From<[u8; STREAM_ID_BYTES]> for StreamId { + #[inline] + fn from(value: [u8; STREAM_ID_BYTES]) -> Self { + let mut result = Self(Default::default()); + for (n, chunk) in result + .0 + .iter_mut() + .zip(value.chunks_exact(size_of::())) + { *n = u32::from_le_bytes(chunk.try_into().unwrap()).to_le(); } result @@ -131,13 +144,11 @@ impl From<[u8; 12]> for StreamId { } impl From for StreamId { + #[inline] fn from(value: u128) -> Self { - let bytes = value.to_le_bytes(); - let mut result = Self([0u32; 3]); - for (n, chunk) in result.0.iter_mut().zip(bytes[0..12].chunks_exact(4)) { - *n = u32::from_le_bytes(chunk.try_into().unwrap()).to_le(); - } - result + let result: [u8; STREAM_ID_BYTES] = + value.to_le_bytes()[..STREAM_ID_BYTES].try_into().unwrap(); + result.into() } } @@ -415,8 +426,8 @@ macro_rules! impl_chacha_rng { /// Set the offset from the start of the stream, in 32-bit words. This method /// takes either: - /// * u64 - /// * [u8; 5] + /// * `[u8; 5]` + /// * `u64` /// /// As with `get_word_pos`, we use a 36-bit number. When given a `u64`, we use /// the least significant 4 bits as the RNG's index, and the 32 bits before it @@ -432,20 +443,20 @@ macro_rules! impl_chacha_rng { self.core.generate_and_set(word_pos.index); } - /// Sets the block pos and resets the RNG's index. + /// Set the block pos and reset the RNG's index. /// /// The word pos will be equal to `block_pos * 16 words per block`. /// /// This can be used with either: - /// * u32 - /// * [u8; 4] + /// * `[u8; 4]` + /// * `u32` #[inline] pub fn set_block_pos>(&mut self, block_pos: B) { self.core.reset(); self.core.core.0.state[12] = block_pos.into().0.to_le() } - /// Gets the block pos. + /// Get the block pos. #[inline] pub fn get_block_pos(&self) -> u32 { self.core.core.0.state[12] @@ -453,9 +464,9 @@ macro_rules! impl_chacha_rng { /// Set the stream number. The lower 96 bits are used and the rest are /// discarded. This method takes either: - /// * [u32; 3] - /// * [u8; 12] - /// * u128 + /// * `[u32; 3]` + /// * `[u8; 12]` + /// * `u128` /// /// This is initialized to zero; 296 unique streams of output /// are available per seed/key. From b749c00d595767b20e84e93b774fd391d6d3a5a4 Mon Sep 17 00:00:00 2001 From: silverstillisntgold Date: Sun, 16 Feb 2025 22:23:51 -0500 Subject: [PATCH 2/6] more adjacent doc changes --- chacha20/src/rng.rs | 26 +++++++++++++++----------- 1 file changed, 15 insertions(+), 11 deletions(-) diff --git a/chacha20/src/rng.rs b/chacha20/src/rng.rs index f28ebe11..72bc801f 100644 --- a/chacha20/src/rng.rs +++ b/chacha20/src/rng.rs @@ -82,9 +82,10 @@ impl Debug for Seed { } } -/// A wrapper for set_word_pos() input that can be assembled from: -/// * `u64` +/// A wrapper for set_word_pos() input. +/// Can be constructed from any of the following: /// * `[u8; 5]` +/// * `u64` pub struct WordPosInput { block_pos: u32, index: usize, @@ -113,7 +114,7 @@ const STREAM_ID_BYTES: usize = size_of::(); /// The length of the array contained within `StreamId`. const STREAM_ID_LEN: usize = 3; -/// A wrapper for the `stream_id`. +/// A wrapper for `stream_id`. /// Can be constructed from any of the following: /// * `[u32; 3]` /// * `[u8; 12]` @@ -132,12 +133,12 @@ impl From<[u8; STREAM_ID_BYTES]> for StreamId { #[inline] fn from(value: [u8; STREAM_ID_BYTES]) -> Self { let mut result = Self(Default::default()); - for (n, chunk) in result + for (cur, chunk) in result .0 .iter_mut() .zip(value.chunks_exact(size_of::())) { - *n = u32::from_le_bytes(chunk.try_into().unwrap()).to_le(); + *cur = u32::from_le_bytes(chunk.try_into().unwrap()).to_le(); } result } @@ -152,18 +153,21 @@ impl From for StreamId { } } -/// A wrapper for `block_pos`. It can be used with: -/// * u32 -/// * [u8; 4] +/// A wrapper for `block_pos`. +/// Can be constructed from any of the following: +/// * `[u8; 4]` +/// * `u32` pub struct BlockPos(u32); impl From for BlockPos { + #[inline] fn from(value: u32) -> Self { Self(value.to_le()) } } impl From<[u8; 4]> for BlockPos { + #[inline] fn from(value: [u8; 4]) -> Self { Self(u32::from_le_bytes(value).to_le()) } @@ -425,7 +429,7 @@ macro_rules! impl_chacha_rng { } /// Set the offset from the start of the stream, in 32-bit words. This method - /// takes either: + /// takes any of the following: /// * `[u8; 5]` /// * `u64` /// @@ -447,7 +451,7 @@ macro_rules! impl_chacha_rng { /// /// The word pos will be equal to `block_pos * 16 words per block`. /// - /// This can be used with either: + /// This method takes any of the following: /// * `[u8; 4]` /// * `u32` #[inline] @@ -463,7 +467,7 @@ macro_rules! impl_chacha_rng { } /// Set the stream number. The lower 96 bits are used and the rest are - /// discarded. This method takes either: + /// discarded. This method takes any of the following: /// * `[u32; 3]` /// * `[u8; 12]` /// * `u128` From 5ea3d273e5a2b6bf97824a31c8da3ae44f0bbbfc Mon Sep 17 00:00:00 2001 From: silverstillisntgold Date: Tue, 18 Feb 2025 19:37:09 -0500 Subject: [PATCH 3/6] Use inherent constants for `StreamId` --- chacha20/src/rng.rs | 26 ++++++++++++++------------ 1 file changed, 14 insertions(+), 12 deletions(-) diff --git a/chacha20/src/rng.rs b/chacha20/src/rng.rs index 72bc801f..97b7519d 100644 --- a/chacha20/src/rng.rs +++ b/chacha20/src/rng.rs @@ -109,29 +109,32 @@ impl From for WordPosInput { } } -/// Amount of raw bytes backing a `StreamId` instance. -const STREAM_ID_BYTES: usize = size_of::(); -/// The length of the array contained within `StreamId`. -const STREAM_ID_LEN: usize = 3; - /// A wrapper for `stream_id`. /// Can be constructed from any of the following: /// * `[u32; 3]` /// * `[u8; 12]` /// * `u128` -pub struct StreamId([u32; STREAM_ID_LEN]); +pub struct StreamId([u32; Self::LEN]); + +impl StreamId { + /// Amount of raw bytes backing a `StreamId` instance. + const BYTES: usize = size_of::(); + + /// The length of the array contained within `StreamId`. + const LEN: usize = 3; +} -impl From<[u32; STREAM_ID_LEN]> for StreamId { +impl From<[u32; Self::LEN]> for StreamId { #[inline] - fn from(value: [u32; STREAM_ID_LEN]) -> Self { + fn from(value: [u32; Self::LEN]) -> Self { let result = value.map(|v| v.to_le()); Self(result) } } -impl From<[u8; STREAM_ID_BYTES]> for StreamId { +impl From<[u8; Self::BYTES]> for StreamId { #[inline] - fn from(value: [u8; STREAM_ID_BYTES]) -> Self { + fn from(value: [u8; Self::BYTES]) -> Self { let mut result = Self(Default::default()); for (cur, chunk) in result .0 @@ -147,8 +150,7 @@ impl From<[u8; STREAM_ID_BYTES]> for StreamId { impl From for StreamId { #[inline] fn from(value: u128) -> Self { - let result: [u8; STREAM_ID_BYTES] = - value.to_le_bytes()[..STREAM_ID_BYTES].try_into().unwrap(); + let result: [u8; Self::BYTES] = value.to_le_bytes()[..Self::BYTES].try_into().unwrap(); result.into() } } From 74ff93c4da08054037f26c0d88abaa5f616e2f60 Mon Sep 17 00:00:00 2001 From: Tony Arcieri Date: Fri, 28 Feb 2025 12:27:33 +0000 Subject: [PATCH 4/6] Update chacha20/src/rng.rs --- chacha20/src/rng.rs | 1 + 1 file changed, 1 insertion(+) diff --git a/chacha20/src/rng.rs b/chacha20/src/rng.rs index 97b7519d..d7cc8422 100644 --- a/chacha20/src/rng.rs +++ b/chacha20/src/rng.rs @@ -83,6 +83,7 @@ impl Debug for Seed { } /// A wrapper for set_word_pos() input. +/// /// Can be constructed from any of the following: /// * `[u8; 5]` /// * `u64` From 56b825201565ae7669f2e77b9a29e98dfa01720f Mon Sep 17 00:00:00 2001 From: Tony Arcieri Date: Fri, 28 Feb 2025 12:28:02 +0000 Subject: [PATCH 5/6] Update chacha20/src/rng.rs --- chacha20/src/rng.rs | 1 + 1 file changed, 1 insertion(+) diff --git a/chacha20/src/rng.rs b/chacha20/src/rng.rs index d7cc8422..becb7ee5 100644 --- a/chacha20/src/rng.rs +++ b/chacha20/src/rng.rs @@ -111,6 +111,7 @@ impl From for WordPosInput { } /// A wrapper for `stream_id`. +/// /// Can be constructed from any of the following: /// * `[u32; 3]` /// * `[u8; 12]` From f5f247614caae1a73b722d098065b730be458d74 Mon Sep 17 00:00:00 2001 From: Tony Arcieri Date: Fri, 28 Feb 2025 12:29:23 +0000 Subject: [PATCH 6/6] Update chacha20/src/rng.rs --- chacha20/src/rng.rs | 1 + 1 file changed, 1 insertion(+) diff --git a/chacha20/src/rng.rs b/chacha20/src/rng.rs index becb7ee5..5e97e185 100644 --- a/chacha20/src/rng.rs +++ b/chacha20/src/rng.rs @@ -158,6 +158,7 @@ impl From for StreamId { } /// A wrapper for `block_pos`. +/// /// Can be constructed from any of the following: /// * `[u8; 4]` /// * `u32`