Skip to content

Commit

Permalink
make sure the miri-unleash-flag is not used to circumvent feature gates
Browse files Browse the repository at this point in the history
  • Loading branch information
RalfJung committed May 2, 2020
1 parent c7eb916 commit 08ba014
Show file tree
Hide file tree
Showing 6 changed files with 49 additions and 18 deletions.
3 changes: 3 additions & 0 deletions src/librustc_mir/transform/check_consts/validation.rs
Original file line number Diff line number Diff line change
Expand Up @@ -254,6 +254,9 @@ impl Validator<'mir, 'tcx> {

if is_unleashable && self.tcx.sess.opts.debugging_opts.unleash_the_miri_inside_of_you {
self.tcx.sess.span_warn(self.tcx.def_span(self.def_id), "skipping const checks");
if let Some(feature) = O::feature_gate() {
self.tcx.sess.miri_unleashed_feature(feature);
}
return;
}

Expand Down
37 changes: 36 additions & 1 deletion src/librustc_session/session.rs
Original file line number Diff line number Diff line change
Expand Up @@ -21,11 +21,12 @@ use rustc_errors::json::JsonEmitter;
use rustc_errors::{Applicability, DiagnosticBuilder, DiagnosticId, ErrorReported};
use rustc_span::edition::Edition;
use rustc_span::source_map::{self, FileLoader, MultiSpan, RealFileLoader, SourceMap, Span};
use rustc_span::SourceFileHashAlgorithm;
use rustc_span::{SourceFileHashAlgorithm, Symbol};
use rustc_target::spec::{PanicStrategy, RelocModel, RelroLevel, Target, TargetTriple, TlsModel};

use std::cell::{self, RefCell};
use std::env;
use std::fmt::Write as _;
use std::io::Write;
use std::num::NonZeroU32;
use std::path::PathBuf;
Expand Down Expand Up @@ -142,6 +143,10 @@ pub struct Session {
/// and immediately printing the backtrace to stderr.
pub ctfe_backtrace: Lock<CtfeBacktrace>,

/// This tracks whether `-Zunleash-the-miri-inside-of-you` was used to get around a
/// feature gate. If yes, this file must fail to compile.
miri_unleashed_features: Lock<FxHashSet<Symbol>>,

/// Base directory containing the `src/` for the Rust standard library, and
/// potentially `rustc` as well, if we can can find it. Right now it's always
/// `$sysroot/lib/rustlib/src/rust` (i.e. the `rustup` `rust-src` component).
Expand Down Expand Up @@ -188,7 +193,36 @@ impl From<&'static lint::Lint> for DiagnosticMessageId {
}
}

impl Drop for Session {
fn drop(&mut self) {
if !self.has_errors_or_delayed_span_bugs() {
let unleashed_features = self.miri_unleashed_features.get_mut();
if !unleashed_features.is_empty() {
// Join the strings (itertools has it but libstd does not...)
let mut list = String::new();
for feature in unleashed_features.iter() {
if !list.is_empty() {
list.push_str(", ");
}
write!(&mut list, "{}", feature).unwrap();
}
// We have skipped a feature gate, and not run into other errors... reject.
panic!(
"`-Zunleash-the-miri-inside-of-you` may not be used to circumvent feature \
gates, except when testing error paths in the CTFE engine.\n\
The following feature flags are missing from this crate: {}",
list,
);
}
}
}
}

impl Session {
pub fn miri_unleashed_feature(&self, s: Symbol) {
self.miri_unleashed_features.lock().insert(s);
}

pub fn local_crate_disambiguator(&self) -> CrateDisambiguator {
*self.crate_disambiguator.get()
}
Expand Down Expand Up @@ -1139,6 +1173,7 @@ pub fn build_session_with_source_map(
confused_type_with_std_module: Lock::new(Default::default()),
system_library_path: OneThread::new(RefCell::new(Default::default())),
ctfe_backtrace,
miri_unleashed_features: Lock::new(Default::default()),
real_rust_source_base_dir,
};

Expand Down
4 changes: 3 additions & 1 deletion src/test/ui/consts/miri_unleashed/const_refers_to_static.rs
Original file line number Diff line number Diff line change
@@ -1,6 +1,8 @@
// build-fail
// compile-flags: -Zunleash-the-miri-inside-of-you -Zdeduplicate-diagnostics
#![allow(const_err)]
#![feature(const_raw_ptr_deref)] // FIXME: cannot remove because then rustc thinks there is no error
#![crate_type = "lib"]

use std::sync::atomic::AtomicUsize;
use std::sync::atomic::Ordering;
Expand All @@ -24,7 +26,7 @@ static mut MUTABLE: u32 = 0;
const READ_MUT: u32 = unsafe { MUTABLE };
//~^ WARN skipping const checks

fn main() {
pub fn main() {
MUTATE_INTERIOR_MUT;
//~^ ERROR: erroneous constant used
READ_INTERIOR_MUT;
Expand Down
12 changes: 6 additions & 6 deletions src/test/ui/consts/miri_unleashed/const_refers_to_static.stderr
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
warning: skipping const checks
--> $DIR/const_refers_to_static.rs:11:1
--> $DIR/const_refers_to_static.rs:13:1
|
LL | / const MUTATE_INTERIOR_MUT: usize = {
LL | |
Expand All @@ -9,7 +9,7 @@ LL | | };
| |__^

warning: skipping const checks
--> $DIR/const_refers_to_static.rs:17:1
--> $DIR/const_refers_to_static.rs:19:1
|
LL | / const READ_INTERIOR_MUT: usize = {
LL | |
Expand All @@ -19,25 +19,25 @@ LL | | };
| |__^

warning: skipping const checks
--> $DIR/const_refers_to_static.rs:24:1
--> $DIR/const_refers_to_static.rs:26:1
|
LL | const READ_MUT: u32 = unsafe { MUTABLE };
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^

error[E0080]: erroneous constant used
--> $DIR/const_refers_to_static.rs:28:5
--> $DIR/const_refers_to_static.rs:30:5
|
LL | MUTATE_INTERIOR_MUT;
| ^^^^^^^^^^^^^^^^^^^ referenced constant has errors

error[E0080]: erroneous constant used
--> $DIR/const_refers_to_static.rs:30:5
--> $DIR/const_refers_to_static.rs:32:5
|
LL | READ_INTERIOR_MUT;
| ^^^^^^^^^^^^^^^^^ referenced constant has errors

error[E0080]: erroneous constant used
--> $DIR/const_refers_to_static.rs:32:5
--> $DIR/const_refers_to_static.rs:34:5
|
LL | READ_MUT;
| ^^^^^^^^ referenced constant has errors
Expand Down
8 changes: 0 additions & 8 deletions src/test/ui/consts/miri_unleashed/read_from_static.stderr

This file was deleted.

Original file line number Diff line number Diff line change
@@ -1,9 +1,8 @@
// run-pass
// compile-flags: -Zunleash-the-miri-inside-of-you
#![feature(const_mut_refs)]
#![allow(const_err)]

static OH_YES: &mut i32 = &mut 42;
//~^ WARN skipping const checks

fn main() {
// Make sure `OH_YES` can be read.
Expand Down

0 comments on commit 08ba014

Please sign in to comment.