From 500d530eaf1cc1dd3d2b54f7768aeccea7d3efb3 Mon Sep 17 00:00:00 2001 From: Lang Hames Date: Sun, 19 Mar 2023 15:50:44 -0700 Subject: [PATCH] Revert "[ORC] Introduce SetUpExecutorNativePlatform utility." This reverts commit bdf5f9c3228d6ed1d7c6f87b3828a7d573b34c03, which was a work in progress for https://reviews.llvm.org/D144276 and accidentally committed early. --- .../llvm/ExecutionEngine/Orc/COFFPlatform.h | 20 +- llvm/include/llvm/ExecutionEngine/Orc/Core.h | 4 - llvm/include/llvm/ExecutionEngine/Orc/LLJIT.h | 99 +-------- llvm/lib/ExecutionEngine/Orc/COFFPlatform.cpp | 95 ++++----- llvm/lib/ExecutionEngine/Orc/Core.cpp | 7 - llvm/lib/ExecutionEngine/Orc/LLJIT.cpp | 201 +++--------------- .../ExecutionEngine/OrcLazy/emulated-tls.ll | 2 +- llvm/tools/lli/lli.cpp | 93 +++++--- 8 files changed, 140 insertions(+), 381 deletions(-) diff --git a/llvm/include/llvm/ExecutionEngine/Orc/COFFPlatform.h b/llvm/include/llvm/ExecutionEngine/Orc/COFFPlatform.h index 4ef208dbbca22..969c6f0b15afc 100644 --- a/llvm/include/llvm/ExecutionEngine/Orc/COFFPlatform.h +++ b/llvm/include/llvm/ExecutionEngine/Orc/COFFPlatform.h @@ -39,14 +39,6 @@ class COFFPlatform : public Platform { /// Try to create a COFFPlatform instance, adding the ORC runtime to the /// given JITDylib. - static Expected> - Create(ExecutionSession &ES, ObjectLinkingLayer &ObjLinkingLayer, - JITDylib &PlatformJD, - std::unique_ptr OrcRuntimeArchiveBuffer, - LoadDynamicLibrary LoadDynLibrary, bool StaticVCRuntime = false, - const char *VCRuntimePath = nullptr, - std::optional RuntimeAliases = std::nullopt); - static Expected> Create(ExecutionSession &ES, ObjectLinkingLayer &ObjLinkingLayer, JITDylib &PlatformJD, const char *OrcRuntimePath, @@ -144,14 +136,10 @@ class COFFPlatform : public Platform { static bool supportedTarget(const Triple &TT); - COFFPlatform( - ExecutionSession &ES, ObjectLinkingLayer &ObjLinkingLayer, - JITDylib &PlatformJD, - std::unique_ptr OrcRuntimeGenerator, - std::unique_ptr OrcRuntimeArchiveBuffer, - std::unique_ptr OrcRuntimeArchive, - LoadDynamicLibrary LoadDynLibrary, bool StaticVCRuntime, - const char *VCRuntimePath, Error &Err); + COFFPlatform(ExecutionSession &ES, ObjectLinkingLayer &ObjLinkingLayer, + JITDylib &PlatformJD, const char *OrcRuntimePath, + LoadDynamicLibrary LoadDynamicLibrary, bool StaticVCRuntime, + const char *VCRuntimePath, Error &Err); // Associate COFFPlatform JIT-side runtime support functions with handlers. Error associateRuntimeSupportFunctions(JITDylib &PlatformJD); diff --git a/llvm/include/llvm/ExecutionEngine/Orc/Core.h b/llvm/include/llvm/ExecutionEngine/Orc/Core.h index ff391e1671cf4..adab75d3aaf15 100644 --- a/llvm/include/llvm/ExecutionEngine/Orc/Core.h +++ b/llvm/include/llvm/ExecutionEngine/Orc/Core.h @@ -1054,10 +1054,6 @@ class JITDylib : public ThreadSafeRefCountedBase, void setLinkOrder(JITDylibSearchOrder NewSearchOrder, bool LinkAgainstThisJITDylibFirst = true); - /// Append the given JITDylibSearchOrder to the link order for this - /// JITDylib. - void addToLinkOrder(const JITDylibSearchOrder &NewLinks); - /// Add the given JITDylib to the link order for definitions in this /// JITDylib. /// diff --git a/llvm/include/llvm/ExecutionEngine/Orc/LLJIT.h b/llvm/include/llvm/ExecutionEngine/Orc/LLJIT.h index e347c5de71882..2982a7af09b05 100644 --- a/llvm/include/llvm/ExecutionEngine/Orc/LLJIT.h +++ b/llvm/include/llvm/ExecutionEngine/Orc/LLJIT.h @@ -37,7 +37,7 @@ class ExecutorProcessControl; class LLJIT { template friend class LLJITBuilderSetters; - friend Expected setUpGenericLLVMIRPlatform(LLJIT &J); + friend void setUpGenericLLVMIRPlatform(LLJIT &J); public: /// Initializer support for LLJIT. @@ -70,20 +70,6 @@ class LLJIT { /// Returns a reference to the JITDylib representing the JIT'd main program. JITDylib &getMainJITDylib() { return *Main; } - /// Returns the ProcessSymbols JITDylib, which by default reflects non-JIT'd - /// symbols in the host process. - /// - /// Note: JIT'd code should not be added to the ProcessSymbols JITDylib. Use - /// the main JITDylib or a custom JITDylib instead. - JITDylibSP getProcessSymbolsJITDylib(); - - /// Returns the Platform JITDylib, which will contain the ORC runtime (if - /// given) and any platform symbols. - /// - /// Note: JIT'd code should not be added to the Platform JITDylib. Use the - /// main JITDylib or a custom JITDylib instead. - JITDylibSP getPlatformJITDylib(); - /// Returns the JITDylib with the given name, or nullptr if no JITDylib with /// that name exists. JITDylib *getJITDylibByName(StringRef Name) { @@ -96,12 +82,9 @@ class LLJIT { /// input or elsewhere in the environment then the client should check /// (e.g. by calling getJITDylibByName) that the given name is not already in /// use. - Expected createJITDylib(std::string Name); - - /// Returns the default link order for this LLJIT instance. This link order - /// will be appended to the link order of JITDylibs created by LLJIT's - /// createJITDylib method. - JITDylibSearchOrder defaultLinkOrder() { return DefaultLinks; } + Expected createJITDylib(std::string Name) { + return ES->createJITDylib(std::move(Name)); + } /// Adds an IR module with the given ResourceTracker. Error addIRModule(ResourceTrackerSP RT, ThreadSafeModule TSM); @@ -220,10 +203,6 @@ class LLJIT { std::unique_ptr PS; JITDylib *Main = nullptr; - JITDylib *ProcessSymbols = nullptr; - JITDylib *Platform = nullptr; - - JITDylibSearchOrder DefaultLinks; DataLayout DL; Triple TT; @@ -279,17 +258,12 @@ class LLJITBuilderState { std::function>( JITTargetMachineBuilder JTMB)>; - using ProcessSymbolsJITDylibSetupFunction = - std::function; - - using PlatformSetupFunction = unique_function(LLJIT &J)>; + using PlatformSetupFunction = std::function; std::unique_ptr EPC; std::unique_ptr ES; std::optional JTMB; std::optional DL; - bool LinkProcessSymbolsJITDylibByDefault = true; - ProcessSymbolsJITDylibSetupFunction SetupProcessSymbolsJITDylib; ObjectLinkingLayerCreator CreateObjectLinkingLayer; CompileFunctionCreator CreateCompileFunction; PlatformSetupFunction SetUpPlatform; @@ -342,29 +316,6 @@ class LLJITBuilderSetters { return impl(); } - /// The LinkProcessSymbolsJITDylibDyDefault flag determines whether the - /// "Process" JITDylib will be added to the default link order at LLJIT - /// construction time. If true, the Process JITDylib will be added as the last - /// item in the default link order. If false (or if the Process JITDylib is - /// disabled via setProcessSymbolsJITDylibSetup) then the Process JITDylib - /// will not appear in the default link order. - SetterImpl & - setLinkProcessSymbolsJITDylibByDefault(bool LinkProcessSymsByDefault) { - impl().LinkProcessSymbolsJITDylibByDefault = LinkProcessSymsByDefault; - return impl(); - } - - /// Set a setup function for the process symbols dylib. If not provided, - /// but LinkProcessSymbolsJITDylibByDefault is true, then the process-symbols - /// JITDylib will be configured with a DynamicLibrarySearchGenerator with a - /// default symbol filter. - SetterImpl &setProcessSymbolsJITDylibSetup( - LLJITBuilderState::ProcessSymbolsJITDylibSetupFunction - SetupProcessSymbolsJITDylib) { - impl().SetupProcessSymbolsJITDylib = std::move(SetupProcessSymbolsJITDylib); - return impl(); - } - /// Set an ObjectLinkingLayer creation function. /// /// If this method is not called, a default creation function will be used @@ -496,52 +447,20 @@ class LLLazyJITBuilder public LLLazyJITBuilderSetters {}; -/// Configure the LLJIT instance to use orc runtime support. This overload -/// assumes that the client has manually configured a Platform object. -Error setUpOrcPlatformManually(LLJIT &J); - -/// Configure the LLJIT instance to use the ORC runtime and the detected -/// native target for the executor. -class SetUpExecutorNativePlatform { -public: - /// Set up using path to Orc runtime. CreatePlatformJD will be run before - /// attempting to construct the platform instance. It should be used (if - /// needed) to provide the offers an opportunity - /// to load process symbols. - SetUpExecutorNativePlatform(std::string OrcRuntimePath) - : OrcRuntime(std::move(OrcRuntimePath)) {} - - /// Set up using the given memory buffer. - SetUpExecutorNativePlatform(std::unique_ptr OrcRuntimeMB) - : OrcRuntime(std::move(OrcRuntimeMB)) {} - - // TODO: add compiler-rt. - - /// Add a path to the VC runtime. - SetUpExecutorNativePlatform &addVCRuntime(std::string VCRuntimePath, - bool StaticVCRuntime) { - VCRuntime = {std::move(VCRuntimePath), StaticVCRuntime}; - return *this; - } - - Expected operator()(LLJIT &J); - -private: - std::variant> OrcRuntime; - std::optional> VCRuntime; -}; +/// Configure the LLJIT instance to use orc runtime support. +Error setUpOrcPlatform(LLJIT& J); /// Configure the LLJIT instance to scrape modules for llvm.global_ctors and /// llvm.global_dtors variables and (if present) build initialization and /// deinitialization functions. Platform specific initialization configurations /// should be preferred where available. -Expected setUpGenericLLVMIRPlatform(LLJIT &J); +void setUpGenericLLVMIRPlatform(LLJIT &J); /// Configure the LLJIT instance to disable platform support explicitly. This is /// useful in two cases: for platforms that don't have such requirements and for /// platforms, that we have no explicit support yet and that don't work well /// with the generic IR platform. -Expected setUpInactivePlatform(LLJIT &J); +Error setUpInactivePlatform(LLJIT &J); } // End namespace orc } // End namespace llvm diff --git a/llvm/lib/ExecutionEngine/Orc/COFFPlatform.cpp b/llvm/lib/ExecutionEngine/Orc/COFFPlatform.cpp index 91ae61be888fa..dfafc429843fb 100644 --- a/llvm/lib/ExecutionEngine/Orc/COFFPlatform.cpp +++ b/llvm/lib/ExecutionEngine/Orc/COFFPlatform.cpp @@ -159,11 +159,12 @@ class COFFHeaderMaterializationUnit : public MaterializationUnit { namespace llvm { namespace orc { -Expected> COFFPlatform::Create( - ExecutionSession &ES, ObjectLinkingLayer &ObjLinkingLayer, - JITDylib &PlatformJD, std::unique_ptr OrcRuntimeArchiveBuffer, - LoadDynamicLibrary LoadDynLibrary, bool StaticVCRuntime, - const char *VCRuntimePath, std::optional RuntimeAliases) { +Expected> +COFFPlatform::Create(ExecutionSession &ES, ObjectLinkingLayer &ObjLinkingLayer, + JITDylib &PlatformJD, const char *OrcRuntimePath, + LoadDynamicLibrary LoadDynLibrary, bool StaticVCRuntime, + const char *VCRuntimePath, + std::optional RuntimeAliases) { // If the target is not supported then bail out immediately. if (!supportedTarget(ES.getTargetTriple())) @@ -173,22 +174,6 @@ Expected> COFFPlatform::Create( auto &EPC = ES.getExecutorProcessControl(); - auto GeneratorArchive = - object::Archive::create(OrcRuntimeArchiveBuffer->getMemBufferRef()); - if (!GeneratorArchive) - return GeneratorArchive.takeError(); - - auto OrcRuntimeArchiveGenerator = StaticLibraryDefinitionGenerator::Create( - ObjLinkingLayer, nullptr, std::move(*GeneratorArchive)); - if (!OrcRuntimeArchiveGenerator) - return OrcRuntimeArchiveGenerator.takeError(); - - // We need a second instance of the archive (for now) for the Platform. We - // can `cantFail` this call, since if it were going to fail it would have - // failed above. - auto RuntimeArchive = cantFail( - object::Archive::create(OrcRuntimeArchiveBuffer->getMemBufferRef())); - // Create default aliases if the caller didn't supply any. if (!RuntimeAliases) RuntimeAliases = standardPlatformAliases(ES); @@ -214,30 +199,13 @@ Expected> COFFPlatform::Create( // Create the instance. Error Err = Error::success(); auto P = std::unique_ptr(new COFFPlatform( - ES, ObjLinkingLayer, PlatformJD, std::move(*OrcRuntimeArchiveGenerator), - std::move(OrcRuntimeArchiveBuffer), std::move(RuntimeArchive), + ES, ObjLinkingLayer, PlatformJD, OrcRuntimePath, std::move(LoadDynLibrary), StaticVCRuntime, VCRuntimePath, Err)); if (Err) return std::move(Err); return std::move(P); } -Expected> -COFFPlatform::Create(ExecutionSession &ES, ObjectLinkingLayer &ObjLinkingLayer, - JITDylib &PlatformJD, const char *OrcRuntimePath, - LoadDynamicLibrary LoadDynLibrary, bool StaticVCRuntime, - const char *VCRuntimePath, - std::optional RuntimeAliases) { - - auto ArchiveBuffer = MemoryBuffer::getFile(OrcRuntimePath); - if (!ArchiveBuffer) - return createFileError(OrcRuntimePath, ArchiveBuffer.getError()); - - return Create(ES, ObjLinkingLayer, PlatformJD, std::move(*ArchiveBuffer), - std::move(LoadDynLibrary), StaticVCRuntime, VCRuntimePath, - std::move(RuntimeAliases)); -} - Expected COFFPlatform::getPerJDObjectFile() { auto PerJDObj = OrcRuntimeArchive->findSym("__orc_rt_coff_per_jd_marker"); if (!PerJDObj) @@ -381,22 +349,37 @@ bool COFFPlatform::supportedTarget(const Triple &TT) { } } -COFFPlatform::COFFPlatform( - ExecutionSession &ES, ObjectLinkingLayer &ObjLinkingLayer, - JITDylib &PlatformJD, - std::unique_ptr OrcRuntimeGenerator, - std::unique_ptr OrcRuntimeArchiveBuffer, - std::unique_ptr OrcRuntimeArchive, - LoadDynamicLibrary LoadDynLibrary, bool StaticVCRuntime, - const char *VCRuntimePath, Error &Err) +COFFPlatform::COFFPlatform(ExecutionSession &ES, + ObjectLinkingLayer &ObjLinkingLayer, + JITDylib &PlatformJD, const char *OrcRuntimePath, + LoadDynamicLibrary LoadDynamicLibrary, + bool StaticVCRuntime, const char *VCRuntimePath, + Error &Err) : ES(ES), ObjLinkingLayer(ObjLinkingLayer), - LoadDynLibrary(std::move(LoadDynLibrary)), - OrcRuntimeArchiveBuffer(std::move(OrcRuntimeArchiveBuffer)), - OrcRuntimeArchive(std::move(OrcRuntimeArchive)), + LoadDynLibrary(std::move(LoadDynamicLibrary)), StaticVCRuntime(StaticVCRuntime), COFFHeaderStartSymbol(ES.intern("__ImageBase")) { ErrorAsOutParameter _(&Err); + // Create a generator for the ORC runtime archive. + auto OrcRuntimeArchiveGenerator = + StaticLibraryDefinitionGenerator::Load(ObjLinkingLayer, OrcRuntimePath); + if (!OrcRuntimeArchiveGenerator) { + Err = OrcRuntimeArchiveGenerator.takeError(); + return; + } + + auto ArchiveBuffer = MemoryBuffer::getFile(OrcRuntimePath); + if (!ArchiveBuffer) { + Err = createFileError(OrcRuntimePath, ArchiveBuffer.getError()); + return; + } + OrcRuntimeArchiveBuffer = std::move(*ArchiveBuffer); + OrcRuntimeArchive = + std::make_unique(*OrcRuntimeArchiveBuffer, Err); + if (Err) + return; + Bootstrapping.store(true); ObjLinkingLayer.addPlugin(std::make_unique(*this)); @@ -409,7 +392,7 @@ COFFPlatform::COFFPlatform( } VCRuntimeBootstrap = std::move(*VCRT); - for (auto &Lib : OrcRuntimeGenerator->getImportedDynamicLibraries()) + for (auto &Lib : (*OrcRuntimeArchiveGenerator)->getImportedDynamicLibraries()) DylibsToPreload.insert(Lib); auto ImportedLibs = @@ -423,7 +406,7 @@ COFFPlatform::COFFPlatform( for (auto &Lib : *ImportedLibs) DylibsToPreload.insert(Lib); - PlatformJD.addGenerator(std::move(OrcRuntimeGenerator)); + PlatformJD.addGenerator(std::move(*OrcRuntimeArchiveGenerator)); // PlatformJD hasn't been set up by the platform yet (since we're creating // the platform now), so set it up. @@ -433,10 +416,10 @@ COFFPlatform::COFFPlatform( } for (auto& Lib : DylibsToPreload) - if (auto E2 = this->LoadDynLibrary(PlatformJD, Lib)) { - Err = std::move(E2); - return; - } + if (auto E2 = LoadDynLibrary(PlatformJD, Lib)) { + Err = std::move(E2); + return; + } if (StaticVCRuntime) if (auto E2 = VCRuntimeBootstrap->initializeStaticVCRuntime(PlatformJD)) { diff --git a/llvm/lib/ExecutionEngine/Orc/Core.cpp b/llvm/lib/ExecutionEngine/Orc/Core.cpp index ad218317d7ab6..f85719195532d 100644 --- a/llvm/lib/ExecutionEngine/Orc/Core.cpp +++ b/llvm/lib/ExecutionEngine/Orc/Core.cpp @@ -1329,13 +1329,6 @@ void JITDylib::setLinkOrder(JITDylibSearchOrder NewLinkOrder, }); } -void JITDylib::addToLinkOrder(const JITDylibSearchOrder &NewLinks) { - ES.runSessionLocked([&]() { - LinkOrder.reserve(LinkOrder.size() + NewLinks.size()); - llvm::append_range(LinkOrder, NewLinks); - }); -} - void JITDylib::addToLinkOrder(JITDylib &JD, JITDylibLookupFlags JDLookupFlags) { ES.runSessionLocked([&]() { LinkOrder.push_back({&JD, JDLookupFlags}); }); } diff --git a/llvm/lib/ExecutionEngine/Orc/LLJIT.cpp b/llvm/lib/ExecutionEngine/Orc/LLJIT.cpp index fabbfcd2651a9..a9cc6680c9eb4 100644 --- a/llvm/lib/ExecutionEngine/Orc/LLJIT.cpp +++ b/llvm/lib/ExecutionEngine/Orc/LLJIT.cpp @@ -9,8 +9,6 @@ #include "llvm/ExecutionEngine/Orc/LLJIT.h" #include "llvm/ExecutionEngine/JITLink/EHFrameSupport.h" #include "llvm/ExecutionEngine/JITLink/JITLinkMemoryManager.h" -#include "llvm/ExecutionEngine/Orc/COFFPlatform.h" -#include "llvm/ExecutionEngine/Orc/ELFNixPlatform.h" #include "llvm/ExecutionEngine/Orc/EPCEHFrameRegistrar.h" #include "llvm/ExecutionEngine/Orc/ExecutorProcessControl.h" #include "llvm/ExecutionEngine/Orc/MachOPlatform.h" @@ -178,7 +176,7 @@ class GlobalCtorDtorScraper { /// some runtime API, including __cxa_atexit, dlopen, and dlclose. class GenericLLVMIRPlatformSupport : public LLJIT::PlatformSupport { public: - GenericLLVMIRPlatformSupport(LLJIT &J, JITDylib &PlatformJD) + GenericLLVMIRPlatformSupport(LLJIT &J) : J(J), InitFunctionPrefix(J.mangle("__orc_init_func.")), DeInitFunctionPrefix(J.mangle("__orc_deinit_func.")) { @@ -197,9 +195,10 @@ class GenericLLVMIRPlatformSupport : public LLJIT::PlatformSupport { JITEvaluatedSymbol(pointerToJITTargetAddress(registerCxaAtExitHelper), JITSymbolFlags()); - cantFail(PlatformJD.define(absoluteSymbols(std::move(StdInterposes)))); - cantFail(setupJITDylib(PlatformJD)); - cantFail(J.addIRModule(PlatformJD, createPlatformRuntimeModule())); + cantFail( + J.getMainJITDylib().define(absoluteSymbols(std::move(StdInterposes)))); + cantFail(setupJITDylib(J.getMainJITDylib())); + cantFail(J.addIRModule(J.getMainJITDylib(), createPlatformRuntimeModule())); } ExecutionSession &getExecutionSession() { return J.getExecutionSession(); } @@ -759,19 +758,6 @@ LLJIT::~LLJIT() { ES->reportError(std::move(Err)); } -JITDylibSP LLJIT::getProcessSymbolsJITDylib() { return ProcessSymbols; } - -JITDylibSP LLJIT::getPlatformJITDylib() { return Platform; } - -Expected LLJIT::createJITDylib(std::string Name) { - auto JD = ES->createJITDylib(std::move(Name)); - if (!JD) - return JD.takeError(); - - JD->addToLinkOrder(DefaultLinks); - return JD; -} - Error LLJIT::addIRModule(ResourceTrackerSP RT, ThreadSafeModule TSM) { assert(TSM && "Can not add null module"); @@ -876,6 +862,13 @@ LLJIT::LLJIT(LLJITBuilderState &S, Error &Err) } } + if (auto MainOrErr = this->ES->createJITDylib("main")) + Main = &*MainOrErr; + else { + Err = MainOrErr.takeError(); + return; + } + if (S.DL) DL = std::move(*S.DL); else if (auto DLOrErr = S.JTMB->getDefaultDataLayoutForTarget()) @@ -923,47 +916,10 @@ LLJIT::LLJIT(LLJITBuilderState &S, Error &Err) }); } - if (S.LinkProcessSymbolsJITDylibByDefault && !S.SetupProcessSymbolsJITDylib) - S.SetupProcessSymbolsJITDylib = [this](JITDylib &JD) -> Error { - auto G = orc::DynamicLibrarySearchGenerator::GetForCurrentProcess( - DL.getGlobalPrefix()); - if (!G) - return G.takeError(); - JD.addGenerator(std::move(*G)); - return Error::success(); - }; - - if (S.SetupProcessSymbolsJITDylib) { - ProcessSymbols = &ES->createBareJITDylib(""); - if (auto Err2 = S.SetupProcessSymbolsJITDylib(*ProcessSymbols)) { - Err = std::move(Err2); - return; - } - } - - if (!S.SetUpPlatform) - S.SetUpPlatform = setUpGenericLLVMIRPlatform; - - if (auto PlatformJDOrErr = S.SetUpPlatform(*this)) { - Platform = PlatformJDOrErr->get(); - if (Platform) - DefaultLinks.push_back( - {Platform, JITDylibLookupFlags::MatchExportedSymbolsOnly}); - } else { - Err = PlatformJDOrErr.takeError(); - return; - } - - if (S.LinkProcessSymbolsJITDylibByDefault) - DefaultLinks.push_back( - {ProcessSymbols, JITDylibLookupFlags::MatchExportedSymbolsOnly}); - - if (auto MainOrErr = createJITDylib("main")) - Main = &*MainOrErr; - else { - Err = MainOrErr.takeError(); - return; - } + if (S.SetUpPlatform) + Err = S.SetUpPlatform(*this); + else + setUpGenericLLVMIRPlatform(*this); } std::string LLJIT::mangle(StringRef UnmangledName) const { @@ -989,133 +945,24 @@ Error LLJIT::applyDataLayout(Module &M) { return Error::success(); } -Error setUpOrcPlatformManually(LLJIT &J) { - LLVM_DEBUG({ dbgs() << "Setting up orc platform support for LLJIT\n"; }); - J.setPlatformSupport(std::make_unique(J)); - return Error::success(); -} - -class LoadAndLinkDynLibrary { -public: - LoadAndLinkDynLibrary(LLJIT &J) : J(J) {} - Error operator()(JITDylib &JD, StringRef DLLName) { - if (!DLLName.endswith_insensitive(".dll")) - return make_error("DLLName not ending with .dll", - inconvertibleErrorCode()); - // TODO: Actually load library. - (void)J; +Error setUpOrcPlatform(LLJIT& J) { + LLVM_DEBUG( + { dbgs() << "Setting up orc platform support for LLJIT\n"; }); + J.setPlatformSupport(std::make_unique(J)); return Error::success(); - } - -private: - LLJIT &J; -}; - -Expected SetUpExecutorNativePlatform::operator()(LLJIT &J) { - auto ProcessSymbolsJD = J.getProcessSymbolsJITDylib(); - if (!ProcessSymbolsJD) - return make_error( - "Native platforms require a process symbols JITDylib", - inconvertibleErrorCode()); - - const Triple &TT = J.getTargetTriple(); - ObjectLinkingLayer *ObjLinkingLayer = - dyn_cast(&J.getObjLinkingLayer()); - - if (!ObjLinkingLayer) - return make_error( - "SetUpTargetPlatform requires ObjectLinkingLayer", - inconvertibleErrorCode()); - - std::unique_ptr RuntimeArchiveBuffer; - if (OrcRuntime.index() == 0) { - auto A = errorOrToExpected(MemoryBuffer::getFile(std::get<0>(OrcRuntime))); - if (!A) - return A.takeError(); - RuntimeArchiveBuffer = std::move(*A); - } else - RuntimeArchiveBuffer = std::move(std::get<1>(OrcRuntime)); - - auto &ES = J.getExecutionSession(); - auto &PlatformJD = ES.createBareJITDylib(""); - PlatformJD.addToLinkOrder(*ProcessSymbolsJD); - - J.setPlatformSupport(std::make_unique(J)); - - switch (TT.getObjectFormat()) { - case Triple::COFF: { - const char *VCRuntimePath = nullptr; - bool StaticVCRuntime = false; - if (VCRuntime) { - VCRuntimePath = VCRuntime->first.c_str(); - StaticVCRuntime = VCRuntime->second; - } - if (auto P = COFFPlatform::Create( - ES, *ObjLinkingLayer, PlatformJD, std::move(RuntimeArchiveBuffer), - LoadAndLinkDynLibrary(J), StaticVCRuntime, VCRuntimePath)) - J.getExecutionSession().setPlatform(std::move(*P)); - else - return P.takeError(); - break; - } - case Triple::ELF: { - auto G = StaticLibraryDefinitionGenerator::Create( - *ObjLinkingLayer, std::move(RuntimeArchiveBuffer)); - if (!G) - return G.takeError(); - - if (auto P = ELFNixPlatform::Create(ES, *ObjLinkingLayer, PlatformJD, - std::move(*G))) - J.getExecutionSession().setPlatform(std::move(*P)); - else - return P.takeError(); - break; - } - case Triple::MachO: { - auto G = StaticLibraryDefinitionGenerator::Create( - *ObjLinkingLayer, std::move(RuntimeArchiveBuffer)); - if (!G) - return G.takeError(); - - if (auto P = MachOPlatform::Create(ES, *ObjLinkingLayer, PlatformJD, - std::move(*G))) - ES.setPlatform(std::move(*P)); - else - return P.takeError(); - break; - } - default: - return make_error("Unsupported object format in triple " + - TT.str(), - inconvertibleErrorCode()); - } - - return &PlatformJD; } -Expected setUpGenericLLVMIRPlatform(LLJIT &J) { +void setUpGenericLLVMIRPlatform(LLJIT &J) { LLVM_DEBUG( { dbgs() << "Setting up GenericLLVMIRPlatform support for LLJIT\n"; }); - auto ProcessSymbolsJD = J.getProcessSymbolsJITDylib(); - if (!ProcessSymbolsJD) - return make_error( - "Native platforms require a process symbols JITDylib", - inconvertibleErrorCode()); - - auto &PlatformJD = J.getExecutionSession().createBareJITDylib(""); - PlatformJD.addToLinkOrder(*ProcessSymbolsJD); - - J.setPlatformSupport( - std::make_unique(J, PlatformJD)); - - return &PlatformJD; + J.setPlatformSupport(std::make_unique(J)); } -Expected setUpInactivePlatform(LLJIT &J) { +Error setUpInactivePlatform(LLJIT &J) { LLVM_DEBUG( { dbgs() << "Explicitly deactivated platform support for LLJIT\n"; }); J.setPlatformSupport(std::make_unique()); - return nullptr; + return Error::success(); } Error LLLazyJITBuilderState::prepareForConstruction() { diff --git a/llvm/test/ExecutionEngine/OrcLazy/emulated-tls.ll b/llvm/test/ExecutionEngine/OrcLazy/emulated-tls.ll index 6310be47d3c4c..51a5905feefa9 100644 --- a/llvm/test/ExecutionEngine/OrcLazy/emulated-tls.ll +++ b/llvm/test/ExecutionEngine/OrcLazy/emulated-tls.ll @@ -1,7 +1,7 @@ ; LoongArch does not support emulated tls. ; UNSUPPORTED: target=loongarch{{.*}} -; RUN: not lli -emulated-tls -jit-kind=orc-lazy %s 2>&1 \ +; RUN: not lli -no-process-syms -emulated-tls -jit-kind=orc-lazy %s 2>&1 \ ; RUN: | FileCheck %s ; ; Test that emulated-tls does not generate any unexpected errors. diff --git a/llvm/tools/lli/lli.cpp b/llvm/tools/lli/lli.cpp index 33270c6276943..ff73ac18f5eee 100644 --- a/llvm/tools/lli/lli.cpp +++ b/llvm/tools/lli/lli.cpp @@ -27,6 +27,7 @@ #include "llvm/ExecutionEngine/ObjectCache.h" #include "llvm/ExecutionEngine/Orc/DebugObjectManagerPlugin.h" #include "llvm/ExecutionEngine/Orc/DebugUtils.h" +#include "llvm/ExecutionEngine/Orc/ELFNixPlatform.h" #include "llvm/ExecutionEngine/Orc/EPCDebugObjectRegistrar.h" #include "llvm/ExecutionEngine/Orc/EPCDynamicLibrarySearchGenerator.h" #include "llvm/ExecutionEngine/Orc/EPCEHFrameRegistrar.h" @@ -34,6 +35,7 @@ #include "llvm/ExecutionEngine/Orc/ExecutionUtils.h" #include "llvm/ExecutionEngine/Orc/JITTargetMachineBuilder.h" #include "llvm/ExecutionEngine/Orc/LLJIT.h" +#include "llvm/ExecutionEngine/Orc/MachOPlatform.h" #include "llvm/ExecutionEngine/Orc/RTDyldObjectLinkingLayer.h" #include "llvm/ExecutionEngine/Orc/SimpleRemoteEPC.h" #include "llvm/ExecutionEngine/Orc/SymbolStringPool.h" @@ -234,22 +236,20 @@ namespace { cl::desc("Do not resolve lli process symbols in JIT'd code"), cl::init(false)); - enum class LLJITPlatform { Inactive, Auto, ExecutorNative, GenericIR }; - - cl::opt Platform( - "lljit-platform", cl::desc("Platform to use with LLJIT"), - cl::init(LLJITPlatform::Auto), - cl::values(clEnumValN(LLJITPlatform::Auto, "Auto", - "Like 'ExecutorNative' if ORC runtime " - "provided, otherwise like 'GenericIR'"), - clEnumValN(LLJITPlatform::ExecutorNative, "ExecutorNative", - "Use the native platform for the executor." - "Requires -orc-runtime"), - clEnumValN(LLJITPlatform::GenericIR, "GenericIR", - "Use LLJITGenericIRPlatform"), - clEnumValN(LLJITPlatform::Inactive, "Inactive", - "Disable platform support explicitly")), - cl::Hidden); + enum class LLJITPlatform { Inactive, DetectHost, ORC, GenericIR }; + + cl::opt + Platform("lljit-platform", cl::desc("Platform to use with LLJIT"), + cl::init(LLJITPlatform::DetectHost), + cl::values(clEnumValN(LLJITPlatform::DetectHost, "DetectHost", + "Select based on JIT target triple"), + clEnumValN(LLJITPlatform::ORC, "ORC", + "Use ORCPlatform with the ORC runtime"), + clEnumValN(LLJITPlatform::GenericIR, "GenericIR", + "Use LLJITGenericIRPlatform"), + clEnumValN(LLJITPlatform::Inactive, "Inactive", + "Disable platform support explicitly")), + cl::Hidden); enum class DumpKind { NoDump, @@ -864,9 +864,6 @@ int runOrcJIT(const char *ProgName) { .setRelocationModel(codegen::getExplicitRelocModel()) .setCodeModel(codegen::getExplicitCodeModel()); - // Link process symbols unless NoProcessSymbols is set. - Builder.setLinkProcessSymbolsJITDylibByDefault(!NoProcessSymbols); - // FIXME: Setting a dummy call-through manager in non-lazy mode prevents the // JIT builder to instantiate a default (which would fail with an error for // unsupported architectures). @@ -907,15 +904,17 @@ int runOrcJIT(const char *ProgName) { // Set up LLJIT platform. LLJITPlatform P = Platform; - if (P == LLJITPlatform::Auto) - P = OrcRuntime.empty() ? LLJITPlatform::GenericIR - : LLJITPlatform::ExecutorNative; - + if (P == LLJITPlatform::DetectHost) { + if (JITLinker == JITLinkerKind::JITLink && !OrcRuntime.empty() && + (TT->isOSBinFormatMachO() || TT->isOSBinFormatELF())) + P = LLJITPlatform::ORC; + else + P = LLJITPlatform::GenericIR; + } switch (P) { - case LLJITPlatform::ExecutorNative: { - Builder.setPlatformSetUp(orc::SetUpExecutorNativePlatform(OrcRuntime)); + case LLJITPlatform::ORC: + Builder.setPlatformSetUp(orc::setUpOrcPlatform); break; - } case LLJITPlatform::GenericIR: // Nothing to do: LLJITBuilder will use this by default. break; @@ -934,7 +933,7 @@ int runOrcJIT(const char *ProgName) { Builder.setObjectLinkingLayerCreator([&EPC, &P](orc::ExecutionSession &ES, const Triple &TT) { auto L = std::make_unique(ES, EPC->getMemMgr()); - if (P != LLJITPlatform::ExecutorNative) { + if (P != LLJITPlatform::ORC) { L->addPlugin(std::make_unique( ES, ExitOnErr(orc::EPCEHFrameRegistrar::Create(ES)))); L->addPlugin(std::make_unique( @@ -982,12 +981,46 @@ int runOrcJIT(const char *ProgName) { return TSM; }); - if (GenerateBuiltinFunctions.size() > 0) { - // Add LLI builtins. - orc::MangleAndInterner Mangle(J->getExecutionSession(), J->getDataLayout()); + orc::MangleAndInterner Mangle(J->getExecutionSession(), J->getDataLayout()); + + // Unless they've been explicitly disabled, make process symbols available to + // JIT'd code. + if (!NoProcessSymbols) + J->getMainJITDylib().addGenerator( + ExitOnErr(orc::DynamicLibrarySearchGenerator::GetForCurrentProcess( + J->getDataLayout().getGlobalPrefix(), + [MainName = Mangle("main")](const orc::SymbolStringPtr &Name) { + return Name != MainName; + }))); + + if (GenerateBuiltinFunctions.size() > 0) J->getMainJITDylib().addGenerator( std::make_unique(GenerateBuiltinFunctions, Mangle)); + + if (P == LLJITPlatform::ORC) { + if (auto *OLL = llvm::dyn_cast(ObjLayer)) { + auto &ES = J->getExecutionSession(); + if (TT->isOSBinFormatMachO()) { + if (auto P = llvm::orc::MachOPlatform::Create( + ES, *OLL, J->getMainJITDylib(), OrcRuntime.c_str())) + ES.setPlatform(std::move(*P)); + else + ExitOnErr(P.takeError()); + } else if (TT->isOSBinFormatELF()) { + if (auto P = llvm::orc::ELFNixPlatform::Create( + ES, *OLL, J->getMainJITDylib(), OrcRuntime.c_str())) + ES.setPlatform(std::move(*P)); + else + ExitOnErr(P.takeError()); + } else { + errs() << "No ORC platform support\n"; + exit(1); + } + } else { + errs() << "ORC platform requires JITLink\n"; + exit(1); + } } // Regular modules are greedy: They materialize as a whole and trigger