Merge "Allocation API update."
diff --git a/graphics/java/android/renderscript/Allocation.java b/graphics/java/android/renderscript/Allocation.java
index 074e423..97d513a 100644
--- a/graphics/java/android/renderscript/Allocation.java
+++ b/graphics/java/android/renderscript/Allocation.java
@@ -33,6 +33,15 @@
 public class Allocation extends BaseObj {
     Type mType;
     Bitmap mBitmap;
+    int mUsage;
+
+    public static final int USAGE_SCRIPT = 0x0001;
+    public static final int USAGE_GRAPHICS_TEXTURE = 0x0002;
+    public static final int USAGE_GRAPHICS_VERTEX = 0x0004;
+    public static final int USAGE_GRAPHICS_CONSTANTS = 0x0008;
+
+    private static final int USAGE_ALL = 0x000F;
+
 
     public enum CubemapLayout {
         VERTICAL_FACE_LIST (0),
@@ -46,13 +55,23 @@
         }
     }
 
-    Allocation(int id, RenderScript rs, Type t) {
-        super(id, rs);
-        mType = t;
+    public enum MipmapGenerationControl {
+        MIPMAP_NONE(0),
+        MIPMAP_FULL(1),
+        MIPMAP_ON_SYNC_TO_TEXTURE(2);
+
+        int mID;
+        MipmapGenerationControl(int id) {
+            mID = id;
+        }
     }
 
-    Allocation(int id, RenderScript rs) {
+    Allocation(int id, RenderScript rs, Type t, int usage) {
         super(id, rs);
+        if (usage > USAGE_ALL) {
+            throw new RSIllegalArgumentException("Unknown usage specified.");
+        }
+        mType = t;
     }
 
     @Override
@@ -69,6 +88,20 @@
         return mType;
     }
 
+    public void syncAll(int srcLocation) {
+        switch (srcLocation) {
+        case USAGE_SCRIPT:
+        case USAGE_GRAPHICS_CONSTANTS:
+        case USAGE_GRAPHICS_TEXTURE:
+        case USAGE_GRAPHICS_VERTEX:
+            break;
+        default:
+            throw new RSIllegalArgumentException("Source must be exactly one usage type.");
+        }
+        mRS.validate();
+        mRS.nAllocationSyncAll(getID(), srcLocation);
+    }
+
     public void uploadToTexture(int baseMipLevel) {
         mRS.validate();
         mRS.nAllocationUploadToTexture(getID(), false, baseMipLevel);
@@ -242,6 +275,7 @@
     }
     */
 
+    /*
     public class Adapter1D extends BaseObj {
         Adapter1D(int id, RenderScript rs) {
             super(id, rs);
@@ -282,6 +316,7 @@
         mRS.nAdapter1DBindAllocation(id, getID());
         return new Adapter1D(id, mRS);
     }
+    */
 
 
     public class Adapter2D extends BaseObj {
@@ -336,32 +371,38 @@
         mBitmapOptions.inScaled = false;
     }
 
-    static public Allocation createTyped(RenderScript rs, Type type) {
-
+    static public Allocation createTyped(RenderScript rs, Type type, int usage) {
         rs.validate();
-        if(type.getID() == 0) {
+        if (type.getID() == 0) {
             throw new RSInvalidStateException("Bad Type");
         }
-        int id = rs.nAllocationCreateTyped(type.getID());
-        if(id == 0) {
+        int id = rs.nAllocationCreateTyped(type.getID(), usage);
+        if (id == 0) {
             throw new RSRuntimeException("Allocation creation failed.");
         }
-        return new Allocation(id, rs, type);
+        return new Allocation(id, rs, type, usage);
     }
 
-    static public Allocation createSized(RenderScript rs, Element e, int count)
-        throws IllegalArgumentException {
+    static public Allocation createTyped(RenderScript rs, Type type) {
+        return createTyped(rs, type, USAGE_ALL);
+    }
 
+    static public Allocation createSized(RenderScript rs, Element e,
+                                         int count, int usage) {
         rs.validate();
         Type.Builder b = new Type.Builder(rs, e);
         b.setX(count);
         Type t = b.create();
 
-        int id = rs.nAllocationCreateTyped(t.getID());
-        if(id == 0) {
+        int id = rs.nAllocationCreateTyped(t.getID(), usage);
+        if (id == 0) {
             throw new RSRuntimeException("Allocation creation failed.");
         }
-        return new Allocation(id, rs, t);
+        return new Allocation(id, rs, t, usage);
+    }
+
+    static public Allocation createSized(RenderScript rs, Element e, int count) {
+        return createSized(rs, e, count, USAGE_ALL);
     }
 
     static private Element elementFromBitmap(RenderScript rs, Bitmap b) {
@@ -381,32 +422,44 @@
         throw new RSInvalidStateException("Bad bitmap type: " + bc);
     }
 
-    static private Type typeFromBitmap(RenderScript rs, Bitmap b, boolean mip) {
+    static private Type typeFromBitmap(RenderScript rs, Bitmap b,
+                                       MipmapGenerationControl mip) {
         Element e = elementFromBitmap(rs, b);
         Type.Builder tb = new Type.Builder(rs, e);
         tb.setX(b.getWidth());
         tb.setY(b.getHeight());
-        tb.setMipmaps(mip);
+        tb.setMipmaps(mip == MipmapGenerationControl.MIPMAP_FULL);
         return tb.create();
     }
 
     static public Allocation createFromBitmap(RenderScript rs, Bitmap b,
-                                              Element dstFmt, boolean genMips) {
+                                              MipmapGenerationControl mips,
+                                              int usage) {
         rs.validate();
-        Type t = typeFromBitmap(rs, b, genMips);
+        Type t = typeFromBitmap(rs, b, mips);
 
-        int id = rs.nAllocationCreateFromBitmap(dstFmt.getID(), genMips, b);
-        if(id == 0) {
+        int id = rs.nAllocationCreateFromBitmap(t.getID(), mips.mID, b, usage);
+        if (id == 0) {
             throw new RSRuntimeException("Load failed.");
         }
-        return new Allocation(id, rs, t);
+        return new Allocation(id, rs, t, usage);
+    }
+
+    static public Allocation createFromBitmap(RenderScript rs, Bitmap b,
+                                              Element dstFmt, boolean genMips) {
+        MipmapGenerationControl mc = MipmapGenerationControl.MIPMAP_NONE;
+        if (genMips) {
+            mc = MipmapGenerationControl.MIPMAP_ON_SYNC_TO_TEXTURE;
+        }
+        return createFromBitmap(rs, b, mc, USAGE_ALL);
     }
 
     static public Allocation createCubemapFromBitmap(RenderScript rs, Bitmap b,
-                                                     Element dstFmt,
-                                                     boolean genMips,
-                                                     CubemapLayout layout) {
+                                                     MipmapGenerationControl mips,
+                                                     CubemapLayout layout,
+                                                     int usage) {
         rs.validate();
+
         int height = b.getHeight();
         int width = b.getWidth();
 
@@ -429,64 +482,76 @@
         tb.setX(width);
         tb.setY(width);
         tb.setFaces(true);
-        tb.setMipmaps(genMips);
+        tb.setMipmaps(mips == MipmapGenerationControl.MIPMAP_FULL);
         Type t = tb.create();
 
-        int id = rs.nAllocationCubeCreateFromBitmap(dstFmt.getID(), genMips, b);
+        int id = rs.nAllocationCubeCreateFromBitmap(t.getID(), mips.mID, b, usage);
         if(id == 0) {
             throw new RSRuntimeException("Load failed for bitmap " + b + " element " + e);
         }
-        return new Allocation(id, rs, t);
+        return new Allocation(id, rs, t, usage);
     }
 
+    static public Allocation createCubemapFromBitmap(RenderScript rs, Bitmap b,
+                                                     Element dstFmt,
+                                                     boolean genMips,
+                                                     CubemapLayout layout) {
+        MipmapGenerationControl mc = MipmapGenerationControl.MIPMAP_NONE;
+        if (genMips) {
+            mc = MipmapGenerationControl.MIPMAP_ON_SYNC_TO_TEXTURE;
+        }
+        return createCubemapFromBitmap(rs, b, mc, layout, USAGE_ALL);
+    }
+
+
     static public Allocation createBitmapRef(RenderScript rs, Bitmap b) {
 
         rs.validate();
-        Type t = typeFromBitmap(rs, b, false);
+        Type t = typeFromBitmap(rs, b, MipmapGenerationControl.MIPMAP_NONE);
 
         int id = rs.nAllocationCreateBitmapRef(t.getID(), b);
         if(id == 0) {
             throw new RSRuntimeException("Load failed.");
         }
 
-        Allocation a = new Allocation(id, rs, t);
+        Allocation a = new Allocation(id, rs, t, USAGE_SCRIPT);
         a.mBitmap = b;
         return a;
     }
 
-    static public Allocation createFromBitmapResource(RenderScript rs, Resources res, int id, Element dstFmt, boolean genMips) {
+    static public Allocation createFromBitmapResource(RenderScript rs,
+                                                      Resources res,
+                                                      int id,
+                                                      MipmapGenerationControl mips,
+                                                      int usage) {
 
         rs.validate();
-        InputStream is = null;
-        try {
-            final TypedValue value = new TypedValue();
-            is = res.openRawResource(id, value);
-
-            int asset = ((AssetManager.AssetInputStream) is).getAssetInt();
-            int aId = rs.nAllocationCreateFromAssetStream(dstFmt.getID(), genMips, asset);
-
-            if (aId == 0) {
-                throw new RSRuntimeException("Load failed.");
-            }
-            Allocation alloc = new Allocation(aId, rs, null);
-            alloc.updateFromNative();
-            return alloc;
-        } finally {
-            if (is != null) {
-                try {
-                    is.close();
-                } catch (IOException e) {
-                    // Ignore
-                }
-            }
-        }
+        Bitmap b = BitmapFactory.decodeResource(res, id);
+        Allocation alloc = createFromBitmap(rs, b, mips, usage);
+        b.recycle();
+        return alloc;
     }
 
-    static public Allocation createFromString(RenderScript rs, String str) {
+    static public Allocation createFromBitmapResource(RenderScript rs,
+                                                      Resources res,
+                                                      int id,
+                                                      Element dstFmt,
+                                                      boolean genMips) {
+        MipmapGenerationControl mc = MipmapGenerationControl.MIPMAP_NONE;
+        if (genMips) {
+            mc = MipmapGenerationControl.MIPMAP_ON_SYNC_TO_TEXTURE;
+        }
+        return createFromBitmapResource(rs, res, id, mc, USAGE_ALL);
+    }
+
+    static public Allocation createFromString(RenderScript rs,
+                                              String str,
+                                              int usage) {
+        rs.validate();
         byte[] allocArray = null;
         try {
             allocArray = str.getBytes("UTF-8");
-            Allocation alloc = Allocation.createSized(rs, Element.U8(rs), allocArray.length);
+            Allocation alloc = Allocation.createSized(rs, Element.U8(rs), allocArray.length, usage);
             alloc.copyFrom(allocArray);
             return alloc;
         }
diff --git a/graphics/java/android/renderscript/BaseObj.java b/graphics/java/android/renderscript/BaseObj.java
index c02435f..05f1bec 100644
--- a/graphics/java/android/renderscript/BaseObj.java
+++ b/graphics/java/android/renderscript/BaseObj.java
@@ -52,6 +52,9 @@
         if (mDestroyed) {
             throw new RSInvalidStateException("using a destroyed object.");
         }
+        if (mID == 0) {
+            throw new RSRuntimeException("Internal error: Object id 0.");
+        }
         return mID;
     }
 
diff --git a/graphics/java/android/renderscript/Mesh.java b/graphics/java/android/renderscript/Mesh.java
index 9176bc8..44faa32 100644
--- a/graphics/java/android/renderscript/Mesh.java
+++ b/graphics/java/android/renderscript/Mesh.java
@@ -77,14 +77,18 @@
 
         for(int i = 0; i < vtxCount; i ++) {
             if(vtxIDs[i] != 0) {
-                mVertexBuffers[i] = new Allocation(vtxIDs[i], mRS);
+                mVertexBuffers[i] = new Allocation(vtxIDs[i], mRS, null,
+                                                   Allocation.USAGE_GRAPHICS_VERTEX |
+                                                   Allocation.USAGE_SCRIPT);
                 mVertexBuffers[i].updateFromNative();
             }
         }
 
         for(int i = 0; i < idxCount; i ++) {
             if(idxIDs[i] != 0) {
-                mIndexBuffers[i] = new Allocation(idxIDs[i], mRS);
+                mIndexBuffers[i] = new Allocation(idxIDs[i], mRS, null,
+                                                  Allocation.USAGE_GRAPHICS_VERTEX |
+                                                  Allocation.USAGE_SCRIPT);
                 mIndexBuffers[i].updateFromNative();
             }
             mPrimitives[i] = Primitive.values()[primitives[i]];
diff --git a/graphics/java/android/renderscript/RenderScript.java b/graphics/java/android/renderscript/RenderScript.java
index 6ff894d..e3a9a67 100644
--- a/graphics/java/android/renderscript/RenderScript.java
+++ b/graphics/java/android/renderscript/RenderScript.java
@@ -192,29 +192,34 @@
         rsnTypeGetNativeData(mContext, id, typeData);
     }
 
-    native int  rsnAllocationCreateTyped(int con, int type);
-    synchronized int nAllocationCreateTyped(int type) {
-        return rsnAllocationCreateTyped(mContext, type);
+    native int  rsnAllocationCreateTyped(int con, int type, int usage);
+    synchronized int nAllocationCreateTyped(int type, int usage) {
+        return rsnAllocationCreateTyped(mContext, type, usage);
     }
-    native void  rsnAllocationUpdateFromBitmap(int con, int alloc, Bitmap bmp);
-    synchronized void nAllocationUpdateFromBitmap(int alloc, Bitmap bmp) {
-        rsnAllocationUpdateFromBitmap(mContext, alloc, bmp);
+    native int  rsnAllocationCreateFromBitmap(int con, int type, int mip, Bitmap bmp, int usage);
+    synchronized int nAllocationCreateFromBitmap(int type, int mip, Bitmap bmp, int usage) {
+        return rsnAllocationCreateFromBitmap(mContext, type, mip, bmp, usage);
     }
-    native int  rsnAllocationCreateFromBitmap(int con, int dstFmt, boolean genMips, Bitmap bmp);
-    synchronized int nAllocationCreateFromBitmap(int dstFmt, boolean genMips, Bitmap bmp) {
-        return rsnAllocationCreateFromBitmap(mContext, dstFmt, genMips, bmp);
-    }
-    native int  rsnAllocationCubeCreateFromBitmap(int con, int dstFmt, boolean genMips, Bitmap bmp);
-    synchronized int nAllocationCubeCreateFromBitmap(int dstFmt, boolean genMips, Bitmap bmp) {
-        return rsnAllocationCubeCreateFromBitmap(mContext, dstFmt, genMips, bmp);
+    native int  rsnAllocationCubeCreateFromBitmap(int con, int type, int mip, Bitmap bmp, int usage);
+    synchronized int nAllocationCubeCreateFromBitmap(int type, int mip, Bitmap bmp, int usage) {
+        return rsnAllocationCubeCreateFromBitmap(mContext, type, mip, bmp, usage);
     }
     native int  rsnAllocationCreateBitmapRef(int con, int type, Bitmap bmp);
     synchronized int nAllocationCreateBitmapRef(int type, Bitmap bmp) {
         return rsnAllocationCreateBitmapRef(mContext, type, bmp);
     }
-    native int  rsnAllocationCreateFromAssetStream(int con, int dstFmt, boolean genMips, int assetStream);
-    synchronized int nAllocationCreateFromAssetStream(int dstFmt, boolean genMips, int assetStream) {
-        return rsnAllocationCreateFromAssetStream(mContext, dstFmt, genMips, assetStream);
+    native int  rsnAllocationCreateFromAssetStream(int con, int mips, int assetStream, int usage);
+    synchronized int nAllocationCreateFromAssetStream(int mips, int assetStream, int usage) {
+        return rsnAllocationCreateFromAssetStream(mContext, mips, assetStream, usage);
+    }
+
+    native void rsnAllocationSyncAll(int con, int alloc, int src);
+    synchronized void nAllocationSyncAll(int alloc, int src) {
+        rsnAllocationSyncAll(mContext, alloc, src);
+    }
+    native void  rsnAllocationUpdateFromBitmap(int con, int alloc, Bitmap bmp);
+    synchronized void nAllocationUpdateFromBitmap(int alloc, Bitmap bmp) {
+        rsnAllocationUpdateFromBitmap(mContext, alloc, bmp);
     }
 
     native void rsnAllocationUploadToTexture(int con, int alloc, boolean genMips, int baseMioLevel);
diff --git a/graphics/java/android/renderscript/Script.java b/graphics/java/android/renderscript/Script.java
index ea616c6..aaf5475 100644
--- a/graphics/java/android/renderscript/Script.java
+++ b/graphics/java/android/renderscript/Script.java
@@ -119,7 +119,11 @@
         protected Allocation mAllocation;
 
         protected void init(RenderScript rs, int dimx) {
-            mAllocation = Allocation.createSized(rs, mElement, dimx);
+            mAllocation = Allocation.createSized(rs, mElement, dimx, Allocation.USAGE_SCRIPT);
+        }
+
+        protected void init(RenderScript rs, int dimx, int usages) {
+            mAllocation = Allocation.createSized(rs, mElement, dimx, Allocation.USAGE_SCRIPT | usages);
         }
 
         protected FieldBase() {
diff --git a/graphics/jni/android_renderscript_RenderScript.cpp b/graphics/jni/android_renderscript_RenderScript.cpp
index c4e0372..65acf93 100644
--- a/graphics/jni/android_renderscript_RenderScript.cpp
+++ b/graphics/jni/android_renderscript_RenderScript.cpp
@@ -388,10 +388,10 @@
 // -----------------------------------
 
 static jint
-nAllocationCreateTyped(JNIEnv *_env, jobject _this, RsContext con, jint e)
+nAllocationCreateTyped(JNIEnv *_env, jobject _this, RsContext con, jint type, jint mips, jint usage)
 {
-    LOG_API("nAllocationCreateTyped, con(%p), e(%p)", con, (RsElement)e);
-    return (jint) rsaAllocationCreateTyped(con, (RsElement)e);
+    LOG_API("nAllocationCreateTyped, con(%p), type(%p), mip(%i), usage(%i)", con, (RsElement)type, mip, usage);
+    return (jint) rsaAllocationCreateTyped(con, (RsType)type, (RsAllocationMipmapGenerationControl)mips, (uint32_t)usage);
 }
 
 static void
@@ -408,6 +408,13 @@
     rsAllocationUploadToBufferObject(con, (RsAllocation)a);
 }
 
+static void
+nAllocationSyncAll(JNIEnv *_env, jobject _this, RsContext con, jint a, jint bits)
+{
+    LOG_API("nAllocationSyncAll, con(%p), a(%p), bits(0x%08x)", con, (RsAllocation)a, bits);
+    rsAllocationSyncAll(con, (RsAllocation)a, (RsAllocationUsageType)bits);
+}
+
 static RsElement SkBitmapToPredefined(SkBitmap::Config cfg)
 {
     switch (cfg) {
@@ -429,45 +436,31 @@
 }
 
 static int
-nAllocationCreateFromBitmap(JNIEnv *_env, jobject _this, RsContext con, jint dstFmt, jboolean genMips, jobject jbitmap)
+nAllocationCreateFromBitmap(JNIEnv *_env, jobject _this, RsContext con, jint type, jint mip, jobject jbitmap, jint usage)
 {
     SkBitmap const * nativeBitmap =
             (SkBitmap const *)_env->GetIntField(jbitmap, gNativeBitmapID);
     const SkBitmap& bitmap(*nativeBitmap);
-    SkBitmap::Config config = bitmap.getConfig();
 
-    RsElement e = SkBitmapToPredefined(config);
-    if (e) {
-        bitmap.lockPixels();
-        const int w = bitmap.width();
-        const int h = bitmap.height();
-        const void* ptr = bitmap.getPixels();
-        jint id = (jint)rsaAllocationCreateFromBitmap(con, w, h, (RsElement)dstFmt, e, genMips, ptr);
-        bitmap.unlockPixels();
-        return id;
-    }
-    return 0;
+    bitmap.lockPixels();
+    const void* ptr = bitmap.getPixels();
+    jint id = (jint)rsaAllocationCreateFromBitmap(con, (RsType)type, (RsAllocationMipmapGenerationControl)mip, ptr, usage);
+    bitmap.unlockPixels();
+    return id;
 }
 
 static int
-nAllocationCubeCreateFromBitmap(JNIEnv *_env, jobject _this, RsContext con, jint dstFmt, jboolean genMips, jobject jbitmap)
+nAllocationCubeCreateFromBitmap(JNIEnv *_env, jobject _this, RsContext con, jint type, jint mip, jobject jbitmap, jint usage)
 {
     SkBitmap const * nativeBitmap =
             (SkBitmap const *)_env->GetIntField(jbitmap, gNativeBitmapID);
     const SkBitmap& bitmap(*nativeBitmap);
-    SkBitmap::Config config = bitmap.getConfig();
 
-    RsElement e = SkBitmapToPredefined(config);
-    if (e) {
-        bitmap.lockPixels();
-        const int w = bitmap.width();
-        const int h = bitmap.height();
-        const void* ptr = bitmap.getPixels();
-        jint id = (jint)rsaAllocationCubeCreateFromBitmap(con, w, h, (RsElement)dstFmt, e, genMips, ptr);
-        bitmap.unlockPixels();
-        return id;
-    }
-    return 0;
+    bitmap.lockPixels();
+    const void* ptr = bitmap.getPixels();
+    jint id = (jint)rsaAllocationCubeCreateFromBitmap(con, (RsType)type, (RsAllocationMipmapGenerationControl)mip, ptr, usage);
+    bitmap.unlockPixels();
+    return id;
 }
 
 static void
@@ -507,8 +500,9 @@
 }
 
 static int
-nAllocationCreateFromAssetStream(JNIEnv *_env, jobject _this, RsContext con, jint dstFmt, jboolean genMips, jint native_asset)
+nAllocationCreateFromAssetStream(JNIEnv *_env, jobject _this, RsContext con, jint dstFmt, jboolean genMips, jint native_asset, jint usage)
 {
+    /*
     Asset* asset = reinterpret_cast<Asset*>(native_asset);
     SkBitmap bitmap;
     SkImageDecoder::DecodeMemory(asset->getBuffer(false), asset->getLength(),
@@ -523,10 +517,11 @@
         const int w = bitmap.width();
         const int h = bitmap.height();
         const void* ptr = bitmap.getPixels();
-        jint id = (jint)rsaAllocationCreateFromBitmap(con, w, h, (RsElement)dstFmt, e, genMips, ptr);
+        jint id = (jint)rsaAllocationCreateFromBitmap(con, w, h, (RsElement)dstFmt, e, genMips, ptr, usage);
         bitmap.unlockPixels();
         return id;
     }
+    */
     return 0;
 }
 
@@ -1313,14 +1308,16 @@
 {"rsnTypeCreate",                    "(IIIIIZZ)I",                            (void*)nTypeCreate },
 {"rsnTypeGetNativeData",             "(II[I)V",                               (void*)nTypeGetNativeData },
 
-{"rsnAllocationCreateTyped",         "(II)I",                                 (void*)nAllocationCreateTyped },
-{"rsnAllocationUpdateFromBitmap",    "(IILandroid/graphics/Bitmap;)V",        (void*)nAllocationUpdateFromBitmap },
-{"rsnAllocationCreateFromBitmap",    "(IIZLandroid/graphics/Bitmap;)I",       (void*)nAllocationCreateFromBitmap },
-{"rsnAllocationCubeCreateFromBitmap","(IIZLandroid/graphics/Bitmap;)I",       (void*)nAllocationCubeCreateFromBitmap },
+{"rsnAllocationCreateTyped",         "(III)I",                                (void*)nAllocationCreateTyped },
+{"rsnAllocationCreateFromBitmap",    "(IIILandroid/graphics/Bitmap;I)I",      (void*)nAllocationCreateFromBitmap },
+{"rsnAllocationCubeCreateFromBitmap","(IIILandroid/graphics/Bitmap;I)I",      (void*)nAllocationCubeCreateFromBitmap },
 {"rsnAllocationCreateBitmapRef",     "(IILandroid/graphics/Bitmap;)I",        (void*)nAllocationCreateBitmapRef },
-{"rsnAllocationCreateFromAssetStream","(IIZI)I",                              (void*)nAllocationCreateFromAssetStream },
+{"rsnAllocationCreateFromAssetStream","(IIII)I",                              (void*)nAllocationCreateFromAssetStream },
+
+{"rsnAllocationUpdateFromBitmap",    "(IILandroid/graphics/Bitmap;)V",        (void*)nAllocationUpdateFromBitmap },
 {"rsnAllocationUploadToTexture",     "(IIZI)V",                               (void*)nAllocationUploadToTexture },
 {"rsnAllocationUploadToBufferObject","(II)V",                                 (void*)nAllocationUploadToBufferObject },
+{"rsnAllocationSyncAll",             "(III)V",                                (void*)nAllocationSyncAll },
 {"rsnAllocationSubData1D",           "(IIII[II)V",                            (void*)nAllocationSubData1D_i },
 {"rsnAllocationSubData1D",           "(IIII[SI)V",                            (void*)nAllocationSubData1D_s },
 {"rsnAllocationSubData1D",           "(IIII[BI)V",                            (void*)nAllocationSubData1D_b },
diff --git a/libs/rs/RenderScript.h b/libs/rs/RenderScript.h
index 7351793..9e30799 100644
--- a/libs/rs/RenderScript.h
+++ b/libs/rs/RenderScript.h
@@ -96,6 +96,20 @@
 #define RS_MAX_ATTRIBS 16
 
 
+enum RsAllocationUsageType {
+    RS_ALLOCATION_USAGE_SCRIPT = 0x0001,
+    RS_ALLOCATION_USAGE_GRAPHICS_TEXTURE = 0x0002,
+    RS_ALLOCATION_USAGE_GRAPHICS_VERTEX = 0x0004,
+    RS_ALLOCATION_USAGE_GRAPHICS_CONSTANTS = 0x0008,
+
+    RS_ALLOCATION_USAGE_ALL = 0x000F
+};
+
+enum RsAllocationMipmapGenerationControl {
+    RS_MIPMAP_NONE = 0,
+    RS_MIPMAP_FULL = 1,
+    RS_MIPMAP_TEXTURE_ONLY = 2
+};
 
 enum RsDataType {
     RS_TYPE_NONE,
@@ -328,10 +342,17 @@
 void rsaElementGetSubElements(RsContext, RsElement, uint32_t *ids, const char **names, uint32_t dataSize);
 
 // Async commands for returning new IDS
-RsType rsaTypeCreate(RsContext, RsElement, uint32_t dimX, uint32_t dimY, uint32_t dimZ, bool mips, bool faces);
-RsAllocation rsaAllocationCreateTyped(RsContext rsc, RsType vtype);
-RsAllocation rsaAllocationCreateFromBitmap(RsContext con, uint32_t w, uint32_t h, RsElement _dst, RsElement _src,  bool genMips, const void *data);
-RsAllocation rsaAllocationCubeCreateFromBitmap(RsContext con, uint32_t w, uint32_t h, RsElement _dst, RsElement _src,  bool genMips, const void *data);
+RsType rsaTypeCreate(RsContext, RsElement, uint32_t dimX, uint32_t dimY,
+                     uint32_t dimZ, bool mips, bool faces);
+RsAllocation rsaAllocationCreateTyped(RsContext rsc, RsType vtype,
+                                      RsAllocationMipmapGenerationControl mips,
+                                      uint32_t usages);
+RsAllocation rsaAllocationCreateFromBitmap(RsContext con, RsType vtype,
+                                           RsAllocationMipmapGenerationControl mips,
+                                           const void *data, uint32_t usages);
+RsAllocation rsaAllocationCubeCreateFromBitmap(RsContext con, RsType vtype,
+                                               RsAllocationMipmapGenerationControl mips,
+                                               const void *data, uint32_t usages);
 
 #ifndef NO_RS_FUNCS
 #include "rsgApiFuncDecl.h"
diff --git a/libs/rs/java/Balls/src/com/android/balls/BallsRS.java b/libs/rs/java/Balls/src/com/android/balls/BallsRS.java
index 83b755f..897b231 100644
--- a/libs/rs/java/Balls/src/com/android/balls/BallsRS.java
+++ b/libs/rs/java/Balls/src/com/android/balls/BallsRS.java
@@ -21,7 +21,7 @@
 import android.util.Log;
 
 public class BallsRS {
-    public static final int PART_COUNT = 1000;
+    public static final int PART_COUNT = 900;
 
     public BallsRS() {
     }
@@ -55,7 +55,7 @@
                     "  vec4 pos = vec4(0.0, 0.0, 0.0, 1.0);\n" +
                     "  pos.xy = ATTRIB_position;\n" +
                     "  gl_Position = UNI_MVP * pos;\n" +
-                    "  varColor = ATTRIB_color;\n" +
+                    "  varColor = vec4(1.0, 1.0, 1.0, 1.0);\n" +
                     "  gl_PointSize = ATTRIB_size;\n" +
                     "}\n";
         sb.setShader(t);
diff --git a/libs/rs/java/Balls/src/com/android/balls/ball_physics.rs b/libs/rs/java/Balls/src/com/android/balls/ball_physics.rs
index 47eaf1b..7c86c67 100644
--- a/libs/rs/java/Balls/src/com/android/balls/ball_physics.rs
+++ b/libs/rs/java/Balls/src/com/android/balls/ball_physics.rs
@@ -30,17 +30,21 @@
         float2 vec2 = vec * vec;
         float len2 = vec2.x + vec2.y;
 
-        if (len2 < 1000) {
-            if (len2 > (4*4)) {
+        if (len2 < 10000) {
+            //float minDist = ballIn->size + bPtr[xin].size;
+            float forceScale = ballIn->size * bPtr[xin].size;
+            forceScale *= forceScale;
+
+            if (len2 > 16 /* (minDist*minDist)*/)  {
                 // Repulsion
                 float len = sqrt(len2);
-                if (len < arcInvStr) {
-                    arcInvStr = len;
-                    arcID = xin;
-                }
-                fv -= (vec / (len * len * len)) * 20000.f;
+                //if (len < arcInvStr) {
+                    //arcInvStr = len;
+                    //arcID = xin;
+                //}
+                fv -= (vec / (len * len * len)) * 20000.f * forceScale;
             } else {
-                if (len2 < 0.1) {
+                if (len2 < 1) {
                     if (xin == x) {
                         continue;
                     }
@@ -51,9 +55,9 @@
                     } else {
                         ballOut->position.x -= 1.f;
                     }
-                    ballOut->color.rgb = 1.f;
-                    ballOut->arcID = -1;
-                    ballOut->arcStr = 0;
+                    //ballOut->color.rgb = 1.f;
+                    //ballOut->arcID = -1;
+                    //ballOut->arcStr = 0;
                     return;
                 }
                 // Collision
@@ -70,57 +74,76 @@
         }
     }
 
-    fv -= gGravityVector;
+    fv /= ballIn->size * ballIn->size * ballIn->size;
+    fv -= gGravityVector * 4.f;
     fv *= ctl->dt;
 
-    {
+    if (touchPressure > 0.1f) {
         float2 tp = {touchX, touchY};
         float2 vec = tp - ballIn->position;
         float2 vec2 = vec * vec;
-        float len2 = vec2.x + vec2.y;
+        float len2 = max(2.f, vec2.x + vec2.y);
+        fv -= (vec / len2) * touchPressure * 400.f;
+    }
 
-        if (len2 > 0.2) {
-            float len = sqrt(len2);
-            fv -= (vec / (len * len)) * touchPressure * 1000.f;
+    ballOut->delta = (ballIn->delta * (1.f - 0.004f)) + fv;
+    ballOut->position = ballIn->position + (ballOut->delta * ctl->dt);
+
+    const float wallForce = 400.f;
+    if (ballOut->position.x > (gMaxPos.x - 20.f)) {
+        float d = gMaxPos.x - ballOut->position.x;
+        if (d < 0.f) {
+            if (ballOut->delta.x > 0) {
+                ballOut->delta.x *= -0.7;
+            }
+            ballOut->position.x = gMaxPos.x;
+        } else {
+            ballOut->delta.x -= min(wallForce / (d * d), 10.f);
         }
     }
 
-    ballOut->delta = ballIn->delta * 0.998f;
-    ballOut->position = ballIn->position;
-
-    ballOut->delta += fv;
-    ballOut->position += ballOut->delta * ctl->dt;
-
-    if (ballOut->position.x > gMaxPos.x) {
-        if (ballOut->delta.x > 0) {
-            ballOut->delta.x *= -0.7;
+    if (ballOut->position.x < (gMinPos.x + 20.f)) {
+        float d = ballOut->position.x - gMinPos.x;
+        if (d < 0.f) {
+            if (ballOut->delta.x < 0) {
+                ballOut->delta.x *= -0.7;
+            }
+            ballOut->position.x = gMinPos.x + 1.f;
+        } else {
+            ballOut->delta.x += min(wallForce / (d * d), 10.f);
         }
-        ballOut->position.x = gMaxPos.x;
-    }
-    if (ballOut->position.y > gMaxPos.y) {
-        if (ballOut->delta.y > 0) {
-            ballOut->delta.y *= -0.7;
-        }
-        ballOut->position.y = gMaxPos.y - 1.f;
-    }
-    if (ballOut->position.x < gMinPos.x) {
-        if (ballOut->delta.x < 0) {
-            ballOut->delta.x *= -0.7;
-        }
-        ballOut->position.x = gMinPos.x + 1.f;
-    }
-    if (ballOut->position.y < gMinPos.y) {
-        if (ballOut->delta.y < 0) {
-            ballOut->delta.y *= -0.7;
-        }
-        ballOut->position.y = gMinPos.y + 1.f;
     }
 
-    ballOut->color.b = 1.f;
-    ballOut->color.r = min(sqrt(length(ballOut->delta)) * 0.1f, 1.f);
-    ballOut->color.g = min(sqrt(length(fv) * 0.1f), 1.f);
-    ballOut->arcID = arcID;
-    ballOut->arcStr = 8 / arcInvStr;
+    if (ballOut->position.y > (gMaxPos.y - 20.f)) {
+        float d = gMaxPos.y - ballOut->position.y;
+        if (d < 0.f) {
+            if (ballOut->delta.y > 0) {
+                ballOut->delta.y *= -0.7;
+            }
+            ballOut->position.y = gMaxPos.y;
+        } else {
+            ballOut->delta.y -= min(wallForce / (d * d), 10.f);
+        }
+    }
+
+    if (ballOut->position.y < (gMinPos.y + 20.f)) {
+        float d = ballOut->position.y - gMinPos.y;
+        if (d < 0.f) {
+            if (ballOut->delta.y < 0) {
+                ballOut->delta.y *= -0.7;
+            }
+            ballOut->position.y = gMinPos.y + 1.f;
+        } else {
+            ballOut->delta.y += min(wallForce / (d * d * d), 10.f);
+        }
+    }
+
+    //ballOut->color.b = 1.f;
+    //ballOut->color.r = min(sqrt(length(ballOut->delta)) * 0.1f, 1.f);
+    //ballOut->color.g = min(sqrt(length(fv) * 0.1f), 1.f);
+    //ballOut->arcID = arcID;
+    //ballOut->arcStr = 8 / arcInvStr;
+    ballOut->size = ballIn->size;
 
     //rsDebug("physics pos out", ballOut->position);
 }
diff --git a/libs/rs/java/Balls/src/com/android/balls/balls.rs b/libs/rs/java/Balls/src/com/android/balls/balls.rs
index 9fd4722..c41ed0f 100644
--- a/libs/rs/java/Balls/src/com/android/balls/balls.rs
+++ b/libs/rs/java/Balls/src/com/android/balls/balls.rs
@@ -14,7 +14,7 @@
 
 typedef struct __attribute__((packed, aligned(4))) Point {
     float2 position;
-    uchar4 color;
+    //uchar4 color;
     float size;
 } Point_t;
 Point_t *point;
@@ -42,8 +42,14 @@
         balls1[ct].position.y = rsRand(0.f, (float)h);
         balls1[ct].delta.x = 0.f;
         balls1[ct].delta.y = 0.f;
-        balls1[ct].arcID = -1;
-        balls1[ct].color = 0.f;
+        //balls1[ct].arcID = -1;
+        //balls1[ct].color = 0.f;
+        balls1[ct].size = 1.f;
+
+        float r = rsRand(100.f);
+        if (r > 90.f) {
+            balls1[ct].size += pow(10.f, rsRand(0.f, 2.f)) * 0.07;
+        }
     }
 }
 
@@ -73,9 +79,9 @@
     uint32_t arcIdx = 0;
     for (uint32_t ct=0; ct < bc.dimX; ct++) {
         point[ct].position = bout[ct].position;
-        point[ct].color = rsPackColorTo8888(bout[ct].color);
-        point[ct].size = 6.f + bout[ct].color.g * 6.f;
-
+        ///point[ct].color = 0xff;//rsPackColorTo8888(bout[ct].color);
+        point[ct].size = 6.f /*+ bout[ct].color.g * 6.f*/ * bout[ct].size;
+/*
         if (bout[ct].arcID >= 0) {
             arc[arcIdx].position = bout[ct].position;
             arc[arcIdx].color.r = min(bout[ct].arcStr, 1.f) * 0xff;
@@ -86,11 +92,12 @@
             arc[arcIdx+1].color = arc[arcIdx].color;
             arcIdx += 2;
         }
+        */
     }
 
     frame++;
-    rsgBindProgramFragment(gPFLines);
-    rsgDrawMesh(arcMesh, 0, 0, arcIdx);
+    //rsgBindProgramFragment(gPFLines);
+    //rsgDrawMesh(arcMesh, 0, 0, arcIdx);
     rsgBindProgramFragment(gPFPoints);
     rsgDrawMesh(partMesh);
     rsClearObject(&bc.ain);
diff --git a/libs/rs/java/Balls/src/com/android/balls/balls.rsh b/libs/rs/java/Balls/src/com/android/balls/balls.rsh
index ed3c31a..fc886f9 100644
--- a/libs/rs/java/Balls/src/com/android/balls/balls.rsh
+++ b/libs/rs/java/Balls/src/com/android/balls/balls.rsh
@@ -2,9 +2,10 @@
 typedef struct __attribute__((packed, aligned(4))) Ball {
     float2 delta;
     float2 position;
-    float3 color;
-    int arcID;
-    float arcStr;
+    //float3 color;
+    float size;
+    //int arcID;
+    //float arcStr;
 } Ball_t;
 Ball_t *balls;
 
diff --git a/libs/rs/java/Fountain/src/com/android/fountain/FountainRS.java b/libs/rs/java/Fountain/src/com/android/fountain/FountainRS.java
index 5188050..04b7f1b 100644
--- a/libs/rs/java/Fountain/src/com/android/fountain/FountainRS.java
+++ b/libs/rs/java/Fountain/src/com/android/fountain/FountainRS.java
@@ -38,7 +38,8 @@
         pfb.setVaryingColor(true);
         rs.bindProgramFragment(pfb.create());
 
-        ScriptField_Point points = new ScriptField_Point(mRS, PART_COUNT);
+        ScriptField_Point points = new ScriptField_Point(mRS, PART_COUNT,
+                                                         Allocation.USAGE_GRAPHICS_VERTEX);
 
         Mesh.AllocationBuilder smb = new Mesh.AllocationBuilder(mRS);
         smb.addVertexAllocation(points.getAllocation());
diff --git a/libs/rs/java/ModelViewer/src/com/android/modelviewer/SceneGraphRS.java b/libs/rs/java/ModelViewer/src/com/android/modelviewer/SceneGraphRS.java
index 07a4412..f61cf25 100644
--- a/libs/rs/java/ModelViewer/src/com/android/modelviewer/SceneGraphRS.java
+++ b/libs/rs/java/ModelViewer/src/com/android/modelviewer/SceneGraphRS.java
@@ -136,7 +136,7 @@
 
     private void initTextAllocation() {
         String allocString = "Displaying file: R.raw.robot";
-        mTextAlloc = Allocation.createFromString(mRS, allocString);
+        mTextAlloc = Allocation.createFromString(mRS, allocString, Allocation.USAGE_SCRIPT);
         mScript.set_gTextAlloc(mTextAlloc);
     }
 
diff --git a/libs/rs/java/ModelViewer/src/com/android/modelviewer/SimpleModelRS.java b/libs/rs/java/ModelViewer/src/com/android/modelviewer/SimpleModelRS.java
index fb9e4c1..22b3fff 100644
--- a/libs/rs/java/ModelViewer/src/com/android/modelviewer/SimpleModelRS.java
+++ b/libs/rs/java/ModelViewer/src/com/android/modelviewer/SimpleModelRS.java
@@ -132,7 +132,7 @@
 
     private void initTextAllocation() {
         String allocString = "Displaying file: R.raw.robot";
-        mTextAlloc = Allocation.createFromString(mRS, allocString);
+        mTextAlloc = Allocation.createFromString(mRS, allocString, Allocation.USAGE_SCRIPT);
         mScript.set_gTextAlloc(mTextAlloc);
     }
 
diff --git a/libs/rs/java/Samples/src/com/android/samples/RsListRS.java b/libs/rs/java/Samples/src/com/android/samples/RsListRS.java
index e139107..223f552 100644
--- a/libs/rs/java/Samples/src/com/android/samples/RsListRS.java
+++ b/libs/rs/java/Samples/src/com/android/samples/RsListRS.java
@@ -126,7 +126,7 @@
         mListAllocs = new ScriptField_ListAllocs_s(mRS, DATA_LIST.length);
         for (int i = 0; i < DATA_LIST.length; i ++) {
             ScriptField_ListAllocs_s.Item listElem = new ScriptField_ListAllocs_s.Item();
-            listElem.text = Allocation.createFromString(mRS, DATA_LIST[i]);
+            listElem.text = Allocation.createFromString(mRS, DATA_LIST[i], Allocation.USAGE_SCRIPT);
             mListAllocs.set(listElem, i, false);
         }
 
diff --git a/libs/rs/java/Samples/src/com/android/samples/RsRenderStatesRS.java b/libs/rs/java/Samples/src/com/android/samples/RsRenderStatesRS.java
index aff36de..6258c9b 100644
--- a/libs/rs/java/Samples/src/com/android/samples/RsRenderStatesRS.java
+++ b/libs/rs/java/Samples/src/com/android/samples/RsRenderStatesRS.java
@@ -315,7 +315,7 @@
         mFontSerifBoldItalic = Font.createFromFamily(mRS, mRes, "serif", Font.Style.BOLD_ITALIC, 8);
         mFontMono = Font.createFromFamily(mRS, mRes, "mono", Font.Style.NORMAL, 8);
 
-        mTextAlloc = Allocation.createFromString(mRS, "String from allocation");
+        mTextAlloc = Allocation.createFromString(mRS, "String from allocation", Allocation.USAGE_SCRIPT);
 
         mScript.set_gFontSans(mFontSans);
         mScript.set_gFontSerif(mFontSerif);
diff --git a/libs/rs/java/tests/src/com/android/rs/test/RSTestCore.java b/libs/rs/java/tests/src/com/android/rs/test/RSTestCore.java
index a1d1c2b..11b0fcd 100644
--- a/libs/rs/java/tests/src/com/android/rs/test/RSTestCore.java
+++ b/libs/rs/java/tests/src/com/android/rs/test/RSTestCore.java
@@ -82,7 +82,7 @@
         mListAllocs = new ScriptField_ListAllocs_s(mRS, uta.length);
         for (int i = 0; i < uta.length; i++) {
             ScriptField_ListAllocs_s.Item listElem = new ScriptField_ListAllocs_s.Item();
-            listElem.text = Allocation.createFromString(mRS, uta[i].name);
+            listElem.text = Allocation.createFromString(mRS, uta[i].name, Allocation.USAGE_SCRIPT);
             listElem.result = uta[i].result;
             mListAllocs.set(listElem, i, false);
             uta[i].setItem(listElem);
diff --git a/libs/rs/rs.spec b/libs/rs/rs.spec
index 7b35305..b1551ba 100644
--- a/libs/rs/rs.spec
+++ b/libs/rs/rs.spec
@@ -151,6 +151,11 @@
 	param void * data
 	}
 
+AllocationSyncAll {
+	param RsAllocation va
+	param RsAllocationUsageType src
+}
+
 Adapter1DCreate {
 	ret RsAdapter1D
 	}
diff --git a/libs/rs/rsAllocation.cpp b/libs/rs/rsAllocation.cpp
index fbb5ac9..f42be0e 100644
--- a/libs/rs/rsAllocation.cpp
+++ b/libs/rs/rsAllocation.cpp
@@ -31,9 +31,11 @@
 using namespace android;
 using namespace android::renderscript;
 
-Allocation::Allocation(Context *rsc, const Type *type) : ObjectBase(rsc) {
+Allocation::Allocation(Context *rsc, const Type *type, uint32_t usages) : ObjectBase(rsc) {
     init(rsc, type);
 
+    mUsageFlags = usages;
+
     mPtr = malloc(mType->getSizeBytes());
     if (mType->getElement()->getHasReferences()) {
         memset(mPtr, 0, mType->getSizeBytes());
@@ -48,6 +50,8 @@
                        : ObjectBase(rsc) {
     init(rsc, type);
 
+    mUsageFlags = RS_ALLOCATION_USAGE_SCRIPT | RS_ALLOCATION_USAGE_GRAPHICS_TEXTURE;
+
     mPtr = bmp;
     mUserBitmapCallback = callback;
     mUserBitmapCallbackData = callbackData;
@@ -137,15 +141,22 @@
     return 0;
 }
 
+void Allocation::syncAll(Context *rsc, RsAllocationUsageType src) {
+    rsAssert(src == RS_ALLOCATION_USAGE_SCRIPT);
+
+    if (mIsTexture) {
+        uploadToTexture(rsc);
+    }
+    if (mIsVertexBuffer) {
+        uploadToBufferObject(rsc);
+    }
+
+    mUploadDefered = false;
+}
 
 void Allocation::uploadToTexture(const Context *rsc) {
 
     mIsTexture = true;
-    if (!rsc->checkDriver()) {
-        mUploadDefered = true;
-        return;
-    }
-
     GLenum type = mType->getElement()->getComponent().getGLType();
     GLenum format = mType->getElement()->getComponent().getGLFormat();
 
@@ -255,10 +266,6 @@
     rsAssert(!mType->getDimZ());
 
     mIsVertexBuffer = true;
-    if (!rsc->checkDriver()) {
-        mUploadDefered = true;
-        return;
-    }
 
     if (!mBufferID) {
         glGenBuffers(1, &mBufferID);
@@ -275,15 +282,9 @@
     rsc->checkError("Allocation::uploadToBufferObject");
 }
 
-void Allocation::uploadCheck(const Context *rsc) {
+void Allocation::uploadCheck(Context *rsc) {
     if (mUploadDefered) {
-        mUploadDefered = false;
-        if (mIsVertexBuffer) {
-            uploadToBufferObject(rsc);
-        }
-        if (mIsTexture) {
-            uploadToTexture(rsc);
-        }
+        syncAll(rsc, RS_ALLOCATION_USAGE_SCRIPT);
     }
 }
 
@@ -516,7 +517,7 @@
         return NULL;
     }
 
-    Allocation *alloc = new Allocation(rsc, type);
+    Allocation *alloc = new Allocation(rsc, type, RS_ALLOCATION_USAGE_ALL);
     alloc->setName(name.string(), name.size());
 
     // Read in all of our allocation data
@@ -748,6 +749,11 @@
 
 #ifndef ANDROID_RS_BUILD_FOR_HOST
 
+void rsi_AllocationSyncAll(Context *rsc, RsAllocation va, RsAllocationUsageType src) {
+    Allocation *a = static_cast<Allocation *>(va);
+    a->syncAll(rsc, src);
+}
+
 RsAllocation rsi_AllocationCreateBitmapRef(Context *rsc, RsType vtype,
                                            void *bmp, void *callbackData,
                                            RsBitmapCallback_t callback) {
@@ -835,60 +841,53 @@
     return a->getType();
 }
 
-RsAllocation rsaAllocationCreateTyped(RsContext con, RsType vtype) {
+RsAllocation rsaAllocationCreateTyped(RsContext con, RsType vtype,
+                                      RsAllocationMipmapGenerationControl mips,
+                                      uint32_t usages) {
     Context *rsc = static_cast<Context *>(con);
-    Allocation * alloc = new Allocation(rsc, static_cast<Type *>(vtype));
+    Allocation * alloc = new Allocation(rsc, static_cast<Type *>(vtype), usages);
     alloc->incUserRef();
     return alloc;
 }
 
-RsAllocation rsaAllocationCreateFromBitmap(RsContext con, uint32_t w, uint32_t h, RsElement _dst, RsElement _src,  bool genMips, const void *data) {
+
+RsAllocation rsaAllocationCreateFromBitmap(RsContext con, RsType vtype,
+                                           RsAllocationMipmapGenerationControl mips,
+                                           const void *data, uint32_t usages) {
     Context *rsc = static_cast<Context *>(con);
-    const Element *src = static_cast<const Element *>(_src);
-    const Element *dst = static_cast<const Element *>(_dst);
+    Type *t = static_cast<Type *>(vtype);
 
-    //LOGE("%p rsi_AllocationCreateFromBitmap %i %i %i", rsc, w, h, genMips);
-    RsType type = rsaTypeCreate(rsc, _dst, w, h, 0, genMips, false);
-
-    RsAllocation vTexAlloc = rsaAllocationCreateTyped(rsc, type);
+    RsAllocation vTexAlloc = rsaAllocationCreateTyped(rsc, vtype, mips, usages);
     Allocation *texAlloc = static_cast<Allocation *>(vTexAlloc);
     if (texAlloc == NULL) {
         LOGE("Memory allocation failure");
         return NULL;
     }
 
-    ElementConverter_t cvt = pickConverter(dst, src);
-    if (cvt) {
-        cvt(texAlloc->getPtr(), data, w * h);
-        if (genMips) {
-            Adapter2D adapt(rsc, texAlloc);
-            Adapter2D adapt2(rsc, texAlloc);
-            for (uint32_t lod=0; lod < (texAlloc->getType()->getLODCount() -1); lod++) {
-                adapt.setLOD(lod);
-                adapt2.setLOD(lod + 1);
-                mip(adapt2, adapt);
-            }
+    memcpy(texAlloc->getPtr(), data, t->getDimX() * t->getDimY() * t->getElementSizeBytes());
+    if (mips == RS_MIPMAP_FULL) {
+        Adapter2D adapt(rsc, texAlloc);
+        Adapter2D adapt2(rsc, texAlloc);
+        for (uint32_t lod=0; lod < (texAlloc->getType()->getLODCount() -1); lod++) {
+            adapt.setLOD(lod);
+            adapt2.setLOD(lod + 1);
+            mip(adapt2, adapt);
         }
-    } else {
-        rsc->setError(RS_ERROR_BAD_VALUE, "Unsupported bitmap format");
-        delete texAlloc;
-        return NULL;
     }
 
     return texAlloc;
 }
 
-RsAllocation rsaAllocationCubeCreateFromBitmap(RsContext con, uint32_t w, uint32_t h, RsElement _dst, RsElement _src,  bool genMips, const void *data) {
+RsAllocation rsaAllocationCubeCreateFromBitmap(RsContext con, RsType vtype,
+                                               RsAllocationMipmapGenerationControl mips,
+                                               const void *data, uint32_t usages) {
     Context *rsc = static_cast<Context *>(con);
-    const Element *src = static_cast<const Element *>(_src);
-    const Element *dst = static_cast<const Element *>(_dst);
+    Type *t = static_cast<Type *>(vtype);
 
     // Cubemap allocation's faces should be Width by Width each.
     // Source data should have 6 * Width by Width pixels
     // Error checking is done in the java layer
-    RsType type = rsaTypeCreate(rsc, _dst, w, h, 0, genMips, true);
-
-    RsAllocation vTexAlloc = rsaAllocationCreateTyped(rsc, type);
+    RsAllocation vTexAlloc = rsaAllocationCreateTyped(rsc, t, mips, usages);
     Allocation *texAlloc = static_cast<Allocation *>(vTexAlloc);
     if (texAlloc == NULL) {
         LOGE("Memory allocation failure");
@@ -896,33 +895,27 @@
     }
 
     uint8_t *sourcePtr = (uint8_t*)data;
-    ElementConverter_t cvt = pickConverter(dst, src);
-    if (cvt) {
-        for (uint32_t face = 0; face < 6; face ++) {
-            Adapter2D faceAdapter(rsc, texAlloc);
-            faceAdapter.setFace(face);
+    for (uint32_t face = 0; face < 6; face ++) {
+        Adapter2D faceAdapter(rsc, texAlloc);
+        faceAdapter.setFace(face);
 
-            cvt(faceAdapter.getElement(0, 0), sourcePtr, w * w);
+        size_t cpySize = t->getDimX() * t->getDimX() * t->getElementSizeBytes();
+        memcpy(faceAdapter.getElement(0, 0), sourcePtr, cpySize);
 
-            // Move the data pointer to the next cube face
-            sourcePtr += w * w * src->getSizeBytes();
+        // Move the data pointer to the next cube face
+        sourcePtr += cpySize;
 
-            if (genMips) {
-                Adapter2D adapt(rsc, texAlloc);
-                Adapter2D adapt2(rsc, texAlloc);
-                adapt.setFace(face);
-                adapt2.setFace(face);
-                for (uint32_t lod=0; lod < (texAlloc->getType()->getLODCount() -1); lod++) {
-                    adapt.setLOD(lod);
-                    adapt2.setLOD(lod + 1);
-                    mip(adapt2, adapt);
-                }
+        if (mips == RS_MIPMAP_FULL) {
+            Adapter2D adapt(rsc, texAlloc);
+            Adapter2D adapt2(rsc, texAlloc);
+            adapt.setFace(face);
+            adapt2.setFace(face);
+            for (uint32_t lod=0; lod < (texAlloc->getType()->getLODCount() -1); lod++) {
+                adapt.setLOD(lod);
+                adapt2.setLOD(lod + 1);
+                mip(adapt2, adapt);
             }
         }
-    } else {
-        rsc->setError(RS_ERROR_BAD_VALUE, "Unsupported bitmap format");
-        delete texAlloc;
-        return NULL;
     }
 
     return texAlloc;
diff --git a/libs/rs/rsAllocation.h b/libs/rs/rsAllocation.h
index 5b432f2..e63c7ab 100644
--- a/libs/rs/rsAllocation.h
+++ b/libs/rs/rsAllocation.h
@@ -29,7 +29,7 @@
     // The graphics equilivent of malloc.  The allocation contains a structure of elements.
 
 public:
-    Allocation(Context *rsc, const Type *);
+    Allocation(Context *rsc, const Type *, uint32_t usages);
     Allocation(Context *rsc, const Type *, void *bmp, void *callbackData, RsBitmapCallback_t callback);
 
     virtual ~Allocation();
@@ -44,6 +44,8 @@
     void * getPtr() const {return mPtr;}
     const Type * getType() const {return mType.get();}
 
+    void syncAll(Context *rsc, RsAllocationUsageType src);
+
     void deferedUploadToTexture(const Context *rsc, bool genMipmap, uint32_t lodOffset);
     void uploadToTexture(const Context *rsc);
     uint32_t getTextureID() const {return mTextureID;}
@@ -84,7 +86,7 @@
     virtual RsA3DClassID getClassId() const { return RS_A3D_CLASS_ID_ALLOCATION; }
     static Allocation *createFromStream(Context *rsc, IStream *stream);
 
-    virtual void uploadCheck(const Context *rsc);
+    virtual void uploadCheck(Context *rsc);
 
     bool getIsTexture() const {return mIsTexture;}
     bool getIsBufferObject() const {return mIsVertexBuffer;}
@@ -112,6 +114,8 @@
     bool mGpuWrite;
     bool mGpuRead;
 
+    uint32_t mUsageFlags;
+
     // more usage hint data from the application
     // which can be used by a driver to pick the best memory type.
     // Likely ignored for now
diff --git a/libs/rs/rsContext.h b/libs/rs/rsContext.h
index cafbdff5..1dc9540 100644
--- a/libs/rs/rsContext.h
+++ b/libs/rs/rsContext.h
@@ -132,7 +132,6 @@
 
     bool setupCheck();
     void setupProgramStore();
-    bool checkDriver() const {return mEGL.mSurface != 0;}
 
     void pause();
     void resume();
diff --git a/libs/rs/rsContextHostStub.h b/libs/rs/rsContextHostStub.h
index aa18bdd..c22647f 100644
--- a/libs/rs/rsContextHostStub.h
+++ b/libs/rs/rsContextHostStub.h
@@ -73,7 +73,6 @@
     RsSurfaceConfig mUserSurfaceConfig;
 
     //bool setupCheck();
-    bool checkDriver() const {return false;}
 
     ProgramFragment * getDefaultProgramFragment() const {
         return NULL;
diff --git a/libs/rs/rsFont.cpp b/libs/rs/rsFont.cpp
index 107022d..3d17be2 100644
--- a/libs/rs/rsFont.cpp
+++ b/libs/rs/rsFont.cpp
@@ -501,7 +501,8 @@
     tmp[2] = RS_PROGRAM_PARAM_TEXTURE_TYPE;
     tmp[3] = RS_TEXTURE_2D;
 
-    mFontShaderFConstant.set(new Allocation(mRSC, inputType));
+    mFontShaderFConstant.set(new Allocation(mRSC, inputType,
+                                            RS_ALLOCATION_USAGE_SCRIPT | RS_ALLOCATION_USAGE_GRAPHICS_CONSTANTS));
     ProgramFragment *pf = new ProgramFragment(mRSC, shaderString.string(),
                                               shaderString.length(), tmp, 4);
     mFontShaderF.set(pf);
@@ -526,7 +527,7 @@
     // We will allocate a texture to initially hold 32 character bitmaps
     Type *texType = Type::getType(mRSC, alphaElem, 1024, 256, 0, false, false);
 
-    Allocation *cacheAlloc = new Allocation(mRSC, texType);
+    Allocation *cacheAlloc = new Allocation(mRSC, texType, RS_ALLOCATION_USAGE_SCRIPT | RS_ALLOCATION_USAGE_GRAPHICS_TEXTURE);
     mTextTexture.set(cacheAlloc);
     mTextTexture->deferedUploadToTexture(mRSC, false, 0);
 
@@ -554,7 +555,7 @@
     uint32_t numIndicies = mMaxNumberOfQuads * 6;
     Type *indexType = Type::getType(mRSC, indexElem, numIndicies, 0, 0, false, false);
 
-    Allocation *indexAlloc = new Allocation(mRSC, indexType);
+    Allocation *indexAlloc = new Allocation(mRSC, indexType, RS_ALLOCATION_USAGE_SCRIPT | RS_ALLOCATION_USAGE_GRAPHICS_VERTEX);
     uint16_t *indexPtr = (uint16_t*)indexAlloc->getPtr();
 
     // Four verts, two triangles , six indices per quad
@@ -586,7 +587,7 @@
                                          mMaxNumberOfQuads * 4,
                                          0, 0, false, false);
 
-    Allocation *vertexAlloc = new Allocation(mRSC, vertexDataType);
+    Allocation *vertexAlloc = new Allocation(mRSC, vertexDataType, RS_ALLOCATION_USAGE_SCRIPT | RS_ALLOCATION_USAGE_GRAPHICS_VERTEX);
     mTextMeshPtr = (float*)vertexAlloc->getPtr();
 
     mVertexArray.set(vertexAlloc);
diff --git a/libs/rs/rsProgramFragment.cpp b/libs/rs/rsProgramFragment.cpp
index 0713fb3..22cd5d3 100644
--- a/libs/rs/rsProgramFragment.cpp
+++ b/libs/rs/rsProgramFragment.cpp
@@ -204,7 +204,7 @@
     tmp[0] = RS_PROGRAM_PARAM_CONSTANT;
     tmp[1] = (uint32_t)inputType;
 
-    Allocation *constAlloc = new Allocation(rsc, inputType);
+    Allocation *constAlloc = new Allocation(rsc, inputType, RS_ALLOCATION_USAGE_SCRIPT | RS_ALLOCATION_USAGE_GRAPHICS_CONSTANTS);
     ProgramFragment *pf = new ProgramFragment(rsc, shaderString.string(),
                                               shaderString.length(), tmp, 2);
     pf->bindAllocation(rsc, constAlloc, 0);
diff --git a/libs/rs/rsProgramVertex.cpp b/libs/rs/rsProgramVertex.cpp
index a28b9bd..ad2beaf 100644
--- a/libs/rs/rsProgramVertex.cpp
+++ b/libs/rs/rsProgramVertex.cpp
@@ -261,7 +261,7 @@
 
     ProgramVertex *pv = new ProgramVertex(rsc, shaderString.string(),
                                           shaderString.length(), tmp, 4);
-    Allocation *alloc = new Allocation(rsc, inputType);
+    Allocation *alloc = new Allocation(rsc, inputType, RS_ALLOCATION_USAGE_SCRIPT | RS_ALLOCATION_USAGE_GRAPHICS_CONSTANTS);
     pv->bindAllocation(rsc, alloc, 0);
 
     mDefaultAlloc.set(alloc);
diff --git a/libs/rs/rsScriptC_Lib.cpp b/libs/rs/rsScriptC_Lib.cpp
index 7e4a247..f61b983 100644
--- a/libs/rs/rsScriptC_Lib.cpp
+++ b/libs/rs/rsScriptC_Lib.cpp
@@ -73,12 +73,14 @@
 
 static float SC_randf(float max) {
     float r = (float)rand();
-    return r / RAND_MAX * max;
+    r *= max;
+    return r / RAND_MAX;
 }
 
 static float SC_randf2(float min, float max) {
     float r = (float)rand();
-    return r / RAND_MAX * (max - min) + min;
+    r = r * (max - min) + min;
+    return r / RAND_MAX;
 }
 
 static int SC_randi(int max) {
diff --git a/libs/rs/rsVertexArray.cpp b/libs/rs/rsVertexArray.cpp
index 5062156..8a9fafe 100644
--- a/libs/rs/rsVertexArray.cpp
+++ b/libs/rs/rsVertexArray.cpp
@@ -81,7 +81,7 @@
                            class VertexArrayState *state,
                            ShaderCache *sc) const {
     rsc->checkError("VertexArray::setupGL2 start");
-    for (uint32_t ct=1; ct <= 0xf/*state->mLastEnableCount*/; ct++) {
+    for (uint32_t ct=1; ct <= state->mLastEnableCount; ct++) {
         glDisableVertexAttribArray(ct);
     }
 
diff --git a/libs/rs/rsg_ScriptJavaClass.cpp b/libs/rs/rsg_ScriptJavaClass.cpp
deleted file mode 100644
index a38553f..0000000
--- a/libs/rs/rsg_ScriptJavaClass.cpp
+++ /dev/null
@@ -1,260 +0,0 @@
-#define NO_RS_FUNCS 1
-
-#include "stdio.h"
-#include "RenderScript.h"
-#include <vector>
-
-struct Element;
-
-struct ElementField {
-    // An Element Field is a combination of an Element with a name assigned.
-
-    const char *name;
-    Element *e;
-
-
-    ElementField(const char *n, Element *_e) {
-        name = n;
-        e = _e;
-    }
-    ElementField() {
-        name = NULL;
-        e = NULL;
-    }
-};
-
-struct Element {
-    // An Element can take one of two forms.
-    // 1: Basic.  It contains a single basic type and vector size.
-    // 2: Complex.  It contains a list of fields with names.  Each field
-    // will in turn be another element.
-
-    ElementField *fields;
-    size_t fieldCount;  // If field count is 0, the element is a Basic type.
-    const char *name;
-    bool generated;
-
-    // The basic data type from RenderScript.h
-    RsDataType compType;
-
-    // The vector size of the data type for float2, float3, ....
-    // Allowed sizes are 2,3,4,8,16
-    uint32_t compVectorSize;
-
-    Element() {
-        fields = NULL;
-        fieldCount = 0;
-        name = NULL;
-        generated = false;
-        compType = RS_TYPE_ELEMENT;
-        compVectorSize = 0;
-    }
-
-    Element(uint32_t _fieldCount, const char *_name) {
-        fields = new ElementField[_fieldCount];
-        fieldCount = _fieldCount;
-        name = _name;
-        generated = false;
-        compType = RS_TYPE_ELEMENT;
-        compVectorSize = 0;
-    }
-
-    Element(RsDataType t, uint32_t s) {
-        fields = NULL;
-        fieldCount = 0;
-        name = NULL;
-        generated = false;
-        compType = t;
-        compVectorSize = s;
-    }
-
-};
-
-
-static void genHeader(FILE *f, const char *packageName) {
-    fprintf(f, "package %s;\n", packageName);
-    fprintf(f, "\n");
-    fprintf(f, "import android.renderscript.*;\n");
-    fprintf(f, "\n");
-    fprintf(f, "\n");
-}
-
-static const char * RSTypeToJava(RsDataType dt) {
-    switch (dt) {
-    //case RS_TYPE_FLOAT_16:         return "float";
-    case RS_TYPE_FLOAT_32:         return "float";
-    //case RS_TYPE_FLOAT_64:         return "double";
-
-    case RS_TYPE_SIGNED_8:         return "byte";
-    case RS_TYPE_SIGNED_16:        return "short";
-    case RS_TYPE_SIGNED_32:        return "int";
-    //case RS_TYPE_SIGNED_64:        return "long";
-
-    case RS_TYPE_UNSIGNED_8:       return "short";
-    case RS_TYPE_UNSIGNED_16:      return "int";
-    case RS_TYPE_UNSIGNED_32:      return "long";
-    //case RS_TYPE_UNSIGNED_64:      return NULL;
-
-    //case RS_TYPE_ELEMENT:          return "android.renderscript.Element";
-    //case RS_TYPE_TYPE:             return "android.renderscript.Type";
-    //case RS_TYPE_ALLOCATION:       return "android.renderscript.Allocation";
-    //case RS_TYPE_SAMPLER:          return "android.renderscript.Sampler";
-    //case RS_TYPE_SCRIPT:           return "android.renderscript.Script";
-    //case RS_TYPE_MESH:             return "android.renderscript.Mesh";
-    //case RS_TYPE_PROGRAM_FRAGMENT: return "android.renderscript.ProgramFragment";
-    //case RS_TYPE_PROGRAM_VERTEX:   return "android.renderscript.ProgramVertex";
-    //case RS_TYPE_PROGRAM_RASTER:   return "android.renderscript.ProgramRaster";
-    //case RS_TYPE_PROGRAM_STORE:    return "android.renderscript.ProgramStore";
-    default: return NULL;
-    }
-    return NULL;
-}
-
-static const char * RSTypeToString(RsDataType dt) {
-    switch (dt) {
-    case RS_TYPE_FLOAT_16:         return "F16";
-    case RS_TYPE_FLOAT_32:         return "F32";
-    case RS_TYPE_FLOAT_64:         return "F64";
-
-    case RS_TYPE_SIGNED_8:         return "I8";
-    case RS_TYPE_SIGNED_16:        return "I16";
-    case RS_TYPE_SIGNED_32:        return "I32";
-    case RS_TYPE_SIGNED_64:        return "I64";
-
-    case RS_TYPE_UNSIGNED_8:       return "U8";
-    case RS_TYPE_UNSIGNED_16:      return "U16";
-    case RS_TYPE_UNSIGNED_32:      return "U32";
-    case RS_TYPE_UNSIGNED_64:      return "U64";
-
-    //case RS_TYPE_ELEMENT:          return "android.renderscript.Element";
-    //case RS_TYPE_TYPE:             return "android.renderscript.Type";
-    //case RS_TYPE_ALLOCATION:       return "android.renderscript.Allocation";
-    //case RS_TYPE_SAMPLER:          return "android.renderscript.Sampler";
-    //case RS_TYPE_SCRIPT:           return "android.renderscript.Script";
-    //case RS_TYPE_MESH:             return "android.renderscript.Mesh";
-    //case RS_TYPE_PROGRAM_FRAGMENT: return "android.renderscript.ProgramFragment";
-    //case RS_TYPE_PROGRAM_VERTEX:   return "android.renderscript.ProgramVertex";
-    //case RS_TYPE_PROGRAM_RASTER:   return "android.renderscript.ProgramRaster";
-    //case RS_TYPE_PROGRAM_STORE:    return "android.renderscript.ProgramStore";
-    default: return NULL;
-    }
-    return NULL;
-}
-
-bool rsGenerateElementClass(const Element *e, const char *packageName, FILE *f) {
-    genHeader(f, packageName);
-
-    fprintf(f, "class Element_%s {\n", e->name);
-
-    for (size_t ct=0; ct < e->fieldCount; ct++) {
-        const char *ts = RSTypeToJava(e->fields[ct].e->compType);
-        if (ts == NULL) {
-            return false;
-        }
-        fprintf(f, "    public %s %s;\n", ts, e->fields[ct].name);
-    }
-
-    fprintf(f, "\n");
-    fprintf(f, "    static Element getElement(RenderScript rs) {\n");
-    fprintf(f, "        Element.Builder eb = new Element.Builder(rs);\n");
-    for (size_t ct=0; ct < e->fieldCount; ct++) {
-        const char *ts = RSTypeToString(e->fields[ct].e->compType);
-        fprintf(f, "         eb.add(Element.USER_%s(rs), \"%s\");\n", ts, e->fields[ct].name);
-    }
-    fprintf(f, "        return eb.create();\n");
-    fprintf(f, "    }\n");
-
-    fprintf(f, "    static Allocation createAllocation(RenderScript rs) {\n");
-    fprintf(f, "        Element e = getElement(rs);\n");
-    fprintf(f, "        Allocation a = Allocation.createSized(rs, e, 1);\n");
-    fprintf(f, "        return a;\n");
-    fprintf(f, "    }\n");
-
-
-    fprintf(f, "    void copyToAllocation(Allocation a) {\n");
-    fprintf(f, "        mIOBuffer.reset();\n");
-    for (size_t ct=0; ct < e->fieldCount; ct++) {
-        const char *ts = RSTypeToString(e->fields[ct].e->compType);
-        fprintf(f, "         mIOBuffer.add%s(%s);\n", ts, e->fields[ct].name);
-    }
-    fprintf(f, "        a.data(mIOBuffer.getData());\n");
-    fprintf(f, "    }\n");
-
-
-
-    fprintf(f, "    private FieldPacker mIOBuffer[];\n");
-    fprintf(f, "    public Element_%s() {\n", e->name);
-    fprintf(f, "        mIOBuffer = new FieldPacker(%i);\n", 100/*element->getSizeBytes()*/);
-    fprintf(f, "    }\n");
-
-
-    fprintf(f, "}\n");
-
-    return true;
-}
-
-bool rsGenerateElementClassFile(Element *e, const char *packageName) {
-    char buf[1024];
-    sprintf(buf, "Element_%s.java", e->name);
-    printf("Creating file %s \n", buf);
-    FILE *f = fopen(buf, "w");
-    bool ret = rsGenerateElementClass(e, packageName, f);
-    fclose(f);
-    return ret;
-}
-
-
-
-
-/*
-bool rsGenerateScriptClass(const ScriptC *script, const char *packageName, FILE *f)
-{
-    genHeader(f, packageName);
-
-    fprintf(f, "class ScriptC_%s {\n", script->getName());
-
-
-
-        ObjectBaseRef<const Type> mTypes[MAX_SCRIPT_BANKS];
-    String8 mSlotNames[MAX_SCRIPT_BANKS];
-    bool mSlotWritable[MAX_SCRIPT_BANKS];
-
-
-}
-*/
-
-
-
-int main(int argc, const char *argv) {
-    Element *u8 = new Element(RS_TYPE_UNSIGNED_8, 1);
-    Element *i32 = new Element(RS_TYPE_SIGNED_32, 1);
-    Element *f32 = new Element(RS_TYPE_FLOAT_32, 1);
-
-    Element *e_Pixel = new Element(4, "Pixel");
-    e_Pixel->fields[0].e = u8;
-    e_Pixel->fields[0].name = "a";
-    e_Pixel->fields[1].e = u8;
-    e_Pixel->fields[1].name = "b";
-    e_Pixel->fields[2].e = u8;
-    e_Pixel->fields[2].name = "g";
-    e_Pixel->fields[3].e = u8;
-    e_Pixel->fields[3].name = "r";
-
-    Element *e_Params = new Element(5, "Params");
-    e_Params->fields[0].e = i32;
-    e_Params->fields[0].name = "inHeight";
-    e_Params->fields[1].e = i32;
-    e_Params->fields[1].name = "inWidth";
-    e_Params->fields[2].e = i32;
-    e_Params->fields[2].name = "outHeight";
-    e_Params->fields[3].e = i32;
-    e_Params->fields[3].name = "outWidth";
-    e_Params->fields[4].e = f32;
-    e_Params->fields[4].name = "threshold";
-
-
-    printf("1\n");
-    rsGenerateElementClassFile(e_Pixel, "android");
-    rsGenerateElementClassFile(e_Params, "android");
-}
-