@@ -280,8 +280,11 @@ impl Hasher {
280
280
281
281
/// Feeds data into the hasher.
282
282
pub fn update ( & mut self , data : & [ u8 ] ) -> Result < ( ) , ErrorStack > {
283
- if self . state == Finalized {
284
- self . init ( ) ?;
283
+ match self . state {
284
+ #[ cfg( ossl330) ]
285
+ Squeeze => self . init ( ) ?,
286
+ Finalized => self . init ( ) ?,
287
+ _ => { }
285
288
}
286
289
unsafe {
287
290
cvt ( ffi:: EVP_DigestUpdate (
@@ -298,6 +301,9 @@ impl Hasher {
298
301
/// The output will be as long as the buf.
299
302
#[ cfg( ossl330) ]
300
303
pub fn squeeze_xof ( & mut self , buf : & mut [ u8 ] ) -> Result < ( ) , ErrorStack > {
304
+ if self . state == Finalized {
305
+ self . init ( ) ?;
306
+ }
301
307
unsafe {
302
308
cvt ( ffi:: EVP_DigestSqueeze (
303
309
self . ctx ,
@@ -311,8 +317,11 @@ impl Hasher {
311
317
312
318
/// Returns the hash of the data written and resets the non-XOF hasher.
313
319
pub fn finish ( & mut self ) -> Result < DigestBytes , ErrorStack > {
314
- if self . state == Finalized {
315
- self . init ( ) ?;
320
+ match self . state {
321
+ #[ cfg( ossl330) ]
322
+ Squeeze => self . init ( ) ?,
323
+ Finalized => self . init ( ) ?,
324
+ _ => { }
316
325
}
317
326
unsafe {
318
327
#[ cfg( not( boringssl) ) ]
@@ -337,8 +346,11 @@ impl Hasher {
337
346
/// The hash will be as long as the buf.
338
347
#[ cfg( ossl111) ]
339
348
pub fn finish_xof ( & mut self , buf : & mut [ u8 ] ) -> Result < ( ) , ErrorStack > {
340
- if self . state == Finalized {
341
- self . init ( ) ?;
349
+ match self . state {
350
+ #[ cfg( ossl330) ]
351
+ Squeeze => self . init ( ) ?,
352
+ Finalized => self . init ( ) ?,
353
+ _ => { }
342
354
}
343
355
unsafe {
344
356
cvt ( ffi:: EVP_DigestFinalXOF (
@@ -576,6 +588,32 @@ mod tests {
576
588
assert_eq ! ( & * res, & * null) ;
577
589
}
578
590
591
+ #[ cfg( ossl330) ]
592
+ #[ test]
593
+ fn test_finish_then_squeeze ( ) {
594
+ let digest = MessageDigest :: shake_128 ( ) ;
595
+ let mut h = Hasher :: new ( digest) . unwrap ( ) ;
596
+ let mut buf = vec ! [ 0 ; digest. size( ) ] ;
597
+ h. finish_xof ( & mut buf) . unwrap ( ) ;
598
+ h. squeeze_xof ( & mut buf) . unwrap ( ) ;
599
+ let null = hash ( digest, & [ ] ) . unwrap ( ) ;
600
+ assert_eq ! ( & * buf, & * null) ;
601
+ }
602
+
603
+ #[ cfg( ossl330) ]
604
+ #[ test]
605
+ fn test_squeeze_then_update ( ) {
606
+ let digest = MessageDigest :: shake_128 ( ) ;
607
+ let data = Vec :: from_hex ( MD5_TESTS [ 6 ] . 0 ) . unwrap ( ) ;
608
+ let mut h = Hasher :: new ( digest) . unwrap ( ) ;
609
+ let mut buf = vec ! [ 0 ; digest. size( ) ] ;
610
+ h. squeeze_xof ( & mut buf) . unwrap ( ) ;
611
+ h. update ( & data) . unwrap ( ) ;
612
+ h. squeeze_xof ( & mut buf) . unwrap ( ) ;
613
+ let null = hash ( digest, & data) . unwrap ( ) ;
614
+ assert_eq ! ( & * buf, & * null) ;
615
+ }
616
+
579
617
#[ test]
580
618
#[ allow( clippy:: redundant_clone) ]
581
619
fn test_clone ( ) {
0 commit comments