Skip to content

Commit 3590068

Browse files
committed
[ELF] Pass Ctx & to OutputSections
1 parent 7ab488e commit 3590068

File tree

8 files changed

+47
-45
lines changed

8 files changed

+47
-45
lines changed

lld/ELF/Arch/ARM.cpp

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1469,7 +1469,7 @@ template <typename ELFT> void elf::writeARMCmseImportLib() {
14691469
for (auto &[osec, isec] : osIsPairs) {
14701470
osec->sectionIndex = ++idx;
14711471
osec->recordSection(isec);
1472-
osec->finalizeInputSections();
1472+
osec->finalizeInputSections(ctx);
14731473
osec->shName = shstrtab->addString(osec->name);
14741474
osec->size = isec->getSize();
14751475
isec->finalizeContents();

lld/ELF/Driver.cpp

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -3194,7 +3194,7 @@ template <class ELFT> void LinkerDriver::link(opt::InputArgList &args) {
31943194
// sectionBases.
31953195
for (SectionCommand *cmd : ctx.script->sectionCommands)
31963196
if (auto *osd = dyn_cast<OutputDesc>(cmd))
3197-
osd->osec.finalizeInputSections(ctx.script);
3197+
osd->osec.finalizeInputSections(ctx);
31983198
}
31993199

32003200
// Two input sections with different output sections should not be folded.

lld/ELF/LinkerScript.cpp

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1442,7 +1442,7 @@ void LinkerScript::allocateHeaders(SmallVector<PhdrEntry *, 0> &phdrs) {
14421442
return cmd.hasPhdrs || cmd.hasFilehdr;
14431443
});
14441444
bool paged = !ctx.arg.omagic && !ctx.arg.nmagic;
1445-
uint64_t headerSize = getHeaderSize();
1445+
uint64_t headerSize = getHeaderSize(ctx);
14461446

14471447
uint64_t base = 0;
14481448
// If SECTIONS is present and the linkerscript is not explicit about program
@@ -1491,7 +1491,7 @@ LinkerScript::assignAddresses() {
14911491
dot = ctx.target->getImageBase();
14921492
ctx.out.elfHeader->addr = dot;
14931493
ctx.out.programHeaders->addr = dot + ctx.out.elfHeader->size;
1494-
dot += getHeaderSize();
1494+
dot += getHeaderSize(ctx);
14951495
}
14961496

14971497
OutputSection *changedOsec = nullptr;

lld/ELF/OutputSections.cpp

Lines changed: 30 additions & 28 deletions
Original file line numberDiff line numberDiff line change
@@ -78,7 +78,7 @@ OutputSection::OutputSection(StringRef name, uint32_t type, uint64_t flags)
7878
//
7979
// NOTE: clang since rL252300 emits SHT_X86_64_UNWIND .eh_frame sections. Allow
8080
// them to be merged into SHT_PROGBITS .eh_frame (GNU as .cfi_*).
81-
static bool canMergeToProgbits(unsigned type) {
81+
static bool canMergeToProgbits(Ctx &ctx, unsigned type) {
8282
return type == SHT_NOBITS || type == SHT_PROGBITS || type == SHT_INIT_ARRAY ||
8383
type == SHT_PREINIT_ARRAY || type == SHT_FINI_ARRAY ||
8484
type == SHT_NOTE ||
@@ -105,7 +105,7 @@ void OutputSection::recordSection(InputSectionBase *isec) {
105105
// Update fields (type, flags, alignment, etc) according to the InputSection
106106
// isec. Also check whether the InputSection flags and type are consistent with
107107
// other InputSections.
108-
void OutputSection::commitSection(InputSection *isec) {
108+
void OutputSection::commitSection(Ctx &ctx, InputSection *isec) {
109109
if (LLVM_UNLIKELY(type != isec->type)) {
110110
if (!hasInputSections && !typeIsSet) {
111111
type = isec->type;
@@ -120,8 +120,8 @@ void OutputSection::commitSection(InputSection *isec) {
120120
name = saver().save(".crel" + name);
121121
}
122122
} else {
123-
if (typeIsSet || !canMergeToProgbits(type) ||
124-
!canMergeToProgbits(isec->type)) {
123+
if (typeIsSet || !canMergeToProgbits(ctx, type) ||
124+
!canMergeToProgbits(ctx, isec->type)) {
125125
// The (NOLOAD) changes the section type to SHT_NOBITS, the intention is
126126
// that the contents at that address is provided by some other means.
127127
// Some projects (e.g.
@@ -172,7 +172,7 @@ void OutputSection::commitSection(InputSection *isec) {
172172
entsize = 0;
173173
}
174174

175-
static MergeSyntheticSection *createMergeSynthetic(StringRef name,
175+
static MergeSyntheticSection *createMergeSynthetic(Ctx &ctx, StringRef name,
176176
uint32_t type,
177177
uint64_t flags,
178178
uint32_t addralign) {
@@ -188,7 +188,8 @@ static MergeSyntheticSection *createMergeSynthetic(StringRef name,
188188
// new synthetic sections at the location of the first input section
189189
// that it replaces. It then finalizes each synthetic section in order
190190
// to compute an output offset for each piece of each input section.
191-
void OutputSection::finalizeInputSections(LinkerScript *script) {
191+
void OutputSection::finalizeInputSections(Ctx &ctx) {
192+
auto *script = ctx.script;
192193
std::vector<MergeSyntheticSection *> mergeSections;
193194
for (SectionCommand *cmd : commands) {
194195
auto *isd = dyn_cast<InputSectionDescription>(cmd);
@@ -222,8 +223,8 @@ void OutputSection::finalizeInputSections(LinkerScript *script) {
222223
(sec->addralign == ms->addralign || !(sec->flags & SHF_STRINGS));
223224
});
224225
if (i == mergeSections.end()) {
225-
MergeSyntheticSection *syn =
226-
createMergeSynthetic(s->name, ms->type, ms->flags, ms->addralign);
226+
MergeSyntheticSection *syn = createMergeSynthetic(
227+
ctx, s->name, ms->type, ms->flags, ms->addralign);
227228
mergeSections.push_back(syn);
228229
i = std::prev(mergeSections.end());
229230
syn->entsize = ms->entsize;
@@ -243,7 +244,7 @@ void OutputSection::finalizeInputSections(LinkerScript *script) {
243244

244245
// Some input sections may be removed from the list after ICF.
245246
for (InputSection *s : isd->sections)
246-
commitSection(s);
247+
commitSection(ctx, s);
247248
}
248249
for (auto *ms : mergeSections)
249250
ms->finalizeContents();
@@ -260,7 +261,7 @@ static void sortByOrder(MutableArrayRef<InputSection *> in,
260261
in[i] = v[i].second;
261262
}
262263

263-
uint64_t elf::getHeaderSize() {
264+
uint64_t elf::getHeaderSize(Ctx &ctx) {
264265
if (ctx.arg.oFormatBinary)
265266
return 0;
266267
return ctx.out.elfHeader->size + ctx.out.programHeaders->size;
@@ -273,7 +274,7 @@ void OutputSection::sort(llvm::function_ref<int(InputSectionBase *s)> order) {
273274
sortByOrder(isd->sections, order);
274275
}
275276

276-
static void nopInstrFill(uint8_t *buf, size_t size) {
277+
static void nopInstrFill(Ctx &ctx, uint8_t *buf, size_t size) {
277278
if (size == 0)
278279
return;
279280
unsigned i = 0;
@@ -341,7 +342,7 @@ static SmallVector<uint8_t, 0> deflateShard(ArrayRef<uint8_t> in, int level,
341342
//
342343
// * (if --compress-debug-sections is specified) non-empty .debug_* sections
343344
// * (if --compress-sections is specified) matched sections
344-
template <class ELFT> void OutputSection::maybeCompress() {
345+
template <class ELFT> void OutputSection::maybeCompress(Ctx &ctx) {
345346
using Elf_Chdr = typename ELFT::Chdr;
346347
(void)sizeof(Elf_Chdr);
347348

@@ -507,7 +508,7 @@ void OutputSection::writeTo(uint8_t *buf, parallel::TaskGroup &tg) {
507508

508509
// Write leading padding.
509510
ArrayRef<InputSection *> sections = getInputSections(*this, storage);
510-
std::array<uint8_t, 4> filler = getFiller();
511+
std::array<uint8_t, 4> filler = getFiller(ctx);
511512
bool nonZeroFiller = read32(filler.data()) != 0;
512513
if (nonZeroFiller)
513514
fill(buf, sections.empty() ? size : sections[0]->outSecOff, filler);
@@ -543,7 +544,7 @@ void OutputSection::writeTo(uint8_t *buf, parallel::TaskGroup &tg) {
543544
end = buf + sections[i + 1]->outSecOff;
544545
if (isec->nopFiller) {
545546
assert(ctx.target->nopInstrs);
546-
nopInstrFill(start, end - start);
547+
nopInstrFill(ctx, start, end - start);
547548
} else
548549
fill(start, end - start, filler);
549550
}
@@ -582,7 +583,8 @@ void OutputSection::writeTo(uint8_t *buf, parallel::TaskGroup &tg) {
582583
}
583584
}
584585

585-
static void finalizeShtGroup(OutputSection *os, InputSection *section) {
586+
static void finalizeShtGroup(Ctx &ctx, OutputSection *os,
587+
InputSection *section) {
586588
// sh_link field for SHT_GROUP sections should contain the section index of
587589
// the symbol table.
588590
os->link = ctx.in.symTab->getParent()->sectionIndex;
@@ -668,7 +670,7 @@ static size_t relToCrel(raw_svector_ostream &os, Elf_Crel<ELFT::Is64Bits> &out,
668670

669671
// Compute the content of a non-alloc CREL section due to -r or --emit-relocs.
670672
// Input CREL sections are decoded while REL[A] need to be converted.
671-
template <bool is64> void OutputSection::finalizeNonAllocCrel() {
673+
template <bool is64> void OutputSection::finalizeNonAllocCrel(Ctx &ctx) {
672674
using uint = typename Elf_Crel_Impl<is64>::uint;
673675
raw_svector_ostream os(crelBody);
674676
uint64_t totalCount = 0;
@@ -702,7 +704,7 @@ template <bool is64> void OutputSection::finalizeNonAllocCrel() {
702704
size = getULEB128Size(crelHeader) + crelBody.size();
703705
}
704706

705-
void OutputSection::finalize() {
707+
void OutputSection::finalize(Ctx &ctx) {
706708
InputSection *first = getFirstInputSection(this);
707709

708710
if (flags & SHF_LINK_ORDER) {
@@ -718,7 +720,7 @@ void OutputSection::finalize() {
718720
}
719721

720722
if (type == SHT_GROUP) {
721-
finalizeShtGroup(this, first);
723+
finalizeShtGroup(ctx, this, first);
722724
return;
723725
}
724726

@@ -741,9 +743,9 @@ void OutputSection::finalize() {
741743
// Finalize the content of non-alloc CREL.
742744
if (type == SHT_CREL) {
743745
if (ctx.arg.is64)
744-
finalizeNonAllocCrel<true>();
746+
finalizeNonAllocCrel<true>(ctx);
745747
else
746-
finalizeNonAllocCrel<false>();
748+
finalizeNonAllocCrel<false>(ctx);
747749
}
748750
}
749751

@@ -854,15 +856,15 @@ void OutputSection::sortInitFini() {
854856
sort([](InputSectionBase *s) { return getPriority(s->name); });
855857
}
856858

857-
std::array<uint8_t, 4> OutputSection::getFiller() {
859+
std::array<uint8_t, 4> OutputSection::getFiller(Ctx &ctx) {
858860
if (filler)
859861
return *filler;
860862
if (flags & SHF_EXECINSTR)
861863
return ctx.target->trapInstr;
862864
return {0, 0, 0, 0};
863865
}
864866

865-
void OutputSection::checkDynRelAddends(const uint8_t *bufStart) {
867+
void OutputSection::checkDynRelAddends(Ctx &ctx) {
866868
assert(ctx.arg.writeAddends && ctx.arg.checkDynamicRelocs);
867869
assert(isStaticRelSecType(type));
868870
SmallVector<InputSection *, 0> storage;
@@ -885,8 +887,8 @@ void OutputSection::checkDynRelAddends(const uint8_t *bufStart) {
885887
(rel.inputSec == ctx.in.ppc64LongBranchTarget.get() ||
886888
rel.inputSec == ctx.in.igotPlt.get()))
887889
continue;
888-
const uint8_t *relocTarget =
889-
bufStart + relOsec->offset + rel.inputSec->getOffset(rel.offsetInSec);
890+
const uint8_t *relocTarget = ctx.bufferStart + relOsec->offset +
891+
rel.inputSec->getOffset(rel.offsetInSec);
890892
// For SHT_NOBITS the written addend is always zero.
891893
int64_t writtenAddend =
892894
relOsec->type == SHT_NOBITS
@@ -918,7 +920,7 @@ template void OutputSection::writeTo<ELF64LE>(uint8_t *,
918920
template void OutputSection::writeTo<ELF64BE>(uint8_t *,
919921
llvm::parallel::TaskGroup &);
920922

921-
template void OutputSection::maybeCompress<ELF32LE>();
922-
template void OutputSection::maybeCompress<ELF32BE>();
923-
template void OutputSection::maybeCompress<ELF64LE>();
924-
template void OutputSection::maybeCompress<ELF64BE>();
923+
template void OutputSection::maybeCompress<ELF32LE>(Ctx &);
924+
template void OutputSection::maybeCompress<ELF32BE>(Ctx &);
925+
template void OutputSection::maybeCompress<ELF64LE>(Ctx &);
926+
template void OutputSection::maybeCompress<ELF64BE>(Ctx &);

lld/ELF/OutputSections.h

Lines changed: 8 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -74,8 +74,8 @@ class OutputSection final : public SectionBase {
7474
uint32_t shName = 0;
7575

7676
void recordSection(InputSectionBase *isec);
77-
void commitSection(InputSection *isec);
78-
void finalizeInputSections(LinkerScript *script = nullptr);
77+
void commitSection(Ctx &ctx, InputSection *isec);
78+
void finalizeInputSections(Ctx &ctx);
7979

8080
// The following members are normally only used in linker scripts.
8181
MemoryRegion *memRegion = nullptr;
@@ -111,13 +111,13 @@ class OutputSection final : public SectionBase {
111111
// DATA_RELRO_END.
112112
bool relro = false;
113113

114-
template <bool is64> void finalizeNonAllocCrel();
115-
void finalize();
114+
template <bool is64> void finalizeNonAllocCrel(Ctx &);
115+
void finalize(Ctx &);
116116
template <class ELFT>
117117
void writeTo(uint8_t *buf, llvm::parallel::TaskGroup &tg);
118118
// Check that the addends for dynamic relocations were written correctly.
119-
void checkDynRelAddends(const uint8_t *bufStart);
120-
template <class ELFT> void maybeCompress();
119+
void checkDynRelAddends(Ctx &);
120+
template <class ELFT> void maybeCompress(Ctx &);
121121

122122
void sort(llvm::function_ref<int(InputSectionBase *s)> order);
123123
void sortInitFini();
@@ -130,7 +130,7 @@ class OutputSection final : public SectionBase {
130130
private:
131131
SmallVector<InputSection *, 0> storage;
132132

133-
std::array<uint8_t, 4> getFiller();
133+
std::array<uint8_t, 4> getFiller(Ctx &);
134134
};
135135

136136
struct OutputDesc final : SectionCommand {
@@ -169,7 +169,7 @@ llvm::ArrayRef<InputSection *>
169169
getInputSections(const OutputSection &os,
170170
SmallVector<InputSection *, 0> &storage);
171171

172-
uint64_t getHeaderSize();
172+
uint64_t getHeaderSize(Ctx &);
173173
} // namespace lld::elf
174174

175175
#endif

lld/ELF/Relocations.cpp

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -392,7 +392,7 @@ template <class ELFT> static void addCopyRelSymbol(Ctx &ctx, SharedSymbol &ss) {
392392
osec->commands.push_back(make<InputSectionDescription>(""));
393393
auto *isd = cast<InputSectionDescription>(osec->commands.back());
394394
isd->sections.push_back(sec);
395-
osec->commitSection(sec);
395+
osec->commitSection(ctx, sec);
396396

397397
// Look through the DSO's dynamic symbol table for aliases and create a
398398
// dynamic symbol for each one. This causes the copy relocation to correctly

lld/ELF/ScriptParser.cpp

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1647,7 +1647,7 @@ Expr ScriptParser::readPrimary() {
16471647
return [=] { return cmd->size; };
16481648
}
16491649
if (tok == "SIZEOF_HEADERS")
1650-
return [=] { return elf::getHeaderSize(); };
1650+
return [=, &ctx = ctx] { return elf::getHeaderSize(ctx); };
16511651

16521652
// Tok is the dot.
16531653
if (tok == ".")

lld/ELF/Writer.cpp

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -315,7 +315,7 @@ template <class ELFT> void Writer<ELFT>::run() {
315315
// If --compressed-debug-sections is specified, compress .debug_* sections.
316316
// Do it right now because it changes the size of output sections.
317317
for (OutputSection *sec : ctx.outputSections)
318-
sec->maybeCompress<ELFT>();
318+
sec->maybeCompress<ELFT>(ctx);
319319

320320
if (ctx.script->hasSectionsCommand)
321321
ctx.script->allocateHeaders(ctx.mainPart->phdrs);
@@ -2077,7 +2077,7 @@ template <class ELFT> void Writer<ELFT>::finalizeSections() {
20772077
// at the end because some tags like RELSZ depend on result
20782078
// of finalizing other sections.
20792079
for (OutputSection *sec : ctx.outputSections)
2080-
sec->finalize();
2080+
sec->finalize(ctx);
20812081

20822082
ctx.script->checkFinalScriptConditions();
20832083

@@ -2870,7 +2870,7 @@ template <class ELFT> void Writer<ELFT>::writeSections() {
28702870
if (ctx.arg.checkDynamicRelocs && ctx.arg.writeAddends) {
28712871
for (OutputSection *sec : ctx.outputSections)
28722872
if (isStaticRelSecType(sec->type))
2873-
sec->checkDynRelAddends(ctx.bufferStart);
2873+
sec->checkDynRelAddends(ctx);
28742874
}
28752875
}
28762876

0 commit comments

Comments
 (0)