@@ -378,10 +378,10 @@ impl<'a, 'b, S: Syscall> Executor<'a, 'b, S> {
378
378
fn ecall_software ( & mut self ) -> Result < bool > {
379
379
tracing:: debug!( "[{}] ecall_software" , self . insn_cycles) ;
380
380
let into_guest_ptr = ByteAddr ( self . load_register ( REG_A0 ) ?) ;
381
- if !is_guest_memory ( into_guest_ptr. 0 ) && !into_guest_ptr. is_null ( ) {
381
+ let into_guest_len = self . load_register ( REG_A1 ) ? as usize ;
382
+ if into_guest_len > 0 && !is_guest_memory ( into_guest_ptr. 0 ) {
382
383
bail ! ( "{into_guest_ptr:?} is an invalid guest address" ) ;
383
384
}
384
- let into_guest_len = self . load_register ( REG_A1 ) ? as usize ;
385
385
let name_ptr = self . load_guest_addr_from_register ( REG_A2 ) ?;
386
386
let syscall_name = self . peek_string ( name_ptr) ?;
387
387
let name_end = name_ptr + syscall_name. len ( ) ;
@@ -410,7 +410,7 @@ impl<'a, 'b, S: Syscall> Executor<'a, 'b, S> {
410
410
411
411
// The guest uses a null pointer to indicate that a transfer from host
412
412
// to guest is not needed.
413
- if !into_guest_ptr. is_null ( ) {
413
+ if into_guest_len > 0 && !into_guest_ptr. is_null ( ) {
414
414
Self :: check_guest_addr ( into_guest_ptr + into_guest_len) ?;
415
415
self . store_region ( into_guest_ptr, bytemuck:: cast_slice ( & syscall. to_guest ) ) ?
416
416
}
@@ -431,8 +431,6 @@ impl<'a, 'b, S: Syscall> Executor<'a, 'b, S> {
431
431
tracing:: debug!( "[{}] ecall_sha" , self . insn_cycles) ;
432
432
let state_out_ptr = self . load_guest_addr_from_register ( REG_A0 ) ?;
433
433
let state_in_ptr = self . load_guest_addr_from_register ( REG_A1 ) ?;
434
- let mut block1_ptr = self . load_guest_addr_from_register ( REG_A2 ) ?;
435
- let mut block2_ptr = self . load_guest_addr_from_register ( REG_A3 ) ?;
436
434
let count = self . load_register ( REG_A4 ) ?;
437
435
438
436
let state_in: [ u8 ; DIGEST_BYTES ] = self . load_array_from_guest ( state_in_ptr) ?;
@@ -441,25 +439,30 @@ impl<'a, 'b, S: Syscall> Executor<'a, 'b, S> {
441
439
* word = word. to_be ( ) ;
442
440
}
443
441
444
- // tracing::debug!("ecall_sha: start state: {state:08x?}");
445
- let mut block = [ 0u32 ; BLOCK_WORDS ] ;
442
+ if count > 0 {
443
+ let mut block1_ptr = self . load_guest_addr_from_register ( REG_A2 ) ?;
444
+ let mut block2_ptr = self . load_guest_addr_from_register ( REG_A3 ) ?;
446
445
447
- for _ in 0 ..count {
448
- let ( digest1, digest2) = block. split_at_mut ( DIGEST_WORDS ) ;
449
- for ( i, word) in digest1. iter_mut ( ) . enumerate ( ) {
450
- * word = self . load_u32_from_guest ( block1_ptr + ( i * WORD_SIZE ) ) ?;
451
- }
452
- for ( i, word) in digest2. iter_mut ( ) . enumerate ( ) {
453
- * word = self . load_u32_from_guest ( block2_ptr + ( i * WORD_SIZE ) ) ?;
446
+ // tracing::debug!("ecall_sha: start state: {state:08x?}");
447
+ let mut block = [ 0u32 ; BLOCK_WORDS ] ;
448
+
449
+ for _ in 0 ..count {
450
+ let ( digest1, digest2) = block. split_at_mut ( DIGEST_WORDS ) ;
451
+ for ( i, word) in digest1. iter_mut ( ) . enumerate ( ) {
452
+ * word = self . load_u32_from_guest ( block1_ptr + ( i * WORD_SIZE ) ) ?;
453
+ }
454
+ for ( i, word) in digest2. iter_mut ( ) . enumerate ( ) {
455
+ * word = self . load_u32_from_guest ( block2_ptr + ( i * WORD_SIZE ) ) ?;
456
+ }
457
+ // tracing::debug!("Compressing block {block:02x?}");
458
+ sha2:: compress256 (
459
+ & mut state,
460
+ & [ * GenericArray :: from_slice ( bytemuck:: cast_slice ( & block) ) ] ,
461
+ ) ;
462
+
463
+ block1_ptr += BLOCK_BYTES ;
464
+ block2_ptr += BLOCK_BYTES ;
454
465
}
455
- // tracing::debug!("Compressing block {block:02x?}");
456
- sha2:: compress256 (
457
- & mut state,
458
- & [ * GenericArray :: from_slice ( bytemuck:: cast_slice ( & block) ) ] ,
459
- ) ;
460
-
461
- block1_ptr += BLOCK_BYTES ;
462
- block2_ptr += BLOCK_BYTES ;
463
466
}
464
467
465
468
// tracing::debug!("ecall_sha: final state: {state:08x?}");
0 commit comments