brintos

brintos / llvm-project-archived public Read only

0
0
Text · 25.5 KiB · 8ec5a2c Raw
807 lines · c
1//===- Config.h -------------------------------------------------*- C++ -*-===//2//3// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.4// See https://llvm.org/LICENSE.txt for license information.5// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception6//7//===----------------------------------------------------------------------===//8 9#ifndef LLD_ELF_CONFIG_H10#define LLD_ELF_CONFIG_H11 12#include "lld/Common/CommonLinkerContext.h"13#include "lld/Common/ErrorHandler.h"14#include "llvm/ADT/CachedHashString.h"15#include "llvm/ADT/DenseSet.h"16#include "llvm/ADT/MapVector.h"17#include "llvm/ADT/SetVector.h"18#include "llvm/ADT/SmallSet.h"19#include "llvm/ADT/StringRef.h"20#include "llvm/ADT/StringSet.h"21#include "llvm/BinaryFormat/ELF.h"22#include "llvm/Option/ArgList.h"23#include "llvm/Support/CachePruning.h"24#include "llvm/Support/CodeGen.h"25#include "llvm/Support/Compiler.h"26#include "llvm/Support/Compression.h"27#include "llvm/Support/Endian.h"28#include "llvm/Support/FileSystem.h"29#include "llvm/Support/GlobPattern.h"30#include "llvm/Support/TarWriter.h"31#include <atomic>32#include <memory>33#include <mutex>34#include <optional>35#include <vector>36 37namespace lld::elf {38 39class InputFile;40class BinaryFile;41class BitcodeFile;42class ELFFileBase;43class SharedFile;44class InputSectionBase;45class EhInputSection;46class Defined;47class Undefined;48class Symbol;49class SymbolTable;50class BitcodeCompiler;51class OutputSection;52class LinkerScript;53class TargetInfo;54struct Ctx;55struct Partition;56struct PhdrEntry;57 58class BssSection;59class GdbIndexSection;60class GotPltSection;61class GotSection;62class IBTPltSection;63class IgotPltSection;64class InputSection;65class IpltSection;66class MipsGotSection;67class MipsRldMapSection;68class PPC32Got2Section;69class PPC64LongBranchTargetSection;70class PltSection;71class RelocationBaseSection;72class RelroPaddingSection;73class StringTableSection;74class SymbolTableBaseSection;75class SymtabShndxSection;76class SyntheticSection;77 78enum ELFKind : uint8_t {79  ELFNoneKind,80  ELF32LEKind,81  ELF32BEKind,82  ELF64LEKind,83  ELF64BEKind84};85 86// For -Bno-symbolic, -Bsymbolic-non-weak-functions, -Bsymbolic-functions,87// -Bsymbolic-non-weak, -Bsymbolic.88enum class BsymbolicKind { None, NonWeakFunctions, Functions, NonWeak, All };89 90// For --build-id.91enum class BuildIdKind { None, Fast, Md5, Sha1, Hexstring, Uuid };92 93// For --call-graph-profile-sort={none,hfsort,cdsort}.94enum class CGProfileSortKind { None, Hfsort, Cdsort };95 96// For --discard-{all,locals,none}.97enum class DiscardPolicy { Default, All, Locals, None };98 99// For --icf={none,safe,all}.100enum class ICFLevel { None, Safe, All };101 102// For --strip-{all,debug}.103enum class StripPolicy { None, All, Debug };104 105// For --unresolved-symbols.106enum class UnresolvedPolicy { ReportError, Warn, Ignore };107 108// For --orphan-handling.109enum class OrphanHandlingPolicy { Place, Warn, Error };110 111// For --sort-section and linkerscript sorting rules.112enum class SortSectionPolicy {113  Default,114  None,115  Alignment,116  Name,117  Priority,118  Reverse,119};120 121// For --target2122enum class Target2Policy { Abs, Rel, GotRel };123 124// For tracking ARM Float Argument PCS125enum class ARMVFPArgKind { Default, Base, VFP, ToolChain };126 127// For -z noseparate-code, -z separate-code and -z separate-loadable-segments.128enum class SeparateSegmentKind { None, Code, Loadable };129 130// For -z *stack131enum class GnuStackKind { None, Exec, NoExec };132 133// For --lto=134enum LtoKind : uint8_t {UnifiedThin, UnifiedRegular, Default};135 136// For -z gcs=137enum class GcsPolicy { Implicit, Never, Always };138 139// For -z zicfilp=140enum class ZicfilpPolicy { Implicit, Never, Unlabeled, FuncSig };141 142// For -z zicfiss=143enum class ZicfissPolicy { Implicit, Never, Always };144 145// For some options that resemble -z bti-report={none,warning,error}146enum class ReportPolicy { None, Warning, Error };147 148// Describes the signing schema for a file using the PAuth ABI extension.149// Two files are considered compatible when both `platform` and `version` match.150// The pair (0, 0) is reserved to indicate incompatibility with the PAuth ABI.151struct AArch64PauthAbiCoreInfo {152  uint64_t platform;153  uint64_t version;154  // Returns true if the core info is not the reserved (0, 0) value.155  bool isValid() const { return platform || version; }156  static constexpr size_t size() { return sizeof(platform) + sizeof(version); }157  bool operator==(const AArch64PauthAbiCoreInfo &other) const {158    return platform == other.platform && version == other.version;159  }160  bool operator!=(const AArch64PauthAbiCoreInfo &other) const {161    return !(*this == other);162  }163};164 165struct SymbolVersion {166  llvm::StringRef name;167  bool isExternCpp;168  bool hasWildcard;169};170 171// This struct contains symbols version definition that172// can be found in version script if it is used for link.173struct VersionDefinition {174  llvm::StringRef name;175  uint16_t id;176  SmallVector<SymbolVersion, 0> nonLocalPatterns;177  SmallVector<SymbolVersion, 0> localPatterns;178};179 180class LinkerDriver {181public:182  LinkerDriver(Ctx &ctx);183  LinkerDriver(LinkerDriver &) = delete;184  void linkerMain(ArrayRef<const char *> args);185  void addFile(StringRef path, bool withLOption);186  void addLibrary(StringRef name);187 188private:189  Ctx &ctx;190  void createFiles(llvm::opt::InputArgList &args);191  void inferMachineType();192  template <class ELFT> void link(llvm::opt::InputArgList &args);193  template <class ELFT> void compileBitcodeFiles(bool skipLinkedOutput);194  bool tryAddFatLTOFile(MemoryBufferRef mb, StringRef archiveName,195                        uint64_t offsetInArchive, bool lazy);196  // True if we are in --whole-archive and --no-whole-archive.197  bool inWholeArchive = false;198 199  // True if we are in --start-lib and --end-lib.200  bool inLib = false;201 202  std::unique_ptr<BitcodeCompiler> lto;203  SmallVector<std::unique_ptr<InputFile>, 0> files, ltoObjectFiles;204 205public:206  // See InputFile::groupId.207  uint32_t nextGroupId;208  bool isInGroup;209  std::unique_ptr<InputFile> armCmseImpLib;210  SmallVector<std::pair<StringRef, unsigned>, 0> archiveFiles;211};212 213// This struct contains the global configuration for the linker.214// Most fields are direct mapping from the command line options215// and such fields have the same name as the corresponding options.216// Most fields are initialized by the ctx.driver.217struct Config {218  uint8_t osabi = 0;219  uint32_t andFeatures = 0;220  llvm::CachePruningPolicy thinLTOCachePolicy;221  llvm::SetVector<llvm::CachedHashString> dependencyFiles; // for --dependency-file222  llvm::StringMap<uint64_t> sectionStartMap;223  llvm::StringRef bfdname;224  llvm::StringRef chroot;225  llvm::StringRef dependencyFile;226  llvm::StringRef dwoDir;227  llvm::StringRef dynamicLinker;228  llvm::StringRef entry;229  llvm::StringRef emulation;230  llvm::StringRef fini;231  llvm::StringRef init;232  llvm::StringRef ltoAAPipeline;233  llvm::StringRef ltoCSProfileFile;234  llvm::StringRef ltoNewPmPasses;235  llvm::StringRef ltoObjPath;236  llvm::StringRef ltoSampleProfile;237  llvm::StringRef mapFile;238  llvm::StringRef outputFile;239  llvm::StringRef optRemarksFilename;240  std::optional<uint64_t> optRemarksHotnessThreshold = 0;241  llvm::StringRef optRemarksPasses;242  llvm::StringRef optRemarksFormat;243  llvm::StringRef optStatsFilename;244  llvm::StringRef progName;245  llvm::StringRef printArchiveStats;246  llvm::StringRef printSymbolOrder;247  llvm::StringRef soName;248  llvm::StringRef sysroot;249  llvm::StringRef thinLTOCacheDir;250  llvm::StringRef thinLTOIndexOnlyArg;251  llvm::StringRef whyExtract;252  llvm::SmallVector<llvm::GlobPattern, 0> whyLive;253  llvm::StringRef cmseInputLib;254  llvm::StringRef cmseOutputLib;255  ReportPolicy zBtiReport = ReportPolicy::None;256  ReportPolicy zCetReport = ReportPolicy::None;257  ReportPolicy zPauthReport = ReportPolicy::None;258  ReportPolicy zGcsReport = ReportPolicy::None;259  ReportPolicy zGcsReportDynamic = ReportPolicy::None;260  ReportPolicy zExecuteOnlyReport = ReportPolicy::None;261  ReportPolicy zZicfilpUnlabeledReport = ReportPolicy::None;262  ReportPolicy zZicfilpFuncSigReport = ReportPolicy::None;263  ReportPolicy zZicfissReport = ReportPolicy::None;264  bool ltoBBAddrMap;265  llvm::StringRef ltoBasicBlockSections;266  std::pair<llvm::StringRef, llvm::StringRef> thinLTOObjectSuffixReplace;267  llvm::StringRef thinLTOPrefixReplaceOld;268  llvm::StringRef thinLTOPrefixReplaceNew;269  llvm::StringRef thinLTOPrefixReplaceNativeObject;270  std::string rpath;271  llvm::SmallVector<VersionDefinition, 0> versionDefinitions;272  llvm::SmallVector<llvm::StringRef, 0> auxiliaryList;273  llvm::SmallVector<llvm::StringRef, 0> filterList;274  llvm::SmallVector<llvm::StringRef, 0> passPlugins;275  llvm::SmallVector<llvm::StringRef, 0> searchPaths;276  llvm::SmallVector<llvm::StringRef, 0> symbolOrderingFile;277  llvm::SmallVector<llvm::StringRef, 0> thinLTOModulesToCompile;278  llvm::StringRef dtltoDistributor;279  llvm::SmallVector<llvm::StringRef, 0> dtltoDistributorArgs;280  llvm::StringRef dtltoCompiler;281  llvm::SmallVector<llvm::StringRef, 0> dtltoCompilerPrependArgs;282  llvm::SmallVector<llvm::StringRef, 0> dtltoCompilerArgs;283  llvm::SmallVector<llvm::StringRef, 0> undefined;284  llvm::SmallVector<SymbolVersion, 0> dynamicList;285  llvm::SmallVector<uint8_t, 0> buildIdVector;286  llvm::SmallVector<llvm::StringRef, 0> mllvmOpts;287  llvm::MapVector<std::pair<const InputSectionBase *, const InputSectionBase *>,288                  uint64_t>289      callGraphProfile;290  bool cmseImplib = false;291  bool allowMultipleDefinition;292  bool fatLTOObjects;293  bool androidPackDynRelocs = false;294  bool armHasArmISA = false;295  bool armHasThumb2ISA = false;296  bool armHasBlx = false;297  bool armHasMovtMovw = false;298  bool armJ1J2BranchEncoding = false;299  bool armCMSESupport = false;300  bool asNeeded = false;301  bool armBe8 = false;302  BsymbolicKind bsymbolic = BsymbolicKind::None;303  CGProfileSortKind callGraphProfileSort;304  llvm::StringRef irpgoProfilePath;305  bool bpStartupFunctionSort = false;306  bool bpCompressionSortStartupFunctions = false;307  bool bpFunctionOrderForCompression = false;308  bool bpDataOrderForCompression = false;309  bool bpVerboseSectionOrderer = false;310  bool branchToBranch = false;311  bool checkSections;312  bool checkDynamicRelocs;313  std::optional<llvm::DebugCompressionType> compressDebugSections;314  llvm::SmallVector<315      std::tuple<llvm::GlobPattern, llvm::DebugCompressionType, unsigned>, 0>316      compressSections;317  bool cref;318  llvm::SmallVector<std::pair<llvm::GlobPattern, uint64_t>, 0>319      deadRelocInNonAlloc;320  bool debugNames;321  bool demangle = true;322  bool dependentLibraries;323  bool disableVerify;324  bool ehFrameHdr;325  bool emitLLVM;326  bool emitRelocs;327  bool enableNewDtags;328  bool enableNonContiguousRegions;329  bool executeOnly;330  bool exportDynamic;331  bool fixCortexA53Errata843419;332  bool fixCortexA8;333  bool formatBinary = false;334  bool fortranCommon;335  bool gcSections;336  bool gdbIndex;337  bool gnuHash = false;338  bool gnuUnique;339  bool ignoreDataAddressEquality;340  bool ignoreFunctionAddressEquality;341  bool ltoCSProfileGenerate;342  bool ltoPGOWarnMismatch;343  bool ltoDebugPassManager;344  bool ltoEmitAsm;345  bool ltoUniqueBasicBlockSectionNames;346  bool ltoValidateAllVtablesHaveTypeInfos;347  bool ltoWholeProgramVisibility;348  bool mergeArmExidx;349  bool mipsN32Abi = false;350  bool mmapOutputFile;351  bool nmagic;352  bool noinhibitExec;353  bool nostdlib;354  bool oFormatBinary;355  bool omagic;356  bool optEB = false;357  bool optEL = false;358  bool optimizeBBJumps;359  bool optRemarksWithHotness;360  bool picThunk;361  bool pie;362  llvm::StringRef printGcSections;363  bool printIcfSections;364  bool printMemoryUsage;365  std::optional<uint64_t> randomizeSectionPadding;366  bool rejectMismatch;367  bool relax;368  bool relaxGP;369  bool relocatable;370  bool resolveGroups;371  bool relrGlibc = false;372  bool relrPackDynRelocs = false;373  llvm::DenseSet<llvm::StringRef> saveTempsArgs;374  llvm::SmallVector<std::pair<llvm::GlobPattern, uint32_t>, 0> shuffleSections;375  bool singleRoRx;376  bool singleXoRx;377  bool shared;378  bool symbolic;379  bool isStatic = false;380  bool sysvHash = false;381  bool target1Rel;382  bool trace;383  bool thinLTOEmitImportsFiles;384  bool thinLTOEmitIndexFiles;385  bool thinLTOIndexOnly;386  bool timeTraceEnabled;387  bool tocOptimize;388  bool pcRelOptimize;389  bool undefinedVersion;390  bool unique;391  bool useAndroidRelrTags = false;392  bool warnBackrefs;393  llvm::SmallVector<llvm::GlobPattern, 0> warnBackrefsExclude;394  bool warnCommon;395  bool warnMissingEntry;396  bool warnSymbolOrdering;397  bool writeAddends;398  bool zCombreloc;399  bool zCopyreloc;400  bool zDynamicUndefined;401  bool zForceBti;402  bool zForceIbt;403  bool zGlobal;404  bool zHazardplt;405  bool zIfuncNoplt;406  bool zInitfirst;407  bool zInterpose;408  bool zKeepDataSectionPrefix;409  bool zKeepTextSectionPrefix;410  bool zLrodataAfterBss;411  bool zNoBtCfi;412  bool zNodefaultlib;413  bool zNodelete;414  bool zNodlopen;415  bool zNow;416  bool zOrigin;417  bool zPacPlt;418  bool zRelro;419  bool zRodynamic;420  bool zSectionHeader;421  bool zShstk;422  bool zStartStopGC;423  uint8_t zStartStopVisibility;424  bool zText;425  bool zRetpolineplt;426  bool zWxneeded;427  ZicfilpPolicy zZicfilp;428  ZicfissPolicy zZicfiss;429  DiscardPolicy discard;430  GnuStackKind zGnustack;431  ICFLevel icf;432  OrphanHandlingPolicy orphanHandling;433  SortSectionPolicy sortSection;434  StripPolicy strip;435  UnresolvedPolicy unresolvedSymbols;436  UnresolvedPolicy unresolvedSymbolsInShlib;437  Target2Policy target2;438  GcsPolicy zGcs;439  bool power10Stubs;440  ARMVFPArgKind armVFPArgs = ARMVFPArgKind::Default;441  BuildIdKind buildId = BuildIdKind::None;442  SeparateSegmentKind zSeparate;443  ELFKind ekind = ELFNoneKind;444  uint16_t emachine = llvm::ELF::EM_NONE;445  std::optional<uint64_t> imageBase;446  uint64_t commonPageSize;447  uint64_t maxPageSize;448  uint64_t mipsGotSize;449  uint64_t zStackSize;450  unsigned ltoPartitions;451  unsigned ltoo;452  llvm::CodeGenOptLevel ltoCgo;453  unsigned optimize;454  StringRef thinLTOJobs;455  unsigned timeTraceGranularity;456  int32_t splitStackAdjustSize;457  SmallVector<uint8_t, 0> packageMetadata;458 459  // The following config options do not directly correspond to any460  // particular command line options.461 462  // True if we need to pass through relocations in input files to the463  // output file. Usually false because we consume relocations.464  bool copyRelocs;465 466  // True if the target is ELF64. False if ELF32.467  bool is64;468 469  // True if the target is little-endian. False if big-endian.470  bool isLE;471 472  // endianness::little if isLE is true. endianness::big otherwise.473  llvm::endianness endianness;474 475  // True if the target is the little-endian MIPS64.476  //477  // The reason why we have this variable only for the MIPS is because478  // we use this often.  Some ELF headers for MIPS64EL are in a479  // mixed-endian (which is horrible and I'd say that's a serious spec480  // bug), and we need to know whether we are reading MIPS ELF files or481  // not in various places.482  //483  // (Note that MIPS64EL is not a typo for MIPS64LE. This is the official484  // name whatever that means. A fun hypothesis is that "EL" is short for485  // little-endian written in the little-endian order, but I don't know486  // if that's true.)487  bool isMips64EL;488 489  // True if we need to set the DF_STATIC_TLS flag to an output file, which490  // works as a hint to the dynamic loader that the shared object contains code491  // compiled with the initial-exec TLS model.492  bool hasTlsIe = false;493 494  // Holds set of ELF header flags for the target.495  uint32_t eflags = 0;496 497  // The ELF spec defines two types of relocation table entries, RELA and498  // REL. RELA is a triplet of (offset, info, addend) while REL is a499  // tuple of (offset, info). Addends for REL are implicit and read from500  // the location where the relocations are applied. So, REL is more501  // compact than RELA but requires a bit of more work to process.502  //503  // (From the linker writer's view, this distinction is not necessary.504  // If the ELF had chosen whichever and sticked with it, it would have505  // been easier to write code to process relocations, but it's too late506  // to change the spec.)507  //508  // Each ABI defines its relocation type. IsRela is true if target509  // uses RELA. As far as we know, all 64-bit ABIs are using RELA. A510  // few 32-bit ABIs are using RELA too.511  bool isRela;512 513  // True if we are creating position-independent code.514  bool isPic;515 516  // 4 for ELF32, 8 for ELF64.517  int wordsize;518 519  // Mode of MTE to write to the ELF note. Should be one of NT_MEMTAG_ASYNC (for520  // async), NT_MEMTAG_SYNC (for sync), or NT_MEMTAG_LEVEL_NONE (for none). If521  // async or sync is enabled, write the ELF note specifying the default MTE522  // mode.523  int androidMemtagMode;524  // Signal to the dynamic loader to enable heap MTE.525  bool androidMemtagHeap;526  // Signal to the dynamic loader that this binary expects stack MTE. Generally,527  // this means to map the primary and thread stacks as PROT_MTE. Note: This is528  // not supported on Android 11 & 12.529  bool androidMemtagStack;530 531  // When using a unified pre-link LTO pipeline, specify the backend LTO mode.532  LtoKind ltoKind = LtoKind::Default;533 534  unsigned threadCount;535 536  // If an input file equals a key, remap it to the value.537  llvm::DenseMap<llvm::StringRef, llvm::StringRef> remapInputs;538  // If an input file matches a wildcard pattern, remap it to the value.539  llvm::SmallVector<std::pair<llvm::GlobPattern, llvm::StringRef>, 0>540      remapInputsWildcards;541};542 543// Some index properties of a symbol are stored separately in this auxiliary544// struct to decrease sizeof(SymbolUnion) in the majority of cases.545struct SymbolAux {546  uint32_t gotIdx = -1;547  uint32_t pltIdx = -1;548  uint32_t tlsDescIdx = -1;549  uint32_t tlsGdIdx = -1;550};551 552struct DuplicateSymbol {553  const Symbol *sym;554  const InputFile *file;555  InputSectionBase *section;556  uint64_t value;557};558 559struct UndefinedDiag {560  Undefined *sym;561  struct Loc {562    InputSectionBase *sec;563    uint64_t offset;564  };565  SmallVector<Loc, 0> locs;566  bool isWarning;567};568 569// Linker generated sections which can be used as inputs and are not specific to570// a partition.571struct InStruct {572  std::unique_ptr<InputSection> attributes;573  std::unique_ptr<SyntheticSection> hexagonAttributes;574  std::unique_ptr<SyntheticSection> riscvAttributes;575  std::unique_ptr<BssSection> bss;576  std::unique_ptr<BssSection> bssRelRo;577  std::unique_ptr<SyntheticSection> gnuProperty;578  std::unique_ptr<SyntheticSection> gnuStack;579  std::unique_ptr<GotSection> got;580  std::unique_ptr<GotPltSection> gotPlt;581  std::unique_ptr<IgotPltSection> igotPlt;582  std::unique_ptr<RelroPaddingSection> relroPadding;583  std::unique_ptr<SyntheticSection> armCmseSGSection;584  std::unique_ptr<PPC64LongBranchTargetSection> ppc64LongBranchTarget;585  std::unique_ptr<SyntheticSection> mipsAbiFlags;586  std::unique_ptr<MipsGotSection> mipsGot;587  std::unique_ptr<SyntheticSection> mipsOptions;588  std::unique_ptr<SyntheticSection> mipsReginfo;589  std::unique_ptr<MipsRldMapSection> mipsRldMap;590  std::unique_ptr<SyntheticSection> partEnd;591  std::unique_ptr<SyntheticSection> partIndex;592  std::unique_ptr<PltSection> plt;593  std::unique_ptr<IpltSection> iplt;594  std::unique_ptr<PPC32Got2Section> ppc32Got2;595  std::unique_ptr<IBTPltSection> ibtPlt;596  std::unique_ptr<RelocationBaseSection> relaPlt;597  // Non-SHF_ALLOC sections598  std::unique_ptr<SyntheticSection> debugNames;599  std::unique_ptr<GdbIndexSection> gdbIndex;600  std::unique_ptr<StringTableSection> shStrTab;601  std::unique_ptr<StringTableSection> strTab;602  std::unique_ptr<SymbolTableBaseSection> symTab;603  std::unique_ptr<SymtabShndxSection> symTabShndx;604};605 606struct Ctx : CommonLinkerContext {607  Config arg;608  LinkerDriver driver;609  LinkerScript *script;610  std::unique_ptr<TargetInfo> target;611 612  // These variables are initialized by Writer and should not be used before613  // Writer is initialized.614  uint8_t *bufferStart = nullptr;615  Partition *mainPart = nullptr;616  PhdrEntry *tlsPhdr = nullptr;617  struct OutSections {618    std::unique_ptr<OutputSection> elfHeader;619    std::unique_ptr<OutputSection> programHeaders;620    OutputSection *preinitArray = nullptr;621    OutputSection *initArray = nullptr;622    OutputSection *finiArray = nullptr;623  };624  OutSections out;625  SmallVector<OutputSection *, 0> outputSections;626  std::vector<Partition> partitions;627 628  InStruct in;629 630  // Some linker-generated symbols need to be created as631  // Defined symbols.632  struct ElfSym {633    // __bss_start634    Defined *bss;635 636    // etext and _etext637    Defined *etext1;638    Defined *etext2;639 640    // edata and _edata641    Defined *edata1;642    Defined *edata2;643 644    // end and _end645    Defined *end1;646    Defined *end2;647 648    // The _GLOBAL_OFFSET_TABLE_ symbol is defined by target convention to649    // be at some offset from the base of the .got section, usually 0 or650    // the end of the .got.651    Defined *globalOffsetTable;652 653    // _gp, _gp_disp and __gnu_local_gp symbols. Only for MIPS.654    Defined *mipsGp;655    Defined *mipsGpDisp;656    Defined *mipsLocalGp;657 658    // __global_pointer$ for RISC-V.659    Defined *riscvGlobalPointer;660 661    // __rel{,a}_iplt_{start,end} symbols.662    Defined *relaIpltStart;663    Defined *relaIpltEnd;664 665    // _TLS_MODULE_BASE_ on targets that support TLSDESC.666    Defined *tlsModuleBase;667  };668  ElfSym sym{};669  std::unique_ptr<SymbolTable> symtab;670  SmallVector<Symbol *, 0> synthesizedSymbols;671 672  SmallVector<std::unique_ptr<MemoryBuffer>> memoryBuffers;673  SmallVector<ELFFileBase *, 0> objectFiles;674  SmallVector<SharedFile *, 0> sharedFiles;675  SmallVector<BinaryFile *, 0> binaryFiles;676  SmallVector<BitcodeFile *, 0> bitcodeFiles;677  SmallVector<BitcodeFile *, 0> lazyBitcodeFiles;678  SmallVector<InputSectionBase *, 0> inputSections;679  SmallVector<EhInputSection *, 0> ehInputSections;680 681  SmallVector<SymbolAux, 0> symAux;682  // Duplicate symbol candidates.683  SmallVector<DuplicateSymbol, 0> duplicates;684  // Undefined diagnostics are collected in a vector and emitted once all of685  // them are known, so that some postprocessing on the list of undefined686  // symbols can happen before lld emits diagnostics.687  std::mutex relocMutex;688  SmallVector<UndefinedDiag, 0> undefErrs;689  // Symbols in a non-prevailing COMDAT group which should be changed to an690  // Undefined.691  SmallVector<std::pair<Symbol *, unsigned>, 0> nonPrevailingSyms;692  // A tuple of (reference, extractedFile, sym). Used by --why-extract=.693  SmallVector<std::tuple<std::string, const InputFile *, const Symbol &>, 0>694      whyExtractRecords;695  // A mapping from a symbol to an InputFile referencing it backward. Used by696  // --warn-backrefs.697  llvm::DenseMap<const Symbol *,698                 std::pair<const InputFile *, const InputFile *>>699      backwardReferences;700  llvm::SmallSet<llvm::StringRef, 0> auxiliaryFiles;701  // If --reproduce is specified, all input files are written to this tar702  // archive.703  std::unique_ptr<llvm::TarWriter> tar;704  // InputFile for linker created symbols with no source location.705  InputFile *internalFile = nullptr;706  // Dummy Undefined for relocations without a symbol.707  Undefined *dummySym = nullptr;708  // True if symbols can be exported (isExported) or preemptible.709  bool hasDynsym = false;710  // True if SHT_LLVM_SYMPART is used.711  std::atomic<bool> hasSympart{false};712  // True if there are TLS IE relocations. Set DF_STATIC_TLS if -shared.713  std::atomic<bool> hasTlsIe{false};714  // True if we need to reserve two .got entries for local-dynamic TLS model.715  std::atomic<bool> needsTlsLd{false};716  // True if all native vtable symbols have corresponding type info symbols717  // during LTO.718  bool ltoAllVtablesHaveTypeInfos = false;719  // Number of Vernaux entries (needed shared object names).720  uint32_t vernauxNum = 0;721 722  // Each symbol assignment and DEFINED(sym) reference is assigned an increasing723  // order. Each DEFINED(sym) evaluation checks whether the reference happens724  // before a possible `sym = expr;`.725  unsigned scriptSymOrderCounter = 1;726  llvm::DenseMap<const Symbol *, unsigned> scriptSymOrder;727 728  // The set of TOC entries (.toc + addend) for which we should not apply729  // toc-indirect to toc-relative relaxation. const Symbol * refers to the730  // STT_SECTION symbol associated to the .toc input section.731  llvm::DenseSet<std::pair<const Symbol *, uint64_t>> ppc64noTocRelax;732 733  Ctx();734 735  llvm::raw_fd_ostream openAuxiliaryFile(llvm::StringRef, std::error_code &);736 737  std::optional<AArch64PauthAbiCoreInfo> aarch64PauthAbiCoreInfo;738};739 740// The first two elements of versionDefinitions represent VER_NDX_LOCAL and741// VER_NDX_GLOBAL. This helper returns other elements.742static inline ArrayRef<VersionDefinition> namedVersionDefs(Ctx &ctx) {743  return llvm::ArrayRef(ctx.arg.versionDefinitions).slice(2);744}745 746struct ELFSyncStream : SyncStream {747  Ctx &ctx;748  ELFSyncStream(Ctx &ctx, DiagLevel level)749      : SyncStream(ctx.e, level), ctx(ctx) {}750};751 752template <typename T>753std::enable_if_t<!std::is_pointer_v<std::remove_reference_t<T>>,754                 const ELFSyncStream &>755operator<<(const ELFSyncStream &s, T &&v) {756  s.os << std::forward<T>(v);757  return s;758}759 760inline const ELFSyncStream &operator<<(const ELFSyncStream &s, const char *v) {761  s.os << v;762  return s;763}764 765inline const ELFSyncStream &operator<<(const ELFSyncStream &s, Error v) {766  s.os << llvm::toString(std::move(v));767  return s;768}769 770// Report a log if --verbose is specified.771ELFSyncStream Log(Ctx &ctx);772 773// Print a message to stdout.774ELFSyncStream Msg(Ctx &ctx);775 776// Report a warning. Upgraded to an error if --fatal-warnings is specified.777ELFSyncStream Warn(Ctx &ctx);778 779// Report an error that will suppress the output file generation. Downgraded to780// a warning if --noinhibit-exec is specified.781ELFSyncStream Err(Ctx &ctx);782 783// Report an error regardless of --noinhibit-exec.784ELFSyncStream ErrAlways(Ctx &ctx);785 786// Report a fatal error that exits immediately. This should generally be avoided787// in favor of Err.788ELFSyncStream Fatal(Ctx &ctx);789 790uint64_t errCount(Ctx &ctx);791 792ELFSyncStream InternalErr(Ctx &ctx, const uint8_t *buf);793 794#define CHECK2(E, S) lld::check2((E), [&] { return toStr(ctx, S); })795 796inline DiagLevel toDiagLevel(ReportPolicy policy) {797  if (policy == ReportPolicy::Error)798    return DiagLevel::Err;799  else if (policy == ReportPolicy::Warning)800    return DiagLevel::Warn;801  return DiagLevel::None;802}803 804} // namespace lld::elf805 806#endif807