Skip to content
Permalink
Browse files

Make `-Z treat-err-as-bug` take a number of errors to be emitted

`-Z treat-err-as-bug=0` will cause `rustc` to panic after the first
error is reported. `-Z treat-err-as-bug=2` will cause `rustc` to
panic after 3 errors have been reported.
  • Loading branch information...
estebank committed Mar 7, 2019
1 parent f22dca0 commit 7a55a004fa3b3eb933637a4aeec9b8576b31a033
@@ -1234,7 +1234,7 @@ options! {DebuggingOptions, DebuggingSetter, basic_debugging_options,
"parse only; do not compile, assemble, or link"),
no_codegen: bool = (false, parse_bool, [TRACKED],
"run all passes except codegen; no output"),
treat_err_as_bug: bool = (false, parse_bool, [TRACKED],
treat_err_as_bug: Option<usize> = (None, parse_opt_uint, [TRACKED],
"treat all errors that occur as bugs"),
report_delayed_bugs: bool = (false, parse_bool, [TRACKED],
"immediately print bugs registered with `delay_span_bug`"),
@@ -3212,7 +3212,7 @@ mod tests {
assert!(reference.dep_tracking_hash() != opts.dep_tracking_hash());

opts = reference.clone();
opts.debugging_opts.treat_err_as_bug = true;
opts.debugging_opts.treat_err_as_bug = Some(1);
assert!(reference.dep_tracking_hash() != opts.dep_tracking_hash());

opts = reference.clone();
@@ -1315,7 +1315,7 @@ pub fn early_error(output: config::ErrorOutputType, msg: &str) -> ! {
Box::new(EmitterWriter::stderr(color_config, None, true, false))
}
};
let handler = errors::Handler::with_emitter(true, false, emitter);
let handler = errors::Handler::with_emitter(true, None, emitter);
handler.emit(&MultiSpan::new(), msg, errors::Level::Fatal);
errors::FatalError.raise();
}
@@ -1330,7 +1330,7 @@ pub fn early_warn(output: config::ErrorOutputType, msg: &str) {
Box::new(EmitterWriter::stderr(color_config, None, true, false))
}
};
let handler = errors::Handler::with_emitter(true, false, emitter);
let handler = errors::Handler::with_emitter(true, None, emitter);
handler.emit(&MultiSpan::new(), msg, errors::Level::Warning);
}

@@ -247,7 +247,7 @@ pub struct CodegenContext<B: WriteBackendMethods> {

impl<B: WriteBackendMethods> CodegenContext<B> {
pub fn create_diag_handler(&self) -> Handler {
Handler::with_emitter(true, false, Box::new(self.diag_emitter.clone()))
Handler::with_emitter(true, None, Box::new(self.diag_emitter.clone()))
}

pub fn config(&self, kind: ModuleKind) -> &ModuleConfig {
@@ -148,7 +148,7 @@ pub fn run<F>(run_compiler: F) -> isize
true,
false
);
let handler = errors::Handler::with_emitter(true, false, Box::new(emitter));
let handler = errors::Handler::with_emitter(true, None, Box::new(emitter));
handler.emit(&MultiSpan::new(),
"aborting due to previous error(s)",
errors::Level::Fatal);
@@ -1327,7 +1327,7 @@ pub fn monitor<F: FnOnce() + Send + 'static>(f: F) -> Result<(), CompilationFail
None,
false,
false));
let handler = errors::Handler::with_emitter(true, false, emitter);
let handler = errors::Handler::with_emitter(true, None, emitter);

// a .span_bug or .bug call has already printed what
// it wants to print.
@@ -103,7 +103,7 @@ impl<'a> DiagnosticBuilder<'a> {
/// Buffers the diagnostic for later emission, unless handler
/// has disabled such buffering.
pub fn buffer(mut self, buffered_diagnostics: &mut Vec<Diagnostic>) {
if self.handler.flags.dont_buffer_diagnostics || self.handler.flags.treat_err_as_bug {
if self.handler.flags.dont_buffer_diagnostics || self.handler.treat_err_as_bug() {
self.emit();
return;
}
@@ -330,7 +330,7 @@ pub struct HandlerFlags {
pub can_emit_warnings: bool,
/// If true, error-level diagnostics are upgraded to bug-level.
/// (rustc: see `-Z treat-err-as-bug`)
pub treat_err_as_bug: bool,
pub treat_err_as_bug: Option<usize>,
/// If true, immediately emit diagnostics that would otherwise be buffered.
/// (rustc: see `-Z dont-buffer-diagnostics` and `-Z treat-err-as-bug`)
pub dont_buffer_diagnostics: bool,
@@ -360,7 +360,7 @@ impl Drop for Handler {
impl Handler {
pub fn with_tty_emitter(color_config: ColorConfig,
can_emit_warnings: bool,
treat_err_as_bug: bool,
treat_err_as_bug: Option<usize>,
cm: Option<Lrc<SourceMapperDyn>>)
-> Handler {
Handler::with_tty_emitter_and_flags(
@@ -382,7 +382,7 @@ impl Handler {
}

pub fn with_emitter(can_emit_warnings: bool,
treat_err_as_bug: bool,
treat_err_as_bug: Option<usize>,
e: Box<dyn Emitter + sync::Send>)
-> Handler {
Handler::with_emitter_and_flags(
@@ -516,7 +516,7 @@ impl Handler {
}

fn panic_if_treat_err_as_bug(&self) {
if self.flags.treat_err_as_bug {
if self.treat_err_as_bug() {
panic!("encountered error with `-Z treat_err_as_bug");
}
}
@@ -558,7 +558,7 @@ impl Handler {
panic!(ExplicitBug);
}
pub fn delay_span_bug<S: Into<MultiSpan>>(&self, sp: S, msg: &str) {
if self.flags.treat_err_as_bug {
if self.treat_err_as_bug() {
// FIXME: don't abort here if report_delayed_bugs is off
self.span_bug(sp, msg);
}
@@ -593,14 +593,14 @@ impl Handler {
DiagnosticBuilder::new(self, FailureNote, msg).emit()
}
pub fn fatal(&self, msg: &str) -> FatalError {
if self.flags.treat_err_as_bug {
if self.treat_err_as_bug() {
self.bug(msg);
}
DiagnosticBuilder::new(self, Fatal, msg).emit();
FatalError
}
pub fn err(&self, msg: &str) {
if self.flags.treat_err_as_bug {
if self.treat_err_as_bug() {
self.bug(msg);
}
let mut db = DiagnosticBuilder::new(self, Error, msg);
@@ -610,6 +610,9 @@ impl Handler {
let mut db = DiagnosticBuilder::new(self, Warning, msg);
db.emit();
}
fn treat_err_as_bug(&self) -> bool {
self.flags.treat_err_as_bug.map(|c| self.err_count() >= c).unwrap_or(false)
}
pub fn note_without_error(&self, msg: &str) {
let mut db = DiagnosticBuilder::new(self, Note, msg);
db.emit();
@@ -624,8 +627,8 @@ impl Handler {
}

fn bump_err_count(&self) {
self.panic_if_treat_err_as_bug();
self.err_count.fetch_add(1, SeqCst);
self.panic_if_treat_err_as_bug();
}

pub fn err_count(&self) -> usize {
@@ -643,7 +646,13 @@ impl Handler {
_ => format!("aborting due to {} previous errors", self.err_count())
};

let _ = self.fatal(&s);
let _ = if self.treat_err_as_bug() {
self.fatal(&s)
} else {
// only emit one backtrace when using `-Z treat-err-as-bug=X`
DiagnosticBuilder::new(self, Fatal, &s).emit();
FatalError
};

let can_show_explain = self.emitter.borrow().should_show_explain();
let are_there_diagnostics = !self.emitted_diagnostic_codes.borrow().is_empty();
@@ -266,7 +266,7 @@ impl DocAccessLevels for AccessLevels<DefId> {
/// will be created for the handler.
pub fn new_handler(error_format: ErrorOutputType,
source_map: Option<Lrc<source_map::SourceMap>>,
treat_err_as_bug: bool,
treat_err_as_bug: Option<usize>,
ui_testing: bool,
) -> errors::Handler {
// rustdoc doesn't override (or allow to override) anything from this that is relevant here, so
@@ -53,7 +53,7 @@ impl ParseSess {
let cm = Lrc::new(SourceMap::new(file_path_mapping));
let handler = Handler::with_tty_emitter(ColorConfig::Auto,
true,
false,
None,
Some(cm.clone()));
ParseSess::with_span_handler(handler, cm)
}

0 comments on commit 7a55a00

Please sign in to comment.
You can’t perform that action at this time.