From eac985fe73cc4fa89eaabe71eec4c3b013bbd56b Mon Sep 17 00:00:00 2001 From: Vinzent Steinberg Date: Fri, 17 Sep 2021 21:35:48 +0200 Subject: [PATCH 1/5] Fix spelling --- rand_core/src/lib.rs | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/rand_core/src/lib.rs b/rand_core/src/lib.rs index 1ae692cc701..fccbbd09c25 100644 --- a/rand_core/src/lib.rs +++ b/rand_core/src/lib.rs @@ -448,10 +448,10 @@ impl std::io::Read for dyn RngCore { } } -// Implement `CryptoRng` for references to an `CryptoRng`. +// Implement `CryptoRng` for references to a `CryptoRng`. impl<'a, R: CryptoRng + ?Sized> CryptoRng for &'a mut R {} -// Implement `CryptoRng` for boxed references to an `CryptoRng`. +// Implement `CryptoRng` for boxed references to a `CryptoRng`. #[cfg(feature = "alloc")] impl CryptoRng for Box {} From 51d1365370893297f79b187b0f717da4ef1645aa Mon Sep 17 00:00:00 2001 From: Vinzent Steinberg Date: Fri, 17 Sep 2021 21:53:32 +0200 Subject: [PATCH 2/5] rand_core: Add `CryptoRngCore` to support `CryptoRng` trait objects Fixes #1143. --- rand_core/src/lib.rs | 14 ++++++++++++++ 1 file changed, 14 insertions(+) diff --git a/rand_core/src/lib.rs b/rand_core/src/lib.rs index fccbbd09c25..cdc130067e2 100644 --- a/rand_core/src/lib.rs +++ b/rand_core/src/lib.rs @@ -208,6 +208,20 @@ pub trait RngCore { /// [`BlockRngCore`]: block::BlockRngCore pub trait CryptoRng {} +/// An extension trait to support trait objects that implement [`RngCore`] and +/// [`CryptoRng`]. Upcasting to [`RngCore`] is supported via the +/// [`CryptoRngCore::upcast`] method. +pub trait CryptoRngCore: RngCore { + /// Upcast to an [`RngCore`] trait object. + fn upcast(&mut self) -> &mut dyn RngCore; +} + +impl CryptoRngCore for T { + fn upcast(&mut self) -> &mut dyn RngCore { + self + } +} + /// A random number generator that can be explicitly seeded. /// /// This trait encapsulates the low-level functionality common to all From fe236c52f32b666da1050493efa74db89a633bfb Mon Sep 17 00:00:00 2001 From: Vinzent Steinberg Date: Fri, 17 Sep 2021 21:59:16 +0200 Subject: [PATCH 3/5] rand_chacha: Add test for trait object upcasting --- rand_chacha/src/chacha.rs | 11 +++++++++++ 1 file changed, 11 insertions(+) diff --git a/rand_chacha/src/chacha.rs b/rand_chacha/src/chacha.rs index fce8e493796..956fc1c38fc 100644 --- a/rand_chacha/src/chacha.rs +++ b/rand_chacha/src/chacha.rs @@ -623,4 +623,15 @@ mod test { rng.set_word_pos(0); assert_eq!(rng.get_word_pos(), 0); } + + #[test] + fn test_trait_objects() { + use rand_core::CryptoRngCore; + + let rng = &mut ChaChaRng::from_seed(Default::default()) as &mut dyn CryptoRngCore; + let r1 = rng.next_u64(); + let rng: &mut dyn RngCore = rng.upcast(); + let r2 = rng.next_u64(); + assert_ne!(r1, r2); + } } From c797f070b125084d727dc0ba5104bbdae966ba78 Mon Sep 17 00:00:00 2001 From: Vinzent Steinberg Date: Mon, 20 Sep 2021 14:08:39 +0200 Subject: [PATCH 4/5] rand_core: Rename `CryptoRngCore::upcast` to `as_rngcore` --- rand_chacha/src/chacha.rs | 2 +- rand_core/src/lib.rs | 6 +++--- 2 files changed, 4 insertions(+), 4 deletions(-) diff --git a/rand_chacha/src/chacha.rs b/rand_chacha/src/chacha.rs index 956fc1c38fc..ad74b35f62b 100644 --- a/rand_chacha/src/chacha.rs +++ b/rand_chacha/src/chacha.rs @@ -630,7 +630,7 @@ mod test { let rng = &mut ChaChaRng::from_seed(Default::default()) as &mut dyn CryptoRngCore; let r1 = rng.next_u64(); - let rng: &mut dyn RngCore = rng.upcast(); + let rng: &mut dyn RngCore = rng.as_rngcore(); let r2 = rng.next_u64(); assert_ne!(r1, r2); } diff --git a/rand_core/src/lib.rs b/rand_core/src/lib.rs index cdc130067e2..9ac353b4526 100644 --- a/rand_core/src/lib.rs +++ b/rand_core/src/lib.rs @@ -210,14 +210,14 @@ pub trait CryptoRng {} /// An extension trait to support trait objects that implement [`RngCore`] and /// [`CryptoRng`]. Upcasting to [`RngCore`] is supported via the -/// [`CryptoRngCore::upcast`] method. +/// [`CryptoRngCore::as_rngcore`] method. pub trait CryptoRngCore: RngCore { /// Upcast to an [`RngCore`] trait object. - fn upcast(&mut self) -> &mut dyn RngCore; + fn as_rngcore(&mut self) -> &mut dyn RngCore; } impl CryptoRngCore for T { - fn upcast(&mut self) -> &mut dyn RngCore { + fn as_rngcore(&mut self) -> &mut dyn RngCore { self } } From a4fa0771a2605d6759a8c0fe252534c1f54fad6e Mon Sep 17 00:00:00 2001 From: Vinzent Steinberg Date: Mon, 20 Sep 2021 14:27:14 +0200 Subject: [PATCH 5/5] CryptoRngCore: Improve docs --- rand_core/src/lib.rs | 21 ++++++++++++++++++--- 1 file changed, 18 insertions(+), 3 deletions(-) diff --git a/rand_core/src/lib.rs b/rand_core/src/lib.rs index 9ac353b4526..fdbf6675b96 100644 --- a/rand_core/src/lib.rs +++ b/rand_core/src/lib.rs @@ -208,9 +208,24 @@ pub trait RngCore { /// [`BlockRngCore`]: block::BlockRngCore pub trait CryptoRng {} -/// An extension trait to support trait objects that implement [`RngCore`] and -/// [`CryptoRng`]. Upcasting to [`RngCore`] is supported via the -/// [`CryptoRngCore::as_rngcore`] method. +/// An extension trait that is automatically implemented for any type +/// implementing [`RngCore`] and [`CryptoRng`]. +/// +/// It may be used as a trait object, and supports upcasting to [`RngCore`] via +/// the [`CryptoRngCore::as_rngcore`] method. +/// +/// # Example +/// +/// ``` +/// use rand_core::CryptoRngCore; +/// +/// #[allow(unused)] +/// fn make_token(rng: &mut dyn CryptoRngCore) -> [u8; 32] { +/// let mut buf = [0u8; 32]; +/// rng.fill_bytes(&mut buf); +/// buf +/// } +/// ``` pub trait CryptoRngCore: RngCore { /// Upcast to an [`RngCore`] trait object. fn as_rngcore(&mut self) -> &mut dyn RngCore;