diff --git a/lld/lib/ReaderWriter/ELF/SectionChunks.h b/lld/lib/ReaderWriter/ELF/SectionChunks.h index 28a5d8f95f6b..66f8892f346a 100644 --- a/lld/lib/ReaderWriter/ELF/SectionChunks.h +++ b/lld/lib/ReaderWriter/ELF/SectionChunks.h @@ -954,6 +954,16 @@ public: _symbolTable = symbolTable; } + /// \brief Check if any relocation modifies a read-only section. + bool canModifyReadonlySection() const { + for (const auto &rel : _relocs) { + const DefinedAtom *atom = rel.first; + if ((atom->permissions() & DefinedAtom::permRW_) != DefinedAtom::permRW_) + return true; + } + return false; + } + virtual void finalize() { this->_link = _symbolTable ? _symbolTable->ordinal() : 0; if (this->_parent) @@ -1080,6 +1090,11 @@ public: _dt_relasz = addEntry(dyn); dyn.d_tag = isRela ? DT_RELAENT : DT_RELENT; _dt_relaent = addEntry(dyn); + + if (_layout.getDynamicRelocationTable()->canModifyReadonlySection()) { + dyn.d_tag = DT_TEXTREL; + _dt_textrel = addEntry(dyn); + } } if (_layout.hasPLTRelocationTable()) { dyn.d_tag = DT_PLTRELSZ; @@ -1165,6 +1180,7 @@ private: std::size_t _dt_jmprel; std::size_t _dt_fini_array; std::size_t _dt_fini_arraysz; + std::size_t _dt_textrel; TargetLayout &_layout; DynamicSymbolTable *_dynamicSymbolTable; HashSection *_hashTable; diff --git a/lld/test/elf/Mips/dt-textrel.test b/lld/test/elf/Mips/dt-textrel.test new file mode 100644 index 000000000000..13cbea6e1dd3 --- /dev/null +++ b/lld/test/elf/Mips/dt-textrel.test @@ -0,0 +1,47 @@ +# Check that if a dynamic relocation modify a read-only section, +# .dynamic section contains the DT_TEXTREL tag. + +# RUN: yaml2obj -format=elf %S/Inputs/pic-obj.yaml > %t-so-obj +# RUN: lld -flavor gnu -target mipsel -shared -o %t-so %t-so-obj +# RUN: yaml2obj -format=elf %s > %t-obj +# RUN: lld -flavor gnu -target mipsel -e T0 -o %t-exe %t-obj %t-so +# RUN: llvm-readobj -dynamic-table %t-exe | FileCheck %s + +# CHECK: 0x{{[0-9A-F]+}} TEXTREL + +FileHeader: + Class: ELFCLASS32 + Data: ELFDATA2LSB + Type: ET_REL + Machine: EM_MIPS + Flags: [ EF_MIPS_NOREORDER, EF_MIPS_PIC, EF_MIPS_CPIC, + EF_MIPS_ABI_O32, EF_MIPS_ARCH_32 ] +Sections: + - Name: .text + Type: SHT_PROGBITS + Flags: [ SHF_ALLOC, SHF_EXECINSTR ] + AddressAlign: 0x04 + Content: '00000000' + + - Name: .rel.text + Type: SHT_REL + Link: .symtab + Info: .text + AddressAlign: 0x04 + Relocations: + - Offset: 0 + Symbol: T1 + Type: R_MIPS_32 + +Symbols: + Local: + - Name: .text + Type: STT_SECTION + Section: .text + + Global: + - Name: T0 + Type: STT_FUNC + Section: .text + Size: 0x04 + - Name: T1