Skip to content

Commit 4311f2e

Browse files
committed
Auto merge of rust-lang#118518 - weihanglo:trim-paths-macos, r=<try>
fix(trim-paths): trim `SO` and `DW_AT_comp_dir` symbols for root DI node This is one way to fix <rust-lang#117652>. ## The issue When `--remap-path-scope=object` is specified, user expect that there is no local path embedded in final executables. Under `object` scope, the current implementation only remap debug symbols if debug info is splitted into its own file. In other words, when `split-debuginfo=packed|unpacked` is set, rustc assumes there is no embedded path in the final executable needing to be remapped. However, this doesn't work. * On Linux, the root `DW_AT_comp_dir` of a compile unit seems to go into the binary executables. * On macOS, `SO` symbols are embedded in binary executables and libraries regardless a split-debuginfo file is built. Each `SO` symbol contains a path to the root source file of a debug info compile unit. ## The approach Path of working directory in the root DI node seems to be embedded in executables. Hence, we trim them when the scope of `unsplit-debuginfo` is present, as if it is kinda a "unsplit" debuginfo. ## Unresolved issue * Not sure where to add more test to consolidate it. * Haven't investigate if we should apply the same logic to cranelift [here](https://github.com/rust-lang/rust/blob/64d7e0d0b61c460fbc882ae37c0f236756dd9c39/compiler/rustc_codegen_cranelift/src/debuginfo/mod.rs#L68-L80). * Not sure if there is any other consequence doing this, but AFAIK debugging still works on macOS and Linux with `profile.dev.trim-paths="object"` fairly (with some extra tweaks in cargo).
2 parents 2b399b5 + 4fa22f1 commit 4311f2e

File tree

2 files changed

+128
-31
lines changed

2 files changed

+128
-31
lines changed

compiler/rustc_codegen_llvm/src/debuginfo/metadata.rs

+15-2
Original file line numberDiff line numberDiff line change
@@ -851,9 +851,22 @@ pub fn build_compile_unit_di_node<'ll, 'tcx>(
851851
// FIXME(#41252) Remove "clang LLVM" if we can get GDB and LLVM to play nice.
852852
let producer = format!("clang LLVM ({rustc_producer})");
853853

854-
use rustc_session::RemapFileNameExt;
855854
let name_in_debuginfo = name_in_debuginfo.to_string_lossy();
856-
let work_dir = tcx.sess.opts.working_dir.for_codegen(tcx.sess).to_string_lossy();
855+
debug!(?name_in_debuginfo, "build_compile_unit_di_node");
856+
857+
// Path of working directory in the root DI node seems to be embedded in
858+
// executables. Hence, we trim them when the scope of `unsplit-debuginfo`
859+
// is present, as if it is kinda a "unsplit" debuginfo.
860+
use rustc_session::config::RemapPathScopeComponents;
861+
use rustc_session::RemapFileNameExt;
862+
let work_dir = tcx
863+
.sess
864+
.opts
865+
.working_dir
866+
.for_scope(tcx.sess, RemapPathScopeComponents::UNSPLIT_DEBUGINFO)
867+
.to_string_lossy();
868+
debug!(?work_dir, "build_compile_unit_di_node");
869+
857870
let flags = "\0";
858871
let output_filenames = tcx.output_filenames(());
859872
let split_name = if tcx.sess.target_can_use_split_dwarf() {

tests/run-make/split-debuginfo/Makefile

+113-29
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,8 @@
11
# ignore-cross-compile
22
include ../tools.mk
33

4+
export HERE := $(shell pwd)
5+
46
all: off packed unpacked
57

68
ifeq ($(UNAME),Darwin)
@@ -11,23 +13,77 @@ off:
1113
[ ! -d $(TMPDIR)/foo.dSYM ]
1214

1315
# Packed by default, but only if debuginfo is requested
14-
packed:
15-
rm -rf $(TMPDIR)/*.dSYM
16-
$(RUSTC) foo.rs
17-
[ ! -d $(TMPDIR)/foo.dSYM ]
18-
rm -rf $(TMPDIR)/*.dSYM
19-
$(RUSTC) foo.rs -g
16+
packed: packed-remapped-scope packed-remapped-wrong-scope
17+
18+
# - Debuginfo in binary file
19+
# - `.o` deleted
20+
# - `.dSYM` present
21+
# - in binary, paths from `N_SO` (source files) and `N_OSO` (object files) shouldn be remapped
22+
packed-remapped-scope:
23+
$(RUSTC) $(UNSTABLEOPTS) -C split-debuginfo=packed -C debuginfo=2 \
24+
--remap-path-prefix $(TMPDIR)=/a \
25+
--remap-path-prefix $(HERE)=/b \
26+
-Z remap-path-scope=object foo.rs -g
27+
ls $(TMPDIR)/*.o && exit 1 || exit 0
2028
[ -d $(TMPDIR)/foo.dSYM ]
21-
rm -rf $(TMPDIR)/*.dSYM
22-
$(RUSTC) foo.rs -g -C split-debuginfo=packed
29+
# As of 2023-12, `OSO` should be the only thing that cannot be trimmed. See rust-lang/rust#116948
30+
dsymutil -s $(TMPDIR)/foo | grep $(TMPDIR) || exit 1 # expected: `grep $(TMPDIR)` to exit 1
31+
dsymutil -s $(TMPDIR)/foo | (! grep $(HERE)) || exit 1
32+
rm -rf $(TMPDIR)/foo.dSYM
33+
rm $(TMPDIR)/$(call BIN,foo)
34+
35+
# - Debuginfo in binary file
36+
# - `.o` deleted
37+
# - `.dSYM` present
38+
# - in binary, paths from `N_SO` (source files) and `N_OSO` (object files) shouldn't be remapped
39+
packed-remapped-wrong-scope:
40+
$(RUSTC) $(UNSTABLEOPTS) -C split-debuginfo=packed -C debuginfo=2 \
41+
--remap-path-prefix $(TMPDIR)=/a \
42+
--remap-path-prefix $(HERE)=/b \
43+
-Z remap-path-scope=macro foo.rs -g
44+
ls $(TMPDIR)/*.o && exit 1 || exit 0
2345
[ -d $(TMPDIR)/foo.dSYM ]
24-
rm -rf $(TMPDIR)/*.dSYM
46+
dsymutil -s $(TMPDIR)/foo | grep 'N_OSO' | grep $(TMPDIR) || exit 1
47+
dsymutil -s $(TMPDIR)/foo | grep 'N_SO' | grep $(HERE) || exit 1
48+
rm -rf $(TMPDIR)/foo.dSYM
49+
rm $(TMPDIR)/$(call BIN,foo)
2550

2651
# Object files are preserved with unpacked and `dsymutil` isn't run
27-
unpacked:
28-
$(RUSTC) foo.rs -g -C split-debuginfo=unpacked
52+
unpacked: unpacked-remapped-scope unpacked-remapped-wrong-scope
53+
54+
# - Debuginfo in object files
55+
# - `.o` present
56+
# - `.dSYM` never created
57+
# - in binary, paths from `N_SO` (source files) and `N_OSO` (object files) should be remapped
58+
unpacked-remapped-scope:
59+
$(RUSTC) $(UNSTABLEOPTS) -C split-debuginfo=unpacked -C debuginfo=2 \
60+
--remap-path-prefix $(TMPDIR)=/a \
61+
--remap-path-prefix $(HERE)=/b \
62+
-Z remap-path-scope=object foo.rs -g
63+
ls $(TMPDIR)/*.o
64+
[ ! -d $(TMPDIR)/foo.dSYM ]
65+
# As of 2023-12, `OSO` should be the only thing that cannot be trimmed. See rust-lang/rust#116948
66+
dsymutil -s $(TMPDIR)/foo | grep $(TMPDIR) || exit 1 # expected: `grep $(TMPDIR)` to exit 1
67+
dsymutil -s $(TMPDIR)/foo | (! grep $(HERE)) || exit 1
68+
rm $(TMPDIR)/*.o
69+
rm $(TMPDIR)/$(call BIN,foo)
70+
71+
# - Debuginfo in object files
72+
# - `.o` present,
73+
# - `.dSYM` never created
74+
# - in binary, paths from `N_SO` (source files) and `N_OSO` (object files) shouldn't be remapped
75+
unpacked-remapped-wrong-scope:
76+
$(RUSTC) $(UNSTABLEOPTS) -C split-debuginfo=unpacked -C debuginfo=2 \
77+
--remap-path-prefix $(TMPDIR)=/a \
78+
--remap-path-prefix $(HERE)=/b \
79+
-Z remap-path-scope=macro foo.rs -g
2980
ls $(TMPDIR)/*.o
3081
[ ! -d $(TMPDIR)/foo.dSYM ]
82+
dsymutil -s $(TMPDIR)/foo | grep 'N_OSO' | (grep $(TMPDIR)) || exit 1
83+
dsymutil -s $(TMPDIR)/foo | grep 'N_SO' | (grep $(HERE)) || exit 1
84+
rm $(TMPDIR)/*.o
85+
rm $(TMPDIR)/$(call BIN,foo)
86+
3187
else
3288
ifdef IS_WINDOWS
3389
# Windows only supports packed debuginfo - nothing to test.
@@ -113,8 +169,12 @@ packed-remapped: packed-remapped-split packed-remapped-single packed-remapped-sc
113169
# - `.dwp` present
114170
packed-remapped-split:
115171
$(RUSTC) $(UNSTABLEOPTS) -C split-debuginfo=packed -C debuginfo=2 \
116-
-Z split-dwarf-kind=split --remap-path-prefix $(TMPDIR)=/a foo.rs -g
117-
objdump -Wi $(TMPDIR)/foo | grep DW_AT_GNU_dwo_name | (! grep $(TMPDIR)) || exit 1
172+
-Z split-dwarf-kind=split \
173+
--remap-path-prefix $(TMPDIR)=/a \
174+
--remap-path-prefix $(HERE)=/b \
175+
foo.rs -g
176+
readelf -wi $(TMPDIR)/foo | (! grep $(TMPDIR)) || exit 1
177+
readelf -wi $(TMPDIR)/foo | (! grep $(HERE)) || exit 1
118178
ls $(TMPDIR)/*.o && exit 1 || exit 0
119179
ls $(TMPDIR)/*.dwo && exit 1 || exit 0
120180
rm $(TMPDIR)/foo.dwp
@@ -127,8 +187,12 @@ packed-remapped-split:
127187
# - `.dwp` present
128188
packed-remapped-single:
129189
$(RUSTC) $(UNSTABLEOPTS) -C split-debuginfo=packed -C debuginfo=2 \
130-
-Z split-dwarf-kind=single --remap-path-prefix $(TMPDIR)=/a foo.rs -g
131-
objdump -Wi $(TMPDIR)/foo | grep DW_AT_GNU_dwo_name | (! grep $(TMPDIR)) || exit 1
190+
-Z split-dwarf-kind=single \
191+
--remap-path-prefix $(TMPDIR)=/a \
192+
--remap-path-prefix $(HERE)=/b \
193+
foo.rs -g
194+
readelf -wi $(TMPDIR)/foo | (! grep $(TMPDIR)) || exit 1
195+
readelf -wi $(TMPDIR)/foo | (! grep $(HERE)) || exit 1
132196
ls $(TMPDIR)/*.o && exit 1 || exit 0
133197
ls $(TMPDIR)/*.dwo && exit 1 || exit 0
134198
rm $(TMPDIR)/foo.dwp
@@ -141,9 +205,12 @@ packed-remapped-single:
141205
# - `.dwp` present
142206
packed-remapped-scope:
143207
$(RUSTC) $(UNSTABLEOPTS) -C split-debuginfo=packed -C debuginfo=2 \
144-
-Z split-dwarf-kind=single --remap-path-prefix $(TMPDIR)=/a \
145-
-Z remap-path-scope=split-debuginfo-path foo.rs -g
146-
objdump -Wi $(TMPDIR)/foo | grep DW_AT_GNU_dwo_name | (! grep $(TMPDIR)) || exit 1
208+
-Z split-dwarf-kind=single \
209+
--remap-path-prefix $(TMPDIR)=/a \
210+
--remap-path-prefix $(HERE)=/b \
211+
-Z remap-path-scope=object foo.rs -g
212+
readelf -wi $(TMPDIR)/foo | (! grep $(TMPDIR)) || exit 1
213+
readelf -wi $(TMPDIR)/foo | (! grep $(HERE)) || exit 1
147214
ls $(TMPDIR)/*.o && exit 1 || exit 0
148215
ls $(TMPDIR)/*.dwo && exit 1 || exit 0
149216
rm $(TMPDIR)/foo.dwp
@@ -156,9 +223,12 @@ packed-remapped-scope:
156223
# - `.dwp` present
157224
packed-remapped-wrong-scope:
158225
$(RUSTC) $(UNSTABLEOPTS) -C split-debuginfo=packed -C debuginfo=2 \
159-
-Z split-dwarf-kind=single --remap-path-prefix $(TMPDIR)=/a \
226+
-Z split-dwarf-kind=single \
227+
--remap-path-prefix $(TMPDIR)=/a \
228+
--remap-path-prefix $(TMPDIR)=/b \
160229
-Z remap-path-scope=macro foo.rs -g
161-
objdump -Wi $(TMPDIR)/foo | grep DW_AT_GNU_dwo_name | (grep $(TMPDIR)) || exit 1
230+
readelf -wi $(TMPDIR)/foo | (grep $(TMPDIR)) || exit 1
231+
readelf -wi $(TMPDIR)/foo | grep $(HERE) || exit 1
162232
ls $(TMPDIR)/*.o && exit 1 || exit 0
163233
ls $(TMPDIR)/*.dwo && exit 1 || exit 0
164234
rm $(TMPDIR)/foo.dwp
@@ -269,8 +339,12 @@ unpacked-remapped: unpacked-remapped-split unpacked-remapped-single unpacked-rem
269339
# - `.dwp` never created
270340
unpacked-remapped-split:
271341
$(RUSTC) $(UNSTABLEOPTS) -C split-debuginfo=unpacked -C debuginfo=2 \
272-
-Z split-dwarf-kind=split --remap-path-prefix $(TMPDIR)=/a foo.rs -g
273-
objdump -Wi $(TMPDIR)/foo | grep DW_AT_GNU_dwo_name | (! grep $(TMPDIR)) || exit 1
342+
-Z split-dwarf-kind=split \
343+
--remap-path-prefix $(TMPDIR)=/a \
344+
--remap-path-prefix $(HERE)=/b \
345+
foo.rs -g
346+
readelf -wi $(TMPDIR)/foo | (! grep $(TMPDIR)) || exit 1
347+
readelf -wi $(TMPDIR)/foo | (! grep $(HERE)) || exit 1
274348
ls $(TMPDIR)/*.o && exit 1 || exit 0
275349
rm $(TMPDIR)/*.dwo
276350
ls $(TMPDIR)/*.dwp && exit 1 || exit 0
@@ -283,8 +357,12 @@ unpacked-remapped-split:
283357
# - `.dwp` never created
284358
unpacked-remapped-single:
285359
$(RUSTC) $(UNSTABLEOPTS) -C split-debuginfo=unpacked -C debuginfo=2 \
286-
-Z split-dwarf-kind=single --remap-path-prefix $(TMPDIR)=/a foo.rs -g
287-
objdump -Wi $(TMPDIR)/foo | grep DW_AT_GNU_dwo_name | (! grep $(TMPDIR)) || exit 1
360+
-Z split-dwarf-kind=single \
361+
--remap-path-prefix $(TMPDIR)=/a \
362+
--remap-path-prefix $(HERE)=/b \
363+
foo.rs -g
364+
readelf -wi $(TMPDIR)/foo | (! grep $(TMPDIR)) || exit 1
365+
readelf -wi $(TMPDIR)/foo | (! grep $(HERE)) || exit 1
288366
rm $(TMPDIR)/*.o
289367
ls $(TMPDIR)/*.dwo && exit 1 || exit 0
290368
ls $(TMPDIR)/*.dwp && exit 1 || exit 0
@@ -297,9 +375,12 @@ unpacked-remapped-single:
297375
# - `.dwp` never created
298376
unpacked-remapped-scope:
299377
$(RUSTC) $(UNSTABLEOPTS) -C split-debuginfo=unpacked -C debuginfo=2 \
300-
-Z split-dwarf-kind=single --remap-path-prefix $(TMPDIR)=/a \
301-
-Z remap-path-scope=split-debuginfo-path foo.rs -g
302-
objdump -Wi $(TMPDIR)/foo | grep DW_AT_GNU_dwo_name | (! grep $(TMPDIR)) || exit 1
378+
-Z split-dwarf-kind=single \
379+
--remap-path-prefix $(TMPDIR)=/a \
380+
--remap-path-prefix $(HERE)=/b \
381+
-Z remap-path-scope=object foo.rs -g
382+
readelf -wi $(TMPDIR)/foo | (! grep $(TMPDIR)) || exit 1
383+
readelf -wi $(TMPDIR)/foo | (! grep $(HERE)) || exit 1
303384
rm $(TMPDIR)/*.o
304385
ls $(TMPDIR)/*.dwo && exit 1 || exit 0
305386
ls $(TMPDIR)/*.dwp && exit 1 || exit 0
@@ -312,9 +393,12 @@ unpacked-remapped-scope:
312393
# - `.dwp` never created
313394
unpacked-remapped-wrong-scope:
314395
$(RUSTC) $(UNSTABLEOPTS) -C split-debuginfo=unpacked -C debuginfo=2 \
315-
-Z split-dwarf-kind=single --remap-path-prefix $(TMPDIR)=/a \
396+
-Z split-dwarf-kind=single \
397+
--remap-path-prefix $(TMPDIR)=/a \
398+
--remap-path-prefix $(HERE)=/b \
316399
-Z remap-path-scope=macro foo.rs -g
317-
objdump -Wi $(TMPDIR)/foo | grep DW_AT_GNU_dwo_name | (grep $(TMPDIR)) || exit 1
400+
readelf -wi $(TMPDIR)/foo | grep $(TMPDIR) || exit 1
401+
readelf -wi $(TMPDIR)/foo | grep $(HERE) || exit 1
318402
rm $(TMPDIR)/*.o
319403
ls $(TMPDIR)/*.dwo && exit 1 || exit 0
320404
ls $(TMPDIR)/*.dwp && exit 1 || exit 0

0 commit comments

Comments
 (0)