[go: nahoru, domu]

RenderScript.java revision 93697c5f8eba2e0e9e67222f5505a6cd44416022
1/*
2 * Copyright (C) 2008-2012 The Android Open Source Project
3 *
4 * Licensed under the Apache License, Version 2.0 (the "License");
5 * you may not use this file except in compliance with the License.
6 * You may obtain a copy of the License at
7 *
8 *      http://www.apache.org/licenses/LICENSE-2.0
9 *
10 * Unless required by applicable law or agreed to in writing, software
11 * distributed under the License is distributed on an "AS IS" BASIS,
12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 * See the License for the specific language governing permissions and
14 * limitations under the License.
15 */
16
17package android.renderscript;
18
19import java.io.File;
20import java.lang.reflect.Method;
21import java.util.concurrent.locks.ReentrantReadWriteLock;
22
23import android.content.Context;
24import android.content.res.AssetManager;
25import android.graphics.Bitmap;
26import android.graphics.SurfaceTexture;
27import android.os.Process;
28import android.util.Log;
29import android.view.Surface;
30import android.os.SystemProperties;
31import android.os.Trace;
32
33/**
34 * This class provides access to a RenderScript context, which controls RenderScript
35 * initialization, resource management, and teardown. An instance of the RenderScript
36 * class must be created before any other RS objects can be created.
37 *
38 * <div class="special reference">
39 * <h3>Developer Guides</h3>
40 * <p>For more information about creating an application that uses RenderScript, read the
41 * <a href="{@docRoot}guide/topics/renderscript/index.html">RenderScript</a> developer guide.</p>
42 * </div>
43 **/
44public class RenderScript {
45    static final long TRACE_TAG = Trace.TRACE_TAG_RS;
46
47    static final String LOG_TAG = "RenderScript_jni";
48    static final boolean DEBUG  = false;
49    @SuppressWarnings({"UnusedDeclaration", "deprecation"})
50    static final boolean LOG_ENABLED = false;
51
52    private Context mApplicationContext;
53
54    /*
55     * We use a class initializer to allow the native code to cache some
56     * field offsets.
57     */
58    @SuppressWarnings({"FieldCanBeLocal", "UnusedDeclaration"}) // TODO: now used locally; remove?
59    static boolean sInitialized;
60    native static void _nInit();
61
62    static Object sRuntime;
63    static Method registerNativeAllocation;
64    static Method registerNativeFree;
65
66    /*
67     * Context creation flag that specifies a normal context.
68    */
69    public static final int CREATE_FLAG_NONE = 0x0000;
70
71    /*
72     * Context creation flag which specifies a context optimized for low
73     * latency over peak performance. This is a hint and may have no effect
74     * on some implementations.
75    */
76    public static final int CREATE_FLAG_LOW_LATENCY = 0x0002;
77
78    /*
79     * Context creation flag which specifies a context optimized for long
80     * battery life over peak performance. This is a hint and may have no effect
81     * on some implementations.
82    */
83    public static final int CREATE_FLAG_LOW_POWER = 0x0004;
84
85    /*
86     * Detect the bitness of the VM to allow FieldPacker to do the right thing.
87     */
88    static native int rsnSystemGetPointerSize();
89    static int sPointerSize;
90
91    static {
92        sInitialized = false;
93        if (!SystemProperties.getBoolean("config.disable_renderscript", false)) {
94            try {
95                Class<?> vm_runtime = Class.forName("dalvik.system.VMRuntime");
96                Method get_runtime = vm_runtime.getDeclaredMethod("getRuntime");
97                sRuntime = get_runtime.invoke(null);
98                registerNativeAllocation = vm_runtime.getDeclaredMethod("registerNativeAllocation", Integer.TYPE);
99                registerNativeFree = vm_runtime.getDeclaredMethod("registerNativeFree", Integer.TYPE);
100            } catch (Exception e) {
101                Log.e(LOG_TAG, "Error loading GC methods: " + e);
102                throw new RSRuntimeException("Error loading GC methods: " + e);
103            }
104            try {
105                System.loadLibrary("rs_jni");
106                _nInit();
107                sInitialized = true;
108                sPointerSize = rsnSystemGetPointerSize();
109            } catch (UnsatisfiedLinkError e) {
110                Log.e(LOG_TAG, "Error loading RS jni library: " + e);
111                throw new RSRuntimeException("Error loading RS jni library: " + e);
112            }
113        }
114    }
115
116    // Non-threadsafe functions.
117    native long  nDeviceCreate();
118    native void nDeviceDestroy(long dev);
119    native void nDeviceSetConfig(long dev, int param, int value);
120    native int nContextGetUserMessage(long con, int[] data);
121    native String nContextGetErrorMessage(long con);
122    native int  nContextPeekMessage(long con, int[] subID);
123    native void nContextInitToClient(long con);
124    native void nContextDeinitToClient(long con);
125
126    static File mCacheDir;
127
128    // this should be a monotonically increasing ID
129    // used in conjunction with the API version of a device
130    static final long sMinorID = 1;
131
132    /**
133     * Returns an identifier that can be used to identify a particular
134     * minor version of RS.
135     *
136     * @hide
137     */
138    public static long getMinorID() {
139        return sMinorID;
140    }
141
142     /**
143     * Sets the directory to use as a persistent storage for the
144     * renderscript object file cache.
145     *
146     * @hide
147     * @param cacheDir A directory the current process can write to
148     */
149    public static void setupDiskCache(File cacheDir) {
150        if (!sInitialized) {
151            Log.e(LOG_TAG, "RenderScript.setupDiskCache() called when disabled");
152            return;
153        }
154
155        // Defer creation of cache path to nScriptCCreate().
156        mCacheDir = cacheDir;
157    }
158
159    /**
160     * ContextType specifies the specific type of context to be created.
161     *
162     */
163    public enum ContextType {
164        /**
165         * NORMAL context, this is the default and what shipping apps should
166         * use.
167         */
168        NORMAL (0),
169
170        /**
171         * DEBUG context, perform extra runtime checks to validate the
172         * kernels and APIs are being used as intended.  Get and SetElementAt
173         * will be bounds checked in this mode.
174         */
175        DEBUG (1),
176
177        /**
178         * PROFILE context, Intended to be used once the first time an
179         * application is run on a new device.  This mode allows the runtime to
180         * do additional testing and performance tuning.
181         */
182        PROFILE (2);
183
184        int mID;
185        ContextType(int id) {
186            mID = id;
187        }
188    }
189
190    ContextType mContextType;
191    ReentrantReadWriteLock mRWLock;
192
193    // Methods below are wrapped to protect the non-threadsafe
194    // lockless fifo.
195    native long  rsnContextCreateGL(long dev, int ver, int sdkVer,
196                 int colorMin, int colorPref,
197                 int alphaMin, int alphaPref,
198                 int depthMin, int depthPref,
199                 int stencilMin, int stencilPref,
200                 int samplesMin, int samplesPref, float samplesQ, int dpi);
201    synchronized long nContextCreateGL(long dev, int ver, int sdkVer,
202                 int colorMin, int colorPref,
203                 int alphaMin, int alphaPref,
204                 int depthMin, int depthPref,
205                 int stencilMin, int stencilPref,
206                 int samplesMin, int samplesPref, float samplesQ, int dpi) {
207        return rsnContextCreateGL(dev, ver, sdkVer, colorMin, colorPref,
208                                  alphaMin, alphaPref, depthMin, depthPref,
209                                  stencilMin, stencilPref,
210                                  samplesMin, samplesPref, samplesQ, dpi);
211    }
212    native long  rsnContextCreate(long dev, int ver, int sdkVer, int contextType);
213    synchronized long nContextCreate(long dev, int ver, int sdkVer, int contextType) {
214        return rsnContextCreate(dev, ver, sdkVer, contextType);
215    }
216    native void rsnContextDestroy(long con);
217    synchronized void nContextDestroy() {
218        validate();
219
220        // take teardown lock
221        // teardown lock can only be taken when no objects are being destroyed
222        ReentrantReadWriteLock.WriteLock wlock = mRWLock.writeLock();
223        wlock.lock();
224
225        long curCon = mContext;
226        // context is considered dead as of this point
227        mContext = 0;
228
229        wlock.unlock();
230        rsnContextDestroy(curCon);
231    }
232    native void rsnContextSetSurface(long con, int w, int h, Surface sur);
233    synchronized void nContextSetSurface(int w, int h, Surface sur) {
234        validate();
235        rsnContextSetSurface(mContext, w, h, sur);
236    }
237    native void rsnContextSetSurfaceTexture(long con, int w, int h, SurfaceTexture sur);
238    synchronized void nContextSetSurfaceTexture(int w, int h, SurfaceTexture sur) {
239        validate();
240        rsnContextSetSurfaceTexture(mContext, w, h, sur);
241    }
242    native void rsnContextSetPriority(long con, int p);
243    synchronized void nContextSetPriority(int p) {
244        validate();
245        rsnContextSetPriority(mContext, p);
246    }
247    native void rsnContextDump(long con, int bits);
248    synchronized void nContextDump(int bits) {
249        validate();
250        rsnContextDump(mContext, bits);
251    }
252    native void rsnContextFinish(long con);
253    synchronized void nContextFinish() {
254        validate();
255        rsnContextFinish(mContext);
256    }
257
258    native void rsnContextSendMessage(long con, int id, int[] data);
259    synchronized void nContextSendMessage(int id, int[] data) {
260        validate();
261        rsnContextSendMessage(mContext, id, data);
262    }
263
264    native void rsnContextBindRootScript(long con, long script);
265    synchronized void nContextBindRootScript(long script) {
266        validate();
267        rsnContextBindRootScript(mContext, script);
268    }
269    native void rsnContextBindSampler(long con, int sampler, int slot);
270    synchronized void nContextBindSampler(int sampler, int slot) {
271        validate();
272        rsnContextBindSampler(mContext, sampler, slot);
273    }
274    native void rsnContextBindProgramStore(long con, long pfs);
275    synchronized void nContextBindProgramStore(long pfs) {
276        validate();
277        rsnContextBindProgramStore(mContext, pfs);
278    }
279    native void rsnContextBindProgramFragment(long con, long pf);
280    synchronized void nContextBindProgramFragment(long pf) {
281        validate();
282        rsnContextBindProgramFragment(mContext, pf);
283    }
284    native void rsnContextBindProgramVertex(long con, long pv);
285    synchronized void nContextBindProgramVertex(long pv) {
286        validate();
287        rsnContextBindProgramVertex(mContext, pv);
288    }
289    native void rsnContextBindProgramRaster(long con, long pr);
290    synchronized void nContextBindProgramRaster(long pr) {
291        validate();
292        rsnContextBindProgramRaster(mContext, pr);
293    }
294    native void rsnContextPause(long con);
295    synchronized void nContextPause() {
296        validate();
297        rsnContextPause(mContext);
298    }
299    native void rsnContextResume(long con);
300    synchronized void nContextResume() {
301        validate();
302        rsnContextResume(mContext);
303    }
304
305    native void rsnAssignName(long con, long obj, byte[] name);
306    synchronized void nAssignName(long obj, byte[] name) {
307        validate();
308        rsnAssignName(mContext, obj, name);
309    }
310    native String rsnGetName(long con, long obj);
311    synchronized String nGetName(long obj) {
312        validate();
313        return rsnGetName(mContext, obj);
314    }
315
316    // nObjDestroy is explicitly _not_ synchronous to prevent crashes in finalizers
317    native void rsnObjDestroy(long con, long id);
318    void nObjDestroy(long id) {
319        // There is a race condition here.  The calling code may be run
320        // by the gc while teardown is occuring.  This protects againts
321        // deleting dead objects.
322        if (mContext != 0) {
323            rsnObjDestroy(mContext, id);
324        }
325    }
326
327    native long rsnElementCreate(long con, long type, int kind, boolean norm, int vecSize);
328    synchronized long nElementCreate(long type, int kind, boolean norm, int vecSize) {
329        validate();
330        return rsnElementCreate(mContext, type, kind, norm, vecSize);
331    }
332    native long rsnElementCreate2(long con, long[] elements, String[] names, int[] arraySizes);
333    synchronized long nElementCreate2(long[] elements, String[] names, int[] arraySizes) {
334        validate();
335        return rsnElementCreate2(mContext, elements, names, arraySizes);
336    }
337    native void rsnElementGetNativeData(long con, long id, int[] elementData);
338    synchronized void nElementGetNativeData(long id, int[] elementData) {
339        validate();
340        rsnElementGetNativeData(mContext, id, elementData);
341    }
342    native void rsnElementGetSubElements(long con, long id,
343                                         long[] IDs, String[] names, int[] arraySizes);
344    synchronized void nElementGetSubElements(long id, long[] IDs, String[] names, int[] arraySizes) {
345        validate();
346        rsnElementGetSubElements(mContext, id, IDs, names, arraySizes);
347    }
348
349    native long rsnTypeCreate(long con, long eid, int x, int y, int z, boolean mips, boolean faces, int yuv);
350    synchronized long nTypeCreate(long eid, int x, int y, int z, boolean mips, boolean faces, int yuv) {
351        validate();
352        return rsnTypeCreate(mContext, eid, x, y, z, mips, faces, yuv);
353    }
354    native void rsnTypeGetNativeData(long con, long id, long[] typeData);
355    synchronized void nTypeGetNativeData(long id, long[] typeData) {
356        validate();
357        rsnTypeGetNativeData(mContext, id, typeData);
358    }
359
360    native long rsnAllocationCreateTyped(long con, long type, int mip, int usage, long pointer);
361    synchronized long nAllocationCreateTyped(long type, int mip, int usage, long pointer) {
362        validate();
363        return rsnAllocationCreateTyped(mContext, type, mip, usage, pointer);
364    }
365    native long rsnAllocationCreateFromBitmap(long con, long type, int mip, Bitmap bmp, int usage);
366    synchronized long nAllocationCreateFromBitmap(long type, int mip, Bitmap bmp, int usage) {
367        validate();
368        return rsnAllocationCreateFromBitmap(mContext, type, mip, bmp, usage);
369    }
370
371    native long rsnAllocationCreateBitmapBackedAllocation(long con, long type, int mip, Bitmap bmp, int usage);
372    synchronized long nAllocationCreateBitmapBackedAllocation(long type, int mip, Bitmap bmp, int usage) {
373        validate();
374        return rsnAllocationCreateBitmapBackedAllocation(mContext, type, mip, bmp, usage);
375    }
376
377    native long rsnAllocationCubeCreateFromBitmap(long con, long type, int mip, Bitmap bmp, int usage);
378    synchronized long nAllocationCubeCreateFromBitmap(long type, int mip, Bitmap bmp, int usage) {
379        validate();
380        return rsnAllocationCubeCreateFromBitmap(mContext, type, mip, bmp, usage);
381    }
382    native long  rsnAllocationCreateBitmapRef(long con, long type, Bitmap bmp);
383    synchronized long nAllocationCreateBitmapRef(long type, Bitmap bmp) {
384        validate();
385        return rsnAllocationCreateBitmapRef(mContext, type, bmp);
386    }
387    native long  rsnAllocationCreateFromAssetStream(long con, int mips, int assetStream, int usage);
388    synchronized long nAllocationCreateFromAssetStream(int mips, int assetStream, int usage) {
389        validate();
390        return rsnAllocationCreateFromAssetStream(mContext, mips, assetStream, usage);
391    }
392
393    native void  rsnAllocationCopyToBitmap(long con, long alloc, Bitmap bmp);
394    synchronized void nAllocationCopyToBitmap(long alloc, Bitmap bmp) {
395        validate();
396        rsnAllocationCopyToBitmap(mContext, alloc, bmp);
397    }
398
399
400    native void rsnAllocationSyncAll(long con, long alloc, int src);
401    synchronized void nAllocationSyncAll(long alloc, int src) {
402        validate();
403        rsnAllocationSyncAll(mContext, alloc, src);
404    }
405    native Surface rsnAllocationGetSurface(long con, long alloc);
406    synchronized Surface nAllocationGetSurface(long alloc) {
407        validate();
408        return rsnAllocationGetSurface(mContext, alloc);
409    }
410    native void rsnAllocationSetSurface(long con, long alloc, Surface sur);
411    synchronized void nAllocationSetSurface(long alloc, Surface sur) {
412        validate();
413        rsnAllocationSetSurface(mContext, alloc, sur);
414    }
415    native void rsnAllocationIoSend(long con, long alloc);
416    synchronized void nAllocationIoSend(long alloc) {
417        validate();
418        rsnAllocationIoSend(mContext, alloc);
419    }
420    native void rsnAllocationIoReceive(long con, long alloc);
421    synchronized void nAllocationIoReceive(long alloc) {
422        validate();
423        rsnAllocationIoReceive(mContext, alloc);
424    }
425
426
427    native void rsnAllocationGenerateMipmaps(long con, long alloc);
428    synchronized void nAllocationGenerateMipmaps(long alloc) {
429        validate();
430        rsnAllocationGenerateMipmaps(mContext, alloc);
431    }
432    native void  rsnAllocationCopyFromBitmap(long con, long alloc, Bitmap bmp);
433    synchronized void nAllocationCopyFromBitmap(long alloc, Bitmap bmp) {
434        validate();
435        rsnAllocationCopyFromBitmap(mContext, alloc, bmp);
436    }
437
438
439    native void rsnAllocationData1D(long con, long id, int off, int mip, int count, Object d, int sizeBytes, int dt);
440    synchronized void nAllocationData1D(long id, int off, int mip, int count, Object d, int sizeBytes, Element.DataType dt) {
441        validate();
442        rsnAllocationData1D(mContext, id, off, mip, count, d, sizeBytes, dt.mID);
443    }
444
445    native void rsnAllocationElementData1D(long con,long id, int xoff, int mip, int compIdx, byte[] d, int sizeBytes);
446    synchronized void nAllocationElementData1D(long id, int xoff, int mip, int compIdx, byte[] d, int sizeBytes) {
447        validate();
448        rsnAllocationElementData1D(mContext, id, xoff, mip, compIdx, d, sizeBytes);
449    }
450
451    native void rsnAllocationData2D(long con,
452                                    long dstAlloc, int dstXoff, int dstYoff,
453                                    int dstMip, int dstFace,
454                                    int width, int height,
455                                    long srcAlloc, int srcXoff, int srcYoff,
456                                    int srcMip, int srcFace);
457    synchronized void nAllocationData2D(long dstAlloc, int dstXoff, int dstYoff,
458                                        int dstMip, int dstFace,
459                                        int width, int height,
460                                        long srcAlloc, int srcXoff, int srcYoff,
461                                        int srcMip, int srcFace) {
462        validate();
463        rsnAllocationData2D(mContext,
464                            dstAlloc, dstXoff, dstYoff,
465                            dstMip, dstFace,
466                            width, height,
467                            srcAlloc, srcXoff, srcYoff,
468                            srcMip, srcFace);
469    }
470
471    native void rsnAllocationData2D(long con, long id, int xoff, int yoff, int mip, int face,
472                                    int w, int h, Object d, int sizeBytes, int dt);
473    synchronized void nAllocationData2D(long id, int xoff, int yoff, int mip, int face,
474                                        int w, int h, Object d, int sizeBytes, Element.DataType dt) {
475        validate();
476        rsnAllocationData2D(mContext, id, xoff, yoff, mip, face, w, h, d, sizeBytes, dt.mID);
477    }
478
479    native void rsnAllocationData2D(long con, long id, int xoff, int yoff, int mip, int face, Bitmap b);
480    synchronized void nAllocationData2D(long id, int xoff, int yoff, int mip, int face, Bitmap b) {
481        validate();
482        rsnAllocationData2D(mContext, id, xoff, yoff, mip, face, b);
483    }
484
485    native void rsnAllocationData3D(long con,
486                                    long dstAlloc, int dstXoff, int dstYoff, int dstZoff,
487                                    int dstMip,
488                                    int width, int height, int depth,
489                                    long srcAlloc, int srcXoff, int srcYoff, int srcZoff,
490                                    int srcMip);
491    synchronized void nAllocationData3D(long dstAlloc, int dstXoff, int dstYoff, int dstZoff,
492                                        int dstMip,
493                                        int width, int height, int depth,
494                                        long srcAlloc, int srcXoff, int srcYoff, int srcZoff,
495                                        int srcMip) {
496        validate();
497        rsnAllocationData3D(mContext,
498                            dstAlloc, dstXoff, dstYoff, dstZoff,
499                            dstMip, width, height, depth,
500                            srcAlloc, srcXoff, srcYoff, srcZoff, srcMip);
501    }
502
503    native void rsnAllocationData3D(long con, long id, int xoff, int yoff, int zoff, int mip,
504                                    int w, int h, int depth, Object d, int sizeBytes, int dt);
505    synchronized void nAllocationData3D(long id, int xoff, int yoff, int zoff, int mip,
506                                        int w, int h, int depth, Object d, int sizeBytes, Element.DataType dt) {
507        validate();
508        rsnAllocationData3D(mContext, id, xoff, yoff, zoff, mip, w, h, depth, d, sizeBytes, dt.mID);
509    }
510
511    native void rsnAllocationRead(long con, long id, Object d, int dt);
512    synchronized void nAllocationRead(long id, Object d, Element.DataType dt) {
513        validate();
514        rsnAllocationRead(mContext, id, d, dt.mID);
515    }
516
517    native void rsnAllocationRead1D(long con, long id, int off, int mip, int count, Object d,
518                                    int sizeBytes, int dt);
519    synchronized void nAllocationRead1D(long id, int off, int mip, int count, Object d,
520                                        int sizeBytes, Element.DataType dt) {
521        validate();
522        rsnAllocationRead1D(mContext, id, off, mip, count, d, sizeBytes, dt.mID);
523    }
524
525    native void rsnAllocationRead2D(long con, long id, int xoff, int yoff, int mip, int face,
526                                    int w, int h, Object d, int sizeBytes, int dt);
527    synchronized void nAllocationRead2D(long id, int xoff, int yoff, int mip, int face,
528                                        int w, int h, Object d, int sizeBytes, Element.DataType dt) {
529        validate();
530        rsnAllocationRead2D(mContext, id, xoff, yoff, mip, face, w, h, d, sizeBytes, dt.mID);
531    }
532
533    native long  rsnAllocationGetType(long con, long id);
534    synchronized long nAllocationGetType(long id) {
535        validate();
536        return rsnAllocationGetType(mContext, id);
537    }
538
539    native void rsnAllocationResize1D(long con, long id, int dimX);
540    synchronized void nAllocationResize1D(long id, int dimX) {
541        validate();
542        rsnAllocationResize1D(mContext, id, dimX);
543    }
544
545    native long rsnFileA3DCreateFromAssetStream(long con, long assetStream);
546    synchronized long nFileA3DCreateFromAssetStream(long assetStream) {
547        validate();
548        return rsnFileA3DCreateFromAssetStream(mContext, assetStream);
549    }
550    native long rsnFileA3DCreateFromFile(long con, String path);
551    synchronized long nFileA3DCreateFromFile(String path) {
552        validate();
553        return rsnFileA3DCreateFromFile(mContext, path);
554    }
555    native long rsnFileA3DCreateFromAsset(long con, AssetManager mgr, String path);
556    synchronized long nFileA3DCreateFromAsset(AssetManager mgr, String path) {
557        validate();
558        return rsnFileA3DCreateFromAsset(mContext, mgr, path);
559    }
560    native int  rsnFileA3DGetNumIndexEntries(long con, long fileA3D);
561    synchronized int nFileA3DGetNumIndexEntries(long fileA3D) {
562        validate();
563        return rsnFileA3DGetNumIndexEntries(mContext, fileA3D);
564    }
565    native void rsnFileA3DGetIndexEntries(long con, long fileA3D, int numEntries, int[] IDs, String[] names);
566    synchronized void nFileA3DGetIndexEntries(long fileA3D, int numEntries, int[] IDs, String[] names) {
567        validate();
568        rsnFileA3DGetIndexEntries(mContext, fileA3D, numEntries, IDs, names);
569    }
570    native long rsnFileA3DGetEntryByIndex(long con, long fileA3D, int index);
571    synchronized long nFileA3DGetEntryByIndex(long fileA3D, int index) {
572        validate();
573        return rsnFileA3DGetEntryByIndex(mContext, fileA3D, index);
574    }
575
576    native long rsnFontCreateFromFile(long con, String fileName, float size, int dpi);
577    synchronized long nFontCreateFromFile(String fileName, float size, int dpi) {
578        validate();
579        return rsnFontCreateFromFile(mContext, fileName, size, dpi);
580    }
581    native long rsnFontCreateFromAssetStream(long con, String name, float size, int dpi, long assetStream);
582    synchronized long nFontCreateFromAssetStream(String name, float size, int dpi, long assetStream) {
583        validate();
584        return rsnFontCreateFromAssetStream(mContext, name, size, dpi, assetStream);
585    }
586    native long rsnFontCreateFromAsset(long con, AssetManager mgr, String path, float size, int dpi);
587    synchronized long nFontCreateFromAsset(AssetManager mgr, String path, float size, int dpi) {
588        validate();
589        return rsnFontCreateFromAsset(mContext, mgr, path, size, dpi);
590    }
591
592
593    native void rsnScriptBindAllocation(long con, long script, long alloc, int slot);
594    synchronized void nScriptBindAllocation(long script, long alloc, int slot) {
595        validate();
596        rsnScriptBindAllocation(mContext, script, alloc, slot);
597    }
598    native void rsnScriptSetTimeZone(long con, long script, byte[] timeZone);
599    synchronized void nScriptSetTimeZone(long script, byte[] timeZone) {
600        validate();
601        rsnScriptSetTimeZone(mContext, script, timeZone);
602    }
603    native void rsnScriptInvoke(long con, long id, int slot);
604    synchronized void nScriptInvoke(long id, int slot) {
605        validate();
606        rsnScriptInvoke(mContext, id, slot);
607    }
608
609    native void rsnScriptForEach(long con, long id, int slot, long[] ains,
610                                 long aout, byte[] params, int[] limits);
611
612    synchronized void nScriptForEach(long id, int slot, long[] ains, long aout,
613                                     byte[] params, int[] limits) {
614        validate();
615        rsnScriptForEach(mContext, id, slot, ains, aout, params, limits);
616    }
617
618    native void rsnScriptInvokeV(long con, long id, int slot, byte[] params);
619    synchronized void nScriptInvokeV(long id, int slot, byte[] params) {
620        validate();
621        rsnScriptInvokeV(mContext, id, slot, params);
622    }
623
624    native void rsnScriptSetVarI(long con, long id, int slot, int val);
625    synchronized void nScriptSetVarI(long id, int slot, int val) {
626        validate();
627        rsnScriptSetVarI(mContext, id, slot, val);
628    }
629    native int rsnScriptGetVarI(long con, long id, int slot);
630    synchronized int nScriptGetVarI(long id, int slot) {
631        validate();
632        return rsnScriptGetVarI(mContext, id, slot);
633    }
634
635    native void rsnScriptSetVarJ(long con, long id, int slot, long val);
636    synchronized void nScriptSetVarJ(long id, int slot, long val) {
637        validate();
638        rsnScriptSetVarJ(mContext, id, slot, val);
639    }
640    native long rsnScriptGetVarJ(long con, long id, int slot);
641    synchronized long nScriptGetVarJ(long id, int slot) {
642        validate();
643        return rsnScriptGetVarJ(mContext, id, slot);
644    }
645
646    native void rsnScriptSetVarF(long con, long id, int slot, float val);
647    synchronized void nScriptSetVarF(long id, int slot, float val) {
648        validate();
649        rsnScriptSetVarF(mContext, id, slot, val);
650    }
651    native float rsnScriptGetVarF(long con, long id, int slot);
652    synchronized float nScriptGetVarF(long id, int slot) {
653        validate();
654        return rsnScriptGetVarF(mContext, id, slot);
655    }
656    native void rsnScriptSetVarD(long con, long id, int slot, double val);
657    synchronized void nScriptSetVarD(long id, int slot, double val) {
658        validate();
659        rsnScriptSetVarD(mContext, id, slot, val);
660    }
661    native double rsnScriptGetVarD(long con, long id, int slot);
662    synchronized double nScriptGetVarD(long id, int slot) {
663        validate();
664        return rsnScriptGetVarD(mContext, id, slot);
665    }
666    native void rsnScriptSetVarV(long con, long id, int slot, byte[] val);
667    synchronized void nScriptSetVarV(long id, int slot, byte[] val) {
668        validate();
669        rsnScriptSetVarV(mContext, id, slot, val);
670    }
671    native void rsnScriptGetVarV(long con, long id, int slot, byte[] val);
672    synchronized void nScriptGetVarV(long id, int slot, byte[] val) {
673        validate();
674        rsnScriptGetVarV(mContext, id, slot, val);
675    }
676    native void rsnScriptSetVarVE(long con, long id, int slot, byte[] val,
677                                  long e, int[] dims);
678    synchronized void nScriptSetVarVE(long id, int slot, byte[] val,
679                                      long e, int[] dims) {
680        validate();
681        rsnScriptSetVarVE(mContext, id, slot, val, e, dims);
682    }
683    native void rsnScriptSetVarObj(long con, long id, int slot, long val);
684    synchronized void nScriptSetVarObj(long id, int slot, long val) {
685        validate();
686        rsnScriptSetVarObj(mContext, id, slot, val);
687    }
688
689    native long rsnScriptCCreate(long con, String resName, String cacheDir,
690                                 byte[] script, int length);
691    synchronized long nScriptCCreate(String resName, String cacheDir, byte[] script, int length) {
692        validate();
693        return rsnScriptCCreate(mContext, resName, cacheDir, script, length);
694    }
695
696    native long rsnScriptIntrinsicCreate(long con, int id, long eid);
697    synchronized long nScriptIntrinsicCreate(int id, long eid) {
698        validate();
699        return rsnScriptIntrinsicCreate(mContext, id, eid);
700    }
701
702    native long  rsnScriptKernelIDCreate(long con, long sid, int slot, int sig);
703    synchronized long nScriptKernelIDCreate(long sid, int slot, int sig) {
704        validate();
705        return rsnScriptKernelIDCreate(mContext, sid, slot, sig);
706    }
707
708    native long  rsnScriptFieldIDCreate(long con, long sid, int slot);
709    synchronized long nScriptFieldIDCreate(long sid, int slot) {
710        validate();
711        return rsnScriptFieldIDCreate(mContext, sid, slot);
712    }
713
714    native long rsnScriptGroupCreate(long con, long[] kernels, long[] src, long[] dstk, long[] dstf, long[] types);
715    synchronized long nScriptGroupCreate(long[] kernels, long[] src, long[] dstk, long[] dstf, long[] types) {
716        validate();
717        return rsnScriptGroupCreate(mContext, kernels, src, dstk, dstf, types);
718    }
719
720    native void rsnScriptGroupSetInput(long con, long group, long kernel, long alloc);
721    synchronized void nScriptGroupSetInput(long group, long kernel, long alloc) {
722        validate();
723        rsnScriptGroupSetInput(mContext, group, kernel, alloc);
724    }
725
726    native void rsnScriptGroupSetOutput(long con, long group, long kernel, long alloc);
727    synchronized void nScriptGroupSetOutput(long group, long kernel, long alloc) {
728        validate();
729        rsnScriptGroupSetOutput(mContext, group, kernel, alloc);
730    }
731
732    native void rsnScriptGroupExecute(long con, long group);
733    synchronized void nScriptGroupExecute(long group) {
734        validate();
735        rsnScriptGroupExecute(mContext, group);
736    }
737
738    native long  rsnSamplerCreate(long con, int magFilter, int minFilter,
739                                 int wrapS, int wrapT, int wrapR, float aniso);
740    synchronized long nSamplerCreate(int magFilter, int minFilter,
741                                 int wrapS, int wrapT, int wrapR, float aniso) {
742        validate();
743        return rsnSamplerCreate(mContext, magFilter, minFilter, wrapS, wrapT, wrapR, aniso);
744    }
745
746    native long rsnProgramStoreCreate(long con, boolean r, boolean g, boolean b, boolean a,
747                                      boolean depthMask, boolean dither,
748                                      int srcMode, int dstMode, int depthFunc);
749    synchronized long nProgramStoreCreate(boolean r, boolean g, boolean b, boolean a,
750                                         boolean depthMask, boolean dither,
751                                         int srcMode, int dstMode, int depthFunc) {
752        validate();
753        return rsnProgramStoreCreate(mContext, r, g, b, a, depthMask, dither, srcMode,
754                                     dstMode, depthFunc);
755    }
756
757    native long rsnProgramRasterCreate(long con, boolean pointSprite, int cullMode);
758    synchronized long nProgramRasterCreate(boolean pointSprite, int cullMode) {
759        validate();
760        return rsnProgramRasterCreate(mContext, pointSprite, cullMode);
761    }
762
763    native void rsnProgramBindConstants(long con, long pv, int slot, long mID);
764    synchronized void nProgramBindConstants(long pv, int slot, long mID) {
765        validate();
766        rsnProgramBindConstants(mContext, pv, slot, mID);
767    }
768    native void rsnProgramBindTexture(long con, long vpf, int slot, long a);
769    synchronized void nProgramBindTexture(long vpf, int slot, long a) {
770        validate();
771        rsnProgramBindTexture(mContext, vpf, slot, a);
772    }
773    native void rsnProgramBindSampler(long con, long vpf, int slot, long s);
774    synchronized void nProgramBindSampler(long vpf, int slot, long s) {
775        validate();
776        rsnProgramBindSampler(mContext, vpf, slot, s);
777    }
778    native long rsnProgramFragmentCreate(long con, String shader, String[] texNames, long[] params);
779    synchronized long nProgramFragmentCreate(String shader, String[] texNames, long[] params) {
780        validate();
781        return rsnProgramFragmentCreate(mContext, shader, texNames, params);
782    }
783    native long rsnProgramVertexCreate(long con, String shader, String[] texNames, long[] params);
784    synchronized long nProgramVertexCreate(String shader, String[] texNames, long[] params) {
785        validate();
786        return rsnProgramVertexCreate(mContext, shader, texNames, params);
787    }
788
789    native long rsnMeshCreate(long con, long[] vtx, long[] idx, int[] prim);
790    synchronized long nMeshCreate(long[] vtx, long[] idx, int[] prim) {
791        validate();
792        return rsnMeshCreate(mContext, vtx, idx, prim);
793    }
794    native int  rsnMeshGetVertexBufferCount(long con, long id);
795    synchronized int nMeshGetVertexBufferCount(long id) {
796        validate();
797        return rsnMeshGetVertexBufferCount(mContext, id);
798    }
799    native int  rsnMeshGetIndexCount(long con, long id);
800    synchronized int nMeshGetIndexCount(long id) {
801        validate();
802        return rsnMeshGetIndexCount(mContext, id);
803    }
804    native void rsnMeshGetVertices(long con, long id, long[] vtxIds, int vtxIdCount);
805    synchronized void nMeshGetVertices(long id, long[] vtxIds, int vtxIdCount) {
806        validate();
807        rsnMeshGetVertices(mContext, id, vtxIds, vtxIdCount);
808    }
809    native void rsnMeshGetIndices(long con, long id, long[] idxIds, int[] primitives, int vtxIdCount);
810    synchronized void nMeshGetIndices(long id, long[] idxIds, int[] primitives, int vtxIdCount) {
811        validate();
812        rsnMeshGetIndices(mContext, id, idxIds, primitives, vtxIdCount);
813    }
814
815    native long rsnPathCreate(long con, int prim, boolean isStatic, long vtx, long loop, float q);
816    synchronized long nPathCreate(int prim, boolean isStatic, long vtx, long loop, float q) {
817        validate();
818        return rsnPathCreate(mContext, prim, isStatic, vtx, loop, q);
819    }
820
821    long     mDev;
822    long     mContext;
823    @SuppressWarnings({"FieldCanBeLocal"})
824    MessageThread mMessageThread;
825
826    Element mElement_U8;
827    Element mElement_I8;
828    Element mElement_U16;
829    Element mElement_I16;
830    Element mElement_U32;
831    Element mElement_I32;
832    Element mElement_U64;
833    Element mElement_I64;
834    Element mElement_F32;
835    Element mElement_F64;
836    Element mElement_BOOLEAN;
837
838    Element mElement_ELEMENT;
839    Element mElement_TYPE;
840    Element mElement_ALLOCATION;
841    Element mElement_SAMPLER;
842    Element mElement_SCRIPT;
843    Element mElement_MESH;
844    Element mElement_PROGRAM_FRAGMENT;
845    Element mElement_PROGRAM_VERTEX;
846    Element mElement_PROGRAM_RASTER;
847    Element mElement_PROGRAM_STORE;
848    Element mElement_FONT;
849
850    Element mElement_A_8;
851    Element mElement_RGB_565;
852    Element mElement_RGB_888;
853    Element mElement_RGBA_5551;
854    Element mElement_RGBA_4444;
855    Element mElement_RGBA_8888;
856
857    Element mElement_FLOAT_2;
858    Element mElement_FLOAT_3;
859    Element mElement_FLOAT_4;
860
861    Element mElement_DOUBLE_2;
862    Element mElement_DOUBLE_3;
863    Element mElement_DOUBLE_4;
864
865    Element mElement_UCHAR_2;
866    Element mElement_UCHAR_3;
867    Element mElement_UCHAR_4;
868
869    Element mElement_CHAR_2;
870    Element mElement_CHAR_3;
871    Element mElement_CHAR_4;
872
873    Element mElement_USHORT_2;
874    Element mElement_USHORT_3;
875    Element mElement_USHORT_4;
876
877    Element mElement_SHORT_2;
878    Element mElement_SHORT_3;
879    Element mElement_SHORT_4;
880
881    Element mElement_UINT_2;
882    Element mElement_UINT_3;
883    Element mElement_UINT_4;
884
885    Element mElement_INT_2;
886    Element mElement_INT_3;
887    Element mElement_INT_4;
888
889    Element mElement_ULONG_2;
890    Element mElement_ULONG_3;
891    Element mElement_ULONG_4;
892
893    Element mElement_LONG_2;
894    Element mElement_LONG_3;
895    Element mElement_LONG_4;
896
897    Element mElement_YUV;
898
899    Element mElement_MATRIX_4X4;
900    Element mElement_MATRIX_3X3;
901    Element mElement_MATRIX_2X2;
902
903    Sampler mSampler_CLAMP_NEAREST;
904    Sampler mSampler_CLAMP_LINEAR;
905    Sampler mSampler_CLAMP_LINEAR_MIP_LINEAR;
906    Sampler mSampler_WRAP_NEAREST;
907    Sampler mSampler_WRAP_LINEAR;
908    Sampler mSampler_WRAP_LINEAR_MIP_LINEAR;
909    Sampler mSampler_MIRRORED_REPEAT_NEAREST;
910    Sampler mSampler_MIRRORED_REPEAT_LINEAR;
911    Sampler mSampler_MIRRORED_REPEAT_LINEAR_MIP_LINEAR;
912
913    ProgramStore mProgramStore_BLEND_NONE_DEPTH_TEST;
914    ProgramStore mProgramStore_BLEND_NONE_DEPTH_NO_DEPTH;
915    ProgramStore mProgramStore_BLEND_ALPHA_DEPTH_TEST;
916    ProgramStore mProgramStore_BLEND_ALPHA_DEPTH_NO_DEPTH;
917
918    ProgramRaster mProgramRaster_CULL_BACK;
919    ProgramRaster mProgramRaster_CULL_FRONT;
920    ProgramRaster mProgramRaster_CULL_NONE;
921
922    ///////////////////////////////////////////////////////////////////////////////////
923    //
924
925    /**
926     * The base class from which an application should derive in order
927     * to receive RS messages from scripts. When a script calls {@code
928     * rsSendToClient}, the data fields will be filled, and the run
929     * method will be called on a separate thread.  This will occur
930     * some time after {@code rsSendToClient} completes in the script,
931     * as {@code rsSendToClient} is asynchronous. Message handlers are
932     * not guaranteed to have completed when {@link
933     * android.renderscript.RenderScript#finish} returns.
934     *
935     */
936    public static class RSMessageHandler implements Runnable {
937        protected int[] mData;
938        protected int mID;
939        protected int mLength;
940        public void run() {
941        }
942    }
943    /**
944     * If an application is expecting messages, it should set this
945     * field to an instance of {@link RSMessageHandler}.  This
946     * instance will receive all the user messages sent from {@code
947     * sendToClient} by scripts from this context.
948     *
949     */
950    RSMessageHandler mMessageCallback = null;
951
952    public void setMessageHandler(RSMessageHandler msg) {
953        mMessageCallback = msg;
954    }
955    public RSMessageHandler getMessageHandler() {
956        return mMessageCallback;
957    }
958
959    /**
960     * Place a message into the message queue to be sent back to the message
961     * handler once all previous commands have been executed.
962     *
963     * @param id
964     * @param data
965     */
966    public void sendMessage(int id, int[] data) {
967        nContextSendMessage(id, data);
968    }
969
970    /**
971     * The runtime error handler base class.  An application should derive from this class
972     * if it wishes to install an error handler.  When errors occur at runtime,
973     * the fields in this class will be filled, and the run method will be called.
974     *
975     */
976    public static class RSErrorHandler implements Runnable {
977        protected String mErrorMessage;
978        protected int mErrorNum;
979        public void run() {
980        }
981    }
982
983    /**
984     * Application Error handler.  All runtime errors will be dispatched to the
985     * instance of RSAsyncError set here.  If this field is null a
986     * {@link RSRuntimeException} will instead be thrown with details about the error.
987     * This will cause program termaination.
988     *
989     */
990    RSErrorHandler mErrorCallback = null;
991
992    public void setErrorHandler(RSErrorHandler msg) {
993        mErrorCallback = msg;
994    }
995    public RSErrorHandler getErrorHandler() {
996        return mErrorCallback;
997    }
998
999    /**
1000     * RenderScript worker thread priority enumeration.  The default value is
1001     * NORMAL.  Applications wishing to do background processing should set
1002     * their priority to LOW to avoid starving forground processes.
1003     */
1004    public enum Priority {
1005        LOW (Process.THREAD_PRIORITY_BACKGROUND + (5 * Process.THREAD_PRIORITY_LESS_FAVORABLE)),
1006        NORMAL (Process.THREAD_PRIORITY_DISPLAY);
1007
1008        int mID;
1009        Priority(int id) {
1010            mID = id;
1011        }
1012    }
1013
1014    void validateObject(BaseObj o) {
1015        if (o != null) {
1016            if (o.mRS != this) {
1017                throw new RSIllegalArgumentException("Attempting to use an object across contexts.");
1018            }
1019        }
1020    }
1021
1022    void validate() {
1023        if (mContext == 0) {
1024            throw new RSInvalidStateException("Calling RS with no Context active.");
1025        }
1026    }
1027
1028
1029    /**
1030     * Change the priority of the worker threads for this context.
1031     *
1032     * @param p New priority to be set.
1033     */
1034    public void setPriority(Priority p) {
1035        validate();
1036        nContextSetPriority(p.mID);
1037    }
1038
1039    static class MessageThread extends Thread {
1040        RenderScript mRS;
1041        boolean mRun = true;
1042        int[] mAuxData = new int[2];
1043
1044        static final int RS_MESSAGE_TO_CLIENT_NONE = 0;
1045        static final int RS_MESSAGE_TO_CLIENT_EXCEPTION = 1;
1046        static final int RS_MESSAGE_TO_CLIENT_RESIZE = 2;
1047        static final int RS_MESSAGE_TO_CLIENT_ERROR = 3;
1048        static final int RS_MESSAGE_TO_CLIENT_USER = 4;
1049        static final int RS_MESSAGE_TO_CLIENT_NEW_BUFFER = 5;
1050
1051        static final int RS_ERROR_FATAL_DEBUG = 0x0800;
1052        static final int RS_ERROR_FATAL_UNKNOWN = 0x1000;
1053
1054        MessageThread(RenderScript rs) {
1055            super("RSMessageThread");
1056            mRS = rs;
1057
1058        }
1059
1060        public void run() {
1061            // This function is a temporary solution.  The final solution will
1062            // used typed allocations where the message id is the type indicator.
1063            int[] rbuf = new int[16];
1064            mRS.nContextInitToClient(mRS.mContext);
1065            while(mRun) {
1066                rbuf[0] = 0;
1067                int msg = mRS.nContextPeekMessage(mRS.mContext, mAuxData);
1068                int size = mAuxData[1];
1069                int subID = mAuxData[0];
1070
1071                if (msg == RS_MESSAGE_TO_CLIENT_USER) {
1072                    if ((size>>2) >= rbuf.length) {
1073                        rbuf = new int[(size + 3) >> 2];
1074                    }
1075                    if (mRS.nContextGetUserMessage(mRS.mContext, rbuf) !=
1076                        RS_MESSAGE_TO_CLIENT_USER) {
1077                        throw new RSDriverException("Error processing message from RenderScript.");
1078                    }
1079
1080                    if(mRS.mMessageCallback != null) {
1081                        mRS.mMessageCallback.mData = rbuf;
1082                        mRS.mMessageCallback.mID = subID;
1083                        mRS.mMessageCallback.mLength = size;
1084                        mRS.mMessageCallback.run();
1085                    } else {
1086                        throw new RSInvalidStateException("Received a message from the script with no message handler installed.");
1087                    }
1088                    continue;
1089                }
1090
1091                if (msg == RS_MESSAGE_TO_CLIENT_ERROR) {
1092                    String e = mRS.nContextGetErrorMessage(mRS.mContext);
1093
1094                    // Throw RSRuntimeException under the following conditions:
1095                    //
1096                    // 1) It is an unknown fatal error.
1097                    // 2) It is a debug fatal error, and we are not in a
1098                    //    debug context.
1099                    // 3) It is a debug fatal error, and we do not have an
1100                    //    error callback.
1101                    if (subID >= RS_ERROR_FATAL_UNKNOWN ||
1102                        (subID >= RS_ERROR_FATAL_DEBUG &&
1103                         (mRS.mContextType != ContextType.DEBUG ||
1104                          mRS.mErrorCallback == null))) {
1105                        throw new RSRuntimeException("Fatal error " + subID + ", details: " + e);
1106                    }
1107
1108                    if(mRS.mErrorCallback != null) {
1109                        mRS.mErrorCallback.mErrorMessage = e;
1110                        mRS.mErrorCallback.mErrorNum = subID;
1111                        mRS.mErrorCallback.run();
1112                    } else {
1113                        android.util.Log.e(LOG_TAG, "non fatal RS error, " + e);
1114                        // Do not throw here. In these cases, we do not have
1115                        // a fatal error.
1116                    }
1117                    continue;
1118                }
1119
1120                if (msg == RS_MESSAGE_TO_CLIENT_NEW_BUFFER) {
1121                    Allocation.sendBufferNotification(subID);
1122                    continue;
1123                }
1124
1125                // 2: teardown.
1126                // But we want to avoid starving other threads during
1127                // teardown by yielding until the next line in the destructor
1128                // can execute to set mRun = false
1129                try {
1130                    sleep(1, 0);
1131                } catch(InterruptedException e) {
1132                }
1133            }
1134            //Log.d(LOG_TAG, "MessageThread exiting.");
1135        }
1136    }
1137
1138    RenderScript(Context ctx) {
1139        mContextType = ContextType.NORMAL;
1140        if (ctx != null) {
1141            mApplicationContext = ctx.getApplicationContext();
1142        }
1143        mRWLock = new ReentrantReadWriteLock();
1144    }
1145
1146    /**
1147     * Gets the application context associated with the RenderScript context.
1148     *
1149     * @return The application context.
1150     */
1151    public final Context getApplicationContext() {
1152        return mApplicationContext;
1153    }
1154
1155    /**
1156     * @hide
1157     */
1158    public static RenderScript create(Context ctx, int sdkVersion) {
1159        return create(ctx, sdkVersion, ContextType.NORMAL, CREATE_FLAG_NONE);
1160    }
1161
1162    /**
1163     * Create a RenderScript context.
1164     *
1165     * @hide
1166     * @param ctx The context.
1167     * @return RenderScript
1168     */
1169    public static RenderScript create(Context ctx, int sdkVersion, ContextType ct, int flags) {
1170        if (!sInitialized) {
1171            Log.e(LOG_TAG, "RenderScript.create() called when disabled; someone is likely to crash");
1172            return null;
1173        }
1174
1175        if ((flags & ~(CREATE_FLAG_LOW_LATENCY | CREATE_FLAG_LOW_POWER)) != 0) {
1176            throw new RSIllegalArgumentException("Invalid flags passed.");
1177        }
1178
1179        RenderScript rs = new RenderScript(ctx);
1180
1181        rs.mDev = rs.nDeviceCreate();
1182        rs.mContext = rs.nContextCreate(rs.mDev, flags, sdkVersion, ct.mID);
1183        rs.mContextType = ct;
1184        if (rs.mContext == 0) {
1185            throw new RSDriverException("Failed to create RS context.");
1186        }
1187        rs.mMessageThread = new MessageThread(rs);
1188        rs.mMessageThread.start();
1189        return rs;
1190    }
1191
1192    /**
1193     * Create a RenderScript context.
1194     *
1195     * @param ctx The context.
1196     * @return RenderScript
1197     */
1198    public static RenderScript create(Context ctx) {
1199        return create(ctx, ContextType.NORMAL);
1200    }
1201
1202    /**
1203     * Create a RenderScript context.
1204     *
1205     *
1206     * @param ctx The context.
1207     * @param ct The type of context to be created.
1208     * @return RenderScript
1209     */
1210    public static RenderScript create(Context ctx, ContextType ct) {
1211        int v = ctx.getApplicationInfo().targetSdkVersion;
1212        return create(ctx, v, ct, CREATE_FLAG_NONE);
1213    }
1214
1215     /**
1216     * Create a RenderScript context.
1217     *
1218     *
1219     * @param ctx The context.
1220     * @param ct The type of context to be created.
1221     * @param flags The OR of the CREATE_FLAG_* options desired
1222     * @return RenderScript
1223     */
1224    public static RenderScript create(Context ctx, ContextType ct, int flags) {
1225        int v = ctx.getApplicationInfo().targetSdkVersion;
1226        return create(ctx, v, ct, flags);
1227    }
1228
1229    /**
1230     * Print the currently available debugging information about the state of
1231     * the RS context to the log.
1232     *
1233     */
1234    public void contextDump() {
1235        validate();
1236        nContextDump(0);
1237    }
1238
1239    /**
1240     * Wait for any pending asynchronous opeations (such as copies to a RS
1241     * allocation or RS script executions) to complete.
1242     *
1243     */
1244    public void finish() {
1245        nContextFinish();
1246    }
1247
1248    /**
1249     * Destroys this RenderScript context.  Once this function is called,
1250     * using this context or any objects belonging to this context is
1251     * illegal.
1252     *
1253     */
1254    public void destroy() {
1255        validate();
1256        nContextFinish();
1257
1258        nContextDeinitToClient(mContext);
1259        mMessageThread.mRun = false;
1260        try {
1261            mMessageThread.join();
1262        } catch(InterruptedException e) {
1263        }
1264
1265        nContextDestroy();
1266
1267        nDeviceDestroy(mDev);
1268        mDev = 0;
1269    }
1270
1271    boolean isAlive() {
1272        return mContext != 0;
1273    }
1274
1275    long safeID(BaseObj o) {
1276        if(o != null) {
1277            return o.getID(this);
1278        }
1279        return 0;
1280    }
1281}
1282