diff options
author | Rafael Espindola <rafael.espindola@gmail.com> | 2014-08-19 04:04:25 +0000 |
---|---|---|
committer | Rafael Espindola <rafael.espindola@gmail.com> | 2014-08-19 04:04:25 +0000 |
commit | 3f4ed32b4398eaf4fe0080d8001ba01e6c2f43c8 (patch) | |
tree | 961679644a48b563e0febf6499460ea12c247b95 /lib/ExecutionEngine | |
parent | 4d48c3f2a498d169af596871cd23ce7b6e961d43 (diff) |
Make it explicit that ExecutionEngine takes ownership of the modules.
git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@215967 91177308-0d34-0410-b5e6-96231b3b80d8
Diffstat (limited to 'lib/ExecutionEngine')
-rw-r--r-- | lib/ExecutionEngine/ExecutionEngine.cpp | 34 | ||||
-rw-r--r-- | lib/ExecutionEngine/ExecutionEngineBindings.cpp | 10 | ||||
-rw-r--r-- | lib/ExecutionEngine/Interpreter/Interpreter.cpp | 13 | ||||
-rw-r--r-- | lib/ExecutionEngine/Interpreter/Interpreter.h | 9 | ||||
-rw-r--r-- | lib/ExecutionEngine/JIT/JIT.cpp | 38 | ||||
-rw-r--r-- | lib/ExecutionEngine/JIT/JIT.h | 6 | ||||
-rw-r--r-- | lib/ExecutionEngine/MCJIT/MCJIT.cpp | 34 | ||||
-rw-r--r-- | lib/ExecutionEngine/MCJIT/MCJIT.h | 11 |
8 files changed, 80 insertions, 75 deletions
diff --git a/lib/ExecutionEngine/ExecutionEngine.cpp b/lib/ExecutionEngine/ExecutionEngine.cpp index a41dd26ee68..4ef6e73c131 100644 --- a/lib/ExecutionEngine/ExecutionEngine.cpp +++ b/lib/ExecutionEngine/ExecutionEngine.cpp @@ -49,20 +49,20 @@ void ObjectBuffer::anchor() {} void ObjectBufferStream::anchor() {} ExecutionEngine *(*ExecutionEngine::JITCtor)( - Module *M, + std::unique_ptr<Module> M, std::string *ErrorStr, JITMemoryManager *JMM, bool GVsWithCode, TargetMachine *TM) = nullptr; ExecutionEngine *(*ExecutionEngine::MCJITCtor)( - Module *M, + std::unique_ptr<Module >M, std::string *ErrorStr, RTDyldMemoryManager *MCJMM, TargetMachine *TM) = nullptr; -ExecutionEngine *(*ExecutionEngine::InterpCtor)(Module *M, +ExecutionEngine *(*ExecutionEngine::InterpCtor)(std::unique_ptr<Module> M, std::string *ErrorStr) =nullptr; -ExecutionEngine::ExecutionEngine(Module *M) +ExecutionEngine::ExecutionEngine(std::unique_ptr<Module> M) : EEState(*this), LazyFunctionCreator(nullptr) { CompilingLazily = false; @@ -77,14 +77,12 @@ ExecutionEngine::ExecutionEngine(Module *M) VerifyModules = false; #endif - Modules.push_back(M); assert(M && "Module is null?"); + Modules.push_back(std::move(M)); } ExecutionEngine::~ExecutionEngine() { clearAllGlobalMappings(); - for (unsigned i = 0, e = Modules.size(); i != e; ++i) - delete Modules[i]; } namespace { @@ -131,10 +129,10 @@ void ExecutionEngine::addArchive(std::unique_ptr<object::Archive> A) { } bool ExecutionEngine::removeModule(Module *M) { - for(SmallVectorImpl<Module *>::iterator I = Modules.begin(), - E = Modules.end(); I != E; ++I) { - Module *Found = *I; + for (auto I = Modules.begin(), E = Modules.end(); I != E; ++I) { + Module *Found = I->get(); if (Found == M) { + I->release(); Modules.erase(I); clearGlobalMappingsFromModule(M); return true; @@ -307,10 +305,10 @@ void *ArgvArray::reset(LLVMContext &C, ExecutionEngine *EE, return Array; } -void ExecutionEngine::runStaticConstructorsDestructors(Module *module, +void ExecutionEngine::runStaticConstructorsDestructors(Module &module, bool isDtors) { const char *Name = isDtors ? "llvm.global_dtors" : "llvm.global_ctors"; - GlobalVariable *GV = module->getNamedGlobal(Name); + GlobalVariable *GV = module.getNamedGlobal(Name); // If this global has internal linkage, or if it has a use, then it must be // an old-style (llvmgcc3) static ctor with __main linked in and in use. If @@ -348,8 +346,8 @@ void ExecutionEngine::runStaticConstructorsDestructors(Module *module, void ExecutionEngine::runStaticConstructorsDestructors(bool isDtors) { // Execute global ctors/dtors for each module in the program. - for (Module *M : Modules) - runStaticConstructorsDestructors(M, isDtors); + for (std::unique_ptr<Module> &M : Modules) + runStaticConstructorsDestructors(*M, isDtors); } #ifndef NDEBUG @@ -474,10 +472,10 @@ ExecutionEngine *EngineBuilder::create(TargetMachine *TM) { ExecutionEngine *EE = nullptr; if (UseMCJIT && ExecutionEngine::MCJITCtor) - EE = ExecutionEngine::MCJITCtor(M, ErrorStr, MCJMM ? MCJMM : JMM, - TheTM.release()); + EE = ExecutionEngine::MCJITCtor(std::move(M), ErrorStr, + MCJMM ? MCJMM : JMM, TheTM.release()); else if (ExecutionEngine::JITCtor) - EE = ExecutionEngine::JITCtor(M, ErrorStr, JMM, + EE = ExecutionEngine::JITCtor(std::move(M), ErrorStr, JMM, AllocateGVsWithCode, TheTM.release()); if (EE) { @@ -490,7 +488,7 @@ ExecutionEngine *EngineBuilder::create(TargetMachine *TM) { // an interpreter instead. if (WhichEngine & EngineKind::Interpreter) { if (ExecutionEngine::InterpCtor) - return ExecutionEngine::InterpCtor(M, ErrorStr); + return ExecutionEngine::InterpCtor(std::move(M), ErrorStr); if (ErrorStr) *ErrorStr = "Interpreter has not been linked in."; return nullptr; diff --git a/lib/ExecutionEngine/ExecutionEngineBindings.cpp b/lib/ExecutionEngine/ExecutionEngineBindings.cpp index 6ff1e7ac063..9ce194c0017 100644 --- a/lib/ExecutionEngine/ExecutionEngineBindings.cpp +++ b/lib/ExecutionEngine/ExecutionEngineBindings.cpp @@ -110,7 +110,7 @@ LLVMBool LLVMCreateExecutionEngineForModule(LLVMExecutionEngineRef *OutEE, LLVMModuleRef M, char **OutError) { std::string Error; - EngineBuilder builder(unwrap(M)); + EngineBuilder builder(std::unique_ptr<Module>(unwrap(M))); builder.setEngineKind(EngineKind::Either) .setErrorStr(&Error); if (ExecutionEngine *EE = builder.create()){ @@ -125,7 +125,7 @@ LLVMBool LLVMCreateInterpreterForModule(LLVMExecutionEngineRef *OutInterp, LLVMModuleRef M, char **OutError) { std::string Error; - EngineBuilder builder(unwrap(M)); + EngineBuilder builder(std::unique_ptr<Module>(unwrap(M))); builder.setEngineKind(EngineKind::Interpreter) .setErrorStr(&Error); if (ExecutionEngine *Interp = builder.create()) { @@ -141,7 +141,7 @@ LLVMBool LLVMCreateJITCompilerForModule(LLVMExecutionEngineRef *OutJIT, unsigned OptLevel, char **OutError) { std::string Error; - EngineBuilder builder(unwrap(M)); + EngineBuilder builder(std::unique_ptr<Module>(unwrap(M))); builder.setEngineKind(EngineKind::JIT) .setErrorStr(&Error) .setOptLevel((CodeGenOpt::Level)OptLevel); @@ -189,7 +189,7 @@ LLVMBool LLVMCreateMCJITCompilerForModule( targetOptions.EnableFastISel = options.EnableFastISel; std::string Error; - EngineBuilder builder(unwrap(M)); + EngineBuilder builder(std::unique_ptr<Module>(unwrap(M))); builder.setEngineKind(EngineKind::JIT) .setErrorStr(&Error) .setUseMCJIT(true) @@ -279,7 +279,7 @@ void LLVMFreeMachineCodeForFunction(LLVMExecutionEngineRef EE, LLVMValueRef F) { } void LLVMAddModule(LLVMExecutionEngineRef EE, LLVMModuleRef M){ - unwrap(EE)->addModule(unwrap(M)); + unwrap(EE)->addModule(std::unique_ptr<Module>(unwrap(M))); } void LLVMAddModuleProvider(LLVMExecutionEngineRef EE, LLVMModuleProviderRef MP){ diff --git a/lib/ExecutionEngine/Interpreter/Interpreter.cpp b/lib/ExecutionEngine/Interpreter/Interpreter.cpp index 814efcc27fc..8562981b629 100644 --- a/lib/ExecutionEngine/Interpreter/Interpreter.cpp +++ b/lib/ExecutionEngine/Interpreter/Interpreter.cpp @@ -30,9 +30,10 @@ static struct RegisterInterp { extern "C" void LLVMLinkInInterpreter() { } -/// create - Create a new interpreter object. This can never fail. +/// Create a new interpreter object. /// -ExecutionEngine *Interpreter::create(Module *M, std::string* ErrStr) { +ExecutionEngine *Interpreter::create(std::unique_ptr<Module> M, + std::string *ErrStr) { // Tell this Module to materialize everything and release the GVMaterializer. if (std::error_code EC = M->materializeAllPermanently()) { if (ErrStr) @@ -41,15 +42,15 @@ ExecutionEngine *Interpreter::create(Module *M, std::string* ErrStr) { return nullptr; } - return new Interpreter(M); + return new Interpreter(std::move(M)); } //===----------------------------------------------------------------------===// // Interpreter ctor - Initialize stuff // -Interpreter::Interpreter(Module *M) - : ExecutionEngine(M), TD(M) { - +Interpreter::Interpreter(std::unique_ptr<Module> M) + : ExecutionEngine(std::move(M)), TD(Modules.back().get()) { + memset(&ExitValue.Untyped, 0, sizeof(ExitValue.Untyped)); setDataLayout(&TD); // Initialize the "backend" diff --git a/lib/ExecutionEngine/Interpreter/Interpreter.h b/lib/ExecutionEngine/Interpreter/Interpreter.h index 84a1c6b1ba3..4a5fbb96dfd 100644 --- a/lib/ExecutionEngine/Interpreter/Interpreter.h +++ b/lib/ExecutionEngine/Interpreter/Interpreter.h @@ -94,7 +94,7 @@ class Interpreter : public ExecutionEngine, public InstVisitor<Interpreter> { std::vector<Function*> AtExitHandlers; public: - explicit Interpreter(Module *M); + explicit Interpreter(std::unique_ptr<Module> M); ~Interpreter(); /// runAtExitHandlers - Run any functions registered by the program's calls to @@ -105,10 +105,11 @@ public: static void Register() { InterpCtor = create; } - - /// create - Create an interpreter ExecutionEngine. This can never fail. + + /// Create an interpreter ExecutionEngine. /// - static ExecutionEngine *create(Module *M, std::string *ErrorStr = nullptr); + static ExecutionEngine *create(std::unique_ptr<Module> M, + std::string *ErrorStr = nullptr); /// run - Start execution with the specified function and arguments. /// diff --git a/lib/ExecutionEngine/JIT/JIT.cpp b/lib/ExecutionEngine/JIT/JIT.cpp index ab0c1a680bd..063b35f478c 100644 --- a/lib/ExecutionEngine/JIT/JIT.cpp +++ b/lib/ExecutionEngine/JIT/JIT.cpp @@ -69,10 +69,9 @@ static struct RegisterJIT { extern "C" void LLVMLinkInJIT() { } -/// createJIT - This is the factory method for creating a JIT for the current -/// machine, it does not fall back to the interpreter. This takes ownership -/// of the module. -ExecutionEngine *JIT::createJIT(Module *M, +/// This is the factory method for creating a JIT for the current machine, it +/// does not fall back to the interpreter. +ExecutionEngine *JIT::createJIT(std::unique_ptr<Module> M, std::string *ErrorStr, JITMemoryManager *JMM, bool GVsWithCode, @@ -84,7 +83,7 @@ ExecutionEngine *JIT::createJIT(Module *M, // If the target supports JIT code generation, create the JIT. if (TargetJITInfo *TJ = TM->getSubtargetImpl()->getJITInfo()) { - return new JIT(M, *TM, *TJ, JMM, GVsWithCode); + return new JIT(std::move(M), *TM, *TJ, JMM, GVsWithCode); } else { if (ErrorStr) *ErrorStr = "target does not support JIT code generation"; @@ -135,14 +134,15 @@ extern "C" { } } -JIT::JIT(Module *M, TargetMachine &tm, TargetJITInfo &tji, +JIT::JIT(std::unique_ptr<Module> M, TargetMachine &tm, TargetJITInfo &tji, JITMemoryManager *jmm, bool GVsWithCode) - : ExecutionEngine(M), TM(tm), TJI(tji), + : ExecutionEngine(std::move(M)), TM(tm), TJI(tji), JMM(jmm ? jmm : JITMemoryManager::CreateDefaultMemManager()), AllocateGVsWithCode(GVsWithCode), isAlreadyCodeGenerating(false) { setDataLayout(TM.getSubtargetImpl()->getDataLayout()); - jitstate = new JITState(M); + Module *Mod = Modules.back().get(); + jitstate = new JITState(Mod); // Initialize JCE JCE = createEmitter(*this, JMM, TM); @@ -153,8 +153,8 @@ JIT::JIT(Module *M, TargetMachine &tm, TargetJITInfo &tji, // Add target data MutexGuard locked(lock); FunctionPassManager &PM = jitstate->getPM(); - M->setDataLayout(TM.getSubtargetImpl()->getDataLayout()); - PM.add(new DataLayoutPass(M)); + Mod->setDataLayout(TM.getSubtargetImpl()->getDataLayout()); + PM.add(new DataLayoutPass(Mod)); // Turn the machine code intermediate representation into bytes in memory that // may be executed. @@ -175,19 +175,19 @@ JIT::~JIT() { delete &TM; } -/// addModule - Add a new Module to the JIT. If we previously removed the last -/// Module, we need re-initialize jitstate with a valid Module. -void JIT::addModule(Module *M) { +/// Add a new Module to the JIT. If we previously removed the last Module, we +/// need re-initialize jitstate with a valid Module. +void JIT::addModule(std::unique_ptr<Module> M) { MutexGuard locked(lock); if (Modules.empty()) { assert(!jitstate && "jitstate should be NULL if Modules vector is empty!"); - jitstate = new JITState(M); + jitstate = new JITState(M.get()); FunctionPassManager &PM = jitstate->getPM(); M->setDataLayout(TM.getSubtargetImpl()->getDataLayout()); - PM.add(new DataLayoutPass(M)); + PM.add(new DataLayoutPass(M.get())); // Turn the machine code intermediate representation into bytes in memory // that may be executed. @@ -199,11 +199,11 @@ void JIT::addModule(Module *M) { PM.doInitialization(); } - ExecutionEngine::addModule(M); + ExecutionEngine::addModule(std::move(M)); } -/// removeModule - If we are removing the last Module, invalidate the jitstate -/// since the PassManager it contains references a released Module. +/// If we are removing the last Module, invalidate the jitstate since the +/// PassManager it contains references a released Module. bool JIT::removeModule(Module *M) { bool result = ExecutionEngine::removeModule(M); @@ -215,7 +215,7 @@ bool JIT::removeModule(Module *M) { } if (!jitstate && !Modules.empty()) { - jitstate = new JITState(Modules[0]); + jitstate = new JITState(Modules[0].get()); FunctionPassManager &PM = jitstate->getPM(); M->setDataLayout(TM.getSubtargetImpl()->getDataLayout()); diff --git a/lib/ExecutionEngine/JIT/JIT.h b/lib/ExecutionEngine/JIT/JIT.h index 4a10ca4d379..c3bc740d7ec 100644 --- a/lib/ExecutionEngine/JIT/JIT.h +++ b/lib/ExecutionEngine/JIT/JIT.h @@ -78,7 +78,7 @@ class JIT : public ExecutionEngine { BasicBlockAddressMapTy BasicBlockAddressMap; - JIT(Module *M, TargetMachine &tm, TargetJITInfo &tji, + JIT(std::unique_ptr<Module> M, TargetMachine &tm, TargetJITInfo &tji, JITMemoryManager *JMM, bool AllocateGVsWithCode); public: ~JIT(); @@ -91,7 +91,7 @@ public: /// TargetJITInfo &getJITInfo() const { return TJI; } - void addModule(Module *M) override; + void addModule(std::unique_ptr<Module> M) override; /// removeModule - Remove a Module from the list of modules. Returns true if /// M is found. @@ -167,7 +167,7 @@ public: /// JITCodeEmitter *getCodeEmitter() const { return JCE; } - static ExecutionEngine *createJIT(Module *M, + static ExecutionEngine *createJIT(std::unique_ptr<Module> M, std::string *ErrorStr, JITMemoryManager *JMM, bool GVsWithCode, diff --git a/lib/ExecutionEngine/MCJIT/MCJIT.cpp b/lib/ExecutionEngine/MCJIT/MCJIT.cpp index 8c6db75487f..65e2aba29ee 100644 --- a/lib/ExecutionEngine/MCJIT/MCJIT.cpp +++ b/lib/ExecutionEngine/MCJIT/MCJIT.cpp @@ -43,7 +43,7 @@ static struct RegisterJIT { extern "C" void LLVMLinkInMCJIT() { } -ExecutionEngine *MCJIT::createJIT(Module *M, +ExecutionEngine *MCJIT::createJIT(std::unique_ptr<Module> M, std::string *ErrorStr, RTDyldMemoryManager *MemMgr, TargetMachine *TM) { @@ -52,19 +52,14 @@ ExecutionEngine *MCJIT::createJIT(Module *M, // FIXME: Don't do this here. sys::DynamicLibrary::LoadLibraryPermanently(nullptr, nullptr); - return new MCJIT(M, TM, MemMgr ? MemMgr : new SectionMemoryManager()); + return new MCJIT(std::move(M), TM, + MemMgr ? MemMgr : new SectionMemoryManager()); } -MCJIT::MCJIT(Module *m, TargetMachine *tm, RTDyldMemoryManager *MM) - : ExecutionEngine(m), TM(tm), Ctx(nullptr), MemMgr(this, MM), Dyld(&MemMgr), - ObjCache(nullptr) { - - OwnedModules.addModule(m); - setDataLayout(TM->getSubtargetImpl()->getDataLayout()); -} - -MCJIT::~MCJIT() { - MutexGuard locked(lock); +MCJIT::MCJIT(std::unique_ptr<Module> M, TargetMachine *tm, + RTDyldMemoryManager *MM) + : ExecutionEngine(std::move(M)), TM(tm), Ctx(nullptr), MemMgr(this, MM), + Dyld(&MemMgr), ObjCache(nullptr) { // FIXME: We are managing our modules, so we do not want the base class // ExecutionEngine to manage them as well. To avoid double destruction // of the first (and only) module added in ExecutionEngine constructor @@ -75,7 +70,16 @@ MCJIT::~MCJIT() { // If so, additional functions: addModule, removeModule, FindFunctionNamed, // runStaticConstructorsDestructors could be moved back to EE as well. // + std::unique_ptr<Module> First = std::move(Modules[0]); Modules.clear(); + + OwnedModules.addModule(std::move(First)); + setDataLayout(TM->getSubtargetImpl()->getDataLayout()); +} + +MCJIT::~MCJIT() { + MutexGuard locked(lock); + Dyld.deregisterEHFrames(); LoadedObjectList::iterator it, end; @@ -93,9 +97,9 @@ MCJIT::~MCJIT() { delete TM; } -void MCJIT::addModule(Module *M) { +void MCJIT::addModule(std::unique_ptr<Module> M) { MutexGuard locked(lock); - OwnedModules.addModule(M); + OwnedModules.addModule(std::move(M)); } bool MCJIT::removeModule(Module *M) { @@ -389,7 +393,7 @@ void MCJIT::freeMachineCodeForFunction(Function *F) { void MCJIT::runStaticConstructorsDestructorsInModulePtrSet( bool isDtors, ModulePtrSet::iterator I, ModulePtrSet::iterator E) { for (; I != E; ++I) { - ExecutionEngine::runStaticConstructorsDestructors(*I, isDtors); + ExecutionEngine::runStaticConstructorsDestructors(**I, isDtors); } } diff --git a/lib/ExecutionEngine/MCJIT/MCJIT.h b/lib/ExecutionEngine/MCJIT/MCJIT.h index 1a81bc39eee..6a814db5ef2 100644 --- a/lib/ExecutionEngine/MCJIT/MCJIT.h +++ b/lib/ExecutionEngine/MCJIT/MCJIT.h @@ -101,7 +101,8 @@ private: // called. class MCJIT : public ExecutionEngine { - MCJIT(Module *M, TargetMachine *tm, RTDyldMemoryManager *MemMgr); + MCJIT(std::unique_ptr<Module> M, TargetMachine *tm, + RTDyldMemoryManager *MemMgr); typedef llvm::SmallPtrSet<Module *, 4> ModulePtrSet; @@ -124,8 +125,8 @@ class MCJIT : public ExecutionEngine { ModulePtrSet::iterator begin_finalized() { return FinalizedModules.begin(); } ModulePtrSet::iterator end_finalized() { return FinalizedModules.end(); } - void addModule(Module *M) { - AddedModules.insert(M); + void addModule(std::unique_ptr<Module> M) { + AddedModules.insert(M.release()); } bool removeModule(Module *M) { @@ -237,7 +238,7 @@ public: /// @name ExecutionEngine interface implementation /// @{ - void addModule(Module *M) override; + void addModule(std::unique_ptr<Module> M) override; void addObjectFile(std::unique_ptr<object::ObjectFile> O) override; void addArchive(std::unique_ptr<object::Archive> O) override; bool removeModule(Module *M) override; @@ -324,7 +325,7 @@ public: MCJITCtor = createJIT; } - static ExecutionEngine *createJIT(Module *M, + static ExecutionEngine *createJIT(std::unique_ptr<Module> M, std::string *ErrorStr, RTDyldMemoryManager *MemMgr, TargetMachine *TM); |