Skip to content

[lld][WebAssembly] Move linker global state in to context object. NFC #78629

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Merged
merged 1 commit into from
Jan 18, 2024
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
22 changes: 11 additions & 11 deletions lld/wasm/Config.h
Original file line number Diff line number Diff line change
Expand Up @@ -71,6 +71,11 @@ struct Configuration {
uint64_t initialHeap;
uint64_t initialMemory;
uint64_t maxMemory;
// The table offset at which to place function addresses. We reserve zero
// for the null function pointer. This gets set to 1 for executables and 0
// for shared libraries (since they always added to a dynamic offset at
// runtime).
uint64_t tableBase;
uint64_t zStackSize;
unsigned ltoPartitions;
unsigned ltoo;
Expand All @@ -96,24 +101,20 @@ struct Configuration {
std::optional<std::vector<std::string>> features;
std::optional<std::vector<std::string>> extraFeatures;
llvm::SmallVector<uint8_t, 0> buildIdVector;
};

// The following config options do not directly correspond to any
// particular command line options, and should probably be moved to separate
// Ctx struct as in ELF/Config.h
// The only instance of Configuration struct.
extern Configuration *config;

// The Ctx object hold all other (non-configuration) global state.
struct Ctx {
// True if we are creating position-independent code.
bool isPic;

// True if we have an MVP input that uses __indirect_function_table and which
// requires it to be allocated to table number 0.
bool legacyFunctionTable = false;

// The table offset at which to place function addresses. We reserve zero
// for the null function pointer. This gets set to 1 for executables and 0
// for shared libraries (since they always added to a dynamic offset at
// runtime).
uint32_t tableBase = 0;

// Will be set to true if bss data segments should be emitted. In most cases
// this is not necessary.
bool emitBssSegments = false;
Expand All @@ -124,8 +125,7 @@ struct Configuration {
whyExtractRecords;
};

// The only instance of Configuration struct.
extern Configuration *config;
extern Ctx ctx;

} // namespace lld::wasm

Expand Down
28 changes: 14 additions & 14 deletions lld/wasm/Driver.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -45,6 +45,7 @@ using namespace llvm::wasm;

namespace lld::wasm {
Configuration *config;
Ctx ctx;

namespace {

Expand Down Expand Up @@ -308,7 +309,7 @@ static std::optional<std::string> searchLibraryBaseName(StringRef name) {
for (StringRef dir : config->searchPaths) {
// Currently we don't enable dynamic linking at all unless -shared or -pie
// are used, so don't even look for .so files in that case..
if (config->isPic && !config->isStatic)
if (ctx.isPic && !config->isStatic)
if (std::optional<std::string> s = findFile(dir, "lib" + name + ".so"))
return s;
if (std::optional<std::string> s = findFile(dir, "lib" + name + ".a"))
Expand Down Expand Up @@ -571,9 +572,9 @@ static void readConfigs(opt::InputArgList &args) {
// This function initialize such members. See Config.h for the details
// of these values.
static void setConfigs() {
config->isPic = config->pie || config->shared;
ctx.isPic = config->pie || config->shared;

if (config->isPic) {
if (ctx.isPic) {
if (config->exportTable)
error("-shared/-pie is incompatible with --export-table");
config->importTable = true;
Expand Down Expand Up @@ -680,7 +681,7 @@ static void checkOptions(opt::InputArgList &args) {
warn("-Bsymbolic is only meaningful when combined with -shared");
}

if (config->isPic) {
if (ctx.isPic) {
if (config->globalBase)
error("--global-base may not be used with -shared/-pie");
if (config->tableBase)
Expand All @@ -707,7 +708,7 @@ static Symbol *handleUndefined(StringRef name, const char *option) {
if (auto *lazySym = dyn_cast<LazySymbol>(sym)) {
lazySym->extract();
if (!config->whyExtract.empty())
config->whyExtractRecords.emplace_back(option, sym->getFile(), *sym);
ctx.whyExtractRecords.emplace_back(option, sym->getFile(), *sym);
}

return sym;
Expand All @@ -722,8 +723,7 @@ static void handleLibcall(StringRef name) {
MemoryBufferRef mb = lazySym->getMemberBuffer();
if (isBitcode(mb)) {
if (!config->whyExtract.empty())
config->whyExtractRecords.emplace_back("<libcall>", sym->getFile(),
*sym);
ctx.whyExtractRecords.emplace_back("<libcall>", sym->getFile(), *sym);
lazySym->extract();
}
}
Expand All @@ -742,7 +742,7 @@ static void writeWhyExtract() {
}

os << "reference\textracted\tsymbol\n";
for (auto &entry : config->whyExtractRecords) {
for (auto &entry : ctx.whyExtractRecords) {
os << std::get<0>(entry) << '\t' << toString(std::get<1>(entry)) << '\t'
<< toString(std::get<2>(entry)) << '\n';
}
Expand Down Expand Up @@ -811,7 +811,7 @@ static void createSyntheticSymbols() {

bool is64 = config->is64.value_or(false);

if (config->isPic) {
if (ctx.isPic) {
WasmSym::stackPointer =
createUndefinedGlobal("__stack_pointer", config->is64.value_or(false)
? &mutableGlobalTypeI64
Expand Down Expand Up @@ -850,7 +850,7 @@ static void createSyntheticSymbols() {
"__wasm_init_tls"));
}

if (config->isPic ||
if (ctx.isPic ||
config->unresolvedSymbols == UnresolvedPolicy::ImportDynamic) {
// For PIC code, or when dynamically importing addresses, we create
// synthetic functions that apply relocations. These get called from
Expand All @@ -871,7 +871,7 @@ static void createOptionalSymbols() {
if (!config->shared)
WasmSym::dataEnd = symtab->addOptionalDataSymbol("__data_end");

if (!config->isPic) {
if (!ctx.isPic) {
WasmSym::stackLow = symtab->addOptionalDataSymbol("__stack_low");
WasmSym::stackHigh = symtab->addOptionalDataSymbol("__stack_high");
WasmSym::globalBase = symtab->addOptionalDataSymbol("__global_base");
Expand Down Expand Up @@ -967,8 +967,8 @@ static void processStubLibraries() {
depsAdded = true;
lazy->extract();
if (!config->whyExtract.empty())
config->whyExtractRecords.emplace_back(stub_file->getName(),
sym->getFile(), *sym);
ctx.whyExtractRecords.emplace_back(stub_file->getName(),
sym->getFile(), *sym);
}
}
}
Expand Down Expand Up @@ -1305,7 +1305,7 @@ void LinkerDriver::linkerMain(ArrayRef<const char *> argsArr) {
sym->forceExport = true;
}

if (!config->relocatable && !config->isPic) {
if (!config->relocatable && !ctx.isPic) {
// Add synthetic dummies for weak undefined functions. Must happen
// after LTO otherwise functions may not yet have signatures.
symtab->handleWeakUndefines();
Expand Down
6 changes: 3 additions & 3 deletions lld/wasm/InputChunks.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -378,7 +378,7 @@ void InputChunk::generateRelocationCode(raw_ostream &os) const {
uint64_t offset = getVA(rel.Offset) - getInputSectionOffset();

Symbol *sym = file->getSymbol(rel);
if (!config->isPic && sym->isDefined())
if (!ctx.isPic && sym->isDefined())
continue;

LLVM_DEBUG(dbgs() << "gen reloc: type=" << relocTypeToString(rel.Type)
Expand All @@ -390,7 +390,7 @@ void InputChunk::generateRelocationCode(raw_ostream &os) const {
writeSleb128(os, offset, "offset");

// In PIC mode we need to add the __memory_base
if (config->isPic) {
if (ctx.isPic) {
writeU8(os, WASM_OPCODE_GLOBAL_GET, "GLOBAL_GET");
if (isTLS())
writeUleb128(os, WasmSym::tlsBase->getGlobalIndex(), "tls_base");
Expand All @@ -417,7 +417,7 @@ void InputChunk::generateRelocationCode(raw_ostream &os) const {
writeU8(os, opcode_reloc_add, "ADD");
}
} else {
assert(config->isPic);
assert(ctx.isPic);
const GlobalSymbol* baseSymbol = WasmSym::memoryBase;
if (rel.Type == R_WASM_TABLE_INDEX_I32 ||
rel.Type == R_WASM_TABLE_INDEX_I64)
Expand Down
2 changes: 1 addition & 1 deletion lld/wasm/InputFiles.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -351,7 +351,7 @@ void ObjFile::addLegacyIndirectFunctionTableIfNeeded(

// We assume that this compilation unit has unrelocatable references to
// this table.
config->legacyFunctionTable = true;
ctx.legacyFunctionTable = true;
}

static bool shouldMerge(const WasmSection &sec) {
Expand Down
2 changes: 1 addition & 1 deletion lld/wasm/LTO.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -55,7 +55,7 @@ static std::unique_ptr<lto::LTO> createLTO() {

if (config->relocatable)
c.RelocModel = std::nullopt;
else if (config->isPic)
else if (ctx.isPic)
c.RelocModel = Reloc::PIC_;
else
c.RelocModel = Reloc::Static;
Expand Down
2 changes: 1 addition & 1 deletion lld/wasm/MarkLive.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -187,7 +187,7 @@ bool MarkLive::isCallCtorsLive() {

// In Emscripten-style PIC, we call `__wasm_call_ctors` which calls
// `__wasm_apply_data_relocs`.
if (config->isPic)
if (ctx.isPic)
return true;

// If there are any init functions, mark `__wasm_call_ctors` live so that
Expand Down
6 changes: 3 additions & 3 deletions lld/wasm/OutputSections.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -107,7 +107,7 @@ void DataSection::finalizeContents() {
});
#endif

assert((config->sharedMemory || !config->isPic || config->extendedConst ||
assert((config->sharedMemory || !ctx.isPic || config->extendedConst ||
activeCount <= 1) &&
"output segments should have been combined by now");

Expand All @@ -124,7 +124,7 @@ void DataSection::finalizeContents() {
if (segment->initFlags & WASM_DATA_SEGMENT_HAS_MEMINDEX)
writeUleb128(os, 0, "memory index");
if ((segment->initFlags & WASM_DATA_SEGMENT_IS_PASSIVE) == 0) {
if (config->isPic && config->extendedConst) {
if (ctx.isPic && config->extendedConst) {
writeU8(os, WASM_OPCODE_GLOBAL_GET, "global get");
writeUleb128(os, WasmSym::memoryBase->getGlobalIndex(),
"literal (global index)");
Expand All @@ -136,7 +136,7 @@ void DataSection::finalizeContents() {
} else {
WasmInitExpr initExpr;
initExpr.Extended = false;
if (config->isPic) {
if (ctx.isPic) {
assert(segment->startVA == 0);
initExpr.Inst.Opcode = WASM_OPCODE_GLOBAL_GET;
initExpr.Inst.Value.Global = WasmSym::memoryBase->getGlobalIndex();
Expand Down
2 changes: 1 addition & 1 deletion lld/wasm/OutputSegment.h
Original file line number Diff line number Diff line change
Expand Up @@ -27,7 +27,7 @@ class OutputSegment {
// to the output binary. However if the memory is imported, and
// we can't use memory.fill during startup (due to lack of bulk
// memory feature) then we include BSS segments verbatim.
bool requiredInBinary() const { return !isBss || config->emitBssSegments; }
bool requiredInBinary() const { return !isBss || ctx.emitBssSegments; }

bool isTLS() const { return name == ".tdata"; }

Expand Down
4 changes: 2 additions & 2 deletions lld/wasm/Relocations.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -19,7 +19,7 @@ using namespace llvm::wasm;
namespace lld::wasm {

static bool requiresGOTAccess(const Symbol *sym) {
if (!config->isPic &&
if (!ctx.isPic &&
config->unresolvedSymbols != UnresolvedPolicy::ImportDynamic)
return false;
if (sym->isHidden() || sym->isLocal())
Expand Down Expand Up @@ -141,7 +141,7 @@ void scanRelocations(InputChunk *chunk) {
break;
}

if (config->isPic ||
if (ctx.isPic ||
(sym->isUndefined() &&
config->unresolvedSymbols == UnresolvedPolicy::ImportDynamic)) {
switch (reloc.Type) {
Expand Down
5 changes: 2 additions & 3 deletions lld/wasm/SymbolTable.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -535,8 +535,7 @@ Symbol *SymbolTable::addUndefinedFunction(StringRef name,
} else {
lazy->extract();
if (!config->whyExtract.empty())
config->whyExtractRecords.emplace_back(toString(file), s->getFile(),
*s);
ctx.whyExtractRecords.emplace_back(toString(file), s->getFile(), *s);
}
} else {
auto existingFunction = dyn_cast<FunctionSymbol>(s);
Expand Down Expand Up @@ -774,7 +773,7 @@ void SymbolTable::addLazy(ArchiveFile *file, const Archive::Symbol *sym) {
const InputFile *oldFile = s->getFile();
file->addMember(sym);
if (!config->whyExtract.empty())
config->whyExtractRecords.emplace_back(toString(oldFile), s->getFile(), *s);
ctx.whyExtractRecords.emplace_back(toString(oldFile), s->getFile(), *s);
}

bool SymbolTable::addComdat(StringRef name) {
Expand Down
12 changes: 6 additions & 6 deletions lld/wasm/SyntheticSections.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -55,7 +55,7 @@ class SubSection {
} // namespace

bool DylinkSection::isNeeded() const {
return config->isPic ||
return ctx.isPic ||
config->unresolvedSymbols == UnresolvedPolicy::ImportDynamic ||
!symtab->sharedFiles.empty();
}
Expand Down Expand Up @@ -174,7 +174,7 @@ void ImportSection::addGOTEntry(Symbol *sym) {
return;
LLVM_DEBUG(dbgs() << "addGOTEntry: " << toString(*sym) << "\n");
sym->setGOTIndex(numImportedGlobals++);
if (config->isPic) {
if (ctx.isPic) {
// Any symbol that is assigned an normal GOT entry must be exported
// otherwise the dynamic linker won't be able create the entry that contains
// it.
Expand Down Expand Up @@ -319,7 +319,7 @@ void TableSection::addTable(InputTable *table) {
return;
// Some inputs require that the indirect function table be assigned to table
// number 0.
if (config->legacyFunctionTable &&
if (ctx.legacyFunctionTable &&
isa<DefinedTable>(WasmSym::indirectFunctionTable) &&
cast<DefinedTable>(WasmSym::indirectFunctionTable)->table == table) {
if (out.importSec->getNumImportedTables()) {
Expand Down Expand Up @@ -474,7 +474,7 @@ void GlobalSection::writeBody() {
// In the case of dynamic linking, unless we have 'extended-const'
// available, these global must to be mutable since they get updated to
// the correct runtime value during `__wasm_apply_global_relocs`.
if (!config->extendedConst && config->isPic && !sym->isTLS())
if (!config->extendedConst && ctx.isPic && !sym->isTLS())
mutable_ = true;
// With multi-theadeding any TLS globals must be mutable since they get
// set during `__wasm_apply_global_tls_relocs`
Expand All @@ -487,7 +487,7 @@ void GlobalSection::writeBody() {
bool useExtendedConst = false;
uint32_t globalIdx;
int64_t offset;
if (config->extendedConst && config->isPic) {
if (config->extendedConst && ctx.isPic) {
if (auto *d = dyn_cast<DefinedData>(sym)) {
if (!sym->isTLS()) {
globalIdx = WasmSym::memoryBase->getGlobalIndex();
Expand Down Expand Up @@ -582,7 +582,7 @@ void ElemSection::writeBody() {

WasmInitExpr initExpr;
initExpr.Extended = false;
if (config->isPic) {
if (ctx.isPic) {
initExpr.Inst.Opcode = WASM_OPCODE_GLOBAL_GET;
initExpr.Inst.Value.Global =
(config->is64.value_or(false) ? WasmSym::tableBase32
Expand Down
Loading