Index: lib/ReaderWriter/ELF/SectionChunks.h =================================================================== --- lib/ReaderWriter/ELF/SectionChunks.h +++ lib/ReaderWriter/ELF/SectionChunks.h @@ -1436,7 +1436,8 @@ public: EHFrameHeader(const ELFLinkingContext &context, StringRef name, TargetLayout &layout, int32_t order) - : Section(context, name, "EHFrameHeader"), _layout(layout) { + : Section(context, name, "EHFrameHeader"), _ehFrameOffset(0), + _layout(layout) { this->setOrder(order); this->_entSize = 0; this->_type = SHT_PROGBITS; @@ -1453,24 +1454,27 @@ void finalize() override { OutputSection *s = _layout.findOutputSection(".eh_frame"); - _ehFrameAddr = s ? s->virtualAddr() : 0; + OutputSection *h = _layout.findOutputSection(".eh_frame_hdr"); + if (s && h) + _ehFrameOffset = s->virtualAddr() - (h->virtualAddr() + 4); } - virtual void write(ELFWriter *writer, TargetLayout &layout, - llvm::FileOutputBuffer &buffer) override { + void write(ELFWriter *writer, TargetLayout &layout, + llvm::FileOutputBuffer &buffer) override { uint8_t *chunkBuffer = buffer.getBufferStart(); uint8_t *dest = chunkBuffer + this->fileOffset(); int pos = 0; dest[pos++] = 1; // version - dest[pos++] = llvm::dwarf::DW_EH_PE_udata4; // eh_frame_ptr_enc + dest[pos++] = llvm::dwarf::DW_EH_PE_pcrel | + llvm::dwarf::DW_EH_PE_sdata4; // eh_frame_ptr_enc dest[pos++] = llvm::dwarf::DW_EH_PE_omit; // fde_count_enc dest[pos++] = llvm::dwarf::DW_EH_PE_omit; // table_enc - *reinterpret_cast::Elf_Word *>( - dest + pos) = (uint32_t)_ehFrameAddr; + *reinterpret_cast::Elf_Sword *>( + dest + pos) = _ehFrameOffset; } private: - uint64_t _ehFrameAddr; + int32_t _ehFrameOffset; TargetLayout &_layout; }; } // end namespace elf Index: test/elf/eh_frame_hdr.test =================================================================== --- test/elf/eh_frame_hdr.test +++ test/elf/eh_frame_hdr.test @@ -1,7 +1,7 @@ #RUN: yaml2obj -format=elf %s > %t #RUN: lld -flavor gnu -target x86_64-linux %t --noinhibit-exec \ #RUN: -o %t1 -#RUN: llvm-readobj -s %t1 | FileCheck %s +#RUN: llvm-objdump -s %t1 | FileCheck %s !ELF FileHeader: @@ -23,4 +23,8 @@ Type: STT_SECTION Section: .eh_frame -#CHECK: .eh_frame_hdr +# CHECK: Contents of section .eh_frame: +# CHECK-NEXT: 4001e0 00 +# CHECK-NEXT: Contents of section .eh_frame_hdr: +# CHECK-NEXT: 4001e8 011bffff f4ffffff +# ^ 0x4001e0 - 0x4001e8 - 4 = 0xfffffff4