1bb684c34Spatrick //===- SyntheticSections.h -------------------------------------*- C++ -*-===// 2bb684c34Spatrick // 3bb684c34Spatrick // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. 4bb684c34Spatrick // See https://llvm.org/LICENSE.txt for license information. 5bb684c34Spatrick // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception 6bb684c34Spatrick // 7bb684c34Spatrick //===----------------------------------------------------------------------===// 8bb684c34Spatrick 9bb684c34Spatrick #ifndef LLD_MACHO_SYNTHETIC_SECTIONS_H 10bb684c34Spatrick #define LLD_MACHO_SYNTHETIC_SECTIONS_H 11bb684c34Spatrick 12bb684c34Spatrick #include "Config.h" 13bb684c34Spatrick #include "ExportTrie.h" 14bb684c34Spatrick #include "InputSection.h" 15bb684c34Spatrick #include "OutputSection.h" 161cf9926bSpatrick #include "OutputSegment.h" 17bb684c34Spatrick #include "Target.h" 181cf9926bSpatrick #include "Writer.h" 19bb684c34Spatrick 201cf9926bSpatrick #include "llvm/ADT/DenseMap.h" 211cf9926bSpatrick #include "llvm/ADT/Hashing.h" 22bb684c34Spatrick #include "llvm/ADT/SetVector.h" 23*dfe94b16Srobert #include "llvm/BinaryFormat/MachO.h" 241cf9926bSpatrick #include "llvm/Support/MathExtras.h" 25bb684c34Spatrick #include "llvm/Support/raw_ostream.h" 26bb684c34Spatrick 271cf9926bSpatrick #include <unordered_map> 281cf9926bSpatrick 291cf9926bSpatrick namespace llvm { 301cf9926bSpatrick class DWARFUnit; 311cf9926bSpatrick } // namespace llvm 321cf9926bSpatrick 33*dfe94b16Srobert namespace lld::macho { 34bb684c34Spatrick 351cf9926bSpatrick class Defined; 36bb684c34Spatrick class DylibSymbol; 37bb684c34Spatrick class LoadCommand; 381cf9926bSpatrick class ObjFile; 391cf9926bSpatrick class UnwindInfoSection; 40bb684c34Spatrick 41bb684c34Spatrick class SyntheticSection : public OutputSection { 42bb684c34Spatrick public: 43bb684c34Spatrick SyntheticSection(const char *segname, const char *name); 44bb684c34Spatrick virtual ~SyntheticSection() = default; 45bb684c34Spatrick classof(const OutputSection * sec)46bb684c34Spatrick static bool classof(const OutputSection *sec) { 47bb684c34Spatrick return sec->kind() == SyntheticKind; 48bb684c34Spatrick } 49bb684c34Spatrick 501cf9926bSpatrick StringRef segname; 511cf9926bSpatrick // This fake InputSection makes it easier for us to write code that applies 521cf9926bSpatrick // generically to both user inputs and synthetics. 531cf9926bSpatrick InputSection *isec; 541cf9926bSpatrick }; 551cf9926bSpatrick 561cf9926bSpatrick // All sections in __LINKEDIT should inherit from this. 571cf9926bSpatrick class LinkEditSection : public SyntheticSection { 581cf9926bSpatrick public: LinkEditSection(const char * segname,const char * name)591cf9926bSpatrick LinkEditSection(const char *segname, const char *name) 601cf9926bSpatrick : SyntheticSection(segname, name) { 611cf9926bSpatrick align = target->wordSize; 621cf9926bSpatrick } 631cf9926bSpatrick 64*dfe94b16Srobert // Implementations of this method can assume that the regular (non-__LINKEDIT) 65*dfe94b16Srobert // sections already have their addresses assigned. finalizeContents()661cf9926bSpatrick virtual void finalizeContents() {} 671cf9926bSpatrick 681cf9926bSpatrick // Sections in __LINKEDIT are special: their offsets are recorded in the 691cf9926bSpatrick // load commands like LC_DYLD_INFO_ONLY and LC_SYMTAB, instead of in section 701cf9926bSpatrick // headers. isHidden()71*dfe94b16Srobert bool isHidden() const final { return true; } 721cf9926bSpatrick 731cf9926bSpatrick virtual uint64_t getRawSize() const = 0; 741cf9926bSpatrick 751cf9926bSpatrick // codesign (or more specifically libstuff) checks that each section in 761cf9926bSpatrick // __LINKEDIT ends where the next one starts -- no gaps are permitted. We 771cf9926bSpatrick // therefore align every section's start and end points to WordSize. 781cf9926bSpatrick // 791cf9926bSpatrick // NOTE: This assumes that the extra bytes required for alignment can be 801cf9926bSpatrick // zero-valued bytes. getSize()81*dfe94b16Srobert uint64_t getSize() const final { return llvm::alignTo(getRawSize(), align); } 82bb684c34Spatrick }; 83bb684c34Spatrick 84bb684c34Spatrick // The header of the Mach-O file, which must have a file offset of zero. 851cf9926bSpatrick class MachHeaderSection final : public SyntheticSection { 86bb684c34Spatrick public: 87bb684c34Spatrick MachHeaderSection(); isHidden()88bb684c34Spatrick bool isHidden() const override { return true; } 89bb684c34Spatrick uint64_t getSize() const override; 90bb684c34Spatrick void writeTo(uint8_t *buf) const override; 91bb684c34Spatrick 921cf9926bSpatrick void addLoadCommand(LoadCommand *); 931cf9926bSpatrick 941cf9926bSpatrick protected: 95bb684c34Spatrick std::vector<LoadCommand *> loadCommands; 96bb684c34Spatrick uint32_t sizeOfCmds = 0; 97bb684c34Spatrick }; 98bb684c34Spatrick 99bb684c34Spatrick // A hidden section that exists solely for the purpose of creating the 100bb684c34Spatrick // __PAGEZERO segment, which is used to catch null pointer dereferences. 1011cf9926bSpatrick class PageZeroSection final : public SyntheticSection { 102bb684c34Spatrick public: 103bb684c34Spatrick PageZeroSection(); isHidden()104bb684c34Spatrick bool isHidden() const override { return true; } isNeeded()105*dfe94b16Srobert bool isNeeded() const override { return target->pageZeroSize != 0; } getSize()1061cf9926bSpatrick uint64_t getSize() const override { return target->pageZeroSize; } getFileSize()107bb684c34Spatrick uint64_t getFileSize() const override { return 0; } writeTo(uint8_t * buf)108bb684c34Spatrick void writeTo(uint8_t *buf) const override {} 109bb684c34Spatrick }; 110bb684c34Spatrick 1111cf9926bSpatrick // This is the base class for the GOT and TLVPointer sections, which are nearly 1121cf9926bSpatrick // functionally identical -- they will both be populated by dyld with addresses 1131cf9926bSpatrick // to non-lazily-loaded dylib symbols. The main difference is that the 1141cf9926bSpatrick // TLVPointerSection stores references to thread-local variables. 1151cf9926bSpatrick class NonLazyPointerSectionBase : public SyntheticSection { 116bb684c34Spatrick public: 1171cf9926bSpatrick NonLazyPointerSectionBase(const char *segname, const char *name); getEntries()118bb684c34Spatrick const llvm::SetVector<const Symbol *> &getEntries() const { return entries; } isNeeded()119bb684c34Spatrick bool isNeeded() const override { return !entries.empty(); } getSize()1201cf9926bSpatrick uint64_t getSize() const override { 1211cf9926bSpatrick return entries.size() * target->wordSize; 1221cf9926bSpatrick } 123bb684c34Spatrick void writeTo(uint8_t *buf) const override; 1241cf9926bSpatrick void addEntry(Symbol *sym); getVA(uint32_t gotIndex)1251cf9926bSpatrick uint64_t getVA(uint32_t gotIndex) const { 1261cf9926bSpatrick return addr + gotIndex * target->wordSize; 1271cf9926bSpatrick } 128bb684c34Spatrick 129bb684c34Spatrick private: 130bb684c34Spatrick llvm::SetVector<const Symbol *> entries; 131bb684c34Spatrick }; 132bb684c34Spatrick 1331cf9926bSpatrick class GotSection final : public NonLazyPointerSectionBase { 1341cf9926bSpatrick public: 1351cf9926bSpatrick GotSection(); 136bb684c34Spatrick }; 137bb684c34Spatrick 1381cf9926bSpatrick class TlvPointerSection final : public NonLazyPointerSectionBase { 139bb684c34Spatrick public: 1401cf9926bSpatrick TlvPointerSection(); 1411cf9926bSpatrick }; 1421cf9926bSpatrick 1431cf9926bSpatrick struct Location { 1441cf9926bSpatrick const InputSection *isec; 1451cf9926bSpatrick uint64_t offset; 1461cf9926bSpatrick LocationLocation1471cf9926bSpatrick Location(const InputSection *isec, uint64_t offset) 1481cf9926bSpatrick : isec(isec), offset(offset) {} getVALocation1491cf9926bSpatrick uint64_t getVA() const { return isec->getVA(offset); } 1501cf9926bSpatrick }; 1511cf9926bSpatrick 1521cf9926bSpatrick // Stores rebase opcodes, which tell dyld where absolute addresses have been 1531cf9926bSpatrick // encoded in the binary. If the binary is not loaded at its preferred address, 1541cf9926bSpatrick // dyld has to rebase these addresses by adding an offset to them. 1551cf9926bSpatrick class RebaseSection final : public LinkEditSection { 1561cf9926bSpatrick public: 1571cf9926bSpatrick RebaseSection(); 1581cf9926bSpatrick void finalizeContents() override; getRawSize()1591cf9926bSpatrick uint64_t getRawSize() const override { return contents.size(); } isNeeded()1601cf9926bSpatrick bool isNeeded() const override { return !locations.empty(); } 161bb684c34Spatrick void writeTo(uint8_t *buf) const override; 162bb684c34Spatrick addEntry(const InputSection * isec,uint64_t offset)1631cf9926bSpatrick void addEntry(const InputSection *isec, uint64_t offset) { 1641cf9926bSpatrick if (config->isPic) 1651cf9926bSpatrick locations.push_back({isec, offset}); 166bb684c34Spatrick } 167bb684c34Spatrick 168bb684c34Spatrick private: 1691cf9926bSpatrick std::vector<Location> locations; 1701cf9926bSpatrick SmallVector<char, 128> contents; 1711cf9926bSpatrick }; 1721cf9926bSpatrick 1731cf9926bSpatrick struct BindingEntry { 1741cf9926bSpatrick int64_t addend; 1751cf9926bSpatrick Location target; BindingEntryBindingEntry1761cf9926bSpatrick BindingEntry(int64_t addend, Location target) 1771cf9926bSpatrick : addend(addend), target(std::move(target)) {} 1781cf9926bSpatrick }; 1791cf9926bSpatrick 1801cf9926bSpatrick template <class Sym> 1811cf9926bSpatrick using BindingsMap = llvm::DenseMap<Sym, std::vector<BindingEntry>>; 1821cf9926bSpatrick 1831cf9926bSpatrick // Stores bind opcodes for telling dyld which symbols to load non-lazily. 1841cf9926bSpatrick class BindingSection final : public LinkEditSection { 1851cf9926bSpatrick public: 1861cf9926bSpatrick BindingSection(); 1871cf9926bSpatrick void finalizeContents() override; getRawSize()1881cf9926bSpatrick uint64_t getRawSize() const override { return contents.size(); } isNeeded()1891cf9926bSpatrick bool isNeeded() const override { return !bindingsMap.empty(); } 1901cf9926bSpatrick void writeTo(uint8_t *buf) const override; 1911cf9926bSpatrick 192*dfe94b16Srobert void addEntry(const Symbol *dysym, const InputSection *isec, uint64_t offset, 193*dfe94b16Srobert int64_t addend = 0) { 1941cf9926bSpatrick bindingsMap[dysym].emplace_back(addend, Location(isec, offset)); 1951cf9926bSpatrick } 1961cf9926bSpatrick 1971cf9926bSpatrick private: 198*dfe94b16Srobert BindingsMap<const Symbol *> bindingsMap; 1991cf9926bSpatrick SmallVector<char, 128> contents; 2001cf9926bSpatrick }; 2011cf9926bSpatrick 2021cf9926bSpatrick // Stores bind opcodes for telling dyld which weak symbols need coalescing. 2031cf9926bSpatrick // There are two types of entries in this section: 2041cf9926bSpatrick // 2051cf9926bSpatrick // 1) Non-weak definitions: This is a symbol definition that weak symbols in 2061cf9926bSpatrick // other dylibs should coalesce to. 2071cf9926bSpatrick // 2081cf9926bSpatrick // 2) Weak bindings: These tell dyld that a given symbol reference should 2091cf9926bSpatrick // coalesce to a non-weak definition if one is found. Note that unlike the 2101cf9926bSpatrick // entries in the BindingSection, the bindings here only refer to these 2111cf9926bSpatrick // symbols by name, but do not specify which dylib to load them from. 2121cf9926bSpatrick class WeakBindingSection final : public LinkEditSection { 2131cf9926bSpatrick public: 2141cf9926bSpatrick WeakBindingSection(); 2151cf9926bSpatrick void finalizeContents() override; getRawSize()2161cf9926bSpatrick uint64_t getRawSize() const override { return contents.size(); } isNeeded()2171cf9926bSpatrick bool isNeeded() const override { 2181cf9926bSpatrick return !bindingsMap.empty() || !definitions.empty(); 2191cf9926bSpatrick } 2201cf9926bSpatrick 2211cf9926bSpatrick void writeTo(uint8_t *buf) const override; 2221cf9926bSpatrick 2231cf9926bSpatrick void addEntry(const Symbol *symbol, const InputSection *isec, uint64_t offset, 2241cf9926bSpatrick int64_t addend = 0) { 2251cf9926bSpatrick bindingsMap[symbol].emplace_back(addend, Location(isec, offset)); 2261cf9926bSpatrick } 2271cf9926bSpatrick hasEntry()2281cf9926bSpatrick bool hasEntry() const { return !bindingsMap.empty(); } 2291cf9926bSpatrick addNonWeakDefinition(const Defined * defined)2301cf9926bSpatrick void addNonWeakDefinition(const Defined *defined) { 2311cf9926bSpatrick definitions.emplace_back(defined); 2321cf9926bSpatrick } 2331cf9926bSpatrick hasNonWeakDefinition()2341cf9926bSpatrick bool hasNonWeakDefinition() const { return !definitions.empty(); } 2351cf9926bSpatrick 2361cf9926bSpatrick private: 2371cf9926bSpatrick BindingsMap<const Symbol *> bindingsMap; 2381cf9926bSpatrick std::vector<const Defined *> definitions; 239bb684c34Spatrick SmallVector<char, 128> contents; 240bb684c34Spatrick }; 241bb684c34Spatrick 242bb684c34Spatrick // The following sections implement lazy symbol binding -- very similar to the 243bb684c34Spatrick // PLT mechanism in ELF. 244bb684c34Spatrick // 2451cf9926bSpatrick // ELF's .plt section is broken up into two sections in Mach-O: StubsSection 2461cf9926bSpatrick // and StubHelperSection. Calls to functions in dylibs will end up calling into 247bb684c34Spatrick // StubsSection, which contains indirect jumps to addresses stored in the 248bb684c34Spatrick // LazyPointerSection (the counterpart to ELF's .plt.got). 249bb684c34Spatrick // 2501cf9926bSpatrick // We will first describe how non-weak symbols are handled. 2511cf9926bSpatrick // 2521cf9926bSpatrick // At program start, the LazyPointerSection contains addresses that point into 2531cf9926bSpatrick // one of the entry points in the middle of the StubHelperSection. The code in 254bb684c34Spatrick // StubHelperSection will push on the stack an offset into the 255bb684c34Spatrick // LazyBindingSection. The push is followed by a jump to the beginning of the 256bb684c34Spatrick // StubHelperSection (similar to PLT0), which then calls into dyld_stub_binder. 257bb684c34Spatrick // dyld_stub_binder is a non-lazily-bound symbol, so this call looks it up in 258bb684c34Spatrick // the GOT. 259bb684c34Spatrick // 260bb684c34Spatrick // The stub binder will look up the bind opcodes in the LazyBindingSection at 2611cf9926bSpatrick // the given offset. The bind opcodes will tell the binder to update the 2621cf9926bSpatrick // address in the LazyPointerSection to point to the symbol, so that subsequent 2631cf9926bSpatrick // calls don't have to redo the symbol resolution. The binder will then jump to 2641cf9926bSpatrick // the resolved symbol. 2651cf9926bSpatrick // 2661cf9926bSpatrick // With weak symbols, the situation is slightly different. Since there is no 2671cf9926bSpatrick // "weak lazy" lookup, function calls to weak symbols are always non-lazily 2681cf9926bSpatrick // bound. We emit both regular non-lazy bindings as well as weak bindings, in 2691cf9926bSpatrick // order that the weak bindings may overwrite the non-lazy bindings if an 2701cf9926bSpatrick // appropriate symbol is found at runtime. However, the bound addresses will 2711cf9926bSpatrick // still be written (non-lazily) into the LazyPointerSection. 272*dfe94b16Srobert // 273*dfe94b16Srobert // Symbols are always bound eagerly when chained fixups are used. In that case, 274*dfe94b16Srobert // StubsSection contains indirect jumps to addresses stored in the GotSection. 275*dfe94b16Srobert // The GOT directly contains the fixup entries, which will be replaced by the 276*dfe94b16Srobert // address of the target symbols on load. LazyPointerSection and 277*dfe94b16Srobert // StubHelperSection are not used. 278bb684c34Spatrick 2791cf9926bSpatrick class StubsSection final : public SyntheticSection { 280bb684c34Spatrick public: 281bb684c34Spatrick StubsSection(); 282bb684c34Spatrick uint64_t getSize() const override; isNeeded()283bb684c34Spatrick bool isNeeded() const override { return !entries.empty(); } 2841cf9926bSpatrick void finalize() override; 285bb684c34Spatrick void writeTo(uint8_t *buf) const override; getEntries()2861cf9926bSpatrick const llvm::SetVector<Symbol *> &getEntries() const { return entries; } 287*dfe94b16Srobert // Creates a stub for the symbol and the corresponding entry in the 288*dfe94b16Srobert // LazyPointerSection. 289*dfe94b16Srobert void addEntry(Symbol *); getVA(uint32_t stubsIndex)2901cf9926bSpatrick uint64_t getVA(uint32_t stubsIndex) const { 2911cf9926bSpatrick assert(isFinal || target->usesThunks()); 2921cf9926bSpatrick // ConcatOutputSection::finalize() can seek the address of a 2931cf9926bSpatrick // stub before its address is assigned. Before __stubs is 2941cf9926bSpatrick // finalized, return a contrived out-of-range address. 2951cf9926bSpatrick return isFinal ? addr + stubsIndex * target->stubSize 2961cf9926bSpatrick : TargetInfo::outOfRangeVA; 2971cf9926bSpatrick } 298bb684c34Spatrick 2991cf9926bSpatrick bool isFinal = false; // is address assigned? 300bb684c34Spatrick 301bb684c34Spatrick private: 3021cf9926bSpatrick llvm::SetVector<Symbol *> entries; 303bb684c34Spatrick }; 304bb684c34Spatrick 3051cf9926bSpatrick class StubHelperSection final : public SyntheticSection { 306bb684c34Spatrick public: 307bb684c34Spatrick StubHelperSection(); 308bb684c34Spatrick uint64_t getSize() const override; 309bb684c34Spatrick bool isNeeded() const override; 310bb684c34Spatrick void writeTo(uint8_t *buf) const override; 311bb684c34Spatrick 312*dfe94b16Srobert void setUp(); 313bb684c34Spatrick 314bb684c34Spatrick DylibSymbol *stubBinder = nullptr; 3151cf9926bSpatrick Defined *dyldPrivate = nullptr; 316bb684c34Spatrick }; 317bb684c34Spatrick 318*dfe94b16Srobert // Objective-C stubs are hoisted objc_msgSend calls per selector called in the 319*dfe94b16Srobert // program. Apple Clang produces undefined symbols to each stub, such as 320*dfe94b16Srobert // '_objc_msgSend$foo', which are then synthesized by the linker. The stubs 321*dfe94b16Srobert // load the particular selector 'foo' from __objc_selrefs, setting it to the 322*dfe94b16Srobert // first argument of the objc_msgSend call, and then jumps to objc_msgSend. The 323*dfe94b16Srobert // actual stub contents are mirrored from ld64. 324*dfe94b16Srobert class ObjCStubsSection final : public SyntheticSection { 325*dfe94b16Srobert public: 326*dfe94b16Srobert ObjCStubsSection(); 327*dfe94b16Srobert void addEntry(Symbol *sym); 328*dfe94b16Srobert uint64_t getSize() const override; isNeeded()329*dfe94b16Srobert bool isNeeded() const override { return !symbols.empty(); } finalize()330*dfe94b16Srobert void finalize() override { isec->isFinal = true; } 331*dfe94b16Srobert void writeTo(uint8_t *buf) const override; 332*dfe94b16Srobert void setUp(); 333*dfe94b16Srobert 334*dfe94b16Srobert static constexpr llvm::StringLiteral symbolPrefix = "_objc_msgSend$"; 335*dfe94b16Srobert 336*dfe94b16Srobert private: 337*dfe94b16Srobert std::vector<Defined *> symbols; 338*dfe94b16Srobert std::vector<uint32_t> offsets; 339*dfe94b16Srobert int objcMsgSendGotIndex = 0; 340*dfe94b16Srobert }; 341*dfe94b16Srobert 3421cf9926bSpatrick // Note that this section may also be targeted by non-lazy bindings. In 3431cf9926bSpatrick // particular, this happens when branch relocations target weak symbols. 3441cf9926bSpatrick class LazyPointerSection final : public SyntheticSection { 345bb684c34Spatrick public: 346bb684c34Spatrick LazyPointerSection(); 347bb684c34Spatrick uint64_t getSize() const override; 348bb684c34Spatrick bool isNeeded() const override; 349bb684c34Spatrick void writeTo(uint8_t *buf) const override; getVA(uint32_t index)350*dfe94b16Srobert uint64_t getVA(uint32_t index) const { 351*dfe94b16Srobert return addr + (index << target->p2WordSize); 352*dfe94b16Srobert } 353bb684c34Spatrick }; 354bb684c34Spatrick 3551cf9926bSpatrick class LazyBindingSection final : public LinkEditSection { 356bb684c34Spatrick public: 357bb684c34Spatrick LazyBindingSection(); 3581cf9926bSpatrick void finalizeContents() override; getRawSize()3591cf9926bSpatrick uint64_t getRawSize() const override { return contents.size(); } isNeeded()3601cf9926bSpatrick bool isNeeded() const override { return !entries.empty(); } 361bb684c34Spatrick void writeTo(uint8_t *buf) const override; 3621cf9926bSpatrick // Note that every entry here will by referenced by a corresponding entry in 3631cf9926bSpatrick // the StubHelperSection. 364*dfe94b16Srobert void addEntry(Symbol *dysym); getEntries()365*dfe94b16Srobert const llvm::SetVector<Symbol *> &getEntries() const { return entries; } 366bb684c34Spatrick 367bb684c34Spatrick private: 368*dfe94b16Srobert uint32_t encode(const Symbol &); 3691cf9926bSpatrick 370*dfe94b16Srobert llvm::SetVector<Symbol *> entries; 371bb684c34Spatrick SmallVector<char, 128> contents; 372bb684c34Spatrick llvm::raw_svector_ostream os{contents}; 373bb684c34Spatrick }; 374bb684c34Spatrick 375bb684c34Spatrick // Stores a trie that describes the set of exported symbols. 3761cf9926bSpatrick class ExportSection final : public LinkEditSection { 377bb684c34Spatrick public: 378bb684c34Spatrick ExportSection(); 3791cf9926bSpatrick void finalizeContents() override; getRawSize()3801cf9926bSpatrick uint64_t getRawSize() const override { return size; } isNeeded()381*dfe94b16Srobert bool isNeeded() const override { return size; } 382bb684c34Spatrick void writeTo(uint8_t *buf) const override; 383bb684c34Spatrick 3841cf9926bSpatrick bool hasWeakSymbol = false; 3851cf9926bSpatrick 386bb684c34Spatrick private: 387bb684c34Spatrick TrieBuilder trieBuilder; 388bb684c34Spatrick size_t size = 0; 389bb684c34Spatrick }; 390bb684c34Spatrick 391*dfe94b16Srobert // Stores 'data in code' entries that describe the locations of data regions 392*dfe94b16Srobert // inside code sections. This is used by llvm-objdump to distinguish jump tables 393*dfe94b16Srobert // and stop them from being disassembled as instructions. 3941cf9926bSpatrick class DataInCodeSection final : public LinkEditSection { 3951cf9926bSpatrick public: 3961cf9926bSpatrick DataInCodeSection(); 3971cf9926bSpatrick void finalizeContents() override; getRawSize()3981cf9926bSpatrick uint64_t getRawSize() const override { 3991cf9926bSpatrick return sizeof(llvm::MachO::data_in_code_entry) * entries.size(); 4001cf9926bSpatrick } 4011cf9926bSpatrick void writeTo(uint8_t *buf) const override; 4021cf9926bSpatrick 4031cf9926bSpatrick private: 4041cf9926bSpatrick std::vector<llvm::MachO::data_in_code_entry> entries; 4051cf9926bSpatrick }; 4061cf9926bSpatrick 4071cf9926bSpatrick // Stores ULEB128 delta encoded addresses of functions. 4081cf9926bSpatrick class FunctionStartsSection final : public LinkEditSection { 4091cf9926bSpatrick public: 4101cf9926bSpatrick FunctionStartsSection(); 4111cf9926bSpatrick void finalizeContents() override; getRawSize()4121cf9926bSpatrick uint64_t getRawSize() const override { return contents.size(); } 4131cf9926bSpatrick void writeTo(uint8_t *buf) const override; 4141cf9926bSpatrick 4151cf9926bSpatrick private: 4161cf9926bSpatrick SmallVector<char, 128> contents; 4171cf9926bSpatrick }; 4181cf9926bSpatrick 419bb684c34Spatrick // Stores the strings referenced by the symbol table. 4201cf9926bSpatrick class StringTableSection final : public LinkEditSection { 421bb684c34Spatrick public: 422bb684c34Spatrick StringTableSection(); 423bb684c34Spatrick // Returns the start offset of the added string. 424bb684c34Spatrick uint32_t addString(StringRef); getRawSize()4251cf9926bSpatrick uint64_t getRawSize() const override { return size; } 426bb684c34Spatrick void writeTo(uint8_t *buf) const override; 427bb684c34Spatrick 4281cf9926bSpatrick static constexpr size_t emptyStringIndex = 1; 4291cf9926bSpatrick 430bb684c34Spatrick private: 4311cf9926bSpatrick // ld64 emits string tables which start with a space and a zero byte. We 4321cf9926bSpatrick // match its behavior here since some tools depend on it. 4331cf9926bSpatrick // Consequently, the empty string will be at index 1, not zero. 4341cf9926bSpatrick std::vector<StringRef> strings{" "}; 4351cf9926bSpatrick size_t size = 2; 436bb684c34Spatrick }; 437bb684c34Spatrick 438bb684c34Spatrick struct SymtabEntry { 439bb684c34Spatrick Symbol *sym; 440bb684c34Spatrick size_t strx; 441bb684c34Spatrick }; 442bb684c34Spatrick 4431cf9926bSpatrick struct StabsEntry { 4441cf9926bSpatrick uint8_t type = 0; 4451cf9926bSpatrick uint32_t strx = StringTableSection::emptyStringIndex; 4461cf9926bSpatrick uint8_t sect = 0; 4471cf9926bSpatrick uint16_t desc = 0; 4481cf9926bSpatrick uint64_t value = 0; 4491cf9926bSpatrick 4501cf9926bSpatrick StabsEntry() = default; StabsEntryStabsEntry4511cf9926bSpatrick explicit StabsEntry(uint8_t type) : type(type) {} 4521cf9926bSpatrick }; 4531cf9926bSpatrick 4541cf9926bSpatrick // Symbols of the same type must be laid out contiguously: we choose to emit 4551cf9926bSpatrick // all local symbols first, then external symbols, and finally undefined 4561cf9926bSpatrick // symbols. For each symbol type, the LC_DYSYMTAB load command will record the 4571cf9926bSpatrick // range (start index and total number) of those symbols in the symbol table. 4581cf9926bSpatrick class SymtabSection : public LinkEditSection { 459bb684c34Spatrick public: 4601cf9926bSpatrick void finalizeContents() override; 4611cf9926bSpatrick uint32_t getNumSymbols() const; getNumLocalSymbols()4621cf9926bSpatrick uint32_t getNumLocalSymbols() const { 4631cf9926bSpatrick return stabs.size() + localSymbols.size(); 4641cf9926bSpatrick } getNumExternalSymbols()4651cf9926bSpatrick uint32_t getNumExternalSymbols() const { return externalSymbols.size(); } getNumUndefinedSymbols()4661cf9926bSpatrick uint32_t getNumUndefinedSymbols() const { return undefinedSymbols.size(); } 4671cf9926bSpatrick 4681cf9926bSpatrick private: 469*dfe94b16Srobert void emitBeginSourceStab(StringRef); 4701cf9926bSpatrick void emitEndSourceStab(); 4711cf9926bSpatrick void emitObjectFileStab(ObjFile *); 4721cf9926bSpatrick void emitEndFunStab(Defined *); 4731cf9926bSpatrick void emitStabs(); 4741cf9926bSpatrick 4751cf9926bSpatrick protected: 476bb684c34Spatrick SymtabSection(StringTableSection &); 4771cf9926bSpatrick 4781cf9926bSpatrick StringTableSection &stringTableSection; 4791cf9926bSpatrick // STABS symbols are always local symbols, but we represent them with special 4801cf9926bSpatrick // entries because they may use fields like n_sect and n_desc differently. 4811cf9926bSpatrick std::vector<StabsEntry> stabs; 4821cf9926bSpatrick std::vector<SymtabEntry> localSymbols; 4831cf9926bSpatrick std::vector<SymtabEntry> externalSymbols; 4841cf9926bSpatrick std::vector<SymtabEntry> undefinedSymbols; 4851cf9926bSpatrick }; 4861cf9926bSpatrick 4871cf9926bSpatrick template <class LP> SymtabSection *makeSymtabSection(StringTableSection &); 4881cf9926bSpatrick 4891cf9926bSpatrick // The indirect symbol table is a list of 32-bit integers that serve as indices 4901cf9926bSpatrick // into the (actual) symbol table. The indirect symbol table is a 4911cf9926bSpatrick // concatenation of several sub-arrays of indices, each sub-array belonging to 4921cf9926bSpatrick // a separate section. The starting offset of each sub-array is stored in the 4931cf9926bSpatrick // reserved1 header field of the respective section. 4941cf9926bSpatrick // 4951cf9926bSpatrick // These sub-arrays provide symbol information for sections that store 4961cf9926bSpatrick // contiguous sequences of symbol references. These references can be pointers 4971cf9926bSpatrick // (e.g. those in the GOT and TLVP sections) or assembly sequences (e.g. 4981cf9926bSpatrick // function stubs). 4991cf9926bSpatrick class IndirectSymtabSection final : public LinkEditSection { 5001cf9926bSpatrick public: 5011cf9926bSpatrick IndirectSymtabSection(); 5021cf9926bSpatrick void finalizeContents() override; 5031cf9926bSpatrick uint32_t getNumSymbols() const; getRawSize()5041cf9926bSpatrick uint64_t getRawSize() const override { 5051cf9926bSpatrick return getNumSymbols() * sizeof(uint32_t); 5061cf9926bSpatrick } 5071cf9926bSpatrick bool isNeeded() const override; 5081cf9926bSpatrick void writeTo(uint8_t *buf) const override; 5091cf9926bSpatrick }; 5101cf9926bSpatrick 5111cf9926bSpatrick // The code signature comes at the very end of the linked output file. 5121cf9926bSpatrick class CodeSignatureSection final : public LinkEditSection { 5131cf9926bSpatrick public: 514*dfe94b16Srobert // NOTE: These values are duplicated in llvm-objcopy's MachO/Object.h file 515*dfe94b16Srobert // and any changes here, should be repeated there. 5161cf9926bSpatrick static constexpr uint8_t blockSizeShift = 12; 5171cf9926bSpatrick static constexpr size_t blockSize = (1 << blockSizeShift); // 4 KiB 5181cf9926bSpatrick static constexpr size_t hashSize = 256 / 8; 5191cf9926bSpatrick static constexpr size_t blobHeadersSize = llvm::alignTo<8>( 5201cf9926bSpatrick sizeof(llvm::MachO::CS_SuperBlob) + sizeof(llvm::MachO::CS_BlobIndex)); 5211cf9926bSpatrick static constexpr uint32_t fixedHeadersSize = 5221cf9926bSpatrick blobHeadersSize + sizeof(llvm::MachO::CS_CodeDirectory); 5231cf9926bSpatrick 5241cf9926bSpatrick uint32_t fileNamePad = 0; 5251cf9926bSpatrick uint32_t allHeadersSize = 0; 5261cf9926bSpatrick StringRef fileName; 5271cf9926bSpatrick 5281cf9926bSpatrick CodeSignatureSection(); 5291cf9926bSpatrick uint64_t getRawSize() const override; isNeeded()5301cf9926bSpatrick bool isNeeded() const override { return true; } 5311cf9926bSpatrick void writeTo(uint8_t *buf) const override; 5321cf9926bSpatrick uint32_t getBlockCount() const; 5331cf9926bSpatrick void writeHashes(uint8_t *buf) const; 5341cf9926bSpatrick }; 5351cf9926bSpatrick 5361cf9926bSpatrick class BitcodeBundleSection final : public SyntheticSection { 5371cf9926bSpatrick public: 5381cf9926bSpatrick BitcodeBundleSection(); getSize()5391cf9926bSpatrick uint64_t getSize() const override { return xarSize; } 5401cf9926bSpatrick void finalize() override; 541bb684c34Spatrick void writeTo(uint8_t *buf) const override; 542bb684c34Spatrick 543bb684c34Spatrick private: 5441cf9926bSpatrick llvm::SmallString<261> xarPath; 5451cf9926bSpatrick uint64_t xarSize; 5461cf9926bSpatrick }; 5471cf9926bSpatrick 5481cf9926bSpatrick class CStringSection : public SyntheticSection { 5491cf9926bSpatrick public: 550*dfe94b16Srobert CStringSection(const char *name); 5511cf9926bSpatrick void addInput(CStringInputSection *); getSize()5521cf9926bSpatrick uint64_t getSize() const override { return size; } 5531cf9926bSpatrick virtual void finalizeContents(); isNeeded()5541cf9926bSpatrick bool isNeeded() const override { return !inputs.empty(); } 5551cf9926bSpatrick void writeTo(uint8_t *buf) const override; 5561cf9926bSpatrick 5571cf9926bSpatrick std::vector<CStringInputSection *> inputs; 5581cf9926bSpatrick 5591cf9926bSpatrick private: 5601cf9926bSpatrick uint64_t size; 5611cf9926bSpatrick }; 5621cf9926bSpatrick 5631cf9926bSpatrick class DeduplicatedCStringSection final : public CStringSection { 5641cf9926bSpatrick public: DeduplicatedCStringSection(const char * name)565*dfe94b16Srobert DeduplicatedCStringSection(const char *name) : CStringSection(name){}; getSize()566*dfe94b16Srobert uint64_t getSize() const override { return size; } 5671cf9926bSpatrick void finalizeContents() override; 568*dfe94b16Srobert void writeTo(uint8_t *buf) const override; 569*dfe94b16Srobert 570*dfe94b16Srobert struct StringOffset { 571*dfe94b16Srobert uint8_t trailingZeros; 572*dfe94b16Srobert uint64_t outSecOff = UINT64_MAX; 573*dfe94b16Srobert StringOffsetStringOffset574*dfe94b16Srobert explicit StringOffset(uint8_t zeros) : trailingZeros(zeros) {} 575*dfe94b16Srobert }; 576*dfe94b16Srobert 577*dfe94b16Srobert StringOffset getStringOffset(StringRef str) const; 5781cf9926bSpatrick 5791cf9926bSpatrick private: 580*dfe94b16Srobert llvm::DenseMap<llvm::CachedHashStringRef, StringOffset> stringOffsetMap; 581*dfe94b16Srobert size_t size = 0; 5821cf9926bSpatrick }; 5831cf9926bSpatrick 5841cf9926bSpatrick /* 5851cf9926bSpatrick * This section contains deduplicated literal values. The 16-byte values are 5861cf9926bSpatrick * laid out first, followed by the 8- and then the 4-byte ones. 5871cf9926bSpatrick */ 5881cf9926bSpatrick class WordLiteralSection final : public SyntheticSection { 5891cf9926bSpatrick public: 5901cf9926bSpatrick using UInt128 = std::pair<uint64_t, uint64_t>; 5911cf9926bSpatrick // I don't think the standard guarantees the size of a pair, so let's make 5921cf9926bSpatrick // sure it's exact -- that way we can construct it via `mmap`. 593*dfe94b16Srobert static_assert(sizeof(UInt128) == 16); 5941cf9926bSpatrick 5951cf9926bSpatrick WordLiteralSection(); 5961cf9926bSpatrick void addInput(WordLiteralInputSection *); 5971cf9926bSpatrick void finalizeContents(); 5981cf9926bSpatrick void writeTo(uint8_t *buf) const override; 5991cf9926bSpatrick getSize()6001cf9926bSpatrick uint64_t getSize() const override { 6011cf9926bSpatrick return literal16Map.size() * 16 + literal8Map.size() * 8 + 6021cf9926bSpatrick literal4Map.size() * 4; 6031cf9926bSpatrick } 6041cf9926bSpatrick isNeeded()6051cf9926bSpatrick bool isNeeded() const override { 6061cf9926bSpatrick return !literal16Map.empty() || !literal4Map.empty() || 6071cf9926bSpatrick !literal8Map.empty(); 6081cf9926bSpatrick } 6091cf9926bSpatrick getLiteral16Offset(uintptr_t buf)610*dfe94b16Srobert uint64_t getLiteral16Offset(uintptr_t buf) const { 6111cf9926bSpatrick return literal16Map.at(*reinterpret_cast<const UInt128 *>(buf)) * 16; 6121cf9926bSpatrick } 6131cf9926bSpatrick getLiteral8Offset(uintptr_t buf)614*dfe94b16Srobert uint64_t getLiteral8Offset(uintptr_t buf) const { 6151cf9926bSpatrick return literal16Map.size() * 16 + 6161cf9926bSpatrick literal8Map.at(*reinterpret_cast<const uint64_t *>(buf)) * 8; 6171cf9926bSpatrick } 6181cf9926bSpatrick getLiteral4Offset(uintptr_t buf)619*dfe94b16Srobert uint64_t getLiteral4Offset(uintptr_t buf) const { 6201cf9926bSpatrick return literal16Map.size() * 16 + literal8Map.size() * 8 + 6211cf9926bSpatrick literal4Map.at(*reinterpret_cast<const uint32_t *>(buf)) * 4; 6221cf9926bSpatrick } 6231cf9926bSpatrick 6241cf9926bSpatrick private: 6251cf9926bSpatrick std::vector<WordLiteralInputSection *> inputs; 6261cf9926bSpatrick 6271cf9926bSpatrick template <class T> struct Hasher { operatorHasher6281cf9926bSpatrick llvm::hash_code operator()(T v) const { return llvm::hash_value(v); } 6291cf9926bSpatrick }; 6301cf9926bSpatrick // We're using unordered_map instead of DenseMap here because we need to 6311cf9926bSpatrick // support all possible integer values -- there are no suitable tombstone 6321cf9926bSpatrick // values for DenseMap. 6331cf9926bSpatrick std::unordered_map<UInt128, uint64_t, Hasher<UInt128>> literal16Map; 6341cf9926bSpatrick std::unordered_map<uint64_t, uint64_t> literal8Map; 6351cf9926bSpatrick std::unordered_map<uint32_t, uint64_t> literal4Map; 636bb684c34Spatrick }; 637bb684c34Spatrick 638*dfe94b16Srobert class ObjCImageInfoSection final : public SyntheticSection { 639*dfe94b16Srobert public: 640*dfe94b16Srobert ObjCImageInfoSection(); isNeeded()641*dfe94b16Srobert bool isNeeded() const override { return !files.empty(); } getSize()642*dfe94b16Srobert uint64_t getSize() const override { return 8; } addFile(const InputFile * file)643*dfe94b16Srobert void addFile(const InputFile *file) { 644*dfe94b16Srobert assert(!file->objCImageInfo.empty()); 645*dfe94b16Srobert files.push_back(file); 646*dfe94b16Srobert } 647*dfe94b16Srobert void finalizeContents(); 648*dfe94b16Srobert void writeTo(uint8_t *buf) const override; 649*dfe94b16Srobert 650*dfe94b16Srobert private: 651*dfe94b16Srobert struct ImageInfo { 652*dfe94b16Srobert uint8_t swiftVersion = 0; 653*dfe94b16Srobert bool hasCategoryClassProperties = false; 654*dfe94b16Srobert } info; 655*dfe94b16Srobert static ImageInfo parseImageInfo(const InputFile *); 656*dfe94b16Srobert std::vector<const InputFile *> files; // files with image info 657*dfe94b16Srobert }; 658*dfe94b16Srobert 659*dfe94b16Srobert // This section stores 32-bit __TEXT segment offsets of initializer functions. 660*dfe94b16Srobert // 661*dfe94b16Srobert // The compiler stores pointers to initializers in __mod_init_func. These need 662*dfe94b16Srobert // to be fixed up at load time, which takes time and dirties memory. By 663*dfe94b16Srobert // synthesizing InitOffsetsSection from them, this data can live in the 664*dfe94b16Srobert // read-only __TEXT segment instead. This section is used by default when 665*dfe94b16Srobert // chained fixups are enabled. 666*dfe94b16Srobert // 667*dfe94b16Srobert // There is no similar counterpart to __mod_term_func, as that section is 668*dfe94b16Srobert // deprecated, and static destructors are instead handled by registering them 669*dfe94b16Srobert // via __cxa_atexit from an autogenerated initializer function (see D121736). 670*dfe94b16Srobert class InitOffsetsSection final : public SyntheticSection { 671*dfe94b16Srobert public: 672*dfe94b16Srobert InitOffsetsSection(); isNeeded()673*dfe94b16Srobert bool isNeeded() const override { return !sections.empty(); } 674*dfe94b16Srobert uint64_t getSize() const override; 675*dfe94b16Srobert void writeTo(uint8_t *buf) const override; 676*dfe94b16Srobert void setUp(); 677*dfe94b16Srobert addInput(ConcatInputSection * isec)678*dfe94b16Srobert void addInput(ConcatInputSection *isec) { sections.push_back(isec); } inputs()679*dfe94b16Srobert const std::vector<ConcatInputSection *> &inputs() const { return sections; } 680*dfe94b16Srobert 681*dfe94b16Srobert private: 682*dfe94b16Srobert std::vector<ConcatInputSection *> sections; 683*dfe94b16Srobert }; 684*dfe94b16Srobert 685*dfe94b16Srobert // Chained fixups are a replacement for classic dyld opcodes. In this format, 686*dfe94b16Srobert // most of the metadata necessary for binding symbols and rebasing addresses is 687*dfe94b16Srobert // stored directly in the memory location that will have the fixup applied. 688*dfe94b16Srobert // 689*dfe94b16Srobert // The fixups form singly linked lists; each one covering a single page in 690*dfe94b16Srobert // memory. The __LINKEDIT,__chainfixups section stores the page offset of the 691*dfe94b16Srobert // first fixup of each page; the rest can be found by walking the chain using 692*dfe94b16Srobert // the offset that is embedded in each entry. 693*dfe94b16Srobert // 694*dfe94b16Srobert // This setup allows pages to be relocated lazily at page-in time and without 695*dfe94b16Srobert // being dirtied. The kernel can discard and load them again as needed. This 696*dfe94b16Srobert // technique, called page-in linking, was introduced in macOS 13. 697*dfe94b16Srobert // 698*dfe94b16Srobert // The benefits of this format are: 699*dfe94b16Srobert // - smaller __LINKEDIT segment, as most of the fixup information is stored in 700*dfe94b16Srobert // the data segment 701*dfe94b16Srobert // - faster startup, since not all relocations need to be done upfront 702*dfe94b16Srobert // - slightly lower memory usage, as fewer pages are dirtied 703*dfe94b16Srobert // 704*dfe94b16Srobert // Userspace x86_64 and arm64 binaries have two types of fixup entries: 705*dfe94b16Srobert // - Rebase entries contain an absolute address, to which the object's load 706*dfe94b16Srobert // address will be added to get the final value. This is used for loading 707*dfe94b16Srobert // the address of a symbol defined in the same binary. 708*dfe94b16Srobert // - Binding entries are mostly used for symbols imported from other dylibs, 709*dfe94b16Srobert // but for weakly bound and interposable symbols as well. They are looked up 710*dfe94b16Srobert // by a (symbol name, library) pair stored in __chainfixups. This import 711*dfe94b16Srobert // entry also encodes whether the import is weak (i.e. if the symbol is 712*dfe94b16Srobert // missing, it should be set to null instead of producing a load error). 713*dfe94b16Srobert // The fixup encodes an ordinal associated with the import, and an optional 714*dfe94b16Srobert // addend. 715*dfe94b16Srobert // 716*dfe94b16Srobert // The entries are tightly packed 64-bit bitfields. One of the bits specifies 717*dfe94b16Srobert // which kind of fixup to interpret them as. 718*dfe94b16Srobert // 719*dfe94b16Srobert // LLD generates the fixup data in 5 stages: 720*dfe94b16Srobert // 1. While scanning relocations, we make a note of each location that needs 721*dfe94b16Srobert // a fixup by calling addRebase() or addBinding(). During this, we assign 722*dfe94b16Srobert // a unique ordinal for each (symbol name, library, addend) import tuple. 723*dfe94b16Srobert // 2. After addresses have been assigned to all sections, and thus the memory 724*dfe94b16Srobert // layout of the linked image is final; finalizeContents() is called. Here, 725*dfe94b16Srobert // the page offsets of the chain start entries are calculated. 726*dfe94b16Srobert // 3. ChainedFixupsSection::writeTo() writes the page start offsets and the 727*dfe94b16Srobert // imports table to the output file. 728*dfe94b16Srobert // 4. Each section's fixup entries are encoded and written to disk in 729*dfe94b16Srobert // ConcatInputSection::writeTo(), but without writing the offsets that form 730*dfe94b16Srobert // the chain. 731*dfe94b16Srobert // 5. Finally, each page's (which might correspond to multiple sections) 732*dfe94b16Srobert // fixups are linked together in Writer::buildFixupChains(). 733*dfe94b16Srobert class ChainedFixupsSection final : public LinkEditSection { 734*dfe94b16Srobert public: 735*dfe94b16Srobert ChainedFixupsSection(); 736*dfe94b16Srobert void finalizeContents() override; getRawSize()737*dfe94b16Srobert uint64_t getRawSize() const override { return size; } 738*dfe94b16Srobert bool isNeeded() const override; 739*dfe94b16Srobert void writeTo(uint8_t *buf) const override; 740*dfe94b16Srobert addRebase(const InputSection * isec,uint64_t offset)741*dfe94b16Srobert void addRebase(const InputSection *isec, uint64_t offset) { 742*dfe94b16Srobert locations.emplace_back(isec, offset); 743*dfe94b16Srobert } 744*dfe94b16Srobert void addBinding(const Symbol *dysym, const InputSection *isec, 745*dfe94b16Srobert uint64_t offset, int64_t addend = 0); 746*dfe94b16Srobert setHasNonWeakDefinition()747*dfe94b16Srobert void setHasNonWeakDefinition() { hasNonWeakDef = true; } 748*dfe94b16Srobert 749*dfe94b16Srobert // Returns an (ordinal, inline addend) tuple used by dyld_chained_ptr_64_bind. 750*dfe94b16Srobert std::pair<uint32_t, uint8_t> getBinding(const Symbol *sym, 751*dfe94b16Srobert int64_t addend) const; 752*dfe94b16Srobert getLocations()753*dfe94b16Srobert const std::vector<Location> &getLocations() const { return locations; } 754*dfe94b16Srobert hasWeakBinding()755*dfe94b16Srobert bool hasWeakBinding() const { return hasWeakBind; } hasNonWeakDefinition()756*dfe94b16Srobert bool hasNonWeakDefinition() const { return hasNonWeakDef; } 757*dfe94b16Srobert 758*dfe94b16Srobert private: 759*dfe94b16Srobert // Location::offset initially stores the offset within an InputSection, but 760*dfe94b16Srobert // contains output segment offsets after finalizeContents(). 761*dfe94b16Srobert std::vector<Location> locations; 762*dfe94b16Srobert // (target symbol, addend) => import ordinal 763*dfe94b16Srobert llvm::MapVector<std::pair<const Symbol *, int64_t>, uint32_t> bindings; 764*dfe94b16Srobert 765*dfe94b16Srobert struct SegmentInfo { SegmentInfoSegmentInfo766*dfe94b16Srobert SegmentInfo(const OutputSegment *oseg) : oseg(oseg) {} 767*dfe94b16Srobert 768*dfe94b16Srobert const OutputSegment *oseg; 769*dfe94b16Srobert // (page index, fixup starts offset) 770*dfe94b16Srobert llvm::SmallVector<std::pair<uint16_t, uint16_t>> pageStarts; 771*dfe94b16Srobert 772*dfe94b16Srobert size_t getSize() const; 773*dfe94b16Srobert size_t writeTo(uint8_t *buf) const; 774*dfe94b16Srobert }; 775*dfe94b16Srobert llvm::SmallVector<SegmentInfo, 4> fixupSegments; 776*dfe94b16Srobert 777*dfe94b16Srobert size_t symtabSize = 0; 778*dfe94b16Srobert size_t size = 0; 779*dfe94b16Srobert 780*dfe94b16Srobert bool needsAddend = false; 781*dfe94b16Srobert bool needsLargeAddend = false; 782*dfe94b16Srobert bool hasWeakBind = false; 783*dfe94b16Srobert bool hasNonWeakDef = false; 784*dfe94b16Srobert llvm::MachO::ChainedImportFormat importFormat; 785*dfe94b16Srobert }; 786*dfe94b16Srobert 787*dfe94b16Srobert void writeChainedRebase(uint8_t *buf, uint64_t targetVA); 788*dfe94b16Srobert void writeChainedFixup(uint8_t *buf, const Symbol *sym, int64_t addend); 789*dfe94b16Srobert 790bb684c34Spatrick struct InStruct { 791*dfe94b16Srobert const uint8_t *bufferStart = nullptr; 7921cf9926bSpatrick MachHeaderSection *header = nullptr; 7931cf9926bSpatrick CStringSection *cStringSection = nullptr; 794*dfe94b16Srobert DeduplicatedCStringSection *objcMethnameSection = nullptr; 7951cf9926bSpatrick WordLiteralSection *wordLiteralSection = nullptr; 7961cf9926bSpatrick RebaseSection *rebase = nullptr; 797bb684c34Spatrick BindingSection *binding = nullptr; 7981cf9926bSpatrick WeakBindingSection *weakBinding = nullptr; 7991cf9926bSpatrick LazyBindingSection *lazyBinding = nullptr; 8001cf9926bSpatrick ExportSection *exports = nullptr; 801bb684c34Spatrick GotSection *got = nullptr; 8021cf9926bSpatrick TlvPointerSection *tlvPointers = nullptr; 803bb684c34Spatrick LazyPointerSection *lazyPointers = nullptr; 804bb684c34Spatrick StubsSection *stubs = nullptr; 805bb684c34Spatrick StubHelperSection *stubHelper = nullptr; 806*dfe94b16Srobert ObjCStubsSection *objcStubs = nullptr; 807*dfe94b16Srobert ConcatInputSection *objcSelrefs = nullptr; 8081cf9926bSpatrick UnwindInfoSection *unwindInfo = nullptr; 809*dfe94b16Srobert ObjCImageInfoSection *objCImageInfo = nullptr; 8101cf9926bSpatrick ConcatInputSection *imageLoaderCache = nullptr; 811*dfe94b16Srobert InitOffsetsSection *initOffsets = nullptr; 812*dfe94b16Srobert ChainedFixupsSection *chainedFixups = nullptr; 813bb684c34Spatrick }; 814bb684c34Spatrick 815bb684c34Spatrick extern InStruct in; 816bb684c34Spatrick extern std::vector<SyntheticSection *> syntheticSections; 817bb684c34Spatrick 8181cf9926bSpatrick void createSyntheticSymbols(); 8191cf9926bSpatrick 820*dfe94b16Srobert } // namespace lld::macho 821bb684c34Spatrick 822bb684c34Spatrick #endif 823