From acb51b5a50c5e01d40a1971c44891b24d9401b0a Mon Sep 17 00:00:00 2001 From: Pointerbender Date: Thu, 8 Dec 2022 20:56:23 +0100 Subject: [PATCH 01/28] add graceful shim for the custom `O_TMPFILE` linux file opening flag plus test case --- src/shims/unix/fs.rs | 9 +++++++++ tests/pass-dep/shims/libc-fs.rs | 32 +++++++++++++++++++++++++++++++- 2 files changed, 40 insertions(+), 1 deletion(-) diff --git a/src/shims/unix/fs.rs b/src/shims/unix/fs.rs index 988627db56..bf99412af6 100644 --- a/src/shims/unix/fs.rs +++ b/src/shims/unix/fs.rs @@ -605,6 +605,15 @@ pub trait EvalContextExt<'mir, 'tcx: 'mir>: crate::MiriInterpCxExt<'mir, 'tcx> { // (Technically we do not support *not* setting this flag, but we ignore that.) mirror |= o_cloexec; } + if this.tcx.sess.target.os == "linux" { + let o_tmpfile = this.eval_libc_i32("O_TMPFILE")?; + if flag & o_tmpfile != 0 { + // if the flag contains `O_TMPFILE` then we return a graceful error + let eopnotsupp = this.eval_libc("EOPNOTSUPP")?; + this.set_last_error(eopnotsupp)?; + return Ok(-1); + } + } // If `flag` is not equal to `mirror`, there is an unsupported option enabled in `flag`, // then we throw an error. if flag != mirror { diff --git a/tests/pass-dep/shims/libc-fs.rs b/tests/pass-dep/shims/libc-fs.rs index acf16ecb7e..93c0fad9c1 100644 --- a/tests/pass-dep/shims/libc-fs.rs +++ b/tests/pass-dep/shims/libc-fs.rs @@ -6,7 +6,7 @@ use std::convert::TryInto; use std::ffi::CString; -use std::fs::{canonicalize, remove_file, File}; +use std::fs::{canonicalize, remove_dir_all, remove_file, File}; use std::io::{Error, ErrorKind, Write}; use std::os::unix::ffi::OsStrExt; use std::path::PathBuf; @@ -18,6 +18,8 @@ fn main() { test_file_open_unix_allow_two_args(); test_file_open_unix_needs_three_args(); test_file_open_unix_extra_third_arg(); + #[cfg(target_os = "linux")] + test_o_tmpfile_flag(); } fn tmp() -> PathBuf { @@ -45,6 +47,15 @@ fn prepare(filename: &str) -> PathBuf { path } +/// Prepare directory: compute directory name and make sure it does not exist. +#[allow(unused)] +fn prepare_dir(dirname: &str) -> PathBuf { + let path = tmp().join(&dirname); + // Clean the directory for robustness. + remove_dir_all(&path).ok(); + path +} + /// Prepare like above, and also write some initial content to the file. fn prepare_with_content(filename: &str, content: &[u8]) -> PathBuf { let path = prepare(filename); @@ -135,3 +146,22 @@ fn test_readlink() { assert_eq!(res, -1); assert_eq!(Error::last_os_error().kind(), ErrorKind::NotFound); } + +#[cfg(target_os = "linux")] +fn test_o_tmpfile_flag() { + use std::fs::{create_dir, OpenOptions}; + use std::os::unix::fs::OpenOptionsExt; + let dir_path = prepare_dir("miri_test_fs_dir"); + create_dir(&dir_path).unwrap(); + // test that the `O_TMPFILE` custom flag gracefully errors instead of stopping execution + assert_eq!( + Some(libc::EOPNOTSUPP), + OpenOptions::new() + .read(true) + .write(true) + .custom_flags(libc::O_TMPFILE) + .open(dir_path) + .unwrap_err() + .raw_os_error(), + ); +} From 4d697119ab24de683b0ca9d939c662f76c9de626 Mon Sep 17 00:00:00 2001 From: Ralf Jung Date: Fri, 9 Dec 2022 08:54:20 +0100 Subject: [PATCH 02/28] Preparing for merge from rustc --- rust-version | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/rust-version b/rust-version index 8dd18ae98e..781e2c95a2 100644 --- a/rust-version +++ b/rust-version @@ -1 +1 @@ -203c8765ea33c65d888febe0e8219c4bb11b0d89 +7701a7e7d4eed74a106f39fa64899dffd1e1025f From bb7c9e75f55283ac4f91a27df2df6784205fb53c Mon Sep 17 00:00:00 2001 From: Ralf Jung Date: Fri, 9 Dec 2022 08:59:08 +0100 Subject: [PATCH 03/28] fmt and clippy --- src/borrow_tracker/mod.rs | 12 ++++++++++-- src/borrow_tracker/stacked_borrows/diagnostics.rs | 4 +++- src/borrow_tracker/stacked_borrows/mod.rs | 5 +++-- src/diagnostics.rs | 3 ++- src/machine.rs | 5 ++--- 5 files changed, 20 insertions(+), 9 deletions(-) diff --git a/src/borrow_tracker/mod.rs b/src/borrow_tracker/mod.rs index f896a337f4..9f6cbe7f3c 100644 --- a/src/borrow_tracker/mod.rs +++ b/src/borrow_tracker/mod.rs @@ -264,7 +264,11 @@ impl GlobalStateInner { impl<'mir, 'tcx: 'mir> EvalContextExt<'mir, 'tcx> for crate::MiriInterpCx<'mir, 'tcx> {} pub trait EvalContextExt<'mir, 'tcx: 'mir>: crate::MiriInterpCxExt<'mir, 'tcx> { - fn retag_ptr_value(&mut self, kind: RetagKind, val: &ImmTy<'tcx, Provenance>) -> InterpResult<'tcx, ImmTy<'tcx, Provenance>> { + fn retag_ptr_value( + &mut self, + kind: RetagKind, + val: &ImmTy<'tcx, Provenance>, + ) -> InterpResult<'tcx, ImmTy<'tcx, Provenance>> { let this = self.eval_context_mut(); let method = this.machine.borrow_tracker.as_ref().unwrap().borrow().borrow_tracker_method; match method { @@ -272,7 +276,11 @@ pub trait EvalContextExt<'mir, 'tcx: 'mir>: crate::MiriInterpCxExt<'mir, 'tcx> { } } - fn retag_place_contents(&mut self, kind: RetagKind, place: &PlaceTy<'tcx, Provenance>) -> InterpResult<'tcx> { + fn retag_place_contents( + &mut self, + kind: RetagKind, + place: &PlaceTy<'tcx, Provenance>, + ) -> InterpResult<'tcx> { let this = self.eval_context_mut(); let method = this.machine.borrow_tracker.as_ref().unwrap().borrow().borrow_tracker_method; match method { diff --git a/src/borrow_tracker/stacked_borrows/diagnostics.rs b/src/borrow_tracker/stacked_borrows/diagnostics.rs index 24b3489e0d..5f132bf11a 100644 --- a/src/borrow_tracker/stacked_borrows/diagnostics.rs +++ b/src/borrow_tracker/stacked_borrows/diagnostics.rs @@ -462,7 +462,9 @@ impl<'history, 'ecx, 'mir, 'tcx> DiagnosticCx<'history, 'ecx, 'mir, 'tcx> { Operation::Retag(RetagOp { orig_tag, permission, new_tag, .. }) => { let permission = permission .expect("start_grant should set the current permission before popping a tag"); - format!(" due to {permission:?} retag from {orig_tag:?} (that retag created {new_tag:?})") + format!( + " due to {permission:?} retag from {orig_tag:?} (that retag created {new_tag:?})" + ) } }; diff --git a/src/borrow_tracker/stacked_borrows/mod.rs b/src/borrow_tracker/stacked_borrows/mod.rs index ffbc008640..bcdf2e7517 100644 --- a/src/borrow_tracker/stacked_borrows/mod.rs +++ b/src/borrow_tracker/stacked_borrows/mod.rs @@ -14,6 +14,7 @@ use rustc_middle::mir::{Mutability, RetagKind}; use rustc_middle::ty::{ self, layout::{HasParamEnv, LayoutOf}, + Ty, }; use rustc_target::abi::{Abi, Size}; @@ -64,7 +65,7 @@ impl NewPermission { /// A key function: determine the permissions to grant at a retag for the given kind of /// reference/pointer. fn from_ref_ty<'tcx>( - ty: ty::Ty<'tcx>, + ty: Ty<'tcx>, kind: RetagKind, cx: &crate::MiriInterpCx<'_, 'tcx>, ) -> Self { @@ -864,7 +865,7 @@ pub trait EvalContextExt<'mir, 'tcx: 'mir>: crate::MiriInterpCxExt<'mir, 'tcx> { RetagKind::FnEntry => unreachable!(), RetagKind::Raw | RetagKind::Default => RetagCause::Normal, }; - this.sb_retag_reference(&val, new_perm, retag_cause) + this.sb_retag_reference(val, new_perm, retag_cause) } fn sb_retag_place_contents( diff --git a/src/diagnostics.rs b/src/diagnostics.rs index d0fb9f9b0b..c4f4d018f8 100644 --- a/src/diagnostics.rs +++ b/src/diagnostics.rs @@ -393,7 +393,8 @@ impl<'mir, 'tcx> MiriMachine<'mir, 'tcx> { let msg = match &e { CreatedPointerTag(tag, None, _) => format!("created base tag {tag:?}"), - CreatedPointerTag(tag, Some(perm), None) => format!("created {tag:?} with {perm} derived from unknown tag"), + CreatedPointerTag(tag, Some(perm), None) => + format!("created {tag:?} with {perm} derived from unknown tag"), CreatedPointerTag(tag, Some(perm), Some((alloc_id, range, orig_tag))) => format!( "created tag {tag:?} with {perm} at {alloc_id:?}{range:?} derived from {orig_tag:?}" diff --git a/src/machine.rs b/src/machine.rs index e5b1eb2e48..5d43df9cf1 100644 --- a/src/machine.rs +++ b/src/machine.rs @@ -967,9 +967,8 @@ impl<'mir, 'tcx> Machine<'mir, 'tcx> for MiriMachine<'mir, 'tcx> { ptr: Pointer, ) -> InterpResult<'tcx> { match ptr.provenance { - Provenance::Concrete { alloc_id, tag } => { - intptrcast::GlobalStateInner::expose_ptr(ecx, alloc_id, tag) - } + Provenance::Concrete { alloc_id, tag } => + intptrcast::GlobalStateInner::expose_ptr(ecx, alloc_id, tag), Provenance::Wildcard => { // No need to do anything for wildcard pointers as // their provenances have already been previously exposed. From 97c218237e5e977570b84af7eae40ecc4f45fa55 Mon Sep 17 00:00:00 2001 From: Ralf Jung Date: Sun, 11 Dec 2022 09:52:08 +0100 Subject: [PATCH 04/28] Preparing for merge from rustc --- rust-version | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/rust-version b/rust-version index 781e2c95a2..5f1a4428fe 100644 --- a/rust-version +++ b/rust-version @@ -1 +1 @@ -7701a7e7d4eed74a106f39fa64899dffd1e1025f +e1c91213ff80af5b87a197b784b40bcbc8cf3add From 22628ff47a225fffc49307a9a5cf2dc283126eec Mon Sep 17 00:00:00 2001 From: Nia Espera Date: Fri, 9 Dec 2022 17:59:06 +0100 Subject: [PATCH 05/28] add support for variable page sizes to miri --- README.md | 2 ++ src/bin/miri.rs | 12 +++++++++ src/eval.rs | 3 +++ src/intptrcast.rs | 4 +-- src/lib.rs | 2 +- src/machine.rs | 37 ++++++++++++++++++++++----- src/shims/unix/foreign_items.rs | 8 +++--- src/shims/unix/macos/foreign_items.rs | 4 +-- src/shims/windows/foreign_items.rs | 2 +- tests/pass-dep/page_size.rs | 13 ++++++++++ tests/pass-dep/page_size_override.rs | 7 +++++ 11 files changed, 78 insertions(+), 16 deletions(-) create mode 100644 tests/pass-dep/page_size_override.rs diff --git a/README.md b/README.md index dac0a9820b..909e5bd510 100644 --- a/README.md +++ b/README.md @@ -399,6 +399,8 @@ to Miri failing to detect cases of undefined behavior in a program. * `-Zmiri-track-weak-memory-loads` shows a backtrace when weak memory emulation returns an outdated value from a load. This can help diagnose problems that disappear under `-Zmiri-disable-weak-memory-emulation`. +* `-Zmiri-force-page-size=` overrides the default page size for an architecture, in multiples of 1k. + `4` is default for most targets. This value should always be a power of 2 and nonzero. [function ABI]: https://doc.rust-lang.org/reference/items/functions.html#extern-function-qualifier diff --git a/src/bin/miri.rs b/src/bin/miri.rs index fce95b987f..8c01748613 100644 --- a/src/bin/miri.rs +++ b/src/bin/miri.rs @@ -512,6 +512,18 @@ fn main() { }; miri_config.num_cpus = num_cpus; + } else if let Some(param) = arg.strip_prefix("-Zmiri-force-page-size=") { + let page_size = match param.parse::() { + Ok(i) => + if i.is_power_of_two() { + i * 1024 + } else { + show_error!("-Zmiri-force-page-size requires a power of 2: {}", i) + }, + Err(err) => show_error!("-Zmiri-force-page-size requires a `u64`: {}", err), + }; + + miri_config.page_size = Some(page_size); } else { // Forward to rustc. rustc_args.push(arg); diff --git a/src/eval.rs b/src/eval.rs index 7b4973f3b9..9d1574b318 100644 --- a/src/eval.rs +++ b/src/eval.rs @@ -143,6 +143,8 @@ pub struct MiriConfig { pub gc_interval: u32, /// The number of CPUs to be reported by miri. pub num_cpus: u32, + /// Requires Miri to emulate pages of a certain size + pub page_size: Option, } impl Default for MiriConfig { @@ -176,6 +178,7 @@ impl Default for MiriConfig { external_so_file: None, gc_interval: 10_000, num_cpus: 1, + page_size: None, } } } diff --git a/src/intptrcast.rs b/src/intptrcast.rs index c26828b11e..618cf9df7f 100644 --- a/src/intptrcast.rs +++ b/src/intptrcast.rs @@ -51,12 +51,12 @@ impl VisitTags for GlobalStateInner { } impl GlobalStateInner { - pub fn new(config: &MiriConfig) -> Self { + pub fn new(config: &MiriConfig, stack_addr: u64) -> Self { GlobalStateInner { int_to_ptr_map: Vec::default(), base_addr: FxHashMap::default(), exposed: FxHashSet::default(), - next_base_addr: STACK_ADDR, + next_base_addr: stack_addr, provenance_mode: config.provenance_mode, } } diff --git a/src/lib.rs b/src/lib.rs index 4251979797..d65bd10e6f 100644 --- a/src/lib.rs +++ b/src/lib.rs @@ -107,7 +107,7 @@ pub use crate::helpers::EvalContextExt as _; pub use crate::intptrcast::ProvenanceMode; pub use crate::machine::{ AllocExtra, FrameExtra, MiriInterpCx, MiriInterpCxExt, MiriMachine, MiriMemoryKind, - PrimitiveLayouts, Provenance, ProvenanceExtra, PAGE_SIZE, STACK_ADDR, STACK_SIZE, + PrimitiveLayouts, Provenance, ProvenanceExtra, }; pub use crate::mono_hash_map::MonoHashMap; pub use crate::operator::EvalContextExt as _; diff --git a/src/machine.rs b/src/machine.rs index 5d43df9cf1..72f71db34b 100644 --- a/src/machine.rs +++ b/src/machine.rs @@ -31,11 +31,6 @@ use crate::{ *, }; -// Some global facts about the emulated machine. -pub const PAGE_SIZE: u64 = 4 * 1024; // FIXME: adjust to target architecture -pub const STACK_ADDR: u64 = 32 * PAGE_SIZE; // not really about the "stack", but where we start assigning integer addresses to allocations -pub const STACK_SIZE: u64 = 16 * PAGE_SIZE; // whatever - /// Extra data stored with each stack frame pub struct FrameExtra<'tcx> { /// Extra data for Stacked Borrows. @@ -469,6 +464,10 @@ pub struct MiriMachine<'mir, 'tcx> { pub(crate) since_gc: u32, /// The number of CPUs to be reported by miri. pub(crate) num_cpus: u32, + /// Determines Miri's page size and associated values + pub(crate) page_size: u64, + pub(crate) stack_addr: u64, + pub(crate) stack_size: u64, } impl<'mir, 'tcx> MiriMachine<'mir, 'tcx> { @@ -482,11 +481,31 @@ impl<'mir, 'tcx> MiriMachine<'mir, 'tcx> { let rng = StdRng::seed_from_u64(config.seed.unwrap_or(0)); let borrow_tracker = config.borrow_tracker.map(|bt| bt.instanciate_global_state(config)); let data_race = config.data_race_detector.then(|| data_race::GlobalState::new(config)); + let page_size = if let Some(page_size) = config.page_size { + page_size + } else { + let target = &layout_cx.tcx.sess.target; + match target.arch.as_ref() { + "wasm32" | "wasm64" => 64 * 1024, // https://webassembly.github.io/spec/core/exec/runtime.html#memory-instances + "aarch64" => + if target.options.vendor.as_ref() == "apple" { + // No "definitive" source, but see: + // https://www.wwdcnotes.com/notes/wwdc20/10214/ + // https://github.com/ziglang/zig/issues/11308 etc. + 16 * 1024 + } else { + 4 * 1024 + }, + _ => 4 * 1024, + } + }; + let stack_addr = page_size * 32; + let stack_size = page_size * 16; MiriMachine { tcx: layout_cx.tcx, borrow_tracker, data_race, - intptrcast: RefCell::new(intptrcast::GlobalStateInner::new(config)), + intptrcast: RefCell::new(intptrcast::GlobalStateInner::new(config, stack_addr)), // `env_vars` depends on a full interpreter so we cannot properly initialize it yet. env_vars: EnvVars::default(), main_fn_ret_place: None, @@ -548,6 +567,9 @@ impl<'mir, 'tcx> MiriMachine<'mir, 'tcx> { gc_interval: config.gc_interval, since_gc: 0, num_cpus: config.num_cpus, + page_size, + stack_addr, + stack_size, } } @@ -692,6 +714,9 @@ impl VisitTags for MiriMachine<'_, '_> { gc_interval: _, since_gc: _, num_cpus: _, + page_size: _, + stack_addr: _, + stack_size: _, } = self; threads.visit_tags(visit); diff --git a/src/shims/unix/foreign_items.rs b/src/shims/unix/foreign_items.rs index d746f9df90..e851d6d513 100644 --- a/src/shims/unix/foreign_items.rs +++ b/src/shims/unix/foreign_items.rs @@ -234,7 +234,7 @@ pub trait EvalContextExt<'mir, 'tcx: 'mir>: crate::MiriInterpCxExt<'mir, 'tcx> { // FIXME: Which of these are POSIX, and which are GNU/Linux? // At least the names seem to all also exist on macOS. let sysconfs: &[(&str, fn(&MiriInterpCx<'_, '_>) -> Scalar)] = &[ - ("_SC_PAGESIZE", |this| Scalar::from_int(PAGE_SIZE, this.pointer_size())), + ("_SC_PAGESIZE", |this| Scalar::from_int(this.machine.page_size, this.pointer_size())), ("_SC_NPROCESSORS_CONF", |this| Scalar::from_int(this.machine.num_cpus, this.pointer_size())), ("_SC_NPROCESSORS_ONLN", |this| Scalar::from_int(this.machine.num_cpus, this.pointer_size())), // 512 seems to be a reasonable default. The value is not critical, in @@ -496,7 +496,7 @@ pub trait EvalContextExt<'mir, 'tcx: 'mir>: crate::MiriInterpCxExt<'mir, 'tcx> { let [_attr, guard_size] = this.check_shim(abi, Abi::C { unwind: false }, link_name, args)?; let guard_size = this.deref_operand(guard_size)?; let guard_size_layout = this.libc_ty_layout("size_t")?; - this.write_scalar(Scalar::from_uint(crate::PAGE_SIZE, guard_size_layout.size), &guard_size.into())?; + this.write_scalar(Scalar::from_uint(this.machine.page_size, guard_size_layout.size), &guard_size.into())?; // Return success (`0`). this.write_null(dest)?; @@ -525,11 +525,11 @@ pub trait EvalContextExt<'mir, 'tcx: 'mir>: crate::MiriInterpCxExt<'mir, 'tcx> { let size_place = this.deref_operand(size_place)?; this.write_scalar( - Scalar::from_uint(STACK_ADDR, this.pointer_size()), + Scalar::from_uint(this.machine.stack_addr, this.pointer_size()), &addr_place.into(), )?; this.write_scalar( - Scalar::from_uint(STACK_SIZE, this.pointer_size()), + Scalar::from_uint(this.machine.stack_size, this.pointer_size()), &size_place.into(), )?; diff --git a/src/shims/unix/macos/foreign_items.rs b/src/shims/unix/macos/foreign_items.rs index 221dc39697..282bfc8024 100644 --- a/src/shims/unix/macos/foreign_items.rs +++ b/src/shims/unix/macos/foreign_items.rs @@ -162,13 +162,13 @@ pub trait EvalContextExt<'mir, 'tcx: 'mir>: crate::MiriInterpCxExt<'mir, 'tcx> { "pthread_get_stackaddr_np" => { let [thread] = this.check_shim(abi, Abi::C { unwind: false }, link_name, args)?; this.read_scalar(thread)?.to_machine_usize(this)?; - let stack_addr = Scalar::from_uint(STACK_ADDR, this.pointer_size()); + let stack_addr = Scalar::from_uint(this.machine.stack_addr, this.pointer_size()); this.write_scalar(stack_addr, dest)?; } "pthread_get_stacksize_np" => { let [thread] = this.check_shim(abi, Abi::C { unwind: false }, link_name, args)?; this.read_scalar(thread)?.to_machine_usize(this)?; - let stack_size = Scalar::from_uint(STACK_SIZE, this.pointer_size()); + let stack_size = Scalar::from_uint(this.machine.stack_size, this.pointer_size()); this.write_scalar(stack_size, dest)?; } diff --git a/src/shims/windows/foreign_items.rs b/src/shims/windows/foreign_items.rs index e16749c986..05ce81b71a 100644 --- a/src/shims/windows/foreign_items.rs +++ b/src/shims/windows/foreign_items.rs @@ -158,7 +158,7 @@ pub trait EvalContextExt<'mir, 'tcx: 'mir>: crate::MiriInterpCxExt<'mir, 'tcx> { // Set page size. let page_size = system_info.offset(field_offsets[2], dword_layout, &this.tcx)?; this.write_scalar( - Scalar::from_int(PAGE_SIZE, dword_layout.size), + Scalar::from_int(this.machine.page_size, dword_layout.size), &page_size.into(), )?; // Set number of processors. diff --git a/tests/pass-dep/page_size.rs b/tests/pass-dep/page_size.rs index cdcabf3333..fb06031753 100644 --- a/tests/pass-dep/page_size.rs +++ b/tests/pass-dep/page_size.rs @@ -3,4 +3,17 @@ fn main() { // In particular, this checks that it is not 0. assert!(page_size.is_power_of_two(), "page size not a power of two: {}", page_size); + // Most architectures have 4k pages by default + #[cfg(not(any( + target_arch = "wasm32", + target_arch = "wasm64", + all(target_arch = "aarch64", target_vendor = "apple") + )))] + assert!(page_size == 4 * 1024, "non-4k default page size: {}", page_size); + // ... except aarch64-apple with 16k + #[cfg(all(target_arch = "aarch64", target_vendor = "apple"))] + assert!(page_size == 16 * 1024, "aarch64 apple reports non-16k page size: {}", page_size); + // ... and wasm with 64k + #[cfg(any(target_arch = "wasm32", target_arch = "wasm64"))] + assert!(page_size == 64 * 1024, "wasm reports non-64k page size: {}", page_size); } diff --git a/tests/pass-dep/page_size_override.rs b/tests/pass-dep/page_size_override.rs new file mode 100644 index 0000000000..68858f3875 --- /dev/null +++ b/tests/pass-dep/page_size_override.rs @@ -0,0 +1,7 @@ +//@compile-flags: -Zmiri-force-page-size=8 + +fn main() { + let page_size = page_size::get(); + + assert!(page_size == 8 * 1024, "8k page size override not respected: {}", page_size); +} From 0e89b052855810afb1a30a96c26693e1fb241b4c Mon Sep 17 00:00:00 2001 From: Ralf Jung Date: Sun, 11 Dec 2022 23:04:03 +0100 Subject: [PATCH 06/28] add provenance-related test --- tests/pass/provenance.rs | 7 +++++++ 1 file changed, 7 insertions(+) diff --git a/tests/pass/provenance.rs b/tests/pass/provenance.rs index b18d903e36..c411f748a0 100644 --- a/tests/pass/provenance.rs +++ b/tests/pass/provenance.rs @@ -10,6 +10,7 @@ fn main() { bytewise_ptr_methods(); bytewise_custom_memcpy(); bytewise_custom_memcpy_chunked(); + int_load_strip_provenance(); } /// Some basic smoke tests for provenance. @@ -137,3 +138,9 @@ fn bytewise_custom_memcpy_chunked() { assert_eq!(*ptr, 42); } } + +fn int_load_strip_provenance() { + let ptrs = [&42]; + let ints: [usize; 1] = unsafe { mem::transmute(ptrs) }; + assert_eq!(ptrs[0] as *const _ as usize, ints[0]); +} From ef304a018fff19f083a845ad09ee6ea488306e85 Mon Sep 17 00:00:00 2001 From: Ralf Jung Date: Mon, 12 Dec 2022 07:57:17 +0100 Subject: [PATCH 07/28] make flag checks reobust against multi-bit flags --- src/shims/unix/fs.rs | 15 ++++++++------- src/shims/unix/linux/sync.rs | 7 ++++--- src/shims/windows/foreign_items.rs | 3 ++- 3 files changed, 14 insertions(+), 11 deletions(-) diff --git a/src/shims/unix/fs.rs b/src/shims/unix/fs.rs index bf99412af6..0a26657f57 100644 --- a/src/shims/unix/fs.rs +++ b/src/shims/unix/fs.rs @@ -562,17 +562,17 @@ pub trait EvalContextExt<'mir, 'tcx: 'mir>: crate::MiriInterpCxExt<'mir, 'tcx> { let mut mirror = access_mode; let o_append = this.eval_libc_i32("O_APPEND")?; - if flag & o_append != 0 { + if flag & o_append == o_append { options.append(true); mirror |= o_append; } let o_trunc = this.eval_libc_i32("O_TRUNC")?; - if flag & o_trunc != 0 { + if flag & o_trunc == o_trunc { options.truncate(true); mirror |= o_trunc; } let o_creat = this.eval_libc_i32("O_CREAT")?; - if flag & o_creat != 0 { + if flag & o_creat == o_creat { // Get the mode. On macOS, the argument type `mode_t` is actually `u16`, but // C integer promotion rules mean that on the ABI level, it gets passed as `u32` // (see https://github.com/rust-lang/rust/issues/71915). @@ -592,7 +592,7 @@ pub trait EvalContextExt<'mir, 'tcx: 'mir>: crate::MiriInterpCxExt<'mir, 'tcx> { mirror |= o_creat; let o_excl = this.eval_libc_i32("O_EXCL")?; - if flag & o_excl != 0 { + if flag & o_excl == o_excl { mirror |= o_excl; options.create_new(true); } else { @@ -600,14 +600,14 @@ pub trait EvalContextExt<'mir, 'tcx: 'mir>: crate::MiriInterpCxExt<'mir, 'tcx> { } } let o_cloexec = this.eval_libc_i32("O_CLOEXEC")?; - if flag & o_cloexec != 0 { + if flag & o_cloexec == o_cloexec { // We do not need to do anything for this flag because `std` already sets it. // (Technically we do not support *not* setting this flag, but we ignore that.) mirror |= o_cloexec; } if this.tcx.sess.target.os == "linux" { let o_tmpfile = this.eval_libc_i32("O_TMPFILE")?; - if flag & o_tmpfile != 0 { + if flag & o_tmpfile == o_tmpfile { // if the flag contains `O_TMPFILE` then we return a graceful error let eopnotsupp = this.eval_libc("EOPNOTSUPP")?; this.set_last_error(eopnotsupp)?; @@ -1020,7 +1020,8 @@ pub trait EvalContextExt<'mir, 'tcx: 'mir>: crate::MiriInterpCxExt<'mir, 'tcx> { let path = this.read_path_from_c_str(pathname_ptr)?.into_owned(); // See for a discussion of argument sizes. - let empty_path_flag = flags & this.eval_libc("AT_EMPTY_PATH")?.to_i32()? != 0; + let at_ampty_path = this.eval_libc_i32("AT_EMPTY_PATH")?; + let empty_path_flag = flags & at_ampty_path == at_ampty_path; // We only support: // * interpreting `path` as an absolute directory, // * interpreting `path` as a path relative to `dirfd` when the latter is `AT_FDCWD`, or diff --git a/src/shims/unix/linux/sync.rs b/src/shims/unix/linux/sync.rs index 343232c4bb..31461e4c9f 100644 --- a/src/shims/unix/linux/sync.rs +++ b/src/shims/unix/linux/sync.rs @@ -90,7 +90,8 @@ pub fn futex<'tcx>( let timeout_time = if this.ptr_is_null(timeout.ptr)? { None } else { - if op & futex_realtime != 0 { + let realtime = op & futex_realtime == futex_realtime; + if realtime { this.check_no_isolation( "`futex` syscall with `op=FUTEX_WAIT` and non-null timeout with `FUTEX_CLOCK_REALTIME`", )?; @@ -106,14 +107,14 @@ pub fn futex<'tcx>( }; Some(if wait_bitset { // FUTEX_WAIT_BITSET uses an absolute timestamp. - if op & futex_realtime != 0 { + if realtime { Time::RealTime(SystemTime::UNIX_EPOCH.checked_add(duration).unwrap()) } else { Time::Monotonic(this.machine.clock.anchor().checked_add(duration).unwrap()) } } else { // FUTEX_WAIT uses a relative timestamp. - if op & futex_realtime != 0 { + if realtime { Time::RealTime(SystemTime::now().checked_add(duration).unwrap()) } else { Time::Monotonic(this.machine.clock.now().checked_add(duration).unwrap()) diff --git a/src/shims/windows/foreign_items.rs b/src/shims/windows/foreign_items.rs index 05ce81b71a..81af325968 100644 --- a/src/shims/windows/foreign_items.rs +++ b/src/shims/windows/foreign_items.rs @@ -76,7 +76,8 @@ pub trait EvalContextExt<'mir, 'tcx: 'mir>: crate::MiriInterpCxExt<'mir, 'tcx> { this.read_scalar(handle)?.to_machine_isize(this)?; let flags = this.read_scalar(flags)?.to_u32()?; let size = this.read_scalar(size)?.to_machine_usize(this)?; - let zero_init = (flags & 0x00000008) != 0; // HEAP_ZERO_MEMORY + let heap_zero_memory = 0x00000008; // HEAP_ZERO_MEMORY + let zero_init = (flags & heap_zero_memory) == heap_zero_memory; let res = this.malloc(size, zero_init, MiriMemoryKind::WinHeap)?; this.write_pointer(res, dest)?; } From 0169a521aa668f774ce3462d80b54a91f818b112 Mon Sep 17 00:00:00 2001 From: Ralf Jung Date: Mon, 12 Dec 2022 08:14:22 +0100 Subject: [PATCH 08/28] make eval_libc functions ICE on any problem --- src/helpers.rs | 58 ++++++++---- src/shims/env.rs | 18 ++-- src/shims/time.rs | 26 +++--- src/shims/tls.rs | 4 +- src/shims/unix/foreign_items.rs | 10 +- src/shims/unix/fs.rs | 129 +++++++++++++------------- src/shims/unix/linux/foreign_items.rs | 8 +- src/shims/unix/linux/sync.rs | 22 ++--- src/shims/unix/macos/foreign_items.rs | 2 +- src/shims/unix/sync.rs | 66 ++++++------- src/shims/unix/thread.rs | 4 +- src/shims/windows/sync.rs | 28 +++--- src/shims/windows/thread.rs | 4 +- 13 files changed, 200 insertions(+), 179 deletions(-) diff --git a/src/helpers.rs b/src/helpers.rs index 7fb2539ca5..c11c6104c2 100644 --- a/src/helpers.rs +++ b/src/helpers.rs @@ -138,55 +138,77 @@ pub trait EvalContextExt<'mir, 'tcx: 'mir>: crate::MiriInterpCxExt<'mir, 'tcx> { .unwrap_or_else(|| panic!("failed to find required Rust item: {path:?}")) } - /// Evaluates the scalar at the specified path. Returns Some(val) - /// if the path could be resolved, and None otherwise - fn eval_path_scalar(&self, path: &[&str]) -> InterpResult<'tcx, Scalar> { + /// Evaluates the scalar at the specified path. + fn eval_path_scalar(&self, path: &[&str]) -> Scalar { let this = self.eval_context_ref(); let instance = this.resolve_path(path, Namespace::ValueNS); let cid = GlobalId { instance, promoted: None }; // We don't give a span -- this isn't actually used directly by the program anyway. - let const_val = this.eval_global(cid, None)?; + let const_val = this + .eval_global(cid, None) + .unwrap_or_else(|err| panic!("failed to evaluate required Rust item: {path:?}\n{err}")); this.read_scalar(&const_val.into()) + .unwrap_or_else(|err| panic!("failed to read required Rust item: {path:?}\n{err}")) } /// Helper function to get a `libc` constant as a `Scalar`. - fn eval_libc(&self, name: &str) -> InterpResult<'tcx, Scalar> { + fn eval_libc(&self, name: &str) -> Scalar { self.eval_path_scalar(&["libc", name]) } /// Helper function to get a `libc` constant as an `i32`. - fn eval_libc_i32(&self, name: &str) -> InterpResult<'tcx, i32> { + fn eval_libc_i32(&self, name: &str) -> i32 { // TODO: Cache the result. - self.eval_libc(name)?.to_i32() + self.eval_libc(name).to_i32().unwrap_or_else(|_err| { + panic!("required libc item has unexpected type (not `i32`): {name}") + }) + } + + /// Helper function to get a `libc` constant as an `u32`. + fn eval_libc_u32(&self, name: &str) -> u32 { + // TODO: Cache the result. + self.eval_libc(name).to_u32().unwrap_or_else(|_err| { + panic!("required libc item has unexpected type (not `u32`): {name}") + }) } /// Helper function to get a `windows` constant as a `Scalar`. - fn eval_windows(&self, module: &str, name: &str) -> InterpResult<'tcx, Scalar> { + fn eval_windows(&self, module: &str, name: &str) -> Scalar { self.eval_context_ref().eval_path_scalar(&["std", "sys", "windows", module, name]) } + /// Helper function to get a `windows` constant as a `u32`. + fn eval_windows_u32(&self, module: &str, name: &str) -> u32 { + // TODO: Cache the result. + self.eval_windows(module, name).to_u32().unwrap_or_else(|_err| { + panic!("required Windows item has unexpected type (not `u32`): {module}::{name}") + }) + } + /// Helper function to get a `windows` constant as a `u64`. - fn eval_windows_u64(&self, module: &str, name: &str) -> InterpResult<'tcx, u64> { + fn eval_windows_u64(&self, module: &str, name: &str) -> u64 { // TODO: Cache the result. - self.eval_windows(module, name)?.to_u64() + self.eval_windows(module, name).to_u64().unwrap_or_else(|_err| { + panic!("required Windows item has unexpected type (not `u64`): {module}::{name}") + }) } /// Helper function to get the `TyAndLayout` of a `libc` type - fn libc_ty_layout(&self, name: &str) -> InterpResult<'tcx, TyAndLayout<'tcx>> { + fn libc_ty_layout(&self, name: &str) -> TyAndLayout<'tcx> { let this = self.eval_context_ref(); let ty = this .resolve_path(&["libc", name], Namespace::TypeNS) .ty(*this.tcx, ty::ParamEnv::reveal_all()); - this.layout_of(ty) + this.layout_of(ty).unwrap() } /// Helper function to get the `TyAndLayout` of a `windows` type - fn windows_ty_layout(&self, name: &str) -> InterpResult<'tcx, TyAndLayout<'tcx>> { + fn windows_ty_layout(&self, name: &str) -> TyAndLayout<'tcx> { let this = self.eval_context_ref(); let ty = this .resolve_path(&["std", "sys", "windows", "c", name], Namespace::TypeNS) .ty(*this.tcx, ty::ParamEnv::reveal_all()); - this.layout_of(ty) + this.layout_of(ty).unwrap() } /// Project to the given *named* field of the mplace (which must be a struct or union type). @@ -609,14 +631,14 @@ pub trait EvalContextExt<'mir, 'tcx: 'mir>: crate::MiriInterpCxExt<'mir, 'tcx> { if target.families.iter().any(|f| f == "unix") { for &(name, kind) in UNIX_IO_ERROR_TABLE { if err_kind == kind { - return this.eval_libc(name); + return Ok(this.eval_libc(name)); } } throw_unsup_format!("io error {:?} cannot be translated into a raw os error", err_kind) } else if target.families.iter().any(|f| f == "windows") { // FIXME: we have to finish implementing the Windows equivalent of this. use std::io::ErrorKind::*; - this.eval_windows( + Ok(this.eval_windows( "c", match err_kind { NotFound => "ERROR_FILE_NOT_FOUND", @@ -627,7 +649,7 @@ pub trait EvalContextExt<'mir, 'tcx: 'mir>: crate::MiriInterpCxExt<'mir, 'tcx> { err_kind ), }, - ) + )) } else { throw_unsup_format!( "converting io::Error into errnum is unsupported for OS {}", @@ -647,7 +669,7 @@ pub trait EvalContextExt<'mir, 'tcx: 'mir>: crate::MiriInterpCxExt<'mir, 'tcx> { if target.families.iter().any(|f| f == "unix") { let errnum = errnum.to_i32()?; for &(name, kind) in UNIX_IO_ERROR_TABLE { - if errnum == this.eval_libc_i32(name)? { + if errnum == this.eval_libc_i32(name) { return Ok(Some(kind)); } } diff --git a/src/shims/env.rs b/src/shims/env.rs index 80fb4ff2fe..054162a4ea 100644 --- a/src/shims/env.rs +++ b/src/shims/env.rs @@ -170,7 +170,7 @@ pub trait EvalContextExt<'mir, 'tcx: 'mir>: crate::MiriInterpCxExt<'mir, 'tcx> { )) } None => { - let envvar_not_found = this.eval_windows("c", "ERROR_ENVVAR_NOT_FOUND")?; + let envvar_not_found = this.eval_windows("c", "ERROR_ENVVAR_NOT_FOUND"); this.set_last_error(envvar_not_found)?; Scalar::from_u32(0) // return zero upon failure } @@ -240,7 +240,7 @@ pub trait EvalContextExt<'mir, 'tcx: 'mir>: crate::MiriInterpCxExt<'mir, 'tcx> { Ok(0) // return zero on success } else { // name argument is a null pointer, points to an empty string, or points to a string containing an '=' character. - let einval = this.eval_libc("EINVAL")?; + let einval = this.eval_libc("EINVAL"); this.set_last_error(einval)?; Ok(-1) } @@ -274,7 +274,7 @@ pub trait EvalContextExt<'mir, 'tcx: 'mir>: crate::MiriInterpCxExt<'mir, 'tcx> { this.deallocate_ptr(var, None, MiriMemoryKind::Runtime.into())?; this.update_environ()?; } - Ok(this.eval_windows("c", "TRUE")?) + Ok(this.eval_windows("c", "TRUE")) } else { let value = this.read_os_str_from_wide_str(value_ptr)?; let var_ptr = alloc_env_var_as_wide_str(&name, &value, this)?; @@ -282,7 +282,7 @@ pub trait EvalContextExt<'mir, 'tcx: 'mir>: crate::MiriInterpCxExt<'mir, 'tcx> { this.deallocate_ptr(var, None, MiriMemoryKind::Runtime.into())?; } this.update_environ()?; - Ok(this.eval_windows("c", "TRUE")?) + Ok(this.eval_windows("c", "TRUE")) } } @@ -306,7 +306,7 @@ pub trait EvalContextExt<'mir, 'tcx: 'mir>: crate::MiriInterpCxExt<'mir, 'tcx> { Ok(0) } else { // name argument is a null pointer, points to an empty string, or points to a string containing an '=' character. - let einval = this.eval_libc("EINVAL")?; + let einval = this.eval_libc("EINVAL"); this.set_last_error(einval)?; Ok(-1) } @@ -335,7 +335,7 @@ pub trait EvalContextExt<'mir, 'tcx: 'mir>: crate::MiriInterpCxExt<'mir, 'tcx> { if this.write_path_to_c_str(&cwd, buf, size)?.0 { return Ok(buf); } - let erange = this.eval_libc("ERANGE")?; + let erange = this.eval_libc("ERANGE"); this.set_last_error(erange)?; } Err(e) => this.set_last_error_from_io_error(e.kind())?, @@ -411,14 +411,14 @@ pub trait EvalContextExt<'mir, 'tcx: 'mir>: crate::MiriInterpCxExt<'mir, 'tcx> { this.reject_in_isolation("`SetCurrentDirectoryW`", reject_with)?; this.set_last_error_from_io_error(ErrorKind::PermissionDenied)?; - return this.eval_windows("c", "FALSE"); + return Ok(this.eval_windows("c", "FALSE")); } match env::set_current_dir(path) { - Ok(()) => this.eval_windows("c", "TRUE"), + Ok(()) => Ok(this.eval_windows("c", "TRUE")), Err(e) => { this.set_last_error_from_io_error(e.kind())?; - this.eval_windows("c", "FALSE") + Ok(this.eval_windows("c", "FALSE")) } } } diff --git a/src/shims/time.rs b/src/shims/time.rs index d263aab351..ef411eb8aa 100644 --- a/src/shims/time.rs +++ b/src/shims/time.rs @@ -36,26 +36,26 @@ pub trait EvalContextExt<'mir, 'tcx: 'mir>: crate::MiriInterpCxExt<'mir, 'tcx> { // Linux further distinguishes regular and "coarse" clocks, but the "coarse" version // is just specified to be "faster and less precise", so we implement both the same way. absolute_clocks = vec![ - this.eval_libc_i32("CLOCK_REALTIME")?, - this.eval_libc_i32("CLOCK_REALTIME_COARSE")?, + this.eval_libc_i32("CLOCK_REALTIME"), + this.eval_libc_i32("CLOCK_REALTIME_COARSE"), ]; // The second kind is MONOTONIC clocks for which 0 is an arbitrary time point, but they are // never allowed to go backwards. We don't need to do any additonal monotonicity // enforcement because std::time::Instant already guarantees that it is monotonic. relative_clocks = vec![ - this.eval_libc_i32("CLOCK_MONOTONIC")?, - this.eval_libc_i32("CLOCK_MONOTONIC_COARSE")?, + this.eval_libc_i32("CLOCK_MONOTONIC"), + this.eval_libc_i32("CLOCK_MONOTONIC_COARSE"), ]; } "macos" => { - absolute_clocks = vec![this.eval_libc_i32("CLOCK_REALTIME")?]; - relative_clocks = vec![this.eval_libc_i32("CLOCK_MONOTONIC")?]; + absolute_clocks = vec![this.eval_libc_i32("CLOCK_REALTIME")]; + relative_clocks = vec![this.eval_libc_i32("CLOCK_MONOTONIC")]; // Some clocks only seem to exist in the aarch64 version of the target. if this.tcx.sess.target.arch == "aarch64" { // `CLOCK_UPTIME_RAW` supposed to not increment while the system is asleep... but // that's not really something a program running inside Miri can tell, anyway. // We need to support it because std uses it. - relative_clocks.push(this.eval_libc_i32("CLOCK_UPTIME_RAW")?); + relative_clocks.push(this.eval_libc_i32("CLOCK_UPTIME_RAW")); } } target => throw_unsup_format!("`clock_gettime` is not supported on target OS {target}"), @@ -68,7 +68,7 @@ pub trait EvalContextExt<'mir, 'tcx: 'mir>: crate::MiriInterpCxExt<'mir, 'tcx> { this.machine.clock.now().duration_since(this.machine.clock.anchor()) } else { // Unsupported clock. - let einval = this.eval_libc("EINVAL")?; + let einval = this.eval_libc("EINVAL"); this.set_last_error(einval)?; return Ok(Scalar::from_i32(-1)); }; @@ -94,7 +94,7 @@ pub trait EvalContextExt<'mir, 'tcx: 'mir>: crate::MiriInterpCxExt<'mir, 'tcx> { // Using tz is obsolete and should always be null let tz = this.read_pointer(tz_op)?; if !this.ptr_is_null(tz)? { - let einval = this.eval_libc("EINVAL")?; + let einval = this.eval_libc("EINVAL"); this.set_last_error(einval)?; return Ok(-1); } @@ -118,9 +118,9 @@ pub trait EvalContextExt<'mir, 'tcx: 'mir>: crate::MiriInterpCxExt<'mir, 'tcx> { this.assert_target_os("windows", "GetSystemTimeAsFileTime"); this.check_no_isolation("`GetSystemTimeAsFileTime`")?; - let NANOS_PER_SEC = this.eval_windows_u64("time", "NANOS_PER_SEC")?; - let INTERVALS_PER_SEC = this.eval_windows_u64("time", "INTERVALS_PER_SEC")?; - let INTERVALS_TO_UNIX_EPOCH = this.eval_windows_u64("time", "INTERVALS_TO_UNIX_EPOCH")?; + let NANOS_PER_SEC = this.eval_windows_u64("time", "NANOS_PER_SEC"); + let INTERVALS_PER_SEC = this.eval_windows_u64("time", "INTERVALS_PER_SEC"); + let INTERVALS_TO_UNIX_EPOCH = this.eval_windows_u64("time", "INTERVALS_TO_UNIX_EPOCH"); let NANOS_PER_INTERVAL = NANOS_PER_SEC / INTERVALS_PER_SEC; let SECONDS_TO_UNIX_EPOCH = INTERVALS_TO_UNIX_EPOCH / INTERVALS_PER_SEC; @@ -226,7 +226,7 @@ pub trait EvalContextExt<'mir, 'tcx: 'mir>: crate::MiriInterpCxExt<'mir, 'tcx> { let duration = match this.read_timespec(&this.deref_operand(req_op)?)? { Some(duration) => duration, None => { - let einval = this.eval_libc("EINVAL")?; + let einval = this.eval_libc("EINVAL"); this.set_last_error(einval)?; return Ok(-1); } diff --git a/src/shims/tls.rs b/src/shims/tls.rs index 54fdf2872a..7768772338 100644 --- a/src/shims/tls.rs +++ b/src/shims/tls.rs @@ -303,12 +303,12 @@ trait EvalContextPrivExt<'mir, 'tcx: 'mir>: crate::MiriInterpCxExt<'mir, 'tcx> { return Ok(()); } let thread_callback = - this.eval_windows("thread_local_key", "p_thread_callback")?.to_pointer(this)?; + this.eval_windows("thread_local_key", "p_thread_callback").to_pointer(this)?; let thread_callback = this.get_ptr_fn(thread_callback)?.as_instance()?; // FIXME: Technically, the reason should be `DLL_PROCESS_DETACH` when the main thread exits // but std treats both the same. - let reason = this.eval_windows("c", "DLL_THREAD_DETACH")?; + let reason = this.eval_windows("c", "DLL_THREAD_DETACH"); // The signature of this function is `unsafe extern "system" fn(h: c::LPVOID, dwReason: c::DWORD, pv: c::LPVOID)`. // FIXME: `h` should be a handle to the current module and what `pv` should be is unknown diff --git a/src/shims/unix/foreign_items.rs b/src/shims/unix/foreign_items.rs index e851d6d513..f155e11241 100644 --- a/src/shims/unix/foreign_items.rs +++ b/src/shims/unix/foreign_items.rs @@ -196,7 +196,7 @@ pub trait EvalContextExt<'mir, 'tcx: 'mir>: crate::MiriInterpCxExt<'mir, 'tcx> { // Align must be power of 2, and also at least ptr-sized (POSIX rules). // But failure to adhere to this is not UB, it's an error condition. if !align.is_power_of_two() || align < this.pointer_size().bytes() { - let einval = this.eval_libc_i32("EINVAL")?; + let einval = this.eval_libc_i32("EINVAL"); this.write_int(einval, dest)?; } else { if size == 0 { @@ -243,7 +243,7 @@ pub trait EvalContextExt<'mir, 'tcx: 'mir>: crate::MiriInterpCxExt<'mir, 'tcx> { ]; let mut result = None; for &(sysconf_name, value) in sysconfs { - let sysconf_name = this.eval_libc_i32(sysconf_name)?; + let sysconf_name = this.eval_libc_i32(sysconf_name); if sysconf_name == name { result = Some(value(this)); break; @@ -480,7 +480,7 @@ pub trait EvalContextExt<'mir, 'tcx: 'mir>: crate::MiriInterpCxExt<'mir, 'tcx> { None => format!(""), }; let (complete, _) = this.write_os_str_to_c_str(OsStr::new(&formatted), buf, buflen)?; - let ret = if complete { 0 } else { this.eval_libc_i32("ERANGE")? }; + let ret = if complete { 0 } else { this.eval_libc_i32("ERANGE") }; this.write_int(ret, dest)?; } "getpid" => { @@ -495,7 +495,7 @@ pub trait EvalContextExt<'mir, 'tcx: 'mir>: crate::MiriInterpCxExt<'mir, 'tcx> { if this.frame_in_std() => { let [_attr, guard_size] = this.check_shim(abi, Abi::C { unwind: false }, link_name, args)?; let guard_size = this.deref_operand(guard_size)?; - let guard_size_layout = this.libc_ty_layout("size_t")?; + let guard_size_layout = this.libc_ty_layout("size_t"); this.write_scalar(Scalar::from_uint(this.machine.page_size, guard_size_layout.size), &guard_size.into())?; // Return success (`0`). @@ -589,7 +589,7 @@ pub trait EvalContextExt<'mir, 'tcx: 'mir>: crate::MiriInterpCxExt<'mir, 'tcx> { this.write_null(dest)?; } else { this.write_null(&result.into())?; - this.write_scalar(this.eval_libc("ERANGE")?, dest)?; + this.write_scalar(this.eval_libc("ERANGE"), dest)?; } } diff --git a/src/shims/unix/fs.rs b/src/shims/unix/fs.rs index 0a26657f57..22fbd940e7 100644 --- a/src/shims/unix/fs.rs +++ b/src/shims/unix/fs.rs @@ -382,7 +382,7 @@ trait EvalContextExtPrivate<'mir, 'tcx: 'mir>: crate::MiriInterpCxExt<'mir, 'tcx /// types (like `read`, that returns an `i64`). fn handle_not_found>(&mut self) -> InterpResult<'tcx, T> { let this = self.eval_context_mut(); - let ebadf = this.eval_libc("EBADF")?; + let ebadf = this.eval_libc("EBADF"); this.set_last_error(ebadf)?; Ok((-1).into()) } @@ -395,11 +395,11 @@ trait EvalContextExtPrivate<'mir, 'tcx: 'mir>: crate::MiriInterpCxExt<'mir, 'tcx match file_type { Ok(file_type) => { if file_type.is_dir() { - Ok(this.eval_libc("DT_DIR")?.to_u8()?.into()) + Ok(this.eval_libc("DT_DIR").to_u8()?.into()) } else if file_type.is_file() { - Ok(this.eval_libc("DT_REG")?.to_u8()?.into()) + Ok(this.eval_libc("DT_REG").to_u8()?.into()) } else if file_type.is_symlink() { - Ok(this.eval_libc("DT_LNK")?.to_u8()?.into()) + Ok(this.eval_libc("DT_LNK").to_u8()?.into()) } else { // Certain file types are only supported when the host is a Unix system. // (i.e. devices and sockets) If it is, check those cases, if not, fall back to @@ -409,19 +409,19 @@ trait EvalContextExtPrivate<'mir, 'tcx: 'mir>: crate::MiriInterpCxExt<'mir, 'tcx { use std::os::unix::fs::FileTypeExt; if file_type.is_block_device() { - Ok(this.eval_libc("DT_BLK")?.to_u8()?.into()) + Ok(this.eval_libc("DT_BLK").to_u8()?.into()) } else if file_type.is_char_device() { - Ok(this.eval_libc("DT_CHR")?.to_u8()?.into()) + Ok(this.eval_libc("DT_CHR").to_u8()?.into()) } else if file_type.is_fifo() { - Ok(this.eval_libc("DT_FIFO")?.to_u8()?.into()) + Ok(this.eval_libc("DT_FIFO").to_u8()?.into()) } else if file_type.is_socket() { - Ok(this.eval_libc("DT_SOCK")?.to_u8()?.into()) + Ok(this.eval_libc("DT_SOCK").to_u8()?.into()) } else { - Ok(this.eval_libc("DT_UNKNOWN")?.to_u8()?.into()) + Ok(this.eval_libc("DT_UNKNOWN").to_u8()?.into()) } } #[cfg(not(unix))] - Ok(this.eval_libc("DT_UNKNOWN")?.to_u8()?.into()) + Ok(this.eval_libc("DT_UNKNOWN").to_u8()?.into()) } } Err(e) => @@ -532,9 +532,9 @@ pub trait EvalContextExt<'mir, 'tcx: 'mir>: crate::MiriInterpCxExt<'mir, 'tcx> { let mut options = OpenOptions::new(); - let o_rdonly = this.eval_libc_i32("O_RDONLY")?; - let o_wronly = this.eval_libc_i32("O_WRONLY")?; - let o_rdwr = this.eval_libc_i32("O_RDWR")?; + let o_rdonly = this.eval_libc_i32("O_RDONLY"); + let o_wronly = this.eval_libc_i32("O_WRONLY"); + let o_rdwr = this.eval_libc_i32("O_RDWR"); // The first two bits of the flag correspond to the access mode in linux, macOS and // windows. We need to check that in fact the access mode flags for the current target // only use these two bits, otherwise we are in an unsupported target and should error. @@ -561,17 +561,17 @@ pub trait EvalContextExt<'mir, 'tcx: 'mir>: crate::MiriInterpCxExt<'mir, 'tcx> { // options. let mut mirror = access_mode; - let o_append = this.eval_libc_i32("O_APPEND")?; + let o_append = this.eval_libc_i32("O_APPEND"); if flag & o_append == o_append { options.append(true); mirror |= o_append; } - let o_trunc = this.eval_libc_i32("O_TRUNC")?; + let o_trunc = this.eval_libc_i32("O_TRUNC"); if flag & o_trunc == o_trunc { options.truncate(true); mirror |= o_trunc; } - let o_creat = this.eval_libc_i32("O_CREAT")?; + let o_creat = this.eval_libc_i32("O_CREAT"); if flag & o_creat == o_creat { // Get the mode. On macOS, the argument type `mode_t` is actually `u16`, but // C integer promotion rules mean that on the ABI level, it gets passed as `u32` @@ -591,7 +591,7 @@ pub trait EvalContextExt<'mir, 'tcx: 'mir>: crate::MiriInterpCxExt<'mir, 'tcx> { mirror |= o_creat; - let o_excl = this.eval_libc_i32("O_EXCL")?; + let o_excl = this.eval_libc_i32("O_EXCL"); if flag & o_excl == o_excl { mirror |= o_excl; options.create_new(true); @@ -599,17 +599,17 @@ pub trait EvalContextExt<'mir, 'tcx: 'mir>: crate::MiriInterpCxExt<'mir, 'tcx> { options.create(true); } } - let o_cloexec = this.eval_libc_i32("O_CLOEXEC")?; + let o_cloexec = this.eval_libc_i32("O_CLOEXEC"); if flag & o_cloexec == o_cloexec { // We do not need to do anything for this flag because `std` already sets it. // (Technically we do not support *not* setting this flag, but we ignore that.) mirror |= o_cloexec; } if this.tcx.sess.target.os == "linux" { - let o_tmpfile = this.eval_libc_i32("O_TMPFILE")?; + let o_tmpfile = this.eval_libc_i32("O_TMPFILE"); if flag & o_tmpfile == o_tmpfile { // if the flag contains `O_TMPFILE` then we return a graceful error - let eopnotsupp = this.eval_libc("EOPNOTSUPP")?; + let eopnotsupp = this.eval_libc("EOPNOTSUPP"); this.set_last_error(eopnotsupp)?; return Ok(-1); } @@ -657,18 +657,18 @@ pub trait EvalContextExt<'mir, 'tcx: 'mir>: crate::MiriInterpCxExt<'mir, 'tcx> { } // We only support getting the flags for a descriptor. - if cmd == this.eval_libc_i32("F_GETFD")? { + if cmd == this.eval_libc_i32("F_GETFD") { // Currently this is the only flag that `F_GETFD` returns. It is OK to just return the // `FD_CLOEXEC` value without checking if the flag is set for the file because `std` // always sets this flag when opening a file. However we still need to check that the // file itself is open. if this.machine.file_handler.handles.contains_key(&fd) { - Ok(this.eval_libc_i32("FD_CLOEXEC")?) + Ok(this.eval_libc_i32("FD_CLOEXEC")) } else { this.handle_not_found() } - } else if cmd == this.eval_libc_i32("F_DUPFD")? - || cmd == this.eval_libc_i32("F_DUPFD_CLOEXEC")? + } else if cmd == this.eval_libc_i32("F_DUPFD") + || cmd == this.eval_libc_i32("F_DUPFD_CLOEXEC") { // Note that we always assume the FD_CLOEXEC flag is set for every open file, in part // because exec() isn't supported. The F_DUPFD and F_DUPFD_CLOEXEC commands only @@ -697,7 +697,7 @@ pub trait EvalContextExt<'mir, 'tcx: 'mir>: crate::MiriInterpCxExt<'mir, 'tcx> { } None => this.handle_not_found(), } - } else if this.tcx.sess.target.os == "macos" && cmd == this.eval_libc_i32("F_FULLFSYNC")? { + } else if this.tcx.sess.target.os == "macos" && cmd == this.eval_libc_i32("F_FULLFSYNC") { if let Some(file_descriptor) = this.machine.file_handler.handles.get(&fd) { // FIXME: Support fullfsync for all FDs let FileHandle { file, writable } = file_descriptor.as_file_handle()?; @@ -830,14 +830,14 @@ pub trait EvalContextExt<'mir, 'tcx: 'mir>: crate::MiriInterpCxExt<'mir, 'tcx> { let offset = this.read_scalar(offset_op)?.to_i64()?; let whence = this.read_scalar(whence_op)?.to_i32()?; - let seek_from = if whence == this.eval_libc_i32("SEEK_SET")? { + let seek_from = if whence == this.eval_libc_i32("SEEK_SET") { SeekFrom::Start(u64::try_from(offset).unwrap()) - } else if whence == this.eval_libc_i32("SEEK_CUR")? { + } else if whence == this.eval_libc_i32("SEEK_CUR") { SeekFrom::Current(offset) - } else if whence == this.eval_libc_i32("SEEK_END")? { + } else if whence == this.eval_libc_i32("SEEK_END") { SeekFrom::End(offset) } else { - let einval = this.eval_libc("EINVAL")?; + let einval = this.eval_libc("EINVAL"); this.set_last_error(einval)?; return Ok(Scalar::from_i64(-1)); }; @@ -916,7 +916,7 @@ pub trait EvalContextExt<'mir, 'tcx: 'mir>: crate::MiriInterpCxExt<'mir, 'tcx> { // Reject if isolation is enabled. if let IsolatedOp::Reject(reject_with) = this.machine.isolated_op { this.reject_in_isolation("`stat`", reject_with)?; - let eacc = this.eval_libc("EACCES")?; + let eacc = this.eval_libc("EACCES"); this.set_last_error(eacc)?; return Ok(Scalar::from_i32(-1)); } @@ -945,7 +945,7 @@ pub trait EvalContextExt<'mir, 'tcx: 'mir>: crate::MiriInterpCxExt<'mir, 'tcx> { // Reject if isolation is enabled. if let IsolatedOp::Reject(reject_with) = this.machine.isolated_op { this.reject_in_isolation("`lstat`", reject_with)?; - let eacc = this.eval_libc("EACCES")?; + let eacc = this.eval_libc("EACCES"); this.set_last_error(eacc)?; return Ok(Scalar::from_i32(-1)); } @@ -1003,7 +1003,7 @@ pub trait EvalContextExt<'mir, 'tcx: 'mir>: crate::MiriInterpCxExt<'mir, 'tcx> { // If the statxbuf or pathname pointers are null, the function fails with `EFAULT`. if this.ptr_is_null(statxbuf_ptr)? || this.ptr_is_null(pathname_ptr)? { - let efault = this.eval_libc("EFAULT")?; + let efault = this.eval_libc("EFAULT"); this.set_last_error(efault)?; return Ok(-1); } @@ -1014,13 +1014,13 @@ pub trait EvalContextExt<'mir, 'tcx: 'mir>: crate::MiriInterpCxExt<'mir, 'tcx> { // as `isize`s instead of having the proper types. Thus, we have to recover the layout of // `statxbuf_op` by using the `libc::statx` struct type. let statxbuf = { - let statx_layout = this.libc_ty_layout("statx")?; + let statx_layout = this.libc_ty_layout("statx"); MPlaceTy::from_aligned_ptr(statxbuf_ptr, statx_layout) }; let path = this.read_path_from_c_str(pathname_ptr)?.into_owned(); // See for a discussion of argument sizes. - let at_ampty_path = this.eval_libc_i32("AT_EMPTY_PATH")?; + let at_ampty_path = this.eval_libc_i32("AT_EMPTY_PATH"); let empty_path_flag = flags & at_ampty_path == at_ampty_path; // We only support: // * interpreting `path` as an absolute directory, @@ -1030,7 +1030,7 @@ pub trait EvalContextExt<'mir, 'tcx: 'mir>: crate::MiriInterpCxExt<'mir, 'tcx> { // Other behaviors cannot be tested from `libstd` and thus are not implemented. If you // found this error, please open an issue reporting it. if !(path.is_absolute() - || dirfd == this.eval_libc_i32("AT_FDCWD")? + || dirfd == this.eval_libc_i32("AT_FDCWD") || (path.as_os_str().is_empty() && empty_path_flag)) { throw_unsup_format!( @@ -1043,16 +1043,16 @@ pub trait EvalContextExt<'mir, 'tcx: 'mir>: crate::MiriInterpCxExt<'mir, 'tcx> { // Reject if isolation is enabled. if let IsolatedOp::Reject(reject_with) = this.machine.isolated_op { this.reject_in_isolation("`statx`", reject_with)?; - let ecode = if path.is_absolute() || dirfd == this.eval_libc_i32("AT_FDCWD")? { + let ecode = if path.is_absolute() || dirfd == this.eval_libc_i32("AT_FDCWD") { // since `path` is provided, either absolute or // relative to CWD, `EACCES` is the most relevant. - this.eval_libc("EACCES")? + this.eval_libc("EACCES") } else { // `dirfd` is set to target file, and `path` is empty // (or we would have hit the `throw_unsup_format` // above). `EACCES` would violate the spec. assert!(empty_path_flag); - this.eval_libc("EBADF")? + this.eval_libc("EBADF") }; this.set_last_error(ecode)?; return Ok(-1); @@ -1062,12 +1062,11 @@ pub trait EvalContextExt<'mir, 'tcx: 'mir>: crate::MiriInterpCxExt<'mir, 'tcx> { // However `statx` is allowed to return information that was not requested or to not // return information that was requested. This `mask` represents the information we can // actually provide for any target. - let mut mask = - this.eval_libc("STATX_TYPE")?.to_u32()? | this.eval_libc("STATX_SIZE")?.to_u32()?; + let mut mask = this.eval_libc_u32("STATX_TYPE") | this.eval_libc_u32("STATX_SIZE"); // If the `AT_SYMLINK_NOFOLLOW` flag is set, we query the file's metadata without following // symbolic links. - let follow_symlink = flags & this.eval_libc("AT_SYMLINK_NOFOLLOW")?.to_i32()? == 0; + let follow_symlink = flags & this.eval_libc_i32("AT_SYMLINK_NOFOLLOW") == 0; // If the path is empty, and the AT_EMPTY_PATH flag is set, we query the open file // represented by dirfd, whether it's a directory or otherwise. @@ -1096,7 +1095,7 @@ pub trait EvalContextExt<'mir, 'tcx: 'mir>: crate::MiriInterpCxExt<'mir, 'tcx> { let (access_sec, access_nsec) = metadata .accessed .map(|tup| { - mask |= this.eval_libc("STATX_ATIME")?.to_u32()?; + mask |= this.eval_libc_u32("STATX_ATIME"); InterpResult::Ok(tup) }) .unwrap_or_else(|| Ok((0, 0)))?; @@ -1104,7 +1103,7 @@ pub trait EvalContextExt<'mir, 'tcx: 'mir>: crate::MiriInterpCxExt<'mir, 'tcx> { let (created_sec, created_nsec) = metadata .created .map(|tup| { - mask |= this.eval_libc("STATX_BTIME")?.to_u32()?; + mask |= this.eval_libc_u32("STATX_BTIME"); InterpResult::Ok(tup) }) .unwrap_or_else(|| Ok((0, 0)))?; @@ -1112,7 +1111,7 @@ pub trait EvalContextExt<'mir, 'tcx: 'mir>: crate::MiriInterpCxExt<'mir, 'tcx> { let (modified_sec, modified_nsec) = metadata .modified .map(|tup| { - mask |= this.eval_libc("STATX_MTIME")?.to_u32()?; + mask |= this.eval_libc_u32("STATX_MTIME"); InterpResult::Ok(tup) }) .unwrap_or_else(|| Ok((0, 0)))?; @@ -1185,7 +1184,7 @@ pub trait EvalContextExt<'mir, 'tcx: 'mir>: crate::MiriInterpCxExt<'mir, 'tcx> { let newpath_ptr = this.read_pointer(newpath_op)?; if this.ptr_is_null(oldpath_ptr)? || this.ptr_is_null(newpath_ptr)? { - let efault = this.eval_libc("EFAULT")?; + let efault = this.eval_libc("EFAULT"); this.set_last_error(efault)?; return Ok(-1); } @@ -1272,7 +1271,7 @@ pub trait EvalContextExt<'mir, 'tcx: 'mir>: crate::MiriInterpCxExt<'mir, 'tcx> { // Reject if isolation is enabled. if let IsolatedOp::Reject(reject_with) = this.machine.isolated_op { this.reject_in_isolation("`opendir`", reject_with)?; - let eacc = this.eval_libc("EACCES")?; + let eacc = this.eval_libc("EACCES"); this.set_last_error(eacc)?; return Ok(Scalar::null_ptr(this)); } @@ -1308,7 +1307,7 @@ pub trait EvalContextExt<'mir, 'tcx: 'mir>: crate::MiriInterpCxExt<'mir, 'tcx> { // Reject if isolation is enabled. if let IsolatedOp::Reject(reject_with) = this.machine.isolated_op { this.reject_in_isolation("`readdir`", reject_with)?; - let eacc = this.eval_libc("EBADF")?; + let eacc = this.eval_libc("EBADF"); this.set_last_error(eacc)?; return Ok(Scalar::null_ptr(this)); } @@ -1337,7 +1336,7 @@ pub trait EvalContextExt<'mir, 'tcx: 'mir>: crate::MiriInterpCxExt<'mir, 'tcx> { let name_bytes = os_str_to_bytes(&name)?; let name_len = u64::try_from(name_bytes.len()).unwrap(); - let dirent64_layout = this.libc_ty_layout("dirent64")?; + let dirent64_layout = this.libc_ty_layout("dirent64"); let d_name_offset = dirent64_layout.fields.offset(4 /* d_name */).bytes(); let size = d_name_offset.checked_add(name_len).unwrap(); @@ -1532,13 +1531,13 @@ pub trait EvalContextExt<'mir, 'tcx: 'mir>: crate::MiriInterpCxExt<'mir, 'tcx> { let result = file.set_len(length); this.try_unwrap_io_result(result.map(|_| 0i32))? } else { - let einval = this.eval_libc("EINVAL")?; + let einval = this.eval_libc("EINVAL"); this.set_last_error(einval)?; -1 } } else { // The file is not writable - let einval = this.eval_libc("EINVAL")?; + let einval = this.eval_libc("EINVAL"); this.set_last_error(einval)?; -1 } @@ -1612,15 +1611,15 @@ pub trait EvalContextExt<'mir, 'tcx: 'mir>: crate::MiriInterpCxExt<'mir, 'tcx> { let flags = this.read_scalar(flags_op)?.to_i32()?; if offset < 0 || nbytes < 0 { - let einval = this.eval_libc("EINVAL")?; + let einval = this.eval_libc("EINVAL"); this.set_last_error(einval)?; return Ok(Scalar::from_i32(-1)); } - let allowed_flags = this.eval_libc_i32("SYNC_FILE_RANGE_WAIT_BEFORE")? - | this.eval_libc_i32("SYNC_FILE_RANGE_WRITE")? - | this.eval_libc_i32("SYNC_FILE_RANGE_WAIT_AFTER")?; + let allowed_flags = this.eval_libc_i32("SYNC_FILE_RANGE_WAIT_BEFORE") + | this.eval_libc_i32("SYNC_FILE_RANGE_WRITE") + | this.eval_libc_i32("SYNC_FILE_RANGE_WAIT_AFTER"); if flags & allowed_flags != flags { - let einval = this.eval_libc("EINVAL")?; + let einval = this.eval_libc("EINVAL"); this.set_last_error(einval)?; return Ok(Scalar::from_i32(-1)); } @@ -1657,7 +1656,7 @@ pub trait EvalContextExt<'mir, 'tcx: 'mir>: crate::MiriInterpCxExt<'mir, 'tcx> { // Reject if isolation is enabled. if let IsolatedOp::Reject(reject_with) = this.machine.isolated_op { this.reject_in_isolation("`readlink`", reject_with)?; - let eacc = this.eval_libc("EACCES")?; + let eacc = this.eval_libc("EACCES"); this.set_last_error(eacc)?; return Ok(-1); } @@ -1702,7 +1701,7 @@ pub trait EvalContextExt<'mir, 'tcx: 'mir>: crate::MiriInterpCxExt<'mir, 'tcx> { } } // Fallback when the FD was not found or isolation is enabled. - let enotty = this.eval_libc("ENOTTY")?; + let enotty = this.eval_libc("ENOTTY"); this.set_last_error(enotty)?; Ok(Scalar::from_i32(0)) } @@ -1721,7 +1720,7 @@ pub trait EvalContextExt<'mir, 'tcx: 'mir>: crate::MiriInterpCxExt<'mir, 'tcx> { // Reject if isolation is enabled. if let IsolatedOp::Reject(reject_with) = this.machine.isolated_op { this.reject_in_isolation("`realpath`", reject_with)?; - let eacc = this.eval_libc("EACCES")?; + let eacc = this.eval_libc("EACCES"); this.set_last_error(eacc)?; return Ok(Scalar::from_machine_usize(0, this)); } @@ -1730,7 +1729,7 @@ pub trait EvalContextExt<'mir, 'tcx: 'mir>: crate::MiriInterpCxExt<'mir, 'tcx> { match result { Ok(resolved) => { let path_max = this - .eval_libc_i32("PATH_MAX")? + .eval_libc_i32("PATH_MAX") .try_into() .expect("PATH_MAX does not fit in u64"); let dest = if this.ptr_is_null(processed_ptr)? { @@ -1752,7 +1751,7 @@ pub trait EvalContextExt<'mir, 'tcx: 'mir>: crate::MiriInterpCxExt<'mir, 'tcx> { // Note that we do not explicitly handle `FILENAME_MAX` // (different from `PATH_MAX` above) as it is Linux-specific and // seems like a bit of a mess anyway: . - let enametoolong = this.eval_libc("ENAMETOOLONG")?; + let enametoolong = this.eval_libc("ENAMETOOLONG"); this.set_last_error(enametoolong)?; return Ok(Scalar::from_machine_usize(0, this)); } @@ -1785,7 +1784,7 @@ pub trait EvalContextExt<'mir, 'tcx: 'mir>: crate::MiriInterpCxExt<'mir, 'tcx> { // * The value of `TMP_MAX` is at least 25. // * On XSI-conformant systems, the value of `TMP_MAX` is at least 10000. // See . - let max_attempts = this.eval_libc("TMP_MAX")?.to_u32()?; + let max_attempts = this.eval_libc_u32("TMP_MAX"); // Get the raw bytes from the template -- as a byte slice, this is a string in the target // (and the target is unix, so a byte slice is the right representation). @@ -1796,7 +1795,7 @@ pub trait EvalContextExt<'mir, 'tcx: 'mir>: crate::MiriInterpCxExt<'mir, 'tcx> { // Reject if isolation is enabled. if let IsolatedOp::Reject(reject_with) = this.machine.isolated_op { this.reject_in_isolation("`mkstemp`", reject_with)?; - let eacc = this.eval_libc("EACCES")?; + let eacc = this.eval_libc("EACCES"); this.set_last_error(eacc)?; return Ok(-1); } @@ -1814,7 +1813,7 @@ pub trait EvalContextExt<'mir, 'tcx: 'mir>: crate::MiriInterpCxExt<'mir, 'tcx> { // If we don't find the suffix, it is an error. if last_six_char_bytes != suffix_bytes { - let einval = this.eval_libc("EINVAL")?; + let einval = this.eval_libc("EINVAL"); this.set_last_error(einval)?; return Ok(-1); } @@ -1890,7 +1889,7 @@ pub trait EvalContextExt<'mir, 'tcx: 'mir>: crate::MiriInterpCxExt<'mir, 'tcx> { } // We ran out of attempts to create the file, return an error. - let eexist = this.eval_libc("EEXIST")?; + let eexist = this.eval_libc("EEXIST"); this.set_last_error(eexist)?; Ok(-1) } @@ -1968,7 +1967,7 @@ impl FileMetadata { "S_IFLNK" }; - let mode = ecx.eval_libc(mode_name)?; + let mode = ecx.eval_libc(mode_name); let size = metadata.len(); diff --git a/src/shims/unix/linux/foreign_items.rs b/src/shims/unix/linux/foreign_items.rs index 34076e842d..ff7b2b352f 100644 --- a/src/shims/unix/linux/foreign_items.rs +++ b/src/shims/unix/linux/foreign_items.rs @@ -88,11 +88,11 @@ pub trait EvalContextExt<'mir, 'tcx: 'mir>: crate::MiriInterpCxExt<'mir, 'tcx> { // argument, we have to also check all arguments *before* it to ensure that they // have the right type. - let sys_getrandom = this.eval_libc("SYS_getrandom")?.to_machine_usize(this)?; + let sys_getrandom = this.eval_libc("SYS_getrandom").to_machine_usize(this)?; - let sys_statx = this.eval_libc("SYS_statx")?.to_machine_usize(this)?; + let sys_statx = this.eval_libc("SYS_statx").to_machine_usize(this)?; - let sys_futex = this.eval_libc("SYS_futex")?.to_machine_usize(this)?; + let sys_futex = this.eval_libc("SYS_futex").to_machine_usize(this)?; if args.is_empty() { throw_ub_format!( @@ -150,7 +150,7 @@ pub trait EvalContextExt<'mir, 'tcx: 'mir>: crate::MiriInterpCxExt<'mir, 'tcx> { this.read_scalar(cpusetsize)?.to_machine_usize(this)?; this.deref_operand(mask)?; // FIXME: we just return an error; `num_cpus` then falls back to `sysconf`. - let einval = this.eval_libc("EINVAL")?; + let einval = this.eval_libc("EINVAL"); this.set_last_error(einval)?; this.write_scalar(Scalar::from_i32(-1), dest)?; } diff --git a/src/shims/unix/linux/sync.rs b/src/shims/unix/linux/sync.rs index 31461e4c9f..ef43c9b0ff 100644 --- a/src/shims/unix/linux/sync.rs +++ b/src/shims/unix/linux/sync.rs @@ -37,12 +37,12 @@ pub fn futex<'tcx>( let addr = MPlaceTy::from_aligned_ptr(addr, this.machine.layouts.i32); let addr_usize = addr.ptr.addr().bytes(); - let futex_private = this.eval_libc_i32("FUTEX_PRIVATE_FLAG")?; - let futex_wait = this.eval_libc_i32("FUTEX_WAIT")?; - let futex_wait_bitset = this.eval_libc_i32("FUTEX_WAIT_BITSET")?; - let futex_wake = this.eval_libc_i32("FUTEX_WAKE")?; - let futex_wake_bitset = this.eval_libc_i32("FUTEX_WAKE_BITSET")?; - let futex_realtime = this.eval_libc_i32("FUTEX_CLOCK_REALTIME")?; + let futex_private = this.eval_libc_i32("FUTEX_PRIVATE_FLAG"); + let futex_wait = this.eval_libc_i32("FUTEX_WAIT"); + let futex_wait_bitset = this.eval_libc_i32("FUTEX_WAIT_BITSET"); + let futex_wake = this.eval_libc_i32("FUTEX_WAKE"); + let futex_wake_bitset = this.eval_libc_i32("FUTEX_WAKE_BITSET"); + let futex_realtime = this.eval_libc_i32("FUTEX_CLOCK_REALTIME"); // FUTEX_PRIVATE enables an optimization that stops it from working across processes. // Miri doesn't support that anyway, so we ignore that flag. @@ -79,7 +79,7 @@ pub fn futex<'tcx>( }; if bitset == 0 { - let einval = this.eval_libc("EINVAL")?; + let einval = this.eval_libc("EINVAL"); this.set_last_error(einval)?; this.write_scalar(Scalar::from_machine_isize(-1, this), dest)?; return Ok(()); @@ -99,7 +99,7 @@ pub fn futex<'tcx>( let duration = match this.read_timespec(&timeout)? { Some(duration) => duration, None => { - let einval = this.eval_libc("EINVAL")?; + let einval = this.eval_libc("EINVAL"); this.set_last_error(einval)?; this.write_scalar(Scalar::from_machine_isize(-1, this), dest)?; return Ok(()); @@ -194,7 +194,7 @@ pub fn futex<'tcx>( fn call(&self, this: &mut MiriInterpCx<'mir, 'tcx>) -> InterpResult<'tcx> { this.unblock_thread(self.thread); this.futex_remove_waiter(self.addr_usize, self.thread); - let etimedout = this.eval_libc("ETIMEDOUT")?; + let etimedout = this.eval_libc("ETIMEDOUT"); this.set_last_error(etimedout)?; this.write_scalar(Scalar::from_machine_isize(-1, this), &self.dest)?; @@ -211,7 +211,7 @@ pub fn futex<'tcx>( } else { // The futex value doesn't match the expected value, so we return failure // right away without sleeping: -1 and errno set to EAGAIN. - let eagain = this.eval_libc("EAGAIN")?; + let eagain = this.eval_libc("EAGAIN"); this.set_last_error(eagain)?; this.write_scalar(Scalar::from_machine_isize(-1, this), dest)?; } @@ -237,7 +237,7 @@ pub fn futex<'tcx>( u32::MAX }; if bitset == 0 { - let einval = this.eval_libc("EINVAL")?; + let einval = this.eval_libc("EINVAL"); this.set_last_error(einval)?; this.write_scalar(Scalar::from_machine_isize(-1, this), dest)?; return Ok(()); diff --git a/src/shims/unix/macos/foreign_items.rs b/src/shims/unix/macos/foreign_items.rs index 282bfc8024..d616126cb2 100644 --- a/src/shims/unix/macos/foreign_items.rs +++ b/src/shims/unix/macos/foreign_items.rs @@ -176,7 +176,7 @@ pub trait EvalContextExt<'mir, 'tcx: 'mir>: crate::MiriInterpCxExt<'mir, 'tcx> { "pthread_setname_np" => { let [name] = this.check_shim(abi, Abi::C { unwind: false }, link_name, args)?; let thread = this.pthread_self()?; - let max_len = this.eval_libc("MAXTHREADNAMESIZE")?.to_machine_usize(this)?; + let max_len = this.eval_libc("MAXTHREADNAMESIZE").to_machine_usize(this)?; let res = this.pthread_setname_np( thread, this.read_scalar(name)?, diff --git a/src/shims/unix/sync.rs b/src/shims/unix/sync.rs index f9b5774f00..b3c474dd3c 100644 --- a/src/shims/unix/sync.rs +++ b/src/shims/unix/sync.rs @@ -21,14 +21,14 @@ fn is_mutex_kind_default<'mir, 'tcx: 'mir>( ecx: &mut MiriInterpCx<'mir, 'tcx>, kind: i32, ) -> InterpResult<'tcx, bool> { - Ok(kind == ecx.eval_libc_i32("PTHREAD_MUTEX_DEFAULT")?) + Ok(kind == ecx.eval_libc_i32("PTHREAD_MUTEX_DEFAULT")) } fn is_mutex_kind_normal<'mir, 'tcx: 'mir>( ecx: &mut MiriInterpCx<'mir, 'tcx>, kind: i32, ) -> InterpResult<'tcx, bool> { - let mutex_normal_kind = ecx.eval_libc_i32("PTHREAD_MUTEX_NORMAL")?; + let mutex_normal_kind = ecx.eval_libc_i32("PTHREAD_MUTEX_NORMAL"); Ok(kind == (mutex_normal_kind | PTHREAD_MUTEX_NORMAL_FLAG)) } @@ -217,7 +217,7 @@ pub trait EvalContextExt<'mir, 'tcx: 'mir>: crate::MiriInterpCxExt<'mir, 'tcx> { ) -> InterpResult<'tcx, i32> { let this = self.eval_context_mut(); - let default_kind = this.eval_libc_i32("PTHREAD_MUTEX_DEFAULT")?; + let default_kind = this.eval_libc_i32("PTHREAD_MUTEX_DEFAULT"); mutexattr_set_kind(this, attr_op, default_kind)?; Ok(0) @@ -231,7 +231,7 @@ pub trait EvalContextExt<'mir, 'tcx: 'mir>: crate::MiriInterpCxExt<'mir, 'tcx> { let this = self.eval_context_mut(); let kind = this.read_scalar(kind_op)?.to_i32()?; - if kind == this.eval_libc_i32("PTHREAD_MUTEX_NORMAL")? { + if kind == this.eval_libc_i32("PTHREAD_MUTEX_NORMAL") { // In `glibc` implementation, the numeric values of // `PTHREAD_MUTEX_NORMAL` and `PTHREAD_MUTEX_DEFAULT` are equal. // However, a mutex created by explicitly passing @@ -247,17 +247,17 @@ pub trait EvalContextExt<'mir, 'tcx: 'mir>: crate::MiriInterpCxExt<'mir, 'tcx> { let normal_kind = kind | PTHREAD_MUTEX_NORMAL_FLAG; // Check that after setting the flag, the kind is distinguishable // from all other kinds. - assert_ne!(normal_kind, this.eval_libc_i32("PTHREAD_MUTEX_DEFAULT")?); - assert_ne!(normal_kind, this.eval_libc_i32("PTHREAD_MUTEX_ERRORCHECK")?); - assert_ne!(normal_kind, this.eval_libc_i32("PTHREAD_MUTEX_RECURSIVE")?); + assert_ne!(normal_kind, this.eval_libc_i32("PTHREAD_MUTEX_DEFAULT")); + assert_ne!(normal_kind, this.eval_libc_i32("PTHREAD_MUTEX_ERRORCHECK")); + assert_ne!(normal_kind, this.eval_libc_i32("PTHREAD_MUTEX_RECURSIVE")); mutexattr_set_kind(this, attr_op, normal_kind)?; - } else if kind == this.eval_libc_i32("PTHREAD_MUTEX_DEFAULT")? - || kind == this.eval_libc_i32("PTHREAD_MUTEX_ERRORCHECK")? - || kind == this.eval_libc_i32("PTHREAD_MUTEX_RECURSIVE")? + } else if kind == this.eval_libc_i32("PTHREAD_MUTEX_DEFAULT") + || kind == this.eval_libc_i32("PTHREAD_MUTEX_ERRORCHECK") + || kind == this.eval_libc_i32("PTHREAD_MUTEX_RECURSIVE") { mutexattr_set_kind(this, attr_op, kind)?; } else { - let einval = this.eval_libc_i32("EINVAL")?; + let einval = this.eval_libc_i32("EINVAL"); return Ok(einval); } @@ -299,7 +299,7 @@ pub trait EvalContextExt<'mir, 'tcx: 'mir>: crate::MiriInterpCxExt<'mir, 'tcx> { let attr = this.read_pointer(attr_op)?; let kind = if this.ptr_is_null(attr)? { - this.eval_libc_i32("PTHREAD_MUTEX_DEFAULT")? + this.eval_libc_i32("PTHREAD_MUTEX_DEFAULT") } else { mutexattr_get_kind(this, attr_op)? }; @@ -331,9 +331,9 @@ pub trait EvalContextExt<'mir, 'tcx: 'mir>: crate::MiriInterpCxExt<'mir, 'tcx> { throw_ub_format!("trying to acquire already locked default mutex"); } else if is_mutex_kind_normal(this, kind)? { throw_machine_stop!(TerminationInfo::Deadlock); - } else if kind == this.eval_libc_i32("PTHREAD_MUTEX_ERRORCHECK")? { - this.eval_libc_i32("EDEADLK") - } else if kind == this.eval_libc_i32("PTHREAD_MUTEX_RECURSIVE")? { + } else if kind == this.eval_libc_i32("PTHREAD_MUTEX_ERRORCHECK") { + Ok(this.eval_libc_i32("EDEADLK")) + } else if kind == this.eval_libc_i32("PTHREAD_MUTEX_RECURSIVE") { this.mutex_lock(id, active_thread); Ok(0) } else { @@ -362,14 +362,14 @@ pub trait EvalContextExt<'mir, 'tcx: 'mir>: crate::MiriInterpCxExt<'mir, 'tcx> { if this.mutex_is_locked(id) { let owner_thread = this.mutex_get_owner(id); if owner_thread != active_thread { - this.eval_libc_i32("EBUSY") + Ok(this.eval_libc_i32("EBUSY")) } else { if is_mutex_kind_default(this, kind)? || is_mutex_kind_normal(this, kind)? - || kind == this.eval_libc_i32("PTHREAD_MUTEX_ERRORCHECK")? + || kind == this.eval_libc_i32("PTHREAD_MUTEX_ERRORCHECK") { - this.eval_libc_i32("EBUSY") - } else if kind == this.eval_libc_i32("PTHREAD_MUTEX_RECURSIVE")? { + Ok(this.eval_libc_i32("EBUSY")) + } else if kind == this.eval_libc_i32("PTHREAD_MUTEX_RECURSIVE") { this.mutex_lock(id, active_thread); Ok(0) } else { @@ -410,10 +410,10 @@ pub trait EvalContextExt<'mir, 'tcx: 'mir>: crate::MiriInterpCxExt<'mir, 'tcx> { throw_ub_format!( "unlocked a PTHREAD_MUTEX_NORMAL mutex that was not locked by the current thread" ); - } else if kind == this.eval_libc_i32("PTHREAD_MUTEX_ERRORCHECK")? - || kind == this.eval_libc_i32("PTHREAD_MUTEX_RECURSIVE")? + } else if kind == this.eval_libc_i32("PTHREAD_MUTEX_ERRORCHECK") + || kind == this.eval_libc_i32("PTHREAD_MUTEX_RECURSIVE") { - this.eval_libc_i32("EPERM") + Ok(this.eval_libc_i32("EPERM")) } else { throw_unsup_format!("called pthread_mutex_unlock on an unsupported type of mutex"); } @@ -471,7 +471,7 @@ pub trait EvalContextExt<'mir, 'tcx: 'mir>: crate::MiriInterpCxExt<'mir, 'tcx> { let active_thread = this.get_active_thread(); if this.rwlock_is_write_locked(id) { - this.eval_libc_i32("EBUSY") + Ok(this.eval_libc_i32("EBUSY")) } else { this.rwlock_reader_lock(id, active_thread); Ok(0) @@ -518,7 +518,7 @@ pub trait EvalContextExt<'mir, 'tcx: 'mir>: crate::MiriInterpCxExt<'mir, 'tcx> { let active_thread = this.get_active_thread(); if this.rwlock_is_locked(id) { - this.eval_libc_i32("EBUSY") + Ok(this.eval_libc_i32("EBUSY")) } else { this.rwlock_writer_lock(id, active_thread); Ok(0) @@ -575,7 +575,7 @@ pub trait EvalContextExt<'mir, 'tcx: 'mir>: crate::MiriInterpCxExt<'mir, 'tcx> { // The default value of the clock attribute shall refer to the system // clock. // https://pubs.opengroup.org/onlinepubs/9699919799/functions/pthread_condattr_setclock.html - let default_clock_id = this.eval_libc_i32("CLOCK_REALTIME")?; + let default_clock_id = this.eval_libc_i32("CLOCK_REALTIME"); condattr_set_clock_id(this, attr_op, default_clock_id)?; Ok(0) @@ -589,12 +589,12 @@ pub trait EvalContextExt<'mir, 'tcx: 'mir>: crate::MiriInterpCxExt<'mir, 'tcx> { let this = self.eval_context_mut(); let clock_id = this.read_scalar(clock_id_op)?.to_i32()?; - if clock_id == this.eval_libc_i32("CLOCK_REALTIME")? - || clock_id == this.eval_libc_i32("CLOCK_MONOTONIC")? + if clock_id == this.eval_libc_i32("CLOCK_REALTIME") + || clock_id == this.eval_libc_i32("CLOCK_MONOTONIC") { condattr_set_clock_id(this, attr_op, clock_id)?; } else { - let einval = this.eval_libc_i32("EINVAL")?; + let einval = this.eval_libc_i32("EINVAL"); return Ok(Scalar::from_i32(einval)); } @@ -638,7 +638,7 @@ pub trait EvalContextExt<'mir, 'tcx: 'mir>: crate::MiriInterpCxExt<'mir, 'tcx> { let attr = this.read_pointer(attr_op)?; let clock_id = if this.ptr_is_null(attr)? { - this.eval_libc_i32("CLOCK_REALTIME")? + this.eval_libc_i32("CLOCK_REALTIME") } else { condattr_get_clock_id(this, attr_op)? }; @@ -718,16 +718,16 @@ pub trait EvalContextExt<'mir, 'tcx: 'mir>: crate::MiriInterpCxExt<'mir, 'tcx> { let duration = match this.read_timespec(&this.deref_operand(abstime_op)?)? { Some(duration) => duration, None => { - let einval = this.eval_libc("EINVAL")?; + let einval = this.eval_libc("EINVAL"); this.write_scalar(einval, dest)?; return Ok(()); } }; - let timeout_time = if clock_id == this.eval_libc_i32("CLOCK_REALTIME")? { + let timeout_time = if clock_id == this.eval_libc_i32("CLOCK_REALTIME") { this.check_no_isolation("`pthread_cond_timedwait` with `CLOCK_REALTIME`")?; Time::RealTime(SystemTime::UNIX_EPOCH.checked_add(duration).unwrap()) - } else if clock_id == this.eval_libc_i32("CLOCK_MONOTONIC")? { + } else if clock_id == this.eval_libc_i32("CLOCK_MONOTONIC") { Time::Monotonic(this.machine.clock.anchor().checked_add(duration).unwrap()) } else { throw_unsup_format!("unsupported clock id: {}", clock_id); @@ -763,7 +763,7 @@ pub trait EvalContextExt<'mir, 'tcx: 'mir>: crate::MiriInterpCxExt<'mir, 'tcx> { ecx.condvar_remove_waiter(self.id, self.active_thread); // Set the return value: we timed out. - let etimedout = ecx.eval_libc("ETIMEDOUT")?; + let etimedout = ecx.eval_libc("ETIMEDOUT"); ecx.write_scalar(etimedout, &self.dest)?; Ok(()) diff --git a/src/shims/unix/thread.rs b/src/shims/unix/thread.rs index 5b9dc90f0f..4f7b028d35 100644 --- a/src/shims/unix/thread.rs +++ b/src/shims/unix/thread.rs @@ -84,7 +84,7 @@ pub trait EvalContextExt<'mir, 'tcx: 'mir>: crate::MiriInterpCxExt<'mir, 'tcx> { // Comparing with `>=` to account for null terminator. if name.len() >= max_name_len { - return this.eval_libc("ERANGE"); + return Ok(this.eval_libc("ERANGE")); } this.set_thread_name(thread, name); @@ -107,7 +107,7 @@ pub trait EvalContextExt<'mir, 'tcx: 'mir>: crate::MiriInterpCxExt<'mir, 'tcx> { let name = this.get_thread_name(thread).to_owned(); let (success, _written) = this.write_c_str(&name, name_out, len)?; - if success { Ok(Scalar::from_u32(0)) } else { this.eval_libc("ERANGE") } + Ok(if success { Scalar::from_u32(0) } else { this.eval_libc("ERANGE") }) } fn sched_yield(&mut self) -> InterpResult<'tcx, i32> { diff --git a/src/shims/windows/sync.rs b/src/shims/windows/sync.rs index 6b043c6d2c..61cb3b382b 100644 --- a/src/shims/windows/sync.rs +++ b/src/shims/windows/sync.rs @@ -170,7 +170,7 @@ pub trait EvalContextExt<'mir, 'tcx: 'mir>: crate::MiriInterpCxExt<'mir, 'tcx> { match this.init_once_status(id) { InitOnceStatus::Uninitialized => { this.init_once_begin(id); - this.write_scalar(this.eval_windows("c", "TRUE")?, &pending_place)?; + this.write_scalar(this.eval_windows("c", "TRUE"), &pending_place)?; } InitOnceStatus::Begun => { // Someone else is already on it. @@ -195,8 +195,8 @@ pub trait EvalContextExt<'mir, 'tcx: 'mir>: crate::MiriInterpCxExt<'mir, 'tcx> { unreachable!( "status should have either been set to begun or complete" ), - InitOnceStatus::Begun => this.eval_windows("c", "TRUE")?, - InitOnceStatus::Complete => this.eval_windows("c", "FALSE")?, + InitOnceStatus::Begun => this.eval_windows("c", "TRUE"), + InitOnceStatus::Complete => this.eval_windows("c", "FALSE"), }; this.write_scalar(pending, &self.pending_place)?; @@ -213,12 +213,12 @@ pub trait EvalContextExt<'mir, 'tcx: 'mir>: crate::MiriInterpCxExt<'mir, 'tcx> { } InitOnceStatus::Complete => { this.init_once_observe_completed(id); - this.write_scalar(this.eval_windows("c", "FALSE")?, &pending_place)?; + this.write_scalar(this.eval_windows("c", "FALSE"), &pending_place)?; } } // This always succeeds (even if the thread is blocked, we will succeed if we ever unblock). - this.eval_windows("c", "TRUE") + Ok(this.eval_windows("c", "TRUE")) } fn InitOnceComplete( @@ -235,7 +235,7 @@ pub trait EvalContextExt<'mir, 'tcx: 'mir>: crate::MiriInterpCxExt<'mir, 'tcx> { let success = if flags == 0 { true - } else if flags == this.eval_windows("c", "INIT_ONCE_INIT_FAILED")?.to_u32()? { + } else if flags == this.eval_windows_u32("c", "INIT_ONCE_INIT_FAILED") { false } else { throw_unsup_format!("unsupported `dwFlags` {flags} in `InitOnceBeginInitialize`"); @@ -258,7 +258,7 @@ pub trait EvalContextExt<'mir, 'tcx: 'mir>: crate::MiriInterpCxExt<'mir, 'tcx> { this.init_once_fail(id)?; } - this.eval_windows("c", "TRUE") + Ok(this.eval_windows("c", "TRUE")) } fn WaitOnAddress( @@ -280,14 +280,14 @@ pub trait EvalContextExt<'mir, 'tcx: 'mir>: crate::MiriInterpCxExt<'mir, 'tcx> { let addr = ptr.addr().bytes(); if size > 8 || !size.is_power_of_two() { - let invalid_param = this.eval_windows("c", "ERROR_INVALID_PARAMETER")?; + let invalid_param = this.eval_windows("c", "ERROR_INVALID_PARAMETER"); this.set_last_error(invalid_param)?; this.write_scalar(Scalar::from_i32(0), dest)?; return Ok(()); }; let size = Size::from_bytes(size); - let timeout_time = if timeout_ms == this.eval_windows("c", "INFINITE")?.to_u32()? { + let timeout_time = if timeout_ms == this.eval_windows_u32("c", "INFINITE") { None } else { let duration = Duration::from_millis(timeout_ms.into()); @@ -325,7 +325,7 @@ pub trait EvalContextExt<'mir, 'tcx: 'mir>: crate::MiriInterpCxExt<'mir, 'tcx> { fn call(&self, this: &mut MiriInterpCx<'mir, 'tcx>) -> InterpResult<'tcx> { this.unblock_thread(self.thread); this.futex_remove_waiter(self.addr, self.thread); - let error_timeout = this.eval_windows("c", "ERROR_TIMEOUT")?; + let error_timeout = this.eval_windows("c", "ERROR_TIMEOUT"); this.set_last_error(error_timeout)?; this.write_scalar(Scalar::from_i32(0), &self.dest)?; @@ -377,7 +377,7 @@ pub trait EvalContextExt<'mir, 'tcx: 'mir>: crate::MiriInterpCxExt<'mir, 'tcx> { let timeout_ms = this.read_scalar(timeout_op)?.to_u32()?; let flags = this.read_scalar(flags_op)?.to_u32()?; - let timeout_time = if timeout_ms == this.eval_windows("c", "INFINITE")?.to_u32()? { + let timeout_time = if timeout_ms == this.eval_windows_u32("c", "INFINITE") { None } else { let duration = Duration::from_millis(timeout_ms.into()); @@ -431,9 +431,9 @@ pub trait EvalContextExt<'mir, 'tcx: 'mir>: crate::MiriInterpCxExt<'mir, 'tcx> { this.condvar_remove_waiter(self.condvar_id, self.thread); - let error_timeout = this.eval_windows("c", "ERROR_TIMEOUT")?; + let error_timeout = this.eval_windows("c", "ERROR_TIMEOUT"); this.set_last_error(error_timeout)?; - this.write_scalar(this.eval_windows("c", "FALSE")?, &self.dest)?; + this.write_scalar(this.eval_windows("c", "FALSE"), &self.dest)?; Ok(()) } } @@ -451,7 +451,7 @@ pub trait EvalContextExt<'mir, 'tcx: 'mir>: crate::MiriInterpCxExt<'mir, 'tcx> { ); } - this.eval_windows("c", "TRUE") + Ok(this.eval_windows("c", "TRUE")) } fn WakeConditionVariable(&mut self, condvar_op: &OpTy<'tcx, Provenance>) -> InterpResult<'tcx> { diff --git a/src/shims/windows/thread.rs b/src/shims/windows/thread.rs index 25a5194caa..c3a450db48 100644 --- a/src/shims/windows/thread.rs +++ b/src/shims/windows/thread.rs @@ -34,7 +34,7 @@ pub trait EvalContextExt<'mir, 'tcx: 'mir>: crate::MiriInterpCxExt<'mir, 'tcx> { }; let stack_size_param_is_a_reservation = - this.eval_windows("c", "STACK_SIZE_PARAM_IS_A_RESERVATION")?.to_u32()?; + this.eval_windows_u32("c", "STACK_SIZE_PARAM_IS_A_RESERVATION"); // We ignore the stack size, so we also ignore the // `STACK_SIZE_PARAM_IS_A_RESERVATION` flag. @@ -73,7 +73,7 @@ pub trait EvalContextExt<'mir, 'tcx: 'mir>: crate::MiriInterpCxExt<'mir, 'tcx> { _ => this.invalid_handle("WaitForSingleObject")?, }; - if timeout != this.eval_windows("c", "INFINITE")?.to_u32()? { + if timeout != this.eval_windows_u32("c", "INFINITE") { throw_unsup_format!("`WaitForSingleObject` with non-infinite timeout"); } From d267f7f89185439eec9d3e04e22a33f83d8db0a2 Mon Sep 17 00:00:00 2001 From: Ralf Jung Date: Sun, 11 Dec 2022 19:15:17 +0100 Subject: [PATCH 09/28] expose host-to-target path conversion to interpreted program --- README.md | 15 +++++++++++++++ src/shims/foreign_items.rs | 17 ++++++++++++++++- tests/pass-dep/shims/libc-fs.rs | 31 ++++++++++++++++--------------- tests/pass-dep/shims/libc-misc.rs | 26 +++++++++++++++++--------- tests/pass/shims/fs.rs | 31 +++++++++++++++++-------------- 5 files changed, 81 insertions(+), 39 deletions(-) diff --git a/README.md b/README.md index 909e5bd510..8cc7e84695 100644 --- a/README.md +++ b/README.md @@ -576,6 +576,21 @@ extern "Rust" { /// Miri-provided extern function to deallocate memory. fn miri_dealloc(ptr: *mut u8, size: usize, align: usize); + + /// Convert a path from the host Miri runs on to the target Miri interprets. + /// Performs conversion of path separators as needed. + /// + /// Usually Miri performs this kind of conversion automatically. However, manual conversion + /// might be necessary when reading an environment variable that was set of the host + /// (such as TMPDIR) and using it as a target path. + /// + /// Only works with isolation disabled. + /// + /// `in` must point to a null-terminated string, and will be read as the input host path. + /// `out` must point to at least `out_size` many bytes, and the result will be stored there + /// with a null terminator. + /// Returns 0 if the `out` buffer was large enough, and the required size otherwise. + fn miri_host_to_target_path(path: *const i8, out: *mut i8, out_size: usize) -> usize; } ``` diff --git a/src/shims/foreign_items.rs b/src/shims/foreign_items.rs index 8370e02b58..abfa73db64 100644 --- a/src/shims/foreign_items.rs +++ b/src/shims/foreign_items.rs @@ -1,4 +1,4 @@ -use std::{collections::hash_map::Entry, io::Write, iter}; +use std::{collections::hash_map::Entry, io::Write, iter, path::Path}; use log::trace; @@ -442,6 +442,21 @@ pub trait EvalContextExt<'mir, 'tcx: 'mir>: crate::MiriInterpCxExt<'mir, 'tcx> { } this.machine.static_roots.push(alloc_id); } + "miri_host_to_target_path" => { + let [ptr, out, out_size] = this.check_shim(abi, Abi::Rust, link_name, args)?; + let ptr = this.read_pointer(ptr)?; + let out = this.read_pointer(out)?; + let out_size = this.read_scalar(out_size)?.to_machine_usize(this)?; + + // The host affects program behavior here, so this requires isolation to be disabled. + this.check_no_isolation("`miri_host_to_target_path`")?; + + // We read this as a plain OsStr and write it as a path, which will convert it to the target. + let path = this.read_os_str_from_c_str(ptr)?.to_owned(); + let (success, needed_size) = this.write_path_to_c_str(Path::new(&path), out, out_size)?; + // Return value: 0 on success, otherwise the size it would have needed. + this.write_int(if success { 0 } else { needed_size }, dest)?; + } // Obtains the size of a Miri backtrace. See the README for details. "miri_backtrace_size" => { diff --git a/tests/pass-dep/shims/libc-fs.rs b/tests/pass-dep/shims/libc-fs.rs index 93c0fad9c1..ba5b269f65 100644 --- a/tests/pass-dep/shims/libc-fs.rs +++ b/tests/pass-dep/shims/libc-fs.rs @@ -5,7 +5,7 @@ #![feature(io_error_uncategorized)] use std::convert::TryInto; -use std::ffi::CString; +use std::ffi::{CStr, CString}; use std::fs::{canonicalize, remove_dir_all, remove_file, File}; use std::io::{Error, ErrorKind, Write}; use std::os::unix::ffi::OsStrExt; @@ -23,20 +23,21 @@ fn main() { } fn tmp() -> PathBuf { - std::env::var("MIRI_TEMP") - .map(|tmp| { - // MIRI_TEMP is set outside of our emulated - // program, so it may have path separators that don't - // correspond to our target platform. We normalize them here - // before constructing a `PathBuf` - - #[cfg(windows)] - return PathBuf::from(tmp.replace("/", "\\")); - - #[cfg(not(windows))] - return PathBuf::from(tmp.replace("\\", "/")); - }) - .unwrap_or_else(|_| std::env::temp_dir()) + let path = std::env::var("MIRI_TEMP") + .unwrap_or_else(|_| std::env::temp_dir().into_os_string().into_string().unwrap()); + // These are host paths. We need to convert them to the target. + let path = CString::new(path).unwrap(); + let mut out = Vec::with_capacity(1024); + + unsafe { + extern "Rust" { + fn miri_host_to_target_path(path: *const i8, out: *mut i8, out_size: usize) -> usize; + } + let ret = miri_host_to_target_path(path.as_ptr(), out.as_mut_ptr(), out.capacity()); + assert_eq!(ret, 0); + let out = CStr::from_ptr(out.as_ptr()).to_str().unwrap(); + PathBuf::from(out) + } } /// Prepare: compute filename and make sure the file does not exist. diff --git a/tests/pass-dep/shims/libc-misc.rs b/tests/pass-dep/shims/libc-misc.rs index 2a4300fcd0..20e96a92c7 100644 --- a/tests/pass-dep/shims/libc-misc.rs +++ b/tests/pass-dep/shims/libc-misc.rs @@ -7,15 +7,23 @@ use std::os::unix::io::AsRawFd; use std::path::PathBuf; fn tmp() -> PathBuf { - std::env::var("MIRI_TEMP") - .map(|tmp| { - // MIRI_TEMP is set outside of our emulated - // program, so it may have path separators that don't - // correspond to our target platform. We normalize them here - // before constructing a `PathBuf` - return PathBuf::from(tmp.replace("\\", "/")); - }) - .unwrap_or_else(|_| std::env::temp_dir()) + use std::ffi::{CStr, CString}; + + let path = std::env::var("MIRI_TEMP") + .unwrap_or_else(|_| std::env::temp_dir().into_os_string().into_string().unwrap()); + // These are host paths. We need to convert them to the target. + let path = CString::new(path).unwrap(); + let mut out = Vec::with_capacity(1024); + + unsafe { + extern "Rust" { + fn miri_host_to_target_path(path: *const i8, out: *mut i8, out_size: usize) -> usize; + } + let ret = miri_host_to_target_path(path.as_ptr(), out.as_mut_ptr(), out.capacity()); + assert_eq!(ret, 0); + let out = CStr::from_ptr(out.as_ptr()).to_str().unwrap(); + PathBuf::from(out) + } } /// Test allocating variant of `realpath`. diff --git a/tests/pass/shims/fs.rs b/tests/pass/shims/fs.rs index 65cf6fe66b..901a2ab102 100644 --- a/tests/pass/shims/fs.rs +++ b/tests/pass/shims/fs.rs @@ -31,20 +31,23 @@ fn main() { } fn tmp() -> PathBuf { - std::env::var("MIRI_TEMP") - .map(|tmp| { - // MIRI_TEMP is set outside of our emulated - // program, so it may have path separators that don't - // correspond to our target platform. We normalize them here - // before constructing a `PathBuf` - - #[cfg(windows)] - return PathBuf::from(tmp.replace("/", "\\")); - - #[cfg(not(windows))] - return PathBuf::from(tmp.replace("\\", "/")); - }) - .unwrap_or_else(|_| std::env::temp_dir()) + use std::ffi::{CStr, CString}; + + let path = std::env::var("MIRI_TEMP") + .unwrap_or_else(|_| std::env::temp_dir().into_os_string().into_string().unwrap()); + // These are host paths. We need to convert them to the target. + let path = CString::new(path).unwrap(); + let mut out = Vec::with_capacity(1024); + + unsafe { + extern "Rust" { + fn miri_host_to_target_path(path: *const i8, out: *mut i8, out_size: usize) -> usize; + } + let ret = miri_host_to_target_path(path.as_ptr(), out.as_mut_ptr(), out.capacity()); + assert_eq!(ret, 0); + let out = CStr::from_ptr(out.as_ptr()).to_str().unwrap(); + PathBuf::from(out) + } } /// Prepare: compute filename and make sure the file does not exist. From 4bf26df9805c373b1a8b0850898e38a74ee6e939 Mon Sep 17 00:00:00 2001 From: Ralf Jung Date: Sun, 11 Dec 2022 19:22:55 +0100 Subject: [PATCH 10/28] More host/target path conversion tests: - test that the tmpdir Miri tests see is absolute and a directory - test that current_dir returns an absolute path --- tests/pass/shims/env/current_dir.rs | 3 ++- tests/pass/shims/fs.rs | 7 +++++++ 2 files changed, 9 insertions(+), 1 deletion(-) diff --git a/tests/pass/shims/env/current_dir.rs b/tests/pass/shims/env/current_dir.rs index 069b462ab3..ca90912eab 100644 --- a/tests/pass/shims/env/current_dir.rs +++ b/tests/pass/shims/env/current_dir.rs @@ -3,8 +3,9 @@ use std::env; use std::io::ErrorKind; fn main() { - // Test that `getcwd` is available + // Test that `getcwd` is available and an absolute path let cwd = env::current_dir().unwrap(); + assert!(cwd.is_absolute(), "cwd {:?} is not absolute", cwd); // Test that changing dir to `..` actually sets the current directory to the parent of `cwd`. // The only exception here is if `cwd` is the root directory, then changing directory must // keep the current directory equal to `cwd`. diff --git a/tests/pass/shims/fs.rs b/tests/pass/shims/fs.rs index 901a2ab102..e3ebbc8c8d 100644 --- a/tests/pass/shims/fs.rs +++ b/tests/pass/shims/fs.rs @@ -28,6 +28,7 @@ fn main() { test_directory(); test_canonicalize(); test_from_raw_os_error(); + test_path_conversion(); } fn tmp() -> PathBuf { @@ -74,6 +75,12 @@ fn prepare_with_content(filename: &str, content: &[u8]) -> PathBuf { path } +fn test_path_conversion() { + let tmp = tmp(); + assert!(tmp.is_absolute(), "{:?} is not absolute", tmp); + assert!(tmp.is_dir(), "{:?} is not a directory", tmp); +} + fn test_file() { let bytes = b"Hello, World!\n"; let path = prepare("miri_test_fs_file.txt"); From 9db5511ab26f35b4cc4fce1579e122b33a6e5644 Mon Sep 17 00:00:00 2001 From: Ralf Jung Date: Sun, 11 Dec 2022 19:49:29 +0100 Subject: [PATCH 11/28] make unix path handling on Windows hosts preserve absoluteness --- README.md | 2 +- src/shims/os_str.rs | 51 ++++++++++++++++++++++++-------- src/shims/unix/fs.rs | 2 +- test-cargo-miri/src/main.rs | 27 ++++++++++++++--- test-cargo-miri/subcrate/main.rs | 29 ++++++++++++++---- test-cargo-miri/subcrate/test.rs | 27 +++++++++++++++-- tests/pass/shims/fs.rs | 14 +++++---- 7 files changed, 119 insertions(+), 33 deletions(-) diff --git a/README.md b/README.md index 8cc7e84695..9a4dea949d 100644 --- a/README.md +++ b/README.md @@ -581,7 +581,7 @@ extern "Rust" { /// Performs conversion of path separators as needed. /// /// Usually Miri performs this kind of conversion automatically. However, manual conversion - /// might be necessary when reading an environment variable that was set of the host + /// might be necessary when reading an environment variable that was set on the host /// (such as TMPDIR) and using it as a target path. /// /// Only works with isolation disabled. diff --git a/src/shims/os_str.rs b/src/shims/os_str.rs index bc7ca82997..e42ebc187b 100644 --- a/src/shims/os_str.rs +++ b/src/shims/os_str.rs @@ -174,7 +174,7 @@ pub trait EvalContextExt<'mir, 'tcx: 'mir>: crate::MiriInterpCxExt<'mir, 'tcx> { let this = self.eval_context_ref(); let os_str = this.read_os_str_from_c_str(ptr)?; - Ok(match this.convert_path_separator(Cow::Borrowed(os_str), PathConversion::TargetToHost) { + Ok(match this.convert_path(Cow::Borrowed(os_str), PathConversion::TargetToHost) { Cow::Borrowed(x) => Cow::Borrowed(Path::new(x)), Cow::Owned(y) => Cow::Owned(PathBuf::from(y)), }) @@ -188,10 +188,7 @@ pub trait EvalContextExt<'mir, 'tcx: 'mir>: crate::MiriInterpCxExt<'mir, 'tcx> { let this = self.eval_context_ref(); let os_str = this.read_os_str_from_wide_str(ptr)?; - Ok(this - .convert_path_separator(Cow::Owned(os_str), PathConversion::TargetToHost) - .into_owned() - .into()) + Ok(this.convert_path(Cow::Owned(os_str), PathConversion::TargetToHost).into_owned().into()) } /// Write a Path to the machine memory (as a null-terminated sequence of bytes), @@ -203,8 +200,8 @@ pub trait EvalContextExt<'mir, 'tcx: 'mir>: crate::MiriInterpCxExt<'mir, 'tcx> { size: u64, ) -> InterpResult<'tcx, (bool, u64)> { let this = self.eval_context_mut(); - let os_str = this - .convert_path_separator(Cow::Borrowed(path.as_os_str()), PathConversion::HostToTarget); + let os_str = + this.convert_path(Cow::Borrowed(path.as_os_str()), PathConversion::HostToTarget); this.write_os_str_to_c_str(&os_str, ptr, size) } @@ -217,8 +214,8 @@ pub trait EvalContextExt<'mir, 'tcx: 'mir>: crate::MiriInterpCxExt<'mir, 'tcx> { size: u64, ) -> InterpResult<'tcx, (bool, u64)> { let this = self.eval_context_mut(); - let os_str = this - .convert_path_separator(Cow::Borrowed(path.as_os_str()), PathConversion::HostToTarget); + let os_str = + this.convert_path(Cow::Borrowed(path.as_os_str()), PathConversion::HostToTarget); this.write_os_str_to_wide_str(&os_str, ptr, size) } @@ -230,18 +227,19 @@ pub trait EvalContextExt<'mir, 'tcx: 'mir>: crate::MiriInterpCxExt<'mir, 'tcx> { memkind: MemoryKind, ) -> InterpResult<'tcx, Pointer>> { let this = self.eval_context_mut(); - let os_str = this - .convert_path_separator(Cow::Borrowed(path.as_os_str()), PathConversion::HostToTarget); + let os_str = + this.convert_path(Cow::Borrowed(path.as_os_str()), PathConversion::HostToTarget); this.alloc_os_str_as_c_str(&os_str, memkind) } - fn convert_path_separator<'a>( + fn convert_path<'a>( &self, os_str: Cow<'a, OsStr>, direction: PathConversion, ) -> Cow<'a, OsStr> { let this = self.eval_context_ref(); let target_os = &this.tcx.sess.target.os; + #[cfg(windows)] return if target_os == "windows" { // Windows-on-Windows, all fine. @@ -252,10 +250,35 @@ pub trait EvalContextExt<'mir, 'tcx: 'mir>: crate::MiriInterpCxExt<'mir, 'tcx> { PathConversion::HostToTarget => ('\\', '/'), PathConversion::TargetToHost => ('/', '\\'), }; - let converted = os_str + let mut converted = os_str .encode_wide() .map(|wchar| if wchar == from as u16 { to as u16 } else { wchar }) .collect::>(); + // We also have to ensure that absolute paths remain absolute. + match direction { + PathConversion::HostToTarget => { + // If this is an absolute Windows path that starts with a drive letter (`C:/...` + // after separator conversion), it would not be considered absolute by Unix + // target code. + if converted.get(1).copied() == Some(':' as u16) + && converted.get(2).copied() == Some('/' as u16) + { + // We add a `/` at the beginning, to store the absolute Windows + // path in something that looks like an absolute Unix path. + converted.insert(0, '/' as u16); + } + } + PathConversion::TargetToHost => { + // If the path is `\C:\`, the leading backslash was probably added by the above code + // and we should get rid of it again. + if converted.get(0).copied() == Some('\\' as u16) + && converted.get(2).copied() == Some(':' as u16) + && converted.get(3).copied() == Some('\\' as u16) + { + converted.remove(0); + } + } + } Cow::Owned(OsString::from_wide(&converted)) }; #[cfg(unix)] @@ -270,6 +293,8 @@ pub trait EvalContextExt<'mir, 'tcx: 'mir>: crate::MiriInterpCxExt<'mir, 'tcx> { .iter() .map(|&wchar| if wchar == from as u8 { to as u8 } else { wchar }) .collect::>(); + // TODO: Once we actually support file system things on Windows targets, we'll probably + // have to also do something clever for absolute path preservation here, like above. Cow::Owned(OsString::from_vec(converted)) } else { // Unix-on-Unix, all is fine. diff --git a/src/shims/unix/fs.rs b/src/shims/unix/fs.rs index bf99412af6..8b869a6525 100644 --- a/src/shims/unix/fs.rs +++ b/src/shims/unix/fs.rs @@ -1667,7 +1667,7 @@ pub trait EvalContextExt<'mir, 'tcx: 'mir>: crate::MiriInterpCxExt<'mir, 'tcx> { // 'readlink' truncates the resolved path if the provided buffer is not large // enough, and does *not* add a null terminator. That means we cannot use the usual // `write_path_to_c_str` and have to re-implement parts of it ourselves. - let resolved = this.convert_path_separator( + let resolved = this.convert_path( Cow::Borrowed(resolved.as_ref()), crate::shims::os_str::PathConversion::HostToTarget, ); diff --git a/test-cargo-miri/src/main.rs b/test-cargo-miri/src/main.rs index 41c52b7017..048dbbbaa0 100644 --- a/test-cargo-miri/src/main.rs +++ b/test-cargo-miri/src/main.rs @@ -2,6 +2,7 @@ use byteorder::{BigEndian, ByteOrder}; use std::env; #[cfg(unix)] use std::io::{self, BufRead}; +use std::path::PathBuf; fn main() { // Check env var set by `build.rs`. @@ -21,12 +22,30 @@ fn main() { // If there were no arguments, access stdin and test working dir. // (We rely on the test runner to always disable isolation when passing no arguments.) if std::env::args().len() <= 1 { + fn host_to_target_path(path: String) -> PathBuf { + use std::ffi::{CStr, CString}; + + let path = CString::new(path).unwrap(); + let mut out = Vec::with_capacity(1024); + + unsafe { + extern "Rust" { + fn miri_host_to_target_path( + path: *const i8, + out: *mut i8, + out_size: usize, + ) -> usize; + } + let ret = miri_host_to_target_path(path.as_ptr(), out.as_mut_ptr(), out.capacity()); + assert_eq!(ret, 0); + let out = CStr::from_ptr(out.as_ptr()).to_str().unwrap(); + PathBuf::from(out) + } + } + // CWD should be crate root. - // We have to normalize slashes, as the env var might be set for a different target's conventions. let env_dir = env::current_dir().unwrap(); - let env_dir = env_dir.to_string_lossy().replace("\\", "/"); - let crate_dir = env::var_os("CARGO_MANIFEST_DIR").unwrap(); - let crate_dir = crate_dir.to_string_lossy().replace("\\", "/"); + let crate_dir = host_to_target_path(env::var("CARGO_MANIFEST_DIR").unwrap()); assert_eq!(env_dir, crate_dir); #[cfg(unix)] diff --git a/test-cargo-miri/subcrate/main.rs b/test-cargo-miri/subcrate/main.rs index 4ce80b3707..1cb8091f87 100644 --- a/test-cargo-miri/subcrate/main.rs +++ b/test-cargo-miri/subcrate/main.rs @@ -4,13 +4,30 @@ use std::path::PathBuf; fn main() { println!("subcrate running"); + fn host_to_target_path(path: String) -> PathBuf { + use std::ffi::{CStr, CString}; + + let path = CString::new(path).unwrap(); + let mut out = Vec::with_capacity(1024); + + unsafe { + extern "Rust" { + fn miri_host_to_target_path( + path: *const i8, + out: *mut i8, + out_size: usize, + ) -> usize; + } + let ret = miri_host_to_target_path(path.as_ptr(), out.as_mut_ptr(), out.capacity()); + assert_eq!(ret, 0); + let out = CStr::from_ptr(out.as_ptr()).to_str().unwrap(); + PathBuf::from(out) + } + } + // CWD should be workspace root, i.e., one level up from crate root. - // We have to normalize slashes, as the env var might be set for a different target's conventions. let env_dir = env::current_dir().unwrap(); - let env_dir = env_dir.to_string_lossy().replace("\\", "/"); - let crate_dir = env::var_os("CARGO_MANIFEST_DIR").unwrap(); - let crate_dir = crate_dir.to_string_lossy().replace("\\", "/"); - let crate_dir = PathBuf::from(crate_dir); - let crate_dir = crate_dir.parent().unwrap().to_string_lossy(); + let crate_dir = host_to_target_path(env::var("CARGO_MANIFEST_DIR").unwrap()); + let crate_dir = crate_dir.parent().unwrap(); assert_eq!(env_dir, crate_dir); } diff --git a/test-cargo-miri/subcrate/test.rs b/test-cargo-miri/subcrate/test.rs index 77e3c2878c..619d8c72fd 100644 --- a/test-cargo-miri/subcrate/test.rs +++ b/test-cargo-miri/subcrate/test.rs @@ -1,16 +1,37 @@ use std::env; +use std::path::PathBuf; + use byteorder::{ByteOrder, LittleEndian}; fn main() { println!("subcrate testing"); + fn host_to_target_path(path: String) -> PathBuf { + use std::ffi::{CStr, CString}; + + let path = CString::new(path).unwrap(); + let mut out = Vec::with_capacity(1024); + + unsafe { + extern "Rust" { + fn miri_host_to_target_path( + path: *const i8, + out: *mut i8, + out_size: usize, + ) -> usize; + } + let ret = miri_host_to_target_path(path.as_ptr(), out.as_mut_ptr(), out.capacity()); + assert_eq!(ret, 0); + let out = CStr::from_ptr(out.as_ptr()).to_str().unwrap(); + PathBuf::from(out) + } + } + // CWD should be crate root. // We have to normalize slashes, as the env var might be set for a different target's conventions. let env_dir = env::current_dir().unwrap(); - let env_dir = env_dir.to_string_lossy().replace("\\", "/"); - let crate_dir = env::var_os("CARGO_MANIFEST_DIR").unwrap(); - let crate_dir = crate_dir.to_string_lossy().replace("\\", "/"); + let crate_dir = host_to_target_path(env::var("CARGO_MANIFEST_DIR").unwrap()); assert_eq!(env_dir, crate_dir); // Make sure we can call dev-dependencies. diff --git a/tests/pass/shims/fs.rs b/tests/pass/shims/fs.rs index e3ebbc8c8d..a7d4800fae 100644 --- a/tests/pass/shims/fs.rs +++ b/tests/pass/shims/fs.rs @@ -15,6 +15,7 @@ use std::io::{Error, ErrorKind, IsTerminal, Read, Result, Seek, SeekFrom, Write} use std::path::{Path, PathBuf}; fn main() { + test_path_conversion(); test_file(); test_file_clone(); test_file_create_new(); @@ -28,15 +29,11 @@ fn main() { test_directory(); test_canonicalize(); test_from_raw_os_error(); - test_path_conversion(); } -fn tmp() -> PathBuf { +fn host_to_target_path(path: String) -> PathBuf { use std::ffi::{CStr, CString}; - let path = std::env::var("MIRI_TEMP") - .unwrap_or_else(|_| std::env::temp_dir().into_os_string().into_string().unwrap()); - // These are host paths. We need to convert them to the target. let path = CString::new(path).unwrap(); let mut out = Vec::with_capacity(1024); @@ -51,6 +48,13 @@ fn tmp() -> PathBuf { } } +fn tmp() -> PathBuf { + let path = std::env::var("MIRI_TEMP") + .unwrap_or_else(|_| std::env::temp_dir().into_os_string().into_string().unwrap()); + // These are host paths. We need to convert them to the target. + host_to_target_path(path) +} + /// Prepare: compute filename and make sure the file does not exist. fn prepare(filename: &str) -> PathBuf { let path = tmp().join(filename); From 03f1ce4a61f8cd765fdfb1449988cad4c4ed842a Mon Sep 17 00:00:00 2001 From: Ralf Jung Date: Sun, 11 Dec 2022 22:34:45 +0100 Subject: [PATCH 12/28] Windows targets: make sure current_dir is absolute --- src/shims/os_str.rs | 45 +++++++++++++++++++++++++++++++++------------ 1 file changed, 33 insertions(+), 12 deletions(-) diff --git a/src/shims/os_str.rs b/src/shims/os_str.rs index e42ebc187b..0375a228a2 100644 --- a/src/shims/os_str.rs +++ b/src/shims/os_str.rs @@ -232,6 +232,7 @@ pub trait EvalContextExt<'mir, 'tcx: 'mir>: crate::MiriInterpCxExt<'mir, 'tcx> { this.alloc_os_str_as_c_str(&os_str, memkind) } + #[allow(clippy::get_first)] fn convert_path<'a>( &self, os_str: Cow<'a, OsStr>, @@ -260,20 +261,20 @@ pub trait EvalContextExt<'mir, 'tcx: 'mir>: crate::MiriInterpCxExt<'mir, 'tcx> { // If this is an absolute Windows path that starts with a drive letter (`C:/...` // after separator conversion), it would not be considered absolute by Unix // target code. - if converted.get(1).copied() == Some(':' as u16) - && converted.get(2).copied() == Some('/' as u16) + if converted.get(1).copied() == Some(b':' as u16) + && converted.get(2).copied() == Some(b'/' as u16) { // We add a `/` at the beginning, to store the absolute Windows // path in something that looks like an absolute Unix path. - converted.insert(0, '/' as u16); + converted.insert(0, b'/' as u16); } } PathConversion::TargetToHost => { // If the path is `\C:\`, the leading backslash was probably added by the above code // and we should get rid of it again. - if converted.get(0).copied() == Some('\\' as u16) - && converted.get(2).copied() == Some(':' as u16) - && converted.get(3).copied() == Some('\\' as u16) + if converted.get(0).copied() == Some(b'\\' as u16) + && converted.get(2).copied() == Some(b':' as u16) + && converted.get(3).copied() == Some(b'\\' as u16) { converted.remove(0); } @@ -285,16 +286,36 @@ pub trait EvalContextExt<'mir, 'tcx: 'mir>: crate::MiriInterpCxExt<'mir, 'tcx> { return if target_os == "windows" { // Windows target, Unix host. let (from, to) = match direction { - PathConversion::HostToTarget => ('/', '\\'), - PathConversion::TargetToHost => ('\\', '/'), + PathConversion::HostToTarget => (b'/', b'\\'), + PathConversion::TargetToHost => (b'\\', b'/'), }; - let converted = os_str + let mut converted = os_str .as_bytes() .iter() - .map(|&wchar| if wchar == from as u8 { to as u8 } else { wchar }) + .map(|&wchar| if wchar == from { to } else { wchar }) .collect::>(); - // TODO: Once we actually support file system things on Windows targets, we'll probably - // have to also do something clever for absolute path preservation here, like above. + // We also have to ensure that absolute paths remain absolute. + match direction { + PathConversion::HostToTarget => { + // If this start withs a `\`, we add `\\?` so it starts with `\\?\` which is + // some magic path on Windos that *is* considered absolute. + if converted.get(0).copied() == Some(b'\\') { + converted.splice(0..0, b"\\\\?".iter().copied()); + } + } + PathConversion::TargetToHost => { + // If this starts with `//?/`, it was probably produced by the above code and we + // remove the `//?` that got added to get the Unix path back out. + if converted.get(0).copied() == Some(b'/') + && converted.get(1).copied() == Some(b'/') + && converted.get(2).copied() == Some(b'?') + && converted.get(3).copied() == Some(b'/') + { + // Remove first 3 characters + converted.splice(0..3, std::iter::empty()); + } + } + } Cow::Owned(OsString::from_vec(converted)) } else { // Unix-on-Unix, all is fine. From 0dfa31bed596c5eaa100b2be55f4adbc63b28c5e Mon Sep 17 00:00:00 2001 From: DebugSteven Date: Mon, 11 Jul 2022 09:29:54 -0600 Subject: [PATCH 13/28] implement minimal epoll_create1 shim --- src/lib.rs | 1 + src/machine.rs | 4 + src/shims/unix/fs.rs | 35 +++-- src/shims/unix/linux/fd.rs | 191 ++++++++++++++++++++++++++ src/shims/unix/linux/fd/epoll.rs | 53 +++++++ src/shims/unix/linux/fd/event.rs | 38 +++++ src/shims/unix/linux/fd/socketpair.rs | 32 +++++ src/shims/unix/linux/foreign_items.rs | 31 +++++ src/shims/unix/linux/mod.rs | 1 + tests/fail/crates/tokio_mvp.rs | 7 - tests/fail/crates/tokio_mvp.stderr | 19 --- tests/pass-dep/tokio_mvp.rs | 6 + 12 files changed, 377 insertions(+), 41 deletions(-) create mode 100644 src/shims/unix/linux/fd.rs create mode 100644 src/shims/unix/linux/fd/epoll.rs create mode 100644 src/shims/unix/linux/fd/event.rs create mode 100644 src/shims/unix/linux/fd/socketpair.rs delete mode 100644 tests/fail/crates/tokio_mvp.rs delete mode 100644 tests/fail/crates/tokio_mvp.stderr create mode 100644 tests/pass-dep/tokio_mvp.rs diff --git a/src/lib.rs b/src/lib.rs index d65bd10e6f..97750cb78c 100644 --- a/src/lib.rs +++ b/src/lib.rs @@ -27,6 +27,7 @@ clippy::single_element_loop, clippy::needless_return, clippy::bool_to_int_with_if, + clippy::box_default, // We are not implementing queries here so it's fine rustc::potential_query_instability )] diff --git a/src/machine.rs b/src/machine.rs index 72f71db34b..a7a61a1f44 100644 --- a/src/machine.rs +++ b/src/machine.rs @@ -31,6 +31,10 @@ use crate::{ *, }; +/// The number of the available real-time signal with the lowest priority. +/// Dummy constant related to epoll, must be between 32 and 64. +pub const SIGRTMAX: i32 = 42; + /// Extra data stored with each stack frame pub struct FrameExtra<'tcx> { /// Extra data for Stacked Borrows. diff --git a/src/shims/unix/fs.rs b/src/shims/unix/fs.rs index ce2b0143b5..c46506e20a 100644 --- a/src/shims/unix/fs.rs +++ b/src/shims/unix/fs.rs @@ -17,20 +17,25 @@ use crate::shims::os_str::bytes_to_os_str; use crate::*; use shims::os_str::os_str_to_bytes; use shims::time::system_time_to_duration; +use shims::unix::linux::fd::epoll::Epoll; #[derive(Debug)] -struct FileHandle { +pub struct FileHandle { file: File, writable: bool, } -trait FileDescriptor: std::fmt::Debug { +pub trait FileDescriptor: std::fmt::Debug { fn name(&self) -> &'static str; fn as_file_handle<'tcx>(&self) -> InterpResult<'tcx, &FileHandle> { throw_unsup_format!("{} cannot be used as FileHandle", self.name()); } + fn as_epoll_handle<'tcx>(&mut self) -> InterpResult<'tcx, &mut Epoll> { + throw_unsup_format!("not an epoll file descriptor"); + } + fn read<'tcx>( &mut self, _communicate_allowed: bool, @@ -274,7 +279,7 @@ impl FileDescriptor for NullOutput { #[derive(Debug)] pub struct FileHandler { - handles: BTreeMap>, + pub handles: BTreeMap>, } impl VisitTags for FileHandler { @@ -297,7 +302,7 @@ impl FileHandler { FileHandler { handles } } - fn insert_fd(&mut self, file_handle: Box) -> i32 { + pub fn insert_fd(&mut self, file_handle: Box) -> i32 { self.insert_fd_with_min_fd(file_handle, 0) } @@ -376,17 +381,6 @@ trait EvalContextExtPrivate<'mir, 'tcx: 'mir>: crate::MiriInterpCxExt<'mir, 'tcx Ok(0) } - /// Function used when a handle is not found inside `FileHandler`. It returns `Ok(-1)`and sets - /// the last OS error to `libc::EBADF` (invalid file descriptor). This function uses - /// `T: From` instead of `i32` directly because some fs functions return different integer - /// types (like `read`, that returns an `i64`). - fn handle_not_found>(&mut self) -> InterpResult<'tcx, T> { - let this = self.eval_context_mut(); - let ebadf = this.eval_libc("EBADF"); - this.set_last_error(ebadf)?; - Ok((-1).into()) - } - fn file_type_to_d_type( &mut self, file_type: std::io::Result, @@ -726,6 +720,17 @@ pub trait EvalContextExt<'mir, 'tcx: 'mir>: crate::MiriInterpCxExt<'mir, 'tcx> { )) } + /// Function used when a handle is not found inside `FileHandler`. It returns `Ok(-1)`and sets + /// the last OS error to `libc::EBADF` (invalid file descriptor). This function uses + /// `T: From` instead of `i32` directly because some fs functions return different integer + /// types (like `read`, that returns an `i64`). + fn handle_not_found>(&mut self) -> InterpResult<'tcx, T> { + let this = self.eval_context_mut(); + let ebadf = this.eval_libc("EBADF"); + this.set_last_error(ebadf)?; + Ok((-1).into()) + } + fn read( &mut self, fd: i32, diff --git a/src/shims/unix/linux/fd.rs b/src/shims/unix/linux/fd.rs new file mode 100644 index 0000000000..212b793634 --- /dev/null +++ b/src/shims/unix/linux/fd.rs @@ -0,0 +1,191 @@ +use rustc_middle::ty::ScalarInt; + +use crate::*; +use epoll::{Epoll, EpollEvent}; +use event::Event; +use socketpair::SocketPair; + +use shims::unix::fs::EvalContextExt as _; + +pub mod epoll; +pub mod event; +pub mod socketpair; + +impl<'mir, 'tcx: 'mir> EvalContextExt<'mir, 'tcx> for crate::MiriInterpCx<'mir, 'tcx> {} +pub trait EvalContextExt<'mir, 'tcx: 'mir>: crate::MiriInterpCxExt<'mir, 'tcx> { + /// This function returns a file descriptor referring to the new `Epoll` instance. This file + /// descriptor is used for all subsequent calls to the epoll interface. If the `flags` argument + /// is 0, then this function is the same as `epoll_create()`. + /// + /// + fn epoll_create1( + &mut self, + flags: &OpTy<'tcx, Provenance>, + ) -> InterpResult<'tcx, Scalar> { + let this = self.eval_context_mut(); + + let flags = this.read_scalar(flags)?.to_i32()?; + + let epoll_cloexec = this.eval_libc_i32("EPOLL_CLOEXEC"); + if flags == epoll_cloexec { + // Miri does not support exec, so this flag has no effect. + } else if flags != 0 { + throw_unsup_format!("epoll_create1 flags {flags} are not implemented"); + } + + let fd = this.machine.file_handler.insert_fd(Box::new(Epoll::default())); + Ok(Scalar::from_i32(fd)) + } + + /// This function performs control operations on the `Epoll` instance referred to by the file + /// descriptor `epfd`. It requests that the operation `op` be performed for the target file + /// descriptor, `fd`. + /// + /// Valid values for the op argument are: + /// `EPOLL_CTL_ADD` - Register the target file descriptor `fd` on the `Epoll` instance referred + /// to by the file descriptor `epfd` and associate the event `event` with the internal file + /// linked to `fd`. + /// `EPOLL_CTL_MOD` - Change the event `event` associated with the target file descriptor `fd`. + /// `EPOLL_CTL_DEL` - Deregister the target file descriptor `fd` from the `Epoll` instance + /// referred to by `epfd`. The `event` is ignored and can be null. + /// + /// + fn epoll_ctl( + &mut self, + epfd: &OpTy<'tcx, Provenance>, + op: &OpTy<'tcx, Provenance>, + fd: &OpTy<'tcx, Provenance>, + event: &OpTy<'tcx, Provenance>, + ) -> InterpResult<'tcx, Scalar> { + let this = self.eval_context_mut(); + + let epfd = this.read_scalar(epfd)?.to_i32()?; + let op = this.read_scalar(op)?.to_i32()?; + let fd = this.read_scalar(fd)?.to_i32()?; + let _event = this.read_scalar(event)?.to_pointer(this)?; + + let epoll_ctl_add = this.eval_libc_i32("EPOLL_CTL_ADD"); + let epoll_ctl_mod = this.eval_libc_i32("EPOLL_CTL_MOD"); + let epoll_ctl_del = this.eval_libc_i32("EPOLL_CTL_DEL"); + + if op == epoll_ctl_add || op == epoll_ctl_mod { + let event = this.deref_operand(event)?; + + let events = this.mplace_field(&event, 0)?; + let events = this.read_scalar(&events.into())?.to_u32()?; + let data = this.mplace_field(&event, 1)?; + let data = this.read_scalar(&data.into())?; + let event = EpollEvent { events, data }; + + if let Some(epfd) = this.machine.file_handler.handles.get_mut(&epfd) { + let epfd = epfd.as_epoll_handle()?; + + epfd.file_descriptors.insert(fd, event); + Ok(Scalar::from_i32(0)) + } else { + Ok(Scalar::from_i32(this.handle_not_found()?)) + } + } else if op == epoll_ctl_del { + if let Some(epfd) = this.machine.file_handler.handles.get_mut(&epfd) { + let epfd = epfd.as_epoll_handle()?; + + epfd.file_descriptors.remove(&fd); + Ok(Scalar::from_i32(0)) + } else { + Ok(Scalar::from_i32(this.handle_not_found()?)) + } + } else { + let einval = this.eval_libc("EINVAL"); + this.set_last_error(einval)?; + Ok(Scalar::from_i32(-1)) + } + } + + /// This function creates an `Event` that is used as an event wait/notify mechanism by + /// user-space applications, and by the kernel to notify user-space applications of events. + /// The `Event` contains an `u64` counter maintained by the kernel. The counter is initialized + /// with the value specified in the `initval` argument. + /// + /// A new file descriptor referring to the `Event` is returned. The `read`, `write`, `poll`, + /// `select`, and `close` operations can be performed on the file descriptor. For more + /// information on these operations, see the man page linked below. + /// + /// The `flags` are not currently implemented for eventfd. + /// The `flags` may be bitwise ORed to change the behavior of `eventfd`: + /// `EFD_CLOEXEC` - Set the close-on-exec (`FD_CLOEXEC`) flag on the new file descriptor. + /// `EFD_NONBLOCK` - Set the `O_NONBLOCK` file status flag on the new open file description. + /// `EFD_SEMAPHORE` - miri does not support semaphore-like semantics. + /// + /// + fn eventfd( + &mut self, + val: &OpTy<'tcx, Provenance>, + flags: &OpTy<'tcx, Provenance>, + ) -> InterpResult<'tcx, Scalar> { + let this = self.eval_context_mut(); + + let val = this.read_scalar(val)?.to_u32()?; + let flags = this.read_scalar(flags)?.to_i32()?; + + let efd_cloexec = this.eval_libc_i32("EFD_CLOEXEC"); + let efd_nonblock = this.eval_libc_i32("EFD_NONBLOCK"); + let efd_semaphore = this.eval_libc_i32("EFD_SEMAPHORE"); + + if flags & (efd_cloexec | efd_nonblock | efd_semaphore) == 0 { + throw_unsup_format!("{flags} is unsupported"); + } + // FIXME handle the cloexec and nonblock flags + if flags & efd_cloexec == efd_cloexec {} + if flags & efd_nonblock == efd_nonblock {} + if flags & efd_semaphore == efd_semaphore { + throw_unsup_format!("EFD_SEMAPHORE is unsupported"); + } + + let fh = &mut this.machine.file_handler; + let fd = fh.insert_fd(Box::new(Event { val })); + Ok(Scalar::from_i32(fd)) + } + + /// Currently this function creates new `SocketPair`s without specifying the domain, type, or + /// protocol of the new socket and these are stored in the socket values `sv` argument. + /// + /// This function creates an unnamed pair of connected sockets in the specified domain, of the + /// specified type, and using the optionally specified protocol. + /// + /// The `domain` argument specified a communication domain; this selects the protocol family + /// used for communication. The socket `type` specifies the communication semantics. + /// The `protocol` specifies a particular protocol to use with the socket. Normally there's + /// only a single protocol supported for a particular socket type within a given protocol + /// family, in which case `protocol` can be specified as 0. It is possible that many protocols + /// exist and in that case, a particular protocol must be specified. + /// + /// For more information on the arguments see the socket manpage: + /// + /// + /// + fn socketpair( + &mut self, + domain: &OpTy<'tcx, Provenance>, + type_: &OpTy<'tcx, Provenance>, + protocol: &OpTy<'tcx, Provenance>, + sv: &OpTy<'tcx, Provenance>, + ) -> InterpResult<'tcx, Scalar> { + let this = self.eval_context_mut(); + + let _domain = this.read_scalar(domain)?.to_i32()?; + let _type_ = this.read_scalar(type_)?.to_i32()?; + let _protocol = this.read_scalar(protocol)?.to_i32()?; + let sv = this.deref_operand(sv)?; + + let fh = &mut this.machine.file_handler; + let sv0 = fh.insert_fd(Box::new(SocketPair)); + let sv0 = ScalarInt::try_from_int(sv0, sv.layout.size).unwrap(); + let sv1 = fh.insert_fd(Box::new(SocketPair)); + let sv1 = ScalarInt::try_from_int(sv1, sv.layout.size).unwrap(); + + this.write_scalar(sv0, &sv.into())?; + this.write_scalar(sv1, &sv.offset(sv.layout.size, sv.layout, this)?.into())?; + + Ok(Scalar::from_i32(0)) + } +} diff --git a/src/shims/unix/linux/fd/epoll.rs b/src/shims/unix/linux/fd/epoll.rs new file mode 100644 index 0000000000..eb86773e6b --- /dev/null +++ b/src/shims/unix/linux/fd/epoll.rs @@ -0,0 +1,53 @@ +use crate::*; + +use crate::shims::unix::fs::FileDescriptor; + +use rustc_data_structures::fx::FxHashMap; +use std::io; + +/// An `Epoll` file descriptor connects file handles and epoll events +#[derive(Clone, Debug, Default)] +pub struct Epoll { + /// The file descriptors we are watching, and what we are watching for. + pub file_descriptors: FxHashMap, +} + +/// Epoll Events associate events with data. +/// These fields are currently unused by miri. +/// This matches the `epoll_event` struct defined +/// by the epoll_ctl man page. For more information +/// see the man page: +/// +/// +#[derive(Clone, Debug)] +pub struct EpollEvent { + pub events: u32, + /// `Scalar` is used to represent the + /// `epoll_data` type union. + pub data: Scalar, +} + +impl FileDescriptor for Epoll { + fn name(&self) -> &'static str { + "epoll" + } + + fn as_epoll_handle<'tcx>(&mut self) -> InterpResult<'tcx, &mut Epoll> { + Ok(self) + } + + fn dup<'tcx>(&mut self) -> io::Result> { + Ok(Box::new(self.clone())) + } + + fn is_tty(&self) -> bool { + false + } + + fn close<'tcx>( + self: Box, + _communicate_allowed: bool, + ) -> InterpResult<'tcx, io::Result> { + Ok(Ok(0)) + } +} diff --git a/src/shims/unix/linux/fd/event.rs b/src/shims/unix/linux/fd/event.rs new file mode 100644 index 0000000000..e87ff56bee --- /dev/null +++ b/src/shims/unix/linux/fd/event.rs @@ -0,0 +1,38 @@ +use crate::shims::unix::fs::FileDescriptor; + +use rustc_const_eval::interpret::InterpResult; + +use std::io; + +/// A kind of file descriptor created by `eventfd`. +/// The `Event` type isn't currently written to by `eventfd`. +/// The interface is meant to keep track of objects associated +/// with a file descriptor. For more information see the man +/// page below: +/// +/// +#[derive(Debug)] +pub struct Event { + pub val: u32, +} + +impl FileDescriptor for Event { + fn name(&self) -> &'static str { + "event" + } + + fn dup<'tcx>(&mut self) -> io::Result> { + Ok(Box::new(Event { val: self.val })) + } + + fn is_tty(&self) -> bool { + false + } + + fn close<'tcx>( + self: Box, + _communicate_allowed: bool, + ) -> InterpResult<'tcx, io::Result> { + Ok(Ok(0)) + } +} diff --git a/src/shims/unix/linux/fd/socketpair.rs b/src/shims/unix/linux/fd/socketpair.rs new file mode 100644 index 0000000000..036d3a2e31 --- /dev/null +++ b/src/shims/unix/linux/fd/socketpair.rs @@ -0,0 +1,32 @@ +use crate::*; + +use crate::shims::unix::fs::FileDescriptor; + +use std::io; + +/// Pair of connected sockets. +/// +/// We currently don't allow sending any data through this pair, so this can be just a dummy. +#[derive(Debug)] +pub struct SocketPair; + +impl FileDescriptor for SocketPair { + fn name(&self) -> &'static str { + "socketpair" + } + + fn dup<'tcx>(&mut self) -> io::Result> { + Ok(Box::new(SocketPair)) + } + + fn is_tty(&self) -> bool { + false + } + + fn close<'tcx>( + self: Box, + _communicate_allowed: bool, + ) -> InterpResult<'tcx, io::Result> { + Ok(Ok(0)) + } +} diff --git a/src/shims/unix/linux/foreign_items.rs b/src/shims/unix/linux/foreign_items.rs index ff7b2b352f..be541deae4 100644 --- a/src/shims/unix/linux/foreign_items.rs +++ b/src/shims/unix/linux/foreign_items.rs @@ -1,9 +1,11 @@ use rustc_span::Symbol; use rustc_target::spec::abi::Abi; +use crate::machine::SIGRTMAX; use crate::*; use shims::foreign_items::EmulateByNameResult; use shims::unix::fs::EvalContextExt as _; +use shims::unix::linux::fd::EvalContextExt as _; use shims::unix::linux::sync::futex; use shims::unix::sync::EvalContextExt as _; use shims::unix::thread::EvalContextExt as _; @@ -42,6 +44,35 @@ pub trait EvalContextExt<'mir, 'tcx: 'mir>: crate::MiriInterpCxExt<'mir, 'tcx> { let result = this.sync_file_range(fd, offset, nbytes, flags)?; this.write_scalar(result, dest)?; } + "epoll_create1" => { + let [flag] = this.check_shim(abi, Abi::C { unwind: false }, link_name, args)?; + let result = this.epoll_create1(flag)?; + this.write_scalar(result, dest)?; + } + "epoll_ctl" => { + let [epfd, op, fd, event] = + this.check_shim(abi, Abi::C { unwind: false }, link_name, args)?; + let result = this.epoll_ctl(epfd, op, fd, event)?; + this.write_scalar(result, dest)?; + } + "eventfd" => { + let [val, flag] = + this.check_shim(abi, Abi::C { unwind: false }, link_name, args)?; + let result = this.eventfd(val, flag)?; + this.write_scalar(result, dest)?; + } + "socketpair" => { + let [domain, type_, protocol, sv] = + this.check_shim(abi, Abi::C { unwind: false }, link_name, args)?; + + let result = this.socketpair(domain, type_, protocol, sv)?; + this.write_scalar(result, dest)?; + } + "__libc_current_sigrtmax" => { + let [] = this.check_shim(abi, Abi::C { unwind: false }, link_name, args)?; + + this.write_scalar(Scalar::from_i32(SIGRTMAX), dest)?; + } // Threading "pthread_condattr_setclock" => { diff --git a/src/shims/unix/linux/mod.rs b/src/shims/unix/linux/mod.rs index 498eb57c57..437764c382 100644 --- a/src/shims/unix/linux/mod.rs +++ b/src/shims/unix/linux/mod.rs @@ -1,3 +1,4 @@ pub mod dlsym; +pub mod fd; pub mod foreign_items; pub mod sync; diff --git a/tests/fail/crates/tokio_mvp.rs b/tests/fail/crates/tokio_mvp.rs deleted file mode 100644 index 7cb42c09a9..0000000000 --- a/tests/fail/crates/tokio_mvp.rs +++ /dev/null @@ -1,7 +0,0 @@ -//@compile-flags: -Zmiri-disable-isolation -//@error-pattern: can't call foreign function: epoll_create1 -//@normalize-stderr-test: " = note: inside .*\n" -> "" -//@only-target-linux: the errors differ too much between platforms - -#[tokio::main] -async fn main() {} diff --git a/tests/fail/crates/tokio_mvp.stderr b/tests/fail/crates/tokio_mvp.stderr deleted file mode 100644 index 1e7dfaa749..0000000000 --- a/tests/fail/crates/tokio_mvp.stderr +++ /dev/null @@ -1,19 +0,0 @@ -error: unsupported operation: can't call foreign function: epoll_create1 - --> CARGO_REGISTRY/.../epoll.rs:LL:CC - | -LL | let res = syscall!(epoll_create1(libc::EPOLL_CLOEXEC)); - | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ can't call foreign function: epoll_create1 - | - = help: this is likely not a bug in the program; it indicates that the program performed an operation that the interpreter does not support - = note: BACKTRACE: -note: inside `main` - --> $DIR/tokio_mvp.rs:LL:CC - | -LL | #[tokio::main] - | ^^^^^^^^^^^^^^ - = note: this error originates in the macro `syscall` which comes from the expansion of the attribute macro `tokio::main` (in Nightly builds, run with -Z macro-backtrace for more info) - -note: some details are omitted, run with `MIRIFLAGS=-Zmiri-backtrace=full` for a verbose backtrace - -error: aborting due to previous error - diff --git a/tests/pass-dep/tokio_mvp.rs b/tests/pass-dep/tokio_mvp.rs new file mode 100644 index 0000000000..642168253c --- /dev/null +++ b/tests/pass-dep/tokio_mvp.rs @@ -0,0 +1,6 @@ +// Need to disable preemption to stay on the supported MVP codepath in mio. +//@compile-flags: -Zmiri-disable-isolation -Zmiri-permissive-provenance -Zmiri-preemption-rate=0 +//@only-target-x86_64-unknown-linux: support for tokio exists only on linux and x86 + +#[tokio::main] +async fn main() {} From 44580098aed45b554140428a545625a20301efd3 Mon Sep 17 00:00:00 2001 From: Ralf Jung Date: Fri, 16 Dec 2022 12:19:21 +0100 Subject: [PATCH 14/28] Preparing for merge from rustc --- rust-version | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/rust-version b/rust-version index 5f1a4428fe..e6c238023e 100644 --- a/rust-version +++ b/rust-version @@ -1 +1 @@ -e1c91213ff80af5b87a197b784b40bcbc8cf3add +a803f313fdf8f6eb2d674d7dfb3694a2b437ee1e From 3e3e5e624a8ff932e373f219f35de574f25048da Mon Sep 17 00:00:00 2001 From: Ralf Jung Date: Fri, 16 Dec 2022 14:19:48 +0100 Subject: [PATCH 15/28] fmt --- src/machine.rs | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/src/machine.rs b/src/machine.rs index 32ae3fad57..e5a748453e 100644 --- a/src/machine.rs +++ b/src/machine.rs @@ -9,6 +9,7 @@ use rand::rngs::StdRng; use rand::SeedableRng; use rustc_ast::ast::Mutability; +use rustc_const_eval::const_eval::CheckAlignment; use rustc_data_structures::fx::{FxHashMap, FxHashSet}; #[allow(unused)] use rustc_data_structures::static_assert_size; @@ -22,9 +23,8 @@ use rustc_middle::{ }; use rustc_span::def_id::{CrateNum, DefId}; use rustc_span::Symbol; -use rustc_target::abi::{Size, Align}; +use rustc_target::abi::{Align, Size}; use rustc_target::spec::abi::Abi; -use rustc_const_eval::const_eval::CheckAlignment; use crate::{ concurrency::{data_race, weak_memory}, From b06737ebcc94a2be74c56d45087ec6bf0bc6a59e Mon Sep 17 00:00:00 2001 From: Ben Kimock Date: Sun, 30 Oct 2022 21:04:00 -0400 Subject: [PATCH 16/28] Include a Span in VClock --- src/concurrency/data_race.rs | 171 +++++++++++------- src/concurrency/init_once.rs | 6 +- src/concurrency/sync.rs | 33 +++- src/concurrency/thread.rs | 12 +- src/concurrency/vector_clock.rs | 90 +++++++-- src/concurrency/weak_memory.rs | 2 +- src/diagnostics.rs | 26 ++- src/machine.rs | 1 + tests/fail/data_race/alloc_read_race.stderr | 10 + tests/fail/data_race/alloc_write_race.stderr | 10 + .../atomic_read_na_write_race1.stderr | 10 + .../atomic_read_na_write_race2.stderr | 10 + .../atomic_write_na_read_race1.stderr | 10 + .../atomic_write_na_read_race2.stderr | 10 + .../atomic_write_na_write_race1.stderr | 10 + .../atomic_write_na_write_race2.stderr | 10 + .../dangling_thread_async_race.stderr | 10 + .../data_race/dangling_thread_race.stderr | 10 + .../fail/data_race/dealloc_read_race1.stderr | 15 ++ .../data_race/dealloc_read_race_stack.stderr | 10 + .../fail/data_race/dealloc_write_race1.stderr | 15 ++ .../data_race/dealloc_write_race_stack.stderr | 10 + .../enable_after_join_to_main.stderr | 10 + tests/fail/data_race/fence_after_load.stderr | 10 + tests/fail/data_race/read_write_race.stderr | 10 + .../data_race/read_write_race_stack.stderr | 10 + .../fail/data_race/relax_acquire_race.stderr | 10 + tests/fail/data_race/release_seq_race.stderr | 10 + .../release_seq_race_same_thread.stderr | 10 + tests/fail/data_race/rmw_race.stderr | 10 + tests/fail/data_race/stack_pop_race.stderr | 10 + tests/fail/data_race/write_write_race.stderr | 10 + .../data_race/write_write_race_stack.stderr | 10 + .../retag_data_race_read.stderr | 10 + .../retag_data_race_write.stderr | 10 + 35 files changed, 532 insertions(+), 89 deletions(-) diff --git a/src/concurrency/data_race.rs b/src/concurrency/data_race.rs index bcbf45a3d2..8b343dd2fe 100644 --- a/src/concurrency/data_race.rs +++ b/src/concurrency/data_race.rs @@ -50,8 +50,11 @@ use rustc_ast::Mutability; use rustc_data_structures::fx::{FxHashMap, FxHashSet}; use rustc_index::vec::{Idx, IndexVec}; use rustc_middle::mir; +use rustc_span::Span; +use rustc_span::DUMMY_SP; use rustc_target::abi::{Align, Size}; +use crate::diagnostics::RacingOp; use crate::*; use super::{ @@ -144,8 +147,8 @@ impl ThreadClockSet { /// Increment the happens-before clock at a /// known index. #[inline] - fn increment_clock(&mut self, index: VectorIdx) { - self.clock.increment_index(index); + fn increment_clock(&mut self, index: VectorIdx, current_span: Span) { + self.clock.increment_index(index, current_span); } /// Join the happens-before clock with that of @@ -361,6 +364,8 @@ impl MemoryCellClocks { atomic.read_vector.set_at_index(&clocks.clock, index); Ok(()) } else { + let atomic = self.atomic_mut(); + atomic.read_vector.set_at_index(&clocks.clock, index); Err(DataRace) } } @@ -378,6 +383,8 @@ impl MemoryCellClocks { atomic.write_vector.set_at_index(&clocks.clock, index); Ok(()) } else { + let atomic = self.atomic_mut(); + atomic.write_vector.set_at_index(&clocks.clock, index); Err(DataRace) } } @@ -386,46 +393,51 @@ impl MemoryCellClocks { /// returns true if a data-race is detected. fn read_race_detect( &mut self, - clocks: &ThreadClockSet, + clocks: &mut ThreadClockSet, index: VectorIdx, + current_span: Span, ) -> Result<(), DataRace> { log::trace!("Unsynchronized read with vectors: {:#?} :: {:#?}", self, clocks); - if self.write <= clocks.clock[self.write_index] { + let res = if self.write <= clocks.clock[self.write_index] { let race_free = if let Some(atomic) = self.atomic() { atomic.write_vector <= clocks.clock } else { true }; - if race_free { - self.read.set_at_index(&clocks.clock, index); - Ok(()) - } else { - Err(DataRace) - } + self.read.set_at_index(&clocks.clock, index); + if race_free { Ok(()) } else { Err(DataRace) } } else { Err(DataRace) + }; + if res.is_ok() && current_span != DUMMY_SP { + clocks.clock[index].span = current_span; } + res } /// Detect races for non-atomic write operations at the current memory cell /// returns true if a data-race is detected. fn write_race_detect( &mut self, - clocks: &ThreadClockSet, + clocks: &mut ThreadClockSet, index: VectorIdx, write_type: WriteType, + current_span: Span, ) -> Result<(), DataRace> { log::trace!("Unsynchronized write with vectors: {:#?} :: {:#?}", self, clocks); + if current_span != DUMMY_SP { + clocks.clock[index].span = current_span; + } if self.write <= clocks.clock[self.write_index] && self.read <= clocks.clock { let race_free = if let Some(atomic) = self.atomic() { atomic.write_vector <= clocks.clock && atomic.read_vector <= clocks.clock } else { true }; + self.write = clocks.clock[index]; + self.write_index = index; + self.write_type = write_type; if race_free { - self.write = clocks.clock[index]; - self.write_index = index; - self.write_type = write_type; self.read.set_zero_vector(); Ok(()) } else { @@ -621,30 +633,35 @@ pub trait EvalContextExt<'mir, 'tcx: 'mir>: MiriInterpCxExt<'mir, 'tcx> { /// Update the data-race detector for an atomic fence on the current thread. fn atomic_fence(&mut self, atomic: AtomicFenceOrd) -> InterpResult<'tcx> { let this = self.eval_context_mut(); + let current_span = this.machine.current_span(); if let Some(data_race) = &mut this.machine.data_race { - data_race.maybe_perform_sync_operation(&this.machine.threads, |index, mut clocks| { - log::trace!("Atomic fence on {:?} with ordering {:?}", index, atomic); - - // Apply data-race detection for the current fences - // this treats AcqRel and SeqCst as the same as an acquire - // and release fence applied in the same timestamp. - if atomic != AtomicFenceOrd::Release { - // Either Acquire | AcqRel | SeqCst - clocks.apply_acquire_fence(); - } - if atomic != AtomicFenceOrd::Acquire { - // Either Release | AcqRel | SeqCst - clocks.apply_release_fence(); - } - if atomic == AtomicFenceOrd::SeqCst { - data_race.last_sc_fence.borrow_mut().set_at_index(&clocks.clock, index); - clocks.fence_seqcst.join(&data_race.last_sc_fence.borrow()); - clocks.write_seqcst.join(&data_race.last_sc_write.borrow()); - } + data_race.maybe_perform_sync_operation( + &this.machine.threads, + |index, mut clocks| { + log::trace!("Atomic fence on {:?} with ordering {:?}", index, atomic); + + // Apply data-race detection for the current fences + // this treats AcqRel and SeqCst as the same as an acquire + // and release fence applied in the same timestamp. + if atomic != AtomicFenceOrd::Release { + // Either Acquire | AcqRel | SeqCst + clocks.apply_acquire_fence(); + } + if atomic != AtomicFenceOrd::Acquire { + // Either Release | AcqRel | SeqCst + clocks.apply_release_fence(); + } + if atomic == AtomicFenceOrd::SeqCst { + data_race.last_sc_fence.borrow_mut().set_at_index(&clocks.clock, index); + clocks.fence_seqcst.join(&data_race.last_sc_fence.borrow()); + clocks.write_seqcst.join(&data_race.last_sc_write.borrow()); + } - // Increment timestamp in case of release semantics. - Ok(atomic != AtomicFenceOrd::Acquire) - }) + // Increment timestamp in case of release semantics. + Ok(atomic != AtomicFenceOrd::Acquire) + }, + current_span, + ) } else { Ok(()) } @@ -682,6 +699,7 @@ impl VClockAlloc { thread_mgr: &ThreadManager<'_, '_>, len: Size, kind: MemoryKind, + current_span: Span, ) -> VClockAlloc { let (alloc_timestamp, alloc_index) = match kind { // User allocated and stack memory should track allocation. @@ -693,7 +711,10 @@ impl VClockAlloc { ) | MemoryKind::Stack => { let (alloc_index, clocks) = global.current_thread_state(thread_mgr); - let alloc_timestamp = clocks.clock[alloc_index]; + let mut alloc_timestamp = clocks.clock[alloc_index]; + if current_span != DUMMY_SP { + alloc_timestamp.span = current_span; + } (alloc_timestamp, alloc_index) } // Other global memory should trace races but be allocated at the 0 timestamp. @@ -704,7 +725,7 @@ impl VClockAlloc { | MiriMemoryKind::ExternStatic | MiriMemoryKind::Tls, ) - | MemoryKind::CallerLocation => (0, VectorIdx::MAX_INDEX), + | MemoryKind::CallerLocation => (VTimestamp::NONE, VectorIdx::MAX_INDEX), }; VClockAlloc { alloc_ranges: RefCell::new(RangeMap::new( @@ -735,7 +756,7 @@ impl VClockAlloc { let idx = l_remainder_slice .iter() .enumerate() - .find_map(|(idx, &r)| if r == 0 { None } else { Some(idx) }) + .find_map(|(idx, &r)| if r == VTimestamp::NONE { None } else { Some(idx) }) .expect("Invalid VClock Invariant"); Some(idx + r_slice.len()) } else { @@ -762,7 +783,7 @@ impl VClockAlloc { ) -> InterpResult<'tcx> { let (current_index, current_clocks) = global.current_thread_state(thread_mgr); let write_clock; - let (other_action, other_thread, _other_clock) = if range.write + let (other_action, other_thread, other_clock) = if range.write > current_clocks.clock[range.write_index] { // Convert the write action into the vector clock it @@ -799,14 +820,19 @@ impl VClockAlloc { let other_thread_info = global.print_thread_metadata(thread_mgr, other_thread); // Throw the data-race detection. - throw_ub_format!( - "Data race detected between {} on {} and {} on {} at {:?}", - action, - current_thread_info, - other_action, - other_thread_info, - ptr_dbg, - ) + Err(err_machine_stop!(TerminationInfo::DataRace { + ptr: ptr_dbg, + op1: RacingOp { + action: action.to_string(), + thread_info: current_thread_info, + span: current_clocks.clock.as_slice()[current_index.index()].span_data(), + }, + op2: RacingOp { + action: other_action.to_string(), + thread_info: other_thread_info, + span: other_clock.as_slice()[other_thread.index()].span_data(), + }, + }))? } /// Detect racing atomic read and writes (not data races) @@ -840,12 +866,14 @@ impl VClockAlloc { range: AllocRange, machine: &MiriMachine<'_, '_>, ) -> InterpResult<'tcx> { + let current_span = machine.current_span(); let global = machine.data_race.as_ref().unwrap(); if global.race_detecting() { - let (index, clocks) = global.current_thread_state(&machine.threads); + let (index, mut clocks) = global.current_thread_state_mut(&machine.threads); let mut alloc_ranges = self.alloc_ranges.borrow_mut(); for (offset, range) in alloc_ranges.iter_mut(range.start, range.size) { - if let Err(DataRace) = range.read_race_detect(&clocks, index) { + if let Err(DataRace) = range.read_race_detect(&mut clocks, index, current_span) { + drop(clocks); // Report data-race. return Self::report_data_race( global, @@ -871,11 +899,15 @@ impl VClockAlloc { write_type: WriteType, machine: &mut MiriMachine<'_, '_>, ) -> InterpResult<'tcx> { + let current_span = machine.current_span(); let global = machine.data_race.as_mut().unwrap(); if global.race_detecting() { - let (index, clocks) = global.current_thread_state(&machine.threads); + let (index, mut clocks) = global.current_thread_state_mut(&machine.threads); for (offset, range) in self.alloc_ranges.get_mut().iter_mut(range.start, range.size) { - if let Err(DataRace) = range.write_race_detect(&clocks, index, write_type) { + if let Err(DataRace) = + range.write_race_detect(&mut clocks, index, write_type, current_span) + { + drop(clocks); // Report data-race return Self::report_data_race( global, @@ -1100,6 +1132,7 @@ trait EvalContextPrivExt<'mir, 'tcx: 'mir>: MiriInterpCxExt<'mir, 'tcx> { size.bytes() ); + let current_span = this.machine.current_span(); // Perform the atomic operation. data_race.maybe_perform_sync_operation( &this.machine.threads, @@ -1124,6 +1157,7 @@ trait EvalContextPrivExt<'mir, 'tcx: 'mir>: MiriInterpCxExt<'mir, 'tcx> { // This conservatively assumes all operations have release semantics Ok(true) }, + current_span, )?; // Log changes to atomic memory. @@ -1303,7 +1337,12 @@ impl GlobalState { // Hook for thread creation, enabled multi-threaded execution and marks // the current thread timestamp as happening-before the current thread. #[inline] - pub fn thread_created(&mut self, thread_mgr: &ThreadManager<'_, '_>, thread: ThreadId) { + pub fn thread_created( + &mut self, + thread_mgr: &ThreadManager<'_, '_>, + thread: ThreadId, + current_span: Span, + ) { let current_index = self.current_index(thread_mgr); // Enable multi-threaded execution, there are now at least two threads @@ -1320,7 +1359,7 @@ impl GlobalState { // Now re-configure the re-use candidate, increment the clock // for the new sync use of the vector. let vector_clocks = self.vector_clocks.get_mut(); - vector_clocks[reuse_index].increment_clock(reuse_index); + vector_clocks[reuse_index].increment_clock(reuse_index, current_span); // Locate the old thread the vector was associated with and update // it to represent the new thread instead. @@ -1360,8 +1399,8 @@ impl GlobalState { // Advance both threads after the synchronized operation. // Both operations are considered to have release semantics. - current.increment_clock(current_index); - created.increment_clock(created_index); + current.increment_clock(current_index, current_span); + created.increment_clock(created_index, current_span); } /// Hook on a thread join to update the implicit happens-before relation between the joined @@ -1427,13 +1466,13 @@ impl GlobalState { /// This should be called strictly before any calls to /// `thread_joined`. #[inline] - pub fn thread_terminated(&mut self, thread_mgr: &ThreadManager<'_, '_>) { + pub fn thread_terminated(&mut self, thread_mgr: &ThreadManager<'_, '_>, current_span: Span) { let current_index = self.current_index(thread_mgr); // Increment the clock to a unique termination timestamp. let vector_clocks = self.vector_clocks.get_mut(); let current_clocks = &mut vector_clocks[current_index]; - current_clocks.increment_clock(current_index); + current_clocks.increment_clock(current_index, current_span); // Load the current thread id for the executing vector. let vector_info = self.vector_info.get_mut(); @@ -1463,12 +1502,13 @@ impl GlobalState { &self, thread_mgr: &ThreadManager<'_, '_>, op: impl FnOnce(VectorIdx, RefMut<'_, ThreadClockSet>) -> InterpResult<'tcx, bool>, + current_span: Span, ) -> InterpResult<'tcx> { if self.multi_threaded.get() { let (index, clocks) = self.current_thread_state_mut(thread_mgr); if op(index, clocks)? { let (_, mut clocks) = self.current_thread_state_mut(thread_mgr); - clocks.increment_clock(index); + clocks.increment_clock(index, current_span); } } Ok(()) @@ -1501,10 +1541,10 @@ impl GlobalState { /// since an acquire operation should have occurred before, however /// for futex & condvar operations this is not the case and this /// operation must be used. - pub fn validate_lock_release(&self, lock: &mut VClock, thread: ThreadId) { + pub fn validate_lock_release(&self, lock: &mut VClock, thread: ThreadId, current_span: Span) { let (index, mut clocks) = self.load_thread_state_mut(thread); lock.clone_from(&clocks.clock); - clocks.increment_clock(index); + clocks.increment_clock(index, current_span); } /// Release a lock handle, express that this happens-before @@ -1514,10 +1554,15 @@ impl GlobalState { /// For normal locks this should be equivalent to `validate_lock_release`. /// This function only exists for joining over the set of concurrent readers /// in a read-write lock and should not be used for anything else. - pub fn validate_lock_release_shared(&self, lock: &mut VClock, thread: ThreadId) { + pub fn validate_lock_release_shared( + &self, + lock: &mut VClock, + thread: ThreadId, + current_span: Span, + ) { let (index, mut clocks) = self.load_thread_state_mut(thread); lock.join(&clocks.clock); - clocks.increment_clock(index); + clocks.increment_clock(index, current_span); } /// Load the vector index used by the given thread as well as the set of vector clocks diff --git a/src/concurrency/init_once.rs b/src/concurrency/init_once.rs index 9c9d505297..867683d355 100644 --- a/src/concurrency/init_once.rs +++ b/src/concurrency/init_once.rs @@ -160,6 +160,7 @@ pub trait EvalContextExt<'mir, 'tcx: 'mir>: crate::MiriInterpCxExt<'mir, 'tcx> { fn init_once_complete(&mut self, id: InitOnceId) -> InterpResult<'tcx> { let this = self.eval_context_mut(); let current_thread = this.get_active_thread(); + let current_span = this.machine.current_span(); let init_once = &mut this.machine.threads.sync.init_onces[id]; assert_eq!( @@ -172,7 +173,7 @@ pub trait EvalContextExt<'mir, 'tcx: 'mir>: crate::MiriInterpCxExt<'mir, 'tcx> { // Each complete happens-before the end of the wait if let Some(data_race) = &this.machine.data_race { - data_race.validate_lock_release(&mut init_once.data_race, current_thread); + data_race.validate_lock_release(&mut init_once.data_race, current_thread, current_span); } // Wake up everyone. @@ -188,6 +189,7 @@ pub trait EvalContextExt<'mir, 'tcx: 'mir>: crate::MiriInterpCxExt<'mir, 'tcx> { fn init_once_fail(&mut self, id: InitOnceId) -> InterpResult<'tcx> { let this = self.eval_context_mut(); let current_thread = this.get_active_thread(); + let current_span = this.machine.current_span(); let init_once = &mut this.machine.threads.sync.init_onces[id]; assert_eq!( init_once.status, @@ -197,7 +199,7 @@ pub trait EvalContextExt<'mir, 'tcx: 'mir>: crate::MiriInterpCxExt<'mir, 'tcx> { // Each complete happens-before the end of the wait if let Some(data_race) = &this.machine.data_race { - data_race.validate_lock_release(&mut init_once.data_race, current_thread); + data_race.validate_lock_release(&mut init_once.data_race, current_thread, current_span); } // Wake up one waiting thread, so they can go ahead and try to init this. diff --git a/src/concurrency/sync.rs b/src/concurrency/sync.rs index 402c9ce6fc..b962052397 100644 --- a/src/concurrency/sync.rs +++ b/src/concurrency/sync.rs @@ -359,6 +359,7 @@ pub trait EvalContextExt<'mir, 'tcx: 'mir>: crate::MiriInterpCxExt<'mir, 'tcx> { /// return `None`. fn mutex_unlock(&mut self, id: MutexId, expected_owner: ThreadId) -> Option { let this = self.eval_context_mut(); + let current_span = this.machine.current_span(); let mutex = &mut this.machine.threads.sync.mutexes[id]; if let Some(current_owner) = mutex.owner { // Mutex is locked. @@ -375,7 +376,11 @@ pub trait EvalContextExt<'mir, 'tcx: 'mir>: crate::MiriInterpCxExt<'mir, 'tcx> { // The mutex is completely unlocked. Try transfering ownership // to another thread. if let Some(data_race) = &this.machine.data_race { - data_race.validate_lock_release(&mut mutex.data_race, current_owner); + data_race.validate_lock_release( + &mut mutex.data_race, + current_owner, + current_span, + ); } this.mutex_dequeue_and_lock(id); } @@ -454,6 +459,7 @@ pub trait EvalContextExt<'mir, 'tcx: 'mir>: crate::MiriInterpCxExt<'mir, 'tcx> { /// Returns `true` if succeeded, `false` if this `reader` did not hold the lock. fn rwlock_reader_unlock(&mut self, id: RwLockId, reader: ThreadId) -> bool { let this = self.eval_context_mut(); + let current_span = this.machine.current_span(); let rwlock = &mut this.machine.threads.sync.rwlocks[id]; match rwlock.readers.entry(reader) { Entry::Occupied(mut entry) => { @@ -470,7 +476,11 @@ pub trait EvalContextExt<'mir, 'tcx: 'mir>: crate::MiriInterpCxExt<'mir, 'tcx> { Entry::Vacant(_) => return false, // we did not even own this lock } if let Some(data_race) = &this.machine.data_race { - data_race.validate_lock_release_shared(&mut rwlock.data_race_reader, reader); + data_race.validate_lock_release_shared( + &mut rwlock.data_race_reader, + reader, + current_span, + ); } // The thread was a reader. If the lock is not held any more, give it to a writer. @@ -511,6 +521,7 @@ pub trait EvalContextExt<'mir, 'tcx: 'mir>: crate::MiriInterpCxExt<'mir, 'tcx> { #[inline] fn rwlock_writer_unlock(&mut self, id: RwLockId, expected_writer: ThreadId) -> bool { let this = self.eval_context_mut(); + let current_span = this.machine.current_span(); let rwlock = &mut this.machine.threads.sync.rwlocks[id]; if let Some(current_writer) = rwlock.writer { if current_writer != expected_writer { @@ -523,8 +534,16 @@ pub trait EvalContextExt<'mir, 'tcx: 'mir>: crate::MiriInterpCxExt<'mir, 'tcx> { // since this writer happens-before both the union of readers once they are finished // and the next writer if let Some(data_race) = &this.machine.data_race { - data_race.validate_lock_release(&mut rwlock.data_race, current_writer); - data_race.validate_lock_release(&mut rwlock.data_race_reader, current_writer); + data_race.validate_lock_release( + &mut rwlock.data_race, + current_writer, + current_span, + ); + data_race.validate_lock_release( + &mut rwlock.data_race_reader, + current_writer, + current_span, + ); } // The thread was a writer. // @@ -595,12 +614,13 @@ pub trait EvalContextExt<'mir, 'tcx: 'mir>: crate::MiriInterpCxExt<'mir, 'tcx> { fn condvar_signal(&mut self, id: CondvarId) -> Option<(ThreadId, CondvarLock)> { let this = self.eval_context_mut(); let current_thread = this.get_active_thread(); + let current_span = this.machine.current_span(); let condvar = &mut this.machine.threads.sync.condvars[id]; let data_race = &this.machine.data_race; // Each condvar signal happens-before the end of the condvar wake if let Some(data_race) = data_race { - data_race.validate_lock_release(&mut condvar.data_race, current_thread); + data_race.validate_lock_release(&mut condvar.data_race, current_thread, current_span); } condvar.waiters.pop_front().map(|waiter| { if let Some(data_race) = data_race { @@ -628,12 +648,13 @@ pub trait EvalContextExt<'mir, 'tcx: 'mir>: crate::MiriInterpCxExt<'mir, 'tcx> { fn futex_wake(&mut self, addr: u64, bitset: u32) -> Option { let this = self.eval_context_mut(); let current_thread = this.get_active_thread(); + let current_span = this.machine.current_span(); let futex = &mut this.machine.threads.sync.futexes.get_mut(&addr)?; let data_race = &this.machine.data_race; // Each futex-wake happens-before the end of the futex wait if let Some(data_race) = data_race { - data_race.validate_lock_release(&mut futex.data_race, current_thread); + data_race.validate_lock_release(&mut futex.data_race, current_thread, current_span); } // Wake up the first thread in the queue that matches any of the bits in the bitset. diff --git a/src/concurrency/thread.rs b/src/concurrency/thread.rs index 03f9ed351f..9173eb3c4e 100644 --- a/src/concurrency/thread.rs +++ b/src/concurrency/thread.rs @@ -13,6 +13,7 @@ use rustc_hir::def_id::DefId; use rustc_index::vec::{Idx, IndexVec}; use rustc_middle::mir::Mutability; use rustc_middle::ty::layout::TyAndLayout; +use rustc_span::Span; use rustc_target::spec::abi::Abi; use crate::concurrency::data_race; @@ -617,6 +618,7 @@ impl<'mir, 'tcx: 'mir> ThreadManager<'mir, 'tcx> { fn thread_terminated( &mut self, mut data_race: Option<&mut data_race::GlobalState>, + current_span: Span, ) -> Vec> { let mut free_tls_statics = Vec::new(); { @@ -634,7 +636,7 @@ impl<'mir, 'tcx: 'mir> ThreadManager<'mir, 'tcx> { } // Set the thread into a terminated state in the data-race detector. if let Some(ref mut data_race) = data_race { - data_race.thread_terminated(self); + data_race.thread_terminated(self, current_span); } // Check if we need to unblock any threads. let mut joined_threads = vec![]; // store which threads joined, we'll need it @@ -813,8 +815,9 @@ pub trait EvalContextExt<'mir, 'tcx: 'mir>: crate::MiriInterpCxExt<'mir, 'tcx> { let mut state = tls::TlsDtorsState::default(); Box::new(move |m| state.on_stack_empty(m)) }); + let current_span = this.machine.current_span(); if let Some(data_race) = &mut this.machine.data_race { - data_race.thread_created(&this.machine.threads, new_thread_id); + data_race.thread_created(&this.machine.threads, new_thread_id, current_span); } // Write the current thread-id, switch to the next thread later @@ -1041,7 +1044,10 @@ pub trait EvalContextExt<'mir, 'tcx: 'mir>: crate::MiriInterpCxExt<'mir, 'tcx> { assert!(thread.stack.is_empty(), "only threads with an empty stack can be terminated"); thread.state = ThreadState::Terminated; - for ptr in this.machine.threads.thread_terminated(this.machine.data_race.as_mut()) { + let current_span = this.machine.current_span(); + for ptr in + this.machine.threads.thread_terminated(this.machine.data_race.as_mut(), current_span) + { this.deallocate_ptr(ptr.into(), None, MiriMemoryKind::Tls.into())?; } Ok(()) diff --git a/src/concurrency/vector_clock.rs b/src/concurrency/vector_clock.rs index ba04991a58..191bb1449a 100644 --- a/src/concurrency/vector_clock.rs +++ b/src/concurrency/vector_clock.rs @@ -1,6 +1,11 @@ use rustc_index::vec::Idx; +use rustc_span::{Span, SpanData, DUMMY_SP}; use smallvec::SmallVec; -use std::{cmp::Ordering, fmt::Debug, ops::Index}; +use std::{ + cmp::Ordering, + fmt::Debug, + ops::{Index, IndexMut}, +}; /// A vector clock index, this is associated with a thread id /// but in some cases one vector index may be shared with @@ -42,7 +47,37 @@ const SMALL_VECTOR: usize = 4; /// The type of the time-stamps recorded in the data-race detector /// set to a type of unsigned integer -pub type VTimestamp = u32; +#[derive(Clone, Copy, Debug, Eq)] +pub struct VTimestamp { + time: u32, + pub span: Span, +} + +impl VTimestamp { + pub const NONE: VTimestamp = VTimestamp { time: 0, span: DUMMY_SP }; + + pub fn span_data(&self) -> SpanData { + self.span.data() + } +} + +impl PartialEq for VTimestamp { + fn eq(&self, other: &Self) -> bool { + self.time == other.time + } +} + +impl PartialOrd for VTimestamp { + fn partial_cmp(&self, other: &Self) -> Option { + Some(self.cmp(other)) + } +} + +impl Ord for VTimestamp { + fn cmp(&self, other: &Self) -> Ordering { + self.time.cmp(&other.time) + } +} /// A vector clock for detecting data-races, this is conceptually /// a map from a vector index (and thus a thread id) to a timestamp. @@ -62,7 +97,7 @@ impl VClock { /// for a value at the given index pub fn new_with_index(index: VectorIdx, timestamp: VTimestamp) -> VClock { let len = index.index() + 1; - let mut vec = smallvec::smallvec![0; len]; + let mut vec = smallvec::smallvec![VTimestamp::NONE; len]; vec[index.index()] = timestamp; VClock(vec) } @@ -79,7 +114,7 @@ impl VClock { #[inline] fn get_mut_with_min_len(&mut self, min_len: usize) -> &mut [VTimestamp] { if self.0.len() < min_len { - self.0.resize(min_len, 0); + self.0.resize(min_len, VTimestamp::NONE); } assert!(self.0.len() >= min_len); self.0.as_mut_slice() @@ -88,11 +123,14 @@ impl VClock { /// Increment the vector clock at a known index /// this will panic if the vector index overflows #[inline] - pub fn increment_index(&mut self, idx: VectorIdx) { + pub fn increment_index(&mut self, idx: VectorIdx, current_span: Span) { let idx = idx.index(); let mut_slice = self.get_mut_with_min_len(idx + 1); let idx_ref = &mut mut_slice[idx]; - *idx_ref = idx_ref.checked_add(1).expect("Vector clock overflow") + idx_ref.time = idx_ref.time.checked_add(1).expect("Vector clock overflow"); + if current_span != DUMMY_SP { + idx_ref.span = current_span; + } } // Join the two vector-clocks together, this @@ -102,14 +140,31 @@ impl VClock { let rhs_slice = other.as_slice(); let lhs_slice = self.get_mut_with_min_len(rhs_slice.len()); for (l, &r) in lhs_slice.iter_mut().zip(rhs_slice.iter()) { + let l_span = l.span; + let r_span = r.span; *l = r.max(*l); + if l.span == DUMMY_SP { + if r_span != DUMMY_SP { + l.span = r_span; + } + if l_span != DUMMY_SP { + l.span = l_span; + } + } } } /// Set the element at the current index of the vector pub fn set_at_index(&mut self, other: &Self, idx: VectorIdx) { let mut_slice = self.get_mut_with_min_len(idx.index() + 1); + + let prev_span = mut_slice[idx.index()].span; + mut_slice[idx.index()] = other[idx]; + + if other[idx].span == DUMMY_SP { + mut_slice[idx.index()].span = prev_span; + } } /// Set the vector to the all-zero vector @@ -313,7 +368,14 @@ impl Index for VClock { #[inline] fn index(&self, index: VectorIdx) -> &VTimestamp { - self.as_slice().get(index.to_u32() as usize).unwrap_or(&0) + self.as_slice().get(index.to_u32() as usize).unwrap_or(&VTimestamp::NONE) + } +} + +impl IndexMut for VClock { + #[inline] + fn index_mut(&mut self, index: VectorIdx) -> &mut VTimestamp { + self.0.as_mut_slice().get_mut(index.to_u32() as usize).unwrap() } } @@ -323,24 +385,25 @@ impl Index for VClock { #[cfg(test)] mod tests { - use super::{VClock, VTimestamp, VectorIdx}; - use std::cmp::Ordering; + use super::{VClock, VectorIdx}; + use rustc_span::DUMMY_SP; #[test] fn test_equal() { let mut c1 = VClock::default(); let mut c2 = VClock::default(); assert_eq!(c1, c2); - c1.increment_index(VectorIdx(5)); + c1.increment_index(VectorIdx(5), DUMMY_SP); assert_ne!(c1, c2); - c2.increment_index(VectorIdx(53)); + c2.increment_index(VectorIdx(53), DUMMY_SP); assert_ne!(c1, c2); - c1.increment_index(VectorIdx(53)); + c1.increment_index(VectorIdx(53), DUMMY_SP); assert_ne!(c1, c2); - c2.increment_index(VectorIdx(5)); + c2.increment_index(VectorIdx(5), DUMMY_SP); assert_eq!(c1, c2); } + /* #[test] fn test_partial_order() { // Small test @@ -449,4 +512,5 @@ mod tests { "Invalid alt (>=):\n l: {l:?}\n r: {r:?}" ); } + */ } diff --git a/src/concurrency/weak_memory.rs b/src/concurrency/weak_memory.rs index 391681444d..c02ec7ded7 100644 --- a/src/concurrency/weak_memory.rs +++ b/src/concurrency/weak_memory.rs @@ -258,7 +258,7 @@ impl<'mir, 'tcx: 'mir> StoreBuffer { // The thread index and timestamp of the initialisation write // are never meaningfully used, so it's fine to leave them as 0 store_index: VectorIdx::from(0), - timestamp: 0, + timestamp: VTimestamp::NONE, val: init, is_seqcst: false, load_info: RefCell::new(LoadInfo::default()), diff --git a/src/diagnostics.rs b/src/diagnostics.rs index efe79269b5..d9f40b55cd 100644 --- a/src/diagnostics.rs +++ b/src/diagnostics.rs @@ -35,6 +35,17 @@ pub enum TerminationInfo { link_name: Symbol, span: SpanData, }, + DataRace { + op1: RacingOp, + op2: RacingOp, + ptr: Pointer, + }, +} + +pub struct RacingOp { + pub action: String, + pub thread_info: String, + pub span: SpanData, } impl fmt::Display for TerminationInfo { @@ -55,6 +66,12 @@ impl fmt::Display for TerminationInfo { write!(f, "multiple definitions of symbol `{link_name}`"), SymbolShimClashing { link_name, .. } => write!(f, "found `{link_name}` symbol definition that clashes with a built-in shim",), + DataRace { ptr, op1, op2 } => + write!( + f, + "Data race detected between {} on {} and {} on {} at {:?}", + op1.action, op1.thread_info, op2.action, op2.thread_info, ptr, + ), } } } @@ -167,7 +184,7 @@ pub fn report_error<'tcx, 'mir>( Abort(_) => Some("abnormal termination"), UnsupportedInIsolation(_) | Int2PtrWithStrictProvenance => Some("unsupported operation"), - StackedBorrowsUb { .. } => Some("Undefined Behavior"), + StackedBorrowsUb { .. } | DataRace { .. } => Some("Undefined Behavior"), Deadlock => Some("deadlock"), MultipleSymbolDefinitions { .. } | SymbolShimClashing { .. } => None, }; @@ -205,6 +222,13 @@ pub fn report_error<'tcx, 'mir>( vec![(Some(*span), format!("the `{link_name}` symbol is defined here"))], Int2PtrWithStrictProvenance => vec![(None, format!("use Strict Provenance APIs (https://doc.rust-lang.org/nightly/std/ptr/index.html#strict-provenance, https://crates.io/crates/sptr) instead"))], + DataRace { ptr: _, op1, op2 } => + vec![ + (Some(op1.span), format!("The {} on {} is here", op1.action, op1.thread_info)), + (Some(op2.span), format!("The {} on {} is here", op2.action, op2.thread_info)), + (None, format!("this indicates a bug in the program: it performed an invalid operation, and caused Undefined Behavior")), + (None, format!("see https://doc.rust-lang.org/nightly/reference/behavior-considered-undefined.html for further information")), + ], _ => vec![], }; (title, helps) diff --git a/src/machine.rs b/src/machine.rs index e5a748453e..01a3d7550e 100644 --- a/src/machine.rs +++ b/src/machine.rs @@ -956,6 +956,7 @@ impl<'mir, 'tcx> Machine<'mir, 'tcx> for MiriMachine<'mir, 'tcx> { &ecx.machine.threads, alloc.size(), kind, + ecx.machine.current_span(), ) }); let buffer_alloc = ecx.machine.weak_memory.then(weak_memory::AllocState::new_allocation); diff --git a/tests/fail/data_race/alloc_read_race.stderr b/tests/fail/data_race/alloc_read_race.stderr index c6bfd12b24..d0ec8c1f12 100644 --- a/tests/fail/data_race/alloc_read_race.stderr +++ b/tests/fail/data_race/alloc_read_race.stderr @@ -4,6 +4,16 @@ error: Undefined Behavior: Data race detected between Read on thread `` LL | *pointer.load(Ordering::Relaxed) | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ Data race detected between Read on thread `` and Allocate on thread `` at ALLOC | +help: The Read on thread `` is here + --> $DIR/alloc_read_race.rs:LL:CC + | +LL | ... *pointer.load(Ordering::Relaxed) + | ^ +help: The Allocate on thread `` is here + --> $DIR/alloc_read_race.rs:LL:CC + | +LL | pointer.store(Box::into_raw(Box::new_uninit()), Ordering::Relaxed); + | ^^^^^^^^^^^^^^^^^ = help: this indicates a bug in the program: it performed an invalid operation, and caused Undefined Behavior = help: see https://doc.rust-lang.org/nightly/reference/behavior-considered-undefined.html for further information = note: BACKTRACE: diff --git a/tests/fail/data_race/alloc_write_race.stderr b/tests/fail/data_race/alloc_write_race.stderr index c4efc175c2..1149353680 100644 --- a/tests/fail/data_race/alloc_write_race.stderr +++ b/tests/fail/data_race/alloc_write_race.stderr @@ -4,6 +4,16 @@ error: Undefined Behavior: Data race detected between Write on thread ` LL | *pointer.load(Ordering::Relaxed) = 2; | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ Data race detected between Write on thread `` and Allocate on thread `` at ALLOC | +help: The Write on thread `` is here + --> $DIR/alloc_write_race.rs:LL:CC + | +LL | ... *pointer.load(Ordering::Relaxed) = 2; + | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ +help: The Allocate on thread `` is here + --> $DIR/alloc_write_race.rs:LL:CC + | +LL | .store(Box::into_raw(Box::::new_uninit()) as *mut usize, Ordering::Relaxed); + | ^^^^^^^^^^^^^^^^^^^^^^^^^^ = help: this indicates a bug in the program: it performed an invalid operation, and caused Undefined Behavior = help: see https://doc.rust-lang.org/nightly/reference/behavior-considered-undefined.html for further information = note: BACKTRACE: diff --git a/tests/fail/data_race/atomic_read_na_write_race1.stderr b/tests/fail/data_race/atomic_read_na_write_race1.stderr index 04adf0a98b..e77afe7b82 100644 --- a/tests/fail/data_race/atomic_read_na_write_race1.stderr +++ b/tests/fail/data_race/atomic_read_na_write_race1.stderr @@ -4,6 +4,16 @@ error: Undefined Behavior: Data race detected between Atomic Load on thread `` and Write on thread `` at ALLOC | +help: The Atomic Load on thread `` is here + --> $DIR/atomic_read_na_write_race1.rs:LL:CC + | +LL | ... (&*c.0).load(Ordering::SeqCst) + | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ +help: The Write on thread `` is here + --> $DIR/atomic_read_na_write_race1.rs:LL:CC + | +LL | *(c.0 as *mut usize) = 32; + | ^^^^^^^^^^^^^^^^^^^^^^^^^ = help: this indicates a bug in the program: it performed an invalid operation, and caused Undefined Behavior = help: see https://doc.rust-lang.org/nightly/reference/behavior-considered-undefined.html for further information = note: BACKTRACE: diff --git a/tests/fail/data_race/atomic_read_na_write_race2.stderr b/tests/fail/data_race/atomic_read_na_write_race2.stderr index b48f927b8f..6b30442169 100644 --- a/tests/fail/data_race/atomic_read_na_write_race2.stderr +++ b/tests/fail/data_race/atomic_read_na_write_race2.stderr @@ -4,6 +4,16 @@ error: Undefined Behavior: Data race detected between Write on thread ` LL | *atomic_ref.get_mut() = 32; | ^^^^^^^^^^^^^^^^^^^^^^^^^^ Data race detected between Write on thread `` and Atomic Load on thread `` at ALLOC | +help: The Write on thread `` is here + --> $DIR/atomic_read_na_write_race2.rs:LL:CC + | +LL | ... *atomic_ref.get_mut() = 32; + | ^^^^^^^^^^^^^^^^^^^^^^^^^^ +help: The Atomic Load on thread `` is here + --> $DIR/atomic_read_na_write_race2.rs:LL:CC + | +LL | atomic_ref.load(Ordering::SeqCst) + | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ = help: this indicates a bug in the program: it performed an invalid operation, and caused Undefined Behavior = help: see https://doc.rust-lang.org/nightly/reference/behavior-considered-undefined.html for further information = note: BACKTRACE: diff --git a/tests/fail/data_race/atomic_write_na_read_race1.stderr b/tests/fail/data_race/atomic_write_na_read_race1.stderr index fdb9b353a6..32485d3f8f 100644 --- a/tests/fail/data_race/atomic_write_na_read_race1.stderr +++ b/tests/fail/data_race/atomic_write_na_read_race1.stderr @@ -4,6 +4,16 @@ error: Undefined Behavior: Data race detected between Read on thread `` LL | *atomic_ref.get_mut() | ^^^^^^^^^^^^^^^^^^^^^ Data race detected between Read on thread `` and Atomic Store on thread `` at ALLOC | +help: The Read on thread `` is here + --> RUSTLIB/core/src/ptr/mod.rs:LL:CC + | +LL | } + | ^ +help: The Atomic Store on thread `` is here + --> $DIR/atomic_write_na_read_race1.rs:LL:CC + | +LL | atomic_ref.store(32, Ordering::SeqCst) + | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ = help: this indicates a bug in the program: it performed an invalid operation, and caused Undefined Behavior = help: see https://doc.rust-lang.org/nightly/reference/behavior-considered-undefined.html for further information = note: BACKTRACE: diff --git a/tests/fail/data_race/atomic_write_na_read_race2.stderr b/tests/fail/data_race/atomic_write_na_read_race2.stderr index ec581e322b..5217f3d8a7 100644 --- a/tests/fail/data_race/atomic_write_na_read_race2.stderr +++ b/tests/fail/data_race/atomic_write_na_read_race2.stderr @@ -4,6 +4,16 @@ error: Undefined Behavior: Data race detected between Atomic Store on thread `` and Read on thread `` at ALLOC | +help: The Atomic Store on thread `` is here + --> $DIR/atomic_write_na_read_race2.rs:LL:CC + | +LL | ... (&*c.0).store(32, Ordering::SeqCst); + | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ +help: The Read on thread `` is here + --> RUSTLIB/core/src/ptr/mod.rs:LL:CC + | +LL | } + | ^ = help: this indicates a bug in the program: it performed an invalid operation, and caused Undefined Behavior = help: see https://doc.rust-lang.org/nightly/reference/behavior-considered-undefined.html for further information = note: BACKTRACE: diff --git a/tests/fail/data_race/atomic_write_na_write_race1.stderr b/tests/fail/data_race/atomic_write_na_write_race1.stderr index 4c75f94d71..55cc212ec0 100644 --- a/tests/fail/data_race/atomic_write_na_write_race1.stderr +++ b/tests/fail/data_race/atomic_write_na_write_race1.stderr @@ -4,6 +4,16 @@ error: Undefined Behavior: Data race detected between Atomic Store on thread `` and Write on thread `` at ALLOC | +help: The Atomic Store on thread `` is here + --> $DIR/atomic_write_na_write_race1.rs:LL:CC + | +LL | ... (&*c.0).store(64, Ordering::SeqCst); + | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ +help: The Write on thread `` is here + --> $DIR/atomic_write_na_write_race1.rs:LL:CC + | +LL | *(c.0 as *mut usize) = 32; + | ^^^^^^^^^^^^^^^^^^^^^^^^^ = help: this indicates a bug in the program: it performed an invalid operation, and caused Undefined Behavior = help: see https://doc.rust-lang.org/nightly/reference/behavior-considered-undefined.html for further information = note: BACKTRACE: diff --git a/tests/fail/data_race/atomic_write_na_write_race2.stderr b/tests/fail/data_race/atomic_write_na_write_race2.stderr index 8c7f14081c..2b666ef027 100644 --- a/tests/fail/data_race/atomic_write_na_write_race2.stderr +++ b/tests/fail/data_race/atomic_write_na_write_race2.stderr @@ -4,6 +4,16 @@ error: Undefined Behavior: Data race detected between Write on thread ` LL | *atomic_ref.get_mut() = 32; | ^^^^^^^^^^^^^^^^^^^^^^^^^^ Data race detected between Write on thread `` and Atomic Store on thread `` at ALLOC | +help: The Write on thread `` is here + --> $DIR/atomic_write_na_write_race2.rs:LL:CC + | +LL | ... *atomic_ref.get_mut() = 32; + | ^^^^^^^^^^^^^^^^^^^^^^^^^^ +help: The Atomic Store on thread `` is here + --> $DIR/atomic_write_na_write_race2.rs:LL:CC + | +LL | atomic_ref.store(64, Ordering::SeqCst); + | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ = help: this indicates a bug in the program: it performed an invalid operation, and caused Undefined Behavior = help: see https://doc.rust-lang.org/nightly/reference/behavior-considered-undefined.html for further information = note: BACKTRACE: diff --git a/tests/fail/data_race/dangling_thread_async_race.stderr b/tests/fail/data_race/dangling_thread_async_race.stderr index 663bb8d4af..156261b353 100644 --- a/tests/fail/data_race/dangling_thread_async_race.stderr +++ b/tests/fail/data_race/dangling_thread_async_race.stderr @@ -4,6 +4,16 @@ error: Undefined Behavior: Data race detected between Write on thread ` LL | *c.0 = 64; | ^^^^^^^^^ Data race detected between Write on thread `` and Write on thread `` at ALLOC | +help: The Write on thread `` is here + --> $DIR/dangling_thread_async_race.rs:LL:CC + | +LL | *c.0 = 64; + | ^^^^^^^^^ +help: The Write on thread `` is here + --> $DIR/dangling_thread_async_race.rs:LL:CC + | +LL | *c.0 = 32; + | ^^^^^^^^^ = help: this indicates a bug in the program: it performed an invalid operation, and caused Undefined Behavior = help: see https://doc.rust-lang.org/nightly/reference/behavior-considered-undefined.html for further information = note: BACKTRACE: diff --git a/tests/fail/data_race/dangling_thread_race.stderr b/tests/fail/data_race/dangling_thread_race.stderr index ad3e173537..bd0d34929e 100644 --- a/tests/fail/data_race/dangling_thread_race.stderr +++ b/tests/fail/data_race/dangling_thread_race.stderr @@ -4,6 +4,16 @@ error: Undefined Behavior: Data race detected between Write on thread `main` and LL | *c.0 = 64; | ^^^^^^^^^ Data race detected between Write on thread `main` and Write on thread `` at ALLOC | +help: The Write on thread `main` is here + --> $DIR/dangling_thread_race.rs:LL:CC + | +LL | *c.0 = 64; + | ^^^^^^^^^ +help: The Write on thread `` is here + --> $DIR/dangling_thread_race.rs:LL:CC + | +LL | *c.0 = 32; + | ^^^^^^^^^ = help: this indicates a bug in the program: it performed an invalid operation, and caused Undefined Behavior = help: see https://doc.rust-lang.org/nightly/reference/behavior-considered-undefined.html for further information = note: BACKTRACE: diff --git a/tests/fail/data_race/dealloc_read_race1.stderr b/tests/fail/data_race/dealloc_read_race1.stderr index 194c2260ba..ac20d05bf1 100644 --- a/tests/fail/data_race/dealloc_read_race1.stderr +++ b/tests/fail/data_race/dealloc_read_race1.stderr @@ -9,6 +9,21 @@ LL | | std::mem::align_of::(), LL | | ); | |_____________^ Data race detected between Deallocate on thread `` and Read on thread `` at ALLOC | +help: The Deallocate on thread `` is here + --> $DIR/dealloc_read_race1.rs:LL:CC + | +LL | / __rust_dealloc( +LL | | +LL | | ptr.0 as *mut _, +LL | | std::mem::size_of::(), +LL | | std::mem::align_of::(), +LL | | ); + | |_____________^ +help: The Read on thread `` is here + --> RUSTLIB/core/src/ptr/mod.rs:LL:CC + | +LL | } + | ^ = help: this indicates a bug in the program: it performed an invalid operation, and caused Undefined Behavior = help: see https://doc.rust-lang.org/nightly/reference/behavior-considered-undefined.html for further information = note: BACKTRACE: diff --git a/tests/fail/data_race/dealloc_read_race_stack.stderr b/tests/fail/data_race/dealloc_read_race_stack.stderr index c986e912f0..93c7db3875 100644 --- a/tests/fail/data_race/dealloc_read_race_stack.stderr +++ b/tests/fail/data_race/dealloc_read_race_stack.stderr @@ -4,6 +4,16 @@ error: Undefined Behavior: Data race detected between Deallocate on thread `` and Read on thread `` at ALLOC | +help: The Deallocate on thread `` is here + --> $DIR/dealloc_read_race_stack.rs:LL:CC + | +LL | } + | ^ +help: The Read on thread `` is here + --> $DIR/dealloc_read_race_stack.rs:LL:CC + | +LL | *pointer.load(Ordering::Acquire) + | ^ = help: this indicates a bug in the program: it performed an invalid operation, and caused Undefined Behavior = help: see https://doc.rust-lang.org/nightly/reference/behavior-considered-undefined.html for further information = note: BACKTRACE: diff --git a/tests/fail/data_race/dealloc_write_race1.stderr b/tests/fail/data_race/dealloc_write_race1.stderr index 56eb0b519c..9e59d5a647 100644 --- a/tests/fail/data_race/dealloc_write_race1.stderr +++ b/tests/fail/data_race/dealloc_write_race1.stderr @@ -9,6 +9,21 @@ LL | | std::mem::align_of::(), LL | | ); | |_____________^ Data race detected between Deallocate on thread `` and Write on thread `` at ALLOC | +help: The Deallocate on thread `` is here + --> $DIR/dealloc_write_race1.rs:LL:CC + | +LL | / __rust_dealloc( +LL | | +LL | | ptr.0 as *mut _, +LL | | std::mem::size_of::(), +LL | | std::mem::align_of::(), +LL | | ); + | |_____________^ +help: The Write on thread `` is here + --> $DIR/dealloc_write_race1.rs:LL:CC + | +LL | *ptr.0 = 2; + | ^^^^^^^^^^ = help: this indicates a bug in the program: it performed an invalid operation, and caused Undefined Behavior = help: see https://doc.rust-lang.org/nightly/reference/behavior-considered-undefined.html for further information = note: BACKTRACE: diff --git a/tests/fail/data_race/dealloc_write_race_stack.stderr b/tests/fail/data_race/dealloc_write_race_stack.stderr index 7b77e2470a..5ac7c2d5a1 100644 --- a/tests/fail/data_race/dealloc_write_race_stack.stderr +++ b/tests/fail/data_race/dealloc_write_race_stack.stderr @@ -4,6 +4,16 @@ error: Undefined Behavior: Data race detected between Deallocate on thread `` and Write on thread `` at ALLOC | +help: The Deallocate on thread `` is here + --> $DIR/dealloc_write_race_stack.rs:LL:CC + | +LL | } + | ^ +help: The Write on thread `` is here + --> $DIR/dealloc_write_race_stack.rs:LL:CC + | +LL | *pointer.load(Ordering::Acquire) = 3; + | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ = help: this indicates a bug in the program: it performed an invalid operation, and caused Undefined Behavior = help: see https://doc.rust-lang.org/nightly/reference/behavior-considered-undefined.html for further information = note: BACKTRACE: diff --git a/tests/fail/data_race/enable_after_join_to_main.stderr b/tests/fail/data_race/enable_after_join_to_main.stderr index 26c07ae696..636a686f84 100644 --- a/tests/fail/data_race/enable_after_join_to_main.stderr +++ b/tests/fail/data_race/enable_after_join_to_main.stderr @@ -4,6 +4,16 @@ error: Undefined Behavior: Data race detected between Write on thread ` LL | *c.0 = 64; | ^^^^^^^^^ Data race detected between Write on thread `` and Write on thread `` at ALLOC | +help: The Write on thread `` is here + --> $DIR/enable_after_join_to_main.rs:LL:CC + | +LL | *c.0 = 64; + | ^^^^^^^^^ +help: The Write on thread `` is here + --> $DIR/enable_after_join_to_main.rs:LL:CC + | +LL | *c.0 = 32; + | ^^^^^^^^^ = help: this indicates a bug in the program: it performed an invalid operation, and caused Undefined Behavior = help: see https://doc.rust-lang.org/nightly/reference/behavior-considered-undefined.html for further information = note: BACKTRACE: diff --git a/tests/fail/data_race/fence_after_load.stderr b/tests/fail/data_race/fence_after_load.stderr index 0abfe213db..e686291638 100644 --- a/tests/fail/data_race/fence_after_load.stderr +++ b/tests/fail/data_race/fence_after_load.stderr @@ -4,6 +4,16 @@ error: Undefined Behavior: Data race detected between Write on thread `main` and LL | unsafe { V = 2 } | ^^^^^ Data race detected between Write on thread `main` and Write on thread `` at ALLOC | +help: The Write on thread `main` is here + --> $DIR/fence_after_load.rs:LL:CC + | +LL | unsafe { V = 2 } + | ^^^^^ +help: The Write on thread `` is here + --> $DIR/fence_after_load.rs:LL:CC + | +LL | unsafe { V = 1 } + | ^^^^^ = help: this indicates a bug in the program: it performed an invalid operation, and caused Undefined Behavior = help: see https://doc.rust-lang.org/nightly/reference/behavior-considered-undefined.html for further information = note: BACKTRACE: diff --git a/tests/fail/data_race/read_write_race.stderr b/tests/fail/data_race/read_write_race.stderr index 08a1953731..b1441dabaf 100644 --- a/tests/fail/data_race/read_write_race.stderr +++ b/tests/fail/data_race/read_write_race.stderr @@ -4,6 +4,16 @@ error: Undefined Behavior: Data race detected between Write on thread ` LL | *c.0 = 64; | ^^^^^^^^^ Data race detected between Write on thread `` and Read on thread `` at ALLOC | +help: The Write on thread `` is here + --> $DIR/read_write_race.rs:LL:CC + | +LL | *c.0 = 64; + | ^^^^^^^^^ +help: The Read on thread `` is here + --> RUSTLIB/core/src/ptr/mod.rs:LL:CC + | +LL | } + | ^ = help: this indicates a bug in the program: it performed an invalid operation, and caused Undefined Behavior = help: see https://doc.rust-lang.org/nightly/reference/behavior-considered-undefined.html for further information = note: BACKTRACE: diff --git a/tests/fail/data_race/read_write_race_stack.stderr b/tests/fail/data_race/read_write_race_stack.stderr index 20f137afe7..2a2572576d 100644 --- a/tests/fail/data_race/read_write_race_stack.stderr +++ b/tests/fail/data_race/read_write_race_stack.stderr @@ -4,6 +4,16 @@ error: Undefined Behavior: Data race detected between Read on thread `` LL | stack_var | ^^^^^^^^^ Data race detected between Read on thread `` and Write on thread `` at ALLOC | +help: The Read on thread `` is here + --> $DIR/read_write_race_stack.rs:LL:CC + | +LL | sleep(Duration::from_millis(200)); + | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ +help: The Write on thread `` is here + --> $DIR/read_write_race_stack.rs:LL:CC + | +LL | *pointer.load(Ordering::Acquire) = 3; + | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ = help: this indicates a bug in the program: it performed an invalid operation, and caused Undefined Behavior = help: see https://doc.rust-lang.org/nightly/reference/behavior-considered-undefined.html for further information = note: BACKTRACE: diff --git a/tests/fail/data_race/relax_acquire_race.stderr b/tests/fail/data_race/relax_acquire_race.stderr index 6121c25db2..e4819614dd 100644 --- a/tests/fail/data_race/relax_acquire_race.stderr +++ b/tests/fail/data_race/relax_acquire_race.stderr @@ -4,6 +4,16 @@ error: Undefined Behavior: Data race detected between Read on thread `` LL | *c.0 | ^^^^ Data race detected between Read on thread `` and Write on thread `` at ALLOC | +help: The Read on thread `` is here + --> $DIR/relax_acquire_race.rs:LL:CC + | +LL | if SYNC.load(Ordering::Acquire) == 2 { + | ^ +help: The Write on thread `` is here + --> $DIR/relax_acquire_race.rs:LL:CC + | +LL | *c.0 = 1; + | ^^^^^^^^ = help: this indicates a bug in the program: it performed an invalid operation, and caused Undefined Behavior = help: see https://doc.rust-lang.org/nightly/reference/behavior-considered-undefined.html for further information = note: BACKTRACE: diff --git a/tests/fail/data_race/release_seq_race.stderr b/tests/fail/data_race/release_seq_race.stderr index 777bc4adad..6bc8bccbbf 100644 --- a/tests/fail/data_race/release_seq_race.stderr +++ b/tests/fail/data_race/release_seq_race.stderr @@ -4,6 +4,16 @@ error: Undefined Behavior: Data race detected between Read on thread `` LL | *c.0 | ^^^^ Data race detected between Read on thread `` and Write on thread `` at ALLOC | +help: The Read on thread `` is here + --> $DIR/release_seq_race.rs:LL:CC + | +LL | if SYNC.load(Ordering::Acquire) == 3 { + | ^ +help: The Write on thread `` is here + --> $DIR/release_seq_race.rs:LL:CC + | +LL | *c.0 = 1; + | ^^^^^^^^ = help: this indicates a bug in the program: it performed an invalid operation, and caused Undefined Behavior = help: see https://doc.rust-lang.org/nightly/reference/behavior-considered-undefined.html for further information = note: BACKTRACE: diff --git a/tests/fail/data_race/release_seq_race_same_thread.stderr b/tests/fail/data_race/release_seq_race_same_thread.stderr index 0fcb192d92..6997685dc3 100644 --- a/tests/fail/data_race/release_seq_race_same_thread.stderr +++ b/tests/fail/data_race/release_seq_race_same_thread.stderr @@ -4,6 +4,16 @@ error: Undefined Behavior: Data race detected between Read on thread `` LL | *c.0 | ^^^^ Data race detected between Read on thread `` and Write on thread `` at ALLOC | +help: The Read on thread `` is here + --> $DIR/release_seq_race_same_thread.rs:LL:CC + | +LL | if SYNC.load(Ordering::Acquire) == 2 { + | ^ +help: The Write on thread `` is here + --> $DIR/release_seq_race_same_thread.rs:LL:CC + | +LL | *c.0 = 1; + | ^^^^^^^^ = help: this indicates a bug in the program: it performed an invalid operation, and caused Undefined Behavior = help: see https://doc.rust-lang.org/nightly/reference/behavior-considered-undefined.html for further information = note: BACKTRACE: diff --git a/tests/fail/data_race/rmw_race.stderr b/tests/fail/data_race/rmw_race.stderr index 3ae6f3b84f..e4f3ecf89c 100644 --- a/tests/fail/data_race/rmw_race.stderr +++ b/tests/fail/data_race/rmw_race.stderr @@ -4,6 +4,16 @@ error: Undefined Behavior: Data race detected between Read on thread `` LL | *c.0 | ^^^^ Data race detected between Read on thread `` and Write on thread `` at ALLOC | +help: The Read on thread `` is here + --> $DIR/rmw_race.rs:LL:CC + | +LL | if SYNC.load(Ordering::Acquire) == 3 { + | ^ +help: The Write on thread `` is here + --> $DIR/rmw_race.rs:LL:CC + | +LL | *c.0 = 1; + | ^^^^^^^^ = help: this indicates a bug in the program: it performed an invalid operation, and caused Undefined Behavior = help: see https://doc.rust-lang.org/nightly/reference/behavior-considered-undefined.html for further information = note: BACKTRACE: diff --git a/tests/fail/data_race/stack_pop_race.stderr b/tests/fail/data_race/stack_pop_race.stderr index 0075f877b2..b156179da4 100644 --- a/tests/fail/data_race/stack_pop_race.stderr +++ b/tests/fail/data_race/stack_pop_race.stderr @@ -4,6 +4,16 @@ error: Undefined Behavior: Data race detected between Deallocate on thread `main LL | } | ^ Data race detected between Deallocate on thread `main` and Read on thread `` at ALLOC | +help: The Deallocate on thread `main` is here + --> $DIR/stack_pop_race.rs:LL:CC + | +LL | } + | ^ +help: The Read on thread `` is here + --> RUSTLIB/core/src/ptr/mod.rs:LL:CC + | +LL | } + | ^ = help: this indicates a bug in the program: it performed an invalid operation, and caused Undefined Behavior = help: see https://doc.rust-lang.org/nightly/reference/behavior-considered-undefined.html for further information = note: BACKTRACE: diff --git a/tests/fail/data_race/write_write_race.stderr b/tests/fail/data_race/write_write_race.stderr index ee7072ccf5..132cd50304 100644 --- a/tests/fail/data_race/write_write_race.stderr +++ b/tests/fail/data_race/write_write_race.stderr @@ -4,6 +4,16 @@ error: Undefined Behavior: Data race detected between Write on thread ` LL | *c.0 = 64; | ^^^^^^^^^ Data race detected between Write on thread `` and Write on thread `` at ALLOC | +help: The Write on thread `` is here + --> $DIR/write_write_race.rs:LL:CC + | +LL | *c.0 = 64; + | ^^^^^^^^^ +help: The Write on thread `` is here + --> $DIR/write_write_race.rs:LL:CC + | +LL | *c.0 = 32; + | ^^^^^^^^^ = help: this indicates a bug in the program: it performed an invalid operation, and caused Undefined Behavior = help: see https://doc.rust-lang.org/nightly/reference/behavior-considered-undefined.html for further information = note: BACKTRACE: diff --git a/tests/fail/data_race/write_write_race_stack.stderr b/tests/fail/data_race/write_write_race_stack.stderr index ceb473c2a4..25963d63db 100644 --- a/tests/fail/data_race/write_write_race_stack.stderr +++ b/tests/fail/data_race/write_write_race_stack.stderr @@ -4,6 +4,16 @@ error: Undefined Behavior: Data race detected between Write on thread ` LL | stack_var = 1usize; | ^^^^^^^^^^^^^^^^^^ Data race detected between Write on thread `` and Write on thread `` at ALLOC | +help: The Write on thread `` is here + --> $DIR/write_write_race_stack.rs:LL:CC + | +LL | stack_var = 1usize; + | ^^^^^^^^^^^^^^^^^^ +help: The Write on thread `` is here + --> $DIR/write_write_race_stack.rs:LL:CC + | +LL | *pointer.load(Ordering::Acquire) = 3; + | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ = help: this indicates a bug in the program: it performed an invalid operation, and caused Undefined Behavior = help: see https://doc.rust-lang.org/nightly/reference/behavior-considered-undefined.html for further information = note: BACKTRACE: diff --git a/tests/fail/stacked_borrows/retag_data_race_read.stderr b/tests/fail/stacked_borrows/retag_data_race_read.stderr index 5dc936f070..6b280a16a3 100644 --- a/tests/fail/stacked_borrows/retag_data_race_read.stderr +++ b/tests/fail/stacked_borrows/retag_data_race_read.stderr @@ -4,6 +4,16 @@ error: Undefined Behavior: Data race detected between Write on thread ` LL | *p = 5; | ^^^^^^ Data race detected between Write on thread `` and Read on thread `` at ALLOC | +help: The Write on thread `` is here + --> $DIR/retag_data_race_read.rs:LL:CC + | +LL | *p = 5; + | ^^^^^^ +help: The Read on thread `` is here + --> $DIR/retag_data_race_read.rs:LL:CC + | +LL | let t1 = std::thread::spawn(move || thread_1(p)); + | ^ = help: this indicates a bug in the program: it performed an invalid operation, and caused Undefined Behavior = help: see https://doc.rust-lang.org/nightly/reference/behavior-considered-undefined.html for further information = note: BACKTRACE: diff --git a/tests/fail/stacked_borrows/retag_data_race_write.stderr b/tests/fail/stacked_borrows/retag_data_race_write.stderr index 03c2450356..80b6ac6e13 100644 --- a/tests/fail/stacked_borrows/retag_data_race_write.stderr +++ b/tests/fail/stacked_borrows/retag_data_race_write.stderr @@ -4,6 +4,16 @@ error: Undefined Behavior: Data race detected between Write on thread ` LL | *p = 5; | ^^^^^^ Data race detected between Write on thread `` and Write on thread `` at ALLOC | +help: The Write on thread `` is here + --> $DIR/retag_data_race_write.rs:LL:CC + | +LL | *p = 5; + | ^^^^^^ +help: The Write on thread `` is here + --> $DIR/retag_data_race_write.rs:LL:CC + | +LL | let _r = &mut *p; + | ^^^^^^^ = help: this indicates a bug in the program: it performed an invalid operation, and caused Undefined Behavior = help: see https://doc.rust-lang.org/nightly/reference/behavior-considered-undefined.html for further information = note: BACKTRACE: From a799f026e9c6170924efc86498410f9fd9addd75 Mon Sep 17 00:00:00 2001 From: Ben Kimock Date: Tue, 20 Dec 2022 22:48:23 -0500 Subject: [PATCH 17/28] Fix span management --- src/concurrency/data_race.rs | 16 ++++++-------- src/concurrency/vector_clock.rs | 21 +++++++------------ tests/fail/data_race/alloc_read_race.stderr | 2 +- .../atomic_write_na_read_race1.stderr | 6 +++--- .../atomic_write_na_read_race2.stderr | 6 +++--- .../fail/data_race/dealloc_read_race1.stderr | 6 +++--- .../data_race/dealloc_read_race_stack.stderr | 2 +- tests/fail/data_race/read_write_race.stderr | 6 +++--- .../data_race/read_write_race_stack.stderr | 4 ++-- .../fail/data_race/relax_acquire_race.stderr | 4 ++-- tests/fail/data_race/release_seq_race.stderr | 4 ++-- .../release_seq_race_same_thread.stderr | 4 ++-- tests/fail/data_race/rmw_race.stderr | 4 ++-- tests/fail/data_race/stack_pop_race.stderr | 6 +++--- .../retag_data_race_read.stderr | 4 ++-- 15 files changed, 42 insertions(+), 53 deletions(-) diff --git a/src/concurrency/data_race.rs b/src/concurrency/data_race.rs index 8b343dd2fe..2d825b369c 100644 --- a/src/concurrency/data_race.rs +++ b/src/concurrency/data_race.rs @@ -51,7 +51,6 @@ use rustc_data_structures::fx::{FxHashMap, FxHashSet}; use rustc_index::vec::{Idx, IndexVec}; use rustc_middle::mir; use rustc_span::Span; -use rustc_span::DUMMY_SP; use rustc_target::abi::{Align, Size}; use crate::diagnostics::RacingOp; @@ -398,7 +397,10 @@ impl MemoryCellClocks { current_span: Span, ) -> Result<(), DataRace> { log::trace!("Unsynchronized read with vectors: {:#?} :: {:#?}", self, clocks); - let res = if self.write <= clocks.clock[self.write_index] { + if !current_span.is_dummy() { + clocks.clock[index].span = current_span; + } + if self.write <= clocks.clock[self.write_index] { let race_free = if let Some(atomic) = self.atomic() { atomic.write_vector <= clocks.clock } else { @@ -408,11 +410,7 @@ impl MemoryCellClocks { if race_free { Ok(()) } else { Err(DataRace) } } else { Err(DataRace) - }; - if res.is_ok() && current_span != DUMMY_SP { - clocks.clock[index].span = current_span; } - res } /// Detect races for non-atomic write operations at the current memory cell @@ -425,7 +423,7 @@ impl MemoryCellClocks { current_span: Span, ) -> Result<(), DataRace> { log::trace!("Unsynchronized write with vectors: {:#?} :: {:#?}", self, clocks); - if current_span != DUMMY_SP { + if !current_span.is_dummy() { clocks.clock[index].span = current_span; } if self.write <= clocks.clock[self.write_index] && self.read <= clocks.clock { @@ -712,9 +710,7 @@ impl VClockAlloc { | MemoryKind::Stack => { let (alloc_index, clocks) = global.current_thread_state(thread_mgr); let mut alloc_timestamp = clocks.clock[alloc_index]; - if current_span != DUMMY_SP { - alloc_timestamp.span = current_span; - } + alloc_timestamp.span = current_span; (alloc_timestamp, alloc_index) } // Other global memory should trace races but be allocated at the 0 timestamp. diff --git a/src/concurrency/vector_clock.rs b/src/concurrency/vector_clock.rs index 191bb1449a..0dcd6830b4 100644 --- a/src/concurrency/vector_clock.rs +++ b/src/concurrency/vector_clock.rs @@ -45,8 +45,9 @@ impl From for VectorIdx { /// clock vectors larger than this will be stored on the heap const SMALL_VECTOR: usize = 4; -/// The type of the time-stamps recorded in the data-race detector -/// set to a type of unsigned integer +/// The time-stamps recorded in the data-race detector consist of both +/// a 32-bit unsigned integer which is the actual timestamp, and a `Span` +/// so that diagnostics can report what code was responsible for an operation. #[derive(Clone, Copy, Debug, Eq)] pub struct VTimestamp { time: u32, @@ -128,7 +129,7 @@ impl VClock { let mut_slice = self.get_mut_with_min_len(idx + 1); let idx_ref = &mut mut_slice[idx]; idx_ref.time = idx_ref.time.checked_add(1).expect("Vector clock overflow"); - if current_span != DUMMY_SP { + if !current_span.is_dummy() { idx_ref.span = current_span; } } @@ -143,14 +144,7 @@ impl VClock { let l_span = l.span; let r_span = r.span; *l = r.max(*l); - if l.span == DUMMY_SP { - if r_span != DUMMY_SP { - l.span = r_span; - } - if l_span != DUMMY_SP { - l.span = l_span; - } - } + l.span = l.span.substitute_dummy(r_span).substitute_dummy(l_span); } } @@ -162,9 +156,8 @@ impl VClock { mut_slice[idx.index()] = other[idx]; - if other[idx].span == DUMMY_SP { - mut_slice[idx.index()].span = prev_span; - } + let span = &mut mut_slice[idx.index()].span; + *span = span.substitute_dummy(prev_span); } /// Set the vector to the all-zero vector diff --git a/tests/fail/data_race/alloc_read_race.stderr b/tests/fail/data_race/alloc_read_race.stderr index d0ec8c1f12..510b177fc7 100644 --- a/tests/fail/data_race/alloc_read_race.stderr +++ b/tests/fail/data_race/alloc_read_race.stderr @@ -8,7 +8,7 @@ help: The Read on thread `` is here --> $DIR/alloc_read_race.rs:LL:CC | LL | ... *pointer.load(Ordering::Relaxed) - | ^ + | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ help: The Allocate on thread `` is here --> $DIR/alloc_read_race.rs:LL:CC | diff --git a/tests/fail/data_race/atomic_write_na_read_race1.stderr b/tests/fail/data_race/atomic_write_na_read_race1.stderr index 32485d3f8f..ffc985c04c 100644 --- a/tests/fail/data_race/atomic_write_na_read_race1.stderr +++ b/tests/fail/data_race/atomic_write_na_read_race1.stderr @@ -5,10 +5,10 @@ LL | *atomic_ref.get_mut() | ^^^^^^^^^^^^^^^^^^^^^ Data race detected between Read on thread `` and Atomic Store on thread `` at ALLOC | help: The Read on thread `` is here - --> RUSTLIB/core/src/ptr/mod.rs:LL:CC + --> $DIR/atomic_write_na_read_race1.rs:LL:CC | -LL | } - | ^ +LL | *atomic_ref.get_mut() + | ^^^^^^^^^^^^^^^^^^^^^ help: The Atomic Store on thread `` is here --> $DIR/atomic_write_na_read_race1.rs:LL:CC | diff --git a/tests/fail/data_race/atomic_write_na_read_race2.stderr b/tests/fail/data_race/atomic_write_na_read_race2.stderr index 5217f3d8a7..5b5c8d07f8 100644 --- a/tests/fail/data_race/atomic_write_na_read_race2.stderr +++ b/tests/fail/data_race/atomic_write_na_read_race2.stderr @@ -10,10 +10,10 @@ help: The Atomic Store on thread `` is here LL | ... (&*c.0).store(32, Ordering::SeqCst); | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ help: The Read on thread `` is here - --> RUSTLIB/core/src/ptr/mod.rs:LL:CC + --> $DIR/atomic_write_na_read_race2.rs:LL:CC | -LL | } - | ^ +LL | let _val = *(c.0 as *mut usize); + | ^^^^^^^^^^^^^^^^^^^^ = help: this indicates a bug in the program: it performed an invalid operation, and caused Undefined Behavior = help: see https://doc.rust-lang.org/nightly/reference/behavior-considered-undefined.html for further information = note: BACKTRACE: diff --git a/tests/fail/data_race/dealloc_read_race1.stderr b/tests/fail/data_race/dealloc_read_race1.stderr index ac20d05bf1..02a9bb63b5 100644 --- a/tests/fail/data_race/dealloc_read_race1.stderr +++ b/tests/fail/data_race/dealloc_read_race1.stderr @@ -20,10 +20,10 @@ LL | | std::mem::align_of::(), LL | | ); | |_____________^ help: The Read on thread `` is here - --> RUSTLIB/core/src/ptr/mod.rs:LL:CC + --> $DIR/dealloc_read_race1.rs:LL:CC | -LL | } - | ^ +LL | let _val = *ptr.0; + | ^^^^^^ = help: this indicates a bug in the program: it performed an invalid operation, and caused Undefined Behavior = help: see https://doc.rust-lang.org/nightly/reference/behavior-considered-undefined.html for further information = note: BACKTRACE: diff --git a/tests/fail/data_race/dealloc_read_race_stack.stderr b/tests/fail/data_race/dealloc_read_race_stack.stderr index 93c7db3875..18a30bd5a6 100644 --- a/tests/fail/data_race/dealloc_read_race_stack.stderr +++ b/tests/fail/data_race/dealloc_read_race_stack.stderr @@ -13,7 +13,7 @@ help: The Read on thread `` is here --> $DIR/dealloc_read_race_stack.rs:LL:CC | LL | *pointer.load(Ordering::Acquire) - | ^ + | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ = help: this indicates a bug in the program: it performed an invalid operation, and caused Undefined Behavior = help: see https://doc.rust-lang.org/nightly/reference/behavior-considered-undefined.html for further information = note: BACKTRACE: diff --git a/tests/fail/data_race/read_write_race.stderr b/tests/fail/data_race/read_write_race.stderr index b1441dabaf..afba81ee8f 100644 --- a/tests/fail/data_race/read_write_race.stderr +++ b/tests/fail/data_race/read_write_race.stderr @@ -10,10 +10,10 @@ help: The Write on thread `` is here LL | *c.0 = 64; | ^^^^^^^^^ help: The Read on thread `` is here - --> RUSTLIB/core/src/ptr/mod.rs:LL:CC + --> $DIR/read_write_race.rs:LL:CC | -LL | } - | ^ +LL | let _val = *c.0; + | ^^^^ = help: this indicates a bug in the program: it performed an invalid operation, and caused Undefined Behavior = help: see https://doc.rust-lang.org/nightly/reference/behavior-considered-undefined.html for further information = note: BACKTRACE: diff --git a/tests/fail/data_race/read_write_race_stack.stderr b/tests/fail/data_race/read_write_race_stack.stderr index 2a2572576d..e1e4604aa6 100644 --- a/tests/fail/data_race/read_write_race_stack.stderr +++ b/tests/fail/data_race/read_write_race_stack.stderr @@ -7,8 +7,8 @@ LL | stack_var help: The Read on thread `` is here --> $DIR/read_write_race_stack.rs:LL:CC | -LL | sleep(Duration::from_millis(200)); - | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ +LL | stack_var + | ^^^^^^^^^ help: The Write on thread `` is here --> $DIR/read_write_race_stack.rs:LL:CC | diff --git a/tests/fail/data_race/relax_acquire_race.stderr b/tests/fail/data_race/relax_acquire_race.stderr index e4819614dd..aae90e0c9e 100644 --- a/tests/fail/data_race/relax_acquire_race.stderr +++ b/tests/fail/data_race/relax_acquire_race.stderr @@ -7,8 +7,8 @@ LL | *c.0 help: The Read on thread `` is here --> $DIR/relax_acquire_race.rs:LL:CC | -LL | if SYNC.load(Ordering::Acquire) == 2 { - | ^ +LL | *c.0 + | ^^^^ help: The Write on thread `` is here --> $DIR/relax_acquire_race.rs:LL:CC | diff --git a/tests/fail/data_race/release_seq_race.stderr b/tests/fail/data_race/release_seq_race.stderr index 6bc8bccbbf..02413e6baa 100644 --- a/tests/fail/data_race/release_seq_race.stderr +++ b/tests/fail/data_race/release_seq_race.stderr @@ -7,8 +7,8 @@ LL | *c.0 help: The Read on thread `` is here --> $DIR/release_seq_race.rs:LL:CC | -LL | if SYNC.load(Ordering::Acquire) == 3 { - | ^ +LL | *c.0 + | ^^^^ help: The Write on thread `` is here --> $DIR/release_seq_race.rs:LL:CC | diff --git a/tests/fail/data_race/release_seq_race_same_thread.stderr b/tests/fail/data_race/release_seq_race_same_thread.stderr index 6997685dc3..9573ca9586 100644 --- a/tests/fail/data_race/release_seq_race_same_thread.stderr +++ b/tests/fail/data_race/release_seq_race_same_thread.stderr @@ -7,8 +7,8 @@ LL | *c.0 help: The Read on thread `` is here --> $DIR/release_seq_race_same_thread.rs:LL:CC | -LL | if SYNC.load(Ordering::Acquire) == 2 { - | ^ +LL | *c.0 + | ^^^^ help: The Write on thread `` is here --> $DIR/release_seq_race_same_thread.rs:LL:CC | diff --git a/tests/fail/data_race/rmw_race.stderr b/tests/fail/data_race/rmw_race.stderr index e4f3ecf89c..ae53cc0c75 100644 --- a/tests/fail/data_race/rmw_race.stderr +++ b/tests/fail/data_race/rmw_race.stderr @@ -7,8 +7,8 @@ LL | *c.0 help: The Read on thread `` is here --> $DIR/rmw_race.rs:LL:CC | -LL | if SYNC.load(Ordering::Acquire) == 3 { - | ^ +LL | *c.0 + | ^^^^ help: The Write on thread `` is here --> $DIR/rmw_race.rs:LL:CC | diff --git a/tests/fail/data_race/stack_pop_race.stderr b/tests/fail/data_race/stack_pop_race.stderr index b156179da4..0853e0830c 100644 --- a/tests/fail/data_race/stack_pop_race.stderr +++ b/tests/fail/data_race/stack_pop_race.stderr @@ -10,10 +10,10 @@ help: The Deallocate on thread `main` is here LL | } | ^ help: The Read on thread `` is here - --> RUSTLIB/core/src/ptr/mod.rs:LL:CC + --> $DIR/stack_pop_race.rs:LL:CC | -LL | } - | ^ +LL | let _val = unsafe { *ptr.0 }; + | ^^^^^^ = help: this indicates a bug in the program: it performed an invalid operation, and caused Undefined Behavior = help: see https://doc.rust-lang.org/nightly/reference/behavior-considered-undefined.html for further information = note: BACKTRACE: diff --git a/tests/fail/stacked_borrows/retag_data_race_read.stderr b/tests/fail/stacked_borrows/retag_data_race_read.stderr index 6b280a16a3..ff874bd9e8 100644 --- a/tests/fail/stacked_borrows/retag_data_race_read.stderr +++ b/tests/fail/stacked_borrows/retag_data_race_read.stderr @@ -12,8 +12,8 @@ LL | *p = 5; help: The Read on thread `` is here --> $DIR/retag_data_race_read.rs:LL:CC | -LL | let t1 = std::thread::spawn(move || thread_1(p)); - | ^ +LL | let _r = &*p; + | ^^^ = help: this indicates a bug in the program: it performed an invalid operation, and caused Undefined Behavior = help: see https://doc.rust-lang.org/nightly/reference/behavior-considered-undefined.html for further information = note: BACKTRACE: From cca5ae95a3f3a047963c252d8c792f63331d2e04 Mon Sep 17 00:00:00 2001 From: Ben Kimock Date: Tue, 20 Dec 2022 22:54:44 -0500 Subject: [PATCH 18/28] Re-enable the VClock ordering tests --- src/concurrency/vector_clock.rs | 11 +++++------ 1 file changed, 5 insertions(+), 6 deletions(-) diff --git a/src/concurrency/vector_clock.rs b/src/concurrency/vector_clock.rs index 0dcd6830b4..d6d8e1c4b3 100644 --- a/src/concurrency/vector_clock.rs +++ b/src/concurrency/vector_clock.rs @@ -378,8 +378,9 @@ impl IndexMut for VClock { #[cfg(test)] mod tests { - use super::{VClock, VectorIdx}; + use super::{VClock, VTimestamp, VectorIdx}; use rustc_span::DUMMY_SP; + use std::cmp::Ordering; #[test] fn test_equal() { @@ -396,7 +397,6 @@ mod tests { assert_eq!(c1, c2); } - /* #[test] fn test_partial_order() { // Small test @@ -442,14 +442,14 @@ mod tests { ); } - fn from_slice(mut slice: &[VTimestamp]) -> VClock { + fn from_slice(mut slice: &[u32]) -> VClock { while let Some(0) = slice.last() { slice = &slice[..slice.len() - 1] } - VClock(smallvec::SmallVec::from_slice(slice)) + VClock(slice.iter().copied().map(|time| VTimestamp { time, span: DUMMY_SP }).collect()) } - fn assert_order(l: &[VTimestamp], r: &[VTimestamp], o: Option) { + fn assert_order(l: &[u32], r: &[u32], o: Option) { let l = from_slice(l); let r = from_slice(r); @@ -505,5 +505,4 @@ mod tests { "Invalid alt (>=):\n l: {l:?}\n r: {r:?}" ); } - */ } From 87249ad32fb09fdad5558244cfeba03ddcf80d0b Mon Sep 17 00:00:00 2001 From: Ralf Jung Date: Wed, 21 Dec 2022 17:54:10 +0100 Subject: [PATCH 19/28] update josh onstructions --- CONTRIBUTING.md | 12 ++++++------ 1 file changed, 6 insertions(+), 6 deletions(-) diff --git a/CONTRIBUTING.md b/CONTRIBUTING.md index 9d61cc4e2d..6efaefdeff 100644 --- a/CONTRIBUTING.md +++ b/CONTRIBUTING.md @@ -232,16 +232,16 @@ You can also directly run Miri on a Rust source file: ## Advanced topic: Syncing with the rustc repo -We use the [`josh` proxy](https://github.com/josh-project/josh) to transmit -changes between the rustc and Miri repositories. For now, the latest git version -of josh needs to be built from source. This downloads and runs josh: +We use the [`josh` proxy](https://github.com/josh-project/josh) to transmit changes between the +rustc and Miri repositories. The eaisest way to run josh is via docker: ```sh -git clone https://github.com/josh-project/josh -cd josh -cargo run --release -p josh-proxy -- --local=local --remote=https://github.com --no-background +docker pull joshproject/josh-proxy:latest +docker run -it -p 8000:8000 -e JOSH_REMOTE=https://github.com -e JOSH_EXTRA_OPTS=--no-background -v josh-vol:/data/git joshproject/josh-proxy:latest ``` +This sets up a local volume `josh-vol` for josh's cache. + ### Importing changes from the rustc repo Josh needs to be running, as described above. From e589f0f7afdc9c6ba4ecce4d3686c39556a1deb3 Mon Sep 17 00:00:00 2001 From: Ben Kimock Date: Wed, 21 Dec 2022 21:11:19 -0500 Subject: [PATCH 20/28] Clean up implementation, deduplicate in errors --- src/concurrency/data_race.rs | 28 +++++++------------ src/concurrency/vector_clock.rs | 12 ++++---- src/concurrency/weak_memory.rs | 2 +- src/diagnostics.rs | 9 +++--- tests/fail/data_race/alloc_read_race.stderr | 11 ++------ tests/fail/data_race/alloc_write_race.stderr | 11 ++------ .../atomic_read_na_write_race1.stderr | 11 ++------ .../atomic_read_na_write_race2.stderr | 11 ++------ .../atomic_write_na_read_race1.stderr | 11 ++------ .../atomic_write_na_read_race2.stderr | 11 ++------ .../atomic_write_na_write_race1.stderr | 11 ++------ .../atomic_write_na_write_race2.stderr | 11 ++------ .../dangling_thread_async_race.stderr | 11 ++------ .../data_race/dangling_thread_race.stderr | 11 ++------ .../fail/data_race/dealloc_read_race1.stderr | 16 ++--------- .../data_race/dealloc_read_race_stack.stderr | 11 ++------ .../fail/data_race/dealloc_write_race1.stderr | 16 ++--------- .../data_race/dealloc_write_race_stack.stderr | 11 ++------ .../enable_after_join_to_main.stderr | 11 ++------ tests/fail/data_race/fence_after_load.stderr | 11 ++------ tests/fail/data_race/read_write_race.stderr | 11 ++------ .../data_race/read_write_race_stack.stderr | 11 ++------ .../fail/data_race/relax_acquire_race.stderr | 11 ++------ tests/fail/data_race/release_seq_race.stderr | 11 ++------ .../release_seq_race_same_thread.stderr | 11 ++------ tests/fail/data_race/rmw_race.stderr | 11 ++------ tests/fail/data_race/stack_pop_race.stderr | 11 ++------ tests/fail/data_race/write_write_race.stderr | 11 ++------ .../data_race/write_write_race_stack.stderr | 11 ++------ .../retag_data_race_read.stderr | 11 ++------ .../retag_data_race_write.stderr | 11 ++------ 31 files changed, 103 insertions(+), 255 deletions(-) diff --git a/src/concurrency/data_race.rs b/src/concurrency/data_race.rs index 2d825b369c..5dcaebadc4 100644 --- a/src/concurrency/data_race.rs +++ b/src/concurrency/data_race.rs @@ -358,15 +358,9 @@ impl MemoryCellClocks { index: VectorIdx, ) -> Result<(), DataRace> { log::trace!("Atomic read with vectors: {:#?} :: {:#?}", self, clocks); - if self.write <= clocks.clock[self.write_index] { - let atomic = self.atomic_mut(); - atomic.read_vector.set_at_index(&clocks.clock, index); - Ok(()) - } else { - let atomic = self.atomic_mut(); - atomic.read_vector.set_at_index(&clocks.clock, index); - Err(DataRace) - } + let atomic = self.atomic_mut(); + atomic.read_vector.set_at_index(&clocks.clock, index); + if self.write <= clocks.clock[self.write_index] { Ok(()) } else { Err(DataRace) } } /// Detect data-races with an atomic write, either with a non-atomic read or with @@ -377,13 +371,11 @@ impl MemoryCellClocks { index: VectorIdx, ) -> Result<(), DataRace> { log::trace!("Atomic write with vectors: {:#?} :: {:#?}", self, clocks); + let atomic = self.atomic_mut(); + atomic.write_vector.set_at_index(&clocks.clock, index); if self.write <= clocks.clock[self.write_index] && self.read <= clocks.clock { - let atomic = self.atomic_mut(); - atomic.write_vector.set_at_index(&clocks.clock, index); Ok(()) } else { - let atomic = self.atomic_mut(); - atomic.write_vector.set_at_index(&clocks.clock, index); Err(DataRace) } } @@ -635,6 +627,7 @@ pub trait EvalContextExt<'mir, 'tcx: 'mir>: MiriInterpCxExt<'mir, 'tcx> { if let Some(data_race) = &mut this.machine.data_race { data_race.maybe_perform_sync_operation( &this.machine.threads, + current_span, |index, mut clocks| { log::trace!("Atomic fence on {:?} with ordering {:?}", index, atomic); @@ -658,7 +651,6 @@ pub trait EvalContextExt<'mir, 'tcx: 'mir>: MiriInterpCxExt<'mir, 'tcx> { // Increment timestamp in case of release semantics. Ok(atomic != AtomicFenceOrd::Acquire) }, - current_span, ) } else { Ok(()) @@ -721,7 +713,7 @@ impl VClockAlloc { | MiriMemoryKind::ExternStatic | MiriMemoryKind::Tls, ) - | MemoryKind::CallerLocation => (VTimestamp::NONE, VectorIdx::MAX_INDEX), + | MemoryKind::CallerLocation => (VTimestamp::ZERO, VectorIdx::MAX_INDEX), }; VClockAlloc { alloc_ranges: RefCell::new(RangeMap::new( @@ -752,7 +744,7 @@ impl VClockAlloc { let idx = l_remainder_slice .iter() .enumerate() - .find_map(|(idx, &r)| if r == VTimestamp::NONE { None } else { Some(idx) }) + .find_map(|(idx, &r)| if r == VTimestamp::ZERO { None } else { Some(idx) }) .expect("Invalid VClock Invariant"); Some(idx + r_slice.len()) } else { @@ -1132,6 +1124,7 @@ trait EvalContextPrivExt<'mir, 'tcx: 'mir>: MiriInterpCxExt<'mir, 'tcx> { // Perform the atomic operation. data_race.maybe_perform_sync_operation( &this.machine.threads, + current_span, |index, mut clocks| { for (offset, range) in alloc_meta.alloc_ranges.borrow_mut().iter_mut(base_offset, size) @@ -1153,7 +1146,6 @@ trait EvalContextPrivExt<'mir, 'tcx: 'mir>: MiriInterpCxExt<'mir, 'tcx> { // This conservatively assumes all operations have release semantics Ok(true) }, - current_span, )?; // Log changes to atomic memory. @@ -1497,8 +1489,8 @@ impl GlobalState { fn maybe_perform_sync_operation<'tcx>( &self, thread_mgr: &ThreadManager<'_, '_>, - op: impl FnOnce(VectorIdx, RefMut<'_, ThreadClockSet>) -> InterpResult<'tcx, bool>, current_span: Span, + op: impl FnOnce(VectorIdx, RefMut<'_, ThreadClockSet>) -> InterpResult<'tcx, bool>, ) -> InterpResult<'tcx> { if self.multi_threaded.get() { let (index, clocks) = self.current_thread_state_mut(thread_mgr); diff --git a/src/concurrency/vector_clock.rs b/src/concurrency/vector_clock.rs index d6d8e1c4b3..ab4764dd1c 100644 --- a/src/concurrency/vector_clock.rs +++ b/src/concurrency/vector_clock.rs @@ -48,14 +48,14 @@ const SMALL_VECTOR: usize = 4; /// The time-stamps recorded in the data-race detector consist of both /// a 32-bit unsigned integer which is the actual timestamp, and a `Span` /// so that diagnostics can report what code was responsible for an operation. -#[derive(Clone, Copy, Debug, Eq)] +#[derive(Clone, Copy, Debug)] pub struct VTimestamp { time: u32, pub span: Span, } impl VTimestamp { - pub const NONE: VTimestamp = VTimestamp { time: 0, span: DUMMY_SP }; + pub const ZERO: VTimestamp = VTimestamp { time: 0, span: DUMMY_SP }; pub fn span_data(&self) -> SpanData { self.span.data() @@ -68,6 +68,8 @@ impl PartialEq for VTimestamp { } } +impl Eq for VTimestamp {} + impl PartialOrd for VTimestamp { fn partial_cmp(&self, other: &Self) -> Option { Some(self.cmp(other)) @@ -98,7 +100,7 @@ impl VClock { /// for a value at the given index pub fn new_with_index(index: VectorIdx, timestamp: VTimestamp) -> VClock { let len = index.index() + 1; - let mut vec = smallvec::smallvec![VTimestamp::NONE; len]; + let mut vec = smallvec::smallvec![VTimestamp::ZERO; len]; vec[index.index()] = timestamp; VClock(vec) } @@ -115,7 +117,7 @@ impl VClock { #[inline] fn get_mut_with_min_len(&mut self, min_len: usize) -> &mut [VTimestamp] { if self.0.len() < min_len { - self.0.resize(min_len, VTimestamp::NONE); + self.0.resize(min_len, VTimestamp::ZERO); } assert!(self.0.len() >= min_len); self.0.as_mut_slice() @@ -361,7 +363,7 @@ impl Index for VClock { #[inline] fn index(&self, index: VectorIdx) -> &VTimestamp { - self.as_slice().get(index.to_u32() as usize).unwrap_or(&VTimestamp::NONE) + self.as_slice().get(index.to_u32() as usize).unwrap_or(&VTimestamp::ZERO) } } diff --git a/src/concurrency/weak_memory.rs b/src/concurrency/weak_memory.rs index c02ec7ded7..2a48c9e6cd 100644 --- a/src/concurrency/weak_memory.rs +++ b/src/concurrency/weak_memory.rs @@ -258,7 +258,7 @@ impl<'mir, 'tcx: 'mir> StoreBuffer { // The thread index and timestamp of the initialisation write // are never meaningfully used, so it's fine to leave them as 0 store_index: VectorIdx::from(0), - timestamp: VTimestamp::NONE, + timestamp: VTimestamp::ZERO, val: init, is_seqcst: false, load_info: RefCell::new(LoadInfo::default()), diff --git a/src/diagnostics.rs b/src/diagnostics.rs index d9f40b55cd..66cdd331f9 100644 --- a/src/diagnostics.rs +++ b/src/diagnostics.rs @@ -69,8 +69,8 @@ impl fmt::Display for TerminationInfo { DataRace { ptr, op1, op2 } => write!( f, - "Data race detected between {} on {} and {} on {} at {:?}", - op1.action, op1.thread_info, op2.action, op2.thread_info, ptr, + "Data race detected between {} on {} and {} on {} at {:?}. The {} is here", + op1.action, op1.thread_info, op2.action, op2.thread_info, ptr, op1.action ), } } @@ -222,10 +222,9 @@ pub fn report_error<'tcx, 'mir>( vec![(Some(*span), format!("the `{link_name}` symbol is defined here"))], Int2PtrWithStrictProvenance => vec![(None, format!("use Strict Provenance APIs (https://doc.rust-lang.org/nightly/std/ptr/index.html#strict-provenance, https://crates.io/crates/sptr) instead"))], - DataRace { ptr: _, op1, op2 } => + DataRace { op2, .. } => vec![ - (Some(op1.span), format!("The {} on {} is here", op1.action, op1.thread_info)), - (Some(op2.span), format!("The {} on {} is here", op2.action, op2.thread_info)), + (Some(op2.span), format!("and {} on {}, which is here", op2.action, op2.thread_info)), (None, format!("this indicates a bug in the program: it performed an invalid operation, and caused Undefined Behavior")), (None, format!("see https://doc.rust-lang.org/nightly/reference/behavior-considered-undefined.html for further information")), ], diff --git a/tests/fail/data_race/alloc_read_race.stderr b/tests/fail/data_race/alloc_read_race.stderr index 510b177fc7..ff79f07ba8 100644 --- a/tests/fail/data_race/alloc_read_race.stderr +++ b/tests/fail/data_race/alloc_read_race.stderr @@ -1,15 +1,10 @@ -error: Undefined Behavior: Data race detected between Read on thread `` and Allocate on thread `` at ALLOC +error: Undefined Behavior: Data race detected between Read on thread `` and Allocate on thread `` at ALLOC. The Read is here --> $DIR/alloc_read_race.rs:LL:CC | LL | *pointer.load(Ordering::Relaxed) - | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ Data race detected between Read on thread `` and Allocate on thread `` at ALLOC + | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ Data race detected between Read on thread `` and Allocate on thread `` at ALLOC. The Read is here | -help: The Read on thread `` is here - --> $DIR/alloc_read_race.rs:LL:CC - | -LL | ... *pointer.load(Ordering::Relaxed) - | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ -help: The Allocate on thread `` is here +help: and Allocate on thread ``, which is here --> $DIR/alloc_read_race.rs:LL:CC | LL | pointer.store(Box::into_raw(Box::new_uninit()), Ordering::Relaxed); diff --git a/tests/fail/data_race/alloc_write_race.stderr b/tests/fail/data_race/alloc_write_race.stderr index 1149353680..2398cbf12e 100644 --- a/tests/fail/data_race/alloc_write_race.stderr +++ b/tests/fail/data_race/alloc_write_race.stderr @@ -1,15 +1,10 @@ -error: Undefined Behavior: Data race detected between Write on thread `` and Allocate on thread `` at ALLOC +error: Undefined Behavior: Data race detected between Write on thread `` and Allocate on thread `` at ALLOC. The Write is here --> $DIR/alloc_write_race.rs:LL:CC | LL | *pointer.load(Ordering::Relaxed) = 2; - | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ Data race detected between Write on thread `` and Allocate on thread `` at ALLOC + | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ Data race detected between Write on thread `` and Allocate on thread `` at ALLOC. The Write is here | -help: The Write on thread `` is here - --> $DIR/alloc_write_race.rs:LL:CC - | -LL | ... *pointer.load(Ordering::Relaxed) = 2; - | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ -help: The Allocate on thread `` is here +help: and Allocate on thread ``, which is here --> $DIR/alloc_write_race.rs:LL:CC | LL | .store(Box::into_raw(Box::::new_uninit()) as *mut usize, Ordering::Relaxed); diff --git a/tests/fail/data_race/atomic_read_na_write_race1.stderr b/tests/fail/data_race/atomic_read_na_write_race1.stderr index e77afe7b82..15cfaef11c 100644 --- a/tests/fail/data_race/atomic_read_na_write_race1.stderr +++ b/tests/fail/data_race/atomic_read_na_write_race1.stderr @@ -1,15 +1,10 @@ -error: Undefined Behavior: Data race detected between Atomic Load on thread `` and Write on thread `` at ALLOC +error: Undefined Behavior: Data race detected between Atomic Load on thread `` and Write on thread `` at ALLOC. The Atomic Load is here --> $DIR/atomic_read_na_write_race1.rs:LL:CC | LL | (&*c.0).load(Ordering::SeqCst) - | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ Data race detected between Atomic Load on thread `` and Write on thread `` at ALLOC + | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ Data race detected between Atomic Load on thread `` and Write on thread `` at ALLOC. The Atomic Load is here | -help: The Atomic Load on thread `` is here - --> $DIR/atomic_read_na_write_race1.rs:LL:CC - | -LL | ... (&*c.0).load(Ordering::SeqCst) - | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ -help: The Write on thread `` is here +help: and Write on thread ``, which is here --> $DIR/atomic_read_na_write_race1.rs:LL:CC | LL | *(c.0 as *mut usize) = 32; diff --git a/tests/fail/data_race/atomic_read_na_write_race2.stderr b/tests/fail/data_race/atomic_read_na_write_race2.stderr index 6b30442169..d498914657 100644 --- a/tests/fail/data_race/atomic_read_na_write_race2.stderr +++ b/tests/fail/data_race/atomic_read_na_write_race2.stderr @@ -1,15 +1,10 @@ -error: Undefined Behavior: Data race detected between Write on thread `` and Atomic Load on thread `` at ALLOC +error: Undefined Behavior: Data race detected between Write on thread `` and Atomic Load on thread `` at ALLOC. The Write is here --> $DIR/atomic_read_na_write_race2.rs:LL:CC | LL | *atomic_ref.get_mut() = 32; - | ^^^^^^^^^^^^^^^^^^^^^^^^^^ Data race detected between Write on thread `` and Atomic Load on thread `` at ALLOC + | ^^^^^^^^^^^^^^^^^^^^^^^^^^ Data race detected between Write on thread `` and Atomic Load on thread `` at ALLOC. The Write is here | -help: The Write on thread `` is here - --> $DIR/atomic_read_na_write_race2.rs:LL:CC - | -LL | ... *atomic_ref.get_mut() = 32; - | ^^^^^^^^^^^^^^^^^^^^^^^^^^ -help: The Atomic Load on thread `` is here +help: and Atomic Load on thread ``, which is here --> $DIR/atomic_read_na_write_race2.rs:LL:CC | LL | atomic_ref.load(Ordering::SeqCst) diff --git a/tests/fail/data_race/atomic_write_na_read_race1.stderr b/tests/fail/data_race/atomic_write_na_read_race1.stderr index ffc985c04c..5378ea6067 100644 --- a/tests/fail/data_race/atomic_write_na_read_race1.stderr +++ b/tests/fail/data_race/atomic_write_na_read_race1.stderr @@ -1,15 +1,10 @@ -error: Undefined Behavior: Data race detected between Read on thread `` and Atomic Store on thread `` at ALLOC +error: Undefined Behavior: Data race detected between Read on thread `` and Atomic Store on thread `` at ALLOC. The Read is here --> $DIR/atomic_write_na_read_race1.rs:LL:CC | LL | *atomic_ref.get_mut() - | ^^^^^^^^^^^^^^^^^^^^^ Data race detected between Read on thread `` and Atomic Store on thread `` at ALLOC + | ^^^^^^^^^^^^^^^^^^^^^ Data race detected between Read on thread `` and Atomic Store on thread `` at ALLOC. The Read is here | -help: The Read on thread `` is here - --> $DIR/atomic_write_na_read_race1.rs:LL:CC - | -LL | *atomic_ref.get_mut() - | ^^^^^^^^^^^^^^^^^^^^^ -help: The Atomic Store on thread `` is here +help: and Atomic Store on thread ``, which is here --> $DIR/atomic_write_na_read_race1.rs:LL:CC | LL | atomic_ref.store(32, Ordering::SeqCst) diff --git a/tests/fail/data_race/atomic_write_na_read_race2.stderr b/tests/fail/data_race/atomic_write_na_read_race2.stderr index 5b5c8d07f8..3da2f624bf 100644 --- a/tests/fail/data_race/atomic_write_na_read_race2.stderr +++ b/tests/fail/data_race/atomic_write_na_read_race2.stderr @@ -1,15 +1,10 @@ -error: Undefined Behavior: Data race detected between Atomic Store on thread `` and Read on thread `` at ALLOC +error: Undefined Behavior: Data race detected between Atomic Store on thread `` and Read on thread `` at ALLOC. The Atomic Store is here --> $DIR/atomic_write_na_read_race2.rs:LL:CC | LL | (&*c.0).store(32, Ordering::SeqCst); - | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ Data race detected between Atomic Store on thread `` and Read on thread `` at ALLOC + | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ Data race detected between Atomic Store on thread `` and Read on thread `` at ALLOC. The Atomic Store is here | -help: The Atomic Store on thread `` is here - --> $DIR/atomic_write_na_read_race2.rs:LL:CC - | -LL | ... (&*c.0).store(32, Ordering::SeqCst); - | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ -help: The Read on thread `` is here +help: and Read on thread ``, which is here --> $DIR/atomic_write_na_read_race2.rs:LL:CC | LL | let _val = *(c.0 as *mut usize); diff --git a/tests/fail/data_race/atomic_write_na_write_race1.stderr b/tests/fail/data_race/atomic_write_na_write_race1.stderr index 55cc212ec0..4d1dbc0b84 100644 --- a/tests/fail/data_race/atomic_write_na_write_race1.stderr +++ b/tests/fail/data_race/atomic_write_na_write_race1.stderr @@ -1,15 +1,10 @@ -error: Undefined Behavior: Data race detected between Atomic Store on thread `` and Write on thread `` at ALLOC +error: Undefined Behavior: Data race detected between Atomic Store on thread `` and Write on thread `` at ALLOC. The Atomic Store is here --> $DIR/atomic_write_na_write_race1.rs:LL:CC | LL | (&*c.0).store(64, Ordering::SeqCst); - | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ Data race detected between Atomic Store on thread `` and Write on thread `` at ALLOC + | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ Data race detected between Atomic Store on thread `` and Write on thread `` at ALLOC. The Atomic Store is here | -help: The Atomic Store on thread `` is here - --> $DIR/atomic_write_na_write_race1.rs:LL:CC - | -LL | ... (&*c.0).store(64, Ordering::SeqCst); - | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ -help: The Write on thread `` is here +help: and Write on thread ``, which is here --> $DIR/atomic_write_na_write_race1.rs:LL:CC | LL | *(c.0 as *mut usize) = 32; diff --git a/tests/fail/data_race/atomic_write_na_write_race2.stderr b/tests/fail/data_race/atomic_write_na_write_race2.stderr index 2b666ef027..cec68ba159 100644 --- a/tests/fail/data_race/atomic_write_na_write_race2.stderr +++ b/tests/fail/data_race/atomic_write_na_write_race2.stderr @@ -1,15 +1,10 @@ -error: Undefined Behavior: Data race detected between Write on thread `` and Atomic Store on thread `` at ALLOC +error: Undefined Behavior: Data race detected between Write on thread `` and Atomic Store on thread `` at ALLOC. The Write is here --> $DIR/atomic_write_na_write_race2.rs:LL:CC | LL | *atomic_ref.get_mut() = 32; - | ^^^^^^^^^^^^^^^^^^^^^^^^^^ Data race detected between Write on thread `` and Atomic Store on thread `` at ALLOC + | ^^^^^^^^^^^^^^^^^^^^^^^^^^ Data race detected between Write on thread `` and Atomic Store on thread `` at ALLOC. The Write is here | -help: The Write on thread `` is here - --> $DIR/atomic_write_na_write_race2.rs:LL:CC - | -LL | ... *atomic_ref.get_mut() = 32; - | ^^^^^^^^^^^^^^^^^^^^^^^^^^ -help: The Atomic Store on thread `` is here +help: and Atomic Store on thread ``, which is here --> $DIR/atomic_write_na_write_race2.rs:LL:CC | LL | atomic_ref.store(64, Ordering::SeqCst); diff --git a/tests/fail/data_race/dangling_thread_async_race.stderr b/tests/fail/data_race/dangling_thread_async_race.stderr index 156261b353..7ef38c6706 100644 --- a/tests/fail/data_race/dangling_thread_async_race.stderr +++ b/tests/fail/data_race/dangling_thread_async_race.stderr @@ -1,15 +1,10 @@ -error: Undefined Behavior: Data race detected between Write on thread `` and Write on thread `` at ALLOC +error: Undefined Behavior: Data race detected between Write on thread `` and Write on thread `` at ALLOC. The Write is here --> $DIR/dangling_thread_async_race.rs:LL:CC | LL | *c.0 = 64; - | ^^^^^^^^^ Data race detected between Write on thread `` and Write on thread `` at ALLOC + | ^^^^^^^^^ Data race detected between Write on thread `` and Write on thread `` at ALLOC. The Write is here | -help: The Write on thread `` is here - --> $DIR/dangling_thread_async_race.rs:LL:CC - | -LL | *c.0 = 64; - | ^^^^^^^^^ -help: The Write on thread `` is here +help: and Write on thread ``, which is here --> $DIR/dangling_thread_async_race.rs:LL:CC | LL | *c.0 = 32; diff --git a/tests/fail/data_race/dangling_thread_race.stderr b/tests/fail/data_race/dangling_thread_race.stderr index bd0d34929e..3f556b6a8a 100644 --- a/tests/fail/data_race/dangling_thread_race.stderr +++ b/tests/fail/data_race/dangling_thread_race.stderr @@ -1,15 +1,10 @@ -error: Undefined Behavior: Data race detected between Write on thread `main` and Write on thread `` at ALLOC +error: Undefined Behavior: Data race detected between Write on thread `main` and Write on thread `` at ALLOC. The Write is here --> $DIR/dangling_thread_race.rs:LL:CC | LL | *c.0 = 64; - | ^^^^^^^^^ Data race detected between Write on thread `main` and Write on thread `` at ALLOC + | ^^^^^^^^^ Data race detected between Write on thread `main` and Write on thread `` at ALLOC. The Write is here | -help: The Write on thread `main` is here - --> $DIR/dangling_thread_race.rs:LL:CC - | -LL | *c.0 = 64; - | ^^^^^^^^^ -help: The Write on thread `` is here +help: and Write on thread ``, which is here --> $DIR/dangling_thread_race.rs:LL:CC | LL | *c.0 = 32; diff --git a/tests/fail/data_race/dealloc_read_race1.stderr b/tests/fail/data_race/dealloc_read_race1.stderr index 02a9bb63b5..af2b2ed398 100644 --- a/tests/fail/data_race/dealloc_read_race1.stderr +++ b/tests/fail/data_race/dealloc_read_race1.stderr @@ -1,4 +1,4 @@ -error: Undefined Behavior: Data race detected between Deallocate on thread `` and Read on thread `` at ALLOC +error: Undefined Behavior: Data race detected between Deallocate on thread `` and Read on thread `` at ALLOC. The Deallocate is here --> $DIR/dealloc_read_race1.rs:LL:CC | LL | / __rust_dealloc( @@ -7,19 +7,9 @@ LL | | ptr.0 as *mut _, LL | | std::mem::size_of::(), LL | | std::mem::align_of::(), LL | | ); - | |_____________^ Data race detected between Deallocate on thread `` and Read on thread `` at ALLOC + | |_____________^ Data race detected between Deallocate on thread `` and Read on thread `` at ALLOC. The Deallocate is here | -help: The Deallocate on thread `` is here - --> $DIR/dealloc_read_race1.rs:LL:CC - | -LL | / __rust_dealloc( -LL | | -LL | | ptr.0 as *mut _, -LL | | std::mem::size_of::(), -LL | | std::mem::align_of::(), -LL | | ); - | |_____________^ -help: The Read on thread `` is here +help: and Read on thread ``, which is here --> $DIR/dealloc_read_race1.rs:LL:CC | LL | let _val = *ptr.0; diff --git a/tests/fail/data_race/dealloc_read_race_stack.stderr b/tests/fail/data_race/dealloc_read_race_stack.stderr index 18a30bd5a6..d6b2a8a573 100644 --- a/tests/fail/data_race/dealloc_read_race_stack.stderr +++ b/tests/fail/data_race/dealloc_read_race_stack.stderr @@ -1,15 +1,10 @@ -error: Undefined Behavior: Data race detected between Deallocate on thread `` and Read on thread `` at ALLOC +error: Undefined Behavior: Data race detected between Deallocate on thread `` and Read on thread `` at ALLOC. The Deallocate is here --> $DIR/dealloc_read_race_stack.rs:LL:CC | LL | } - | ^ Data race detected between Deallocate on thread `` and Read on thread `` at ALLOC + | ^ Data race detected between Deallocate on thread `` and Read on thread `` at ALLOC. The Deallocate is here | -help: The Deallocate on thread `` is here - --> $DIR/dealloc_read_race_stack.rs:LL:CC - | -LL | } - | ^ -help: The Read on thread `` is here +help: and Read on thread ``, which is here --> $DIR/dealloc_read_race_stack.rs:LL:CC | LL | *pointer.load(Ordering::Acquire) diff --git a/tests/fail/data_race/dealloc_write_race1.stderr b/tests/fail/data_race/dealloc_write_race1.stderr index 9e59d5a647..6b235f651a 100644 --- a/tests/fail/data_race/dealloc_write_race1.stderr +++ b/tests/fail/data_race/dealloc_write_race1.stderr @@ -1,4 +1,4 @@ -error: Undefined Behavior: Data race detected between Deallocate on thread `` and Write on thread `` at ALLOC +error: Undefined Behavior: Data race detected between Deallocate on thread `` and Write on thread `` at ALLOC. The Deallocate is here --> $DIR/dealloc_write_race1.rs:LL:CC | LL | / __rust_dealloc( @@ -7,19 +7,9 @@ LL | | ptr.0 as *mut _, LL | | std::mem::size_of::(), LL | | std::mem::align_of::(), LL | | ); - | |_____________^ Data race detected between Deallocate on thread `` and Write on thread `` at ALLOC + | |_____________^ Data race detected between Deallocate on thread `` and Write on thread `` at ALLOC. The Deallocate is here | -help: The Deallocate on thread `` is here - --> $DIR/dealloc_write_race1.rs:LL:CC - | -LL | / __rust_dealloc( -LL | | -LL | | ptr.0 as *mut _, -LL | | std::mem::size_of::(), -LL | | std::mem::align_of::(), -LL | | ); - | |_____________^ -help: The Write on thread `` is here +help: and Write on thread ``, which is here --> $DIR/dealloc_write_race1.rs:LL:CC | LL | *ptr.0 = 2; diff --git a/tests/fail/data_race/dealloc_write_race_stack.stderr b/tests/fail/data_race/dealloc_write_race_stack.stderr index 5ac7c2d5a1..6e20a1aa5e 100644 --- a/tests/fail/data_race/dealloc_write_race_stack.stderr +++ b/tests/fail/data_race/dealloc_write_race_stack.stderr @@ -1,15 +1,10 @@ -error: Undefined Behavior: Data race detected between Deallocate on thread `` and Write on thread `` at ALLOC +error: Undefined Behavior: Data race detected between Deallocate on thread `` and Write on thread `` at ALLOC. The Deallocate is here --> $DIR/dealloc_write_race_stack.rs:LL:CC | LL | } - | ^ Data race detected between Deallocate on thread `` and Write on thread `` at ALLOC + | ^ Data race detected between Deallocate on thread `` and Write on thread `` at ALLOC. The Deallocate is here | -help: The Deallocate on thread `` is here - --> $DIR/dealloc_write_race_stack.rs:LL:CC - | -LL | } - | ^ -help: The Write on thread `` is here +help: and Write on thread ``, which is here --> $DIR/dealloc_write_race_stack.rs:LL:CC | LL | *pointer.load(Ordering::Acquire) = 3; diff --git a/tests/fail/data_race/enable_after_join_to_main.stderr b/tests/fail/data_race/enable_after_join_to_main.stderr index 636a686f84..70d671ea7b 100644 --- a/tests/fail/data_race/enable_after_join_to_main.stderr +++ b/tests/fail/data_race/enable_after_join_to_main.stderr @@ -1,15 +1,10 @@ -error: Undefined Behavior: Data race detected between Write on thread `` and Write on thread `` at ALLOC +error: Undefined Behavior: Data race detected between Write on thread `` and Write on thread `` at ALLOC. The Write is here --> $DIR/enable_after_join_to_main.rs:LL:CC | LL | *c.0 = 64; - | ^^^^^^^^^ Data race detected between Write on thread `` and Write on thread `` at ALLOC + | ^^^^^^^^^ Data race detected between Write on thread `` and Write on thread `` at ALLOC. The Write is here | -help: The Write on thread `` is here - --> $DIR/enable_after_join_to_main.rs:LL:CC - | -LL | *c.0 = 64; - | ^^^^^^^^^ -help: The Write on thread `` is here +help: and Write on thread ``, which is here --> $DIR/enable_after_join_to_main.rs:LL:CC | LL | *c.0 = 32; diff --git a/tests/fail/data_race/fence_after_load.stderr b/tests/fail/data_race/fence_after_load.stderr index e686291638..d073124df0 100644 --- a/tests/fail/data_race/fence_after_load.stderr +++ b/tests/fail/data_race/fence_after_load.stderr @@ -1,15 +1,10 @@ -error: Undefined Behavior: Data race detected between Write on thread `main` and Write on thread `` at ALLOC +error: Undefined Behavior: Data race detected between Write on thread `main` and Write on thread `` at ALLOC. The Write is here --> $DIR/fence_after_load.rs:LL:CC | LL | unsafe { V = 2 } - | ^^^^^ Data race detected between Write on thread `main` and Write on thread `` at ALLOC + | ^^^^^ Data race detected between Write on thread `main` and Write on thread `` at ALLOC. The Write is here | -help: The Write on thread `main` is here - --> $DIR/fence_after_load.rs:LL:CC - | -LL | unsafe { V = 2 } - | ^^^^^ -help: The Write on thread `` is here +help: and Write on thread ``, which is here --> $DIR/fence_after_load.rs:LL:CC | LL | unsafe { V = 1 } diff --git a/tests/fail/data_race/read_write_race.stderr b/tests/fail/data_race/read_write_race.stderr index afba81ee8f..ae237a9890 100644 --- a/tests/fail/data_race/read_write_race.stderr +++ b/tests/fail/data_race/read_write_race.stderr @@ -1,15 +1,10 @@ -error: Undefined Behavior: Data race detected between Write on thread `` and Read on thread `` at ALLOC +error: Undefined Behavior: Data race detected between Write on thread `` and Read on thread `` at ALLOC. The Write is here --> $DIR/read_write_race.rs:LL:CC | LL | *c.0 = 64; - | ^^^^^^^^^ Data race detected between Write on thread `` and Read on thread `` at ALLOC + | ^^^^^^^^^ Data race detected between Write on thread `` and Read on thread `` at ALLOC. The Write is here | -help: The Write on thread `` is here - --> $DIR/read_write_race.rs:LL:CC - | -LL | *c.0 = 64; - | ^^^^^^^^^ -help: The Read on thread `` is here +help: and Read on thread ``, which is here --> $DIR/read_write_race.rs:LL:CC | LL | let _val = *c.0; diff --git a/tests/fail/data_race/read_write_race_stack.stderr b/tests/fail/data_race/read_write_race_stack.stderr index e1e4604aa6..ec01d9be6e 100644 --- a/tests/fail/data_race/read_write_race_stack.stderr +++ b/tests/fail/data_race/read_write_race_stack.stderr @@ -1,15 +1,10 @@ -error: Undefined Behavior: Data race detected between Read on thread `` and Write on thread `` at ALLOC +error: Undefined Behavior: Data race detected between Read on thread `` and Write on thread `` at ALLOC. The Read is here --> $DIR/read_write_race_stack.rs:LL:CC | LL | stack_var - | ^^^^^^^^^ Data race detected between Read on thread `` and Write on thread `` at ALLOC + | ^^^^^^^^^ Data race detected between Read on thread `` and Write on thread `` at ALLOC. The Read is here | -help: The Read on thread `` is here - --> $DIR/read_write_race_stack.rs:LL:CC - | -LL | stack_var - | ^^^^^^^^^ -help: The Write on thread `` is here +help: and Write on thread ``, which is here --> $DIR/read_write_race_stack.rs:LL:CC | LL | *pointer.load(Ordering::Acquire) = 3; diff --git a/tests/fail/data_race/relax_acquire_race.stderr b/tests/fail/data_race/relax_acquire_race.stderr index aae90e0c9e..50768ebcdb 100644 --- a/tests/fail/data_race/relax_acquire_race.stderr +++ b/tests/fail/data_race/relax_acquire_race.stderr @@ -1,15 +1,10 @@ -error: Undefined Behavior: Data race detected between Read on thread `` and Write on thread `` at ALLOC +error: Undefined Behavior: Data race detected between Read on thread `` and Write on thread `` at ALLOC. The Read is here --> $DIR/relax_acquire_race.rs:LL:CC | LL | *c.0 - | ^^^^ Data race detected between Read on thread `` and Write on thread `` at ALLOC + | ^^^^ Data race detected between Read on thread `` and Write on thread `` at ALLOC. The Read is here | -help: The Read on thread `` is here - --> $DIR/relax_acquire_race.rs:LL:CC - | -LL | *c.0 - | ^^^^ -help: The Write on thread `` is here +help: and Write on thread ``, which is here --> $DIR/relax_acquire_race.rs:LL:CC | LL | *c.0 = 1; diff --git a/tests/fail/data_race/release_seq_race.stderr b/tests/fail/data_race/release_seq_race.stderr index 02413e6baa..c3348ae0a3 100644 --- a/tests/fail/data_race/release_seq_race.stderr +++ b/tests/fail/data_race/release_seq_race.stderr @@ -1,15 +1,10 @@ -error: Undefined Behavior: Data race detected between Read on thread `` and Write on thread `` at ALLOC +error: Undefined Behavior: Data race detected between Read on thread `` and Write on thread `` at ALLOC. The Read is here --> $DIR/release_seq_race.rs:LL:CC | LL | *c.0 - | ^^^^ Data race detected between Read on thread `` and Write on thread `` at ALLOC + | ^^^^ Data race detected between Read on thread `` and Write on thread `` at ALLOC. The Read is here | -help: The Read on thread `` is here - --> $DIR/release_seq_race.rs:LL:CC - | -LL | *c.0 - | ^^^^ -help: The Write on thread `` is here +help: and Write on thread ``, which is here --> $DIR/release_seq_race.rs:LL:CC | LL | *c.0 = 1; diff --git a/tests/fail/data_race/release_seq_race_same_thread.stderr b/tests/fail/data_race/release_seq_race_same_thread.stderr index 9573ca9586..522226faa4 100644 --- a/tests/fail/data_race/release_seq_race_same_thread.stderr +++ b/tests/fail/data_race/release_seq_race_same_thread.stderr @@ -1,15 +1,10 @@ -error: Undefined Behavior: Data race detected between Read on thread `` and Write on thread `` at ALLOC +error: Undefined Behavior: Data race detected between Read on thread `` and Write on thread `` at ALLOC. The Read is here --> $DIR/release_seq_race_same_thread.rs:LL:CC | LL | *c.0 - | ^^^^ Data race detected between Read on thread `` and Write on thread `` at ALLOC + | ^^^^ Data race detected between Read on thread `` and Write on thread `` at ALLOC. The Read is here | -help: The Read on thread `` is here - --> $DIR/release_seq_race_same_thread.rs:LL:CC - | -LL | *c.0 - | ^^^^ -help: The Write on thread `` is here +help: and Write on thread ``, which is here --> $DIR/release_seq_race_same_thread.rs:LL:CC | LL | *c.0 = 1; diff --git a/tests/fail/data_race/rmw_race.stderr b/tests/fail/data_race/rmw_race.stderr index ae53cc0c75..672f08c422 100644 --- a/tests/fail/data_race/rmw_race.stderr +++ b/tests/fail/data_race/rmw_race.stderr @@ -1,15 +1,10 @@ -error: Undefined Behavior: Data race detected between Read on thread `` and Write on thread `` at ALLOC +error: Undefined Behavior: Data race detected between Read on thread `` and Write on thread `` at ALLOC. The Read is here --> $DIR/rmw_race.rs:LL:CC | LL | *c.0 - | ^^^^ Data race detected between Read on thread `` and Write on thread `` at ALLOC + | ^^^^ Data race detected between Read on thread `` and Write on thread `` at ALLOC. The Read is here | -help: The Read on thread `` is here - --> $DIR/rmw_race.rs:LL:CC - | -LL | *c.0 - | ^^^^ -help: The Write on thread `` is here +help: and Write on thread ``, which is here --> $DIR/rmw_race.rs:LL:CC | LL | *c.0 = 1; diff --git a/tests/fail/data_race/stack_pop_race.stderr b/tests/fail/data_race/stack_pop_race.stderr index 0853e0830c..e21fe201d1 100644 --- a/tests/fail/data_race/stack_pop_race.stderr +++ b/tests/fail/data_race/stack_pop_race.stderr @@ -1,15 +1,10 @@ -error: Undefined Behavior: Data race detected between Deallocate on thread `main` and Read on thread `` at ALLOC +error: Undefined Behavior: Data race detected between Deallocate on thread `main` and Read on thread `` at ALLOC. The Deallocate is here --> $DIR/stack_pop_race.rs:LL:CC | LL | } - | ^ Data race detected between Deallocate on thread `main` and Read on thread `` at ALLOC + | ^ Data race detected between Deallocate on thread `main` and Read on thread `` at ALLOC. The Deallocate is here | -help: The Deallocate on thread `main` is here - --> $DIR/stack_pop_race.rs:LL:CC - | -LL | } - | ^ -help: The Read on thread `` is here +help: and Read on thread ``, which is here --> $DIR/stack_pop_race.rs:LL:CC | LL | let _val = unsafe { *ptr.0 }; diff --git a/tests/fail/data_race/write_write_race.stderr b/tests/fail/data_race/write_write_race.stderr index 132cd50304..1f67303e59 100644 --- a/tests/fail/data_race/write_write_race.stderr +++ b/tests/fail/data_race/write_write_race.stderr @@ -1,15 +1,10 @@ -error: Undefined Behavior: Data race detected between Write on thread `` and Write on thread `` at ALLOC +error: Undefined Behavior: Data race detected between Write on thread `` and Write on thread `` at ALLOC. The Write is here --> $DIR/write_write_race.rs:LL:CC | LL | *c.0 = 64; - | ^^^^^^^^^ Data race detected between Write on thread `` and Write on thread `` at ALLOC + | ^^^^^^^^^ Data race detected between Write on thread `` and Write on thread `` at ALLOC. The Write is here | -help: The Write on thread `` is here - --> $DIR/write_write_race.rs:LL:CC - | -LL | *c.0 = 64; - | ^^^^^^^^^ -help: The Write on thread `` is here +help: and Write on thread ``, which is here --> $DIR/write_write_race.rs:LL:CC | LL | *c.0 = 32; diff --git a/tests/fail/data_race/write_write_race_stack.stderr b/tests/fail/data_race/write_write_race_stack.stderr index 25963d63db..5b6481327c 100644 --- a/tests/fail/data_race/write_write_race_stack.stderr +++ b/tests/fail/data_race/write_write_race_stack.stderr @@ -1,15 +1,10 @@ -error: Undefined Behavior: Data race detected between Write on thread `` and Write on thread `` at ALLOC +error: Undefined Behavior: Data race detected between Write on thread `` and Write on thread `` at ALLOC. The Write is here --> $DIR/write_write_race_stack.rs:LL:CC | LL | stack_var = 1usize; - | ^^^^^^^^^^^^^^^^^^ Data race detected between Write on thread `` and Write on thread `` at ALLOC + | ^^^^^^^^^^^^^^^^^^ Data race detected between Write on thread `` and Write on thread `` at ALLOC. The Write is here | -help: The Write on thread `` is here - --> $DIR/write_write_race_stack.rs:LL:CC - | -LL | stack_var = 1usize; - | ^^^^^^^^^^^^^^^^^^ -help: The Write on thread `` is here +help: and Write on thread ``, which is here --> $DIR/write_write_race_stack.rs:LL:CC | LL | *pointer.load(Ordering::Acquire) = 3; diff --git a/tests/fail/stacked_borrows/retag_data_race_read.stderr b/tests/fail/stacked_borrows/retag_data_race_read.stderr index ff874bd9e8..6f9ea26c08 100644 --- a/tests/fail/stacked_borrows/retag_data_race_read.stderr +++ b/tests/fail/stacked_borrows/retag_data_race_read.stderr @@ -1,15 +1,10 @@ -error: Undefined Behavior: Data race detected between Write on thread `` and Read on thread `` at ALLOC +error: Undefined Behavior: Data race detected between Write on thread `` and Read on thread `` at ALLOC. The Write is here --> $DIR/retag_data_race_read.rs:LL:CC | LL | *p = 5; - | ^^^^^^ Data race detected between Write on thread `` and Read on thread `` at ALLOC + | ^^^^^^ Data race detected between Write on thread `` and Read on thread `` at ALLOC. The Write is here | -help: The Write on thread `` is here - --> $DIR/retag_data_race_read.rs:LL:CC - | -LL | *p = 5; - | ^^^^^^ -help: The Read on thread `` is here +help: and Read on thread ``, which is here --> $DIR/retag_data_race_read.rs:LL:CC | LL | let _r = &*p; diff --git a/tests/fail/stacked_borrows/retag_data_race_write.stderr b/tests/fail/stacked_borrows/retag_data_race_write.stderr index 80b6ac6e13..44f17bd6ff 100644 --- a/tests/fail/stacked_borrows/retag_data_race_write.stderr +++ b/tests/fail/stacked_borrows/retag_data_race_write.stderr @@ -1,15 +1,10 @@ -error: Undefined Behavior: Data race detected between Write on thread `` and Write on thread `` at ALLOC +error: Undefined Behavior: Data race detected between Write on thread `` and Write on thread `` at ALLOC. The Write is here --> $DIR/retag_data_race_write.rs:LL:CC | LL | *p = 5; - | ^^^^^^ Data race detected between Write on thread `` and Write on thread `` at ALLOC + | ^^^^^^ Data race detected between Write on thread `` and Write on thread `` at ALLOC. The Write is here | -help: The Write on thread `` is here - --> $DIR/retag_data_race_write.rs:LL:CC - | -LL | *p = 5; - | ^^^^^^ -help: The Write on thread `` is here +help: and Write on thread ``, which is here --> $DIR/retag_data_race_write.rs:LL:CC | LL | let _r = &mut *p; From ba1fa8826bef5c97ae58a21ff32b2434017dca58 Mon Sep 17 00:00:00 2001 From: Ben Kimock Date: Wed, 21 Dec 2022 23:21:40 -0500 Subject: [PATCH 21/28] Fix phrasing --- src/diagnostics.rs | 2 +- tests/fail/data_race/alloc_read_race.stderr | 2 +- tests/fail/data_race/alloc_write_race.stderr | 2 +- tests/fail/data_race/atomic_read_na_write_race1.stderr | 2 +- tests/fail/data_race/atomic_read_na_write_race2.stderr | 2 +- tests/fail/data_race/atomic_write_na_read_race1.stderr | 2 +- tests/fail/data_race/atomic_write_na_read_race2.stderr | 2 +- tests/fail/data_race/atomic_write_na_write_race1.stderr | 2 +- tests/fail/data_race/atomic_write_na_write_race2.stderr | 2 +- tests/fail/data_race/dangling_thread_async_race.stderr | 2 +- tests/fail/data_race/dangling_thread_race.stderr | 2 +- tests/fail/data_race/dealloc_read_race1.stderr | 2 +- tests/fail/data_race/dealloc_read_race_stack.stderr | 2 +- tests/fail/data_race/dealloc_write_race1.stderr | 2 +- tests/fail/data_race/dealloc_write_race_stack.stderr | 2 +- tests/fail/data_race/enable_after_join_to_main.stderr | 2 +- tests/fail/data_race/fence_after_load.stderr | 2 +- tests/fail/data_race/read_write_race.stderr | 2 +- tests/fail/data_race/read_write_race_stack.stderr | 2 +- tests/fail/data_race/relax_acquire_race.stderr | 2 +- tests/fail/data_race/release_seq_race.stderr | 2 +- tests/fail/data_race/release_seq_race_same_thread.stderr | 2 +- tests/fail/data_race/rmw_race.stderr | 2 +- tests/fail/data_race/stack_pop_race.stderr | 2 +- tests/fail/data_race/write_write_race.stderr | 2 +- tests/fail/data_race/write_write_race_stack.stderr | 2 +- tests/fail/stacked_borrows/retag_data_race_read.stderr | 2 +- tests/fail/stacked_borrows/retag_data_race_write.stderr | 2 +- 28 files changed, 28 insertions(+), 28 deletions(-) diff --git a/src/diagnostics.rs b/src/diagnostics.rs index 66cdd331f9..9f7be0f3b5 100644 --- a/src/diagnostics.rs +++ b/src/diagnostics.rs @@ -224,7 +224,7 @@ pub fn report_error<'tcx, 'mir>( vec![(None, format!("use Strict Provenance APIs (https://doc.rust-lang.org/nightly/std/ptr/index.html#strict-provenance, https://crates.io/crates/sptr) instead"))], DataRace { op2, .. } => vec![ - (Some(op2.span), format!("and {} on {}, which is here", op2.action, op2.thread_info)), + (Some(op2.span), format!("and the {} on {} is here", op2.action, op2.thread_info)), (None, format!("this indicates a bug in the program: it performed an invalid operation, and caused Undefined Behavior")), (None, format!("see https://doc.rust-lang.org/nightly/reference/behavior-considered-undefined.html for further information")), ], diff --git a/tests/fail/data_race/alloc_read_race.stderr b/tests/fail/data_race/alloc_read_race.stderr index ff79f07ba8..9b487dacca 100644 --- a/tests/fail/data_race/alloc_read_race.stderr +++ b/tests/fail/data_race/alloc_read_race.stderr @@ -4,7 +4,7 @@ error: Undefined Behavior: Data race detected between Read on thread `` LL | *pointer.load(Ordering::Relaxed) | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ Data race detected between Read on thread `` and Allocate on thread `` at ALLOC. The Read is here | -help: and Allocate on thread ``, which is here +help: and the Allocate on thread `` is here --> $DIR/alloc_read_race.rs:LL:CC | LL | pointer.store(Box::into_raw(Box::new_uninit()), Ordering::Relaxed); diff --git a/tests/fail/data_race/alloc_write_race.stderr b/tests/fail/data_race/alloc_write_race.stderr index 2398cbf12e..7b1fcdf05b 100644 --- a/tests/fail/data_race/alloc_write_race.stderr +++ b/tests/fail/data_race/alloc_write_race.stderr @@ -4,7 +4,7 @@ error: Undefined Behavior: Data race detected between Write on thread ` LL | *pointer.load(Ordering::Relaxed) = 2; | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ Data race detected between Write on thread `` and Allocate on thread `` at ALLOC. The Write is here | -help: and Allocate on thread ``, which is here +help: and the Allocate on thread `` is here --> $DIR/alloc_write_race.rs:LL:CC | LL | .store(Box::into_raw(Box::::new_uninit()) as *mut usize, Ordering::Relaxed); diff --git a/tests/fail/data_race/atomic_read_na_write_race1.stderr b/tests/fail/data_race/atomic_read_na_write_race1.stderr index 15cfaef11c..a66f73bf57 100644 --- a/tests/fail/data_race/atomic_read_na_write_race1.stderr +++ b/tests/fail/data_race/atomic_read_na_write_race1.stderr @@ -4,7 +4,7 @@ error: Undefined Behavior: Data race detected between Atomic Load on thread `` and Write on thread `` at ALLOC. The Atomic Load is here | -help: and Write on thread ``, which is here +help: and the Write on thread `` is here --> $DIR/atomic_read_na_write_race1.rs:LL:CC | LL | *(c.0 as *mut usize) = 32; diff --git a/tests/fail/data_race/atomic_read_na_write_race2.stderr b/tests/fail/data_race/atomic_read_na_write_race2.stderr index d498914657..776ca8bc4d 100644 --- a/tests/fail/data_race/atomic_read_na_write_race2.stderr +++ b/tests/fail/data_race/atomic_read_na_write_race2.stderr @@ -4,7 +4,7 @@ error: Undefined Behavior: Data race detected between Write on thread ` LL | *atomic_ref.get_mut() = 32; | ^^^^^^^^^^^^^^^^^^^^^^^^^^ Data race detected between Write on thread `` and Atomic Load on thread `` at ALLOC. The Write is here | -help: and Atomic Load on thread ``, which is here +help: and the Atomic Load on thread `` is here --> $DIR/atomic_read_na_write_race2.rs:LL:CC | LL | atomic_ref.load(Ordering::SeqCst) diff --git a/tests/fail/data_race/atomic_write_na_read_race1.stderr b/tests/fail/data_race/atomic_write_na_read_race1.stderr index 5378ea6067..a59b449094 100644 --- a/tests/fail/data_race/atomic_write_na_read_race1.stderr +++ b/tests/fail/data_race/atomic_write_na_read_race1.stderr @@ -4,7 +4,7 @@ error: Undefined Behavior: Data race detected between Read on thread `` LL | *atomic_ref.get_mut() | ^^^^^^^^^^^^^^^^^^^^^ Data race detected between Read on thread `` and Atomic Store on thread `` at ALLOC. The Read is here | -help: and Atomic Store on thread ``, which is here +help: and the Atomic Store on thread `` is here --> $DIR/atomic_write_na_read_race1.rs:LL:CC | LL | atomic_ref.store(32, Ordering::SeqCst) diff --git a/tests/fail/data_race/atomic_write_na_read_race2.stderr b/tests/fail/data_race/atomic_write_na_read_race2.stderr index 3da2f624bf..5fb0821e54 100644 --- a/tests/fail/data_race/atomic_write_na_read_race2.stderr +++ b/tests/fail/data_race/atomic_write_na_read_race2.stderr @@ -4,7 +4,7 @@ error: Undefined Behavior: Data race detected between Atomic Store on thread `` and Read on thread `` at ALLOC. The Atomic Store is here | -help: and Read on thread ``, which is here +help: and the Read on thread `` is here --> $DIR/atomic_write_na_read_race2.rs:LL:CC | LL | let _val = *(c.0 as *mut usize); diff --git a/tests/fail/data_race/atomic_write_na_write_race1.stderr b/tests/fail/data_race/atomic_write_na_write_race1.stderr index 4d1dbc0b84..ec4e2da26b 100644 --- a/tests/fail/data_race/atomic_write_na_write_race1.stderr +++ b/tests/fail/data_race/atomic_write_na_write_race1.stderr @@ -4,7 +4,7 @@ error: Undefined Behavior: Data race detected between Atomic Store on thread `` and Write on thread `` at ALLOC. The Atomic Store is here | -help: and Write on thread ``, which is here +help: and the Write on thread `` is here --> $DIR/atomic_write_na_write_race1.rs:LL:CC | LL | *(c.0 as *mut usize) = 32; diff --git a/tests/fail/data_race/atomic_write_na_write_race2.stderr b/tests/fail/data_race/atomic_write_na_write_race2.stderr index cec68ba159..d532ce4db6 100644 --- a/tests/fail/data_race/atomic_write_na_write_race2.stderr +++ b/tests/fail/data_race/atomic_write_na_write_race2.stderr @@ -4,7 +4,7 @@ error: Undefined Behavior: Data race detected between Write on thread ` LL | *atomic_ref.get_mut() = 32; | ^^^^^^^^^^^^^^^^^^^^^^^^^^ Data race detected between Write on thread `` and Atomic Store on thread `` at ALLOC. The Write is here | -help: and Atomic Store on thread ``, which is here +help: and the Atomic Store on thread `` is here --> $DIR/atomic_write_na_write_race2.rs:LL:CC | LL | atomic_ref.store(64, Ordering::SeqCst); diff --git a/tests/fail/data_race/dangling_thread_async_race.stderr b/tests/fail/data_race/dangling_thread_async_race.stderr index 7ef38c6706..0eb51d7c95 100644 --- a/tests/fail/data_race/dangling_thread_async_race.stderr +++ b/tests/fail/data_race/dangling_thread_async_race.stderr @@ -4,7 +4,7 @@ error: Undefined Behavior: Data race detected between Write on thread ` LL | *c.0 = 64; | ^^^^^^^^^ Data race detected between Write on thread `` and Write on thread `` at ALLOC. The Write is here | -help: and Write on thread ``, which is here +help: and the Write on thread `` is here --> $DIR/dangling_thread_async_race.rs:LL:CC | LL | *c.0 = 32; diff --git a/tests/fail/data_race/dangling_thread_race.stderr b/tests/fail/data_race/dangling_thread_race.stderr index 3f556b6a8a..bd1de464ea 100644 --- a/tests/fail/data_race/dangling_thread_race.stderr +++ b/tests/fail/data_race/dangling_thread_race.stderr @@ -4,7 +4,7 @@ error: Undefined Behavior: Data race detected between Write on thread `main` and LL | *c.0 = 64; | ^^^^^^^^^ Data race detected between Write on thread `main` and Write on thread `` at ALLOC. The Write is here | -help: and Write on thread ``, which is here +help: and the Write on thread `` is here --> $DIR/dangling_thread_race.rs:LL:CC | LL | *c.0 = 32; diff --git a/tests/fail/data_race/dealloc_read_race1.stderr b/tests/fail/data_race/dealloc_read_race1.stderr index af2b2ed398..051ba69c97 100644 --- a/tests/fail/data_race/dealloc_read_race1.stderr +++ b/tests/fail/data_race/dealloc_read_race1.stderr @@ -9,7 +9,7 @@ LL | | std::mem::align_of::(), LL | | ); | |_____________^ Data race detected between Deallocate on thread `` and Read on thread `` at ALLOC. The Deallocate is here | -help: and Read on thread ``, which is here +help: and the Read on thread `` is here --> $DIR/dealloc_read_race1.rs:LL:CC | LL | let _val = *ptr.0; diff --git a/tests/fail/data_race/dealloc_read_race_stack.stderr b/tests/fail/data_race/dealloc_read_race_stack.stderr index d6b2a8a573..c147f33b95 100644 --- a/tests/fail/data_race/dealloc_read_race_stack.stderr +++ b/tests/fail/data_race/dealloc_read_race_stack.stderr @@ -4,7 +4,7 @@ error: Undefined Behavior: Data race detected between Deallocate on thread `` and Read on thread `` at ALLOC. The Deallocate is here | -help: and Read on thread ``, which is here +help: and the Read on thread `` is here --> $DIR/dealloc_read_race_stack.rs:LL:CC | LL | *pointer.load(Ordering::Acquire) diff --git a/tests/fail/data_race/dealloc_write_race1.stderr b/tests/fail/data_race/dealloc_write_race1.stderr index 6b235f651a..de71275261 100644 --- a/tests/fail/data_race/dealloc_write_race1.stderr +++ b/tests/fail/data_race/dealloc_write_race1.stderr @@ -9,7 +9,7 @@ LL | | std::mem::align_of::(), LL | | ); | |_____________^ Data race detected between Deallocate on thread `` and Write on thread `` at ALLOC. The Deallocate is here | -help: and Write on thread ``, which is here +help: and the Write on thread `` is here --> $DIR/dealloc_write_race1.rs:LL:CC | LL | *ptr.0 = 2; diff --git a/tests/fail/data_race/dealloc_write_race_stack.stderr b/tests/fail/data_race/dealloc_write_race_stack.stderr index 6e20a1aa5e..142c90b0b9 100644 --- a/tests/fail/data_race/dealloc_write_race_stack.stderr +++ b/tests/fail/data_race/dealloc_write_race_stack.stderr @@ -4,7 +4,7 @@ error: Undefined Behavior: Data race detected between Deallocate on thread `` and Write on thread `` at ALLOC. The Deallocate is here | -help: and Write on thread ``, which is here +help: and the Write on thread `` is here --> $DIR/dealloc_write_race_stack.rs:LL:CC | LL | *pointer.load(Ordering::Acquire) = 3; diff --git a/tests/fail/data_race/enable_after_join_to_main.stderr b/tests/fail/data_race/enable_after_join_to_main.stderr index 70d671ea7b..bb791300f5 100644 --- a/tests/fail/data_race/enable_after_join_to_main.stderr +++ b/tests/fail/data_race/enable_after_join_to_main.stderr @@ -4,7 +4,7 @@ error: Undefined Behavior: Data race detected between Write on thread ` LL | *c.0 = 64; | ^^^^^^^^^ Data race detected between Write on thread `` and Write on thread `` at ALLOC. The Write is here | -help: and Write on thread ``, which is here +help: and the Write on thread `` is here --> $DIR/enable_after_join_to_main.rs:LL:CC | LL | *c.0 = 32; diff --git a/tests/fail/data_race/fence_after_load.stderr b/tests/fail/data_race/fence_after_load.stderr index d073124df0..c44bc743ab 100644 --- a/tests/fail/data_race/fence_after_load.stderr +++ b/tests/fail/data_race/fence_after_load.stderr @@ -4,7 +4,7 @@ error: Undefined Behavior: Data race detected between Write on thread `main` and LL | unsafe { V = 2 } | ^^^^^ Data race detected between Write on thread `main` and Write on thread `` at ALLOC. The Write is here | -help: and Write on thread ``, which is here +help: and the Write on thread `` is here --> $DIR/fence_after_load.rs:LL:CC | LL | unsafe { V = 1 } diff --git a/tests/fail/data_race/read_write_race.stderr b/tests/fail/data_race/read_write_race.stderr index ae237a9890..ac08d2d790 100644 --- a/tests/fail/data_race/read_write_race.stderr +++ b/tests/fail/data_race/read_write_race.stderr @@ -4,7 +4,7 @@ error: Undefined Behavior: Data race detected between Write on thread ` LL | *c.0 = 64; | ^^^^^^^^^ Data race detected between Write on thread `` and Read on thread `` at ALLOC. The Write is here | -help: and Read on thread ``, which is here +help: and the Read on thread `` is here --> $DIR/read_write_race.rs:LL:CC | LL | let _val = *c.0; diff --git a/tests/fail/data_race/read_write_race_stack.stderr b/tests/fail/data_race/read_write_race_stack.stderr index ec01d9be6e..996f1ec6fa 100644 --- a/tests/fail/data_race/read_write_race_stack.stderr +++ b/tests/fail/data_race/read_write_race_stack.stderr @@ -4,7 +4,7 @@ error: Undefined Behavior: Data race detected between Read on thread `` LL | stack_var | ^^^^^^^^^ Data race detected between Read on thread `` and Write on thread `` at ALLOC. The Read is here | -help: and Write on thread ``, which is here +help: and the Write on thread `` is here --> $DIR/read_write_race_stack.rs:LL:CC | LL | *pointer.load(Ordering::Acquire) = 3; diff --git a/tests/fail/data_race/relax_acquire_race.stderr b/tests/fail/data_race/relax_acquire_race.stderr index 50768ebcdb..4c3021d24d 100644 --- a/tests/fail/data_race/relax_acquire_race.stderr +++ b/tests/fail/data_race/relax_acquire_race.stderr @@ -4,7 +4,7 @@ error: Undefined Behavior: Data race detected between Read on thread `` LL | *c.0 | ^^^^ Data race detected between Read on thread `` and Write on thread `` at ALLOC. The Read is here | -help: and Write on thread ``, which is here +help: and the Write on thread `` is here --> $DIR/relax_acquire_race.rs:LL:CC | LL | *c.0 = 1; diff --git a/tests/fail/data_race/release_seq_race.stderr b/tests/fail/data_race/release_seq_race.stderr index c3348ae0a3..ee0853dca6 100644 --- a/tests/fail/data_race/release_seq_race.stderr +++ b/tests/fail/data_race/release_seq_race.stderr @@ -4,7 +4,7 @@ error: Undefined Behavior: Data race detected between Read on thread `` LL | *c.0 | ^^^^ Data race detected between Read on thread `` and Write on thread `` at ALLOC. The Read is here | -help: and Write on thread ``, which is here +help: and the Write on thread `` is here --> $DIR/release_seq_race.rs:LL:CC | LL | *c.0 = 1; diff --git a/tests/fail/data_race/release_seq_race_same_thread.stderr b/tests/fail/data_race/release_seq_race_same_thread.stderr index 522226faa4..8156fa717e 100644 --- a/tests/fail/data_race/release_seq_race_same_thread.stderr +++ b/tests/fail/data_race/release_seq_race_same_thread.stderr @@ -4,7 +4,7 @@ error: Undefined Behavior: Data race detected between Read on thread `` LL | *c.0 | ^^^^ Data race detected between Read on thread `` and Write on thread `` at ALLOC. The Read is here | -help: and Write on thread ``, which is here +help: and the Write on thread `` is here --> $DIR/release_seq_race_same_thread.rs:LL:CC | LL | *c.0 = 1; diff --git a/tests/fail/data_race/rmw_race.stderr b/tests/fail/data_race/rmw_race.stderr index 672f08c422..c8089cf06d 100644 --- a/tests/fail/data_race/rmw_race.stderr +++ b/tests/fail/data_race/rmw_race.stderr @@ -4,7 +4,7 @@ error: Undefined Behavior: Data race detected between Read on thread `` LL | *c.0 | ^^^^ Data race detected between Read on thread `` and Write on thread `` at ALLOC. The Read is here | -help: and Write on thread ``, which is here +help: and the Write on thread `` is here --> $DIR/rmw_race.rs:LL:CC | LL | *c.0 = 1; diff --git a/tests/fail/data_race/stack_pop_race.stderr b/tests/fail/data_race/stack_pop_race.stderr index e21fe201d1..fb6f4470f8 100644 --- a/tests/fail/data_race/stack_pop_race.stderr +++ b/tests/fail/data_race/stack_pop_race.stderr @@ -4,7 +4,7 @@ error: Undefined Behavior: Data race detected between Deallocate on thread `main LL | } | ^ Data race detected between Deallocate on thread `main` and Read on thread `` at ALLOC. The Deallocate is here | -help: and Read on thread ``, which is here +help: and the Read on thread `` is here --> $DIR/stack_pop_race.rs:LL:CC | LL | let _val = unsafe { *ptr.0 }; diff --git a/tests/fail/data_race/write_write_race.stderr b/tests/fail/data_race/write_write_race.stderr index 1f67303e59..27218cf77d 100644 --- a/tests/fail/data_race/write_write_race.stderr +++ b/tests/fail/data_race/write_write_race.stderr @@ -4,7 +4,7 @@ error: Undefined Behavior: Data race detected between Write on thread ` LL | *c.0 = 64; | ^^^^^^^^^ Data race detected between Write on thread `` and Write on thread `` at ALLOC. The Write is here | -help: and Write on thread ``, which is here +help: and the Write on thread `` is here --> $DIR/write_write_race.rs:LL:CC | LL | *c.0 = 32; diff --git a/tests/fail/data_race/write_write_race_stack.stderr b/tests/fail/data_race/write_write_race_stack.stderr index 5b6481327c..9f3dcf6170 100644 --- a/tests/fail/data_race/write_write_race_stack.stderr +++ b/tests/fail/data_race/write_write_race_stack.stderr @@ -4,7 +4,7 @@ error: Undefined Behavior: Data race detected between Write on thread ` LL | stack_var = 1usize; | ^^^^^^^^^^^^^^^^^^ Data race detected between Write on thread `` and Write on thread `` at ALLOC. The Write is here | -help: and Write on thread ``, which is here +help: and the Write on thread `` is here --> $DIR/write_write_race_stack.rs:LL:CC | LL | *pointer.load(Ordering::Acquire) = 3; diff --git a/tests/fail/stacked_borrows/retag_data_race_read.stderr b/tests/fail/stacked_borrows/retag_data_race_read.stderr index 6f9ea26c08..ea2b8c8c0a 100644 --- a/tests/fail/stacked_borrows/retag_data_race_read.stderr +++ b/tests/fail/stacked_borrows/retag_data_race_read.stderr @@ -4,7 +4,7 @@ error: Undefined Behavior: Data race detected between Write on thread ` LL | *p = 5; | ^^^^^^ Data race detected between Write on thread `` and Read on thread `` at ALLOC. The Write is here | -help: and Read on thread ``, which is here +help: and the Read on thread `` is here --> $DIR/retag_data_race_read.rs:LL:CC | LL | let _r = &*p; diff --git a/tests/fail/stacked_borrows/retag_data_race_write.stderr b/tests/fail/stacked_borrows/retag_data_race_write.stderr index 44f17bd6ff..34170bb0b3 100644 --- a/tests/fail/stacked_borrows/retag_data_race_write.stderr +++ b/tests/fail/stacked_borrows/retag_data_race_write.stderr @@ -4,7 +4,7 @@ error: Undefined Behavior: Data race detected between Write on thread ` LL | *p = 5; | ^^^^^^ Data race detected between Write on thread `` and Write on thread `` at ALLOC. The Write is here | -help: and Write on thread ``, which is here +help: and the Write on thread `` is here --> $DIR/retag_data_race_write.rs:LL:CC | LL | let _r = &mut *p; From dad16694b01166a15f663d4c7e44c776735bf128 Mon Sep 17 00:00:00 2001 From: Ben Kimock Date: Thu, 22 Dec 2022 14:24:10 -0500 Subject: [PATCH 22/28] Add a (1) and (2) to the data race errors --- src/diagnostics.rs | 6 +++--- tests/fail/data_race/alloc_read_race.rs | 2 +- tests/fail/data_race/alloc_read_race.stderr | 6 +++--- tests/fail/data_race/alloc_write_race.rs | 2 +- tests/fail/data_race/alloc_write_race.stderr | 6 +++--- tests/fail/data_race/atomic_read_na_write_race1.rs | 2 +- tests/fail/data_race/atomic_read_na_write_race1.stderr | 6 +++--- tests/fail/data_race/atomic_read_na_write_race2.rs | 2 +- tests/fail/data_race/atomic_read_na_write_race2.stderr | 6 +++--- tests/fail/data_race/atomic_write_na_read_race1.rs | 2 +- tests/fail/data_race/atomic_write_na_read_race1.stderr | 6 +++--- tests/fail/data_race/atomic_write_na_read_race2.rs | 2 +- tests/fail/data_race/atomic_write_na_read_race2.stderr | 6 +++--- tests/fail/data_race/atomic_write_na_write_race1.rs | 2 +- tests/fail/data_race/atomic_write_na_write_race1.stderr | 6 +++--- tests/fail/data_race/atomic_write_na_write_race2.rs | 2 +- tests/fail/data_race/atomic_write_na_write_race2.stderr | 6 +++--- tests/fail/data_race/dangling_thread_async_race.rs | 2 +- tests/fail/data_race/dangling_thread_async_race.stderr | 6 +++--- tests/fail/data_race/dangling_thread_race.rs | 2 +- tests/fail/data_race/dangling_thread_race.stderr | 6 +++--- tests/fail/data_race/dealloc_read_race1.rs | 2 +- tests/fail/data_race/dealloc_read_race1.stderr | 6 +++--- tests/fail/data_race/dealloc_read_race2.rs | 2 +- tests/fail/data_race/dealloc_read_race_stack.rs | 2 +- tests/fail/data_race/dealloc_read_race_stack.stderr | 6 +++--- tests/fail/data_race/dealloc_write_race1.rs | 2 +- tests/fail/data_race/dealloc_write_race1.stderr | 6 +++--- tests/fail/data_race/dealloc_write_race2.rs | 2 +- tests/fail/data_race/dealloc_write_race_stack.rs | 2 +- tests/fail/data_race/dealloc_write_race_stack.stderr | 6 +++--- tests/fail/data_race/enable_after_join_to_main.rs | 2 +- tests/fail/data_race/enable_after_join_to_main.stderr | 6 +++--- tests/fail/data_race/fence_after_load.rs | 2 +- tests/fail/data_race/fence_after_load.stderr | 6 +++--- tests/fail/data_race/read_write_race.rs | 2 +- tests/fail/data_race/read_write_race.stderr | 6 +++--- tests/fail/data_race/read_write_race_stack.rs | 2 +- tests/fail/data_race/read_write_race_stack.stderr | 6 +++--- tests/fail/data_race/relax_acquire_race.rs | 2 +- tests/fail/data_race/relax_acquire_race.stderr | 6 +++--- tests/fail/data_race/release_seq_race.rs | 2 +- tests/fail/data_race/release_seq_race.stderr | 6 +++--- tests/fail/data_race/release_seq_race_same_thread.rs | 2 +- tests/fail/data_race/release_seq_race_same_thread.stderr | 6 +++--- tests/fail/data_race/rmw_race.rs | 2 +- tests/fail/data_race/rmw_race.stderr | 6 +++--- tests/fail/data_race/stack_pop_race.rs | 2 +- tests/fail/data_race/stack_pop_race.stderr | 6 +++--- tests/fail/data_race/write_write_race.rs | 2 +- tests/fail/data_race/write_write_race.stderr | 6 +++--- tests/fail/data_race/write_write_race_stack.rs | 2 +- tests/fail/data_race/write_write_race_stack.stderr | 6 +++--- tests/fail/stacked_borrows/retag_data_race_read.rs | 2 +- tests/fail/stacked_borrows/retag_data_race_read.stderr | 6 +++--- tests/fail/stacked_borrows/retag_data_race_write.rs | 2 +- tests/fail/stacked_borrows/retag_data_race_write.stderr | 6 +++--- 57 files changed, 113 insertions(+), 113 deletions(-) diff --git a/src/diagnostics.rs b/src/diagnostics.rs index 9f7be0f3b5..6f94d57bcc 100644 --- a/src/diagnostics.rs +++ b/src/diagnostics.rs @@ -69,8 +69,8 @@ impl fmt::Display for TerminationInfo { DataRace { ptr, op1, op2 } => write!( f, - "Data race detected between {} on {} and {} on {} at {:?}. The {} is here", - op1.action, op1.thread_info, op2.action, op2.thread_info, ptr, op1.action + "Data race detected between (1) {} on {} and (2) {} on {} at {ptr:?}. (1) just happened here", + op1.action, op1.thread_info, op2.action, op2.thread_info ), } } @@ -224,7 +224,7 @@ pub fn report_error<'tcx, 'mir>( vec![(None, format!("use Strict Provenance APIs (https://doc.rust-lang.org/nightly/std/ptr/index.html#strict-provenance, https://crates.io/crates/sptr) instead"))], DataRace { op2, .. } => vec![ - (Some(op2.span), format!("and the {} on {} is here", op2.action, op2.thread_info)), + (Some(op2.span), format!("and (2) occurred earlier here")), (None, format!("this indicates a bug in the program: it performed an invalid operation, and caused Undefined Behavior")), (None, format!("see https://doc.rust-lang.org/nightly/reference/behavior-considered-undefined.html for further information")), ], diff --git a/tests/fail/data_race/alloc_read_race.rs b/tests/fail/data_race/alloc_read_race.rs index 6040452a16..ba1d54e36c 100644 --- a/tests/fail/data_race/alloc_read_race.rs +++ b/tests/fail/data_race/alloc_read_race.rs @@ -37,7 +37,7 @@ pub fn main() { let pointer = &*ptr.0; // Note: could also error due to reading uninitialized memory, but the data-race detector triggers first. - *pointer.load(Ordering::Relaxed) //~ ERROR: Data race detected between Read on thread `` and Allocate on thread `` + *pointer.load(Ordering::Relaxed) //~ ERROR: Data race detected between (1) Read on thread `` and (2) Allocate on thread `` }); j1.join().unwrap(); diff --git a/tests/fail/data_race/alloc_read_race.stderr b/tests/fail/data_race/alloc_read_race.stderr index 9b487dacca..38b1ad3cfe 100644 --- a/tests/fail/data_race/alloc_read_race.stderr +++ b/tests/fail/data_race/alloc_read_race.stderr @@ -1,10 +1,10 @@ -error: Undefined Behavior: Data race detected between Read on thread `` and Allocate on thread `` at ALLOC. The Read is here +error: Undefined Behavior: Data race detected between (1) Read on thread `` and (2) Allocate on thread `` at ALLOC. (1) just happened here --> $DIR/alloc_read_race.rs:LL:CC | LL | *pointer.load(Ordering::Relaxed) - | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ Data race detected between Read on thread `` and Allocate on thread `` at ALLOC. The Read is here + | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ Data race detected between (1) Read on thread `` and (2) Allocate on thread `` at ALLOC. (1) just happened here | -help: and the Allocate on thread `` is here +help: and (2) occurred earlier here --> $DIR/alloc_read_race.rs:LL:CC | LL | pointer.store(Box::into_raw(Box::new_uninit()), Ordering::Relaxed); diff --git a/tests/fail/data_race/alloc_write_race.rs b/tests/fail/data_race/alloc_write_race.rs index 51d431b36f..9f85fb13ab 100644 --- a/tests/fail/data_race/alloc_write_race.rs +++ b/tests/fail/data_race/alloc_write_race.rs @@ -35,7 +35,7 @@ pub fn main() { let j2 = spawn(move || { let pointer = &*ptr.0; - *pointer.load(Ordering::Relaxed) = 2; //~ ERROR: Data race detected between Write on thread `` and Allocate on thread `` + *pointer.load(Ordering::Relaxed) = 2; //~ ERROR: Data race detected between (1) Write on thread `` and (2) Allocate on thread `` }); j1.join().unwrap(); diff --git a/tests/fail/data_race/alloc_write_race.stderr b/tests/fail/data_race/alloc_write_race.stderr index 7b1fcdf05b..473a694522 100644 --- a/tests/fail/data_race/alloc_write_race.stderr +++ b/tests/fail/data_race/alloc_write_race.stderr @@ -1,10 +1,10 @@ -error: Undefined Behavior: Data race detected between Write on thread `` and Allocate on thread `` at ALLOC. The Write is here +error: Undefined Behavior: Data race detected between (1) Write on thread `` and (2) Allocate on thread `` at ALLOC. (1) just happened here --> $DIR/alloc_write_race.rs:LL:CC | LL | *pointer.load(Ordering::Relaxed) = 2; - | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ Data race detected between Write on thread `` and Allocate on thread `` at ALLOC. The Write is here + | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ Data race detected between (1) Write on thread `` and (2) Allocate on thread `` at ALLOC. (1) just happened here | -help: and the Allocate on thread `` is here +help: and (2) occurred earlier here --> $DIR/alloc_write_race.rs:LL:CC | LL | .store(Box::into_raw(Box::::new_uninit()) as *mut usize, Ordering::Relaxed); diff --git a/tests/fail/data_race/atomic_read_na_write_race1.rs b/tests/fail/data_race/atomic_read_na_write_race1.rs index 79c6760b7c..4aa96de877 100644 --- a/tests/fail/data_race/atomic_read_na_write_race1.rs +++ b/tests/fail/data_race/atomic_read_na_write_race1.rs @@ -20,7 +20,7 @@ pub fn main() { }); let j2 = spawn(move || { - (&*c.0).load(Ordering::SeqCst) //~ ERROR: Data race detected between Atomic Load on thread `` and Write on thread `` + (&*c.0).load(Ordering::SeqCst) //~ ERROR: Data race detected between (1) Atomic Load on thread `` and (2) Write on thread `` }); j1.join().unwrap(); diff --git a/tests/fail/data_race/atomic_read_na_write_race1.stderr b/tests/fail/data_race/atomic_read_na_write_race1.stderr index a66f73bf57..565fba3280 100644 --- a/tests/fail/data_race/atomic_read_na_write_race1.stderr +++ b/tests/fail/data_race/atomic_read_na_write_race1.stderr @@ -1,10 +1,10 @@ -error: Undefined Behavior: Data race detected between Atomic Load on thread `` and Write on thread `` at ALLOC. The Atomic Load is here +error: Undefined Behavior: Data race detected between (1) Atomic Load on thread `` and (2) Write on thread `` at ALLOC. (1) just happened here --> $DIR/atomic_read_na_write_race1.rs:LL:CC | LL | (&*c.0).load(Ordering::SeqCst) - | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ Data race detected between Atomic Load on thread `` and Write on thread `` at ALLOC. The Atomic Load is here + | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ Data race detected between (1) Atomic Load on thread `` and (2) Write on thread `` at ALLOC. (1) just happened here | -help: and the Write on thread `` is here +help: and (2) occurred earlier here --> $DIR/atomic_read_na_write_race1.rs:LL:CC | LL | *(c.0 as *mut usize) = 32; diff --git a/tests/fail/data_race/atomic_read_na_write_race2.rs b/tests/fail/data_race/atomic_read_na_write_race2.rs index e069ac4ad6..135017d35b 100644 --- a/tests/fail/data_race/atomic_read_na_write_race2.rs +++ b/tests/fail/data_race/atomic_read_na_write_race2.rs @@ -23,7 +23,7 @@ pub fn main() { let j2 = spawn(move || { let atomic_ref = &mut *c.0; - *atomic_ref.get_mut() = 32; //~ ERROR: Data race detected between Write on thread `` and Atomic Load on thread `` + *atomic_ref.get_mut() = 32; //~ ERROR: Data race detected between (1) Write on thread `` and (2) Atomic Load on thread `` }); j1.join().unwrap(); diff --git a/tests/fail/data_race/atomic_read_na_write_race2.stderr b/tests/fail/data_race/atomic_read_na_write_race2.stderr index 776ca8bc4d..753a2961b4 100644 --- a/tests/fail/data_race/atomic_read_na_write_race2.stderr +++ b/tests/fail/data_race/atomic_read_na_write_race2.stderr @@ -1,10 +1,10 @@ -error: Undefined Behavior: Data race detected between Write on thread `` and Atomic Load on thread `` at ALLOC. The Write is here +error: Undefined Behavior: Data race detected between (1) Write on thread `` and (2) Atomic Load on thread `` at ALLOC. (1) just happened here --> $DIR/atomic_read_na_write_race2.rs:LL:CC | LL | *atomic_ref.get_mut() = 32; - | ^^^^^^^^^^^^^^^^^^^^^^^^^^ Data race detected between Write on thread `` and Atomic Load on thread `` at ALLOC. The Write is here + | ^^^^^^^^^^^^^^^^^^^^^^^^^^ Data race detected between (1) Write on thread `` and (2) Atomic Load on thread `` at ALLOC. (1) just happened here | -help: and the Atomic Load on thread `` is here +help: and (2) occurred earlier here --> $DIR/atomic_read_na_write_race2.rs:LL:CC | LL | atomic_ref.load(Ordering::SeqCst) diff --git a/tests/fail/data_race/atomic_write_na_read_race1.rs b/tests/fail/data_race/atomic_write_na_read_race1.rs index 9c025a0153..345b53ab5c 100644 --- a/tests/fail/data_race/atomic_write_na_read_race1.rs +++ b/tests/fail/data_race/atomic_write_na_read_race1.rs @@ -23,7 +23,7 @@ pub fn main() { let j2 = spawn(move || { let atomic_ref = &mut *c.0; - *atomic_ref.get_mut() //~ ERROR: Data race detected between Read on thread `` and Atomic Store on thread `` + *atomic_ref.get_mut() //~ ERROR: Data race detected between (1) Read on thread `` and (2) Atomic Store on thread `` }); j1.join().unwrap(); diff --git a/tests/fail/data_race/atomic_write_na_read_race1.stderr b/tests/fail/data_race/atomic_write_na_read_race1.stderr index a59b449094..5be597b7f5 100644 --- a/tests/fail/data_race/atomic_write_na_read_race1.stderr +++ b/tests/fail/data_race/atomic_write_na_read_race1.stderr @@ -1,10 +1,10 @@ -error: Undefined Behavior: Data race detected between Read on thread `` and Atomic Store on thread `` at ALLOC. The Read is here +error: Undefined Behavior: Data race detected between (1) Read on thread `` and (2) Atomic Store on thread `` at ALLOC. (1) just happened here --> $DIR/atomic_write_na_read_race1.rs:LL:CC | LL | *atomic_ref.get_mut() - | ^^^^^^^^^^^^^^^^^^^^^ Data race detected between Read on thread `` and Atomic Store on thread `` at ALLOC. The Read is here + | ^^^^^^^^^^^^^^^^^^^^^ Data race detected between (1) Read on thread `` and (2) Atomic Store on thread `` at ALLOC. (1) just happened here | -help: and the Atomic Store on thread `` is here +help: and (2) occurred earlier here --> $DIR/atomic_write_na_read_race1.rs:LL:CC | LL | atomic_ref.store(32, Ordering::SeqCst) diff --git a/tests/fail/data_race/atomic_write_na_read_race2.rs b/tests/fail/data_race/atomic_write_na_read_race2.rs index 30b3c48637..bc37f6442e 100644 --- a/tests/fail/data_race/atomic_write_na_read_race2.rs +++ b/tests/fail/data_race/atomic_write_na_read_race2.rs @@ -20,7 +20,7 @@ pub fn main() { }); let j2 = spawn(move || { - (&*c.0).store(32, Ordering::SeqCst); //~ ERROR: Data race detected between Atomic Store on thread `` and Read on thread `` + (&*c.0).store(32, Ordering::SeqCst); //~ ERROR: Data race detected between (1) Atomic Store on thread `` and (2) Read on thread `` }); j1.join().unwrap(); diff --git a/tests/fail/data_race/atomic_write_na_read_race2.stderr b/tests/fail/data_race/atomic_write_na_read_race2.stderr index 5fb0821e54..2c21337029 100644 --- a/tests/fail/data_race/atomic_write_na_read_race2.stderr +++ b/tests/fail/data_race/atomic_write_na_read_race2.stderr @@ -1,10 +1,10 @@ -error: Undefined Behavior: Data race detected between Atomic Store on thread `` and Read on thread `` at ALLOC. The Atomic Store is here +error: Undefined Behavior: Data race detected between (1) Atomic Store on thread `` and (2) Read on thread `` at ALLOC. (1) just happened here --> $DIR/atomic_write_na_read_race2.rs:LL:CC | LL | (&*c.0).store(32, Ordering::SeqCst); - | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ Data race detected between Atomic Store on thread `` and Read on thread `` at ALLOC. The Atomic Store is here + | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ Data race detected between (1) Atomic Store on thread `` and (2) Read on thread `` at ALLOC. (1) just happened here | -help: and the Read on thread `` is here +help: and (2) occurred earlier here --> $DIR/atomic_write_na_read_race2.rs:LL:CC | LL | let _val = *(c.0 as *mut usize); diff --git a/tests/fail/data_race/atomic_write_na_write_race1.rs b/tests/fail/data_race/atomic_write_na_write_race1.rs index 02b17cc57b..f1647ce4a9 100644 --- a/tests/fail/data_race/atomic_write_na_write_race1.rs +++ b/tests/fail/data_race/atomic_write_na_write_race1.rs @@ -20,7 +20,7 @@ pub fn main() { }); let j2 = spawn(move || { - (&*c.0).store(64, Ordering::SeqCst); //~ ERROR: Data race detected between Atomic Store on thread `` and Write on thread `` + (&*c.0).store(64, Ordering::SeqCst); //~ ERROR: Data race detected between (1) Atomic Store on thread `` and (2) Write on thread `` }); j1.join().unwrap(); diff --git a/tests/fail/data_race/atomic_write_na_write_race1.stderr b/tests/fail/data_race/atomic_write_na_write_race1.stderr index ec4e2da26b..b10724aa67 100644 --- a/tests/fail/data_race/atomic_write_na_write_race1.stderr +++ b/tests/fail/data_race/atomic_write_na_write_race1.stderr @@ -1,10 +1,10 @@ -error: Undefined Behavior: Data race detected between Atomic Store on thread `` and Write on thread `` at ALLOC. The Atomic Store is here +error: Undefined Behavior: Data race detected between (1) Atomic Store on thread `` and (2) Write on thread `` at ALLOC. (1) just happened here --> $DIR/atomic_write_na_write_race1.rs:LL:CC | LL | (&*c.0).store(64, Ordering::SeqCst); - | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ Data race detected between Atomic Store on thread `` and Write on thread `` at ALLOC. The Atomic Store is here + | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ Data race detected between (1) Atomic Store on thread `` and (2) Write on thread `` at ALLOC. (1) just happened here | -help: and the Write on thread `` is here +help: and (2) occurred earlier here --> $DIR/atomic_write_na_write_race1.rs:LL:CC | LL | *(c.0 as *mut usize) = 32; diff --git a/tests/fail/data_race/atomic_write_na_write_race2.rs b/tests/fail/data_race/atomic_write_na_write_race2.rs index b5f4966d88..343b46ea4e 100644 --- a/tests/fail/data_race/atomic_write_na_write_race2.rs +++ b/tests/fail/data_race/atomic_write_na_write_race2.rs @@ -23,7 +23,7 @@ pub fn main() { let j2 = spawn(move || { let atomic_ref = &mut *c.0; - *atomic_ref.get_mut() = 32; //~ ERROR: Data race detected between Write on thread `` and Atomic Store on thread `` + *atomic_ref.get_mut() = 32; //~ ERROR: Data race detected between (1) Write on thread `` and (2) Atomic Store on thread `` }); j1.join().unwrap(); diff --git a/tests/fail/data_race/atomic_write_na_write_race2.stderr b/tests/fail/data_race/atomic_write_na_write_race2.stderr index d532ce4db6..63393a2a8b 100644 --- a/tests/fail/data_race/atomic_write_na_write_race2.stderr +++ b/tests/fail/data_race/atomic_write_na_write_race2.stderr @@ -1,10 +1,10 @@ -error: Undefined Behavior: Data race detected between Write on thread `` and Atomic Store on thread `` at ALLOC. The Write is here +error: Undefined Behavior: Data race detected between (1) Write on thread `` and (2) Atomic Store on thread `` at ALLOC. (1) just happened here --> $DIR/atomic_write_na_write_race2.rs:LL:CC | LL | *atomic_ref.get_mut() = 32; - | ^^^^^^^^^^^^^^^^^^^^^^^^^^ Data race detected between Write on thread `` and Atomic Store on thread `` at ALLOC. The Write is here + | ^^^^^^^^^^^^^^^^^^^^^^^^^^ Data race detected between (1) Write on thread `` and (2) Atomic Store on thread `` at ALLOC. (1) just happened here | -help: and the Atomic Store on thread `` is here +help: and (2) occurred earlier here --> $DIR/atomic_write_na_write_race2.rs:LL:CC | LL | atomic_ref.store(64, Ordering::SeqCst); diff --git a/tests/fail/data_race/dangling_thread_async_race.rs b/tests/fail/data_race/dangling_thread_async_race.rs index 9922468e5f..eecb980e90 100644 --- a/tests/fail/data_race/dangling_thread_async_race.rs +++ b/tests/fail/data_race/dangling_thread_async_race.rs @@ -34,7 +34,7 @@ fn main() { let join2 = unsafe { spawn(move || { - *c.0 = 64; //~ ERROR: Data race detected between Write on thread `` and Write on thread `` + *c.0 = 64; //~ ERROR: Data race detected between (1) Write on thread `` and (2) Write on thread `` }) }; diff --git a/tests/fail/data_race/dangling_thread_async_race.stderr b/tests/fail/data_race/dangling_thread_async_race.stderr index 0eb51d7c95..26ab3c1673 100644 --- a/tests/fail/data_race/dangling_thread_async_race.stderr +++ b/tests/fail/data_race/dangling_thread_async_race.stderr @@ -1,10 +1,10 @@ -error: Undefined Behavior: Data race detected between Write on thread `` and Write on thread `` at ALLOC. The Write is here +error: Undefined Behavior: Data race detected between (1) Write on thread `` and (2) Write on thread `` at ALLOC. (1) just happened here --> $DIR/dangling_thread_async_race.rs:LL:CC | LL | *c.0 = 64; - | ^^^^^^^^^ Data race detected between Write on thread `` and Write on thread `` at ALLOC. The Write is here + | ^^^^^^^^^ Data race detected between (1) Write on thread `` and (2) Write on thread `` at ALLOC. (1) just happened here | -help: and the Write on thread `` is here +help: and (2) occurred earlier here --> $DIR/dangling_thread_async_race.rs:LL:CC | LL | *c.0 = 32; diff --git a/tests/fail/data_race/dangling_thread_race.rs b/tests/fail/data_race/dangling_thread_race.rs index 8c8a6ac87f..3ead4eedd7 100644 --- a/tests/fail/data_race/dangling_thread_race.rs +++ b/tests/fail/data_race/dangling_thread_race.rs @@ -33,6 +33,6 @@ fn main() { spawn(|| ()).join().unwrap(); unsafe { - *c.0 = 64; //~ ERROR: Data race detected between Write on thread `main` and Write on thread `` + *c.0 = 64; //~ ERROR: Data race detected between (1) Write on thread `main` and (2) Write on thread `` } } diff --git a/tests/fail/data_race/dangling_thread_race.stderr b/tests/fail/data_race/dangling_thread_race.stderr index bd1de464ea..23ccb33e9a 100644 --- a/tests/fail/data_race/dangling_thread_race.stderr +++ b/tests/fail/data_race/dangling_thread_race.stderr @@ -1,10 +1,10 @@ -error: Undefined Behavior: Data race detected between Write on thread `main` and Write on thread `` at ALLOC. The Write is here +error: Undefined Behavior: Data race detected between (1) Write on thread `main` and (2) Write on thread `` at ALLOC. (1) just happened here --> $DIR/dangling_thread_race.rs:LL:CC | LL | *c.0 = 64; - | ^^^^^^^^^ Data race detected between Write on thread `main` and Write on thread `` at ALLOC. The Write is here + | ^^^^^^^^^ Data race detected between (1) Write on thread `main` and (2) Write on thread `` at ALLOC. (1) just happened here | -help: and the Write on thread `` is here +help: and (2) occurred earlier here --> $DIR/dangling_thread_race.rs:LL:CC | LL | *c.0 = 32; diff --git a/tests/fail/data_race/dealloc_read_race1.rs b/tests/fail/data_race/dealloc_read_race1.rs index 8e1216f5bf..a94459ca4e 100644 --- a/tests/fail/data_race/dealloc_read_race1.rs +++ b/tests/fail/data_race/dealloc_read_race1.rs @@ -25,7 +25,7 @@ pub fn main() { let j2 = spawn(move || { __rust_dealloc( - //~^ ERROR: Data race detected between Deallocate on thread `` and Read on thread `` + //~^ ERROR: Data race detected between (1) Deallocate on thread `` and (2) Read on thread `` ptr.0 as *mut _, std::mem::size_of::(), std::mem::align_of::(), diff --git a/tests/fail/data_race/dealloc_read_race1.stderr b/tests/fail/data_race/dealloc_read_race1.stderr index 051ba69c97..baf3f85216 100644 --- a/tests/fail/data_race/dealloc_read_race1.stderr +++ b/tests/fail/data_race/dealloc_read_race1.stderr @@ -1,4 +1,4 @@ -error: Undefined Behavior: Data race detected between Deallocate on thread `` and Read on thread `` at ALLOC. The Deallocate is here +error: Undefined Behavior: Data race detected between (1) Deallocate on thread `` and (2) Read on thread `` at ALLOC. (1) just happened here --> $DIR/dealloc_read_race1.rs:LL:CC | LL | / __rust_dealloc( @@ -7,9 +7,9 @@ LL | | ptr.0 as *mut _, LL | | std::mem::size_of::(), LL | | std::mem::align_of::(), LL | | ); - | |_____________^ Data race detected between Deallocate on thread `` and Read on thread `` at ALLOC. The Deallocate is here + | |_____________^ Data race detected between (1) Deallocate on thread `` and (2) Read on thread `` at ALLOC. (1) just happened here | -help: and the Read on thread `` is here +help: and (2) occurred earlier here --> $DIR/dealloc_read_race1.rs:LL:CC | LL | let _val = *ptr.0; diff --git a/tests/fail/data_race/dealloc_read_race2.rs b/tests/fail/data_race/dealloc_read_race2.rs index 38f76af9de..6e6b6af5a6 100644 --- a/tests/fail/data_race/dealloc_read_race2.rs +++ b/tests/fail/data_race/dealloc_read_race2.rs @@ -28,7 +28,7 @@ pub fn main() { }); let j2 = spawn(move || { - // Also an error of the form: Data race detected between Read on thread `` and Deallocate on thread `` + // Also an error of the form: Data race detected between (1) Read on thread `` and (2) Deallocate on thread `` // but the invalid allocation is detected first. *ptr.0 //~ ERROR: dereferenced after this allocation got freed }); diff --git a/tests/fail/data_race/dealloc_read_race_stack.rs b/tests/fail/data_race/dealloc_read_race_stack.rs index 665e5ce4a1..ee3c66fb19 100644 --- a/tests/fail/data_race/dealloc_read_race_stack.rs +++ b/tests/fail/data_race/dealloc_read_race_stack.rs @@ -35,7 +35,7 @@ pub fn main() { sleep(Duration::from_millis(200)); // Now `stack_var` gets deallocated. - } //~ ERROR: Data race detected between Deallocate on thread `` and Read on thread `` + } //~ ERROR: Data race detected between (1) Deallocate on thread `` and (2) Read on thread `` }); let j2 = spawn(move || { diff --git a/tests/fail/data_race/dealloc_read_race_stack.stderr b/tests/fail/data_race/dealloc_read_race_stack.stderr index c147f33b95..94d95d44ac 100644 --- a/tests/fail/data_race/dealloc_read_race_stack.stderr +++ b/tests/fail/data_race/dealloc_read_race_stack.stderr @@ -1,10 +1,10 @@ -error: Undefined Behavior: Data race detected between Deallocate on thread `` and Read on thread `` at ALLOC. The Deallocate is here +error: Undefined Behavior: Data race detected between (1) Deallocate on thread `` and (2) Read on thread `` at ALLOC. (1) just happened here --> $DIR/dealloc_read_race_stack.rs:LL:CC | LL | } - | ^ Data race detected between Deallocate on thread `` and Read on thread `` at ALLOC. The Deallocate is here + | ^ Data race detected between (1) Deallocate on thread `` and (2) Read on thread `` at ALLOC. (1) just happened here | -help: and the Read on thread `` is here +help: and (2) occurred earlier here --> $DIR/dealloc_read_race_stack.rs:LL:CC | LL | *pointer.load(Ordering::Acquire) diff --git a/tests/fail/data_race/dealloc_write_race1.rs b/tests/fail/data_race/dealloc_write_race1.rs index b36c6b5ac0..041df291ed 100644 --- a/tests/fail/data_race/dealloc_write_race1.rs +++ b/tests/fail/data_race/dealloc_write_race1.rs @@ -24,7 +24,7 @@ pub fn main() { let j2 = spawn(move || { __rust_dealloc( - //~^ ERROR: Data race detected between Deallocate on thread `` and Write on thread `` + //~^ ERROR: Data race detected between (1) Deallocate on thread `` and (2) Write on thread `` ptr.0 as *mut _, std::mem::size_of::(), std::mem::align_of::(), diff --git a/tests/fail/data_race/dealloc_write_race1.stderr b/tests/fail/data_race/dealloc_write_race1.stderr index de71275261..cce2701a03 100644 --- a/tests/fail/data_race/dealloc_write_race1.stderr +++ b/tests/fail/data_race/dealloc_write_race1.stderr @@ -1,4 +1,4 @@ -error: Undefined Behavior: Data race detected between Deallocate on thread `` and Write on thread `` at ALLOC. The Deallocate is here +error: Undefined Behavior: Data race detected between (1) Deallocate on thread `` and (2) Write on thread `` at ALLOC. (1) just happened here --> $DIR/dealloc_write_race1.rs:LL:CC | LL | / __rust_dealloc( @@ -7,9 +7,9 @@ LL | | ptr.0 as *mut _, LL | | std::mem::size_of::(), LL | | std::mem::align_of::(), LL | | ); - | |_____________^ Data race detected between Deallocate on thread `` and Write on thread `` at ALLOC. The Deallocate is here + | |_____________^ Data race detected between (1) Deallocate on thread `` and (2) Write on thread `` at ALLOC. (1) just happened here | -help: and the Write on thread `` is here +help: and (2) occurred earlier here --> $DIR/dealloc_write_race1.rs:LL:CC | LL | *ptr.0 = 2; diff --git a/tests/fail/data_race/dealloc_write_race2.rs b/tests/fail/data_race/dealloc_write_race2.rs index 4af8b90462..b94fa8a14a 100644 --- a/tests/fail/data_race/dealloc_write_race2.rs +++ b/tests/fail/data_race/dealloc_write_race2.rs @@ -27,7 +27,7 @@ pub fn main() { }); let j2 = spawn(move || { - // Also an error of the form: Data race detected between Write on thread `` and Deallocate on thread `` + // Also an error of the form: Data race detected between (1) Write on thread `` and (2) Deallocate on thread `` // but the invalid allocation is detected first. *ptr.0 = 2; //~ ERROR: dereferenced after this allocation got freed }); diff --git a/tests/fail/data_race/dealloc_write_race_stack.rs b/tests/fail/data_race/dealloc_write_race_stack.rs index f851ce9578..78f11c14fb 100644 --- a/tests/fail/data_race/dealloc_write_race_stack.rs +++ b/tests/fail/data_race/dealloc_write_race_stack.rs @@ -35,7 +35,7 @@ pub fn main() { sleep(Duration::from_millis(200)); // Now `stack_var` gets deallocated. - } //~ ERROR: Data race detected between Deallocate on thread `` and Write on thread `` + } //~ ERROR: Data race detected between (1) Deallocate on thread `` and (2) Write on thread `` }); let j2 = spawn(move || { diff --git a/tests/fail/data_race/dealloc_write_race_stack.stderr b/tests/fail/data_race/dealloc_write_race_stack.stderr index 142c90b0b9..0f60926fb5 100644 --- a/tests/fail/data_race/dealloc_write_race_stack.stderr +++ b/tests/fail/data_race/dealloc_write_race_stack.stderr @@ -1,10 +1,10 @@ -error: Undefined Behavior: Data race detected between Deallocate on thread `` and Write on thread `` at ALLOC. The Deallocate is here +error: Undefined Behavior: Data race detected between (1) Deallocate on thread `` and (2) Write on thread `` at ALLOC. (1) just happened here --> $DIR/dealloc_write_race_stack.rs:LL:CC | LL | } - | ^ Data race detected between Deallocate on thread `` and Write on thread `` at ALLOC. The Deallocate is here + | ^ Data race detected between (1) Deallocate on thread `` and (2) Write on thread `` at ALLOC. (1) just happened here | -help: and the Write on thread `` is here +help: and (2) occurred earlier here --> $DIR/dealloc_write_race_stack.rs:LL:CC | LL | *pointer.load(Ordering::Acquire) = 3; diff --git a/tests/fail/data_race/enable_after_join_to_main.rs b/tests/fail/data_race/enable_after_join_to_main.rs index 27aa16a122..3d47b1accb 100644 --- a/tests/fail/data_race/enable_after_join_to_main.rs +++ b/tests/fail/data_race/enable_after_join_to_main.rs @@ -30,7 +30,7 @@ pub fn main() { }); let j2 = spawn(move || { - *c.0 = 64; //~ ERROR: Data race detected between Write on thread `` and Write on thread `` + *c.0 = 64; //~ ERROR: Data race detected between (1) Write on thread `` and (2) Write on thread `` }); j1.join().unwrap(); diff --git a/tests/fail/data_race/enable_after_join_to_main.stderr b/tests/fail/data_race/enable_after_join_to_main.stderr index bb791300f5..e608342f8d 100644 --- a/tests/fail/data_race/enable_after_join_to_main.stderr +++ b/tests/fail/data_race/enable_after_join_to_main.stderr @@ -1,10 +1,10 @@ -error: Undefined Behavior: Data race detected between Write on thread `` and Write on thread `` at ALLOC. The Write is here +error: Undefined Behavior: Data race detected between (1) Write on thread `` and (2) Write on thread `` at ALLOC. (1) just happened here --> $DIR/enable_after_join_to_main.rs:LL:CC | LL | *c.0 = 64; - | ^^^^^^^^^ Data race detected between Write on thread `` and Write on thread `` at ALLOC. The Write is here + | ^^^^^^^^^ Data race detected between (1) Write on thread `` and (2) Write on thread `` at ALLOC. (1) just happened here | -help: and the Write on thread `` is here +help: and (2) occurred earlier here --> $DIR/enable_after_join_to_main.rs:LL:CC | LL | *c.0 = 32; diff --git a/tests/fail/data_race/fence_after_load.rs b/tests/fail/data_race/fence_after_load.rs index 4d436d51f9..8de61d14ac 100644 --- a/tests/fail/data_race/fence_after_load.rs +++ b/tests/fail/data_race/fence_after_load.rs @@ -20,5 +20,5 @@ fn main() { // The fence is useless, since it did not happen-after the `store` in the other thread. // Hence this is a data race. // Also see https://github.com/rust-lang/miri/issues/2192. - unsafe { V = 2 } //~ERROR: Data race detected between Write on thread `main` and Write on thread `` + unsafe { V = 2 } //~ERROR: Data race detected between (1) Write on thread `main` and (2) Write on thread `` } diff --git a/tests/fail/data_race/fence_after_load.stderr b/tests/fail/data_race/fence_after_load.stderr index c44bc743ab..9c1d92d14f 100644 --- a/tests/fail/data_race/fence_after_load.stderr +++ b/tests/fail/data_race/fence_after_load.stderr @@ -1,10 +1,10 @@ -error: Undefined Behavior: Data race detected between Write on thread `main` and Write on thread `` at ALLOC. The Write is here +error: Undefined Behavior: Data race detected between (1) Write on thread `main` and (2) Write on thread `` at ALLOC. (1) just happened here --> $DIR/fence_after_load.rs:LL:CC | LL | unsafe { V = 2 } - | ^^^^^ Data race detected between Write on thread `main` and Write on thread `` at ALLOC. The Write is here + | ^^^^^ Data race detected between (1) Write on thread `main` and (2) Write on thread `` at ALLOC. (1) just happened here | -help: and the Write on thread `` is here +help: and (2) occurred earlier here --> $DIR/fence_after_load.rs:LL:CC | LL | unsafe { V = 1 } diff --git a/tests/fail/data_race/read_write_race.rs b/tests/fail/data_race/read_write_race.rs index b26ec6c414..f18d2da831 100644 --- a/tests/fail/data_race/read_write_race.rs +++ b/tests/fail/data_race/read_write_race.rs @@ -19,7 +19,7 @@ pub fn main() { }); let j2 = spawn(move || { - *c.0 = 64; //~ ERROR: Data race detected between Write on thread `` and Read on thread `` + *c.0 = 64; //~ ERROR: Data race detected between (1) Write on thread `` and (2) Read on thread `` }); j1.join().unwrap(); diff --git a/tests/fail/data_race/read_write_race.stderr b/tests/fail/data_race/read_write_race.stderr index ac08d2d790..e31bc5fbb4 100644 --- a/tests/fail/data_race/read_write_race.stderr +++ b/tests/fail/data_race/read_write_race.stderr @@ -1,10 +1,10 @@ -error: Undefined Behavior: Data race detected between Write on thread `` and Read on thread `` at ALLOC. The Write is here +error: Undefined Behavior: Data race detected between (1) Write on thread `` and (2) Read on thread `` at ALLOC. (1) just happened here --> $DIR/read_write_race.rs:LL:CC | LL | *c.0 = 64; - | ^^^^^^^^^ Data race detected between Write on thread `` and Read on thread `` at ALLOC. The Write is here + | ^^^^^^^^^ Data race detected between (1) Write on thread `` and (2) Read on thread `` at ALLOC. (1) just happened here | -help: and the Read on thread `` is here +help: and (2) occurred earlier here --> $DIR/read_write_race.rs:LL:CC | LL | let _val = *c.0; diff --git a/tests/fail/data_race/read_write_race_stack.rs b/tests/fail/data_race/read_write_race_stack.rs index 2fbac17399..acbe2a09e9 100644 --- a/tests/fail/data_race/read_write_race_stack.rs +++ b/tests/fail/data_race/read_write_race_stack.rs @@ -42,7 +42,7 @@ pub fn main() { sleep(Duration::from_millis(200)); - stack_var //~ ERROR: Data race detected between Read on thread `` and Write on thread `` + stack_var //~ ERROR: Data race detected between (1) Read on thread `` and (2) Write on thread `` }); let j2 = spawn(move || { diff --git a/tests/fail/data_race/read_write_race_stack.stderr b/tests/fail/data_race/read_write_race_stack.stderr index 996f1ec6fa..09b704e063 100644 --- a/tests/fail/data_race/read_write_race_stack.stderr +++ b/tests/fail/data_race/read_write_race_stack.stderr @@ -1,10 +1,10 @@ -error: Undefined Behavior: Data race detected between Read on thread `` and Write on thread `` at ALLOC. The Read is here +error: Undefined Behavior: Data race detected between (1) Read on thread `` and (2) Write on thread `` at ALLOC. (1) just happened here --> $DIR/read_write_race_stack.rs:LL:CC | LL | stack_var - | ^^^^^^^^^ Data race detected between Read on thread `` and Write on thread `` at ALLOC. The Read is here + | ^^^^^^^^^ Data race detected between (1) Read on thread `` and (2) Write on thread `` at ALLOC. (1) just happened here | -help: and the Write on thread `` is here +help: and (2) occurred earlier here --> $DIR/read_write_race_stack.rs:LL:CC | LL | *pointer.load(Ordering::Acquire) = 3; diff --git a/tests/fail/data_race/relax_acquire_race.rs b/tests/fail/data_race/relax_acquire_race.rs index 24040a9496..cc49e8a04f 100644 --- a/tests/fail/data_race/relax_acquire_race.rs +++ b/tests/fail/data_race/relax_acquire_race.rs @@ -37,7 +37,7 @@ pub fn main() { let j3 = spawn(move || { if SYNC.load(Ordering::Acquire) == 2 { - *c.0 //~ ERROR: Data race detected between Read on thread `` and Write on thread `` + *c.0 //~ ERROR: Data race detected between (1) Read on thread `` and (2) Write on thread `` } else { 0 } diff --git a/tests/fail/data_race/relax_acquire_race.stderr b/tests/fail/data_race/relax_acquire_race.stderr index 4c3021d24d..a996fc3500 100644 --- a/tests/fail/data_race/relax_acquire_race.stderr +++ b/tests/fail/data_race/relax_acquire_race.stderr @@ -1,10 +1,10 @@ -error: Undefined Behavior: Data race detected between Read on thread `` and Write on thread `` at ALLOC. The Read is here +error: Undefined Behavior: Data race detected between (1) Read on thread `` and (2) Write on thread `` at ALLOC. (1) just happened here --> $DIR/relax_acquire_race.rs:LL:CC | LL | *c.0 - | ^^^^ Data race detected between Read on thread `` and Write on thread `` at ALLOC. The Read is here + | ^^^^ Data race detected between (1) Read on thread `` and (2) Write on thread `` at ALLOC. (1) just happened here | -help: and the Write on thread `` is here +help: and (2) occurred earlier here --> $DIR/relax_acquire_race.rs:LL:CC | LL | *c.0 = 1; diff --git a/tests/fail/data_race/release_seq_race.rs b/tests/fail/data_race/release_seq_race.rs index 2d7246858e..ba917cd0dd 100644 --- a/tests/fail/data_race/release_seq_race.rs +++ b/tests/fail/data_race/release_seq_race.rs @@ -41,7 +41,7 @@ pub fn main() { let j3 = spawn(move || { sleep(Duration::from_millis(500)); if SYNC.load(Ordering::Acquire) == 3 { - *c.0 //~ ERROR: Data race detected between Read on thread `` and Write on thread `` + *c.0 //~ ERROR: Data race detected between (1) Read on thread `` and (2) Write on thread `` } else { 0 } diff --git a/tests/fail/data_race/release_seq_race.stderr b/tests/fail/data_race/release_seq_race.stderr index ee0853dca6..8b27a18856 100644 --- a/tests/fail/data_race/release_seq_race.stderr +++ b/tests/fail/data_race/release_seq_race.stderr @@ -1,10 +1,10 @@ -error: Undefined Behavior: Data race detected between Read on thread `` and Write on thread `` at ALLOC. The Read is here +error: Undefined Behavior: Data race detected between (1) Read on thread `` and (2) Write on thread `` at ALLOC. (1) just happened here --> $DIR/release_seq_race.rs:LL:CC | LL | *c.0 - | ^^^^ Data race detected between Read on thread `` and Write on thread `` at ALLOC. The Read is here + | ^^^^ Data race detected between (1) Read on thread `` and (2) Write on thread `` at ALLOC. (1) just happened here | -help: and the Write on thread `` is here +help: and (2) occurred earlier here --> $DIR/release_seq_race.rs:LL:CC | LL | *c.0 = 1; diff --git a/tests/fail/data_race/release_seq_race_same_thread.rs b/tests/fail/data_race/release_seq_race_same_thread.rs index 0f974e1c56..c34f4ebe42 100644 --- a/tests/fail/data_race/release_seq_race_same_thread.rs +++ b/tests/fail/data_race/release_seq_race_same_thread.rs @@ -37,7 +37,7 @@ pub fn main() { let j2 = spawn(move || { if SYNC.load(Ordering::Acquire) == 2 { - *c.0 //~ ERROR: Data race detected between Read on thread `` and Write on thread `` + *c.0 //~ ERROR: Data race detected between (1) Read on thread `` and (2) Write on thread `` } else { 0 } diff --git a/tests/fail/data_race/release_seq_race_same_thread.stderr b/tests/fail/data_race/release_seq_race_same_thread.stderr index 8156fa717e..a3561b1a26 100644 --- a/tests/fail/data_race/release_seq_race_same_thread.stderr +++ b/tests/fail/data_race/release_seq_race_same_thread.stderr @@ -1,10 +1,10 @@ -error: Undefined Behavior: Data race detected between Read on thread `` and Write on thread `` at ALLOC. The Read is here +error: Undefined Behavior: Data race detected between (1) Read on thread `` and (2) Write on thread `` at ALLOC. (1) just happened here --> $DIR/release_seq_race_same_thread.rs:LL:CC | LL | *c.0 - | ^^^^ Data race detected between Read on thread `` and Write on thread `` at ALLOC. The Read is here + | ^^^^ Data race detected between (1) Read on thread `` and (2) Write on thread `` at ALLOC. (1) just happened here | -help: and the Write on thread `` is here +help: and (2) occurred earlier here --> $DIR/release_seq_race_same_thread.rs:LL:CC | LL | *c.0 = 1; diff --git a/tests/fail/data_race/rmw_race.rs b/tests/fail/data_race/rmw_race.rs index 2d13da30b4..f96ebef284 100644 --- a/tests/fail/data_race/rmw_race.rs +++ b/tests/fail/data_race/rmw_race.rs @@ -38,7 +38,7 @@ pub fn main() { let j3 = spawn(move || { if SYNC.load(Ordering::Acquire) == 3 { - *c.0 //~ ERROR: Data race detected between Read on thread `` and Write on thread `` + *c.0 //~ ERROR: Data race detected between (1) Read on thread `` and (2) Write on thread `` } else { 0 } diff --git a/tests/fail/data_race/rmw_race.stderr b/tests/fail/data_race/rmw_race.stderr index c8089cf06d..9448d9059b 100644 --- a/tests/fail/data_race/rmw_race.stderr +++ b/tests/fail/data_race/rmw_race.stderr @@ -1,10 +1,10 @@ -error: Undefined Behavior: Data race detected between Read on thread `` and Write on thread `` at ALLOC. The Read is here +error: Undefined Behavior: Data race detected between (1) Read on thread `` and (2) Write on thread `` at ALLOC. (1) just happened here --> $DIR/rmw_race.rs:LL:CC | LL | *c.0 - | ^^^^ Data race detected between Read on thread `` and Write on thread `` at ALLOC. The Read is here + | ^^^^ Data race detected between (1) Read on thread `` and (2) Write on thread `` at ALLOC. (1) just happened here | -help: and the Write on thread `` is here +help: and (2) occurred earlier here --> $DIR/rmw_race.rs:LL:CC | LL | *c.0 = 1; diff --git a/tests/fail/data_race/stack_pop_race.rs b/tests/fail/data_race/stack_pop_race.rs index cf5c2ed81c..fb3ec5a22b 100644 --- a/tests/fail/data_race/stack_pop_race.rs +++ b/tests/fail/data_race/stack_pop_race.rs @@ -21,4 +21,4 @@ fn race(local: i32) { // Deallocating the local (when `main` returns) // races with the read in the other thread. // Make sure the error points at this function's end, not just the call site. -} //~ERROR: Data race detected between Deallocate on thread `main` and Read on thread `` +} //~ERROR: Data race detected between (1) Deallocate on thread `main` and (2) Read on thread `` diff --git a/tests/fail/data_race/stack_pop_race.stderr b/tests/fail/data_race/stack_pop_race.stderr index fb6f4470f8..0e2e202900 100644 --- a/tests/fail/data_race/stack_pop_race.stderr +++ b/tests/fail/data_race/stack_pop_race.stderr @@ -1,10 +1,10 @@ -error: Undefined Behavior: Data race detected between Deallocate on thread `main` and Read on thread `` at ALLOC. The Deallocate is here +error: Undefined Behavior: Data race detected between (1) Deallocate on thread `main` and (2) Read on thread `` at ALLOC. (1) just happened here --> $DIR/stack_pop_race.rs:LL:CC | LL | } - | ^ Data race detected between Deallocate on thread `main` and Read on thread `` at ALLOC. The Deallocate is here + | ^ Data race detected between (1) Deallocate on thread `main` and (2) Read on thread `` at ALLOC. (1) just happened here | -help: and the Read on thread `` is here +help: and (2) occurred earlier here --> $DIR/stack_pop_race.rs:LL:CC | LL | let _val = unsafe { *ptr.0 }; diff --git a/tests/fail/data_race/write_write_race.rs b/tests/fail/data_race/write_write_race.rs index 60e9ac2ac6..fe02d02f9d 100644 --- a/tests/fail/data_race/write_write_race.rs +++ b/tests/fail/data_race/write_write_race.rs @@ -19,7 +19,7 @@ pub fn main() { }); let j2 = spawn(move || { - *c.0 = 64; //~ ERROR: Data race detected between Write on thread `` and Write on thread `` + *c.0 = 64; //~ ERROR: Data race detected between (1) Write on thread `` and (2) Write on thread `` }); j1.join().unwrap(); diff --git a/tests/fail/data_race/write_write_race.stderr b/tests/fail/data_race/write_write_race.stderr index 27218cf77d..dcc94a9d25 100644 --- a/tests/fail/data_race/write_write_race.stderr +++ b/tests/fail/data_race/write_write_race.stderr @@ -1,10 +1,10 @@ -error: Undefined Behavior: Data race detected between Write on thread `` and Write on thread `` at ALLOC. The Write is here +error: Undefined Behavior: Data race detected between (1) Write on thread `` and (2) Write on thread `` at ALLOC. (1) just happened here --> $DIR/write_write_race.rs:LL:CC | LL | *c.0 = 64; - | ^^^^^^^^^ Data race detected between Write on thread `` and Write on thread `` at ALLOC. The Write is here + | ^^^^^^^^^ Data race detected between (1) Write on thread `` and (2) Write on thread `` at ALLOC. (1) just happened here | -help: and the Write on thread `` is here +help: and (2) occurred earlier here --> $DIR/write_write_race.rs:LL:CC | LL | *c.0 = 32; diff --git a/tests/fail/data_race/write_write_race_stack.rs b/tests/fail/data_race/write_write_race_stack.rs index 0a29dc13cb..c1c1b1fa6e 100644 --- a/tests/fail/data_race/write_write_race_stack.rs +++ b/tests/fail/data_race/write_write_race_stack.rs @@ -39,7 +39,7 @@ pub fn main() { sleep(Duration::from_millis(200)); - stack_var = 1usize; //~ ERROR: Data race detected between Write on thread `` and Write on thread `` + stack_var = 1usize; //~ ERROR: Data race detected between (1) Write on thread `` and (2) Write on thread `` // read to silence errors stack_var diff --git a/tests/fail/data_race/write_write_race_stack.stderr b/tests/fail/data_race/write_write_race_stack.stderr index 9f3dcf6170..8b0250593d 100644 --- a/tests/fail/data_race/write_write_race_stack.stderr +++ b/tests/fail/data_race/write_write_race_stack.stderr @@ -1,10 +1,10 @@ -error: Undefined Behavior: Data race detected between Write on thread `` and Write on thread `` at ALLOC. The Write is here +error: Undefined Behavior: Data race detected between (1) Write on thread `` and (2) Write on thread `` at ALLOC. (1) just happened here --> $DIR/write_write_race_stack.rs:LL:CC | LL | stack_var = 1usize; - | ^^^^^^^^^^^^^^^^^^ Data race detected between Write on thread `` and Write on thread `` at ALLOC. The Write is here + | ^^^^^^^^^^^^^^^^^^ Data race detected between (1) Write on thread `` and (2) Write on thread `` at ALLOC. (1) just happened here | -help: and the Write on thread `` is here +help: and (2) occurred earlier here --> $DIR/write_write_race_stack.rs:LL:CC | LL | *pointer.load(Ordering::Acquire) = 3; diff --git a/tests/fail/stacked_borrows/retag_data_race_read.rs b/tests/fail/stacked_borrows/retag_data_race_read.rs index 309d7a22be..8c97a31c32 100644 --- a/tests/fail/stacked_borrows/retag_data_race_read.rs +++ b/tests/fail/stacked_borrows/retag_data_race_read.rs @@ -15,7 +15,7 @@ fn thread_1(p: SendPtr) { fn thread_2(p: SendPtr) { let p = p.0; unsafe { - *p = 5; //~ ERROR: Data race detected between Write on thread `` and Read on thread `` + *p = 5; //~ ERROR: Data race detected between (1) Write on thread `` and (2) Read on thread `` } } diff --git a/tests/fail/stacked_borrows/retag_data_race_read.stderr b/tests/fail/stacked_borrows/retag_data_race_read.stderr index ea2b8c8c0a..790fd51ec3 100644 --- a/tests/fail/stacked_borrows/retag_data_race_read.stderr +++ b/tests/fail/stacked_borrows/retag_data_race_read.stderr @@ -1,10 +1,10 @@ -error: Undefined Behavior: Data race detected between Write on thread `` and Read on thread `` at ALLOC. The Write is here +error: Undefined Behavior: Data race detected between (1) Write on thread `` and (2) Read on thread `` at ALLOC. (1) just happened here --> $DIR/retag_data_race_read.rs:LL:CC | LL | *p = 5; - | ^^^^^^ Data race detected between Write on thread `` and Read on thread `` at ALLOC. The Write is here + | ^^^^^^ Data race detected between (1) Write on thread `` and (2) Read on thread `` at ALLOC. (1) just happened here | -help: and the Read on thread `` is here +help: and (2) occurred earlier here --> $DIR/retag_data_race_read.rs:LL:CC | LL | let _r = &*p; diff --git a/tests/fail/stacked_borrows/retag_data_race_write.rs b/tests/fail/stacked_borrows/retag_data_race_write.rs index 9368a0a919..c1dded40d3 100644 --- a/tests/fail/stacked_borrows/retag_data_race_write.rs +++ b/tests/fail/stacked_borrows/retag_data_race_write.rs @@ -15,7 +15,7 @@ fn thread_1(p: SendPtr) { fn thread_2(p: SendPtr) { let p = p.0; unsafe { - *p = 5; //~ ERROR: Data race detected between Write on thread `` and Write on thread `` + *p = 5; //~ ERROR: Data race detected between (1) Write on thread `` and (2) Write on thread `` } } diff --git a/tests/fail/stacked_borrows/retag_data_race_write.stderr b/tests/fail/stacked_borrows/retag_data_race_write.stderr index 34170bb0b3..c5b8b4c41f 100644 --- a/tests/fail/stacked_borrows/retag_data_race_write.stderr +++ b/tests/fail/stacked_borrows/retag_data_race_write.stderr @@ -1,10 +1,10 @@ -error: Undefined Behavior: Data race detected between Write on thread `` and Write on thread `` at ALLOC. The Write is here +error: Undefined Behavior: Data race detected between (1) Write on thread `` and (2) Write on thread `` at ALLOC. (1) just happened here --> $DIR/retag_data_race_write.rs:LL:CC | LL | *p = 5; - | ^^^^^^ Data race detected between Write on thread `` and Write on thread `` at ALLOC. The Write is here + | ^^^^^^ Data race detected between (1) Write on thread `` and (2) Write on thread `` at ALLOC. (1) just happened here | -help: and the Write on thread `` is here +help: and (2) occurred earlier here --> $DIR/retag_data_race_write.rs:LL:CC | LL | let _r = &mut *p; From def32e1c7d2e83bce6e3281e6da43c248af9c067 Mon Sep 17 00:00:00 2001 From: Ralf Jung Date: Fri, 23 Dec 2022 15:39:14 +0100 Subject: [PATCH 23/28] attempt to clarify what the backtrace belongs to when there could be ambiguity --- src/diagnostics.rs | 5 ++++- tests/fail/box-cell-alias.stderr | 2 +- tests/fail/data_race/alloc_read_race.stderr | 2 +- tests/fail/data_race/alloc_write_race.stderr | 2 +- tests/fail/data_race/atomic_read_na_write_race1.stderr | 2 +- tests/fail/data_race/atomic_read_na_write_race2.stderr | 2 +- tests/fail/data_race/atomic_write_na_read_race1.stderr | 2 +- tests/fail/data_race/atomic_write_na_read_race2.stderr | 2 +- tests/fail/data_race/atomic_write_na_write_race1.stderr | 2 +- tests/fail/data_race/atomic_write_na_write_race2.stderr | 2 +- tests/fail/data_race/dangling_thread_async_race.stderr | 2 +- tests/fail/data_race/dangling_thread_race.stderr | 2 +- tests/fail/data_race/dealloc_read_race1.stderr | 2 +- tests/fail/data_race/dealloc_read_race_stack.stderr | 2 +- tests/fail/data_race/dealloc_write_race1.stderr | 2 +- tests/fail/data_race/dealloc_write_race_stack.stderr | 2 +- tests/fail/data_race/enable_after_join_to_main.stderr | 2 +- tests/fail/data_race/fence_after_load.stderr | 2 +- tests/fail/data_race/read_write_race.stderr | 2 +- tests/fail/data_race/read_write_race_stack.stderr | 2 +- tests/fail/data_race/relax_acquire_race.stderr | 2 +- tests/fail/data_race/release_seq_race.stderr | 2 +- tests/fail/data_race/release_seq_race_same_thread.stderr | 2 +- tests/fail/data_race/rmw_race.stderr | 2 +- tests/fail/data_race/stack_pop_race.stderr | 2 +- tests/fail/data_race/write_write_race.stderr | 2 +- tests/fail/data_race/write_write_race_stack.stderr | 2 +- tests/fail/function_calls/exported_symbol_clashing.stderr | 2 +- .../fail/function_calls/exported_symbol_shim_clashing.stderr | 2 +- tests/fail/stacked_borrows/alias_through_mutation.stderr | 2 +- tests/fail/stacked_borrows/aliasing_mut1.stderr | 2 +- tests/fail/stacked_borrows/aliasing_mut2.stderr | 2 +- tests/fail/stacked_borrows/aliasing_mut3.stderr | 2 +- tests/fail/stacked_borrows/aliasing_mut4.stderr | 2 +- tests/fail/stacked_borrows/box_exclusive_violation1.stderr | 2 +- tests/fail/stacked_borrows/box_noalias_violation.stderr | 2 +- tests/fail/stacked_borrows/buggy_as_mut_slice.stderr | 2 +- tests/fail/stacked_borrows/buggy_split_at_mut.stderr | 2 +- .../stacked_borrows/disable_mut_does_not_merge_srw.stderr | 2 +- tests/fail/stacked_borrows/fnentry_invalidation.stderr | 2 +- tests/fail/stacked_borrows/fnentry_invalidation2.stderr | 2 +- tests/fail/stacked_borrows/illegal_dealloc1.stderr | 2 +- tests/fail/stacked_borrows/illegal_read1.stderr | 2 +- tests/fail/stacked_borrows/illegal_read2.stderr | 2 +- tests/fail/stacked_borrows/illegal_read3.stderr | 2 +- tests/fail/stacked_borrows/illegal_read4.stderr | 2 +- tests/fail/stacked_borrows/illegal_read5.stderr | 2 +- tests/fail/stacked_borrows/illegal_read6.stderr | 2 +- tests/fail/stacked_borrows/illegal_read7.stderr | 2 +- tests/fail/stacked_borrows/illegal_read8.stderr | 2 +- .../stacked_borrows/illegal_read_despite_exposed1.stderr | 2 +- .../stacked_borrows/illegal_read_despite_exposed2.stderr | 2 +- tests/fail/stacked_borrows/illegal_write1.stderr | 2 +- tests/fail/stacked_borrows/illegal_write2.stderr | 2 +- tests/fail/stacked_borrows/illegal_write3.stderr | 2 +- tests/fail/stacked_borrows/illegal_write4.stderr | 2 +- tests/fail/stacked_borrows/illegal_write5.stderr | 2 +- tests/fail/stacked_borrows/illegal_write6.stderr | 2 +- .../stacked_borrows/illegal_write_despite_exposed1.stderr | 2 +- tests/fail/stacked_borrows/interior_mut1.stderr | 2 +- tests/fail/stacked_borrows/interior_mut2.stderr | 2 +- .../stacked_borrows/invalidate_against_protector1.stderr | 2 +- .../stacked_borrows/invalidate_against_protector2.stderr | 2 +- .../stacked_borrows/invalidate_against_protector3.stderr | 2 +- tests/fail/stacked_borrows/load_invalid_mut.stderr | 2 +- tests/fail/stacked_borrows/load_invalid_shr.stderr | 2 +- tests/fail/stacked_borrows/mut_exclusive_violation1.stderr | 2 +- tests/fail/stacked_borrows/mut_exclusive_violation2.stderr | 2 +- tests/fail/stacked_borrows/newtype_pair_retagging.stderr | 2 +- tests/fail/stacked_borrows/newtype_retagging.stderr | 2 +- tests/fail/stacked_borrows/outdated_local.stderr | 2 +- tests/fail/stacked_borrows/pass_invalid_mut.stderr | 2 +- tests/fail/stacked_borrows/pass_invalid_shr.stderr | 2 +- tests/fail/stacked_borrows/pointer_smuggling.stderr | 2 +- tests/fail/stacked_borrows/raw_tracking.stderr | 2 +- tests/fail/stacked_borrows/retag_data_race_read.stderr | 2 +- tests/fail/stacked_borrows/retag_data_race_write.stderr | 2 +- tests/fail/stacked_borrows/return_invalid_mut.stderr | 2 +- tests/fail/stacked_borrows/return_invalid_mut_option.stderr | 2 +- tests/fail/stacked_borrows/return_invalid_mut_tuple.stderr | 2 +- tests/fail/stacked_borrows/return_invalid_shr.stderr | 2 +- tests/fail/stacked_borrows/return_invalid_shr_option.stderr | 2 +- tests/fail/stacked_borrows/return_invalid_shr_tuple.stderr | 2 +- .../fail/stacked_borrows/shared_rw_borrows_are_weak1.stderr | 2 +- .../fail/stacked_borrows/shared_rw_borrows_are_weak2.stderr | 2 +- tests/fail/stacked_borrows/shr_frozen_violation1.stderr | 2 +- tests/fail/stacked_borrows/track_caller.stderr | 2 +- tests/fail/stacked_borrows/transmute-is-no-escape.stderr | 2 +- tests/fail/stacked_borrows/unescaped_static.stderr | 2 +- tests/fail/stacked_borrows/zst_slice.stderr | 2 +- 90 files changed, 93 insertions(+), 90 deletions(-) diff --git a/src/diagnostics.rs b/src/diagnostics.rs index 6f94d57bcc..2087d0cb54 100644 --- a/src/diagnostics.rs +++ b/src/diagnostics.rs @@ -362,9 +362,11 @@ fn report_msg<'tcx>( } // Show note and help messages. + let mut extra_span = false; for (span_data, note) in ¬es { if let Some(span_data) = span_data { err.span_note(span_data.span(), note); + extra_span = true; } else { err.note(note); } @@ -372,13 +374,14 @@ fn report_msg<'tcx>( for (span_data, help) in &helps { if let Some(span_data) = span_data { err.span_help(span_data.span(), help); + extra_span = true; } else { err.help(help); } } if notes.len() + helps.len() > 0 { // Add visual separator before backtrace. - err.note("BACKTRACE:"); + err.note(if extra_span { "BACKTRACE (of the first span):" } else { "BACKTRACE:" }); } // Add backtrace for (idx, frame_info) in stacktrace.iter().enumerate() { diff --git a/tests/fail/box-cell-alias.stderr b/tests/fail/box-cell-alias.stderr index f57b52c4bd..fc946d6d39 100644 --- a/tests/fail/box-cell-alias.stderr +++ b/tests/fail/box-cell-alias.stderr @@ -19,7 +19,7 @@ help: was later invalidated at offsets [0x0..0x1] by a Unique retag | LL | let res = helper(val, ptr); | ^^^ - = note: BACKTRACE: + = note: BACKTRACE (of the first span): = note: inside `helper` at $DIR/box-cell-alias.rs:LL:CC note: inside `main` --> $DIR/box-cell-alias.rs:LL:CC diff --git a/tests/fail/data_race/alloc_read_race.stderr b/tests/fail/data_race/alloc_read_race.stderr index 38b1ad3cfe..59b3802416 100644 --- a/tests/fail/data_race/alloc_read_race.stderr +++ b/tests/fail/data_race/alloc_read_race.stderr @@ -11,7 +11,7 @@ LL | pointer.store(Box::into_raw(Box::new_uninit()), Ordering::Relax | ^^^^^^^^^^^^^^^^^ = help: this indicates a bug in the program: it performed an invalid operation, and caused Undefined Behavior = help: see https://doc.rust-lang.org/nightly/reference/behavior-considered-undefined.html for further information - = note: BACKTRACE: + = note: BACKTRACE (of the first span): = note: inside closure at $DIR/alloc_read_race.rs:LL:CC note: some details are omitted, run with `MIRIFLAGS=-Zmiri-backtrace=full` for a verbose backtrace diff --git a/tests/fail/data_race/alloc_write_race.stderr b/tests/fail/data_race/alloc_write_race.stderr index 473a694522..0564e4b5bf 100644 --- a/tests/fail/data_race/alloc_write_race.stderr +++ b/tests/fail/data_race/alloc_write_race.stderr @@ -11,7 +11,7 @@ LL | .store(Box::into_raw(Box::::new_uninit()) as *mut us | ^^^^^^^^^^^^^^^^^^^^^^^^^^ = help: this indicates a bug in the program: it performed an invalid operation, and caused Undefined Behavior = help: see https://doc.rust-lang.org/nightly/reference/behavior-considered-undefined.html for further information - = note: BACKTRACE: + = note: BACKTRACE (of the first span): = note: inside closure at $DIR/alloc_write_race.rs:LL:CC note: some details are omitted, run with `MIRIFLAGS=-Zmiri-backtrace=full` for a verbose backtrace diff --git a/tests/fail/data_race/atomic_read_na_write_race1.stderr b/tests/fail/data_race/atomic_read_na_write_race1.stderr index 565fba3280..ab7a617810 100644 --- a/tests/fail/data_race/atomic_read_na_write_race1.stderr +++ b/tests/fail/data_race/atomic_read_na_write_race1.stderr @@ -11,7 +11,7 @@ LL | *(c.0 as *mut usize) = 32; | ^^^^^^^^^^^^^^^^^^^^^^^^^ = help: this indicates a bug in the program: it performed an invalid operation, and caused Undefined Behavior = help: see https://doc.rust-lang.org/nightly/reference/behavior-considered-undefined.html for further information - = note: BACKTRACE: + = note: BACKTRACE (of the first span): = note: inside closure at $DIR/atomic_read_na_write_race1.rs:LL:CC note: some details are omitted, run with `MIRIFLAGS=-Zmiri-backtrace=full` for a verbose backtrace diff --git a/tests/fail/data_race/atomic_read_na_write_race2.stderr b/tests/fail/data_race/atomic_read_na_write_race2.stderr index 753a2961b4..cd8e095a6e 100644 --- a/tests/fail/data_race/atomic_read_na_write_race2.stderr +++ b/tests/fail/data_race/atomic_read_na_write_race2.stderr @@ -11,7 +11,7 @@ LL | atomic_ref.load(Ordering::SeqCst) | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ = help: this indicates a bug in the program: it performed an invalid operation, and caused Undefined Behavior = help: see https://doc.rust-lang.org/nightly/reference/behavior-considered-undefined.html for further information - = note: BACKTRACE: + = note: BACKTRACE (of the first span): = note: inside closure at $DIR/atomic_read_na_write_race2.rs:LL:CC note: some details are omitted, run with `MIRIFLAGS=-Zmiri-backtrace=full` for a verbose backtrace diff --git a/tests/fail/data_race/atomic_write_na_read_race1.stderr b/tests/fail/data_race/atomic_write_na_read_race1.stderr index 5be597b7f5..b339e5adf8 100644 --- a/tests/fail/data_race/atomic_write_na_read_race1.stderr +++ b/tests/fail/data_race/atomic_write_na_read_race1.stderr @@ -11,7 +11,7 @@ LL | atomic_ref.store(32, Ordering::SeqCst) | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ = help: this indicates a bug in the program: it performed an invalid operation, and caused Undefined Behavior = help: see https://doc.rust-lang.org/nightly/reference/behavior-considered-undefined.html for further information - = note: BACKTRACE: + = note: BACKTRACE (of the first span): = note: inside closure at $DIR/atomic_write_na_read_race1.rs:LL:CC note: some details are omitted, run with `MIRIFLAGS=-Zmiri-backtrace=full` for a verbose backtrace diff --git a/tests/fail/data_race/atomic_write_na_read_race2.stderr b/tests/fail/data_race/atomic_write_na_read_race2.stderr index 2c21337029..3968620349 100644 --- a/tests/fail/data_race/atomic_write_na_read_race2.stderr +++ b/tests/fail/data_race/atomic_write_na_read_race2.stderr @@ -11,7 +11,7 @@ LL | let _val = *(c.0 as *mut usize); | ^^^^^^^^^^^^^^^^^^^^ = help: this indicates a bug in the program: it performed an invalid operation, and caused Undefined Behavior = help: see https://doc.rust-lang.org/nightly/reference/behavior-considered-undefined.html for further information - = note: BACKTRACE: + = note: BACKTRACE (of the first span): = note: inside closure at $DIR/atomic_write_na_read_race2.rs:LL:CC note: some details are omitted, run with `MIRIFLAGS=-Zmiri-backtrace=full` for a verbose backtrace diff --git a/tests/fail/data_race/atomic_write_na_write_race1.stderr b/tests/fail/data_race/atomic_write_na_write_race1.stderr index b10724aa67..fd360797d3 100644 --- a/tests/fail/data_race/atomic_write_na_write_race1.stderr +++ b/tests/fail/data_race/atomic_write_na_write_race1.stderr @@ -11,7 +11,7 @@ LL | *(c.0 as *mut usize) = 32; | ^^^^^^^^^^^^^^^^^^^^^^^^^ = help: this indicates a bug in the program: it performed an invalid operation, and caused Undefined Behavior = help: see https://doc.rust-lang.org/nightly/reference/behavior-considered-undefined.html for further information - = note: BACKTRACE: + = note: BACKTRACE (of the first span): = note: inside closure at $DIR/atomic_write_na_write_race1.rs:LL:CC note: some details are omitted, run with `MIRIFLAGS=-Zmiri-backtrace=full` for a verbose backtrace diff --git a/tests/fail/data_race/atomic_write_na_write_race2.stderr b/tests/fail/data_race/atomic_write_na_write_race2.stderr index 63393a2a8b..4e2494cf57 100644 --- a/tests/fail/data_race/atomic_write_na_write_race2.stderr +++ b/tests/fail/data_race/atomic_write_na_write_race2.stderr @@ -11,7 +11,7 @@ LL | atomic_ref.store(64, Ordering::SeqCst); | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ = help: this indicates a bug in the program: it performed an invalid operation, and caused Undefined Behavior = help: see https://doc.rust-lang.org/nightly/reference/behavior-considered-undefined.html for further information - = note: BACKTRACE: + = note: BACKTRACE (of the first span): = note: inside closure at $DIR/atomic_write_na_write_race2.rs:LL:CC note: some details are omitted, run with `MIRIFLAGS=-Zmiri-backtrace=full` for a verbose backtrace diff --git a/tests/fail/data_race/dangling_thread_async_race.stderr b/tests/fail/data_race/dangling_thread_async_race.stderr index 26ab3c1673..aba051a2b6 100644 --- a/tests/fail/data_race/dangling_thread_async_race.stderr +++ b/tests/fail/data_race/dangling_thread_async_race.stderr @@ -11,7 +11,7 @@ LL | *c.0 = 32; | ^^^^^^^^^ = help: this indicates a bug in the program: it performed an invalid operation, and caused Undefined Behavior = help: see https://doc.rust-lang.org/nightly/reference/behavior-considered-undefined.html for further information - = note: BACKTRACE: + = note: BACKTRACE (of the first span): = note: inside closure at $DIR/dangling_thread_async_race.rs:LL:CC note: some details are omitted, run with `MIRIFLAGS=-Zmiri-backtrace=full` for a verbose backtrace diff --git a/tests/fail/data_race/dangling_thread_race.stderr b/tests/fail/data_race/dangling_thread_race.stderr index 23ccb33e9a..dc35ccf354 100644 --- a/tests/fail/data_race/dangling_thread_race.stderr +++ b/tests/fail/data_race/dangling_thread_race.stderr @@ -11,7 +11,7 @@ LL | *c.0 = 32; | ^^^^^^^^^ = help: this indicates a bug in the program: it performed an invalid operation, and caused Undefined Behavior = help: see https://doc.rust-lang.org/nightly/reference/behavior-considered-undefined.html for further information - = note: BACKTRACE: + = note: BACKTRACE (of the first span): = note: inside `main` at $DIR/dangling_thread_race.rs:LL:CC note: some details are omitted, run with `MIRIFLAGS=-Zmiri-backtrace=full` for a verbose backtrace diff --git a/tests/fail/data_race/dealloc_read_race1.stderr b/tests/fail/data_race/dealloc_read_race1.stderr index baf3f85216..fbeab37e17 100644 --- a/tests/fail/data_race/dealloc_read_race1.stderr +++ b/tests/fail/data_race/dealloc_read_race1.stderr @@ -16,7 +16,7 @@ LL | let _val = *ptr.0; | ^^^^^^ = help: this indicates a bug in the program: it performed an invalid operation, and caused Undefined Behavior = help: see https://doc.rust-lang.org/nightly/reference/behavior-considered-undefined.html for further information - = note: BACKTRACE: + = note: BACKTRACE (of the first span): = note: inside closure at $DIR/dealloc_read_race1.rs:LL:CC note: some details are omitted, run with `MIRIFLAGS=-Zmiri-backtrace=full` for a verbose backtrace diff --git a/tests/fail/data_race/dealloc_read_race_stack.stderr b/tests/fail/data_race/dealloc_read_race_stack.stderr index 94d95d44ac..9ef9bf35ae 100644 --- a/tests/fail/data_race/dealloc_read_race_stack.stderr +++ b/tests/fail/data_race/dealloc_read_race_stack.stderr @@ -11,7 +11,7 @@ LL | *pointer.load(Ordering::Acquire) | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ = help: this indicates a bug in the program: it performed an invalid operation, and caused Undefined Behavior = help: see https://doc.rust-lang.org/nightly/reference/behavior-considered-undefined.html for further information - = note: BACKTRACE: + = note: BACKTRACE (of the first span): = note: inside closure at $DIR/dealloc_read_race_stack.rs:LL:CC note: some details are omitted, run with `MIRIFLAGS=-Zmiri-backtrace=full` for a verbose backtrace diff --git a/tests/fail/data_race/dealloc_write_race1.stderr b/tests/fail/data_race/dealloc_write_race1.stderr index cce2701a03..75a98cc5d7 100644 --- a/tests/fail/data_race/dealloc_write_race1.stderr +++ b/tests/fail/data_race/dealloc_write_race1.stderr @@ -16,7 +16,7 @@ LL | *ptr.0 = 2; | ^^^^^^^^^^ = help: this indicates a bug in the program: it performed an invalid operation, and caused Undefined Behavior = help: see https://doc.rust-lang.org/nightly/reference/behavior-considered-undefined.html for further information - = note: BACKTRACE: + = note: BACKTRACE (of the first span): = note: inside closure at $DIR/dealloc_write_race1.rs:LL:CC note: some details are omitted, run with `MIRIFLAGS=-Zmiri-backtrace=full` for a verbose backtrace diff --git a/tests/fail/data_race/dealloc_write_race_stack.stderr b/tests/fail/data_race/dealloc_write_race_stack.stderr index 0f60926fb5..f2fc338b33 100644 --- a/tests/fail/data_race/dealloc_write_race_stack.stderr +++ b/tests/fail/data_race/dealloc_write_race_stack.stderr @@ -11,7 +11,7 @@ LL | *pointer.load(Ordering::Acquire) = 3; | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ = help: this indicates a bug in the program: it performed an invalid operation, and caused Undefined Behavior = help: see https://doc.rust-lang.org/nightly/reference/behavior-considered-undefined.html for further information - = note: BACKTRACE: + = note: BACKTRACE (of the first span): = note: inside closure at $DIR/dealloc_write_race_stack.rs:LL:CC note: some details are omitted, run with `MIRIFLAGS=-Zmiri-backtrace=full` for a verbose backtrace diff --git a/tests/fail/data_race/enable_after_join_to_main.stderr b/tests/fail/data_race/enable_after_join_to_main.stderr index e608342f8d..620cb37859 100644 --- a/tests/fail/data_race/enable_after_join_to_main.stderr +++ b/tests/fail/data_race/enable_after_join_to_main.stderr @@ -11,7 +11,7 @@ LL | *c.0 = 32; | ^^^^^^^^^ = help: this indicates a bug in the program: it performed an invalid operation, and caused Undefined Behavior = help: see https://doc.rust-lang.org/nightly/reference/behavior-considered-undefined.html for further information - = note: BACKTRACE: + = note: BACKTRACE (of the first span): = note: inside closure at $DIR/enable_after_join_to_main.rs:LL:CC note: some details are omitted, run with `MIRIFLAGS=-Zmiri-backtrace=full` for a verbose backtrace diff --git a/tests/fail/data_race/fence_after_load.stderr b/tests/fail/data_race/fence_after_load.stderr index 9c1d92d14f..0bd36067d9 100644 --- a/tests/fail/data_race/fence_after_load.stderr +++ b/tests/fail/data_race/fence_after_load.stderr @@ -11,7 +11,7 @@ LL | unsafe { V = 1 } | ^^^^^ = help: this indicates a bug in the program: it performed an invalid operation, and caused Undefined Behavior = help: see https://doc.rust-lang.org/nightly/reference/behavior-considered-undefined.html for further information - = note: BACKTRACE: + = note: BACKTRACE (of the first span): = note: inside `main` at $DIR/fence_after_load.rs:LL:CC note: some details are omitted, run with `MIRIFLAGS=-Zmiri-backtrace=full` for a verbose backtrace diff --git a/tests/fail/data_race/read_write_race.stderr b/tests/fail/data_race/read_write_race.stderr index e31bc5fbb4..0c0d2fa32c 100644 --- a/tests/fail/data_race/read_write_race.stderr +++ b/tests/fail/data_race/read_write_race.stderr @@ -11,7 +11,7 @@ LL | let _val = *c.0; | ^^^^ = help: this indicates a bug in the program: it performed an invalid operation, and caused Undefined Behavior = help: see https://doc.rust-lang.org/nightly/reference/behavior-considered-undefined.html for further information - = note: BACKTRACE: + = note: BACKTRACE (of the first span): = note: inside closure at $DIR/read_write_race.rs:LL:CC note: some details are omitted, run with `MIRIFLAGS=-Zmiri-backtrace=full` for a verbose backtrace diff --git a/tests/fail/data_race/read_write_race_stack.stderr b/tests/fail/data_race/read_write_race_stack.stderr index 09b704e063..e1d0a52d42 100644 --- a/tests/fail/data_race/read_write_race_stack.stderr +++ b/tests/fail/data_race/read_write_race_stack.stderr @@ -11,7 +11,7 @@ LL | *pointer.load(Ordering::Acquire) = 3; | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ = help: this indicates a bug in the program: it performed an invalid operation, and caused Undefined Behavior = help: see https://doc.rust-lang.org/nightly/reference/behavior-considered-undefined.html for further information - = note: BACKTRACE: + = note: BACKTRACE (of the first span): = note: inside closure at $DIR/read_write_race_stack.rs:LL:CC note: some details are omitted, run with `MIRIFLAGS=-Zmiri-backtrace=full` for a verbose backtrace diff --git a/tests/fail/data_race/relax_acquire_race.stderr b/tests/fail/data_race/relax_acquire_race.stderr index a996fc3500..fdf0e4917d 100644 --- a/tests/fail/data_race/relax_acquire_race.stderr +++ b/tests/fail/data_race/relax_acquire_race.stderr @@ -11,7 +11,7 @@ LL | *c.0 = 1; | ^^^^^^^^ = help: this indicates a bug in the program: it performed an invalid operation, and caused Undefined Behavior = help: see https://doc.rust-lang.org/nightly/reference/behavior-considered-undefined.html for further information - = note: BACKTRACE: + = note: BACKTRACE (of the first span): = note: inside closure at $DIR/relax_acquire_race.rs:LL:CC note: some details are omitted, run with `MIRIFLAGS=-Zmiri-backtrace=full` for a verbose backtrace diff --git a/tests/fail/data_race/release_seq_race.stderr b/tests/fail/data_race/release_seq_race.stderr index 8b27a18856..234ce48e76 100644 --- a/tests/fail/data_race/release_seq_race.stderr +++ b/tests/fail/data_race/release_seq_race.stderr @@ -11,7 +11,7 @@ LL | *c.0 = 1; | ^^^^^^^^ = help: this indicates a bug in the program: it performed an invalid operation, and caused Undefined Behavior = help: see https://doc.rust-lang.org/nightly/reference/behavior-considered-undefined.html for further information - = note: BACKTRACE: + = note: BACKTRACE (of the first span): = note: inside closure at $DIR/release_seq_race.rs:LL:CC note: some details are omitted, run with `MIRIFLAGS=-Zmiri-backtrace=full` for a verbose backtrace diff --git a/tests/fail/data_race/release_seq_race_same_thread.stderr b/tests/fail/data_race/release_seq_race_same_thread.stderr index a3561b1a26..8e95d3593b 100644 --- a/tests/fail/data_race/release_seq_race_same_thread.stderr +++ b/tests/fail/data_race/release_seq_race_same_thread.stderr @@ -11,7 +11,7 @@ LL | *c.0 = 1; | ^^^^^^^^ = help: this indicates a bug in the program: it performed an invalid operation, and caused Undefined Behavior = help: see https://doc.rust-lang.org/nightly/reference/behavior-considered-undefined.html for further information - = note: BACKTRACE: + = note: BACKTRACE (of the first span): = note: inside closure at $DIR/release_seq_race_same_thread.rs:LL:CC note: some details are omitted, run with `MIRIFLAGS=-Zmiri-backtrace=full` for a verbose backtrace diff --git a/tests/fail/data_race/rmw_race.stderr b/tests/fail/data_race/rmw_race.stderr index 9448d9059b..6252cd5a71 100644 --- a/tests/fail/data_race/rmw_race.stderr +++ b/tests/fail/data_race/rmw_race.stderr @@ -11,7 +11,7 @@ LL | *c.0 = 1; | ^^^^^^^^ = help: this indicates a bug in the program: it performed an invalid operation, and caused Undefined Behavior = help: see https://doc.rust-lang.org/nightly/reference/behavior-considered-undefined.html for further information - = note: BACKTRACE: + = note: BACKTRACE (of the first span): = note: inside closure at $DIR/rmw_race.rs:LL:CC note: some details are omitted, run with `MIRIFLAGS=-Zmiri-backtrace=full` for a verbose backtrace diff --git a/tests/fail/data_race/stack_pop_race.stderr b/tests/fail/data_race/stack_pop_race.stderr index 0e2e202900..6cb0270b3d 100644 --- a/tests/fail/data_race/stack_pop_race.stderr +++ b/tests/fail/data_race/stack_pop_race.stderr @@ -11,7 +11,7 @@ LL | let _val = unsafe { *ptr.0 }; | ^^^^^^ = help: this indicates a bug in the program: it performed an invalid operation, and caused Undefined Behavior = help: see https://doc.rust-lang.org/nightly/reference/behavior-considered-undefined.html for further information - = note: BACKTRACE: + = note: BACKTRACE (of the first span): = note: inside `race` at $DIR/stack_pop_race.rs:LL:CC note: inside `main` --> $DIR/stack_pop_race.rs:LL:CC diff --git a/tests/fail/data_race/write_write_race.stderr b/tests/fail/data_race/write_write_race.stderr index dcc94a9d25..e9055932c5 100644 --- a/tests/fail/data_race/write_write_race.stderr +++ b/tests/fail/data_race/write_write_race.stderr @@ -11,7 +11,7 @@ LL | *c.0 = 32; | ^^^^^^^^^ = help: this indicates a bug in the program: it performed an invalid operation, and caused Undefined Behavior = help: see https://doc.rust-lang.org/nightly/reference/behavior-considered-undefined.html for further information - = note: BACKTRACE: + = note: BACKTRACE (of the first span): = note: inside closure at $DIR/write_write_race.rs:LL:CC note: some details are omitted, run with `MIRIFLAGS=-Zmiri-backtrace=full` for a verbose backtrace diff --git a/tests/fail/data_race/write_write_race_stack.stderr b/tests/fail/data_race/write_write_race_stack.stderr index 8b0250593d..d156ece4a1 100644 --- a/tests/fail/data_race/write_write_race_stack.stderr +++ b/tests/fail/data_race/write_write_race_stack.stderr @@ -11,7 +11,7 @@ LL | *pointer.load(Ordering::Acquire) = 3; | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ = help: this indicates a bug in the program: it performed an invalid operation, and caused Undefined Behavior = help: see https://doc.rust-lang.org/nightly/reference/behavior-considered-undefined.html for further information - = note: BACKTRACE: + = note: BACKTRACE (of the first span): = note: inside closure at $DIR/write_write_race_stack.rs:LL:CC note: some details are omitted, run with `MIRIFLAGS=-Zmiri-backtrace=full` for a verbose backtrace diff --git a/tests/fail/function_calls/exported_symbol_clashing.stderr b/tests/fail/function_calls/exported_symbol_clashing.stderr index 8eb9fa4ff5..09e4157b31 100644 --- a/tests/fail/function_calls/exported_symbol_clashing.stderr +++ b/tests/fail/function_calls/exported_symbol_clashing.stderr @@ -14,7 +14,7 @@ help: then it's defined here again, in crate `exported_symbol_clashing` | LL | fn bar() {} | ^^^^^^^^ - = note: BACKTRACE: + = note: BACKTRACE (of the first span): = note: inside `main` at $DIR/exported_symbol_clashing.rs:LL:CC note: some details are omitted, run with `MIRIFLAGS=-Zmiri-backtrace=full` for a verbose backtrace diff --git a/tests/fail/function_calls/exported_symbol_shim_clashing.stderr b/tests/fail/function_calls/exported_symbol_shim_clashing.stderr index 58a996e645..0d0055bb85 100644 --- a/tests/fail/function_calls/exported_symbol_shim_clashing.stderr +++ b/tests/fail/function_calls/exported_symbol_shim_clashing.stderr @@ -12,7 +12,7 @@ LL | | LL | | unreachable!() LL | | } | |_^ - = note: BACKTRACE: + = note: BACKTRACE (of the first span): = note: inside `main` at $DIR/exported_symbol_shim_clashing.rs:LL:CC note: some details are omitted, run with `MIRIFLAGS=-Zmiri-backtrace=full` for a verbose backtrace diff --git a/tests/fail/stacked_borrows/alias_through_mutation.stderr b/tests/fail/stacked_borrows/alias_through_mutation.stderr index 461275c3fa..b22db3eb12 100644 --- a/tests/fail/stacked_borrows/alias_through_mutation.stderr +++ b/tests/fail/stacked_borrows/alias_through_mutation.stderr @@ -19,7 +19,7 @@ help: was later invalidated at offsets [0x0..0x4] by a write access | LL | *target = 13; | ^^^^^^^^^^^^ - = note: BACKTRACE: + = note: BACKTRACE (of the first span): = note: inside `main` at $DIR/alias_through_mutation.rs:LL:CC note: some details are omitted, run with `MIRIFLAGS=-Zmiri-backtrace=full` for a verbose backtrace diff --git a/tests/fail/stacked_borrows/aliasing_mut1.stderr b/tests/fail/stacked_borrows/aliasing_mut1.stderr index 4514abb4ab..3ce39968cb 100644 --- a/tests/fail/stacked_borrows/aliasing_mut1.stderr +++ b/tests/fail/stacked_borrows/aliasing_mut1.stderr @@ -16,7 +16,7 @@ help: is this argument | LL | pub fn safe(_x: &mut i32, _y: &mut i32) {} | ^^ - = note: BACKTRACE: + = note: BACKTRACE (of the first span): = note: inside `safe` at $DIR/aliasing_mut1.rs:LL:CC note: inside `main` --> $DIR/aliasing_mut1.rs:LL:CC diff --git a/tests/fail/stacked_borrows/aliasing_mut2.stderr b/tests/fail/stacked_borrows/aliasing_mut2.stderr index 9ca9743cbd..df4b6cf025 100644 --- a/tests/fail/stacked_borrows/aliasing_mut2.stderr +++ b/tests/fail/stacked_borrows/aliasing_mut2.stderr @@ -16,7 +16,7 @@ help: is this argument | LL | pub fn safe(_x: &i32, _y: &mut i32) {} | ^^ - = note: BACKTRACE: + = note: BACKTRACE (of the first span): = note: inside `safe` at $DIR/aliasing_mut2.rs:LL:CC note: inside `main` --> $DIR/aliasing_mut2.rs:LL:CC diff --git a/tests/fail/stacked_borrows/aliasing_mut3.stderr b/tests/fail/stacked_borrows/aliasing_mut3.stderr index b504097a3c..55aaed62f4 100644 --- a/tests/fail/stacked_borrows/aliasing_mut3.stderr +++ b/tests/fail/stacked_borrows/aliasing_mut3.stderr @@ -19,7 +19,7 @@ help: was later invalidated at offsets [0x0..0x4] by a Unique FnEntry reta | LL | safe_raw(xraw, xshr); | ^^^^^^^^^^^^^^^^^^^^ - = note: BACKTRACE: + = note: BACKTRACE (of the first span): = note: inside `safe` at $DIR/aliasing_mut3.rs:LL:CC note: inside `main` --> $DIR/aliasing_mut3.rs:LL:CC diff --git a/tests/fail/stacked_borrows/aliasing_mut4.stderr b/tests/fail/stacked_borrows/aliasing_mut4.stderr index 6fe0d70902..ddf197bc63 100644 --- a/tests/fail/stacked_borrows/aliasing_mut4.stderr +++ b/tests/fail/stacked_borrows/aliasing_mut4.stderr @@ -16,7 +16,7 @@ help: is this argument | LL | pub fn safe(_x: &i32, _y: &mut Cell) {} | ^^ - = note: BACKTRACE: + = note: BACKTRACE (of the first span): = note: inside `safe` at $DIR/aliasing_mut4.rs:LL:CC note: inside `main` --> $DIR/aliasing_mut4.rs:LL:CC diff --git a/tests/fail/stacked_borrows/box_exclusive_violation1.stderr b/tests/fail/stacked_borrows/box_exclusive_violation1.stderr index f114130f6f..76f4e81f71 100644 --- a/tests/fail/stacked_borrows/box_exclusive_violation1.stderr +++ b/tests/fail/stacked_borrows/box_exclusive_violation1.stderr @@ -19,7 +19,7 @@ help: was later invalidated at offsets [0x0..0x4] by a write access | LL | *our = 5; | ^^^^^^^^ - = note: BACKTRACE: + = note: BACKTRACE (of the first span): = note: inside `unknown_code_2` at $DIR/box_exclusive_violation1.rs:LL:CC note: inside `demo_box_advanced_unique` --> $DIR/box_exclusive_violation1.rs:LL:CC diff --git a/tests/fail/stacked_borrows/box_noalias_violation.stderr b/tests/fail/stacked_borrows/box_noalias_violation.stderr index 139fcd0ca4..59377aeb97 100644 --- a/tests/fail/stacked_borrows/box_noalias_violation.stderr +++ b/tests/fail/stacked_borrows/box_noalias_violation.stderr @@ -16,7 +16,7 @@ help: is this argument | LL | unsafe fn test(mut x: Box, y: *const i32) -> i32 { | ^^^^^ - = note: BACKTRACE: + = note: BACKTRACE (of the first span): = note: inside `test` at $DIR/box_noalias_violation.rs:LL:CC note: inside `main` --> $DIR/box_noalias_violation.rs:LL:CC diff --git a/tests/fail/stacked_borrows/buggy_as_mut_slice.stderr b/tests/fail/stacked_borrows/buggy_as_mut_slice.stderr index 6aa1436128..fa3d7ca367 100644 --- a/tests/fail/stacked_borrows/buggy_as_mut_slice.stderr +++ b/tests/fail/stacked_borrows/buggy_as_mut_slice.stderr @@ -19,7 +19,7 @@ help: was later invalidated at offsets [0x0..0xc] by a Unique retag | LL | unsafe { from_raw_parts_mut(self_.as_ptr() as *mut T, self_.len()) } | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ - = note: BACKTRACE: + = note: BACKTRACE (of the first span): = note: inside `main` at $DIR/buggy_as_mut_slice.rs:LL:CC note: some details are omitted, run with `MIRIFLAGS=-Zmiri-backtrace=full` for a verbose backtrace diff --git a/tests/fail/stacked_borrows/buggy_split_at_mut.stderr b/tests/fail/stacked_borrows/buggy_split_at_mut.stderr index cdeccc0855..c75d8cab3f 100644 --- a/tests/fail/stacked_borrows/buggy_split_at_mut.stderr +++ b/tests/fail/stacked_borrows/buggy_split_at_mut.stderr @@ -19,7 +19,7 @@ help: was later invalidated at offsets [0x0..0x10] by a Unique retag | LL | from_raw_parts_mut(ptr.offset(mid as isize), len - mid), | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ - = note: BACKTRACE: + = note: BACKTRACE (of the first span): = note: inside `main` at $DIR/buggy_split_at_mut.rs:LL:CC note: some details are omitted, run with `MIRIFLAGS=-Zmiri-backtrace=full` for a verbose backtrace diff --git a/tests/fail/stacked_borrows/disable_mut_does_not_merge_srw.stderr b/tests/fail/stacked_borrows/disable_mut_does_not_merge_srw.stderr index e05f44fac9..bd79b401f6 100644 --- a/tests/fail/stacked_borrows/disable_mut_does_not_merge_srw.stderr +++ b/tests/fail/stacked_borrows/disable_mut_does_not_merge_srw.stderr @@ -19,7 +19,7 @@ help: was later invalidated at offsets [0x0..0x4] by a write access | LL | *base = 1; | ^^^^^^^^^ - = note: BACKTRACE: + = note: BACKTRACE (of the first span): = note: inside `main` at $DIR/disable_mut_does_not_merge_srw.rs:LL:CC note: some details are omitted, run with `MIRIFLAGS=-Zmiri-backtrace=full` for a verbose backtrace diff --git a/tests/fail/stacked_borrows/fnentry_invalidation.stderr b/tests/fail/stacked_borrows/fnentry_invalidation.stderr index e81411bbdd..e3bffde1f0 100644 --- a/tests/fail/stacked_borrows/fnentry_invalidation.stderr +++ b/tests/fail/stacked_borrows/fnentry_invalidation.stderr @@ -19,7 +19,7 @@ help: was later invalidated at offsets [0x0..0x4] by a Unique FnEntry reta | LL | x.do_bad(); | ^^^^^^^^^^ - = note: BACKTRACE: + = note: BACKTRACE (of the first span): = note: inside `main` at $DIR/fnentry_invalidation.rs:LL:CC note: some details are omitted, run with `MIRIFLAGS=-Zmiri-backtrace=full` for a verbose backtrace diff --git a/tests/fail/stacked_borrows/fnentry_invalidation2.stderr b/tests/fail/stacked_borrows/fnentry_invalidation2.stderr index d6d0084fa2..b104de4b8d 100644 --- a/tests/fail/stacked_borrows/fnentry_invalidation2.stderr +++ b/tests/fail/stacked_borrows/fnentry_invalidation2.stderr @@ -19,7 +19,7 @@ help: was later invalidated at offsets [0x0..0xc] by a Unique FnEntry reta | LL | let _ = t.sli.as_mut_ptr(); | ^^^^^^^^^^^^^^^^^^ - = note: BACKTRACE: + = note: BACKTRACE (of the first span): = note: inside `main` at $DIR/fnentry_invalidation2.rs:LL:CC note: some details are omitted, run with `MIRIFLAGS=-Zmiri-backtrace=full` for a verbose backtrace diff --git a/tests/fail/stacked_borrows/illegal_dealloc1.stderr b/tests/fail/stacked_borrows/illegal_dealloc1.stderr index f2f13d0d55..7fff60f25f 100644 --- a/tests/fail/stacked_borrows/illegal_dealloc1.stderr +++ b/tests/fail/stacked_borrows/illegal_dealloc1.stderr @@ -16,7 +16,7 @@ help: was later invalidated at offsets [0x0..0x1] by a write access | LL | ptr1.write(0); | ^^^^^^^^^^^^^ - = note: BACKTRACE: + = note: BACKTRACE (of the first span): = note: inside `std::alloc::dealloc` at RUSTLIB/alloc/src/alloc.rs:LL:CC note: inside `main` --> $DIR/illegal_deALLOC.rs:LL:CC diff --git a/tests/fail/stacked_borrows/illegal_read1.stderr b/tests/fail/stacked_borrows/illegal_read1.stderr index 95ff05d70c..7a159c9d3f 100644 --- a/tests/fail/stacked_borrows/illegal_read1.stderr +++ b/tests/fail/stacked_borrows/illegal_read1.stderr @@ -19,7 +19,7 @@ help: was later invalidated at offsets [0x0..0x4] by a read access | LL | let _val = unsafe { *xraw }; | ^^^^^ - = note: BACKTRACE: + = note: BACKTRACE (of the first span): = note: inside `main` at $DIR/illegal_read1.rs:LL:CC note: some details are omitted, run with `MIRIFLAGS=-Zmiri-backtrace=full` for a verbose backtrace diff --git a/tests/fail/stacked_borrows/illegal_read2.stderr b/tests/fail/stacked_borrows/illegal_read2.stderr index 5cfdf77dee..e3e79f6f0f 100644 --- a/tests/fail/stacked_borrows/illegal_read2.stderr +++ b/tests/fail/stacked_borrows/illegal_read2.stderr @@ -19,7 +19,7 @@ help: was later invalidated at offsets [0x0..0x4] by a SharedReadOnly reta | LL | let shr = unsafe { &*xraw }; | ^^^^^^ - = note: BACKTRACE: + = note: BACKTRACE (of the first span): = note: inside `main` at $DIR/illegal_read2.rs:LL:CC note: some details are omitted, run with `MIRIFLAGS=-Zmiri-backtrace=full` for a verbose backtrace diff --git a/tests/fail/stacked_borrows/illegal_read3.stderr b/tests/fail/stacked_borrows/illegal_read3.stderr index dacf71fa3e..3a8687ad9a 100644 --- a/tests/fail/stacked_borrows/illegal_read3.stderr +++ b/tests/fail/stacked_borrows/illegal_read3.stderr @@ -19,7 +19,7 @@ help: was later invalidated at offsets [0x0..0x4] by a read access | LL | let _val = unsafe { *xref1.r }; | ^^^^^^^^ - = note: BACKTRACE: + = note: BACKTRACE (of the first span): = note: inside `main` at $DIR/illegal_read3.rs:LL:CC note: some details are omitted, run with `MIRIFLAGS=-Zmiri-backtrace=full` for a verbose backtrace diff --git a/tests/fail/stacked_borrows/illegal_read4.stderr b/tests/fail/stacked_borrows/illegal_read4.stderr index 5ce0cba617..dcf37b2690 100644 --- a/tests/fail/stacked_borrows/illegal_read4.stderr +++ b/tests/fail/stacked_borrows/illegal_read4.stderr @@ -19,7 +19,7 @@ help: was later invalidated at offsets [0x0..0x4] by a read access | LL | let _val = unsafe { *xraw }; // use the raw again, this invalidates xref2 *even* with the special read except for uniq refs | ^^^^^ - = note: BACKTRACE: + = note: BACKTRACE (of the first span): = note: inside `main` at $DIR/illegal_read4.rs:LL:CC note: some details are omitted, run with `MIRIFLAGS=-Zmiri-backtrace=full` for a verbose backtrace diff --git a/tests/fail/stacked_borrows/illegal_read5.stderr b/tests/fail/stacked_borrows/illegal_read5.stderr index 63532f8794..1793798d15 100644 --- a/tests/fail/stacked_borrows/illegal_read5.stderr +++ b/tests/fail/stacked_borrows/illegal_read5.stderr @@ -19,7 +19,7 @@ help: was later invalidated at offsets [$HEX..$HEX] by a read access | LL | mem::forget(unsafe { ptr::read(xshr) }); // but after reading through the shared ref | ^^^^^^^^^^^^^^^ - = note: BACKTRACE: + = note: BACKTRACE (of the first span): = note: inside `main` at $DIR/illegal_read5.rs:LL:CC note: some details are omitted, run with `MIRIFLAGS=-Zmiri-backtrace=full` for a verbose backtrace diff --git a/tests/fail/stacked_borrows/illegal_read6.stderr b/tests/fail/stacked_borrows/illegal_read6.stderr index 93a96ab601..17b28dee3c 100644 --- a/tests/fail/stacked_borrows/illegal_read6.stderr +++ b/tests/fail/stacked_borrows/illegal_read6.stderr @@ -19,7 +19,7 @@ help: was later invalidated at offsets [0x0..0x4] by a Unique retag | LL | let x = &mut *x; // kill `raw` | ^^^^^^^ - = note: BACKTRACE: + = note: BACKTRACE (of the first span): = note: inside `main` at $DIR/illegal_read6.rs:LL:CC note: some details are omitted, run with `MIRIFLAGS=-Zmiri-backtrace=full` for a verbose backtrace diff --git a/tests/fail/stacked_borrows/illegal_read7.stderr b/tests/fail/stacked_borrows/illegal_read7.stderr index 2e8ac207be..b76446d60f 100644 --- a/tests/fail/stacked_borrows/illegal_read7.stderr +++ b/tests/fail/stacked_borrows/illegal_read7.stderr @@ -19,7 +19,7 @@ help: was later invalidated at offsets [0x0..0x4] by a read access | LL | let _val = ptr::read(raw); | ^^^^^^^^^^^^^^ - = note: BACKTRACE: + = note: BACKTRACE (of the first span): = note: inside `main` at $DIR/illegal_read7.rs:LL:CC note: some details are omitted, run with `MIRIFLAGS=-Zmiri-backtrace=full` for a verbose backtrace diff --git a/tests/fail/stacked_borrows/illegal_read8.stderr b/tests/fail/stacked_borrows/illegal_read8.stderr index c34fa2d895..b43079c3b7 100644 --- a/tests/fail/stacked_borrows/illegal_read8.stderr +++ b/tests/fail/stacked_borrows/illegal_read8.stderr @@ -19,7 +19,7 @@ help: was later invalidated at offsets [0x0..0x4] by a write access | LL | *y2 += 1; | ^^^^^^^^ - = note: BACKTRACE: + = note: BACKTRACE (of the first span): = note: inside `main` at $DIR/illegal_read8.rs:LL:CC note: some details are omitted, run with `MIRIFLAGS=-Zmiri-backtrace=full` for a verbose backtrace diff --git a/tests/fail/stacked_borrows/illegal_read_despite_exposed1.stderr b/tests/fail/stacked_borrows/illegal_read_despite_exposed1.stderr index 43b4ec2ba6..fbd5d8b956 100644 --- a/tests/fail/stacked_borrows/illegal_read_despite_exposed1.stderr +++ b/tests/fail/stacked_borrows/illegal_read_despite_exposed1.stderr @@ -19,7 +19,7 @@ help: was later invalidated at offsets [0x0..0x4] by a write access | LL | *exposed_ptr = 0; | ^^^^^^^^^^^^^^^^ - = note: BACKTRACE: + = note: BACKTRACE (of the first span): = note: inside `main` at $DIR/illegal_read_despite_exposed1.rs:LL:CC note: some details are omitted, run with `MIRIFLAGS=-Zmiri-backtrace=full` for a verbose backtrace diff --git a/tests/fail/stacked_borrows/illegal_read_despite_exposed2.stderr b/tests/fail/stacked_borrows/illegal_read_despite_exposed2.stderr index 832320fc20..19e4cbdb93 100644 --- a/tests/fail/stacked_borrows/illegal_read_despite_exposed2.stderr +++ b/tests/fail/stacked_borrows/illegal_read_despite_exposed2.stderr @@ -19,7 +19,7 @@ help: was later invalidated at offsets [0x0..0x4] by a read access | LL | let _val = *exposed_ptr; | ^^^^^^^^^^^^ - = note: BACKTRACE: + = note: BACKTRACE (of the first span): = note: inside `main` at $DIR/illegal_read_despite_exposed2.rs:LL:CC note: some details are omitted, run with `MIRIFLAGS=-Zmiri-backtrace=full` for a verbose backtrace diff --git a/tests/fail/stacked_borrows/illegal_write1.stderr b/tests/fail/stacked_borrows/illegal_write1.stderr index 3bf27f4815..c1e4918146 100644 --- a/tests/fail/stacked_borrows/illegal_write1.stderr +++ b/tests/fail/stacked_borrows/illegal_write1.stderr @@ -14,7 +14,7 @@ help: was created by a SharedReadOnly retag at offsets [0x0..0x4] | LL | let x: *mut u32 = xref as *const _ as *mut _; | ^^^^ - = note: BACKTRACE: + = note: BACKTRACE (of the first span): = note: inside `main` at $DIR/illegal_write1.rs:LL:CC note: some details are omitted, run with `MIRIFLAGS=-Zmiri-backtrace=full` for a verbose backtrace diff --git a/tests/fail/stacked_borrows/illegal_write2.stderr b/tests/fail/stacked_borrows/illegal_write2.stderr index a9fe8cb6cc..3e11e86eb8 100644 --- a/tests/fail/stacked_borrows/illegal_write2.stderr +++ b/tests/fail/stacked_borrows/illegal_write2.stderr @@ -19,7 +19,7 @@ help: was later invalidated at offsets [0x0..0x4] by a Unique retag | LL | drop(&mut *target); // reborrow | ^^^^^^^^^^^^ - = note: BACKTRACE: + = note: BACKTRACE (of the first span): = note: inside `main` at $DIR/illegal_write2.rs:LL:CC note: some details are omitted, run with `MIRIFLAGS=-Zmiri-backtrace=full` for a verbose backtrace diff --git a/tests/fail/stacked_borrows/illegal_write3.stderr b/tests/fail/stacked_borrows/illegal_write3.stderr index d64f2ddd87..4053325821 100644 --- a/tests/fail/stacked_borrows/illegal_write3.stderr +++ b/tests/fail/stacked_borrows/illegal_write3.stderr @@ -14,7 +14,7 @@ help: was created by a SharedReadOnly retag at offsets [0x0..0x4] | LL | let ptr = r#ref as *const _ as *mut _; // raw ptr, with raw tag | ^^^^^ - = note: BACKTRACE: + = note: BACKTRACE (of the first span): = note: inside `main` at $DIR/illegal_write3.rs:LL:CC note: some details are omitted, run with `MIRIFLAGS=-Zmiri-backtrace=full` for a verbose backtrace diff --git a/tests/fail/stacked_borrows/illegal_write4.stderr b/tests/fail/stacked_borrows/illegal_write4.stderr index e3b8621eb7..fceda8db4c 100644 --- a/tests/fail/stacked_borrows/illegal_write4.stderr +++ b/tests/fail/stacked_borrows/illegal_write4.stderr @@ -19,7 +19,7 @@ help: was later invalidated at offsets [0x0..0x4] by a Unique retag | LL | let _mut_ref: &mut i32 = unsafe { mem::transmute(raw) }; // &mut, with raw tag | ^^^^^^^^^^^^^^^^^^^ - = note: BACKTRACE: + = note: BACKTRACE (of the first span): = note: inside `main` at $DIR/illegal_write4.rs:LL:CC note: some details are omitted, run with `MIRIFLAGS=-Zmiri-backtrace=full` for a verbose backtrace diff --git a/tests/fail/stacked_borrows/illegal_write5.stderr b/tests/fail/stacked_borrows/illegal_write5.stderr index bbeb81258b..c71780b7e0 100644 --- a/tests/fail/stacked_borrows/illegal_write5.stderr +++ b/tests/fail/stacked_borrows/illegal_write5.stderr @@ -19,7 +19,7 @@ help: was later invalidated at offsets [0x0..0x4] by a write access | LL | unsafe { *xraw = 15 }; | ^^^^^^^^^^ - = note: BACKTRACE: + = note: BACKTRACE (of the first span): = note: inside `main` at $DIR/illegal_write5.rs:LL:CC note: some details are omitted, run with `MIRIFLAGS=-Zmiri-backtrace=full` for a verbose backtrace diff --git a/tests/fail/stacked_borrows/illegal_write6.stderr b/tests/fail/stacked_borrows/illegal_write6.stderr index 49d9050f30..3d3d2a24c2 100644 --- a/tests/fail/stacked_borrows/illegal_write6.stderr +++ b/tests/fail/stacked_borrows/illegal_write6.stderr @@ -16,7 +16,7 @@ help: is this argument | LL | fn foo(a: &mut u32, y: *mut u32) -> u32 { | ^ - = note: BACKTRACE: + = note: BACKTRACE (of the first span): = note: inside `foo` at $DIR/illegal_write6.rs:LL:CC note: inside `main` --> $DIR/illegal_write6.rs:LL:CC diff --git a/tests/fail/stacked_borrows/illegal_write_despite_exposed1.stderr b/tests/fail/stacked_borrows/illegal_write_despite_exposed1.stderr index 87ddf61d75..1bb3afe483 100644 --- a/tests/fail/stacked_borrows/illegal_write_despite_exposed1.stderr +++ b/tests/fail/stacked_borrows/illegal_write_despite_exposed1.stderr @@ -19,7 +19,7 @@ help: was later invalidated at offsets [0x0..0x4] by a write access | LL | *exposed_ptr = 0; | ^^^^^^^^^^^^^^^^ - = note: BACKTRACE: + = note: BACKTRACE (of the first span): = note: inside `main` at $DIR/illegal_write_despite_exposed1.rs:LL:CC note: some details are omitted, run with `MIRIFLAGS=-Zmiri-backtrace=full` for a verbose backtrace diff --git a/tests/fail/stacked_borrows/interior_mut1.stderr b/tests/fail/stacked_borrows/interior_mut1.stderr index 1d68727c82..da55e724fd 100644 --- a/tests/fail/stacked_borrows/interior_mut1.stderr +++ b/tests/fail/stacked_borrows/interior_mut1.stderr @@ -19,7 +19,7 @@ help: was later invalidated at offsets [0x0..0x4] by a write access | LL | *c.get() = UnsafeCell::new(1); // invalidates inner_shr | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ - = note: BACKTRACE: + = note: BACKTRACE (of the first span): = note: inside `main` at $DIR/interior_mut1.rs:LL:CC note: some details are omitted, run with `MIRIFLAGS=-Zmiri-backtrace=full` for a verbose backtrace diff --git a/tests/fail/stacked_borrows/interior_mut2.stderr b/tests/fail/stacked_borrows/interior_mut2.stderr index 8a33571422..8c8a96cbbb 100644 --- a/tests/fail/stacked_borrows/interior_mut2.stderr +++ b/tests/fail/stacked_borrows/interior_mut2.stderr @@ -19,7 +19,7 @@ help: was later invalidated at offsets [0x0..0x4] by a write access | LL | *c.get() = UnsafeCell::new(0); // now inner_shr gets invalidated | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ - = note: BACKTRACE: + = note: BACKTRACE (of the first span): = note: inside `main` at $DIR/interior_mut2.rs:LL:CC note: some details are omitted, run with `MIRIFLAGS=-Zmiri-backtrace=full` for a verbose backtrace diff --git a/tests/fail/stacked_borrows/invalidate_against_protector1.stderr b/tests/fail/stacked_borrows/invalidate_against_protector1.stderr index a53c633c38..95fa4c51d1 100644 --- a/tests/fail/stacked_borrows/invalidate_against_protector1.stderr +++ b/tests/fail/stacked_borrows/invalidate_against_protector1.stderr @@ -16,7 +16,7 @@ help: is this argument | LL | fn inner(x: *mut i32, _y: &mut i32) { | ^^ - = note: BACKTRACE: + = note: BACKTRACE (of the first span): = note: inside `inner` at $DIR/invalidate_against_protector1.rs:LL:CC note: inside `main` --> $DIR/invalidate_against_protector1.rs:LL:CC diff --git a/tests/fail/stacked_borrows/invalidate_against_protector2.stderr b/tests/fail/stacked_borrows/invalidate_against_protector2.stderr index 6ee78d1aac..8f677bd547 100644 --- a/tests/fail/stacked_borrows/invalidate_against_protector2.stderr +++ b/tests/fail/stacked_borrows/invalidate_against_protector2.stderr @@ -16,7 +16,7 @@ help: is this argument | LL | fn inner(x: *mut i32, _y: &i32) { | ^^ - = note: BACKTRACE: + = note: BACKTRACE (of the first span): = note: inside `inner` at $DIR/invalidate_against_protector2.rs:LL:CC note: inside `main` --> $DIR/invalidate_against_protector2.rs:LL:CC diff --git a/tests/fail/stacked_borrows/invalidate_against_protector3.stderr b/tests/fail/stacked_borrows/invalidate_against_protector3.stderr index 2b38dea9db..1648ca9e58 100644 --- a/tests/fail/stacked_borrows/invalidate_against_protector3.stderr +++ b/tests/fail/stacked_borrows/invalidate_against_protector3.stderr @@ -16,7 +16,7 @@ help: is this argument | LL | fn inner(x: *mut i32, _y: &i32) { | ^^ - = note: BACKTRACE: + = note: BACKTRACE (of the first span): = note: inside `inner` at $DIR/invalidate_against_protector3.rs:LL:CC note: inside `main` --> $DIR/invalidate_against_protector3.rs:LL:CC diff --git a/tests/fail/stacked_borrows/load_invalid_mut.stderr b/tests/fail/stacked_borrows/load_invalid_mut.stderr index 08dc171c9e..7aca065ca0 100644 --- a/tests/fail/stacked_borrows/load_invalid_mut.stderr +++ b/tests/fail/stacked_borrows/load_invalid_mut.stderr @@ -19,7 +19,7 @@ help: was later invalidated at offsets [0x0..0x4] by a read access | LL | let _val = unsafe { *xraw }; // invalidate xref | ^^^^^ - = note: BACKTRACE: + = note: BACKTRACE (of the first span): = note: inside `main` at $DIR/load_invalid_mut.rs:LL:CC note: some details are omitted, run with `MIRIFLAGS=-Zmiri-backtrace=full` for a verbose backtrace diff --git a/tests/fail/stacked_borrows/load_invalid_shr.stderr b/tests/fail/stacked_borrows/load_invalid_shr.stderr index 50bbed2b29..7eb973ae7f 100644 --- a/tests/fail/stacked_borrows/load_invalid_shr.stderr +++ b/tests/fail/stacked_borrows/load_invalid_shr.stderr @@ -19,7 +19,7 @@ help: was later invalidated at offsets [0x0..0x4] by a write access | LL | unsafe { *xraw = 42 }; // unfreeze | ^^^^^^^^^^ - = note: BACKTRACE: + = note: BACKTRACE (of the first span): = note: inside `main` at $DIR/load_invalid_shr.rs:LL:CC note: some details are omitted, run with `MIRIFLAGS=-Zmiri-backtrace=full` for a verbose backtrace diff --git a/tests/fail/stacked_borrows/mut_exclusive_violation1.stderr b/tests/fail/stacked_borrows/mut_exclusive_violation1.stderr index 2f3900c40d..3e7fe11b52 100644 --- a/tests/fail/stacked_borrows/mut_exclusive_violation1.stderr +++ b/tests/fail/stacked_borrows/mut_exclusive_violation1.stderr @@ -19,7 +19,7 @@ help: was later invalidated at offsets [0x0..0x4] by a write access | LL | *our = 5; | ^^^^^^^^ - = note: BACKTRACE: + = note: BACKTRACE (of the first span): = note: inside `unknown_code_2` at $DIR/mut_exclusive_violation1.rs:LL:CC note: inside `demo_mut_advanced_unique` --> $DIR/mut_exclusive_violation1.rs:LL:CC diff --git a/tests/fail/stacked_borrows/mut_exclusive_violation2.stderr b/tests/fail/stacked_borrows/mut_exclusive_violation2.stderr index 43b5325fc5..30ce698761 100644 --- a/tests/fail/stacked_borrows/mut_exclusive_violation2.stderr +++ b/tests/fail/stacked_borrows/mut_exclusive_violation2.stderr @@ -19,7 +19,7 @@ help: was later invalidated at offsets [0x0..0x4] by a Unique retag | LL | let _raw2 = ptr2.as_mut(); | ^^^^^^^^^^^^^ - = note: BACKTRACE: + = note: BACKTRACE (of the first span): = note: inside `main` at $DIR/mut_exclusive_violation2.rs:LL:CC note: some details are omitted, run with `MIRIFLAGS=-Zmiri-backtrace=full` for a verbose backtrace diff --git a/tests/fail/stacked_borrows/newtype_pair_retagging.stderr b/tests/fail/stacked_borrows/newtype_pair_retagging.stderr index 90677dfaf5..0cba380ea1 100644 --- a/tests/fail/stacked_borrows/newtype_pair_retagging.stderr +++ b/tests/fail/stacked_borrows/newtype_pair_retagging.stderr @@ -16,7 +16,7 @@ help: is this argument | LL | fn dealloc_while_running(_n: Newtype<'_>, dealloc: impl FnOnce()) { | ^^ - = note: BACKTRACE: + = note: BACKTRACE (of the first span): = note: inside `std::boxed::Box::::from_raw_in` at RUSTLIB/alloc/src/boxed.rs:LL:CC = note: inside `std::boxed::Box::::from_raw` at RUSTLIB/alloc/src/boxed.rs:LL:CC note: inside closure diff --git a/tests/fail/stacked_borrows/newtype_retagging.stderr b/tests/fail/stacked_borrows/newtype_retagging.stderr index f189d0483d..f76b6a57ea 100644 --- a/tests/fail/stacked_borrows/newtype_retagging.stderr +++ b/tests/fail/stacked_borrows/newtype_retagging.stderr @@ -16,7 +16,7 @@ help: is this argument | LL | fn dealloc_while_running(_n: Newtype<'_>, dealloc: impl FnOnce()) { | ^^ - = note: BACKTRACE: + = note: BACKTRACE (of the first span): = note: inside `std::boxed::Box::::from_raw_in` at RUSTLIB/alloc/src/boxed.rs:LL:CC = note: inside `std::boxed::Box::::from_raw` at RUSTLIB/alloc/src/boxed.rs:LL:CC note: inside closure diff --git a/tests/fail/stacked_borrows/outdated_local.stderr b/tests/fail/stacked_borrows/outdated_local.stderr index 8c2bba5391..ad366bdabc 100644 --- a/tests/fail/stacked_borrows/outdated_local.stderr +++ b/tests/fail/stacked_borrows/outdated_local.stderr @@ -19,7 +19,7 @@ help: was later invalidated at offsets [0x0..0x4] by a write access | LL | x = 1; // this invalidates y by reactivating the lowermost uniq borrow for this local | ^^^^^ - = note: BACKTRACE: + = note: BACKTRACE (of the first span): = note: inside `main` at $DIR/outdated_local.rs:LL:CC note: some details are omitted, run with `MIRIFLAGS=-Zmiri-backtrace=full` for a verbose backtrace diff --git a/tests/fail/stacked_borrows/pass_invalid_mut.stderr b/tests/fail/stacked_borrows/pass_invalid_mut.stderr index d7ab930aa3..96cec327b9 100644 --- a/tests/fail/stacked_borrows/pass_invalid_mut.stderr +++ b/tests/fail/stacked_borrows/pass_invalid_mut.stderr @@ -19,7 +19,7 @@ help: was later invalidated at offsets [0x0..0x4] by a read access | LL | let _val = unsafe { *xraw }; // invalidate xref | ^^^^^ - = note: BACKTRACE: + = note: BACKTRACE (of the first span): = note: inside `main` at $DIR/pass_invalid_mut.rs:LL:CC note: some details are omitted, run with `MIRIFLAGS=-Zmiri-backtrace=full` for a verbose backtrace diff --git a/tests/fail/stacked_borrows/pass_invalid_shr.stderr b/tests/fail/stacked_borrows/pass_invalid_shr.stderr index c14b35c75c..5243858a91 100644 --- a/tests/fail/stacked_borrows/pass_invalid_shr.stderr +++ b/tests/fail/stacked_borrows/pass_invalid_shr.stderr @@ -19,7 +19,7 @@ help: was later invalidated at offsets [0x0..0x4] by a write access | LL | unsafe { *xraw = 42 }; // unfreeze | ^^^^^^^^^^ - = note: BACKTRACE: + = note: BACKTRACE (of the first span): = note: inside `main` at $DIR/pass_invalid_shr.rs:LL:CC note: some details are omitted, run with `MIRIFLAGS=-Zmiri-backtrace=full` for a verbose backtrace diff --git a/tests/fail/stacked_borrows/pointer_smuggling.stderr b/tests/fail/stacked_borrows/pointer_smuggling.stderr index 7d58d1aebb..e20b5b89a2 100644 --- a/tests/fail/stacked_borrows/pointer_smuggling.stderr +++ b/tests/fail/stacked_borrows/pointer_smuggling.stderr @@ -19,7 +19,7 @@ help: was later invalidated at offsets [0x0..0x1] by a write access | LL | *val = 2; // this invalidates any raw ptrs `fun1` might have created. | ^^^^^^^^ - = note: BACKTRACE: + = note: BACKTRACE (of the first span): = note: inside `fun2` at $DIR/pointer_smuggling.rs:LL:CC note: inside `main` --> $DIR/pointer_smuggling.rs:LL:CC diff --git a/tests/fail/stacked_borrows/raw_tracking.stderr b/tests/fail/stacked_borrows/raw_tracking.stderr index d75934445e..9f7e7a058d 100644 --- a/tests/fail/stacked_borrows/raw_tracking.stderr +++ b/tests/fail/stacked_borrows/raw_tracking.stderr @@ -19,7 +19,7 @@ help: was later invalidated at offsets [0x0..0x4] by a Unique retag | LL | let raw2 = &mut l as *mut _; // invalidates raw1 | ^^^^^^ - = note: BACKTRACE: + = note: BACKTRACE (of the first span): = note: inside `main` at $DIR/raw_tracking.rs:LL:CC note: some details are omitted, run with `MIRIFLAGS=-Zmiri-backtrace=full` for a verbose backtrace diff --git a/tests/fail/stacked_borrows/retag_data_race_read.stderr b/tests/fail/stacked_borrows/retag_data_race_read.stderr index 790fd51ec3..26607e1a69 100644 --- a/tests/fail/stacked_borrows/retag_data_race_read.stderr +++ b/tests/fail/stacked_borrows/retag_data_race_read.stderr @@ -11,7 +11,7 @@ LL | let _r = &*p; | ^^^ = help: this indicates a bug in the program: it performed an invalid operation, and caused Undefined Behavior = help: see https://doc.rust-lang.org/nightly/reference/behavior-considered-undefined.html for further information - = note: BACKTRACE: + = note: BACKTRACE (of the first span): = note: inside `thread_2` at $DIR/retag_data_race_read.rs:LL:CC note: inside closure --> $DIR/retag_data_race_read.rs:LL:CC diff --git a/tests/fail/stacked_borrows/retag_data_race_write.stderr b/tests/fail/stacked_borrows/retag_data_race_write.stderr index c5b8b4c41f..33839d2647 100644 --- a/tests/fail/stacked_borrows/retag_data_race_write.stderr +++ b/tests/fail/stacked_borrows/retag_data_race_write.stderr @@ -11,7 +11,7 @@ LL | let _r = &mut *p; | ^^^^^^^ = help: this indicates a bug in the program: it performed an invalid operation, and caused Undefined Behavior = help: see https://doc.rust-lang.org/nightly/reference/behavior-considered-undefined.html for further information - = note: BACKTRACE: + = note: BACKTRACE (of the first span): = note: inside `thread_2` at $DIR/retag_data_race_write.rs:LL:CC note: inside closure --> $DIR/retag_data_race_write.rs:LL:CC diff --git a/tests/fail/stacked_borrows/return_invalid_mut.stderr b/tests/fail/stacked_borrows/return_invalid_mut.stderr index 1b28f780c1..2bf91b676c 100644 --- a/tests/fail/stacked_borrows/return_invalid_mut.stderr +++ b/tests/fail/stacked_borrows/return_invalid_mut.stderr @@ -19,7 +19,7 @@ help: was later invalidated at offsets [0x0..0x8] by a read access | LL | let _val = unsafe { *xraw }; // invalidate xref | ^^^^^ - = note: BACKTRACE: + = note: BACKTRACE (of the first span): = note: inside `foo` at $DIR/return_invalid_mut.rs:LL:CC note: inside `main` --> $DIR/return_invalid_mut.rs:LL:CC diff --git a/tests/fail/stacked_borrows/return_invalid_mut_option.stderr b/tests/fail/stacked_borrows/return_invalid_mut_option.stderr index db14dcafa0..ff00c54570 100644 --- a/tests/fail/stacked_borrows/return_invalid_mut_option.stderr +++ b/tests/fail/stacked_borrows/return_invalid_mut_option.stderr @@ -19,7 +19,7 @@ help: was later invalidated at offsets [0x0..0x8] by a read access | LL | let _val = unsafe { *xraw }; // invalidate xref | ^^^^^ - = note: BACKTRACE: + = note: BACKTRACE (of the first span): = note: inside `foo` at $DIR/return_invalid_mut_option.rs:LL:CC note: inside `main` --> $DIR/return_invalid_mut_option.rs:LL:CC diff --git a/tests/fail/stacked_borrows/return_invalid_mut_tuple.stderr b/tests/fail/stacked_borrows/return_invalid_mut_tuple.stderr index 81ed4218aa..61d041a881 100644 --- a/tests/fail/stacked_borrows/return_invalid_mut_tuple.stderr +++ b/tests/fail/stacked_borrows/return_invalid_mut_tuple.stderr @@ -19,7 +19,7 @@ help: was later invalidated at offsets [0x0..0x8] by a read access | LL | let _val = unsafe { *xraw }; // invalidate xref | ^^^^^ - = note: BACKTRACE: + = note: BACKTRACE (of the first span): = note: inside `foo` at $DIR/return_invalid_mut_tuple.rs:LL:CC note: inside `main` --> $DIR/return_invalid_mut_tuple.rs:LL:CC diff --git a/tests/fail/stacked_borrows/return_invalid_shr.stderr b/tests/fail/stacked_borrows/return_invalid_shr.stderr index 9c8cc50b2d..d3a73a00fa 100644 --- a/tests/fail/stacked_borrows/return_invalid_shr.stderr +++ b/tests/fail/stacked_borrows/return_invalid_shr.stderr @@ -19,7 +19,7 @@ help: was later invalidated at offsets [0x0..0x8] by a write access | LL | unsafe { *xraw = (42, 23) }; // unfreeze | ^^^^^^^^^^^^^^^^ - = note: BACKTRACE: + = note: BACKTRACE (of the first span): = note: inside `foo` at $DIR/return_invalid_shr.rs:LL:CC note: inside `main` --> $DIR/return_invalid_shr.rs:LL:CC diff --git a/tests/fail/stacked_borrows/return_invalid_shr_option.stderr b/tests/fail/stacked_borrows/return_invalid_shr_option.stderr index 00ce6f6cd5..f14e8b8532 100644 --- a/tests/fail/stacked_borrows/return_invalid_shr_option.stderr +++ b/tests/fail/stacked_borrows/return_invalid_shr_option.stderr @@ -19,7 +19,7 @@ help: was later invalidated at offsets [0x0..0x8] by a write access | LL | unsafe { *xraw = (42, 23) }; // unfreeze | ^^^^^^^^^^^^^^^^ - = note: BACKTRACE: + = note: BACKTRACE (of the first span): = note: inside `foo` at $DIR/return_invalid_shr_option.rs:LL:CC note: inside `main` --> $DIR/return_invalid_shr_option.rs:LL:CC diff --git a/tests/fail/stacked_borrows/return_invalid_shr_tuple.stderr b/tests/fail/stacked_borrows/return_invalid_shr_tuple.stderr index bbd17b1284..9ddaad4d1b 100644 --- a/tests/fail/stacked_borrows/return_invalid_shr_tuple.stderr +++ b/tests/fail/stacked_borrows/return_invalid_shr_tuple.stderr @@ -19,7 +19,7 @@ help: was later invalidated at offsets [0x0..0x8] by a write access | LL | unsafe { *xraw = (42, 23) }; // unfreeze | ^^^^^^^^^^^^^^^^ - = note: BACKTRACE: + = note: BACKTRACE (of the first span): = note: inside `foo` at $DIR/return_invalid_shr_tuple.rs:LL:CC note: inside `main` --> $DIR/return_invalid_shr_tuple.rs:LL:CC diff --git a/tests/fail/stacked_borrows/shared_rw_borrows_are_weak1.stderr b/tests/fail/stacked_borrows/shared_rw_borrows_are_weak1.stderr index 3a139c3ab2..589e1291ba 100644 --- a/tests/fail/stacked_borrows/shared_rw_borrows_are_weak1.stderr +++ b/tests/fail/stacked_borrows/shared_rw_borrows_are_weak1.stderr @@ -19,7 +19,7 @@ help: was later invalidated at offsets [0x0..0x4] by a Unique retag | LL | shr_rw.set(1); | ^^^^^^^^^^^^^ - = note: BACKTRACE: + = note: BACKTRACE (of the first span): = note: inside `main` at $DIR/shared_rw_borrows_are_weak1.rs:LL:CC note: some details are omitted, run with `MIRIFLAGS=-Zmiri-backtrace=full` for a verbose backtrace diff --git a/tests/fail/stacked_borrows/shared_rw_borrows_are_weak2.stderr b/tests/fail/stacked_borrows/shared_rw_borrows_are_weak2.stderr index 0609a73e79..0e37c4ffb3 100644 --- a/tests/fail/stacked_borrows/shared_rw_borrows_are_weak2.stderr +++ b/tests/fail/stacked_borrows/shared_rw_borrows_are_weak2.stderr @@ -19,7 +19,7 @@ help: was later invalidated at offsets [$HEX..$HEX] by a Unique retag | LL | shr_rw.replace(1); | ^^^^^^^^^^^^^^^^^ - = note: BACKTRACE: + = note: BACKTRACE (of the first span): = note: inside `main` at $DIR/shared_rw_borrows_are_weak2.rs:LL:CC note: some details are omitted, run with `MIRIFLAGS=-Zmiri-backtrace=full` for a verbose backtrace diff --git a/tests/fail/stacked_borrows/shr_frozen_violation1.stderr b/tests/fail/stacked_borrows/shr_frozen_violation1.stderr index fe0ac21131..a69116f2af 100644 --- a/tests/fail/stacked_borrows/shr_frozen_violation1.stderr +++ b/tests/fail/stacked_borrows/shr_frozen_violation1.stderr @@ -14,7 +14,7 @@ help: was created by a SharedReadOnly retag at offsets [0x0..0x4] | LL | *(x as *const i32 as *mut i32) = 7; | ^ - = note: BACKTRACE: + = note: BACKTRACE (of the first span): = note: inside `unknown_code` at $DIR/shr_frozen_violation1.rs:LL:CC note: inside `foo` --> $DIR/shr_frozen_violation1.rs:LL:CC diff --git a/tests/fail/stacked_borrows/track_caller.stderr b/tests/fail/stacked_borrows/track_caller.stderr index 6f1d0ccd34..05be0d3f1e 100644 --- a/tests/fail/stacked_borrows/track_caller.stderr +++ b/tests/fail/stacked_borrows/track_caller.stderr @@ -19,7 +19,7 @@ help: was later invalidated at offsets [0x0..0x4] by a read access | LL | callee(xraw); | ^^^^^^^^^^^^ - = note: BACKTRACE: + = note: BACKTRACE (of the first span): = note: inside `main` at $DIR/track_caller.rs:LL:CC note: some details are omitted, run with `MIRIFLAGS=-Zmiri-backtrace=full` for a verbose backtrace diff --git a/tests/fail/stacked_borrows/transmute-is-no-escape.stderr b/tests/fail/stacked_borrows/transmute-is-no-escape.stderr index a2ecb07fd3..ac962311d4 100644 --- a/tests/fail/stacked_borrows/transmute-is-no-escape.stderr +++ b/tests/fail/stacked_borrows/transmute-is-no-escape.stderr @@ -14,7 +14,7 @@ help: was created by a SharedReadWrite retag at offsets [0x4..0x8] | LL | let raw = (&mut x[1] as *mut i32).wrapping_offset(-1); | ^^^^^^^^^ - = note: BACKTRACE: + = note: BACKTRACE (of the first span): = note: inside `main` at $DIR/transmute-is-no-escape.rs:LL:CC note: some details are omitted, run with `MIRIFLAGS=-Zmiri-backtrace=full` for a verbose backtrace diff --git a/tests/fail/stacked_borrows/unescaped_static.stderr b/tests/fail/stacked_borrows/unescaped_static.stderr index 01a4bf4340..7a40d1078b 100644 --- a/tests/fail/stacked_borrows/unescaped_static.stderr +++ b/tests/fail/stacked_borrows/unescaped_static.stderr @@ -14,7 +14,7 @@ help: was created by a SharedReadOnly retag at offsets [0x0..0x1] | LL | let ptr_to_first = &ARRAY[0] as *const u8; | ^^^^^^^^^ - = note: BACKTRACE: + = note: BACKTRACE (of the first span): = note: inside `main` at $DIR/unescaped_static.rs:LL:CC note: some details are omitted, run with `MIRIFLAGS=-Zmiri-backtrace=full` for a verbose backtrace diff --git a/tests/fail/stacked_borrows/zst_slice.stderr b/tests/fail/stacked_borrows/zst_slice.stderr index e134ee2845..950abc4cbc 100644 --- a/tests/fail/stacked_borrows/zst_slice.stderr +++ b/tests/fail/stacked_borrows/zst_slice.stderr @@ -14,7 +14,7 @@ help: would have been created here, but this is a zero-size retag ([0x0..0 | LL | assert_eq!(*s.get_unchecked(1), 2); | ^^^^^^^^^^^^^^^^^^ - = note: BACKTRACE: + = note: BACKTRACE (of the first span): = note: inside `core::slice::::get_unchecked::` at RUSTLIB/core/src/slice/mod.rs:LL:CC note: inside `main` --> $DIR/zst_slice.rs:LL:CC From 60a100ab6a84a478d1729a544ddef6315c334b3e Mon Sep 17 00:00:00 2001 From: Ben Kimock Date: Fri, 23 Dec 2022 13:45:43 -0500 Subject: [PATCH 24/28] Mention and number the components of a race in the order the interpreter sees them --- src/concurrency/data_race.rs | 10 +++++----- src/diagnostics.rs | 6 +++--- tests/fail/data_race/alloc_read_race.rs | 2 +- tests/fail/data_race/alloc_read_race.stderr | 6 +++--- tests/fail/data_race/alloc_write_race.rs | 2 +- tests/fail/data_race/alloc_write_race.stderr | 6 +++--- tests/fail/data_race/atomic_read_na_write_race1.rs | 2 +- tests/fail/data_race/atomic_read_na_write_race1.stderr | 6 +++--- tests/fail/data_race/atomic_read_na_write_race2.rs | 2 +- tests/fail/data_race/atomic_read_na_write_race2.stderr | 6 +++--- tests/fail/data_race/atomic_write_na_read_race1.rs | 2 +- tests/fail/data_race/atomic_write_na_read_race1.stderr | 6 +++--- tests/fail/data_race/atomic_write_na_read_race2.rs | 2 +- tests/fail/data_race/atomic_write_na_read_race2.stderr | 6 +++--- tests/fail/data_race/atomic_write_na_write_race1.rs | 2 +- .../fail/data_race/atomic_write_na_write_race1.stderr | 6 +++--- tests/fail/data_race/atomic_write_na_write_race2.rs | 2 +- .../fail/data_race/atomic_write_na_write_race2.stderr | 6 +++--- tests/fail/data_race/dangling_thread_async_race.stderr | 6 +++--- tests/fail/data_race/dangling_thread_race.rs | 2 +- tests/fail/data_race/dangling_thread_race.stderr | 6 +++--- tests/fail/data_race/dealloc_read_race1.rs | 2 +- tests/fail/data_race/dealloc_read_race1.stderr | 6 +++--- tests/fail/data_race/dealloc_read_race2.rs | 2 +- tests/fail/data_race/dealloc_read_race_stack.rs | 2 +- tests/fail/data_race/dealloc_read_race_stack.stderr | 6 +++--- tests/fail/data_race/dealloc_write_race1.rs | 2 +- tests/fail/data_race/dealloc_write_race1.stderr | 6 +++--- tests/fail/data_race/dealloc_write_race2.rs | 2 +- tests/fail/data_race/dealloc_write_race_stack.rs | 2 +- tests/fail/data_race/dealloc_write_race_stack.stderr | 6 +++--- tests/fail/data_race/enable_after_join_to_main.stderr | 6 +++--- tests/fail/data_race/fence_after_load.rs | 2 +- tests/fail/data_race/fence_after_load.stderr | 6 +++--- tests/fail/data_race/read_write_race.rs | 2 +- tests/fail/data_race/read_write_race.stderr | 6 +++--- tests/fail/data_race/read_write_race_stack.rs | 2 +- tests/fail/data_race/read_write_race_stack.stderr | 6 +++--- tests/fail/data_race/relax_acquire_race.rs | 2 +- tests/fail/data_race/relax_acquire_race.stderr | 6 +++--- tests/fail/data_race/release_seq_race.rs | 2 +- tests/fail/data_race/release_seq_race.stderr | 6 +++--- tests/fail/data_race/release_seq_race_same_thread.rs | 2 +- .../fail/data_race/release_seq_race_same_thread.stderr | 6 +++--- tests/fail/data_race/rmw_race.rs | 2 +- tests/fail/data_race/rmw_race.stderr | 6 +++--- tests/fail/data_race/stack_pop_race.rs | 2 +- tests/fail/data_race/stack_pop_race.stderr | 6 +++--- tests/fail/data_race/write_write_race.stderr | 6 +++--- tests/fail/data_race/write_write_race_stack.stderr | 6 +++--- tests/fail/stacked_borrows/retag_data_race_read.rs | 2 +- tests/fail/stacked_borrows/retag_data_race_read.stderr | 6 +++--- .../fail/stacked_borrows/retag_data_race_write.stderr | 6 +++--- 53 files changed, 113 insertions(+), 113 deletions(-) diff --git a/src/concurrency/data_race.rs b/src/concurrency/data_race.rs index 5dcaebadc4..9646327966 100644 --- a/src/concurrency/data_race.rs +++ b/src/concurrency/data_race.rs @@ -811,15 +811,15 @@ impl VClockAlloc { Err(err_machine_stop!(TerminationInfo::DataRace { ptr: ptr_dbg, op1: RacingOp { - action: action.to_string(), - thread_info: current_thread_info, - span: current_clocks.clock.as_slice()[current_index.index()].span_data(), - }, - op2: RacingOp { action: other_action.to_string(), thread_info: other_thread_info, span: other_clock.as_slice()[other_thread.index()].span_data(), }, + op2: RacingOp { + action: action.to_string(), + thread_info: current_thread_info, + span: current_clocks.clock.as_slice()[current_index.index()].span_data(), + }, }))? } diff --git a/src/diagnostics.rs b/src/diagnostics.rs index 2087d0cb54..035c0e6423 100644 --- a/src/diagnostics.rs +++ b/src/diagnostics.rs @@ -69,7 +69,7 @@ impl fmt::Display for TerminationInfo { DataRace { ptr, op1, op2 } => write!( f, - "Data race detected between (1) {} on {} and (2) {} on {} at {ptr:?}. (1) just happened here", + "Data race detected between (1) {} on {} and (2) {} on {} at {ptr:?}. (2) just happened here", op1.action, op1.thread_info, op2.action, op2.thread_info ), } @@ -222,9 +222,9 @@ pub fn report_error<'tcx, 'mir>( vec![(Some(*span), format!("the `{link_name}` symbol is defined here"))], Int2PtrWithStrictProvenance => vec![(None, format!("use Strict Provenance APIs (https://doc.rust-lang.org/nightly/std/ptr/index.html#strict-provenance, https://crates.io/crates/sptr) instead"))], - DataRace { op2, .. } => + DataRace { op1, .. } => vec![ - (Some(op2.span), format!("and (2) occurred earlier here")), + (Some(op1.span), format!("and (1) occurred earlier here")), (None, format!("this indicates a bug in the program: it performed an invalid operation, and caused Undefined Behavior")), (None, format!("see https://doc.rust-lang.org/nightly/reference/behavior-considered-undefined.html for further information")), ], diff --git a/tests/fail/data_race/alloc_read_race.rs b/tests/fail/data_race/alloc_read_race.rs index ba1d54e36c..2698c63a44 100644 --- a/tests/fail/data_race/alloc_read_race.rs +++ b/tests/fail/data_race/alloc_read_race.rs @@ -37,7 +37,7 @@ pub fn main() { let pointer = &*ptr.0; // Note: could also error due to reading uninitialized memory, but the data-race detector triggers first. - *pointer.load(Ordering::Relaxed) //~ ERROR: Data race detected between (1) Read on thread `` and (2) Allocate on thread `` + *pointer.load(Ordering::Relaxed) //~ ERROR: Data race detected between (1) Allocate on thread `` and (2) Read on thread `` }); j1.join().unwrap(); diff --git a/tests/fail/data_race/alloc_read_race.stderr b/tests/fail/data_race/alloc_read_race.stderr index 59b3802416..5b809722c7 100644 --- a/tests/fail/data_race/alloc_read_race.stderr +++ b/tests/fail/data_race/alloc_read_race.stderr @@ -1,10 +1,10 @@ -error: Undefined Behavior: Data race detected between (1) Read on thread `` and (2) Allocate on thread `` at ALLOC. (1) just happened here +error: Undefined Behavior: Data race detected between (1) Allocate on thread `` and (2) Read on thread `` at ALLOC. (2) just happened here --> $DIR/alloc_read_race.rs:LL:CC | LL | *pointer.load(Ordering::Relaxed) - | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ Data race detected between (1) Read on thread `` and (2) Allocate on thread `` at ALLOC. (1) just happened here + | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ Data race detected between (1) Allocate on thread `` and (2) Read on thread `` at ALLOC. (2) just happened here | -help: and (2) occurred earlier here +help: and (1) occurred earlier here --> $DIR/alloc_read_race.rs:LL:CC | LL | pointer.store(Box::into_raw(Box::new_uninit()), Ordering::Relaxed); diff --git a/tests/fail/data_race/alloc_write_race.rs b/tests/fail/data_race/alloc_write_race.rs index 9f85fb13ab..b78d5ef27d 100644 --- a/tests/fail/data_race/alloc_write_race.rs +++ b/tests/fail/data_race/alloc_write_race.rs @@ -35,7 +35,7 @@ pub fn main() { let j2 = spawn(move || { let pointer = &*ptr.0; - *pointer.load(Ordering::Relaxed) = 2; //~ ERROR: Data race detected between (1) Write on thread `` and (2) Allocate on thread `` + *pointer.load(Ordering::Relaxed) = 2; //~ ERROR: Data race detected between (1) Allocate on thread `` and (2) Write on thread `` }); j1.join().unwrap(); diff --git a/tests/fail/data_race/alloc_write_race.stderr b/tests/fail/data_race/alloc_write_race.stderr index 0564e4b5bf..8520bcf4e4 100644 --- a/tests/fail/data_race/alloc_write_race.stderr +++ b/tests/fail/data_race/alloc_write_race.stderr @@ -1,10 +1,10 @@ -error: Undefined Behavior: Data race detected between (1) Write on thread `` and (2) Allocate on thread `` at ALLOC. (1) just happened here +error: Undefined Behavior: Data race detected between (1) Allocate on thread `` and (2) Write on thread `` at ALLOC. (2) just happened here --> $DIR/alloc_write_race.rs:LL:CC | LL | *pointer.load(Ordering::Relaxed) = 2; - | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ Data race detected between (1) Write on thread `` and (2) Allocate on thread `` at ALLOC. (1) just happened here + | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ Data race detected between (1) Allocate on thread `` and (2) Write on thread `` at ALLOC. (2) just happened here | -help: and (2) occurred earlier here +help: and (1) occurred earlier here --> $DIR/alloc_write_race.rs:LL:CC | LL | .store(Box::into_raw(Box::::new_uninit()) as *mut usize, Ordering::Relaxed); diff --git a/tests/fail/data_race/atomic_read_na_write_race1.rs b/tests/fail/data_race/atomic_read_na_write_race1.rs index 4aa96de877..3f811d0f64 100644 --- a/tests/fail/data_race/atomic_read_na_write_race1.rs +++ b/tests/fail/data_race/atomic_read_na_write_race1.rs @@ -20,7 +20,7 @@ pub fn main() { }); let j2 = spawn(move || { - (&*c.0).load(Ordering::SeqCst) //~ ERROR: Data race detected between (1) Atomic Load on thread `` and (2) Write on thread `` + (&*c.0).load(Ordering::SeqCst) //~ ERROR: Data race detected between (1) Write on thread `` and (2) Atomic Load on thread `` }); j1.join().unwrap(); diff --git a/tests/fail/data_race/atomic_read_na_write_race1.stderr b/tests/fail/data_race/atomic_read_na_write_race1.stderr index ab7a617810..e25629e14e 100644 --- a/tests/fail/data_race/atomic_read_na_write_race1.stderr +++ b/tests/fail/data_race/atomic_read_na_write_race1.stderr @@ -1,10 +1,10 @@ -error: Undefined Behavior: Data race detected between (1) Atomic Load on thread `` and (2) Write on thread `` at ALLOC. (1) just happened here +error: Undefined Behavior: Data race detected between (1) Write on thread `` and (2) Atomic Load on thread `` at ALLOC. (2) just happened here --> $DIR/atomic_read_na_write_race1.rs:LL:CC | LL | (&*c.0).load(Ordering::SeqCst) - | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ Data race detected between (1) Atomic Load on thread `` and (2) Write on thread `` at ALLOC. (1) just happened here + | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ Data race detected between (1) Write on thread `` and (2) Atomic Load on thread `` at ALLOC. (2) just happened here | -help: and (2) occurred earlier here +help: and (1) occurred earlier here --> $DIR/atomic_read_na_write_race1.rs:LL:CC | LL | *(c.0 as *mut usize) = 32; diff --git a/tests/fail/data_race/atomic_read_na_write_race2.rs b/tests/fail/data_race/atomic_read_na_write_race2.rs index 135017d35b..34fb3ac066 100644 --- a/tests/fail/data_race/atomic_read_na_write_race2.rs +++ b/tests/fail/data_race/atomic_read_na_write_race2.rs @@ -23,7 +23,7 @@ pub fn main() { let j2 = spawn(move || { let atomic_ref = &mut *c.0; - *atomic_ref.get_mut() = 32; //~ ERROR: Data race detected between (1) Write on thread `` and (2) Atomic Load on thread `` + *atomic_ref.get_mut() = 32; //~ ERROR: Data race detected between (1) Atomic Load on thread `` and (2) Write on thread `` }); j1.join().unwrap(); diff --git a/tests/fail/data_race/atomic_read_na_write_race2.stderr b/tests/fail/data_race/atomic_read_na_write_race2.stderr index cd8e095a6e..6953b1403b 100644 --- a/tests/fail/data_race/atomic_read_na_write_race2.stderr +++ b/tests/fail/data_race/atomic_read_na_write_race2.stderr @@ -1,10 +1,10 @@ -error: Undefined Behavior: Data race detected between (1) Write on thread `` and (2) Atomic Load on thread `` at ALLOC. (1) just happened here +error: Undefined Behavior: Data race detected between (1) Atomic Load on thread `` and (2) Write on thread `` at ALLOC. (2) just happened here --> $DIR/atomic_read_na_write_race2.rs:LL:CC | LL | *atomic_ref.get_mut() = 32; - | ^^^^^^^^^^^^^^^^^^^^^^^^^^ Data race detected between (1) Write on thread `` and (2) Atomic Load on thread `` at ALLOC. (1) just happened here + | ^^^^^^^^^^^^^^^^^^^^^^^^^^ Data race detected between (1) Atomic Load on thread `` and (2) Write on thread `` at ALLOC. (2) just happened here | -help: and (2) occurred earlier here +help: and (1) occurred earlier here --> $DIR/atomic_read_na_write_race2.rs:LL:CC | LL | atomic_ref.load(Ordering::SeqCst) diff --git a/tests/fail/data_race/atomic_write_na_read_race1.rs b/tests/fail/data_race/atomic_write_na_read_race1.rs index 345b53ab5c..63b0806f3b 100644 --- a/tests/fail/data_race/atomic_write_na_read_race1.rs +++ b/tests/fail/data_race/atomic_write_na_read_race1.rs @@ -23,7 +23,7 @@ pub fn main() { let j2 = spawn(move || { let atomic_ref = &mut *c.0; - *atomic_ref.get_mut() //~ ERROR: Data race detected between (1) Read on thread `` and (2) Atomic Store on thread `` + *atomic_ref.get_mut() //~ ERROR: Data race detected between (1) Atomic Store on thread `` and (2) Read on thread `` }); j1.join().unwrap(); diff --git a/tests/fail/data_race/atomic_write_na_read_race1.stderr b/tests/fail/data_race/atomic_write_na_read_race1.stderr index b339e5adf8..e52b8895a6 100644 --- a/tests/fail/data_race/atomic_write_na_read_race1.stderr +++ b/tests/fail/data_race/atomic_write_na_read_race1.stderr @@ -1,10 +1,10 @@ -error: Undefined Behavior: Data race detected between (1) Read on thread `` and (2) Atomic Store on thread `` at ALLOC. (1) just happened here +error: Undefined Behavior: Data race detected between (1) Atomic Store on thread `` and (2) Read on thread `` at ALLOC. (2) just happened here --> $DIR/atomic_write_na_read_race1.rs:LL:CC | LL | *atomic_ref.get_mut() - | ^^^^^^^^^^^^^^^^^^^^^ Data race detected between (1) Read on thread `` and (2) Atomic Store on thread `` at ALLOC. (1) just happened here + | ^^^^^^^^^^^^^^^^^^^^^ Data race detected between (1) Atomic Store on thread `` and (2) Read on thread `` at ALLOC. (2) just happened here | -help: and (2) occurred earlier here +help: and (1) occurred earlier here --> $DIR/atomic_write_na_read_race1.rs:LL:CC | LL | atomic_ref.store(32, Ordering::SeqCst) diff --git a/tests/fail/data_race/atomic_write_na_read_race2.rs b/tests/fail/data_race/atomic_write_na_read_race2.rs index bc37f6442e..9092254be2 100644 --- a/tests/fail/data_race/atomic_write_na_read_race2.rs +++ b/tests/fail/data_race/atomic_write_na_read_race2.rs @@ -20,7 +20,7 @@ pub fn main() { }); let j2 = spawn(move || { - (&*c.0).store(32, Ordering::SeqCst); //~ ERROR: Data race detected between (1) Atomic Store on thread `` and (2) Read on thread `` + (&*c.0).store(32, Ordering::SeqCst); //~ ERROR: Data race detected between (1) Read on thread `` and (2) Atomic Store on thread `` }); j1.join().unwrap(); diff --git a/tests/fail/data_race/atomic_write_na_read_race2.stderr b/tests/fail/data_race/atomic_write_na_read_race2.stderr index 3968620349..513d13b034 100644 --- a/tests/fail/data_race/atomic_write_na_read_race2.stderr +++ b/tests/fail/data_race/atomic_write_na_read_race2.stderr @@ -1,10 +1,10 @@ -error: Undefined Behavior: Data race detected between (1) Atomic Store on thread `` and (2) Read on thread `` at ALLOC. (1) just happened here +error: Undefined Behavior: Data race detected between (1) Read on thread `` and (2) Atomic Store on thread `` at ALLOC. (2) just happened here --> $DIR/atomic_write_na_read_race2.rs:LL:CC | LL | (&*c.0).store(32, Ordering::SeqCst); - | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ Data race detected between (1) Atomic Store on thread `` and (2) Read on thread `` at ALLOC. (1) just happened here + | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ Data race detected between (1) Read on thread `` and (2) Atomic Store on thread `` at ALLOC. (2) just happened here | -help: and (2) occurred earlier here +help: and (1) occurred earlier here --> $DIR/atomic_write_na_read_race2.rs:LL:CC | LL | let _val = *(c.0 as *mut usize); diff --git a/tests/fail/data_race/atomic_write_na_write_race1.rs b/tests/fail/data_race/atomic_write_na_write_race1.rs index f1647ce4a9..5a713905f4 100644 --- a/tests/fail/data_race/atomic_write_na_write_race1.rs +++ b/tests/fail/data_race/atomic_write_na_write_race1.rs @@ -20,7 +20,7 @@ pub fn main() { }); let j2 = spawn(move || { - (&*c.0).store(64, Ordering::SeqCst); //~ ERROR: Data race detected between (1) Atomic Store on thread `` and (2) Write on thread `` + (&*c.0).store(64, Ordering::SeqCst); //~ ERROR: Data race detected between (1) Write on thread `` and (2) Atomic Store on thread `` }); j1.join().unwrap(); diff --git a/tests/fail/data_race/atomic_write_na_write_race1.stderr b/tests/fail/data_race/atomic_write_na_write_race1.stderr index fd360797d3..2ff70ef1f6 100644 --- a/tests/fail/data_race/atomic_write_na_write_race1.stderr +++ b/tests/fail/data_race/atomic_write_na_write_race1.stderr @@ -1,10 +1,10 @@ -error: Undefined Behavior: Data race detected between (1) Atomic Store on thread `` and (2) Write on thread `` at ALLOC. (1) just happened here +error: Undefined Behavior: Data race detected between (1) Write on thread `` and (2) Atomic Store on thread `` at ALLOC. (2) just happened here --> $DIR/atomic_write_na_write_race1.rs:LL:CC | LL | (&*c.0).store(64, Ordering::SeqCst); - | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ Data race detected between (1) Atomic Store on thread `` and (2) Write on thread `` at ALLOC. (1) just happened here + | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ Data race detected between (1) Write on thread `` and (2) Atomic Store on thread `` at ALLOC. (2) just happened here | -help: and (2) occurred earlier here +help: and (1) occurred earlier here --> $DIR/atomic_write_na_write_race1.rs:LL:CC | LL | *(c.0 as *mut usize) = 32; diff --git a/tests/fail/data_race/atomic_write_na_write_race2.rs b/tests/fail/data_race/atomic_write_na_write_race2.rs index 343b46ea4e..5848aa262b 100644 --- a/tests/fail/data_race/atomic_write_na_write_race2.rs +++ b/tests/fail/data_race/atomic_write_na_write_race2.rs @@ -23,7 +23,7 @@ pub fn main() { let j2 = spawn(move || { let atomic_ref = &mut *c.0; - *atomic_ref.get_mut() = 32; //~ ERROR: Data race detected between (1) Write on thread `` and (2) Atomic Store on thread `` + *atomic_ref.get_mut() = 32; //~ ERROR: Data race detected between (1) Atomic Store on thread `` and (2) Write on thread `` }); j1.join().unwrap(); diff --git a/tests/fail/data_race/atomic_write_na_write_race2.stderr b/tests/fail/data_race/atomic_write_na_write_race2.stderr index 4e2494cf57..166b4d2269 100644 --- a/tests/fail/data_race/atomic_write_na_write_race2.stderr +++ b/tests/fail/data_race/atomic_write_na_write_race2.stderr @@ -1,10 +1,10 @@ -error: Undefined Behavior: Data race detected between (1) Write on thread `` and (2) Atomic Store on thread `` at ALLOC. (1) just happened here +error: Undefined Behavior: Data race detected between (1) Atomic Store on thread `` and (2) Write on thread `` at ALLOC. (2) just happened here --> $DIR/atomic_write_na_write_race2.rs:LL:CC | LL | *atomic_ref.get_mut() = 32; - | ^^^^^^^^^^^^^^^^^^^^^^^^^^ Data race detected between (1) Write on thread `` and (2) Atomic Store on thread `` at ALLOC. (1) just happened here + | ^^^^^^^^^^^^^^^^^^^^^^^^^^ Data race detected between (1) Atomic Store on thread `` and (2) Write on thread `` at ALLOC. (2) just happened here | -help: and (2) occurred earlier here +help: and (1) occurred earlier here --> $DIR/atomic_write_na_write_race2.rs:LL:CC | LL | atomic_ref.store(64, Ordering::SeqCst); diff --git a/tests/fail/data_race/dangling_thread_async_race.stderr b/tests/fail/data_race/dangling_thread_async_race.stderr index aba051a2b6..a08b21ab0e 100644 --- a/tests/fail/data_race/dangling_thread_async_race.stderr +++ b/tests/fail/data_race/dangling_thread_async_race.stderr @@ -1,10 +1,10 @@ -error: Undefined Behavior: Data race detected between (1) Write on thread `` and (2) Write on thread `` at ALLOC. (1) just happened here +error: Undefined Behavior: Data race detected between (1) Write on thread `` and (2) Write on thread `` at ALLOC. (2) just happened here --> $DIR/dangling_thread_async_race.rs:LL:CC | LL | *c.0 = 64; - | ^^^^^^^^^ Data race detected between (1) Write on thread `` and (2) Write on thread `` at ALLOC. (1) just happened here + | ^^^^^^^^^ Data race detected between (1) Write on thread `` and (2) Write on thread `` at ALLOC. (2) just happened here | -help: and (2) occurred earlier here +help: and (1) occurred earlier here --> $DIR/dangling_thread_async_race.rs:LL:CC | LL | *c.0 = 32; diff --git a/tests/fail/data_race/dangling_thread_race.rs b/tests/fail/data_race/dangling_thread_race.rs index 3ead4eedd7..4c7fbdd7fe 100644 --- a/tests/fail/data_race/dangling_thread_race.rs +++ b/tests/fail/data_race/dangling_thread_race.rs @@ -33,6 +33,6 @@ fn main() { spawn(|| ()).join().unwrap(); unsafe { - *c.0 = 64; //~ ERROR: Data race detected between (1) Write on thread `main` and (2) Write on thread `` + *c.0 = 64; //~ ERROR: Data race detected between (1) Write on thread `` and (2) Write on thread `main` } } diff --git a/tests/fail/data_race/dangling_thread_race.stderr b/tests/fail/data_race/dangling_thread_race.stderr index dc35ccf354..aa2e6a6f71 100644 --- a/tests/fail/data_race/dangling_thread_race.stderr +++ b/tests/fail/data_race/dangling_thread_race.stderr @@ -1,10 +1,10 @@ -error: Undefined Behavior: Data race detected between (1) Write on thread `main` and (2) Write on thread `` at ALLOC. (1) just happened here +error: Undefined Behavior: Data race detected between (1) Write on thread `` and (2) Write on thread `main` at ALLOC. (2) just happened here --> $DIR/dangling_thread_race.rs:LL:CC | LL | *c.0 = 64; - | ^^^^^^^^^ Data race detected between (1) Write on thread `main` and (2) Write on thread `` at ALLOC. (1) just happened here + | ^^^^^^^^^ Data race detected between (1) Write on thread `` and (2) Write on thread `main` at ALLOC. (2) just happened here | -help: and (2) occurred earlier here +help: and (1) occurred earlier here --> $DIR/dangling_thread_race.rs:LL:CC | LL | *c.0 = 32; diff --git a/tests/fail/data_race/dealloc_read_race1.rs b/tests/fail/data_race/dealloc_read_race1.rs index a94459ca4e..18593cf56a 100644 --- a/tests/fail/data_race/dealloc_read_race1.rs +++ b/tests/fail/data_race/dealloc_read_race1.rs @@ -25,7 +25,7 @@ pub fn main() { let j2 = spawn(move || { __rust_dealloc( - //~^ ERROR: Data race detected between (1) Deallocate on thread `` and (2) Read on thread `` + //~^ ERROR: Data race detected between (1) Read on thread `` and (2) Deallocate on thread `` ptr.0 as *mut _, std::mem::size_of::(), std::mem::align_of::(), diff --git a/tests/fail/data_race/dealloc_read_race1.stderr b/tests/fail/data_race/dealloc_read_race1.stderr index fbeab37e17..5e54664647 100644 --- a/tests/fail/data_race/dealloc_read_race1.stderr +++ b/tests/fail/data_race/dealloc_read_race1.stderr @@ -1,4 +1,4 @@ -error: Undefined Behavior: Data race detected between (1) Deallocate on thread `` and (2) Read on thread `` at ALLOC. (1) just happened here +error: Undefined Behavior: Data race detected between (1) Read on thread `` and (2) Deallocate on thread `` at ALLOC. (2) just happened here --> $DIR/dealloc_read_race1.rs:LL:CC | LL | / __rust_dealloc( @@ -7,9 +7,9 @@ LL | | ptr.0 as *mut _, LL | | std::mem::size_of::(), LL | | std::mem::align_of::(), LL | | ); - | |_____________^ Data race detected between (1) Deallocate on thread `` and (2) Read on thread `` at ALLOC. (1) just happened here + | |_____________^ Data race detected between (1) Read on thread `` and (2) Deallocate on thread `` at ALLOC. (2) just happened here | -help: and (2) occurred earlier here +help: and (1) occurred earlier here --> $DIR/dealloc_read_race1.rs:LL:CC | LL | let _val = *ptr.0; diff --git a/tests/fail/data_race/dealloc_read_race2.rs b/tests/fail/data_race/dealloc_read_race2.rs index 6e6b6af5a6..a6f83d489e 100644 --- a/tests/fail/data_race/dealloc_read_race2.rs +++ b/tests/fail/data_race/dealloc_read_race2.rs @@ -28,7 +28,7 @@ pub fn main() { }); let j2 = spawn(move || { - // Also an error of the form: Data race detected between (1) Read on thread `` and (2) Deallocate on thread `` + // Also an error of the form: Data race detected between (1) Deallocate on thread `` and (2) Read on thread `` // but the invalid allocation is detected first. *ptr.0 //~ ERROR: dereferenced after this allocation got freed }); diff --git a/tests/fail/data_race/dealloc_read_race_stack.rs b/tests/fail/data_race/dealloc_read_race_stack.rs index ee3c66fb19..c82bfed09e 100644 --- a/tests/fail/data_race/dealloc_read_race_stack.rs +++ b/tests/fail/data_race/dealloc_read_race_stack.rs @@ -35,7 +35,7 @@ pub fn main() { sleep(Duration::from_millis(200)); // Now `stack_var` gets deallocated. - } //~ ERROR: Data race detected between (1) Deallocate on thread `` and (2) Read on thread `` + } //~ ERROR: Data race detected between (1) Read on thread `` and (2) Deallocate on thread `` }); let j2 = spawn(move || { diff --git a/tests/fail/data_race/dealloc_read_race_stack.stderr b/tests/fail/data_race/dealloc_read_race_stack.stderr index 9ef9bf35ae..beb70c5a7f 100644 --- a/tests/fail/data_race/dealloc_read_race_stack.stderr +++ b/tests/fail/data_race/dealloc_read_race_stack.stderr @@ -1,10 +1,10 @@ -error: Undefined Behavior: Data race detected between (1) Deallocate on thread `` and (2) Read on thread `` at ALLOC. (1) just happened here +error: Undefined Behavior: Data race detected between (1) Read on thread `` and (2) Deallocate on thread `` at ALLOC. (2) just happened here --> $DIR/dealloc_read_race_stack.rs:LL:CC | LL | } - | ^ Data race detected between (1) Deallocate on thread `` and (2) Read on thread `` at ALLOC. (1) just happened here + | ^ Data race detected between (1) Read on thread `` and (2) Deallocate on thread `` at ALLOC. (2) just happened here | -help: and (2) occurred earlier here +help: and (1) occurred earlier here --> $DIR/dealloc_read_race_stack.rs:LL:CC | LL | *pointer.load(Ordering::Acquire) diff --git a/tests/fail/data_race/dealloc_write_race1.rs b/tests/fail/data_race/dealloc_write_race1.rs index 041df291ed..1e93a6cb09 100644 --- a/tests/fail/data_race/dealloc_write_race1.rs +++ b/tests/fail/data_race/dealloc_write_race1.rs @@ -24,7 +24,7 @@ pub fn main() { let j2 = spawn(move || { __rust_dealloc( - //~^ ERROR: Data race detected between (1) Deallocate on thread `` and (2) Write on thread `` + //~^ ERROR: Data race detected between (1) Write on thread `` and (2) Deallocate on thread `` ptr.0 as *mut _, std::mem::size_of::(), std::mem::align_of::(), diff --git a/tests/fail/data_race/dealloc_write_race1.stderr b/tests/fail/data_race/dealloc_write_race1.stderr index 75a98cc5d7..cc4c4524ba 100644 --- a/tests/fail/data_race/dealloc_write_race1.stderr +++ b/tests/fail/data_race/dealloc_write_race1.stderr @@ -1,4 +1,4 @@ -error: Undefined Behavior: Data race detected between (1) Deallocate on thread `` and (2) Write on thread `` at ALLOC. (1) just happened here +error: Undefined Behavior: Data race detected between (1) Write on thread `` and (2) Deallocate on thread `` at ALLOC. (2) just happened here --> $DIR/dealloc_write_race1.rs:LL:CC | LL | / __rust_dealloc( @@ -7,9 +7,9 @@ LL | | ptr.0 as *mut _, LL | | std::mem::size_of::(), LL | | std::mem::align_of::(), LL | | ); - | |_____________^ Data race detected between (1) Deallocate on thread `` and (2) Write on thread `` at ALLOC. (1) just happened here + | |_____________^ Data race detected between (1) Write on thread `` and (2) Deallocate on thread `` at ALLOC. (2) just happened here | -help: and (2) occurred earlier here +help: and (1) occurred earlier here --> $DIR/dealloc_write_race1.rs:LL:CC | LL | *ptr.0 = 2; diff --git a/tests/fail/data_race/dealloc_write_race2.rs b/tests/fail/data_race/dealloc_write_race2.rs index b94fa8a14a..385584db27 100644 --- a/tests/fail/data_race/dealloc_write_race2.rs +++ b/tests/fail/data_race/dealloc_write_race2.rs @@ -27,7 +27,7 @@ pub fn main() { }); let j2 = spawn(move || { - // Also an error of the form: Data race detected between (1) Write on thread `` and (2) Deallocate on thread `` + // Also an error of the form: Data race detected between (1) Deallocate on thread `` and (2) Write on thread `` // but the invalid allocation is detected first. *ptr.0 = 2; //~ ERROR: dereferenced after this allocation got freed }); diff --git a/tests/fail/data_race/dealloc_write_race_stack.rs b/tests/fail/data_race/dealloc_write_race_stack.rs index 78f11c14fb..259fbdc497 100644 --- a/tests/fail/data_race/dealloc_write_race_stack.rs +++ b/tests/fail/data_race/dealloc_write_race_stack.rs @@ -35,7 +35,7 @@ pub fn main() { sleep(Duration::from_millis(200)); // Now `stack_var` gets deallocated. - } //~ ERROR: Data race detected between (1) Deallocate on thread `` and (2) Write on thread `` + } //~ ERROR: Data race detected between (1) Write on thread `` and (2) Deallocate on thread `` }); let j2 = spawn(move || { diff --git a/tests/fail/data_race/dealloc_write_race_stack.stderr b/tests/fail/data_race/dealloc_write_race_stack.stderr index f2fc338b33..5f9f4f9bee 100644 --- a/tests/fail/data_race/dealloc_write_race_stack.stderr +++ b/tests/fail/data_race/dealloc_write_race_stack.stderr @@ -1,10 +1,10 @@ -error: Undefined Behavior: Data race detected between (1) Deallocate on thread `` and (2) Write on thread `` at ALLOC. (1) just happened here +error: Undefined Behavior: Data race detected between (1) Write on thread `` and (2) Deallocate on thread `` at ALLOC. (2) just happened here --> $DIR/dealloc_write_race_stack.rs:LL:CC | LL | } - | ^ Data race detected between (1) Deallocate on thread `` and (2) Write on thread `` at ALLOC. (1) just happened here + | ^ Data race detected between (1) Write on thread `` and (2) Deallocate on thread `` at ALLOC. (2) just happened here | -help: and (2) occurred earlier here +help: and (1) occurred earlier here --> $DIR/dealloc_write_race_stack.rs:LL:CC | LL | *pointer.load(Ordering::Acquire) = 3; diff --git a/tests/fail/data_race/enable_after_join_to_main.stderr b/tests/fail/data_race/enable_after_join_to_main.stderr index 620cb37859..84d1c0bf7e 100644 --- a/tests/fail/data_race/enable_after_join_to_main.stderr +++ b/tests/fail/data_race/enable_after_join_to_main.stderr @@ -1,10 +1,10 @@ -error: Undefined Behavior: Data race detected between (1) Write on thread `` and (2) Write on thread `` at ALLOC. (1) just happened here +error: Undefined Behavior: Data race detected between (1) Write on thread `` and (2) Write on thread `` at ALLOC. (2) just happened here --> $DIR/enable_after_join_to_main.rs:LL:CC | LL | *c.0 = 64; - | ^^^^^^^^^ Data race detected between (1) Write on thread `` and (2) Write on thread `` at ALLOC. (1) just happened here + | ^^^^^^^^^ Data race detected between (1) Write on thread `` and (2) Write on thread `` at ALLOC. (2) just happened here | -help: and (2) occurred earlier here +help: and (1) occurred earlier here --> $DIR/enable_after_join_to_main.rs:LL:CC | LL | *c.0 = 32; diff --git a/tests/fail/data_race/fence_after_load.rs b/tests/fail/data_race/fence_after_load.rs index 8de61d14ac..0648aa55f4 100644 --- a/tests/fail/data_race/fence_after_load.rs +++ b/tests/fail/data_race/fence_after_load.rs @@ -20,5 +20,5 @@ fn main() { // The fence is useless, since it did not happen-after the `store` in the other thread. // Hence this is a data race. // Also see https://github.com/rust-lang/miri/issues/2192. - unsafe { V = 2 } //~ERROR: Data race detected between (1) Write on thread `main` and (2) Write on thread `` + unsafe { V = 2 } //~ERROR: Data race detected between (1) Write on thread `` and (2) Write on thread `main` } diff --git a/tests/fail/data_race/fence_after_load.stderr b/tests/fail/data_race/fence_after_load.stderr index 0bd36067d9..c30d2354e7 100644 --- a/tests/fail/data_race/fence_after_load.stderr +++ b/tests/fail/data_race/fence_after_load.stderr @@ -1,10 +1,10 @@ -error: Undefined Behavior: Data race detected between (1) Write on thread `main` and (2) Write on thread `` at ALLOC. (1) just happened here +error: Undefined Behavior: Data race detected between (1) Write on thread `` and (2) Write on thread `main` at ALLOC. (2) just happened here --> $DIR/fence_after_load.rs:LL:CC | LL | unsafe { V = 2 } - | ^^^^^ Data race detected between (1) Write on thread `main` and (2) Write on thread `` at ALLOC. (1) just happened here + | ^^^^^ Data race detected between (1) Write on thread `` and (2) Write on thread `main` at ALLOC. (2) just happened here | -help: and (2) occurred earlier here +help: and (1) occurred earlier here --> $DIR/fence_after_load.rs:LL:CC | LL | unsafe { V = 1 } diff --git a/tests/fail/data_race/read_write_race.rs b/tests/fail/data_race/read_write_race.rs index f18d2da831..d996141db3 100644 --- a/tests/fail/data_race/read_write_race.rs +++ b/tests/fail/data_race/read_write_race.rs @@ -19,7 +19,7 @@ pub fn main() { }); let j2 = spawn(move || { - *c.0 = 64; //~ ERROR: Data race detected between (1) Write on thread `` and (2) Read on thread `` + *c.0 = 64; //~ ERROR: Data race detected between (1) Read on thread `` and (2) Write on thread `` }); j1.join().unwrap(); diff --git a/tests/fail/data_race/read_write_race.stderr b/tests/fail/data_race/read_write_race.stderr index 0c0d2fa32c..13bc5c74ae 100644 --- a/tests/fail/data_race/read_write_race.stderr +++ b/tests/fail/data_race/read_write_race.stderr @@ -1,10 +1,10 @@ -error: Undefined Behavior: Data race detected between (1) Write on thread `` and (2) Read on thread `` at ALLOC. (1) just happened here +error: Undefined Behavior: Data race detected between (1) Read on thread `` and (2) Write on thread `` at ALLOC. (2) just happened here --> $DIR/read_write_race.rs:LL:CC | LL | *c.0 = 64; - | ^^^^^^^^^ Data race detected between (1) Write on thread `` and (2) Read on thread `` at ALLOC. (1) just happened here + | ^^^^^^^^^ Data race detected between (1) Read on thread `` and (2) Write on thread `` at ALLOC. (2) just happened here | -help: and (2) occurred earlier here +help: and (1) occurred earlier here --> $DIR/read_write_race.rs:LL:CC | LL | let _val = *c.0; diff --git a/tests/fail/data_race/read_write_race_stack.rs b/tests/fail/data_race/read_write_race_stack.rs index acbe2a09e9..b4e371f430 100644 --- a/tests/fail/data_race/read_write_race_stack.rs +++ b/tests/fail/data_race/read_write_race_stack.rs @@ -42,7 +42,7 @@ pub fn main() { sleep(Duration::from_millis(200)); - stack_var //~ ERROR: Data race detected between (1) Read on thread `` and (2) Write on thread `` + stack_var //~ ERROR: Data race detected between (1) Write on thread `` and (2) Read on thread `` }); let j2 = spawn(move || { diff --git a/tests/fail/data_race/read_write_race_stack.stderr b/tests/fail/data_race/read_write_race_stack.stderr index e1d0a52d42..96fcb49482 100644 --- a/tests/fail/data_race/read_write_race_stack.stderr +++ b/tests/fail/data_race/read_write_race_stack.stderr @@ -1,10 +1,10 @@ -error: Undefined Behavior: Data race detected between (1) Read on thread `` and (2) Write on thread `` at ALLOC. (1) just happened here +error: Undefined Behavior: Data race detected between (1) Write on thread `` and (2) Read on thread `` at ALLOC. (2) just happened here --> $DIR/read_write_race_stack.rs:LL:CC | LL | stack_var - | ^^^^^^^^^ Data race detected between (1) Read on thread `` and (2) Write on thread `` at ALLOC. (1) just happened here + | ^^^^^^^^^ Data race detected between (1) Write on thread `` and (2) Read on thread `` at ALLOC. (2) just happened here | -help: and (2) occurred earlier here +help: and (1) occurred earlier here --> $DIR/read_write_race_stack.rs:LL:CC | LL | *pointer.load(Ordering::Acquire) = 3; diff --git a/tests/fail/data_race/relax_acquire_race.rs b/tests/fail/data_race/relax_acquire_race.rs index cc49e8a04f..b7226fa626 100644 --- a/tests/fail/data_race/relax_acquire_race.rs +++ b/tests/fail/data_race/relax_acquire_race.rs @@ -37,7 +37,7 @@ pub fn main() { let j3 = spawn(move || { if SYNC.load(Ordering::Acquire) == 2 { - *c.0 //~ ERROR: Data race detected between (1) Read on thread `` and (2) Write on thread `` + *c.0 //~ ERROR: Data race detected between (1) Write on thread `` and (2) Read on thread `` } else { 0 } diff --git a/tests/fail/data_race/relax_acquire_race.stderr b/tests/fail/data_race/relax_acquire_race.stderr index fdf0e4917d..92755f5551 100644 --- a/tests/fail/data_race/relax_acquire_race.stderr +++ b/tests/fail/data_race/relax_acquire_race.stderr @@ -1,10 +1,10 @@ -error: Undefined Behavior: Data race detected between (1) Read on thread `` and (2) Write on thread `` at ALLOC. (1) just happened here +error: Undefined Behavior: Data race detected between (1) Write on thread `` and (2) Read on thread `` at ALLOC. (2) just happened here --> $DIR/relax_acquire_race.rs:LL:CC | LL | *c.0 - | ^^^^ Data race detected between (1) Read on thread `` and (2) Write on thread `` at ALLOC. (1) just happened here + | ^^^^ Data race detected between (1) Write on thread `` and (2) Read on thread `` at ALLOC. (2) just happened here | -help: and (2) occurred earlier here +help: and (1) occurred earlier here --> $DIR/relax_acquire_race.rs:LL:CC | LL | *c.0 = 1; diff --git a/tests/fail/data_race/release_seq_race.rs b/tests/fail/data_race/release_seq_race.rs index ba917cd0dd..dff33a42a1 100644 --- a/tests/fail/data_race/release_seq_race.rs +++ b/tests/fail/data_race/release_seq_race.rs @@ -41,7 +41,7 @@ pub fn main() { let j3 = spawn(move || { sleep(Duration::from_millis(500)); if SYNC.load(Ordering::Acquire) == 3 { - *c.0 //~ ERROR: Data race detected between (1) Read on thread `` and (2) Write on thread `` + *c.0 //~ ERROR: Data race detected between (1) Write on thread `` and (2) Read on thread `` } else { 0 } diff --git a/tests/fail/data_race/release_seq_race.stderr b/tests/fail/data_race/release_seq_race.stderr index 234ce48e76..880268730d 100644 --- a/tests/fail/data_race/release_seq_race.stderr +++ b/tests/fail/data_race/release_seq_race.stderr @@ -1,10 +1,10 @@ -error: Undefined Behavior: Data race detected between (1) Read on thread `` and (2) Write on thread `` at ALLOC. (1) just happened here +error: Undefined Behavior: Data race detected between (1) Write on thread `` and (2) Read on thread `` at ALLOC. (2) just happened here --> $DIR/release_seq_race.rs:LL:CC | LL | *c.0 - | ^^^^ Data race detected between (1) Read on thread `` and (2) Write on thread `` at ALLOC. (1) just happened here + | ^^^^ Data race detected between (1) Write on thread `` and (2) Read on thread `` at ALLOC. (2) just happened here | -help: and (2) occurred earlier here +help: and (1) occurred earlier here --> $DIR/release_seq_race.rs:LL:CC | LL | *c.0 = 1; diff --git a/tests/fail/data_race/release_seq_race_same_thread.rs b/tests/fail/data_race/release_seq_race_same_thread.rs index c34f4ebe42..f7a523841b 100644 --- a/tests/fail/data_race/release_seq_race_same_thread.rs +++ b/tests/fail/data_race/release_seq_race_same_thread.rs @@ -37,7 +37,7 @@ pub fn main() { let j2 = spawn(move || { if SYNC.load(Ordering::Acquire) == 2 { - *c.0 //~ ERROR: Data race detected between (1) Read on thread `` and (2) Write on thread `` + *c.0 //~ ERROR: Data race detected between (1) Write on thread `` and (2) Read on thread `` } else { 0 } diff --git a/tests/fail/data_race/release_seq_race_same_thread.stderr b/tests/fail/data_race/release_seq_race_same_thread.stderr index 8e95d3593b..386c012ba4 100644 --- a/tests/fail/data_race/release_seq_race_same_thread.stderr +++ b/tests/fail/data_race/release_seq_race_same_thread.stderr @@ -1,10 +1,10 @@ -error: Undefined Behavior: Data race detected between (1) Read on thread `` and (2) Write on thread `` at ALLOC. (1) just happened here +error: Undefined Behavior: Data race detected between (1) Write on thread `` and (2) Read on thread `` at ALLOC. (2) just happened here --> $DIR/release_seq_race_same_thread.rs:LL:CC | LL | *c.0 - | ^^^^ Data race detected between (1) Read on thread `` and (2) Write on thread `` at ALLOC. (1) just happened here + | ^^^^ Data race detected between (1) Write on thread `` and (2) Read on thread `` at ALLOC. (2) just happened here | -help: and (2) occurred earlier here +help: and (1) occurred earlier here --> $DIR/release_seq_race_same_thread.rs:LL:CC | LL | *c.0 = 1; diff --git a/tests/fail/data_race/rmw_race.rs b/tests/fail/data_race/rmw_race.rs index f96ebef284..2201362b16 100644 --- a/tests/fail/data_race/rmw_race.rs +++ b/tests/fail/data_race/rmw_race.rs @@ -38,7 +38,7 @@ pub fn main() { let j3 = spawn(move || { if SYNC.load(Ordering::Acquire) == 3 { - *c.0 //~ ERROR: Data race detected between (1) Read on thread `` and (2) Write on thread `` + *c.0 //~ ERROR: Data race detected between (1) Write on thread `` and (2) Read on thread `` } else { 0 } diff --git a/tests/fail/data_race/rmw_race.stderr b/tests/fail/data_race/rmw_race.stderr index 6252cd5a71..82cb2c4ecb 100644 --- a/tests/fail/data_race/rmw_race.stderr +++ b/tests/fail/data_race/rmw_race.stderr @@ -1,10 +1,10 @@ -error: Undefined Behavior: Data race detected between (1) Read on thread `` and (2) Write on thread `` at ALLOC. (1) just happened here +error: Undefined Behavior: Data race detected between (1) Write on thread `` and (2) Read on thread `` at ALLOC. (2) just happened here --> $DIR/rmw_race.rs:LL:CC | LL | *c.0 - | ^^^^ Data race detected between (1) Read on thread `` and (2) Write on thread `` at ALLOC. (1) just happened here + | ^^^^ Data race detected between (1) Write on thread `` and (2) Read on thread `` at ALLOC. (2) just happened here | -help: and (2) occurred earlier here +help: and (1) occurred earlier here --> $DIR/rmw_race.rs:LL:CC | LL | *c.0 = 1; diff --git a/tests/fail/data_race/stack_pop_race.rs b/tests/fail/data_race/stack_pop_race.rs index fb3ec5a22b..dec5ff274c 100644 --- a/tests/fail/data_race/stack_pop_race.rs +++ b/tests/fail/data_race/stack_pop_race.rs @@ -21,4 +21,4 @@ fn race(local: i32) { // Deallocating the local (when `main` returns) // races with the read in the other thread. // Make sure the error points at this function's end, not just the call site. -} //~ERROR: Data race detected between (1) Deallocate on thread `main` and (2) Read on thread `` +} //~ERROR: Data race detected between (1) Read on thread `` and (2) Deallocate on thread `main` diff --git a/tests/fail/data_race/stack_pop_race.stderr b/tests/fail/data_race/stack_pop_race.stderr index 6cb0270b3d..71e38c2727 100644 --- a/tests/fail/data_race/stack_pop_race.stderr +++ b/tests/fail/data_race/stack_pop_race.stderr @@ -1,10 +1,10 @@ -error: Undefined Behavior: Data race detected between (1) Deallocate on thread `main` and (2) Read on thread `` at ALLOC. (1) just happened here +error: Undefined Behavior: Data race detected between (1) Read on thread `` and (2) Deallocate on thread `main` at ALLOC. (2) just happened here --> $DIR/stack_pop_race.rs:LL:CC | LL | } - | ^ Data race detected between (1) Deallocate on thread `main` and (2) Read on thread `` at ALLOC. (1) just happened here + | ^ Data race detected between (1) Read on thread `` and (2) Deallocate on thread `main` at ALLOC. (2) just happened here | -help: and (2) occurred earlier here +help: and (1) occurred earlier here --> $DIR/stack_pop_race.rs:LL:CC | LL | let _val = unsafe { *ptr.0 }; diff --git a/tests/fail/data_race/write_write_race.stderr b/tests/fail/data_race/write_write_race.stderr index e9055932c5..3b7eb2b800 100644 --- a/tests/fail/data_race/write_write_race.stderr +++ b/tests/fail/data_race/write_write_race.stderr @@ -1,10 +1,10 @@ -error: Undefined Behavior: Data race detected between (1) Write on thread `` and (2) Write on thread `` at ALLOC. (1) just happened here +error: Undefined Behavior: Data race detected between (1) Write on thread `` and (2) Write on thread `` at ALLOC. (2) just happened here --> $DIR/write_write_race.rs:LL:CC | LL | *c.0 = 64; - | ^^^^^^^^^ Data race detected between (1) Write on thread `` and (2) Write on thread `` at ALLOC. (1) just happened here + | ^^^^^^^^^ Data race detected between (1) Write on thread `` and (2) Write on thread `` at ALLOC. (2) just happened here | -help: and (2) occurred earlier here +help: and (1) occurred earlier here --> $DIR/write_write_race.rs:LL:CC | LL | *c.0 = 32; diff --git a/tests/fail/data_race/write_write_race_stack.stderr b/tests/fail/data_race/write_write_race_stack.stderr index d156ece4a1..c501ecd11a 100644 --- a/tests/fail/data_race/write_write_race_stack.stderr +++ b/tests/fail/data_race/write_write_race_stack.stderr @@ -1,10 +1,10 @@ -error: Undefined Behavior: Data race detected between (1) Write on thread `` and (2) Write on thread `` at ALLOC. (1) just happened here +error: Undefined Behavior: Data race detected between (1) Write on thread `` and (2) Write on thread `` at ALLOC. (2) just happened here --> $DIR/write_write_race_stack.rs:LL:CC | LL | stack_var = 1usize; - | ^^^^^^^^^^^^^^^^^^ Data race detected between (1) Write on thread `` and (2) Write on thread `` at ALLOC. (1) just happened here + | ^^^^^^^^^^^^^^^^^^ Data race detected between (1) Write on thread `` and (2) Write on thread `` at ALLOC. (2) just happened here | -help: and (2) occurred earlier here +help: and (1) occurred earlier here --> $DIR/write_write_race_stack.rs:LL:CC | LL | *pointer.load(Ordering::Acquire) = 3; diff --git a/tests/fail/stacked_borrows/retag_data_race_read.rs b/tests/fail/stacked_borrows/retag_data_race_read.rs index 8c97a31c32..a63cd03366 100644 --- a/tests/fail/stacked_borrows/retag_data_race_read.rs +++ b/tests/fail/stacked_borrows/retag_data_race_read.rs @@ -15,7 +15,7 @@ fn thread_1(p: SendPtr) { fn thread_2(p: SendPtr) { let p = p.0; unsafe { - *p = 5; //~ ERROR: Data race detected between (1) Write on thread `` and (2) Read on thread `` + *p = 5; //~ ERROR: Data race detected between (1) Read on thread `` and (2) Write on thread `` } } diff --git a/tests/fail/stacked_borrows/retag_data_race_read.stderr b/tests/fail/stacked_borrows/retag_data_race_read.stderr index 26607e1a69..c53a495b5e 100644 --- a/tests/fail/stacked_borrows/retag_data_race_read.stderr +++ b/tests/fail/stacked_borrows/retag_data_race_read.stderr @@ -1,10 +1,10 @@ -error: Undefined Behavior: Data race detected between (1) Write on thread `` and (2) Read on thread `` at ALLOC. (1) just happened here +error: Undefined Behavior: Data race detected between (1) Read on thread `` and (2) Write on thread `` at ALLOC. (2) just happened here --> $DIR/retag_data_race_read.rs:LL:CC | LL | *p = 5; - | ^^^^^^ Data race detected between (1) Write on thread `` and (2) Read on thread `` at ALLOC. (1) just happened here + | ^^^^^^ Data race detected between (1) Read on thread `` and (2) Write on thread `` at ALLOC. (2) just happened here | -help: and (2) occurred earlier here +help: and (1) occurred earlier here --> $DIR/retag_data_race_read.rs:LL:CC | LL | let _r = &*p; diff --git a/tests/fail/stacked_borrows/retag_data_race_write.stderr b/tests/fail/stacked_borrows/retag_data_race_write.stderr index 33839d2647..da5af60067 100644 --- a/tests/fail/stacked_borrows/retag_data_race_write.stderr +++ b/tests/fail/stacked_borrows/retag_data_race_write.stderr @@ -1,10 +1,10 @@ -error: Undefined Behavior: Data race detected between (1) Write on thread `` and (2) Write on thread `` at ALLOC. (1) just happened here +error: Undefined Behavior: Data race detected between (1) Write on thread `` and (2) Write on thread `` at ALLOC. (2) just happened here --> $DIR/retag_data_race_write.rs:LL:CC | LL | *p = 5; - | ^^^^^^ Data race detected between (1) Write on thread `` and (2) Write on thread `` at ALLOC. (1) just happened here + | ^^^^^^ Data race detected between (1) Write on thread `` and (2) Write on thread `` at ALLOC. (2) just happened here | -help: and (2) occurred earlier here +help: and (1) occurred earlier here --> $DIR/retag_data_race_write.rs:LL:CC | LL | let _r = &mut *p; From e59ba32626557d2742062a6d52406e798385f91d Mon Sep 17 00:00:00 2001 From: Ralf Jung Date: Sat, 24 Dec 2022 09:58:29 +0100 Subject: [PATCH 25/28] Preparing for merge from rustc --- rust-version | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/rust-version b/rust-version index e6c238023e..ee75e7a293 100644 --- a/rust-version +++ b/rust-version @@ -1 +1 @@ -a803f313fdf8f6eb2d674d7dfb3694a2b437ee1e +4f4d0586ad20c66a16d547581ca379beafece93a From f93d95657480302db2ebe5918808d442cad93459 Mon Sep 17 00:00:00 2001 From: Ralf Jung Date: Sat, 24 Dec 2022 10:12:28 +0100 Subject: [PATCH 26/28] fix warnings --- tests/fail/stacked_borrows/drop_in_place_protector.stderr | 2 +- tests/fail/stacked_borrows/drop_in_place_retag.stderr | 2 +- tests/pass/vec.rs | 2 +- 3 files changed, 3 insertions(+), 3 deletions(-) diff --git a/tests/fail/stacked_borrows/drop_in_place_protector.stderr b/tests/fail/stacked_borrows/drop_in_place_protector.stderr index bd51a6645a..3d0cef241c 100644 --- a/tests/fail/stacked_borrows/drop_in_place_protector.stderr +++ b/tests/fail/stacked_borrows/drop_in_place_protector.stderr @@ -16,7 +16,7 @@ help: is this argument | LL | core::ptr::drop_in_place(x); | ^^^^^^^^^^^^^^^^^^^^^^^^^^^ - = note: BACKTRACE: + = note: BACKTRACE (of the first span): = note: inside `::drop` at $DIR/drop_in_place_protector.rs:LL:CC = note: inside `std::ptr::drop_in_place:: - shim(Some(HasDrop))` at RUSTLIB/core/src/ptr/mod.rs:LL:CC = note: inside `std::ptr::drop_in_place::<(HasDrop, u8)> - shim(Some((HasDrop, u8)))` at RUSTLIB/core/src/ptr/mod.rs:LL:CC diff --git a/tests/fail/stacked_borrows/drop_in_place_retag.stderr b/tests/fail/stacked_borrows/drop_in_place_retag.stderr index 3f9e6708bd..7f2917e795 100644 --- a/tests/fail/stacked_borrows/drop_in_place_retag.stderr +++ b/tests/fail/stacked_borrows/drop_in_place_retag.stderr @@ -14,7 +14,7 @@ help: was created by a SharedReadOnly retag at offsets [0x0..0x1] | LL | let x = core::ptr::addr_of!(x); | ^^^^^^^^^^^^^^^^^^^^^^ - = note: BACKTRACE: + = note: BACKTRACE (of the first span): = note: inside `std::ptr::drop_in_place:: - shim(None)` at RUSTLIB/core/src/ptr/mod.rs:LL:CC note: inside `main` --> $DIR/drop_in_place_retag.rs:LL:CC diff --git a/tests/pass/vec.rs b/tests/pass/vec.rs index fb1d8e306f..3a6655e2ba 100644 --- a/tests/pass/vec.rs +++ b/tests/pass/vec.rs @@ -48,7 +48,7 @@ fn vec_into_iter_zst() { assert_eq!(v, 0); let mut it = vec![[0u64; 0], [0u64; 0]].into_iter(); - it.advance_by(1); + it.advance_by(1).unwrap(); drop(it); let mut it = vec![[0u64; 0], [0u64; 0]].into_iter(); From e497b2970bfcef0b1ed56fbc32a11db8c5894faf Mon Sep 17 00:00:00 2001 From: Ralf Jung Date: Sun, 25 Dec 2022 14:16:10 +0100 Subject: [PATCH 27/28] use cargo-install to install josh-proxy --- CONTRIBUTING.md | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/CONTRIBUTING.md b/CONTRIBUTING.md index 6efaefdeff..5b538691de 100644 --- a/CONTRIBUTING.md +++ b/CONTRIBUTING.md @@ -233,14 +233,14 @@ You can also directly run Miri on a Rust source file: ## Advanced topic: Syncing with the rustc repo We use the [`josh` proxy](https://github.com/josh-project/josh) to transmit changes between the -rustc and Miri repositories. The eaisest way to run josh is via docker: +rustc and Miri repositories. ```sh -docker pull joshproject/josh-proxy:latest -docker run -it -p 8000:8000 -e JOSH_REMOTE=https://github.com -e JOSH_EXTRA_OPTS=--no-background -v josh-vol:/data/git joshproject/josh-proxy:latest +cargo +stable install josh-proxy --git https://github.com/josh-project/josh --tag r22.12.06 +josh-proxy --local=$HOME/.cache/josh --remote=https://github.com --no-background ``` -This sets up a local volume `josh-vol` for josh's cache. +This uses a directory `$HOME/.cache/josh` as a cache, to speed up repeated pulling/pushing. ### Importing changes from the rustc repo From 63a3a31847ddfc9f4a6ae1408e844a0acf283f16 Mon Sep 17 00:00:00 2001 From: Ralf Jung Date: Sun, 25 Dec 2022 14:18:41 +0100 Subject: [PATCH 28/28] enable some warnings that rustc bootstrap enables --- miri | 2 +- src/shims/unix/linux/fd/epoll.rs | 2 +- src/shims/unix/linux/fd/event.rs | 2 +- src/shims/unix/linux/fd/socketpair.rs | 2 +- 4 files changed, 4 insertions(+), 4 deletions(-) diff --git a/miri b/miri index a259576ed4..0c0bbbc702 100755 --- a/miri +++ b/miri @@ -243,7 +243,7 @@ if [ -z "$CARGO_PROFILE_DEV_OPT_LEVEL" ]; then export CARGO_PROFILE_DEV_OPT_LEVEL=2 fi # Enable rustc-specific lints (ignored without `-Zunstable-options`). -export RUSTFLAGS="-Zunstable-options -Wrustc::internal $RUSTFLAGS" +export RUSTFLAGS="-Zunstable-options -Wrustc::internal -Wrust_2018_idioms -Wunused_lifetimes -Wsemicolon_in_expressions_from_macros $RUSTFLAGS" # We set the rpath so that Miri finds the private rustc libraries it needs. export RUSTFLAGS="-C link-args=-Wl,-rpath,$LIBDIR $RUSTFLAGS" diff --git a/src/shims/unix/linux/fd/epoll.rs b/src/shims/unix/linux/fd/epoll.rs index eb86773e6b..e33673fecf 100644 --- a/src/shims/unix/linux/fd/epoll.rs +++ b/src/shims/unix/linux/fd/epoll.rs @@ -36,7 +36,7 @@ impl FileDescriptor for Epoll { Ok(self) } - fn dup<'tcx>(&mut self) -> io::Result> { + fn dup(&mut self) -> io::Result> { Ok(Box::new(self.clone())) } diff --git a/src/shims/unix/linux/fd/event.rs b/src/shims/unix/linux/fd/event.rs index e87ff56bee..239eb462a1 100644 --- a/src/shims/unix/linux/fd/event.rs +++ b/src/shims/unix/linux/fd/event.rs @@ -21,7 +21,7 @@ impl FileDescriptor for Event { "event" } - fn dup<'tcx>(&mut self) -> io::Result> { + fn dup(&mut self) -> io::Result> { Ok(Box::new(Event { val: self.val })) } diff --git a/src/shims/unix/linux/fd/socketpair.rs b/src/shims/unix/linux/fd/socketpair.rs index 036d3a2e31..f9e56b4a2b 100644 --- a/src/shims/unix/linux/fd/socketpair.rs +++ b/src/shims/unix/linux/fd/socketpair.rs @@ -15,7 +15,7 @@ impl FileDescriptor for SocketPair { "socketpair" } - fn dup<'tcx>(&mut self) -> io::Result> { + fn dup(&mut self) -> io::Result> { Ok(Box::new(SocketPair)) }