rust/lfprng/src/lib.rs
changeset 16101 a4cbc6926439
parent 16086 106674bb21b1
equal deleted inserted replaced
16100:fba762376a07 16101:a4cbc6926439
     1 use rand::{Error, RngCore, SeedableRng};
     1 use rand::{RngCore, SeedableRng};
     2 
     2 
     3 pub struct LaggedFibonacciPRNG {
     3 pub struct LaggedFibonacciPRNG {
     4     circular_buffer: [u32; 64],
     4     circular_buffer: [u32; 64],
     5     index: usize,
     5     index: usize,
     6 }
     6 }
    63     }
    63     }
    64 }
    64 }
    65 
    65 
    66 impl RngCore for LaggedFibonacciPRNG {
    66 impl RngCore for LaggedFibonacciPRNG {
    67     fn next_u32(&mut self) -> u32 {
    67     fn next_u32(&mut self) -> u32 {
    68         self.get_next().wrapping_add(self.get_next())
    68         self.get_next();
       
    69         self.get_next()
    69     }
    70     }
    70 
    71 
    71     fn next_u64(&mut self) -> u64 {
    72     fn next_u64(&mut self) -> u64 {
    72         ((self.next_u32() as u64) << 32) | self.next_u32() as u64
    73         ((self.get_next() as u64) << 32) | self.get_next() as u64
    73     }
    74     }
    74 
    75 
    75     fn fill_bytes(&mut self, dest: &mut [u8]) {
    76     fn fill_bytes(&mut self, dest: &mut [u8]) {
    76         dest.iter_mut().for_each(|x| *x = self.next_u32() as u8);
    77         let mut chunks = dest.chunks_exact_mut(4);
    77     }
       
    78 
    78 
    79     fn try_fill_bytes(&mut self, dest: &mut [u8]) -> Result<(), Error> {
    79         for chunk in chunks.by_ref() {
    80         Ok(self.fill_bytes(dest))
    80             let value = self.get_next();
       
    81             let bytes = value.to_le_bytes();
       
    82             chunk.copy_from_slice(&bytes);
       
    83         }
       
    84 
       
    85         let remainder = chunks.into_remainder();
       
    86         if !remainder.is_empty() {
       
    87             let value = self.next_u32();
       
    88             let bytes = value.to_le_bytes();
       
    89             remainder.copy_from_slice(&bytes[..remainder.len()]);
       
    90         }
    81     }
    91     }
    82 }
    92 }
    83 
    93 
    84 impl SeedableRng for LaggedFibonacciPRNG {
    94 impl SeedableRng for LaggedFibonacciPRNG {
    85     type Seed = [u8; 32];
    95     type Seed = [u8; 32];