From ee073b5ec54a13b393071298acc54e1fd28cfcdf Mon Sep 17 00:00:00 2001 From: David Wood Date: Sun, 8 Nov 2020 17:17:37 +0000 Subject: [PATCH] cg_llvm: split dwarf filename and comp dir llvm-dwp concatenates `DW_AT_comp_dir` with `DW_AT_GNU_dwo_name` (only when `DW_AT_comp_dir` exists), which can result in it failing to find the DWARF object files. In earlier testing, `DW_AT_comp_dir` wasn't present in the final object and the current directory was the output directory. When running tests through compiletest, the working directory of the compilation is different from output directory and that resulted in `DW_AT_comp_dir` being in the object file (and set to the current working directory, rather than the output directory), and `DW_AT_GNU_dwo_name` being set to the full path (rather than just the filename), so llvm-dwp was failing. This commit changes the compilation directory provided to LLVM to match the output directory, where DWARF objects are output; and ensures that only the filename is used for `DW_AT_GNU_dwo_name`. Signed-off-by: David Wood --- compiler/rustc_codegen_llvm/src/back/lto.rs | 2 +- compiler/rustc_codegen_llvm/src/back/write.rs | 2 +- .../rustc_codegen_llvm/src/debuginfo/metadata.rs | 10 ++++++---- compiler/rustc_codegen_llvm/src/lib.rs | 2 +- compiler/rustc_session/src/config.rs | 13 ++++++++++++- 5 files changed, 21 insertions(+), 8 deletions(-) diff --git a/compiler/rustc_codegen_llvm/src/back/lto.rs b/compiler/rustc_codegen_llvm/src/back/lto.rs index 834fc02c48ab8..29415973ed073 100644 --- a/compiler/rustc_codegen_llvm/src/back/lto.rs +++ b/compiler/rustc_codegen_llvm/src/back/lto.rs @@ -734,7 +734,7 @@ pub unsafe fn optimize_thin_module( let module_name = &thin_module.shared.module_names[thin_module.idx]; let split_dwarf_file = cgcx .output_filenames - .split_dwarf_file(cgcx.split_dwarf_kind, Some(module_name.to_str().unwrap())); + .split_dwarf_filename(cgcx.split_dwarf_kind, Some(module_name.to_str().unwrap())); let tm_factory_config = TargetMachineFactoryConfig { split_dwarf_file }; let tm = (cgcx.tm_factory)(tm_factory_config).map_err(|e| write::llvm_err(&diag_handler, &e))?; diff --git a/compiler/rustc_codegen_llvm/src/back/write.rs b/compiler/rustc_codegen_llvm/src/back/write.rs index ef99c87053c76..3fda1e26dae9e 100644 --- a/compiler/rustc_codegen_llvm/src/back/write.rs +++ b/compiler/rustc_codegen_llvm/src/back/write.rs @@ -95,7 +95,7 @@ pub fn create_informational_target_machine(sess: &Session) -> &'static mut llvm: pub fn create_target_machine(tcx: TyCtxt<'_>, mod_name: &str) -> &'static mut llvm::TargetMachine { let split_dwarf_file = tcx .output_filenames(LOCAL_CRATE) - .split_dwarf_file(tcx.sess.opts.debugging_opts.split_dwarf, Some(mod_name)); + .split_dwarf_filename(tcx.sess.opts.debugging_opts.split_dwarf, Some(mod_name)); let config = TargetMachineFactoryConfig { split_dwarf_file }; target_machine_factory(&tcx.sess, tcx.backend_optimization_level(LOCAL_CRATE))(config) .unwrap_or_else(|err| llvm_err(tcx.sess.diagnostic(), &err).raise()) diff --git a/compiler/rustc_codegen_llvm/src/debuginfo/metadata.rs b/compiler/rustc_codegen_llvm/src/debuginfo/metadata.rs index a9eff59b6affa..fa285f3488f84 100644 --- a/compiler/rustc_codegen_llvm/src/debuginfo/metadata.rs +++ b/compiler/rustc_codegen_llvm/src/debuginfo/metadata.rs @@ -993,12 +993,14 @@ pub fn compile_unit_metadata( let producer = format!("clang LLVM ({})", rustc_producer); let name_in_debuginfo = name_in_debuginfo.to_string_lossy(); - let work_dir = tcx.sess.working_dir.0.to_string_lossy(); let flags = "\0"; + + let out_dir = &tcx.output_filenames(LOCAL_CRATE).out_directory; let split_name = tcx .output_filenames(LOCAL_CRATE) - .split_dwarf_file(tcx.sess.opts.debugging_opts.split_dwarf, Some(codegen_unit_name)) + .split_dwarf_filename(tcx.sess.opts.debugging_opts.split_dwarf, Some(codegen_unit_name)) .unwrap_or_default(); + let out_dir = out_dir.to_str().unwrap(); let split_name = split_name.to_str().unwrap(); // FIXME(#60020): @@ -1024,8 +1026,8 @@ pub fn compile_unit_metadata( debug_context.builder, name_in_debuginfo.as_ptr().cast(), name_in_debuginfo.len(), - work_dir.as_ptr().cast(), - work_dir.len(), + out_dir.as_ptr().cast(), + out_dir.len(), llvm::ChecksumKind::None, ptr::null(), 0, diff --git a/compiler/rustc_codegen_llvm/src/lib.rs b/compiler/rustc_codegen_llvm/src/lib.rs index a5f125d114d28..a58c2fbd8ab2c 100644 --- a/compiler/rustc_codegen_llvm/src/lib.rs +++ b/compiler/rustc_codegen_llvm/src/lib.rs @@ -356,7 +356,7 @@ impl ModuleLlvm { let split_dwarf_file = cgcx .output_filenames - .split_dwarf_file(cgcx.split_dwarf_kind, Some(name.to_str().unwrap())); + .split_dwarf_filename(cgcx.split_dwarf_kind, Some(name.to_str().unwrap())); let tm_factory_config = TargetMachineFactoryConfig { split_dwarf_file }; let tm = match (cgcx.tm_factory)(tm_factory_config) { diff --git a/compiler/rustc_session/src/config.rs b/compiler/rustc_session/src/config.rs index b3d4c6e3ec73b..c20b11656b229 100644 --- a/compiler/rustc_session/src/config.rs +++ b/compiler/rustc_session/src/config.rs @@ -617,9 +617,20 @@ impl OutputFilenames { path } + /// Returns the name of the Split DWARF file - this can differ depending on which Split DWARF + /// mode is being used, which is the logic that this function is intended to encapsulate. + pub fn split_dwarf_filename( + &self, + split_dwarf_kind: SplitDwarfKind, + cgu_name: Option<&str>, + ) -> Option { + self.split_dwarf_path(split_dwarf_kind, cgu_name) + .map(|path| path.strip_prefix(&self.out_directory).unwrap_or(&path).to_path_buf()) + } + /// Returns the path for the Split DWARF file - this can differ depending on which Split DWARF /// mode is being used, which is the logic that this function is intended to encapsulate. - pub fn split_dwarf_file( + pub fn split_dwarf_path( &self, split_dwarf_kind: SplitDwarfKind, cgu_name: Option<&str>,