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