Book a Demo!
CoCalc Logo Icon
StoreFeaturesDocsShareSupportNewsAboutPoliciesSign UpSign In
freebsd
GitHub Repository: freebsd/freebsd-src
Path: blob/main/contrib/llvm-project/llvm/lib/ExecutionEngine/Orc/LLJIT.cpp
35266 views
1
//===--------- LLJIT.cpp - An ORC-based JIT for compiling LLVM IR ---------===//
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
#include "llvm/ExecutionEngine/Orc/LLJIT.h"
10
#include "llvm/ExecutionEngine/JITLink/EHFrameSupport.h"
11
#include "llvm/ExecutionEngine/JITLink/JITLinkMemoryManager.h"
12
#include "llvm/ExecutionEngine/Orc/COFFPlatform.h"
13
#include "llvm/ExecutionEngine/Orc/ELFNixPlatform.h"
14
#include "llvm/ExecutionEngine/Orc/EPCDynamicLibrarySearchGenerator.h"
15
#include "llvm/ExecutionEngine/Orc/EPCEHFrameRegistrar.h"
16
#include "llvm/ExecutionEngine/Orc/ExecutorProcessControl.h"
17
#include "llvm/ExecutionEngine/Orc/MachOPlatform.h"
18
#include "llvm/ExecutionEngine/Orc/ObjectLinkingLayer.h"
19
#include "llvm/ExecutionEngine/Orc/ObjectTransformLayer.h"
20
#include "llvm/ExecutionEngine/Orc/RTDyldObjectLinkingLayer.h"
21
#include "llvm/ExecutionEngine/Orc/Shared/OrcError.h"
22
#include "llvm/ExecutionEngine/Orc/TargetProcess/RegisterEHFrames.h"
23
#include "llvm/ExecutionEngine/SectionMemoryManager.h"
24
#include "llvm/IR/GlobalVariable.h"
25
#include "llvm/IR/IRBuilder.h"
26
#include "llvm/IR/Mangler.h"
27
#include "llvm/IR/Module.h"
28
#include "llvm/Support/DynamicLibrary.h"
29
30
#define DEBUG_TYPE "orc"
31
32
using namespace llvm;
33
using namespace llvm::orc;
34
35
namespace {
36
37
/// Adds helper function decls and wrapper functions that call the helper with
38
/// some additional prefix arguments.
39
///
40
/// E.g. For wrapper "foo" with type i8(i8, i64), helper "bar", and prefix
41
/// args i32 4 and i16 12345, this function will add:
42
///
43
/// declare i8 @bar(i32, i16, i8, i64)
44
///
45
/// define i8 @foo(i8, i64) {
46
/// entry:
47
/// %2 = call i8 @bar(i32 4, i16 12345, i8 %0, i64 %1)
48
/// ret i8 %2
49
/// }
50
///
51
Function *addHelperAndWrapper(Module &M, StringRef WrapperName,
52
FunctionType *WrapperFnType,
53
GlobalValue::VisibilityTypes WrapperVisibility,
54
StringRef HelperName,
55
ArrayRef<Value *> HelperPrefixArgs) {
56
std::vector<Type *> HelperArgTypes;
57
for (auto *Arg : HelperPrefixArgs)
58
HelperArgTypes.push_back(Arg->getType());
59
for (auto *T : WrapperFnType->params())
60
HelperArgTypes.push_back(T);
61
auto *HelperFnType =
62
FunctionType::get(WrapperFnType->getReturnType(), HelperArgTypes, false);
63
auto *HelperFn = Function::Create(HelperFnType, GlobalValue::ExternalLinkage,
64
HelperName, M);
65
66
auto *WrapperFn = Function::Create(
67
WrapperFnType, GlobalValue::ExternalLinkage, WrapperName, M);
68
WrapperFn->setVisibility(WrapperVisibility);
69
70
auto *EntryBlock = BasicBlock::Create(M.getContext(), "entry", WrapperFn);
71
IRBuilder<> IB(EntryBlock);
72
73
std::vector<Value *> HelperArgs;
74
for (auto *Arg : HelperPrefixArgs)
75
HelperArgs.push_back(Arg);
76
for (auto &Arg : WrapperFn->args())
77
HelperArgs.push_back(&Arg);
78
auto *HelperResult = IB.CreateCall(HelperFn, HelperArgs);
79
if (HelperFn->getReturnType()->isVoidTy())
80
IB.CreateRetVoid();
81
else
82
IB.CreateRet(HelperResult);
83
84
return WrapperFn;
85
}
86
87
class GenericLLVMIRPlatformSupport;
88
89
/// orc::Platform component of Generic LLVM IR Platform support.
90
/// Just forwards calls to the GenericLLVMIRPlatformSupport class below.
91
class GenericLLVMIRPlatform : public Platform {
92
public:
93
GenericLLVMIRPlatform(GenericLLVMIRPlatformSupport &S) : S(S) {}
94
Error setupJITDylib(JITDylib &JD) override;
95
Error teardownJITDylib(JITDylib &JD) override;
96
Error notifyAdding(ResourceTracker &RT,
97
const MaterializationUnit &MU) override;
98
Error notifyRemoving(ResourceTracker &RT) override {
99
// Noop -- Nothing to do (yet).
100
return Error::success();
101
}
102
103
private:
104
GenericLLVMIRPlatformSupport &S;
105
};
106
107
/// This transform parses llvm.global_ctors to produce a single initialization
108
/// function for the module, records the function, then deletes
109
/// llvm.global_ctors.
110
class GlobalCtorDtorScraper {
111
public:
112
GlobalCtorDtorScraper(GenericLLVMIRPlatformSupport &PS,
113
StringRef InitFunctionPrefix,
114
StringRef DeInitFunctionPrefix)
115
: PS(PS), InitFunctionPrefix(InitFunctionPrefix),
116
DeInitFunctionPrefix(DeInitFunctionPrefix) {}
117
Expected<ThreadSafeModule> operator()(ThreadSafeModule TSM,
118
MaterializationResponsibility &R);
119
120
private:
121
GenericLLVMIRPlatformSupport &PS;
122
StringRef InitFunctionPrefix;
123
StringRef DeInitFunctionPrefix;
124
};
125
126
/// Generic IR Platform Support
127
///
128
/// Scrapes llvm.global_ctors and llvm.global_dtors and replaces them with
129
/// specially named 'init' and 'deinit'. Injects definitions / interposes for
130
/// some runtime API, including __cxa_atexit, dlopen, and dlclose.
131
class GenericLLVMIRPlatformSupport : public LLJIT::PlatformSupport {
132
public:
133
GenericLLVMIRPlatformSupport(LLJIT &J, JITDylib &PlatformJD)
134
: J(J), InitFunctionPrefix(J.mangle("__orc_init_func.")),
135
DeInitFunctionPrefix(J.mangle("__orc_deinit_func.")) {
136
137
getExecutionSession().setPlatform(
138
std::make_unique<GenericLLVMIRPlatform>(*this));
139
140
setInitTransform(J, GlobalCtorDtorScraper(*this, InitFunctionPrefix,
141
DeInitFunctionPrefix));
142
143
SymbolMap StdInterposes;
144
145
StdInterposes[J.mangleAndIntern("__lljit.platform_support_instance")] = {
146
ExecutorAddr::fromPtr(this), JITSymbolFlags::Exported};
147
StdInterposes[J.mangleAndIntern("__lljit.cxa_atexit_helper")] = {
148
ExecutorAddr::fromPtr(registerCxaAtExitHelper), JITSymbolFlags()};
149
150
cantFail(PlatformJD.define(absoluteSymbols(std::move(StdInterposes))));
151
cantFail(setupJITDylib(PlatformJD));
152
cantFail(J.addIRModule(PlatformJD, createPlatformRuntimeModule()));
153
}
154
155
ExecutionSession &getExecutionSession() { return J.getExecutionSession(); }
156
157
/// Adds a module that defines the __dso_handle global.
158
Error setupJITDylib(JITDylib &JD) {
159
160
// Add per-jitdylib standard interposes.
161
SymbolMap PerJDInterposes;
162
PerJDInterposes[J.mangleAndIntern("__lljit.run_atexits_helper")] = {
163
ExecutorAddr::fromPtr(runAtExitsHelper), JITSymbolFlags()};
164
PerJDInterposes[J.mangleAndIntern("__lljit.atexit_helper")] = {
165
ExecutorAddr::fromPtr(registerAtExitHelper), JITSymbolFlags()};
166
cantFail(JD.define(absoluteSymbols(std::move(PerJDInterposes))));
167
168
auto Ctx = std::make_unique<LLVMContext>();
169
auto M = std::make_unique<Module>("__standard_lib", *Ctx);
170
M->setDataLayout(J.getDataLayout());
171
172
auto *Int64Ty = Type::getInt64Ty(*Ctx);
173
auto *DSOHandle = new GlobalVariable(
174
*M, Int64Ty, true, GlobalValue::ExternalLinkage,
175
ConstantInt::get(Int64Ty, reinterpret_cast<uintptr_t>(&JD)),
176
"__dso_handle");
177
DSOHandle->setVisibility(GlobalValue::DefaultVisibility);
178
DSOHandle->setInitializer(
179
ConstantInt::get(Int64Ty, ExecutorAddr::fromPtr(&JD).getValue()));
180
181
auto *GenericIRPlatformSupportTy =
182
StructType::create(*Ctx, "lljit.GenericLLJITIRPlatformSupport");
183
184
auto *PlatformInstanceDecl = new GlobalVariable(
185
*M, GenericIRPlatformSupportTy, true, GlobalValue::ExternalLinkage,
186
nullptr, "__lljit.platform_support_instance");
187
188
auto *VoidTy = Type::getVoidTy(*Ctx);
189
addHelperAndWrapper(
190
*M, "__lljit_run_atexits", FunctionType::get(VoidTy, {}, false),
191
GlobalValue::HiddenVisibility, "__lljit.run_atexits_helper",
192
{PlatformInstanceDecl, DSOHandle});
193
194
auto *IntTy = Type::getIntNTy(*Ctx, sizeof(int) * CHAR_BIT);
195
auto *AtExitCallbackTy = FunctionType::get(VoidTy, {}, false);
196
auto *AtExitCallbackPtrTy = PointerType::getUnqual(AtExitCallbackTy);
197
addHelperAndWrapper(*M, "atexit",
198
FunctionType::get(IntTy, {AtExitCallbackPtrTy}, false),
199
GlobalValue::HiddenVisibility, "__lljit.atexit_helper",
200
{PlatformInstanceDecl, DSOHandle});
201
202
return J.addIRModule(JD, ThreadSafeModule(std::move(M), std::move(Ctx)));
203
}
204
205
Error notifyAdding(ResourceTracker &RT, const MaterializationUnit &MU) {
206
auto &JD = RT.getJITDylib();
207
if (auto &InitSym = MU.getInitializerSymbol())
208
InitSymbols[&JD].add(InitSym, SymbolLookupFlags::WeaklyReferencedSymbol);
209
else {
210
// If there's no identified init symbol attached, but there is a symbol
211
// with the GenericIRPlatform::InitFunctionPrefix, then treat that as
212
// an init function. Add the symbol to both the InitSymbols map (which
213
// will trigger a lookup to materialize the module) and the InitFunctions
214
// map (which holds the names of the symbols to execute).
215
for (auto &KV : MU.getSymbols())
216
if ((*KV.first).starts_with(InitFunctionPrefix)) {
217
InitSymbols[&JD].add(KV.first,
218
SymbolLookupFlags::WeaklyReferencedSymbol);
219
InitFunctions[&JD].add(KV.first);
220
} else if ((*KV.first).starts_with(DeInitFunctionPrefix)) {
221
DeInitFunctions[&JD].add(KV.first);
222
}
223
}
224
return Error::success();
225
}
226
227
Error initialize(JITDylib &JD) override {
228
LLVM_DEBUG({
229
dbgs() << "GenericLLVMIRPlatformSupport getting initializers to run\n";
230
});
231
if (auto Initializers = getInitializers(JD)) {
232
LLVM_DEBUG(
233
{ dbgs() << "GenericLLVMIRPlatformSupport running initializers\n"; });
234
for (auto InitFnAddr : *Initializers) {
235
LLVM_DEBUG({
236
dbgs() << " Running init " << formatv("{0:x16}", InitFnAddr)
237
<< "...\n";
238
});
239
auto *InitFn = InitFnAddr.toPtr<void (*)()>();
240
InitFn();
241
}
242
} else
243
return Initializers.takeError();
244
return Error::success();
245
}
246
247
Error deinitialize(JITDylib &JD) override {
248
LLVM_DEBUG({
249
dbgs() << "GenericLLVMIRPlatformSupport getting deinitializers to run\n";
250
});
251
if (auto Deinitializers = getDeinitializers(JD)) {
252
LLVM_DEBUG({
253
dbgs() << "GenericLLVMIRPlatformSupport running deinitializers\n";
254
});
255
for (auto DeinitFnAddr : *Deinitializers) {
256
LLVM_DEBUG({
257
dbgs() << " Running deinit " << formatv("{0:x16}", DeinitFnAddr)
258
<< "...\n";
259
});
260
auto *DeinitFn = DeinitFnAddr.toPtr<void (*)()>();
261
DeinitFn();
262
}
263
} else
264
return Deinitializers.takeError();
265
266
return Error::success();
267
}
268
269
void registerInitFunc(JITDylib &JD, SymbolStringPtr InitName) {
270
getExecutionSession().runSessionLocked([&]() {
271
InitFunctions[&JD].add(InitName);
272
});
273
}
274
275
void registerDeInitFunc(JITDylib &JD, SymbolStringPtr DeInitName) {
276
getExecutionSession().runSessionLocked(
277
[&]() { DeInitFunctions[&JD].add(DeInitName); });
278
}
279
280
private:
281
Expected<std::vector<ExecutorAddr>> getInitializers(JITDylib &JD) {
282
if (auto Err = issueInitLookups(JD))
283
return std::move(Err);
284
285
DenseMap<JITDylib *, SymbolLookupSet> LookupSymbols;
286
std::vector<JITDylibSP> DFSLinkOrder;
287
288
if (auto Err = getExecutionSession().runSessionLocked([&]() -> Error {
289
if (auto DFSLinkOrderOrErr = JD.getDFSLinkOrder())
290
DFSLinkOrder = std::move(*DFSLinkOrderOrErr);
291
else
292
return DFSLinkOrderOrErr.takeError();
293
294
for (auto &NextJD : DFSLinkOrder) {
295
auto IFItr = InitFunctions.find(NextJD.get());
296
if (IFItr != InitFunctions.end()) {
297
LookupSymbols[NextJD.get()] = std::move(IFItr->second);
298
InitFunctions.erase(IFItr);
299
}
300
}
301
return Error::success();
302
}))
303
return std::move(Err);
304
305
LLVM_DEBUG({
306
dbgs() << "JITDylib init order is [ ";
307
for (auto &JD : llvm::reverse(DFSLinkOrder))
308
dbgs() << "\"" << JD->getName() << "\" ";
309
dbgs() << "]\n";
310
dbgs() << "Looking up init functions:\n";
311
for (auto &KV : LookupSymbols)
312
dbgs() << " \"" << KV.first->getName() << "\": " << KV.second << "\n";
313
});
314
315
auto &ES = getExecutionSession();
316
auto LookupResult = Platform::lookupInitSymbols(ES, LookupSymbols);
317
318
if (!LookupResult)
319
return LookupResult.takeError();
320
321
std::vector<ExecutorAddr> Initializers;
322
while (!DFSLinkOrder.empty()) {
323
auto &NextJD = *DFSLinkOrder.back();
324
DFSLinkOrder.pop_back();
325
auto InitsItr = LookupResult->find(&NextJD);
326
if (InitsItr == LookupResult->end())
327
continue;
328
for (auto &KV : InitsItr->second)
329
Initializers.push_back(KV.second.getAddress());
330
}
331
332
return Initializers;
333
}
334
335
Expected<std::vector<ExecutorAddr>> getDeinitializers(JITDylib &JD) {
336
auto &ES = getExecutionSession();
337
338
auto LLJITRunAtExits = J.mangleAndIntern("__lljit_run_atexits");
339
340
DenseMap<JITDylib *, SymbolLookupSet> LookupSymbols;
341
std::vector<JITDylibSP> DFSLinkOrder;
342
343
if (auto Err = ES.runSessionLocked([&]() -> Error {
344
if (auto DFSLinkOrderOrErr = JD.getDFSLinkOrder())
345
DFSLinkOrder = std::move(*DFSLinkOrderOrErr);
346
else
347
return DFSLinkOrderOrErr.takeError();
348
349
for (auto &NextJD : DFSLinkOrder) {
350
auto &JDLookupSymbols = LookupSymbols[NextJD.get()];
351
auto DIFItr = DeInitFunctions.find(NextJD.get());
352
if (DIFItr != DeInitFunctions.end()) {
353
LookupSymbols[NextJD.get()] = std::move(DIFItr->second);
354
DeInitFunctions.erase(DIFItr);
355
}
356
JDLookupSymbols.add(LLJITRunAtExits,
357
SymbolLookupFlags::WeaklyReferencedSymbol);
358
}
359
return Error::success();
360
}))
361
return std::move(Err);
362
363
LLVM_DEBUG({
364
dbgs() << "JITDylib deinit order is [ ";
365
for (auto &JD : DFSLinkOrder)
366
dbgs() << "\"" << JD->getName() << "\" ";
367
dbgs() << "]\n";
368
dbgs() << "Looking up deinit functions:\n";
369
for (auto &KV : LookupSymbols)
370
dbgs() << " \"" << KV.first->getName() << "\": " << KV.second << "\n";
371
});
372
373
auto LookupResult = Platform::lookupInitSymbols(ES, LookupSymbols);
374
375
if (!LookupResult)
376
return LookupResult.takeError();
377
378
std::vector<ExecutorAddr> DeInitializers;
379
for (auto &NextJD : DFSLinkOrder) {
380
auto DeInitsItr = LookupResult->find(NextJD.get());
381
assert(DeInitsItr != LookupResult->end() &&
382
"Every JD should have at least __lljit_run_atexits");
383
384
auto RunAtExitsItr = DeInitsItr->second.find(LLJITRunAtExits);
385
if (RunAtExitsItr != DeInitsItr->second.end())
386
DeInitializers.push_back(RunAtExitsItr->second.getAddress());
387
388
for (auto &KV : DeInitsItr->second)
389
if (KV.first != LLJITRunAtExits)
390
DeInitializers.push_back(KV.second.getAddress());
391
}
392
393
return DeInitializers;
394
}
395
396
/// Issue lookups for all init symbols required to initialize JD (and any
397
/// JITDylibs that it depends on).
398
Error issueInitLookups(JITDylib &JD) {
399
DenseMap<JITDylib *, SymbolLookupSet> RequiredInitSymbols;
400
std::vector<JITDylibSP> DFSLinkOrder;
401
402
if (auto Err = getExecutionSession().runSessionLocked([&]() -> Error {
403
if (auto DFSLinkOrderOrErr = JD.getDFSLinkOrder())
404
DFSLinkOrder = std::move(*DFSLinkOrderOrErr);
405
else
406
return DFSLinkOrderOrErr.takeError();
407
408
for (auto &NextJD : DFSLinkOrder) {
409
auto ISItr = InitSymbols.find(NextJD.get());
410
if (ISItr != InitSymbols.end()) {
411
RequiredInitSymbols[NextJD.get()] = std::move(ISItr->second);
412
InitSymbols.erase(ISItr);
413
}
414
}
415
return Error::success();
416
}))
417
return Err;
418
419
return Platform::lookupInitSymbols(getExecutionSession(),
420
RequiredInitSymbols)
421
.takeError();
422
}
423
424
static void registerCxaAtExitHelper(void *Self, void (*F)(void *), void *Ctx,
425
void *DSOHandle) {
426
LLVM_DEBUG({
427
dbgs() << "Registering cxa atexit function " << (void *)F << " for JD "
428
<< (*static_cast<JITDylib **>(DSOHandle))->getName() << "\n";
429
});
430
static_cast<GenericLLVMIRPlatformSupport *>(Self)->AtExitMgr.registerAtExit(
431
F, Ctx, DSOHandle);
432
}
433
434
static void registerAtExitHelper(void *Self, void *DSOHandle, void (*F)()) {
435
LLVM_DEBUG({
436
dbgs() << "Registering atexit function " << (void *)F << " for JD "
437
<< (*static_cast<JITDylib **>(DSOHandle))->getName() << "\n";
438
});
439
static_cast<GenericLLVMIRPlatformSupport *>(Self)->AtExitMgr.registerAtExit(
440
reinterpret_cast<void (*)(void *)>(F), nullptr, DSOHandle);
441
}
442
443
static void runAtExitsHelper(void *Self, void *DSOHandle) {
444
LLVM_DEBUG({
445
dbgs() << "Running atexit functions for JD "
446
<< (*static_cast<JITDylib **>(DSOHandle))->getName() << "\n";
447
});
448
static_cast<GenericLLVMIRPlatformSupport *>(Self)->AtExitMgr.runAtExits(
449
DSOHandle);
450
}
451
452
// Constructs an LLVM IR module containing platform runtime globals,
453
// functions, and interposes.
454
ThreadSafeModule createPlatformRuntimeModule() {
455
auto Ctx = std::make_unique<LLVMContext>();
456
auto M = std::make_unique<Module>("__standard_lib", *Ctx);
457
M->setDataLayout(J.getDataLayout());
458
459
auto *GenericIRPlatformSupportTy =
460
StructType::create(*Ctx, "lljit.GenericLLJITIRPlatformSupport");
461
462
auto *PlatformInstanceDecl = new GlobalVariable(
463
*M, GenericIRPlatformSupportTy, true, GlobalValue::ExternalLinkage,
464
nullptr, "__lljit.platform_support_instance");
465
466
auto *Int8Ty = Type::getInt8Ty(*Ctx);
467
auto *IntTy = Type::getIntNTy(*Ctx, sizeof(int) * CHAR_BIT);
468
auto *VoidTy = Type::getVoidTy(*Ctx);
469
auto *BytePtrTy = PointerType::getUnqual(Int8Ty);
470
auto *CxaAtExitCallbackTy = FunctionType::get(VoidTy, {BytePtrTy}, false);
471
auto *CxaAtExitCallbackPtrTy = PointerType::getUnqual(CxaAtExitCallbackTy);
472
473
addHelperAndWrapper(
474
*M, "__cxa_atexit",
475
FunctionType::get(IntTy, {CxaAtExitCallbackPtrTy, BytePtrTy, BytePtrTy},
476
false),
477
GlobalValue::DefaultVisibility, "__lljit.cxa_atexit_helper",
478
{PlatformInstanceDecl});
479
480
return ThreadSafeModule(std::move(M), std::move(Ctx));
481
}
482
483
LLJIT &J;
484
std::string InitFunctionPrefix;
485
std::string DeInitFunctionPrefix;
486
DenseMap<JITDylib *, SymbolLookupSet> InitSymbols;
487
DenseMap<JITDylib *, SymbolLookupSet> InitFunctions;
488
DenseMap<JITDylib *, SymbolLookupSet> DeInitFunctions;
489
ItaniumCXAAtExitSupport AtExitMgr;
490
};
491
492
Error GenericLLVMIRPlatform::setupJITDylib(JITDylib &JD) {
493
return S.setupJITDylib(JD);
494
}
495
496
Error GenericLLVMIRPlatform::teardownJITDylib(JITDylib &JD) {
497
return Error::success();
498
}
499
500
Error GenericLLVMIRPlatform::notifyAdding(ResourceTracker &RT,
501
const MaterializationUnit &MU) {
502
return S.notifyAdding(RT, MU);
503
}
504
505
Expected<ThreadSafeModule>
506
GlobalCtorDtorScraper::operator()(ThreadSafeModule TSM,
507
MaterializationResponsibility &R) {
508
auto Err = TSM.withModuleDo([&](Module &M) -> Error {
509
auto &Ctx = M.getContext();
510
auto *GlobalCtors = M.getNamedGlobal("llvm.global_ctors");
511
auto *GlobalDtors = M.getNamedGlobal("llvm.global_dtors");
512
513
auto RegisterCOrDtors = [&](GlobalVariable *GlobalCOrDtors,
514
bool isCtor) -> Error {
515
// If there's no llvm.global_c/dtor or it's just a decl then skip.
516
if (!GlobalCOrDtors || GlobalCOrDtors->isDeclaration())
517
return Error::success();
518
std::string InitOrDeInitFunctionName;
519
if (isCtor)
520
raw_string_ostream(InitOrDeInitFunctionName)
521
<< InitFunctionPrefix << M.getModuleIdentifier();
522
else
523
raw_string_ostream(InitOrDeInitFunctionName)
524
<< DeInitFunctionPrefix << M.getModuleIdentifier();
525
526
MangleAndInterner Mangle(PS.getExecutionSession(), M.getDataLayout());
527
auto InternedInitOrDeInitName = Mangle(InitOrDeInitFunctionName);
528
if (auto Err = R.defineMaterializing(
529
{{InternedInitOrDeInitName, JITSymbolFlags::Callable}}))
530
return Err;
531
532
auto *InitOrDeInitFunc = Function::Create(
533
FunctionType::get(Type::getVoidTy(Ctx), {}, false),
534
GlobalValue::ExternalLinkage, InitOrDeInitFunctionName, &M);
535
InitOrDeInitFunc->setVisibility(GlobalValue::HiddenVisibility);
536
std::vector<std::pair<Function *, unsigned>> InitsOrDeInits;
537
auto COrDtors = isCtor ? getConstructors(M) : getDestructors(M);
538
539
for (auto E : COrDtors)
540
InitsOrDeInits.push_back(std::make_pair(E.Func, E.Priority));
541
llvm::stable_sort(InitsOrDeInits, llvm::less_second());
542
543
auto *InitOrDeInitFuncEntryBlock =
544
BasicBlock::Create(Ctx, "entry", InitOrDeInitFunc);
545
IRBuilder<> IB(InitOrDeInitFuncEntryBlock);
546
for (auto &KV : InitsOrDeInits)
547
IB.CreateCall(KV.first);
548
IB.CreateRetVoid();
549
550
if (isCtor)
551
PS.registerInitFunc(R.getTargetJITDylib(), InternedInitOrDeInitName);
552
else
553
PS.registerDeInitFunc(R.getTargetJITDylib(), InternedInitOrDeInitName);
554
555
GlobalCOrDtors->eraseFromParent();
556
return Error::success();
557
};
558
559
if (auto Err = RegisterCOrDtors(GlobalCtors, true))
560
return Err;
561
if (auto Err = RegisterCOrDtors(GlobalDtors, false))
562
return Err;
563
564
return Error::success();
565
});
566
567
if (Err)
568
return std::move(Err);
569
570
return std::move(TSM);
571
}
572
573
/// Inactive Platform Support
574
///
575
/// Explicitly disables platform support. JITDylibs are not scanned for special
576
/// init/deinit symbols. No runtime API interposes are injected.
577
class InactivePlatformSupport : public LLJIT::PlatformSupport {
578
public:
579
InactivePlatformSupport() = default;
580
581
Error initialize(JITDylib &JD) override {
582
LLVM_DEBUG(dbgs() << "InactivePlatformSupport: no initializers running for "
583
<< JD.getName() << "\n");
584
return Error::success();
585
}
586
587
Error deinitialize(JITDylib &JD) override {
588
LLVM_DEBUG(
589
dbgs() << "InactivePlatformSupport: no deinitializers running for "
590
<< JD.getName() << "\n");
591
return Error::success();
592
}
593
};
594
595
} // end anonymous namespace
596
597
namespace llvm {
598
namespace orc {
599
600
Error ORCPlatformSupport::initialize(orc::JITDylib &JD) {
601
using llvm::orc::shared::SPSExecutorAddr;
602
using llvm::orc::shared::SPSString;
603
using SPSDLOpenSig = SPSExecutorAddr(SPSString, int32_t);
604
enum dlopen_mode : int32_t {
605
ORC_RT_RTLD_LAZY = 0x1,
606
ORC_RT_RTLD_NOW = 0x2,
607
ORC_RT_RTLD_LOCAL = 0x4,
608
ORC_RT_RTLD_GLOBAL = 0x8
609
};
610
611
auto &ES = J.getExecutionSession();
612
auto MainSearchOrder = J.getMainJITDylib().withLinkOrderDo(
613
[](const JITDylibSearchOrder &SO) { return SO; });
614
615
if (auto WrapperAddr = ES.lookup(
616
MainSearchOrder, J.mangleAndIntern("__orc_rt_jit_dlopen_wrapper"))) {
617
return ES.callSPSWrapper<SPSDLOpenSig>(WrapperAddr->getAddress(),
618
DSOHandles[&JD], JD.getName(),
619
int32_t(ORC_RT_RTLD_LAZY));
620
} else
621
return WrapperAddr.takeError();
622
}
623
624
Error ORCPlatformSupport::deinitialize(orc::JITDylib &JD) {
625
using llvm::orc::shared::SPSExecutorAddr;
626
using SPSDLCloseSig = int32_t(SPSExecutorAddr);
627
628
auto &ES = J.getExecutionSession();
629
auto MainSearchOrder = J.getMainJITDylib().withLinkOrderDo(
630
[](const JITDylibSearchOrder &SO) { return SO; });
631
632
if (auto WrapperAddr = ES.lookup(
633
MainSearchOrder, J.mangleAndIntern("__orc_rt_jit_dlclose_wrapper"))) {
634
int32_t result;
635
auto E = J.getExecutionSession().callSPSWrapper<SPSDLCloseSig>(
636
WrapperAddr->getAddress(), result, DSOHandles[&JD]);
637
if (E)
638
return E;
639
else if (result)
640
return make_error<StringError>("dlclose failed",
641
inconvertibleErrorCode());
642
DSOHandles.erase(&JD);
643
} else
644
return WrapperAddr.takeError();
645
return Error::success();
646
}
647
648
void LLJIT::PlatformSupport::setInitTransform(
649
LLJIT &J, IRTransformLayer::TransformFunction T) {
650
J.InitHelperTransformLayer->setTransform(std::move(T));
651
}
652
653
LLJIT::PlatformSupport::~PlatformSupport() = default;
654
655
Error LLJITBuilderState::prepareForConstruction() {
656
657
LLVM_DEBUG(dbgs() << "Preparing to create LLJIT instance...\n");
658
659
if (!JTMB) {
660
LLVM_DEBUG({
661
dbgs() << " No explicitly set JITTargetMachineBuilder. "
662
"Detecting host...\n";
663
});
664
if (auto JTMBOrErr = JITTargetMachineBuilder::detectHost())
665
JTMB = std::move(*JTMBOrErr);
666
else
667
return JTMBOrErr.takeError();
668
}
669
670
if ((ES || EPC) && NumCompileThreads)
671
return make_error<StringError>(
672
"NumCompileThreads cannot be used with a custom ExecutionSession or "
673
"ExecutorProcessControl",
674
inconvertibleErrorCode());
675
676
#if !LLVM_ENABLE_THREADS
677
if (NumCompileThreads)
678
return make_error<StringError>(
679
"LLJIT num-compile-threads is " + Twine(NumCompileThreads) +
680
" but LLVM was compiled with LLVM_ENABLE_THREADS=Off",
681
inconvertibleErrorCode());
682
#endif // !LLVM_ENABLE_THREADS
683
684
// Only used in debug builds.
685
[[maybe_unused]] bool ConcurrentCompilationSettingDefaulted =
686
!SupportConcurrentCompilation;
687
688
if (!SupportConcurrentCompilation) {
689
#if LLVM_ENABLE_THREADS
690
SupportConcurrentCompilation = NumCompileThreads || ES || EPC;
691
#else
692
SupportConcurrentCompilation = false;
693
#endif // LLVM_ENABLE_THREADS
694
} else {
695
#if !LLVM_ENABLE_THREADS
696
if (*SupportConcurrentCompilation)
697
return make_error<StringError>(
698
"LLJIT concurrent compilation support requested, but LLVM was built "
699
"with LLVM_ENABLE_THREADS=Off",
700
inconvertibleErrorCode());
701
#endif // !LLVM_ENABLE_THREADS
702
}
703
704
LLVM_DEBUG({
705
dbgs() << " JITTargetMachineBuilder is "
706
<< JITTargetMachineBuilderPrinter(*JTMB, " ")
707
<< " Pre-constructed ExecutionSession: " << (ES ? "Yes" : "No")
708
<< "\n"
709
<< " DataLayout: ";
710
if (DL)
711
dbgs() << DL->getStringRepresentation() << "\n";
712
else
713
dbgs() << "None (will be created by JITTargetMachineBuilder)\n";
714
715
dbgs() << " Custom object-linking-layer creator: "
716
<< (CreateObjectLinkingLayer ? "Yes" : "No") << "\n"
717
<< " Custom compile-function creator: "
718
<< (CreateCompileFunction ? "Yes" : "No") << "\n"
719
<< " Custom platform-setup function: "
720
<< (SetUpPlatform ? "Yes" : "No") << "\n"
721
<< " Support concurrent compilation: "
722
<< (*SupportConcurrentCompilation ? "Yes" : "No");
723
if (ConcurrentCompilationSettingDefaulted)
724
dbgs() << " (defaulted based on ES / EPC / NumCompileThreads)\n";
725
else
726
dbgs() << "\n";
727
dbgs() << " Number of compile threads: " << NumCompileThreads << "\n";
728
});
729
730
// Create DL if not specified.
731
if (!DL) {
732
if (auto DLOrErr = JTMB->getDefaultDataLayoutForTarget())
733
DL = std::move(*DLOrErr);
734
else
735
return DLOrErr.takeError();
736
}
737
738
// If neither ES nor EPC has been set then create an EPC instance.
739
if (!ES && !EPC) {
740
LLVM_DEBUG({
741
dbgs() << "ExecutorProcessControl not specified, "
742
"Creating SelfExecutorProcessControl instance\n";
743
});
744
745
std::unique_ptr<TaskDispatcher> D = nullptr;
746
#if LLVM_ENABLE_THREADS
747
if (*SupportConcurrentCompilation) {
748
std::optional<size_t> NumThreads = std ::nullopt;
749
if (NumCompileThreads)
750
NumThreads = NumCompileThreads;
751
D = std::make_unique<DynamicThreadPoolTaskDispatcher>(NumThreads);
752
} else
753
D = std::make_unique<InPlaceTaskDispatcher>();
754
#endif // LLVM_ENABLE_THREADS
755
if (auto EPCOrErr =
756
SelfExecutorProcessControl::Create(nullptr, std::move(D), nullptr))
757
EPC = std::move(*EPCOrErr);
758
else
759
return EPCOrErr.takeError();
760
} else if (EPC) {
761
LLVM_DEBUG({
762
dbgs() << "Using explicitly specified ExecutorProcessControl instance "
763
<< EPC.get() << "\n";
764
});
765
} else {
766
LLVM_DEBUG({
767
dbgs() << "Using explicitly specified ExecutionSession instance "
768
<< ES.get() << "\n";
769
});
770
}
771
772
// If the client didn't configure any linker options then auto-configure the
773
// JIT linker.
774
if (!CreateObjectLinkingLayer) {
775
auto &TT = JTMB->getTargetTriple();
776
bool UseJITLink = false;
777
switch (TT.getArch()) {
778
case Triple::riscv64:
779
case Triple::loongarch64:
780
UseJITLink = true;
781
break;
782
case Triple::aarch64:
783
UseJITLink = !TT.isOSBinFormatCOFF();
784
break;
785
case Triple::arm:
786
case Triple::armeb:
787
case Triple::thumb:
788
case Triple::thumbeb:
789
UseJITLink = TT.isOSBinFormatELF();
790
break;
791
case Triple::x86_64:
792
UseJITLink = !TT.isOSBinFormatCOFF();
793
break;
794
case Triple::ppc64:
795
UseJITLink = TT.isPPC64ELFv2ABI();
796
break;
797
case Triple::ppc64le:
798
UseJITLink = TT.isOSBinFormatELF();
799
break;
800
default:
801
break;
802
}
803
if (UseJITLink) {
804
if (!JTMB->getCodeModel())
805
JTMB->setCodeModel(CodeModel::Small);
806
JTMB->setRelocationModel(Reloc::PIC_);
807
CreateObjectLinkingLayer =
808
[](ExecutionSession &ES,
809
const Triple &) -> Expected<std::unique_ptr<ObjectLayer>> {
810
auto ObjLinkingLayer = std::make_unique<ObjectLinkingLayer>(ES);
811
if (auto EHFrameRegistrar = EPCEHFrameRegistrar::Create(ES))
812
ObjLinkingLayer->addPlugin(
813
std::make_unique<EHFrameRegistrationPlugin>(
814
ES, std::move(*EHFrameRegistrar)));
815
else
816
return EHFrameRegistrar.takeError();
817
return std::move(ObjLinkingLayer);
818
};
819
}
820
}
821
822
// If we need a process JITDylib but no setup function has been given then
823
// create a default one.
824
if (!SetupProcessSymbolsJITDylib && LinkProcessSymbolsByDefault) {
825
LLVM_DEBUG(dbgs() << "Creating default Process JD setup function\n");
826
SetupProcessSymbolsJITDylib = [](LLJIT &J) -> Expected<JITDylibSP> {
827
auto &JD =
828
J.getExecutionSession().createBareJITDylib("<Process Symbols>");
829
auto G = EPCDynamicLibrarySearchGenerator::GetForTargetProcess(
830
J.getExecutionSession());
831
if (!G)
832
return G.takeError();
833
JD.addGenerator(std::move(*G));
834
return &JD;
835
};
836
}
837
838
return Error::success();
839
}
840
841
LLJIT::~LLJIT() {
842
if (auto Err = ES->endSession())
843
ES->reportError(std::move(Err));
844
}
845
846
JITDylibSP LLJIT::getProcessSymbolsJITDylib() { return ProcessSymbols; }
847
848
JITDylibSP LLJIT::getPlatformJITDylib() { return Platform; }
849
850
Expected<JITDylib &> LLJIT::createJITDylib(std::string Name) {
851
auto JD = ES->createJITDylib(std::move(Name));
852
if (!JD)
853
return JD.takeError();
854
855
JD->addToLinkOrder(DefaultLinks);
856
return JD;
857
}
858
859
Expected<JITDylib &> LLJIT::loadPlatformDynamicLibrary(const char *Path) {
860
auto G = EPCDynamicLibrarySearchGenerator::Load(*ES, Path);
861
if (!G)
862
return G.takeError();
863
864
if (auto *ExistingJD = ES->getJITDylibByName(Path))
865
return *ExistingJD;
866
867
auto &JD = ES->createBareJITDylib(Path);
868
JD.addGenerator(std::move(*G));
869
return JD;
870
}
871
872
Error LLJIT::linkStaticLibraryInto(JITDylib &JD,
873
std::unique_ptr<MemoryBuffer> LibBuffer) {
874
auto G = StaticLibraryDefinitionGenerator::Create(*ObjLinkingLayer,
875
std::move(LibBuffer));
876
if (!G)
877
return G.takeError();
878
879
JD.addGenerator(std::move(*G));
880
881
return Error::success();
882
}
883
884
Error LLJIT::linkStaticLibraryInto(JITDylib &JD, const char *Path) {
885
auto G = StaticLibraryDefinitionGenerator::Load(*ObjLinkingLayer, Path);
886
if (!G)
887
return G.takeError();
888
889
JD.addGenerator(std::move(*G));
890
891
return Error::success();
892
}
893
894
Error LLJIT::addIRModule(ResourceTrackerSP RT, ThreadSafeModule TSM) {
895
assert(TSM && "Can not add null module");
896
897
if (auto Err =
898
TSM.withModuleDo([&](Module &M) { return applyDataLayout(M); }))
899
return Err;
900
901
return InitHelperTransformLayer->add(std::move(RT), std::move(TSM));
902
}
903
904
Error LLJIT::addIRModule(JITDylib &JD, ThreadSafeModule TSM) {
905
return addIRModule(JD.getDefaultResourceTracker(), std::move(TSM));
906
}
907
908
Error LLJIT::addObjectFile(ResourceTrackerSP RT,
909
std::unique_ptr<MemoryBuffer> Obj) {
910
assert(Obj && "Can not add null object");
911
912
return ObjTransformLayer->add(std::move(RT), std::move(Obj));
913
}
914
915
Error LLJIT::addObjectFile(JITDylib &JD, std::unique_ptr<MemoryBuffer> Obj) {
916
return addObjectFile(JD.getDefaultResourceTracker(), std::move(Obj));
917
}
918
919
Expected<ExecutorAddr> LLJIT::lookupLinkerMangled(JITDylib &JD,
920
SymbolStringPtr Name) {
921
if (auto Sym = ES->lookup(
922
makeJITDylibSearchOrder(&JD, JITDylibLookupFlags::MatchAllSymbols),
923
Name))
924
return Sym->getAddress();
925
else
926
return Sym.takeError();
927
}
928
929
Expected<std::unique_ptr<ObjectLayer>>
930
LLJIT::createObjectLinkingLayer(LLJITBuilderState &S, ExecutionSession &ES) {
931
932
// If the config state provided an ObjectLinkingLayer factory then use it.
933
if (S.CreateObjectLinkingLayer)
934
return S.CreateObjectLinkingLayer(ES, S.JTMB->getTargetTriple());
935
936
// Otherwise default to creating an RTDyldObjectLinkingLayer that constructs
937
// a new SectionMemoryManager for each object.
938
auto GetMemMgr = []() { return std::make_unique<SectionMemoryManager>(); };
939
auto Layer =
940
std::make_unique<RTDyldObjectLinkingLayer>(ES, std::move(GetMemMgr));
941
942
if (S.JTMB->getTargetTriple().isOSBinFormatCOFF()) {
943
Layer->setOverrideObjectFlagsWithResponsibilityFlags(true);
944
Layer->setAutoClaimResponsibilityForObjectSymbols(true);
945
}
946
947
if (S.JTMB->getTargetTriple().isOSBinFormatELF() &&
948
(S.JTMB->getTargetTriple().getArch() == Triple::ArchType::ppc64 ||
949
S.JTMB->getTargetTriple().getArch() == Triple::ArchType::ppc64le))
950
Layer->setAutoClaimResponsibilityForObjectSymbols(true);
951
952
// FIXME: Explicit conversion to std::unique_ptr<ObjectLayer> added to silence
953
// errors from some GCC / libstdc++ bots. Remove this conversion (i.e.
954
// just return ObjLinkingLayer) once those bots are upgraded.
955
return std::unique_ptr<ObjectLayer>(std::move(Layer));
956
}
957
958
Expected<std::unique_ptr<IRCompileLayer::IRCompiler>>
959
LLJIT::createCompileFunction(LLJITBuilderState &S,
960
JITTargetMachineBuilder JTMB) {
961
962
/// If there is a custom compile function creator set then use it.
963
if (S.CreateCompileFunction)
964
return S.CreateCompileFunction(std::move(JTMB));
965
966
// If using a custom EPC then use a ConcurrentIRCompiler by default.
967
if (*S.SupportConcurrentCompilation)
968
return std::make_unique<ConcurrentIRCompiler>(std::move(JTMB));
969
970
auto TM = JTMB.createTargetMachine();
971
if (!TM)
972
return TM.takeError();
973
974
return std::make_unique<TMOwningSimpleCompiler>(std::move(*TM));
975
}
976
977
LLJIT::LLJIT(LLJITBuilderState &S, Error &Err)
978
: DL(std::move(*S.DL)), TT(S.JTMB->getTargetTriple()) {
979
980
ErrorAsOutParameter _(&Err);
981
982
assert(!(S.EPC && S.ES) && "EPC and ES should not both be set");
983
984
if (S.EPC) {
985
ES = std::make_unique<ExecutionSession>(std::move(S.EPC));
986
} else if (S.ES)
987
ES = std::move(S.ES);
988
else {
989
if (auto EPC = SelfExecutorProcessControl::Create()) {
990
ES = std::make_unique<ExecutionSession>(std::move(*EPC));
991
} else {
992
Err = EPC.takeError();
993
return;
994
}
995
}
996
997
auto ObjLayer = createObjectLinkingLayer(S, *ES);
998
if (!ObjLayer) {
999
Err = ObjLayer.takeError();
1000
return;
1001
}
1002
ObjLinkingLayer = std::move(*ObjLayer);
1003
ObjTransformLayer =
1004
std::make_unique<ObjectTransformLayer>(*ES, *ObjLinkingLayer);
1005
1006
{
1007
auto CompileFunction = createCompileFunction(S, std::move(*S.JTMB));
1008
if (!CompileFunction) {
1009
Err = CompileFunction.takeError();
1010
return;
1011
}
1012
CompileLayer = std::make_unique<IRCompileLayer>(
1013
*ES, *ObjTransformLayer, std::move(*CompileFunction));
1014
TransformLayer = std::make_unique<IRTransformLayer>(*ES, *CompileLayer);
1015
InitHelperTransformLayer =
1016
std::make_unique<IRTransformLayer>(*ES, *TransformLayer);
1017
}
1018
1019
if (*S.SupportConcurrentCompilation)
1020
InitHelperTransformLayer->setCloneToNewContextOnEmit(true);
1021
1022
if (S.SetupProcessSymbolsJITDylib) {
1023
if (auto ProcSymsJD = S.SetupProcessSymbolsJITDylib(*this)) {
1024
ProcessSymbols = ProcSymsJD->get();
1025
} else {
1026
Err = ProcSymsJD.takeError();
1027
return;
1028
}
1029
}
1030
1031
if (S.PrePlatformSetup) {
1032
if (auto Err2 = S.PrePlatformSetup(*this)) {
1033
Err = std::move(Err2);
1034
return;
1035
}
1036
}
1037
1038
if (!S.SetUpPlatform)
1039
S.SetUpPlatform = setUpGenericLLVMIRPlatform;
1040
1041
if (auto PlatformJDOrErr = S.SetUpPlatform(*this)) {
1042
Platform = PlatformJDOrErr->get();
1043
if (Platform)
1044
DefaultLinks.push_back(
1045
{Platform, JITDylibLookupFlags::MatchExportedSymbolsOnly});
1046
} else {
1047
Err = PlatformJDOrErr.takeError();
1048
return;
1049
}
1050
1051
if (S.LinkProcessSymbolsByDefault)
1052
DefaultLinks.push_back(
1053
{ProcessSymbols, JITDylibLookupFlags::MatchExportedSymbolsOnly});
1054
1055
if (auto MainOrErr = createJITDylib("main"))
1056
Main = &*MainOrErr;
1057
else {
1058
Err = MainOrErr.takeError();
1059
return;
1060
}
1061
}
1062
1063
std::string LLJIT::mangle(StringRef UnmangledName) const {
1064
std::string MangledName;
1065
{
1066
raw_string_ostream MangledNameStream(MangledName);
1067
Mangler::getNameWithPrefix(MangledNameStream, UnmangledName, DL);
1068
}
1069
return MangledName;
1070
}
1071
1072
Error LLJIT::applyDataLayout(Module &M) {
1073
if (M.getDataLayout().isDefault())
1074
M.setDataLayout(DL);
1075
1076
if (M.getDataLayout() != DL)
1077
return make_error<StringError>(
1078
"Added modules have incompatible data layouts: " +
1079
M.getDataLayout().getStringRepresentation() + " (module) vs " +
1080
DL.getStringRepresentation() + " (jit)",
1081
inconvertibleErrorCode());
1082
1083
return Error::success();
1084
}
1085
1086
Error setUpOrcPlatformManually(LLJIT &J) {
1087
LLVM_DEBUG({ dbgs() << "Setting up orc platform support for LLJIT\n"; });
1088
J.setPlatformSupport(std::make_unique<ORCPlatformSupport>(J));
1089
return Error::success();
1090
}
1091
1092
class LoadAndLinkDynLibrary {
1093
public:
1094
LoadAndLinkDynLibrary(LLJIT &J) : J(J) {}
1095
Error operator()(JITDylib &JD, StringRef DLLName) {
1096
if (!DLLName.ends_with_insensitive(".dll"))
1097
return make_error<StringError>("DLLName not ending with .dll",
1098
inconvertibleErrorCode());
1099
auto DLLNameStr = DLLName.str(); // Guarantees null-termination.
1100
auto DLLJD = J.loadPlatformDynamicLibrary(DLLNameStr.c_str());
1101
if (!DLLJD)
1102
return DLLJD.takeError();
1103
JD.addToLinkOrder(*DLLJD);
1104
return Error::success();
1105
}
1106
1107
private:
1108
LLJIT &J;
1109
};
1110
1111
Expected<JITDylibSP> ExecutorNativePlatform::operator()(LLJIT &J) {
1112
auto ProcessSymbolsJD = J.getProcessSymbolsJITDylib();
1113
if (!ProcessSymbolsJD)
1114
return make_error<StringError>(
1115
"Native platforms require a process symbols JITDylib",
1116
inconvertibleErrorCode());
1117
1118
const Triple &TT = J.getTargetTriple();
1119
ObjectLinkingLayer *ObjLinkingLayer =
1120
dyn_cast<ObjectLinkingLayer>(&J.getObjLinkingLayer());
1121
1122
if (!ObjLinkingLayer)
1123
return make_error<StringError>(
1124
"ExecutorNativePlatform requires ObjectLinkingLayer",
1125
inconvertibleErrorCode());
1126
1127
std::unique_ptr<MemoryBuffer> RuntimeArchiveBuffer;
1128
if (OrcRuntime.index() == 0) {
1129
auto A = errorOrToExpected(MemoryBuffer::getFile(std::get<0>(OrcRuntime)));
1130
if (!A)
1131
return A.takeError();
1132
RuntimeArchiveBuffer = std::move(*A);
1133
} else
1134
RuntimeArchiveBuffer = std::move(std::get<1>(OrcRuntime));
1135
1136
auto &ES = J.getExecutionSession();
1137
auto &PlatformJD = ES.createBareJITDylib("<Platform>");
1138
PlatformJD.addToLinkOrder(*ProcessSymbolsJD);
1139
1140
J.setPlatformSupport(std::make_unique<ORCPlatformSupport>(J));
1141
1142
switch (TT.getObjectFormat()) {
1143
case Triple::COFF: {
1144
const char *VCRuntimePath = nullptr;
1145
bool StaticVCRuntime = false;
1146
if (VCRuntime) {
1147
VCRuntimePath = VCRuntime->first.c_str();
1148
StaticVCRuntime = VCRuntime->second;
1149
}
1150
if (auto P = COFFPlatform::Create(
1151
ES, *ObjLinkingLayer, PlatformJD, std::move(RuntimeArchiveBuffer),
1152
LoadAndLinkDynLibrary(J), StaticVCRuntime, VCRuntimePath))
1153
J.getExecutionSession().setPlatform(std::move(*P));
1154
else
1155
return P.takeError();
1156
break;
1157
}
1158
case Triple::ELF: {
1159
auto G = StaticLibraryDefinitionGenerator::Create(
1160
*ObjLinkingLayer, std::move(RuntimeArchiveBuffer));
1161
if (!G)
1162
return G.takeError();
1163
1164
if (auto P = ELFNixPlatform::Create(ES, *ObjLinkingLayer, PlatformJD,
1165
std::move(*G)))
1166
J.getExecutionSession().setPlatform(std::move(*P));
1167
else
1168
return P.takeError();
1169
break;
1170
}
1171
case Triple::MachO: {
1172
auto G = StaticLibraryDefinitionGenerator::Create(
1173
*ObjLinkingLayer, std::move(RuntimeArchiveBuffer));
1174
if (!G)
1175
return G.takeError();
1176
1177
if (auto P = MachOPlatform::Create(ES, *ObjLinkingLayer, PlatformJD,
1178
std::move(*G)))
1179
ES.setPlatform(std::move(*P));
1180
else
1181
return P.takeError();
1182
break;
1183
}
1184
default:
1185
return make_error<StringError>("Unsupported object format in triple " +
1186
TT.str(),
1187
inconvertibleErrorCode());
1188
}
1189
1190
return &PlatformJD;
1191
}
1192
1193
Expected<JITDylibSP> setUpGenericLLVMIRPlatform(LLJIT &J) {
1194
LLVM_DEBUG(
1195
{ dbgs() << "Setting up GenericLLVMIRPlatform support for LLJIT\n"; });
1196
auto ProcessSymbolsJD = J.getProcessSymbolsJITDylib();
1197
if (!ProcessSymbolsJD)
1198
return make_error<StringError>(
1199
"Native platforms require a process symbols JITDylib",
1200
inconvertibleErrorCode());
1201
1202
auto &PlatformJD = J.getExecutionSession().createBareJITDylib("<Platform>");
1203
PlatformJD.addToLinkOrder(*ProcessSymbolsJD);
1204
1205
J.setPlatformSupport(
1206
std::make_unique<GenericLLVMIRPlatformSupport>(J, PlatformJD));
1207
1208
return &PlatformJD;
1209
}
1210
1211
Expected<JITDylibSP> setUpInactivePlatform(LLJIT &J) {
1212
LLVM_DEBUG(
1213
{ dbgs() << "Explicitly deactivated platform support for LLJIT\n"; });
1214
J.setPlatformSupport(std::make_unique<InactivePlatformSupport>());
1215
return nullptr;
1216
}
1217
1218
Error LLLazyJITBuilderState::prepareForConstruction() {
1219
if (auto Err = LLJITBuilderState::prepareForConstruction())
1220
return Err;
1221
TT = JTMB->getTargetTriple();
1222
return Error::success();
1223
}
1224
1225
Error LLLazyJIT::addLazyIRModule(JITDylib &JD, ThreadSafeModule TSM) {
1226
assert(TSM && "Can not add null module");
1227
1228
if (auto Err = TSM.withModuleDo(
1229
[&](Module &M) -> Error { return applyDataLayout(M); }))
1230
return Err;
1231
1232
return CODLayer->add(JD, std::move(TSM));
1233
}
1234
1235
LLLazyJIT::LLLazyJIT(LLLazyJITBuilderState &S, Error &Err) : LLJIT(S, Err) {
1236
1237
// If LLJIT construction failed then bail out.
1238
if (Err)
1239
return;
1240
1241
ErrorAsOutParameter _(&Err);
1242
1243
/// Take/Create the lazy-compile callthrough manager.
1244
if (S.LCTMgr)
1245
LCTMgr = std::move(S.LCTMgr);
1246
else {
1247
if (auto LCTMgrOrErr = createLocalLazyCallThroughManager(
1248
S.TT, *ES, S.LazyCompileFailureAddr))
1249
LCTMgr = std::move(*LCTMgrOrErr);
1250
else {
1251
Err = LCTMgrOrErr.takeError();
1252
return;
1253
}
1254
}
1255
1256
// Take/Create the indirect stubs manager builder.
1257
auto ISMBuilder = std::move(S.ISMBuilder);
1258
1259
// If none was provided, try to build one.
1260
if (!ISMBuilder)
1261
ISMBuilder = createLocalIndirectStubsManagerBuilder(S.TT);
1262
1263
// No luck. Bail out.
1264
if (!ISMBuilder) {
1265
Err = make_error<StringError>("Could not construct "
1266
"IndirectStubsManagerBuilder for target " +
1267
S.TT.str(),
1268
inconvertibleErrorCode());
1269
return;
1270
}
1271
1272
// Create the COD layer.
1273
CODLayer = std::make_unique<CompileOnDemandLayer>(
1274
*ES, *InitHelperTransformLayer, *LCTMgr, std::move(ISMBuilder));
1275
1276
if (*S.SupportConcurrentCompilation)
1277
CODLayer->setCloneToNewContextOnEmit(true);
1278
}
1279
1280
// In-process LLJIT uses eh-frame section wrappers via EPC, so we need to force
1281
// them to be linked in.
1282
LLVM_ATTRIBUTE_USED void linkComponents() {
1283
errs() << (void *)&llvm_orc_registerEHFrameSectionWrapper
1284
<< (void *)&llvm_orc_deregisterEHFrameSectionWrapper;
1285
}
1286
1287
} // End namespace orc.
1288
} // End namespace llvm.
1289
1290