]> git.ipfire.org Git - thirdparty/binutils-gdb.git/commitdiff
gdb/testsuite/dwarf: emit type unit sections as COMDAT
authorSimon Marchi <simon.marchi@polymtl.ca>
Fri, 21 Nov 2025 20:14:01 +0000 (15:14 -0500)
committerSimon Marchi <simon.marchi@polymtl.ca>
Mon, 1 Dec 2025 17:45:09 +0000 (12:45 -0500)
In an effort to generate ELF files and DWARF info as close as possible
as an actual compiler would generate, change how we emit type unit
sections to emit each type unit in its own section, in COMDAT section
groups.

We currently emit all type units in a single, standard section (either
.debug_info or .debug_types, depending on the DWARF version).  Compilers
emit each type unit in its own .debug_types section.  Each section is
placed in a COMDAT section group with a signature based on the type
unit's signature.  This lets the linker deduplicate identical type units
by discarding section groups with identical signatures (keeping only one
group with a given signature).

Looking at a .s file generated by gcc, we can see that this is how it
specifies the section for a type unit:

    .section .debug_info,"G",@progbits,wi.006fd2152a3054a6,comdat

The "G" flag tells the assembler to place the section in a section
group with signature "wi.006fd2152a3054a6".  That string was generated
from the type unit, signature.  Finally, the comdat linkage field
indicates that the section group should have the COMDAT flag.

Update the tu proc to emit a section with these properties.  In this
case, it's mandatory to specify the type of the section (progbits).

Update the _section proc to accept the new options "group_signature" and
"linkage".

As a result, if you look at the .debug_types section in a .o file from
gcc:

    $ readelf -g main.o
    COMDAT group section [    1] `.group' [wt.006fd2152a3054a6] contains 2 sections:
       [Index]    Name
       [   11]   .debug_types
       [   12]   .rela.debug_types

    COMDAT group section [    2] `.group' [wt.c621aa8e3c23e450] contains 2 sections:
       [Index]    Name
       [   13]   .debug_types
       [   14]   .rela.debug_types

And a .o file created by our DWARF assembler:

    $ readelf -g testsuite/outputs/gdb.dwarf2/struct-with-sig/struct-with-sig1.o
    COMDAT group section [    1] `.group' [sig.0x0000000000000001] contains 2 sections:
       [Index]    Name
       [   10]   .debug_types
       [   11]   .rela.debug_types

    COMDAT group section [    2] `.group' [sig.0x0000000000000002] contains 2 sections:
       [Index]    Name
       [   12]   .debug_types
       [   13]   .rela.debug_types

In both cases, in the fully linked files, there is a single .debug_types section
containing the two type units, as expected.

Before this patch, when I run gdb.dwarf2/fission-with-type-unit.exp, the
resulting .dwo file has a single .debug_info.dwo.  After this patch it
has two: one with the type unit and one with the compile unit (the test
uses DWARF 5).  Based on what I see gcc generate when using "-gdwarf-5
-gsplit-dwarf -fdebug-types-section", this is what we expect.

Change-Id: Ie1954dc697fe100b5dbe664d148c71fa02888d96
Approved-By: Andrew Burgess <aburgess@redhat.com>
gdb/testsuite/lib/dwarf.exp

index a0da797ca3ffcdb5949dcbb1450ecfd75cd3049d..acec46df71cbabd7dafd3e86a7b93740524e0053 100644 (file)
@@ -1078,6 +1078,8 @@ namespace eval Dwarf {
        parse_options {
            { flags "" }
            { type "" }
+           { group_signature "" }
+           { linkage "" }
        }
 
        if { $name == ".debug_str" } {
@@ -1101,6 +1103,14 @@ namespace eval Dwarf {
            append directive ", %$type"
        }
 
+       if { $group_signature != "" } {
+           append directive ", $group_signature"
+       }
+
+       if { $linkage != "" } {
+           append directive ", $linkage"
+       }
+
        _emit "        $directive"
     }
 
@@ -1721,7 +1731,13 @@ namespace eval Dwarf {
            set _abbrev_section "$_abbrev_section.dwo"
        }
 
-       _section $section
+       # The specific format of the signature is arbitrary.
+       _section $section {
+           flags G
+           type progbits
+           group_signature sig.$signature
+           linkage comdat
+       }
 
        set cu_num [incr _cu_count]