1 /* 2 * Copyright (C) 2013 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 package android.support.v8.renderscript; 18 19 import java.io.File; 20 import java.lang.reflect.Field; 21 import java.lang.reflect.Method; 22 import java.util.concurrent.locks.ReentrantReadWriteLock; 23 import java.util.ArrayList; 24 import java.nio.ByteBuffer; 25 26 import android.content.Context; 27 import android.content.pm.ApplicationInfo; 28 import android.content.pm.PackageManager; 29 import android.content.res.AssetManager; 30 import android.graphics.Bitmap; 31 import android.graphics.BitmapFactory; 32 import android.os.Process; 33 import android.util.Log; 34 import android.view.Surface; 35 36 /** 37 * This class provides access to a RenderScript context, which controls RenderScript 38 * initialization, resource management, and teardown. An instance of the RenderScript 39 * class must be created before any other RS objects can be created. 40 * 41 * <div class="special reference"> 42 * <h3>Developer Guides</h3> 43 * <p>For more information about creating an application that uses RenderScript, read the 44 * <a href="{@docRoot}guide/topics/renderscript/index.html">RenderScript</a> developer guide.</p> 45 * </div> 46 **/ 47 public class RenderScript { 48 static final String LOG_TAG = "RenderScript_jni"; 49 static final boolean DEBUG = false; 50 @SuppressWarnings({"UnusedDeclaration", "deprecation"}) 51 static final boolean LOG_ENABLED = false; 52 static final int SUPPORT_LIB_API = 23; 53 static final int SUPPORT_LIB_VERSION = 2301; 54 55 static private ArrayList<RenderScript> mProcessContextList = new ArrayList<RenderScript>(); 56 private boolean mIsProcessContext = false; 57 private boolean mEnableMultiInput = false; 58 private int mDispatchAPILevel = 0; 59 60 private int mContextFlags = 0; 61 private int mContextSdkVersion = 0; 62 63 private Context mApplicationContext; 64 private String mNativeLibDir; 65 66 static private String mBlackList = ""; 67 /** 68 * Sets the blackList of Models to only use support lib runtime. 69 * Should be used before context create. 70 * 71 * @param blackList User provided black list string. 72 * 73 * Format: "(MANUFACTURER1:PRODUCT1:MODEL1), (MANUFACTURER2:PRODUCT2:MODEL2)..." 74 * e.g. : To Blacklist Nexus 7(2013) and Nexus 5. 75 * mBlackList = "(asus:razor:Nexus 7), (LGE:hammerhead:Nexus 5)"; 76 */ setBlackList(String blackList)77 static public void setBlackList(String blackList) { 78 if (blackList != null) { 79 mBlackList = blackList; 80 } 81 } 82 /** 83 * Force using support lib runtime. 84 * Should be used before context create. 85 * 86 */ forceCompat()87 static public void forceCompat() { 88 sNative = 0; 89 } 90 /* 91 * We use a class initializer to allow the native code to cache some 92 * field offsets. 93 */ 94 @SuppressWarnings({"FieldCanBeLocal", "UnusedDeclaration"}) 95 static boolean sInitialized; 96 static boolean sUseGCHooks; 97 static Object sRuntime; 98 static Method registerNativeAllocation; 99 static Method registerNativeFree; 100 101 static Object lock = new Object(); 102 103 // Non-threadsafe functions. nLoadSO(boolean useNative, int deviceApi, String libPath)104 native boolean nLoadSO(boolean useNative, int deviceApi, String libPath); nLoadIOSO()105 native boolean nLoadIOSO(); nDeviceCreate()106 native long nDeviceCreate(); nDeviceDestroy(long dev)107 native void nDeviceDestroy(long dev); nDeviceSetConfig(long dev, int param, int value)108 native void nDeviceSetConfig(long dev, int param, int value); nContextGetUserMessage(long con, int[] data)109 native int nContextGetUserMessage(long con, int[] data); nContextGetErrorMessage(long con)110 native String nContextGetErrorMessage(long con); nContextPeekMessage(long con, int[] subID)111 native int nContextPeekMessage(long con, int[] subID); nContextInitToClient(long con)112 native void nContextInitToClient(long con); nContextDeinitToClient(long con)113 native void nContextDeinitToClient(long con); 114 115 static private int sNative = -1; 116 static private int sSdkVersion = -1; 117 static private boolean useIOlib = false; 118 static private boolean useNative; 119 120 /* 121 * Context creation flag that specifies a normal context. 122 * RenderScript Support lib only support normal context. 123 */ 124 public static final int CREATE_FLAG_NONE = 0x0000; 125 getDispatchAPILevel()126 int getDispatchAPILevel() { 127 return mDispatchAPILevel; 128 } 129 isUseNative()130 boolean isUseNative() { 131 return useNative; 132 } 133 /* 134 * Detect the bitness of the VM to allow FieldPacker and generated code to do the right thing. 135 */ rsnSystemGetPointerSize()136 static native int rsnSystemGetPointerSize(); 137 static int sPointerSize; getPointerSize()138 static public int getPointerSize() { 139 // We provide an accessor rather than making the data item public for two reasons. 140 // 1) Prevents anyone outside this class from writing the data item. 141 // 2) Prevents anyone outside this class from reading the data item unless a class 142 // instance has been created (ensuring the data item has been initialized). 143 // DISCLAIMER: Reflection can circumvent these preventive measures. 144 synchronized(lock) { 145 if (!sInitialized) 146 throw new RSInvalidStateException("Calling getPointerSize() before any RenderScript instantiated"); 147 } 148 return sPointerSize; 149 } 150 151 /** 152 * Determines whether or not we should be thunking into the native 153 * RenderScript layer or actually using the compatibility library. 154 */ setupNative(int sdkVersion, Context ctx)155 static private boolean setupNative(int sdkVersion, Context ctx) { 156 // if targetSdkVersion is higher than the device api version, always use compat mode. 157 // Workaround for KK 158 if (android.os.Build.VERSION.SDK_INT < sdkVersion && 159 android.os.Build.VERSION.SDK_INT < android.os.Build.VERSION_CODES.LOLLIPOP) { 160 sNative = 0; 161 } 162 163 if (sNative == -1) { 164 165 // get the value of the debug.rs.forcecompat property 166 int forcecompat = 0; 167 try { 168 Class<?> sysprop = Class.forName("android.os.SystemProperties"); 169 Class[] signature = {String.class, Integer.TYPE}; 170 Method getint = sysprop.getDeclaredMethod("getInt", signature); 171 Object[] args = {"debug.rs.forcecompat", new Integer(0)}; 172 forcecompat = ((java.lang.Integer)getint.invoke(null, args)).intValue(); 173 } catch (Exception e) { 174 175 } 176 177 if ((android.os.Build.VERSION.SDK_INT >= android.os.Build.VERSION_CODES.KITKAT) 178 && forcecompat == 0) { 179 sNative = 1; 180 } else { 181 sNative = 0; 182 } 183 184 185 if (sNative == 1) { 186 // Workarounds that may disable thunking go here 187 ApplicationInfo info; 188 try { 189 info = ctx.getPackageManager().getApplicationInfo(ctx.getPackageName(), 190 PackageManager.GET_META_DATA); 191 } catch (PackageManager.NameNotFoundException e) { 192 // assume no workarounds needed 193 return true; 194 } 195 long minorVersion = 0; 196 197 // load minorID from reflection 198 try { 199 Class<?> javaRS = Class.forName("android.renderscript.RenderScript"); 200 Method getMinorID = javaRS.getDeclaredMethod("getMinorID"); 201 minorVersion = ((java.lang.Long)getMinorID.invoke(null)).longValue(); 202 } catch (Exception e) { 203 // minor version remains 0 on devices with no possible WARs 204 } 205 206 if (info.metaData != null) { 207 // asynchronous teardown: minor version 1+ 208 if (info.metaData.getBoolean("com.android.support.v8.renderscript.EnableAsyncTeardown") == true) { 209 if (minorVersion == 0) { 210 sNative = 0; 211 } 212 } 213 214 // blur issues on some drivers with 4.4 215 if (info.metaData.getBoolean("com.android.support.v8.renderscript.EnableBlurWorkaround") == true) { 216 if (android.os.Build.VERSION.SDK_INT <= 19) { 217 //android.util.Log.e("rs", "war on"); 218 sNative = 0; 219 } 220 } 221 } 222 // end of workarounds 223 } 224 } 225 226 if (sNative == 1) { 227 // check against the blacklist 228 if (mBlackList.length() > 0) { 229 String deviceInfo = '(' + 230 android.os.Build.MANUFACTURER + 231 ':' + 232 android.os.Build.PRODUCT + 233 ':' + 234 android.os.Build.MODEL + 235 ')'; 236 if (mBlackList.contains(deviceInfo)) { 237 sNative = 0; 238 return false; 239 } 240 } 241 return true; 242 } 243 return false; 244 } 245 246 /** 247 * Name of the file that holds the object cache. 248 */ 249 private static final String CACHE_PATH = "com.android.renderscript.cache"; 250 static String mCachePath; 251 252 /** 253 * Sets the directory to use as a persistent storage for the 254 * renderscript object file cache. 255 * 256 * @hide 257 * @param cacheDir A directory the current process can write to 258 */ setupDiskCache(File cacheDir)259 public static void setupDiskCache(File cacheDir) { 260 File f = new File(cacheDir, CACHE_PATH); 261 mCachePath = f.getAbsolutePath(); 262 f.mkdirs(); 263 } 264 265 /** 266 * ContextType specifies the specific type of context to be created. 267 * 268 */ 269 public enum ContextType { 270 /** 271 * NORMAL context, this is the default and what shipping apps should 272 * use. 273 */ 274 NORMAL (0), 275 276 /** 277 * DEBUG context, perform extra runtime checks to validate the 278 * kernels and APIs are being used as intended. Get and SetElementAt 279 * will be bounds checked in this mode. 280 */ 281 DEBUG (1), 282 283 /** 284 * PROFILE context, Intended to be used once the first time an 285 * application is run on a new device. This mode allows the runtime to 286 * do additional testing and performance tuning. 287 */ 288 PROFILE (2); 289 290 int mID; ContextType(int id)291 ContextType(int id) { 292 mID = id; 293 } 294 } 295 296 ContextType mContextType; 297 // Methods below are wrapped to protect the non-threadsafe 298 // lockless fifo. 299 rsnContextCreate(long dev, int ver, int sdkVer, int contextType, String nativeLibDir)300 native long rsnContextCreate(long dev, int ver, int sdkVer, int contextType, String nativeLibDir); nContextCreate(long dev, int ver, int sdkVer, int contextType, String nativeLibDir)301 synchronized long nContextCreate(long dev, int ver, int sdkVer, int contextType, String nativeLibDir) { 302 return rsnContextCreate(dev, ver, sdkVer, contextType, nativeLibDir); 303 } rsnContextDestroy(long con)304 native void rsnContextDestroy(long con); nContextDestroy()305 synchronized void nContextDestroy() { 306 validate(); 307 308 // take teardown lock 309 // teardown lock can only be taken when no objects are being destroyed 310 ReentrantReadWriteLock.WriteLock wlock = mRWLock.writeLock(); 311 wlock.lock(); 312 313 long curCon = mContext; 314 // context is considered dead as of this point 315 mContext = 0; 316 317 wlock.unlock(); 318 rsnContextDestroy(curCon); 319 } rsnContextSetPriority(long con, int p)320 native void rsnContextSetPriority(long con, int p); nContextSetPriority(int p)321 synchronized void nContextSetPriority(int p) { 322 validate(); 323 rsnContextSetPriority(mContext, p); 324 } rsnContextDump(long con, int bits)325 native void rsnContextDump(long con, int bits); nContextDump(int bits)326 synchronized void nContextDump(int bits) { 327 validate(); 328 rsnContextDump(mContext, bits); 329 } rsnContextFinish(long con)330 native void rsnContextFinish(long con); nContextFinish()331 synchronized void nContextFinish() { 332 validate(); 333 rsnContextFinish(mContext); 334 } 335 rsnContextSendMessage(long con, int id, int[] data)336 native void rsnContextSendMessage(long con, int id, int[] data); nContextSendMessage(int id, int[] data)337 synchronized void nContextSendMessage(int id, int[] data) { 338 validate(); 339 rsnContextSendMessage(mContext, id, data); 340 } 341 342 // nObjDestroy is explicitly _not_ synchronous to prevent crashes in finalizers rsnObjDestroy(long con, long id)343 native void rsnObjDestroy(long con, long id); nObjDestroy(long id)344 void nObjDestroy(long id) { 345 // There is a race condition here. The calling code may be run 346 // by the gc while teardown is occuring. This protects againts 347 // deleting dead objects. 348 if (mContext != 0) { 349 rsnObjDestroy(mContext, id); 350 } 351 } 352 rsnElementCreate(long con, long type, int kind, boolean norm, int vecSize)353 native long rsnElementCreate(long con, long type, int kind, boolean norm, int vecSize); nElementCreate(long type, int kind, boolean norm, int vecSize)354 synchronized long nElementCreate(long type, int kind, boolean norm, int vecSize) { 355 validate(); 356 return rsnElementCreate(mContext, type, kind, norm, vecSize); 357 } rsnElementCreate2(long con, long[] elements, String[] names, int[] arraySizes)358 native long rsnElementCreate2(long con, long[] elements, String[] names, int[] arraySizes); nElementCreate2(long[] elements, String[] names, int[] arraySizes)359 synchronized long nElementCreate2(long[] elements, String[] names, int[] arraySizes) { 360 validate(); 361 return rsnElementCreate2(mContext, elements, names, arraySizes); 362 } rsnElementGetNativeData(long con, long id, int[] elementData)363 native void rsnElementGetNativeData(long con, long id, int[] elementData); nElementGetNativeData(long id, int[] elementData)364 synchronized void nElementGetNativeData(long id, int[] elementData) { 365 validate(); 366 rsnElementGetNativeData(mContext, id, elementData); 367 } rsnElementGetSubElements(long con, long id, long[] IDs, String[] names, int[] arraySizes)368 native void rsnElementGetSubElements(long con, long id, 369 long[] IDs, String[] names, int[] arraySizes); nElementGetSubElements(long id, long[] IDs, String[] names, int[] arraySizes)370 synchronized void nElementGetSubElements(long id, long[] IDs, String[] names, int[] arraySizes) { 371 validate(); 372 rsnElementGetSubElements(mContext, id, IDs, names, arraySizes); 373 } 374 rsnTypeCreate(long con, long eid, int x, int y, int z, boolean mips, boolean faces, int yuv)375 native long rsnTypeCreate(long con, long eid, int x, int y, int z, boolean mips, boolean faces, int yuv); nTypeCreate(long eid, int x, int y, int z, boolean mips, boolean faces, int yuv)376 synchronized long nTypeCreate(long eid, int x, int y, int z, boolean mips, boolean faces, int yuv) { 377 validate(); 378 return rsnTypeCreate(mContext, eid, x, y, z, mips, faces, yuv); 379 } 380 rsnTypeGetNativeData(long con, long id, long[] typeData)381 native void rsnTypeGetNativeData(long con, long id, long[] typeData); nTypeGetNativeData(long id, long[] typeData)382 synchronized void nTypeGetNativeData(long id, long[] typeData) { 383 validate(); 384 rsnTypeGetNativeData(mContext, id, typeData); 385 } 386 rsnAllocationCreateTyped(long con, long type, int mip, int usage, long pointer)387 native long rsnAllocationCreateTyped(long con, long type, int mip, int usage, long pointer); nAllocationCreateTyped(long type, int mip, int usage, long pointer)388 synchronized long nAllocationCreateTyped(long type, int mip, int usage, long pointer) { 389 validate(); 390 return rsnAllocationCreateTyped(mContext, type, mip, usage, pointer); 391 } rsnAllocationCreateFromBitmap(long con, long type, int mip, Bitmap bmp, int usage)392 native long rsnAllocationCreateFromBitmap(long con, long type, int mip, Bitmap bmp, int usage); nAllocationCreateFromBitmap(long type, int mip, Bitmap bmp, int usage)393 synchronized long nAllocationCreateFromBitmap(long type, int mip, Bitmap bmp, int usage) { 394 validate(); 395 return rsnAllocationCreateFromBitmap(mContext, type, mip, bmp, usage); 396 } 397 rsnAllocationCreateBitmapBackedAllocation(long con, long type, int mip, Bitmap bmp, int usage)398 native long rsnAllocationCreateBitmapBackedAllocation(long con, long type, int mip, Bitmap bmp, int usage); nAllocationCreateBitmapBackedAllocation(long type, int mip, Bitmap bmp, int usage)399 synchronized long nAllocationCreateBitmapBackedAllocation(long type, int mip, Bitmap bmp, int usage) { 400 validate(); 401 return rsnAllocationCreateBitmapBackedAllocation(mContext, type, mip, bmp, usage); 402 } 403 404 rsnAllocationCubeCreateFromBitmap(long con, long type, int mip, Bitmap bmp, int usage)405 native long rsnAllocationCubeCreateFromBitmap(long con, long type, int mip, Bitmap bmp, int usage); nAllocationCubeCreateFromBitmap(long type, int mip, Bitmap bmp, int usage)406 synchronized long nAllocationCubeCreateFromBitmap(long type, int mip, Bitmap bmp, int usage) { 407 validate(); 408 return rsnAllocationCubeCreateFromBitmap(mContext, type, mip, bmp, usage); 409 } rsnAllocationCreateBitmapRef(long con, long type, Bitmap bmp)410 native long rsnAllocationCreateBitmapRef(long con, long type, Bitmap bmp); nAllocationCreateBitmapRef(long type, Bitmap bmp)411 synchronized long nAllocationCreateBitmapRef(long type, Bitmap bmp) { 412 validate(); 413 return rsnAllocationCreateBitmapRef(mContext, type, bmp); 414 } rsnAllocationCreateFromAssetStream(long con, int mips, int assetStream, int usage)415 native long rsnAllocationCreateFromAssetStream(long con, int mips, int assetStream, int usage); nAllocationCreateFromAssetStream(int mips, int assetStream, int usage)416 synchronized long nAllocationCreateFromAssetStream(int mips, int assetStream, int usage) { 417 validate(); 418 return rsnAllocationCreateFromAssetStream(mContext, mips, assetStream, usage); 419 } 420 rsnAllocationCopyToBitmap(long con, long alloc, Bitmap bmp)421 native void rsnAllocationCopyToBitmap(long con, long alloc, Bitmap bmp); nAllocationCopyToBitmap(long alloc, Bitmap bmp)422 synchronized void nAllocationCopyToBitmap(long alloc, Bitmap bmp) { 423 validate(); 424 rsnAllocationCopyToBitmap(mContext, alloc, bmp); 425 } 426 427 rsnAllocationSyncAll(long con, long alloc, int src)428 native void rsnAllocationSyncAll(long con, long alloc, int src); nAllocationSyncAll(long alloc, int src)429 synchronized void nAllocationSyncAll(long alloc, int src) { 430 validate(); 431 rsnAllocationSyncAll(mContext, alloc, src); 432 } 433 rsnAllocationSetSurface(long con, long alloc, Surface sur)434 native void rsnAllocationSetSurface(long con, long alloc, Surface sur); nAllocationSetSurface(long alloc, Surface sur)435 synchronized void nAllocationSetSurface(long alloc, Surface sur) { 436 validate(); 437 rsnAllocationSetSurface(mContext, alloc, sur); 438 } 439 rsnAllocationIoSend(long con, long alloc)440 native void rsnAllocationIoSend(long con, long alloc); nAllocationIoSend(long alloc)441 synchronized void nAllocationIoSend(long alloc) { 442 validate(); 443 rsnAllocationIoSend(mContext, alloc); 444 } rsnAllocationIoReceive(long con, long alloc)445 native void rsnAllocationIoReceive(long con, long alloc); nAllocationIoReceive(long alloc)446 synchronized void nAllocationIoReceive(long alloc) { 447 validate(); 448 rsnAllocationIoReceive(mContext, alloc); 449 } rsnAllocationGetByteBuffer(long con, long alloc, int xBytesSize, int dimY, int dimZ)450 native ByteBuffer rsnAllocationGetByteBuffer(long con, long alloc, int xBytesSize, int dimY, int dimZ); nAllocationGetByteBuffer(long alloc, int xBytesSize, int dimY, int dimZ)451 synchronized ByteBuffer nAllocationGetByteBuffer(long alloc, int xBytesSize, int dimY, int dimZ) { 452 validate(); 453 return rsnAllocationGetByteBuffer(mContext, alloc, xBytesSize, dimY, dimZ); 454 } rsnAllocationGetStride(long con, long alloc)455 native long rsnAllocationGetStride(long con, long alloc); nAllocationGetStride(long alloc)456 synchronized long nAllocationGetStride(long alloc) { 457 validate(); 458 return rsnAllocationGetStride(mContext, alloc); 459 } 460 rsnAllocationGenerateMipmaps(long con, long alloc)461 native void rsnAllocationGenerateMipmaps(long con, long alloc); nAllocationGenerateMipmaps(long alloc)462 synchronized void nAllocationGenerateMipmaps(long alloc) { 463 validate(); 464 rsnAllocationGenerateMipmaps(mContext, alloc); 465 } rsnAllocationCopyFromBitmap(long con, long alloc, Bitmap bmp)466 native void rsnAllocationCopyFromBitmap(long con, long alloc, Bitmap bmp); nAllocationCopyFromBitmap(long alloc, Bitmap bmp)467 synchronized void nAllocationCopyFromBitmap(long alloc, Bitmap bmp) { 468 validate(); 469 rsnAllocationCopyFromBitmap(mContext, alloc, bmp); 470 } 471 472 rsnAllocationData1D(long con, long id, int off, int mip, int count, Object d, int sizeBytes, int dt, int mSize, boolean usePadding)473 native void rsnAllocationData1D(long con, long id, int off, int mip, int count, Object d, int sizeBytes, int dt, 474 int mSize, boolean usePadding); nAllocationData1D(long id, int off, int mip, int count, Object d, int sizeBytes, Element.DataType dt, int mSize, boolean usePadding)475 synchronized void nAllocationData1D(long id, int off, int mip, int count, Object d, int sizeBytes, Element.DataType dt, 476 int mSize, boolean usePadding) { 477 validate(); 478 rsnAllocationData1D(mContext, id, off, mip, count, d, sizeBytes, dt.mID, mSize, usePadding); 479 } 480 rsnAllocationElementData1D(long con,long id, int xoff, int mip, int compIdx, byte[] d, int sizeBytes)481 native void rsnAllocationElementData1D(long con,long id, int xoff, int mip, int compIdx, byte[] d, int sizeBytes); nAllocationElementData1D(long id, int xoff, int mip, int compIdx, byte[] d, int sizeBytes)482 synchronized void nAllocationElementData1D(long id, int xoff, int mip, int compIdx, byte[] d, int sizeBytes) { 483 validate(); 484 rsnAllocationElementData1D(mContext, id, xoff, mip, compIdx, d, sizeBytes); 485 } 486 /* 487 native void rsnAllocationElementData(long con,long id, int xoff, int yoff, int zoff, int mip, int compIdx, byte[] d, int sizeBytes); 488 synchronized void nAllocationElementData(long id, int xoff, int yoff, int zoff, int mip, int compIdx, byte[] d, int sizeBytes) { 489 validate(); 490 rsnAllocationElementData(mContext, id, xoff, yoff, zoff, mip, compIdx, d, sizeBytes); 491 } 492 */ 493 rsnAllocationData2D(long con, long dstAlloc, int dstXoff, int dstYoff, int dstMip, int dstFace, int width, int height, long srcAlloc, int srcXoff, int srcYoff, int srcMip, int srcFace)494 native void rsnAllocationData2D(long con, 495 long dstAlloc, int dstXoff, int dstYoff, 496 int dstMip, int dstFace, 497 int width, int height, 498 long srcAlloc, int srcXoff, int srcYoff, 499 int srcMip, int srcFace); nAllocationData2D(long dstAlloc, int dstXoff, int dstYoff, int dstMip, int dstFace, int width, int height, long srcAlloc, int srcXoff, int srcYoff, int srcMip, int srcFace)500 synchronized void nAllocationData2D(long dstAlloc, int dstXoff, int dstYoff, 501 int dstMip, int dstFace, 502 int width, int height, 503 long srcAlloc, int srcXoff, int srcYoff, 504 int srcMip, int srcFace) { 505 validate(); 506 rsnAllocationData2D(mContext, 507 dstAlloc, dstXoff, dstYoff, 508 dstMip, dstFace, 509 width, height, 510 srcAlloc, srcXoff, srcYoff, 511 srcMip, srcFace); 512 } 513 rsnAllocationData2D(long con, long id, int xoff, int yoff, int mip, int face, int w, int h, Object d, int sizeBytes, int dt, int mSize, boolean usePadding)514 native void rsnAllocationData2D(long con, long id, int xoff, int yoff, int mip, int face, 515 int w, int h, Object d, int sizeBytes, int dt, 516 int mSize, boolean usePadding); nAllocationData2D(long id, int xoff, int yoff, int mip, int face, int w, int h, Object d, int sizeBytes, Element.DataType dt, int mSize, boolean usePadding)517 synchronized void nAllocationData2D(long id, int xoff, int yoff, int mip, int face, 518 int w, int h, Object d, int sizeBytes, Element.DataType dt, 519 int mSize, boolean usePadding) { 520 validate(); 521 rsnAllocationData2D(mContext, id, xoff, yoff, mip, face, w, h, d, sizeBytes, dt.mID, mSize, usePadding); 522 } 523 rsnAllocationData2D(long con, long id, int xoff, int yoff, int mip, int face, Bitmap b)524 native void rsnAllocationData2D(long con, long id, int xoff, int yoff, int mip, int face, Bitmap b); nAllocationData2D(long id, int xoff, int yoff, int mip, int face, Bitmap b)525 synchronized void nAllocationData2D(long id, int xoff, int yoff, int mip, int face, Bitmap b) { 526 validate(); 527 rsnAllocationData2D(mContext, id, xoff, yoff, mip, face, b); 528 } 529 rsnAllocationData3D(long con, long dstAlloc, int dstXoff, int dstYoff, int dstZoff, int dstMip, int width, int height, int depth, long srcAlloc, int srcXoff, int srcYoff, int srcZoff, int srcMip)530 native void rsnAllocationData3D(long con, 531 long dstAlloc, int dstXoff, int dstYoff, int dstZoff, 532 int dstMip, 533 int width, int height, int depth, 534 long srcAlloc, int srcXoff, int srcYoff, int srcZoff, 535 int srcMip); nAllocationData3D(long dstAlloc, int dstXoff, int dstYoff, int dstZoff, int dstMip, int width, int height, int depth, long srcAlloc, int srcXoff, int srcYoff, int srcZoff, int srcMip)536 synchronized void nAllocationData3D(long dstAlloc, int dstXoff, int dstYoff, int dstZoff, 537 int dstMip, 538 int width, int height, int depth, 539 long srcAlloc, int srcXoff, int srcYoff, int srcZoff, 540 int srcMip) { 541 validate(); 542 rsnAllocationData3D(mContext, 543 dstAlloc, dstXoff, dstYoff, dstZoff, 544 dstMip, width, height, depth, 545 srcAlloc, srcXoff, srcYoff, srcZoff, srcMip); 546 } 547 548 rsnAllocationData3D(long con, long id, int xoff, int yoff, int zoff, int mip, int w, int h, int depth, Object d, int sizeBytes, int dt, int mSize, boolean usePadding)549 native void rsnAllocationData3D(long con, long id, int xoff, int yoff, int zoff, int mip, 550 int w, int h, int depth, Object d, int sizeBytes, int dt, 551 int mSize, boolean usePadding); nAllocationData3D(long id, int xoff, int yoff, int zoff, int mip, int w, int h, int depth, Object d, int sizeBytes, Element.DataType dt, int mSize, boolean usePadding)552 synchronized void nAllocationData3D(long id, int xoff, int yoff, int zoff, int mip, 553 int w, int h, int depth, Object d, int sizeBytes, Element.DataType dt, 554 int mSize, boolean usePadding) { 555 validate(); 556 rsnAllocationData3D(mContext, id, xoff, yoff, zoff, mip, w, h, depth, d, sizeBytes, 557 dt.mID, mSize, usePadding); 558 } 559 rsnAllocationRead(long con, long id, Object d, int dt, int mSize, boolean usePadding)560 native void rsnAllocationRead(long con, long id, Object d, int dt, int mSize, boolean usePadding); nAllocationRead(long id, Object d, Element.DataType dt, int mSize, boolean usePadding)561 synchronized void nAllocationRead(long id, Object d, Element.DataType dt, int mSize, boolean usePadding) { 562 validate(); 563 rsnAllocationRead(mContext, id, d, dt.mID, mSize, usePadding); 564 } 565 rsnAllocationRead1D(long con, long id, int off, int mip, int count, Object d, int sizeBytes, int dt, int mSize, boolean usePadding)566 native void rsnAllocationRead1D(long con, long id, int off, int mip, int count, Object d, 567 int sizeBytes, int dt, int mSize, boolean usePadding); nAllocationRead1D(long id, int off, int mip, int count, Object d, int sizeBytes, Element.DataType dt, int mSize, boolean usePadding)568 synchronized void nAllocationRead1D(long id, int off, int mip, int count, Object d, 569 int sizeBytes, Element.DataType dt, int mSize, boolean usePadding) { 570 validate(); 571 rsnAllocationRead1D(mContext, id, off, mip, count, d, sizeBytes, dt.mID, mSize, usePadding); 572 } 573 574 /* 575 native void rsnAllocationElementRead(long con,long id, int xoff, int yoff, int zoff, 576 int mip, int compIdx, byte[] d, int sizeBytes); 577 synchronized void nAllocationElementRead(long id, int xoff, int yoff, int zoff, 578 int mip, int compIdx, byte[] d, int sizeBytes) { 579 validate(); 580 rsnAllocationElementRead(mContext, id, xoff, yoff, zoff, mip, compIdx, d, sizeBytes); 581 } 582 */ 583 rsnAllocationRead2D(long con, long id, int xoff, int yoff, int mip, int face, int w, int h, Object d, int sizeBytes, int dt, int mSize, boolean usePadding)584 native void rsnAllocationRead2D(long con, long id, int xoff, int yoff, int mip, int face, 585 int w, int h, Object d, int sizeBytes, int dt, 586 int mSize, boolean usePadding); nAllocationRead2D(long id, int xoff, int yoff, int mip, int face, int w, int h, Object d, int sizeBytes, Element.DataType dt, int mSize, boolean usePadding)587 synchronized void nAllocationRead2D(long id, int xoff, int yoff, int mip, int face, 588 int w, int h, Object d, int sizeBytes, Element.DataType dt, 589 int mSize, boolean usePadding) { 590 validate(); 591 rsnAllocationRead2D(mContext, id, xoff, yoff, mip, face, w, h, d, sizeBytes, dt.mID, mSize, usePadding); 592 } 593 594 /* 595 native void rsnAllocationRead3D(long con, long id, int xoff, int yoff, int zoff, int mip, 596 int w, int h, int depth, Object d, int sizeBytes, int dt, 597 int mSize, boolean usePadding); 598 synchronized void nAllocationRead3D(long id, int xoff, int yoff, int zoff, int mip, 599 int w, int h, int depth, Object d, int sizeBytes, Element.DataType dt, 600 int mSize, boolean usePadding) { 601 validate(); 602 rsnAllocationRead3D(mContext, id, xoff, yoff, zoff, mip, w, h, depth, d, sizeBytes, dt.mID, mSize, usePadding); 603 } 604 */ 605 rsnAllocationGetType(long con, long id)606 native long rsnAllocationGetType(long con, long id); nAllocationGetType(long id)607 synchronized long nAllocationGetType(long id) { 608 validate(); 609 return rsnAllocationGetType(mContext, id); 610 } 611 rsnAllocationResize1D(long con, long id, int dimX)612 native void rsnAllocationResize1D(long con, long id, int dimX); nAllocationResize1D(long id, int dimX)613 synchronized void nAllocationResize1D(long id, int dimX) { 614 validate(); 615 rsnAllocationResize1D(mContext, id, dimX); 616 } rsnAllocationResize2D(long con, long id, int dimX, int dimY)617 native void rsnAllocationResize2D(long con, long id, int dimX, int dimY); nAllocationResize2D(long id, int dimX, int dimY)618 synchronized void nAllocationResize2D(long id, int dimX, int dimY) { 619 validate(); 620 rsnAllocationResize2D(mContext, id, dimX, dimY); 621 } 622 rsnScriptBindAllocation(long con, long script, long alloc, int slot, boolean mUseInc)623 native void rsnScriptBindAllocation(long con, long script, long alloc, int slot, boolean mUseInc); nScriptBindAllocation(long script, long alloc, int slot, boolean mUseInc)624 synchronized void nScriptBindAllocation(long script, long alloc, int slot, boolean mUseInc) { 625 validate(); 626 long curCon = mContext; 627 if (mUseInc) { 628 curCon = mIncCon; 629 } 630 rsnScriptBindAllocation(curCon, script, alloc, slot, mUseInc); 631 } rsnScriptSetTimeZone(long con, long script, byte[] timeZone, boolean mUseInc)632 native void rsnScriptSetTimeZone(long con, long script, byte[] timeZone, boolean mUseInc); nScriptSetTimeZone(long script, byte[] timeZone, boolean mUseInc)633 synchronized void nScriptSetTimeZone(long script, byte[] timeZone, boolean mUseInc) { 634 validate(); 635 long curCon = mContext; 636 if (mUseInc) { 637 curCon = mIncCon; 638 } 639 rsnScriptSetTimeZone(curCon, script, timeZone, mUseInc); 640 } rsnScriptInvoke(long con, long id, int slot, boolean mUseInc)641 native void rsnScriptInvoke(long con, long id, int slot, boolean mUseInc); nScriptInvoke(long id, int slot, boolean mUseInc)642 synchronized void nScriptInvoke(long id, int slot, boolean mUseInc) { 643 validate(); 644 long curCon = mContext; 645 if (mUseInc) { 646 curCon = mIncCon; 647 } 648 rsnScriptInvoke(curCon, id, slot, mUseInc); 649 } rsnScriptForEach(long con, long incCon, long id, int slot, long ain, long aout, byte[] params, boolean mUseInc)650 native void rsnScriptForEach(long con, long incCon, long id, int slot, long ain, long aout, byte[] params, boolean mUseInc); rsnScriptForEach(long con, long incCon, long id, int slot, long ain, long aout, boolean mUseInc)651 native void rsnScriptForEach(long con, long incCon, long id, int slot, long ain, long aout, boolean mUseInc); rsnScriptForEachClipped(long con, long incCon, long id, int slot, long ain, long aout, byte[] params, int xstart, int xend, int ystart, int yend, int zstart, int zend, boolean mUseInc)652 native void rsnScriptForEachClipped(long con, long incCon, long id, int slot, long ain, long aout, byte[] params, 653 int xstart, int xend, int ystart, int yend, int zstart, int zend, boolean mUseInc); rsnScriptForEachClipped(long con, long incCon, long id, int slot, long ain, long aout, int xstart, int xend, int ystart, int yend, int zstart, int zend, boolean mUseInc)654 native void rsnScriptForEachClipped(long con, long incCon, long id, int slot, long ain, long aout, 655 int xstart, int xend, int ystart, int yend, int zstart, int zend, boolean mUseInc); nScriptForEach(long id, int slot, long ain, long aout, byte[] params, boolean mUseInc)656 synchronized void nScriptForEach(long id, int slot, long ain, long aout, byte[] params, boolean mUseInc) { 657 validate(); 658 if (params == null) { 659 rsnScriptForEach(mContext, mIncCon, id, slot, ain, aout, mUseInc); 660 } else { 661 rsnScriptForEach(mContext, mIncCon, id, slot, ain, aout, params, mUseInc); 662 } 663 } 664 nScriptForEachClipped(long id, int slot, long ain, long aout, byte[] params, int xstart, int xend, int ystart, int yend, int zstart, int zend, boolean mUseInc)665 synchronized void nScriptForEachClipped(long id, int slot, long ain, long aout, byte[] params, 666 int xstart, int xend, int ystart, int yend, int zstart, int zend, boolean mUseInc) { 667 validate(); 668 if (params == null) { 669 rsnScriptForEachClipped(mContext, mIncCon, id, slot, ain, aout, xstart, xend, ystart, yend, zstart, zend, mUseInc); 670 } else { 671 rsnScriptForEachClipped(mContext, mIncCon, id, slot, ain, aout, params, xstart, xend, ystart, yend, zstart, zend, mUseInc); 672 } 673 } 674 rsnScriptForEach(long con, long id, int slot, long[] ains, long aout, byte[] params, int[] limits)675 native void rsnScriptForEach(long con, long id, int slot, long[] ains, 676 long aout, byte[] params, int[] limits); 677 nScriptForEach(long id, int slot, long[] ains, long aout, byte[] params, int[] limits)678 synchronized void nScriptForEach(long id, int slot, long[] ains, long aout, 679 byte[] params, int[] limits) { 680 if (!mEnableMultiInput) { 681 Log.e(LOG_TAG, "Multi-input kernels are not supported, please change targetSdkVersion to >= 23"); 682 throw new RSRuntimeException("Multi-input kernels are not supported before API 23)"); 683 } 684 validate(); 685 rsnScriptForEach(mContext, id, slot, ains, aout, params, limits); 686 } 687 rsnScriptReduce(long con, long id, int slot, long[] ains, long aout, int[] limits)688 native void rsnScriptReduce(long con, long id, int slot, long[] ains, 689 long aout, int[] limits); nScriptReduce(long id, int slot, long ains[], long aout, int[] limits)690 synchronized void nScriptReduce(long id, int slot, long ains[], long aout, 691 int[] limits) { 692 validate(); 693 rsnScriptReduce(mContext, id, slot, ains, aout, limits); 694 } 695 rsnScriptInvokeV(long con, long id, int slot, byte[] params, boolean mUseInc)696 native void rsnScriptInvokeV(long con, long id, int slot, byte[] params, boolean mUseInc); nScriptInvokeV(long id, int slot, byte[] params, boolean mUseInc)697 synchronized void nScriptInvokeV(long id, int slot, byte[] params, boolean mUseInc) { 698 validate(); 699 long curCon = mContext; 700 if (mUseInc) { 701 curCon = mIncCon; 702 } 703 rsnScriptInvokeV(curCon, id, slot, params, mUseInc); 704 } rsnScriptSetVarI(long con, long id, int slot, int val, boolean mUseInc)705 native void rsnScriptSetVarI(long con, long id, int slot, int val, boolean mUseInc); nScriptSetVarI(long id, int slot, int val, boolean mUseInc)706 synchronized void nScriptSetVarI(long id, int slot, int val, boolean mUseInc) { 707 validate(); 708 long curCon = mContext; 709 if (mUseInc) { 710 curCon = mIncCon; 711 } 712 rsnScriptSetVarI(curCon, id, slot, val, mUseInc); 713 } rsnScriptSetVarJ(long con, long id, int slot, long val, boolean mUseInc)714 native void rsnScriptSetVarJ(long con, long id, int slot, long val, boolean mUseInc); nScriptSetVarJ(long id, int slot, long val, boolean mUseInc)715 synchronized void nScriptSetVarJ(long id, int slot, long val, boolean mUseInc) { 716 validate(); 717 long curCon = mContext; 718 if (mUseInc) { 719 curCon = mIncCon; 720 } 721 rsnScriptSetVarJ(curCon, id, slot, val, mUseInc); 722 } rsnScriptSetVarF(long con, long id, int slot, float val, boolean mUseInc)723 native void rsnScriptSetVarF(long con, long id, int slot, float val, boolean mUseInc); nScriptSetVarF(long id, int slot, float val, boolean mUseInc)724 synchronized void nScriptSetVarF(long id, int slot, float val, boolean mUseInc) { 725 validate(); 726 long curCon = mContext; 727 if (mUseInc) { 728 curCon = mIncCon; 729 } 730 rsnScriptSetVarF(curCon, id, slot, val, mUseInc); 731 } rsnScriptSetVarD(long con, long id, int slot, double val, boolean mUseInc)732 native void rsnScriptSetVarD(long con, long id, int slot, double val, boolean mUseInc); nScriptSetVarD(long id, int slot, double val, boolean mUseInc)733 synchronized void nScriptSetVarD(long id, int slot, double val, boolean mUseInc) { 734 validate(); 735 long curCon = mContext; 736 if (mUseInc) { 737 curCon = mIncCon; 738 } 739 rsnScriptSetVarD(curCon, id, slot, val, mUseInc); 740 } rsnScriptSetVarV(long con, long id, int slot, byte[] val, boolean mUseInc)741 native void rsnScriptSetVarV(long con, long id, int slot, byte[] val, boolean mUseInc); nScriptSetVarV(long id, int slot, byte[] val, boolean mUseInc)742 synchronized void nScriptSetVarV(long id, int slot, byte[] val, boolean mUseInc) { 743 validate(); 744 long curCon = mContext; 745 if (mUseInc) { 746 curCon = mIncCon; 747 } 748 rsnScriptSetVarV(curCon, id, slot, val, mUseInc); 749 } rsnScriptSetVarVE(long con, long id, int slot, byte[] val, long e, int[] dims, boolean mUseInc)750 native void rsnScriptSetVarVE(long con, long id, int slot, byte[] val, 751 long e, int[] dims, boolean mUseInc); nScriptSetVarVE(long id, int slot, byte[] val, long e, int[] dims, boolean mUseInc)752 synchronized void nScriptSetVarVE(long id, int slot, byte[] val, 753 long e, int[] dims, boolean mUseInc) { 754 validate(); 755 long curCon = mContext; 756 if (mUseInc) { 757 curCon = mIncCon; 758 } 759 rsnScriptSetVarVE(curCon, id, slot, val, e, dims, mUseInc); 760 } rsnScriptSetVarObj(long con, long id, int slot, long val, boolean mUseInc)761 native void rsnScriptSetVarObj(long con, long id, int slot, long val, boolean mUseInc); nScriptSetVarObj(long id, int slot, long val, boolean mUseInc)762 synchronized void nScriptSetVarObj(long id, int slot, long val, boolean mUseInc) { 763 validate(); 764 long curCon = mContext; 765 if (mUseInc) { 766 curCon = mIncCon; 767 } 768 rsnScriptSetVarObj(curCon, id, slot, val, mUseInc); 769 } 770 rsnScriptCCreate(long con, String resName, String cacheDir, byte[] script, int length)771 native long rsnScriptCCreate(long con, String resName, String cacheDir, 772 byte[] script, int length); nScriptCCreate(String resName, String cacheDir, byte[] script, int length)773 synchronized long nScriptCCreate(String resName, String cacheDir, byte[] script, int length) { 774 validate(); 775 return rsnScriptCCreate(mContext, resName, cacheDir, script, length); 776 } 777 rsnScriptIntrinsicCreate(long con, int id, long eid, boolean mUseInc)778 native long rsnScriptIntrinsicCreate(long con, int id, long eid, boolean mUseInc); nScriptIntrinsicCreate(int id, long eid, boolean mUseInc)779 synchronized long nScriptIntrinsicCreate(int id, long eid, boolean mUseInc) { 780 validate(); 781 if (mUseInc) { 782 if (android.os.Build.VERSION.SDK_INT < android.os.Build.VERSION_CODES.LOLLIPOP) { 783 Log.e(LOG_TAG, "Incremental Intrinsics are not supported, please change targetSdkVersion to >= 21"); 784 throw new RSRuntimeException("Incremental Intrinsics are not supported before Lollipop (API 21)"); 785 } 786 787 if (!mIncLoaded) { 788 try { 789 System.loadLibrary("RSSupport"); 790 } catch (UnsatisfiedLinkError e) { 791 Log.e(LOG_TAG, "Error loading RS Compat library for Incremental Intrinsic Support: " + e); 792 throw new RSRuntimeException("Error loading RS Compat library for Incremental Intrinsic Support: " + e); 793 } 794 if (!nIncLoadSO(SUPPORT_LIB_API, mNativeLibDir + "/libRSSupport.so")) { 795 throw new RSRuntimeException("Error loading libRSSupport library for Incremental Intrinsic Support"); 796 } 797 mIncLoaded = true; 798 } 799 if (mIncCon == 0) { 800 //Create a dummy compat context (synchronous). 801 long device = nIncDeviceCreate(); 802 mIncCon = nIncContextCreate(device, 0, 0, 0); 803 } 804 return rsnScriptIntrinsicCreate(mIncCon, id, eid, mUseInc); 805 } else { 806 return rsnScriptIntrinsicCreate(mContext, id, eid, mUseInc); 807 } 808 } 809 rsnScriptKernelIDCreate(long con, long sid, int slot, int sig, boolean mUseInc)810 native long rsnScriptKernelIDCreate(long con, long sid, int slot, int sig, boolean mUseInc); nScriptKernelIDCreate(long sid, int slot, int sig, boolean mUseInc)811 synchronized long nScriptKernelIDCreate(long sid, int slot, int sig, boolean mUseInc) { 812 validate(); 813 long curCon = mContext; 814 if (mUseInc) { 815 curCon = mIncCon; 816 } 817 return rsnScriptKernelIDCreate(curCon, sid, slot, sig, mUseInc); 818 } 819 rsnScriptInvokeIDCreate(long con, long sid, int slot)820 native long rsnScriptInvokeIDCreate(long con, long sid, int slot); nScriptInvokeIDCreate(long sid, int slot)821 synchronized long nScriptInvokeIDCreate(long sid, int slot) { 822 validate(); 823 return rsnScriptInvokeIDCreate(mContext, sid, slot); 824 } 825 rsnScriptFieldIDCreate(long con, long sid, int slot, boolean mUseInc)826 native long rsnScriptFieldIDCreate(long con, long sid, int slot, boolean mUseInc); nScriptFieldIDCreate(long sid, int slot, boolean mUseInc)827 synchronized long nScriptFieldIDCreate(long sid, int slot, boolean mUseInc) { 828 validate(); 829 long curCon = mContext; 830 if (mUseInc) { 831 curCon = mIncCon; 832 } 833 return rsnScriptFieldIDCreate(curCon, sid, slot, mUseInc); 834 } 835 rsnScriptGroupCreate(long con, long[] kernels, long[] src, long[] dstk, long[] dstf, long[] types)836 native long rsnScriptGroupCreate(long con, long[] kernels, long[] src, long[] dstk, long[] dstf, long[] types); nScriptGroupCreate(long[] kernels, long[] src, long[] dstk, long[] dstf, long[] types)837 synchronized long nScriptGroupCreate(long[] kernels, long[] src, long[] dstk, long[] dstf, long[] types) { 838 validate(); 839 return rsnScriptGroupCreate(mContext, kernels, src, dstk, dstf, types); 840 } 841 rsnScriptGroupSetInput(long con, long group, long kernel, long alloc)842 native void rsnScriptGroupSetInput(long con, long group, long kernel, long alloc); nScriptGroupSetInput(long group, long kernel, long alloc)843 synchronized void nScriptGroupSetInput(long group, long kernel, long alloc) { 844 validate(); 845 rsnScriptGroupSetInput(mContext, group, kernel, alloc); 846 } 847 rsnScriptGroupSetOutput(long con, long group, long kernel, long alloc)848 native void rsnScriptGroupSetOutput(long con, long group, long kernel, long alloc); nScriptGroupSetOutput(long group, long kernel, long alloc)849 synchronized void nScriptGroupSetOutput(long group, long kernel, long alloc) { 850 validate(); 851 rsnScriptGroupSetOutput(mContext, group, kernel, alloc); 852 } 853 rsnScriptGroupExecute(long con, long group)854 native void rsnScriptGroupExecute(long con, long group); nScriptGroupExecute(long group)855 synchronized void nScriptGroupExecute(long group) { 856 validate(); 857 rsnScriptGroupExecute(mContext, group); 858 } 859 rsnSamplerCreate(long con, int magFilter, int minFilter, int wrapS, int wrapT, int wrapR, float aniso)860 native long rsnSamplerCreate(long con, int magFilter, int minFilter, 861 int wrapS, int wrapT, int wrapR, float aniso); nSamplerCreate(int magFilter, int minFilter, int wrapS, int wrapT, int wrapR, float aniso)862 synchronized long nSamplerCreate(int magFilter, int minFilter, 863 int wrapS, int wrapT, int wrapR, float aniso) { 864 validate(); 865 return rsnSamplerCreate(mContext, magFilter, minFilter, wrapS, wrapT, wrapR, aniso); 866 } 867 868 // entry points for ScriptGroup2 rsnClosureCreate(long con, long kernelID, long returnValue, long[] fieldIDs, long[] values, int[] sizes, long[] depClosures, long[] depFieldIDs)869 native long rsnClosureCreate(long con, long kernelID, long returnValue, 870 long[] fieldIDs, long[] values, int[] sizes, long[] depClosures, 871 long[] depFieldIDs); nClosureCreate(long kernelID, long returnValue, long[] fieldIDs, long[] values, int[] sizes, long[] depClosures, long[] depFieldIDs)872 synchronized long nClosureCreate(long kernelID, long returnValue, 873 long[] fieldIDs, long[] values, int[] sizes, long[] depClosures, 874 long[] depFieldIDs) { 875 validate(); 876 long c = rsnClosureCreate(mContext, kernelID, returnValue, fieldIDs, values, 877 sizes, depClosures, depFieldIDs); 878 if (c == 0) { 879 throw new RSRuntimeException("Failed creating closure."); 880 } 881 return c; 882 } 883 rsnInvokeClosureCreate(long con, long invokeID, byte[] params, long[] fieldIDs, long[] values, int[] sizes)884 native long rsnInvokeClosureCreate(long con, long invokeID, byte[] params, 885 long[] fieldIDs, long[] values, int[] sizes); nInvokeClosureCreate(long invokeID, byte[] params, long[] fieldIDs, long[] values, int[] sizes)886 synchronized long nInvokeClosureCreate(long invokeID, byte[] params, 887 long[] fieldIDs, long[] values, int[] sizes) { 888 validate(); 889 long c = rsnInvokeClosureCreate(mContext, invokeID, params, fieldIDs, 890 values, sizes); 891 if (c == 0) { 892 throw new RSRuntimeException("Failed creating closure."); 893 } 894 return c; 895 } 896 rsnClosureSetArg(long con, long closureID, int index, long value, int size)897 native void rsnClosureSetArg(long con, long closureID, int index, 898 long value, int size); nClosureSetArg(long closureID, int index, long value, int size)899 synchronized void nClosureSetArg(long closureID, int index, long value, 900 int size) { 901 validate(); 902 rsnClosureSetArg(mContext, closureID, index, value, size); 903 } 904 rsnClosureSetGlobal(long con, long closureID, long fieldID, long value, int size)905 native void rsnClosureSetGlobal(long con, long closureID, long fieldID, 906 long value, int size); 907 // Does this have to be synchronized? nClosureSetGlobal(long closureID, long fieldID, long value, int size)908 synchronized void nClosureSetGlobal(long closureID, long fieldID, 909 long value, int size) { 910 validate(); // TODO: is this necessary? 911 rsnClosureSetGlobal(mContext, closureID, fieldID, value, size); 912 } 913 rsnScriptGroup2Create(long con, String name, String cachePath, long[] closures)914 native long rsnScriptGroup2Create(long con, String name, String cachePath, 915 long[] closures); nScriptGroup2Create(String name, String cachePath, long[] closures)916 synchronized long nScriptGroup2Create(String name, String cachePath, 917 long[] closures) { 918 validate(); 919 return rsnScriptGroup2Create(mContext, name, cachePath, closures); 920 } 921 rsnScriptGroup2Execute(long con, long groupID)922 native void rsnScriptGroup2Execute(long con, long groupID); nScriptGroup2Execute(long groupID)923 synchronized void nScriptGroup2Execute(long groupID) { 924 validate(); 925 rsnScriptGroup2Execute(mContext, groupID); 926 } 927 rsnScriptIntrinsicBLAS_Single(long con, long incCon, long id, int func, int TransA, int TransB, int Side, int Uplo, int Diag, int M, int N, int K, float alpha, long A, long B, float beta, long C, int incX, int incY, int KL, int KU, boolean mUseInc)928 native void rsnScriptIntrinsicBLAS_Single(long con, long incCon, long id, int func, int TransA, 929 int TransB, int Side, int Uplo, int Diag, int M, int N, int K, 930 float alpha, long A, long B, float beta, long C, int incX, int incY, 931 int KL, int KU, boolean mUseInc); nScriptIntrinsicBLAS_Single(long id, int func, int TransA, int TransB, int Side, int Uplo, int Diag, int M, int N, int K, float alpha, long A, long B, float beta, long C, int incX, int incY, int KL, int KU, boolean mUseInc)932 synchronized void nScriptIntrinsicBLAS_Single(long id, int func, int TransA, 933 int TransB, int Side, int Uplo, int Diag, int M, int N, int K, 934 float alpha, long A, long B, float beta, long C, int incX, int incY, 935 int KL, int KU, boolean mUseInc) { 936 validate(); 937 rsnScriptIntrinsicBLAS_Single(mContext, mIncCon, id, func, TransA, TransB, Side, Uplo, Diag, M, N, K, alpha, A, B, beta, C, incX, incY, KL, KU, mUseInc); 938 } 939 rsnScriptIntrinsicBLAS_Double(long con, long incCon, long id, int func, int TransA, int TransB, int Side, int Uplo, int Diag, int M, int N, int K, double alpha, long A, long B, double beta, long C, int incX, int incY, int KL, int KU, boolean mUseInc)940 native void rsnScriptIntrinsicBLAS_Double(long con, long incCon, long id, int func, int TransA, 941 int TransB, int Side, int Uplo, int Diag, int M, int N, int K, 942 double alpha, long A, long B, double beta, long C, int incX, int incY, 943 int KL, int KU, boolean mUseInc); nScriptIntrinsicBLAS_Double(long id, int func, int TransA, int TransB, int Side, int Uplo, int Diag, int M, int N, int K, double alpha, long A, long B, double beta, long C, int incX, int incY, int KL, int KU, boolean mUseInc)944 synchronized void nScriptIntrinsicBLAS_Double(long id, int func, int TransA, 945 int TransB, int Side, int Uplo, int Diag, int M, int N, int K, 946 double alpha, long A, long B, double beta, long C, int incX, int incY, 947 int KL, int KU, boolean mUseInc) { 948 validate(); 949 rsnScriptIntrinsicBLAS_Double(mContext, mIncCon, id, func, TransA, TransB, Side, Uplo, Diag, M, N, K, alpha, A, B, beta, C, incX, incY, KL, KU, mUseInc); 950 } 951 rsnScriptIntrinsicBLAS_Complex(long con, long incCon, long id, int func, int TransA, int TransB, int Side, int Uplo, int Diag, int M, int N, int K, float alphaX, float alphaY, long A, long B, float betaX, float betaY, long C, int incX, int incY, int KL, int KU, boolean mUseInc)952 native void rsnScriptIntrinsicBLAS_Complex(long con, long incCon, long id, int func, int TransA, 953 int TransB, int Side, int Uplo, int Diag, int M, int N, int K, 954 float alphaX, float alphaY, long A, long B, float betaX, float betaY, long C, int incX, int incY, 955 int KL, int KU, boolean mUseInc); nScriptIntrinsicBLAS_Complex(long id, int func, int TransA, int TransB, int Side, int Uplo, int Diag, int M, int N, int K, float alphaX, float alphaY, long A, long B, float betaX, float betaY, long C, int incX, int incY, int KL, int KU, boolean mUseInc)956 synchronized void nScriptIntrinsicBLAS_Complex(long id, int func, int TransA, 957 int TransB, int Side, int Uplo, int Diag, int M, int N, int K, 958 float alphaX, float alphaY, long A, long B, float betaX, float betaY, long C, int incX, int incY, 959 int KL, int KU, boolean mUseInc) { 960 validate(); 961 rsnScriptIntrinsicBLAS_Complex(mContext, mIncCon, id, func, TransA, TransB, Side, Uplo, Diag, M, N, K, alphaX, alphaY, A, B, betaX, betaY, C, incX, incY, KL, KU, mUseInc); 962 } 963 rsnScriptIntrinsicBLAS_Z(long con, long incCon, long id, int func, int TransA, int TransB, int Side, int Uplo, int Diag, int M, int N, int K, double alphaX, double alphaY, long A, long B, double betaX, double betaY, long C, int incX, int incY, int KL, int KU, boolean mUseInc)964 native void rsnScriptIntrinsicBLAS_Z(long con, long incCon, long id, int func, int TransA, 965 int TransB, int Side, int Uplo, int Diag, int M, int N, int K, 966 double alphaX, double alphaY, long A, long B, double betaX, double betaY, long C, int incX, int incY, 967 int KL, int KU, boolean mUseInc); nScriptIntrinsicBLAS_Z(long id, int func, int TransA, int TransB, int Side, int Uplo, int Diag, int M, int N, int K, double alphaX, double alphaY, long A, long B, double betaX, double betaY, long C, int incX, int incY, int KL, int KU, boolean mUseInc)968 synchronized void nScriptIntrinsicBLAS_Z(long id, int func, int TransA, 969 int TransB, int Side, int Uplo, int Diag, int M, int N, int K, 970 double alphaX, double alphaY, long A, long B, double betaX, double betaY, long C, int incX, int incY, 971 int KL, int KU, boolean mUseInc) { 972 validate(); 973 rsnScriptIntrinsicBLAS_Z(mContext, mIncCon, id, func, TransA, TransB, Side, Uplo, Diag, M, N, K, alphaX, alphaY, A, B, betaX, betaY, C, incX, incY, KL, KU, mUseInc); 974 } 975 rsnScriptIntrinsicBLAS_BNNM(long con, long incCon, long id, int M, int N, int K, long A, int a_offset, long B, int b_offset, long C, int c_offset, int c_mult_int, boolean mUseInc)976 native void rsnScriptIntrinsicBLAS_BNNM(long con, long incCon, long id, int M, int N, int K, 977 long A, int a_offset, long B, int b_offset, long C, int c_offset, 978 int c_mult_int, boolean mUseInc); nScriptIntrinsicBLAS_BNNM(long id, int M, int N, int K, long A, int a_offset, long B, int b_offset, long C, int c_offset, int c_mult_int, boolean mUseInc)979 synchronized void nScriptIntrinsicBLAS_BNNM(long id, int M, int N, int K, 980 long A, int a_offset, long B, int b_offset, long C, int c_offset, 981 int c_mult_int, boolean mUseInc) { 982 validate(); 983 rsnScriptIntrinsicBLAS_BNNM(mContext, mIncCon, id, M, N, K, A, a_offset, B, b_offset, C, c_offset, c_mult_int, mUseInc); 984 } 985 986 // Additional Entry points For inc libRSSupport 987 nIncLoadSO(int deviceApi, String libPath)988 native boolean nIncLoadSO(int deviceApi, String libPath); nIncDeviceCreate()989 native long nIncDeviceCreate(); nIncDeviceDestroy(long dev)990 native void nIncDeviceDestroy(long dev); 991 // Methods below are wrapped to protect the non-threadsafe 992 // lockless fifo. rsnIncContextCreate(long dev, int ver, int sdkVer, int contextType)993 native long rsnIncContextCreate(long dev, int ver, int sdkVer, int contextType); nIncContextCreate(long dev, int ver, int sdkVer, int contextType)994 synchronized long nIncContextCreate(long dev, int ver, int sdkVer, int contextType) { 995 return rsnIncContextCreate(dev, ver, sdkVer, contextType); 996 } rsnIncContextDestroy(long con)997 native void rsnIncContextDestroy(long con); nIncContextDestroy()998 synchronized void nIncContextDestroy() { 999 validate(); 1000 1001 // take teardown lock 1002 // teardown lock can only be taken when no objects are being destroyed 1003 ReentrantReadWriteLock.WriteLock wlock = mRWLock.writeLock(); 1004 wlock.lock(); 1005 1006 long curCon = mIncCon; 1007 // context is considered dead as of this point 1008 mIncCon = 0; 1009 1010 wlock.unlock(); 1011 rsnIncContextDestroy(curCon); 1012 } 1013 rsnIncContextFinish(long con)1014 native void rsnIncContextFinish(long con); nIncContextFinish()1015 synchronized void nIncContextFinish() { 1016 validate(); 1017 rsnIncContextFinish(mIncCon); 1018 } 1019 rsnIncObjDestroy(long con, long id)1020 native void rsnIncObjDestroy(long con, long id); nIncObjDestroy(long id)1021 void nIncObjDestroy(long id) { 1022 // There is a race condition here. The calling code may be run 1023 // by the gc while teardown is occuring. This protects againts 1024 // deleting dead objects. 1025 if (mIncCon != 0) { 1026 rsnIncObjDestroy(mIncCon, id); 1027 } 1028 } rsnIncElementCreate(long con, long type, int kind, boolean norm, int vecSize)1029 native long rsnIncElementCreate(long con, long type, int kind, boolean norm, int vecSize); nIncElementCreate(long type, int kind, boolean norm, int vecSize)1030 synchronized long nIncElementCreate(long type, int kind, boolean norm, int vecSize) { 1031 validate(); 1032 return rsnIncElementCreate(mIncCon, type, kind, norm, vecSize); 1033 } rsnIncTypeCreate(long con, long eid, int x, int y, int z, boolean mips, boolean faces, int yuv)1034 native long rsnIncTypeCreate(long con, long eid, int x, int y, int z, boolean mips, boolean faces, int yuv); nIncTypeCreate(long eid, int x, int y, int z, boolean mips, boolean faces, int yuv)1035 synchronized long nIncTypeCreate(long eid, int x, int y, int z, boolean mips, boolean faces, int yuv) { 1036 validate(); 1037 return rsnIncTypeCreate(mIncCon, eid, x, y, z, mips, faces, yuv); 1038 } rsnIncAllocationCreateTyped(long con, long incCon, long alloc, long type, int xBytesSize)1039 native long rsnIncAllocationCreateTyped(long con, long incCon, long alloc, long type, int xBytesSize); nIncAllocationCreateTyped(long alloc, long type, int xBytesSize)1040 synchronized long nIncAllocationCreateTyped(long alloc, long type, int xBytesSize) { 1041 validate(); 1042 return rsnIncAllocationCreateTyped(mContext, mIncCon, alloc, type, xBytesSize); 1043 } 1044 1045 long mContext; 1046 private boolean mDestroyed = false; 1047 //Dummy device & context for Inc Support Lib 1048 long mIncCon; 1049 //indicator of whether inc support lib has been loaded or not. 1050 boolean mIncLoaded; 1051 ReentrantReadWriteLock mRWLock; 1052 @SuppressWarnings({"FieldCanBeLocal"}) 1053 MessageThread mMessageThread; 1054 1055 Element mElement_U8; 1056 Element mElement_I8; 1057 Element mElement_U16; 1058 Element mElement_I16; 1059 Element mElement_U32; 1060 Element mElement_I32; 1061 Element mElement_U64; 1062 Element mElement_I64; 1063 Element mElement_F32; 1064 Element mElement_F64; 1065 Element mElement_BOOLEAN; 1066 1067 Element mElement_ELEMENT; 1068 Element mElement_TYPE; 1069 Element mElement_ALLOCATION; 1070 Element mElement_SAMPLER; 1071 Element mElement_SCRIPT; 1072 1073 Element mElement_A_8; 1074 Element mElement_RGB_565; 1075 Element mElement_RGB_888; 1076 Element mElement_RGBA_5551; 1077 Element mElement_RGBA_4444; 1078 Element mElement_RGBA_8888; 1079 1080 Element mElement_FLOAT_2; 1081 Element mElement_FLOAT_3; 1082 Element mElement_FLOAT_4; 1083 1084 Element mElement_DOUBLE_2; 1085 Element mElement_DOUBLE_3; 1086 Element mElement_DOUBLE_4; 1087 1088 Element mElement_UCHAR_2; 1089 Element mElement_UCHAR_3; 1090 Element mElement_UCHAR_4; 1091 1092 Element mElement_CHAR_2; 1093 Element mElement_CHAR_3; 1094 Element mElement_CHAR_4; 1095 1096 Element mElement_USHORT_2; 1097 Element mElement_USHORT_3; 1098 Element mElement_USHORT_4; 1099 1100 Element mElement_SHORT_2; 1101 Element mElement_SHORT_3; 1102 Element mElement_SHORT_4; 1103 1104 Element mElement_UINT_2; 1105 Element mElement_UINT_3; 1106 Element mElement_UINT_4; 1107 1108 Element mElement_INT_2; 1109 Element mElement_INT_3; 1110 Element mElement_INT_4; 1111 1112 Element mElement_ULONG_2; 1113 Element mElement_ULONG_3; 1114 Element mElement_ULONG_4; 1115 1116 Element mElement_LONG_2; 1117 Element mElement_LONG_3; 1118 Element mElement_LONG_4; 1119 1120 Element mElement_MATRIX_4X4; 1121 Element mElement_MATRIX_3X3; 1122 Element mElement_MATRIX_2X2; 1123 1124 Sampler mSampler_CLAMP_NEAREST; 1125 Sampler mSampler_CLAMP_LINEAR; 1126 Sampler mSampler_CLAMP_LINEAR_MIP_LINEAR; 1127 Sampler mSampler_WRAP_NEAREST; 1128 Sampler mSampler_WRAP_LINEAR; 1129 Sampler mSampler_WRAP_LINEAR_MIP_LINEAR; 1130 Sampler mSampler_MIRRORED_REPEAT_NEAREST; 1131 Sampler mSampler_MIRRORED_REPEAT_LINEAR; 1132 Sampler mSampler_MIRRORED_REPEAT_LINEAR_MIP_LINEAR; 1133 1134 1135 /////////////////////////////////////////////////////////////////////////////////// 1136 // 1137 1138 /** 1139 * The base class from which an application should derive in order 1140 * to receive RS messages from scripts. When a script calls {@code 1141 * rsSendToClient}, the data fields will be filled, and the run 1142 * method will be called on a separate thread. This will occur 1143 * some time after {@code rsSendToClient} completes in the script, 1144 * as {@code rsSendToClient} is asynchronous. Message handlers are 1145 * not guaranteed to have completed when {@link 1146 * android.support.v8.renderscript.RenderScript#finish} returns. 1147 * 1148 */ 1149 public static class RSMessageHandler implements Runnable { 1150 protected int[] mData; 1151 protected int mID; 1152 protected int mLength; run()1153 public void run() { 1154 } 1155 } 1156 /** 1157 * If an application is expecting messages, it should set this 1158 * field to an instance of {@link RSMessageHandler}. This 1159 * instance will receive all the user messages sent from {@code 1160 * sendToClient} by scripts from this context. 1161 * 1162 */ 1163 RSMessageHandler mMessageCallback = null; 1164 setMessageHandler(RSMessageHandler msg)1165 public void setMessageHandler(RSMessageHandler msg) { 1166 mMessageCallback = msg; 1167 } getMessageHandler()1168 public RSMessageHandler getMessageHandler() { 1169 return mMessageCallback; 1170 } 1171 1172 /** 1173 * Place a message into the message queue to be sent back to the message 1174 * handler once all previous commands have been executed. 1175 * 1176 * @param id 1177 * @param data 1178 */ sendMessage(int id, int[] data)1179 public void sendMessage(int id, int[] data) { 1180 nContextSendMessage(id, data); 1181 } 1182 1183 /** 1184 * The runtime error handler base class. An application should derive from this class 1185 * if it wishes to install an error handler. When errors occur at runtime, 1186 * the fields in this class will be filled, and the run method will be called. 1187 * 1188 */ 1189 public static class RSErrorHandler implements Runnable { 1190 protected String mErrorMessage; 1191 protected int mErrorNum; run()1192 public void run() { 1193 } 1194 } 1195 1196 /** 1197 * Application Error handler. All runtime errors will be dispatched to the 1198 * instance of RSAsyncError set here. If this field is null a 1199 * {@link RSRuntimeException} will instead be thrown with details about the error. 1200 * This will cause program termaination. 1201 * 1202 */ 1203 RSErrorHandler mErrorCallback = null; 1204 setErrorHandler(RSErrorHandler msg)1205 public void setErrorHandler(RSErrorHandler msg) { 1206 mErrorCallback = msg; 1207 } getErrorHandler()1208 public RSErrorHandler getErrorHandler() { 1209 return mErrorCallback; 1210 } 1211 1212 /** 1213 * RenderScript worker thread priority enumeration. The default value is 1214 * NORMAL. Applications wishing to do background processing should set 1215 * their priority to LOW to avoid starving forground processes. 1216 */ 1217 public enum Priority { 1218 LOW (Process.THREAD_PRIORITY_BACKGROUND + (5 * Process.THREAD_PRIORITY_LESS_FAVORABLE)), 1219 NORMAL (Process.THREAD_PRIORITY_DISPLAY); 1220 1221 int mID; Priority(int id)1222 Priority(int id) { 1223 mID = id; 1224 } 1225 } 1226 validateObject(BaseObj o)1227 void validateObject(BaseObj o) { 1228 if (o != null) { 1229 if (o.mRS != this) { 1230 throw new RSIllegalArgumentException("Attempting to use an object across contexts."); 1231 } 1232 } 1233 } 1234 validate()1235 void validate() { 1236 if (mContext == 0) { 1237 throw new RSInvalidStateException("Calling RS with no Context active."); 1238 } 1239 } 1240 1241 /** 1242 * check if IO support lib is available. 1243 */ usingIO()1244 boolean usingIO() { 1245 return useIOlib; 1246 } 1247 /** 1248 * Change the priority of the worker threads for this context. 1249 * 1250 * @param p New priority to be set. 1251 */ setPriority(Priority p)1252 public void setPriority(Priority p) { 1253 validate(); 1254 nContextSetPriority(p.mID); 1255 } 1256 1257 static class MessageThread extends Thread { 1258 RenderScript mRS; 1259 boolean mRun = true; 1260 int[] mAuxData = new int[2]; 1261 1262 static final int RS_MESSAGE_TO_CLIENT_NONE = 0; 1263 static final int RS_MESSAGE_TO_CLIENT_EXCEPTION = 1; 1264 static final int RS_MESSAGE_TO_CLIENT_RESIZE = 2; 1265 static final int RS_MESSAGE_TO_CLIENT_ERROR = 3; 1266 1267 static final int RS_MESSAGE_TO_CLIENT_USER = 4; 1268 static final int RS_ERROR_FATAL_DEBUG = 0x800; 1269 static final int RS_ERROR_FATAL_UNKNOWN = 0x1000; 1270 MessageThread(RenderScript rs)1271 MessageThread(RenderScript rs) { 1272 super("RSMessageThread"); 1273 mRS = rs; 1274 1275 } 1276 run()1277 public void run() { 1278 // This function is a temporary solution. The final solution will 1279 // used typed allocations where the message id is the type indicator. 1280 int[] rbuf = new int[16]; 1281 mRS.nContextInitToClient(mRS.mContext); 1282 while(mRun) { 1283 rbuf[0] = 0; 1284 int msg = mRS.nContextPeekMessage(mRS.mContext, mAuxData); 1285 int size = mAuxData[1]; 1286 int subID = mAuxData[0]; 1287 1288 if (msg == RS_MESSAGE_TO_CLIENT_USER) { 1289 if ((size>>2) >= rbuf.length) { 1290 rbuf = new int[(size + 3) >> 2]; 1291 } 1292 if (mRS.nContextGetUserMessage(mRS.mContext, rbuf) != 1293 RS_MESSAGE_TO_CLIENT_USER) { 1294 throw new RSDriverException("Error processing message from RenderScript."); 1295 } 1296 1297 if(mRS.mMessageCallback != null) { 1298 mRS.mMessageCallback.mData = rbuf; 1299 mRS.mMessageCallback.mID = subID; 1300 mRS.mMessageCallback.mLength = size; 1301 mRS.mMessageCallback.run(); 1302 } else { 1303 throw new RSInvalidStateException("Received a message from the script with no message handler installed."); 1304 } 1305 continue; 1306 } 1307 1308 if (msg == RS_MESSAGE_TO_CLIENT_ERROR) { 1309 String e = mRS.nContextGetErrorMessage(mRS.mContext); 1310 1311 // Copied from java/android/renderscript/RenderScript.java 1312 // Throw RSRuntimeException under the following conditions: 1313 // 1314 // 1) It is an unknown fatal error. 1315 // 2) It is a debug fatal error, and we are not in a 1316 // debug context. 1317 // 3) It is a debug fatal error, and we do not have an 1318 // error callback. 1319 if (subID >= RS_ERROR_FATAL_UNKNOWN || 1320 (subID >= RS_ERROR_FATAL_DEBUG && 1321 (mRS.mContextType != ContextType.DEBUG || 1322 mRS.mErrorCallback == null))) { 1323 android.util.Log.e(LOG_TAG, "fatal RS error, " + e); 1324 throw new RSRuntimeException("Fatal error " + subID + ", details: " + e); 1325 } 1326 1327 if(mRS.mErrorCallback != null) { 1328 mRS.mErrorCallback.mErrorMessage = e; 1329 mRS.mErrorCallback.mErrorNum = subID; 1330 mRS.mErrorCallback.run(); 1331 } else { 1332 android.util.Log.e(LOG_TAG, "non fatal RS error, " + e); 1333 // Do not throw here. In these cases, we do not have 1334 // a fatal error. 1335 } 1336 continue; 1337 } 1338 1339 // 2: teardown. 1340 // But we want to avoid starving other threads during 1341 // teardown by yielding until the next line in the destructor 1342 // can execute to set mRun = false 1343 try { 1344 sleep(1, 0); 1345 } catch(InterruptedException e) { 1346 } 1347 } 1348 //Log.d(LOG_TAG, "MessageThread exiting."); 1349 } 1350 } 1351 RenderScript(Context ctx)1352 RenderScript(Context ctx) { 1353 mContextType = ContextType.NORMAL; 1354 if (ctx != null) { 1355 mApplicationContext = ctx.getApplicationContext(); 1356 // Only set mNativeLibDir for API 9+. 1357 mNativeLibDir = mApplicationContext.getApplicationInfo().nativeLibraryDir; 1358 } 1359 mIncCon = 0; 1360 mIncLoaded = false; 1361 mRWLock = new ReentrantReadWriteLock(); 1362 } 1363 1364 /** 1365 * Gets the application context associated with the RenderScript context. 1366 * 1367 * @return The application context. 1368 */ getApplicationContext()1369 public final Context getApplicationContext() { 1370 return mApplicationContext; 1371 } 1372 1373 /** 1374 * Create a RenderScript context. 1375 * 1376 * @param ctx The context. 1377 * @return RenderScript 1378 */ internalCreate(Context ctx, int sdkVersion, ContextType ct, int flags)1379 private static RenderScript internalCreate(Context ctx, int sdkVersion, ContextType ct, int flags) { 1380 RenderScript rs = new RenderScript(ctx); 1381 1382 if (sSdkVersion == -1) { 1383 sSdkVersion = sdkVersion; 1384 } else if (sSdkVersion != sdkVersion) { 1385 throw new RSRuntimeException("Can't have two contexts with different SDK versions in support lib"); 1386 } 1387 useNative = setupNative(sSdkVersion, ctx); 1388 synchronized(lock) { 1389 if (sInitialized == false) { 1390 try { 1391 Class<?> vm_runtime = Class.forName("dalvik.system.VMRuntime"); 1392 Method get_runtime = vm_runtime.getDeclaredMethod("getRuntime"); 1393 sRuntime = get_runtime.invoke(null); 1394 registerNativeAllocation = vm_runtime.getDeclaredMethod("registerNativeAllocation", Integer.TYPE); 1395 registerNativeFree = vm_runtime.getDeclaredMethod("registerNativeFree", Integer.TYPE); 1396 sUseGCHooks = true; 1397 } catch (Exception e) { 1398 Log.e(LOG_TAG, "No GC methods"); 1399 sUseGCHooks = false; 1400 } 1401 try { 1402 // For API 9 - 22, always use the absolute path of librsjni.so 1403 // http://b/25226912 1404 if (android.os.Build.VERSION.SDK_INT < android.os.Build.VERSION_CODES.M && 1405 rs.mNativeLibDir != null) { 1406 System.load(rs.mNativeLibDir + "/librsjni.so"); 1407 } else { 1408 System.loadLibrary("rsjni"); 1409 } 1410 sInitialized = true; 1411 sPointerSize = rsnSystemGetPointerSize(); 1412 } catch (UnsatisfiedLinkError e) { 1413 Log.e(LOG_TAG, "Error loading RS jni library: " + e); 1414 throw new RSRuntimeException("Error loading RS jni library: " + e + " Support lib API: " + SUPPORT_LIB_VERSION); 1415 } 1416 } 1417 } 1418 1419 if (useNative) { 1420 android.util.Log.v(LOG_TAG, "RS native mode"); 1421 } else { 1422 android.util.Log.v(LOG_TAG, "RS compat mode"); 1423 } 1424 1425 if (android.os.Build.VERSION.SDK_INT >= android.os.Build.VERSION_CODES.ICE_CREAM_SANDWICH) { 1426 useIOlib = true; 1427 } 1428 1429 // The target API level used to init dispatchTable. 1430 int dispatchAPI = sdkVersion; 1431 if (sdkVersion < android.os.Build.VERSION.SDK_INT) { 1432 // If the device API is higher than target API level, init dispatch table based on device API. 1433 dispatchAPI = android.os.Build.VERSION.SDK_INT; 1434 } 1435 1436 String rssupportPath = null; 1437 // For API 9 - 22, always use the absolute path of libRSSupport.so 1438 // http://b/25226912 1439 if (android.os.Build.VERSION.SDK_INT < android.os.Build.VERSION_CODES.M && 1440 rs.mNativeLibDir != null) { 1441 rssupportPath = rs.mNativeLibDir + "/libRSSupport.so"; 1442 } 1443 if (!rs.nLoadSO(useNative, dispatchAPI, rssupportPath)) { 1444 if (useNative) { 1445 android.util.Log.v(LOG_TAG, "Unable to load libRS.so, falling back to compat mode"); 1446 useNative = false; 1447 } 1448 try { 1449 if (android.os.Build.VERSION.SDK_INT < android.os.Build.VERSION_CODES.M && 1450 rs.mNativeLibDir != null) { 1451 System.load(rssupportPath); 1452 } else { 1453 System.loadLibrary("RSSupport"); 1454 } 1455 } catch (UnsatisfiedLinkError e) { 1456 Log.e(LOG_TAG, "Error loading RS Compat library: " + e + " Support lib version: " + SUPPORT_LIB_VERSION); 1457 throw new RSRuntimeException("Error loading RS Compat library: " + e + " Support lib version: " + SUPPORT_LIB_VERSION); 1458 } 1459 if (!rs.nLoadSO(false, dispatchAPI, rssupportPath)) { 1460 Log.e(LOG_TAG, "Error loading RS Compat library: nLoadSO() failed; Support lib version: " + SUPPORT_LIB_VERSION); 1461 throw new RSRuntimeException("Error loading libRSSupport library, Support lib version: " + SUPPORT_LIB_VERSION); 1462 } 1463 } 1464 1465 if (useIOlib) { 1466 try { 1467 System.loadLibrary("RSSupportIO"); 1468 } catch (UnsatisfiedLinkError e) { 1469 useIOlib = false; 1470 } 1471 if (!useIOlib || !rs.nLoadIOSO()) { 1472 android.util.Log.v(LOG_TAG, "Unable to load libRSSupportIO.so, USAGE_IO not supported"); 1473 useIOlib = false; 1474 } 1475 } 1476 1477 // For old APIs with dlopen bug, need to load blas lib in Java first. 1478 // Only try load to blasV8 when the desired API level includes IntrinsicBLAS. 1479 if (dispatchAPI >= 23) { 1480 // Enable multi-input kernels only when diapatchAPI is M+. 1481 rs.mEnableMultiInput = true; 1482 try { 1483 System.loadLibrary("blasV8"); 1484 } catch (UnsatisfiedLinkError e) { 1485 Log.v(LOG_TAG, "Unable to load BLAS lib, ONLY BNNM will be supported: " + e); 1486 } 1487 } 1488 1489 long device = rs.nDeviceCreate(); 1490 rs.mContext = rs.nContextCreate(device, 0, sdkVersion, ct.mID, rs.mNativeLibDir); 1491 rs.mContextType = ct; 1492 rs.mContextFlags = flags; 1493 rs.mContextSdkVersion = sdkVersion; 1494 rs.mDispatchAPILevel = dispatchAPI; 1495 if (rs.mContext == 0) { 1496 throw new RSDriverException("Failed to create RS context."); 1497 } 1498 rs.mMessageThread = new MessageThread(rs); 1499 rs.mMessageThread.start(); 1500 return rs; 1501 } 1502 1503 /** 1504 * Create a RenderScript context. 1505 * 1506 * See documentation for @create for details 1507 * 1508 * @param ctx The context. 1509 * @return RenderScript 1510 */ create(Context ctx)1511 public static RenderScript create(Context ctx) { 1512 return create(ctx, ContextType.NORMAL); 1513 } 1514 1515 /** 1516 * calls create(ctx, ct, CREATE_FLAG_NONE) 1517 * 1518 * See documentation for @create for details 1519 * 1520 * @param ctx The context. 1521 * @param ct The type of context to be created. 1522 * @return RenderScript 1523 */ create(Context ctx, ContextType ct)1524 public static RenderScript create(Context ctx, ContextType ct) { 1525 return create(ctx, ct, CREATE_FLAG_NONE); 1526 } 1527 1528 /** 1529 * Gets or creates a RenderScript context of the specified type. 1530 * 1531 * The returned context will be cached for future reuse within 1532 * the process. When an application is finished using 1533 * RenderScript it should call releaseAllContexts() 1534 * 1535 * A process context is a context designed for easy creation and 1536 * lifecycle management. Multiple calls to this function will 1537 * return the same object provided they are called with the same 1538 * options. This allows it to be used any time a RenderScript 1539 * context is needed. 1540 * 1541 * 1542 * @param ctx The context. 1543 * @param ct The type of context to be created. 1544 * @param flags The OR of the CREATE_FLAG_* options desired 1545 * @return RenderScript 1546 */ create(Context ctx, ContextType ct, int flags)1547 public static RenderScript create(Context ctx, ContextType ct, int flags) { 1548 int v = ctx.getApplicationInfo().targetSdkVersion; 1549 return create(ctx, v, ct, flags); 1550 } 1551 1552 /** 1553 * calls create(ctx, sdkVersion, ContextType.NORMAL, CREATE_FLAG_NONE) 1554 * 1555 * Used by the RenderScriptThunker to maintain backward compatibility. 1556 * 1557 * @hide 1558 * @param ctx The context. 1559 * @param sdkVersion The target SDK Version. 1560 * @return RenderScript 1561 */ create(Context ctx, int sdkVersion)1562 public static RenderScript create(Context ctx, int sdkVersion) { 1563 return create(ctx, sdkVersion, ContextType.NORMAL, CREATE_FLAG_NONE); 1564 } 1565 1566 1567 /** 1568 * calls create(ctx, sdkVersion, ct, CREATE_FLAG_NONE) 1569 * Create a RenderScript context. 1570 * 1571 * @hide 1572 * @param ctx The context. 1573 * @return RenderScript 1574 */ create(Context ctx, int sdkVersion, ContextType ct)1575 public static RenderScript create(Context ctx, int sdkVersion, ContextType ct) { 1576 return create(ctx, sdkVersion, ct, CREATE_FLAG_NONE); 1577 } 1578 1579 /** 1580 * Gets or creates a RenderScript context of the specified type. 1581 * 1582 * @param ctx The context. 1583 * @param ct The type of context to be created. 1584 * @param sdkVersion The target SDK Version. 1585 * @param flags The OR of the CREATE_FLAG_* options desired 1586 * @return RenderScript 1587 */ create(Context ctx, int sdkVersion, ContextType ct, int flags)1588 public static RenderScript create(Context ctx, int sdkVersion, ContextType ct, int flags) { 1589 synchronized (mProcessContextList) { 1590 for (RenderScript prs : mProcessContextList) { 1591 if ((prs.mContextType == ct) && 1592 (prs.mContextFlags == flags) && 1593 (prs.mContextSdkVersion == sdkVersion)) { 1594 1595 return prs; 1596 } 1597 } 1598 1599 RenderScript prs = internalCreate(ctx, sdkVersion, ct, flags); 1600 prs.mIsProcessContext = true; 1601 mProcessContextList.add(prs); 1602 return prs; 1603 } 1604 } 1605 1606 /** 1607 * 1608 * Releases all the process contexts. This is the same as 1609 * calling .destroy() on each unique context retreived with 1610 * create(...). If no contexts have been created this 1611 * function does nothing. 1612 * 1613 * Typically you call this when your application is losing focus 1614 * and will not be using a context for some time. 1615 * 1616 * This has no effect on a context created with 1617 * createMultiContext() 1618 */ releaseAllContexts()1619 public static void releaseAllContexts() { 1620 ArrayList<RenderScript> oldList; 1621 synchronized (mProcessContextList) { 1622 oldList = mProcessContextList; 1623 mProcessContextList = new ArrayList<RenderScript>(); 1624 } 1625 1626 for (RenderScript prs : oldList) { 1627 prs.mIsProcessContext = false; 1628 prs.destroy(); 1629 } 1630 oldList.clear(); 1631 } 1632 1633 1634 1635 /** 1636 * Create a RenderScript context. 1637 * 1638 * This is an advanced function intended for applications which 1639 * need to create more than one RenderScript context to be used 1640 * at the same time. 1641 * 1642 * If you need a single context please use create() 1643 * 1644 * @param ctx The context. 1645 * @return RenderScript 1646 */ createMultiContext(Context ctx, ContextType ct, int flags, int API_number)1647 public static RenderScript createMultiContext(Context ctx, ContextType ct, int flags, int API_number) { 1648 return internalCreate(ctx, API_number, ct, flags); 1649 } 1650 1651 /** 1652 * Print the currently available debugging information about the state of 1653 * the RS context to the log. 1654 * 1655 */ contextDump()1656 public void contextDump() { 1657 validate(); 1658 nContextDump(0); 1659 } 1660 1661 /** 1662 * Wait for any pending asynchronous opeations (such as copies to a RS 1663 * allocation or RS script executions) to complete. 1664 * 1665 */ finish()1666 public void finish() { 1667 nContextFinish(); 1668 } 1669 helpDestroy()1670 private void helpDestroy() { 1671 boolean shouldDestroy = false; 1672 synchronized(this) { 1673 if (!mDestroyed) { 1674 shouldDestroy = true; 1675 mDestroyed = true; 1676 } 1677 } 1678 1679 if (shouldDestroy) { 1680 nContextFinish(); 1681 if (mIncCon != 0) { 1682 nIncContextFinish(); 1683 nIncContextDestroy(); 1684 mIncCon = 0; 1685 } 1686 nContextDeinitToClient(mContext); 1687 mMessageThread.mRun = false; 1688 // Interrupt mMessageThread so it gets to see immediately that mRun is false 1689 // and exit rightaway. 1690 mMessageThread.interrupt(); 1691 1692 // Wait for mMessageThread to join. Try in a loop, in case this thread gets interrupted 1693 // during the wait. If interrupted, set the "interrupted" status of the current thread. 1694 boolean hasJoined = false, interrupted = false; 1695 while (!hasJoined) { 1696 try { 1697 mMessageThread.join(); 1698 hasJoined = true; 1699 } catch (InterruptedException e) { 1700 interrupted = true; 1701 } 1702 } 1703 if (interrupted) { 1704 Log.v(LOG_TAG, "Interrupted during wait for MessageThread to join"); 1705 Thread.currentThread().interrupt(); 1706 } 1707 1708 nContextDestroy(); 1709 } 1710 } 1711 1712 @Override finalize()1713 protected void finalize() throws Throwable { 1714 helpDestroy(); 1715 super.finalize(); 1716 } 1717 1718 /** 1719 * Destroys this RenderScript context. Once this function is called, 1720 * using this context or any objects belonging to this context is 1721 * illegal. 1722 * 1723 * This function is a NOP if the context was created 1724 * with create(). Please use releaseAllContexts() to clean up 1725 * contexts created with the create function. 1726 */ destroy()1727 public void destroy() { 1728 if (mIsProcessContext) { 1729 // users cannot destroy a process context 1730 return; 1731 } 1732 validate(); 1733 helpDestroy(); 1734 } 1735 isAlive()1736 boolean isAlive() { 1737 return mContext != 0; 1738 } 1739 safeID(BaseObj o)1740 long safeID(BaseObj o) { 1741 if(o != null) { 1742 return o.getID(this); 1743 } 1744 return 0; 1745 } 1746 } 1747