[Mips] Set default base address for MIPS executables to 0x400000. Assign

the lowest segment address to the MIPS_BASE_ADDRESS dynamic tag.

llvm-svn: 199234
This commit is contained in:
Simon Atanasyan 2014-01-14 18:19:12 +00:00
parent a565c778b3
commit 663aa62863
4 changed files with 88 additions and 1 deletions

View File

@ -34,6 +34,18 @@ bool MipsLinkingContext::isLittleEndian() const {
return Mips32ElELFType::TargetEndianness == llvm::support::little;
}
uint64_t MipsLinkingContext::getBaseAddress() const {
if (_baseAddress == 0 && getOutputELFType() == llvm::ELF::ET_EXEC)
return 0x400000;
return _baseAddress;
}
StringRef MipsLinkingContext::entrySymbolName() const {
if (_outputELFType == elf::ET_EXEC && _entrySymbolName.empty())
return "__start";
return _entrySymbolName;
}
void MipsLinkingContext::addPasses(PassManager &pm) {
auto pass = createMipsRelocationPass(*this);
if (pass)

View File

@ -35,6 +35,8 @@ public:
// ELFLinkingContext
virtual bool isLittleEndian() const;
virtual uint64_t getBaseAddress() const;
virtual StringRef entrySymbolName() const;
virtual void addPasses(PassManager &pm);
};

View File

@ -64,7 +64,7 @@ public:
// The base address of the segment.
dyn.d_un.d_ptr = 0;
dyn.d_tag = DT_MIPS_BASE_ADDRESS;
addEntry(dyn);
_dt_baseaddr = addEntry(dyn);
// Number of local global offset table entries.
dyn.d_un.d_val = 0;
@ -91,6 +91,13 @@ public:
virtual void updateDynamicTable() {
DynamicTable<Mips32ElELFType>::updateDynamicTable();
// Assign the minimum segment address to the DT_MIPS_BASE_ADDRESS tag.
auto baseAddr = std::numeric_limits<uint64_t>::max();
for (auto si : _layout.segments())
if (si->segmentType() != llvm::ELF::PT_NULL)
baseAddr = std::min(baseAddr, si->virtualAddr());
_entries[_dt_baseaddr].d_un.d_val = baseAddr;
auto &got = _layout.getGOTSection();
_entries[_dt_symtabno].d_un.d_val = getSymbolTable()->size();
@ -108,6 +115,7 @@ private:
std::size_t _dt_localgot;
std::size_t _dt_gotsym;
std::size_t _dt_pltgot;
std::size_t _dt_baseaddr;
};
}

View File

@ -0,0 +1,65 @@
# Check executable base address configuration. Base address should be
# equal to 0x400000 and the MIPS_BASE_ADDRESS dynamic tag's value should
# be the same.
# RUN: llvm-mc -triple=mipsel -filetype=obj -o=%t1 %s
# RUN: lld -flavor gnu -target mipsel --noinhibit-exec -o %t2 %t1
# RUN: llvm-readobj -dynamic-table -program-headers %t2 | FileCheck %s
# CHECK: DynamicSection [ (15 entries)
# CHECK: Tag Type Name/Value
# CHECK: 0x00000004 HASH 0x400110
# CHECK: 0x00000005 STRTAB 0x400130
# CHECK: 0x00000006 SYMTAB 0x400120
# CHECK: 0x0000000A STRSZ 1 (bytes)
# CHECK: 0x0000000B SYMENT 16 (bytes)
# CHECK: 0x0000001A FINI_ARRAY 0x0
# CHECK: 0x0000001C FINI_ARRAYSZ 0 (bytes)
# CHECK: 0x70000001 MIPS_RLD_VERSION 1
# CHECK: 0x70000005 MIPS_FLAGS 0x2
# CHECK: 0x70000006 MIPS_BASE_ADDRESS 0x400000
# CHECK: 0x7000000A MIPS_LOCAL_GOTNO 2
# CHECK: 0x70000011 MIPS_SYMTABNO 1
# CHECK: 0x70000013 MIPS_GOTSYM 0x1
# CHECK: 0x00000003 PLTGOT 0x401000
# CHECK: 0x00000000 NULL 0x0
# CHECK: ]
# CHECK: ProgramHeaders [
# CHECK: ProgramHeader {
# CHECK: Type: PT_PHDR (0x6)
# CHECK: Offset: 0x34
# CHECK: VirtualAddress: 0x400034
# CHECK: }
# CHECK: ProgramHeader {
# CHECK: Type: PT_INTERP (0x3)
# CHECK: Offset: 0xF4
# CHECK: VirtualAddress: 0x4000F4
# CHECK: }
# CHECK: ProgramHeader {
# CHECK: Type: PT_LOAD (0x1)
# CHECK: Offset: 0x0
# CHECK: VirtualAddress: 0x400000
# CHECK: }
# CHECK: ProgramHeader {
# CHECK: Type: PT_LOAD (0x1)
# CHECK: Offset: 0x1000
# CHECK: VirtualAddress: 0x401000
# CHECK: }
# CHECK: ProgramHeader {
# CHECK: Type: PT_LOAD (0x1)
# CHECK: Offset: 0x2000
# CHECK: VirtualAddress: 0x402000
# CHECK: }
# CHECK: ProgramHeader {
# CHECK: Type: PT_DYNAMIC (0x2)
# CHECK: Offset: 0x138
# CHECK: VirtualAddress: 0x400138
# CHECK: }
# CHECK: ]
.global main
.ent main
main:
nop
.end main