LLVM 22.0.0git
MachOLinkGraphBuilder.h
Go to the documentation of this file.
1//===----- MachOLinkGraphBuilder.h - MachO LinkGraph builder ----*- 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-exception
6//
7//===----------------------------------------------------------------------===//
8//
9// Generic MachO LinkGraph building code.
10//
11//===----------------------------------------------------------------------===//
12
13#ifndef LIB_EXECUTIONENGINE_JITLINK_MACHOLINKGRAPHBUILDER_H
14#define LIB_EXECUTIONENGINE_JITLINK_MACHOLINKGRAPHBUILDER_H
15
16#include "llvm/ADT/DenseMap.h"
17#include "llvm/ADT/StringMap.h"
19#include "llvm/Object/MachO.h"
20
21#include "EHFrameSupportImpl.h"
22#include "JITLinkGeneric.h"
23
24namespace llvm {
25namespace jitlink {
26
28public:
31
32protected:
33
34 struct NormalizedSymbol {
36
37 private:
38 NormalizedSymbol(std::optional<StringRef> Name, uint64_t Value,
40 Scope S)
42 S(S) {
43 assert((!Name || !Name->empty()) && "Name must be none or non-empty");
44 }
45
46 public:
47 NormalizedSymbol(const NormalizedSymbol &) = delete;
48 NormalizedSymbol &operator=(const NormalizedSymbol &) = delete;
49 NormalizedSymbol(NormalizedSymbol &&) = delete;
50 NormalizedSymbol &operator=(NormalizedSymbol &&) = delete;
51
52 std::optional<StringRef> Name;
59 Symbol *GraphSymbol = nullptr;
60 };
61
62 // Normalized section representation. Section and segment names are guaranteed
63 // to be null-terminated, hence the extra bytes on SegName and SectName.
64 class NormalizedSection {
66
67 private:
68 NormalizedSection() = default;
69
70 public:
71 char SectName[17];
72 char SegName[17];
77 const char *Data = nullptr;
79 std::map<orc::ExecutorAddr, Symbol *> CanonicalSymbols;
80 };
81
82 using SectionParserFunction = std::function<Error(NormalizedSection &S)>;
83
85 std::shared_ptr<orc::SymbolStringPool> SSP, Triple TT,
86 SubtargetFeatures Features,
88 LinkGraph &getGraph() const { return *G; }
89
90 const object::MachOObjectFile &getObject() const { return Obj; }
91
94
95 virtual Error addRelocations() = 0;
96
97 /// Create a symbol.
98 template <typename... ArgTs>
100 NormalizedSymbol *Sym = reinterpret_cast<NormalizedSymbol *>(
101 Allocator.Allocate<NormalizedSymbol>());
102 new (Sym) NormalizedSymbol(std::forward<ArgTs>(Args)...);
103 return *Sym;
104 }
105
106 /// Index is zero-based (MachO section indexes are usually one-based) and
107 /// assumed to be in-range. Client is responsible for checking.
109 auto I = IndexToSection.find(Index);
110 assert(I != IndexToSection.end() && "No section recorded at index");
111 return I->second;
112 }
113
114 /// Try to get the section at the given index. Will return an error if the
115 /// given index is out of range, or if no section has been added for the given
116 /// index.
118 auto I = IndexToSection.find(Index);
119 if (I == IndexToSection.end())
120 return make_error<JITLinkError>("No section recorded for index " +
121 formatv("{0:d}", Index));
122 return I->second;
123 }
124
125 /// Try to get the symbol at the given index. Will return an error if the
126 /// given index is out of range, or if no symbol has been added for the given
127 /// index.
129 auto I = IndexToSymbol.find(Index);
130 if (I == IndexToSymbol.end())
131 return make_error<JITLinkError>("No symbol at index " +
132 formatv("{0:d}", Index));
133 assert(I->second && "Null symbol at index");
134 return *I->second;
135 }
136
137 /// Returns the symbol with the highest address not greater than the search
138 /// address, or null if no such symbol exists.
141 auto I = NSec.CanonicalSymbols.upper_bound(Address);
142 if (I == NSec.CanonicalSymbols.begin())
143 return nullptr;
144 return std::prev(I)->second;
145 }
146
147 /// Returns the symbol with the highest address not greater than the search
148 /// address, or an error if no such symbol exists.
151 auto *Sym = getSymbolByAddress(NSec, Address);
152 if (Sym)
153 if (Address <= Sym->getAddress() + Sym->getSize())
154 return *Sym;
155 return make_error<JITLinkError>("No symbol covering address " +
156 formatv("{0:x16}", Address));
157 }
158
160 static Scope getScope(StringRef Name, uint8_t Type);
161 static bool isAltEntry(const NormalizedSymbol &NSym);
162
163 static bool isDebugSection(const NormalizedSection &NSec);
164 static bool isZeroFillSection(const NormalizedSection &NSec);
165
171 RI.r_address = ARI.r_word0;
172 RI.r_symbolnum = ARI.r_word1 & 0xffffff;
173 RI.r_pcrel = (ARI.r_word1 >> 24) & 1;
174 RI.r_length = (ARI.r_word1 >> 25) & 3;
175 RI.r_extern = (ARI.r_word1 >> 27) & 1;
176 RI.r_type = (ARI.r_word1 >> 28);
177 return RI;
178 }
179
180private:
181 static unsigned getPointerSize(const object::MachOObjectFile &Obj);
182 static llvm::endianness getEndianness(const object::MachOObjectFile &Obj);
183
184 void setCanonicalSymbol(NormalizedSection &NSec, Symbol &Sym) {
185 auto *&CanonicalSymEntry = NSec.CanonicalSymbols[Sym.getAddress()];
186 // There should be no symbol at this address, or, if there is,
187 // it should be a zero-sized symbol from an empty section (which
188 // we can safely override).
189 assert((!CanonicalSymEntry || CanonicalSymEntry->getSize() == 0) &&
190 "Duplicate canonical symbol at address");
191 CanonicalSymEntry = &Sym;
192 }
193
194 Section &getCommonSection();
195 void addSectionStartSymAndBlock(unsigned SecIndex, Section &GraphSec,
196 orc::ExecutorAddr Address, const char *Data,
198 uint32_t Alignment, bool IsLive);
199
200 Error createNormalizedSections();
201 Error createNormalizedSymbols();
202
203 /// Create graph blocks and symbols for externals, absolutes, commons and
204 /// all defined symbols in sections without custom parsers.
205 Error graphifyRegularSymbols();
206
207 /// Create and return a graph symbol for the given normalized symbol.
208 ///
209 /// NSym's GraphSymbol member will be updated to point at the newly created
210 /// symbol.
211 Symbol &createStandardGraphSymbol(NormalizedSymbol &Sym, Block &B,
212 size_t Size, bool IsText,
213 bool IsNoDeadStrip, bool IsCanonical);
214
215 /// Create graph blocks and symbols for all sections.
216 Error graphifySectionsWithCustomParsers();
217
218 /// Graphify cstring section.
219 Error graphifyCStringSection(NormalizedSection &NSec,
220 std::vector<NormalizedSymbol *> NSyms);
221
222 // Put the BumpPtrAllocator first so that we don't free any of the underlying
223 // memory until the Symbol/Addressable destructors have been run.
225
226 const object::MachOObjectFile &Obj;
227 std::unique_ptr<LinkGraph> G;
228
229 bool SubsectionsViaSymbols = false;
231 Section *CommonSection = nullptr;
232
234 StringMap<SectionParserFunction> CustomSectionParserFunctions;
235};
236
237} // end namespace jitlink
238} // end namespace llvm
239
240#endif // LIB_EXECUTIONENGINE_JITLINK_MACHOLINKGRAPHBUILDER_H
assert(UImm &&(UImm !=~static_cast< T >(0)) &&"Invalid immediate!")
This file defines the StringMap class.
static GCRegistry::Add< OcamlGC > B("ocaml", "ocaml 3.10-compatible GC")
static std::optional< TypeSize > getPointerSize(const Value *V, const DataLayout &DL, const TargetLibraryInfo &TLI, const Function *F)
This file defines the DenseMap class.
#define I(x, y, z)
Definition MD5.cpp:57
#define G(x, y, z)
Definition MD5.cpp:55
Basic Register Allocator
Lightweight error class with error context and mandatory checking.
Definition Error.h:159
Tagged union holding either a T or a Error.
Definition Error.h:485
StringMap - This is an unconventional map that is specialized for handling keys that are "strings",...
Definition StringMap.h:133
StringRef - Represent a constant reference to a string, i.e.
Definition StringRef.h:55
Manages the enabling and disabling of subtarget specific features.
Triple - Helper class for working with autoconf configuration names.
Definition Triple.h:47
The instances of the Type class are immutable: once they are created, they are never changed.
Definition Type.h:45
MachO::any_relocation_info getRelocation(DataRefImpl Rel) const
DataRefImpl getRawDataRefImpl() const
Definition ObjectFile.h:641
Represents an address in the executor process.
content_iterator< RelocationRef > relocation_iterator
Definition ObjectFile.h:79
uint64_t ExecutorAddrDiff
This is an optimization pass for GlobalISel generic memory operations.
Op::Description Desc
auto formatv(bool Validate, const char *Fmt, Ts &&...Vals)
Error make_error(ArgTs &&... Args)
Make a Error instance representing failure using the given error info type.
Definition Error.h:340
FunctionAddr VTableAddr uintptr_t uintptr_t Data
Definition InstrProf.h:189
BumpPtrAllocatorImpl<> BumpPtrAllocator
The standard BumpPtrAllocator which just uses the default template parameters.
Definition Allocator.h:383
endianness
Definition bit.h:71