diff --git a/llvm/include/llvm/DebugInfo/DWARF/DWARFContext.h b/llvm/include/llvm/DebugInfo/DWARF/DWARFContext.h --- a/llvm/include/llvm/DebugInfo/DWARF/DWARFContext.h +++ b/llvm/include/llvm/DebugInfo/DWARF/DWARFContext.h @@ -387,9 +387,12 @@ function_ref getWarningHandler() { return WarningHandler; } + enum class ProcessDebugRelocations { Process, Ignore }; + static std::unique_ptr - create(const object::ObjectFile &Obj, const LoadedObjectInfo *L = nullptr, - std::string DWPName = "", + create(const object::ObjectFile &Obj, + ProcessDebugRelocations RelocAction = ProcessDebugRelocations::Process, + const LoadedObjectInfo *L = nullptr, std::string DWPName = "", std::function RecoverableErrorHandler = WithColor::defaultErrorHandler, std::function WarningHandler = diff --git a/llvm/lib/DebugInfo/DWARF/DWARFContext.cpp b/llvm/lib/DebugInfo/DWARF/DWARFContext.cpp --- a/llvm/lib/DebugInfo/DWARF/DWARFContext.cpp +++ b/llvm/lib/DebugInfo/DWARF/DWARFContext.cpp @@ -1411,7 +1411,8 @@ auto S = std::make_shared(); S->File = std::move(Obj.get()); - S->Context = DWARFContext::create(*S->File.getBinary()); + S->Context = DWARFContext::create(*S->File.getBinary(), + ProcessDebugRelocations::Ignore); *Entry = S; auto *Ctxt = S->Context.get(); return std::shared_ptr(std::move(S), Ctxt); @@ -1652,7 +1653,9 @@ } } DWARFObjInMemory(const object::ObjectFile &Obj, const LoadedObjectInfo *L, - function_ref HandleError, function_ref HandleWarning ) + function_ref HandleError, + function_ref HandleWarning, + DWARFContext::ProcessDebugRelocations RelocAction) : IsLittleEndian(Obj.isLittleEndian()), AddressSize(Obj.getBytesInAddress()), FileName(Obj.getFileName()), Obj(&Obj) { @@ -1735,7 +1738,12 @@ S.Data = Data; } - if (RelocatedSection == Obj.section_end()) + if (RelocatedSection != Obj.section_end() && Name.contains(".dwo")) + HandleWarning( + createError("Unexpected relocations for dwo section " + Name)); + + if (RelocatedSection == Obj.section_end() || + (RelocAction == DWARFContext::ProcessDebugRelocations::Ignore)) continue; StringRef RelSecName; @@ -1772,18 +1780,10 @@ if (RelSecName == "debug_info") Map = &static_cast(InfoSections[*RelocatedSection]) .Relocs; - else if (RelSecName == "debug_info.dwo") - Map = &static_cast( - InfoDWOSections[*RelocatedSection]) - .Relocs; else if (RelSecName == "debug_types") Map = &static_cast(TypesSections[*RelocatedSection]) .Relocs; - else if (RelSecName == "debug_types.dwo") - Map = &static_cast( - TypesDWOSections[*RelocatedSection]) - .Relocs; else continue; } @@ -1966,12 +1966,13 @@ } // namespace std::unique_ptr -DWARFContext::create(const object::ObjectFile &Obj, const LoadedObjectInfo *L, - std::string DWPName, +DWARFContext::create(const object::ObjectFile &Obj, + ProcessDebugRelocations RelocAction, + const LoadedObjectInfo *L, std::string DWPName, std::function RecoverableErrorHandler, std::function WarningHandler) { - auto DObj = - std::make_unique(Obj, L, RecoverableErrorHandler, WarningHandler); + auto DObj = std::make_unique( + Obj, L, RecoverableErrorHandler, WarningHandler, RelocAction); return std::make_unique(std::move(DObj), std::move(DWPName), RecoverableErrorHandler, WarningHandler); diff --git a/llvm/lib/DebugInfo/Symbolize/Symbolize.cpp b/llvm/lib/DebugInfo/Symbolize/Symbolize.cpp --- a/llvm/lib/DebugInfo/Symbolize/Symbolize.cpp +++ b/llvm/lib/DebugInfo/Symbolize/Symbolize.cpp @@ -600,7 +600,9 @@ } } if (!Context) - Context = DWARFContext::create(*Objects.second, nullptr, Opts.DWPName); + Context = DWARFContext::create( + *Objects.second, DWARFContext::ProcessDebugRelocations::Process, + nullptr, Opts.DWPName); return createModuleInfo(Objects.first, std::move(Context), ModuleName); } diff --git a/llvm/test/DebugInfo/X86/dwarfdump-rela-dwo.s b/llvm/test/DebugInfo/X86/dwarfdump-rela-dwo.s new file mode 100644 --- /dev/null +++ b/llvm/test/DebugInfo/X86/dwarfdump-rela-dwo.s @@ -0,0 +1,57 @@ +# Test objective to verify warning is printed if DWO secton has relocations. +# +# RUN: llvm-mc -triple x86_64-unknown-linux %s -filetype=obj -o %t.o +# RUN: llvm-dwarfdump --debug-info %t.o | FileCheck %s +# RUN: llvm-dwarfdump --debug-info %t.o 2> %t.txt +# RUN: cat %t.txt | FileCheck %s --check-prefix=PART2 + + .section .debug_str.dwo,"MSe",@progbits,1 +.dwo_producer: + .asciz "Handmade DWO producer" +.dwo_CU_5: + .asciz "V5_dwo_compile_unit" + + .section .debug_str_offsets.dwo,"e",@progbits + .long Lstr_offsets_end-Lstr_offsets_start # Length of String Offsets Set + Lstr_offsets_start: + .short 5 + .short 0 + .long .dwo_producer-.debug_str.dwo + .long .dwo_CU_5-.debug_str.dwo + Lstr_offsets_end: + +# And a .dwo copy for the .dwo sections. + .section .debug_abbrev.dwo,"e",@progbits + .byte 0x01 # Abbrev code + .byte 0x11 # DW_TAG_compile_unit + .byte 0x00 # DW_CHILDREN_no + .byte 0x25 # DW_AT_producer + .byte 0x0e # DW_FORM_strp + .byte 0x03 # DW_AT_name + .byte 0x25 # DW_FORM_strx1 + .byte 0x00 # EOM(1) + .byte 0x00 # EOM(2) + + .section .debug_info.dwo,"e",@progbits +# CHECK-LABEL: .debug_info.dwo + +# DWARF v5 split CU header. + .long CU_split_5_end-CU_split_5_version # Length of Unit +CU_split_5_version: + .short 5 # DWARF version number + .byte 5 # DWARF Unit Type + .byte 8 # Address Size (in bytes) + .long 0 # Offset Into Abbrev. Section + .quad 0x5a # DWO ID +# The split compile-unit DIE, with DW_AT_producer, DW_AT_name, DW_AT_stmt_list. + .byte 1 + .long .dwo_producer + .byte 1 + .byte 0 # NULL +CU_split_5_end: + +# CHECK: 0x00000000: Compile Unit: length = 0x00000017, format = DWARF32, version = 0x0005, unit_type = DW_UT_split_compile, abbr_offset = 0x0000, addr_size = 0x08, DWO_id = 0x000000000000005a (next unit at 0x0000001b) +# CHECK: 0x00000014: DW_TAG_compile_unit +# CHECK-NEXT: DW_AT_producer ("Handmade DWO producer") +# CHECK-NEXT: DW_AT_name ("V5_dwo_compile_unit") +# PART2: warning: Unexpected relocations for dwo section rela.debug_info.dwo diff --git a/llvm/tools/llvm-dwarfdump/llvm-dwarfdump.cpp b/llvm/tools/llvm-dwarfdump/llvm-dwarfdump.cpp --- a/llvm/tools/llvm-dwarfdump/llvm-dwarfdump.cpp +++ b/llvm/tools/llvm-dwarfdump/llvm-dwarfdump.cpp @@ -536,8 +536,9 @@ }; if (auto *Obj = dyn_cast(BinOrErr->get())) { if (filterArch(*Obj)) { - std::unique_ptr DICtx = - DWARFContext::create(*Obj, nullptr, "", RecoverableErrorHandler); + std::unique_ptr DICtx = DWARFContext::create( + *Obj, DWARFContext::ProcessDebugRelocations::Process, nullptr, "", + RecoverableErrorHandler); if (!HandleObj(*Obj, *DICtx, Filename, OS)) Result = false; } @@ -548,8 +549,9 @@ if (auto MachOOrErr = ObjForArch.getAsObjectFile()) { auto &Obj = **MachOOrErr; if (filterArch(Obj)) { - std::unique_ptr DICtx = - DWARFContext::create(Obj, nullptr, "", RecoverableErrorHandler); + std::unique_ptr DICtx = DWARFContext::create( + Obj, DWARFContext::ProcessDebugRelocations::Process, nullptr, "", + RecoverableErrorHandler); if (!HandleObj(Obj, *DICtx, ObjName, OS)) Result = false; } diff --git a/llvm/tools/llvm-readobj/DwarfCFIEHPrinter.h b/llvm/tools/llvm-readobj/DwarfCFIEHPrinter.h --- a/llvm/tools/llvm-readobj/DwarfCFIEHPrinter.h +++ b/llvm/tools/llvm-readobj/DwarfCFIEHPrinter.h @@ -185,7 +185,8 @@ reportError(DataOrErr.takeError(), ObjF.getFileName()); // Construct DWARFDataExtractor to handle relocations ("PC Begin" fields). - std::unique_ptr DICtx = DWARFContext::create(ObjF, nullptr); + std::unique_ptr DICtx = DWARFContext::create( + ObjF, DWARFContext::ProcessDebugRelocations::Process, nullptr); DWARFDataExtractor DE(DICtx->getDWARFObj(), DICtx->getDWARFObj().getEHFrameSection(), ELFT::TargetEndianness == support::endianness::little, diff --git a/llvm/tools/llvm-rtdyld/llvm-rtdyld.cpp b/llvm/tools/llvm-rtdyld/llvm-rtdyld.cpp --- a/llvm/tools/llvm-rtdyld/llvm-rtdyld.cpp +++ b/llvm/tools/llvm-rtdyld/llvm-rtdyld.cpp @@ -413,8 +413,9 @@ } } - std::unique_ptr Context = - DWARFContext::create(*SymbolObj, LoadedObjInfo.get()); + std::unique_ptr Context = DWARFContext::create( + *SymbolObj, DWARFContext::ProcessDebugRelocations::Process, + LoadedObjInfo.get()); std::vector> SymAddr = object::computeSymbolSizes(*SymbolObj); diff --git a/llvm/unittests/DebugInfo/DWARF/DWARFDebugInfoTest.cpp b/llvm/unittests/DebugInfo/DWARF/DWARFDebugInfoTest.cpp --- a/llvm/unittests/DebugInfo/DWARF/DWARFDebugInfoTest.cpp +++ b/llvm/unittests/DebugInfo/DWARF/DWARFDebugInfoTest.cpp @@ -2519,8 +2519,9 @@ // DWARFContext parses whole file and finds the two errors we expect. int Errors = 0; - std::unique_ptr Ctx1 = - DWARFContext::create(**Obj, nullptr, "", [&](Error E) { + std::unique_ptr Ctx1 = DWARFContext::create( + **Obj, DWARFContext::ProcessDebugRelocations::Process, nullptr, "", + [&](Error E) { ++Errors; consumeError(std::move(E)); });