From 512d666f4033b5b6858f88226699f990cff5b865 Mon Sep 17 00:00:00 2001 From: Fangrui Song Date: Sat, 18 Jul 2020 08:59:05 -0700 Subject: [PATCH] [DebugInfo] Respect relocations when decoding DW_EH_PE_sdata4 & DW_EH_PE_sdata8 and support R_ARM_REL32 The addresses in llvm-dwarfdump --eh-frame output for object files are closer to readelf -wf output now. --- lib/DebugInfo/DWARF/DWARFDataExtractor.cpp | 4 ++-- lib/DebugInfo/DWARF/DWARFDebugFrame.cpp | 6 +++--- lib/Object/RelocationResolver.cpp | 14 ++++++++++++-- test/DebugInfo/AArch64/eh-frame.ll | 3 +-- test/DebugInfo/PowerPC/eh-frame.ll | 5 ++--- test/MC/Mips/eh-frame.s | 3 ++- .../llvm-dwarfdump/X86/debug_frame_offset.test | 2 +- test/tools/llvm-objdump/MachO/eh_frame-arm64.test | 2 +- test/tools/llvm-readobj/ELF/AArch64/dwarf-cfi.s | 5 +++-- test/tools/llvm-readobj/ELF/ARM/dwarf-cfi.s | 5 +++-- 10 files changed, 30 insertions(+), 19 deletions(-) diff --git a/lib/DebugInfo/DWARF/DWARFDataExtractor.cpp b/lib/DebugInfo/DWARF/DWARFDataExtractor.cpp index 886fe1dff97..fa0ceb4bbc0 100644 --- a/lib/DebugInfo/DWARF/DWARFDataExtractor.cpp +++ b/lib/DebugInfo/DWARF/DWARFDataExtractor.cpp @@ -104,10 +104,10 @@ DWARFDataExtractor::getEncodedPointer(uint64_t *Offset, uint8_t Encoding, Result = getSigned(Offset, 2); break; case dwarf::DW_EH_PE_sdata4: - Result = getSigned(Offset, 4); + Result = SignExtend64<32>(getRelocatedValue(4, Offset)); break; case dwarf::DW_EH_PE_sdata8: - Result = getSigned(Offset, 8); + Result = getRelocatedValue(8, Offset); break; default: return None; diff --git a/lib/DebugInfo/DWARF/DWARFDebugFrame.cpp b/lib/DebugInfo/DWARF/DWARFDebugFrame.cpp index 0a1b7559229..ba7449baaf7 100644 --- a/lib/DebugInfo/DWARF/DWARFDebugFrame.cpp +++ b/lib/DebugInfo/DWARF/DWARFDebugFrame.cpp @@ -521,9 +521,9 @@ Error DWARFDebugFrame::parse(DWARFDataExtractor Data) { "parsing FDE data at 0x%" PRIx64 " failed due to missing CIE", StartOffset); - if (auto Val = Data.getEncodedPointer( - &Offset, Cie->getFDEPointerEncoding(), - EHFrameAddress ? EHFrameAddress + Offset : 0)) { + if (auto Val = + Data.getEncodedPointer(&Offset, Cie->getFDEPointerEncoding(), + EHFrameAddress + Offset)) { InitialLocation = *Val; } if (auto Val = Data.getEncodedPointer( diff --git a/lib/Object/RelocationResolver.cpp b/lib/Object/RelocationResolver.cpp index 919799a25c6..83170bbc4e6 100644 --- a/lib/Object/RelocationResolver.cpp +++ b/lib/Object/RelocationResolver.cpp @@ -291,12 +291,22 @@ static uint64_t resolvePPC32(RelocationRef R, uint64_t S, uint64_t A) { } static bool supportsARM(uint64_t Type) { - return Type == ELF::R_ARM_ABS32; + switch (Type) { + case ELF::R_ARM_ABS32: + case ELF::R_ARM_REL32: + return true; + default: + return false; + } } static uint64_t resolveARM(RelocationRef R, uint64_t S, uint64_t A) { - if (R.getType() == ELF::R_ARM_ABS32) + switch (R.getType()) { + case ELF::R_ARM_ABS32: return (S + A) & 0xFFFFFFFF; + case ELF::R_ARM_REL32: + return (S + A - R.getOffset()) & 0xFFFFFFFF; + } llvm_unreachable("Invalid relocation type"); } diff --git a/test/DebugInfo/AArch64/eh-frame.ll b/test/DebugInfo/AArch64/eh-frame.ll index 9651159271e..1becd769d52 100644 --- a/test/DebugInfo/AArch64/eh-frame.ll +++ b/test/DebugInfo/AArch64/eh-frame.ll @@ -7,8 +7,7 @@ ; CHECK-NOT: warning: ; CHECK: FDE cie=00000000 pc=00000000...00000004 -;; TODO Take relocation into consideration -; CHECK: FDE cie=00000000 pc=00000000...00000004 +; CHECK: FDE cie=00000000 pc=00000004...00000008 define void @foo() { entry: diff --git a/test/DebugInfo/PowerPC/eh-frame.ll b/test/DebugInfo/PowerPC/eh-frame.ll index 3a8f7df6b61..36b1c272f94 100644 --- a/test/DebugInfo/PowerPC/eh-frame.ll +++ b/test/DebugInfo/PowerPC/eh-frame.ll @@ -7,8 +7,7 @@ ; PPC-NOT: warning: ; PPC: FDE cie=00000000 pc=00000000...00000004 -;; TODO Take relocation into consideration -; PPC: FDE cie=00000000 pc=00000000...00000004 +; PPC: FDE cie=00000000 pc=00000004...00000008 ; RUN: llc -filetype=obj -mtriple=ppc64 %s -o %t64.o ; RUN: llvm-readobj -r %t64.o | FileCheck %s --check-prefix=PPC64_REL @@ -19,7 +18,7 @@ ; PPC64-NOT: warning: ; PPC64: FDE cie=00000000 pc=00000000...00000010 -; PPC64: FDE cie=00000000 pc=00000000...00000010 +; PPC64: FDE cie=00000000 pc=00000010...00000020 ; RUN: llc -filetype=obj -mtriple=ppc64le -code-model=large %s -o %t64l.o ; RUN: llvm-readobj -r %t64l.o | FileCheck %s --check-prefix=PPC64L_REL diff --git a/test/MC/Mips/eh-frame.s b/test/MC/Mips/eh-frame.s index 5be0d709a89..024b9e6ac48 100644 --- a/test/MC/Mips/eh-frame.s +++ b/test/MC/Mips/eh-frame.s @@ -68,7 +68,8 @@ func: // DWARF32-EMPTY: // DWARF32-NEXT: DW_CFA_def_cfa_register: reg29 // -// DWARF32: 00000014 00000010 00000018 FDE cie=00000000 pc=00000000...00000000 +// DWARF32_ABS: 00000014 00000010 00000018 FDE cie=00000000 pc=00000000...00000000 +// DWARF32_PIC: 00000014 00000010 00000018 FDE cie=00000000 pc=0000001c...0000001c // DWARF32-NEXT: Format: DWARF32 // DWARF32-NEXT: DW_CFA_nop: // DWARF32-NEXT: DW_CFA_nop: diff --git a/test/tools/llvm-dwarfdump/X86/debug_frame_offset.test b/test/tools/llvm-dwarfdump/X86/debug_frame_offset.test index 598f80379c3..27e5dfa622b 100644 --- a/test/tools/llvm-dwarfdump/X86/debug_frame_offset.test +++ b/test/tools/llvm-dwarfdump/X86/debug_frame_offset.test @@ -9,7 +9,7 @@ CHECK-NOT: pc RUN: llvm-dwarfdump %p/../../dsymutil/Inputs/basic1.macho.x86_64.o \ RUN: -eh-frame=0x00000018 | FileCheck %s --check-prefix=EH EH: .eh_frame contents: -EH-NEXT: 00000018 00000024 0000001c FDE cie=00000000 pc=fffffffffffffd00...fffffffffffffd24 +EH-NEXT: 00000018 00000024 0000001c FDE cie=00000000 pc=fffffffffffffd20...fffffffffffffd44 EH-NEXT: Format: DWARF32 EH-NEXT: DW_CFA_advance_loc: 1 EH-NOT: pc diff --git a/test/tools/llvm-objdump/MachO/eh_frame-arm64.test b/test/tools/llvm-objdump/MachO/eh_frame-arm64.test index 1768d019597..31f87a5035e 100644 --- a/test/tools/llvm-objdump/MachO/eh_frame-arm64.test +++ b/test/tools/llvm-objdump/MachO/eh_frame-arm64.test @@ -12,7 +12,7 @@ # CHECK: DW_CFA_def_cfa: reg31 +0 -# CHECK: 00000014 00000020 00000018 FDE cie=00000000 pc=ffffffffffffffe4...00000004 +# CHECK: 00000014 00000020 00000018 FDE cie=00000000 pc=00000000...00000020 # CHECK: DW_CFA_advance_loc: 8 # CHECK: DW_CFA_def_cfa_offset: +16 # CHECK: DW_CFA_offset: reg30 -8 diff --git a/test/tools/llvm-readobj/ELF/AArch64/dwarf-cfi.s b/test/tools/llvm-readobj/ELF/AArch64/dwarf-cfi.s index f1295467876..cefc0017154 100644 --- a/test/tools/llvm-readobj/ELF/AArch64/dwarf-cfi.s +++ b/test/tools/llvm-readobj/ELF/AArch64/dwarf-cfi.s @@ -10,9 +10,10 @@ # CHECK: Program: # CHECK-NEXT: DW_CFA_def_cfa: reg31 +0 +## FIXME Use getEHFrameSection() so that the address is decoded correctly. # CHECK: [0x14] FDE length=16 cie=[0x0] -# CHECK-NEXT: initial_location: 0x0 -# CHECK-NEXT: address_range: 0x4 (end : 0x4) +# CHECK-NEXT: initial_location: 0x1c +# CHECK-NEXT: address_range: 0x4 (end : 0x20) # CHECK: Program: # CHECK-NEXT: DW_CFA_nop: diff --git a/test/tools/llvm-readobj/ELF/ARM/dwarf-cfi.s b/test/tools/llvm-readobj/ELF/ARM/dwarf-cfi.s index 36d71d61c9f..227ac263b4c 100644 --- a/test/tools/llvm-readobj/ELF/ARM/dwarf-cfi.s +++ b/test/tools/llvm-readobj/ELF/ARM/dwarf-cfi.s @@ -10,9 +10,10 @@ # CHECK: Program: # CHECK-NEXT: DW_CFA_def_cfa: reg13 +0 +## FIXME Use getEHFrameSection() so that the address is decoded correctly. # CHECK: [0x14] FDE length=16 cie=[0x0] -# CHECK-NEXT: initial_location: 0x0 -# CHECK-NEXT: address_range: 0x4 (end : 0x4) +# CHECK-NEXT: initial_location: 0x1c +# CHECK-NEXT: address_range: 0x4 (end : 0x20) # CHECK: Program: # CHECK-NEXT: DW_CFA_nop: