<div dir="ltr"><br><br><div class="gmail_quote"><div dir="ltr">On Sat, Sep 16, 2017 at 8:26 PM Lang Hames via llvm-commits <<a href="mailto:llvm-commits@lists.llvm.org">llvm-commits@lists.llvm.org</a>> wrote:<br></div><blockquote class="gmail_quote" style="margin:0 0 0 .8ex;border-left:1px #ccc solid;padding-left:1ex">Author: lhames<br>
Date: Sat Sep 16 20:25:03 2017<br>
New Revision: 313474<br>
<br>
URL: <a href="http://llvm.org/viewvc/llvm-project?rev=313474&view=rev" rel="noreferrer" target="_blank">http://llvm.org/viewvc/llvm-project?rev=313474&view=rev</a><br>
Log:<br>
[ORC] Hook up the LLVMOrcAddObjectFile function in the Orc C Bindings.<br>
<br>
This can be used to add a relocatable object to the JIT session.<br>
<br>
Modified:<br>
    llvm/trunk/include/llvm-c/OrcBindings.h<br>
    llvm/trunk/lib/ExecutionEngine/Orc/OrcCBindings.cpp<br>
    llvm/trunk/lib/ExecutionEngine/Orc/OrcCBindingsStack.h<br>
    llvm/trunk/unittests/ExecutionEngine/Orc/OrcCAPITest.cpp<br>
<br>
Modified: llvm/trunk/include/llvm-c/OrcBindings.h<br>
URL: <a href="http://llvm.org/viewvc/llvm-project/llvm/trunk/include/llvm-c/OrcBindings.h?rev=313474&r1=313473&r2=313474&view=diff" rel="noreferrer" target="_blank">http://llvm.org/viewvc/llvm-project/llvm/trunk/include/llvm-c/OrcBindings.h?rev=313474&r1=313473&r2=313474&view=diff</a><br>
==============================================================================<br>
--- llvm/trunk/include/llvm-c/OrcBindings.h (original)<br>
+++ llvm/trunk/include/llvm-c/OrcBindings.h Sat Sep 16 20:25:03 2017<br>
@@ -30,7 +30,6 @@ extern "C" {<br>
 #endif<br>
<br>
 typedef struct LLVMOpaqueSharedModule *LLVMSharedModuleRef;<br>
-typedef struct LLVMOpaqueSharedObjectBuffer *LLVMSharedObjectBufferRef;<br>
 typedef struct LLVMOrcOpaqueJITStack *LLVMOrcJITStackRef;<br>
 typedef uint32_t LLVMOrcModuleHandle;<br>
 typedef uint64_t LLVMOrcTargetAddress;<br>
@@ -68,18 +67,6 @@ LLVMSharedModuleRef LLVMOrcMakeSharedMod<br>
 void LLVMOrcDisposeSharedModuleRef(LLVMSharedModuleRef SharedMod);<br>
<br>
 /**<br>
- * Get an LLVMSharedObjectBufferRef from an LLVMMemoryBufferRef.<br>
- */<br>
-LLVMSharedObjectBufferRef<br>
-LLVMOrcMakeSharedObjectBuffer(LLVMMemoryBufferRef ObjBuffer);<br>
-<br>
-/**<br>
- * Dispose of a shared object buffer.<br>
- */<br>
-void<br>
-LLVMOrcDisposeSharedObjectBufferRef(LLVMSharedObjectBufferRef SharedObjBuffer);<br>
-<br>
-/**<br>
  * Create an ORC JIT stack.<br>
  *<br>
  * The client owns the resulting stack, and must call OrcDisposeInstance(...)<br>
@@ -155,10 +142,15 @@ LLVMOrcAddLazilyCompiledIR(LLVMOrcJITSta<br>
<br>
 /**<br>
  * Add an object file.<br>
+ *<br>
+ * This method takes ownership of the given memory buffer and attempts to add<br>
+ * it to the JIT as an object file.<br>
+ * Clients should *not* dispose of the 'Obj' argument: the JIT will manage it<br>
+ * from this call onwards.<br>
  */<br>
 LLVMOrcErrorCode LLVMOrcAddObjectFile(LLVMOrcJITStackRef JITStack,<br>
                                       LLVMOrcModuleHandle *RetHandle,<br>
-                                      LLVMSharedObjectBufferRef Obj,<br>
+                                      LLVMMemoryBufferRef Obj,<br>
                                       LLVMOrcSymbolResolverFn SymbolResolver,<br>
                                       void *SymbolResolverCtx);<br>
<br>
<br>
Modified: llvm/trunk/lib/ExecutionEngine/Orc/OrcCBindings.cpp<br>
URL: <a href="http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/ExecutionEngine/Orc/OrcCBindings.cpp?rev=313474&r1=313473&r2=313474&view=diff" rel="noreferrer" target="_blank">http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/ExecutionEngine/Orc/OrcCBindings.cpp?rev=313474&r1=313473&r2=313474&view=diff</a><br>
==============================================================================<br>
--- llvm/trunk/lib/ExecutionEngine/Orc/OrcCBindings.cpp (original)<br>
+++ llvm/trunk/lib/ExecutionEngine/Orc/OrcCBindings.cpp Sat Sep 16 20:25:03 2017<br>
@@ -20,16 +20,6 @@ void LLVMOrcDisposeSharedModuleRef(LLVMS<br>
   delete unwrap(SharedMod);<br>
 }<br>
<br>
-LLVMSharedObjectBufferRef<br>
-LLVMOrcMakeSharedObjectBuffer(LLVMMemoryBufferRef ObjBuffer) {<br>
-  return wrap(new std::shared_ptr<MemoryBuffer>(unwrap(ObjBuffer)));<br>
-}<br>
-<br>
-void<br>
-LLVMOrcDisposeSharedObjectBufferRef(LLVMSharedObjectBufferRef SharedObjBuffer) {<br>
-  delete unwrap(SharedObjBuffer);<br>
-}<br>
-<br>
 LLVMOrcJITStackRef LLVMOrcCreateInstance(LLVMTargetMachineRef TM) {<br>
   TargetMachine *TM2(unwrap(TM));<br>
<br>
@@ -105,6 +95,18 @@ LLVMOrcAddLazilyCompiledIR(LLVMOrcJITSta<br>
   return J.addIRModuleLazy(*RetHandle, *M, SymbolResolver, SymbolResolverCtx);<br>
 }<br>
<br>
+LLVMOrcErrorCode<br>
+LLVMOrcAddObjectFile(LLVMOrcJITStackRef JITStack,<br>
+                     LLVMOrcModuleHandle *RetHandle,<br>
+                     LLVMMemoryBufferRef Obj,<br>
+                     LLVMOrcSymbolResolverFn SymbolResolver,<br>
+                     void *SymbolResolverCtx) {<br>
+  OrcCBindingsStack &J = *unwrap(JITStack);<br>
+  std::unique_ptr<MemoryBuffer> O(unwrap(Obj));<br>
+  return J.addObject(*RetHandle, std::move(O), SymbolResolver,<br>
+                     SymbolResolverCtx);<br>
+}<br>
+<br>
 LLVMOrcErrorCode LLVMOrcRemoveModule(LLVMOrcJITStackRef JITStack,<br>
                                      LLVMOrcModuleHandle H) {<br>
   OrcCBindingsStack &J = *unwrap(JITStack);<br>
<br>
Modified: llvm/trunk/lib/ExecutionEngine/Orc/OrcCBindingsStack.h<br>
URL: <a href="http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/ExecutionEngine/Orc/OrcCBindingsStack.h?rev=313474&r1=313473&r2=313474&view=diff" rel="noreferrer" target="_blank">http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/ExecutionEngine/Orc/OrcCBindingsStack.h?rev=313474&r1=313473&r2=313474&view=diff</a><br>
==============================================================================<br>
--- llvm/trunk/lib/ExecutionEngine/Orc/OrcCBindingsStack.h (original)<br>
+++ llvm/trunk/lib/ExecutionEngine/Orc/OrcCBindingsStack.h Sat Sep 16 20:25:03 2017<br>
@@ -44,26 +44,12 @@ class OrcCBindingsStack;<br>
<br>
 DEFINE_SIMPLE_CONVERSION_FUNCTIONS(std::shared_ptr<Module>,<br>
                                    LLVMSharedModuleRef)<br>
-DEFINE_SIMPLE_CONVERSION_FUNCTIONS(std::shared_ptr<MemoryBuffer>,<br>
-                                   LLVMSharedObjectBufferRef)<br>
 DEFINE_SIMPLE_CONVERSION_FUNCTIONS(OrcCBindingsStack, LLVMOrcJITStackRef)<br>
 DEFINE_SIMPLE_CONVERSION_FUNCTIONS(TargetMachine, LLVMTargetMachineRef)<br>
<br>
-class OrcCBindingsStack {<br>
-public:<br>
-<br>
-  using CompileCallbackMgr = orc::JITCompileCallbackManager;<br>
-  using ObjLayerT = orc::RTDyldObjectLinkingLayer;<br>
-  using CompileLayerT = orc::IRCompileLayer<ObjLayerT, orc::SimpleCompiler>;<br>
-  using CODLayerT =<br>
-        orc::CompileOnDemandLayer<CompileLayerT, CompileCallbackMgr>;<br>
+namespace detail {<br>
<br>
-  using CallbackManagerBuilder =<br>
-      std::function<std::unique_ptr<CompileCallbackMgr>()>;<br>
<br>
-  using IndirectStubsManagerBuilder = CODLayerT::IndirectStubsManagerBuilderT;<br>
-<br>
-private:<br>
   class GenericHandle {<br>
   public:<br>
     virtual ~GenericHandle() = default;<br>
@@ -90,13 +76,56 @@ private:<br>
     typename LayerT::ModuleHandleT Handle;<br>
   };<br>
<br>
-  template <typename LayerT><br>
+  template <><br>
+  class GenericHandleImpl<orc::RTDyldObjectLinkingLayer><br>
+    : public GenericHandle {<br>
+  private:<br>
+    using LayerT = orc::RTDyldObjectLinkingLayer;<br>
+  public:<br>
+<br>
+    GenericHandleImpl(LayerT &Layer, typename LayerT::ObjHandleT Handle)<br>
+        : Layer(Layer), Handle(std::move(Handle)) {}<br>
+<br>
+    JITSymbol findSymbolIn(const std::string &Name,<br>
+                           bool ExportedSymbolsOnly) override {<br>
+      return Layer.findSymbolIn(Handle, Name, ExportedSymbolsOnly);<br>
+    }<br>
+<br>
+    Error removeModule() override { return Layer.removeObject(Handle); }<br>
+<br>
+  private:<br>
+    LayerT &Layer;<br>
+    typename LayerT::ObjHandleT Handle;<br>
+  };<br>
+<br>
+<br>
+  template <typename LayerT, typename HandleT><br>
   std::unique_ptr<GenericHandleImpl<LayerT>><br>
-  createGenericHandle(LayerT &Layer, typename LayerT::ModuleHandleT Handle) {<br>
+  createGenericHandle(LayerT &Layer, HandleT Handle) {<br>
     return llvm::make_unique<GenericHandleImpl<LayerT>>(Layer,<br>
                                                         std::move(Handle));<br>
   }<br>
<br>
+} // end namespace detail<br>
+<br>
+class OrcCBindingsStack {<br>
+public:<br>
+<br>
+  using CompileCallbackMgr = orc::JITCompileCallbackManager;<br>
+  using ObjLayerT = orc::RTDyldObjectLinkingLayer;<br>
+  using CompileLayerT = orc::IRCompileLayer<ObjLayerT, orc::SimpleCompiler>;<br>
+  using CODLayerT =<br>
+        orc::CompileOnDemandLayer<CompileLayerT, CompileCallbackMgr>;<br>
+<br>
+  using CallbackManagerBuilder =<br>
+      std::function<std::unique_ptr<CompileCallbackMgr>()>;<br>
+<br>
+  using IndirectStubsManagerBuilder = CODLayerT::IndirectStubsManagerBuilderT;<br>
+<br>
+private:<br>
+<br>
+  using OwningObject = object::OwningBinary<object::ObjectFile>;<br>
+<br>
 public:<br>
   using ModuleHandleT = unsigned;<br>
<br>
@@ -266,6 +295,33 @@ public:<br>
     return LLVMOrcErrSuccess;<br>
   }<br>
<br>
+  LLVMOrcErrorCode addObject(ModuleHandleT &RetHandle,<br>
+                             std::unique_ptr<MemoryBuffer> ObjBuffer,<br>
+                             LLVMOrcSymbolResolverFn ExternalResolver,<br>
+                             void *ExternalResolverCtx) {<br>
+    if (auto ObjOrErr =<br>
+        object::ObjectFile::createObjectFile(ObjBuffer->getMemBufferRef())) {<br>
+      auto &Obj = *ObjOrErr;<br>
+      auto OwningObj =<br>
+        std::make_shared<OwningObject>(std::move(Obj), std::move(ObjBuffer));<br>
+<br>
+      // Create the resolver.<br>
+      auto Resolver = createResolver(ExternalResolver, ExternalResolverCtx);<br>
+<br>
+      ModuleHandleT H;<br>
+      if (auto HOrErr = ObjectLayer.addObject(std::move(OwningObj),<br>
+                                              std::move(Resolver)))<br>
+        H = createHandle(ObjectLayer, *HOrErr);<br>
+      else<br>
+        return mapError(HOrErr.takeError());<br>
+<br>
+      RetHandle = H;<br>
+<br>
+      return LLVMOrcErrSuccess;<br>
+    } else<br></blockquote><div><br>Remove else after return? <br><br>Also consider inverting to reduce indentation ( !ObjOrErr, return mapError, <good stuff>)<br> </div><blockquote class="gmail_quote" style="margin:0 0 0 .8ex;border-left:1px #ccc solid;padding-left:1ex">
+      return mapError(ObjOrErr.takeError());<br>
+  }<br>
+<br>
   JITSymbol findSymbol(const std::string &Name,<br>
                                  bool ExportedSymbolsOnly) {<br>
     if (auto Sym = IndirectStubsMgr->findStub(Name, ExportedSymbolsOnly))<br>
@@ -301,17 +357,19 @@ public:<br>
   const std::string &getErrorMessage() const { return ErrMsg; }<br>
<br>
 private:<br>
-  template <typename LayerT><br>
-  unsigned createHandle(LayerT &Layer, typename LayerT::ModuleHandleT Handle) {<br>
+  template <typename LayerT, typename HandleT><br>
+  unsigned createHandle(LayerT &Layer, HandleT Handle) {<br>
     unsigned NewHandle;<br>
     if (!FreeHandleIndexes.empty()) {<br>
       NewHandle = FreeHandleIndexes.back();<br>
       FreeHandleIndexes.pop_back();<br>
-      GenericHandles[NewHandle] = createGenericHandle(Layer, std::move(Handle));<br>
+      GenericHandles[NewHandle] =<br>
+        detail::createGenericHandle(Layer, std::move(Handle));<br>
       return NewHandle;<br>
     } else {<br>
       NewHandle = GenericHandles.size();<br>
-      GenericHandles.push_back(createGenericHandle(Layer, std::move(Handle)));<br>
+      GenericHandles.push_back(<br>
+        detail::createGenericHandle(Layer, std::move(Handle)));<br>
     }<br>
     return NewHandle;<br>
   }<br>
@@ -338,7 +396,7 @@ private:<br>
   CompileLayerT CompileLayer;<br>
   CODLayerT CODLayer;<br>
<br>
-  std::vector<std::unique_ptr<GenericHandle>> GenericHandles;<br>
+  std::vector<std::unique_ptr<detail::GenericHandle>> GenericHandles;<br>
   std::vector<unsigned> FreeHandleIndexes;<br>
<br>
   orc::LocalCXXRuntimeOverrides CXXRuntimeOverrides;<br>
<br>
Modified: llvm/trunk/unittests/ExecutionEngine/Orc/OrcCAPITest.cpp<br>
URL: <a href="http://llvm.org/viewvc/llvm-project/llvm/trunk/unittests/ExecutionEngine/Orc/OrcCAPITest.cpp?rev=313474&r1=313473&r2=313474&view=diff" rel="noreferrer" target="_blank">http://llvm.org/viewvc/llvm-project/llvm/trunk/unittests/ExecutionEngine/Orc/OrcCAPITest.cpp?rev=313474&r1=313473&r2=313474&view=diff</a><br>
==============================================================================<br>
--- llvm/trunk/unittests/ExecutionEngine/Orc/OrcCAPITest.cpp (original)<br>
+++ llvm/trunk/unittests/ExecutionEngine/Orc/OrcCAPITest.cpp Sat Sep 16 20:25:03 2017<br>
@@ -8,6 +8,7 @@<br>
 //===----------------------------------------------------------------------===//<br>
<br>
 #include "OrcTestCommon.h"<br>
+#include "llvm/ExecutionEngine/Orc/CompileUtils.h"<br>
 #include "llvm-c/Core.h"<br>
 #include "llvm-c/OrcBindings.h"<br>
 #include "llvm-c/Target.h"<br>
@@ -37,6 +38,15 @@ protected:<br>
     return MB.takeModule();<br>
   }<br>
<br>
+  std::shared_ptr<object::OwningBinary<object::ObjectFile>><br>
+  createTestObject() {<br>
+    orc::SimpleCompiler IRCompiler(*TM);<br>
+    auto M = createTestModule(TM->getTargetTriple());<br>
+    M->setDataLayout(TM->createDataLayout());<br>
+    return std::make_shared<object::OwningBinary<object::ObjectFile>>(<br>
+      IRCompiler(*M));<br>
+  }<br>
+<br>
   typedef int (*MainFnTy)();<br>
<br>
   static int myTestFuncImpl() {<br>
@@ -124,6 +134,36 @@ TEST_F(OrcCAPIExecutionTest, TestLazyIRC<br>
   LLVMOrcTargetAddress MainAddr;<br>
   LLVMOrcGetSymbolAddress(JIT, &MainAddr, "main");<br>
   MainFnTy MainFn = (MainFnTy)MainAddr;<br>
+  int Result = MainFn();<br>
+  EXPECT_EQ(Result, 42)<br>
+    << "Lazily JIT'd code did not return expected result";<br>
+<br>
+  LLVMOrcRemoveModule(JIT, H);<br>
+<br>
+  LLVMOrcDisposeMangledSymbol(testFuncName);<br>
+  LLVMOrcDisposeInstance(JIT);<br>
+}<br>
+<br>
+TEST_F(OrcCAPIExecutionTest, TestAddObjectFile) {<br>
+  if (!TM)<br>
+    return;<br>
+<br>
+  std::unique_ptr<MemoryBuffer> ObjBuffer;<br>
+  {<br>
+    auto OwningObj = createTestObject();<br>
+    auto ObjAndBuffer = OwningObj->takeBinary();<br>
+    ObjBuffer = std::move(ObjAndBuffer.second);<br>
+  }<br>
+<br>
+  LLVMOrcJITStackRef JIT =<br>
+    LLVMOrcCreateInstance(wrap(TM.get()));<br>
+  LLVMOrcGetMangledSymbol(JIT, &testFuncName, "testFunc");<br>
+<br>
+  LLVMOrcModuleHandle H;<br>
+  LLVMOrcAddObjectFile(JIT, &H, wrap(ObjBuffer.release()), myResolver, nullptr);<br>
+  LLVMOrcTargetAddress MainAddr;<br>
+  LLVMOrcGetSymbolAddress(JIT, &MainAddr, "main");<br>
+  MainFnTy MainFn = (MainFnTy)MainAddr;<br>
   int Result = MainFn();<br>
   EXPECT_EQ(Result, 42)<br>
     << "Lazily JIT'd code did not return expected result";<br>
<br>
<br>
_______________________________________________<br>
llvm-commits mailing list<br>
<a href="mailto:llvm-commits@lists.llvm.org" target="_blank">llvm-commits@lists.llvm.org</a><br>
<a href="http://lists.llvm.org/cgi-bin/mailman/listinfo/llvm-commits" rel="noreferrer" target="_blank">http://lists.llvm.org/cgi-bin/mailman/listinfo/llvm-commits</a><br>
</blockquote></div></div>