@@ -311,8 +311,8 @@ pub trait Rng: RngCore {
311
311
///
312
312
/// [`fill_bytes`]: RngCore::fill_bytes
313
313
#[ track_caller]
314
- fn fill < T : Fill + ? Sized > ( & mut self , dest : & mut T ) {
315
- dest . fill ( self )
314
+ fn fill < T : Fill > ( & mut self , dest : & mut [ T ] ) {
315
+ Fill :: fill_slice ( dest , self )
316
316
}
317
317
318
318
/// Alias for [`Rng::random`].
@@ -356,21 +356,24 @@ pub trait Rng: RngCore {
356
356
357
357
impl < R : RngCore + ?Sized > Rng for R { }
358
358
359
- /// Types which may be filled with random data
359
+ /// Support filling a slice with random data
360
360
///
361
- /// This trait allows arrays to be efficiently filled with random data.
361
+ /// This trait allows slices of "plain data" types to be efficiently filled
362
+ /// with random data.
362
363
///
363
364
/// Implementations are expected to be portable across machines unless
364
365
/// clearly documented otherwise (see the
365
366
/// [Chapter on Portability](https://rust-random.github.io/book/portability.html)).
366
- pub trait Fill {
367
- /// Fill self with random data
368
- fn fill < R : Rng + ?Sized > ( & mut self , rng : & mut R ) ;
367
+ /// The implementations provided achieve this by byte-swapping on big-endian
368
+ /// machines.
369
+ pub trait Fill : Sized {
370
+ /// Fill this with random data
371
+ fn fill_slice < R : Rng + ?Sized > ( this : & mut [ Self ] , rng : & mut R ) ;
369
372
}
370
373
371
- impl Fill for [ u8 ] {
372
- fn fill < R : Rng + ?Sized > ( & mut self , rng : & mut R ) {
373
- rng. fill_bytes ( self )
374
+ impl Fill for u8 {
375
+ fn fill_slice < R : Rng + ?Sized > ( this : & mut [ Self ] , rng : & mut R ) {
376
+ rng. fill_bytes ( this )
374
377
}
375
378
}
376
379
@@ -387,48 +390,48 @@ macro_rules! impl_fill {
387
390
// Force caller to wrap with an `unsafe` block
388
391
__unsafe( ) ;
389
392
390
- impl Fill for [ $t ] {
391
- fn fill <R : Rng + ?Sized >( & mut self , rng: & mut R ) {
392
- if self . len( ) > 0 {
393
- let size = mem:: size_of_val( self ) ;
393
+ impl Fill for $t {
394
+ fn fill_slice <R : Rng + ?Sized >( this : & mut [ Self ] , rng: & mut R ) {
395
+ if this . len( ) > 0 {
396
+ let size = mem:: size_of_val( this ) ;
394
397
rng. fill_bytes(
395
- // SAFETY: `self ` non-null and valid for reads and writes within its `size`
396
- // bytes. `self ` meets the alignment requirements of `&mut [u8]`.
397
- // The contents of `self ` are initialized. Both `[u8]` and `[$t]` are valid
398
+ // SAFETY: `this ` non-null and valid for reads and writes within its `size`
399
+ // bytes. `this ` meets the alignment requirements of `&mut [u8]`.
400
+ // The contents of `this ` are initialized. Both `[u8]` and `[$t]` are valid
398
401
// for all bit-patterns of their contents (note that the SAFETY requirement
399
- // on callers of this macro). `self ` is not borrowed.
402
+ // on callers of this macro). `this ` is not borrowed.
400
403
unsafe {
401
- slice:: from_raw_parts_mut( self . as_mut_ptr( )
404
+ slice:: from_raw_parts_mut( this . as_mut_ptr( )
402
405
as * mut u8 ,
403
406
size
404
407
)
405
408
}
406
409
) ;
407
- for x in self {
410
+ for x in this {
408
411
* x = x. to_le( ) ;
409
412
}
410
413
}
411
414
}
412
415
}
413
416
414
- impl Fill for [ Wrapping <$t>] {
415
- fn fill <R : Rng + ?Sized >( & mut self , rng: & mut R ) {
416
- if self . len( ) > 0 {
417
- let size = self . len( ) * mem:: size_of:: <$t>( ) ;
417
+ impl Fill for Wrapping <$t> {
418
+ fn fill_slice <R : Rng + ?Sized >( this : & mut [ Self ] , rng: & mut R ) {
419
+ if this . len( ) > 0 {
420
+ let size = this . len( ) * mem:: size_of:: <$t>( ) ;
418
421
rng. fill_bytes(
419
- // SAFETY: `self ` non-null and valid for reads and writes within its `size`
420
- // bytes. `self ` meets the alignment requirements of `&mut [u8]`.
421
- // The contents of `self ` are initialized. Both `[u8]` and `[$t]` are valid
422
+ // SAFETY: `this ` non-null and valid for reads and writes within its `size`
423
+ // bytes. `this ` meets the alignment requirements of `&mut [u8]`.
424
+ // The contents of `this ` are initialized. Both `[u8]` and `[$t]` are valid
422
425
// for all bit-patterns of their contents (note that the SAFETY requirement
423
- // on callers of this macro). `self ` is not borrowed.
426
+ // on callers of this macro). `this ` is not borrowed.
424
427
unsafe {
425
- slice:: from_raw_parts_mut( self . as_mut_ptr( )
428
+ slice:: from_raw_parts_mut( this . as_mut_ptr( )
426
429
as * mut u8 ,
427
430
size
428
431
)
429
432
}
430
433
) ;
431
- for x in self {
434
+ for x in this {
432
435
* x = Wrapping ( x. 0 . to_le( ) ) ;
433
436
}
434
437
}
@@ -448,15 +451,6 @@ const _: () = unsafe { impl_fill!(u16, u32, u64, u128,) };
448
451
// SAFETY: All bit patterns of `[u8; size_of::<$t>()]` represent values of `i*`.
449
452
const _: ( ) = unsafe { impl_fill ! ( i8 , i16 , i32 , i64 , i128 , ) } ;
450
453
451
- impl < T , const N : usize > Fill for [ T ; N ]
452
- where
453
- [ T ] : Fill ,
454
- {
455
- fn fill < R : Rng + ?Sized > ( & mut self , rng : & mut R ) {
456
- <[ T ] as Fill >:: fill ( self , rng)
457
- }
458
- }
459
-
460
454
#[ cfg( test) ]
461
455
mod test {
462
456
use super :: * ;
@@ -491,19 +485,19 @@ mod test {
491
485
492
486
// Convert to byte sequence and back to u64; byte-swap twice if BE.
493
487
let mut array = [ 0u64 ; 2 ] ;
494
- rng. fill ( & mut array[ .. ] ) ;
488
+ rng. fill ( & mut array) ;
495
489
assert_eq ! ( array, [ x, x] ) ;
496
490
assert_eq ! ( rng. next_u64( ) , x) ;
497
491
498
492
// Convert to bytes then u32 in LE order
499
493
let mut array = [ 0u32 ; 2 ] ;
500
- rng. fill ( & mut array[ .. ] ) ;
494
+ rng. fill ( & mut array) ;
501
495
assert_eq ! ( array, [ x as u32 , ( x >> 32 ) as u32 ] ) ;
502
496
assert_eq ! ( rng. next_u32( ) , x as u32 ) ;
503
497
504
498
// Check equivalence using wrapped arrays
505
499
let mut warray = [ Wrapping ( 0u32 ) ; 2 ] ;
506
- rng. fill ( & mut warray[ .. ] ) ;
500
+ rng. fill ( & mut warray) ;
507
501
assert_eq ! ( array[ 0 ] , warray[ 0 ] . 0 ) ;
508
502
assert_eq ! ( array[ 1 ] , warray[ 1 ] . 0 ) ;
509
503
}
0 commit comments