LLVM 20.0.0git
RuntimeDyld.h
Go to the documentation of this file.
1//===- RuntimeDyld.h - Run-time dynamic linker for MC-JIT -------*- 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// Interface for the runtime dynamic linker facilities of the MC-JIT.
10//
11//===----------------------------------------------------------------------===//
12
13#ifndef LLVM_EXECUTIONENGINE_RUNTIMEDYLD_H
14#define LLVM_EXECUTIONENGINE_RUNTIMEDYLD_H
15
17#include "llvm/ADT/STLExtras.h"
18#include "llvm/ADT/StringRef.h"
22#include "llvm/Support/Error.h"
23#include <algorithm>
24#include <cassert>
25#include <cstddef>
26#include <cstdint>
27#include <map>
28#include <memory>
29#include <string>
30#include <system_error>
31
32namespace llvm {
33
34namespace object {
35
36template <typename T> class OwningBinary;
37
38} // end namespace object
39
40/// Base class for errors originating in RuntimeDyld, e.g. missing relocation
41/// support.
42class RuntimeDyldError : public ErrorInfo<RuntimeDyldError> {
43public:
44 static char ID;
45
46 RuntimeDyldError(std::string ErrMsg) : ErrMsg(std::move(ErrMsg)) {}
47
48 void log(raw_ostream &OS) const override;
49 const std::string &getErrorMessage() const { return ErrMsg; }
50 std::error_code convertToErrorCode() const override;
51
52private:
53 std::string ErrMsg;
54};
55
56class RuntimeDyldImpl;
57
59public:
60 // Change the address associated with a section when resolving relocations.
61 // Any relocations already associated with the symbol will be re-resolved.
62 void reassignSectionAddress(unsigned SectionID, uint64_t Addr);
63
64 using NotifyStubEmittedFunction = std::function<void(
65 StringRef FileName, StringRef SectionName, StringRef SymbolName,
66 unsigned SectionID, uint32_t StubOffset)>;
67
68 /// Information about the loaded object.
70 friend class RuntimeDyldImpl;
71
72 public:
73 using ObjSectionToIDMap = std::map<object::SectionRef, unsigned>;
74
77
80
82 getSectionLoadAddress(const object::SectionRef &Sec) const override;
83
84 protected:
85 virtual void anchor();
86
89 };
90
91 /// Memory Management.
93 friend class RuntimeDyld;
94
95 public:
96 MemoryManager() = default;
97 virtual ~MemoryManager() = default;
98
99 /// Allocate a memory block of (at least) the given size suitable for
100 /// executable code. The SectionID is a unique identifier assigned by the
101 /// RuntimeDyld instance, and optionally recorded by the memory manager to
102 /// access a loaded section.
103 virtual uint8_t *allocateCodeSection(uintptr_t Size, unsigned Alignment,
104 unsigned SectionID,
106
107 /// Allocate a memory block of (at least) the given size suitable for data.
108 /// The SectionID is a unique identifier assigned by the JIT engine, and
109 /// optionally recorded by the memory manager to access a loaded section.
110 virtual uint8_t *allocateDataSection(uintptr_t Size, unsigned Alignment,
111 unsigned SectionID,
113 bool IsReadOnly) = 0;
114
115 /// An allocated TLS section
116 struct TLSSection {
117 /// The pointer to the initialization image
119 /// The TLS offset
120 intptr_t Offset;
121 };
122
123 /// Allocate a memory block of (at least) the given size to be used for
124 /// thread-local storage (TLS).
125 virtual TLSSection allocateTLSSection(uintptr_t Size, unsigned Alignment,
126 unsigned SectionID,
128
129 /// Inform the memory manager about the total amount of memory required to
130 /// allocate all sections to be loaded:
131 /// \p CodeSize - the total size of all code sections
132 /// \p DataSizeRO - the total size of all read-only data sections
133 /// \p DataSizeRW - the total size of all read-write data sections
134 ///
135 /// Note that by default the callback is disabled. To enable it
136 /// redefine the method needsToReserveAllocationSpace to return true.
137 virtual void reserveAllocationSpace(uintptr_t CodeSize, Align CodeAlign,
138 uintptr_t RODataSize, Align RODataAlign,
139 uintptr_t RWDataSize,
140 Align RWDataAlign) {}
141
142 /// Override to return true to enable the reserveAllocationSpace callback.
143 virtual bool needsToReserveAllocationSpace() { return false; }
144
145 /// Override to return false to tell LLVM no stub space will be needed.
146 /// This requires some guarantees depending on architecuture, but when
147 /// you know what you are doing it saves allocated space.
148 virtual bool allowStubAllocation() const { return true; }
149
150 /// Register the EH frames with the runtime so that c++ exceptions work.
151 ///
152 /// \p Addr parameter provides the local address of the EH frame section
153 /// data, while \p LoadAddr provides the address of the data in the target
154 /// address space. If the section has not been remapped (which will usually
155 /// be the case for local execution) these two values will be the same.
156 virtual void registerEHFrames(uint8_t *Addr, uint64_t LoadAddr,
157 size_t Size) = 0;
158 virtual void deregisterEHFrames() = 0;
159
160 /// This method is called when object loading is complete and section page
161 /// permissions can be applied. It is up to the memory manager implementation
162 /// to decide whether or not to act on this method. The memory manager will
163 /// typically allocate all sections as read-write and then apply specific
164 /// permissions when this method is called. Code sections cannot be executed
165 /// until this function has been called. In addition, any cache coherency
166 /// operations needed to reliably use the memory are also performed.
167 ///
168 /// Returns true if an error occurred, false otherwise.
169 virtual bool finalizeMemory(std::string *ErrMsg = nullptr) = 0;
170
171 /// This method is called after an object has been loaded into memory but
172 /// before relocations are applied to the loaded sections.
173 ///
174 /// Memory managers which are preparing code for execution in an external
175 /// address space can use this call to remap the section addresses for the
176 /// newly loaded object.
177 ///
178 /// For clients that do not need access to an ExecutionEngine instance this
179 /// method should be preferred to its cousin
180 /// MCJITMemoryManager::notifyObjectLoaded as this method is compatible with
181 /// ORC JIT stacks.
182 virtual void notifyObjectLoaded(RuntimeDyld &RTDyld,
183 const object::ObjectFile &Obj) {}
184
185 private:
186 virtual void anchor();
187
188 bool FinalizationLocked = false;
189 };
190
191 /// Construct a RuntimeDyld instance.
192 RuntimeDyld(MemoryManager &MemMgr, JITSymbolResolver &Resolver);
193 RuntimeDyld(const RuntimeDyld &) = delete;
196
197 /// Add the referenced object file to the list of objects to be loaded and
198 /// relocated.
199 std::unique_ptr<LoadedObjectInfo> loadObject(const object::ObjectFile &O);
200
201 /// Get the address of our local copy of the symbol. This may or may not
202 /// be the address used for relocation (clients can copy the data around
203 /// and resolve relocatons based on where they put it).
205
206 /// Get the section ID for the section containing the given symbol.
207 unsigned getSymbolSectionID(StringRef Name) const;
208
209 /// Get the target address and flags for the named symbol.
210 /// This address is the one used for relocation.
212
213 /// Returns a copy of the symbol table. This can be used by on-finalized
214 /// callbacks to extract the symbol table before throwing away the
215 /// RuntimeDyld instance. Because the map keys (StringRefs) are backed by
216 /// strings inside the RuntimeDyld instance, the map should be processed
217 /// before the RuntimeDyld instance is discarded.
218 std::map<StringRef, JITEvaluatedSymbol> getSymbolTable() const;
219
220 /// Resolve the relocations for all symbols we currently know about.
221 void resolveRelocations();
222
223 /// Map a section to its target address space value.
224 /// Map the address of a JIT section as returned from the memory manager
225 /// to the address in the target process as the running code will see it.
226 /// This is the address which will be used for relocation resolution.
227 void mapSectionAddress(const void *LocalAddress, uint64_t TargetAddress);
228
229 /// Returns the section's working memory.
230 StringRef getSectionContent(unsigned SectionID) const;
231
232 /// If the section was loaded, return the section's load address,
233 /// otherwise return std::nullopt.
234 uint64_t getSectionLoadAddress(unsigned SectionID) const;
235
236 /// Set the NotifyStubEmitted callback. This is used for debugging
237 /// purposes. A callback is made for each stub that is generated.
239 this->NotifyStubEmitted = std::move(NotifyStubEmitted);
240 }
241
242 /// Register any EH frame sections that have been loaded but not previously
243 /// registered with the memory manager. Note, RuntimeDyld is responsible
244 /// for identifying the EH frame and calling the memory manager with the
245 /// EH frame section data. However, the memory manager itself will handle
246 /// the actual target-specific EH frame registration.
247 void registerEHFrames();
248
249 void deregisterEHFrames();
250
251 bool hasError();
253
254 /// By default, only sections that are "required for execution" are passed to
255 /// the RTDyldMemoryManager, and other sections are discarded. Passing 'true'
256 /// to this method will cause RuntimeDyld to pass all sections to its
257 /// memory manager regardless of whether they are "required to execute" in the
258 /// usual sense. This is useful for inspecting metadata sections that may not
259 /// contain relocations, E.g. Debug info, stackmaps.
260 ///
261 /// Must be called before the first object file is loaded.
262 void setProcessAllSections(bool ProcessAllSections) {
263 assert(!Dyld && "setProcessAllSections must be called before loadObject.");
264 this->ProcessAllSections = ProcessAllSections;
265 }
266
267 /// Perform all actions needed to make the code owned by this RuntimeDyld
268 /// instance executable:
269 ///
270 /// 1) Apply relocations.
271 /// 2) Register EH frames.
272 /// 3) Update memory permissions*.
273 ///
274 /// * Finalization is potentially recursive**, and the 3rd step will only be
275 /// applied by the outermost call to finalize. This allows different
276 /// RuntimeDyld instances to share a memory manager without the innermost
277 /// finalization locking the memory and causing relocation fixup errors in
278 /// outer instances.
279 ///
280 /// ** Recursive finalization occurs when one RuntimeDyld instances needs the
281 /// address of a symbol owned by some other instance in order to apply
282 /// relocations.
283 ///
285
286private:
287 friend void jitLinkForORC(
290 bool ProcessAllSections,
292 std::map<StringRef, JITEvaluatedSymbol>)>
293 OnLoaded,
295 std::unique_ptr<LoadedObjectInfo>, Error)>
296 OnEmitted);
297
298 // RuntimeDyldImpl is the actual class. RuntimeDyld is just the public
299 // interface.
300 std::unique_ptr<RuntimeDyldImpl> Dyld;
301 MemoryManager &MemMgr;
303 bool ProcessAllSections;
304 NotifyStubEmittedFunction NotifyStubEmitted;
305};
306
307// Asynchronous JIT link for ORC.
308//
309// Warning: This API is experimental and probably should not be used by anyone
310// but ORC's RTDyldObjectLinkingLayer2. Internally it constructs a RuntimeDyld
311// instance and uses continuation passing to perform the fix-up and finalize
312// steps asynchronously.
316 bool ProcessAllSections,
319 std::map<StringRef, JITEvaluatedSymbol>)>
320 OnLoaded,
322 std::unique_ptr<RuntimeDyld::LoadedObjectInfo>, Error)>
323 OnEmitted);
324
325} // end namespace llvm
326
327#endif // LLVM_EXECUTIONENGINE_RUNTIMEDYLD_H
uint64_t Addr
std::string Name
uint64_t Size
This file provides a collection of function (or more generally, callable) type erasure utilities supp...
assert(ImpDefSCC.getReg()==AMDGPU::SCC &&ImpDefSCC.isDef())
This file contains some templates that are useful if you are working with the STL at all.
raw_pwrite_stream & OS
Base class for user error types.
Definition: Error.h:355
Lightweight error class with error context and mandatory checking.
Definition: Error.h:160
Represents a symbol that has been evaluated to an address already.
Definition: JITSymbol.h:229
Symbol resolution interface.
Definition: JITSymbol.h:371
An inferface for inquiring the load address of a loaded object file to be used by the DIContext imple...
Definition: DIContext.h:277
Interface for looking up the initializer for a variable name, used by Init::resolveReferences.
Definition: Record.h:2212
Base class for errors originating in RuntimeDyld, e.g.
Definition: RuntimeDyld.h:42
void log(raw_ostream &OS) const override
Print an error message to an output stream.
Definition: RuntimeDyld.cpp:57
const std::string & getErrorMessage() const
Definition: RuntimeDyld.h:49
std::error_code convertToErrorCode() const override
Convert this error to a std::error_code.
Definition: RuntimeDyld.cpp:61
RuntimeDyldError(std::string ErrMsg)
Definition: RuntimeDyld.h:46
Information about the loaded object.
Definition: RuntimeDyld.h:69
uint64_t getSectionLoadAddress(const object::SectionRef &Sec) const override
Obtain the Load Address of a section by SectionRef.
std::map< object::SectionRef, unsigned > ObjSectionToIDMap
Definition: RuntimeDyld.h:73
virtual object::OwningBinary< object::ObjectFile > getObjectForDebug(const object::ObjectFile &Obj) const =0
LoadedObjectInfo(RuntimeDyldImpl &RTDyld, ObjSectionToIDMap ObjSecToIDMap)
Definition: RuntimeDyld.h:75
virtual void reserveAllocationSpace(uintptr_t CodeSize, Align CodeAlign, uintptr_t RODataSize, Align RODataAlign, uintptr_t RWDataSize, Align RWDataAlign)
Inform the memory manager about the total amount of memory required to allocate all sections to be lo...
Definition: RuntimeDyld.h:137
virtual bool needsToReserveAllocationSpace()
Override to return true to enable the reserveAllocationSpace callback.
Definition: RuntimeDyld.h:143
virtual void notifyObjectLoaded(RuntimeDyld &RTDyld, const object::ObjectFile &Obj)
This method is called after an object has been loaded into memory but before relocations are applied ...
Definition: RuntimeDyld.h:182
virtual uint8_t * allocateDataSection(uintptr_t Size, unsigned Alignment, unsigned SectionID, StringRef SectionName, bool IsReadOnly)=0
Allocate a memory block of (at least) the given size suitable for data.
virtual TLSSection allocateTLSSection(uintptr_t Size, unsigned Alignment, unsigned SectionID, StringRef SectionName)
Allocate a memory block of (at least) the given size to be used for thread-local storage (TLS).
virtual ~MemoryManager()=default
virtual uint8_t * allocateCodeSection(uintptr_t Size, unsigned Alignment, unsigned SectionID, StringRef SectionName)=0
Allocate a memory block of (at least) the given size suitable for executable code.
virtual void deregisterEHFrames()=0
virtual bool finalizeMemory(std::string *ErrMsg=nullptr)=0
This method is called when object loading is complete and section page permissions can be applied.
virtual void registerEHFrames(uint8_t *Addr, uint64_t LoadAddr, size_t Size)=0
Register the EH frames with the runtime so that c++ exceptions work.
virtual bool allowStubAllocation() const
Override to return false to tell LLVM no stub space will be needed.
Definition: RuntimeDyld.h:148
RuntimeDyld(const RuntimeDyld &)=delete
void mapSectionAddress(const void *LocalAddress, uint64_t TargetAddress)
Map a section to its target address space value.
void setProcessAllSections(bool ProcessAllSections)
By default, only sections that are "required for execution" are passed to the RTDyldMemoryManager,...
Definition: RuntimeDyld.h:262
void reassignSectionAddress(unsigned SectionID, uint64_t Addr)
uint64_t getSectionLoadAddress(unsigned SectionID) const
If the section was loaded, return the section's load address, otherwise return std::nullopt.
void * getSymbolLocalAddress(StringRef Name) const
Get the address of our local copy of the symbol.
std::map< StringRef, JITEvaluatedSymbol > getSymbolTable() const
Returns a copy of the symbol table.
void resolveRelocations()
Resolve the relocations for all symbols we currently know about.
void finalizeWithMemoryManagerLocking()
Perform all actions needed to make the code owned by this RuntimeDyld instance executable:
void setNotifyStubEmitted(NotifyStubEmittedFunction NotifyStubEmitted)
Set the NotifyStubEmitted callback.
Definition: RuntimeDyld.h:238
void registerEHFrames()
Register any EH frame sections that have been loaded but not previously registered with the memory ma...
StringRef getSectionContent(unsigned SectionID) const
Returns the section's working memory.
JITEvaluatedSymbol getSymbol(StringRef Name) const
Get the target address and flags for the named symbol.
RuntimeDyld & operator=(const RuntimeDyld &)=delete
std::unique_ptr< LoadedObjectInfo > loadObject(const object::ObjectFile &O)
Add the referenced object file to the list of objects to be loaded and relocated.
StringRef getErrorString()
unsigned getSymbolSectionID(StringRef Name) const
Get the section ID for the section containing the given symbol.
std::function< void(StringRef FileName, StringRef SectionName, StringRef SymbolName, unsigned SectionID, uint32_t StubOffset)> NotifyStubEmittedFunction
Definition: RuntimeDyld.h:66
friend void jitLinkForORC(object::OwningBinary< object::ObjectFile > O, RuntimeDyld::MemoryManager &MemMgr, JITSymbolResolver &Resolver, bool ProcessAllSections, unique_function< Error(const object::ObjectFile &Obj, LoadedObjectInfo &, std::map< StringRef, JITEvaluatedSymbol >)> OnLoaded, unique_function< void(object::OwningBinary< object::ObjectFile > O, std::unique_ptr< LoadedObjectInfo >, Error)> OnEmitted)
StringRef - Represent a constant reference to a string, i.e.
Definition: StringRef.h:50
This class is the base class for all object file types.
Definition: ObjectFile.h:229
This is a value type class that represents a single section in the list of sections in the object fil...
Definition: ObjectFile.h:81
This class implements an extremely fast bulk output stream that can only output to a stream.
Definition: raw_ostream.h:52
unique_function is a type-erasing functor similar to std::function.
This is an optimization pass for GlobalISel generic memory operations.
Definition: AddressRanges.h:18
void jitLinkForORC(object::OwningBinary< object::ObjectFile > O, RuntimeDyld::MemoryManager &MemMgr, JITSymbolResolver &Resolver, bool ProcessAllSections, unique_function< Error(const object::ObjectFile &Obj, RuntimeDyld::LoadedObjectInfo &, std::map< StringRef, JITEvaluatedSymbol >)> OnLoaded, unique_function< void(object::OwningBinary< object::ObjectFile >, std::unique_ptr< RuntimeDyld::LoadedObjectInfo >, Error)> OnEmitted)
OutputIt move(R &&Range, OutputIt Out)
Provide wrappers to std::move which take ranges instead of having to pass begin/end explicitly.
Definition: STLExtras.h:1856
Implement std::hash so that hash_code can be used in STL containers.
Definition: BitVector.h:858
This struct is a compact representation of a valid (non-zero power of two) alignment.
Definition: Alignment.h:39
uint8_t * InitializationImage
The pointer to the initialization image.
Definition: RuntimeDyld.h:118