diff --git a/src/librustc/session/config.rs b/src/librustc/session/config.rs index e500c08ce6e32..385cb13c30a84 100644 --- a/src/librustc/session/config.rs +++ b/src/librustc/session/config.rs @@ -253,6 +253,7 @@ top_level_options!( // Include the debug_assertions flag into dependency tracking, since it // can influence whether overflow checks are done or not. debug_assertions: bool [TRACKED], + debug_prefix_map: Option<(String, String)> [TRACKED], debuginfo: DebugInfoLevel [TRACKED], lint_opts: Vec<(String, lint::Level)> [TRACKED], lint_cap: Option [TRACKED], @@ -445,6 +446,7 @@ pub fn basic_options() -> Options { libs: Vec::new(), unstable_features: UnstableFeatures::Disallow, debug_assertions: true, + debug_prefix_map: None, actually_rustdoc: false, } } @@ -801,6 +803,8 @@ options! {CodegenOptions, CodegenSetter, basic_codegen_options, "optimize with possible levels 0-3, s, or z"), debug_assertions: Option = (None, parse_opt_bool, [TRACKED], "explicitly enable the cfg(debug_assertions) directive"), + debug_prefix_map: String = ("".to_string(), parse_string, [TRACKED], + "remap OLD to NEW in debug info (OLD=NEW)"), inline_threshold: Option = (None, parse_opt_uint, [TRACKED], "set the inlining threshold for"), panic: Option = (None, parse_panic_strategy, @@ -1423,6 +1427,20 @@ pub fn build_session_options_and_crate_config(matches: &getopts::Matches) } }; let debug_assertions = cg.debug_assertions.unwrap_or(opt_level == OptLevel::No); + + let debug_prefix_map = if !cg.debug_prefix_map.is_empty() { + let mut parts = cg.debug_prefix_map.splitn(2, '='); + let old = parts.next().unwrap(); + let new = match parts.next() { + Some(new) => new, + None => early_error(error_format, + "-C debug-prefix-map value must be of the format `OLD=NEW`"), + }; + Some((old.to_string(), new.to_string())) + } else { + None + }; + let debuginfo = if matches.opt_present("g") { if cg.debuginfo.is_some() { early_error(error_format, "-g and -C debuginfo both provided"); @@ -1539,6 +1557,7 @@ pub fn build_session_options_and_crate_config(matches: &getopts::Matches) libs: libs, unstable_features: UnstableFeatures::from_environment(), debug_assertions: debug_assertions, + debug_prefix_map: debug_prefix_map, actually_rustdoc: false, }, cfg) @@ -1714,6 +1733,7 @@ mod dep_tracking { impl_dep_tracking_hash_via_hash!(Option); impl_dep_tracking_hash_via_hash!(Option); impl_dep_tracking_hash_via_hash!(Option); + impl_dep_tracking_hash_via_hash!(Option<(String, String)>); impl_dep_tracking_hash_via_hash!(Option); impl_dep_tracking_hash_via_hash!(Option); impl_dep_tracking_hash_via_hash!(Option); diff --git a/src/librustc_trans/debuginfo/metadata.rs b/src/librustc_trans/debuginfo/metadata.rs index 5022e0750e38e..a16236fb9aee2 100644 --- a/src/librustc_trans/debuginfo/metadata.rs +++ b/src/librustc_trans/debuginfo/metadata.rs @@ -657,6 +657,15 @@ pub fn type_metadata<'a, 'tcx>(cx: &CrateContext<'a, 'tcx>, metadata } +fn remap_path(sess: &Session, path: &str) -> String { + for (old, new) in sess.opts.debug_prefix_map.clone() { + if path.starts_with(&old) { + return new + &path[old.len()..]; + } + } + path.to_string() +} + pub fn file_metadata(cx: &CrateContext, path: &str, full_path: &Option) -> DIFile { // FIXME (#9639): This needs to handle non-utf8 paths let work_dir = cx.sess().working_dir.to_str().unwrap(); @@ -669,7 +678,10 @@ pub fn file_metadata(cx: &CrateContext, path: &str, full_path: &Option) } }); - file_metadata_(cx, path, file_name, &work_dir) + let sess = cx.sess(); + let remap_file_name = remap_path(sess, file_name); + let remap_dir = remap_path(sess, work_dir); + file_metadata_(cx, path, &remap_file_name, &remap_dir) } pub fn unknown_file_metadata(cx: &CrateContext) -> DIFile { @@ -759,7 +771,7 @@ pub fn compile_unit_metadata(scc: &SharedCrateContext, debug_context: &CrateDebugContext, sess: &Session) -> DIDescriptor { - let work_dir = &sess.working_dir; + let work_dir = sess.working_dir.to_str().unwrap(); let compile_unit_name = match sess.local_crate_source_file { None => fallback_path(scc), Some(ref abs_path) => { @@ -781,12 +793,14 @@ pub fn compile_unit_metadata(scc: &SharedCrateContext, } }; + let work_dir = remap_path(sess, work_dir); + debug!("compile_unit_metadata: {:?}", compile_unit_name); let producer = format!("rustc version {}", (option_env!("CFG_VERSION")).expect("CFG_VERSION")); let compile_unit_name = compile_unit_name.as_ptr(); - let work_dir = path2cstr(&work_dir); + let work_dir = CString::new(work_dir).unwrap(); let producer = CString::new(producer).unwrap(); let flags = "\0"; let split_name = "\0";