about summary refs log tree commit diff
diff options
context:
space:
mode:
authorRalf Jung <post@ralfj.de>2025-07-18 09:40:58 +0200
committerRalf Jung <post@ralfj.de>2025-07-18 11:05:14 +0200
commit24ea3e22d3e2e02ccf055a45cac3550457a7ae3d (patch)
tree37f28d39cfdff77161d015bf0763d818874416c7
parent83395909d074d81086b49cfc400a910d83f40a1e (diff)
downloadrust-24ea3e22d3e2e02ccf055a45cac3550457a7ae3d.tar.gz
rust-24ea3e22d3e2e02ccf055a45cac3550457a7ae3d.zip
make native-lib support compile-time-optional, and centralize cfg usage
-rw-r--r--src/tools/miri/Cargo.toml15
-rw-r--r--src/tools/miri/src/alloc/alloc_bytes.rs9
-rw-r--r--src/tools/miri/src/alloc/mod.rs28
-rw-r--r--src/tools/miri/src/bin/miri.rs7
-rw-r--r--src/tools/miri/src/lib.rs2
-rw-r--r--src/tools/miri/src/machine.rs20
-rw-r--r--src/tools/miri/src/shims/foreign_items.rs2
-rw-r--r--src/tools/miri/src/shims/mod.rs4
-rw-r--r--src/tools/miri/tests/ui.rs2
9 files changed, 52 insertions, 37 deletions
diff --git a/src/tools/miri/Cargo.toml b/src/tools/miri/Cargo.toml
index 75476d7923c..0aff34e9fbe 100644
--- a/src/tools/miri/Cargo.toml
+++ b/src/tools/miri/Cargo.toml
@@ -38,14 +38,14 @@ features = ['unprefixed_malloc_on_supported_platforms']
 
 [target.'cfg(unix)'.dependencies]
 libc = "0.2"
-libffi = "4.0.0"
-libloading = "0.8"
+libffi = { version = "4.0.0", optional = true }
+libloading = { version = "0.8", optional = true }
+nix = { version = "0.30.1", features = ["mman", "ptrace", "signal"], optional = true }
 
 [target.'cfg(target_os = "linux")'.dependencies]
-nix = { version = "0.30.1", features = ["mman", "ptrace", "signal"] }
-ipc-channel = "0.19.0"
-serde = { version = "1.0.219", features = ["derive"] }
-capstone = "0.13"
+ipc-channel = { version = "0.19.0", optional = true }
+serde = { version = "1.0.219", features = ["derive"], optional = true }
+capstone = { version = "0.13", optional = true }
 
 [dev-dependencies]
 ui_test = "0.29.1"
@@ -64,11 +64,12 @@ name = "ui"
 harness = false
 
 [features]
-default = ["stack-cache"]
+default = ["stack-cache", "native-lib"]
 genmc = []
 stack-cache = []
 stack-cache-consistency-check = ["stack-cache"]
 tracing = ["serde_json"]
+native-lib = ["dep:libffi", "dep:libloading", "dep:capstone", "dep:ipc-channel", "dep:nix", "dep:serde"]
 
 [lints.rust.unexpected_cfgs]
 level = "warn"
diff --git a/src/tools/miri/src/alloc/alloc_bytes.rs b/src/tools/miri/src/alloc/alloc_bytes.rs
index 2a253952b27..5d00d3eafcb 100644
--- a/src/tools/miri/src/alloc/alloc_bytes.rs
+++ b/src/tools/miri/src/alloc/alloc_bytes.rs
@@ -1,20 +1,18 @@
 use std::alloc::Layout;
 use std::borrow::Cow;
+use std::cell::RefCell;
+use std::rc::Rc;
 use std::{alloc, slice};
-#[cfg(target_os = "linux")]
-use std::{cell::RefCell, rc::Rc};
 
 use rustc_abi::{Align, Size};
 use rustc_middle::mir::interpret::AllocBytes;
 
-#[cfg(target_os = "linux")]
 use crate::alloc::isolated_alloc::IsolatedAlloc;
 use crate::helpers::ToU64 as _;
 
 #[derive(Clone, Debug)]
 pub enum MiriAllocParams {
     Global,
-    #[cfg(target_os = "linux")]
     Isolated(Rc<RefCell<IsolatedAlloc>>),
 }
 
@@ -56,7 +54,6 @@ impl Drop for MiriAllocBytes {
         unsafe {
             match self.params.clone() {
                 MiriAllocParams::Global => alloc::dealloc(self.ptr, alloc_layout),
-                #[cfg(target_os = "linux")]
                 MiriAllocParams::Isolated(alloc) =>
                     alloc.borrow_mut().dealloc(self.ptr, alloc_layout),
             }
@@ -123,7 +120,6 @@ impl AllocBytes for MiriAllocBytes {
         let alloc_fn = |layout, params: &MiriAllocParams| unsafe {
             match params {
                 MiriAllocParams::Global => alloc::alloc(layout),
-                #[cfg(target_os = "linux")]
                 MiriAllocParams::Isolated(alloc) => alloc.borrow_mut().alloc(layout),
             }
         };
@@ -144,7 +140,6 @@ impl AllocBytes for MiriAllocBytes {
         let alloc_fn = |layout, params: &MiriAllocParams| unsafe {
             match params {
                 MiriAllocParams::Global => alloc::alloc_zeroed(layout),
-                #[cfg(target_os = "linux")]
                 MiriAllocParams::Isolated(alloc) => alloc.borrow_mut().alloc_zeroed(layout),
             }
         };
diff --git a/src/tools/miri/src/alloc/mod.rs b/src/tools/miri/src/alloc/mod.rs
index 3be885920d2..35158f50a8f 100644
--- a/src/tools/miri/src/alloc/mod.rs
+++ b/src/tools/miri/src/alloc/mod.rs
@@ -1,5 +1,31 @@
 mod alloc_bytes;
-#[cfg(target_os = "linux")]
+#[cfg(all(unix, feature = "native-lib"))]
 pub mod isolated_alloc;
+#[cfg(not(all(unix, feature = "native-lib")))]
+pub mod isolated_alloc {
+    use std::alloc::Layout;
+
+    /// Stub allocator to avoid `cfg`s in the rest of Miri.
+    #[derive(Debug)]
+    pub struct IsolatedAlloc(!);
+
+    impl IsolatedAlloc {
+        pub fn new() -> Self {
+            unreachable!()
+        }
+
+        pub unsafe fn alloc(&mut self, _layout: Layout) -> *mut u8 {
+            match self.0 {}
+        }
+
+        pub unsafe fn alloc_zeroed(&mut self, _layout: Layout) -> *mut u8 {
+            match self.0 {}
+        }
+
+        pub unsafe fn dealloc(&mut self, _ptr: *mut u8, _layout: Layout) {
+            match self.0 {}
+        }
+    }
+}
 
 pub use self::alloc_bytes::{MiriAllocBytes, MiriAllocParams};
diff --git a/src/tools/miri/src/bin/miri.rs b/src/tools/miri/src/bin/miri.rs
index 61cebedf081..5d9c05807b8 100644
--- a/src/tools/miri/src/bin/miri.rs
+++ b/src/tools/miri/src/bin/miri.rs
@@ -335,9 +335,10 @@ impl rustc_driver::Callbacks for MiriBeRustCompilerCalls {
 fn exit(exit_code: i32) -> ! {
     // Drop the tracing guard before exiting, so tracing calls are flushed correctly.
     deinit_loggers();
-    // Make sure the supervisor knows about the code code.
-    #[cfg(target_os = "linux")]
+    // Make sure the supervisor knows about the exit code.
+    #[cfg(all(unix, feature = "native-lib"))]
     miri::native_lib::register_retcode_sv(exit_code);
+    // Actually exit.
     std::process::exit(exit_code);
 }
 
@@ -754,7 +755,7 @@ fn main() {
     debug!("crate arguments: {:?}", miri_config.args);
     if !miri_config.native_lib.is_empty() && miri_config.native_lib_enable_tracing {
         // SAFETY: No other threads are running
-        #[cfg(target_os = "linux")]
+        #[cfg(all(unix, feature = "native-lib"))]
         if unsafe { miri::native_lib::init_sv() }.is_err() {
             eprintln!(
                 "warning: The native-lib tracer could not be started. Is this an x86 Linux system, and does Miri have permissions to ptrace?\n\
diff --git a/src/tools/miri/src/lib.rs b/src/tools/miri/src/lib.rs
index a591d21071d..0f293c0d8f7 100644
--- a/src/tools/miri/src/lib.rs
+++ b/src/tools/miri/src/lib.rs
@@ -97,7 +97,7 @@ pub use rustc_const_eval::interpret::{self, AllocMap, Provenance as _};
 use rustc_middle::{bug, span_bug};
 use tracing::{info, trace};
 
-#[cfg(target_os = "linux")]
+#[cfg(all(unix, feature = "native-lib"))]
 pub mod native_lib {
     pub use crate::shims::{init_sv, register_retcode_sv};
 }
diff --git a/src/tools/miri/src/machine.rs b/src/tools/miri/src/machine.rs
index 9c077e5b7b6..bce0063c9ce 100644
--- a/src/tools/miri/src/machine.rs
+++ b/src/tools/miri/src/machine.rs
@@ -530,7 +530,6 @@ pub struct MiriMachine<'tcx> {
     pub(crate) rng: RefCell<StdRng>,
 
     /// The allocator used for the machine's `AllocBytes` in native-libs mode.
-    #[cfg(target_os = "linux")]
     pub(crate) allocator: Option<Rc<RefCell<crate::alloc::isolated_alloc::IsolatedAlloc>>>,
 
     /// The allocation IDs to report when they are being allocated
@@ -554,9 +553,9 @@ pub struct MiriMachine<'tcx> {
     pub(crate) basic_block_count: u64,
 
     /// Handle of the optional shared object file for native functions.
-    #[cfg(unix)]
+    #[cfg(all(unix, feature = "native-lib"))]
     pub native_lib: Vec<(libloading::Library, std::path::PathBuf)>,
-    #[cfg(not(unix))]
+    #[cfg(not(all(unix, feature = "native-lib")))]
     pub native_lib: Vec<!>,
 
     /// Run a garbage collector for BorTags every N basic blocks.
@@ -603,7 +602,7 @@ pub struct MiriMachine<'tcx> {
     /// Remembers whether we already warned about an extern type with Stacked Borrows.
     pub(crate) sb_extern_type_warned: Cell<bool>,
     /// Remember whether we already warned about sharing memory with a native call.
-    #[cfg(unix)]
+    #[allow(unused)]
     pub(crate) native_call_mem_warned: Cell<bool>,
     /// Remembers which shims have already shown the warning about erroring in isolation.
     pub(crate) reject_in_isolation_warned: RefCell<FxHashSet<String>>,
@@ -718,7 +717,6 @@ impl<'tcx> MiriMachine<'tcx> {
             local_crates,
             extern_statics: FxHashMap::default(),
             rng: RefCell::new(rng),
-            #[cfg(target_os = "linux")]
             allocator: if !config.native_lib.is_empty() {
                 Some(Rc::new(RefCell::new(crate::alloc::isolated_alloc::IsolatedAlloc::new())))
             } else { None },
@@ -730,7 +728,7 @@ impl<'tcx> MiriMachine<'tcx> {
             report_progress: config.report_progress,
             basic_block_count: 0,
             monotonic_clock: MonotonicClock::new(config.isolated_op == IsolatedOp::Allow),
-            #[cfg(unix)]
+            #[cfg(all(unix, feature = "native-lib"))]
             native_lib: config.native_lib.iter().map(|lib_file_path| {
                 let host_triple = rustc_session::config::host_tuple();
                 let target_triple = tcx.sess.opts.target_triple.tuple();
@@ -752,9 +750,9 @@ impl<'tcx> MiriMachine<'tcx> {
                     lib_file_path.clone(),
                 )
             }).collect(),
-            #[cfg(not(unix))]
+            #[cfg(not(all(unix, feature = "native-lib")))]
             native_lib: config.native_lib.iter().map(|_| {
-                panic!("calling functions from native libraries via FFI is only supported on Unix")
+                panic!("calling functions from native libraries via FFI is not supported in this build of Miri")
             }).collect(),
             gc_interval: config.gc_interval,
             since_gc: 0,
@@ -771,7 +769,6 @@ impl<'tcx> MiriMachine<'tcx> {
             pthread_rwlock_sanity: Cell::new(false),
             pthread_condvar_sanity: Cell::new(false),
             sb_extern_type_warned: Cell::new(false),
-            #[cfg(unix)]
             native_call_mem_warned: Cell::new(false),
             reject_in_isolation_warned: Default::default(),
             int2ptr_warned: Default::default(),
@@ -924,7 +921,6 @@ impl VisitProvenance for MiriMachine<'_> {
             backtrace_style: _,
             local_crates: _,
             rng: _,
-            #[cfg(target_os = "linux")]
             allocator: _,
             tracked_alloc_ids: _,
             track_alloc_accesses: _,
@@ -949,7 +945,6 @@ impl VisitProvenance for MiriMachine<'_> {
             pthread_rwlock_sanity: _,
             pthread_condvar_sanity: _,
             sb_extern_type_warned: _,
-            #[cfg(unix)]
             native_call_mem_warned: _,
             reject_in_isolation_warned: _,
             int2ptr_warned: _,
@@ -1817,13 +1812,10 @@ impl<'tcx> Machine<'tcx> for MiriMachine<'tcx> {
     fn get_default_alloc_params(&self) -> <Self::Bytes as AllocBytes>::AllocParams {
         use crate::alloc::MiriAllocParams;
 
-        #[cfg(target_os = "linux")]
         match &self.allocator {
             Some(alloc) => MiriAllocParams::Isolated(alloc.clone()),
             None => MiriAllocParams::Global,
         }
-        #[cfg(not(target_os = "linux"))]
-        MiriAllocParams::Global
     }
 
     fn enter_trace_span(span: impl FnOnce() -> tracing::Span) -> impl EnteredTraceSpan {
diff --git a/src/tools/miri/src/shims/foreign_items.rs b/src/tools/miri/src/shims/foreign_items.rs
index 9ddba8c2b48..94cda57658a 100644
--- a/src/tools/miri/src/shims/foreign_items.rs
+++ b/src/tools/miri/src/shims/foreign_items.rs
@@ -237,7 +237,7 @@ trait EvalContextExtPriv<'tcx>: crate::MiriInterpCxExt<'tcx> {
         let this = self.eval_context_mut();
 
         // First deal with any external C functions in linked .so file.
-        #[cfg(unix)]
+        #[cfg(all(unix, feature = "native-lib"))]
         if !this.machine.native_lib.is_empty() {
             use crate::shims::native_lib::EvalContextExt as _;
             // An Ok(false) here means that the function being called was not exported
diff --git a/src/tools/miri/src/shims/mod.rs b/src/tools/miri/src/shims/mod.rs
index 75540f6f150..2a7709829ee 100644
--- a/src/tools/miri/src/shims/mod.rs
+++ b/src/tools/miri/src/shims/mod.rs
@@ -4,7 +4,7 @@ mod aarch64;
 mod alloc;
 mod backtrace;
 mod files;
-#[cfg(unix)]
+#[cfg(all(unix, feature = "native-lib"))]
 mod native_lib;
 mod unix;
 mod wasi;
@@ -23,7 +23,7 @@ pub mod tls;
 pub mod unwind;
 
 pub use self::files::FdTable;
-#[cfg(target_os = "linux")]
+#[cfg(all(unix, feature = "native-lib"))]
 pub use self::native_lib::trace::{init_sv, register_retcode_sv};
 pub use self::unix::{DirTable, EpollInterestTable};
 
diff --git a/src/tools/miri/tests/ui.rs b/src/tools/miri/tests/ui.rs
index 43f855d57dd..e521269586d 100644
--- a/src/tools/miri/tests/ui.rs
+++ b/src/tools/miri/tests/ui.rs
@@ -335,7 +335,7 @@ fn main() -> Result<()> {
     ui(Mode::Panic, "tests/panic", &target, WithDependencies, tmpdir.path())?;
     ui(Mode::Fail, "tests/fail", &target, WithoutDependencies, tmpdir.path())?;
     ui(Mode::Fail, "tests/fail-dep", &target, WithDependencies, tmpdir.path())?;
-    if cfg!(unix) && target == host {
+    if cfg!(all(unix, feature = "native-lib")) && target == host {
         ui(Mode::Pass, "tests/native-lib/pass", &target, WithoutDependencies, tmpdir.path())?;
         ui(Mode::Fail, "tests/native-lib/fail", &target, WithoutDependencies, tmpdir.path())?;
     }