Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

[dwarf2yaml] Correctly emit type and split unit headers #102471

Merged
merged 1 commit into from
Aug 12, 2024
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
5 changes: 4 additions & 1 deletion llvm/include/llvm/ObjectYAML/DWARFYAML.h
Original file line number Diff line number Diff line change
Expand Up @@ -115,6 +115,9 @@ struct Unit {
llvm::dwarf::UnitType Type; // Added in DWARF 5
std::optional<uint64_t> AbbrevTableID;
std::optional<yaml::Hex64> AbbrOffset;
yaml::Hex64 TypeSignatureOrDwoID; // For type or split units
yaml::Hex64 TypeOffset; // For type units

std::vector<Entry> Entries;
};

Expand Down Expand Up @@ -245,7 +248,7 @@ struct Data {
std::optional<PubSection> GNUPubNames;
std::optional<PubSection> GNUPubTypes;

std::vector<Unit> CompileUnits;
std::vector<Unit> Units;

std::vector<LineTable> DebugLines;
std::optional<std::vector<ListTable<RnglistEntry>>> DebugRnglists;
Expand Down
37 changes: 34 additions & 3 deletions llvm/lib/ObjectYAML/DWARFEmitter.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -405,17 +405,33 @@ static Expected<uint64_t> writeDIE(const DWARFYAML::Data &DI, uint64_t CUIndex,
}

Error DWARFYAML::emitDebugInfo(raw_ostream &OS, const DWARFYAML::Data &DI) {
for (uint64_t I = 0; I < DI.CompileUnits.size(); ++I) {
const DWARFYAML::Unit &Unit = DI.CompileUnits[I];
for (uint64_t I = 0; I < DI.Units.size(); ++I) {
const DWARFYAML::Unit &Unit = DI.Units[I];
uint8_t AddrSize;
if (Unit.AddrSize)
AddrSize = *Unit.AddrSize;
else
AddrSize = DI.Is64BitAddrSize ? 8 : 4;
dwarf::FormParams Params = {Unit.Version, AddrSize, Unit.Format};
uint64_t Length = 3; // sizeof(version) + sizeof(address_size)
Length += Unit.Version >= 5 ? 1 : 0; // sizeof(unit_type)
Length += Params.getDwarfOffsetByteSize(); // sizeof(debug_abbrev_offset)
if (Unit.Version >= 5) {
++Length; // sizeof(unit_type)
switch (Unit.Type) {
case dwarf::DW_UT_compile:
case dwarf::DW_UT_partial:
default:
break;
case dwarf::DW_UT_type:
case dwarf::DW_UT_split_type:
// sizeof(type_signature) + sizeof(type_offset)
Length += 8 + Params.getDwarfOffsetByteSize();
break;
case dwarf::DW_UT_skeleton:
case dwarf::DW_UT_split_compile:
Length += 8; // sizeof(dwo_id)
}
}

// Since the length of the current compilation unit is undetermined yet, we
// firstly write the content of the compilation unit to a buffer to
Expand Down Expand Up @@ -461,6 +477,21 @@ Error DWARFYAML::emitDebugInfo(raw_ostream &OS, const DWARFYAML::Data &DI) {
writeInteger((uint8_t)Unit.Type, OS, DI.IsLittleEndian);
writeInteger((uint8_t)AddrSize, OS, DI.IsLittleEndian);
writeDWARFOffset(AbbrevTableOffset, Unit.Format, OS, DI.IsLittleEndian);
switch (Unit.Type) {
case dwarf::DW_UT_compile:
case dwarf::DW_UT_partial:
default:
break;
case dwarf::DW_UT_type:
case dwarf::DW_UT_split_type:
writeInteger(Unit.TypeSignatureOrDwoID, OS, DI.IsLittleEndian);
writeDWARFOffset(Unit.TypeOffset, Unit.Format, OS, DI.IsLittleEndian);
break;
case dwarf::DW_UT_skeleton:
case dwarf::DW_UT_split_compile:
writeInteger(Unit.TypeSignatureOrDwoID, OS, DI.IsLittleEndian);
break;
}
} else {
writeDWARFOffset(AbbrevTableOffset, Unit.Format, OS, DI.IsLittleEndian);
writeInteger((uint8_t)AddrSize, OS, DI.IsLittleEndian);
Expand Down
20 changes: 18 additions & 2 deletions llvm/lib/ObjectYAML/DWARFYAML.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -36,7 +36,7 @@ SetVector<StringRef> DWARFYAML::Data::getNonEmptySectionNames() const {
SecNames.insert("debug_addr");
if (!DebugAbbrev.empty())
SecNames.insert("debug_abbrev");
if (!CompileUnits.empty())
if (!Units.empty())
SecNames.insert("debug_info");
if (PubNames)
SecNames.insert("debug_pubnames");
Expand Down Expand Up @@ -101,7 +101,7 @@ void MappingTraits<DWARFYAML::Data>::mapping(IO &IO, DWARFYAML::Data &DWARF) {
DWARFCtx.IsGNUPubSec = true;
IO.mapOptional("debug_gnu_pubnames", DWARF.GNUPubNames);
IO.mapOptional("debug_gnu_pubtypes", DWARF.GNUPubTypes);
IO.mapOptional("debug_info", DWARF.CompileUnits);
IO.mapOptional("debug_info", DWARF.Units);
IO.mapOptional("debug_line", DWARF.DebugLines);
IO.mapOptional("debug_addr", DWARF.DebugAddr);
IO.mapOptional("debug_str_offsets", DWARF.DebugStrOffsets);
Expand Down Expand Up @@ -216,6 +216,22 @@ void MappingTraits<DWARFYAML::Unit>::mapping(IO &IO, DWARFYAML::Unit &Unit) {
IO.mapOptional("AbbrevTableID", Unit.AbbrevTableID);
IO.mapOptional("AbbrOffset", Unit.AbbrOffset);
IO.mapOptional("AddrSize", Unit.AddrSize);
if (Unit.Version >= 5) {
switch (Unit.Type) {
case dwarf::DW_UT_compile:
case dwarf::DW_UT_partial:
default:
break;
case dwarf::DW_UT_type:
case dwarf::DW_UT_split_type:
IO.mapRequired("TypeSignature", Unit.TypeSignatureOrDwoID);
IO.mapRequired("TypeOffset", Unit.TypeOffset);
break;
case dwarf::DW_UT_skeleton:
case dwarf::DW_UT_split_compile:
IO.mapRequired("DwoID", Unit.TypeSignatureOrDwoID);
}
}
IO.mapOptional("Entries", Unit.Entries);
}

Expand Down
92 changes: 71 additions & 21 deletions llvm/test/tools/yaml2obj/ELF/DWARF/debug-info.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -21,7 +21,7 @@
# SHDR-NEXT: AddressAlignment: [[ADDRALIGN]]
# SHDR-NEXT: EntrySize: 0
# DWARF32-LE-CONTENT-NEXT: SectionData (
# DWARF32-LE-CONTENT-NEXT: 0000: 34120000 05000204 34120000 01785634
# DWARF32-LE-CONTENT-NEXT: 0000: 34120000 05000304 34120000 01785634
## ^------- unit_length (4-byte)
## ^--- version (2-byte)
## ^- unit_type (1-byte) DW_UT_type
Expand Down Expand Up @@ -208,7 +208,7 @@ DWARF:
debug_info:
- Length: 0x1234
Version: 5
UnitType: DW_UT_type
UnitType: DW_UT_partial
AbbrOffset: 0x1234
AddrSize: 4
Entries:
Expand Down Expand Up @@ -297,7 +297,7 @@ DWARF:
# RUN: FileCheck -DINDEX=2 -DNAME=15 -DOFFSET=0x9B -DSIZE=179 -DADDRALIGN=1 %s --check-prefixes=SHDR,DWARF32-BE-CONTENT

# DWARF32-BE-CONTENT-NEXT: SectionData (
# DWARF32-BE-CONTENT-NEXT: 0000: 00001234 00050204 00001234 01123456
# DWARF32-BE-CONTENT-NEXT: 0000: 00001234 00050304 00001234 01123456
## ^------- unit_length (4-byte)
## ^--- version (2-byte)
## ^- unit_type (1-byte) DW_UT_type
Expand Down Expand Up @@ -449,7 +449,7 @@ DWARF:
debug_info:
- Length: 0x1234
Version: 5
UnitType: DW_UT_type
UnitType: DW_UT_compile
AbbrOffset: 0x1234
Entries: []

Expand All @@ -476,7 +476,7 @@ DWARF:
debug_info:
- Length: 0x1234
Version: 5
UnitType: DW_UT_type
UnitType: DW_UT_compile
AbbrOffset: 0x1234
Entries: []

Expand Down Expand Up @@ -541,7 +541,7 @@ DWARF:
debug_info:
- Length: 0x1234
Version: 5
UnitType: DW_UT_type
UnitType: DW_UT_compile
AbbrOffset: 0x1234
Entries:
- AbbrCode: 0
Expand All @@ -554,7 +554,7 @@ DWARF:
# RUN: FileCheck %s --check-prefix=EMPTY-ENTRIES --match-full-lines

# EMPTY-ENTRIES: Hex dump of section '.debug_info':
# EMPTY-ENTRIES-NEXT: 0x00000000 34120000 05000204 34120000 4.......4...
# EMPTY-ENTRIES-NEXT: 0x00000000 34120000 05000104 34120000 4.......4...
# EMPTY-ENTRIES-EMPTY:
## ^- 'Entries' is empty

Expand All @@ -567,7 +567,7 @@ DWARF:
debug_info:
- Length: 0x1234
Version: 5
UnitType: DW_UT_type
UnitType: DW_UT_compile
AbbrOffset: 0x1234
Entries: []

Expand All @@ -579,7 +579,7 @@ DWARF:
# RUN: FileCheck %s --check-prefix=FORM --match-full-lines

# FORM: Hex dump of section '.debug_info':
# FORM-NEXT: 0x00000000 34120000 05000204 34120000 02341221 4.......4....4.!
# FORM-NEXT: 0x00000000 34120000 05000104 34120000 02341221 4.......4....4.!
## ^------- unit_length (4-byte)
## ^- abbreviation code (ULEB128)
## ^--- Form: DW_FORM_data2 (2-byte)
Expand Down Expand Up @@ -617,7 +617,7 @@ DWARF:
debug_info:
- Length: 0x1234
Version: 5
UnitType: DW_UT_type
UnitType: DW_UT_compile
AbbrOffset: 0x1234
Entries:
## Test that yaml2obj emits values when the abbrev code is specified.
Expand Down Expand Up @@ -655,29 +655,58 @@ DWARF:
debug_info:
- Length: 0x1234
Version: 5
UnitType: DW_UT_type
UnitType: DW_UT_compile
AbbrOffset: 0x1234
Entries:
- AbbrCode: 1
Values:
- Value: 0x1234

## j) Test that yaml2obj emits the correct DWARF64 unit headers.

## DWARFv5 unit header.
## j) Test that yaml2obj emits the correct DWARFv5 unit headers.

# RUN: yaml2obj --docnum=11 %s -o %t11.o
# RUN: llvm-readelf --hex-dump=.debug_info %t11.o | \
# RUN: FileCheck %s --check-prefix=DWARFV5-HEADER

# DWARFV5-HEADER: Hex dump of section '.debug_info':
# DWARFV5-HEADER-NEXT: 0x00000000 ffffffff 0c000000 00000000 05000208 ................
# DWARFV5-HEADER-NEXT: 0x00000000 ffffffff 0d000000 00000000 05000108 ................
## ^------------------------- unit_length (12-byte)
## ^--- version (2-byte)
## ^- unit_type (1-byte)
## ^- address_size (1-byte)
# DWARFV5-HEADER-NEXT: 0x00000010 34120000 00000000 4.......
# DWARFV5-HEADER-NEXT: 0x00000010 34120000 00000000 00150000 00050002 4...............
## ^---------------- debug_abbrev_offset (8-byte)
## ^- End of children (1-byte)
## ^-------- unit_length (4-byte)
## ^--- version (2-byte)
## ^- unit_type (1-byte)
# DWARFV5-HEADER-NEXT: 0x00000020 08341200 000df0ad baefbead de180000 .4..............
## ^- address_size (1-byte)
## ^-------- debug_abbrev_offset (4-byte)
## ^----------------- type_signature (8-byte)
## \/ ^----- type_offset (4-byte)
# DWARFV5-HEADER-NEXT: 0x00000030 0000ffff ffff1d00 00000000 00000500 ................
## ^- End of children (1-byte)
## ^-------------------------- unit_length (12-byte)
## ^--- version (2-byte)
# DWARFV5-HEADER-NEXT: 0x00000040 02083412 00000000 00000df0 adbaefbe ..4.............
## ^- unit_type (1-byte)
## ^- address_size (1-byte)
## ^----------------- debug_abbrev_offset (8-byte)
## \/-- ^------------ type_signature (8-byte)
# DWARFV5-HEADER-NEXT: 0x00000050 adde2800 00000000 00000011 00000005 ..(.............
## ^----------------- type_offset (8-byte)
## ^- End of children (1-byte)
## ^-------- unit_length (4-byte)
## \/ ^- version (2-byte)
# DWARFV5-HEADER-NEXT: 0x00000060 00040834 1200000d f0adbaef beadde00 ...4............
## ^- unit_type (1-byte)
## ^- address_size (1-byte)
## ^-------- debug_abbrev_offset (4-byte)
## ^----------------- type_signature (8-byte)
## ^- End of children (1-byte)



--- !ELF
FileHeader:
Expand All @@ -686,12 +715,33 @@ FileHeader:
Type: ET_EXEC
DWARF:
debug_info:
- Format: DWARF64
Version: 5
UnitType: DW_UT_compile
AbbrOffset: 0x1234
Entries:
- AbbrCode: 0
- Version: 5
UnitType: DW_UT_type
AbbrOffset: 0x1234
TypeSignature: 0xdeadbeefbaadf00d
TypeOffset: 24
Entries:
- AbbrCode: 0
- Format: DWARF64
Length: 0x0c
Version: 5
UnitType: DW_UT_type
AbbrOffset: 0x1234
Entries: []
Version: 5
UnitType: DW_UT_type
AbbrOffset: 0x1234
TypeSignature: 0xdeadbeefbaadf00d
TypeOffset: 40
Entries:
- AbbrCode: 0
- Version: 5
UnitType: DW_UT_skeleton
AbbrOffset: 0x1234
DwoID: 0xdeadbeefbaadf00d
Entries:
- AbbrCode: 0

## DWARFv4 unit header.

Expand Down
2 changes: 1 addition & 1 deletion llvm/tools/obj2yaml/dwarf2yaml.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -338,7 +338,7 @@ void dumpDebugInfo(DWARFContext &DCtx, DWARFYAML::Data &Y) {

NewUnit.Entries.push_back(NewEntry);
}
Y.CompileUnits.push_back(NewUnit);
Y.Units.push_back(NewUnit);
}
}

Expand Down
Loading