From 72664f7760f72181741809a177e73349c53e066e Mon Sep 17 00:00:00 2001 From: Ralf Jung Date: Sat, 26 Oct 2024 08:58:48 +0200 Subject: [PATCH 1/3] fix error returned from readdir_r when isolation is enabled --- src/tools/miri/src/shims/unix/fs.rs | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/src/tools/miri/src/shims/unix/fs.rs b/src/tools/miri/src/shims/unix/fs.rs index 4a94d3807a63..c1d113e00cc6 100644 --- a/src/tools/miri/src/shims/unix/fs.rs +++ b/src/tools/miri/src/shims/unix/fs.rs @@ -1130,8 +1130,8 @@ pub trait EvalContextExt<'tcx>: crate::MiriInterpCxExt<'tcx> { // Reject if isolation is enabled. if let IsolatedOp::Reject(reject_with) = this.machine.isolated_op { this.reject_in_isolation("`readdir_r`", reject_with)?; - // Set error code as "EBADF" (bad fd) - return this.set_last_error_and_return_i32(LibcError("EBADF")); + // Return error code, do *not* set `errno`. + return interp_ok(this.eval_libc("EBADF")); } let open_dir = this.machine.dirs.streams.get_mut(&dirp).ok_or_else(|| { From 3f763c776eaeb0f2c088ec1fec6284d16e66564f Mon Sep 17 00:00:00 2001 From: Ralf Jung Date: Sat, 26 Oct 2024 09:02:26 +0200 Subject: [PATCH 2/3] do not use host 'raw_os_error' to compute target error code --- src/tools/miri/src/shims/unix/fs.rs | 35 +++++++++-------------------- 1 file changed, 11 insertions(+), 24 deletions(-) diff --git a/src/tools/miri/src/shims/unix/fs.rs b/src/tools/miri/src/shims/unix/fs.rs index c1d113e00cc6..e88f62ffbb27 100644 --- a/src/tools/miri/src/shims/unix/fs.rs +++ b/src/tools/miri/src/shims/unix/fs.rs @@ -229,6 +229,8 @@ impl FileDescription for FileHandle { TRUE => Ok(()), FALSE => { let mut err = io::Error::last_os_error(); + // This only runs on Windows hosts so we can use `raw_os_error`. + // We have to be careful not to forward that error code to target code. let code: u32 = err.raw_os_error().unwrap().try_into().unwrap(); if matches!(code, ERROR_IO_PENDING | ERROR_LOCK_VIOLATION) { if lock_nb { @@ -337,15 +339,7 @@ trait EvalContextExtPrivate<'tcx>: crate::MiriInterpCxExt<'tcx> { _ => interp_ok(this.eval_libc("DT_UNKNOWN").to_u8()?.into()), } } - Err(e) => - match e.raw_os_error() { - Some(error) => interp_ok(error), - None => - throw_unsup_format!( - "the error {} couldn't be converted to a return value", - e - ), - }, + Err(e) => this.io_error_to_errnum(e)?.to_i32(), } } } @@ -1137,7 +1131,7 @@ pub trait EvalContextExt<'tcx>: crate::MiriInterpCxExt<'tcx> { let open_dir = this.machine.dirs.streams.get_mut(&dirp).ok_or_else(|| { err_unsup_format!("the DIR pointer passed to readdir_r did not come from opendir") })?; - interp_ok(Scalar::from_i32(match open_dir.read_dir.next() { + interp_ok(match open_dir.read_dir.next() { Some(Ok(dir_entry)) => { // Write into entry, write pointer to result, return 0 on success. // The name is written with write_os_str_to_c_str, while the rest of the @@ -1215,25 +1209,18 @@ pub trait EvalContextExt<'tcx>: crate::MiriInterpCxExt<'tcx> { let result_place = this.deref_pointer(result_op)?; this.write_scalar(this.read_scalar(entry_op)?, &result_place)?; - 0 + Scalar::from_i32(0) } None => { // end of stream: return 0, assign *result=NULL this.write_null(&this.deref_pointer(result_op)?)?; - 0 + Scalar::from_i32(0) } - Some(Err(e)) => - match e.raw_os_error() { - // return positive error number on error - Some(error) => error, - None => { - throw_unsup_format!( - "the error {} couldn't be converted to a return value", - e - ) - } - }, - })) + Some(Err(e)) => { + // return positive error number on error (do *not* set last error) + this.io_error_to_errnum(e)? + } + }) } fn closedir(&mut self, dirp_op: &OpTy<'tcx>) -> InterpResult<'tcx, Scalar> { From 4a34e2784b4eb0bb2c0c3740141937c88c4e4cfd Mon Sep 17 00:00:00 2001 From: Ralf Jung Date: Sat, 26 Oct 2024 09:09:14 +0200 Subject: [PATCH 3/3] do not set the file type to an error code --- src/tools/miri/src/shims/unix/fs.rs | 5 ++++- 1 file changed, 4 insertions(+), 1 deletion(-) diff --git a/src/tools/miri/src/shims/unix/fs.rs b/src/tools/miri/src/shims/unix/fs.rs index e88f62ffbb27..eed6a7b04ff2 100644 --- a/src/tools/miri/src/shims/unix/fs.rs +++ b/src/tools/miri/src/shims/unix/fs.rs @@ -339,7 +339,10 @@ trait EvalContextExtPrivate<'tcx>: crate::MiriInterpCxExt<'tcx> { _ => interp_ok(this.eval_libc("DT_UNKNOWN").to_u8()?.into()), } } - Err(e) => this.io_error_to_errnum(e)?.to_i32(), + Err(_) => { + // Fallback on error + interp_ok(this.eval_libc("DT_UNKNOWN").to_u8()?.into()) + } } } }