diff --git a/com.oracle.truffle.r.native/fficall/src/jni/Rembedded.c b/com.oracle.truffle.r.native/fficall/src/jni/Rembedded.c index 2b4debd6345c0121ed648700464d75bfdab0eb8c..6b062aee269b78d651a63fb41437aeed80733dbb 100644 --- a/com.oracle.truffle.r.native/fficall/src/jni/Rembedded.c +++ b/com.oracle.truffle.r.native/fficall/src/jni/Rembedded.c @@ -602,7 +602,7 @@ CTXT R_getGlobalFunctionContext() { jmethodID methodID = checkGetMethodID(jniEnv, CallRFFIHelperClass, "R_getGlobalFunctionContext", "()Ljava/lang/Object;", 1); CTXT result = (*jniEnv)->CallStaticObjectMethod(jniEnv, CallRFFIHelperClass, methodID); result = checkRef(jniEnv, result); - return result == R_NilValue ? NULL : result; + return result == R_NilValue ? NULL : addGlobalRef(jniEnv, result, 0); } CTXT R_getParentFunctionContext(CTXT c) { @@ -610,7 +610,7 @@ CTXT R_getParentFunctionContext(CTXT c) { jmethodID methodID = checkGetMethodID(jniEnv, CallRFFIHelperClass, "R_getParentFunctionContext", "(Ljava/lang/Object;)Ljava/lang/Object;", 1); CTXT result = (*jniEnv)->CallStaticObjectMethod(jniEnv, CallRFFIHelperClass, methodID, c); result = checkRef(jniEnv, result); - return result == R_NilValue ? NULL : result; + return result == R_NilValue ? NULL : addGlobalRef(jniEnv, result, 0); } SEXP R_getContextEnv(CTXT context) { diff --git a/com.oracle.truffle.r.native/fficall/src/jni/rffiutils.c b/com.oracle.truffle.r.native/fficall/src/jni/rffiutils.c index 99380b2102c596fb7de9dec3ba3458872a079988..5f9425d8a7ffd68d8607ad2c3cc9864671065fb9 100644 --- a/com.oracle.truffle.r.native/fficall/src/jni/rffiutils.c +++ b/com.oracle.truffle.r.native/fficall/src/jni/rffiutils.c @@ -356,7 +356,7 @@ static SEXP findCachedGlobalRef(JNIEnv *env, SEXP obj) { return NULL; } -static SEXP addGlobalRef(JNIEnv *env, SEXP obj, int permanent) { +SEXP addGlobalRef(JNIEnv *env, SEXP obj, int permanent) { SEXP gref; if (cachedGlobalRefsHwm >= cachedGlobalRefsLength) { int newLength = cachedGlobalRefsLength * 2; diff --git a/com.oracle.truffle.r.native/fficall/src/jni/rffiutils.h b/com.oracle.truffle.r.native/fficall/src/jni/rffiutils.h index 6acab7320e57924811436523cfe3aafe20064093..78bbe21b9fe3c27f7113b2f213ac5500e5721929 100644 --- a/com.oracle.truffle.r.native/fficall/src/jni/rffiutils.h +++ b/com.oracle.truffle.r.native/fficall/src/jni/rffiutils.h @@ -75,6 +75,8 @@ void *getNativeArray(JNIEnv *env, SEXP x, SEXPTYPE type); void invalidateNativeArray(JNIEnv *env, SEXP oldObj); void updateNativeArrays(JNIEnv *env); +SEXP addGlobalRef(JNIEnv *env, SEXP obj, int permanent); + void init_rmath(JNIEnv *env); void init_variables(JNIEnv *env, jobjectArray initialValues); void init_dynload(JNIEnv *env); diff --git a/com.oracle.truffle.r.native/fficall/src/jni/variables.c b/com.oracle.truffle.r.native/fficall/src/jni/variables.c index 887dcea7bdda127481c454c0fc447b77dad429b0..ca381df5e2e84d8b6568bca259034d09d8227244 100644 --- a/com.oracle.truffle.r.native/fficall/src/jni/variables.c +++ b/com.oracle.truffle.r.native/fficall/src/jni/variables.c @@ -61,7 +61,8 @@ SEXP FASTR_NamespaceRegistry() { CTXT FASTR_GlobalContext() { JNIEnv *env = getEnv(); - return (*env)->CallStaticObjectMethod(env, CallRFFIHelperClass, getGlobalContextMethodID); + CTXT res = (*env)->CallStaticObjectMethod(env, CallRFFIHelperClass, getGlobalContextMethodID); + return addGlobalRef(env, res, 0); } void init_variables(JNIEnv *env, jobjectArray initialValues) { diff --git a/com.oracle.truffle.r.runtime.ffi/src/com/oracle/truffle/r/runtime/ffi/jnr/CallRFFIHelper.java b/com.oracle.truffle.r.runtime.ffi/src/com/oracle/truffle/r/runtime/ffi/jnr/CallRFFIHelper.java index 60b2aadf4b26095490a9211fa6913c570dc060bb..81c57b689ead21ac118f5bbb0b75a327f91f9948 100644 --- a/com.oracle.truffle.r.runtime.ffi/src/com/oracle/truffle/r/runtime/ffi/jnr/CallRFFIHelper.java +++ b/com.oracle.truffle.r.runtime.ffi/src/com/oracle/truffle/r/runtime/ffi/jnr/CallRFFIHelper.java @@ -1167,6 +1167,7 @@ public class CallRFFIHelper { } public static Object getGlobalContext() { + Utils.warn("Potential memory leak (global context object)"); if (RFFIUtils.traceEnabled()) { RFFIUtils.traceUpCall("getGlobalContext"); } @@ -1251,6 +1252,7 @@ public class CallRFFIHelper { // Checkstyle: stop method name check public static Object R_getGlobalFunctionContext() { + Utils.warn("Potential memory leak (global function context object)"); if (RFFIUtils.traceEnabled()) { RFFIUtils.traceUpCall("getGlobalFunctionContext"); } @@ -1269,6 +1271,7 @@ public class CallRFFIHelper { } public static Object R_getParentFunctionContext(Object c) { + Utils.warn("Potential memory leak (parent function context object)"); if (RFFIUtils.traceEnabled()) { RFFIUtils.traceUpCall("getParentFunctionContext"); }