From 0bb9b7689c5f9f2351955983753c20877ecc4a6f Mon Sep 17 00:00:00 2001 From: Jacek Caban Date: Mon, 9 Dec 2024 20:12:20 +0100 Subject: [PATCH] [LLD][COFF] Move addFile implementation to LinkerDriver (NFC) The addFile implementation does not rely on the SymbolTable object. With #119294, the symbol table for input files is determined during the construction of the objects representing them. To clarify that relationship, this change moves the implementation from the SymbolTable class to the LinkerDriver class. --- lld/COFF/Driver.cpp | 82 ++++++++++++++++++++++++++++++++++++---- lld/COFF/Driver.h | 11 ++++-- lld/COFF/InputFiles.cpp | 2 +- lld/COFF/SymbolTable.cpp | 70 +--------------------------------- lld/COFF/SymbolTable.h | 3 -- 5 files changed, 84 insertions(+), 84 deletions(-) diff --git a/lld/COFF/Driver.cpp b/lld/COFF/Driver.cpp index be01ee41c9a2f..83d3f5d4cf99c 100644 --- a/lld/COFF/Driver.cpp +++ b/lld/COFF/Driver.cpp @@ -189,6 +189,71 @@ bool LinkerDriver::findUnderscoreMangle(StringRef sym) { return s && !isa(s); } +static bool compatibleMachineType(COFFLinkerContext &ctx, MachineTypes mt) { + if (mt == IMAGE_FILE_MACHINE_UNKNOWN) + return true; + switch (ctx.config.machine) { + case ARM64: + return mt == ARM64 || mt == ARM64X; + case ARM64EC: + return isArm64EC(mt) || mt == AMD64; + case ARM64X: + return isAnyArm64(mt) || mt == AMD64; + case IMAGE_FILE_MACHINE_UNKNOWN: + return true; + default: + return ctx.config.machine == mt; + } +} + +void LinkerDriver::addFile(InputFile *file) { + Log(ctx) << "Reading " << toString(file); + if (file->lazy) { + if (auto *f = dyn_cast(file)) + f->parseLazy(); + else + cast(file)->parseLazy(); + } else { + file->parse(); + if (auto *f = dyn_cast(file)) { + ctx.objFileInstances.push_back(f); + } else if (auto *f = dyn_cast(file)) { + if (ltoCompilationDone) { + Err(ctx) << "LTO object file " << toString(file) + << " linked in after " + "doing LTO compilation."; + } + ctx.bitcodeFileInstances.push_back(f); + } else if (auto *f = dyn_cast(file)) { + ctx.importFileInstances.push_back(f); + } + } + + MachineTypes mt = file->getMachineType(); + // The ARM64EC target must be explicitly specified and cannot be inferred. + if (mt == ARM64EC && + (ctx.config.machine == IMAGE_FILE_MACHINE_UNKNOWN || + (ctx.config.machineInferred && + (ctx.config.machine == ARM64 || ctx.config.machine == AMD64)))) { + Err(ctx) << toString(file) + << ": machine type arm64ec is ambiguous and cannot be " + "inferred, use /machine:arm64ec or /machine:arm64x"; + return; + } + if (!compatibleMachineType(ctx, mt)) { + Err(ctx) << toString(file) << ": machine type " << machineToStr(mt) + << " conflicts with " << machineToStr(ctx.config.machine); + return; + } + if (ctx.config.machine == IMAGE_FILE_MACHINE_UNKNOWN && + mt != IMAGE_FILE_MACHINE_UNKNOWN) { + ctx.config.machineInferred = true; + setMachine(mt); + } + + parseDirectives(file); +} + MemoryBufferRef LinkerDriver::takeBuffer(std::unique_ptr mb) { MemoryBufferRef mbref = *mb; make>(std::move(mb)); // take ownership @@ -222,17 +287,17 @@ void LinkerDriver::addBuffer(std::unique_ptr mb, addArchiveBuffer(m, "", filename, memberIndex++); return; } - ctx.symtab.addFile(make(ctx, mbref)); + addFile(make(ctx, mbref)); break; case file_magic::bitcode: - ctx.symtab.addFile(make(ctx, mbref, "", 0, lazy)); + addFile(make(ctx, mbref, "", 0, lazy)); break; case file_magic::coff_object: case file_magic::coff_import_library: - ctx.symtab.addFile(ObjFile::create(ctx, mbref, lazy)); + addFile(ObjFile::create(ctx, mbref, lazy)); break; case file_magic::pdb: - ctx.symtab.addFile(make(ctx, mbref)); + addFile(make(ctx, mbref)); break; case file_magic::coff_cl_gl_object: Err(ctx) << filename @@ -240,7 +305,7 @@ void LinkerDriver::addBuffer(std::unique_ptr mb, break; case file_magic::pecoff_executable: if (ctx.config.mingw) { - ctx.symtab.addFile(make(ctx.symtab, mbref)); + addFile(make(ctx.symtab, mbref)); break; } if (filename.ends_with_insensitive(".dll")) { @@ -306,7 +371,7 @@ void LinkerDriver::addArchiveBuffer(MemoryBufferRef mb, StringRef symName, if (magic == file_magic::coff_import_library) { InputFile *imp = make(ctx, mb); imp->parentName = parentName; - ctx.symtab.addFile(imp); + addFile(imp); return; } @@ -326,7 +391,7 @@ void LinkerDriver::addArchiveBuffer(MemoryBufferRef mb, StringRef symName, } obj->parentName = parentName; - ctx.symtab.addFile(obj); + addFile(obj); Log(ctx) << "Loaded " << obj << " for " << symName; } @@ -1400,7 +1465,7 @@ void LinkerDriver::convertResources() { } ObjFile *f = ObjFile::create(ctx, convertResToCOFF(resources, resourceObjFiles)); - ctx.symtab.addFile(f); + addFile(f); f->includeResourceChunks(); } @@ -2702,6 +2767,7 @@ void LinkerDriver::linkerMain(ArrayRef argsArr) { // Do LTO by compiling bitcode input files to a set of native COFF files then // link those files (unless -thinlto-index-only was given, in which case we // resolve symbols and write indices, but don't generate native code or link). + ltoCompilationDone = true; ctx.symtab.compileBitcodeFiles(); if (Defined *d = diff --git a/lld/COFF/Driver.h b/lld/COFF/Driver.h index c2b92f61dcf4b..b04a00e2d1cd1 100644 --- a/lld/COFF/Driver.h +++ b/lld/COFF/Driver.h @@ -80,13 +80,10 @@ class LinkerDriver { void linkerMain(llvm::ArrayRef args); - void setMachine(llvm::COFF::MachineTypes machine); + void addFile(InputFile *file); void addClangLibSearchPaths(const std::string &argv0); - // Used by the resolver to parse .drectve section contents. - void parseDirectives(InputFile *file); - // Used by ArchiveFile to enqueue members. void enqueueArchiveMember(const Archive::Child &c, const Archive::Symbol &sym, StringRef parentName); @@ -121,6 +118,7 @@ class LinkerDriver { // Symbol names are mangled by prepending "_" on x86. StringRef mangle(StringRef sym); + void setMachine(llvm::COFF::MachineTypes machine); llvm::Triple::ArchType getArch(); uint64_t getDefaultImageBase(); @@ -144,6 +142,9 @@ class LinkerDriver { void createImportLibrary(bool asLib); + // Used by the resolver to parse .drectve section contents. + void parseDirectives(InputFile *file); + void parseModuleDefs(StringRef path); // Parse an /order file. If an option is given, the linker places COMDAT @@ -279,6 +280,8 @@ class LinkerDriver { // Create export thunks for exported and patchable Arm64EC function symbols. void createECExportThunks(); void maybeCreateECExportThunk(StringRef name, Symbol *&sym); + + bool ltoCompilationDone = false; }; // Create enum with OPT_xxx values for each option in Options.td diff --git a/lld/COFF/InputFiles.cpp b/lld/COFF/InputFiles.cpp index ad21311e8b28f..e698f66b84f62 100644 --- a/lld/COFF/InputFiles.cpp +++ b/lld/COFF/InputFiles.cpp @@ -1412,5 +1412,5 @@ void DLLFile::makeImport(DLLFile::Symbol *s) { memcpy(p, s->dllName.data(), s->dllName.size()); MemoryBufferRef mbref = MemoryBufferRef(StringRef(buf, size), s->dllName); ImportFile *impFile = make(symtab.ctx, mbref); - symtab.addFile(impFile); + symtab.ctx.driver.addFile(impFile); } diff --git a/lld/COFF/SymbolTable.cpp b/lld/COFF/SymbolTable.cpp index fc78afb4c9e40..6f25ad0620927 100644 --- a/lld/COFF/SymbolTable.cpp +++ b/lld/COFF/SymbolTable.cpp @@ -37,71 +37,6 @@ StringRef ltrim1(StringRef s, const char *chars) { return s; } -static bool compatibleMachineType(COFFLinkerContext &ctx, MachineTypes mt) { - if (mt == IMAGE_FILE_MACHINE_UNKNOWN) - return true; - switch (ctx.config.machine) { - case ARM64: - return mt == ARM64 || mt == ARM64X; - case ARM64EC: - return COFF::isArm64EC(mt) || mt == AMD64; - case ARM64X: - return COFF::isAnyArm64(mt) || mt == AMD64; - case IMAGE_FILE_MACHINE_UNKNOWN: - return true; - default: - return ctx.config.machine == mt; - } -} - -void SymbolTable::addFile(InputFile *file) { - Log(ctx) << "Reading " << toString(file); - if (file->lazy) { - if (auto *f = dyn_cast(file)) - f->parseLazy(); - else - cast(file)->parseLazy(); - } else { - file->parse(); - if (auto *f = dyn_cast(file)) { - ctx.objFileInstances.push_back(f); - } else if (auto *f = dyn_cast(file)) { - if (ltoCompilationDone) { - Err(ctx) << "LTO object file " << toString(file) - << " linked in after " - "doing LTO compilation."; - } - ctx.bitcodeFileInstances.push_back(f); - } else if (auto *f = dyn_cast(file)) { - ctx.importFileInstances.push_back(f); - } - } - - MachineTypes mt = file->getMachineType(); - // The ARM64EC target must be explicitly specified and cannot be inferred. - if (mt == ARM64EC && - (ctx.config.machine == IMAGE_FILE_MACHINE_UNKNOWN || - (ctx.config.machineInferred && - (ctx.config.machine == ARM64 || ctx.config.machine == AMD64)))) { - Err(ctx) << toString(file) - << ": machine type arm64ec is ambiguous and cannot be " - "inferred, use /machine:arm64ec or /machine:arm64x"; - return; - } - if (!compatibleMachineType(ctx, mt)) { - Err(ctx) << toString(file) << ": machine type " << machineToStr(mt) - << " conflicts with " << machineToStr(ctx.config.machine); - return; - } - if (ctx.config.machine == IMAGE_FILE_MACHINE_UNKNOWN && - mt != IMAGE_FILE_MACHINE_UNKNOWN) { - ctx.config.machineInferred = true; - ctx.driver.setMachine(mt); - } - - ctx.driver.parseDirectives(file); -} - static COFFSyncStream errorOrWarn(COFFLinkerContext &ctx) { return {ctx, ctx.config.forceUnresolved ? DiagLevel::Warn : DiagLevel::Err}; } @@ -118,7 +53,7 @@ static void forceLazy(Symbol *s) { case Symbol::Kind::LazyObjectKind: { InputFile *file = cast(s)->file; file->lazy = false; - file->symtab.addFile(file); + file->symtab.ctx.driver.addFile(file); break; } case Symbol::Kind::LazyDLLSymbolKind: { @@ -776,7 +711,7 @@ void SymbolTable::addLazyObject(InputFile *f, StringRef n) { return; s->pendingArchiveLoad = true; f->lazy = false; - addFile(f); + ctx.driver.addFile(f); } void SymbolTable::addLazyDLLSymbol(DLLFile *f, DLLFile::Symbol *sym, @@ -1054,7 +989,6 @@ Symbol *SymbolTable::addUndefined(StringRef name) { } void SymbolTable::compileBitcodeFiles() { - ltoCompilationDone = true; if (ctx.bitcodeFileInstances.empty()) return; diff --git a/lld/COFF/SymbolTable.h b/lld/COFF/SymbolTable.h index 8548a6d036a9d..5443815172dfd 100644 --- a/lld/COFF/SymbolTable.h +++ b/lld/COFF/SymbolTable.h @@ -51,8 +51,6 @@ class SymbolTable { llvm::COFF::MachineTypes machine = IMAGE_FILE_MACHINE_UNKNOWN) : ctx(c), machine(machine) {} - void addFile(InputFile *file); - // Emit errors for symbols that cannot be resolved. void reportUnresolvable(); @@ -155,7 +153,6 @@ class SymbolTable { llvm::DenseMap symMap; std::unique_ptr lto; - bool ltoCompilationDone = false; std::vector> entryThunks; llvm::DenseMap exitThunks; };