Skip to content

Commit e44893c

Browse files
clayborggithub-actions[bot]
authored andcommitted
Automerge: Fix a spurious error that was emitted for invalid DW_AT_decl_file. (#152608)
The GSYM code was trying to warn if there are no line table entries for a function and if the DW_AT_decl_file attribute had a file index that was invalid. The code was always emitting a error even if a DW_TAG_subprogram DIE had no DW_AT_decl_file. We should only emit an error if there is a DW_AT_decl_file attribute and it's file index isn't valid.
2 parents 6968992 + 93185ea commit e44893c

File tree

2 files changed

+132
-2
lines changed

2 files changed

+132
-2
lines changed

llvm/lib/DebugInfo/GSYM/DwarfTransformer.cpp

Lines changed: 6 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -338,9 +338,13 @@ static void convertFunctionLineTable(OutputAggregator &Out, CUInfo &CUI,
338338
if (FilePath.empty()) {
339339
// If we had a DW_AT_decl_file, but got no file then we need to emit a
340340
// warning.
341+
const uint64_t DwarfFileIdx = dwarf::toUnsigned(
342+
Die.findRecursively(dwarf::DW_AT_decl_file), UINT32_MAX);
343+
// Check if there is no DW_AT_decl_line attribute, and don't report an
344+
// error if it isn't there.
345+
if (DwarfFileIdx == UINT32_MAX)
346+
return;
341347
Out.Report("Invalid file index in DW_AT_decl_file", [&](raw_ostream &OS) {
342-
const uint64_t DwarfFileIdx = dwarf::toUnsigned(
343-
Die.findRecursively(dwarf::DW_AT_decl_file), UINT32_MAX);
344348
OS << "error: function DIE at " << HEX32(Die.getOffset())
345349
<< " has an invalid file index " << DwarfFileIdx
346350
<< " in its DW_AT_decl_file attribute, unable to create a single "

llvm/unittests/DebugInfo/GSYM/GSYMTest.cpp

Lines changed: 126 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -4959,3 +4959,129 @@ TEST(GSYMTest, TestUnableToLocateDWO) {
49594959
std::string warn("warning: Unable to retrieve DWO .debug_info section for");
49604960
EXPECT_TRUE(errors.find(warn) == std::string::npos);
49614961
}
4962+
4963+
TEST(GSYMTest, TestDWARFTransformNoErrorForMissingFileDecl) {
4964+
// Test that if llvm-gsymutil finds a line table for a compile unit and if
4965+
// there are no matching entries for a function in that compile unit, that
4966+
// it doesn't print out a error saying that a DIE has an invalid file index
4967+
// if there is no DW_AT_decl_file attribute.
4968+
//
4969+
// 0x0000000b: DW_TAG_compile_unit
4970+
// DW_AT_name ("main.cpp")
4971+
// DW_AT_language (DW_LANG_C)
4972+
// DW_AT_stmt_list (0x00000000)
4973+
//
4974+
// 0x00000015: DW_TAG_subprogram
4975+
// DW_AT_name ("foo")
4976+
// DW_AT_low_pc (0x0000000000001000)
4977+
// DW_AT_high_pc (0x0000000000001050)
4978+
//
4979+
// 0x0000002a: NULL
4980+
//
4981+
// Line table that has entries, but none that match "foo":
4982+
//
4983+
// Address Line Column File ISA Discriminator OpIndex Flags
4984+
// ------------------ ------ ------ ------ --- ------------- ------- -----
4985+
// 0x0000000000002000 10 0 1 0 0 0 is_stmt
4986+
// 0x0000000000002050 13 0 1 0 0 0 is_stmt
4987+
4988+
StringRef yamldata = R"(
4989+
debug_str:
4990+
- ''
4991+
- main.cpp
4992+
debug_abbrev:
4993+
- ID: 0
4994+
Table:
4995+
- Code: 0x1
4996+
Tag: DW_TAG_compile_unit
4997+
Children: DW_CHILDREN_yes
4998+
Attributes:
4999+
- Attribute: DW_AT_name
5000+
Form: DW_FORM_strp
5001+
- Attribute: DW_AT_language
5002+
Form: DW_FORM_udata
5003+
- Attribute: DW_AT_stmt_list
5004+
Form: DW_FORM_sec_offset
5005+
- Code: 0x2
5006+
Tag: DW_TAG_subprogram
5007+
Children: DW_CHILDREN_no
5008+
Attributes:
5009+
- Attribute: DW_AT_name
5010+
Form: DW_FORM_string
5011+
- Attribute: DW_AT_low_pc
5012+
Form: DW_FORM_addr
5013+
- Attribute: DW_AT_high_pc
5014+
Form: DW_FORM_addr
5015+
debug_info:
5016+
- Length: 0x27
5017+
Version: 4
5018+
AbbrevTableID: 0
5019+
AbbrOffset: 0x0
5020+
AddrSize: 8
5021+
Entries:
5022+
- AbbrCode: 0x1
5023+
Values:
5024+
- Value: 0x1
5025+
- Value: 0x2
5026+
- Value: 0x0
5027+
- AbbrCode: 0x2
5028+
Values:
5029+
- Value: 0xDEADBEEFDEADBEEF
5030+
CStr: foo
5031+
- Value: 0x1000
5032+
- Value: 0x1050
5033+
- AbbrCode: 0x0
5034+
debug_line:
5035+
- Length: 58
5036+
Version: 2
5037+
PrologueLength: 31
5038+
MinInstLength: 1
5039+
DefaultIsStmt: 1
5040+
LineBase: 251
5041+
LineRange: 14
5042+
OpcodeBase: 13
5043+
StandardOpcodeLengths: [ 0, 1, 1, 1, 1, 0, 0, 0, 1, 0, 0, 1 ]
5044+
Files:
5045+
- Name: main.cpp
5046+
DirIdx: 0
5047+
ModTime: 0
5048+
Length: 0
5049+
Opcodes:
5050+
- Opcode: DW_LNS_extended_op
5051+
ExtLen: 9
5052+
SubOpcode: DW_LNE_set_address
5053+
Data: 8192
5054+
- Opcode: DW_LNS_advance_line
5055+
SData: 9
5056+
Data: 0
5057+
- Opcode: DW_LNS_copy
5058+
Data: 0
5059+
- Opcode: DW_LNS_advance_pc
5060+
Data: 80
5061+
- Opcode: DW_LNS_advance_line
5062+
SData: 3
5063+
Data: 0
5064+
- Opcode: DW_LNS_extended_op
5065+
ExtLen: 1
5066+
SubOpcode: DW_LNE_end_sequence
5067+
Data: 0
5068+
)";
5069+
auto ErrOrSections = DWARFYAML::emitDebugSections(yamldata);
5070+
ASSERT_THAT_EXPECTED(ErrOrSections, Succeeded());
5071+
std::unique_ptr<DWARFContext> DwarfContext =
5072+
DWARFContext::create(*ErrOrSections, 8);
5073+
ASSERT_TRUE(DwarfContext.get() != nullptr);
5074+
std::string errors;
5075+
raw_string_ostream OS(errors);
5076+
OutputAggregator OSAgg(&OS);
5077+
GsymCreator GC;
5078+
DwarfTransformer DT(*DwarfContext, GC);
5079+
const uint32_t ThreadCount = 1;
5080+
ASSERT_THAT_ERROR(DT.convert(ThreadCount, OSAgg), Succeeded());
5081+
ASSERT_THAT_ERROR(GC.finalize(OSAgg), Succeeded());
5082+
5083+
// Make sure this warning is not in the binary
5084+
std::string error_str("error: function DIE at 0x00000015 has an invalid file "
5085+
"index 4294967295 in its DW_AT_decl_file attribute");
5086+
EXPECT_TRUE(errors.find(error_str) == std::string::npos);
5087+
}

0 commit comments

Comments
 (0)