1010
1111use crate :: guts:: ChaCha ;
1212use core:: fmt;
13- use rand_core:: { CryptoRng , RngCore , SeedableRng , le } ;
13+ use rand_core:: { le , CryptoRng , RngCore , SeedableRng , Generator , CryptoGenerator } ;
1414
1515#[ cfg( feature = "serde" ) ]
1616use serde:: { Deserialize , Deserializer , Serialize , Serializer } ;
@@ -35,20 +35,28 @@ macro_rules! chacha_impl {
3535 }
3636 }
3737
38- impl $ChaChaXCore {
38+ impl Generator for $ChaChaXCore {
39+ type Result = [ u32 ; 64 ] ;
40+
3941 #[ inline]
40- fn from_seed( seed: [ u8 ; 32 ] ) -> Self {
41- $ChaChaXCore {
42- state: ChaCha :: new( & seed, & [ 0u8 ; 8 ] ) ,
43- }
42+ fn generate( & mut self , r: & mut Self :: Result ) {
43+ self . state. refill4( $rounds, r) ;
4444 }
45+ }
46+
47+ impl SeedableRng for $ChaChaXCore {
48+ type Seed = [ u8 ; 32 ] ;
4549
4650 #[ inline]
47- fn next_block( & mut self , r: & mut [ u32 ; 64 ] ) {
48- self . state. refill4( $rounds, r) ;
51+ fn from_seed( seed: Self :: Seed ) -> Self {
52+ $ChaChaXCore {
53+ state: ChaCha :: new( & seed, & [ 0u8 ; 8 ] ) ,
54+ }
4955 }
5056 }
5157
58+ impl CryptoGenerator for $ChaChaXCore { }
59+
5260 /// A cryptographically secure random number generator that uses the ChaCha algorithm.
5361 ///
5462 /// ChaCha is a stream cipher designed by Daniel J. Bernstein[^1], that we use as an RNG. It is
@@ -80,7 +88,7 @@ macro_rules! chacha_impl {
8088 /// ```
8189 ///
8290 /// This implementation uses an output buffer of sixteen `u32` words, and uses
83- /// them to implement the [`RngCore`] methods.
91+ /// [`BlockRng`] to implement the [`RngCore`] methods.
8492 ///
8593 /// [^1]: D. J. Bernstein, [*ChaCha, a variant of Salsa20*](
8694 /// https://cr.yp.to/chacha.html)
@@ -101,7 +109,7 @@ macro_rules! chacha_impl {
101109 fn generate_and_set( & mut self , index: usize ) {
102110 assert!( index < self . buffer. len( ) ) ;
103111 self . buffer[ 0 ] = if index != 0 {
104- self . core. next_block ( & mut self . buffer) ;
112+ self . core. generate ( & mut self . buffer) ;
105113 index as u32
106114 } else {
107115 self . buffer. len( ) as u32
@@ -125,19 +133,19 @@ macro_rules! chacha_impl {
125133 #[ inline]
126134 fn next_u32( & mut self ) -> u32 {
127135 let Self { core, buffer } = self ;
128- le:: next_word_via_gen_block( buffer, |block| core. next_block ( block) )
136+ le:: next_word_via_gen_block( buffer, |block| core. generate ( block) )
129137 }
130138
131139 #[ inline]
132140 fn next_u64( & mut self ) -> u64 {
133141 let Self { core, buffer } = self ;
134- le:: next_u64_via_gen_block( buffer, |block| core. next_block ( block) )
142+ le:: next_u64_via_gen_block( buffer, |block| core. generate ( block) )
135143 }
136144
137145 #[ inline]
138146 fn fill_bytes( & mut self , dst: & mut [ u8 ] ) {
139147 let Self { core, buffer } = self ;
140- le:: fill_bytes_via_gen_block( dst, buffer, |block| core. next_block ( block) ) ;
148+ le:: fill_bytes_via_gen_block( dst, buffer, |block| core. generate ( block) ) ;
141149 }
142150 }
143151
@@ -177,7 +185,8 @@ macro_rules! chacha_impl {
177185 pub fn set_word_pos( & mut self , word_offset: u128 ) {
178186 let block = ( word_offset / u128 :: from( BLOCK_WORDS ) ) as u64 ;
179187 self . core. state. set_block_pos( block) ;
180- self . generate_and_set( ( word_offset % u128 :: from( BLOCK_WORDS ) ) as usize ) ;
188+ self
189+ . generate_and_set( ( word_offset % u128 :: from( BLOCK_WORDS ) ) as usize ) ;
181190 }
182191
183192 /// Set the stream number.
0 commit comments