Home | History | Annotate | Download | only in jni
      1 /*
      2  * Copyright (C) 2011-2012 The Android Open Source Project
      3  *
      4  * Licensed under the Apache License, Version 2.0 (the "License");
      5  * you may not use this file except in compliance with the License.
      6  * You may obtain a copy of the License at
      7  *
      8  *      http://www.apache.org/licenses/LICENSE-2.0
      9  *
     10  * Unless required by applicable law or agreed to in writing, software
     11  * distributed under the License is distributed on an "AS IS" BASIS,
     12  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
     13  * See the License for the specific language governing permissions and
     14  * limitations under the License.
     15  */
     16 
     17 #define LOG_TAG "RenderScript_jni"
     18 
     19 #include <stdlib.h>
     20 #include <stdio.h>
     21 #include <fcntl.h>
     22 #include <unistd.h>
     23 #include <math.h>
     24 #include <utils/misc.h>
     25 #include <inttypes.h>
     26 
     27 #include <androidfw/Asset.h>
     28 #include <androidfw/AssetManager.h>
     29 #include <androidfw/ResourceTypes.h>
     30 
     31 #include "jni.h"
     32 #include "JNIHelp.h"
     33 #include "android_runtime/AndroidRuntime.h"
     34 #include "android_runtime/android_view_Surface.h"
     35 #include "android_runtime/android_util_AssetManager.h"
     36 #include "android/graphics/GraphicsJNI.h"
     37 #include "android/native_window.h"
     38 #include "android/native_window_jni.h"
     39 
     40 #include <rsEnv.h>
     41 #include <rsApiStubs.h>
     42 #include <gui/Surface.h>
     43 #include <gui/GLConsumer.h>
     44 #include <android_runtime/android_graphics_SurfaceTexture.h>
     45 
     46 //#define LOG_API ALOGE
     47 static constexpr bool kLogApi = false;
     48 
     49 using namespace android;
     50 
     51 #define PER_ARRAY_TYPE(flag, fnc, readonly, ...) {                                      \
     52     jint len = 0;                                                                       \
     53     void *ptr = nullptr;                                                                \
     54     void *srcPtr = nullptr;                                                             \
     55     size_t typeBytes = 0;                                                               \
     56     jint relFlag = 0;                                                                   \
     57     if (readonly) {                                                                     \
     58         /* The on-release mode should only be JNI_ABORT for read-only accesses. */      \
     59         /* readonly = true, also indicates we are copying to the allocation   . */      \
     60         relFlag = JNI_ABORT;                                                            \
     61     }                                                                                   \
     62     switch(dataType) {                                                                  \
     63     case RS_TYPE_FLOAT_32:                                                              \
     64         len = _env->GetArrayLength((jfloatArray)data);                                  \
     65         ptr = _env->GetFloatArrayElements((jfloatArray)data, flag);                     \
     66         if (ptr == nullptr) {                                                           \
     67             ALOGE("Failed to get Java array elements.");                                \
     68             return;                                                                     \
     69         }                                                                               \
     70         typeBytes = 4;                                                                  \
     71         if (usePadding) {                                                               \
     72             srcPtr = ptr;                                                               \
     73             len = len / 3 * 4;                                                          \
     74             if (count == 0) {                                                           \
     75                 count = len / 4;                                                        \
     76             }                                                                           \
     77             ptr = malloc (len * typeBytes);                                             \
     78             if (readonly) {                                                             \
     79                 copyWithPadding(ptr, srcPtr, mSize, count);                             \
     80                 fnc(__VA_ARGS__);                                                       \
     81             } else {                                                                    \
     82                 fnc(__VA_ARGS__);                                                       \
     83                 copyWithUnPadding(srcPtr, ptr, mSize, count);                           \
     84             }                                                                           \
     85             free(ptr);                                                                  \
     86             ptr = srcPtr;                                                               \
     87         } else {                                                                        \
     88             fnc(__VA_ARGS__);                                                           \
     89         }                                                                               \
     90         _env->ReleaseFloatArrayElements((jfloatArray)data, (jfloat *)ptr, relFlag);     \
     91         return;                                                                         \
     92     case RS_TYPE_FLOAT_64:                                                              \
     93         len = _env->GetArrayLength((jdoubleArray)data);                                 \
     94         ptr = _env->GetDoubleArrayElements((jdoubleArray)data, flag);                   \
     95         if (ptr == nullptr) {                                                           \
     96             ALOGE("Failed to get Java array elements.");                                \
     97             return;                                                                     \
     98         }                                                                               \
     99         typeBytes = 8;                                                                  \
    100         if (usePadding) {                                                               \
    101             srcPtr = ptr;                                                               \
    102             len = len / 3 * 4;                                                          \
    103             if (count == 0) {                                                           \
    104                 count = len / 4;                                                        \
    105             }                                                                           \
    106             ptr = malloc (len * typeBytes);                                             \
    107             if (readonly) {                                                             \
    108                 copyWithPadding(ptr, srcPtr, mSize, count);                             \
    109                 fnc(__VA_ARGS__);                                                       \
    110             } else {                                                                    \
    111                 fnc(__VA_ARGS__);                                                       \
    112                 copyWithUnPadding(srcPtr, ptr, mSize, count);                           \
    113             }                                                                           \
    114             free(ptr);                                                                  \
    115             ptr = srcPtr;                                                               \
    116         } else {                                                                        \
    117             fnc(__VA_ARGS__);                                                           \
    118         }                                                                               \
    119         _env->ReleaseDoubleArrayElements((jdoubleArray)data, (jdouble *)ptr, relFlag);  \
    120         return;                                                                         \
    121     case RS_TYPE_SIGNED_8:                                                              \
    122     case RS_TYPE_UNSIGNED_8:                                                            \
    123         len = _env->GetArrayLength((jbyteArray)data);                                   \
    124         ptr = _env->GetByteArrayElements((jbyteArray)data, flag);                       \
    125         if (ptr == nullptr) {                                                           \
    126             ALOGE("Failed to get Java array elements.");                                \
    127             return;                                                                     \
    128         }                                                                               \
    129         typeBytes = 1;                                                                  \
    130         if (usePadding) {                                                               \
    131             srcPtr = ptr;                                                               \
    132             len = len / 3 * 4;                                                          \
    133             if (count == 0) {                                                           \
    134                 count = len / 4;                                                        \
    135             }                                                                           \
    136             ptr = malloc (len * typeBytes);                                             \
    137             if (readonly) {                                                             \
    138                 copyWithPadding(ptr, srcPtr, mSize, count);                             \
    139                 fnc(__VA_ARGS__);                                                       \
    140             } else {                                                                    \
    141                 fnc(__VA_ARGS__);                                                       \
    142                 copyWithUnPadding(srcPtr, ptr, mSize, count);                           \
    143             }                                                                           \
    144             free(ptr);                                                                  \
    145             ptr = srcPtr;                                                               \
    146         } else {                                                                        \
    147             fnc(__VA_ARGS__);                                                           \
    148         }                                                                               \
    149         _env->ReleaseByteArrayElements((jbyteArray)data, (jbyte*)ptr, relFlag);         \
    150         return;                                                                         \
    151     case RS_TYPE_SIGNED_16:                                                             \
    152     case RS_TYPE_UNSIGNED_16:                                                           \
    153     case RS_TYPE_FLOAT_16:                                                              \
    154         len = _env->GetArrayLength((jshortArray)data);                                  \
    155         ptr = _env->GetShortArrayElements((jshortArray)data, flag);                     \
    156         if (ptr == nullptr) {                                                           \
    157             ALOGE("Failed to get Java array elements.");                                \
    158             return;                                                                     \
    159         }                                                                               \
    160         typeBytes = 2;                                                                  \
    161         if (usePadding) {                                                               \
    162             srcPtr = ptr;                                                               \
    163             len = len / 3 * 4;                                                          \
    164             if (count == 0) {                                                           \
    165                 count = len / 4;                                                        \
    166             }                                                                           \
    167             ptr = malloc (len * typeBytes);                                             \
    168             if (readonly) {                                                             \
    169                 copyWithPadding(ptr, srcPtr, mSize, count);                             \
    170                 fnc(__VA_ARGS__);                                                       \
    171             } else {                                                                    \
    172                 fnc(__VA_ARGS__);                                                       \
    173                 copyWithUnPadding(srcPtr, ptr, mSize, count);                           \
    174             }                                                                           \
    175             free(ptr);                                                                  \
    176             ptr = srcPtr;                                                               \
    177         } else {                                                                        \
    178             fnc(__VA_ARGS__);                                                           \
    179         }                                                                               \
    180         _env->ReleaseShortArrayElements((jshortArray)data, (jshort *)ptr, relFlag);     \
    181         return;                                                                         \
    182     case RS_TYPE_SIGNED_32:                                                             \
    183     case RS_TYPE_UNSIGNED_32:                                                           \
    184         len = _env->GetArrayLength((jintArray)data);                                    \
    185         ptr = _env->GetIntArrayElements((jintArray)data, flag);                         \
    186         if (ptr == nullptr) {                                                           \
    187             ALOGE("Failed to get Java array elements.");                                \
    188             return;                                                                     \
    189         }                                                                               \
    190         typeBytes = 4;                                                                  \
    191         if (usePadding) {                                                               \
    192             srcPtr = ptr;                                                               \
    193             len = len / 3 * 4;                                                          \
    194             if (count == 0) {                                                           \
    195                 count = len / 4;                                                        \
    196             }                                                                           \
    197             ptr = malloc (len * typeBytes);                                             \
    198             if (readonly) {                                                             \
    199                 copyWithPadding(ptr, srcPtr, mSize, count);                             \
    200                 fnc(__VA_ARGS__);                                                       \
    201             } else {                                                                    \
    202                 fnc(__VA_ARGS__);                                                       \
    203                 copyWithUnPadding(srcPtr, ptr, mSize, count);                           \
    204             }                                                                           \
    205             free(ptr);                                                                  \
    206             ptr = srcPtr;                                                               \
    207         } else {                                                                        \
    208             fnc(__VA_ARGS__);                                                           \
    209         }                                                                               \
    210         _env->ReleaseIntArrayElements((jintArray)data, (jint *)ptr, relFlag);           \
    211         return;                                                                         \
    212     case RS_TYPE_SIGNED_64:                                                             \
    213     case RS_TYPE_UNSIGNED_64:                                                           \
    214         len = _env->GetArrayLength((jlongArray)data);                                   \
    215         ptr = _env->GetLongArrayElements((jlongArray)data, flag);                       \
    216         if (ptr == nullptr) {                                                           \
    217             ALOGE("Failed to get Java array elements.");                                \
    218             return;                                                                     \
    219         }                                                                               \
    220         typeBytes = 8;                                                                  \
    221         if (usePadding) {                                                               \
    222             srcPtr = ptr;                                                               \
    223             len = len / 3 * 4;                                                          \
    224             if (count == 0) {                                                           \
    225                 count = len / 4;                                                        \
    226             }                                                                           \
    227             ptr = malloc (len * typeBytes);                                             \
    228             if (readonly) {                                                             \
    229                 copyWithPadding(ptr, srcPtr, mSize, count);                             \
    230                 fnc(__VA_ARGS__);                                                       \
    231             } else {                                                                    \
    232                 fnc(__VA_ARGS__);                                                       \
    233                 copyWithUnPadding(srcPtr, ptr, mSize, count);                           \
    234             }                                                                           \
    235             free(ptr);                                                                  \
    236             ptr = srcPtr;                                                               \
    237         } else {                                                                        \
    238             fnc(__VA_ARGS__);                                                           \
    239         }                                                                               \
    240         _env->ReleaseLongArrayElements((jlongArray)data, (jlong *)ptr, relFlag);        \
    241         return;                                                                         \
    242     default:                                                                            \
    243         break;                                                                          \
    244     }                                                                                   \
    245     UNUSED(len, ptr, srcPtr, typeBytes, relFlag);                                       \
    246 }
    247 
    248 
    249 class AutoJavaStringToUTF8 {
    250 public:
    251     AutoJavaStringToUTF8(JNIEnv* env, jstring str) : fEnv(env), fJStr(str) {
    252         fCStr = env->GetStringUTFChars(str, nullptr);
    253         fLength = env->GetStringUTFLength(str);
    254     }
    255     ~AutoJavaStringToUTF8() {
    256         fEnv->ReleaseStringUTFChars(fJStr, fCStr);
    257     }
    258     const char* c_str() const { return fCStr; }
    259     jsize length() const { return fLength; }
    260 
    261 private:
    262     JNIEnv*     fEnv;
    263     jstring     fJStr;
    264     const char* fCStr;
    265     jsize       fLength;
    266 };
    267 
    268 class AutoJavaStringArrayToUTF8 {
    269 public:
    270     AutoJavaStringArrayToUTF8(JNIEnv* env, jobjectArray strings, jsize stringsLength)
    271     : mEnv(env), mStrings(strings), mStringsLength(stringsLength) {
    272         mCStrings = nullptr;
    273         mSizeArray = nullptr;
    274         if (stringsLength > 0) {
    275             mCStrings = (const char **)calloc(stringsLength, sizeof(char *));
    276             mSizeArray = (size_t*)calloc(stringsLength, sizeof(size_t));
    277             for (jsize ct = 0; ct < stringsLength; ct ++) {
    278                 jstring s = (jstring)mEnv->GetObjectArrayElement(mStrings, ct);
    279                 mCStrings[ct] = mEnv->GetStringUTFChars(s, nullptr);
    280                 mSizeArray[ct] = mEnv->GetStringUTFLength(s);
    281             }
    282         }
    283     }
    284     ~AutoJavaStringArrayToUTF8() {
    285         for (jsize ct=0; ct < mStringsLength; ct++) {
    286             jstring s = (jstring)mEnv->GetObjectArrayElement(mStrings, ct);
    287             mEnv->ReleaseStringUTFChars(s, mCStrings[ct]);
    288         }
    289         free(mCStrings);
    290         free(mSizeArray);
    291     }
    292     const char **c_str() const { return mCStrings; }
    293     size_t *c_str_len() const { return mSizeArray; }
    294     jsize length() const { return mStringsLength; }
    295 
    296 private:
    297     JNIEnv      *mEnv;
    298     jobjectArray mStrings;
    299     const char **mCStrings;
    300     size_t      *mSizeArray;
    301     jsize        mStringsLength;
    302 };
    303 
    304 // ---------------------------------------------------------------------------
    305 
    306 static jfieldID gContextId = 0;
    307 
    308 static void _nInit(JNIEnv *_env, jclass _this)
    309 {
    310     gContextId             = _env->GetFieldID(_this, "mContext", "J");
    311 }
    312 
    313 // ---------------------------------------------------------------------------
    314 
    315 static void copyWithPadding(void* ptr, void* srcPtr, int mSize, int count) {
    316     int sizeBytesPad = mSize * 4;
    317     int sizeBytes = mSize * 3;
    318     uint8_t *dst = static_cast<uint8_t *>(ptr);
    319     uint8_t *src = static_cast<uint8_t *>(srcPtr);
    320     for (int i = 0; i < count; i++) {
    321         memcpy(dst, src, sizeBytes);
    322         dst += sizeBytesPad;
    323         src += sizeBytes;
    324     }
    325 }
    326 
    327 static void copyWithUnPadding(void* ptr, void* srcPtr, int mSize, int count) {
    328     int sizeBytesPad = mSize * 4;
    329     int sizeBytes = mSize * 3;
    330     uint8_t *dst = static_cast<uint8_t *>(ptr);
    331     uint8_t *src = static_cast<uint8_t *>(srcPtr);
    332     for (int i = 0; i < count; i++) {
    333         memcpy(dst, src, sizeBytes);
    334         dst += sizeBytes;
    335         src += sizeBytesPad;
    336     }
    337 }
    338 
    339 
    340 // ---------------------------------------------------------------------------
    341 static void
    342 nContextFinish(JNIEnv *_env, jobject _this, jlong con)
    343 {
    344     if (kLogApi) {
    345         ALOGD("nContextFinish, con(%p)", (RsContext)con);
    346     }
    347     rsContextFinish((RsContext)con);
    348 }
    349 
    350 static jlong
    351 nClosureCreate(JNIEnv *_env, jobject _this, jlong con, jlong kernelID,
    352                jlong returnValue, jlongArray fieldIDArray,
    353                jlongArray valueArray, jintArray sizeArray,
    354                jlongArray depClosureArray, jlongArray depFieldIDArray) {
    355   jlong ret = 0;
    356 
    357   jlong* jFieldIDs = _env->GetLongArrayElements(fieldIDArray, nullptr);
    358   jsize fieldIDs_length = _env->GetArrayLength(fieldIDArray);
    359   if (jFieldIDs == nullptr) {
    360       ALOGE("Failed to get Java array elements: fieldIDs.");
    361       return ret;
    362   }
    363 
    364   jlong* jValues = _env->GetLongArrayElements(valueArray, nullptr);
    365   jsize values_length = _env->GetArrayLength(valueArray);
    366   if (jValues == nullptr) {
    367       ALOGE("Failed to get Java array elements: values.");
    368       return ret;
    369   }
    370 
    371   jint* jSizes = _env->GetIntArrayElements(sizeArray, nullptr);
    372   jsize sizes_length = _env->GetArrayLength(sizeArray);
    373   if (jSizes == nullptr) {
    374       ALOGE("Failed to get Java array elements: sizes.");
    375       return ret;
    376   }
    377 
    378   jlong* jDepClosures =
    379       _env->GetLongArrayElements(depClosureArray, nullptr);
    380   jsize depClosures_length = _env->GetArrayLength(depClosureArray);
    381   if (jDepClosures == nullptr) {
    382       ALOGE("Failed to get Java array elements: depClosures.");
    383       return ret;
    384   }
    385 
    386   jlong* jDepFieldIDs =
    387       _env->GetLongArrayElements(depFieldIDArray, nullptr);
    388   jsize depFieldIDs_length = _env->GetArrayLength(depFieldIDArray);
    389   if (jDepFieldIDs == nullptr) {
    390       ALOGE("Failed to get Java array elements: depFieldIDs.");
    391       return ret;
    392   }
    393 
    394   size_t numValues, numDependencies;
    395   RsScriptFieldID* fieldIDs;
    396   RsClosure* depClosures;
    397   RsScriptFieldID* depFieldIDs;
    398 
    399   if (fieldIDs_length != values_length || values_length != sizes_length) {
    400       ALOGE("Unmatched field IDs, values, and sizes in closure creation.");
    401       goto exit;
    402   }
    403 
    404   numValues = (size_t)fieldIDs_length;
    405 
    406   if (depClosures_length != depFieldIDs_length) {
    407       ALOGE("Unmatched closures and field IDs for dependencies in closure creation.");
    408       goto exit;
    409   }
    410 
    411   numDependencies = (size_t)depClosures_length;
    412 
    413   if (numDependencies > numValues) {
    414       ALOGE("Unexpected number of dependencies in closure creation");
    415       goto exit;
    416   }
    417 
    418   if (numValues > RS_CLOSURE_MAX_NUMBER_ARGS_AND_BINDINGS) {
    419       ALOGE("Too many arguments or globals in closure creation");
    420       goto exit;
    421   }
    422 
    423   if (numValues > 0) {
    424       fieldIDs = (RsScriptFieldID*)alloca(sizeof(RsScriptFieldID) * numValues);
    425       if (fieldIDs == nullptr) {
    426           goto exit;
    427       }
    428   } else {
    429       // numValues == 0
    430       // alloca(0) implementation is platform-dependent.
    431       fieldIDs = nullptr;
    432   }
    433 
    434   for (size_t i = 0; i < numValues; i++) {
    435     fieldIDs[i] = (RsScriptFieldID)jFieldIDs[i];
    436   }
    437 
    438   if (numDependencies > 0) {
    439       depClosures = (RsClosure*)alloca(sizeof(RsClosure) * numDependencies);
    440       if (depClosures == nullptr) {
    441           goto exit;
    442       }
    443 
    444       for (size_t i = 0; i < numDependencies; i++) {
    445           depClosures[i] = (RsClosure)jDepClosures[i];
    446       }
    447 
    448       depFieldIDs = (RsScriptFieldID*)alloca(sizeof(RsScriptFieldID) * numDependencies);
    449       if (depFieldIDs == nullptr) {
    450           goto exit;
    451       }
    452 
    453       for (size_t i = 0; i < numDependencies; i++) {
    454           depFieldIDs[i] = (RsClosure)jDepFieldIDs[i];
    455       }
    456   } else {
    457       // alloca(0) implementation is platform-dependent.
    458       depClosures = nullptr;
    459       depFieldIDs = nullptr;
    460   }
    461 
    462   ret = (jlong)(uintptr_t)rsClosureCreate(
    463       (RsContext)con, (RsScriptKernelID)kernelID, (RsAllocation)returnValue,
    464       fieldIDs, numValues, jValues, numValues,
    465       (int*)jSizes, numValues,
    466       depClosures, numDependencies,
    467       depFieldIDs, numDependencies);
    468 
    469 exit:
    470 
    471   _env->ReleaseLongArrayElements(depFieldIDArray, jDepFieldIDs, JNI_ABORT);
    472   _env->ReleaseLongArrayElements(depClosureArray, jDepClosures, JNI_ABORT);
    473   _env->ReleaseIntArrayElements (sizeArray,       jSizes,       JNI_ABORT);
    474   _env->ReleaseLongArrayElements(valueArray,      jValues,      JNI_ABORT);
    475   _env->ReleaseLongArrayElements(fieldIDArray,    jFieldIDs,    JNI_ABORT);
    476 
    477   return ret;
    478 }
    479 
    480 static jlong
    481 nInvokeClosureCreate(JNIEnv *_env, jobject _this, jlong con, jlong invokeID,
    482                      jbyteArray paramArray, jlongArray fieldIDArray, jlongArray valueArray,
    483                      jintArray sizeArray) {
    484   jlong ret = 0;
    485 
    486   jbyte* jParams = _env->GetByteArrayElements(paramArray, nullptr);
    487   jsize jParamLength = _env->GetArrayLength(paramArray);
    488   if (jParams == nullptr) {
    489       ALOGE("Failed to get Java array elements: params.");
    490       return ret;
    491   }
    492 
    493   jlong* jFieldIDs = _env->GetLongArrayElements(fieldIDArray, nullptr);
    494   jsize fieldIDs_length = _env->GetArrayLength(fieldIDArray);
    495   if (jFieldIDs == nullptr) {
    496       ALOGE("Failed to get Java array elements: fieldIDs.");
    497       return ret;
    498   }
    499 
    500   jlong* jValues = _env->GetLongArrayElements(valueArray, nullptr);
    501   jsize values_length = _env->GetArrayLength(valueArray);
    502   if (jValues == nullptr) {
    503       ALOGE("Failed to get Java array elements: values.");
    504       return ret;
    505   }
    506 
    507   jint* jSizes = _env->GetIntArrayElements(sizeArray, nullptr);
    508   jsize sizes_length = _env->GetArrayLength(sizeArray);
    509   if (jSizes == nullptr) {
    510       ALOGE("Failed to get Java array elements: sizes.");
    511       return ret;
    512   }
    513 
    514   size_t numValues;
    515   RsScriptFieldID* fieldIDs;
    516 
    517   if (fieldIDs_length != values_length || values_length != sizes_length) {
    518       ALOGE("Unmatched field IDs, values, and sizes in closure creation.");
    519       goto exit;
    520   }
    521 
    522   numValues = (size_t) fieldIDs_length;
    523 
    524   if (numValues > RS_CLOSURE_MAX_NUMBER_ARGS_AND_BINDINGS) {
    525       ALOGE("Too many arguments or globals in closure creation");
    526       goto exit;
    527   }
    528 
    529   fieldIDs = (RsScriptFieldID*)alloca(sizeof(RsScriptFieldID) * numValues);
    530   if (fieldIDs == nullptr) {
    531       goto exit;
    532   }
    533 
    534   for (size_t i = 0; i< numValues; i++) {
    535     fieldIDs[i] = (RsScriptFieldID)jFieldIDs[i];
    536   }
    537 
    538   ret = (jlong)(uintptr_t)rsInvokeClosureCreate(
    539       (RsContext)con, (RsScriptInvokeID)invokeID, jParams, jParamLength,
    540       fieldIDs, numValues, jValues, numValues,
    541       (int*)jSizes, numValues);
    542 
    543 exit:
    544 
    545   _env->ReleaseIntArrayElements (sizeArray,       jSizes,       JNI_ABORT);
    546   _env->ReleaseLongArrayElements(valueArray,      jValues,      JNI_ABORT);
    547   _env->ReleaseLongArrayElements(fieldIDArray,    jFieldIDs,    JNI_ABORT);
    548   _env->ReleaseByteArrayElements(paramArray,      jParams,      JNI_ABORT);
    549 
    550   return ret;
    551 }
    552 
    553 static void
    554 nClosureSetArg(JNIEnv *_env, jobject _this, jlong con, jlong closureID,
    555                jint index, jlong value, jint size) {
    556   // Size is signed with -1 indicating the value is an Allocation
    557   rsClosureSetArg((RsContext)con, (RsClosure)closureID, (uint32_t)index,
    558                   (uintptr_t)value, size);
    559 }
    560 
    561 static void
    562 nClosureSetGlobal(JNIEnv *_env, jobject _this, jlong con, jlong closureID,
    563                   jlong fieldID, jlong value, jint size) {
    564   // Size is signed with -1 indicating the value is an Allocation
    565   rsClosureSetGlobal((RsContext)con, (RsClosure)closureID,
    566                      (RsScriptFieldID)fieldID, (int64_t)value, size);
    567 }
    568 
    569 static long
    570 nScriptGroup2Create(JNIEnv *_env, jobject _this, jlong con, jstring name,
    571                     jstring cacheDir, jlongArray closureArray) {
    572   jlong ret = 0;
    573 
    574   AutoJavaStringToUTF8 nameUTF(_env, name);
    575   AutoJavaStringToUTF8 cacheDirUTF(_env, cacheDir);
    576 
    577   jlong* jClosures = _env->GetLongArrayElements(closureArray, nullptr);
    578   jsize numClosures = _env->GetArrayLength(closureArray);
    579   if (jClosures == nullptr) {
    580       ALOGE("Failed to get Java array elements: closures.");
    581       return ret;
    582   }
    583 
    584   RsClosure* closures;
    585 
    586   if (numClosures > (jsize) RS_SCRIPT_GROUP_MAX_NUMBER_CLOSURES) {
    587     ALOGE("Too many closures in script group");
    588     goto exit;
    589   }
    590 
    591   closures = (RsClosure*)alloca(sizeof(RsClosure) * numClosures);
    592   if (closures == nullptr) {
    593       goto exit;
    594   }
    595 
    596   for (int i = 0; i < numClosures; i++) {
    597     closures[i] = (RsClosure)jClosures[i];
    598   }
    599 
    600   ret = (jlong)(uintptr_t)rsScriptGroup2Create(
    601       (RsContext)con, nameUTF.c_str(), nameUTF.length(),
    602       cacheDirUTF.c_str(), cacheDirUTF.length(),
    603       closures, numClosures);
    604 
    605 exit:
    606 
    607   _env->ReleaseLongArrayElements(closureArray, jClosures, JNI_ABORT);
    608 
    609   return ret;
    610 }
    611 
    612 static void
    613 nScriptGroup2Execute(JNIEnv *_env, jobject _this, jlong con, jlong groupID) {
    614   rsScriptGroupExecute((RsContext)con, (RsScriptGroup2)groupID);
    615 }
    616 
    617 static void
    618 nScriptIntrinsicBLAS_Single(JNIEnv *_env, jobject _this, jlong con, jlong id, jint func, jint TransA,
    619                             jint TransB, jint Side, jint Uplo, jint Diag, jint M, jint N, jint K,
    620                             jfloat alpha, jlong A, jlong B, jfloat beta, jlong C, jint incX, jint incY,
    621                             jint KL, jint KU) {
    622     RsBlasCall call;
    623     memset(&call, 0, sizeof(call));
    624     call.func = (RsBlasFunction)func;
    625     call.transA = (RsBlasTranspose)TransA;
    626     call.transB = (RsBlasTranspose)TransB;
    627     call.side = (RsBlasSide)Side;
    628     call.uplo = (RsBlasUplo)Uplo;
    629     call.diag = (RsBlasDiag)Diag;
    630     call.M = M;
    631     call.N = N;
    632     call.K = K;
    633     call.alpha.f = alpha;
    634     call.beta.f = beta;
    635     call.incX = incX;
    636     call.incY = incY;
    637     call.KL = KL;
    638     call.KU = KU;
    639 
    640     RsAllocation in_allocs[3];
    641     in_allocs[0] = (RsAllocation)A;
    642     in_allocs[1] = (RsAllocation)B;
    643     in_allocs[2] = (RsAllocation)C;
    644 
    645     rsScriptForEachMulti((RsContext)con, (RsScript)id, 0,
    646                          in_allocs, NELEM(in_allocs), nullptr,
    647                          &call, sizeof(call), nullptr, 0);
    648 }
    649 
    650 static void
    651 nScriptIntrinsicBLAS_Double(JNIEnv *_env, jobject _this, jlong con, jlong id, jint func, jint TransA,
    652                             jint TransB, jint Side, jint Uplo, jint Diag, jint M, jint N, jint K,
    653                             jdouble alpha, jlong A, jlong B, jdouble beta, jlong C, jint incX, jint incY,
    654                             jint KL, jint KU) {
    655     RsBlasCall call;
    656     memset(&call, 0, sizeof(call));
    657     call.func = (RsBlasFunction)func;
    658     call.transA = (RsBlasTranspose)TransA;
    659     call.transB = (RsBlasTranspose)TransB;
    660     call.side = (RsBlasSide)Side;
    661     call.uplo = (RsBlasUplo)Uplo;
    662     call.diag = (RsBlasDiag)Diag;
    663     call.M = M;
    664     call.N = N;
    665     call.K = K;
    666     call.alpha.d = alpha;
    667     call.beta.d = beta;
    668     call.incX = incX;
    669     call.incY = incY;
    670     call.KL = KL;
    671     call.KU = KU;
    672 
    673     RsAllocation in_allocs[3];
    674     in_allocs[0] = (RsAllocation)A;
    675     in_allocs[1] = (RsAllocation)B;
    676     in_allocs[2] = (RsAllocation)C;
    677 
    678     rsScriptForEachMulti((RsContext)con, (RsScript)id, 0,
    679                          in_allocs, NELEM(in_allocs), nullptr,
    680                          &call, sizeof(call), nullptr, 0);
    681 }
    682 
    683 static void
    684 nScriptIntrinsicBLAS_Complex(JNIEnv *_env, jobject _this, jlong con, jlong id, jint func, jint TransA,
    685                              jint TransB, jint Side, jint Uplo, jint Diag, jint M, jint N, jint K,
    686                              jfloat alphaX, jfloat alphaY, jlong A, jlong B, jfloat betaX,
    687                              jfloat betaY, jlong C, jint incX, jint incY, jint KL, jint KU) {
    688     RsBlasCall call;
    689     memset(&call, 0, sizeof(call));
    690     call.func = (RsBlasFunction)func;
    691     call.transA = (RsBlasTranspose)TransA;
    692     call.transB = (RsBlasTranspose)TransB;
    693     call.side = (RsBlasSide)Side;
    694     call.uplo = (RsBlasUplo)Uplo;
    695     call.diag = (RsBlasDiag)Diag;
    696     call.M = M;
    697     call.N = N;
    698     call.K = K;
    699     call.alpha.c.r = alphaX;
    700     call.alpha.c.i = alphaY;
    701     call.beta.c.r = betaX;
    702     call.beta.c.i = betaY;
    703     call.incX = incX;
    704     call.incY = incY;
    705     call.KL = KL;
    706     call.KU = KU;
    707 
    708     RsAllocation in_allocs[3];
    709     in_allocs[0] = (RsAllocation)A;
    710     in_allocs[1] = (RsAllocation)B;
    711     in_allocs[2] = (RsAllocation)C;
    712 
    713     rsScriptForEachMulti((RsContext)con, (RsScript)id, 0,
    714                          in_allocs, NELEM(in_allocs), nullptr,
    715                          &call, sizeof(call), nullptr, 0);
    716 }
    717 
    718 static void
    719 nScriptIntrinsicBLAS_Z(JNIEnv *_env, jobject _this, jlong con, jlong id, jint func, jint TransA,
    720                        jint TransB, jint Side, jint Uplo, jint Diag, jint M, jint N, jint K,
    721                        jdouble alphaX, jdouble alphaY, jlong A, jlong B, jdouble betaX,
    722                        jdouble betaY, jlong C, jint incX, jint incY, jint KL, jint KU) {
    723     RsBlasCall call;
    724     memset(&call, 0, sizeof(call));
    725     call.func = (RsBlasFunction)func;
    726     call.transA = (RsBlasTranspose)TransA;
    727     call.transB = (RsBlasTranspose)TransB;
    728     call.side = (RsBlasSide)Side;
    729     call.uplo = (RsBlasUplo)Uplo;
    730     call.diag = (RsBlasDiag)Diag;
    731     call.M = M;
    732     call.N = N;
    733     call.K = K;
    734     call.alpha.z.r = alphaX;
    735     call.alpha.z.i = alphaY;
    736     call.beta.z.r = betaX;
    737     call.beta.z.i = betaY;
    738     call.incX = incX;
    739     call.incY = incY;
    740     call.KL = KL;
    741     call.KU = KU;
    742 
    743     RsAllocation in_allocs[3];
    744     in_allocs[0] = (RsAllocation)A;
    745     in_allocs[1] = (RsAllocation)B;
    746     in_allocs[2] = (RsAllocation)C;
    747 
    748     rsScriptForEachMulti((RsContext)con, (RsScript)id, 0,
    749                          in_allocs, NELEM(in_allocs), nullptr,
    750                          &call, sizeof(call), nullptr, 0);
    751 }
    752 
    753 
    754 static void
    755 nScriptIntrinsicBLAS_BNNM(JNIEnv *_env, jobject _this, jlong con, jlong id, jint M, jint N, jint K,
    756                                              jlong A, jint a_offset, jlong B, jint b_offset, jlong C, jint c_offset,
    757                                              jint c_mult_int) {
    758     RsBlasCall call;
    759     memset(&call, 0, sizeof(call));
    760     call.func = RsBlas_bnnm;
    761     call.M = M;
    762     call.N = N;
    763     call.K = K;
    764     call.a_offset = a_offset & 0xFF;
    765     call.b_offset = b_offset & 0xFF;
    766     call.c_offset = c_offset;
    767     call.c_mult_int = c_mult_int;
    768 
    769     RsAllocation in_allocs[3];
    770     in_allocs[0] = (RsAllocation)A;
    771     in_allocs[1] = (RsAllocation)B;
    772     in_allocs[2] = (RsAllocation)C;
    773 
    774     rsScriptForEachMulti((RsContext)con, (RsScript)id, 0,
    775                          in_allocs, NELEM(in_allocs), nullptr,
    776                          &call, sizeof(call), nullptr, 0);
    777 }
    778 
    779 
    780 static void
    781 nAssignName(JNIEnv *_env, jobject _this, jlong con, jlong obj, jbyteArray str)
    782 {
    783     if (kLogApi) {
    784         ALOGD("nAssignName, con(%p), obj(%p)", (RsContext)con, (void *)obj);
    785     }
    786     jint len = _env->GetArrayLength(str);
    787     jbyte * cptr = (jbyte *) _env->GetPrimitiveArrayCritical(str, 0);
    788     if (cptr == nullptr) {
    789         ALOGE("Failed to get Java array elements");
    790         return;
    791     }
    792 
    793     rsAssignName((RsContext)con, (void *)obj, (const char *)cptr, len);
    794     _env->ReleasePrimitiveArrayCritical(str, cptr, JNI_ABORT);
    795 }
    796 
    797 static jstring
    798 nGetName(JNIEnv *_env, jobject _this, jlong con, jlong obj)
    799 {
    800     if (kLogApi) {
    801         ALOGD("nGetName, con(%p), obj(%p)", (RsContext)con, (void *)obj);
    802     }
    803     const char *name = nullptr;
    804     rsaGetName((RsContext)con, (void *)obj, &name);
    805     if(name == nullptr || strlen(name) == 0) {
    806         return nullptr;
    807     }
    808     return _env->NewStringUTF(name);
    809 }
    810 
    811 static void
    812 nObjDestroy(JNIEnv *_env, jobject _this, jlong con, jlong obj)
    813 {
    814     if (kLogApi) {
    815         ALOGD("nObjDestroy, con(%p) obj(%p)", (RsContext)con, (void *)obj);
    816     }
    817     rsObjDestroy((RsContext)con, (void *)obj);
    818 }
    819 
    820 // ---------------------------------------------------------------------------
    821 
    822 static jlong
    823 nDeviceCreate(JNIEnv *_env, jobject _this)
    824 {
    825     if (kLogApi) {
    826         ALOGD("nDeviceCreate");
    827     }
    828     return (jlong)(uintptr_t)rsDeviceCreate();
    829 }
    830 
    831 static void
    832 nDeviceDestroy(JNIEnv *_env, jobject _this, jlong dev)
    833 {
    834     if (kLogApi) {
    835         ALOGD("nDeviceDestroy");
    836     }
    837     return rsDeviceDestroy((RsDevice)dev);
    838 }
    839 
    840 static void
    841 nDeviceSetConfig(JNIEnv *_env, jobject _this, jlong dev, jint p, jint value)
    842 {
    843     if (kLogApi) {
    844         ALOGD("nDeviceSetConfig  dev(%p), param(%i), value(%i)", (void *)dev, p, value);
    845     }
    846     return rsDeviceSetConfig((RsDevice)dev, (RsDeviceParam)p, value);
    847 }
    848 
    849 static jlong
    850 nContextCreate(JNIEnv *_env, jobject _this, jlong dev, jint flags, jint sdkVer, jint contextType)
    851 {
    852     if (kLogApi) {
    853         ALOGD("nContextCreate");
    854     }
    855     return (jlong)(uintptr_t)rsContextCreate((RsDevice)dev, 0, sdkVer, (RsContextType)contextType, flags);
    856 }
    857 
    858 static jlong
    859 nContextCreateGL(JNIEnv *_env, jobject _this, jlong dev, jint ver, jint sdkVer,
    860                  jint colorMin, jint colorPref,
    861                  jint alphaMin, jint alphaPref,
    862                  jint depthMin, jint depthPref,
    863                  jint stencilMin, jint stencilPref,
    864                  jint samplesMin, jint samplesPref, jfloat samplesQ,
    865                  jint dpi)
    866 {
    867     RsSurfaceConfig sc = {};
    868     sc.alphaMin = alphaMin;
    869     sc.alphaPref = alphaPref;
    870     sc.colorMin = colorMin;
    871     sc.colorPref = colorPref;
    872     sc.depthMin = depthMin;
    873     sc.depthPref = depthPref;
    874     sc.samplesMin = samplesMin;
    875     sc.samplesPref = samplesPref;
    876     sc.samplesQ = samplesQ;
    877 
    878     if (kLogApi) {
    879         ALOGD("nContextCreateGL");
    880     }
    881     return (jlong)(uintptr_t)rsContextCreateGL((RsDevice)dev, ver, sdkVer, sc, dpi);
    882 }
    883 
    884 static void
    885 nContextSetPriority(JNIEnv *_env, jobject _this, jlong con, jint p)
    886 {
    887     if (kLogApi) {
    888         ALOGD("ContextSetPriority, con(%p), priority(%i)", (RsContext)con, p);
    889     }
    890     rsContextSetPriority((RsContext)con, p);
    891 }
    892 
    893 static void
    894 nContextSetCacheDir(JNIEnv *_env, jobject _this, jlong con, jstring cacheDir)
    895 {
    896     AutoJavaStringToUTF8 cacheDirUTF(_env, cacheDir);
    897 
    898     if (kLogApi) {
    899         ALOGD("ContextSetCacheDir, con(%p), cacheDir(%s)", (RsContext)con, cacheDirUTF.c_str());
    900     }
    901     rsContextSetCacheDir((RsContext)con, cacheDirUTF.c_str(), cacheDirUTF.length());
    902 }
    903 
    904 
    905 
    906 static void
    907 nContextSetSurface(JNIEnv *_env, jobject _this, jlong con, jint width, jint height, jobject wnd)
    908 {
    909     if (kLogApi) {
    910         ALOGD("nContextSetSurface, con(%p), width(%i), height(%i), surface(%p)", (RsContext)con,
    911               width, height, (Surface *)wnd);
    912     }
    913 
    914     ANativeWindow * window = nullptr;
    915     if (wnd == nullptr) {
    916 
    917     } else {
    918         window = android_view_Surface_getNativeWindow(_env, wnd).get();
    919     }
    920 
    921     rsContextSetSurface((RsContext)con, width, height, window);
    922 }
    923 
    924 static void
    925 nContextDestroy(JNIEnv *_env, jobject _this, jlong con)
    926 {
    927     if (kLogApi) {
    928         ALOGD("nContextDestroy, con(%p)", (RsContext)con);
    929     }
    930     rsContextDestroy((RsContext)con);
    931 }
    932 
    933 static void
    934 nContextDump(JNIEnv *_env, jobject _this, jlong con, jint bits)
    935 {
    936     if (kLogApi) {
    937         ALOGD("nContextDump, con(%p)  bits(%i)", (RsContext)con, bits);
    938     }
    939     rsContextDump((RsContext)con, bits);
    940 }
    941 
    942 static void
    943 nContextPause(JNIEnv *_env, jobject _this, jlong con)
    944 {
    945     if (kLogApi) {
    946         ALOGD("nContextPause, con(%p)", (RsContext)con);
    947     }
    948     rsContextPause((RsContext)con);
    949 }
    950 
    951 static void
    952 nContextResume(JNIEnv *_env, jobject _this, jlong con)
    953 {
    954     if (kLogApi) {
    955         ALOGD("nContextResume, con(%p)", (RsContext)con);
    956     }
    957     rsContextResume((RsContext)con);
    958 }
    959 
    960 
    961 static jstring
    962 nContextGetErrorMessage(JNIEnv *_env, jobject _this, jlong con)
    963 {
    964     if (kLogApi) {
    965         ALOGD("nContextGetErrorMessage, con(%p)", (RsContext)con);
    966     }
    967     char buf[1024];
    968 
    969     size_t receiveLen;
    970     uint32_t subID;
    971     int id = rsContextGetMessage((RsContext)con,
    972                                  buf, sizeof(buf),
    973                                  &receiveLen, sizeof(receiveLen),
    974                                  &subID, sizeof(subID));
    975     if (!id && receiveLen) {
    976         ALOGV("message receive buffer too small.  %zu", receiveLen);
    977     }
    978     return _env->NewStringUTF(buf);
    979 }
    980 
    981 static jint
    982 nContextGetUserMessage(JNIEnv *_env, jobject _this, jlong con, jintArray data)
    983 {
    984     jint len = _env->GetArrayLength(data);
    985     if (kLogApi) {
    986         ALOGD("nContextGetMessage, con(%p), len(%i)", (RsContext)con, len);
    987     }
    988     jint *ptr = _env->GetIntArrayElements(data, nullptr);
    989     if (ptr == nullptr) {
    990         ALOGE("Failed to get Java array elements");
    991         return 0;
    992     }
    993     size_t receiveLen;
    994     uint32_t subID;
    995     int id = rsContextGetMessage((RsContext)con,
    996                                  ptr, len * 4,
    997                                  &receiveLen, sizeof(receiveLen),
    998                                  &subID, sizeof(subID));
    999     if (!id && receiveLen) {
   1000         ALOGV("message receive buffer too small.  %zu", receiveLen);
   1001     }
   1002     _env->ReleaseIntArrayElements(data, ptr, 0);
   1003     return (jint)id;
   1004 }
   1005 
   1006 static jint
   1007 nContextPeekMessage(JNIEnv *_env, jobject _this, jlong con, jintArray auxData)
   1008 {
   1009     if (kLogApi) {
   1010         ALOGD("nContextPeekMessage, con(%p)", (RsContext)con);
   1011     }
   1012     jint *auxDataPtr = _env->GetIntArrayElements(auxData, nullptr);
   1013     if (auxDataPtr == nullptr) {
   1014         ALOGE("Failed to get Java array elements");
   1015         return 0;
   1016     }
   1017     size_t receiveLen;
   1018     uint32_t subID;
   1019     int id = rsContextPeekMessage((RsContext)con, &receiveLen, sizeof(receiveLen),
   1020                                   &subID, sizeof(subID));
   1021     auxDataPtr[0] = (jint)subID;
   1022     auxDataPtr[1] = (jint)receiveLen;
   1023     _env->ReleaseIntArrayElements(auxData, auxDataPtr, 0);
   1024     return (jint)id;
   1025 }
   1026 
   1027 static void nContextInitToClient(JNIEnv *_env, jobject _this, jlong con)
   1028 {
   1029     if (kLogApi) {
   1030         ALOGD("nContextInitToClient, con(%p)", (RsContext)con);
   1031     }
   1032     rsContextInitToClient((RsContext)con);
   1033 }
   1034 
   1035 static void nContextDeinitToClient(JNIEnv *_env, jobject _this, jlong con)
   1036 {
   1037     if (kLogApi) {
   1038         ALOGD("nContextDeinitToClient, con(%p)", (RsContext)con);
   1039     }
   1040     rsContextDeinitToClient((RsContext)con);
   1041 }
   1042 
   1043 static void
   1044 nContextSendMessage(JNIEnv *_env, jobject _this, jlong con, jint id, jintArray data)
   1045 {
   1046     jint *ptr = nullptr;
   1047     jint len = 0;
   1048     if (data) {
   1049         len = _env->GetArrayLength(data);
   1050         ptr = _env->GetIntArrayElements(data, nullptr);
   1051         if (ptr == nullptr) {
   1052             ALOGE("Failed to get Java array elements");
   1053             return;
   1054         }
   1055     }
   1056     if (kLogApi) {
   1057         ALOGD("nContextSendMessage, con(%p), id(%i), len(%i)", (RsContext)con, id, len);
   1058     }
   1059     rsContextSendMessage((RsContext)con, id, (const uint8_t *)ptr, len * sizeof(int));
   1060     if (data) {
   1061         _env->ReleaseIntArrayElements(data, ptr, JNI_ABORT);
   1062     }
   1063 }
   1064 
   1065 
   1066 
   1067 static jlong
   1068 nElementCreate(JNIEnv *_env, jobject _this, jlong con, jlong type, jint kind, jboolean norm,
   1069                jint size)
   1070 {
   1071     if (kLogApi) {
   1072         ALOGD("nElementCreate, con(%p), type(%" PRId64 "), kind(%i), norm(%i), size(%i)", (RsContext)con,
   1073               type, kind, norm, size);
   1074     }
   1075     return (jlong)(uintptr_t)rsElementCreate((RsContext)con, (RsDataType)type, (RsDataKind)kind,
   1076                                              norm, size);
   1077 }
   1078 
   1079 static jlong
   1080 nElementCreate2(JNIEnv *_env, jobject _this, jlong con,
   1081                 jlongArray _ids, jobjectArray _names, jintArray _arraySizes)
   1082 {
   1083     int fieldCount = _env->GetArrayLength(_ids);
   1084     if (kLogApi) {
   1085         ALOGD("nElementCreate2, con(%p)", (RsContext)con);
   1086     }
   1087 
   1088     jlong *jIds = _env->GetLongArrayElements(_ids, nullptr);
   1089     if (jIds == nullptr) {
   1090         ALOGE("Failed to get Java array elements: ids");
   1091         return 0;
   1092     }
   1093     jint *jArraySizes = _env->GetIntArrayElements(_arraySizes, nullptr);
   1094     if (jArraySizes == nullptr) {
   1095         ALOGE("Failed to get Java array elements: arraySizes");
   1096         return 0;
   1097     }
   1098 
   1099     RsElement *ids = (RsElement*)malloc(fieldCount * sizeof(RsElement));
   1100     uint32_t *arraySizes = (uint32_t *)malloc(fieldCount * sizeof(uint32_t));
   1101 
   1102     for(int i = 0; i < fieldCount; i ++) {
   1103         ids[i] = (RsElement)jIds[i];
   1104         arraySizes[i] = (uint32_t)jArraySizes[i];
   1105     }
   1106 
   1107     AutoJavaStringArrayToUTF8 names(_env, _names, fieldCount);
   1108 
   1109     const char **nameArray = names.c_str();
   1110     size_t *sizeArray = names.c_str_len();
   1111 
   1112     jlong id = (jlong)(uintptr_t)rsElementCreate2((RsContext)con,
   1113                                      (const RsElement *)ids, fieldCount,
   1114                                      nameArray, fieldCount * sizeof(size_t),  sizeArray,
   1115                                      (const uint32_t *)arraySizes, fieldCount);
   1116 
   1117     free(ids);
   1118     free(arraySizes);
   1119     _env->ReleaseLongArrayElements(_ids, jIds, JNI_ABORT);
   1120     _env->ReleaseIntArrayElements(_arraySizes, jArraySizes, JNI_ABORT);
   1121 
   1122     return (jlong)(uintptr_t)id;
   1123 }
   1124 
   1125 static void
   1126 nElementGetNativeData(JNIEnv *_env, jobject _this, jlong con, jlong id, jintArray _elementData)
   1127 {
   1128     int dataSize = _env->GetArrayLength(_elementData);
   1129     if (kLogApi) {
   1130         ALOGD("nElementGetNativeData, con(%p)", (RsContext)con);
   1131     }
   1132 
   1133     // we will pack mType; mKind; mNormalized; mVectorSize; NumSubElements
   1134     assert(dataSize == 5);
   1135 
   1136     uint32_t elementData[5];
   1137     rsaElementGetNativeData((RsContext)con, (RsElement)id, elementData, dataSize);
   1138 
   1139     for(jint i = 0; i < dataSize; i ++) {
   1140         const jint data = (jint)elementData[i];
   1141         _env->SetIntArrayRegion(_elementData, i, 1, &data);
   1142     }
   1143 }
   1144 
   1145 
   1146 static void
   1147 nElementGetSubElements(JNIEnv *_env, jobject _this, jlong con, jlong id,
   1148                        jlongArray _IDs,
   1149                        jobjectArray _names,
   1150                        jintArray _arraySizes)
   1151 {
   1152     uint32_t dataSize = _env->GetArrayLength(_IDs);
   1153     if (kLogApi) {
   1154         ALOGD("nElementGetSubElements, con(%p)", (RsContext)con);
   1155     }
   1156 
   1157     uintptr_t *ids = (uintptr_t*)malloc(dataSize * sizeof(uintptr_t));
   1158     const char **names = (const char **)malloc(dataSize * sizeof(const char *));
   1159     size_t *arraySizes = (size_t *)malloc(dataSize * sizeof(size_t));
   1160 
   1161     rsaElementGetSubElements((RsContext)con, (RsElement)id, ids, names, arraySizes,
   1162                              (uint32_t)dataSize);
   1163 
   1164     for(uint32_t i = 0; i < dataSize; i++) {
   1165         const jlong id = (jlong)(uintptr_t)ids[i];
   1166         const jint arraySize = (jint)arraySizes[i];
   1167         _env->SetObjectArrayElement(_names, i, _env->NewStringUTF(names[i]));
   1168         _env->SetLongArrayRegion(_IDs, i, 1, &id);
   1169         _env->SetIntArrayRegion(_arraySizes, i, 1, &arraySize);
   1170     }
   1171 
   1172     free(ids);
   1173     free(names);
   1174     free(arraySizes);
   1175 }
   1176 
   1177 // -----------------------------------
   1178 
   1179 static jlong
   1180 nTypeCreate(JNIEnv *_env, jobject _this, jlong con, jlong eid,
   1181             jint dimx, jint dimy, jint dimz, jboolean mips, jboolean faces, jint yuv)
   1182 {
   1183     if (kLogApi) {
   1184         ALOGD("nTypeCreate, con(%p) eid(%p), x(%i), y(%i), z(%i), mips(%i), faces(%i), yuv(%i)",
   1185               (RsContext)con, (void*)eid, dimx, dimy, dimz, mips, faces, yuv);
   1186     }
   1187 
   1188     return (jlong)(uintptr_t)rsTypeCreate((RsContext)con, (RsElement)eid, dimx, dimy, dimz, mips,
   1189                                           faces, yuv);
   1190 }
   1191 
   1192 static void
   1193 nTypeGetNativeData(JNIEnv *_env, jobject _this, jlong con, jlong id, jlongArray _typeData)
   1194 {
   1195     // We are packing 6 items: mDimX; mDimY; mDimZ;
   1196     // mDimLOD; mDimFaces; mElement; into typeData
   1197     int elementCount = _env->GetArrayLength(_typeData);
   1198 
   1199     assert(elementCount == 6);
   1200     if (kLogApi) {
   1201         ALOGD("nTypeGetNativeData, con(%p)", (RsContext)con);
   1202     }
   1203 
   1204     uintptr_t typeData[6];
   1205     rsaTypeGetNativeData((RsContext)con, (RsType)id, typeData, 6);
   1206 
   1207     for(jint i = 0; i < elementCount; i ++) {
   1208         const jlong data = (jlong)(uintptr_t)typeData[i];
   1209         _env->SetLongArrayRegion(_typeData, i, 1, &data);
   1210     }
   1211 }
   1212 
   1213 // -----------------------------------
   1214 
   1215 static jlong
   1216 nAllocationCreateTyped(JNIEnv *_env, jobject _this, jlong con, jlong type, jint mips, jint usage,
   1217                        jlong pointer)
   1218 {
   1219     if (kLogApi) {
   1220         ALOGD("nAllocationCreateTyped, con(%p), type(%p), mip(%i), usage(%i), ptr(%p)",
   1221               (RsContext)con, (RsElement)type, mips, usage, (void *)pointer);
   1222     }
   1223     return (jlong)(uintptr_t) rsAllocationCreateTyped((RsContext)con, (RsType)type,
   1224                                                       (RsAllocationMipmapControl)mips,
   1225                                                       (uint32_t)usage, (uintptr_t)pointer);
   1226 }
   1227 
   1228 static void
   1229 nAllocationSyncAll(JNIEnv *_env, jobject _this, jlong con, jlong a, jint bits)
   1230 {
   1231     if (kLogApi) {
   1232         ALOGD("nAllocationSyncAll, con(%p), a(%p), bits(0x%08x)", (RsContext)con, (RsAllocation)a,
   1233               bits);
   1234     }
   1235     rsAllocationSyncAll((RsContext)con, (RsAllocation)a, (RsAllocationUsageType)bits);
   1236 }
   1237 
   1238 static void
   1239 nAllocationSetupBufferQueue(JNIEnv *_env, jobject _this, jlong con, jlong alloc, jint numAlloc)
   1240 {
   1241     if (kLogApi) {
   1242         ALOGD("nAllocationSetupBufferQueue, con(%p), alloc(%p), numAlloc(%d)", (RsContext)con,
   1243               (RsAllocation)alloc, numAlloc);
   1244     }
   1245     rsAllocationSetupBufferQueue((RsContext)con, (RsAllocation)alloc, (uint32_t)numAlloc);
   1246 }
   1247 
   1248 static void
   1249 nAllocationShareBufferQueue(JNIEnv *_env, jobject _this, jlong con, jlong alloc1, jlong alloc2)
   1250 {
   1251     if (kLogApi) {
   1252         ALOGD("nAllocationShareBufferQueue, con(%p), alloc1(%p), alloc2(%p)", (RsContext)con,
   1253               (RsAllocation)alloc1, (RsAllocation)alloc2);
   1254     }
   1255 
   1256     rsAllocationShareBufferQueue((RsContext)con, (RsAllocation)alloc1, (RsAllocation)alloc2);
   1257 }
   1258 
   1259 static jobject
   1260 nAllocationGetSurface(JNIEnv *_env, jobject _this, jlong con, jlong a)
   1261 {
   1262     if (kLogApi) {
   1263         ALOGD("nAllocationGetSurface, con(%p), a(%p)", (RsContext)con, (RsAllocation)a);
   1264     }
   1265 
   1266     ANativeWindow *anw = (ANativeWindow *)rsAllocationGetSurface((RsContext)con, (RsAllocation)a);
   1267 
   1268     sp<Surface> surface(static_cast<Surface*>(anw));
   1269     sp<IGraphicBufferProducer> bp = surface->getIGraphicBufferProducer();
   1270 
   1271     jobject o = android_view_Surface_createFromIGraphicBufferProducer(_env, bp);
   1272     return o;
   1273 }
   1274 
   1275 static void
   1276 nAllocationSetSurface(JNIEnv *_env, jobject _this, jlong con, jlong alloc, jobject sur)
   1277 {
   1278     if (kLogApi) {
   1279         ALOGD("nAllocationSetSurface, con(%p), alloc(%p), surface(%p)", (RsContext)con,
   1280               (RsAllocation)alloc, (Surface *)sur);
   1281     }
   1282 
   1283     ANativeWindow *anw = nullptr;
   1284     if (sur != 0) {
   1285         // Connect the native window handle to buffer queue.
   1286         anw = ANativeWindow_fromSurface(_env, sur);
   1287         native_window_api_connect(anw, NATIVE_WINDOW_API_CPU);
   1288     }
   1289 
   1290     rsAllocationSetSurface((RsContext)con, (RsAllocation)alloc, anw);
   1291 }
   1292 
   1293 static void
   1294 nAllocationIoSend(JNIEnv *_env, jobject _this, jlong con, jlong alloc)
   1295 {
   1296     if (kLogApi) {
   1297         ALOGD("nAllocationIoSend, con(%p), alloc(%p)", (RsContext)con, (RsAllocation)alloc);
   1298     }
   1299     rsAllocationIoSend((RsContext)con, (RsAllocation)alloc);
   1300 }
   1301 
   1302 static jlong
   1303 nAllocationIoReceive(JNIEnv *_env, jobject _this, jlong con, jlong alloc)
   1304 {
   1305     if (kLogApi) {
   1306         ALOGD("nAllocationIoReceive, con(%p), alloc(%p)", (RsContext)con, (RsAllocation)alloc);
   1307     }
   1308     return (jlong) rsAllocationIoReceive((RsContext)con, (RsAllocation)alloc);
   1309 }
   1310 
   1311 static void
   1312 nAllocationGenerateMipmaps(JNIEnv *_env, jobject _this, jlong con, jlong alloc)
   1313 {
   1314     if (kLogApi) {
   1315         ALOGD("nAllocationGenerateMipmaps, con(%p), a(%p)", (RsContext)con, (RsAllocation)alloc);
   1316     }
   1317     rsAllocationGenerateMipmaps((RsContext)con, (RsAllocation)alloc);
   1318 }
   1319 
   1320 static jlong
   1321 nAllocationCreateFromBitmap(JNIEnv *_env, jobject _this, jlong con, jlong type, jint mip,
   1322                             jobject jbitmap, jint usage)
   1323 {
   1324     SkBitmap bitmap;
   1325     GraphicsJNI::getSkBitmap(_env, jbitmap, &bitmap);
   1326 
   1327     bitmap.lockPixels();
   1328     const void* ptr = bitmap.getPixels();
   1329     jlong id = (jlong)(uintptr_t)rsAllocationCreateFromBitmap((RsContext)con,
   1330                                                   (RsType)type, (RsAllocationMipmapControl)mip,
   1331                                                   ptr, bitmap.getSize(), usage);
   1332     bitmap.unlockPixels();
   1333     return id;
   1334 }
   1335 
   1336 static jlong
   1337 nAllocationCreateBitmapBackedAllocation(JNIEnv *_env, jobject _this, jlong con, jlong type,
   1338                                         jint mip, jobject jbitmap, jint usage)
   1339 {
   1340     SkBitmap bitmap;
   1341     GraphicsJNI::getSkBitmap(_env, jbitmap, &bitmap);
   1342 
   1343     bitmap.lockPixels();
   1344     const void* ptr = bitmap.getPixels();
   1345     jlong id = (jlong)(uintptr_t)rsAllocationCreateTyped((RsContext)con,
   1346                                             (RsType)type, (RsAllocationMipmapControl)mip,
   1347                                             (uint32_t)usage, (uintptr_t)ptr);
   1348     bitmap.unlockPixels();
   1349     return id;
   1350 }
   1351 
   1352 static jlong
   1353 nAllocationCubeCreateFromBitmap(JNIEnv *_env, jobject _this, jlong con, jlong type, jint mip,
   1354                                 jobject jbitmap, jint usage)
   1355 {
   1356     SkBitmap bitmap;
   1357     GraphicsJNI::getSkBitmap(_env, jbitmap, &bitmap);
   1358 
   1359     bitmap.lockPixels();
   1360     const void* ptr = bitmap.getPixels();
   1361     jlong id = (jlong)(uintptr_t)rsAllocationCubeCreateFromBitmap((RsContext)con,
   1362                                                       (RsType)type, (RsAllocationMipmapControl)mip,
   1363                                                       ptr, bitmap.getSize(), usage);
   1364     bitmap.unlockPixels();
   1365     return id;
   1366 }
   1367 
   1368 static void
   1369 nAllocationCopyFromBitmap(JNIEnv *_env, jobject _this, jlong con, jlong alloc, jobject jbitmap)
   1370 {
   1371     SkBitmap bitmap;
   1372     GraphicsJNI::getSkBitmap(_env, jbitmap, &bitmap);
   1373     int w = bitmap.width();
   1374     int h = bitmap.height();
   1375 
   1376     bitmap.lockPixels();
   1377     const void* ptr = bitmap.getPixels();
   1378     rsAllocation2DData((RsContext)con, (RsAllocation)alloc, 0, 0,
   1379                        0, RS_ALLOCATION_CUBEMAP_FACE_POSITIVE_X,
   1380                        w, h, ptr, bitmap.getSize(), 0);
   1381     bitmap.unlockPixels();
   1382 }
   1383 
   1384 static void
   1385 nAllocationCopyToBitmap(JNIEnv *_env, jobject _this, jlong con, jlong alloc, jobject jbitmap)
   1386 {
   1387     SkBitmap bitmap;
   1388     GraphicsJNI::getSkBitmap(_env, jbitmap, &bitmap);
   1389 
   1390     bitmap.lockPixels();
   1391     void* ptr = bitmap.getPixels();
   1392     rsAllocationCopyToBitmap((RsContext)con, (RsAllocation)alloc, ptr, bitmap.getSize());
   1393     bitmap.unlockPixels();
   1394     bitmap.notifyPixelsChanged();
   1395 }
   1396 
   1397 // Copies from the Java object data into the Allocation pointed to by _alloc.
   1398 static void
   1399 nAllocationData1D(JNIEnv *_env, jobject _this, jlong con, jlong _alloc, jint offset, jint lod,
   1400                   jint count, jobject data, jint sizeBytes, jint dataType, jint mSize,
   1401                   jboolean usePadding)
   1402 {
   1403     RsAllocation *alloc = (RsAllocation *)_alloc;
   1404     if (kLogApi) {
   1405         ALOGD("nAllocation1DData, con(%p), adapter(%p), offset(%i), count(%i), sizeBytes(%i), "
   1406               "dataType(%i)", (RsContext)con, (RsAllocation)alloc, offset, count, sizeBytes,
   1407               dataType);
   1408     }
   1409     PER_ARRAY_TYPE(nullptr, rsAllocation1DData, true,
   1410                    (RsContext)con, alloc, offset, lod, count, ptr, sizeBytes);
   1411 }
   1412 
   1413 static void
   1414 nAllocationElementData(JNIEnv *_env, jobject _this, jlong con, jlong alloc,
   1415                        jint xoff, jint yoff, jint zoff,
   1416                        jint lod, jint compIdx, jbyteArray data, jint sizeBytes)
   1417 {
   1418     if (kLogApi) {
   1419         jint len = _env->GetArrayLength(data);
   1420         ALOGD("nAllocationElementData, con(%p), alloc(%p), xoff(%i), yoff(%i), zoff(%i), comp(%i), len(%i), "
   1421               "sizeBytes(%i)", (RsContext)con, (RsAllocation)alloc, xoff, yoff, zoff, compIdx, len,
   1422               sizeBytes);
   1423     }
   1424     jbyte *ptr = _env->GetByteArrayElements(data, nullptr);
   1425     if (ptr == nullptr) {
   1426         ALOGE("Failed to get Java array elements");
   1427         return;
   1428     }
   1429     rsAllocationElementData((RsContext)con, (RsAllocation)alloc,
   1430                             xoff, yoff, zoff,
   1431                             lod, ptr, sizeBytes, compIdx);
   1432     _env->ReleaseByteArrayElements(data, ptr, JNI_ABORT);
   1433 }
   1434 
   1435 
   1436 // Copies from the Java object data into the Allocation pointed to by _alloc.
   1437 static void
   1438 nAllocationData2D(JNIEnv *_env, jobject _this, jlong con, jlong _alloc, jint xoff, jint yoff, jint lod, jint _face,
   1439                   jint w, jint h, jobject data, jint sizeBytes, jint dataType, jint mSize,
   1440                   jboolean usePadding)
   1441 {
   1442     RsAllocation *alloc = (RsAllocation *)_alloc;
   1443     RsAllocationCubemapFace face = (RsAllocationCubemapFace)_face;
   1444     if (kLogApi) {
   1445         ALOGD("nAllocation2DData, con(%p), adapter(%p), xoff(%i), yoff(%i), w(%i), h(%i), len(%i) "
   1446               "type(%i)", (RsContext)con, alloc, xoff, yoff, w, h, sizeBytes, dataType);
   1447     }
   1448     int count = w * h;
   1449     PER_ARRAY_TYPE(nullptr, rsAllocation2DData, true,
   1450                    (RsContext)con, alloc, xoff, yoff, lod, face, w, h, ptr, sizeBytes, 0);
   1451 }
   1452 
   1453 // Copies from the Allocation pointed to by srcAlloc into the Allocation
   1454 // pointed to by dstAlloc.
   1455 static void
   1456 nAllocationData2D_alloc(JNIEnv *_env, jobject _this, jlong con,
   1457                         jlong dstAlloc, jint dstXoff, jint dstYoff,
   1458                         jint dstMip, jint dstFace,
   1459                         jint width, jint height,
   1460                         jlong srcAlloc, jint srcXoff, jint srcYoff,
   1461                         jint srcMip, jint srcFace)
   1462 {
   1463     if (kLogApi) {
   1464         ALOGD("nAllocation2DData_s, con(%p), dstAlloc(%p), dstXoff(%i), dstYoff(%i),"
   1465               " dstMip(%i), dstFace(%i), width(%i), height(%i),"
   1466               " srcAlloc(%p), srcXoff(%i), srcYoff(%i), srcMip(%i), srcFace(%i)",
   1467               (RsContext)con, (RsAllocation)dstAlloc, dstXoff, dstYoff, dstMip, dstFace,
   1468               width, height, (RsAllocation)srcAlloc, srcXoff, srcYoff, srcMip, srcFace);
   1469     }
   1470 
   1471     rsAllocationCopy2DRange((RsContext)con,
   1472                             (RsAllocation)dstAlloc,
   1473                             dstXoff, dstYoff,
   1474                             dstMip, dstFace,
   1475                             width, height,
   1476                             (RsAllocation)srcAlloc,
   1477                             srcXoff, srcYoff,
   1478                             srcMip, srcFace);
   1479 }
   1480 
   1481 // Copies from the Java object data into the Allocation pointed to by _alloc.
   1482 static void
   1483 nAllocationData3D(JNIEnv *_env, jobject _this, jlong con, jlong _alloc, jint xoff, jint yoff, jint zoff, jint lod,
   1484                   jint w, jint h, jint d, jobject data, jint sizeBytes, jint dataType,
   1485                   jint mSize, jboolean usePadding)
   1486 {
   1487     RsAllocation *alloc = (RsAllocation *)_alloc;
   1488     if (kLogApi) {
   1489         ALOGD("nAllocation3DData, con(%p), alloc(%p), xoff(%i), yoff(%i), zoff(%i), lod(%i), w(%i),"
   1490               " h(%i), d(%i), sizeBytes(%i)", (RsContext)con, (RsAllocation)alloc, xoff, yoff, zoff,
   1491               lod, w, h, d, sizeBytes);
   1492     }
   1493     int count = w * h * d;
   1494     PER_ARRAY_TYPE(nullptr, rsAllocation3DData, true,
   1495                    (RsContext)con, alloc, xoff, yoff, zoff, lod, w, h, d, ptr, sizeBytes, 0);
   1496 }
   1497 
   1498 // Copies from the Allocation pointed to by srcAlloc into the Allocation
   1499 // pointed to by dstAlloc.
   1500 static void
   1501 nAllocationData3D_alloc(JNIEnv *_env, jobject _this, jlong con,
   1502                         jlong dstAlloc, jint dstXoff, jint dstYoff, jint dstZoff,
   1503                         jint dstMip,
   1504                         jint width, jint height, jint depth,
   1505                         jlong srcAlloc, jint srcXoff, jint srcYoff, jint srcZoff,
   1506                         jint srcMip)
   1507 {
   1508     if (kLogApi) {
   1509         ALOGD("nAllocationData3D_alloc, con(%p), dstAlloc(%p), dstXoff(%i), dstYoff(%i),"
   1510               " dstMip(%i), width(%i), height(%i),"
   1511               " srcAlloc(%p), srcXoff(%i), srcYoff(%i), srcMip(%i)",
   1512               (RsContext)con, (RsAllocation)dstAlloc, dstXoff, dstYoff, dstMip,
   1513               width, height, (RsAllocation)srcAlloc, srcXoff, srcYoff, srcMip);
   1514     }
   1515 
   1516     rsAllocationCopy3DRange((RsContext)con,
   1517                             (RsAllocation)dstAlloc,
   1518                             dstXoff, dstYoff, dstZoff, dstMip,
   1519                             width, height, depth,
   1520                             (RsAllocation)srcAlloc,
   1521                             srcXoff, srcYoff, srcZoff, srcMip);
   1522 }
   1523 
   1524 
   1525 // Copies from the Allocation pointed to by _alloc into the Java object data.
   1526 static void
   1527 nAllocationRead(JNIEnv *_env, jobject _this, jlong con, jlong _alloc, jobject data, jint dataType,
   1528                 jint mSize, jboolean usePadding)
   1529 {
   1530     RsAllocation *alloc = (RsAllocation *)_alloc;
   1531     if (kLogApi) {
   1532         ALOGD("nAllocationRead, con(%p), alloc(%p)", (RsContext)con, (RsAllocation)alloc);
   1533     }
   1534     int count = 0;
   1535     PER_ARRAY_TYPE(0, rsAllocationRead, false,
   1536                    (RsContext)con, alloc, ptr, len * typeBytes);
   1537 }
   1538 
   1539 // Copies from the Allocation pointed to by _alloc into the Java object data.
   1540 static void
   1541 nAllocationRead1D(JNIEnv *_env, jobject _this, jlong con, jlong _alloc, jint offset, jint lod,
   1542                   jint count, jobject data, jint sizeBytes, jint dataType,
   1543                   jint mSize, jboolean usePadding)
   1544 {
   1545     RsAllocation *alloc = (RsAllocation *)_alloc;
   1546     if (kLogApi) {
   1547         ALOGD("nAllocation1DRead, con(%p), adapter(%p), offset(%i), count(%i), sizeBytes(%i), "
   1548               "dataType(%i)", (RsContext)con, alloc, offset, count, sizeBytes, dataType);
   1549     }
   1550     PER_ARRAY_TYPE(0, rsAllocation1DRead, false,
   1551                    (RsContext)con, alloc, offset, lod, count, ptr, sizeBytes);
   1552 }
   1553 
   1554 // Copies from the Element in the Allocation pointed to by _alloc into the Java array data.
   1555 static void
   1556 nAllocationElementRead(JNIEnv *_env, jobject _this, jlong con, jlong alloc,
   1557                        jint xoff, jint yoff, jint zoff,
   1558                        jint lod, jint compIdx, jbyteArray data, jint sizeBytes)
   1559 {
   1560     if (kLogApi) {
   1561         jint len = _env->GetArrayLength(data);
   1562         ALOGD("nAllocationElementRead, con(%p), alloc(%p), xoff(%i), yoff(%i), zoff(%i), comp(%i), len(%i), "
   1563               "sizeBytes(%i)", (RsContext)con, (RsAllocation)alloc, xoff, yoff, zoff, compIdx, len,
   1564               sizeBytes);
   1565     }
   1566     jbyte *ptr = _env->GetByteArrayElements(data, nullptr);
   1567     if (ptr == nullptr) {
   1568         ALOGE("Failed to get Java array elements");
   1569         return;
   1570     }
   1571     rsAllocationElementRead((RsContext)con, (RsAllocation)alloc,
   1572                             xoff, yoff, zoff,
   1573                             lod, ptr, sizeBytes, compIdx);
   1574     _env->ReleaseByteArrayElements(data, ptr, 0);
   1575 }
   1576 
   1577 // Copies from the Allocation pointed to by _alloc into the Java object data.
   1578 static void
   1579 nAllocationRead2D(JNIEnv *_env, jobject _this, jlong con, jlong _alloc, jint xoff, jint yoff, jint lod, jint _face,
   1580                   jint w, jint h, jobject data, jint sizeBytes, jint dataType,
   1581                   jint mSize, jboolean usePadding)
   1582 {
   1583     RsAllocation *alloc = (RsAllocation *)_alloc;
   1584     RsAllocationCubemapFace face = (RsAllocationCubemapFace)_face;
   1585     if (kLogApi) {
   1586         ALOGD("nAllocation2DRead, con(%p), adapter(%p), xoff(%i), yoff(%i), w(%i), h(%i), len(%i) "
   1587               "type(%i)", (RsContext)con, alloc, xoff, yoff, w, h, sizeBytes, dataType);
   1588     }
   1589     int count = w * h;
   1590     PER_ARRAY_TYPE(0, rsAllocation2DRead, false,
   1591                    (RsContext)con, alloc, xoff, yoff, lod, face, w, h, ptr, sizeBytes, 0);
   1592 }
   1593 
   1594 // Copies from the Allocation pointed to by _alloc into the Java object data.
   1595 static void
   1596 nAllocationRead3D(JNIEnv *_env, jobject _this, jlong con, jlong _alloc, jint xoff, jint yoff, jint zoff, jint lod,
   1597                   jint w, jint h, jint d, jobject data, int sizeBytes, int dataType,
   1598                   jint mSize, jboolean usePadding)
   1599 {
   1600     RsAllocation *alloc = (RsAllocation *)_alloc;
   1601     if (kLogApi) {
   1602         ALOGD("nAllocation3DRead, con(%p), alloc(%p), xoff(%i), yoff(%i), zoff(%i), lod(%i), w(%i),"
   1603               " h(%i), d(%i), sizeBytes(%i)", (RsContext)con, (RsAllocation)alloc, xoff, yoff, zoff,
   1604               lod, w, h, d, sizeBytes);
   1605     }
   1606     int count = w * h * d;
   1607     PER_ARRAY_TYPE(nullptr, rsAllocation3DRead, false,
   1608                    (RsContext)con, alloc, xoff, yoff, zoff, lod, w, h, d, ptr, sizeBytes, 0);
   1609 }
   1610 
   1611 static jlong
   1612 nAllocationGetType(JNIEnv *_env, jobject _this, jlong con, jlong a)
   1613 {
   1614     if (kLogApi) {
   1615         ALOGD("nAllocationGetType, con(%p), a(%p)", (RsContext)con, (RsAllocation)a);
   1616     }
   1617     return (jlong)(uintptr_t) rsaAllocationGetType((RsContext)con, (RsAllocation)a);
   1618 }
   1619 
   1620 static void
   1621 nAllocationResize1D(JNIEnv *_env, jobject _this, jlong con, jlong alloc, jint dimX)
   1622 {
   1623     if (kLogApi) {
   1624         ALOGD("nAllocationResize1D, con(%p), alloc(%p), sizeX(%i)", (RsContext)con,
   1625               (RsAllocation)alloc, dimX);
   1626     }
   1627     rsAllocationResize1D((RsContext)con, (RsAllocation)alloc, dimX);
   1628 }
   1629 
   1630 
   1631 static jlong
   1632 nAllocationAdapterCreate(JNIEnv *_env, jobject _this, jlong con, jlong basealloc, jlong type)
   1633 {
   1634     if (kLogApi) {
   1635         ALOGD("nAllocationAdapterCreate, con(%p), base(%p), type(%p)",
   1636               (RsContext)con, (RsAllocation)basealloc, (RsElement)type);
   1637     }
   1638     return (jlong)(uintptr_t) rsAllocationAdapterCreate((RsContext)con, (RsType)type,
   1639                                                         (RsAllocation)basealloc);
   1640 
   1641 }
   1642 
   1643 static void
   1644 nAllocationAdapterOffset(JNIEnv *_env, jobject _this, jlong con, jlong alloc,
   1645                         jint x, jint y, jint z, jint face, jint lod,
   1646                         jint a1, jint a2, jint a3, jint a4)
   1647 {
   1648     uint32_t params[] = {
   1649         (uint32_t)x, (uint32_t)y, (uint32_t)z, (uint32_t)face,
   1650         (uint32_t)lod, (uint32_t)a1, (uint32_t)a2, (uint32_t)a3, (uint32_t)a4
   1651     };
   1652     if (kLogApi) {
   1653         ALOGD("nAllocationAdapterOffset, con(%p), alloc(%p), x(%i), y(%i), z(%i), face(%i), lod(%i), arrays(%i %i %i %i)",
   1654               (RsContext)con, (RsAllocation)alloc, x, y, z, face, lod, a1, a2, a3, a4);
   1655     }
   1656     rsAllocationAdapterOffset((RsContext)con, (RsAllocation)alloc,
   1657                               params, sizeof(params));
   1658 }
   1659 
   1660 
   1661 // -----------------------------------
   1662 
   1663 static jlong
   1664 nFileA3DCreateFromAssetStream(JNIEnv *_env, jobject _this, jlong con, jlong native_asset)
   1665 {
   1666     Asset* asset = reinterpret_cast<Asset*>(native_asset);
   1667     ALOGV("______nFileA3D %p", asset);
   1668 
   1669     jlong id = (jlong)(uintptr_t)rsaFileA3DCreateFromMemory((RsContext)con, asset->getBuffer(false), asset->getLength());
   1670     return id;
   1671 }
   1672 
   1673 static jlong
   1674 nFileA3DCreateFromAsset(JNIEnv *_env, jobject _this, jlong con, jobject _assetMgr, jstring _path)
   1675 {
   1676     AssetManager* mgr = assetManagerForJavaObject(_env, _assetMgr);
   1677     if (mgr == nullptr) {
   1678         return 0;
   1679     }
   1680 
   1681     AutoJavaStringToUTF8 str(_env, _path);
   1682     Asset* asset = mgr->open(str.c_str(), Asset::ACCESS_BUFFER);
   1683     if (asset == nullptr) {
   1684         return 0;
   1685     }
   1686 
   1687     jlong id = (jlong)(uintptr_t)rsaFileA3DCreateFromAsset((RsContext)con, asset);
   1688     return id;
   1689 }
   1690 
   1691 static jlong
   1692 nFileA3DCreateFromFile(JNIEnv *_env, jobject _this, jlong con, jstring fileName)
   1693 {
   1694     AutoJavaStringToUTF8 fileNameUTF(_env, fileName);
   1695     jlong id = (jlong)(uintptr_t)rsaFileA3DCreateFromFile((RsContext)con, fileNameUTF.c_str());
   1696 
   1697     return id;
   1698 }
   1699 
   1700 static jint
   1701 nFileA3DGetNumIndexEntries(JNIEnv *_env, jobject _this, jlong con, jlong fileA3D)
   1702 {
   1703     int32_t numEntries = 0;
   1704     rsaFileA3DGetNumIndexEntries((RsContext)con, &numEntries, (RsFile)fileA3D);
   1705     return (jint)numEntries;
   1706 }
   1707 
   1708 static void
   1709 nFileA3DGetIndexEntries(JNIEnv *_env, jobject _this, jlong con, jlong fileA3D, jint numEntries, jintArray _ids, jobjectArray _entries)
   1710 {
   1711     ALOGV("______nFileA3D %p", (RsFile) fileA3D);
   1712     RsFileIndexEntry *fileEntries = (RsFileIndexEntry*)malloc((uint32_t)numEntries * sizeof(RsFileIndexEntry));
   1713 
   1714     rsaFileA3DGetIndexEntries((RsContext)con, fileEntries, (uint32_t)numEntries, (RsFile)fileA3D);
   1715 
   1716     for(jint i = 0; i < numEntries; i ++) {
   1717         _env->SetObjectArrayElement(_entries, i, _env->NewStringUTF(fileEntries[i].objectName));
   1718         _env->SetIntArrayRegion(_ids, i, 1, (const jint*)&fileEntries[i].classID);
   1719     }
   1720 
   1721     free(fileEntries);
   1722 }
   1723 
   1724 static jlong
   1725 nFileA3DGetEntryByIndex(JNIEnv *_env, jobject _this, jlong con, jlong fileA3D, jint index)
   1726 {
   1727     ALOGV("______nFileA3D %p", (RsFile) fileA3D);
   1728     jlong id = (jlong)(uintptr_t)rsaFileA3DGetEntryByIndex((RsContext)con, (uint32_t)index, (RsFile)fileA3D);
   1729     return id;
   1730 }
   1731 
   1732 // -----------------------------------
   1733 
   1734 static jlong
   1735 nFontCreateFromFile(JNIEnv *_env, jobject _this, jlong con,
   1736                     jstring fileName, jfloat fontSize, jint dpi)
   1737 {
   1738     AutoJavaStringToUTF8 fileNameUTF(_env, fileName);
   1739     jlong id = (jlong)(uintptr_t)rsFontCreateFromFile((RsContext)con,
   1740                                          fileNameUTF.c_str(), fileNameUTF.length(),
   1741                                          fontSize, dpi);
   1742 
   1743     return id;
   1744 }
   1745 
   1746 static jlong
   1747 nFontCreateFromAssetStream(JNIEnv *_env, jobject _this, jlong con,
   1748                            jstring name, jfloat fontSize, jint dpi, jlong native_asset)
   1749 {
   1750     Asset* asset = reinterpret_cast<Asset*>(native_asset);
   1751     AutoJavaStringToUTF8 nameUTF(_env, name);
   1752 
   1753     jlong id = (jlong)(uintptr_t)rsFontCreateFromMemory((RsContext)con,
   1754                                            nameUTF.c_str(), nameUTF.length(),
   1755                                            fontSize, dpi,
   1756                                            asset->getBuffer(false), asset->getLength());
   1757     return id;
   1758 }
   1759 
   1760 static jlong
   1761 nFontCreateFromAsset(JNIEnv *_env, jobject _this, jlong con, jobject _assetMgr, jstring _path,
   1762                      jfloat fontSize, jint dpi)
   1763 {
   1764     AssetManager* mgr = assetManagerForJavaObject(_env, _assetMgr);
   1765     if (mgr == nullptr) {
   1766         return 0;
   1767     }
   1768 
   1769     AutoJavaStringToUTF8 str(_env, _path);
   1770     Asset* asset = mgr->open(str.c_str(), Asset::ACCESS_BUFFER);
   1771     if (asset == nullptr) {
   1772         return 0;
   1773     }
   1774 
   1775     jlong id = (jlong)(uintptr_t)rsFontCreateFromMemory((RsContext)con,
   1776                                            str.c_str(), str.length(),
   1777                                            fontSize, dpi,
   1778                                            asset->getBuffer(false), asset->getLength());
   1779     delete asset;
   1780     return id;
   1781 }
   1782 
   1783 // -----------------------------------
   1784 
   1785 static void
   1786 nScriptBindAllocation(JNIEnv *_env, jobject _this, jlong con, jlong script, jlong alloc, jint slot)
   1787 {
   1788     if (kLogApi) {
   1789         ALOGD("nScriptBindAllocation, con(%p), script(%p), alloc(%p), slot(%i)", (RsContext)con,
   1790               (RsScript)script, (RsAllocation)alloc, slot);
   1791     }
   1792     rsScriptBindAllocation((RsContext)con, (RsScript)script, (RsAllocation)alloc, slot);
   1793 }
   1794 
   1795 static void
   1796 nScriptSetVarI(JNIEnv *_env, jobject _this, jlong con, jlong script, jint slot, jint val)
   1797 {
   1798     if (kLogApi) {
   1799         ALOGD("nScriptSetVarI, con(%p), s(%p), slot(%i), val(%i)", (RsContext)con, (void *)script,
   1800               slot, val);
   1801     }
   1802     rsScriptSetVarI((RsContext)con, (RsScript)script, slot, val);
   1803 }
   1804 
   1805 static jint
   1806 nScriptGetVarI(JNIEnv *_env, jobject _this, jlong con, jlong script, jint slot)
   1807 {
   1808     if (kLogApi) {
   1809         ALOGD("nScriptGetVarI, con(%p), s(%p), slot(%i)", (RsContext)con, (void *)script, slot);
   1810     }
   1811     int value = 0;
   1812     rsScriptGetVarV((RsContext)con, (RsScript)script, slot, &value, sizeof(value));
   1813     return value;
   1814 }
   1815 
   1816 static void
   1817 nScriptSetVarObj(JNIEnv *_env, jobject _this, jlong con, jlong script, jint slot, jlong val)
   1818 {
   1819     if (kLogApi) {
   1820         ALOGD("nScriptSetVarObj, con(%p), s(%p), slot(%i), val(%" PRId64 ")", (RsContext)con, (void *)script,
   1821               slot, val);
   1822     }
   1823     rsScriptSetVarObj((RsContext)con, (RsScript)script, slot, (RsObjectBase)val);
   1824 }
   1825 
   1826 static void
   1827 nScriptSetVarJ(JNIEnv *_env, jobject _this, jlong con, jlong script, jint slot, jlong val)
   1828 {
   1829     if (kLogApi) {
   1830         ALOGD("nScriptSetVarJ, con(%p), s(%p), slot(%i), val(%" PRId64 ")", (RsContext)con, (void *)script,
   1831               slot, val);
   1832     }
   1833     rsScriptSetVarJ((RsContext)con, (RsScript)script, slot, val);
   1834 }
   1835 
   1836 static jlong
   1837 nScriptGetVarJ(JNIEnv *_env, jobject _this, jlong con, jlong script, jint slot)
   1838 {
   1839     if (kLogApi) {
   1840         ALOGD("nScriptGetVarJ, con(%p), s(%p), slot(%i)", (RsContext)con, (void *)script, slot);
   1841     }
   1842     jlong value = 0;
   1843     rsScriptGetVarV((RsContext)con, (RsScript)script, slot, &value, sizeof(value));
   1844     return value;
   1845 }
   1846 
   1847 static void
   1848 nScriptSetVarF(JNIEnv *_env, jobject _this, jlong con, jlong script, jint slot, float val)
   1849 {
   1850     if (kLogApi) {
   1851         ALOGD("nScriptSetVarF, con(%p), s(%p), slot(%i), val(%f)", (RsContext)con, (void *)script,
   1852               slot, val);
   1853     }
   1854     rsScriptSetVarF((RsContext)con, (RsScript)script, slot, val);
   1855 }
   1856 
   1857 static jfloat
   1858 nScriptGetVarF(JNIEnv *_env, jobject _this, jlong con, jlong script, jint slot)
   1859 {
   1860     if (kLogApi) {
   1861         ALOGD("nScriptGetVarF, con(%p), s(%p), slot(%i)", (RsContext)con, (void *)script, slot);
   1862     }
   1863     jfloat value = 0;
   1864     rsScriptGetVarV((RsContext)con, (RsScript)script, slot, &value, sizeof(value));
   1865     return value;
   1866 }
   1867 
   1868 static void
   1869 nScriptSetVarD(JNIEnv *_env, jobject _this, jlong con, jlong script, jint slot, double val)
   1870 {
   1871     if (kLogApi) {
   1872         ALOGD("nScriptSetVarD, con(%p), s(%p), slot(%i), val(%lf)", (RsContext)con, (void *)script,
   1873               slot, val);
   1874     }
   1875     rsScriptSetVarD((RsContext)con, (RsScript)script, slot, val);
   1876 }
   1877 
   1878 static jdouble
   1879 nScriptGetVarD(JNIEnv *_env, jobject _this, jlong con, jlong script, jint slot)
   1880 {
   1881     if (kLogApi) {
   1882         ALOGD("nScriptGetVarD, con(%p), s(%p), slot(%i)", (RsContext)con, (void *)script, slot);
   1883     }
   1884     jdouble value = 0;
   1885     rsScriptGetVarV((RsContext)con, (RsScript)script, slot, &value, sizeof(value));
   1886     return value;
   1887 }
   1888 
   1889 static void
   1890 nScriptSetVarV(JNIEnv *_env, jobject _this, jlong con, jlong script, jint slot, jbyteArray data)
   1891 {
   1892     if (kLogApi) {
   1893         ALOGD("nScriptSetVarV, con(%p), s(%p), slot(%i)", (RsContext)con, (void *)script, slot);
   1894     }
   1895     jint len = _env->GetArrayLength(data);
   1896     jbyte *ptr = _env->GetByteArrayElements(data, nullptr);
   1897     if (ptr == nullptr) {
   1898         ALOGE("Failed to get Java array elements");
   1899         return;
   1900     }
   1901     rsScriptSetVarV((RsContext)con, (RsScript)script, slot, ptr, len);
   1902     _env->ReleaseByteArrayElements(data, ptr, JNI_ABORT);
   1903 }
   1904 
   1905 static void
   1906 nScriptGetVarV(JNIEnv *_env, jobject _this, jlong con, jlong script, jint slot, jbyteArray data)
   1907 {
   1908     if (kLogApi) {
   1909         ALOGD("nScriptSetVarV, con(%p), s(%p), slot(%i)", (RsContext)con, (void *)script, slot);
   1910     }
   1911     jint len = _env->GetArrayLength(data);
   1912     jbyte *ptr = _env->GetByteArrayElements(data, nullptr);
   1913     if (ptr == nullptr) {
   1914         ALOGE("Failed to get Java array elements");
   1915         return;
   1916     }
   1917     rsScriptGetVarV((RsContext)con, (RsScript)script, slot, ptr, len);
   1918     _env->ReleaseByteArrayElements(data, ptr, 0);
   1919 }
   1920 
   1921 static void
   1922 nScriptSetVarVE(JNIEnv *_env, jobject _this, jlong con, jlong script, jint slot, jbyteArray data,
   1923                 jlong elem, jintArray dims)
   1924 {
   1925     if (kLogApi) {
   1926         ALOGD("nScriptSetVarVE, con(%p), s(%p), slot(%i)", (RsContext)con, (void *)script, slot);
   1927     }
   1928     jint len = _env->GetArrayLength(data);
   1929     jbyte *ptr = _env->GetByteArrayElements(data, nullptr);
   1930     if (ptr == nullptr) {
   1931         ALOGE("Failed to get Java array elements");
   1932         return;
   1933     }
   1934     jint dimsLen = _env->GetArrayLength(dims) * sizeof(int);
   1935     jint *dimsPtr = _env->GetIntArrayElements(dims, nullptr);
   1936     if (dimsPtr == nullptr) {
   1937         ALOGE("Failed to get Java array elements");
   1938         return;
   1939     }
   1940     rsScriptSetVarVE((RsContext)con, (RsScript)script, slot, ptr, len, (RsElement)elem,
   1941                      (const uint32_t*) dimsPtr, dimsLen);
   1942     _env->ReleaseByteArrayElements(data, ptr, JNI_ABORT);
   1943     _env->ReleaseIntArrayElements(dims, dimsPtr, JNI_ABORT);
   1944 }
   1945 
   1946 
   1947 static void
   1948 nScriptSetTimeZone(JNIEnv *_env, jobject _this, jlong con, jlong script, jbyteArray timeZone)
   1949 {
   1950     if (kLogApi) {
   1951         ALOGD("nScriptCSetTimeZone, con(%p), s(%p)", (RsContext)con, (void *)script);
   1952     }
   1953 
   1954     jint length = _env->GetArrayLength(timeZone);
   1955     jbyte* timeZone_ptr;
   1956     timeZone_ptr = (jbyte *) _env->GetPrimitiveArrayCritical(timeZone, (jboolean *)0);
   1957     if (timeZone_ptr == nullptr) {
   1958         ALOGE("Failed to get Java array elements");
   1959         return;
   1960     }
   1961 
   1962     rsScriptSetTimeZone((RsContext)con, (RsScript)script, (const char *)timeZone_ptr, length);
   1963 
   1964     if (timeZone_ptr) {
   1965         _env->ReleasePrimitiveArrayCritical(timeZone, timeZone_ptr, 0);
   1966     }
   1967 }
   1968 
   1969 static void
   1970 nScriptInvoke(JNIEnv *_env, jobject _this, jlong con, jlong obj, jint slot)
   1971 {
   1972     if (kLogApi) {
   1973         ALOGD("nScriptInvoke, con(%p), script(%p)", (RsContext)con, (void *)obj);
   1974     }
   1975     rsScriptInvoke((RsContext)con, (RsScript)obj, slot);
   1976 }
   1977 
   1978 static void
   1979 nScriptInvokeV(JNIEnv *_env, jobject _this, jlong con, jlong script, jint slot, jbyteArray data)
   1980 {
   1981     if (kLogApi) {
   1982         ALOGD("nScriptInvokeV, con(%p), s(%p), slot(%i)", (RsContext)con, (void *)script, slot);
   1983     }
   1984     jint len = _env->GetArrayLength(data);
   1985     jbyte *ptr = _env->GetByteArrayElements(data, nullptr);
   1986     if (ptr == nullptr) {
   1987         ALOGE("Failed to get Java array elements");
   1988         return;
   1989     }
   1990     rsScriptInvokeV((RsContext)con, (RsScript)script, slot, ptr, len);
   1991     _env->ReleaseByteArrayElements(data, ptr, JNI_ABORT);
   1992 }
   1993 
   1994 static void
   1995 nScriptForEach(JNIEnv *_env, jobject _this, jlong con, jlong script, jint slot,
   1996                jlongArray ains, jlong aout, jbyteArray params,
   1997                jintArray limits)
   1998 {
   1999     if (kLogApi) {
   2000         ALOGD("nScriptForEach, con(%p), s(%p), slot(%i) ains(%p) aout(%" PRId64 ")", (RsContext)con, (void *)script, slot, ains, aout);
   2001     }
   2002 
   2003     jint   in_len = 0;
   2004     jlong *in_ptr = nullptr;
   2005 
   2006     RsAllocation *in_allocs = nullptr;
   2007 
   2008     if (ains != nullptr) {
   2009         in_len = _env->GetArrayLength(ains);
   2010         if (in_len > (jint)RS_KERNEL_MAX_ARGUMENTS) {
   2011             ALOGE("Too many arguments in kernel launch.");
   2012             // TODO (b/20758983): Report back to Java and throw an exception
   2013             return;
   2014         }
   2015 
   2016         in_ptr = _env->GetLongArrayElements(ains, nullptr);
   2017         if (in_ptr == nullptr) {
   2018             ALOGE("Failed to get Java array elements");
   2019             return;
   2020         }
   2021 
   2022         if (sizeof(RsAllocation) == sizeof(jlong)) {
   2023             in_allocs = (RsAllocation*)in_ptr;
   2024         } else {
   2025             // Convert from 64-bit jlong types to the native pointer type.
   2026 
   2027             in_allocs = (RsAllocation*)alloca(in_len * sizeof(RsAllocation));
   2028             if (in_allocs == nullptr) {
   2029                 ALOGE("Failed launching kernel for lack of memory.");
   2030                 _env->ReleaseLongArrayElements(ains, in_ptr, JNI_ABORT);
   2031                 return;
   2032             }
   2033 
   2034             for (int index = in_len; --index >= 0;) {
   2035                 in_allocs[index] = (RsAllocation)in_ptr[index];
   2036             }
   2037         }
   2038     }
   2039 
   2040     jint   param_len = 0;
   2041     jbyte *param_ptr = nullptr;
   2042 
   2043     if (params != nullptr) {
   2044         param_len = _env->GetArrayLength(params);
   2045         param_ptr = _env->GetByteArrayElements(params, nullptr);
   2046         if (param_ptr == nullptr) {
   2047             ALOGE("Failed to get Java array elements");
   2048             return;
   2049         }
   2050     }
   2051 
   2052     RsScriptCall sc, *sca = nullptr;
   2053     uint32_t sc_size = 0;
   2054 
   2055     jint  limit_len = 0;
   2056     jint *limit_ptr = nullptr;
   2057 
   2058     if (limits != nullptr) {
   2059         limit_len = _env->GetArrayLength(limits);
   2060         limit_ptr = _env->GetIntArrayElements(limits, nullptr);
   2061         if (limit_ptr == nullptr) {
   2062             ALOGE("Failed to get Java array elements");
   2063             return;
   2064         }
   2065 
   2066         assert(limit_len == 6);
   2067         UNUSED(limit_len);  // As the assert might not be compiled.
   2068 
   2069         sc.xStart     = limit_ptr[0];
   2070         sc.xEnd       = limit_ptr[1];
   2071         sc.yStart     = limit_ptr[2];
   2072         sc.yEnd       = limit_ptr[3];
   2073         sc.zStart     = limit_ptr[4];
   2074         sc.zEnd       = limit_ptr[5];
   2075         sc.strategy   = RS_FOR_EACH_STRATEGY_DONT_CARE;
   2076         sc.arrayStart = 0;
   2077         sc.arrayEnd = 0;
   2078         sc.array2Start = 0;
   2079         sc.array2End = 0;
   2080         sc.array3Start = 0;
   2081         sc.array3End = 0;
   2082         sc.array4Start = 0;
   2083         sc.array4End = 0;
   2084 
   2085         sca = &sc;
   2086         // sc_size is required, but unused, by the runtime and drivers.
   2087         sc_size = sizeof(sc);
   2088     }
   2089 
   2090     rsScriptForEachMulti((RsContext)con, (RsScript)script, slot,
   2091                          in_allocs, in_len, (RsAllocation)aout,
   2092                          param_ptr, param_len, sca, sc_size);
   2093 
   2094     if (ains != nullptr) {
   2095         _env->ReleaseLongArrayElements(ains, in_ptr, JNI_ABORT);
   2096     }
   2097 
   2098     if (params != nullptr) {
   2099         _env->ReleaseByteArrayElements(params, param_ptr, JNI_ABORT);
   2100     }
   2101 
   2102     if (limits != nullptr) {
   2103         _env->ReleaseIntArrayElements(limits, limit_ptr, JNI_ABORT);
   2104     }
   2105 }
   2106 
   2107 static void
   2108 nScriptReduce(JNIEnv *_env, jobject _this, jlong con, jlong script, jint slot,
   2109               jlongArray ains, jlong aout, jintArray limits)
   2110 {
   2111     if (kLogApi) {
   2112         ALOGD("nScriptReduce, con(%p), s(%p), slot(%i) ains(%p) aout(%" PRId64 ")", (RsContext)con, (void *)script, slot, ains, aout);
   2113     }
   2114 
   2115     if (ains == nullptr) {
   2116         ALOGE("At least one input required.");
   2117         // TODO (b/20758983): Report back to Java and throw an exception
   2118         return;
   2119     }
   2120     jint in_len = _env->GetArrayLength(ains);
   2121     if (in_len > (jint)RS_KERNEL_MAX_ARGUMENTS) {
   2122         ALOGE("Too many arguments in kernel launch.");
   2123         // TODO (b/20758983): Report back to Java and throw an exception
   2124         return;
   2125     }
   2126 
   2127     jlong *in_ptr = _env->GetLongArrayElements(ains, nullptr);
   2128     if (in_ptr == nullptr) {
   2129         ALOGE("Failed to get Java array elements");
   2130         // TODO (b/20758983): Report back to Java and throw an exception
   2131         return;
   2132     }
   2133 
   2134     RsAllocation *in_allocs = nullptr;
   2135     if (sizeof(RsAllocation) == sizeof(jlong)) {
   2136         in_allocs = (RsAllocation*)in_ptr;
   2137     } else {
   2138         // Convert from 64-bit jlong types to the native pointer type.
   2139 
   2140         in_allocs = (RsAllocation*)alloca(in_len * sizeof(RsAllocation));
   2141         if (in_allocs == nullptr) {
   2142             ALOGE("Failed launching kernel for lack of memory.");
   2143             // TODO (b/20758983): Report back to Java and throw an exception
   2144             _env->ReleaseLongArrayElements(ains, in_ptr, JNI_ABORT);
   2145             return;
   2146         }
   2147 
   2148         for (int index = in_len; --index >= 0;) {
   2149             in_allocs[index] = (RsAllocation)in_ptr[index];
   2150         }
   2151     }
   2152 
   2153     RsScriptCall sc, *sca = nullptr;
   2154     uint32_t sc_size = 0;
   2155 
   2156     jint  limit_len = 0;
   2157     jint *limit_ptr = nullptr;
   2158 
   2159     if (limits != nullptr) {
   2160         limit_len = _env->GetArrayLength(limits);
   2161         limit_ptr = _env->GetIntArrayElements(limits, nullptr);
   2162         if (limit_ptr == nullptr) {
   2163             ALOGE("Failed to get Java array elements");
   2164             // TODO (b/20758983): Report back to Java and throw an exception
   2165             return;
   2166         }
   2167 
   2168         assert(limit_len == 6);
   2169         UNUSED(limit_len);  // As the assert might not be compiled.
   2170 
   2171         sc.xStart     = limit_ptr[0];
   2172         sc.xEnd       = limit_ptr[1];
   2173         sc.yStart     = limit_ptr[2];
   2174         sc.yEnd       = limit_ptr[3];
   2175         sc.zStart     = limit_ptr[4];
   2176         sc.zEnd       = limit_ptr[5];
   2177         sc.strategy   = RS_FOR_EACH_STRATEGY_DONT_CARE;
   2178         sc.arrayStart = 0;
   2179         sc.arrayEnd = 0;
   2180         sc.array2Start = 0;
   2181         sc.array2End = 0;
   2182         sc.array3Start = 0;
   2183         sc.array3End = 0;
   2184         sc.array4Start = 0;
   2185         sc.array4End = 0;
   2186 
   2187         sca = &sc;
   2188         sc_size = sizeof(sc);
   2189     }
   2190 
   2191     rsScriptReduce((RsContext)con, (RsScript)script, slot,
   2192                    in_allocs, in_len, (RsAllocation)aout,
   2193                    sca, sc_size);
   2194 
   2195     _env->ReleaseLongArrayElements(ains, in_ptr, JNI_ABORT);
   2196 
   2197     if (limits != nullptr) {
   2198         _env->ReleaseIntArrayElements(limits, limit_ptr, JNI_ABORT);
   2199     }
   2200 }
   2201 
   2202 // -----------------------------------
   2203 
   2204 static jlong
   2205 nScriptCCreate(JNIEnv *_env, jobject _this, jlong con,
   2206                jstring resName, jstring cacheDir,
   2207                jbyteArray scriptRef, jint length)
   2208 {
   2209     if (kLogApi) {
   2210         ALOGD("nScriptCCreate, con(%p)", (RsContext)con);
   2211     }
   2212 
   2213     AutoJavaStringToUTF8 resNameUTF(_env, resName);
   2214     AutoJavaStringToUTF8 cacheDirUTF(_env, cacheDir);
   2215     jlong ret = 0;
   2216     jbyte* script_ptr = nullptr;
   2217     jint _exception = 0;
   2218     jint remaining;
   2219     if (!scriptRef) {
   2220         _exception = 1;
   2221         //jniThrowException(_env, "java/lang/IllegalArgumentException", "script == null");
   2222         goto exit;
   2223     }
   2224     if (length < 0) {
   2225         _exception = 1;
   2226         //jniThrowException(_env, "java/lang/IllegalArgumentException", "length < 0");
   2227         goto exit;
   2228     }
   2229     remaining = _env->GetArrayLength(scriptRef);
   2230     if (remaining < length) {
   2231         _exception = 1;
   2232         //jniThrowException(_env, "java/lang/IllegalArgumentException",
   2233         //        "length > script.length - offset");
   2234         goto exit;
   2235     }
   2236     script_ptr = (jbyte *)
   2237         _env->GetPrimitiveArrayCritical(scriptRef, (jboolean *)0);
   2238     if (script_ptr == nullptr) {
   2239         ALOGE("Failed to get Java array elements");
   2240         return ret;
   2241     }
   2242 
   2243     //rsScriptCSetText((RsContext)con, (const char *)script_ptr, length);
   2244 
   2245     ret = (jlong)(uintptr_t)rsScriptCCreate((RsContext)con,
   2246                                 resNameUTF.c_str(), resNameUTF.length(),
   2247                                 cacheDirUTF.c_str(), cacheDirUTF.length(),
   2248                                 (const char *)script_ptr, length);
   2249 
   2250 exit:
   2251     if (script_ptr) {
   2252         _env->ReleasePrimitiveArrayCritical(scriptRef, script_ptr,
   2253                 _exception ? JNI_ABORT: 0);
   2254     }
   2255 
   2256     return (jlong)(uintptr_t)ret;
   2257 }
   2258 
   2259 static jlong
   2260 nScriptIntrinsicCreate(JNIEnv *_env, jobject _this, jlong con, jint id, jlong eid)
   2261 {
   2262     if (kLogApi) {
   2263         ALOGD("nScriptIntrinsicCreate, con(%p) id(%i) element(%p)", (RsContext)con, id,
   2264               (void *)eid);
   2265     }
   2266     return (jlong)(uintptr_t)rsScriptIntrinsicCreate((RsContext)con, id, (RsElement)eid);
   2267 }
   2268 
   2269 static jlong
   2270 nScriptKernelIDCreate(JNIEnv *_env, jobject _this, jlong con, jlong sid, jint slot, jint sig)
   2271 {
   2272     if (kLogApi) {
   2273         ALOGD("nScriptKernelIDCreate, con(%p) script(%p), slot(%i), sig(%i)", (RsContext)con,
   2274               (void *)sid, slot, sig);
   2275     }
   2276     return (jlong)(uintptr_t)rsScriptKernelIDCreate((RsContext)con, (RsScript)sid, slot, sig);
   2277 }
   2278 
   2279 static jlong
   2280 nScriptInvokeIDCreate(JNIEnv *_env, jobject _this, jlong con, jlong sid, jint slot)
   2281 {
   2282     if (kLogApi) {
   2283         ALOGD("nScriptInvokeIDCreate, con(%p) script(%p), slot(%i)", (RsContext)con,
   2284               (void *)sid, slot);
   2285     }
   2286     return (jlong)(uintptr_t)rsScriptInvokeIDCreate((RsContext)con, (RsScript)sid, slot);
   2287 }
   2288 
   2289 static jlong
   2290 nScriptFieldIDCreate(JNIEnv *_env, jobject _this, jlong con, jlong sid, jint slot)
   2291 {
   2292     if (kLogApi) {
   2293         ALOGD("nScriptFieldIDCreate, con(%p) script(%p), slot(%i)", (RsContext)con, (void *)sid,
   2294               slot);
   2295     }
   2296     return (jlong)(uintptr_t)rsScriptFieldIDCreate((RsContext)con, (RsScript)sid, slot);
   2297 }
   2298 
   2299 static jlong
   2300 nScriptGroupCreate(JNIEnv *_env, jobject _this, jlong con, jlongArray _kernels, jlongArray _src,
   2301     jlongArray _dstk, jlongArray _dstf, jlongArray _types)
   2302 {
   2303     if (kLogApi) {
   2304         ALOGD("nScriptGroupCreate, con(%p)", (RsContext)con);
   2305     }
   2306 
   2307     jlong id = 0;
   2308 
   2309     RsScriptKernelID* kernelsPtr;
   2310     jint kernelsLen = _env->GetArrayLength(_kernels);
   2311     jlong *jKernelsPtr = _env->GetLongArrayElements(_kernels, nullptr);
   2312 
   2313     RsScriptKernelID* srcPtr;
   2314     jint srcLen = _env->GetArrayLength(_src);
   2315     jlong *jSrcPtr = _env->GetLongArrayElements(_src, nullptr);
   2316 
   2317     RsScriptKernelID* dstkPtr;
   2318     jint dstkLen = _env->GetArrayLength(_dstk);
   2319     jlong *jDstkPtr = _env->GetLongArrayElements(_dstk, nullptr);
   2320 
   2321     RsScriptKernelID* dstfPtr;
   2322     jint dstfLen = _env->GetArrayLength(_dstf);
   2323     jlong *jDstfPtr = _env->GetLongArrayElements(_dstf, nullptr);
   2324 
   2325     RsType* typesPtr;
   2326     jint typesLen = _env->GetArrayLength(_types);
   2327     jlong *jTypesPtr = _env->GetLongArrayElements(_types, nullptr);
   2328 
   2329     if (jKernelsPtr == nullptr) {
   2330         ALOGE("Failed to get Java array elements: kernels");
   2331         goto cleanup;
   2332     }
   2333     if (jSrcPtr == nullptr) {
   2334         ALOGE("Failed to get Java array elements: src");
   2335         goto cleanup;
   2336     }
   2337     if (jDstkPtr == nullptr) {
   2338         ALOGE("Failed to get Java array elements: dstk");
   2339         goto cleanup;
   2340     }
   2341     if (jDstfPtr == nullptr) {
   2342         ALOGE("Failed to get Java array elements: dstf");
   2343         goto cleanup;
   2344     }
   2345     if (jTypesPtr == nullptr) {
   2346         ALOGE("Failed to get Java array elements: types");
   2347         goto cleanup;
   2348     }
   2349 
   2350     kernelsPtr = (RsScriptKernelID*) malloc(sizeof(RsScriptKernelID) * kernelsLen);
   2351     for(int i = 0; i < kernelsLen; ++i) {
   2352         kernelsPtr[i] = (RsScriptKernelID)jKernelsPtr[i];
   2353     }
   2354 
   2355     srcPtr = (RsScriptKernelID*) malloc(sizeof(RsScriptKernelID) * srcLen);
   2356     for(int i = 0; i < srcLen; ++i) {
   2357         srcPtr[i] = (RsScriptKernelID)jSrcPtr[i];
   2358     }
   2359 
   2360     dstkPtr = (RsScriptKernelID*) malloc(sizeof(RsScriptKernelID) * dstkLen);
   2361     for(int i = 0; i < dstkLen; ++i) {
   2362         dstkPtr[i] = (RsScriptKernelID)jDstkPtr[i];
   2363     }
   2364 
   2365     dstfPtr = (RsScriptKernelID*) malloc(sizeof(RsScriptKernelID) * dstfLen);
   2366     for(int i = 0; i < dstfLen; ++i) {
   2367         dstfPtr[i] = (RsScriptKernelID)jDstfPtr[i];
   2368     }
   2369 
   2370     typesPtr = (RsType*) malloc(sizeof(RsType) * typesLen);
   2371     for(int i = 0; i < typesLen; ++i) {
   2372         typesPtr[i] = (RsType)jTypesPtr[i];
   2373     }
   2374 
   2375     id = (jlong)(uintptr_t)rsScriptGroupCreate((RsContext)con,
   2376                                (RsScriptKernelID *)kernelsPtr, kernelsLen * sizeof(RsScriptKernelID),
   2377                                (RsScriptKernelID *)srcPtr, srcLen * sizeof(RsScriptKernelID),
   2378                                (RsScriptKernelID *)dstkPtr, dstkLen * sizeof(RsScriptKernelID),
   2379                                (RsScriptFieldID *)dstfPtr, dstfLen * sizeof(RsScriptKernelID),
   2380                                (RsType *)typesPtr, typesLen * sizeof(RsType));
   2381 
   2382     free(kernelsPtr);
   2383     free(srcPtr);
   2384     free(dstkPtr);
   2385     free(dstfPtr);
   2386     free(typesPtr);
   2387 
   2388 cleanup:
   2389     if (jKernelsPtr != nullptr) {
   2390         _env->ReleaseLongArrayElements(_kernels, jKernelsPtr, 0);
   2391     }
   2392     if (jSrcPtr != nullptr) {
   2393         _env->ReleaseLongArrayElements(_src, jSrcPtr, 0);
   2394     }
   2395     if (jDstkPtr != nullptr) {
   2396         _env->ReleaseLongArrayElements(_dstk, jDstkPtr, 0);
   2397     }
   2398     if (jDstfPtr != nullptr) {
   2399         _env->ReleaseLongArrayElements(_dstf, jDstfPtr, 0);
   2400     }
   2401     if (jTypesPtr != nullptr) {
   2402         _env->ReleaseLongArrayElements(_types, jTypesPtr, 0);
   2403     }
   2404 
   2405     return id;
   2406 }
   2407 
   2408 static void
   2409 nScriptGroupSetInput(JNIEnv *_env, jobject _this, jlong con, jlong gid, jlong kid, jlong alloc)
   2410 {
   2411     if (kLogApi) {
   2412         ALOGD("nScriptGroupSetInput, con(%p) group(%p), kernelId(%p), alloc(%p)", (RsContext)con,
   2413               (void *)gid, (void *)kid, (void *)alloc);
   2414     }
   2415     rsScriptGroupSetInput((RsContext)con, (RsScriptGroup)gid, (RsScriptKernelID)kid, (RsAllocation)alloc);
   2416 }
   2417 
   2418 static void
   2419 nScriptGroupSetOutput(JNIEnv *_env, jobject _this, jlong con, jlong gid, jlong kid, jlong alloc)
   2420 {
   2421     if (kLogApi) {
   2422         ALOGD("nScriptGroupSetOutput, con(%p) group(%p), kernelId(%p), alloc(%p)", (RsContext)con,
   2423               (void *)gid, (void *)kid, (void *)alloc);
   2424     }
   2425     rsScriptGroupSetOutput((RsContext)con, (RsScriptGroup)gid, (RsScriptKernelID)kid, (RsAllocation)alloc);
   2426 }
   2427 
   2428 static void
   2429 nScriptGroupExecute(JNIEnv *_env, jobject _this, jlong con, jlong gid)
   2430 {
   2431     if (kLogApi) {
   2432         ALOGD("nScriptGroupSetOutput, con(%p) group(%p)", (RsContext)con, (void *)gid);
   2433     }
   2434     rsScriptGroupExecute((RsContext)con, (RsScriptGroup)gid);
   2435 }
   2436 
   2437 // ---------------------------------------------------------------------------
   2438 
   2439 static jlong
   2440 nProgramStoreCreate(JNIEnv *_env, jobject _this, jlong con,
   2441                     jboolean colorMaskR, jboolean colorMaskG, jboolean colorMaskB, jboolean colorMaskA,
   2442                     jboolean depthMask, jboolean ditherEnable,
   2443                     jint srcFunc, jint destFunc,
   2444                     jint depthFunc)
   2445 {
   2446     if (kLogApi) {
   2447         ALOGD("nProgramStoreCreate, con(%p)", (RsContext)con);
   2448     }
   2449     return (jlong)(uintptr_t)rsProgramStoreCreate((RsContext)con, colorMaskR, colorMaskG, colorMaskB, colorMaskA,
   2450                                       depthMask, ditherEnable, (RsBlendSrcFunc)srcFunc,
   2451                                       (RsBlendDstFunc)destFunc, (RsDepthFunc)depthFunc);
   2452 }
   2453 
   2454 // ---------------------------------------------------------------------------
   2455 
   2456 static void
   2457 nProgramBindConstants(JNIEnv *_env, jobject _this, jlong con, jlong vpv, jint slot, jlong a)
   2458 {
   2459     if (kLogApi) {
   2460         ALOGD("nProgramBindConstants, con(%p), vpf(%p), sloat(%i), a(%p)", (RsContext)con,
   2461               (RsProgramVertex)vpv, slot, (RsAllocation)a);
   2462     }
   2463     rsProgramBindConstants((RsContext)con, (RsProgram)vpv, slot, (RsAllocation)a);
   2464 }
   2465 
   2466 static void
   2467 nProgramBindTexture(JNIEnv *_env, jobject _this, jlong con, jlong vpf, jint slot, jlong a)
   2468 {
   2469     if (kLogApi) {
   2470         ALOGD("nProgramBindTexture, con(%p), vpf(%p), slot(%i), a(%p)", (RsContext)con,
   2471               (RsProgramFragment)vpf, slot, (RsAllocation)a);
   2472     }
   2473     rsProgramBindTexture((RsContext)con, (RsProgramFragment)vpf, slot, (RsAllocation)a);
   2474 }
   2475 
   2476 static void
   2477 nProgramBindSampler(JNIEnv *_env, jobject _this, jlong con, jlong vpf, jint slot, jlong a)
   2478 {
   2479     if (kLogApi) {
   2480         ALOGD("nProgramBindSampler, con(%p), vpf(%p), slot(%i), a(%p)", (RsContext)con,
   2481               (RsProgramFragment)vpf, slot, (RsSampler)a);
   2482     }
   2483     rsProgramBindSampler((RsContext)con, (RsProgramFragment)vpf, slot, (RsSampler)a);
   2484 }
   2485 
   2486 // ---------------------------------------------------------------------------
   2487 
   2488 static jlong
   2489 nProgramFragmentCreate(JNIEnv *_env, jobject _this, jlong con, jstring shader,
   2490                        jobjectArray texNames, jlongArray params)
   2491 {
   2492     AutoJavaStringToUTF8 shaderUTF(_env, shader);
   2493     jlong *jParamPtr = _env->GetLongArrayElements(params, nullptr);
   2494     jint paramLen = _env->GetArrayLength(params);
   2495     if (jParamPtr == nullptr) {
   2496         ALOGE("Failed to get Java array elements");
   2497         return 0;
   2498     }
   2499 
   2500     int texCount = _env->GetArrayLength(texNames);
   2501     AutoJavaStringArrayToUTF8 names(_env, texNames, texCount);
   2502     const char ** nameArray = names.c_str();
   2503     size_t* sizeArray = names.c_str_len();
   2504 
   2505     if (kLogApi) {
   2506         ALOGD("nProgramFragmentCreate, con(%p), paramLen(%i)", (RsContext)con, paramLen);
   2507     }
   2508 
   2509     uintptr_t * paramPtr = (uintptr_t*) malloc(sizeof(uintptr_t) * paramLen);
   2510     for(int i = 0; i < paramLen; ++i) {
   2511         paramPtr[i] = (uintptr_t)jParamPtr[i];
   2512     }
   2513     jlong ret = (jlong)(uintptr_t)rsProgramFragmentCreate((RsContext)con, shaderUTF.c_str(), shaderUTF.length(),
   2514                                              nameArray, texCount, sizeArray,
   2515                                              paramPtr, paramLen);
   2516 
   2517     free(paramPtr);
   2518     _env->ReleaseLongArrayElements(params, jParamPtr, JNI_ABORT);
   2519     return ret;
   2520 }
   2521 
   2522 
   2523 // ---------------------------------------------------------------------------
   2524 
   2525 static jlong
   2526 nProgramVertexCreate(JNIEnv *_env, jobject _this, jlong con, jstring shader,
   2527                      jobjectArray texNames, jlongArray params)
   2528 {
   2529     AutoJavaStringToUTF8 shaderUTF(_env, shader);
   2530     jlong *jParamPtr = _env->GetLongArrayElements(params, nullptr);
   2531     jint paramLen = _env->GetArrayLength(params);
   2532     if (jParamPtr == nullptr) {
   2533         ALOGE("Failed to get Java array elements");
   2534         return 0;
   2535     }
   2536 
   2537     if (kLogApi) {
   2538         ALOGD("nProgramVertexCreate, con(%p), paramLen(%i)", (RsContext)con, paramLen);
   2539     }
   2540 
   2541     int texCount = _env->GetArrayLength(texNames);
   2542     AutoJavaStringArrayToUTF8 names(_env, texNames, texCount);
   2543     const char ** nameArray = names.c_str();
   2544     size_t* sizeArray = names.c_str_len();
   2545 
   2546     uintptr_t * paramPtr = (uintptr_t*) malloc(sizeof(uintptr_t) * paramLen);
   2547     for(int i = 0; i < paramLen; ++i) {
   2548         paramPtr[i] = (uintptr_t)jParamPtr[i];
   2549     }
   2550 
   2551     jlong ret = (jlong)(uintptr_t)rsProgramVertexCreate((RsContext)con, shaderUTF.c_str(), shaderUTF.length(),
   2552                                            nameArray, texCount, sizeArray,
   2553                                            paramPtr, paramLen);
   2554 
   2555     free(paramPtr);
   2556     _env->ReleaseLongArrayElements(params, jParamPtr, JNI_ABORT);
   2557     return ret;
   2558 }
   2559 
   2560 // ---------------------------------------------------------------------------
   2561 
   2562 static jlong
   2563 nProgramRasterCreate(JNIEnv *_env, jobject _this, jlong con, jboolean pointSprite, jint cull)
   2564 {
   2565     if (kLogApi) {
   2566         ALOGD("nProgramRasterCreate, con(%p), pointSprite(%i), cull(%i)", (RsContext)con,
   2567               pointSprite, cull);
   2568     }
   2569     return (jlong)(uintptr_t)rsProgramRasterCreate((RsContext)con, pointSprite, (RsCullMode)cull);
   2570 }
   2571 
   2572 
   2573 // ---------------------------------------------------------------------------
   2574 
   2575 static void
   2576 nContextBindRootScript(JNIEnv *_env, jobject _this, jlong con, jlong script)
   2577 {
   2578     if (kLogApi) {
   2579         ALOGD("nContextBindRootScript, con(%p), script(%p)", (RsContext)con, (RsScript)script);
   2580     }
   2581     rsContextBindRootScript((RsContext)con, (RsScript)script);
   2582 }
   2583 
   2584 static void
   2585 nContextBindProgramStore(JNIEnv *_env, jobject _this, jlong con, jlong pfs)
   2586 {
   2587     if (kLogApi) {
   2588         ALOGD("nContextBindProgramStore, con(%p), pfs(%p)", (RsContext)con, (RsProgramStore)pfs);
   2589     }
   2590     rsContextBindProgramStore((RsContext)con, (RsProgramStore)pfs);
   2591 }
   2592 
   2593 static void
   2594 nContextBindProgramFragment(JNIEnv *_env, jobject _this, jlong con, jlong pf)
   2595 {
   2596     if (kLogApi) {
   2597         ALOGD("nContextBindProgramFragment, con(%p), pf(%p)", (RsContext)con,
   2598               (RsProgramFragment)pf);
   2599     }
   2600     rsContextBindProgramFragment((RsContext)con, (RsProgramFragment)pf);
   2601 }
   2602 
   2603 static void
   2604 nContextBindProgramVertex(JNIEnv *_env, jobject _this, jlong con, jlong pf)
   2605 {
   2606     if (kLogApi) {
   2607         ALOGD("nContextBindProgramVertex, con(%p), pf(%p)", (RsContext)con, (RsProgramVertex)pf);
   2608     }
   2609     rsContextBindProgramVertex((RsContext)con, (RsProgramVertex)pf);
   2610 }
   2611 
   2612 static void
   2613 nContextBindProgramRaster(JNIEnv *_env, jobject _this, jlong con, jlong pf)
   2614 {
   2615     if (kLogApi) {
   2616         ALOGD("nContextBindProgramRaster, con(%p), pf(%p)", (RsContext)con, (RsProgramRaster)pf);
   2617     }
   2618     rsContextBindProgramRaster((RsContext)con, (RsProgramRaster)pf);
   2619 }
   2620 
   2621 
   2622 // ---------------------------------------------------------------------------
   2623 
   2624 static jlong
   2625 nSamplerCreate(JNIEnv *_env, jobject _this, jlong con, jint magFilter, jint minFilter,
   2626                jint wrapS, jint wrapT, jint wrapR, jfloat aniso)
   2627 {
   2628     if (kLogApi) {
   2629         ALOGD("nSamplerCreate, con(%p)", (RsContext)con);
   2630     }
   2631     return (jlong)(uintptr_t)rsSamplerCreate((RsContext)con,
   2632                                  (RsSamplerValue)magFilter,
   2633                                  (RsSamplerValue)minFilter,
   2634                                  (RsSamplerValue)wrapS,
   2635                                  (RsSamplerValue)wrapT,
   2636                                  (RsSamplerValue)wrapR,
   2637                                  aniso);
   2638 }
   2639 
   2640 // ---------------------------------------------------------------------------
   2641 
   2642 static jlong
   2643 nMeshCreate(JNIEnv *_env, jobject _this, jlong con, jlongArray _vtx, jlongArray _idx, jintArray _prim)
   2644 {
   2645     if (kLogApi) {
   2646         ALOGD("nMeshCreate, con(%p)", (RsContext)con);
   2647     }
   2648 
   2649     jlong id = 0;
   2650 
   2651     RsAllocation* vtxPtr;
   2652     jint vtxLen = _env->GetArrayLength(_vtx);
   2653     jlong *jVtxPtr = _env->GetLongArrayElements(_vtx, nullptr);
   2654 
   2655     RsAllocation* idxPtr;
   2656     jint idxLen = _env->GetArrayLength(_idx);
   2657     jlong *jIdxPtr = _env->GetLongArrayElements(_idx, nullptr);
   2658 
   2659     jint primLen = _env->GetArrayLength(_prim);
   2660     jint *primPtr = _env->GetIntArrayElements(_prim, nullptr);
   2661 
   2662     if (jVtxPtr == nullptr) {
   2663         ALOGE("Failed to get Java array elements: vtx");
   2664         goto cleanupMesh;
   2665     }
   2666     if (jIdxPtr == nullptr) {
   2667         ALOGE("Failed to get Java array elements: idx");
   2668         goto cleanupMesh;
   2669     }
   2670     if (primPtr == nullptr) {
   2671         ALOGE("Failed to get Java array elements: prim");
   2672         goto cleanupMesh;
   2673     }
   2674 
   2675     vtxPtr = (RsAllocation*) malloc(sizeof(RsAllocation) * vtxLen);
   2676     for(int i = 0; i < vtxLen; ++i) {
   2677         vtxPtr[i] = (RsAllocation)(uintptr_t)jVtxPtr[i];
   2678     }
   2679 
   2680     idxPtr = (RsAllocation*) malloc(sizeof(RsAllocation) * idxLen);
   2681     for(int i = 0; i < idxLen; ++i) {
   2682         idxPtr[i] = (RsAllocation)(uintptr_t)jIdxPtr[i];
   2683     }
   2684 
   2685     id = (jlong)(uintptr_t)rsMeshCreate((RsContext)con,
   2686                                         (RsAllocation *)vtxPtr, vtxLen,
   2687                                         (RsAllocation *)idxPtr, idxLen,
   2688                                         (uint32_t *)primPtr, primLen);
   2689 
   2690     free(vtxPtr);
   2691     free(idxPtr);
   2692 
   2693 cleanupMesh:
   2694     if (jVtxPtr != nullptr) {
   2695         _env->ReleaseLongArrayElements(_vtx, jVtxPtr, 0);
   2696     }
   2697     if (jIdxPtr != nullptr) {
   2698         _env->ReleaseLongArrayElements(_idx, jIdxPtr, 0);
   2699     }
   2700     if (primPtr != nullptr) {
   2701         _env->ReleaseIntArrayElements(_prim, primPtr, 0);
   2702     }
   2703 
   2704     return id;
   2705 }
   2706 
   2707 static jint
   2708 nMeshGetVertexBufferCount(JNIEnv *_env, jobject _this, jlong con, jlong mesh)
   2709 {
   2710     if (kLogApi) {
   2711         ALOGD("nMeshGetVertexBufferCount, con(%p), Mesh(%p)", (RsContext)con, (RsMesh)mesh);
   2712     }
   2713     jint vtxCount = 0;
   2714     rsaMeshGetVertexBufferCount((RsContext)con, (RsMesh)mesh, &vtxCount);
   2715     return vtxCount;
   2716 }
   2717 
   2718 static jint
   2719 nMeshGetIndexCount(JNIEnv *_env, jobject _this, jlong con, jlong mesh)
   2720 {
   2721     if (kLogApi) {
   2722         ALOGD("nMeshGetIndexCount, con(%p), Mesh(%p)", (RsContext)con, (RsMesh)mesh);
   2723     }
   2724     jint idxCount = 0;
   2725     rsaMeshGetIndexCount((RsContext)con, (RsMesh)mesh, &idxCount);
   2726     return idxCount;
   2727 }
   2728 
   2729 static void
   2730 nMeshGetVertices(JNIEnv *_env, jobject _this, jlong con, jlong mesh, jlongArray _ids, jint numVtxIDs)
   2731 {
   2732     if (kLogApi) {
   2733         ALOGD("nMeshGetVertices, con(%p), Mesh(%p)", (RsContext)con, (RsMesh)mesh);
   2734     }
   2735 
   2736     RsAllocation *allocs = (RsAllocation*)malloc((uint32_t)numVtxIDs * sizeof(RsAllocation));
   2737     rsaMeshGetVertices((RsContext)con, (RsMesh)mesh, allocs, (uint32_t)numVtxIDs);
   2738 
   2739     for(jint i = 0; i < numVtxIDs; i ++) {
   2740         const jlong alloc = (jlong)(uintptr_t)allocs[i];
   2741         _env->SetLongArrayRegion(_ids, i, 1, &alloc);
   2742     }
   2743 
   2744     free(allocs);
   2745 }
   2746 
   2747 static void
   2748 nMeshGetIndices(JNIEnv *_env, jobject _this, jlong con, jlong mesh, jlongArray _idxIds, jintArray _primitives, jint numIndices)
   2749 {
   2750     if (kLogApi) {
   2751         ALOGD("nMeshGetVertices, con(%p), Mesh(%p)", (RsContext)con, (RsMesh)mesh);
   2752     }
   2753 
   2754     RsAllocation *allocs = (RsAllocation*)malloc((uint32_t)numIndices * sizeof(RsAllocation));
   2755     uint32_t *prims= (uint32_t*)malloc((uint32_t)numIndices * sizeof(uint32_t));
   2756 
   2757     rsaMeshGetIndices((RsContext)con, (RsMesh)mesh, allocs, prims, (uint32_t)numIndices);
   2758 
   2759     for(jint i = 0; i < numIndices; i ++) {
   2760         const jlong alloc = (jlong)(uintptr_t)allocs[i];
   2761         const jint prim = (jint)prims[i];
   2762         _env->SetLongArrayRegion(_idxIds, i, 1, &alloc);
   2763         _env->SetIntArrayRegion(_primitives, i, 1, &prim);
   2764     }
   2765 
   2766     free(allocs);
   2767     free(prims);
   2768 }
   2769 
   2770 static jint
   2771 nSystemGetPointerSize(JNIEnv *_env, jobject _this) {
   2772     return (jint)sizeof(void*);
   2773 }
   2774 
   2775 static jobject
   2776 nAllocationGetByteBuffer(JNIEnv *_env, jobject _this, jlong con, jlong alloc,
   2777                         jlongArray strideArr, jint xBytesSize,
   2778                         jint dimY, jint dimZ) {
   2779     if (kLogApi) {
   2780         ALOGD("nAllocationGetByteBuffer, con(%p), alloc(%p)", (RsContext)con, (RsAllocation)alloc);
   2781     }
   2782 
   2783     jlong *jStridePtr = _env->GetLongArrayElements(strideArr, nullptr);
   2784     if (jStridePtr == nullptr) {
   2785         ALOGE("Failed to get Java array elements: strideArr");
   2786         return 0;
   2787     }
   2788 
   2789     size_t strideIn = xBytesSize;
   2790     void* ptr = nullptr;
   2791     if (alloc != 0) {
   2792         ptr = rsAllocationGetPointer((RsContext)con, (RsAllocation)alloc, 0,
   2793                                      RS_ALLOCATION_CUBEMAP_FACE_POSITIVE_X, 0, 0,
   2794                                      &strideIn, sizeof(size_t));
   2795     }
   2796 
   2797     jobject byteBuffer = nullptr;
   2798     if (ptr != nullptr) {
   2799         size_t bufferSize = strideIn;
   2800         jStridePtr[0] = strideIn;
   2801         if (dimY > 0) {
   2802             bufferSize *= dimY;
   2803         }
   2804         if (dimZ > 0) {
   2805             bufferSize *= dimZ;
   2806         }
   2807         byteBuffer = _env->NewDirectByteBuffer(ptr, (jlong) bufferSize);
   2808     }
   2809     _env->ReleaseLongArrayElements(strideArr, jStridePtr, 0);
   2810     return byteBuffer;
   2811 }
   2812 // ---------------------------------------------------------------------------
   2813 
   2814 
   2815 static const char *classPathName = "android/renderscript/RenderScript";
   2816 
   2817 static const JNINativeMethod methods[] = {
   2818 {"_nInit",                         "()V",                                     (void*)_nInit },
   2819 
   2820 {"nDeviceCreate",                  "()J",                                     (void*)nDeviceCreate },
   2821 {"nDeviceDestroy",                 "(J)V",                                    (void*)nDeviceDestroy },
   2822 {"nDeviceSetConfig",               "(JII)V",                                  (void*)nDeviceSetConfig },
   2823 {"nContextGetUserMessage",         "(J[I)I",                                  (void*)nContextGetUserMessage },
   2824 {"nContextGetErrorMessage",        "(J)Ljava/lang/String;",                   (void*)nContextGetErrorMessage },
   2825 {"nContextPeekMessage",            "(J[I)I",                                  (void*)nContextPeekMessage },
   2826 
   2827 {"nContextInitToClient",           "(J)V",                                    (void*)nContextInitToClient },
   2828 {"nContextDeinitToClient",         "(J)V",                                    (void*)nContextDeinitToClient },
   2829 
   2830 
   2831 // All methods below are thread protected in java.
   2832 {"rsnContextCreate",                 "(JIII)J",                               (void*)nContextCreate },
   2833 {"rsnContextCreateGL",               "(JIIIIIIIIIIIIFI)J",                    (void*)nContextCreateGL },
   2834 {"rsnContextFinish",                 "(J)V",                                  (void*)nContextFinish },
   2835 {"rsnContextSetPriority",            "(JI)V",                                 (void*)nContextSetPriority },
   2836 {"rsnContextSetCacheDir",            "(JLjava/lang/String;)V",                (void*)nContextSetCacheDir },
   2837 {"rsnContextSetSurface",             "(JIILandroid/view/Surface;)V",          (void*)nContextSetSurface },
   2838 {"rsnContextDestroy",                "(J)V",                                  (void*)nContextDestroy },
   2839 {"rsnContextDump",                   "(JI)V",                                 (void*)nContextDump },
   2840 {"rsnContextPause",                  "(J)V",                                  (void*)nContextPause },
   2841 {"rsnContextResume",                 "(J)V",                                  (void*)nContextResume },
   2842 {"rsnContextSendMessage",            "(JI[I)V",                               (void*)nContextSendMessage },
   2843 {"rsnClosureCreate",                 "(JJJ[J[J[I[J[J)J",                      (void*)nClosureCreate },
   2844 {"rsnInvokeClosureCreate",           "(JJ[B[J[J[I)J",                         (void*)nInvokeClosureCreate },
   2845 {"rsnClosureSetArg",                 "(JJIJI)V",                              (void*)nClosureSetArg },
   2846 {"rsnClosureSetGlobal",              "(JJJJI)V",                              (void*)nClosureSetGlobal },
   2847 {"rsnAssignName",                    "(JJ[B)V",                               (void*)nAssignName },
   2848 {"rsnGetName",                       "(JJ)Ljava/lang/String;",                (void*)nGetName },
   2849 {"rsnObjDestroy",                    "(JJ)V",                                 (void*)nObjDestroy },
   2850 
   2851 {"rsnFileA3DCreateFromFile",         "(JLjava/lang/String;)J",                (void*)nFileA3DCreateFromFile },
   2852 {"rsnFileA3DCreateFromAssetStream",  "(JJ)J",                                 (void*)nFileA3DCreateFromAssetStream },
   2853 {"rsnFileA3DCreateFromAsset",        "(JLandroid/content/res/AssetManager;Ljava/lang/String;)J",            (void*)nFileA3DCreateFromAsset },
   2854 {"rsnFileA3DGetNumIndexEntries",     "(JJ)I",                                 (void*)nFileA3DGetNumIndexEntries },
   2855 {"rsnFileA3DGetIndexEntries",        "(JJI[I[Ljava/lang/String;)V",           (void*)nFileA3DGetIndexEntries },
   2856 {"rsnFileA3DGetEntryByIndex",        "(JJI)J",                                (void*)nFileA3DGetEntryByIndex },
   2857 
   2858 {"rsnFontCreateFromFile",            "(JLjava/lang/String;FI)J",              (void*)nFontCreateFromFile },
   2859 {"rsnFontCreateFromAssetStream",     "(JLjava/lang/String;FIJ)J",             (void*)nFontCreateFromAssetStream },
   2860 {"rsnFontCreateFromAsset",        "(JLandroid/content/res/AssetManager;Ljava/lang/String;FI)J",            (void*)nFontCreateFromAsset },
   2861 
   2862 {"rsnElementCreate",                 "(JJIZI)J",                              (void*)nElementCreate },
   2863 {"rsnElementCreate2",                "(J[J[Ljava/lang/String;[I)J",           (void*)nElementCreate2 },
   2864 {"rsnElementGetNativeData",          "(JJ[I)V",                               (void*)nElementGetNativeData },
   2865 {"rsnElementGetSubElements",         "(JJ[J[Ljava/lang/String;[I)V",          (void*)nElementGetSubElements },
   2866 
   2867 {"rsnTypeCreate",                    "(JJIIIZZI)J",                           (void*)nTypeCreate },
   2868 {"rsnTypeGetNativeData",             "(JJ[J)V",                               (void*)nTypeGetNativeData },
   2869 
   2870 {"rsnAllocationCreateTyped",         "(JJIIJ)J",                               (void*)nAllocationCreateTyped },
   2871 {"rsnAllocationCreateFromBitmap",    "(JJILandroid/graphics/Bitmap;I)J",      (void*)nAllocationCreateFromBitmap },
   2872 {"rsnAllocationCreateBitmapBackedAllocation",    "(JJILandroid/graphics/Bitmap;I)J",      (void*)nAllocationCreateBitmapBackedAllocation },
   2873 {"rsnAllocationCubeCreateFromBitmap","(JJILandroid/graphics/Bitmap;I)J",      (void*)nAllocationCubeCreateFromBitmap },
   2874 
   2875 {"rsnAllocationCopyFromBitmap",      "(JJLandroid/graphics/Bitmap;)V",        (void*)nAllocationCopyFromBitmap },
   2876 {"rsnAllocationCopyToBitmap",        "(JJLandroid/graphics/Bitmap;)V",        (void*)nAllocationCopyToBitmap },
   2877 
   2878 {"rsnAllocationSyncAll",             "(JJI)V",                                (void*)nAllocationSyncAll },
   2879 {"rsnAllocationSetupBufferQueue",    "(JJI)V",                                (void*)nAllocationSetupBufferQueue },
   2880 {"rsnAllocationShareBufferQueue",    "(JJJ)V",                                (void*)nAllocationShareBufferQueue },
   2881 {"rsnAllocationGetSurface",          "(JJ)Landroid/view/Surface;",            (void*)nAllocationGetSurface },
   2882 {"rsnAllocationSetSurface",          "(JJLandroid/view/Surface;)V",           (void*)nAllocationSetSurface },
   2883 {"rsnAllocationIoSend",              "(JJ)V",                                 (void*)nAllocationIoSend },
   2884 {"rsnAllocationIoReceive",           "(JJ)J",                                 (void*)nAllocationIoReceive },
   2885 {"rsnAllocationData1D",              "(JJIIILjava/lang/Object;IIIZ)V",        (void*)nAllocationData1D },
   2886 {"rsnAllocationElementData",         "(JJIIIII[BI)V",                         (void*)nAllocationElementData },
   2887 {"rsnAllocationData2D",              "(JJIIIIIILjava/lang/Object;IIIZ)V",     (void*)nAllocationData2D },
   2888 {"rsnAllocationData2D",              "(JJIIIIIIJIIII)V",                      (void*)nAllocationData2D_alloc },
   2889 {"rsnAllocationData3D",              "(JJIIIIIIILjava/lang/Object;IIIZ)V",    (void*)nAllocationData3D },
   2890 {"rsnAllocationData3D",              "(JJIIIIIIIJIIII)V",                     (void*)nAllocationData3D_alloc },
   2891 {"rsnAllocationRead",                "(JJLjava/lang/Object;IIZ)V",            (void*)nAllocationRead },
   2892 {"rsnAllocationRead1D",              "(JJIIILjava/lang/Object;IIIZ)V",        (void*)nAllocationRead1D },
   2893 {"rsnAllocationElementRead",         "(JJIIIII[BI)V",                         (void*)nAllocationElementRead },
   2894 {"rsnAllocationRead2D",              "(JJIIIIIILjava/lang/Object;IIIZ)V",     (void*)nAllocationRead2D },
   2895 {"rsnAllocationRead3D",              "(JJIIIIIIILjava/lang/Object;IIIZ)V",    (void*)nAllocationRead3D },
   2896 {"rsnAllocationGetType",             "(JJ)J",                                 (void*)nAllocationGetType},
   2897 {"rsnAllocationResize1D",            "(JJI)V",                                (void*)nAllocationResize1D },
   2898 {"rsnAllocationGenerateMipmaps",     "(JJ)V",                                 (void*)nAllocationGenerateMipmaps },
   2899 
   2900 {"rsnAllocationAdapterCreate",       "(JJJ)J",                                (void*)nAllocationAdapterCreate },
   2901 {"rsnAllocationAdapterOffset",       "(JJIIIIIIIII)V",                        (void*)nAllocationAdapterOffset },
   2902 
   2903 {"rsnScriptBindAllocation",          "(JJJI)V",                               (void*)nScriptBindAllocation },
   2904 {"rsnScriptSetTimeZone",             "(JJ[B)V",                               (void*)nScriptSetTimeZone },
   2905 {"rsnScriptInvoke",                  "(JJI)V",                                (void*)nScriptInvoke },
   2906 {"rsnScriptInvokeV",                 "(JJI[B)V",                              (void*)nScriptInvokeV },
   2907 
   2908 {"rsnScriptForEach",                 "(JJI[JJ[B[I)V",                         (void*)nScriptForEach },
   2909 {"rsnScriptReduce",                  "(JJI[JJ[I)V",                           (void*)nScriptReduce },
   2910 
   2911 {"rsnScriptSetVarI",                 "(JJII)V",                               (void*)nScriptSetVarI },
   2912 {"rsnScriptGetVarI",                 "(JJI)I",                                (void*)nScriptGetVarI },
   2913 {"rsnScriptSetVarJ",                 "(JJIJ)V",                               (void*)nScriptSetVarJ },
   2914 {"rsnScriptGetVarJ",                 "(JJI)J",                                (void*)nScriptGetVarJ },
   2915 {"rsnScriptSetVarF",                 "(JJIF)V",                               (void*)nScriptSetVarF },
   2916 {"rsnScriptGetVarF",                 "(JJI)F",                                (void*)nScriptGetVarF },
   2917 {"rsnScriptSetVarD",                 "(JJID)V",                               (void*)nScriptSetVarD },
   2918 {"rsnScriptGetVarD",                 "(JJI)D",                                (void*)nScriptGetVarD },
   2919 {"rsnScriptSetVarV",                 "(JJI[B)V",                              (void*)nScriptSetVarV },
   2920 {"rsnScriptGetVarV",                 "(JJI[B)V",                              (void*)nScriptGetVarV },
   2921 {"rsnScriptSetVarVE",                "(JJI[BJ[I)V",                           (void*)nScriptSetVarVE },
   2922 {"rsnScriptSetVarObj",               "(JJIJ)V",                               (void*)nScriptSetVarObj },
   2923 
   2924 {"rsnScriptCCreate",                 "(JLjava/lang/String;Ljava/lang/String;[BI)J",  (void*)nScriptCCreate },
   2925 {"rsnScriptIntrinsicCreate",         "(JIJ)J",                                (void*)nScriptIntrinsicCreate },
   2926 {"rsnScriptKernelIDCreate",          "(JJII)J",                               (void*)nScriptKernelIDCreate },
   2927 {"rsnScriptInvokeIDCreate",          "(JJI)J",                                (void*)nScriptInvokeIDCreate },
   2928 {"rsnScriptFieldIDCreate",           "(JJI)J",                                (void*)nScriptFieldIDCreate },
   2929 {"rsnScriptGroupCreate",             "(J[J[J[J[J[J)J",                        (void*)nScriptGroupCreate },
   2930 {"rsnScriptGroup2Create",            "(JLjava/lang/String;Ljava/lang/String;[J)J", (void*)nScriptGroup2Create },
   2931 {"rsnScriptGroupSetInput",           "(JJJJ)V",                               (void*)nScriptGroupSetInput },
   2932 {"rsnScriptGroupSetOutput",          "(JJJJ)V",                               (void*)nScriptGroupSetOutput },
   2933 {"rsnScriptGroupExecute",            "(JJ)V",                                 (void*)nScriptGroupExecute },
   2934 {"rsnScriptGroup2Execute",           "(JJ)V",                                 (void*)nScriptGroup2Execute },
   2935 
   2936 {"rsnScriptIntrinsicBLAS_Single",    "(JJIIIIIIIIIFJJFJIIII)V",               (void*)nScriptIntrinsicBLAS_Single },
   2937 {"rsnScriptIntrinsicBLAS_Double",    "(JJIIIIIIIIIDJJDJIIII)V",               (void*)nScriptIntrinsicBLAS_Double },
   2938 {"rsnScriptIntrinsicBLAS_Complex",   "(JJIIIIIIIIIFFJJFFJIIII)V",             (void*)nScriptIntrinsicBLAS_Complex },
   2939 {"rsnScriptIntrinsicBLAS_Z",         "(JJIIIIIIIIIDDJJDDJIIII)V",             (void*)nScriptIntrinsicBLAS_Z },
   2940 
   2941 {"rsnScriptIntrinsicBLAS_BNNM",      "(JJIIIJIJIJII)V",                       (void*)nScriptIntrinsicBLAS_BNNM },
   2942 
   2943 {"rsnProgramStoreCreate",            "(JZZZZZZIII)J",                         (void*)nProgramStoreCreate },
   2944 
   2945 {"rsnProgramBindConstants",          "(JJIJ)V",                               (void*)nProgramBindConstants },
   2946 {"rsnProgramBindTexture",            "(JJIJ)V",                               (void*)nProgramBindTexture },
   2947 {"rsnProgramBindSampler",            "(JJIJ)V",                               (void*)nProgramBindSampler },
   2948 
   2949 {"rsnProgramFragmentCreate",         "(JLjava/lang/String;[Ljava/lang/String;[J)J",              (void*)nProgramFragmentCreate },
   2950 {"rsnProgramRasterCreate",           "(JZI)J",                                (void*)nProgramRasterCreate },
   2951 {"rsnProgramVertexCreate",           "(JLjava/lang/String;[Ljava/lang/String;[J)J",              (void*)nProgramVertexCreate },
   2952 
   2953 {"rsnContextBindRootScript",         "(JJ)V",                                 (void*)nContextBindRootScript },
   2954 {"rsnContextBindProgramStore",       "(JJ)V",                                 (void*)nContextBindProgramStore },
   2955 {"rsnContextBindProgramFragment",    "(JJ)V",                                 (void*)nContextBindProgramFragment },
   2956 {"rsnContextBindProgramVertex",      "(JJ)V",                                 (void*)nContextBindProgramVertex },
   2957 {"rsnContextBindProgramRaster",      "(JJ)V",                                 (void*)nContextBindProgramRaster },
   2958 
   2959 {"rsnSamplerCreate",                 "(JIIIIIF)J",                            (void*)nSamplerCreate },
   2960 
   2961 {"rsnMeshCreate",                    "(J[J[J[I)J",                            (void*)nMeshCreate },
   2962 
   2963 {"rsnMeshGetVertexBufferCount",      "(JJ)I",                                 (void*)nMeshGetVertexBufferCount },
   2964 {"rsnMeshGetIndexCount",             "(JJ)I",                                 (void*)nMeshGetIndexCount },
   2965 {"rsnMeshGetVertices",               "(JJ[JI)V",                              (void*)nMeshGetVertices },
   2966 {"rsnMeshGetIndices",                "(JJ[J[II)V",                            (void*)nMeshGetIndices },
   2967 
   2968 {"rsnSystemGetPointerSize",          "()I",                                   (void*)nSystemGetPointerSize },
   2969 {"rsnAllocationGetByteBuffer",       "(JJ[JIII)Ljava/nio/ByteBuffer;",        (void*)nAllocationGetByteBuffer },
   2970 };
   2971 
   2972 static int registerFuncs(JNIEnv *_env)
   2973 {
   2974     return android::AndroidRuntime::registerNativeMethods(
   2975             _env, classPathName, methods, NELEM(methods));
   2976 }
   2977 
   2978 // ---------------------------------------------------------------------------
   2979 
   2980 jint JNI_OnLoad(JavaVM* vm, void* reserved)
   2981 {
   2982     JNIEnv* env = nullptr;
   2983     jint result = -1;
   2984 
   2985     if (vm->GetEnv((void**) &env, JNI_VERSION_1_4) != JNI_OK) {
   2986         ALOGE("ERROR: GetEnv failed\n");
   2987         goto bail;
   2988     }
   2989     assert(env != nullptr);
   2990 
   2991     if (registerFuncs(env) < 0) {
   2992         ALOGE("ERROR: Renderscript native registration failed\n");
   2993         goto bail;
   2994     }
   2995 
   2996     /* success -- return valid version number */
   2997     result = JNI_VERSION_1_4;
   2998 
   2999 bail:
   3000     return result;
   3001 }
   3002