brintos

brintos / llvm-project-archived public Read only

0
0
Text · 7.0 KiB · e22c35f Raw
217 lines · c
1//===------ OrcTestCommon.h - Utilities for Orc Unit Tests ------*- 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-exception6//7//===----------------------------------------------------------------------===//8//9// Common utilities for the Orc unit tests.10//11//===----------------------------------------------------------------------===//12 13 14#ifndef LLVM_UNITTESTS_EXECUTIONENGINE_ORC_ORCTESTCOMMON_H15#define LLVM_UNITTESTS_EXECUTIONENGINE_ORC_ORCTESTCOMMON_H16 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/InProcessMemoryAccess.h"21#include "llvm/ExecutionEngine/Orc/IndirectionUtils.h"22#include "llvm/IR/Function.h"23#include "llvm/IR/IRBuilder.h"24#include "llvm/IR/LLVMContext.h"25#include "llvm/IR/Module.h"26#include "llvm/MC/TargetRegistry.h"27#include "llvm/Object/ObjectFile.h"28#include "llvm/Support/TargetSelect.h"29#include "gtest/gtest.h"30 31#include <memory>32 33namespace llvm {34 35namespace orc {36// CoreAPIsStandardTest that saves a bunch of boilerplate by providing the37// following:38//39// (1) ES -- An ExecutionSession40// (2) Foo, Bar, Baz, Qux -- SymbolStringPtrs for strings "foo", "bar", "baz",41//     and "qux" respectively.42// (3) FooAddr, BarAddr, BazAddr, QuxAddr -- Dummy addresses. Guaranteed43//     distinct and non-null.44// (4) FooSym, BarSym, BazSym, QuxSym -- JITEvaluatedSymbols with FooAddr,45//     BarAddr, BazAddr, and QuxAddr respectively. All with default strong,46//     linkage and non-hidden visibility.47// (5) V -- A JITDylib associated with ES.48class CoreAPIsBasedStandardTest : public testing::Test {49public:50  ~CoreAPIsBasedStandardTest() override {51    if (auto Err = ES.endSession())52      ES.reportError(std::move(Err));53  }54 55protected:56  class OverridableDispatcher : public InPlaceTaskDispatcher {57  public:58    OverridableDispatcher(CoreAPIsBasedStandardTest &Parent) : Parent(Parent) {}59    void dispatch(std::unique_ptr<Task> T) override;60 61  private:62    CoreAPIsBasedStandardTest &Parent;63  };64 65  std::unique_ptr<llvm::orc::ExecutorProcessControl>66  makeEPC(std::shared_ptr<SymbolStringPool> SSP);67 68  std::shared_ptr<SymbolStringPool> SSP = std::make_shared<SymbolStringPool>();69  ExecutionSession ES{makeEPC(SSP)};70  JITDylib &JD = ES.createBareJITDylib("JD");71  SymbolStringPtr Foo = ES.intern("foo");72  SymbolStringPtr Bar = ES.intern("bar");73  SymbolStringPtr Baz = ES.intern("baz");74  SymbolStringPtr Qux = ES.intern("qux");75  static constexpr ExecutorAddr FooAddr{1};76  static constexpr ExecutorAddr BarAddr{2};77  static constexpr ExecutorAddr BazAddr{3};78  static constexpr ExecutorAddr QuxAddr{4};79  ExecutorSymbolDef FooSym{FooAddr, JITSymbolFlags::Exported};80  ExecutorSymbolDef BarSym{BarAddr, JITSymbolFlags::Exported};81  ExecutorSymbolDef BazSym{BazAddr, JITSymbolFlags::Exported};82  ExecutorSymbolDef QuxSym{QuxAddr, JITSymbolFlags::Exported};83  unique_function<void(std::unique_ptr<Task>)> DispatchOverride;84};85 86/// A ExecutorProcessControl instance that asserts if any of its methods are87/// used. Suitable for use is unit tests, and by ORC clients who haven't moved88/// to ExecutorProcessControl-based APIs yet.89class UnsupportedExecutorProcessControl : public ExecutorProcessControl,90                                          private InProcessMemoryAccess {91public:92  UnsupportedExecutorProcessControl(93      std::shared_ptr<SymbolStringPool> SSP = nullptr,94      std::unique_ptr<TaskDispatcher> D = nullptr, const std::string &TT = "",95      unsigned PageSize = 0)96      : ExecutorProcessControl(97            SSP ? std::move(SSP) : std::make_shared<SymbolStringPool>(),98            D ? std::move(D) : std::make_unique<InPlaceTaskDispatcher>()),99        InProcessMemoryAccess(Triple(TT).isArch64Bit()) {100    this->TargetTriple = Triple(TT);101    this->PageSize = PageSize;102    this->MemAccess = this;103  }104 105  Expected<int32_t> runAsMain(ExecutorAddr MainFnAddr,106                              ArrayRef<std::string> Args) override {107    llvm_unreachable("Unsupported");108  }109 110  Expected<int32_t> runAsVoidFunction(ExecutorAddr VoidFnAddr) override {111    llvm_unreachable("Unsupported");112  }113 114  Expected<int32_t> runAsIntFunction(ExecutorAddr IntFnAddr, int Arg) override {115    llvm_unreachable("Unsupported");116  }117 118  void callWrapperAsync(ExecutorAddr WrapperFnAddr,119                        IncomingWFRHandler OnComplete,120                        ArrayRef<char> ArgBuffer) override {121    llvm_unreachable("Unsupported");122  }123 124  Error disconnect() override { return Error::success(); }125};126 127} // end namespace orc128 129class OrcNativeTarget {130public:131  static void initialize() {132    if (!NativeTargetInitialized) {133      InitializeNativeTarget();134      InitializeNativeTargetAsmParser();135      InitializeNativeTargetAsmPrinter();136      NativeTargetInitialized = true;137    }138  }139 140private:141  static bool NativeTargetInitialized;142};143 144class SimpleMaterializationUnit : public orc::MaterializationUnit {145public:146  using MaterializeFunction =147      std::function<void(std::unique_ptr<orc::MaterializationResponsibility>)>;148  using DiscardFunction =149      std::function<void(const orc::JITDylib &, orc::SymbolStringPtr)>;150  using DestructorFunction = std::function<void()>;151 152  SimpleMaterializationUnit(153      orc::SymbolFlagsMap SymbolFlags, MaterializeFunction Materialize,154      orc::SymbolStringPtr InitSym = nullptr,155      DiscardFunction Discard = DiscardFunction(),156      DestructorFunction Destructor = DestructorFunction())157      : MaterializationUnit(158            Interface(std::move(SymbolFlags), std::move(InitSym))),159        Materialize(std::move(Materialize)), Discard(std::move(Discard)),160        Destructor(std::move(Destructor)) {}161 162  ~SimpleMaterializationUnit() override {163    if (Destructor)164      Destructor();165  }166 167  StringRef getName() const override { return "<Simple>"; }168 169  void170  materialize(std::unique_ptr<orc::MaterializationResponsibility> R) override {171    Materialize(std::move(R));172  }173 174  void discard(const orc::JITDylib &JD,175               const orc::SymbolStringPtr &Name) override {176    if (Discard)177      Discard(JD, std::move(Name));178    else179      llvm_unreachable("Discard not supported");180  }181 182private:183  MaterializeFunction Materialize;184  DiscardFunction Discard;185  DestructorFunction Destructor;186};187 188class ModuleBuilder {189public:190  ModuleBuilder(LLVMContext &Context, StringRef Triple,191                StringRef Name);192 193  Function *createFunctionDecl(FunctionType *FTy, StringRef Name) {194    return Function::Create(FTy, GlobalValue::ExternalLinkage, Name, M.get());195  }196 197  Module* getModule() { return M.get(); }198  const Module* getModule() const { return M.get(); }199  std::unique_ptr<Module> takeModule() { return std::move(M); }200 201private:202  std::unique_ptr<Module> M;203};204 205// Dummy struct type.206struct DummyStruct {207  int X[256];208};209 210inline StructType *getDummyStructTy(LLVMContext &Context) {211  return StructType::get(ArrayType::get(Type::getInt32Ty(Context), 256));212}213 214} // namespace llvm215 216#endif217