From 7cea8caec09c65343d853fac78da6ce6ebed03aa Mon Sep 17 00:00:00 2001 From: Mick Jordan <mick.jordan@oracle.com> Date: Fri, 2 Dec 2016 16:25:14 -0800 Subject: [PATCH] rffi: add interface for RFFI upcalls; refactor native layer to use instance not static class; add factory for alternate upcall implementations --- .../fficall/src/jni/Parse.c | 6 +- .../fficall/src/jni/Random.c | 12 +- .../fficall/src/jni/Rembedded.c | 44 +- .../fficall/src/jni/Rinternals.c | 384 ++++---- .../fficall/src/jni/call_rffi.c | 5 +- .../fficall/src/jni/rffiutils.c | 25 +- .../fficall/src/jni/rffiutils.h | 5 +- .../fficall/src/jni/variables.c | 32 +- ...llRFFIHelper.java => JavaUpCallsRFFI.java} | 899 ++++++++++-------- .../r/runtime/ffi/JavaUpCallsRFFIFactory.java | 32 + .../truffle/r/runtime/ffi/RFFIVariables.java | 3 +- .../truffle/r/runtime/ffi/jni/JNI_Call.java | 6 +- .../runtime/ffi/jni/TraceUpCallsAdapter.java | 893 +++++++++++++++++ .../truffle/r/runtime/ffi/CharSXPWrapper.java | 55 ++ .../truffle/r/runtime/ffi/ParseResult.java | 44 + .../oracle/truffle/r/runtime/ffi/RFFI.java | 3 + .../truffle/r/runtime/ffi/UpCallsRFFI.java | 279 ++++++ .../r/runtime/ffi/UpCallsRFFIFactory.java | 44 + 18 files changed, 2100 insertions(+), 671 deletions(-) rename com.oracle.truffle.r.runtime.ffi/src/com/oracle/truffle/r/runtime/ffi/{jni/CallRFFIHelper.java => JavaUpCallsRFFI.java} (66%) create mode 100644 com.oracle.truffle.r.runtime.ffi/src/com/oracle/truffle/r/runtime/ffi/JavaUpCallsRFFIFactory.java create mode 100644 com.oracle.truffle.r.runtime.ffi/src/com/oracle/truffle/r/runtime/ffi/jni/TraceUpCallsAdapter.java create mode 100644 com.oracle.truffle.r.runtime/src/com/oracle/truffle/r/runtime/ffi/CharSXPWrapper.java create mode 100644 com.oracle.truffle.r.runtime/src/com/oracle/truffle/r/runtime/ffi/ParseResult.java create mode 100644 com.oracle.truffle.r.runtime/src/com/oracle/truffle/r/runtime/ffi/UpCallsRFFI.java create mode 100644 com.oracle.truffle.r.runtime/src/com/oracle/truffle/r/runtime/ffi/UpCallsRFFIFactory.java diff --git a/com.oracle.truffle.r.native/fficall/src/jni/Parse.c b/com.oracle.truffle.r.native/fficall/src/jni/Parse.c index cc55518f19..233a58dbc1 100644 --- a/com.oracle.truffle.r.native/fficall/src/jni/Parse.c +++ b/com.oracle.truffle.r.native/fficall/src/jni/Parse.c @@ -30,15 +30,15 @@ static jfieldID parseExprFieldID; void init_parse(JNIEnv *env) { - parseMethodID = checkGetMethodID(env, CallRFFIHelperClass, "R_ParseVector", "(Ljava/lang/Object;ILjava/lang/Object;)Ljava/lang/Object;", 1); - parseResultClass = checkFindClass(env, "com/oracle/truffle/r/runtime/ffi/jni/CallRFFIHelper$ParseResult"); + parseMethodID = checkGetMethodID(env, UpCallsRFFIClass, "R_ParseVector", "(Ljava/lang/Object;ILjava/lang/Object;)Ljava/lang/Object;", 0); + parseResultClass = checkFindClass(env, "com/oracle/truffle/r/runtime/ffi/ParseResult"); parseStatusFieldID = checkGetFieldID(env, parseResultClass, "parseStatus", "I", 0); parseExprFieldID = checkGetFieldID(env, parseResultClass, "expr", "Ljava/lang/Object;", 0); } SEXP R_ParseVector(SEXP text, int n, ParseStatus *z, SEXP srcfile) { JNIEnv *env = getEnv(); - jobject result = (*env)->CallStaticObjectMethod(env, CallRFFIHelperClass, parseMethodID, text, n, srcfile); + jobject result = (*env)->CallObjectMethod(env, UpCallsRFFIObject, parseMethodID, text, n, srcfile); *z = (*env)->GetIntField(env, result, parseStatusFieldID); return (*env)->GetObjectField(env, result, parseExprFieldID); } diff --git a/com.oracle.truffle.r.native/fficall/src/jni/Random.c b/com.oracle.truffle.r.native/fficall/src/jni/Random.c index 70341f309a..4c958521f1 100644 --- a/com.oracle.truffle.r.native/fficall/src/jni/Random.c +++ b/com.oracle.truffle.r.native/fficall/src/jni/Random.c @@ -27,24 +27,24 @@ static jmethodID PutRNGstate_MethodID; static jmethodID UnifRand_MethodID; void init_random(JNIEnv *env) { - GetRNGstate_MethodID = checkGetMethodID(env, CallRFFIHelperClass, "getRNGstate", "()V", 1); - PutRNGstate_MethodID = checkGetMethodID(env, CallRFFIHelperClass, "putRNGstate", "()V", 1); - UnifRand_MethodID = checkGetMethodID(env, CallRFFIHelperClass, "unifRand", "()D", 1); + GetRNGstate_MethodID = checkGetMethodID(env, UpCallsRFFIClass, "GetRNGstate", "()V", 0); + PutRNGstate_MethodID = checkGetMethodID(env, UpCallsRFFIClass, "PutRNGstate", "()V", 0); + UnifRand_MethodID = checkGetMethodID(env, UpCallsRFFIClass, "unif_rand", "()D", 0); } void GetRNGstate() { JNIEnv *thisenv = getEnv(); - (*thisenv)->CallStaticVoidMethod(thisenv, CallRFFIHelperClass, GetRNGstate_MethodID); + (*thisenv)->CallVoidMethod(thisenv, UpCallsRFFIObject, GetRNGstate_MethodID); } void PutRNGstate() { JNIEnv *thisenv = getEnv(); - (*thisenv)->CallStaticVoidMethod(thisenv, CallRFFIHelperClass, PutRNGstate_MethodID); + (*thisenv)->CallVoidMethod(thisenv, UpCallsRFFIObject, PutRNGstate_MethodID); } double unif_rand() { JNIEnv *thisenv = getEnv(); - return (*thisenv)->CallStaticDoubleMethod(thisenv, CallRFFIHelperClass, UnifRand_MethodID); + return (*thisenv)->CallDoubleMethod(thisenv, UpCallsRFFIObject, UnifRand_MethodID); } double norm_rand() { 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 f7cb4401f5..11bfb92d75 100644 --- a/com.oracle.truffle.r.native/fficall/src/jni/Rembedded.c +++ b/com.oracle.truffle.r.native/fficall/src/jni/Rembedded.c @@ -178,8 +178,8 @@ int Rf_initialize_R(int argc, char *argv[]) { char *R_HomeDir(void) { JNIEnv *jniEnv = getEnv(); - jmethodID R_HomeDirMethodID = checkGetMethodID(jniEnv, CallRFFIHelperClass, "R_HomeDir", "()Ljava/lang/String;", 1); - jstring homeDir = (*jniEnv)->CallStaticObjectMethod(jniEnv, CallRFFIHelperClass, R_HomeDirMethodID); + jmethodID R_HomeDirMethodID = checkGetMethodID(jniEnv, UpCallsRFFIClass, "R_HomeDir", "()Ljava/lang/String;", 0); + jstring homeDir = (*jniEnv)->CallObjectMethod(jniEnv, UpCallsRFFIObject, R_HomeDirMethodID); const char *homeDirChars = stringToChars(jniEnv, homeDir); return (char *)homeDirChars; } @@ -308,8 +308,8 @@ void uR_Busy(int x) { void uR_CleanUp(SA_TYPE x, int y, int z) { JNIEnv *jniEnv = getEnv(); - jmethodID methodID = checkGetMethodID(jniEnv, CallRFFIHelperClass, "R_CleanUp", "(III)V", 1); - (*jniEnv)->CallStaticVoidMethod(jniEnv, CallRFFIHelperClass, methodID, x, y, z); + jmethodID methodID = checkGetMethodID(jniEnv, UpCallsRFFIClass, "R_CleanUp", "(III)V", 1); + (*jniEnv)->CallStaticVoidMethod(jniEnv, UpCallsRFFIClass, methodID, x, y, z); } int uR_ShowFiles(int a, const char **b, const char **c, @@ -599,63 +599,63 @@ static char **update_environ_with_java_home(void) { CTXT R_getGlobalFunctionContext() { JNIEnv *jniEnv = getEnv(); - jmethodID methodID = checkGetMethodID(jniEnv, CallRFFIHelperClass, "R_getGlobalFunctionContext", "()Ljava/lang/Object;", 1); - CTXT result = (*jniEnv)->CallStaticObjectMethod(jniEnv, CallRFFIHelperClass, methodID); + jmethodID methodID = checkGetMethodID(jniEnv, UpCallsRFFIClass, "R_getGlobalFunctionContext", "()Ljava/lang/Object;", 0); + CTXT result = (*jniEnv)->CallObjectMethod(jniEnv, UpCallsRFFIObject, methodID); SEXP new_result = checkRef(jniEnv, result); return new_result == R_NilValue ? NULL : addGlobalRef(jniEnv, result, 0); } CTXT R_getParentFunctionContext(CTXT c) { JNIEnv *jniEnv = getEnv(); - jmethodID methodID = checkGetMethodID(jniEnv, CallRFFIHelperClass, "R_getParentFunctionContext", "(Ljava/lang/Object;)Ljava/lang/Object;", 1); - CTXT result = (*jniEnv)->CallStaticObjectMethod(jniEnv, CallRFFIHelperClass, methodID, c); + jmethodID methodID = checkGetMethodID(jniEnv, UpCallsRFFIClass, "R_getParentFunctionContext", "(Ljava/lang/Object;)Ljava/lang/Object;", 0); + CTXT result = (*jniEnv)->CallObjectMethod(jniEnv, UpCallsRFFIObject, methodID, c); SEXP new_result = checkRef(jniEnv, result); return new_result == R_NilValue ? NULL : addGlobalRef(jniEnv, result, 0); } SEXP R_getContextEnv(CTXT context) { JNIEnv *jniEnv = getEnv(); - jmethodID methodID = checkGetMethodID(jniEnv, CallRFFIHelperClass, "R_getContextEnv", "(Ljava/lang/Object;)Ljava/lang/Object;", 1); - SEXP result = (*jniEnv)->CallStaticObjectMethod(jniEnv, CallRFFIHelperClass, methodID, context); + jmethodID methodID = checkGetMethodID(jniEnv, UpCallsRFFIClass, "R_getContextEnv", "(Ljava/lang/Object;)Ljava/lang/Object;", 0); + SEXP result = (*jniEnv)->CallObjectMethod(jniEnv, UpCallsRFFIObject, methodID, context); return checkRef(jniEnv, result); } SEXP R_getContextFun(CTXT context) { JNIEnv *jniEnv = getEnv(); - jmethodID methodID = checkGetMethodID(jniEnv, CallRFFIHelperClass, "R_getContextFun", "(Ljava/lang/Object;)Ljava/lang/Object;", 1); - SEXP result = (*jniEnv)->CallStaticObjectMethod(jniEnv, CallRFFIHelperClass, methodID, context); + jmethodID methodID = checkGetMethodID(jniEnv, UpCallsRFFIClass, "R_getContextFun", "(Ljava/lang/Object;)Ljava/lang/Object;", 0); + SEXP result = (*jniEnv)->CallObjectMethod(jniEnv, UpCallsRFFIObject, methodID, context); return checkRef(jniEnv, result); } SEXP R_getContextCall(CTXT context) { JNIEnv *jniEnv = getEnv(); - jmethodID methodID = checkGetMethodID(jniEnv, CallRFFIHelperClass, "R_getContextCall", "(Ljava/lang/Object;)Ljava/lang/Object;", 1); - SEXP result = (*jniEnv)->CallStaticObjectMethod(jniEnv, CallRFFIHelperClass, methodID, context); + jmethodID methodID = checkGetMethodID(jniEnv, UpCallsRFFIClass, "R_getContextCall", "(Ljava/lang/Object;)Ljava/lang/Object;", 0); + SEXP result = (*jniEnv)->CallObjectMethod(jniEnv, UpCallsRFFIObject, methodID, context); return checkRef(jniEnv, result); } SEXP R_getContextSrcRef(CTXT context) { JNIEnv *jniEnv = getEnv(); - jmethodID methodID = checkGetMethodID(jniEnv, CallRFFIHelperClass, "R_getContextSrcRef", "(Ljava/lang/Object;)Ljava/lang/Object;", 1); - SEXP result = (*jniEnv)->CallStaticObjectMethod(jniEnv, CallRFFIHelperClass, methodID, context); + jmethodID methodID = checkGetMethodID(jniEnv, UpCallsRFFIClass, "R_getContextSrcRef", "(Ljava/lang/Object;)Ljava/lang/Object;", 0); + SEXP result = (*jniEnv)->CallObjectMethod(jniEnv, UpCallsRFFIObject, methodID, context); result = checkRef(jniEnv, result); return result == R_NilValue ? NULL : result; } int R_insideBrowser() { JNIEnv *jniEnv = getEnv(); - jmethodID methodID = checkGetMethodID(jniEnv, CallRFFIHelperClass, "R_insideBrowser", "()I", 1); - return (*jniEnv)->CallStaticIntMethod(jniEnv, CallRFFIHelperClass, methodID); + jmethodID methodID = checkGetMethodID(jniEnv, UpCallsRFFIClass, "R_insideBrowser", "()I", 0); + return (*jniEnv)->CallStaticIntMethod(jniEnv, UpCallsRFFIClass, methodID); } int R_isGlobal(CTXT context) { JNIEnv *jniEnv = getEnv(); - jmethodID methodID = checkGetMethodID(jniEnv, CallRFFIHelperClass, "R_isGlobal", "(Ljava/lang/Object;)I", 1); - return (*jniEnv)->CallStaticIntMethod(jniEnv, CallRFFIHelperClass, methodID, context); + jmethodID methodID = checkGetMethodID(jniEnv, UpCallsRFFIClass, "R_isGlobal", "(Ljava/lang/Object;)I", 0); + return (*jniEnv)->CallStaticIntMethod(jniEnv, UpCallsRFFIClass, methodID, context); } int R_isEqual(void* x, void* y) { JNIEnv *jniEnv = getEnv(); - jmethodID methodID = checkGetMethodID(jniEnv, CallRFFIHelperClass, "R_isEqual", "(Ljava/lang/Object;Ljava/lang/Object;)I", 1); - return (*jniEnv)->CallStaticIntMethod(jniEnv, CallRFFIHelperClass, methodID, x, y); + jmethodID methodID = checkGetMethodID(jniEnv, UpCallsRFFIClass, "R_isEqual", "(Ljava/lang/Object;Ljava/lang/Object;)I", 0); + return (*jniEnv)->CallStaticIntMethod(jniEnv, UpCallsRFFIClass, methodID, x, y); } diff --git a/com.oracle.truffle.r.native/fficall/src/jni/Rinternals.c b/com.oracle.truffle.r.native/fficall/src/jni/Rinternals.c index 3972ae97f4..aa4b3352b6 100644 --- a/com.oracle.truffle.r.native/fficall/src/jni/Rinternals.c +++ b/com.oracle.truffle.r.native/fficall/src/jni/Rinternals.c @@ -30,7 +30,7 @@ // to ensure that a global JNI handle is created (if necessary) and returned, // otherwise a GC might reclaim the result. -// N.B. ALL functions go via CallRFFIHelper to provide a single point of re-entry +// N.B. ALL functions go via UpCallsRFFI to provide a single point of re-entry static jmethodID Rf_ScalarIntegerMethodID; static jmethodID Rf_ScalarDoubleMethodID; @@ -102,7 +102,7 @@ static jmethodID TYPEOF_MethodID; static jmethodID OBJECT_MethodID; static jmethodID DUPLICATE_ATTRIB_MethodID; static jmethodID isS4ObjectMethodID; -static jmethodID logObject_MethodID; +static jmethodID logNotCharSXPWrapperMethodID; static jmethodID R_tryEvalMethodID; static jmethodID RDEBUGMethodID; static jmethodID SET_RDEBUGMethodID; @@ -113,7 +113,7 @@ static jmethodID PRVALUEMethodID; static jmethodID R_lsInternal3MethodID; static jmethodID R_do_MAKE_CLASS_MethodID; -static jmethodID resetAndGetHandlerStacksMethodID; +static jmethodID R_ToplevelExecMethodID; static jmethodID restoreHandlerStacksMethodID; static jmethodID R_MakeExternalPtrMethodID; @@ -136,107 +136,107 @@ static jfieldID CharSXPWrapperContentsFieldID; jmethodID setCompleteMethodID; void init_internals(JNIEnv *env) { - Rf_ScalarIntegerMethodID = checkGetMethodID(env, CallRFFIHelperClass, "Rf_ScalarInteger", "(I)Lcom/oracle/truffle/r/runtime/data/RIntVector;", 1); - Rf_ScalarDoubleMethodID = checkGetMethodID(env, CallRFFIHelperClass, "Rf_ScalarDouble", "(D)Lcom/oracle/truffle/r/runtime/data/RDoubleVector;", 1); - Rf_ScalarStringMethodID = checkGetMethodID(env, CallRFFIHelperClass, "Rf_ScalarString", "(Ljava/lang/Object;)Lcom/oracle/truffle/r/runtime/data/RStringVector;", 1); - Rf_ScalarLogicalMethodID = checkGetMethodID(env, CallRFFIHelperClass, "Rf_ScalarLogical", "(I)Lcom/oracle/truffle/r/runtime/data/RLogicalVector;", 1); - Rf_consMethodID = checkGetMethodID(env, CallRFFIHelperClass, "Rf_cons", "(Ljava/lang/Object;Ljava/lang/Object;)Ljava/lang/Object;", 1); - Rf_evalMethodID = checkGetMethodID(env, CallRFFIHelperClass, "Rf_eval", "(Ljava/lang/Object;Ljava/lang/Object;)Ljava/lang/Object;", 1); - Rf_findfunMethodID = checkGetMethodID(env, CallRFFIHelperClass, "Rf_findfun", "(Ljava/lang/Object;Ljava/lang/Object;)Ljava/lang/Object;", 1); - Rf_defineVarMethodID = checkGetMethodID(env, CallRFFIHelperClass, "Rf_defineVar", "(Ljava/lang/Object;Ljava/lang/Object;Ljava/lang/Object;)V", 1); - Rf_findVarMethodID = checkGetMethodID(env, CallRFFIHelperClass, "Rf_findVar", "(Ljava/lang/Object;Ljava/lang/Object;)Ljava/lang/Object;", 1); - Rf_findVarInFrameMethodID = checkGetMethodID(env, CallRFFIHelperClass, "Rf_findVarInFrame", "(Ljava/lang/Object;Ljava/lang/Object;)Ljava/lang/Object;", 1); - Rf_findVarInFrame3MethodID = checkGetMethodID(env, CallRFFIHelperClass, "Rf_findVarInFrame3", "(Ljava/lang/Object;Ljava/lang/Object;I)Ljava/lang/Object;", 1); - Rf_getAttribMethodID = checkGetMethodID(env, CallRFFIHelperClass, "Rf_getAttrib", "(Ljava/lang/Object;Ljava/lang/Object;)Ljava/lang/Object;", 1); - Rf_setAttribMethodID = checkGetMethodID(env, CallRFFIHelperClass, "Rf_setAttrib", "(Ljava/lang/Object;Ljava/lang/Object;Ljava/lang/Object;)V", 1); - Rf_isStringMethodID = checkGetMethodID(env, CallRFFIHelperClass, "Rf_isString", "(Ljava/lang/Object;)I", 1); - Rf_isNullMethodID = checkGetMethodID(env, CallRFFIHelperClass, "Rf_isNull", "(Ljava/lang/Object;)I", 1); - Rf_installMethodID = checkGetMethodID(env, CallRFFIHelperClass, "Rf_install", "(Ljava/lang/String;)Ljava/lang/Object;", 1); - Rf_warningMethodID = checkGetMethodID(env, CallRFFIHelperClass, "Rf_warning", "(Ljava/lang/String;)V", 1); - Rf_warningcallMethodID = checkGetMethodID(env, CallRFFIHelperClass, "Rf_warningcall", "(Ljava/lang/Object;Ljava/lang/String;)V", 1); - Rf_errorMethodID = checkGetMethodID(env, CallRFFIHelperClass, "Rf_error", "(Ljava/lang/String;)V", 1); - Rf_allocateVectorMethodID = checkGetMethodID(env, CallRFFIHelperClass, "Rf_allocateVector", "(II)Ljava/lang/Object;", 1); - Rf_allocateMatrixMethodID = checkGetMethodID(env, CallRFFIHelperClass, "Rf_allocateMatrix", "(III)Ljava/lang/Object;", 1); - Rf_allocateArrayMethodID = checkGetMethodID(env, CallRFFIHelperClass, "Rf_allocateArray", "(ILjava/lang/Object;)Ljava/lang/Object;", 1); - Rf_duplicateMethodID = checkGetMethodID(env, CallRFFIHelperClass, "Rf_duplicate", "(Ljava/lang/Object;I)Ljava/lang/Object;", 1); - Rf_anyDuplicatedMethodID = checkGetMethodID(env, CallRFFIHelperClass, "Rf_anyDuplicated", "(Ljava/lang/Object;I)I", 1); - R_NewHashedEnvMethodID = checkGetMethodID(env, CallRFFIHelperClass, "R_NewHashedEnv", "(Lcom/oracle/truffle/r/runtime/env/REnvironment;Ljava/lang/String;ZI)Lcom/oracle/truffle/r/runtime/env/REnvironment;", 1); - Rf_classgetsMethodID = checkGetMethodID(env, CallRFFIHelperClass, "Rf_classgets", "(Ljava/lang/Object;Ljava/lang/Object;)Ljava/lang/Object;", 1); - RprintfMethodID = checkGetMethodID(env, CallRFFIHelperClass, "printf", "(Ljava/lang/String;)V", 1); - R_do_MAKE_CLASS_MethodID = checkGetMethodID(env, CallRFFIHelperClass, "R_do_MAKE_CLASS", "(Ljava/lang/String;)Ljava/lang/Object;", 1); - R_FindNamespaceMethodID = checkGetMethodID(env, CallRFFIHelperClass, "R_FindNamespace", "(Ljava/lang/Object;)Ljava/lang/Object;", 1); - R_BindingIsLockedID = checkGetMethodID(env, CallRFFIHelperClass, "R_BindingIsLocked", "(Ljava/lang/Object;Ljava/lang/Object;)I", 1); - Rf_GetOption1MethodID = checkGetMethodID(env, CallRFFIHelperClass, "Rf_GetOption1", "(Ljava/lang/Object;)Ljava/lang/Object;", 1); - Rf_gsetVarMethodID = checkGetMethodID(env, CallRFFIHelperClass, "Rf_gsetVar", "(Ljava/lang/Object;Ljava/lang/Object;Ljava/lang/Object;)V", 1); - Rf_inheritsMethodID = checkGetMethodID(env, CallRFFIHelperClass, "Rf_inherits", "(Ljava/lang/Object;Ljava/lang/String;)I", 1); - Rf_lengthgetsMethodID = checkGetMethodID(env, CallRFFIHelperClass, "Rf_lengthgets", "(Ljava/lang/Object;I)Ljava/lang/Object;", 1); -// Rf_rPsortMethodID = checkGetMethodID(env, CallRFFIHelperClass, "Rf_rPsort", "(Lcom/oracle/truffle/r/runtime/data/RDoubleVector;II)", 1); -// Rf_iPsortMethodID = checkGetMethodID(env, CallRFFIHelperClass, "Rf_iPsort", "(Lcom/oracle/truffle/r/runtime/data/RIntVector;II)", 1); - CADR_MethodID = checkGetMethodID(env, CallRFFIHelperClass, "CADR", "(Ljava/lang/Object;)Ljava/lang/Object;", 1); - CADDR_MethodID = checkGetMethodID(env, CallRFFIHelperClass, "CADDR", "(Ljava/lang/Object;)Ljava/lang/Object;", 1); - TAG_MethodID = checkGetMethodID(env, CallRFFIHelperClass, "TAG", "(Ljava/lang/Object;)Ljava/lang/Object;", 1); - PRINTNAME_MethodID = checkGetMethodID(env, CallRFFIHelperClass, "PRINTNAME", "(Ljava/lang/Object;)Ljava/lang/Object;", 1); - CAR_MethodID = checkGetMethodID(env, CallRFFIHelperClass, "CAR", "(Ljava/lang/Object;)Ljava/lang/Object;", 1); - CDR_MethodID = checkGetMethodID(env, CallRFFIHelperClass, "CDR", "(Ljava/lang/Object;)Ljava/lang/Object;", 1); - CDDR_MethodID = checkGetMethodID(env, CallRFFIHelperClass, "CDDR", "(Ljava/lang/Object;)Ljava/lang/Object;", 1); - SET_TAG_MethodID = checkGetMethodID(env, CallRFFIHelperClass, "SET_TAG", "(Ljava/lang/Object;Ljava/lang/Object;)Ljava/lang/Object;", 1); - SETCAR_MethodID = checkGetMethodID(env, CallRFFIHelperClass, "SETCAR", "(Ljava/lang/Object;Ljava/lang/Object;)Ljava/lang/Object;", 1); - SETCDR_MethodID = checkGetMethodID(env, CallRFFIHelperClass, "SETCDR", "(Ljava/lang/Object;Ljava/lang/Object;)Ljava/lang/Object;", 1); - SETCADR_MethodID = checkGetMethodID(env, CallRFFIHelperClass, "SETCADR", "(Ljava/lang/Object;Ljava/lang/Object;)Ljava/lang/Object;", 1); - SYMVALUE_MethodID = checkGetMethodID(env, CallRFFIHelperClass, "SYMVALUE", "(Ljava/lang/Object;)Ljava/lang/Object;", 1); - SET_SYMVALUE_MethodID = checkGetMethodID(env, CallRFFIHelperClass, "SET_SYMVALUE", "(Ljava/lang/Object;Ljava/lang/Object;)V", 1); - SET_STRING_ELT_MethodID = checkGetMethodID(env, CallRFFIHelperClass, "SET_STRING_ELT", "(Ljava/lang/Object;ILjava/lang/Object;)V", 1); - SET_VECTOR_ELT_MethodID = checkGetMethodID(env, CallRFFIHelperClass, "SET_VECTOR_ELT", "(Ljava/lang/Object;ILjava/lang/Object;)V", 1); - RAW_MethodID = checkGetMethodID(env, CallRFFIHelperClass, "RAW", "(Ljava/lang/Object;)[B", 1); - REAL_MethodID = checkGetMethodID(env, CallRFFIHelperClass, "REAL", "(Ljava/lang/Object;)[D", 1); - LOGICAL_MethodID = checkGetMethodID(env, CallRFFIHelperClass, "LOGICAL", "(Ljava/lang/Object;)[B", 1); - INTEGER_MethodID = checkGetMethodID(env, CallRFFIHelperClass, "INTEGER", "(Ljava/lang/Object;)[I", 1); - STRING_ELT_MethodID = checkGetMethodID(env, CallRFFIHelperClass, "STRING_ELT", "(Ljava/lang/Object;I)Ljava/lang/Object;", 1); - VECTOR_ELT_MethodID = checkGetMethodID(env, CallRFFIHelperClass, "VECTOR_ELT", "(Ljava/lang/Object;I)Ljava/lang/Object;", 1); - LENGTH_MethodID = checkGetMethodID(env, CallRFFIHelperClass, "LENGTH", "(Ljava/lang/Object;)I", 1); - Rf_asIntegerMethodID = checkGetMethodID(env, CallRFFIHelperClass, "Rf_asInteger", "(Ljava/lang/Object;)I", 1); -// Rf_asRealMethodID = checkGetMethodID(env, CallRFFIHelperClass, "Rf_asReal", "(Ljava/lang/Object;)D", 1); - Rf_asCharMethodID = checkGetMethodID(env, CallRFFIHelperClass, "Rf_asChar", "(Ljava/lang/Object;)Ljava/lang/Object;", 1); - Rf_mkCharLenCEMethodID = checkGetMethodID(env, CallRFFIHelperClass, "Rf_mkCharLenCE", "([BI)Ljava/lang/Object;", 1); - Rf_asLogicalMethodID = checkGetMethodID(env, CallRFFIHelperClass, "Rf_asLogical", "(Ljava/lang/Object;)I", 1); - Rf_PairToVectorListMethodID = checkGetMethodID(env, CallRFFIHelperClass, "Rf_PairToVectorList", "(Ljava/lang/Object;)Ljava/lang/Object;", 1); - NAMED_MethodID = checkGetMethodID(env, CallRFFIHelperClass, "NAMED", "(Ljava/lang/Object;)I", 1); - SET_TYPEOF_FASTR_MethodID = checkGetMethodID(env, CallRFFIHelperClass, "SET_TYPEOF_FASTR", "(Ljava/lang/Object;I)Ljava/lang/Object;", 1); - TYPEOF_MethodID = checkGetMethodID(env, CallRFFIHelperClass, "TYPEOF", "(Ljava/lang/Object;)I", 1); - OBJECT_MethodID = checkGetMethodID(env, CallRFFIHelperClass, "OBJECT", "(Ljava/lang/Object;)I", 1); - DUPLICATE_ATTRIB_MethodID = checkGetMethodID(env, CallRFFIHelperClass, "DUPLICATE_ATTRIB", "(Ljava/lang/Object;Ljava/lang/Object;)V", 1); - isS4ObjectMethodID = checkGetMethodID(env, CallRFFIHelperClass, "isS4Object", "(Ljava/lang/Object;)I", 1); - logObject_MethodID = checkGetMethodID(env, CallRFFIHelperClass, "logObject", "(Ljava/lang/Object;)V", 1); - R_tryEvalMethodID = checkGetMethodID(env, CallRFFIHelperClass, "R_tryEval", "(Ljava/lang/Object;Ljava/lang/Object;Z)Ljava/lang/Object;", 1); - RDEBUGMethodID = checkGetMethodID(env, CallRFFIHelperClass, "RDEBUG", "(Ljava/lang/Object;)I", 1); - SET_RDEBUGMethodID = checkGetMethodID(env, CallRFFIHelperClass, "SET_RDEBUG", "(Ljava/lang/Object;I)V", 1); - RSTEPMethodID = checkGetMethodID(env, CallRFFIHelperClass, "RSTEP", "(Ljava/lang/Object;)I", 1); - SET_RSTEPMethodID = checkGetMethodID(env, CallRFFIHelperClass, "SET_RSTEP", "(Ljava/lang/Object;I)V", 1); - ENCLOSMethodID = checkGetMethodID(env, CallRFFIHelperClass, "ENCLOS", "(Ljava/lang/Object;)Ljava/lang/Object;", 1); - PRVALUEMethodID = checkGetMethodID(env, CallRFFIHelperClass, "PRVALUE", "(Ljava/lang/Object;)Ljava/lang/Object;", 1); - R_lsInternal3MethodID = checkGetMethodID(env, CallRFFIHelperClass, "R_lsInternal3", "(Ljava/lang/Object;II)Ljava/lang/Object;", 1); - - resetAndGetHandlerStacksMethodID = checkGetMethodID(env, CallRFFIHelperClass, "resetAndGetErrorHandlerStacks", "()Ljava/lang/Object;", 1); - restoreHandlerStacksMethodID = checkGetMethodID(env, CallRFFIHelperClass, "restoreErrorHandlerStacks", "(Ljava/lang/Object;)V", 1); - - R_MakeExternalPtrMethodID = checkGetMethodID(env, CallRFFIHelperClass, "R_MakeExternalPtr", "(JLjava/lang/Object;Ljava/lang/Object;)Lcom/oracle/truffle/r/runtime/data/RExternalPtr;", 1); - R_ExternalPtrAddrMethodID = checkGetMethodID(env, CallRFFIHelperClass, "R_ExternalPtrAddr", "(Ljava/lang/Object;)J", 1); - R_ExternalPtrTagMethodID = checkGetMethodID(env, CallRFFIHelperClass, "R_ExternalPtrTag", "(Ljava/lang/Object;)Ljava/lang/Object;", 1); - R_ExternalPtrProtMethodID = checkGetMethodID(env, CallRFFIHelperClass, "R_ExternalPtrProt", "(Ljava/lang/Object;)Ljava/lang/Object;", 1); - R_SetExternalPtrAddrMethodID = checkGetMethodID(env, CallRFFIHelperClass, "R_SetExternalPtrAddr", "(Ljava/lang/Object;J)V", 1); - R_SetExternalPtrTagMethodID = checkGetMethodID(env, CallRFFIHelperClass, "R_SetExternalPtrTag", "(Ljava/lang/Object;Ljava/lang/Object;)V", 1); - R_SetExternalPtrProtMethodID = checkGetMethodID(env, CallRFFIHelperClass, "R_SetExternalPtrProt", "(Ljava/lang/Object;Ljava/lang/Object;)V", 1); - - CharSXPWrapperClass = checkFindClass(env, "com/oracle/truffle/r/runtime/ffi/jni/CallRFFIHelper$CharSXPWrapper"); + Rf_ScalarIntegerMethodID = checkGetMethodID(env, UpCallsRFFIClass, "Rf_ScalarInteger", "(I)Lcom/oracle/truffle/r/runtime/data/RIntVector;", 0); + Rf_ScalarDoubleMethodID = checkGetMethodID(env, UpCallsRFFIClass, "Rf_ScalarDouble", "(D)Lcom/oracle/truffle/r/runtime/data/RDoubleVector;", 0); + Rf_ScalarStringMethodID = checkGetMethodID(env, UpCallsRFFIClass, "Rf_ScalarString", "(Ljava/lang/Object;)Lcom/oracle/truffle/r/runtime/data/RStringVector;", 0); + Rf_ScalarLogicalMethodID = checkGetMethodID(env, UpCallsRFFIClass, "Rf_ScalarLogical", "(I)Lcom/oracle/truffle/r/runtime/data/RLogicalVector;", 0); + Rf_consMethodID = checkGetMethodID(env, UpCallsRFFIClass, "Rf_cons", "(Ljava/lang/Object;Ljava/lang/Object;)Ljava/lang/Object;", 0); + Rf_evalMethodID = checkGetMethodID(env, UpCallsRFFIClass, "Rf_eval", "(Ljava/lang/Object;Ljava/lang/Object;)Ljava/lang/Object;", 0); + Rf_findfunMethodID = checkGetMethodID(env, UpCallsRFFIClass, "Rf_findfun", "(Ljava/lang/Object;Ljava/lang/Object;)Ljava/lang/Object;", 0); + Rf_defineVarMethodID = checkGetMethodID(env, UpCallsRFFIClass, "Rf_defineVar", "(Ljava/lang/Object;Ljava/lang/Object;Ljava/lang/Object;)V", 0); + Rf_findVarMethodID = checkGetMethodID(env, UpCallsRFFIClass, "Rf_findVar", "(Ljava/lang/Object;Ljava/lang/Object;)Ljava/lang/Object;", 0); + Rf_findVarInFrameMethodID = checkGetMethodID(env, UpCallsRFFIClass, "Rf_findVarInFrame", "(Ljava/lang/Object;Ljava/lang/Object;)Ljava/lang/Object;", 0); + Rf_findVarInFrame3MethodID = checkGetMethodID(env, UpCallsRFFIClass, "Rf_findVarInFrame3", "(Ljava/lang/Object;Ljava/lang/Object;I)Ljava/lang/Object;", 0); + Rf_getAttribMethodID = checkGetMethodID(env, UpCallsRFFIClass, "Rf_getAttrib", "(Ljava/lang/Object;Ljava/lang/Object;)Ljava/lang/Object;", 0); + Rf_setAttribMethodID = checkGetMethodID(env, UpCallsRFFIClass, "Rf_setAttrib", "(Ljava/lang/Object;Ljava/lang/Object;Ljava/lang/Object;)V", 0); + Rf_isStringMethodID = checkGetMethodID(env, UpCallsRFFIClass, "Rf_isString", "(Ljava/lang/Object;)I", 0); + Rf_isNullMethodID = checkGetMethodID(env, UpCallsRFFIClass, "Rf_isNull", "(Ljava/lang/Object;)I", 0); + Rf_installMethodID = checkGetMethodID(env, UpCallsRFFIClass, "Rf_install", "(Ljava/lang/String;)Ljava/lang/Object;", 0); + Rf_warningMethodID = checkGetMethodID(env, UpCallsRFFIClass, "Rf_warning", "(Ljava/lang/String;)V", 0); + Rf_warningcallMethodID = checkGetMethodID(env, UpCallsRFFIClass, "Rf_warningcall", "(Ljava/lang/Object;Ljava/lang/String;)V", 0); + Rf_errorMethodID = checkGetMethodID(env, UpCallsRFFIClass, "Rf_error", "(Ljava/lang/String;)V", 0); + Rf_allocateVectorMethodID = checkGetMethodID(env, UpCallsRFFIClass, "Rf_allocateVector", "(II)Ljava/lang/Object;", 0); + Rf_allocateMatrixMethodID = checkGetMethodID(env, UpCallsRFFIClass, "Rf_allocateMatrix", "(III)Ljava/lang/Object;", 0); + Rf_allocateArrayMethodID = checkGetMethodID(env, UpCallsRFFIClass, "Rf_allocateArray", "(ILjava/lang/Object;)Ljava/lang/Object;", 0); + Rf_duplicateMethodID = checkGetMethodID(env, UpCallsRFFIClass, "Rf_duplicate", "(Ljava/lang/Object;I)Ljava/lang/Object;", 0); + Rf_anyDuplicatedMethodID = checkGetMethodID(env, UpCallsRFFIClass, "Rf_anyDuplicated", "(Ljava/lang/Object;I)I", 0); + R_NewHashedEnvMethodID = checkGetMethodID(env, UpCallsRFFIClass, "R_NewHashedEnv", "(Lcom/oracle/truffle/r/runtime/env/REnvironment;Ljava/lang/String;ZI)Lcom/oracle/truffle/r/runtime/env/REnvironment;", 0); + Rf_classgetsMethodID = checkGetMethodID(env, UpCallsRFFIClass, "Rf_classgets", "(Ljava/lang/Object;Ljava/lang/Object;)Ljava/lang/Object;", 0); + RprintfMethodID = checkGetMethodID(env, UpCallsRFFIClass, "Rprintf", "(Ljava/lang/String;)V", 0); + R_do_MAKE_CLASS_MethodID = checkGetMethodID(env, UpCallsRFFIClass, "R_do_MAKE_CLASS", "(Ljava/lang/String;)Ljava/lang/Object;", 0); + R_FindNamespaceMethodID = checkGetMethodID(env, UpCallsRFFIClass, "R_FindNamespace", "(Ljava/lang/Object;)Ljava/lang/Object;", 0); + R_BindingIsLockedID = checkGetMethodID(env, UpCallsRFFIClass, "R_BindingIsLocked", "(Ljava/lang/Object;Ljava/lang/Object;)I", 0); + Rf_GetOption1MethodID = checkGetMethodID(env, UpCallsRFFIClass, "Rf_GetOption1", "(Ljava/lang/Object;)Ljava/lang/Object;", 0); + Rf_gsetVarMethodID = checkGetMethodID(env, UpCallsRFFIClass, "Rf_gsetVar", "(Ljava/lang/Object;Ljava/lang/Object;Ljava/lang/Object;)V", 0); + Rf_inheritsMethodID = checkGetMethodID(env, UpCallsRFFIClass, "Rf_inherits", "(Ljava/lang/Object;Ljava/lang/String;)I", 0); + Rf_lengthgetsMethodID = checkGetMethodID(env, UpCallsRFFIClass, "Rf_lengthgets", "(Ljava/lang/Object;I)Ljava/lang/Object;", 0); +// Rf_rPsortMethodID = checkGetMethodID(env, UpCallsRFFIClass, "Rf_rPsort", "(Lcom/oracle/truffle/r/runtime/data/RDoubleVector;II)", 0); +// Rf_iPsortMethodID = checkGetMethodID(env, UpCallsRFFIClass, "Rf_iPsort", "(Lcom/oracle/truffle/r/runtime/data/RIntVector;II)", 0); + CADR_MethodID = checkGetMethodID(env, UpCallsRFFIClass, "CADR", "(Ljava/lang/Object;)Ljava/lang/Object;", 0); + CADDR_MethodID = checkGetMethodID(env, UpCallsRFFIClass, "CADDR", "(Ljava/lang/Object;)Ljava/lang/Object;", 0); + TAG_MethodID = checkGetMethodID(env, UpCallsRFFIClass, "TAG", "(Ljava/lang/Object;)Ljava/lang/Object;", 0); + PRINTNAME_MethodID = checkGetMethodID(env, UpCallsRFFIClass, "PRINTNAME", "(Ljava/lang/Object;)Ljava/lang/Object;", 0); + CAR_MethodID = checkGetMethodID(env, UpCallsRFFIClass, "CAR", "(Ljava/lang/Object;)Ljava/lang/Object;", 0); + CDR_MethodID = checkGetMethodID(env, UpCallsRFFIClass, "CDR", "(Ljava/lang/Object;)Ljava/lang/Object;", 0); + CDDR_MethodID = checkGetMethodID(env, UpCallsRFFIClass, "CDDR", "(Ljava/lang/Object;)Ljava/lang/Object;", 0); + SET_TAG_MethodID = checkGetMethodID(env, UpCallsRFFIClass, "SET_TAG", "(Ljava/lang/Object;Ljava/lang/Object;)Ljava/lang/Object;", 0); + SETCAR_MethodID = checkGetMethodID(env, UpCallsRFFIClass, "SETCAR", "(Ljava/lang/Object;Ljava/lang/Object;)Ljava/lang/Object;", 0); + SETCDR_MethodID = checkGetMethodID(env, UpCallsRFFIClass, "SETCDR", "(Ljava/lang/Object;Ljava/lang/Object;)Ljava/lang/Object;", 0); + SETCADR_MethodID = checkGetMethodID(env, UpCallsRFFIClass, "SETCADR", "(Ljava/lang/Object;Ljava/lang/Object;)Ljava/lang/Object;", 0); + SYMVALUE_MethodID = checkGetMethodID(env, UpCallsRFFIClass, "SYMVALUE", "(Ljava/lang/Object;)Ljava/lang/Object;", 0); + SET_SYMVALUE_MethodID = checkGetMethodID(env, UpCallsRFFIClass, "SET_SYMVALUE", "(Ljava/lang/Object;Ljava/lang/Object;)V", 0); + SET_STRING_ELT_MethodID = checkGetMethodID(env, UpCallsRFFIClass, "SET_STRING_ELT", "(Ljava/lang/Object;ILjava/lang/Object;)V", 0); + SET_VECTOR_ELT_MethodID = checkGetMethodID(env, UpCallsRFFIClass, "SET_VECTOR_ELT", "(Ljava/lang/Object;ILjava/lang/Object;)V", 0); + RAW_MethodID = checkGetMethodID(env, UpCallsRFFIClass, "RAW", "(Ljava/lang/Object;)[B", 0); + REAL_MethodID = checkGetMethodID(env, UpCallsRFFIClass, "REAL", "(Ljava/lang/Object;)[D", 0); + LOGICAL_MethodID = checkGetMethodID(env, UpCallsRFFIClass, "LOGICAL", "(Ljava/lang/Object;)[B", 0); + INTEGER_MethodID = checkGetMethodID(env, UpCallsRFFIClass, "INTEGER", "(Ljava/lang/Object;)[I", 0); + STRING_ELT_MethodID = checkGetMethodID(env, UpCallsRFFIClass, "STRING_ELT", "(Ljava/lang/Object;I)Ljava/lang/Object;", 0); + VECTOR_ELT_MethodID = checkGetMethodID(env, UpCallsRFFIClass, "VECTOR_ELT", "(Ljava/lang/Object;I)Ljava/lang/Object;", 0); + LENGTH_MethodID = checkGetMethodID(env, UpCallsRFFIClass, "LENGTH", "(Ljava/lang/Object;)I", 0); + Rf_asIntegerMethodID = checkGetMethodID(env, UpCallsRFFIClass, "Rf_asInteger", "(Ljava/lang/Object;)I", 0); +// Rf_asRealMethodID = checkGetMethodID(env, UpCallsRFFIClass, "Rf_asReal", "(Ljava/lang/Object;)D", 0); + Rf_asCharMethodID = checkGetMethodID(env, UpCallsRFFIClass, "Rf_asChar", "(Ljava/lang/Object;)Ljava/lang/Object;", 0); + Rf_mkCharLenCEMethodID = checkGetMethodID(env, UpCallsRFFIClass, "Rf_mkCharLenCE", "([BI)Ljava/lang/Object;", 0); + Rf_asLogicalMethodID = checkGetMethodID(env, UpCallsRFFIClass, "Rf_asLogical", "(Ljava/lang/Object;)I", 0); + Rf_PairToVectorListMethodID = checkGetMethodID(env, UpCallsRFFIClass, "Rf_PairToVectorList", "(Ljava/lang/Object;)Ljava/lang/Object;", 0); + NAMED_MethodID = checkGetMethodID(env, UpCallsRFFIClass, "NAMED", "(Ljava/lang/Object;)I", 0); + SET_TYPEOF_FASTR_MethodID = checkGetMethodID(env, UpCallsRFFIClass, "SET_TYPEOF_FASTR", "(Ljava/lang/Object;I)Ljava/lang/Object;", 0); + TYPEOF_MethodID = checkGetMethodID(env, UpCallsRFFIClass, "TYPEOF", "(Ljava/lang/Object;)I", 0); + OBJECT_MethodID = checkGetMethodID(env, UpCallsRFFIClass, "OBJECT", "(Ljava/lang/Object;)I", 0); + DUPLICATE_ATTRIB_MethodID = checkGetMethodID(env, UpCallsRFFIClass, "DUPLICATE_ATTRIB", "(Ljava/lang/Object;Ljava/lang/Object;)V", 0); + isS4ObjectMethodID = checkGetMethodID(env, UpCallsRFFIClass, "isS4Object", "(Ljava/lang/Object;)I", 0); + logNotCharSXPWrapperMethodID = checkGetMethodID(env, UpCallsRFFIClass, "logNotCharSXPWrapper", "(Ljava/lang/Object;)V", 0); + R_tryEvalMethodID = checkGetMethodID(env, UpCallsRFFIClass, "R_tryEval", "(Ljava/lang/Object;Ljava/lang/Object;Z)Ljava/lang/Object;", 0); + RDEBUGMethodID = checkGetMethodID(env, UpCallsRFFIClass, "RDEBUG", "(Ljava/lang/Object;)I", 0); + SET_RDEBUGMethodID = checkGetMethodID(env, UpCallsRFFIClass, "SET_RDEBUG", "(Ljava/lang/Object;I)V", 0); + RSTEPMethodID = checkGetMethodID(env, UpCallsRFFIClass, "RSTEP", "(Ljava/lang/Object;)I", 0); + SET_RSTEPMethodID = checkGetMethodID(env, UpCallsRFFIClass, "SET_RSTEP", "(Ljava/lang/Object;I)V", 0); + ENCLOSMethodID = checkGetMethodID(env, UpCallsRFFIClass, "ENCLOS", "(Ljava/lang/Object;)Ljava/lang/Object;", 0); + PRVALUEMethodID = checkGetMethodID(env, UpCallsRFFIClass, "PRVALUE", "(Ljava/lang/Object;)Ljava/lang/Object;", 0); + R_lsInternal3MethodID = checkGetMethodID(env, UpCallsRFFIClass, "R_lsInternal3", "(Ljava/lang/Object;II)Ljava/lang/Object;", 0); + + R_ToplevelExecMethodID = checkGetMethodID(env, UpCallsRFFIClass, "R_ToplevelExec", "()Ljava/lang/Object;", 0); + restoreHandlerStacksMethodID = checkGetMethodID(env, UpCallsRFFIClass, "R_ToplevelExecRestoreErrorHandlerStacks", "(Ljava/lang/Object;)V", 0); + + R_MakeExternalPtrMethodID = checkGetMethodID(env, UpCallsRFFIClass, "R_MakeExternalPtr", "(JLjava/lang/Object;Ljava/lang/Object;)Lcom/oracle/truffle/r/runtime/data/RExternalPtr;", 0); + R_ExternalPtrAddrMethodID = checkGetMethodID(env, UpCallsRFFIClass, "R_ExternalPtrAddr", "(Ljava/lang/Object;)J", 0); + R_ExternalPtrTagMethodID = checkGetMethodID(env, UpCallsRFFIClass, "R_ExternalPtrTag", "(Ljava/lang/Object;)Ljava/lang/Object;", 0); + R_ExternalPtrProtMethodID = checkGetMethodID(env, UpCallsRFFIClass, "R_ExternalPtrProt", "(Ljava/lang/Object;)Ljava/lang/Object;", 0); + R_SetExternalPtrAddrMethodID = checkGetMethodID(env, UpCallsRFFIClass, "R_SetExternalPtrAddr", "(Ljava/lang/Object;J)V", 0); + R_SetExternalPtrTagMethodID = checkGetMethodID(env, UpCallsRFFIClass, "R_SetExternalPtrTag", "(Ljava/lang/Object;Ljava/lang/Object;)V", 0); + R_SetExternalPtrProtMethodID = checkGetMethodID(env, UpCallsRFFIClass, "R_SetExternalPtrProt", "(Ljava/lang/Object;Ljava/lang/Object;)V", 0); + + CharSXPWrapperClass = checkFindClass(env, "com/oracle/truffle/r/runtime/ffi/CharSXPWrapper"); CharSXPWrapperContentsFieldID = checkGetFieldID(env, CharSXPWrapperClass, "contents", "Ljava/lang/String;", 0); - R_computeIdenticalMethodID = checkGetMethodID(env, CallRFFIHelperClass, "R_computeIdentical", "(Ljava/lang/Object;Ljava/lang/Object;I)I", 1); - Rf_copyListMatrixMethodID = checkGetMethodID(env, CallRFFIHelperClass, "Rf_copyListMatrix", "(Ljava/lang/Object;Ljava/lang/Object;I)V", 1); - Rf_copyMatrixMethodID = checkGetMethodID(env, CallRFFIHelperClass, "Rf_copyMatrix", "(Ljava/lang/Object;Ljava/lang/Object;I)V", 1); - Rf_nrowsMethodID = checkGetMethodID(env, CallRFFIHelperClass, "Rf_nrows", "(Ljava/lang/Object;)I", 1); - Rf_ncolsMethodID = checkGetMethodID(env, CallRFFIHelperClass, "Rf_ncols", "(Ljava/lang/Object;)I", 1); + R_computeIdenticalMethodID = checkGetMethodID(env, UpCallsRFFIClass, "R_computeIdentical", "(Ljava/lang/Object;Ljava/lang/Object;I)I", 0); + Rf_copyListMatrixMethodID = checkGetMethodID(env, UpCallsRFFIClass, "Rf_copyListMatrix", "(Ljava/lang/Object;Ljava/lang/Object;I)V", 0); + Rf_copyMatrixMethodID = checkGetMethodID(env, UpCallsRFFIClass, "Rf_copyMatrix", "(Ljava/lang/Object;Ljava/lang/Object;I)V", 0); + Rf_nrowsMethodID = checkGetMethodID(env, UpCallsRFFIClass, "Rf_nrows", "(Ljava/lang/Object;)I", 0); + Rf_ncolsMethodID = checkGetMethodID(env, UpCallsRFFIClass, "Rf_ncols", "(Ljava/lang/Object;)I", 0); - setCompleteMethodID = checkGetMethodID(env, CallRFFIHelperClass, "setComplete", "(Ljava/lang/Object;Z)V", 1); + setCompleteMethodID = checkGetMethodID(env, UpCallsRFFIClass, "setComplete", "(Ljava/lang/Object;Z)V", 0); } static jstring stringFromCharSXP(JNIEnv *thisenv, SEXP charsxp) { @@ -244,7 +244,7 @@ static jstring stringFromCharSXP(JNIEnv *thisenv, SEXP charsxp) { validateRef(thisenv, charsxp, "stringFromCharSXP"); if (!(*thisenv)->IsInstanceOf(thisenv, charsxp, CharSXPWrapperClass)) { - (*thisenv)->CallStaticVoidMethod(thisenv, CallRFFIHelperClass, logObject_MethodID, charsxp); + (*thisenv)->CallVoidMethod(thisenv, UpCallsRFFIObject, logNotCharSXPWrapperMethodID, charsxp); fatalError("only CharSXPWrapper expected in stringFromCharSXP"); } #endif @@ -254,27 +254,27 @@ static jstring stringFromCharSXP(JNIEnv *thisenv, SEXP charsxp) { SEXP Rf_ScalarInteger(int value) { TRACE(TARGp, value); JNIEnv *thisenv = getEnv(); - SEXP result = (*thisenv)->CallStaticObjectMethod(thisenv, CallRFFIHelperClass, Rf_ScalarIntegerMethodID, value); + SEXP result = (*thisenv)->CallObjectMethod(thisenv, UpCallsRFFIObject, Rf_ScalarIntegerMethodID, value); return checkRef(thisenv, result); } SEXP Rf_ScalarReal(double value) { JNIEnv *thisenv = getEnv(); - SEXP result = (*thisenv)->CallStaticObjectMethod(thisenv, CallRFFIHelperClass, Rf_ScalarDoubleMethodID, value); + SEXP result = (*thisenv)->CallObjectMethod(thisenv, UpCallsRFFIObject, Rf_ScalarDoubleMethodID, value); return checkRef(thisenv, result); } SEXP Rf_ScalarString(SEXP value) { TRACE(TARGp, value); JNIEnv *thisenv = getEnv(); - SEXP result = (*thisenv)->CallStaticObjectMethod(thisenv, CallRFFIHelperClass, Rf_ScalarStringMethodID, value); + SEXP result = (*thisenv)->CallObjectMethod(thisenv, UpCallsRFFIObject, Rf_ScalarStringMethodID, value); return checkRef(thisenv, result); } SEXP Rf_ScalarLogical(int value) { TRACE(TARGp, value); JNIEnv *thisenv = getEnv(); - SEXP result = (*thisenv)->CallStaticObjectMethod(thisenv, CallRFFIHelperClass, Rf_ScalarLogicalMethodID, value); + SEXP result = (*thisenv)->CallObjectMethod(thisenv, UpCallsRFFIObject, Rf_ScalarLogicalMethodID, value); return checkRef(thisenv, result); } @@ -285,14 +285,14 @@ SEXP Rf_allocVector3(SEXPTYPE t, R_xlen_t len, R_allocator_t* allocator) { } TRACE(TARGpd, t, len); JNIEnv *thisenv = getEnv(); - SEXP result = (*thisenv)->CallStaticObjectMethod(thisenv, CallRFFIHelperClass, Rf_allocateVectorMethodID, t, len); + SEXP result = (*thisenv)->CallObjectMethod(thisenv, UpCallsRFFIObject, Rf_allocateVectorMethodID, t, len); return checkRef(thisenv, result); } SEXP Rf_allocArray(SEXPTYPE t, SEXP dims) { TRACE(TARGppd, t, dims); JNIEnv *thisenv = getEnv(); - SEXP result = (*thisenv)->CallStaticObjectMethod(thisenv, CallRFFIHelperClass, Rf_allocateArrayMethodID, t, dims); + SEXP result = (*thisenv)->CallObjectMethod(thisenv, UpCallsRFFIObject, Rf_allocateArrayMethodID, t, dims); return checkRef(thisenv, result); } @@ -303,7 +303,7 @@ SEXP Rf_alloc3DArray(SEXPTYPE t, int x, int y, int z) { SEXP Rf_allocMatrix(SEXPTYPE mode, int nrow, int ncol) { TRACE(TARGppd, mode, nrow, ncol); JNIEnv *thisenv = getEnv(); - SEXP result = (*thisenv)->CallStaticObjectMethod(thisenv, CallRFFIHelperClass, Rf_allocateMatrixMethodID, mode, nrow, ncol); + SEXP result = (*thisenv)->CallObjectMethod(thisenv, UpCallsRFFIObject, Rf_allocateMatrixMethodID, mode, nrow, ncol); return checkRef(thisenv, result); } @@ -319,14 +319,14 @@ SEXP Rf_allocSExp(SEXPTYPE t) { SEXP Rf_cons(SEXP car, SEXP cdr) { TRACE(TARGpp, car, cdr); JNIEnv *thisenv = getEnv(); - SEXP result = (*thisenv)->CallStaticObjectMethod(thisenv, CallRFFIHelperClass, Rf_consMethodID, car, cdr); + SEXP result = (*thisenv)->CallObjectMethod(thisenv, UpCallsRFFIObject, Rf_consMethodID, car, cdr); return checkRef(thisenv, result); } void Rf_defineVar(SEXP symbol, SEXP value, SEXP rho) { TRACE(TARGppp, symbol, value, rho); JNIEnv *thisenv = getEnv(); - (*thisenv)->CallStaticObjectMethod(thisenv, CallRFFIHelperClass, Rf_defineVarMethodID, symbol, value, rho); + (*thisenv)->CallObjectMethod(thisenv, UpCallsRFFIObject, Rf_defineVarMethodID, symbol, value, rho); } void Rf_setVar(SEXP x, SEXP y, SEXP z) { @@ -345,63 +345,63 @@ SEXP Rf_eval(SEXP expr, SEXP env) { TRACE(TARGpp, expr, env); JNIEnv *thisenv = getEnv(); updateNativeArrays(thisenv); - SEXP result = (*thisenv)->CallStaticObjectMethod(thisenv, CallRFFIHelperClass, Rf_evalMethodID, expr, env); + SEXP result = (*thisenv)->CallObjectMethod(thisenv, UpCallsRFFIObject, Rf_evalMethodID, expr, env); return checkRef(thisenv, result); } SEXP Rf_findFun(SEXP symbol, SEXP rho) { TRACE(TARGpp, symbol, rho); JNIEnv *thisenv = getEnv(); - SEXP result = (*thisenv)->CallStaticObjectMethod(thisenv, CallRFFIHelperClass, Rf_findfunMethodID, symbol, rho); + SEXP result = (*thisenv)->CallObjectMethod(thisenv, UpCallsRFFIObject, Rf_findfunMethodID, symbol, rho); return checkRef(thisenv, result); } SEXP Rf_findVar(SEXP sym, SEXP rho) { TRACE(TARGpp, sym, rho); JNIEnv *thisenv = getEnv(); - SEXP result =(*thisenv)->CallStaticObjectMethod(thisenv, CallRFFIHelperClass, Rf_findVarMethodID, sym, rho); + SEXP result =(*thisenv)->CallObjectMethod(thisenv, UpCallsRFFIObject, Rf_findVarMethodID, sym, rho); return checkRef(thisenv, result); } SEXP Rf_findVarInFrame(SEXP rho, SEXP sym) { TRACE(TARGpp, rho, sym); JNIEnv *thisenv = getEnv(); - SEXP result =(*thisenv)->CallStaticObjectMethod(thisenv, CallRFFIHelperClass, Rf_findVarInFrameMethodID, rho, sym); + SEXP result =(*thisenv)->CallObjectMethod(thisenv, UpCallsRFFIObject, Rf_findVarInFrameMethodID, rho, sym); return checkRef(thisenv, result); } SEXP Rf_findVarInFrame3(SEXP rho, SEXP sym, Rboolean b) { TRACE(TARGppd, rho, sym, b); JNIEnv *thisenv = getEnv(); - SEXP result = (*thisenv)->CallStaticObjectMethod(thisenv, CallRFFIHelperClass, Rf_findVarInFrame3MethodID, rho, sym, b); + SEXP result = (*thisenv)->CallObjectMethod(thisenv, UpCallsRFFIObject, Rf_findVarInFrame3MethodID, rho, sym, b); return checkRef(thisenv, result); } SEXP Rf_getAttrib(SEXP vec, SEXP name) { TRACE(TARGpp, vec, name); JNIEnv *thisenv = getEnv(); - SEXP result = (*thisenv)->CallStaticObjectMethod(thisenv, CallRFFIHelperClass, Rf_getAttribMethodID, vec, name); + SEXP result = (*thisenv)->CallObjectMethod(thisenv, UpCallsRFFIObject, Rf_getAttribMethodID, vec, name); return checkRef(thisenv, result); } SEXP Rf_setAttrib(SEXP vec, SEXP name, SEXP val) { TRACE(TARGppp, vec,name, val); JNIEnv *thisenv = getEnv(); - (*thisenv)->CallStaticVoidMethod(thisenv, CallRFFIHelperClass, Rf_setAttribMethodID, vec, name, val); + (*thisenv)->CallVoidMethod(thisenv, UpCallsRFFIObject, Rf_setAttribMethodID, vec, name, val); return val; } SEXP Rf_duplicate(SEXP x) { TRACE(TARGp, x); JNIEnv *thisenv = getEnv(); - SEXP result = (*thisenv)->CallStaticObjectMethod(thisenv, CallRFFIHelperClass, Rf_duplicateMethodID, x, 1); + SEXP result = (*thisenv)->CallObjectMethod(thisenv, UpCallsRFFIObject, Rf_duplicateMethodID, x, 1); return checkRef(thisenv, result); } SEXP Rf_shallow_duplicate(SEXP x) { TRACE(TARGp, x); JNIEnv *thisenv = getEnv(); - SEXP result = (*thisenv)->CallStaticObjectMethod(thisenv, CallRFFIHelperClass, Rf_duplicateMethodID, x, 0); + SEXP result = (*thisenv)->CallObjectMethod(thisenv, UpCallsRFFIObject, Rf_duplicateMethodID, x, 0); return checkRef(thisenv, result); } @@ -409,7 +409,7 @@ R_xlen_t Rf_any_duplicated(SEXP x, Rboolean from_last) { TRACE(TARGpd, x, from_last); if (!isVector(x)) error(_("'duplicated' applies only to vectors")); JNIEnv *thisenv = getEnv(); - return (*thisenv)->CallStaticIntMethod(thisenv, CallRFFIHelperClass, Rf_anyDuplicatedMethodID, x, from_last); + return (*thisenv)->CallIntMethod(thisenv, UpCallsRFFIObject, Rf_anyDuplicatedMethodID, x, from_last); } SEXP Rf_duplicated(SEXP x, Rboolean y) { @@ -437,7 +437,7 @@ Rboolean Rf_inherits(SEXP x, const char * klass) { TRACE(TARGps, x, klass); JNIEnv *thisenv = getEnv(); jstring klazz = (*thisenv)->NewStringUTF(thisenv, klass); - return (*thisenv)->CallStaticIntMethod(thisenv, CallRFFIHelperClass, Rf_inheritsMethodID, x, klazz); + return (*thisenv)->CallIntMethod(thisenv, UpCallsRFFIObject, Rf_inheritsMethodID, x, klazz); } Rboolean Rf_isReal(SEXP x) { @@ -477,7 +477,7 @@ SEXP Rf_install(const char *name) { TRACE(TARGs, name); JNIEnv *thisenv = getEnv(); jstring string = (*thisenv)->NewStringUTF(thisenv, name); - SEXP result = (*thisenv)->CallStaticObjectMethod(thisenv, CallRFFIHelperClass, Rf_installMethodID, string); + SEXP result = (*thisenv)->CallObjectMethod(thisenv, UpCallsRFFIObject, Rf_installMethodID, string); return checkRef(thisenv, result); } @@ -485,18 +485,18 @@ SEXP Rf_installChar(SEXP charsxp) { TRACE(TARGp, charsxp); JNIEnv *thisenv = getEnv(); jstring string = stringFromCharSXP(thisenv, charsxp); - SEXP result = (*thisenv)->CallStaticObjectMethod(thisenv, CallRFFIHelperClass, Rf_installMethodID, string); + SEXP result = (*thisenv)->CallObjectMethod(thisenv, UpCallsRFFIObject, Rf_installMethodID, string); return checkRef(thisenv, result); } Rboolean Rf_isNull(SEXP s) { JNIEnv *thisenv = getEnv(); - return (*thisenv)->CallStaticIntMethod(thisenv, CallRFFIHelperClass, Rf_isNullMethodID, s); + return (*thisenv)->CallIntMethod(thisenv, UpCallsRFFIObject, Rf_isNullMethodID, s); } Rboolean Rf_isString(SEXP s) { JNIEnv *thisenv = getEnv(); - return (*thisenv)->CallStaticIntMethod(thisenv, CallRFFIHelperClass, Rf_isStringMethodID, s); + return (*thisenv)->CallIntMethod(thisenv, UpCallsRFFIObject, Rf_isStringMethodID, s); } Rboolean R_cycle_detected(SEXP s, SEXP child) { @@ -527,7 +527,7 @@ SEXP Rf_mkCharLenCE(const char *x, int len, cetype_t enc) { JNIEnv *thisenv = getEnv(); jbyteArray bytes = (*thisenv)->NewByteArray(thisenv, len); (*thisenv)->SetByteArrayRegion(thisenv, bytes, 0, len, (const jbyte *) x); - SEXP result = (*thisenv)->CallStaticObjectMethod(thisenv, CallRFFIHelperClass, Rf_mkCharLenCEMethodID, bytes, (int) enc); + SEXP result = (*thisenv)->CallObjectMethod(thisenv, UpCallsRFFIObject, Rf_mkCharLenCEMethodID, bytes, (int) enc); return checkRef(thisenv, result); } @@ -543,13 +543,13 @@ SEXP Rf_mkString(const char *s) { int Rf_ncols(SEXP x) { TRACE(TARGs, x); JNIEnv *thisenv = getEnv(); - return (*thisenv)->CallStaticIntMethod(thisenv, CallRFFIHelperClass, Rf_ncolsMethodID, x); + return (*thisenv)->CallIntMethod(thisenv, UpCallsRFFIObject, Rf_ncolsMethodID, x); } int Rf_nrows(SEXP x) { TRACE(TARGs, x); JNIEnv *thisenv = getEnv(); - return (*thisenv)->CallStaticIntMethod(thisenv, CallRFFIHelperClass, Rf_nrowsMethodID, x); + return (*thisenv)->CallIntMethod(thisenv, UpCallsRFFIObject, Rf_nrowsMethodID, x); } @@ -591,7 +591,7 @@ void Rf_error(const char *format, ...) { // RError.error does quite a lot of stuff including potentially searching for R condition handlers // and, if it finds any, does not return, but throws a different exception than RError. // We definitely need to exit the FFI call and we certainly cannot return to our caller. - // So we call CallRFFIHelper.Rf_error to throw the RError exception. When the pending + // So we call RFFIUpCallsObject.Rf_error to throw the RError exception. When the pending // exception (whatever it is) is observed by JNI, the call to Rf_error will return where we do a // non-local transfer of control back to the entry point (which will cleanup). char buf[8192]; @@ -602,7 +602,7 @@ void Rf_error(const char *format, ...) { JNIEnv *thisenv = getEnv(); jstring string = (*thisenv)->NewStringUTF(thisenv, buf); // This will set a pending exception - (*thisenv)->CallStaticObjectMethod(thisenv, CallRFFIHelperClass, Rf_errorMethodID, string); + (*thisenv)->CallObjectMethod(thisenv, UpCallsRFFIObject, Rf_errorMethodID, string); // just transfer back which will cleanup and exit the entire JNI call longjmp(*getErrorJmpBuf(), 1); @@ -620,7 +620,7 @@ void Rf_warningcall(SEXP x, const char *format, ...) { va_end(ap); JNIEnv *thisenv = getEnv(); jstring string = (*thisenv)->NewStringUTF(thisenv, buf); - (*thisenv)->CallStaticObjectMethod(thisenv, CallRFFIHelperClass, Rf_warningcallMethodID, x, string); + (*thisenv)->CallObjectMethod(thisenv, UpCallsRFFIObject, Rf_warningcallMethodID, x, string); } void Rf_warning(const char *format, ...) { @@ -631,7 +631,7 @@ void Rf_warning(const char *format, ...) { va_end(ap); JNIEnv *thisenv = getEnv(); jstring string = (*thisenv)->NewStringUTF(thisenv, buf); - (*thisenv)->CallStaticObjectMethod(thisenv, CallRFFIHelperClass, Rf_warningMethodID, string); + (*thisenv)->CallObjectMethod(thisenv, UpCallsRFFIObject, Rf_warningMethodID, string); } void Rprintf(const char *format, ...) { @@ -642,7 +642,7 @@ void Rprintf(const char *format, ...) { va_end(ap); JNIEnv *thisenv = getEnv(); jstring string = (*thisenv)->NewStringUTF(thisenv, buf); - (*thisenv)->CallStaticObjectMethod(thisenv, CallRFFIHelperClass, RprintfMethodID, string); + (*thisenv)->CallObjectMethod(thisenv, UpCallsRFFIObject, RprintfMethodID, string); } /* @@ -660,7 +660,7 @@ void REprintf(const char *format, ...) va_end(ap); JNIEnv *thisenv = getEnv(); jstring string = (*thisenv)->NewStringUTF(thisenv, buf); - (*thisenv)->CallStaticObjectMethod(thisenv, CallRFFIHelperClass, RprintfMethodID, string); + (*thisenv)->CallObjectMethod(thisenv, UpCallsRFFIObject, RprintfMethodID, string); } void Rvprintf(const char *format, va_list args) { @@ -681,13 +681,13 @@ void R_ProcessEvents(void) { // Tools package support, not in public API SEXP R_NewHashedEnv(SEXP parent, SEXP size) { JNIEnv *thisenv = getEnv(); - SEXP result = (*thisenv)->CallStaticObjectMethod(thisenv, CallRFFIHelperClass, R_NewHashedEnvMethodID, parent, size); + SEXP result = (*thisenv)->CallObjectMethod(thisenv, UpCallsRFFIObject, R_NewHashedEnvMethodID, parent, size); return checkRef(thisenv, result); } SEXP Rf_classgets(SEXP vec, SEXP klass) { JNIEnv *thisenv = getEnv(); - SEXP result = (*thisenv)->CallStaticObjectMethod(thisenv, CallRFFIHelperClass, Rf_classgetsMethodID, vec, klass); + SEXP result = (*thisenv)->CallObjectMethod(thisenv, UpCallsRFFIObject, Rf_classgetsMethodID, vec, klass); return checkRef(thisenv, result); } @@ -716,7 +716,7 @@ SEXP Rf_lengthgets(SEXP x, R_len_t y) { TRACE(TARGp, x); JNIEnv *thisenv = getEnv(); invalidateNativeArray(thisenv, x); - SEXP result = (*thisenv)->CallStaticObjectMethod(thisenv, CallRFFIHelperClass, Rf_lengthgetsMethodID, x, y); + SEXP result = (*thisenv)->CallObjectMethod(thisenv, UpCallsRFFIObject, Rf_lengthgetsMethodID, x, y); return checkRef(thisenv, result); } @@ -731,7 +731,7 @@ SEXP R_lsInternal(SEXP env, Rboolean all) { SEXP R_lsInternal3(SEXP env, Rboolean all, Rboolean sorted) { JNIEnv *thisenv = getEnv(); - SEXP result = (*thisenv)->CallStaticObjectMethod(thisenv, CallRFFIHelperClass, R_lsInternal3MethodID, env, all, sorted); + SEXP result = (*thisenv)->CallObjectMethod(thisenv, UpCallsRFFIObject, R_lsInternal3MethodID, env, all, sorted); return checkRef(thisenv, result); } @@ -742,7 +742,7 @@ SEXP Rf_namesgets(SEXP x, SEXP y) { SEXP GetOption1(SEXP tag) { JNIEnv *thisenv = getEnv(); - SEXP result = (*thisenv)->CallStaticObjectMethod(thisenv, CallRFFIHelperClass, Rf_GetOption1MethodID, tag); + SEXP result = (*thisenv)->CallObjectMethod(thisenv, UpCallsRFFIObject, Rf_GetOption1MethodID, tag); return checkRef(thisenv, result); } @@ -803,34 +803,34 @@ Rboolean Rf_GetOptionDeviceAsk(void) void Rf_gsetVar(SEXP symbol, SEXP value, SEXP rho) { JNIEnv *thisenv = getEnv(); - (*thisenv)->CallStaticObjectMethod(thisenv, CallRFFIHelperClass, Rf_gsetVarMethodID, symbol, value, rho); + (*thisenv)->CallObjectMethod(thisenv, UpCallsRFFIObject, Rf_gsetVarMethodID, symbol, value, rho); } SEXP TAG(SEXP e) { TRACE(TARGp, e); JNIEnv *thisenv = getEnv(); - SEXP result = (*thisenv)->CallStaticObjectMethod(thisenv, CallRFFIHelperClass, TAG_MethodID, e); + SEXP result = (*thisenv)->CallObjectMethod(thisenv, UpCallsRFFIObject, TAG_MethodID, e); return checkRef(thisenv, result); } SEXP PRINTNAME(SEXP e) { TRACE(TARGp, e); JNIEnv *thisenv = getEnv(); - SEXP result = (*thisenv)->CallStaticObjectMethod(thisenv, CallRFFIHelperClass, PRINTNAME_MethodID, e); + SEXP result = (*thisenv)->CallObjectMethod(thisenv, UpCallsRFFIObject, PRINTNAME_MethodID, e); return checkRef(thisenv, result); } SEXP CAR(SEXP e) { TRACE(TARGp, e); JNIEnv *thisenv = getEnv(); - SEXP result = (*thisenv)->CallStaticObjectMethod(thisenv, CallRFFIHelperClass, CAR_MethodID, e); + SEXP result = (*thisenv)->CallObjectMethod(thisenv, UpCallsRFFIObject, CAR_MethodID, e); return checkRef(thisenv, result); } SEXP CDR(SEXP e) { TRACE(TARGp, e); JNIEnv *thisenv = getEnv(); - SEXP result = (*thisenv)->CallStaticObjectMethod(thisenv, CallRFFIHelperClass, CDR_MethodID, e); + SEXP result = (*thisenv)->CallObjectMethod(thisenv, UpCallsRFFIObject, CDR_MethodID, e); return checkRef(thisenv, result); } @@ -847,14 +847,14 @@ SEXP CDAR(SEXP e) { SEXP CADR(SEXP e) { TRACE(TARGp, e); JNIEnv *thisenv = getEnv(); - SEXP result = (*thisenv)->CallStaticObjectMethod(thisenv, CallRFFIHelperClass, CADR_MethodID, e); + SEXP result = (*thisenv)->CallObjectMethod(thisenv, UpCallsRFFIObject, CADR_MethodID, e); return checkRef(thisenv, result); } SEXP CDDR(SEXP e) { TRACE(TARGp, e); JNIEnv *thisenv = getEnv(); - SEXP result = (*thisenv)->CallStaticObjectMethod(thisenv, CallRFFIHelperClass, CDDR_MethodID, e); + SEXP result = (*thisenv)->CallObjectMethod(thisenv, UpCallsRFFIObject, CDDR_MethodID, e); return checkRef(thisenv, result); } @@ -866,7 +866,7 @@ SEXP CDDDR(SEXP e) { SEXP CADDR(SEXP e) { TRACE(TARGp, e); JNIEnv *thisenv = getEnv(); - SEXP result = (*thisenv)->CallStaticObjectMethod(thisenv, CallRFFIHelperClass, CADDR_MethodID, e); + SEXP result = (*thisenv)->CallObjectMethod(thisenv, UpCallsRFFIObject, CADDR_MethodID, e); return checkRef(thisenv, result); } @@ -892,27 +892,27 @@ void SET_MISSING(SEXP x, int v) { void SET_TAG(SEXP x, SEXP y) { TRACE(TARGpp, x, y); JNIEnv *thisenv = getEnv(); - (*thisenv)->CallStaticObjectMethod(thisenv, CallRFFIHelperClass, SET_TAG_MethodID, x, y); + (*thisenv)->CallObjectMethod(thisenv, UpCallsRFFIObject, SET_TAG_MethodID, x, y); } SEXP SETCAR(SEXP x, SEXP y) { TRACE(TARGpp, x, y); JNIEnv *thisenv = getEnv(); - SEXP result = (*thisenv)->CallStaticObjectMethod(thisenv, CallRFFIHelperClass, SETCAR_MethodID, x, y); + SEXP result = (*thisenv)->CallObjectMethod(thisenv, UpCallsRFFIObject, SETCAR_MethodID, x, y); return checkRef(thisenv, result); } SEXP SETCDR(SEXP x, SEXP y) { TRACE(TARGpp, x, y); JNIEnv *thisenv = getEnv(); - SEXP result = (*thisenv)->CallStaticObjectMethod(thisenv, CallRFFIHelperClass, SETCDR_MethodID, x, y); + SEXP result = (*thisenv)->CallObjectMethod(thisenv, UpCallsRFFIObject, SETCDR_MethodID, x, y); return checkRef(thisenv, result); } SEXP SETCADR(SEXP x, SEXP y) { TRACE(TARGpp, x, y); JNIEnv *thisenv = getEnv(); - SEXP result = (*thisenv)->CallStaticObjectMethod(thisenv, CallRFFIHelperClass, SETCADR_MethodID, x, y); + SEXP result = (*thisenv)->CallObjectMethod(thisenv, UpCallsRFFIObject, SETCADR_MethodID, x, y); return checkRef(thisenv, result); } @@ -945,12 +945,12 @@ SEXP CLOENV(SEXP x) { int RDEBUG(SEXP x) { JNIEnv *thisenv = getEnv(); - return (*thisenv)->CallStaticIntMethod(thisenv, CallRFFIHelperClass, RDEBUGMethodID, x); + return (*thisenv)->CallIntMethod(thisenv, UpCallsRFFIObject, RDEBUGMethodID, x); } int RSTEP(SEXP x) { JNIEnv *thisenv = getEnv(); - return (*thisenv)->CallStaticIntMethod(thisenv, CallRFFIHelperClass, RSTEPMethodID, x); + return (*thisenv)->CallIntMethod(thisenv, UpCallsRFFIObject, RSTEPMethodID, x); } int RTRACE(SEXP x) { @@ -960,12 +960,12 @@ int RTRACE(SEXP x) { void SET_RDEBUG(SEXP x, int v) { JNIEnv *thisenv = getEnv(); - (*thisenv)->CallStaticVoidMethod(thisenv, CallRFFIHelperClass, SET_RDEBUGMethodID, x, v); + (*thisenv)->CallVoidMethod(thisenv, UpCallsRFFIObject, SET_RDEBUGMethodID, x, v); } void SET_RSTEP(SEXP x, int v) { JNIEnv *thisenv = getEnv(); - (*thisenv)->CallStaticVoidMethod(thisenv, CallRFFIHelperClass, SET_RSTEPMethodID, x, v); + (*thisenv)->CallVoidMethod(thisenv, UpCallsRFFIObject, SET_RSTEPMethodID, x, v); } void SET_RTRACE(SEXP x, int v) { @@ -986,7 +986,7 @@ void SET_CLOENV(SEXP x, SEXP v) { SEXP SYMVALUE(SEXP x) { JNIEnv *thisenv = getEnv(); - SEXP result = (*thisenv)->CallStaticObjectMethod(thisenv, CallRFFIHelperClass, SYMVALUE_MethodID, x); + SEXP result = (*thisenv)->CallObjectMethod(thisenv, UpCallsRFFIObject, SYMVALUE_MethodID, x); return checkRef(thisenv, result); } @@ -1005,7 +1005,7 @@ void SET_DDVAL(SEXP x, int v) { void SET_SYMVALUE(SEXP x, SEXP v) { JNIEnv *thisenv = getEnv(); - (*thisenv)->CallStaticVoidMethod(thisenv, CallRFFIHelperClass, SET_SYMVALUE_MethodID, x, v); + (*thisenv)->CallVoidMethod(thisenv, UpCallsRFFIObject, SET_SYMVALUE_MethodID, x, v); } void SET_INTERNAL(SEXP x, SEXP v) { @@ -1018,7 +1018,7 @@ SEXP FRAME(SEXP x) { SEXP ENCLOS(SEXP x) { JNIEnv *thisenv = getEnv(); - SEXP result = (*thisenv)->CallStaticObjectMethod(thisenv, CallRFFIHelperClass, ENCLOSMethodID, x); + SEXP result = (*thisenv)->CallObjectMethod(thisenv, UpCallsRFFIObject, ENCLOSMethodID, x); return checkRef(thisenv, result); } @@ -1059,7 +1059,7 @@ SEXP PRENV(SEXP x) { SEXP PRVALUE(SEXP x) { JNIEnv *thisenv = getEnv(); - SEXP result = (*thisenv)->CallStaticObjectMethod(thisenv, CallRFFIHelperClass, PRVALUEMethodID, x); + SEXP result = (*thisenv)->CallObjectMethod(thisenv, UpCallsRFFIObject, PRVALUEMethodID, x); return checkRef(thisenv, result); } @@ -1086,7 +1086,7 @@ void SET_PRCODE(SEXP x, SEXP v) { int LENGTH(SEXP x) { TRACE(TARGp, x); JNIEnv *thisenv = getEnv(); - return (*thisenv)->CallStaticIntMethod(thisenv, CallRFFIHelperClass, LENGTH_MethodID, x); + return (*thisenv)->CallIntMethod(thisenv, UpCallsRFFIObject, LENGTH_MethodID, x); } int TRUELENGTH(SEXP x){ @@ -1172,7 +1172,7 @@ Rcomplex *COMPLEX(SEXP x){ SEXP STRING_ELT(SEXP x, R_xlen_t i){ TRACE(TARGpd, x, i); JNIEnv *thisenv = getEnv(); - SEXP result = (*thisenv)->CallStaticObjectMethod(thisenv, CallRFFIHelperClass, STRING_ELT_MethodID, x, i); + SEXP result = (*thisenv)->CallObjectMethod(thisenv, UpCallsRFFIObject, STRING_ELT_MethodID, x, i); return checkRef(thisenv, result); } @@ -1180,21 +1180,21 @@ SEXP STRING_ELT(SEXP x, R_xlen_t i){ SEXP VECTOR_ELT(SEXP x, R_xlen_t i){ TRACE(TARGpd, x, i); JNIEnv *thisenv = getEnv(); - SEXP result = (*thisenv)->CallStaticObjectMethod(thisenv, CallRFFIHelperClass, VECTOR_ELT_MethodID, x, i); + SEXP result = (*thisenv)->CallObjectMethod(thisenv, UpCallsRFFIObject, VECTOR_ELT_MethodID, x, i); return checkRef(thisenv, result); } void SET_STRING_ELT(SEXP x, R_xlen_t i, SEXP v){ TRACE("%s(%p, %d, %p)\n", x, i, v); JNIEnv *thisenv = getEnv(); - (*thisenv)->CallStaticVoidMethod(thisenv, CallRFFIHelperClass, SET_STRING_ELT_MethodID, x, i, v); + (*thisenv)->CallVoidMethod(thisenv, UpCallsRFFIObject, SET_STRING_ELT_MethodID, x, i, v); } SEXP SET_VECTOR_ELT(SEXP x, R_xlen_t i, SEXP v){ TRACE("%s(%p, %d, %p)\n", x, i, v); JNIEnv *thisenv = getEnv(); - (*thisenv)->CallStaticVoidMethod(thisenv, CallRFFIHelperClass, SET_VECTOR_ELT_MethodID, x, i, v); + (*thisenv)->CallVoidMethod(thisenv, UpCallsRFFIObject, SET_VECTOR_ELT_MethodID, x, i, v); return v; } @@ -1213,14 +1213,14 @@ SEXP *VECTOR_PTR(SEXP x){ SEXP Rf_asChar(SEXP x){ TRACE(TARGp, x); JNIEnv *thisenv = getEnv(); - SEXP result = (*thisenv)->CallStaticObjectMethod(thisenv, CallRFFIHelperClass, Rf_asCharMethodID, x); + SEXP result = (*thisenv)->CallObjectMethod(thisenv, UpCallsRFFIObject, Rf_asCharMethodID, x); return checkRef(thisenv, result); } SEXP Rf_PairToVectorList(SEXP x){ TRACE(TARGp, x); JNIEnv *thisenv = getEnv(); - SEXP result = (*thisenv)->CallStaticObjectMethod(thisenv, CallRFFIHelperClass, Rf_PairToVectorListMethodID, x); + SEXP result = (*thisenv)->CallObjectMethod(thisenv, UpCallsRFFIObject, Rf_PairToVectorListMethodID, x); return checkRef(thisenv, result); } @@ -1237,19 +1237,19 @@ SEXP Rf_asCharacterFactor(SEXP x){ int Rf_asLogical(SEXP x){ TRACE(TARGp, x); JNIEnv *thisenv = getEnv(); - return (*thisenv)->CallStaticIntMethod(thisenv, CallRFFIHelperClass, Rf_asLogicalMethodID, x); + return (*thisenv)->CallIntMethod(thisenv, UpCallsRFFIObject, Rf_asLogicalMethodID, x); } int Rf_asInteger(SEXP x) { TRACE(TARGp, x); JNIEnv *thisenv = getEnv(); - return (*thisenv)->CallStaticIntMethod(thisenv, CallRFFIHelperClass, Rf_asIntegerMethodID, x); + return (*thisenv)->CallIntMethod(thisenv, UpCallsRFFIObject, Rf_asIntegerMethodID, x); } //double Rf_asReal(SEXP x) { // TRACE(TARGp, x); // JNIEnv *thisenv = getEnv(); -// return (*thisenv)->CallStaticDoubleMethod(thisenv, CallRFFIHelperClass, Rf_asRealMethodID, x); +// return (*thisenv)->CallDoubleMethod(thisenv, UpCallsRFFIObject, Rf_asRealMethodID, x); //} Rcomplex Rf_asComplex(SEXP x){ @@ -1260,7 +1260,7 @@ Rcomplex Rf_asComplex(SEXP x){ int TYPEOF(SEXP x) { TRACE(TARGp, x); JNIEnv *thisenv = getEnv(); - return (*thisenv)->CallStaticIntMethod(thisenv, CallRFFIHelperClass, TYPEOF_MethodID, x); + return (*thisenv)->CallIntMethod(thisenv, UpCallsRFFIObject, TYPEOF_MethodID, x); } SEXP ATTRIB(SEXP x){ @@ -1270,7 +1270,7 @@ SEXP ATTRIB(SEXP x){ int OBJECT(SEXP x){ JNIEnv *env = getEnv(); - return (*env)->CallStaticIntMethod(env, CallRFFIHelperClass, OBJECT_MethodID, x); + return (*env)->CallIntMethod(env, UpCallsRFFIObject, OBJECT_MethodID, x); } int MARK(SEXP x){ @@ -1280,7 +1280,7 @@ int MARK(SEXP x){ int NAMED(SEXP x){ JNIEnv *thisenv = getEnv(); - return (*thisenv)->CallStaticIntMethod(thisenv, CallRFFIHelperClass, NAMED_MethodID, x); + return (*thisenv)->CallIntMethod(thisenv, UpCallsRFFIObject, NAMED_MethodID, x); } int REFCNT(SEXP x){ @@ -1298,7 +1298,7 @@ void SET_TYPEOF(SEXP x, int v){ SEXP SET_TYPEOF_FASTR(SEXP x, int v){ JNIEnv *thisenv = getEnv(); - SEXP result = (*thisenv)->CallStaticObjectMethod(thisenv, CallRFFIHelperClass, SET_TYPEOF_FASTR_MethodID, x, v); + SEXP result = (*thisenv)->CallObjectMethod(thisenv, UpCallsRFFIObject, SET_TYPEOF_FASTR_MethodID, x, v); return checkRef(thisenv, result); } @@ -1312,7 +1312,7 @@ void SET_ATTRIB(SEXP x, SEXP v){ void DUPLICATE_ATTRIB(SEXP to, SEXP from){ JNIEnv *thisenv = getEnv(); - (*thisenv)->CallStaticVoidMethod(thisenv, CallRFFIHelperClass, DUPLICATE_ATTRIB_MethodID, to, from); + (*thisenv)->CallVoidMethod(thisenv, UpCallsRFFIObject, DUPLICATE_ATTRIB_MethodID, to, from); } char *dgettext(const char *domainname, const char *msgid) { @@ -1367,7 +1367,7 @@ R_len_t R_BadLongVector(SEXP x, const char *y, int z) { int IS_S4_OBJECT(SEXP x) { JNIEnv *env = getEnv(); - return (*env)->CallStaticIntMethod(env, CallRFFIHelperClass, isS4ObjectMethodID, x); + return (*env)->CallIntMethod(env, UpCallsRFFIObject, isS4ObjectMethodID, x); } void SET_S4_OBJECT(SEXP x) { @@ -1379,9 +1379,9 @@ void UNSET_S4_OBJECT(SEXP x) { Rboolean R_ToplevelExec(void (*fun)(void *), void *data) { JNIEnv *env = getEnv(); - jobject handlerStacks = (*env)->CallStaticObjectMethod(env, CallRFFIHelperClass, resetAndGetHandlerStacksMethodID); + jobject handlerStacks = (*env)->CallObjectMethod(env, UpCallsRFFIObject, R_ToplevelExecMethodID); fun(data); - (*env)->CallStaticVoidMethod(env, CallRFFIHelperClass, restoreHandlerStacksMethodID, handlerStacks); + (*env)->CallVoidMethod(env, UpCallsRFFIObject, restoreHandlerStacksMethodID, handlerStacks); // TODO how do we detect error return TRUE; } @@ -1418,7 +1418,7 @@ SEXP R_NamespaceEnvSpec(SEXP rho) { SEXP R_FindNamespace(SEXP info) { JNIEnv *thisenv = getEnv(); - SEXP result = (*thisenv)->CallStaticObjectMethod(thisenv, CallRFFIHelperClass, R_FindNamespaceMethodID, info); + SEXP result = (*thisenv)->CallObjectMethod(thisenv, UpCallsRFFIObject, R_FindNamespaceMethodID, info); return checkRef(thisenv, result); } @@ -1444,7 +1444,7 @@ void R_MakeActiveBinding(SEXP sym, SEXP fun, SEXP env) { Rboolean R_BindingIsLocked(SEXP sym, SEXP env) { JNIEnv *thisenv = getEnv(); - return (*thisenv)->CallStaticIntMethod(thisenv, CallRFFIHelperClass, R_BindingIsLockedID, sym, env); + return (*thisenv)->CallIntMethod(thisenv, UpCallsRFFIObject, R_BindingIsLockedID, sym, env); } Rboolean R_BindingIsActive(SEXP sym, SEXP env) { @@ -1467,7 +1467,7 @@ SEXP Rf_asS4(SEXP x, Rboolean b, int i) { static SEXP R_tryEvalInternal(SEXP x, SEXP y, int *ErrorOccurred, jboolean silent) { JNIEnv *thisenv = getEnv(); updateNativeArrays(thisenv); - jobject tryResult = (*thisenv)->CallStaticObjectMethod(thisenv, CallRFFIHelperClass, R_tryEvalMethodID, x, y, silent); + jobject tryResult = (*thisenv)->CallObjectMethod(thisenv, UpCallsRFFIObject, R_tryEvalMethodID, x, y, silent); // If tryResult is NULL, an error occurred if (ErrorOccurred) { *ErrorOccurred = tryResult == NULL; @@ -1507,40 +1507,40 @@ SEXP R_forceAndCall(SEXP e, int n, SEXP rho) { SEXP R_MakeExternalPtr(void *p, SEXP tag, SEXP prot) { JNIEnv *thisenv = getEnv(); - SEXP result = (*thisenv)->CallStaticObjectMethod(thisenv, CallRFFIHelperClass, R_MakeExternalPtrMethodID, (jlong) p, tag, prot); + SEXP result = (*thisenv)->CallObjectMethod(thisenv, UpCallsRFFIObject, R_MakeExternalPtrMethodID, (jlong) p, tag, prot); return checkRef(thisenv, result); } void *R_ExternalPtrAddr(SEXP s) { JNIEnv *thisenv = getEnv(); - return (void *) (*thisenv)->CallStaticLongMethod(thisenv, CallRFFIHelperClass, R_ExternalPtrAddrMethodID, s); + return (void *) (*thisenv)->CallLongMethod(thisenv, UpCallsRFFIObject, R_ExternalPtrAddrMethodID, s); } SEXP R_ExternalPtrTag(SEXP s) { JNIEnv *thisenv = getEnv(); - SEXP result = (*thisenv)->CallStaticObjectMethod(thisenv, CallRFFIHelperClass, R_ExternalPtrTagMethodID, s); + SEXP result = (*thisenv)->CallObjectMethod(thisenv, UpCallsRFFIObject, R_ExternalPtrTagMethodID, s); return checkRef(thisenv, result); } SEXP R_ExternalPtrProt(SEXP s) { JNIEnv *thisenv = getEnv(); - SEXP result = (*thisenv)->CallStaticObjectMethod(thisenv, CallRFFIHelperClass, R_ExternalPtrProtMethodID, s); + SEXP result = (*thisenv)->CallObjectMethod(thisenv, UpCallsRFFIObject, R_ExternalPtrProtMethodID, s); return checkRef(thisenv, result); } void R_SetExternalPtrAddr(SEXP s, void *p) { JNIEnv *thisenv = getEnv(); - (*thisenv)->CallStaticVoidMethod(thisenv, CallRFFIHelperClass, R_SetExternalPtrAddrMethodID, s, (jlong) p); + (*thisenv)->CallVoidMethod(thisenv, UpCallsRFFIObject, R_SetExternalPtrAddrMethodID, s, (jlong) p); } void R_SetExternalPtrTag(SEXP s, SEXP tag) { JNIEnv *thisenv = getEnv(); - (*thisenv)->CallStaticVoidMethod(thisenv, CallRFFIHelperClass, R_SetExternalPtrTagMethodID, s, tag); + (*thisenv)->CallVoidMethod(thisenv, UpCallsRFFIObject, R_SetExternalPtrTagMethodID, s, tag); } void R_SetExternalPtrProtected(SEXP s, SEXP p) { JNIEnv *thisenv = getEnv(); - (*thisenv)->CallStaticVoidMethod(thisenv, CallRFFIHelperClass, R_SetExternalPtrProtMethodID, s, p); + (*thisenv)->CallVoidMethod(thisenv, UpCallsRFFIObject, R_SetExternalPtrProtMethodID, s, p); } void R_ClearExternalPtr(SEXP s) { @@ -1602,7 +1602,7 @@ int R_has_slot(SEXP obj, SEXP name) { SEXP R_do_MAKE_CLASS(const char *what) { JNIEnv *thisenv = getEnv(); jstring string = (*thisenv)->NewStringUTF(thisenv, what); - return (*thisenv)->CallStaticObjectMethod(thisenv, CallRFFIHelperClass, R_do_MAKE_CLASS_MethodID, string); + return (*thisenv)->CallObjectMethod(thisenv, UpCallsRFFIObject, R_do_MAKE_CLASS_MethodID, string); } SEXP R_getClassDef (const char *what) { @@ -1637,15 +1637,15 @@ void R_dot_Last(void) { Rboolean R_compute_identical(SEXP x, SEXP y, int flags) { JNIEnv *thisenv = getEnv(); - return (*thisenv)->CallStaticIntMethod(thisenv, CallRFFIHelperClass, R_computeIdenticalMethodID, x, y, flags); + return (*thisenv)->CallIntMethod(thisenv, UpCallsRFFIObject, R_computeIdenticalMethodID, x, y, flags); } void Rf_copyListMatrix(SEXP s, SEXP t, Rboolean byrow) { JNIEnv *thisenv = getEnv(); - (*thisenv)->CallStaticIntMethod(thisenv, CallRFFIHelperClass, Rf_copyListMatrixMethodID, s, t, byrow); + (*thisenv)->CallIntMethod(thisenv, UpCallsRFFIObject, Rf_copyListMatrixMethodID, s, t, byrow); } void Rf_copyMatrix(SEXP s, SEXP t, Rboolean byrow) { JNIEnv *thisenv = getEnv(); - (*thisenv)->CallStaticIntMethod(thisenv, CallRFFIHelperClass, Rf_copyMatrixMethodID, s, t, byrow); + (*thisenv)->CallIntMethod(thisenv, UpCallsRFFIObject, Rf_copyMatrixMethodID, s, t, byrow); } diff --git a/com.oracle.truffle.r.native/fficall/src/jni/call_rffi.c b/com.oracle.truffle.r.native/fficall/src/jni/call_rffi.c index 7b9a14296c..eb81606672 100644 --- a/com.oracle.truffle.r.native/fficall/src/jni/call_rffi.c +++ b/com.oracle.truffle.r.native/fficall/src/jni/call_rffi.c @@ -25,10 +25,11 @@ #include <string.h> #include <setjmp.h> +// The entry point from JNI_Call that initializes the system JNIEXPORT void JNICALL Java_com_oracle_truffle_r_runtime_ffi_jni_JNI_1Call_initialize(JNIEnv *env, jclass c, - jobjectArray initialValues) { - init_utils(env); // must be first + jobject upCallInstance, jobjectArray initialValues) { + init_utils(env, upCallInstance); // must be first init_variables(env, initialValues); init_dynload(env); init_internals(env); 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 0010587bcc..69d19f2aec 100644 --- a/com.oracle.truffle.r.native/fficall/src/jni/rffiutils.c +++ b/com.oracle.truffle.r.native/fficall/src/jni/rffiutils.c @@ -32,11 +32,10 @@ * so we are safe to use static variables. TODO Figure out where to store such state * (portably) for MT use. JNI provides no help. */ -jclass CallRFFIHelperClass; +jclass UpCallsRFFIClass; +jobject UpCallsRFFIObject; jclass CharSXPWrapperClass; -static jmethodID validateMethodID; - static JNIEnv *curenv = NULL; // default for trace output when enabled @@ -87,8 +86,10 @@ static int nativeArrayTableHwmStack[CALLDEPTH_STACK_SIZE]; static jmp_buf* callErrorJmpBufTable[CALLDEPTH_STACK_SIZE]; -void init_utils(JNIEnv *env) { +void init_utils(JNIEnv *env, jobject upCallsInstance) { curenv = env; + UpCallsRFFIClass = (*env)->GetObjectClass(env, upCallsInstance); + UpCallsRFFIObject = (*env)->NewGlobalRef(env, upCallsInstance); if (TRACE_ENABLED && traceFile == NULL) { if (!isEmbedded) { traceFile = stdout; @@ -109,8 +110,6 @@ void init_utils(JNIEnv *env) { setvbuf(traceFile, (char*) NULL, _IONBF, 0); } } - CallRFFIHelperClass = checkFindClass(env, "com/oracle/truffle/r/runtime/ffi/jni/CallRFFIHelper"); - validateMethodID = checkGetMethodID(env, CallRFFIHelperClass, "validate", "(Ljava/lang/Object;)Ljava/lang/Object;", 1); cachedGlobalRefs = calloc(CACHED_GLOBALREFS_INITIAL_SIZE, sizeof(GlobalRefElem)); cachedGlobalRefsLength = CACHED_GLOBALREFS_INITIAL_SIZE; cachedGlobalRefsHwm = 0; @@ -230,7 +229,7 @@ void *getNativeArray(JNIEnv *thisenv, SEXP x, SEXPTYPE type) { jarray jArray; switch (type) { case INTSXP: { - jintArray intArray = (*thisenv)->CallStaticObjectMethod(thisenv, CallRFFIHelperClass, INTEGER_MethodID, x); + jintArray intArray = (*thisenv)->CallObjectMethod(thisenv, UpCallsRFFIObject, INTEGER_MethodID, x); int len = (*thisenv)->GetArrayLength(thisenv, intArray); data = (*thisenv)->GetIntArrayElements(thisenv, intArray, &isCopy); jArray = intArray; @@ -238,7 +237,7 @@ void *getNativeArray(JNIEnv *thisenv, SEXP x, SEXPTYPE type) { } case REALSXP: { - jdoubleArray doubleArray = (*thisenv)->CallStaticObjectMethod(thisenv, CallRFFIHelperClass, REAL_MethodID, x); + jdoubleArray doubleArray = (*thisenv)->CallObjectMethod(thisenv, UpCallsRFFIObject, REAL_MethodID, x); int len = (*thisenv)->GetArrayLength(thisenv, doubleArray); data = (*thisenv)->GetDoubleArrayElements(thisenv, doubleArray, &isCopy); jArray = doubleArray; @@ -246,7 +245,7 @@ void *getNativeArray(JNIEnv *thisenv, SEXP x, SEXPTYPE type) { } case RAWSXP: { - jbyteArray byteArray = (*thisenv)->CallStaticObjectMethod(thisenv, CallRFFIHelperClass, RAW_MethodID, x); + jbyteArray byteArray = (*thisenv)->CallObjectMethod(thisenv, UpCallsRFFIObject, RAW_MethodID, x); int len = (*thisenv)->GetArrayLength(thisenv, byteArray); data = (*thisenv)->GetByteArrayElements(thisenv, byteArray, &isCopy); jArray = byteArray; @@ -255,7 +254,7 @@ void *getNativeArray(JNIEnv *thisenv, SEXP x, SEXPTYPE type) { case LGLSXP: { // Special treatment becuase R FFI wants int* and FastR represents using byte[] - jbyteArray byteArray = (*thisenv)->CallStaticObjectMethod(thisenv, CallRFFIHelperClass, LOGICAL_MethodID, x); + jbyteArray byteArray = (*thisenv)->CallObjectMethod(thisenv, UpCallsRFFIObject, LOGICAL_MethodID, x); int len = (*thisenv)->GetArrayLength(thisenv, byteArray); jbyte* internalData = (*thisenv)->GetByteArrayElements(thisenv, byteArray, &isCopy); int* idata = malloc(len * sizeof(int)); @@ -333,7 +332,7 @@ static void releaseNativeArray(JNIEnv *env, int i, int freedata) { fatalError("releaseNativeArray type"); } // update complete status - (*env)->CallVoidMethod(env, cv.obj, setCompleteMethodID, cv.obj, complete); + (*env)->CallVoidMethod(env, UpCallsRFFIObject, setCompleteMethodID, cv.obj, complete); if (freedata) { // free up the slot @@ -427,10 +426,6 @@ void validateRef(JNIEnv *env, SEXP x, const char *msg) { } } -void validate(SEXP x) { - (*curenv)->CallStaticObjectMethod(curenv, CallRFFIHelperClass, validateMethodID, x); -} - JNIEnv *getEnv() { // fprintf(traceFile, "getEnv()=%p\n", curenv); return curenv; 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 3a3539579e..99732f9376 100644 --- a/com.oracle.truffle.r.native/fficall/src/jni/rffiutils.h +++ b/com.oracle.truffle.r.native/fficall/src/jni/rffiutils.h @@ -76,12 +76,12 @@ void updateNativeArrays(JNIEnv *env); SEXP addGlobalRef(JNIEnv *env, SEXP obj, int permanent); +void init_utils(JNIEnv *env, jobject upCallsInstance); void init_rmath(JNIEnv *env); void init_variables(JNIEnv *env, jobjectArray initialValues); void init_dynload(JNIEnv *env); void init_internals(JNIEnv *env); void init_random(JNIEnv *env); -void init_utils(JNIEnv *env); void init_parse(JNIEnv *env); void init_pcre(JNIEnv *env); void init_c(JNIEnv *env); @@ -90,7 +90,8 @@ void setEmbedded(void); void setTempDir(JNIEnv *, jstring tempDir); -extern jclass CallRFFIHelperClass; +extern jclass UpCallsRFFIClass; +extern jobject UpCallsRFFIObject; extern FILE *traceFile; // tracing/debugging support, set to 1 and recompile to enable 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 ca381df5e2..aaf00d68fe 100644 --- a/com.oracle.truffle.r.native/fficall/src/jni/variables.c +++ b/com.oracle.truffle.r.native/fficall/src/jni/variables.c @@ -31,37 +31,37 @@ #include <rffiutils.h> #include <variable_defs.h> -jmethodID getGlobalEnvMethodID; -jmethodID getBaseEnvMethodID; -jmethodID getBaseNamespaceMethodID; -jmethodID getNamespaceRegistryMethodID; +jmethodID R_GlobalEnvMethodID; +jmethodID R_BaseEnvMethodID; +jmethodID R_BaseNamespaceMethodID; +jmethodID R_NamespaceRegistryMethodID; jmethodID isInteractiveMethodID; -jmethodID getGlobalContextMethodID; +jmethodID R_GlobalContextMethodID; // R_GlobalEnv et al are not a variables in FASTR as they are RContext specific SEXP FASTR_GlobalEnv() { JNIEnv *env = getEnv(); - return (*env)->CallStaticObjectMethod(env, CallRFFIHelperClass, getGlobalEnvMethodID); + return (*env)->CallObjectMethod(env, UpCallsRFFIObject, R_GlobalEnvMethodID); } SEXP FASTR_BaseEnv() { JNIEnv *env = getEnv(); - return (*env)->CallStaticObjectMethod(env, CallRFFIHelperClass, getBaseEnvMethodID); + return (*env)->CallObjectMethod(env, UpCallsRFFIObject, R_BaseEnvMethodID); } SEXP FASTR_BaseNamespace() { JNIEnv *env = getEnv(); - return (*env)->CallStaticObjectMethod(env, CallRFFIHelperClass, getBaseNamespaceMethodID); + return (*env)->CallObjectMethod(env, UpCallsRFFIObject, R_BaseNamespaceMethodID); } SEXP FASTR_NamespaceRegistry() { JNIEnv *env = getEnv(); - return (*env)->CallStaticObjectMethod(env, CallRFFIHelperClass, getNamespaceRegistryMethodID); + return (*env)->CallObjectMethod(env, UpCallsRFFIObject, R_NamespaceRegistryMethodID); } CTXT FASTR_GlobalContext() { JNIEnv *env = getEnv(); - CTXT res = (*env)->CallStaticObjectMethod(env, CallRFFIHelperClass, getGlobalContextMethodID); + CTXT res = (*env)->CallObjectMethod(env, UpCallsRFFIObject, R_GlobalContextMethodID); return addGlobalRef(env, res, 0); } @@ -77,12 +77,12 @@ void init_variables(JNIEnv *env, jobjectArray initialValues) { jmethodID doubleValueMethodID = checkGetMethodID(env, doubleClass, "doubleValue", "()D", 0); jmethodID intValueMethodID = checkGetMethodID(env, intClass, "intValue", "()I", 0); - getGlobalEnvMethodID = checkGetMethodID(env, CallRFFIHelperClass, "getGlobalEnv", "()Ljava/lang/Object;", 1); - getBaseEnvMethodID = checkGetMethodID(env, CallRFFIHelperClass, "getBaseEnv", "()Ljava/lang/Object;", 1); - getBaseNamespaceMethodID = checkGetMethodID(env, CallRFFIHelperClass, "getBaseNamespace", "()Ljava/lang/Object;", 1); - getNamespaceRegistryMethodID = checkGetMethodID(env, CallRFFIHelperClass, "getNamespaceRegistry", "()Ljava/lang/Object;", 1); - isInteractiveMethodID = checkGetMethodID(env, CallRFFIHelperClass, "isInteractive", "()I", 1); - getGlobalContextMethodID = checkGetMethodID(env, CallRFFIHelperClass, "getGlobalContext", "()Ljava/lang/Object;", 1); + R_GlobalEnvMethodID = checkGetMethodID(env, UpCallsRFFIClass, "R_GlobalEnv", "()Ljava/lang/Object;", 0); + R_BaseEnvMethodID = checkGetMethodID(env, UpCallsRFFIClass, "R_BaseEnv", "()Ljava/lang/Object;", 0); + R_BaseNamespaceMethodID = checkGetMethodID(env, UpCallsRFFIClass, "R_BaseNamespace", "()Ljava/lang/Object;", 0); + R_NamespaceRegistryMethodID = checkGetMethodID(env, UpCallsRFFIClass, "R_NamespaceRegistry", "()Ljava/lang/Object;", 0); + isInteractiveMethodID = checkGetMethodID(env, UpCallsRFFIClass, "isInteractive", "()I", 0); + R_GlobalContextMethodID = checkGetMethodID(env, UpCallsRFFIClass, "R_GlobalContext", "()Ljava/lang/Object;", 0); int length = (*env)->GetArrayLength(env, initialValues); int index; diff --git a/com.oracle.truffle.r.runtime.ffi/src/com/oracle/truffle/r/runtime/ffi/jni/CallRFFIHelper.java b/com.oracle.truffle.r.runtime.ffi/src/com/oracle/truffle/r/runtime/ffi/JavaUpCallsRFFI.java similarity index 66% rename from com.oracle.truffle.r.runtime.ffi/src/com/oracle/truffle/r/runtime/ffi/jni/CallRFFIHelper.java rename to com.oracle.truffle.r.runtime.ffi/src/com/oracle/truffle/r/runtime/ffi/JavaUpCallsRFFI.java index fa73127bce..4f0611ede2 100644 --- a/com.oracle.truffle.r.runtime.ffi/src/com/oracle/truffle/r/runtime/ffi/jni/CallRFFIHelper.java +++ b/com.oracle.truffle.r.runtime.ffi/src/com/oracle/truffle/r/runtime/ffi/JavaUpCallsRFFI.java @@ -20,12 +20,11 @@ * or visit www.oracle.com if you need additional information or have any * questions. */ -package com.oracle.truffle.r.runtime.ffi.jni; +package com.oracle.truffle.r.runtime.ffi; import java.nio.charset.StandardCharsets; import java.util.function.Function; -import com.oracle.truffle.api.CompilerDirectives.TruffleBoundary; import com.oracle.truffle.api.frame.Frame; import com.oracle.truffle.api.frame.FrameInstance.FrameAccess; import com.oracle.truffle.api.object.DynamicObject; @@ -79,17 +78,16 @@ import com.oracle.truffle.r.runtime.data.model.RAbstractVector; import com.oracle.truffle.r.runtime.env.REnvironment; import com.oracle.truffle.r.runtime.env.REnvironment.PutException; import com.oracle.truffle.r.runtime.ffi.DLL.SymbolHandle; -import com.oracle.truffle.r.runtime.ffi.RFFIUtils; +import com.oracle.truffle.r.runtime.ffi.ParseResult.ParseStatus; +import com.oracle.truffle.r.runtime.ffi.jni.TraceUpCallsAdapter; import com.oracle.truffle.r.runtime.gnur.SEXPTYPE; import com.oracle.truffle.r.runtime.nodes.DuplicationHelper; import com.oracle.truffle.r.runtime.nodes.RNode; import com.oracle.truffle.r.runtime.rng.RRNG; /** - * This class provides methods that match the functionality of the macro/function definitions in the - * R header files, e.g. {@code Rinternals.h} that are used by C/C++ code. For ease of - * identification, we use method names that, as far as possible, match the names in the header - * files. These methods should never be called from normal FastR code. + * This class provides a simple Java-based implementation of {@link UpCallsRFFI}, using no Truffle + * mechanisms. * * TODO Many of the implementations here are incomplete and/or duplicate code that exists in the * Truffle side of the implementation, i.e., {@link RNode} subclasses. A complete refactoring that @@ -98,37 +96,16 @@ import com.oracle.truffle.r.runtime.rng.RRNG; * is desirable. In some cases it may be possible to "implement" the functions in R (which is a * simple way to achieve the above). */ -public class CallRFFIHelper { +public class JavaUpCallsRFFI implements UpCallsRFFI { - /** - * Internally GNU R distinguishes "strings" and "vectors of strings" using the {@code CHARSXP} - * and {@code STRSXP} types, respectively. Although this difference is invisible at the R level, - * it manifests itself in the R FFI as several functions traffic in the {@code CHARSXP} type. - * Since FastR already uses {@code String} to denote a length-1 string vector, it cannot be used - * to represent a {@code CHARSXP}, so this class exists to do so. - * - */ - public static final class CharSXPWrapper { - private final String contents; - - CharSXPWrapper(String contents) { - this.contents = contents; - } - - public String getContents() { - return contents; - } + private TraceUpCallsAdapter tracer; - @Override - public String toString() { - return "CHARSXP(" + contents + ")"; + public JavaUpCallsRFFI() { + if (RFFIUtils.traceEnabled()) { + tracer = new TraceUpCallsAdapter(); } } - public static Object createCharSXP(String contents) { - return new CharSXPWrapper(contents); - } - private static RuntimeException unimplemented() { return unimplemented(""); } @@ -169,38 +146,43 @@ public class CallRFFIHelper { // Checkstyle: stop method name check - public static RIntVector Rf_ScalarInteger(int value) { - if (RFFIUtils.traceEnabled()) { - RFFIUtils.traceUpCall("Rf_ScalarInteger", value); + @Override + public RIntVector Rf_ScalarInteger(int value) { + if (tracer != null) { + tracer.Rf_ScalarInteger(value); } return RDataFactory.createIntVectorFromScalar(value); } - public static RLogicalVector Rf_ScalarLogical(int value) { - if (RFFIUtils.traceEnabled()) { - RFFIUtils.traceUpCall("Rf_ScalarLogical", value); + @Override + public RLogicalVector Rf_ScalarLogical(int value) { + if (tracer != null) { + tracer.Rf_ScalarLogical(value); } return RDataFactory.createLogicalVectorFromScalar(value != 0); } - public static RDoubleVector Rf_ScalarDouble(double value) { - if (RFFIUtils.traceEnabled()) { - RFFIUtils.traceUpCall("Rf_ScalarDouble", value); + @Override + public RDoubleVector Rf_ScalarDouble(double value) { + if (tracer != null) { + tracer.Rf_ScalarDouble(value); } return RDataFactory.createDoubleVectorFromScalar(value); } - public static RStringVector Rf_ScalarString(Object value) { - if (RFFIUtils.traceEnabled()) { - RFFIUtils.traceUpCall("Rf_ScalarString", value); + @Override + public RStringVector Rf_ScalarString(Object value) { + if (tracer != null) { + tracer.Rf_ScalarString(value); } CharSXPWrapper chars = guaranteeInstanceOf(value, CharSXPWrapper.class); return RDataFactory.createStringVectorFromScalar(chars.getContents()); } - public static int Rf_asInteger(Object x) { - if (RFFIUtils.traceEnabled()) { - RFFIUtils.traceUpCall("Rf_asInteger", x); + @Override + public int Rf_asInteger(Object x) { + if (tracer != null) { + tracer.Rf_asInteger(x); } // TODO this is quite incomplete and really should be implemented with CastIntegerNode if (x instanceof Integer) { @@ -217,9 +199,10 @@ public class CallRFFIHelper { } } - public static double Rf_asReal(Object x) { - if (RFFIUtils.traceEnabled()) { - RFFIUtils.traceUpCall("Rf_asReal", x); + @Override + public double Rf_asReal(Object x) { + if (tracer != null) { + tracer.Rf_asReal(x); } if (x instanceof Double) { return ((Double) x).doubleValue(); @@ -231,9 +214,10 @@ public class CallRFFIHelper { } } - public static int Rf_asLogical(Object x) { - if (RFFIUtils.traceEnabled()) { - RFFIUtils.traceUpCall("Rf_asLogical", x); + @Override + public int Rf_asLogical(Object x) { + if (tracer != null) { + tracer.Rf_asLogical(x); } if (x instanceof Byte) { return ((Byte) x).intValue(); @@ -243,14 +227,15 @@ public class CallRFFIHelper { } } - public static Object Rf_asChar(Object x) { - if (RFFIUtils.traceEnabled()) { - RFFIUtils.traceUpCall("Rf_asChar", x); + @Override + public Object Rf_asChar(Object x) { + if (tracer != null) { + tracer.Rf_asChar(x); } if (x instanceof CharSXPWrapper) { return x; } else if (x instanceof RSymbol) { - return new CharSXPWrapper(((RSymbol) x).getName()); + return CharSXPWrapper.create(((RSymbol) x).getName()); } Object obj = RRuntime.asAbstractVector(x); @@ -258,34 +243,37 @@ public class CallRFFIHelper { RAbstractVector vector = (RAbstractVector) obj; if (vector.getLength() > 0) { if (vector instanceof RAbstractStringVector) { - return new CharSXPWrapper(((RAbstractStringVector) vector).getDataAt(0)); + return CharSXPWrapper.create(((RAbstractStringVector) vector).getDataAt(0)); } else { unimplemented("asChar type " + x.getClass()); } } } - return new CharSXPWrapper(RRuntime.STRING_NA); + return CharSXPWrapper.create(RRuntime.STRING_NA); } - public static Object Rf_mkCharLenCE(byte[] bytes, @SuppressWarnings("unused") int encoding) { - if (RFFIUtils.traceEnabled()) { - RFFIUtils.traceUpCall("Rf_mkCharLenCE", bytes); + @Override + public Object Rf_mkCharLenCE(byte[] bytes, int encoding) { + if (tracer != null) { + tracer.Rf_mkCharLenCE(bytes, encoding); } // TODO: handle encoding properly - return new CharSXPWrapper(new String(bytes, StandardCharsets.UTF_8)); + return CharSXPWrapper.create(new String(bytes, StandardCharsets.UTF_8)); } - public static Object Rf_cons(Object car, Object cdr) { - if (RFFIUtils.traceEnabled()) { - RFFIUtils.traceUpCall("Rf_cons", car, cdr); + @Override + public Object Rf_cons(Object car, Object cdr) { + if (tracer != null) { + tracer.Rf_cons(car, cdr); } return RDataFactory.createPairList(car, cdr); } - public static void Rf_defineVar(Object symbolArg, Object value, Object envArg) { - if (RFFIUtils.traceEnabled()) { - RFFIUtils.traceUpCall("Rf_defineVar", symbolArg, value, envArg); + @Override + public void Rf_defineVar(Object symbolArg, Object value, Object envArg) { + if (tracer != null) { + tracer.Rf_defineVar(symbolArg, value, envArg); } REnvironment env = (REnvironment) envArg; RSymbol name = (RSymbol) symbolArg; @@ -296,33 +284,39 @@ public class CallRFFIHelper { } } - public static Object R_do_MAKE_CLASS(String clazz) { + @Override + public Object R_do_MAKE_CLASS(String clazz) { + if (tracer != null) { + tracer.R_do_MAKE_CLASS(clazz); + } String name = "getClass"; RFunction getClass = (RFunction) RContext.getRRuntimeASTAccess().forcePromise(name, REnvironment.getRegisteredNamespace("methods").get(name)); return RContext.getEngine().evalFunction(getClass, null, RCaller.createInvalid(null), null, clazz); } - public static Object Rf_findVar(Object symbolArg, Object envArg) { - // WARNING: argument order reversed from Rf_findVarInFrame! - if (RFFIUtils.traceEnabled()) { - RFFIUtils.traceUpCall("Rf_findVar", symbolArg, envArg); + @Override + public Object Rf_findVar(Object symbolArg, Object envArg) { + if (tracer != null) { + tracer.Rf_findVar(symbolArg, envArg); } return findVarInFrameHelper(envArg, symbolArg, true); } - public static Object Rf_findVarInFrame(Object envArg, Object symbolArg) { - if (RFFIUtils.traceEnabled()) { - RFFIUtils.traceUpCall("Rf_findVarInFrame", envArg, symbolArg); + @Override + public Object Rf_findVarInFrame(Object envArg, Object symbolArg) { + if (tracer != null) { + tracer.Rf_findVarInFrame(envArg, symbolArg); } return findVarInFrameHelper(envArg, symbolArg, false); } - public static Object Rf_findVarInFrame3(Object envArg, Object symbolArg, @SuppressWarnings("unused") int doGet) { + @Override + public Object Rf_findVarInFrame3(Object envArg, Object symbolArg, int doGet) { + if (tracer != null) { + tracer.Rf_findVarInFrame3(envArg, symbolArg, doGet); + } // GNU R has code for IS_USER_DATBASE that uses doGet // This is a lookup in the single environment (envArg) only, i.e. inherits=false - if (RFFIUtils.traceEnabled()) { - RFFIUtils.traceUpCall("Rf_findVarInFrame3", envArg, symbolArg); - } return findVarInFrameHelper(envArg, symbolArg, false); } @@ -349,9 +343,10 @@ public class CallRFFIHelper { return RUnboundValue.instance; } - public static Object Rf_getAttrib(Object obj, Object name) { - if (RFFIUtils.traceEnabled()) { - RFFIUtils.traceUpCall("Rf_getAttrib", obj, name); + @Override + public Object Rf_getAttrib(Object obj, Object name) { + if (tracer != null) { + tracer.Rf_getAttrib(obj, name); } Object result = RNull.instance; if (obj instanceof RAttributable) { @@ -368,9 +363,10 @@ public class CallRFFIHelper { return result; } - public static void Rf_setAttrib(Object obj, Object name, Object val) { - if (RFFIUtils.traceEnabled()) { - RFFIUtils.traceUpCall("Rf_setAttrib", obj, name, val); + @Override + public void Rf_setAttrib(Object obj, Object name, Object val) { + if (tracer != null) { + tracer.Rf_setAttrib(obj, name, val); } if (obj instanceof RAttributable) { RAttributable attrObj = (RAttributable) obj; @@ -415,9 +411,10 @@ public class CallRFFIHelper { return result; } - public static int Rf_inherits(Object x, String clazz) { - if (RFFIUtils.traceEnabled()) { - RFFIUtils.traceUpCall("Rf_inherits", x, clazz); + @Override + public int Rf_inherits(Object x, String clazz) { + if (tracer != null) { + tracer.Rf_inherits(x, clazz); } int result = 0; RStringVector hierarchy = getClassHr(x); @@ -429,38 +426,43 @@ public class CallRFFIHelper { return result; } - public static Object Rf_install(String name) { - if (RFFIUtils.traceEnabled()) { - RFFIUtils.traceUpCall("Rf_install", name); + @Override + public Object Rf_install(String name) { + if (tracer != null) { + tracer.Rf_install(name); } return RDataFactory.createSymbolInterned(name); } - public static Object Rf_lengthgets(Object x, int newSize) { - if (RFFIUtils.traceEnabled()) { - RFFIUtils.traceUpCall("Rf_lengthgets", x, newSize); + @Override + public Object Rf_lengthgets(Object x, int newSize) { + if (tracer != null) { + tracer.Rf_lengthgets(x, newSize); } RAbstractVector vec = (RAbstractVector) RRuntime.asAbstractVector(x); return vec.resize(newSize); } - public static int Rf_isString(Object x) { - if (RFFIUtils.traceEnabled()) { - RFFIUtils.traceUpCall("Rf_isString", x); + @Override + public int Rf_isString(Object x) { + if (tracer != null) { + tracer.Rf_isString(x); } return RRuntime.checkType(x, RType.Character) ? 1 : 0; } - public static int Rf_isNull(Object x) { - if (RFFIUtils.traceEnabled()) { - RFFIUtils.traceUpCall("Rf_isNull", x); + @Override + public int Rf_isNull(Object x) { + if (tracer != null) { + tracer.Rf_isNull(x); } return x == RNull.instance ? 1 : 0; } - public static Object Rf_PairToVectorList(Object x) { - if (RFFIUtils.traceEnabled()) { - RFFIUtils.traceUpCall("Rf_PairToVectorList", x); + @Override + public Object Rf_PairToVectorList(Object x) { + if (tracer != null) { + tracer.Rf_PairToVectorList(x); } if (x == RNull.instance) { return RDataFactory.createList(); @@ -469,30 +471,34 @@ public class CallRFFIHelper { return pl.toRList(); } - public static void Rf_error(String msg) { - if (RFFIUtils.traceEnabled()) { - RFFIUtils.traceUpCall("Rf_error", msg); + @Override + public void Rf_error(String msg) { + if (tracer != null) { + tracer.Rf_error(msg); } throw RError.error(RError.SHOW_CALLER2, RError.Message.GENERIC, msg); } - public static void Rf_warning(String msg) { - if (RFFIUtils.traceEnabled()) { - RFFIUtils.traceUpCall("Rf_warning", msg); + @Override + public void Rf_warning(String msg) { + if (tracer != null) { + tracer.Rf_warning(msg); } RError.warning(RError.SHOW_CALLER2, RError.Message.GENERIC, msg); } - public static void Rf_warningcall(Object call, String msg) { - if (RFFIUtils.traceEnabled()) { - RFFIUtils.traceUpCall("Rf_warningcall", call, msg); + @Override + public void Rf_warningcall(Object call, String msg) { + if (tracer != null) { + tracer.Rf_warningcall(call, msg); } RErrorHandling.warningcallRFFI(call, msg); } - public static Object Rf_allocateVector(int mode, int n) { - if (RFFIUtils.traceEnabled()) { - RFFIUtils.traceUpCall("Rf_allocateVector", mode, n); + @Override + public Object Rf_allocateVector(int mode, int n) { + if (tracer != null) { + tracer.Rf_allocateVector(mode, n); } SEXPTYPE type = SEXPTYPE.mapInt(mode); if (n < 0) { @@ -521,9 +527,10 @@ public class CallRFFIHelper { } } - public static Object Rf_allocateArray(int mode, Object dimsObj) { - if (RFFIUtils.traceEnabled()) { - RFFIUtils.traceUpCall("Rf_allocateArray", mode, dimsObj); + @Override + public Object Rf_allocateArray(int mode, Object dimsObj) { + if (tracer != null) { + tracer.Rf_allocateArray(mode, dimsObj); } RIntVector dims = (RIntVector) dimsObj; int n = 1; @@ -539,9 +546,10 @@ public class CallRFFIHelper { } - public static Object Rf_allocateMatrix(int mode, int nrow, int ncol) { - if (RFFIUtils.traceEnabled()) { - RFFIUtils.traceUpCall("Rf_allocateMatrix", mode, ncol, nrow); + @Override + public Object Rf_allocateMatrix(int mode, int nrow, int ncol) { + if (tracer != null) { + tracer.Rf_allocateMatrix(mode, ncol, nrow); } SEXPTYPE type = SEXPTYPE.mapInt(mode); if (nrow < 0 || ncol < 0) { @@ -565,23 +573,26 @@ public class CallRFFIHelper { } } - public static int Rf_nrows(Object x) { - if (RFFIUtils.traceEnabled()) { - RFFIUtils.traceUpCall("Rf_nrows", x); + @Override + public int Rf_nrows(Object x) { + if (tracer != null) { + tracer.Rf_nrows(x); } return RRuntime.nrows(x); } - public static int Rf_ncols(Object x) { - if (RFFIUtils.traceEnabled()) { - RFFIUtils.traceUpCall("Rf_ncols", x); + @Override + public int Rf_ncols(Object x) { + if (tracer != null) { + tracer.Rf_ncols(x); } return RRuntime.ncols(x); } - public static int LENGTH(Object x) { - if (RFFIUtils.traceEnabled()) { - RFFIUtils.traceUpCall("LENGTH", x); + @Override + public int LENGTH(Object x) { + if (tracer != null) { + tracer.LENGTH(x); } if (x instanceof RAbstractContainer) { return ((RAbstractContainer) x).getLength(); @@ -596,26 +607,29 @@ public class CallRFFIHelper { } } - public static void SET_STRING_ELT(Object x, int i, Object v) { - if (RFFIUtils.traceEnabled()) { - RFFIUtils.traceUpCall("SET_STRING_ELT", x, i, v); + @Override + public void SET_STRING_ELT(Object x, int i, Object v) { + if (tracer != null) { + tracer.SET_STRING_ELT(x, i, v); } RStringVector vector = guaranteeInstanceOf(x, RStringVector.class); CharSXPWrapper element = guaranteeInstanceOf(v, CharSXPWrapper.class); vector.setElement(i, element.getContents()); } - public static void SET_VECTOR_ELT(Object x, int i, Object v) { - if (RFFIUtils.traceEnabled()) { - RFFIUtils.traceUpCall("SET_VECTOR_ELT", i, v); + @Override + public void SET_VECTOR_ELT(Object x, int i, Object v) { + if (tracer != null) { + tracer.SET_VECTOR_ELT(x, i, v); } RList list = guaranteeInstanceOf(x, RList.class); list.setElement(i, v); } - public static byte[] RAW(Object x) { - if (RFFIUtils.traceEnabled()) { - RFFIUtils.traceUpCall("RAW", x); + @Override + public byte[] RAW(Object x) { + if (tracer != null) { + tracer.RAW(x); } if (x instanceof RRawVector) { return ((RRawVector) x).getDataWithoutCopying(); @@ -626,9 +640,10 @@ public class CallRFFIHelper { } } - public static byte[] LOGICAL(Object x) { - if (RFFIUtils.traceEnabled()) { - RFFIUtils.traceUpCall("LOGICAL", x); + @Override + public byte[] LOGICAL(Object x) { + if (tracer != null) { + tracer.LOGICAL(x); } if (x instanceof RLogicalVector) { return ((RLogicalVector) x).getDataWithoutCopying(); @@ -639,9 +654,10 @@ public class CallRFFIHelper { } } - public static int[] INTEGER(Object x) { - if (RFFIUtils.traceEnabled()) { - RFFIUtils.traceUpCall("INTEGER", x); + @Override + public int[] INTEGER(Object x) { + if (tracer != null) { + tracer.INTEGER(x); } if (x instanceof RIntVector) { return ((RIntVector) x).getDataWithoutCopying(); @@ -662,9 +678,10 @@ public class CallRFFIHelper { } } - public static double[] REAL(Object x) { - if (RFFIUtils.traceEnabled()) { - RFFIUtils.traceUpCall("REAL", x); + @Override + public double[] REAL(Object x) { + if (tracer != null) { + tracer.REAL(x); } if (x instanceof RDoubleVector) { return ((RDoubleVector) x).getDataWithoutCopying(); @@ -676,33 +693,19 @@ public class CallRFFIHelper { } } - /** - * Called to possibly update the "complete" status on {@code x}. N.B. {@code x} may not be an - * object with a concrete {@code setComplete} method, e.g. see {@link #INTEGER(Object)}. - */ - public static void setComplete(Object x, boolean complete) { - // only care about concrete vectors - if (x instanceof RVector) { - ((RVector<?>) x).setComplete(complete); - } - } - - public static void logObject(Object x) { - System.out.println("object " + x); - System.out.println("class " + x.getClass()); - } - - public static Object STRING_ELT(Object x, int i) { - if (RFFIUtils.traceEnabled()) { - RFFIUtils.traceUpCall("STRING_ELT", x, i); + @Override + public Object STRING_ELT(Object x, int i) { + if (tracer != null) { + tracer.STRING_ELT(x, i); } RAbstractStringVector vector = guaranteeInstanceOf(RRuntime.asAbstractVector(x), RAbstractStringVector.class); - return new CharSXPWrapper(vector.getDataAt(i)); + return CharSXPWrapper.create(vector.getDataAt(i)); } - public static Object VECTOR_ELT(Object x, int i) { - if (RFFIUtils.traceEnabled()) { - RFFIUtils.traceUpCall("VECTOR_ELT", x, i); + @Override + public Object VECTOR_ELT(Object x, int i) { + if (tracer != null) { + tracer.VECTOR_ELT(x, i); } Object vec = x; if (vec instanceof RExpression) { @@ -712,9 +715,10 @@ public class CallRFFIHelper { return list.getDataAt(i); } - public static int NAMED(Object x) { - if (RFFIUtils.traceEnabled()) { - RFFIUtils.traceUpCall("NAMED", x); + @Override + public int NAMED(Object x) { + if (tracer != null) { + tracer.NAMED(x); } if (x instanceof RShareable) { return ((RShareable) x).isShared() ? 1 : 0; @@ -723,9 +727,10 @@ public class CallRFFIHelper { } } - public static Object SET_TYPEOF_FASTR(Object x, int v) { - if (RFFIUtils.traceEnabled()) { - RFFIUtils.traceUpCall("SET_TYPEOF_FASTR", x, v); + @Override + public Object SET_TYPEOF_FASTR(Object x, int v) { + if (tracer != null) { + tracer.SET_TYPEOF_FASTR(x, v); } int code = SEXPTYPE.gnuRCodeForObject(x); if (code == SEXPTYPE.LISTSXP.code && v == SEXPTYPE.LANGSXP.code) { @@ -735,9 +740,10 @@ public class CallRFFIHelper { } } - public static int TYPEOF(Object x) { - if (RFFIUtils.traceEnabled()) { - RFFIUtils.traceUpCall("TYPEOF", x); + @Override + public int TYPEOF(Object x) { + if (tracer != null) { + tracer.TYPEOF(x); } if (x instanceof CharSXPWrapper) { return SEXPTYPE.CHARSXP.code; @@ -746,9 +752,10 @@ public class CallRFFIHelper { } } - public static int OBJECT(Object x) { - if (RFFIUtils.traceEnabled()) { - RFFIUtils.traceUpCall("OBJECT", x); + @Override + public int OBJECT(Object x) { + if (tracer != null) { + tracer.OBJECT(x); } if (x instanceof RAttributable) { return ((RAttributable) x).getAttr(RRuntime.CLASS_ATTR_KEY) == null ? 0 : 1; @@ -757,9 +764,10 @@ public class CallRFFIHelper { } } - public static Object Rf_duplicate(Object x, int deep) { - if (RFFIUtils.traceEnabled()) { - RFFIUtils.traceUpCall("Rf_duplicate", x, deep); + @Override + public Object Rf_duplicate(Object x, int deep) { + if (tracer != null) { + tracer.Rf_duplicate(x, deep); } guarantee(x != null, "unexpected type: null instead of " + x.getClass().getSimpleName()); guarantee(x instanceof RShareable || x instanceof RIntSequence || x instanceof RExternalPtr, @@ -773,9 +781,10 @@ public class CallRFFIHelper { } } - public static int Rf_anyDuplicated(Object x, int fromLast) { - if (RFFIUtils.traceEnabled()) { - RFFIUtils.traceUpCall("Rf_anyDuplicated", x, fromLast); + @Override + public int Rf_anyDuplicated(Object x, int fromLast) { + if (tracer != null) { + tracer.Rf_anyDuplicated(x, fromLast); } RAbstractVector vec = (RAbstractVector) x; if (vec.getLength() == 0) { @@ -785,17 +794,19 @@ public class CallRFFIHelper { } } - public static Object PRINTNAME(Object x) { - if (RFFIUtils.traceEnabled()) { - RFFIUtils.traceUpCall("PRINTNAME", x); + @Override + public Object PRINTNAME(Object x) { + if (tracer != null) { + tracer.PRINTNAME(x); } guaranteeInstanceOf(x, RSymbol.class); - return new CharSXPWrapper(((RSymbol) x).getName()); + return CharSXPWrapper.create(((RSymbol) x).getName()); } - public static Object TAG(Object e) { - if (RFFIUtils.traceEnabled()) { - RFFIUtils.traceUpCall("TAG", e); + @Override + public Object TAG(Object e) { + if (tracer != null) { + tracer.TAG(e); } if (e instanceof RPairList) { return ((RPairList) e).getTag(); @@ -806,9 +817,10 @@ public class CallRFFIHelper { } } - public static Object CAR(Object e) { - if (RFFIUtils.traceEnabled()) { - RFFIUtils.traceUpCall("CAR", e); + @Override + public Object CAR(Object e) { + if (tracer != null) { + tracer.CAR(e); } guarantee(e != null && (RPairList.class.isInstance(e) || RLanguage.class.isInstance(e)), "CAR only works on pair lists and language objects"); if (e instanceof RPairList) { @@ -818,9 +830,10 @@ public class CallRFFIHelper { } } - public static Object CDR(Object e) { - if (RFFIUtils.traceEnabled()) { - RFFIUtils.traceUpCall("CDR", e); + @Override + public Object CDR(Object e) { + if (tracer != null) { + tracer.CDR(e); } if (e instanceof RLanguage) { RLanguage lang = (RLanguage) e; @@ -832,9 +845,10 @@ public class CallRFFIHelper { } } - public static Object CADR(Object e) { - if (RFFIUtils.traceEnabled()) { - RFFIUtils.traceUpCall("CADR", e); + @Override + public Object CADR(Object e) { + if (tracer != null) { + tracer.CADR(e); } guarantee(e != null && (RPairList.class.isInstance(e) || RLanguage.class.isInstance(e)), "CADR only works on pair lists and language objects"); if (e instanceof RPairList) { @@ -844,9 +858,10 @@ public class CallRFFIHelper { } } - public static Object CADDR(Object e) { - if (RFFIUtils.traceEnabled()) { - RFFIUtils.traceUpCall("CADDR", e); + @Override + public Object CADDR(Object e) { + if (tracer != null) { + tracer.CADDR(e); } guarantee(e != null && (RPairList.class.isInstance(e) || RLanguage.class.isInstance(e)), "CADDR only works on pair lists and language objects"); if (e instanceof RPairList) { @@ -856,9 +871,10 @@ public class CallRFFIHelper { } } - public static Object CDDR(Object e) { - if (RFFIUtils.traceEnabled()) { - RFFIUtils.traceUpCall("CDDR", e); + @Override + public Object CDDR(Object e) { + if (tracer != null) { + tracer.CDDR(e); } if (e instanceof RLanguage) { RLanguage lang = (RLanguage) e; @@ -870,9 +886,10 @@ public class CallRFFIHelper { } } - public static Object SET_TAG(Object x, Object y) { - if (RFFIUtils.traceEnabled()) { - RFFIUtils.traceUpCall("SET_TAG", x, y); + @Override + public Object SET_TAG(Object x, Object y) { + if (tracer != null) { + tracer.SET_TAG(x, y); } if (x instanceof RPairList) { ((RPairList) x).setTag(y); @@ -884,32 +901,39 @@ public class CallRFFIHelper { return y; } - public static Object SETCAR(Object x, Object y) { - if (RFFIUtils.traceEnabled()) { - RFFIUtils.traceUpCall("SETCAR", x, y); + @Override + public Object SETCAR(Object x, Object y) { + if (tracer != null) { + tracer.SETCAR(x, y); } guaranteeInstanceOf(x, RPairList.class); ((RPairList) x).setCar(y); return y; } - public static Object SETCDR(Object x, Object y) { - if (RFFIUtils.traceEnabled()) { - RFFIUtils.traceUpCall("SETCDR", x, y); + @Override + public Object SETCDR(Object x, Object y) { + if (tracer != null) { + tracer.SETCDR(x, y); } guaranteeInstanceOf(x, RPairList.class); ((RPairList) x).setCdr(y); return y; } - public static Object SETCADR(Object x, Object y) { + @Override + public Object SETCADR(Object x, Object y) { + if (tracer != null) { + tracer.SETCADR(x, y); + } SETCAR(CDR(x), y); return y; } - public static Object SYMVALUE(Object x) { - if (RFFIUtils.traceEnabled()) { - RFFIUtils.traceUpCall("SYMVALUE", x); + @Override + public Object SYMVALUE(Object x) { + if (tracer != null) { + tracer.SYMVALUE(x); } if (!(x instanceof RSymbol)) { throw RInternalError.shouldNotReachHere(); @@ -922,9 +946,10 @@ public class CallRFFIHelper { } } - public static void SET_SYMVALUE(Object x, Object v) { - if (RFFIUtils.traceEnabled()) { - RFFIUtils.traceUpCall("SET_SYMVALUE", x, v); + @Override + public void SET_SYMVALUE(Object x, Object v) { + if (tracer != null) { + tracer.SET_SYMVALUE(x, v); } if (!(x instanceof RSymbol)) { throw RInternalError.shouldNotReachHere(); @@ -932,27 +957,29 @@ public class CallRFFIHelper { REnvironment.baseEnv().safePut(((RSymbol) x).getName(), v); } - public static int R_BindingIsLocked(Object sym, Object env) { - if (RFFIUtils.traceEnabled()) { - RFFIUtils.traceUpCall("R_BindingIsLocked", sym, env); + @Override + public int R_BindingIsLocked(Object sym, Object env) { + if (tracer != null) { + tracer.R_BindingIsLocked(sym, env); } guaranteeInstanceOf(sym, RSymbol.class); guaranteeInstanceOf(env, REnvironment.class); return ((REnvironment) env).bindingIsLocked(((RSymbol) sym).getName()) ? 1 : 0; } - public static Object R_FindNamespace(Object name) { - if (RFFIUtils.traceEnabled()) { - RFFIUtils.traceUpCall("R_FindNamespace", name); + @Override + public Object R_FindNamespace(Object name) { + if (tracer != null) { + tracer.R_FindNamespace(name); } Object result = RContext.getInstance().stateREnvironment.getNamespaceRegistry().get(RRuntime.asString(name)); return result; } - @TruffleBoundary - public static Object Rf_eval(Object expr, Object env) { - if (RFFIUtils.traceEnabled()) { - RFFIUtils.traceUpCall("Rf_eval", expr, env); + @Override + public Object Rf_eval(Object expr, Object env) { + if (tracer != null) { + tracer.Rf_eval(expr, env); } guarantee(env instanceof REnvironment); Object result; @@ -981,9 +1008,10 @@ public class CallRFFIHelper { return result; } - public static Object Rf_findfun(Object symbolObj, Object envObj) { - if (RFFIUtils.traceEnabled()) { - RFFIUtils.traceUpCall("Rf_findfun", symbolObj, envObj); + @Override + public Object Rf_findfun(Object symbolObj, Object envObj) { + if (tracer != null) { + tracer.Rf_findfun(symbolObj, envObj); } guarantee(envObj instanceof REnvironment); REnvironment env = (REnvironment) envObj; @@ -999,18 +1027,20 @@ public class CallRFFIHelper { } } - public static Object Rf_GetOption1(Object tag) { - if (RFFIUtils.traceEnabled()) { - RFFIUtils.traceUpCall("Rf_GetOption1", tag); + @Override + public Object Rf_GetOption1(Object tag) { + if (tracer != null) { + tracer.Rf_GetOption1(tag); } guarantee(tag instanceof RSymbol); Object result = RContext.getInstance().stateROptions.getValue(((RSymbol) tag).getName()); return result; } - public static void Rf_gsetVar(Object symbol, Object value, Object rho) { - if (RFFIUtils.traceEnabled()) { - RFFIUtils.traceUpCall("Rf_gsetVar", symbol, value, rho); + @Override + public void Rf_gsetVar(Object symbol, Object value, Object rho) { + if (tracer != null) { + tracer.Rf_gsetVar(symbol, value, rho); } guarantee(symbol instanceof RSymbol); REnvironment baseEnv = RContext.getInstance().stateREnvironment.getBaseEnv(); @@ -1022,9 +1052,10 @@ public class CallRFFIHelper { } } - public static void DUPLICATE_ATTRIB(Object to, Object from) { - if (RFFIUtils.traceEnabled()) { - RFFIUtils.traceUpCall("DUPLICATE_ATTRIB", to, from); + @Override + public void DUPLICATE_ATTRIB(Object to, Object from) { + if (tracer != null) { + tracer.DUPLICATE_ATTRIB(to, from); } if (from instanceof RAttributable) { guaranteeInstanceOf(to, RAttributable.class); @@ -1034,9 +1065,10 @@ public class CallRFFIHelper { // TODO: copy OBJECT? and S4 attributes } - public static int R_computeIdentical(Object x, Object y, int flags) { - if (RFFIUtils.traceEnabled()) { - RFFIUtils.traceUpCall("R_computeIdentical", x, y, flags); + @Override + public int R_computeIdentical(Object x, Object y, int flags) { + if (tracer != null) { + tracer.R_computeIdentical(x, y, flags); } RFunction indenticalBuiltin = RContext.lookupBuiltin("identical"); Object res = RContext.getEngine().evalFunction(indenticalBuiltin, null, null, null, x, y, RRuntime.asLogical((!((flags & 1) == 0))), @@ -1044,25 +1076,26 @@ public class CallRFFIHelper { return (int) res; } - @SuppressWarnings("unused") - public static void Rf_copyListMatrix(Object s, Object t, int byrow) { - if (RFFIUtils.traceEnabled()) { - RFFIUtils.traceUpCall("Rf_copyListMatrix", t, byrow); + @Override + public void Rf_copyListMatrix(Object s, Object t, int byrow) { + if (tracer != null) { + tracer.Rf_copyListMatrix(s, t, byrow); } throw unimplemented(); } - @SuppressWarnings("unused") - public static void Rf_copyMatrix(Object s, Object t, int byrow) { - if (RFFIUtils.traceEnabled()) { - RFFIUtils.traceUpCall("Rf_copyMatrix", t, byrow); + @Override + public void Rf_copyMatrix(Object s, Object t, int byrow) { + if (tracer != null) { + tracer.Rf_copyMatrix(s, t, byrow); } throw unimplemented(); } - public static Object R_tryEval(Object expr, Object env, boolean silent) { - if (RFFIUtils.traceEnabled()) { - RFFIUtils.traceUpCall("R_tryEval", expr, env, silent); + @Override + public Object R_tryEval(Object expr, Object env, boolean silent) { + if (tracer != null) { + tracer.R_tryEval(expr, env, silent); } Object handlerStack = RErrorHandling.getHandlerStack(); Object restartStack = RErrorHandling.getRestartStack(); @@ -1083,25 +1116,27 @@ public class CallRFFIHelper { * a C function is invoked (in the native layer) instead of an R expression. assert: this is * ONLY called from R_TopLevelExec prior to calling C function. */ - public static Object resetAndGetErrorHandlerStacks() { - if (RFFIUtils.traceEnabled()) { - RFFIUtils.traceUpCall("R_TopLevelExec"); + @Override + public Object R_ToplevelExec() { + if (tracer != null) { + tracer.R_ToplevelExec(); } return RErrorHandling.resetAndGetHandlerStacks(); } /** - * Helper function for {@code R_TopLevelExec}, see {@link #resetAndGetErrorHandlerStacks()}, - * called after C function returns. + * Helper function for {@code R_TopLevelExec}, see {@link #R_ToplevelExec()}, called after C + * function returns. */ - public static void restoreErrorHandlerStacks(Object stacks) { + public void R_ToplevelExecRestoreErrorHandlerStacks(Object stacks) { RErrorHandling.HandlerStacks handlerStacks = guaranteeInstanceOf(stacks, RErrorHandling.HandlerStacks.class); RErrorHandling.restoreHandlerStacks(handlerStacks); } - public static int RDEBUG(Object x) { - if (RFFIUtils.traceEnabled()) { - RFFIUtils.traceUpCall("RDEBUG", x); + @Override + public int RDEBUG(Object x) { + if (tracer != null) { + tracer.RDEBUG(x); } REnvironment env = guaranteeInstanceOf(x, REnvironment.class); if (env instanceof REnvironment.Function) { @@ -1113,9 +1148,10 @@ public class CallRFFIHelper { } } - public static void SET_RDEBUG(Object x, int v) { - if (RFFIUtils.traceEnabled()) { - RFFIUtils.traceUpCall("SET_RDEBUG", x, v); + @Override + public void SET_RDEBUG(Object x, int v) { + if (tracer != null) { + tracer.SET_RDEBUG(x, v); } REnvironment env = guaranteeInstanceOf(x, REnvironment.class); if (env instanceof REnvironment.Function) { @@ -1129,27 +1165,30 @@ public class CallRFFIHelper { } } - public static int RSTEP(Object x) { - if (RFFIUtils.traceEnabled()) { - RFFIUtils.traceUpCall("RSTEP", x); + @Override + public int RSTEP(Object x) { + if (tracer != null) { + tracer.RSTEP(x); } @SuppressWarnings("unused") REnvironment env = guaranteeInstanceOf(x, REnvironment.class); throw RInternalError.unimplemented("RSTEP"); } - public static void SET_RSTEP(Object x, int v) { - if (RFFIUtils.traceEnabled()) { - RFFIUtils.traceUpCall("SET_RSTEP", x, v); + @Override + public void SET_RSTEP(Object x, int v) { + if (tracer != null) { + tracer.SET_RSTEP(x, v); } @SuppressWarnings("unused") REnvironment env = guaranteeInstanceOf(x, REnvironment.class); throw RInternalError.unimplemented("SET_RSTEP"); } - public static Object ENCLOS(Object x) { - if (RFFIUtils.traceEnabled()) { - RFFIUtils.traceUpCall("ENCLOS", x); + @Override + public Object ENCLOS(Object x) { + if (tracer != null) { + tracer.ENCLOS(x); } REnvironment env = guaranteeInstanceOf(x, REnvironment.class); Object result = env.getParent(); @@ -1159,35 +1198,19 @@ public class CallRFFIHelper { return result; } - public static Object PRVALUE(Object x) { - if (RFFIUtils.traceEnabled()) { - RFFIUtils.traceUpCall("PRVALUE", x); + @Override + public Object PRVALUE(Object x) { + if (tracer != null) { + tracer.PRVALUE(x); } RPromise p = guaranteeInstanceOf(x, RPromise.class); return p.isEvaluated() ? p.getValue() : RUnboundValue.instance; } - private enum ParseStatus { - PARSE_NULL, - PARSE_OK, - PARSE_INCOMPLETE, - PARSE_ERROR, - PARSE_EOF - } - - private static class ParseResult { - @SuppressWarnings("unused") private final int parseStatus; - @SuppressWarnings("unused") private final Object expr; - - private ParseResult(int parseStatus, Object expr) { - this.parseStatus = parseStatus; - this.expr = expr; - } - } - - public static Object R_ParseVector(Object text, int n, Object srcFile) { - if (RFFIUtils.traceEnabled()) { - RFFIUtils.traceUpCall("R_ParseVector", text, n, srcFile); + @Override + public Object R_ParseVector(Object text, int n, Object srcFile) { + if (tracer != null) { + tracer.R_ParseVector(text, n, srcFile); } // TODO general case assert n == 1; @@ -1206,9 +1229,10 @@ public class CallRFFIHelper { } - public static Object R_lsInternal3(Object envArg, int allArg, int sortedArg) { - if (RFFIUtils.traceEnabled()) { - RFFIUtils.traceUpCall("R_lsInternal3", envArg, allArg, sortedArg); + @Override + public Object R_lsInternal3(Object envArg, int allArg, int sortedArg) { + if (tracer != null) { + tracer.R_lsInternal3(envArg, allArg, sortedArg); } boolean sorted = sortedArg != 0; boolean all = allArg != 0; @@ -1216,29 +1240,28 @@ public class CallRFFIHelper { return env.ls(all, null, sorted); } - public static String R_HomeDir() { - if (RFFIUtils.traceEnabled()) { - RFFIUtils.traceUpCall("R_HomeDir"); + @Override + public String R_HomeDir() { + if (tracer != null) { + tracer.R_HomeDir(); } return REnvVars.rHome(); } - @SuppressWarnings("unused") - private static void R_CleanUp(int sa, int status, int runlast) { + @Override + public void R_CleanUp(int sa, int status, int runlast) { + if (tracer != null) { + tracer.R_CleanUp(sa, status, runlast); + } RCleanUp.stdCleanUp(SA_TYPE.values()[sa], status, runlast != 0); } - // Checkstyle: resume method name check - - public static Object validate(Object x) { - return x; - } - - public static Object getGlobalContext() { - Utils.warn("Potential memory leak (global context object)"); - if (RFFIUtils.traceEnabled()) { - RFFIUtils.traceUpCall("getGlobalContext"); + @Override + public Object R_GlobalContext() { + if (tracer != null) { + tracer.R_GlobalContext(); } + Utils.warn("Potential memory leak (global context object)"); Frame frame = Utils.getActualCurrentFrame(); if (frame == null) { return RCaller.topLevel; @@ -1250,80 +1273,94 @@ public class CallRFFIHelper { return rCaller == null ? RCaller.topLevel : rCaller; } - public static Object getGlobalEnv() { - if (RFFIUtils.traceEnabled()) { - RFFIUtils.traceUpCall("getGlobalEnv"); + @Override + public Object R_GlobalEnv() { + if (tracer != null) { + tracer.R_GlobalEnv(); } return RContext.getInstance().stateREnvironment.getGlobalEnv(); } - public static Object getBaseEnv() { - if (RFFIUtils.traceEnabled()) { - RFFIUtils.traceUpCall("getBaseEnv"); + @Override + public Object R_BaseEnv() { + if (tracer != null) { + tracer.R_BaseEnv(); } return RContext.getInstance().stateREnvironment.getBaseEnv(); } - public static Object getBaseNamespace() { - if (RFFIUtils.traceEnabled()) { - RFFIUtils.traceUpCall("getBaseNamespace"); + @Override + public Object R_BaseNamespace() { + if (tracer != null) { + tracer.R_BaseNamespace(); } return RContext.getInstance().stateREnvironment.getBaseNamespace(); } - public static Object getNamespaceRegistry() { - if (RFFIUtils.traceEnabled()) { - RFFIUtils.traceUpCall("getNamespaceRegistry"); + @Override + public Object R_NamespaceRegistry() { + if (tracer != null) { + tracer.R_NamespaceRegistry(); } return RContext.getInstance().stateREnvironment.getNamespaceRegistry(); } - public static int isInteractive() { - if (RFFIUtils.traceEnabled()) { - RFFIUtils.traceUpCall("isInteractive"); + @Override + public int isInteractive() { + if (tracer != null) { + tracer.isInteractive(); } return RContext.getInstance().isInteractive() ? 1 : 0; } - public static int isS4Object(Object x) { - if (RFFIUtils.traceEnabled()) { - RFFIUtils.traceUpCall("isS4Object"); + @Override + public int isS4Object(Object x) { + if (tracer != null) { + tracer.isS4Object(x); } return x instanceof RS4Object ? 1 : 0; } - public static void printf(String message) { + @Override + public void Rprintf(String message) { + if (tracer != null) { + tracer.Rprintf(message); + } RContext.getInstance().getConsoleHandler().print(message); } - public static void getRNGstate() { - if (RFFIUtils.traceEnabled()) { - RFFIUtils.traceUpCall("getRNGstate"); + @Override + public void GetRNGstate() { + if (tracer != null) { + tracer.GetRNGstate(); } RRNG.getRNGState(); } - public static void putRNGstate() { - if (RFFIUtils.traceEnabled()) { - RFFIUtils.traceUpCall("putRNGstate"); + @Override + public void PutRNGstate() { + if (tracer != null) { + tracer.PutRNGstate(); } RRNG.putRNGState(); } - public static double unifRand() { - if (RFFIUtils.traceEnabled()) { - RFFIUtils.traceUpCall("unifRand"); + @Override + public double unif_rand() { + if (tracer != null) { + tracer.unif_rand(); } return RRNG.unifRand(); } // 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"); + @Override + public Object R_getGlobalFunctionContext() { + if (tracer != null) { + tracer.R_getGlobalFunctionContext(); } + Utils.warn("Potential memory leak (global function context object)"); Frame frame = Utils.getActualCurrentFrame(); if (frame == null) { return RNull.instance; @@ -1338,11 +1375,12 @@ public class CallRFFIHelper { return currentCaller == null || currentCaller == RCaller.topLevel ? RNull.instance : currentCaller; } - public static Object R_getParentFunctionContext(Object c) { - Utils.warn("Potential memory leak (parent function context object)"); - if (RFFIUtils.traceEnabled()) { - RFFIUtils.traceUpCall("getParentFunctionContext"); + @Override + public Object R_getParentFunctionContext(Object c) { + if (tracer != null) { + tracer.R_getParentFunctionContext(c); } + Utils.warn("Potential memory leak (parent function context object)"); RCaller currentCaller = guaranteeInstanceOf(c, RCaller.class); while (true) { currentCaller = currentCaller.getParent(); @@ -1354,9 +1392,10 @@ public class CallRFFIHelper { return currentCaller == null || currentCaller == RCaller.topLevel ? RNull.instance : currentCaller; } - public static Object R_getContextEnv(Object c) { - if (RFFIUtils.traceEnabled()) { - RFFIUtils.traceUpCall("getContextEnv", c); + @Override + public Object R_getContextEnv(Object c) { + if (tracer != null) { + tracer.R_getContextEnv(c); } RCaller rCaller = guaranteeInstanceOf(c, RCaller.class); if (rCaller == RCaller.topLevel) { @@ -1382,9 +1421,10 @@ public class CallRFFIHelper { } } - public static Object R_getContextFun(Object c) { - if (RFFIUtils.traceEnabled()) { - RFFIUtils.traceUpCall("getContextEnv", c); + @Override + public Object R_getContextFun(Object c) { + if (tracer != null) { + tracer.R_getContextFun(c); } RCaller rCaller = guaranteeInstanceOf(c, RCaller.class); if (rCaller == RCaller.topLevel) { @@ -1410,9 +1450,10 @@ public class CallRFFIHelper { } } - public static Object R_getContextCall(Object c) { - if (RFFIUtils.traceEnabled()) { - RFFIUtils.traceUpCall("getContextEnv", c); + @Override + public Object R_getContextCall(Object c) { + if (tracer != null) { + tracer.R_getContextCall(c); } RCaller rCaller = guaranteeInstanceOf(c, RCaller.class); if (rCaller == RCaller.topLevel) { @@ -1421,9 +1462,10 @@ public class CallRFFIHelper { return RContext.getRRuntimeASTAccess().getSyntaxCaller(rCaller); } - public static Object R_getContextSrcRef(Object c) { - if (RFFIUtils.traceEnabled()) { - RFFIUtils.traceUpCall("getContextSrcRef", c); + @Override + public Object R_getContextSrcRef(Object c) { + if (tracer != null) { + tracer.R_getContextSrcRef(c); } Object o = R_getContextFun(c); if (!(o instanceof RFunction)) { @@ -1438,94 +1480,133 @@ public class CallRFFIHelper { } - public static int R_insideBrowser() { + @Override + public int R_insideBrowser() { + if (tracer != null) { + tracer.R_insideBrowser(); + } return RContext.getInstance().stateInstrumentation.getBrowserState().inBrowser() ? 1 : 0; } - public static int R_isGlobal(Object c) { - if (RFFIUtils.traceEnabled()) { - RFFIUtils.traceUpCall("isGlobal", c); + @Override + public int R_isGlobal(Object c) { + if (tracer != null) { + tracer.R_isGlobal(c); } RCaller rCaller = guaranteeInstanceOf(c, RCaller.class); return rCaller == RCaller.topLevel ? 1 : 0; } - public static int R_isEqual(Object x, Object y) { - if (RFFIUtils.traceEnabled()) { - RFFIUtils.traceUpCall("isEqual", x, y); + @Override + public int R_isEqual(Object x, Object y) { + if (tracer != null) { + tracer.R_isEqual(x, y); } return x == y ? 1 : 0; } - public static Object Rf_classgets(Object x, Object y) { + @Override + public Object Rf_classgets(Object x, Object y) { + if (tracer != null) { + tracer.Rf_classgets(x, y); + } RAbstractVector vector = guaranteeInstanceOf(x, RAbstractVector.class); vector.setClassAttr(guaranteeInstanceOf(y, RStringVector.class)); return RNull.instance; } - public static RExternalPtr R_MakeExternalPtr(long addr, Object tag, Object prot) { - if (RFFIUtils.traceEnabled()) { - RFFIUtils.traceUpCall("R_MakeExternalPtr", addr, tag, prot); + @Override + public RExternalPtr R_MakeExternalPtr(long addr, Object tag, Object prot) { + if (tracer != null) { + tracer.R_MakeExternalPtr(addr, tag, prot); } return RDataFactory.createExternalPtr(new SymbolHandle(addr), tag, prot); } - public static long R_ExternalPtrAddr(Object x) { - if (RFFIUtils.traceEnabled()) { - RFFIUtils.traceUpCall("R_ExternalPtrAddr", x); + @Override + public long R_ExternalPtrAddr(Object x) { + if (tracer != null) { + tracer.R_ExternalPtrAddr(x); } RExternalPtr p = guaranteeInstanceOf(x, RExternalPtr.class); return p.getAddr().asAddress(); } - public static Object R_ExternalPtrTag(Object x) { - if (RFFIUtils.traceEnabled()) { - RFFIUtils.traceUpCall("R_ExternalPtrTag", x); + @Override + public Object R_ExternalPtrTag(Object x) { + if (tracer != null) { + tracer.R_ExternalPtrTag(x); } RExternalPtr p = guaranteeInstanceOf(x, RExternalPtr.class); return p.getTag(); } - public static Object R_ExternalPtrProt(Object x) { - if (RFFIUtils.traceEnabled()) { - RFFIUtils.traceUpCall("R_ExternalPtrProt", x); + @Override + public Object R_ExternalPtrProt(Object x) { + if (tracer != null) { + tracer.R_ExternalPtrProt(x); } RExternalPtr p = guaranteeInstanceOf(x, RExternalPtr.class); return p.getProt(); } - public static void R_SetExternalPtrAddr(Object x, long addr) { - if (RFFIUtils.traceEnabled()) { - RFFIUtils.traceUpCall("R_SetExternalPtrAddr", x); + @Override + public void R_SetExternalPtrAddr(Object x, long addr) { + if (tracer != null) { + tracer.R_SetExternalPtrAddr(x, addr); } RExternalPtr p = guaranteeInstanceOf(x, RExternalPtr.class); p.setAddr(new SymbolHandle(addr)); } - public static void R_SetExternalPtrTag(Object x, Object tag) { - if (RFFIUtils.traceEnabled()) { - RFFIUtils.traceUpCall("R_SetExternalPtrTag", x); + @Override + public void R_SetExternalPtrTag(Object x, Object tag) { + if (tracer != null) { + tracer.R_SetExternalPtrTag(x, tag); } RExternalPtr p = guaranteeInstanceOf(x, RExternalPtr.class); p.setTag(tag); } - public static void R_SetExternalPtrProt(Object x, Object prot) { - if (RFFIUtils.traceEnabled()) { - RFFIUtils.traceUpCall("R_ExternalPtrProt", x); + @Override + public void R_SetExternalPtrProt(Object x, Object prot) { + if (tracer != null) { + tracer.R_SetExternalPtrProt(x, prot); } RExternalPtr p = guaranteeInstanceOf(x, RExternalPtr.class); p.setProt(prot); } - public static REnvironment R_NewHashedEnv(REnvironment parent, String name, boolean hashed, int initialSize) { - if (RFFIUtils.traceEnabled()) { - RFFIUtils.traceUpCall("R_NewHashedEnv", parent, name, hashed, initialSize); + @Override + public REnvironment R_NewHashedEnv(REnvironment parent, String name, boolean hashed, int initialSize) { + if (tracer != null) { + tracer.R_NewHashedEnv(parent, name, hashed, initialSize); } REnvironment env = RDataFactory.createNewEnv(name, hashed, initialSize); RArguments.initializeEnclosingFrame(env.getFrame(), parent.getFrame()); return env; } + // Implementation specific support + + /** + * Called to possibly update the "complete" status on {@code x}. N.B. {@code x} may not be an + * object with a concrete {@code setComplete} method, e.g. see {@link #INTEGER(Object)}. + */ + public void setComplete(Object x, boolean complete) { + // only care about concrete vectors + if (x instanceof RVector) { + ((RVector<?>) x).setComplete(complete); + } + } + + /** + * Called when a {@link CharSXPWrapper} is expected and not found. + */ + public void logNotCharSXPWrapper(Object x) { + System.out.println("object " + x); + System.out.println("class " + x.getClass()); + } + } diff --git a/com.oracle.truffle.r.runtime.ffi/src/com/oracle/truffle/r/runtime/ffi/JavaUpCallsRFFIFactory.java b/com.oracle.truffle.r.runtime.ffi/src/com/oracle/truffle/r/runtime/ffi/JavaUpCallsRFFIFactory.java new file mode 100644 index 0000000000..d9666616f0 --- /dev/null +++ b/com.oracle.truffle.r.runtime.ffi/src/com/oracle/truffle/r/runtime/ffi/JavaUpCallsRFFIFactory.java @@ -0,0 +1,32 @@ +/* + * Copyright (c) 2014, 2016, Oracle and/or its affiliates. All rights reserved. + * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. + * + * This code is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License version 2 only, as + * published by the Free Software Foundation. + * + * This code is distributed in the hope that it will be useful, but WITHOUT + * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License + * version 2 for more details (a copy is included in the LICENSE file that + * accompanied this code). + * + * You should have received a copy of the GNU General Public License version + * 2 along with this work; if not, write to the Free Software Foundation, + * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA. + * + * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA + * or visit www.oracle.com if you need additional information or have any + * questions. + */ +package com.oracle.truffle.r.runtime.ffi; + +public class JavaUpCallsRFFIFactory extends UpCallsRFFIFactory { + + @Override + public UpCallsRFFI getUpcallsRFFI() { + return new JavaUpCallsRFFI(); + } + +} 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 0695d46b3a..77628a0b8d 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 @@ -29,7 +29,6 @@ import com.oracle.truffle.r.runtime.data.RMissing; import com.oracle.truffle.r.runtime.data.RNull; import com.oracle.truffle.r.runtime.data.RUnboundValue; import com.oracle.truffle.r.runtime.env.REnvironment; -import com.oracle.truffle.r.runtime.ffi.jni.CallRFFIHelper; public enum RFFIVariables { R_Home(REnvVars.rHome()), @@ -71,7 +70,7 @@ public enum RFFIVariables { R_dot_target(RDataFactory.createSymbol(".target")), R_SrcrefSymbol(RDataFactory.createSymbol("srcref")), R_SrcfileSymbol(RDataFactory.createSymbol("srcfile")), - R_NaString(CallRFFIHelper.createCharSXP(RRuntime.STRING_NA)), + R_NaString(CharSXPWrapper.create(RRuntime.STRING_NA)), R_NaN(Double.NaN), R_PosInf(Double.POSITIVE_INFINITY), R_NegInf(Double.NEGATIVE_INFINITY), diff --git a/com.oracle.truffle.r.runtime.ffi/src/com/oracle/truffle/r/runtime/ffi/jni/JNI_Call.java b/com.oracle.truffle.r.runtime.ffi/src/com/oracle/truffle/r/runtime/ffi/jni/JNI_Call.java index 8ea6fac033..2108c61447 100644 --- a/com.oracle.truffle.r.runtime.ffi/src/com/oracle/truffle/r/runtime/ffi/jni/JNI_Call.java +++ b/com.oracle.truffle.r.runtime.ffi/src/com/oracle/truffle/r/runtime/ffi/jni/JNI_Call.java @@ -36,6 +36,8 @@ import com.oracle.truffle.r.runtime.ffi.LibPaths; import com.oracle.truffle.r.runtime.ffi.NativeCallInfo; import com.oracle.truffle.r.runtime.ffi.RFFIUtils; import com.oracle.truffle.r.runtime.ffi.RFFIVariables; +import com.oracle.truffle.r.runtime.ffi.UpCallsRFFI; +import com.oracle.truffle.r.runtime.ffi.UpCallsRFFIFactory; /** * The only variety in the signatures for {@code .Call} is the number of arguments. GnuR supports a @@ -80,7 +82,7 @@ public class JNI_Call implements CallRFFI { traceDownCall("initialize"); } try { - initialize(RFFIVariables.values()); + initialize(UpCallsRFFIFactory.getInstance().getUpcallsRFFI(), RFFIVariables.values()); } finally { if (traceEnabled()) { traceDownCallReturn("initialize", null); @@ -122,7 +124,7 @@ public class JNI_Call implements CallRFFI { } } - private static native void initialize(RFFIVariables[] variables); + private static native void initialize(UpCallsRFFI upCallRFFI, RFFIVariables[] variables); private static native void nativeSetTempDir(String tempDir); diff --git a/com.oracle.truffle.r.runtime.ffi/src/com/oracle/truffle/r/runtime/ffi/jni/TraceUpCallsAdapter.java b/com.oracle.truffle.r.runtime.ffi/src/com/oracle/truffle/r/runtime/ffi/jni/TraceUpCallsAdapter.java new file mode 100644 index 0000000000..461863208e --- /dev/null +++ b/com.oracle.truffle.r.runtime.ffi/src/com/oracle/truffle/r/runtime/ffi/jni/TraceUpCallsAdapter.java @@ -0,0 +1,893 @@ +/* + * Copyright (c) 2016, 2016, Oracle and/or its affiliates. All rights reserved. + * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. + * + * This code is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License version 2 only, as + * published by the Free Software Foundation. + * + * This code is distributed in the hope that it will be useful, but WITHOUT + * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License + * version 2 for more details (a copy is included in the LICENSE file that + * accompanied this code). + * + * You should have received a copy of the GNU General Public License version + * 2 along with this work; if not, write to the Free Software Foundation, + * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA. + * + * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA + * or visit www.oracle.com if you need additional information or have any + * questions. + */ +package com.oracle.truffle.r.runtime.ffi.jni; + +import com.oracle.truffle.r.runtime.data.RDoubleVector; +import com.oracle.truffle.r.runtime.data.RExternalPtr; +import com.oracle.truffle.r.runtime.data.RIntVector; +import com.oracle.truffle.r.runtime.data.RLogicalVector; +import com.oracle.truffle.r.runtime.data.RStringVector; +import com.oracle.truffle.r.runtime.env.REnvironment; +import com.oracle.truffle.r.runtime.ffi.RFFIUtils; +import com.oracle.truffle.r.runtime.ffi.UpCallsRFFI; + +public class TraceUpCallsAdapter implements UpCallsRFFI { + @Override + public RIntVector Rf_ScalarInteger(int value) { + if (RFFIUtils.traceEnabled()) { + RFFIUtils.traceUpCall("Rf_ScalarInteger", value); + } + return null; + } + + @Override + public RLogicalVector Rf_ScalarLogical(int value) { + if (RFFIUtils.traceEnabled()) { + RFFIUtils.traceUpCall("Rf_ScalarLogical", value); + } + return null; + } + + @Override + public RDoubleVector Rf_ScalarDouble(double value) { + if (RFFIUtils.traceEnabled()) { + RFFIUtils.traceUpCall("Rf_ScalarDouble", value); + } + return null; + } + + @Override + public RStringVector Rf_ScalarString(Object value) { + if (RFFIUtils.traceEnabled()) { + RFFIUtils.traceUpCall("Rf_ScalarString", value); + } + return null; + } + + @Override + public int Rf_asInteger(Object x) { + if (RFFIUtils.traceEnabled()) { + RFFIUtils.traceUpCall("Rf_asInteger", x); + } + return 0; + } + + @Override + public double Rf_asReal(Object x) { + if (RFFIUtils.traceEnabled()) { + RFFIUtils.traceUpCall("Rf_asReal", x); + } + return 0; + } + + @Override + public int Rf_asLogical(Object x) { + if (RFFIUtils.traceEnabled()) { + RFFIUtils.traceUpCall("Rf_asLogical", x); + } + return 0; + } + + @Override + public Object Rf_asChar(Object x) { + if (RFFIUtils.traceEnabled()) { + RFFIUtils.traceUpCall("Rf_asChar", x); + } + return null; + } + + @Override + public Object Rf_mkCharLenCE(byte[] bytes, int encoding) { + if (RFFIUtils.traceEnabled()) { + RFFIUtils.traceUpCall("Rf_mkCharLenCE", bytes); + } + return null; + } + + @Override + public Object Rf_cons(Object car, Object cdr) { + if (RFFIUtils.traceEnabled()) { + RFFIUtils.traceUpCall("Rf_cons", car, cdr); + } + return null; + } + + @Override + public void Rf_defineVar(Object symbolArg, Object value, Object envArg) { + if (RFFIUtils.traceEnabled()) { + RFFIUtils.traceUpCall("Rf_defineVar", symbolArg, value, envArg); + } + } + + @Override + public Object R_do_MAKE_CLASS(String clazz) { + if (RFFIUtils.traceEnabled()) { + RFFIUtils.traceUpCall("R_do_MAKE_CLASS", clazz); + } + return null; + } + + @Override + public Object Rf_findVar(Object symbolArg, Object envArg) { + if (RFFIUtils.traceEnabled()) { + RFFIUtils.traceUpCall("Rf_findVar", symbolArg, envArg); + } + return null; + } + + @Override + public Object Rf_findVarInFrame(Object envArg, Object symbolArg) { + if (RFFIUtils.traceEnabled()) { + RFFIUtils.traceUpCall("Rf_findVarInFrame", envArg, symbolArg); + } + return null; + } + + @Override + public Object Rf_findVarInFrame3(Object envArg, Object symbolArg, int doGet) { + if (RFFIUtils.traceEnabled()) { + RFFIUtils.traceUpCall("Rf_findVarInFrame3", envArg, symbolArg); + } + return null; + } + + @Override + public Object Rf_getAttrib(Object obj, Object name) { + if (RFFIUtils.traceEnabled()) { + RFFIUtils.traceUpCall("Rf_getAttrib", obj, name); + } + return null; + } + + @Override + public void Rf_setAttrib(Object obj, Object name, Object val) { + if (RFFIUtils.traceEnabled()) { + RFFIUtils.traceUpCall("Rf_setAttrib", obj, name, val); + } + } + + @Override + public int Rf_inherits(Object x, String clazz) { + if (RFFIUtils.traceEnabled()) { + RFFIUtils.traceUpCall("Rf_inherits", x, clazz); + } + return 0; + } + + @Override + public Object Rf_install(String name) { + if (RFFIUtils.traceEnabled()) { + RFFIUtils.traceUpCall("Rf_install", name); + } + return null; + } + + @Override + public Object Rf_lengthgets(Object x, int newSize) { + if (RFFIUtils.traceEnabled()) { + RFFIUtils.traceUpCall("Rf_lengthgets", x, newSize); + } + return null; + } + + @Override + public int Rf_isString(Object x) { + if (RFFIUtils.traceEnabled()) { + RFFIUtils.traceUpCall("Rf_isString", x); + } + return 0; + } + + @Override + public int Rf_isNull(Object x) { + if (RFFIUtils.traceEnabled()) { + RFFIUtils.traceUpCall("Rf_isNull", x); + } + return 0; + } + + @Override + public Object Rf_PairToVectorList(Object x) { + if (RFFIUtils.traceEnabled()) { + RFFIUtils.traceUpCall("Rf_PairToVectorList", x); + } + return null; + } + + @Override + public void Rf_error(String msg) { + if (RFFIUtils.traceEnabled()) { + RFFIUtils.traceUpCall("Rf_error", msg); + } + } + + @Override + public void Rf_warning(String msg) { + if (RFFIUtils.traceEnabled()) { + RFFIUtils.traceUpCall("Rf_warning", msg); + } + } + + @Override + public void Rf_warningcall(Object call, String msg) { + if (RFFIUtils.traceEnabled()) { + RFFIUtils.traceUpCall("Rf_warningcall", call, msg); + } + } + + @Override + public Object Rf_allocateVector(int mode, int n) { + if (RFFIUtils.traceEnabled()) { + RFFIUtils.traceUpCall("Rf_allocateVector", mode, n); + } + return null; + } + + @Override + public Object Rf_allocateArray(int mode, Object dimsObj) { + if (RFFIUtils.traceEnabled()) { + RFFIUtils.traceUpCall("Rf_allocateArray", mode, dimsObj); + } + return null; + } + + @Override + public Object Rf_allocateMatrix(int mode, int nrow, int ncol) { + if (RFFIUtils.traceEnabled()) { + RFFIUtils.traceUpCall("Rf_allocateMatrix", mode, ncol, nrow); + } + return null; + } + + @Override + public int Rf_nrows(Object x) { + if (RFFIUtils.traceEnabled()) { + RFFIUtils.traceUpCall("Rf_nrows", x); + } + return 0; + } + + @Override + public int Rf_ncols(Object x) { + if (RFFIUtils.traceEnabled()) { + RFFIUtils.traceUpCall("Rf_ncols", x); + } + return 0; + } + + @Override + public int LENGTH(Object x) { + if (RFFIUtils.traceEnabled()) { + RFFIUtils.traceUpCall("LENGTH", x); + } + return 0; + } + + @Override + public void SET_STRING_ELT(Object x, int i, Object v) { + if (RFFIUtils.traceEnabled()) { + RFFIUtils.traceUpCall("SET_STRING_ELT", x, i, v); + } + } + + @Override + public void SET_VECTOR_ELT(Object x, int i, Object v) { + if (RFFIUtils.traceEnabled()) { + RFFIUtils.traceUpCall("SET_VECTOR_ELT", i, v); + } + } + + @Override + public byte[] RAW(Object x) { + if (RFFIUtils.traceEnabled()) { + RFFIUtils.traceUpCall("RAW", x); + } + return null; + } + + @Override + public byte[] LOGICAL(Object x) { + if (RFFIUtils.traceEnabled()) { + RFFIUtils.traceUpCall("LOGICAL", x); + } + return null; + } + + @Override + public int[] INTEGER(Object x) { + if (RFFIUtils.traceEnabled()) { + RFFIUtils.traceUpCall("INTEGER", x); + } + return null; + } + + @Override + public double[] REAL(Object x) { + if (RFFIUtils.traceEnabled()) { + RFFIUtils.traceUpCall("REAL", x); + } + return null; + } + + @Override + public Object STRING_ELT(Object x, int i) { + if (RFFIUtils.traceEnabled()) { + RFFIUtils.traceUpCall("STRING_ELT", x, i); + } + return null; + } + + @Override + public Object VECTOR_ELT(Object x, int i) { + if (RFFIUtils.traceEnabled()) { + RFFIUtils.traceUpCall("VECTOR_ELT", x, i); + } + return null; + } + + @Override + public int NAMED(Object x) { + if (RFFIUtils.traceEnabled()) { + RFFIUtils.traceUpCall("NAMED", x); + } + return 0; + } + + @Override + public Object SET_TYPEOF_FASTR(Object x, int v) { + if (RFFIUtils.traceEnabled()) { + RFFIUtils.traceUpCall("SET_TYPEOF_FASTR", x, v); + } + return null; + } + + @Override + public int TYPEOF(Object x) { + if (RFFIUtils.traceEnabled()) { + RFFIUtils.traceUpCall("TYPEOF", x); + } + return 0; + } + + @Override + public int OBJECT(Object x) { + if (RFFIUtils.traceEnabled()) { + RFFIUtils.traceUpCall("OBJECT", x); + } + return 0; + } + + @Override + public Object Rf_duplicate(Object x, int deep) { + if (RFFIUtils.traceEnabled()) { + RFFIUtils.traceUpCall("Rf_duplicate", x, deep); + } + return null; + } + + @Override + public int Rf_anyDuplicated(Object x, int fromLast) { + if (RFFIUtils.traceEnabled()) { + RFFIUtils.traceUpCall("Rf_anyDuplicated", x, fromLast); + } + return 0; + } + + @Override + public Object PRINTNAME(Object x) { + if (RFFIUtils.traceEnabled()) { + RFFIUtils.traceUpCall("PRINTNAME", x); + } + return null; + } + + @Override + public Object TAG(Object e) { + if (RFFIUtils.traceEnabled()) { + RFFIUtils.traceUpCall("TAG", e); + } + return null; + } + + @Override + public Object CAR(Object e) { + if (RFFIUtils.traceEnabled()) { + RFFIUtils.traceUpCall("CAR", e); + } + return null; + } + + @Override + public Object CDR(Object e) { + if (RFFIUtils.traceEnabled()) { + RFFIUtils.traceUpCall("CDR", e); + } + return null; + } + + @Override + public Object CADR(Object e) { + if (RFFIUtils.traceEnabled()) { + RFFIUtils.traceUpCall("CADR", e); + } + return null; + } + + @Override + public Object CADDR(Object e) { + if (RFFIUtils.traceEnabled()) { + RFFIUtils.traceUpCall("CADDR", e); + } + return null; + } + + @Override + public Object CDDR(Object e) { + if (RFFIUtils.traceEnabled()) { + RFFIUtils.traceUpCall("CDDR", e); + } + return null; + } + + @Override + public Object SET_TAG(Object x, Object y) { + if (RFFIUtils.traceEnabled()) { + RFFIUtils.traceUpCall("SET_TAG", x, y); + } + return null; + } + + @Override + public Object SETCAR(Object x, Object y) { + if (RFFIUtils.traceEnabled()) { + RFFIUtils.traceUpCall("SETCAR", x, y); + } + return null; + } + + @Override + public Object SETCDR(Object x, Object y) { + if (RFFIUtils.traceEnabled()) { + RFFIUtils.traceUpCall("SETCDR", x, y); + } + return null; + } + + @Override + public Object SETCADR(Object x, Object y) { + if (RFFIUtils.traceEnabled()) { + RFFIUtils.traceUpCall("SETCADR", x); + } + return null; + } + + @Override + public Object SYMVALUE(Object x) { + if (RFFIUtils.traceEnabled()) { + RFFIUtils.traceUpCall("SYMVALUE", x); + } + return null; + } + + @Override + public void SET_SYMVALUE(Object x, Object v) { + if (RFFIUtils.traceEnabled()) { + RFFIUtils.traceUpCall("SET_SYMVALUE", x, v); + } + } + + @Override + public int R_BindingIsLocked(Object sym, Object env) { + if (RFFIUtils.traceEnabled()) { + RFFIUtils.traceUpCall("R_BindingIsLocked", sym, env); + } + return 0; + } + + @Override + public Object R_FindNamespace(Object name) { + if (RFFIUtils.traceEnabled()) { + RFFIUtils.traceUpCall("R_FindNamespace", name); + } + return null; + } + + @Override + public Object Rf_eval(Object expr, Object env) { + if (RFFIUtils.traceEnabled()) { + RFFIUtils.traceUpCall("Rf_eval", expr, env); + } + return null; + } + + @Override + public Object Rf_findfun(Object symbolObj, Object envObj) { + if (RFFIUtils.traceEnabled()) { + RFFIUtils.traceUpCall("Rf_findfun", symbolObj, envObj); + } + return null; + } + + @Override + public Object Rf_GetOption1(Object tag) { + if (RFFIUtils.traceEnabled()) { + RFFIUtils.traceUpCall("Rf_GetOption1", tag); + } + return null; + } + + @Override + public void Rf_gsetVar(Object symbol, Object value, Object rho) { + if (RFFIUtils.traceEnabled()) { + RFFIUtils.traceUpCall("Rf_gsetVar", symbol, value, rho); + } + } + + @Override + public void DUPLICATE_ATTRIB(Object to, Object from) { + if (RFFIUtils.traceEnabled()) { + RFFIUtils.traceUpCall("DUPLICATE_ATTRIB", to, from); + } + } + + @Override + public int R_computeIdentical(Object x, Object y, int flags) { + if (RFFIUtils.traceEnabled()) { + RFFIUtils.traceUpCall("R_computeIdentical", x, y, flags); + } + return 0; + } + + @Override + public void Rf_copyListMatrix(Object s, Object t, int byrow) { + if (RFFIUtils.traceEnabled()) { + RFFIUtils.traceUpCall("Rf_copyListMatrix", t, byrow); + } + } + + @Override + public void Rf_copyMatrix(Object s, Object t, int byrow) { + if (RFFIUtils.traceEnabled()) { + RFFIUtils.traceUpCall("Rf_copyMatrix", t, byrow); + } + } + + @Override + public Object R_tryEval(Object expr, Object env, boolean silent) { + if (RFFIUtils.traceEnabled()) { + RFFIUtils.traceUpCall("R_tryEval", expr, env, silent); + } + return null; + } + + @Override + public Object R_ToplevelExec() { + if (RFFIUtils.traceEnabled()) { + RFFIUtils.traceUpCall("R_TopLevelExec"); + } + return null; + } + + @Override + public int RDEBUG(Object x) { + if (RFFIUtils.traceEnabled()) { + RFFIUtils.traceUpCall("RDEBUG", x); + } + return 0; + } + + @Override + public void SET_RDEBUG(Object x, int v) { + if (RFFIUtils.traceEnabled()) { + RFFIUtils.traceUpCall("SET_RDEBUG", x, v); + } + } + + @Override + public int RSTEP(Object x) { + if (RFFIUtils.traceEnabled()) { + RFFIUtils.traceUpCall("RSTEP", x); + } + return 0; + } + + @Override + public void SET_RSTEP(Object x, int v) { + if (RFFIUtils.traceEnabled()) { + RFFIUtils.traceUpCall("SET_RSTEP", x, v); + } + } + + @Override + public Object ENCLOS(Object x) { + if (RFFIUtils.traceEnabled()) { + RFFIUtils.traceUpCall("ENCLOS", x); + } + return null; + } + + @Override + public Object PRVALUE(Object x) { + if (RFFIUtils.traceEnabled()) { + RFFIUtils.traceUpCall("PRVALUE", x); + } + return null; + } + + @Override + public Object R_ParseVector(Object text, int n, Object srcFile) { + if (RFFIUtils.traceEnabled()) { + RFFIUtils.traceUpCall("R_ParseVector", text, n, srcFile); + } + return null; + } + + @Override + public Object R_lsInternal3(Object envArg, int allArg, int sortedArg) { + if (RFFIUtils.traceEnabled()) { + RFFIUtils.traceUpCall("R_lsInternal3", envArg, allArg, sortedArg); + } + return null; + } + + @Override + public String R_HomeDir() { + if (RFFIUtils.traceEnabled()) { + RFFIUtils.traceUpCall("R_HomeDir"); + } + return null; + } + + @Override + public void R_CleanUp(int sa, int status, int runlast) { + if (RFFIUtils.traceEnabled()) { + RFFIUtils.traceUpCall("R_Cleanup", sa, status, runlast); + } + } + + @Override + public Object R_GlobalContext() { + if (RFFIUtils.traceEnabled()) { + RFFIUtils.traceUpCall("R_GlobalContext"); + } + return null; + } + + @Override + public Object R_GlobalEnv() { + if (RFFIUtils.traceEnabled()) { + RFFIUtils.traceUpCall("R_GlobalEnv"); + } + return null; + } + + @Override + public Object R_BaseEnv() { + if (RFFIUtils.traceEnabled()) { + RFFIUtils.traceUpCall("R_BaseEnv"); + } + return null; + } + + @Override + public Object R_BaseNamespace() { + if (RFFIUtils.traceEnabled()) { + RFFIUtils.traceUpCall("R_BaseNamespace"); + } + return null; + } + + @Override + public Object R_NamespaceRegistry() { + if (RFFIUtils.traceEnabled()) { + RFFIUtils.traceUpCall("R_NamespaceRegistry"); + } + return null; + } + + @Override + public int isInteractive() { + if (RFFIUtils.traceEnabled()) { + RFFIUtils.traceUpCall("isInteractive"); + } + return 0; + } + + @Override + public int isS4Object(Object x) { + if (RFFIUtils.traceEnabled()) { + RFFIUtils.traceUpCall("isS4Object"); + } + return 0; + } + + @Override + public void Rprintf(String message) { + if (RFFIUtils.traceEnabled()) { + RFFIUtils.traceUpCall("Rprintf", message); + } + } + + @Override + public void GetRNGstate() { + if (RFFIUtils.traceEnabled()) { + RFFIUtils.traceUpCall("GetRNGstate"); + } + } + + @Override + public void PutRNGstate() { + if (RFFIUtils.traceEnabled()) { + RFFIUtils.traceUpCall("PutRNGstate"); + } + } + + @Override + public double unif_rand() { + if (RFFIUtils.traceEnabled()) { + RFFIUtils.traceUpCall("unif_rand"); + } + return 0; + } + + @Override + public Object R_getGlobalFunctionContext() { + if (RFFIUtils.traceEnabled()) { + RFFIUtils.traceUpCall("R_getGlobalFunctionContext"); + } + return null; + } + + @Override + public Object R_getParentFunctionContext(Object c) { + if (RFFIUtils.traceEnabled()) { + RFFIUtils.traceUpCall("R_getParentFunctionContext"); + } + return null; + } + + @Override + public Object R_getContextEnv(Object c) { + if (RFFIUtils.traceEnabled()) { + RFFIUtils.traceUpCall("R_getContextEnv", c); + } + return null; + } + + @Override + public Object R_getContextFun(Object c) { + if (RFFIUtils.traceEnabled()) { + RFFIUtils.traceUpCall("R_getContextFun", c); + } + return null; + } + + @Override + public Object R_getContextCall(Object c) { + if (RFFIUtils.traceEnabled()) { + RFFIUtils.traceUpCall("R_getContextCall", c); + } + return null; + } + + @Override + public Object R_getContextSrcRef(Object c) { + if (RFFIUtils.traceEnabled()) { + RFFIUtils.traceUpCall("R_getContextSrcRef", c); + } + return null; + } + + @Override + public int R_insideBrowser() { + if (RFFIUtils.traceEnabled()) { + RFFIUtils.traceUpCall("R_insideBrowser"); + } + return 0; + } + + @Override + public int R_isGlobal(Object c) { + if (RFFIUtils.traceEnabled()) { + RFFIUtils.traceUpCall("R_isGlobal", c); + } + return 0; + } + + @Override + public int R_isEqual(Object x, Object y) { + if (RFFIUtils.traceEnabled()) { + RFFIUtils.traceUpCall("isEqual", x, y); + } + return 0; + } + + @Override + public Object Rf_classgets(Object x, Object y) { + if (RFFIUtils.traceEnabled()) { + RFFIUtils.traceUpCall("Rf_classgets", x, y); + } + return null; + } + + @Override + public RExternalPtr R_MakeExternalPtr(long addr, Object tag, Object prot) { + if (RFFIUtils.traceEnabled()) { + RFFIUtils.traceUpCall("R_MakeExternalPtr", addr, tag, prot); + } + return null; + } + + @Override + public long R_ExternalPtrAddr(Object x) { + if (RFFIUtils.traceEnabled()) { + RFFIUtils.traceUpCall("R_ExternalPtrAddr", x); + } + return 0; + } + + @Override + public Object R_ExternalPtrTag(Object x) { + if (RFFIUtils.traceEnabled()) { + RFFIUtils.traceUpCall("R_ExternalPtrTag", x); + } + return null; + } + + @Override + public Object R_ExternalPtrProt(Object x) { + if (RFFIUtils.traceEnabled()) { + RFFIUtils.traceUpCall("R_ExternalPtrProt", x); + } + return null; + } + + @Override + public void R_SetExternalPtrAddr(Object x, long addr) { + if (RFFIUtils.traceEnabled()) { + RFFIUtils.traceUpCall("R_SetExternalPtrAddr", x); + } + } + + @Override + public void R_SetExternalPtrTag(Object x, Object tag) { + if (RFFIUtils.traceEnabled()) { + RFFIUtils.traceUpCall("R_SetExternalPtrTag", x); + } + } + + @Override + public void R_SetExternalPtrProt(Object x, Object prot) { + if (RFFIUtils.traceEnabled()) { + RFFIUtils.traceUpCall("R_ExternalPtrProt", x); + } + } + + @Override + public REnvironment R_NewHashedEnv(REnvironment parent, String name, boolean hashed, int initialSize) { + if (RFFIUtils.traceEnabled()) { + RFFIUtils.traceUpCall("R_NewHashedEnv", parent, name, hashed, initialSize); + } + return null; + } +} diff --git a/com.oracle.truffle.r.runtime/src/com/oracle/truffle/r/runtime/ffi/CharSXPWrapper.java b/com.oracle.truffle.r.runtime/src/com/oracle/truffle/r/runtime/ffi/CharSXPWrapper.java new file mode 100644 index 0000000000..f7e83255eb --- /dev/null +++ b/com.oracle.truffle.r.runtime/src/com/oracle/truffle/r/runtime/ffi/CharSXPWrapper.java @@ -0,0 +1,55 @@ +/* + * Copyright (c) 2014, 2016, Oracle and/or its affiliates. All rights reserved. + * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. + * + * This code is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License version 2 only, as + * published by the Free Software Foundation. + * + * This code is distributed in the hope that it will be useful, but WITHOUT + * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License + * version 2 for more details (a copy is included in the LICENSE file that + * accompanied this code). + * + * You should have received a copy of the GNU General Public License version + * 2 along with this work; if not, write to the Free Software Foundation, + * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA. + * + * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA + * or visit www.oracle.com if you need additional information or have any + * questions. + */ +package com.oracle.truffle.r.runtime.ffi; + +/** + * Internally GNU R distinguishes "strings" and "vectors of strings" using the {@code CHARSXP} and + * {@code STRSXP} types, respectively. Although this difference is invisible at the R level, it + * manifests itself in the R FFI as several functions traffic in the {@code CHARSXP} type. Since + * FastR already uses {@code String} to denote a length-1 string vector, it cannot be used to + * represent a {@code CHARSXP}, so this class exists to do so. + * + * N.B. Use limited to RFFI implementations. + * + */ +public final class CharSXPWrapper { + private final String contents; + + private CharSXPWrapper(String contents) { + this.contents = contents; + } + + public String getContents() { + return contents; + } + + @Override + public String toString() { + return "CHARSXP(" + contents + ")"; + } + + public static Object create(String contents) { + return new CharSXPWrapper(contents); + } + +} diff --git a/com.oracle.truffle.r.runtime/src/com/oracle/truffle/r/runtime/ffi/ParseResult.java b/com.oracle.truffle.r.runtime/src/com/oracle/truffle/r/runtime/ffi/ParseResult.java new file mode 100644 index 0000000000..d4c71e01bd --- /dev/null +++ b/com.oracle.truffle.r.runtime/src/com/oracle/truffle/r/runtime/ffi/ParseResult.java @@ -0,0 +1,44 @@ +/* + * Copyright (c) 2014, 2016, Oracle and/or its affiliates. All rights reserved. + * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. + * + * This code is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License version 2 only, as + * published by the Free Software Foundation. + * + * This code is distributed in the hope that it will be useful, but WITHOUT + * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License + * version 2 for more details (a copy is included in the LICENSE file that + * accompanied this code). + * + * You should have received a copy of the GNU General Public License version + * 2 along with this work; if not, write to the Free Software Foundation, + * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA. + * + * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA + * or visit www.oracle.com if you need additional information or have any + * questions. + */ +package com.oracle.truffle.r.runtime.ffi; + +/** + * Used in implementation of {@link UpCallsRFFI#R_ParseVector(Object, int, Object)}. + */ +public class ParseResult { + public enum ParseStatus { + PARSE_NULL, + PARSE_OK, + PARSE_INCOMPLETE, + PARSE_ERROR, + PARSE_EOF + } + + @SuppressWarnings("unused") private final int parseStatus; + @SuppressWarnings("unused") private final Object expr; + + ParseResult(int parseStatus, Object expr) { + this.parseStatus = parseStatus; + this.expr = expr; + } +} diff --git a/com.oracle.truffle.r.runtime/src/com/oracle/truffle/r/runtime/ffi/RFFI.java b/com.oracle.truffle.r.runtime/src/com/oracle/truffle/r/runtime/ffi/RFFI.java index 99378fa1af..ccc6224ba1 100644 --- a/com.oracle.truffle.r.runtime/src/com/oracle/truffle/r/runtime/ffi/RFFI.java +++ b/com.oracle.truffle.r.runtime/src/com/oracle/truffle/r/runtime/ffi/RFFI.java @@ -42,6 +42,9 @@ package com.oracle.truffle.r.runtime.ffi; * <li>{@link DLLRFFI}: interface to dll functions, e.g., {@code dlopen}</li> * <li>{@link REmbedRFFI}: interface to embedded support</li> * <li>{@link MiscRFFI}: interface to miscellaneous native functions</li> + * <li>{@link UpCallsRFFI}: interface that defines the set of upcalls from native code (resulting + * from {@link CallRFFI}). There is no public access to this interface as it should never be called + * from FastR Java code and is always implemented by a specific FFI factory. * </ul> * * These interfaces may be implemented by one or more providers, specified either when the FastR diff --git a/com.oracle.truffle.r.runtime/src/com/oracle/truffle/r/runtime/ffi/UpCallsRFFI.java b/com.oracle.truffle.r.runtime/src/com/oracle/truffle/r/runtime/ffi/UpCallsRFFI.java new file mode 100644 index 0000000000..d643ba908f --- /dev/null +++ b/com.oracle.truffle.r.runtime/src/com/oracle/truffle/r/runtime/ffi/UpCallsRFFI.java @@ -0,0 +1,279 @@ +/* + * Copyright (c) 2014, 2016, Oracle and/or its affiliates. All rights reserved. + * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. + * + * This code is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License version 2 only, as + * published by the Free Software Foundation. + * + * This code is distributed in the hope that it will be useful, but WITHOUT + * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License + * version 2 for more details (a copy is included in the LICENSE file that + * accompanied this code). + * + * You should have received a copy of the GNU General Public License version + * 2 along with this work; if not, write to the Free Software Foundation, + * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA. + * + * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA + * or visit www.oracle.com if you need additional information or have any + * questions. + */ +package com.oracle.truffle.r.runtime.ffi; + +import com.oracle.truffle.r.runtime.data.RDoubleVector; +import com.oracle.truffle.r.runtime.data.RExternalPtr; +import com.oracle.truffle.r.runtime.data.RIntVector; +import com.oracle.truffle.r.runtime.data.RLogicalVector; +import com.oracle.truffle.r.runtime.data.RStringVector; +import com.oracle.truffle.r.runtime.env.REnvironment; + +/** + * This class defines methods that match the functionality of the macro/function definitions in the + * R header files, e.g. {@code Rinternals.h} that are used by C/C++ code to call into the R + * implementation. For ease of identification, we use method names that match the names in the R + * header files. These methods should never be called from normal FastR code. + * + * The set is incomplete; these are the functions that have been found to be used to at this time of + * writing. From the GNU R perspective all {@code Object} parameters are {@code SEXP} instances. + * Some of the functions are typed with a specific return type but, again, this is a {@code SEXP} in + * GNU R terms. The native side does not require a specific Java type. + * + */ +public interface UpCallsRFFI { + + // Checkstyle: stop method name check + + RIntVector Rf_ScalarInteger(int value); + + RLogicalVector Rf_ScalarLogical(int value); + + RDoubleVector Rf_ScalarDouble(double value); + + RStringVector Rf_ScalarString(Object value); + + int Rf_asInteger(Object x); + + double Rf_asReal(Object x); + + int Rf_asLogical(Object x); + + Object Rf_asChar(Object x); + + Object Rf_mkCharLenCE(byte[] bytes, int encoding); + + Object Rf_cons(Object car, Object cdr); + + void Rf_defineVar(Object symbolArg, Object value, Object envArg); + + Object R_do_MAKE_CLASS(String clazz); + + /** + * WARNING: argument order reversed from Rf_findVarInFrame! + */ + Object Rf_findVar(Object symbolArg, Object envArg); + + Object Rf_findVarInFrame(Object envArg, Object symbolArg); + + Object Rf_findVarInFrame3(Object envArg, Object symbolArg, int doGet); + + Object Rf_getAttrib(Object obj, Object name); + + void Rf_setAttrib(Object obj, Object name, Object val); + + int Rf_inherits(Object x, String clazz); + + Object Rf_install(String name); + + Object Rf_lengthgets(Object x, int newSize); + + int Rf_isString(Object x); + + int Rf_isNull(Object x); + + Object Rf_PairToVectorList(Object x); + + void Rf_error(String msg); + + void Rf_warning(String msg); + + void Rf_warningcall(Object call, String msg); + + Object Rf_allocateVector(int mode, int n); + + Object Rf_allocateArray(int mode, Object dimsObj); + + Object Rf_allocateMatrix(int mode, int nrow, int ncol); + + int Rf_nrows(Object x); + + int Rf_ncols(Object x); + + int LENGTH(Object x); + + void SET_STRING_ELT(Object x, int i, Object v); + + void SET_VECTOR_ELT(Object x, int i, Object v); + + byte[] RAW(Object x); + + byte[] LOGICAL(Object x); + + int[] INTEGER(Object x); + + double[] REAL(Object x); + + Object STRING_ELT(Object x, int i); + + Object VECTOR_ELT(Object x, int i); + + int NAMED(Object x); + + Object SET_TYPEOF_FASTR(Object x, int v); + + int TYPEOF(Object x); + + int OBJECT(Object x); + + Object Rf_duplicate(Object x, int deep); + + int Rf_anyDuplicated(Object x, int fromLast); + + Object PRINTNAME(Object x); + + Object TAG(Object e); + + Object CAR(Object e); + + Object CDR(Object e); + + Object CADR(Object e); + + Object CADDR(Object e); + + Object CDDR(Object e); + + Object SET_TAG(Object x, Object y); + + Object SETCAR(Object x, Object y); + + Object SETCDR(Object x, Object y); + + Object SETCADR(Object x, Object y); + + Object SYMVALUE(Object x); + + void SET_SYMVALUE(Object x, Object v); + + int R_BindingIsLocked(Object sym, Object env); + + Object R_FindNamespace(Object name); + + Object Rf_eval(Object expr, Object env); + + Object Rf_findfun(Object symbolObj, Object envObj); + + Object Rf_GetOption1(Object tag); + + void Rf_gsetVar(Object symbol, Object value, Object rho); + + void DUPLICATE_ATTRIB(Object to, Object from); + + int R_computeIdentical(Object x, Object y, int flags); + + void Rf_copyListMatrix(Object s, Object t, int byrow); + + void Rf_copyMatrix(Object s, Object t, int byrow); + + Object R_tryEval(Object expr, Object env, boolean silent); + + Object R_ToplevelExec(); + + int RDEBUG(Object x); + + void SET_RDEBUG(Object x, int v); + + int RSTEP(Object x); + + void SET_RSTEP(Object x, int v); + + Object ENCLOS(Object x); + + Object PRVALUE(Object x); + + Object R_ParseVector(Object text, int n, Object srcFile); + + Object R_lsInternal3(Object envArg, int allArg, int sortedArg); + + String R_HomeDir(); + + int isInteractive(); + + int isS4Object(Object x); + + void Rprintf(String message); + + void GetRNGstate(); + + void PutRNGstate(); + + double unif_rand(); + + Object Rf_classgets(Object x, Object y); + + RExternalPtr R_MakeExternalPtr(long addr, Object tag, Object prot); + + long R_ExternalPtrAddr(Object x); + + Object R_ExternalPtrTag(Object x); + + Object R_ExternalPtrProt(Object x); + + void R_SetExternalPtrAddr(Object x, long addr); + + void R_SetExternalPtrTag(Object x, Object tag); + + void R_SetExternalPtrProt(Object x, Object prot); + + void R_CleanUp(int sa, int status, int runlast); + + REnvironment R_NewHashedEnv(REnvironment parent, String name, boolean hashed, int initialSize); + + /* + * The following functions are global variables in the standard R FFI. However, owing to the + * support for virtual R sessions (see .fastr.context) in FastR they are remapped as functions. + */ + Object R_GlobalContext(); + + Object R_GlobalEnv(); + + Object R_BaseEnv(); + + Object R_BaseNamespace(); + + Object R_NamespaceRegistry(); + + /* + * The following functions are FastR extensions to support RStudio + */ + + Object R_getGlobalFunctionContext(); + + Object R_getParentFunctionContext(Object c); + + Object R_getContextEnv(Object c); + + Object R_getContextFun(Object c); + + Object R_getContextCall(Object c); + + Object R_getContextSrcRef(Object c); + + int R_insideBrowser(); + + int R_isGlobal(Object c); + + int R_isEqual(Object x, Object y); + +} diff --git a/com.oracle.truffle.r.runtime/src/com/oracle/truffle/r/runtime/ffi/UpCallsRFFIFactory.java b/com.oracle.truffle.r.runtime/src/com/oracle/truffle/r/runtime/ffi/UpCallsRFFIFactory.java new file mode 100644 index 0000000000..ad90095e5d --- /dev/null +++ b/com.oracle.truffle.r.runtime/src/com/oracle/truffle/r/runtime/ffi/UpCallsRFFIFactory.java @@ -0,0 +1,44 @@ +/* + * Copyright (c) 2016, 2016, Oracle and/or its affiliates. All rights reserved. + * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. + * + * This code is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License version 2 only, as + * published by the Free Software Foundation. + * + * This code is distributed in the hope that it will be useful, but WITHOUT + * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License + * version 2 for more details (a copy is included in the LICENSE file that + * accompanied this code). + * + * You should have received a copy of the GNU General Public License version + * 2 along with this work; if not, write to the Free Software Foundation, + * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA. + * + * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA + * or visit www.oracle.com if you need additional information or have any + * questions. + */ +package com.oracle.truffle.r.runtime.ffi; + +public abstract class UpCallsRFFIFactory { + static { + final String prop = System.getProperty("fastr.upcalls.factory.class", "com.oracle.truffle.r.runtime.ffi.JavaUpCallsRFFIFactory"); + try { + theInstance = (UpCallsRFFIFactory) Class.forName(prop).newInstance(); + } catch (Exception ex) { + // CheckStyle: stop system..print check + System.err.println("Failed to instantiate class: " + prop); + } + } + + private static UpCallsRFFIFactory theInstance; + + public static UpCallsRFFIFactory getInstance() { + return theInstance; + } + + public abstract UpCallsRFFI getUpcallsRFFI(); + +} -- GitLab