diff --git a/src/tools/miri/src/helpers.rs b/src/tools/miri/src/helpers.rs index ae5a975bb87ca..c19d691ede6ad 100644 --- a/src/tools/miri/src/helpers.rs +++ b/src/tools/miri/src/helpers.rs @@ -746,6 +746,20 @@ pub trait EvalContextExt<'mir, 'tcx: 'mir>: crate::MiriInterpCxExt<'mir, 'tcx> { Ok(mplace) } + fn deref_pointer_as( + &self, + val: &ImmTy<'tcx, Provenance>, + layout: TyAndLayout<'tcx>, + ) -> InterpResult<'tcx, MPlaceTy<'tcx, Provenance>> { + let this = self.eval_context_ref(); + let mut mplace = this.ref_to_mplace(val)?; + + mplace.layout = layout; + mplace.align = layout.align.abi; + + Ok(mplace) + } + /// Calculates the MPlaceTy given the offset and layout of an access on an operand fn deref_operand_and_offset( &self, diff --git a/src/tools/miri/src/shims/unix/linux/sync.rs b/src/tools/miri/src/shims/unix/linux/sync.rs index e26e29362adae..873b84e30599d 100644 --- a/src/tools/miri/src/shims/unix/linux/sync.rs +++ b/src/tools/miri/src/shims/unix/linux/sync.rs @@ -85,8 +85,11 @@ pub fn futex<'tcx>( return Ok(()); } - let timeout_op = &args[3]; - let timeout_time = if this.ptr_is_null(this.read_pointer(timeout_op)?)? { + let timeout = this.deref_pointer_as( + &this.read_immediate(&args[3])?, + this.libc_ty_layout("timespec"), + )?; + let timeout_time = if this.ptr_is_null(timeout.ptr)? { None } else { let realtime = op & futex_realtime == futex_realtime; @@ -95,7 +98,6 @@ pub fn futex<'tcx>( "`futex` syscall with `op=FUTEX_WAIT` and non-null timeout with `FUTEX_CLOCK_REALTIME`", )?; } - let timeout = this.deref_operand_as(timeout_op, this.libc_ty_layout("timespec"))?; let duration = match this.read_timespec(&timeout)? { Some(duration) => duration, None => {