diff --git a/lld/ELF/Arch/PPC.cpp b/lld/ELF/Arch/PPC.cpp index 9a32e8cad4e3..67bc264b8322 100644 --- a/lld/ELF/Arch/PPC.cpp +++ b/lld/ELF/Arch/PPC.cpp @@ -29,7 +29,6 @@ public: PPC::PPC() { NoneRel = R_PPC_NONE; - GotBaseSymOff = 0x8000; GotBaseSymInGotPlt = false; } diff --git a/lld/ELF/Arch/PPC64.cpp b/lld/ELF/Arch/PPC64.cpp index 4f5aa45aac6c..cf1d3dd478f9 100644 --- a/lld/ELF/Arch/PPC64.cpp +++ b/lld/ELF/Arch/PPC64.cpp @@ -208,7 +208,6 @@ PPC64::PPC64() { PltEntrySize = 4; GotPltEntrySize = 8; GotBaseSymInGotPlt = false; - GotBaseSymOff = 0x8000; GotHeaderEntriesNum = 1; GotPltHeaderEntriesNum = 2; PltHeaderSize = 60; diff --git a/lld/ELF/Driver.cpp b/lld/ELF/Driver.cpp index fc2df90f3674..a380f695661d 100644 --- a/lld/ELF/Driver.cpp +++ b/lld/ELF/Driver.cpp @@ -1454,11 +1454,6 @@ static const char *LibcallRoutineNames[] = { // Do actual linking. Note that when this function is called, // all linker scripts have already been parsed. template void LinkerDriver::link(opt::InputArgList &Args) { - Target = getTarget(); - - Config->MaxPageSize = getMaxPageSize(Args); - Config->ImageBase = getImageBase(Args); - // If a -hash-style option was not given, set to a default value, // which varies depending on the target. if (!Args.hasArg(OPT_hash_style)) { @@ -1616,12 +1611,21 @@ template void LinkerDriver::link(opt::InputArgList &Args) { // We do not want to emit debug sections if --strip-all // or -strip-debug are given. - if (Config->Strip != StripPolicy::None) + if (Config->Strip != StripPolicy::None) { llvm::erase_if(InputSections, [](InputSectionBase *S) { return S->Name.startswith(".debug") || S->Name.startswith(".zdebug"); }); + } + + // The Target instance handles target-specific stuff, such as applying + // relocations or writing a PLT section. It also contains target-dependent + // values such as a default image base address. + Target = getTarget(); Config->EFlags = Target->calcEFlags(); + Config->EFlags = Target->calcEFlags(); + Config->MaxPageSize = getMaxPageSize(Args); + Config->ImageBase = getImageBase(Args); if (Config->EMachine == EM_ARM) { // FIXME: These warnings can be removed when lld only uses these features diff --git a/lld/ELF/Target.h b/lld/ELF/Target.h index 1ac38b4d2841..22d95e0d1721 100644 --- a/lld/ELF/Target.h +++ b/lld/ELF/Target.h @@ -86,8 +86,6 @@ public: uint64_t getImageBase() const; - // Offset of _GLOBAL_OFFSET_TABLE_ from base of .got or .got.plt section. - uint64_t GotBaseSymOff = 0; // True if _GLOBAL_OFFSET_TABLE_ is relative to .got.plt, false if .got. bool GotBaseSymInGotPlt = true; diff --git a/lld/ELF/Writer.cpp b/lld/ELF/Writer.cpp index 5d899c016fbd..2d9019df0fe6 100644 --- a/lld/ELF/Writer.cpp +++ b/lld/ELF/Writer.cpp @@ -214,17 +214,24 @@ void elf::addReservedSymbols() { // the .got section. // We do not allow _GLOBAL_OFFSET_TABLE_ to be defined by input objects as the // correctness of some relocations depends on its value. - StringRef GotTableSymName = + StringRef GotSymName = (Config->EMachine == EM_PPC64) ? ".TOC." : "_GLOBAL_OFFSET_TABLE_"; - if (Symbol *S = Symtab->find(GotTableSymName)) { - if (S->isDefined()) + + if (Symbol *S = Symtab->find(GotSymName)) { + if (S->isDefined()) { error(toString(S->File) + " cannot redefine linker defined symbol '" + - GotTableSymName + "'"); - else - ElfSym::GlobalOffsetTable = Symtab->addDefined( - GotTableSymName, STV_HIDDEN, STT_NOTYPE, Target->GotBaseSymOff, - /*Size=*/0, STB_GLOBAL, Out::ElfHeader, - /*File=*/nullptr); + GotSymName + "'"); + return; + } + + uint64_t GotOff = 0; + if (Config->EMachine == EM_PPC || Config->EMachine == EM_PPC64) + GotOff = 0x8000; + + ElfSym::GlobalOffsetTable = + Symtab->addDefined(GotSymName, STV_HIDDEN, STT_NOTYPE, GotOff, + /*Size=*/0, STB_GLOBAL, Out::ElfHeader, + /*File=*/nullptr); } // __ehdr_start is the location of ELF file headers. Note that we define