diff options
Diffstat (limited to 'lld/ELF/Relocations.cpp')
| -rw-r--r-- | lld/ELF/Relocations.cpp | 72 |
1 files changed, 36 insertions, 36 deletions
diff --git a/lld/ELF/Relocations.cpp b/lld/ELF/Relocations.cpp index 9c22ce7d6013..5136ba2151a3 100644 --- a/lld/ELF/Relocations.cpp +++ b/lld/ELF/Relocations.cpp @@ -66,10 +66,10 @@ using namespace lld; using namespace lld::elf; static Optional<std::string> getLinkerScriptLocation(const Symbol &sym) { - for (BaseCommand *base : script->sectionCommands) - if (auto *cmd = dyn_cast<SymbolAssignment>(base)) - if (cmd->sym == &sym) - return cmd->location; + for (SectionCommand *cmd : script->sectionCommands) + if (auto *assign = dyn_cast<SymbolAssignment>(cmd)) + if (assign->sym == &sym) + return assign->location; return None; } @@ -366,10 +366,10 @@ template <class ELFT> static void addCopyRelSymbol(SharedSymbol &ss) { // At this point, sectionBases has been migrated to sections. Append sec to // sections. - if (osec->sectionCommands.empty() || - !isa<InputSectionDescription>(osec->sectionCommands.back())) - osec->sectionCommands.push_back(make<InputSectionDescription>("")); - auto *isd = cast<InputSectionDescription>(osec->sectionCommands.back()); + if (osec->commands.empty() || + !isa<InputSectionDescription>(osec->commands.back())) + osec->commands.push_back(make<InputSectionDescription>("")); + auto *isd = cast<InputSectionDescription>(osec->commands.back()); isd->sections.push_back(sec); osec->commitSection(sec); @@ -1358,32 +1358,6 @@ static void scanReloc(InputSectionBase &sec, OffsetGetter &getOffset, RelTy *&i, } } - // Relax relocations. - // - // If we know that a PLT entry will be resolved within the same ELF module, we - // can skip PLT access and directly jump to the destination function. For - // example, if we are linking a main executable, all dynamic symbols that can - // be resolved within the executable will actually be resolved that way at - // runtime, because the main executable is always at the beginning of a search - // list. We can leverage that fact. - if (!sym.isPreemptible && (!sym.isGnuIFunc() || config->zIfuncNoplt)) { - if (expr != R_GOT_PC) { - // The 0x8000 bit of r_addend of R_PPC_PLTREL24 is used to choose call - // stub type. It should be ignored if optimized to R_PC. - if (config->emachine == EM_PPC && expr == R_PPC32_PLTREL) - addend &= ~0x8000; - // R_HEX_GD_PLT_B22_PCREL (call a@GDPLT) is transformed into - // call __tls_get_addr even if the symbol is non-preemptible. - if (!(config->emachine == EM_HEXAGON && - (type == R_HEX_GD_PLT_B22_PCREL || - type == R_HEX_GD_PLT_B22_PCREL_X || - type == R_HEX_GD_PLT_B32_PCREL_X))) - expr = fromPlt(expr); - } else if (!isAbsoluteValue(sym)) { - expr = target->adjustGotPcExpr(type, addend, relocatedAddr); - } - } - // If the relocation does not emit a GOT or GOTPLT entry but its computation // uses their addresses, we need GOT or GOTPLT to be created. // @@ -1411,6 +1385,32 @@ static void scanReloc(InputSectionBase &sec, OffsetGetter &getOffset, RelTy *&i, return; } + // Relax relocations. + // + // If we know that a PLT entry will be resolved within the same ELF module, we + // can skip PLT access and directly jump to the destination function. For + // example, if we are linking a main executable, all dynamic symbols that can + // be resolved within the executable will actually be resolved that way at + // runtime, because the main executable is always at the beginning of a search + // list. We can leverage that fact. + if (!sym.isPreemptible && (!sym.isGnuIFunc() || config->zIfuncNoplt)) { + if (expr != R_GOT_PC) { + // The 0x8000 bit of r_addend of R_PPC_PLTREL24 is used to choose call + // stub type. It should be ignored if optimized to R_PC. + if (config->emachine == EM_PPC && expr == R_PPC32_PLTREL) + addend &= ~0x8000; + // R_HEX_GD_PLT_B22_PCREL (call a@GDPLT) is transformed into + // call __tls_get_addr even if the symbol is non-preemptible. + if (!(config->emachine == EM_HEXAGON && + (type == R_HEX_GD_PLT_B22_PCREL || + type == R_HEX_GD_PLT_B22_PCREL_X || + type == R_HEX_GD_PLT_B32_PCREL_X))) + expr = fromPlt(expr); + } else if (!isAbsoluteValue(sym)) { + expr = target->adjustGotPcExpr(type, addend, relocatedAddr); + } + } + // We were asked not to generate PLT entries for ifuncs. Instead, pass the // direct relocation on through. if (sym.isGnuIFunc() && config->zIfuncNoplt) { @@ -1640,7 +1640,7 @@ static void forEachInputSectionDescription( for (OutputSection *os : outputSections) { if (!(os->flags & SHF_ALLOC) || !(os->flags & SHF_EXECINSTR)) continue; - for (BaseCommand *bc : os->sectionCommands) + for (SectionCommand *bc : os->commands) if (auto *isd = dyn_cast<InputSectionDescription>(bc)) fn(os, isd); } @@ -1817,7 +1817,7 @@ ThunkSection *ThunkCreator::getISThunkSec(InputSection *isec) { // Find InputSectionRange within Target Output Section (TOS) that the // InputSection (IS) that we need to precede is in. OutputSection *tos = isec->getParent(); - for (BaseCommand *bc : tos->sectionCommands) { + for (SectionCommand *bc : tos->commands) { auto *isd = dyn_cast<InputSectionDescription>(bc); if (!isd || isd->sections.empty()) continue; |
