diff options
| author | Sebastian Poeplau <poeplau@adacore.com> | 2025-08-01 12:39:50 +0200 |
|---|---|---|
| committer | Sebastian Poeplau <poeplau@adacore.com> | 2025-08-05 10:55:07 +0200 |
| commit | 868bdde25b030e0b71a29a5dbc04a891036e702e (patch) | |
| tree | 4fdbccbcc0f1760014fba2ae3e771f76bb065c04 /compiler/rustc_codegen_llvm/src/debuginfo/gdb.rs | |
| parent | 0f353363965ebf05e0757f7679c800b39c51a07e (diff) | |
| download | rust-868bdde25b030e0b71a29a5dbc04a891036e702e.tar.gz rust-868bdde25b030e0b71a29a5dbc04a891036e702e.zip | |
Preserve the .debug_gdb_scripts section
Make sure that compiler and linker don't optimize the section's contents away by adding the global holding the data to "llvm.used". The volatile load in the main shim is retained because "llvm.used", which translates to SHF_GNU_RETAIN on ELF targets, requires a reasonably recent linker; emitting the volatile load ensures compatibility with older linkers, at least when libstd is used. Pretty printers in dylib dependencies are now emitted by the main crate instead of the dylib; apart from matching how rlibs are handled, this approach has the advantage that `omit_gdb_pretty_printer_section` keeps working with dylib dependencies.
Diffstat (limited to 'compiler/rustc_codegen_llvm/src/debuginfo/gdb.rs')
| -rw-r--r-- | compiler/rustc_codegen_llvm/src/debuginfo/gdb.rs | 30 |
1 files changed, 16 insertions, 14 deletions
diff --git a/compiler/rustc_codegen_llvm/src/debuginfo/gdb.rs b/compiler/rustc_codegen_llvm/src/debuginfo/gdb.rs index 6eb7042da61..b3e978be570 100644 --- a/compiler/rustc_codegen_llvm/src/debuginfo/gdb.rs +++ b/compiler/rustc_codegen_llvm/src/debuginfo/gdb.rs @@ -1,5 +1,7 @@ // .debug_gdb_scripts binary section. +use std::ffi::CString; + use rustc_codegen_ssa::base::collect_debugger_visualizers_transitive; use rustc_codegen_ssa::traits::*; use rustc_hir::def_id::LOCAL_CRATE; @@ -31,7 +33,12 @@ pub(crate) fn insert_reference_to_gdb_debug_scripts_section_global(bx: &mut Buil pub(crate) fn get_or_insert_gdb_debug_scripts_section_global<'ll>( cx: &CodegenCx<'ll, '_>, ) -> &'ll Value { - let c_section_var_name = c"__rustc_debug_gdb_scripts_section__"; + let c_section_var_name = CString::new(format!( + "__rustc_debug_gdb_scripts_section_{}_{:08x}", + cx.tcx.crate_name(LOCAL_CRATE), + cx.tcx.stable_crate_id(LOCAL_CRATE), + )) + .unwrap(); let section_var_name = c_section_var_name.to_str().unwrap(); let section_var = unsafe { llvm::LLVMGetNamedGlobal(cx.llmod, c_section_var_name.as_ptr()) }; @@ -84,17 +91,10 @@ pub(crate) fn get_or_insert_gdb_debug_scripts_section_global<'ll>( } pub(crate) fn needs_gdb_debug_scripts_section(cx: &CodegenCx<'_, '_>) -> bool { - // To ensure the section `__rustc_debug_gdb_scripts_section__` will not create - // ODR violations at link time, this section will not be emitted for rlibs since - // each rlib could produce a different set of visualizers that would be embedded - // in the `.debug_gdb_scripts` section. For that reason, we make sure that the - // section is only emitted for leaf crates. + // We collect pretty printers transitively for all crates, so we make sure + // that the section is only emitted for leaf crates. let embed_visualizers = cx.tcx.crate_types().iter().any(|&crate_type| match crate_type { - CrateType::Executable - | CrateType::Dylib - | CrateType::Cdylib - | CrateType::Staticlib - | CrateType::Sdylib => { + CrateType::Executable | CrateType::Cdylib | CrateType::Staticlib | CrateType::Sdylib => { // These are crate types for which we will embed pretty printers since they // are treated as leaf crates. true @@ -105,9 +105,11 @@ pub(crate) fn needs_gdb_debug_scripts_section(cx: &CodegenCx<'_, '_>) -> bool { // want to slow down the common case. false } - CrateType::Rlib => { - // As per the above description, embedding pretty printers for rlibs could - // lead to ODR violations so we skip this crate type as well. + CrateType::Rlib | CrateType::Dylib => { + // Don't embed pretty printers for these crate types; the compiler + // can see the `#[debug_visualizer]` attributes when using the + // library, and emitting `.debug_gdb_scripts` regardless would + // break `#![omit_gdb_pretty_printer_section]`. false } }); |
