@@ -4156,16 +4156,24 @@ pub fn render_cat_avatar_for_identity_with_background(
41564156 Ok ( render_cat_avatar_with_identity ( spec, identity, background) )
41574157}
41584158
4159+ fn seeded_renderer_rng ( spec : AvatarSpec , identity : & AvatarIdentity ) -> StdRng {
4160+ let mut rng_seed = identity. rng_seed ( ) ;
4161+ for ( index, byte) in spec. seed . to_le_bytes ( ) . iter ( ) . enumerate ( ) {
4162+ rng_seed[ index] ^= * byte;
4163+ }
4164+ let mut rng_seed_value = * rng_seed;
4165+ drop ( rng_seed) ;
4166+ let rng = StdRng :: from_seed ( rng_seed_value) ;
4167+ rng_seed_value. zeroize ( ) ;
4168+ rng
4169+ }
4170+
41594171fn render_cat_avatar_with_identity (
41604172 spec : AvatarSpec ,
41614173 identity : & AvatarIdentity ,
41624174 background : AvatarBackground ,
41634175) -> RgbaImage {
4164- let mut rng_seed = identity. rng_seed ( ) ;
4165- for ( index, byte) in spec. seed . to_le_bytes ( ) . iter ( ) . enumerate ( ) {
4166- rng_seed[ index] ^= * byte;
4167- }
4168- let mut rng = StdRng :: from_seed ( * rng_seed) ;
4176+ let mut rng = seeded_renderer_rng ( spec, identity) ;
41694177 let genome = CatGenome :: from_identity ( identity, & mut rng) ;
41704178 let palette = CatPalette :: from_genome ( & genome) ;
41714179 let mut image = ImageBuffer :: from_pixel (
@@ -9895,6 +9903,25 @@ mod tests {
98959903 assert_eq ! ( rng_seed. len( ) , 32 ) ;
98969904 }
98979905
9906+ #[ test]
9907+ fn renderer_rng_seed_copy_is_zeroized_before_rng_use ( ) {
9908+ let source = include_str ! ( concat!( env!( "CARGO_MANIFEST_DIR" ) , "/src/lib.rs" ) ) ;
9909+ let helper = source
9910+ . split ( "fn seeded_renderer_rng" )
9911+ . nth ( 1 )
9912+ . and_then ( |after_name| {
9913+ after_name
9914+ . split ( "fn render_cat_avatar_with_identity" )
9915+ . next ( )
9916+ } )
9917+ . expect ( "seeded renderer rng helper should exist" ) ;
9918+
9919+ assert ! ( helper. contains( "let mut rng_seed_value = *rng_seed;" ) ) ;
9920+ assert ! ( helper. contains( "drop(rng_seed);" ) ) ;
9921+ assert ! ( helper. contains( "let rng = StdRng::from_seed(rng_seed_value);" ) ) ;
9922+ assert ! ( helper. contains( "rng_seed_value.zeroize();" ) ) ;
9923+ }
9924+
98989925 #[ test]
98999926 fn avatar_identity_equality_compares_digest_values ( ) {
99009927 let left = valid_identity ( "alice@example.com" ) ;
0 commit comments