From 9be5804a892d7027bd46045cbe3348fe62dfa1aa Mon Sep 17 00:00:00 2001 From: Frederic Riss Date: Mon, 31 Aug 2015 05:09:32 +0000 Subject: [PATCH] [dsymutil] Do not crash on empty debug_range range. The fix is trivial (The actual patch is 2 lines, but as it changes indentation it looks like more). clang does not produce this kind of (slightly bogus) debug info anymore, thus I had to rely on a hand-crafted assembly test to trigger that case. git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@246410 91177308-0d34-0410-b5e6-96231b3b80d8 --- test/tools/dsymutil/Inputs/empty_range/1.o | Bin 0 -> 636 bytes test/tools/dsymutil/X86/empty_range.s | 57 +++++++++++++++++++++ test/tools/dsymutil/X86/lit.local.cfg | 2 +- tools/dsymutil/DwarfLinker.cpp | 20 ++++---- 4 files changed, 69 insertions(+), 10 deletions(-) create mode 100644 test/tools/dsymutil/Inputs/empty_range/1.o create mode 100644 test/tools/dsymutil/X86/empty_range.s diff --git a/test/tools/dsymutil/Inputs/empty_range/1.o b/test/tools/dsymutil/Inputs/empty_range/1.o new file mode 100644 index 0000000000000000000000000000000000000000..671bf4a0ccdb69b480e51a84ca0dadad159c44fc GIT binary patch literal 636 zcmX^A>+L^w1_nlE1|R{%EI`b_1R@|n5=eD`Bya$8sJH@D4~!2qlL3Um<^k#W_>$C$ z5~yM@Kg2a61i^=~*q{uMc`&_TAr^)Pm>LirAD@z%RGJ>2n3PnMS_a~~ggXYg!Ii+w z;fIQ-A^8a^gdzenFEcMKA0&@%o+wn46qGiF>W%=?(BQ#pUQuFRdTKGIdHPUuIH0sY zif*tViiiqONB|_v%>|c~0J0LG_7?zY9*{H;2Y^)|2$1{mL?J>U7FMW7=hN83jDkS@ tOnMB0jG>@_6$4_3>o^!uT!}D%7sv$aVFTIAk8F8-e3Wroem*eD7yvknD>eWC literal 0 HcmV?d00001 diff --git a/test/tools/dsymutil/X86/empty_range.s b/test/tools/dsymutil/X86/empty_range.s new file mode 100644 index 00000000000..5c8ae6a1826 --- /dev/null +++ b/test/tools/dsymutil/X86/empty_range.s @@ -0,0 +1,57 @@ +# This test verifies that an empty range list in the .debug_ranges section +# doesn't crash llvm-dsymutil. As clang does not produce this kind of debug +# info anymore, we used this hand-crafted assembly file to produce a testcase +# Compile with: +# llvm-mc -triple x86_64-apple-darwin -filetype=obj -o 1.o empty_range.o + +# RUN: llvm-dsymutil -f -y %p/dummy-debug-map.map -oso-prepend-path %p/../Inputs/empty_range -o - | llvm-dwarfdump -debug-dump=info - | FileCheck %s + + .section __TEXT,__text,regular,pure_instructions + .macosx_version_min 10, 11 + .globl __Z3foov + .align 4, 0x90 +__Z3foov: ## @_Z3foov +Lfunc_begin0: + pushq %rbp + movq %rsp, %rbp + popq %rbp + retq +Lfunc_end0: + .section __DWARF,__debug_abbrev,regular,debug +Lsection_abbrev: + .byte 1 ## Abbreviation Code + .byte 17 ## DW_TAG_compile_unit + .byte 1 ## DW_CHILDREN_yes + .byte 0 ## EOM(1) + .byte 0 ## EOM(2) + .byte 2 ## Abbreviation Code + .byte 46 ## DW_TAG_subprogram + .byte 0 ## DW_CHILDREN_no + .byte 17 ## DW_AT_low_pc + .byte 1 ## DW_FORM_addr + .byte 0x55 ## DW_AT_ranges + .byte 6 ## DW_FORM_data4 + .byte 0 ## EOM(1) + .byte 0 ## EOM(2) + .byte 0 ## EOM(3) + .section __DWARF,__debug_info,regular,debug +Lsection_info: + .long 22 ## Length of Unit + .short 2 ## DWARF version number + .long 0 ## Offset Into Abbrev. Section + .byte 8 ## Address Size (in bytes) + .byte 1 ## Abbrev [1] DW_TAG_compile_unit + .byte 2 ## Abbrev [2] DW_TAG_subprogram + .quad Lfunc_begin0 ## DW_AT_low_pc + .long 0 ## DW_AT_ranges (pointing at an empty entry) + .byte 0 ## End Of Children Mark + .section __DWARF,__debug_ranges,regular,debug +Ldebug_range: + .long 0 + .long 0 + +# CHECK: DW_TAG_compile_unit +# CHECK: DW_TAG_subprogram +# CHECK-NEXT: DW_AT_low_pc{{.*}}(0x0000000000010000) +# CHECK-NEXT: DW_AT_ranges{{.*}}(0x00000000) + diff --git a/test/tools/dsymutil/X86/lit.local.cfg b/test/tools/dsymutil/X86/lit.local.cfg index 7b8ecfecc2b..ed9eba0b0d9 100644 --- a/test/tools/dsymutil/X86/lit.local.cfg +++ b/test/tools/dsymutil/X86/lit.local.cfg @@ -1,4 +1,4 @@ if not 'X86' in config.root.targets: config.unsupported = True -config.suffixes = ['.test', '.cpp'] +config.suffixes = ['.test', '.cpp', '.s'] diff --git a/tools/dsymutil/DwarfLinker.cpp b/tools/dsymutil/DwarfLinker.cpp index 6881eab9c35..f3e48f5033e 100644 --- a/tools/dsymutil/DwarfLinker.cpp +++ b/tools/dsymutil/DwarfLinker.cpp @@ -688,7 +688,7 @@ void DwarfStreamer::emitRangesEntries( MS->SwitchSection(MC->getObjectFileInfo()->getDwarfRangesSection()); // Offset each range by the right amount. - int64_t PcOffset = FuncRange.value() + UnitPcOffset; + int64_t PcOffset = Entries.empty() ? 0 : FuncRange.value() + UnitPcOffset; for (const auto &Range : Entries) { if (Range.isBaseAddressSelectionEntry(AddressSize)) { warn("unsupported base address selection operation", @@ -2638,16 +2638,18 @@ void DwarfLinker::patchRangesForUnit(const CompileUnit &Unit, RangeAttribute.set(Streamer->getRangesSectionSize()); RangeList.extract(RangeExtractor, &Offset); const auto &Entries = RangeList.getEntries(); - const DWARFDebugRangeList::RangeListEntry &First = Entries.front(); + if (!Entries.empty()) { + const DWARFDebugRangeList::RangeListEntry &First = Entries.front(); - if (CurrRange == InvalidRange || - First.StartAddress + OrigLowPc < CurrRange.start() || - First.StartAddress + OrigLowPc >= CurrRange.stop()) { - CurrRange = FunctionRanges.find(First.StartAddress + OrigLowPc); if (CurrRange == InvalidRange || - CurrRange.start() > First.StartAddress + OrigLowPc) { - reportWarning("no mapping for range."); - continue; + First.StartAddress + OrigLowPc < CurrRange.start() || + First.StartAddress + OrigLowPc >= CurrRange.stop()) { + CurrRange = FunctionRanges.find(First.StartAddress + OrigLowPc); + if (CurrRange == InvalidRange || + CurrRange.start() > First.StartAddress + OrigLowPc) { + reportWarning("no mapping for range."); + continue; + } } } -- 2.34.1