From 3537ea42fb7ad54084b62a01d7ba3308feed75fa Mon Sep 17 00:00:00 2001
From: Mick Jordan <mick.jordan@oracle.com>
Date: Mon, 30 Jan 2017 10:40:48 -0800
Subject: [PATCH] rffi: Truffle_LLVM fixes

---
 .../interop/ffi/llvm/TruffleLLVM_CAccess.java |  4 +--
 .../interop/ffi/llvm/TruffleLLVM_Call.java    |  3 ++-
 .../interop/ffi/llvm/TruffleLLVM_DLL.java     | 26 +++++++++++++++----
 .../interop/ffi/llvm/TruffleLLVM_PkgInit.java |  3 ++-
 .../llvm/TruffleLLVM_RFFIContextState.java    |  5 +++-
 .../ffi/llvm/TruffleLLVM_RFFIFactory.java     |  7 +----
 .../truffle/r/runtime/ffi/RFFIVariables.java  |  2 +-
 7 files changed, 33 insertions(+), 17 deletions(-)

diff --git a/com.oracle.truffle.r.engine/src/com/oracle/truffle/r/engine/interop/ffi/llvm/TruffleLLVM_CAccess.java b/com.oracle.truffle.r.engine/src/com/oracle/truffle/r/engine/interop/ffi/llvm/TruffleLLVM_CAccess.java
index 8df6ca4e53..f94c7ffa21 100644
--- a/com.oracle.truffle.r.engine/src/com/oracle/truffle/r/engine/interop/ffi/llvm/TruffleLLVM_CAccess.java
+++ b/com.oracle.truffle.r.engine/src/com/oracle/truffle/r/engine/interop/ffi/llvm/TruffleLLVM_CAccess.java
@@ -31,11 +31,11 @@ import com.oracle.truffle.r.runtime.rng.user.UserRNG;
  * with {@code double *}.
  *
  * N.B. When {@code libR} is not completely in LLVM mode (as now), we have to look up the symbols
- * using an explicitly created {@link TruffleLLVM_DLL.LLVM_Handle}and not go via generic lookup in
+ * using an explicitly created {@link TruffleLLVM_DLL.LLVM_Handle} and not go via generic lookup in
  * {@link DLL} as that would use a {@link JNI_DLL} handle.
  */
 public class TruffleLLVM_CAccess {
-    private static final TruffleLLVM_DLL.LLVM_Handle handle = new TruffleLLVM_DLL.LLVM_Handle("libR");
+    private static final TruffleLLVM_DLL.LLVM_Handle handle = new TruffleLLVM_DLL.LLVM_Handle("libR", null);
 
     public enum Function {
         READ_POINTER_INT,
diff --git a/com.oracle.truffle.r.engine/src/com/oracle/truffle/r/engine/interop/ffi/llvm/TruffleLLVM_Call.java b/com.oracle.truffle.r.engine/src/com/oracle/truffle/r/engine/interop/ffi/llvm/TruffleLLVM_Call.java
index 5b70553584..56e4a10fa4 100644
--- a/com.oracle.truffle.r.engine/src/com/oracle/truffle/r/engine/interop/ffi/llvm/TruffleLLVM_Call.java
+++ b/com.oracle.truffle.r.engine/src/com/oracle/truffle/r/engine/interop/ffi/llvm/TruffleLLVM_Call.java
@@ -40,6 +40,7 @@ import com.oracle.truffle.r.runtime.data.RNull;
 import com.oracle.truffle.r.runtime.ffi.CallRFFI;
 import com.oracle.truffle.r.runtime.ffi.DLL.SymbolHandle;
 import com.oracle.truffle.r.runtime.ffi.NativeCallInfo;
+import com.oracle.truffle.r.runtime.ffi.RFFIFactory;
 import com.oracle.truffle.r.runtime.ffi.RFFIVariables;
 import com.oracle.truffle.r.runtime.ffi.jni.JNI_Call;
 import com.oracle.truffle.r.runtime.ffi.jni.JNI_Call.JNI_CallRFFINode;
@@ -55,7 +56,6 @@ class TruffleLLVM_Call implements CallRFFI {
         new JNI_Call();
         truffleCall = this;
         truffleCallTruffleObject = JavaInterop.asTruffleObject(truffleCall);
-        TruffleLLVM_PkgInit.initialize();
         truffleCallHelper = TruffleLLVM_UpCallsRFFIImpl.initialize();
     }
 
@@ -66,6 +66,7 @@ class TruffleLLVM_Call implements CallRFFI {
         @Override
         public ContextState initialize(RContext contextA) {
             this.context = contextA;
+            RFFIFactory.getRFFI().getCallRFFI();
             context.addExportedSymbol("_fastr_rffi_call", truffleCallTruffleObject);
             context.addExportedSymbol("_fastr_rffi_callhelper", truffleCallHelper);
             return this;
diff --git a/com.oracle.truffle.r.engine/src/com/oracle/truffle/r/engine/interop/ffi/llvm/TruffleLLVM_DLL.java b/com.oracle.truffle.r.engine/src/com/oracle/truffle/r/engine/interop/ffi/llvm/TruffleLLVM_DLL.java
index b7c6a35f64..8df55ed11f 100644
--- a/com.oracle.truffle.r.engine/src/com/oracle/truffle/r/engine/interop/ffi/llvm/TruffleLLVM_DLL.java
+++ b/com.oracle.truffle.r.engine/src/com/oracle/truffle/r/engine/interop/ffi/llvm/TruffleLLVM_DLL.java
@@ -23,6 +23,7 @@
 package com.oracle.truffle.r.engine.interop.ffi.llvm;
 
 import java.nio.file.FileSystems;
+import java.util.ArrayList;
 import java.util.HashMap;
 import java.util.Map;
 
@@ -35,6 +36,7 @@ import com.oracle.truffle.r.runtime.Utils;
 import com.oracle.truffle.r.runtime.context.RContext;
 import com.oracle.truffle.r.runtime.context.RContext.ContextState;
 import com.oracle.truffle.r.runtime.ffi.DLL;
+import com.oracle.truffle.r.runtime.ffi.DLL.DLLInfo;
 import com.oracle.truffle.r.runtime.ffi.DLL.SymbolHandle;
 import com.oracle.truffle.r.runtime.ffi.DLLRFFI;
 import com.oracle.truffle.r.runtime.ffi.NativeCallInfo;
@@ -111,7 +113,7 @@ class TruffleLLVM_DLL extends JNI_DLL implements DLLRFFI {
         }
     }
 
-    class ContextStateImpl implements RContext.ContextState {
+    static class ContextStateImpl implements RContext.ContextState {
         /**
          * A map from function name to its {@link ParseStatus}, allowing fast determination whether
          * parsing is required in a call, see {@link #ensureParsed}. N.B. parsing happens at the
@@ -128,9 +130,21 @@ class TruffleLLVM_DLL extends JNI_DLL implements DLLRFFI {
          */
         @Override
         public ContextState initialize(RContext context) {
-            for (LLVM_IR ir : libRModules) {
+            for (LLVM_IR ir : truffleDLL.libRModules) {
                 addExportsToMap(this, "libR", ir, (name) -> name.endsWith("_llvm"));
             }
+            if (context.getKind() == RContext.ContextKind.SHARE_PARENT_RW) {
+                // must propagate all LLVM library exports
+                ArrayList<DLLInfo> loadedDLLs = DLL.getLoadedDLLs();
+                for (DLLInfo dllInfo : loadedDLLs) {
+                    if (dllInfo.handle instanceof LLVM_Handle) {
+                        LLVM_Handle llvmHandle = (LLVM_Handle) dllInfo.handle;
+                        for (LLVM_IR ir : llvmHandle.irs) {
+                            addExportsToMap(this, llvmHandle.libName, ir, (name) -> true);
+                        }
+                    }
+                }
+            }
             return this;
         }
 
@@ -150,7 +164,7 @@ class TruffleLLVM_DLL extends JNI_DLL implements DLLRFFI {
     }
 
     static ContextStateImpl newContextState() {
-        return truffleDLL.new ContextStateImpl();
+        return new ContextStateImpl();
     }
 
     static boolean isBlacklisted(String libName) {
@@ -170,9 +184,11 @@ class TruffleLLVM_DLL extends JNI_DLL implements DLLRFFI {
 
     static class LLVM_Handle {
         private final String libName;
+        private final LLVM_IR[] irs;
 
-        LLVM_Handle(String libName) {
+        LLVM_Handle(String libName, LLVM_IR[] irs) {
             this.libName = libName;
+            this.irs = irs;
         }
     }
 
@@ -207,7 +223,7 @@ class TruffleLLVM_DLL extends JNI_DLL implements DLLRFFI {
                         LLVM_IR ir = irs[i];
                         addExportsToMap(contextState, libName, ir, (name) -> true);
                     }
-                    return new LLVM_Handle(libName);
+                    return new LLVM_Handle(libName, irs);
                 }
             } catch (Exception ex) {
                 return null;
diff --git a/com.oracle.truffle.r.engine/src/com/oracle/truffle/r/engine/interop/ffi/llvm/TruffleLLVM_PkgInit.java b/com.oracle.truffle.r.engine/src/com/oracle/truffle/r/engine/interop/ffi/llvm/TruffleLLVM_PkgInit.java
index 0524af4dbf..80151638dc 100644
--- a/com.oracle.truffle.r.engine/src/com/oracle/truffle/r/engine/interop/ffi/llvm/TruffleLLVM_PkgInit.java
+++ b/com.oracle.truffle.r.engine/src/com/oracle/truffle/r/engine/interop/ffi/llvm/TruffleLLVM_PkgInit.java
@@ -45,6 +45,7 @@ class TruffleLLVM_PkgInit {
     static class ContextStateImpl implements RContext.ContextState {
         @Override
         public ContextState initialize(RContext context) {
+            TruffleLLVM_PkgInit.initialize();
             context.addExportedSymbol("_fastr_rffi_pkginit", trufflePkgInitTruffleObject);
             return this;
         }
@@ -58,7 +59,7 @@ class TruffleLLVM_PkgInit {
         return new ContextStateImpl();
     }
 
-    static TruffleLLVM_PkgInit initialize() {
+    private static TruffleLLVM_PkgInit initialize() {
         if (trufflePkgInit == null) {
             trufflePkgInit = new TruffleLLVM_PkgInit();
             trufflePkgInitTruffleObject = JavaInterop.asTruffleObject(trufflePkgInit);
diff --git a/com.oracle.truffle.r.engine/src/com/oracle/truffle/r/engine/interop/ffi/llvm/TruffleLLVM_RFFIContextState.java b/com.oracle.truffle.r.engine/src/com/oracle/truffle/r/engine/interop/ffi/llvm/TruffleLLVM_RFFIContextState.java
index 75fae59b7f..9caaec1719 100644
--- a/com.oracle.truffle.r.engine/src/com/oracle/truffle/r/engine/interop/ffi/llvm/TruffleLLVM_RFFIContextState.java
+++ b/com.oracle.truffle.r.engine/src/com/oracle/truffle/r/engine/interop/ffi/llvm/TruffleLLVM_RFFIContextState.java
@@ -34,8 +34,10 @@ class TruffleLLVM_RFFIContextState implements ContextState {
     TruffleLLVM_PkgInit.ContextStateImpl pkgInitState;
     TruffleLLVM_Call.ContextStateImpl callState;
     TruffleLLVM_Stats.ContextStateImpl statsState;
+    private final ContextState jniContextState;
 
-    TruffleLLVM_RFFIContextState() {
+    TruffleLLVM_RFFIContextState(ContextState jniContextState) {
+        this.jniContextState = jniContextState;
         dllState = TruffleLLVM_DLL.newContextState();
         pkgInitState = TruffleLLVM_PkgInit.newContextState();
         callState = TruffleLLVM_Call.newContextState();
@@ -52,6 +54,7 @@ class TruffleLLVM_RFFIContextState implements ContextState {
 
     @Override
     public ContextState initialize(RContext context) {
+        jniContextState.initialize(context);
         dllState.initialize(context);
         pkgInitState.initialize(context);
         callState.initialize(context);
diff --git a/com.oracle.truffle.r.engine/src/com/oracle/truffle/r/engine/interop/ffi/llvm/TruffleLLVM_RFFIFactory.java b/com.oracle.truffle.r.engine/src/com/oracle/truffle/r/engine/interop/ffi/llvm/TruffleLLVM_RFFIFactory.java
index dbac7eb62f..5a3324b951 100644
--- a/com.oracle.truffle.r.engine/src/com/oracle/truffle/r/engine/interop/ffi/llvm/TruffleLLVM_RFFIFactory.java
+++ b/com.oracle.truffle.r.engine/src/com/oracle/truffle/r/engine/interop/ffi/llvm/TruffleLLVM_RFFIFactory.java
@@ -37,14 +37,9 @@ import com.oracle.truffle.r.runtime.ffi.jni.JNI_RFFIFactory;
  */
 public class TruffleLLVM_RFFIFactory extends JNI_RFFIFactory implements RFFI {
 
-    @Override
-    protected void initialize(boolean runtime) {
-        super.initialize(runtime);
-    }
-
     @Override
     public ContextState newContextState() {
-        return new TruffleLLVM_RFFIContextState();
+        return new TruffleLLVM_RFFIContextState(super.newContextState());
     }
 
     private CRFFI cRFFI;
diff --git a/com.oracle.truffle.r.runtime.ffi/src/com/oracle/truffle/r/runtime/ffi/RFFIVariables.java b/com.oracle.truffle.r.runtime.ffi/src/com/oracle/truffle/r/runtime/ffi/RFFIVariables.java
index dc5591473a..2e7b18ce9b 100644
--- a/com.oracle.truffle.r.runtime.ffi/src/com/oracle/truffle/r/runtime/ffi/RFFIVariables.java
+++ b/com.oracle.truffle.r.runtime.ffi/src/com/oracle/truffle/r/runtime/ffi/RFFIVariables.java
@@ -80,7 +80,7 @@ public enum RFFIVariables {
     R_BlankString(RDataFactory.createStringVectorFromScalar("")),
     R_TrueValue(RRuntime.LOGICAL_TRUE),
     R_FalseValue(RRuntime.LOGICAL_FALSE),
-    R_LogicalNAValue(RRuntime.LOGICAL_NA); // updated with setInteractive
+    R_LogicalNAValue(RRuntime.LOGICAL_NA);
 
     private Object value;
 
-- 
GitLab