[Bug d/90778] New: Strange differences in D runtime debug-info between builds
rguenth at gcc dot gnu.org
gcc-bugzilla@gcc.gnu.org
Fri Jun 7 11:05:00 GMT 2019
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=90778
Bug ID: 90778
Summary: Strange differences in D runtime debug-info between
builds
Product: gcc
Version: 9.0
Status: UNCONFIRMED
Severity: normal
Priority: P3
Component: d
Assignee: ibuclaw at gdcproject dot org
Reporter: rguenth at gcc dot gnu.org
Target Milestone: ---
We see builds of the D runtime be not reproducible when compiling from the
same source multiple times. This for example shows in
libdruntime/rt/lifetime.d
objects which have
@@ -3853,17 +3853,17 @@
<2212> DW_AT_location : 0x1692 (location list)
<2216> DW_AT_GNU_locviews: 0x1684
<2><221a>: Abbrev Number: 48 (DW_TAG_label)
- <221b> DW_AT_name : (indirect string, offset: 0x22f2): Lcontinue
+ <221b> DW_AT_name : (indirect string, offset: 0xcac): Loverflow
<221f> DW_AT_decl_file : 1
- <2220> DW_AT_decl_line : 784
+ <2220> DW_AT_decl_line : 781
<2222> DW_AT_decl_column : 1
- <2223> DW_AT_low_pc : 0xaaa
+ <2223> DW_AT_low_pc : 0xe4e
<2><222b>: Abbrev Number: 48 (DW_TAG_label)
- <222c> DW_AT_name : (indirect string, offset: 0xcdc): Loverflow
+ <222c> DW_AT_name : (indirect string, offset: 0x22f2): Lcontinue
<2230> DW_AT_decl_file : 1
- <2231> DW_AT_decl_line : 781
+ <2231> DW_AT_decl_line : 784
<2233> DW_AT_decl_column : 1
- <2234> DW_AT_low_pc : 0xe4e
+ <2234> DW_AT_low_pc : 0xaaa
<2><223c>: Abbrev Number: 9 (DW_TAG_variable)
<223d> DW_AT_name : tgt
<2241> DW_AT_decl_file : 1
which appears in
<1><21b2>: Abbrev Number: 21 (DW_TAG_subprogram)
<21b3> DW_AT_external : 1
<21b3> DW_AT_name : (indirect string, offset: 0x880):
_d_arraysetcapacity
<21b7> DW_AT_decl_file : 1
<21b8> DW_AT_decl_line : 734
<21ba> DW_AT_decl_column : 18
<21bb> DW_AT_type : <0x29>
<21bf> DW_AT_low_pc : 0xa00
<21c7> DW_AT_high_pc : 0x46b
<21cf> DW_AT_frame_base : 1 byte block: 9c (DW_OP_call_frame_cfa)
<21d1> DW_AT_GNU_all_call_sites: 1
<21d1> DW_AT_sibling : <0x2609>
it looks like D maintains labels in a hash-map, doing
/* Pop all the labels declared in the function. */
if (d_function_chain->labels)
d_function_chain->labels->traverse<tree, &pop_label> (block);
and
bool
pop_label (Statement * const &s, d_label_entry *ent, tree block)
{
if (!ent->bc_label)
{
/* Put the labels into the "variables" of the top-level block,
so debugger can see them. */
if (DECL_NAME (ent->label))
{
gcc_assert (DECL_INITIAL (ent->label) != NULL_TREE);
DECL_CHAIN (ent->label) = BLOCK_VARS (block);
BLOCK_VARS (block) = ent->label;
so the order of labels depend on the order of them appearing in the hashtable
which means depending on virtual addresses and hashtable size.
I suggest to fix this by sorting the labels after DECL_UID (which should
order them after time of creation which should roughly match parsing/source
order) and emit them from there. This means putting the hashtable
contents into a vector and sorting that, sth GCC does elsewhere to avoid
random code-generation differences with for example address-space
randomization.
grepping for 'traverse' this might be the only place D does this.
I'm also not sure it is safe to remove elements while traversing.
More information about the Gcc-bugs
mailing list