diff options
| author | Ralf Jung <post@ralfj.de> | 2017-08-04 10:55:35 -0700 |
|---|---|---|
| committer | Ralf Jung <post@ralfj.de> | 2017-08-04 10:55:35 -0700 |
| commit | ac49e7c650afcff2d253a1a156592f72c44a49d2 (patch) | |
| tree | ef278ea00d1c3c3b221677847202f8c6d583a950 /src | |
| parent | 726b027ba3d2658d1a7796f46ea404c7299b7c0c (diff) | |
| download | rust-ac49e7c650afcff2d253a1a156592f72c44a49d2.tar.gz rust-ac49e7c650afcff2d253a1a156592f72c44a49d2.zip | |
only collect backtrace when RUST_BACKTRACE is set; resolve symbols lazily when printing
Diffstat (limited to 'src')
| -rw-r--r-- | src/librustc_mir/Cargo.toml | 2 | ||||
| -rw-r--r-- | src/librustc_mir/interpret/error.rs | 10 | ||||
| -rw-r--r-- | src/librustc_mir/interpret/eval_context.rs | 76 |
3 files changed, 48 insertions, 40 deletions
diff --git a/src/librustc_mir/Cargo.toml b/src/librustc_mir/Cargo.toml index 1ccb9ec0d29..1a64bb8c7c7 100644 --- a/src/librustc_mir/Cargo.toml +++ b/src/librustc_mir/Cargo.toml @@ -17,4 +17,4 @@ log = "0.3.6" log_settings = "0.1.1" lazy_static = "0.2.8" regex = "0.2.2" -backtrace = "0.3" +backtrace = { version = "0.3", git = "https://github.com/alexcrichton/backtrace-rs" } diff --git a/src/librustc_mir/interpret/error.rs b/src/librustc_mir/interpret/error.rs index 3b297ed5bd0..f22d26ab8bf 100644 --- a/src/librustc_mir/interpret/error.rs +++ b/src/librustc_mir/interpret/error.rs @@ -1,5 +1,5 @@ use std::error::Error; -use std::fmt; +use std::{fmt, env}; use rustc::mir; use rustc::ty::{FnSig, Ty, layout}; @@ -15,14 +15,18 @@ use backtrace::Backtrace; #[derive(Debug)] pub struct EvalError<'tcx> { pub kind: EvalErrorKind<'tcx>, - pub backtrace: Backtrace, + pub backtrace: Option<Backtrace>, } impl<'tcx> From<EvalErrorKind<'tcx>> for EvalError<'tcx> { fn from(kind: EvalErrorKind<'tcx>) -> Self { + let backtrace = match env::var("RUST_BACKTRACE") { + Ok(ref val) if !val.is_empty() => Some(Backtrace::new_unresolved()), + _ => None + }; EvalError { kind, - backtrace: Backtrace::new(), + backtrace, } } } diff --git a/src/librustc_mir/interpret/eval_context.rs b/src/librustc_mir/interpret/eval_context.rs index 9f37b3521dc..6f47dd03573 100644 --- a/src/librustc_mir/interpret/eval_context.rs +++ b/src/librustc_mir/interpret/eval_context.rs @@ -1716,49 +1716,53 @@ impl<'a, 'tcx, M: Machine<'tcx>> EvalContext<'a, 'tcx, M> { Ok(()) } - pub fn report(&self, e: &EvalError) { - let mut trace_text = "\n################################\nerror occurred in miri at\n".to_string(); - let mut skip_init = true; - 'frames: for (i, frame) in e.backtrace.frames().iter().enumerate() { - for symbol in frame.symbols() { - if let Some(name) = symbol.name() { - // unmangle the symbol via `to_string` - let name = name.to_string(); - if name.starts_with("miri::after_analysis") { - // don't report initialization gibberish - break 'frames; - } else if name.starts_with("backtrace::capture::Backtrace::new") + pub fn report(&self, e: &mut EvalError) { + if let Some(ref mut backtrace) = e.backtrace { + let mut trace_text = "\n\nAn error occurred in miri:\n".to_string(); + let mut skip_init = true; + backtrace.resolve(); + 'frames: for (i, frame) in backtrace.frames().iter().enumerate() { + for symbol in frame.symbols() { + if let Some(name) = symbol.name() { + // unmangle the symbol via `to_string` + let name = name.to_string(); + if name.starts_with("miri::after_analysis") { + // don't report initialization gibberish + break 'frames; + } else if name.starts_with("backtrace::capture::Backtrace::new") // debug mode produces funky symbol names - || name.starts_with("backtrace::capture::{{impl}}::new") { - // don't report backtrace internals - skip_init = false; - continue 'frames; + || name.starts_with("backtrace::capture::{{impl}}::new") { + // don't report backtrace internals + skip_init = false; + continue 'frames; + } } } - } - if skip_init { - continue; - } - write!(trace_text, "{}\n", i).unwrap(); - for symbol in frame.symbols() { - if let Some(name) = symbol.name() { - write!(trace_text, "# {}\n", name).unwrap(); - } else { - write!(trace_text, "# <unknown>\n").unwrap(); - } - if let Some(file_path) = symbol.filename() { - write!(trace_text, "{}", file_path.display()).unwrap(); - } else { - write!(trace_text, "<unknown_file>").unwrap(); + if skip_init { + continue; } - if let Some(line) = symbol.lineno() { - write!(trace_text, ":{}\n", line).unwrap(); - } else { - write!(trace_text, "\n").unwrap(); + for symbol in frame.symbols() { + write!(trace_text, "{}: " , i).unwrap(); + if let Some(name) = symbol.name() { + write!(trace_text, "{}\n", name).unwrap(); + } else { + write!(trace_text, "<unknown>\n").unwrap(); + } + write!(trace_text, "\tat ").unwrap(); + if let Some(file_path) = symbol.filename() { + write!(trace_text, "{}", file_path.display()).unwrap(); + } else { + write!(trace_text, "<unknown_file>").unwrap(); + } + if let Some(line) = symbol.lineno() { + write!(trace_text, ":{}\n", line).unwrap(); + } else { + write!(trace_text, "\n").unwrap(); + } } } + error!("{}", trace_text); } - trace!("{}", trace_text); if let Some(frame) = self.stack().last() { let block = &frame.mir.basic_blocks()[frame.block]; let span = if frame.stmt < block.statements.len() { |
