diff --git a/src/eval.rs b/src/eval.rs index 79ceb6be806e..24cf0cbf06be 100644 --- a/src/eval.rs +++ b/src/eval.rs @@ -5,6 +5,7 @@ use std::ffi::OsStr; use rand::rngs::StdRng; use rand::SeedableRng; +use log::info; use rustc_hir::def_id::DefId; use rustc_middle::ty::{self, layout::LayoutCx, TyCtxt}; @@ -195,8 +196,8 @@ pub fn create_ecx<'mir, 'tcx: 'mir>( /// Returns `Some(return_code)` if program executed completed. /// Returns `None` if an evaluation error occured. pub fn eval_main<'tcx>(tcx: TyCtxt<'tcx>, main_id: DefId, config: MiriConfig) -> Option { - // FIXME: on Windows, we ignore leaks (https://github.com/rust-lang/miri/issues/1302). - let ignore_leaks = config.ignore_leaks || tcx.sess.target.target.target_os == "windows"; + // Copy setting before we move `config`. + let ignore_leaks = config.ignore_leaks; let (mut ecx, ret_place) = match create_ecx(tcx, main_id, config) { Ok(v) => v, @@ -244,7 +245,8 @@ pub fn eval_main<'tcx>(tcx: TyCtxt<'tcx>, main_id: DefId, config: MiriConfig) -> match res { Ok(return_code) => { if !ignore_leaks { - let leaks = ecx.memory.leak_report(); + info!("Additonal static roots: {:?}", ecx.machine.static_roots); + let leaks = ecx.memory.leak_report(&ecx.machine.static_roots); if leaks != 0 { tcx.sess.err("the evaluated program leaked memory"); // Ignore the provided return code - let the reported error diff --git a/src/machine.rs b/src/machine.rs index 49d647838c9e..e9217896ef6e 100644 --- a/src/machine.rs +++ b/src/machine.rs @@ -262,6 +262,9 @@ pub struct Evaluator<'mir, 'tcx> { /// Precomputed `TyLayout`s for primitive data types that are commonly used inside Miri. pub(crate) layouts: PrimitiveLayouts<'tcx>, + + /// Allocations that are considered roots of static memory (that may leak). + pub(crate) static_roots: Vec, } impl<'mir, 'tcx> Evaluator<'mir, 'tcx> { @@ -289,6 +292,7 @@ impl<'mir, 'tcx> Evaluator<'mir, 'tcx> { time_anchor: Instant::now(), layouts, threads: ThreadManager::default(), + static_roots: Vec::new(), } } } diff --git a/src/shims/foreign_items.rs b/src/shims/foreign_items.rs index cf85636b57bf..f1b04afe0a62 100644 --- a/src/shims/foreign_items.rs +++ b/src/shims/foreign_items.rs @@ -197,6 +197,17 @@ pub trait EvalContextExt<'mir, 'tcx: 'mir>: crate::MiriEvalContextExt<'mir, 'tcx // Here we dispatch all the shims for foreign functions. If you have a platform specific // shim, add it to the corresponding submodule. match link_name { + // Miri-specific extern functions + "miri_static_root" => { + let &[ptr] = check_arg_count(args)?; + let ptr = this.read_scalar(ptr)?.not_undef()?; + let ptr = this.force_ptr(ptr)?; + if ptr.offset != Size::ZERO { + throw_unsup_format!("Pointer passed to miri_static_root must point to beginning of an allocated block"); + } + this.machine.static_roots.push(ptr.alloc_id); + } + // Standard C allocation "malloc" => { let &[size] = check_arg_count(args)?;