1 //===------ OrcTestCommon.h - Utilities for Orc Unit Tests ------*- C++ -*-===//
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
7 //===----------------------------------------------------------------------===//
9 // Common utilities for the Orc unit tests.
11 //===----------------------------------------------------------------------===//
14 #ifndef LLVM_UNITTESTS_EXECUTIONENGINE_ORC_ORCTESTCOMMON_H
15 #define LLVM_UNITTESTS_EXECUTIONENGINE_ORC_ORCTESTCOMMON_H
17 #include "llvm/ExecutionEngine/JITSymbol.h"
18 #include "llvm/ExecutionEngine/Orc/Core.h"
19 #include "llvm/ExecutionEngine/Orc/ExecutorProcessControl.h"
20 #include "llvm/ExecutionEngine/Orc/IndirectionUtils.h"
21 #include "llvm/IR/Function.h"
22 #include "llvm/IR/IRBuilder.h"
23 #include "llvm/IR/LLVMContext.h"
24 #include "llvm/IR/Module.h"
25 #include "llvm/MC/TargetRegistry.h"
26 #include "llvm/Object/ObjectFile.h"
27 #include "llvm/Support/TargetSelect.h"
28 #include "gtest/gtest.h"
35 // CoreAPIsStandardTest that saves a bunch of boilerplate by providing the
38 // (1) ES -- An ExecutionSession
39 // (2) Foo, Bar, Baz, Qux -- SymbolStringPtrs for strings "foo", "bar", "baz",
40 // and "qux" respectively.
41 // (3) FooAddr, BarAddr, BazAddr, QuxAddr -- Dummy addresses. Guaranteed
42 // distinct and non-null.
43 // (4) FooSym, BarSym, BazSym, QuxSym -- JITEvaluatedSymbols with FooAddr,
44 // BarAddr, BazAddr, and QuxAddr respectively. All with default strong,
45 // linkage and non-hidden visibility.
46 // (5) V -- A JITDylib associated with ES.
47 class CoreAPIsBasedStandardTest
: public testing::Test
{
49 ~CoreAPIsBasedStandardTest() {
50 if (auto Err
= ES
.endSession())
51 ES
.reportError(std::move(Err
));
55 class OverridableDispatcher
: public InPlaceTaskDispatcher
{
57 OverridableDispatcher(CoreAPIsBasedStandardTest
&Parent
) : Parent(Parent
) {}
58 void dispatch(std::unique_ptr
<Task
> T
) override
;
61 CoreAPIsBasedStandardTest
&Parent
;
64 std::unique_ptr
<llvm::orc::ExecutorProcessControl
>
65 makeEPC(std::shared_ptr
<SymbolStringPool
> SSP
);
67 std::shared_ptr
<SymbolStringPool
> SSP
= std::make_shared
<SymbolStringPool
>();
68 ExecutionSession ES
{makeEPC(SSP
)};
69 JITDylib
&JD
= ES
.createBareJITDylib("JD");
70 SymbolStringPtr Foo
= ES
.intern("foo");
71 SymbolStringPtr Bar
= ES
.intern("bar");
72 SymbolStringPtr Baz
= ES
.intern("baz");
73 SymbolStringPtr Qux
= ES
.intern("qux");
74 static constexpr ExecutorAddr FooAddr
{1};
75 static constexpr ExecutorAddr BarAddr
{2};
76 static constexpr ExecutorAddr BazAddr
{3};
77 static constexpr ExecutorAddr QuxAddr
{4};
78 ExecutorSymbolDef FooSym
{FooAddr
, JITSymbolFlags::Exported
};
79 ExecutorSymbolDef BarSym
{BarAddr
, JITSymbolFlags::Exported
};
80 ExecutorSymbolDef BazSym
{BazAddr
, JITSymbolFlags::Exported
};
81 ExecutorSymbolDef QuxSym
{QuxAddr
, JITSymbolFlags::Exported
};
82 unique_function
<void(std::unique_ptr
<Task
>)> DispatchOverride
;
85 } // end namespace orc
87 class OrcNativeTarget
{
89 static void initialize() {
90 if (!NativeTargetInitialized
) {
91 InitializeNativeTarget();
92 InitializeNativeTargetAsmParser();
93 InitializeNativeTargetAsmPrinter();
94 NativeTargetInitialized
= true;
99 static bool NativeTargetInitialized
;
102 class SimpleMaterializationUnit
: public orc::MaterializationUnit
{
104 using MaterializeFunction
=
105 std::function
<void(std::unique_ptr
<orc::MaterializationResponsibility
>)>;
106 using DiscardFunction
=
107 std::function
<void(const orc::JITDylib
&, orc::SymbolStringPtr
)>;
108 using DestructorFunction
= std::function
<void()>;
110 SimpleMaterializationUnit(
111 orc::SymbolFlagsMap SymbolFlags
, MaterializeFunction Materialize
,
112 orc::SymbolStringPtr InitSym
= nullptr,
113 DiscardFunction Discard
= DiscardFunction(),
114 DestructorFunction Destructor
= DestructorFunction())
115 : MaterializationUnit(
116 Interface(std::move(SymbolFlags
), std::move(InitSym
))),
117 Materialize(std::move(Materialize
)), Discard(std::move(Discard
)),
118 Destructor(std::move(Destructor
)) {}
120 ~SimpleMaterializationUnit() override
{
125 StringRef
getName() const override
{ return "<Simple>"; }
128 materialize(std::unique_ptr
<orc::MaterializationResponsibility
> R
) override
{
129 Materialize(std::move(R
));
132 void discard(const orc::JITDylib
&JD
,
133 const orc::SymbolStringPtr
&Name
) override
{
135 Discard(JD
, std::move(Name
));
137 llvm_unreachable("Discard not supported");
141 MaterializeFunction Materialize
;
142 DiscardFunction Discard
;
143 DestructorFunction Destructor
;
146 class ModuleBuilder
{
148 ModuleBuilder(LLVMContext
&Context
, StringRef Triple
,
151 Function
*createFunctionDecl(FunctionType
*FTy
, StringRef Name
) {
152 return Function::Create(FTy
, GlobalValue::ExternalLinkage
, Name
, M
.get());
155 Module
* getModule() { return M
.get(); }
156 const Module
* getModule() const { return M
.get(); }
157 std::unique_ptr
<Module
> takeModule() { return std::move(M
); }
160 std::unique_ptr
<Module
> M
;
163 // Dummy struct type.
168 inline StructType
*getDummyStructTy(LLVMContext
&Context
) {
169 return StructType::get(ArrayType::get(Type::getInt32Ty(Context
), 256));