android_renderscript_RenderScript.cpp revision a89094aa3bc059c6e03b20b4c5b1ede4582f3da9
1/*
2 * Copyright (C) 2006 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 "libRS_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
26#include <surfaceflinger/Surface.h>
27
28#include <core/SkBitmap.h>
29#include <core/SkPixelRef.h>
30#include <core/SkStream.h>
31#include <core/SkTemplates.h>
32#include <images/SkImageDecoder.h>
33
34#include <utils/Asset.h>
35#include <utils/AssetManager.h>
36#include <utils/ResourceTypes.h>
37
38#include "jni.h"
39#include "JNIHelp.h"
40#include "android_runtime/AndroidRuntime.h"
41#include "android_runtime/android_view_Surface.h"
42#include "android_runtime/android_util_AssetManager.h"
43
44#include <RenderScript.h>
45#include <RenderScriptEnv.h>
46
47//#define LOG_API LOGE
48#define LOG_API(...)
49
50using namespace android;
51
52class AutoJavaStringToUTF8 {
53public:
54    AutoJavaStringToUTF8(JNIEnv* env, jstring str) : fEnv(env), fJStr(str)
55    {
56        fCStr = env->GetStringUTFChars(str, NULL);
57        fLength = env->GetStringUTFLength(str);
58    }
59    ~AutoJavaStringToUTF8()
60    {
61        fEnv->ReleaseStringUTFChars(fJStr, fCStr);
62    }
63    const char* c_str() const { return fCStr; }
64    jsize length() const { return fLength; }
65
66private:
67    JNIEnv*     fEnv;
68    jstring     fJStr;
69    const char* fCStr;
70    jsize       fLength;
71};
72
73// ---------------------------------------------------------------------------
74
75static jfieldID gContextId = 0;
76static jfieldID gNativeBitmapID = 0;
77static jfieldID gTypeNativeCache = 0;
78
79static void _nInit(JNIEnv *_env, jclass _this)
80{
81    gContextId             = _env->GetFieldID(_this, "mContext", "I");
82
83    jclass bitmapClass = _env->FindClass("android/graphics/Bitmap");
84    gNativeBitmapID = _env->GetFieldID(bitmapClass, "mNativeBitmap", "I");
85}
86
87// ---------------------------------------------------------------------------
88
89static void
90nContextFinish(JNIEnv *_env, jobject _this, RsContext con)
91{
92    LOG_API("nContextFinish, con(%p)", con);
93    rsContextFinish(con);
94}
95
96static void
97nAssignName(JNIEnv *_env, jobject _this, RsContext con, jint obj, jbyteArray str)
98{
99    LOG_API("nAssignName, con(%p), obj(%p)", con, (void *)obj);
100    jint len = _env->GetArrayLength(str);
101    jbyte * cptr = (jbyte *) _env->GetPrimitiveArrayCritical(str, 0);
102    rsAssignName(con, (void *)obj, (const char *)cptr, len);
103    _env->ReleasePrimitiveArrayCritical(str, cptr, JNI_ABORT);
104}
105
106static jstring
107nGetName(JNIEnv *_env, jobject _this, RsContext con, jint obj)
108{
109    LOG_API("nGetName, con(%p), obj(%p)", con, (void *)obj);
110    const char *name = NULL;
111    rsaGetName(con, (void *)obj, &name);
112    if(name == NULL || strlen(name) == 0) {
113        return NULL;
114    }
115    return _env->NewStringUTF(name);
116}
117
118static void
119nObjDestroy(JNIEnv *_env, jobject _this, RsContext con, jint obj)
120{
121    LOG_API("nObjDestroy, con(%p) obj(%p)", con, (void *)obj);
122    rsObjDestroy(con, (void *)obj);
123}
124
125// ---------------------------------------------------------------------------
126
127static jint
128nDeviceCreate(JNIEnv *_env, jobject _this)
129{
130    LOG_API("nDeviceCreate");
131    return (jint)rsDeviceCreate();
132}
133
134static void
135nDeviceDestroy(JNIEnv *_env, jobject _this, jint dev)
136{
137    LOG_API("nDeviceDestroy");
138    return rsDeviceDestroy((RsDevice)dev);
139}
140
141static void
142nDeviceSetConfig(JNIEnv *_env, jobject _this, jint dev, jint p, jint value)
143{
144    LOG_API("nDeviceSetConfig  dev(%p), param(%i), value(%i)", (void *)dev, p, value);
145    return rsDeviceSetConfig((RsDevice)dev, (RsDeviceParam)p, value);
146}
147
148static jint
149nContextCreate(JNIEnv *_env, jobject _this, jint dev, jint ver)
150{
151    LOG_API("nContextCreate");
152    return (jint)rsContextCreate((RsDevice)dev, ver);
153}
154
155static jint
156nContextCreateGL(JNIEnv *_env, jobject _this, jint dev, jint ver,
157                 int colorMin, int colorPref,
158                 int alphaMin, int alphaPref,
159                 int depthMin, int depthPref,
160                 int stencilMin, int stencilPref,
161                 int samplesMin, int samplesPref, float samplesQ,
162                 int dpi)
163{
164    RsSurfaceConfig sc;
165    sc.alphaMin = alphaMin;
166    sc.alphaPref = alphaPref;
167    sc.colorMin = colorMin;
168    sc.colorPref = colorPref;
169    sc.depthMin = depthMin;
170    sc.depthPref = depthPref;
171    sc.samplesMin = samplesMin;
172    sc.samplesPref = samplesPref;
173    sc.samplesQ = samplesQ;
174
175    LOG_API("nContextCreateGL");
176    return (jint)rsContextCreateGL((RsDevice)dev, ver, sc, dpi);
177}
178
179static void
180nContextSetPriority(JNIEnv *_env, jobject _this, RsContext con, jint p)
181{
182    LOG_API("ContextSetPriority, con(%p), priority(%i)", con, p);
183    rsContextSetPriority(con, p);
184}
185
186
187
188static void
189nContextSetSurface(JNIEnv *_env, jobject _this, RsContext con, jint width, jint height, jobject wnd)
190{
191    LOG_API("nContextSetSurface, con(%p), width(%i), height(%i), surface(%p)", con, width, height, (Surface *)wnd);
192
193    Surface * window = NULL;
194    if (wnd == NULL) {
195
196    } else {
197        window = (Surface*) android_Surface_getNativeWindow(_env, wnd).get();
198    }
199
200    rsContextSetSurface(con, width, height, window, 1);
201}
202
203static void
204nContextDestroy(JNIEnv *_env, jobject _this, RsContext con)
205{
206    LOG_API("nContextDestroy, con(%p)", con);
207    rsContextDestroy(con);
208}
209
210static void
211nContextDump(JNIEnv *_env, jobject _this, RsContext con, jint bits)
212{
213    LOG_API("nContextDump, con(%p)  bits(%i)", (RsContext)con, bits);
214    rsContextDump((RsContext)con, bits);
215}
216
217static void
218nContextPause(JNIEnv *_env, jobject _this, RsContext con)
219{
220    LOG_API("nContextPause, con(%p)", con);
221    rsContextPause(con);
222}
223
224static void
225nContextResume(JNIEnv *_env, jobject _this, RsContext con)
226{
227    LOG_API("nContextResume, con(%p)", con);
228    rsContextResume(con);
229}
230
231
232static jstring
233nContextGetErrorMessage(JNIEnv *_env, jobject _this, RsContext con)
234{
235    LOG_API("nContextGetErrorMessage, con(%p)", con);
236    char buf[1024];
237
238    size_t receiveLen;
239    uint32_t subID;
240    int id = rsContextGetMessage(con,
241                                 buf, sizeof(buf),
242                                 &receiveLen, sizeof(receiveLen),
243                                 &subID, sizeof(subID),
244                                 true);
245    if (!id && receiveLen) {
246        LOGV("message receive buffer too small.  %i", receiveLen);
247    }
248    return _env->NewStringUTF(buf);
249}
250
251static void
252nContextGetUserMessage(JNIEnv *_env, jobject _this, RsContext con, jintArray data)
253{
254    jint len = _env->GetArrayLength(data);
255    LOG_API("nContextGetMessage, con(%p), len(%i)", con, len);
256    jint *ptr = _env->GetIntArrayElements(data, NULL);
257    size_t receiveLen;
258    uint32_t subID;
259    int id = rsContextGetMessage(con,
260                                 ptr, len * 4,
261                                 &receiveLen, sizeof(receiveLen),
262                                 &subID, sizeof(subID),
263                                 true);
264    if (!id && receiveLen) {
265        LOGV("message receive buffer too small.  %i", receiveLen);
266    }
267    _env->ReleaseIntArrayElements(data, ptr, 0);
268}
269
270static jint
271nContextPeekMessage(JNIEnv *_env, jobject _this, RsContext con, jintArray auxData, jboolean wait)
272{
273    LOG_API("nContextPeekMessage, con(%p)", con);
274    jint *auxDataPtr = _env->GetIntArrayElements(auxData, NULL);
275    size_t receiveLen;
276    uint32_t subID;
277    int id = rsContextPeekMessage(con, &receiveLen, sizeof(receiveLen),
278                                  &subID, sizeof(subID), wait);
279    auxDataPtr[0] = (jint)subID;
280    auxDataPtr[1] = (jint)receiveLen;
281    _env->ReleaseIntArrayElements(auxData, auxDataPtr, 0);
282    return id;
283}
284
285static void nContextInitToClient(JNIEnv *_env, jobject _this, RsContext con)
286{
287    LOG_API("nContextInitToClient, con(%p)", con);
288    rsContextInitToClient(con);
289}
290
291static void nContextDeinitToClient(JNIEnv *_env, jobject _this, RsContext con)
292{
293    LOG_API("nContextDeinitToClient, con(%p)", con);
294    rsContextDeinitToClient(con);
295}
296
297
298static jint
299nElementCreate(JNIEnv *_env, jobject _this, RsContext con, jint type, jint kind, jboolean norm, jint size)
300{
301    LOG_API("nElementCreate, con(%p), type(%i), kind(%i), norm(%i), size(%i)", con, type, kind, norm, size);
302    return (jint)rsElementCreate(con, (RsDataType)type, (RsDataKind)kind, norm, size);
303}
304
305static jint
306nElementCreate2(JNIEnv *_env, jobject _this, RsContext con, jintArray _ids, jobjectArray _names, jintArray _arraySizes)
307{
308    int fieldCount = _env->GetArrayLength(_ids);
309    LOG_API("nElementCreate2, con(%p)", con);
310
311    jint *ids = _env->GetIntArrayElements(_ids, NULL);
312    jint *arraySizes = _env->GetIntArrayElements(_arraySizes, NULL);
313    const char ** nameArray = (const char **)calloc(fieldCount, sizeof(char *));
314    size_t* sizeArray = (size_t*)calloc(fieldCount, sizeof(size_t));
315
316    for (int ct=0; ct < fieldCount; ct++) {
317        jstring s = (jstring)_env->GetObjectArrayElement(_names, ct);
318        nameArray[ct] = _env->GetStringUTFChars(s, NULL);
319        sizeArray[ct] = _env->GetStringUTFLength(s);
320    }
321    jint id = (jint)rsElementCreate2(con,
322                                     (RsElement *)ids, fieldCount,
323                                     nameArray, fieldCount,
324                                     sizeArray, fieldCount,
325                                     (const uint32_t *)arraySizes, fieldCount);
326    for (int ct=0; ct < fieldCount; ct++) {
327        jstring s = (jstring)_env->GetObjectArrayElement(_names, ct);
328        _env->ReleaseStringUTFChars(s, nameArray[ct]);
329    }
330    _env->ReleaseIntArrayElements(_ids, ids, JNI_ABORT);
331    _env->ReleaseIntArrayElements(_arraySizes, arraySizes, JNI_ABORT);
332    free(nameArray);
333    free(sizeArray);
334    return (jint)id;
335}
336
337static void
338nElementGetNativeData(JNIEnv *_env, jobject _this, RsContext con, jint id, jintArray _elementData)
339{
340    int dataSize = _env->GetArrayLength(_elementData);
341    LOG_API("nElementGetNativeData, con(%p)", con);
342
343    // we will pack mType; mKind; mNormalized; mVectorSize; NumSubElements
344    assert(dataSize == 5);
345
346    uint32_t elementData[5];
347    rsaElementGetNativeData(con, (RsElement)id, elementData, dataSize);
348
349    for(jint i = 0; i < dataSize; i ++) {
350        _env->SetIntArrayRegion(_elementData, i, 1, (const jint*)&elementData[i]);
351    }
352}
353
354
355static void
356nElementGetSubElements(JNIEnv *_env, jobject _this, RsContext con, jint id, jintArray _IDs, jobjectArray _names)
357{
358    int dataSize = _env->GetArrayLength(_IDs);
359    LOG_API("nElementGetSubElements, con(%p)", con);
360
361    uint32_t *ids = (uint32_t *)malloc((uint32_t)dataSize * sizeof(uint32_t));
362    const char **names = (const char **)malloc((uint32_t)dataSize * sizeof(const char *));
363
364    rsaElementGetSubElements(con, (RsElement)id, ids, names, (uint32_t)dataSize);
365
366    for(jint i = 0; i < dataSize; i++) {
367        _env->SetObjectArrayElement(_names, i, _env->NewStringUTF(names[i]));
368        _env->SetIntArrayRegion(_IDs, i, 1, (const jint*)&ids[i]);
369    }
370
371    free(ids);
372    free(names);
373}
374
375// -----------------------------------
376
377static int
378nTypeCreate(JNIEnv *_env, jobject _this, RsContext con, RsElement eid,
379            jint dimx, jint dimy, jint dimz, jboolean mips, jboolean faces)
380{
381    LOG_API("nTypeCreate, con(%p) eid(%p), x(%i), y(%i), z(%i), mips(%i), faces(%i)",
382            con, eid, dimx, dimy, dimz, mips, faces);
383
384    jint id = (jint)rsTypeCreate(con, (RsElement)eid, dimx, dimy, dimz, mips, faces);
385    return (jint)id;
386}
387
388static void
389nTypeGetNativeData(JNIEnv *_env, jobject _this, RsContext con, jint id, jintArray _typeData)
390{
391    // We are packing 6 items: mDimX; mDimY; mDimZ;
392    // mDimLOD; mDimFaces; mElement; into typeData
393    int elementCount = _env->GetArrayLength(_typeData);
394
395    assert(elementCount == 6);
396    LOG_API("nTypeCreate, con(%p)", con);
397
398    uint32_t typeData[6];
399    rsaTypeGetNativeData(con, (RsType)id, typeData, 6);
400
401    for(jint i = 0; i < elementCount; i ++) {
402        _env->SetIntArrayRegion(_typeData, i, 1, (const jint*)&typeData[i]);
403    }
404}
405
406// -----------------------------------
407
408static jint
409nAllocationCreateTyped(JNIEnv *_env, jobject _this, RsContext con, jint type, jint mips, jint usage)
410{
411    LOG_API("nAllocationCreateTyped, con(%p), type(%p), mip(%i), usage(%i)", con, (RsElement)type, mips, usage);
412    return (jint) rsAllocationCreateTyped(con, (RsType)type, (RsAllocationMipmapControl)mips, (uint32_t)usage);
413}
414
415static void
416nAllocationSyncAll(JNIEnv *_env, jobject _this, RsContext con, jint a, jint bits)
417{
418    LOG_API("nAllocationSyncAll, con(%p), a(%p), bits(0x%08x)", con, (RsAllocation)a, bits);
419    rsAllocationSyncAll(con, (RsAllocation)a, (RsAllocationUsageType)bits);
420}
421
422static void
423nAllocationGenerateMipmaps(JNIEnv *_env, jobject _this, RsContext con, jint alloc)
424{
425    LOG_API("nAllocationGenerateMipmaps, con(%p), a(%p)", con, (RsAllocation)alloc);
426    rsAllocationGenerateMipmaps(con, (RsAllocation)alloc);
427}
428
429static int
430nAllocationCreateFromBitmap(JNIEnv *_env, jobject _this, RsContext con, jint type, jint mip, jobject jbitmap, jint usage)
431{
432    SkBitmap const * nativeBitmap =
433            (SkBitmap const *)_env->GetIntField(jbitmap, gNativeBitmapID);
434    const SkBitmap& bitmap(*nativeBitmap);
435
436    bitmap.lockPixels();
437    const void* ptr = bitmap.getPixels();
438    jint id = (jint)rsAllocationCreateFromBitmap(con,
439                                                  (RsType)type, (RsAllocationMipmapControl)mip,
440                                                  ptr, bitmap.getSize(), usage);
441    bitmap.unlockPixels();
442    return id;
443}
444
445static int
446nAllocationCubeCreateFromBitmap(JNIEnv *_env, jobject _this, RsContext con, jint type, jint mip, jobject jbitmap, jint usage)
447{
448    SkBitmap const * nativeBitmap =
449            (SkBitmap const *)_env->GetIntField(jbitmap, gNativeBitmapID);
450    const SkBitmap& bitmap(*nativeBitmap);
451
452    bitmap.lockPixels();
453    const void* ptr = bitmap.getPixels();
454    jint id = (jint)rsAllocationCubeCreateFromBitmap(con,
455                                                      (RsType)type, (RsAllocationMipmapControl)mip,
456                                                      ptr, bitmap.getSize(), usage);
457    bitmap.unlockPixels();
458    return id;
459}
460
461static void
462nAllocationCopyFromBitmap(JNIEnv *_env, jobject _this, RsContext con, jint alloc, jobject jbitmap)
463{
464    SkBitmap const * nativeBitmap =
465            (SkBitmap const *)_env->GetIntField(jbitmap, gNativeBitmapID);
466    const SkBitmap& bitmap(*nativeBitmap);
467    int w = bitmap.width();
468    int h = bitmap.height();
469
470    bitmap.lockPixels();
471    const void* ptr = bitmap.getPixels();
472    rsAllocation2DData(con, (RsAllocation)alloc, 0, 0,
473                       0, RS_ALLOCATION_CUBMAP_FACE_POSITVE_X,
474                       w, h, ptr, bitmap.getSize());
475    bitmap.unlockPixels();
476}
477
478static void
479nAllocationCopyToBitmap(JNIEnv *_env, jobject _this, RsContext con, jint alloc, jobject jbitmap)
480{
481    SkBitmap const * nativeBitmap =
482            (SkBitmap const *)_env->GetIntField(jbitmap, gNativeBitmapID);
483    const SkBitmap& bitmap(*nativeBitmap);
484
485    bitmap.lockPixels();
486    void* ptr = bitmap.getPixels();
487    rsAllocationCopyToBitmap(con, (RsAllocation)alloc, ptr, bitmap.getSize());
488    bitmap.unlockPixels();
489}
490
491static void ReleaseBitmapCallback(void *bmp)
492{
493    SkBitmap const * nativeBitmap = (SkBitmap const *)bmp;
494    nativeBitmap->unlockPixels();
495}
496
497
498static void
499nAllocationData1D_i(JNIEnv *_env, jobject _this, RsContext con, jint alloc, jint offset, jint lod, jint count, jintArray data, int sizeBytes)
500{
501    jint len = _env->GetArrayLength(data);
502    LOG_API("nAllocation1DData_i, con(%p), adapter(%p), offset(%i), count(%i), len(%i), sizeBytes(%i)", con, (RsAllocation)alloc, offset, count, len, sizeBytes);
503    jint *ptr = _env->GetIntArrayElements(data, NULL);
504    rsAllocation1DData(con, (RsAllocation)alloc, offset, lod, count, ptr, sizeBytes);
505    _env->ReleaseIntArrayElements(data, ptr, JNI_ABORT);
506}
507
508static void
509nAllocationData1D_s(JNIEnv *_env, jobject _this, RsContext con, jint alloc, jint offset, jint lod, jint count, jshortArray data, int sizeBytes)
510{
511    jint len = _env->GetArrayLength(data);
512    LOG_API("nAllocation1DData_s, con(%p), adapter(%p), offset(%i), count(%i), len(%i), sizeBytes(%i)", con, (RsAllocation)alloc, offset, count, len, sizeBytes);
513    jshort *ptr = _env->GetShortArrayElements(data, NULL);
514    rsAllocation1DData(con, (RsAllocation)alloc, offset, lod, count, ptr, sizeBytes);
515    _env->ReleaseShortArrayElements(data, ptr, JNI_ABORT);
516}
517
518static void
519nAllocationData1D_b(JNIEnv *_env, jobject _this, RsContext con, jint alloc, jint offset, jint lod, jint count, jbyteArray data, int sizeBytes)
520{
521    jint len = _env->GetArrayLength(data);
522    LOG_API("nAllocation1DData_b, con(%p), adapter(%p), offset(%i), count(%i), len(%i), sizeBytes(%i)", con, (RsAllocation)alloc, offset, count, len, sizeBytes);
523    jbyte *ptr = _env->GetByteArrayElements(data, NULL);
524    rsAllocation1DData(con, (RsAllocation)alloc, offset, lod, count, ptr, sizeBytes);
525    _env->ReleaseByteArrayElements(data, ptr, JNI_ABORT);
526}
527
528static void
529nAllocationData1D_f(JNIEnv *_env, jobject _this, RsContext con, jint alloc, jint offset, jint lod, jint count, jfloatArray data, int sizeBytes)
530{
531    jint len = _env->GetArrayLength(data);
532    LOG_API("nAllocation1DData_f, con(%p), adapter(%p), offset(%i), count(%i), len(%i), sizeBytes(%i)", con, (RsAllocation)alloc, offset, count, len, sizeBytes);
533    jfloat *ptr = _env->GetFloatArrayElements(data, NULL);
534    rsAllocation1DData(con, (RsAllocation)alloc, offset, lod, count, ptr, sizeBytes);
535    _env->ReleaseFloatArrayElements(data, ptr, JNI_ABORT);
536}
537
538static void
539//    native void rsnAllocationElementData1D(int con, int id, int xoff, int compIdx, byte[] d, int sizeBytes);
540nAllocationElementData1D(JNIEnv *_env, jobject _this, RsContext con, jint alloc, jint offset, jint lod, jint compIdx, jbyteArray data, int sizeBytes)
541{
542    jint len = _env->GetArrayLength(data);
543    LOG_API("nAllocationElementData1D, con(%p), alloc(%p), offset(%i), comp(%i), len(%i), sizeBytes(%i)", con, (RsAllocation)alloc, offset, compIdx, len, sizeBytes);
544    jbyte *ptr = _env->GetByteArrayElements(data, NULL);
545    rsAllocation1DElementData(con, (RsAllocation)alloc, offset, lod, ptr, compIdx, sizeBytes);
546    _env->ReleaseByteArrayElements(data, ptr, JNI_ABORT);
547}
548
549static void
550nAllocationData2D_s(JNIEnv *_env, jobject _this, RsContext con, jint alloc, jint xoff, jint yoff, jint lod, jint face,
551                    jint w, jint h, jshortArray data, int sizeBytes)
552{
553    jint len = _env->GetArrayLength(data);
554    LOG_API("nAllocation2DData_s, con(%p), adapter(%p), xoff(%i), yoff(%i), w(%i), h(%i), len(%i)", con, (RsAllocation)alloc, xoff, yoff, w, h, len);
555    jshort *ptr = _env->GetShortArrayElements(data, NULL);
556    rsAllocation2DData(con, (RsAllocation)alloc, xoff, yoff, lod, (RsAllocationCubemapFace)face, w, h, ptr, sizeBytes);
557    _env->ReleaseShortArrayElements(data, ptr, JNI_ABORT);
558}
559
560static void
561nAllocationData2D_b(JNIEnv *_env, jobject _this, RsContext con, jint alloc, jint xoff, jint yoff, jint lod, jint face,
562                    jint w, jint h, jbyteArray data, int sizeBytes)
563{
564    jint len = _env->GetArrayLength(data);
565    LOG_API("nAllocation2DData_b, con(%p), adapter(%p), xoff(%i), yoff(%i), w(%i), h(%i), len(%i)", con, (RsAllocation)alloc, xoff, yoff, w, h, len);
566    jbyte *ptr = _env->GetByteArrayElements(data, NULL);
567    rsAllocation2DData(con, (RsAllocation)alloc, xoff, yoff, lod, (RsAllocationCubemapFace)face, w, h, ptr, sizeBytes);
568    _env->ReleaseByteArrayElements(data, ptr, JNI_ABORT);
569}
570
571static void
572nAllocationData2D_i(JNIEnv *_env, jobject _this, RsContext con, jint alloc, jint xoff, jint yoff, jint lod, jint face,
573                    jint w, jint h, jintArray data, int sizeBytes)
574{
575    jint len = _env->GetArrayLength(data);
576    LOG_API("nAllocation2DData_i, con(%p), adapter(%p), xoff(%i), yoff(%i), w(%i), h(%i), len(%i)", con, (RsAllocation)alloc, xoff, yoff, w, h, len);
577    jint *ptr = _env->GetIntArrayElements(data, NULL);
578    rsAllocation2DData(con, (RsAllocation)alloc, xoff, yoff, lod, (RsAllocationCubemapFace)face, w, h, ptr, sizeBytes);
579    _env->ReleaseIntArrayElements(data, ptr, JNI_ABORT);
580}
581
582static void
583nAllocationData2D_f(JNIEnv *_env, jobject _this, RsContext con, jint alloc, jint xoff, jint yoff, jint lod, jint face,
584                    jint w, jint h, jfloatArray data, int sizeBytes)
585{
586    jint len = _env->GetArrayLength(data);
587    LOG_API("nAllocation2DData_i, con(%p), adapter(%p), xoff(%i), yoff(%i), w(%i), h(%i), len(%i)", con, (RsAllocation)alloc, xoff, yoff, w, h, len);
588    jfloat *ptr = _env->GetFloatArrayElements(data, NULL);
589    rsAllocation2DData(con, (RsAllocation)alloc, xoff, yoff, lod, (RsAllocationCubemapFace)face, w, h, ptr, sizeBytes);
590    _env->ReleaseFloatArrayElements(data, ptr, JNI_ABORT);
591}
592
593static void
594nAllocationRead_i(JNIEnv *_env, jobject _this, RsContext con, jint alloc, jintArray data)
595{
596    jint len = _env->GetArrayLength(data);
597    LOG_API("nAllocationRead_i, con(%p), alloc(%p), len(%i)", con, (RsAllocation)alloc, len);
598    jint *ptr = _env->GetIntArrayElements(data, NULL);
599    jsize length = _env->GetArrayLength(data);
600    rsAllocationRead(con, (RsAllocation)alloc, ptr, length);
601    _env->ReleaseIntArrayElements(data, ptr, 0);
602}
603
604static void
605nAllocationRead_s(JNIEnv *_env, jobject _this, RsContext con, jint alloc, jshortArray data)
606{
607    jint len = _env->GetArrayLength(data);
608    LOG_API("nAllocationRead_i, con(%p), alloc(%p), len(%i)", con, (RsAllocation)alloc, len);
609    jshort *ptr = _env->GetShortArrayElements(data, NULL);
610    jsize length = _env->GetArrayLength(data);
611    rsAllocationRead(con, (RsAllocation)alloc, ptr, length);
612    _env->ReleaseShortArrayElements(data, ptr, 0);
613}
614
615static void
616nAllocationRead_b(JNIEnv *_env, jobject _this, RsContext con, jint alloc, jbyteArray data)
617{
618    jint len = _env->GetArrayLength(data);
619    LOG_API("nAllocationRead_i, con(%p), alloc(%p), len(%i)", con, (RsAllocation)alloc, len);
620    jbyte *ptr = _env->GetByteArrayElements(data, NULL);
621    jsize length = _env->GetArrayLength(data);
622    rsAllocationRead(con, (RsAllocation)alloc, ptr, length);
623    _env->ReleaseByteArrayElements(data, ptr, 0);
624}
625
626static void
627nAllocationRead_f(JNIEnv *_env, jobject _this, RsContext con, jint alloc, jfloatArray data)
628{
629    jint len = _env->GetArrayLength(data);
630    LOG_API("nAllocationRead_f, con(%p), alloc(%p), len(%i)", con, (RsAllocation)alloc, len);
631    jfloat *ptr = _env->GetFloatArrayElements(data, NULL);
632    jsize length = _env->GetArrayLength(data);
633    rsAllocationRead(con, (RsAllocation)alloc, ptr, length);
634    _env->ReleaseFloatArrayElements(data, ptr, 0);
635}
636
637static jint
638nAllocationGetType(JNIEnv *_env, jobject _this, RsContext con, jint a)
639{
640    LOG_API("nAllocationGetType, con(%p), a(%p)", con, (RsAllocation)a);
641    return (jint) rsaAllocationGetType(con, (RsAllocation)a);
642}
643
644static void
645nAllocationResize1D(JNIEnv *_env, jobject _this, RsContext con, jint alloc, jint dimX)
646{
647    LOG_API("nAllocationResize1D, con(%p), alloc(%p), sizeX(%i)", con, (RsAllocation)alloc, dimX);
648    rsAllocationResize1D(con, (RsAllocation)alloc, dimX);
649}
650
651static void
652nAllocationResize2D(JNIEnv *_env, jobject _this, RsContext con, jint alloc, jint dimX, jint dimY)
653{
654    LOG_API("nAllocationResize1D, con(%p), alloc(%p), sizeX(%i), sizeY(%i)", con, (RsAllocation)alloc, dimX, dimY);
655    rsAllocationResize2D(con, (RsAllocation)alloc, dimX, dimY);
656}
657
658// -----------------------------------
659
660static int
661nFileA3DCreateFromAssetStream(JNIEnv *_env, jobject _this, RsContext con, jint native_asset)
662{
663    LOGV("______nFileA3D %u", (uint32_t) native_asset);
664
665    Asset* asset = reinterpret_cast<Asset*>(native_asset);
666
667    jint id = (jint)rsaFileA3DCreateFromMemory(con, asset->getBuffer(false), asset->getLength());
668    return id;
669}
670
671static int
672nFileA3DCreateFromAsset(JNIEnv *_env, jobject _this, RsContext con, jobject _assetMgr, jstring _path)
673{
674    AssetManager* mgr = assetManagerForJavaObject(_env, _assetMgr);
675    if (mgr == NULL) {
676        return 0;
677    }
678
679    AutoJavaStringToUTF8 str(_env, _path);
680    Asset* asset = mgr->open(str.c_str(), Asset::ACCESS_BUFFER);
681    if (asset == NULL) {
682        return 0;
683    }
684
685    jint id = (jint)rsaFileA3DCreateFromAsset(con, asset);
686    return id;
687}
688
689static int
690nFileA3DCreateFromFile(JNIEnv *_env, jobject _this, RsContext con, jstring fileName)
691{
692    AutoJavaStringToUTF8 fileNameUTF(_env, fileName);
693    jint id = (jint)rsaFileA3DCreateFromFile(con, fileNameUTF.c_str());
694
695    return id;
696}
697
698static int
699nFileA3DGetNumIndexEntries(JNIEnv *_env, jobject _this, RsContext con, jint fileA3D)
700{
701    int32_t numEntries = 0;
702    rsaFileA3DGetNumIndexEntries(con, &numEntries, (RsFile)fileA3D);
703    return numEntries;
704}
705
706static void
707nFileA3DGetIndexEntries(JNIEnv *_env, jobject _this, RsContext con, jint fileA3D, jint numEntries, jintArray _ids, jobjectArray _entries)
708{
709    LOGV("______nFileA3D %u", (uint32_t) fileA3D);
710    RsFileIndexEntry *fileEntries = (RsFileIndexEntry*)malloc((uint32_t)numEntries * sizeof(RsFileIndexEntry));
711
712    rsaFileA3DGetIndexEntries(con, fileEntries, (uint32_t)numEntries, (RsFile)fileA3D);
713
714    for(jint i = 0; i < numEntries; i ++) {
715        _env->SetObjectArrayElement(_entries, i, _env->NewStringUTF(fileEntries[i].objectName));
716        _env->SetIntArrayRegion(_ids, i, 1, (const jint*)&fileEntries[i].classID);
717    }
718
719    free(fileEntries);
720}
721
722static int
723nFileA3DGetEntryByIndex(JNIEnv *_env, jobject _this, RsContext con, jint fileA3D, jint index)
724{
725    LOGV("______nFileA3D %u", (uint32_t) fileA3D);
726    jint id = (jint)rsaFileA3DGetEntryByIndex(con, (uint32_t)index, (RsFile)fileA3D);
727    return id;
728}
729
730// -----------------------------------
731
732static int
733nFontCreateFromFile(JNIEnv *_env, jobject _this, RsContext con,
734                    jstring fileName, jfloat fontSize, jint dpi)
735{
736    AutoJavaStringToUTF8 fileNameUTF(_env, fileName);
737    jint id = (jint)rsFontCreateFromFile(con,
738                                         fileNameUTF.c_str(), fileNameUTF.length(),
739                                         fontSize, dpi);
740
741    return id;
742}
743
744static int
745nFontCreateFromAssetStream(JNIEnv *_env, jobject _this, RsContext con,
746                           jstring name, jfloat fontSize, jint dpi, jint native_asset)
747{
748    Asset* asset = reinterpret_cast<Asset*>(native_asset);
749    AutoJavaStringToUTF8 nameUTF(_env, name);
750
751    jint id = (jint)rsFontCreateFromMemory(con,
752                                           nameUTF.c_str(), nameUTF.length(),
753                                           fontSize, dpi,
754                                           asset->getBuffer(false), asset->getLength());
755    return id;
756}
757
758static int
759nFontCreateFromAsset(JNIEnv *_env, jobject _this, RsContext con, jobject _assetMgr, jstring _path,
760                     jfloat fontSize, jint dpi)
761{
762    AssetManager* mgr = assetManagerForJavaObject(_env, _assetMgr);
763    if (mgr == NULL) {
764        return 0;
765    }
766
767    AutoJavaStringToUTF8 str(_env, _path);
768    Asset* asset = mgr->open(str.c_str(), Asset::ACCESS_BUFFER);
769    if (asset == NULL) {
770        return 0;
771    }
772
773    jint id = (jint)rsFontCreateFromMemory(con,
774                                           str.c_str(), str.length(),
775                                           fontSize, dpi,
776                                           asset->getBuffer(false), asset->getLength());
777    delete asset;
778    return id;
779}
780
781// -----------------------------------
782
783static void
784nScriptBindAllocation(JNIEnv *_env, jobject _this, RsContext con, jint script, jint alloc, jint slot)
785{
786    LOG_API("nScriptBindAllocation, con(%p), script(%p), alloc(%p), slot(%i)", con, (RsScript)script, (RsAllocation)alloc, slot);
787    rsScriptBindAllocation(con, (RsScript)script, (RsAllocation)alloc, slot);
788}
789
790static void
791nScriptSetVarI(JNIEnv *_env, jobject _this, RsContext con, jint script, jint slot, jint val)
792{
793    LOG_API("nScriptSetVarI, con(%p), s(%p), slot(%i), val(%i)", con, (void *)script, slot, val);
794    rsScriptSetVarI(con, (RsScript)script, slot, val);
795}
796
797static void
798nScriptSetVarObj(JNIEnv *_env, jobject _this, RsContext con, jint script, jint slot, jint val)
799{
800    LOG_API("nScriptSetVarObj, con(%p), s(%p), slot(%i), val(%i)", con, (void *)script, slot, val);
801    rsScriptSetVarObj(con, (RsScript)script, slot, (RsObjectBase)val);
802}
803
804static void
805nScriptSetVarJ(JNIEnv *_env, jobject _this, RsContext con, jint script, jint slot, jlong val)
806{
807    LOG_API("nScriptSetVarJ, con(%p), s(%p), slot(%i), val(%lli)", con, (void *)script, slot, val);
808    rsScriptSetVarJ(con, (RsScript)script, slot, val);
809}
810
811static void
812nScriptSetVarF(JNIEnv *_env, jobject _this, RsContext con, jint script, jint slot, float val)
813{
814    LOG_API("nScriptSetVarF, con(%p), s(%p), slot(%i), val(%f)", con, (void *)script, slot, val);
815    rsScriptSetVarF(con, (RsScript)script, slot, val);
816}
817
818static void
819nScriptSetVarD(JNIEnv *_env, jobject _this, RsContext con, jint script, jint slot, double val)
820{
821    LOG_API("nScriptSetVarD, con(%p), s(%p), slot(%i), val(%lf)", con, (void *)script, slot, val);
822    rsScriptSetVarD(con, (RsScript)script, slot, val);
823}
824
825static void
826nScriptSetVarV(JNIEnv *_env, jobject _this, RsContext con, jint script, jint slot, jbyteArray data)
827{
828    LOG_API("nScriptSetVarV, con(%p), s(%p), slot(%i)", con, (void *)script, slot);
829    jint len = _env->GetArrayLength(data);
830    jbyte *ptr = _env->GetByteArrayElements(data, NULL);
831    rsScriptSetVarV(con, (RsScript)script, slot, ptr, len);
832    _env->ReleaseByteArrayElements(data, ptr, JNI_ABORT);
833}
834
835
836static void
837nScriptSetTimeZone(JNIEnv *_env, jobject _this, RsContext con, jint script, jbyteArray timeZone)
838{
839    LOG_API("nScriptCSetTimeZone, con(%p), s(%p), timeZone(%s)", con, (void *)script, (const char *)timeZone);
840
841    jint length = _env->GetArrayLength(timeZone);
842    jbyte* timeZone_ptr;
843    timeZone_ptr = (jbyte *) _env->GetPrimitiveArrayCritical(timeZone, (jboolean *)0);
844
845    rsScriptSetTimeZone(con, (RsScript)script, (const char *)timeZone_ptr, length);
846
847    if (timeZone_ptr) {
848        _env->ReleasePrimitiveArrayCritical(timeZone, timeZone_ptr, 0);
849    }
850}
851
852static void
853nScriptInvoke(JNIEnv *_env, jobject _this, RsContext con, jint obj, jint slot)
854{
855    LOG_API("nScriptInvoke, con(%p), script(%p)", con, (void *)obj);
856    rsScriptInvoke(con, (RsScript)obj, slot);
857}
858
859static void
860nScriptInvokeV(JNIEnv *_env, jobject _this, RsContext con, jint script, jint slot, jbyteArray data)
861{
862    LOG_API("nScriptInvokeV, con(%p), s(%p), slot(%i)", con, (void *)script, slot);
863    jint len = _env->GetArrayLength(data);
864    jbyte *ptr = _env->GetByteArrayElements(data, NULL);
865    rsScriptInvokeV(con, (RsScript)script, slot, ptr, len);
866    _env->ReleaseByteArrayElements(data, ptr, JNI_ABORT);
867}
868
869static void
870nScriptForEach(JNIEnv *_env, jobject _this, RsContext con,
871               jint script, jint slot, jint ain, jint aout)
872{
873    LOG_API("nScriptForEach, con(%p), s(%p), slot(%i)", con, (void *)script, slot);
874    rsScriptForEach(con, (RsScript)script, slot, (RsAllocation)ain, (RsAllocation)aout, NULL, 0);
875}
876static void
877nScriptForEachV(JNIEnv *_env, jobject _this, RsContext con,
878                jint script, jint slot, jint ain, jint aout, jbyteArray params)
879{
880    LOG_API("nScriptForEach, con(%p), s(%p), slot(%i)", con, (void *)script, slot);
881    jint len = _env->GetArrayLength(params);
882    jbyte *ptr = _env->GetByteArrayElements(params, NULL);
883    rsScriptForEach(con, (RsScript)script, slot, (RsAllocation)ain, (RsAllocation)aout, ptr, len);
884    _env->ReleaseByteArrayElements(params, ptr, JNI_ABORT);
885}
886
887
888// -----------------------------------
889
890static jint
891nScriptCCreate(JNIEnv *_env, jobject _this, RsContext con,
892               jstring resName, jstring cacheDir,
893               jbyteArray scriptRef, jint length)
894{
895    LOG_API("nScriptCCreate, con(%p)", con);
896
897    AutoJavaStringToUTF8 resNameUTF(_env, resName);
898    AutoJavaStringToUTF8 cacheDirUTF(_env, cacheDir);
899    jint ret = 0;
900    jbyte* script_ptr = NULL;
901    jint _exception = 0;
902    jint remaining;
903    if (!scriptRef) {
904        _exception = 1;
905        //jniThrowException(_env, "java/lang/IllegalArgumentException", "script == null");
906        goto exit;
907    }
908    if (length < 0) {
909        _exception = 1;
910        //jniThrowException(_env, "java/lang/IllegalArgumentException", "length < 0");
911        goto exit;
912    }
913    remaining = _env->GetArrayLength(scriptRef);
914    if (remaining < length) {
915        _exception = 1;
916        //jniThrowException(_env, "java/lang/IllegalArgumentException",
917        //        "length > script.length - offset");
918        goto exit;
919    }
920    script_ptr = (jbyte *)
921        _env->GetPrimitiveArrayCritical(scriptRef, (jboolean *)0);
922
923    //rsScriptCSetText(con, (const char *)script_ptr, length);
924
925    ret = (jint)rsScriptCCreate(con,
926                                resNameUTF.c_str(), resNameUTF.length(),
927                                cacheDirUTF.c_str(), cacheDirUTF.length(),
928                                (const char *)script_ptr, length);
929
930exit:
931    if (script_ptr) {
932        _env->ReleasePrimitiveArrayCritical(scriptRef, script_ptr,
933                _exception ? JNI_ABORT: 0);
934    }
935
936    return ret;
937}
938
939// ---------------------------------------------------------------------------
940
941static jint
942nProgramStoreCreate(JNIEnv *_env, jobject _this, RsContext con,
943                    jboolean colorMaskR, jboolean colorMaskG, jboolean colorMaskB, jboolean colorMaskA,
944                    jboolean depthMask, jboolean ditherEnable,
945                    jint srcFunc, jint destFunc,
946                    jint depthFunc)
947{
948    LOG_API("nProgramStoreCreate, con(%p)", con);
949    return (jint)rsProgramStoreCreate(con, colorMaskR, colorMaskG, colorMaskB, colorMaskA,
950                                      depthMask, ditherEnable, (RsBlendSrcFunc)srcFunc,
951                                      (RsBlendDstFunc)destFunc, (RsDepthFunc)depthFunc);
952}
953
954// ---------------------------------------------------------------------------
955
956static void
957nProgramBindConstants(JNIEnv *_env, jobject _this, RsContext con, jint vpv, jint slot, jint a)
958{
959    LOG_API("nProgramBindConstants, con(%p), vpf(%p), sloat(%i), a(%p)", con, (RsProgramVertex)vpv, slot, (RsAllocation)a);
960    rsProgramBindConstants(con, (RsProgram)vpv, slot, (RsAllocation)a);
961}
962
963static void
964nProgramBindTexture(JNIEnv *_env, jobject _this, RsContext con, jint vpf, jint slot, jint a)
965{
966    LOG_API("nProgramBindTexture, con(%p), vpf(%p), slot(%i), a(%p)", con, (RsProgramFragment)vpf, slot, (RsAllocation)a);
967    rsProgramBindTexture(con, (RsProgramFragment)vpf, slot, (RsAllocation)a);
968}
969
970static void
971nProgramBindSampler(JNIEnv *_env, jobject _this, RsContext con, jint vpf, jint slot, jint a)
972{
973    LOG_API("nProgramBindSampler, con(%p), vpf(%p), slot(%i), a(%p)", con, (RsProgramFragment)vpf, slot, (RsSampler)a);
974    rsProgramBindSampler(con, (RsProgramFragment)vpf, slot, (RsSampler)a);
975}
976
977// ---------------------------------------------------------------------------
978
979static jint
980nProgramFragmentCreate(JNIEnv *_env, jobject _this, RsContext con, jstring shader, jintArray params)
981{
982    AutoJavaStringToUTF8 shaderUTF(_env, shader);
983    jint *paramPtr = _env->GetIntArrayElements(params, NULL);
984    jint paramLen = _env->GetArrayLength(params);
985
986    LOG_API("nProgramFragmentCreate, con(%p), paramLen(%i)", con, paramLen);
987
988    jint ret = (jint)rsProgramFragmentCreate(con, shaderUTF.c_str(), shaderUTF.length(), (uint32_t *)paramPtr, paramLen);
989    _env->ReleaseIntArrayElements(params, paramPtr, JNI_ABORT);
990    return ret;
991}
992
993
994// ---------------------------------------------------------------------------
995
996static jint
997nProgramVertexCreate(JNIEnv *_env, jobject _this, RsContext con, jstring shader, jintArray params)
998{
999    AutoJavaStringToUTF8 shaderUTF(_env, shader);
1000    jint *paramPtr = _env->GetIntArrayElements(params, NULL);
1001    jint paramLen = _env->GetArrayLength(params);
1002
1003    LOG_API("nProgramVertexCreate, con(%p), paramLen(%i)", con, paramLen);
1004
1005    jint ret = (jint)rsProgramVertexCreate(con, shaderUTF.c_str(), shaderUTF.length(), (uint32_t *)paramPtr, paramLen);
1006    _env->ReleaseIntArrayElements(params, paramPtr, JNI_ABORT);
1007    return ret;
1008}
1009
1010// ---------------------------------------------------------------------------
1011
1012static jint
1013nProgramRasterCreate(JNIEnv *_env, jobject _this, RsContext con, jboolean pointSmooth,
1014                     jboolean lineSmooth, jboolean pointSprite, jfloat lineWidth, jint cull)
1015{
1016    LOG_API("nProgramRasterCreate, con(%p), pointSmooth(%i), lineSmooth(%i), pointSprite(%i)",
1017            con, pointSmooth, lineSmooth, pointSprite);
1018    return (jint)rsProgramRasterCreate(con, pointSmooth, lineSmooth, pointSprite, lineWidth, (RsCullMode)cull);
1019}
1020
1021
1022// ---------------------------------------------------------------------------
1023
1024static void
1025nContextBindRootScript(JNIEnv *_env, jobject _this, RsContext con, jint script)
1026{
1027    LOG_API("nContextBindRootScript, con(%p), script(%p)", con, (RsScript)script);
1028    rsContextBindRootScript(con, (RsScript)script);
1029}
1030
1031static void
1032nContextBindProgramStore(JNIEnv *_env, jobject _this, RsContext con, jint pfs)
1033{
1034    LOG_API("nContextBindProgramStore, con(%p), pfs(%p)", con, (RsProgramStore)pfs);
1035    rsContextBindProgramStore(con, (RsProgramStore)pfs);
1036}
1037
1038static void
1039nContextBindProgramFragment(JNIEnv *_env, jobject _this, RsContext con, jint pf)
1040{
1041    LOG_API("nContextBindProgramFragment, con(%p), pf(%p)", con, (RsProgramFragment)pf);
1042    rsContextBindProgramFragment(con, (RsProgramFragment)pf);
1043}
1044
1045static void
1046nContextBindProgramVertex(JNIEnv *_env, jobject _this, RsContext con, jint pf)
1047{
1048    LOG_API("nContextBindProgramVertex, con(%p), pf(%p)", con, (RsProgramVertex)pf);
1049    rsContextBindProgramVertex(con, (RsProgramVertex)pf);
1050}
1051
1052static void
1053nContextBindProgramRaster(JNIEnv *_env, jobject _this, RsContext con, jint pf)
1054{
1055    LOG_API("nContextBindProgramRaster, con(%p), pf(%p)", con, (RsProgramRaster)pf);
1056    rsContextBindProgramRaster(con, (RsProgramRaster)pf);
1057}
1058
1059
1060// ---------------------------------------------------------------------------
1061
1062static jint
1063nSamplerCreate(JNIEnv *_env, jobject _this, RsContext con, jint magFilter, jint minFilter,
1064               jint wrapS, jint wrapT, jint wrapR, jfloat aniso)
1065{
1066    LOG_API("nSamplerCreate, con(%p)", con);
1067    return (jint)rsSamplerCreate(con,
1068                                 (RsSamplerValue)magFilter,
1069                                 (RsSamplerValue)minFilter,
1070                                 (RsSamplerValue)wrapS,
1071                                 (RsSamplerValue)wrapT,
1072                                 (RsSamplerValue)wrapR,
1073                                 aniso);
1074}
1075
1076// ---------------------------------------------------------------------------
1077
1078static jint
1079nMeshCreate(JNIEnv *_env, jobject _this, RsContext con, jint vtxCount, jint idxCount)
1080{
1081    LOG_API("nMeshCreate, con(%p), vtxCount(%i), idxCount(%i)", con, vtxCount, idxCount);
1082    int id = (int)rsMeshCreate(con, vtxCount, idxCount);
1083    return id;
1084}
1085
1086static void
1087nMeshBindVertex(JNIEnv *_env, jobject _this, RsContext con, jint mesh, jint alloc, jint slot)
1088{
1089    LOG_API("nMeshBindVertex, con(%p), Mesh(%p), Alloc(%p), slot(%i)", con, (RsMesh)mesh, (RsAllocation)alloc, slot);
1090    rsMeshBindVertex(con, (RsMesh)mesh, (RsAllocation)alloc, slot);
1091}
1092
1093static void
1094nMeshBindIndex(JNIEnv *_env, jobject _this, RsContext con, jint mesh, jint alloc, jint primID, jint slot)
1095{
1096    LOG_API("nMeshBindIndex, con(%p), Mesh(%p), Alloc(%p)", con, (RsMesh)mesh, (RsAllocation)alloc);
1097    rsMeshBindIndex(con, (RsMesh)mesh, (RsAllocation)alloc, primID, slot);
1098}
1099
1100static void
1101nMeshInitVertexAttribs(JNIEnv *_env, jobject _this, RsContext con, jint mesh)
1102{
1103    LOG_API("nMeshInitVertexAttribs, con(%p), Mesh(%p)", con, (RsMesh)mesh);
1104    rsMeshInitVertexAttribs(con, (RsMesh)mesh);
1105}
1106
1107
1108static jint
1109nMeshGetVertexBufferCount(JNIEnv *_env, jobject _this, RsContext con, jint mesh)
1110{
1111    LOG_API("nMeshGetVertexBufferCount, con(%p), Mesh(%p)", con, (RsMesh)mesh);
1112    jint vtxCount = 0;
1113    rsaMeshGetVertexBufferCount(con, (RsMesh)mesh, &vtxCount);
1114    return vtxCount;
1115}
1116
1117static jint
1118nMeshGetIndexCount(JNIEnv *_env, jobject _this, RsContext con, jint mesh)
1119{
1120    LOG_API("nMeshGetIndexCount, con(%p), Mesh(%p)", con, (RsMesh)mesh);
1121    jint idxCount = 0;
1122    rsaMeshGetIndexCount(con, (RsMesh)mesh, &idxCount);
1123    return idxCount;
1124}
1125
1126static void
1127nMeshGetVertices(JNIEnv *_env, jobject _this, RsContext con, jint mesh, jintArray _ids, int numVtxIDs)
1128{
1129    LOG_API("nMeshGetVertices, con(%p), Mesh(%p)", con, (RsMesh)mesh);
1130
1131    RsAllocation *allocs = (RsAllocation*)malloc((uint32_t)numVtxIDs * sizeof(RsAllocation));
1132    rsaMeshGetVertices(con, (RsMesh)mesh, allocs, (uint32_t)numVtxIDs);
1133
1134    for(jint i = 0; i < numVtxIDs; i ++) {
1135        _env->SetIntArrayRegion(_ids, i, 1, (const jint*)&allocs[i]);
1136    }
1137
1138    free(allocs);
1139}
1140
1141static void
1142nMeshGetIndices(JNIEnv *_env, jobject _this, RsContext con, jint mesh, jintArray _idxIds, jintArray _primitives, int numIndices)
1143{
1144    LOG_API("nMeshGetVertices, con(%p), Mesh(%p)", con, (RsMesh)mesh);
1145
1146    RsAllocation *allocs = (RsAllocation*)malloc((uint32_t)numIndices * sizeof(RsAllocation));
1147    uint32_t *prims= (uint32_t*)malloc((uint32_t)numIndices * sizeof(uint32_t));
1148
1149    rsaMeshGetIndices(con, (RsMesh)mesh, allocs, prims, (uint32_t)numIndices);
1150
1151    for(jint i = 0; i < numIndices; i ++) {
1152        _env->SetIntArrayRegion(_idxIds, i, 1, (const jint*)&allocs[i]);
1153        _env->SetIntArrayRegion(_primitives, i, 1, (const jint*)&prims[i]);
1154    }
1155
1156    free(allocs);
1157    free(prims);
1158}
1159
1160// ---------------------------------------------------------------------------
1161
1162
1163static const char *classPathName = "android/renderscript/RenderScript";
1164
1165static JNINativeMethod methods[] = {
1166{"_nInit",                         "()V",                                     (void*)_nInit },
1167
1168{"nDeviceCreate",                  "()I",                                     (void*)nDeviceCreate },
1169{"nDeviceDestroy",                 "(I)V",                                    (void*)nDeviceDestroy },
1170{"nDeviceSetConfig",               "(III)V",                                  (void*)nDeviceSetConfig },
1171{"nContextGetUserMessage",         "(I[I)V",                                  (void*)nContextGetUserMessage },
1172{"nContextGetErrorMessage",        "(I)Ljava/lang/String;",                   (void*)nContextGetErrorMessage },
1173{"nContextPeekMessage",            "(I[IZ)I",                                 (void*)nContextPeekMessage },
1174
1175{"nContextInitToClient",           "(I)V",                                    (void*)nContextInitToClient },
1176{"nContextDeinitToClient",         "(I)V",                                    (void*)nContextDeinitToClient },
1177
1178
1179// All methods below are thread protected in java.
1180{"rsnContextCreate",                 "(II)I",                                 (void*)nContextCreate },
1181{"rsnContextCreateGL",               "(IIIIIIIIIIIIFI)I",                     (void*)nContextCreateGL },
1182{"rsnContextFinish",                 "(I)V",                                  (void*)nContextFinish },
1183{"rsnContextSetPriority",            "(II)V",                                 (void*)nContextSetPriority },
1184{"rsnContextSetSurface",             "(IIILandroid/view/Surface;)V",          (void*)nContextSetSurface },
1185{"rsnContextDestroy",                "(I)V",                                  (void*)nContextDestroy },
1186{"rsnContextDump",                   "(II)V",                                 (void*)nContextDump },
1187{"rsnContextPause",                  "(I)V",                                  (void*)nContextPause },
1188{"rsnContextResume",                 "(I)V",                                  (void*)nContextResume },
1189{"rsnAssignName",                    "(II[B)V",                               (void*)nAssignName },
1190{"rsnGetName",                       "(II)Ljava/lang/String;",                (void*)nGetName },
1191{"rsnObjDestroy",                    "(II)V",                                 (void*)nObjDestroy },
1192
1193{"rsnFileA3DCreateFromFile",         "(ILjava/lang/String;)I",                (void*)nFileA3DCreateFromFile },
1194{"rsnFileA3DCreateFromAssetStream",  "(II)I",                                 (void*)nFileA3DCreateFromAssetStream },
1195{"rsnFileA3DCreateFromAsset",        "(ILandroid/content/res/AssetManager;Ljava/lang/String;)I",            (void*)nFileA3DCreateFromAsset },
1196{"rsnFileA3DGetNumIndexEntries",     "(II)I",                                 (void*)nFileA3DGetNumIndexEntries },
1197{"rsnFileA3DGetIndexEntries",        "(III[I[Ljava/lang/String;)V",           (void*)nFileA3DGetIndexEntries },
1198{"rsnFileA3DGetEntryByIndex",        "(III)I",                                (void*)nFileA3DGetEntryByIndex },
1199
1200{"rsnFontCreateFromFile",            "(ILjava/lang/String;FI)I",              (void*)nFontCreateFromFile },
1201{"rsnFontCreateFromAssetStream",     "(ILjava/lang/String;FII)I",             (void*)nFontCreateFromAssetStream },
1202{"rsnFontCreateFromAsset",        "(ILandroid/content/res/AssetManager;Ljava/lang/String;FI)I",            (void*)nFontCreateFromAsset },
1203
1204{"rsnElementCreate",                 "(IIIZI)I",                              (void*)nElementCreate },
1205{"rsnElementCreate2",                "(I[I[Ljava/lang/String;[I)I",           (void*)nElementCreate2 },
1206{"rsnElementGetNativeData",          "(II[I)V",                               (void*)nElementGetNativeData },
1207{"rsnElementGetSubElements",         "(II[I[Ljava/lang/String;)V",            (void*)nElementGetSubElements },
1208
1209{"rsnTypeCreate",                    "(IIIIIZZ)I",                            (void*)nTypeCreate },
1210{"rsnTypeGetNativeData",             "(II[I)V",                               (void*)nTypeGetNativeData },
1211
1212{"rsnAllocationCreateTyped",         "(IIII)I",                               (void*)nAllocationCreateTyped },
1213{"rsnAllocationCreateFromBitmap",    "(IIILandroid/graphics/Bitmap;I)I",      (void*)nAllocationCreateFromBitmap },
1214{"rsnAllocationCubeCreateFromBitmap","(IIILandroid/graphics/Bitmap;I)I",      (void*)nAllocationCubeCreateFromBitmap },
1215
1216{"rsnAllocationCopyFromBitmap",      "(IILandroid/graphics/Bitmap;)V",        (void*)nAllocationCopyFromBitmap },
1217{"rsnAllocationCopyToBitmap",        "(IILandroid/graphics/Bitmap;)V",        (void*)nAllocationCopyToBitmap },
1218
1219{"rsnAllocationSyncAll",             "(III)V",                                (void*)nAllocationSyncAll },
1220{"rsnAllocationData1D",              "(IIIII[II)V",                           (void*)nAllocationData1D_i },
1221{"rsnAllocationData1D",              "(IIIII[SI)V",                           (void*)nAllocationData1D_s },
1222{"rsnAllocationData1D",              "(IIIII[BI)V",                           (void*)nAllocationData1D_b },
1223{"rsnAllocationData1D",              "(IIIII[FI)V",                           (void*)nAllocationData1D_f },
1224{"rsnAllocationElementData1D",       "(IIIII[BI)V",                           (void*)nAllocationElementData1D },
1225{"rsnAllocationData2D",              "(IIIIIIII[II)V",                        (void*)nAllocationData2D_i },
1226{"rsnAllocationData2D",              "(IIIIIIII[SI)V",                        (void*)nAllocationData2D_s },
1227{"rsnAllocationData2D",              "(IIIIIIII[BI)V",                        (void*)nAllocationData2D_b },
1228{"rsnAllocationData2D",              "(IIIIIIII[FI)V",                        (void*)nAllocationData2D_f },
1229{"rsnAllocationRead",                "(II[I)V",                               (void*)nAllocationRead_i },
1230{"rsnAllocationRead",                "(II[S)V",                               (void*)nAllocationRead_s },
1231{"rsnAllocationRead",                "(II[B)V",                               (void*)nAllocationRead_b },
1232{"rsnAllocationRead",                "(II[F)V",                               (void*)nAllocationRead_f },
1233{"rsnAllocationGetType",             "(II)I",                                 (void*)nAllocationGetType},
1234{"rsnAllocationResize1D",            "(III)V",                                (void*)nAllocationResize1D },
1235{"rsnAllocationResize2D",            "(IIII)V",                               (void*)nAllocationResize2D },
1236{"rsnAllocationGenerateMipmaps",     "(II)V",                                 (void*)nAllocationGenerateMipmaps },
1237
1238{"rsnScriptBindAllocation",          "(IIII)V",                               (void*)nScriptBindAllocation },
1239{"rsnScriptSetTimeZone",             "(II[B)V",                               (void*)nScriptSetTimeZone },
1240{"rsnScriptInvoke",                  "(III)V",                                (void*)nScriptInvoke },
1241{"rsnScriptInvokeV",                 "(III[B)V",                              (void*)nScriptInvokeV },
1242{"rsnScriptForEach",                 "(IIIII)V",                              (void*)nScriptForEach },
1243{"rsnScriptForEach",                 "(IIIII[B)V",                            (void*)nScriptForEachV },
1244{"rsnScriptSetVarI",                 "(IIII)V",                               (void*)nScriptSetVarI },
1245{"rsnScriptSetVarJ",                 "(IIIJ)V",                               (void*)nScriptSetVarJ },
1246{"rsnScriptSetVarF",                 "(IIIF)V",                               (void*)nScriptSetVarF },
1247{"rsnScriptSetVarD",                 "(IIID)V",                               (void*)nScriptSetVarD },
1248{"rsnScriptSetVarV",                 "(III[B)V",                              (void*)nScriptSetVarV },
1249{"rsnScriptSetVarObj",               "(IIII)V",                               (void*)nScriptSetVarObj },
1250
1251{"rsnScriptCCreate",                 "(ILjava/lang/String;Ljava/lang/String;[BI)I",  (void*)nScriptCCreate },
1252
1253{"rsnProgramStoreCreate",            "(IZZZZZZIII)I",                         (void*)nProgramStoreCreate },
1254
1255{"rsnProgramBindConstants",          "(IIII)V",                               (void*)nProgramBindConstants },
1256{"rsnProgramBindTexture",            "(IIII)V",                               (void*)nProgramBindTexture },
1257{"rsnProgramBindSampler",            "(IIII)V",                               (void*)nProgramBindSampler },
1258
1259{"rsnProgramFragmentCreate",         "(ILjava/lang/String;[I)I",              (void*)nProgramFragmentCreate },
1260{"rsnProgramRasterCreate",           "(IZZZFI)I",                             (void*)nProgramRasterCreate },
1261{"rsnProgramVertexCreate",           "(ILjava/lang/String;[I)I",              (void*)nProgramVertexCreate },
1262
1263{"rsnContextBindRootScript",         "(II)V",                                 (void*)nContextBindRootScript },
1264{"rsnContextBindProgramStore",       "(II)V",                                 (void*)nContextBindProgramStore },
1265{"rsnContextBindProgramFragment",    "(II)V",                                 (void*)nContextBindProgramFragment },
1266{"rsnContextBindProgramVertex",      "(II)V",                                 (void*)nContextBindProgramVertex },
1267{"rsnContextBindProgramRaster",      "(II)V",                                 (void*)nContextBindProgramRaster },
1268
1269{"rsnSamplerCreate",                 "(IIIIIIF)I",                            (void*)nSamplerCreate },
1270
1271{"rsnMeshCreate",                    "(III)I",                                (void*)nMeshCreate },
1272{"rsnMeshBindVertex",                "(IIII)V",                               (void*)nMeshBindVertex },
1273{"rsnMeshBindIndex",                 "(IIIII)V",                              (void*)nMeshBindIndex },
1274{"rsnMeshInitVertexAttribs",         "(II)V",                                 (void*)nMeshInitVertexAttribs },
1275
1276{"rsnMeshGetVertexBufferCount",      "(II)I",                                 (void*)nMeshGetVertexBufferCount },
1277{"rsnMeshGetIndexCount",             "(II)I",                                 (void*)nMeshGetIndexCount },
1278{"rsnMeshGetVertices",               "(II[II)V",                              (void*)nMeshGetVertices },
1279{"rsnMeshGetIndices",                "(II[I[II)V",                            (void*)nMeshGetIndices },
1280
1281};
1282
1283static int registerFuncs(JNIEnv *_env)
1284{
1285    return android::AndroidRuntime::registerNativeMethods(
1286            _env, classPathName, methods, NELEM(methods));
1287}
1288
1289// ---------------------------------------------------------------------------
1290
1291jint JNI_OnLoad(JavaVM* vm, void* reserved)
1292{
1293    JNIEnv* env = NULL;
1294    jint result = -1;
1295
1296    if (vm->GetEnv((void**) &env, JNI_VERSION_1_4) != JNI_OK) {
1297        LOGE("ERROR: GetEnv failed\n");
1298        goto bail;
1299    }
1300    assert(env != NULL);
1301
1302    if (registerFuncs(env) < 0) {
1303        LOGE("ERROR: MediaPlayer native registration failed\n");
1304        goto bail;
1305    }
1306
1307    /* success -- return valid version number */
1308    result = JNI_VERSION_1_4;
1309
1310bail:
1311    return result;
1312}
1313