diff --git a/design/src/android/support/design/widget/FloatingActionButton.java b/design/src/android/support/design/widget/FloatingActionButton.java
index 99085bd..d932d87 100644
--- a/design/src/android/support/design/widget/FloatingActionButton.java
+++ b/design/src/android/support/design/widget/FloatingActionButton.java
@@ -117,6 +117,8 @@
                 mBackgroundTintMode, mRippleColor);
         mImpl.setElevation(elevation);
         mImpl.setPressedTranslationZ(pressedTranslationZ);
+
+        setClickable(true);
     }
 
     @Override
@@ -201,7 +203,10 @@
 
     @Override
     public void setBackgroundDrawable(Drawable background) {
-        mImpl.setBackgroundDrawable(background, mBackgroundTint, mBackgroundTintMode, mRippleColor);
+        if (mImpl != null) {
+            mImpl.setBackgroundDrawable(
+                background, mBackgroundTint, mBackgroundTintMode, mRippleColor);
+        }
     }
 
     final int getSizeDimension() {
diff --git a/design/src/android/support/design/widget/TabLayout.java b/design/src/android/support/design/widget/TabLayout.java
index dade816..5b23fcb 100755
--- a/design/src/android/support/design/widget/TabLayout.java
+++ b/design/src/android/support/design/widget/TabLayout.java
@@ -309,6 +309,8 @@
      */
     public ViewPager.OnPageChangeListener createOnPageChangeListener() {
         return new ViewPager.SimpleOnPageChangeListener() {
+            private int mScrollState;
+
             @Override
             public void onPageScrolled(int position, float positionOffset,
                     int positionOffsetPixels) {
@@ -317,7 +319,14 @@
 
             @Override
             public void onPageSelected(int position) {
-                getTabAt(position).select();
+                if (mScrollState == ViewPager.SCROLL_STATE_IDLE) {
+                    getTabAt(position).select();
+                }
+            }
+
+            @Override
+            public void onPageScrollStateChanged(int state) {
+                mScrollState = state;
             }
         };
     }
@@ -672,7 +681,7 @@
         if (newPosition == Tab.INVALID_POSITION) {
             return;
         }
-        
+
         if (getWindowToken() == null || !ViewCompat.isLaidOut(this)) {
             // If we don't have a window token, or we haven't been laid out yet just draw the new
             // position now
@@ -1048,7 +1057,7 @@
         public void onMeasure(int widthMeasureSpec, int heightMeasureSpec) {
             super.onMeasure(widthMeasureSpec, heightMeasureSpec);
 
-            if (getMeasuredWidth() > mTabMaxWidth) {
+            if (mTabMaxWidth != 0 && getMeasuredWidth() > mTabMaxWidth) {
                 // Re-measure if we went beyond our maximum size.
                 super.onMeasure(MeasureSpec.makeMeasureSpec(
                         mTabMaxWidth, MeasureSpec.EXACTLY), heightMeasureSpec);
diff --git a/v8/renderscript/java/src/android/support/v8/renderscript/Allocation.java b/v8/renderscript/java/src/android/support/v8/renderscript/Allocation.java
index 4b019e9..92c3eb5 100644
--- a/v8/renderscript/java/src/android/support/v8/renderscript/Allocation.java
+++ b/v8/renderscript/java/src/android/support/v8/renderscript/Allocation.java
@@ -268,7 +268,7 @@
      * @hide
      * Enable/Disable AutoPadding for Vec3 elements.
      *
-     * @param useAutoPadding True: enable AutoPadding; flase: disable AutoPadding
+     * @param useAutoPadding True: enable AutoPadding; False: disable AutoPadding
      *
      */
     public void setAutoPadding(boolean useAutoPadding) {
@@ -1253,7 +1253,7 @@
      * @param w Width of the region to update
      * @param h Height of the region to update
      * @param d Depth of the region to update
-     * @param data to be placed into the allocation
+     * @param array to be placed into the allocation
      */
     public void copy3DRangeFrom(int xoff, int yoff, int zoff, int w, int h, int d, Object array) {
         copy3DRangeFromUnchecked(xoff, yoff, zoff, w, h, d, array,
@@ -1306,6 +1306,17 @@
         if (mAutoPadding && (mType.getElement().getVectorSize() == 3)) {
             usePadding = true;
         }
+        if (usePadding) {
+            if (dt.mSize * arrayLen < mSize / 4 * 3) {
+                throw new RSIllegalArgumentException(
+                    "Size of output array cannot be smaller than size of allocation.");
+            }
+        } else {
+            if (dt.mSize * arrayLen < mSize) {
+                throw new RSIllegalArgumentException(
+                    "Size of output array cannot be smaller than size of allocation.");
+            }
+        }
         mRS.nAllocationRead(getID(mRS), array, dt, mType.mElement.mType.mSize, usePadding);
     }
 
@@ -1617,7 +1628,7 @@
      * @param yoff Y offset of the region to copy in this Allocation
      * @param w Width of the region to copy
      * @param h Height of the region to copy
-     * @param array Dest Array to be copied into
+     * @param data Dest Array to be copied into
      */
     public void copy2DRangeTo(int xoff, int yoff, int w, int h, byte[] data) {
         validateIsInt8();
@@ -1633,7 +1644,7 @@
      * @param yoff Y offset of the region to copy in this Allocation
      * @param w Width of the region to copy
      * @param h Height of the region to copy
-     * @param array Dest Array to be copied into
+     * @param data Dest Array to be copied into
      */
     public void copy2DRangeTo(int xoff, int yoff, int w, int h, short[] data) {
         validateIsInt16();
@@ -1649,7 +1660,7 @@
      * @param yoff Y offset of the region to copy in this Allocation
      * @param w Width of the region to copy
      * @param h Height of the region to copy
-     * @param array Dest Array to be copied into
+     * @param data Dest Array to be copied into
      */
     public void copy2DRangeTo(int xoff, int yoff, int w, int h, int[] data) {
         validateIsInt32();
@@ -1665,7 +1676,7 @@
      * @param yoff Y offset of the region to copy in this Allocation
      * @param w Width of the region to copy
      * @param h Height of the region to copy
-     * @param array Dest Array to be copied into
+     * @param data Dest Array to be copied into
      */
     public void copy2DRangeTo(int xoff, int yoff, int w, int h, float[] data) {
         validateIsFloat32();
@@ -2216,4 +2227,3 @@
     }
 
 }
-
diff --git a/v8/renderscript/java/src/android/support/v8/renderscript/FieldPacker.java b/v8/renderscript/java/src/android/support/v8/renderscript/FieldPacker.java
index ccb6d95..5f61920 100644
--- a/v8/renderscript/java/src/android/support/v8/renderscript/FieldPacker.java
+++ b/v8/renderscript/java/src/android/support/v8/renderscript/FieldPacker.java
@@ -48,6 +48,15 @@
         // subAlign() can never work correctly for copied FieldPacker objects.
     }
 
+    static FieldPacker createFromArray(Object[] args) {
+        FieldPacker fp = new FieldPacker(RenderScript.sPointerSize * 8);
+        for (Object arg : args) {
+            fp.addSafely(arg);
+        }
+        fp.resize(fp.mPos);
+        return fp;
+    }
+
     public void align(int v) {
         if ((v <= 0) || ((v & (v - 1)) != 0)) {
             throw new RSIllegalArgumentException("argument must be a non-negative non-zero power of 2: " + v);
@@ -242,8 +251,7 @@
                 addI64(0);
                 addI64(0);
                 addI64(0);
-            }
-            else {
+            } else {
                 addI32((int)obj.getID(null));
             }
         } else {
@@ -903,11 +911,36 @@
         return fp;
     }
 
-    private final byte mData[];
+
+    private boolean resize(int newSize) {
+        if (newSize == mLen) {
+            return false;
+        }
+
+        byte[] newData = new byte[newSize];
+        System.arraycopy(mData, 0, newData, 0, mPos);
+        mData = newData;
+        mLen = newSize;
+        return true;
+    }
+
+    private void addSafely(Object obj) {
+        boolean retry;
+        final int oldPos = mPos;
+        do {
+            retry = false;
+            try {
+                addToPack(this, obj);
+            } catch (ArrayIndexOutOfBoundsException e) {
+                mPos = oldPos;
+                resize(mLen * 2);
+                retry = true;
+            }
+        } while (retry);
+    }
+
+    private byte mData[];
     private int mPos;
     private int mLen;
     private BitSet mAlignment;
-
 }
-
-
diff --git a/v8/renderscript/java/src/android/support/v8/renderscript/RenderScript.java b/v8/renderscript/java/src/android/support/v8/renderscript/RenderScript.java
index 796c41f..4bbbdfe 100644
--- a/v8/renderscript/java/src/android/support/v8/renderscript/RenderScript.java
+++ b/v8/renderscript/java/src/android/support/v8/renderscript/RenderScript.java
@@ -812,10 +812,12 @@
       rsnClosureSetGlobal(mContext, closureID, fieldID, value, size);
     }
 
-    native long rsnScriptGroup2Create(long con, String cachePath, long[] closures);
-    synchronized long nScriptGroup2Create(String cachePath, long[] closures) {
+    native long rsnScriptGroup2Create(long con, String name, String cachePath,
+                                      long[] closures);
+    synchronized long nScriptGroup2Create(String name, String cachePath,
+                                          long[] closures) {
       validate();
-      return rsnScriptGroup2Create(mContext, cachePath, closures);
+      return rsnScriptGroup2Create(mContext, name, cachePath, closures);
     }
 
     native void rsnScriptGroup2Execute(long con, long groupID);
diff --git a/v8/renderscript/java/src/android/support/v8/renderscript/ScriptGroup.java b/v8/renderscript/java/src/android/support/v8/renderscript/ScriptGroup.java
index a6e6d00..6861754 100644
--- a/v8/renderscript/java/src/android/support/v8/renderscript/ScriptGroup.java
+++ b/v8/renderscript/java/src/android/support/v8/renderscript/ScriptGroup.java
@@ -16,36 +16,35 @@
 
 package android.support.v8.renderscript;
 
+import android.util.Log;
+import android.util.Pair;
 import java.lang.reflect.Method;
 import java.util.ArrayList;
 import java.util.Collections;
 import java.util.Comparator;
+import java.util.HashMap;
+import java.util.List;
+import java.util.Map;
 
 /**
- * ScriptGroup creates a group of kernels that are executed
- * together with one execution call as if they were a single kernel.
- * The kernels may be connected internally or to an external allocation.
- * The intermediate results for internal connections are not observable
- * after the execution of the script.
+ * A group of kernels that are executed
+ * together with one execution call as if they were a single kernel
  * <p>
- * External connections are grouped into inputs and outputs.
- * All outputs are produced by a script kernel and placed into a
- * user-supplied allocation. Inputs provide the input of a kernel.
- * Inputs bound to script globals are set directly upon the script.
+ * In addition to kernels, a script group may contain invocable functions as well.
+ * A script group may take inputs and generate outputs, which are consumed and
+ * produced by its member kernels.
+ * Inside a script group, outputs from one kernel can be passed to another kernel as inputs.
+ * The API disallows cyclic dependencies among kernels in a script group,
+ * effectively making it a directed acyclic graph (DAG) of kernels.
  * <p>
- * A ScriptGroup must contain at least one kernel. A ScriptGroup
- * must contain only a single directed acyclic graph (DAG) of
- * script kernels and connections. Attempting to create a
- * ScriptGroup with multiple DAGs or attempting to create
- * a cycle within a ScriptGroup will throw an exception.
- * <p>
- * Currently, all kernels in a ScriptGroup must be from separate
- * Script objects. Attempting to use multiple kernels from the same
- * Script object will result in an
- * {@link android.support.v8.renderscript.RSInvalidStateException}.
- *
+ * Grouping kernels together allows for more efficient execution. For example,
+ * runtime and compiler optimization can be applied to reduce computation and
+ * communication overhead, and to make better use of the CPU and the GPU.
  **/
 public class ScriptGroup extends BaseObj {
+    //FIXME: Change 23 to the codename when that is decided.
+    private static final int MIN_API_VERSION = 23;
+
     IO mOutputs[];
     IO mInputs[];
     private boolean mUseIncSupp = false;
@@ -96,16 +95,395 @@
         }
     }
 
+    /**
+     * An opaque class for closures
+     * <p>
+     * A closure represents a function call to a kernel or invocable function,
+     * combined with arguments and values for global variables. A closure is
+     * created using the {@link android.renderscript.ScriptGroup.Builder2#addKernel} or
+     * {@link android.renderscript.ScriptGroup.Builder2#addInvoke}
+     * method.
+     */
+
+    public static final class Closure extends BaseObj {
+        private Object[] mArgs;
+        private Allocation mReturnValue;
+        private Map<Script.FieldID, Object> mBindings;
+
+        private Future mReturnFuture;
+        private Map<Script.FieldID, Future> mGlobalFuture;
+
+        private FieldPacker mFP;
+
+        private static final String TAG = "Closure";
+
+        private Closure(long id, RenderScript rs) {
+            super(id, rs);
+        }
+
+        private Closure(RenderScript rs, Script.KernelID kernelID, Type returnType,
+                       Object[] args, Map<Script.FieldID, Object> globals) {
+            super(0, rs);
+
+            if (android.os.Build.VERSION.SDK_INT < MIN_API_VERSION && rs.isUseNative()) {
+                throw new RSRuntimeException("ScriptGroup2 not supported in this API level");
+            }
+
+            mArgs = args;
+            mReturnValue = Allocation.createTyped(rs, returnType);
+            mBindings = globals;
+            mGlobalFuture = new HashMap<Script.FieldID, Future>();
+
+            int numValues = args.length + globals.size();
+
+            long[] fieldIDs = new long[numValues];
+            long[] values = new long[numValues];
+            int[] sizes = new int[numValues];
+            long[] depClosures = new long[numValues];
+            long[] depFieldIDs = new long[numValues];
+
+            int i;
+            for (i = 0; i < args.length; i++) {
+                Object obj = args[i];
+                fieldIDs[i] = 0;
+                if (obj instanceof Input) {
+                    Input unbound = (Input)obj;
+                    unbound.addReference(this, i);
+                } else {
+                    retrieveValueAndDependenceInfo(rs, i, args[i], values, sizes,
+                                                   depClosures, depFieldIDs);
+                }
+            }
+
+            for (Map.Entry<Script.FieldID, Object> entry : globals.entrySet()) {
+                Object obj = entry.getValue();
+                Script.FieldID fieldID = entry.getKey();
+                fieldIDs[i] = fieldID.getID(rs);
+                if (obj instanceof Input) {
+                    Input unbound = (Input)obj;
+                    unbound.addReference(this, fieldID);
+                } else {
+                    retrieveValueAndDependenceInfo(rs, i, obj, values,
+                                                   sizes, depClosures, depFieldIDs);
+                }
+                i++;
+            }
+
+            long id = rs.nClosureCreate(kernelID.getID(rs), mReturnValue.getID(rs),
+                                        fieldIDs, values, sizes, depClosures, depFieldIDs);
+
+            setID(id);
+        }
+
+        private Closure(RenderScript rs, Script.InvokeID invokeID,
+                       Object[] args, Map<Script.FieldID, Object> globals) {
+            super(0, rs);
+
+            if (android.os.Build.VERSION.SDK_INT < MIN_API_VERSION && rs.isUseNative()) {
+                throw new RSRuntimeException("ScriptGroup2 not supported in this API level");
+            }
+
+            mFP = FieldPacker.createFromArray(args);
+
+            mArgs = args;
+            mBindings = globals;
+            mGlobalFuture = new HashMap<Script.FieldID, Future>();
+
+            int numValues = globals.size();
+
+            long[] fieldIDs = new long[numValues];
+            long[] values = new long[numValues];
+            int[] sizes = new int[numValues];
+            long[] depClosures = new long[numValues];
+            long[] depFieldIDs = new long[numValues];
+
+            int i = 0;
+            for (Map.Entry<Script.FieldID, Object> entry : globals.entrySet()) {
+                Object obj = entry.getValue();
+                Script.FieldID fieldID = entry.getKey();
+                fieldIDs[i] = fieldID.getID(rs);
+                if (obj instanceof Input) {
+                    Input unbound = (Input)obj;
+                    unbound.addReference(this, fieldID);
+                } else {
+                    // TODO(yangni): Verify obj not a future.
+                    retrieveValueAndDependenceInfo(rs, i, obj, values,
+                                                   sizes, depClosures, depFieldIDs);
+                }
+                i++;
+            }
+
+            long id = rs.nInvokeClosureCreate(invokeID.getID(rs), mFP.getData(), fieldIDs,
+                                              values, sizes);
+
+            setID(id);
+        }
+
+        private static
+                void retrieveValueAndDependenceInfo(RenderScript rs,
+                                                    int index, Object obj,
+                                                    long[] values, int[] sizes,
+                                                    long[] depClosures,
+                                                    long[] depFieldIDs) {
+
+            if (obj instanceof Future) {
+                Future f = (Future)obj;
+                obj = f.getValue();
+                depClosures[index] = f.getClosure().getID(rs);
+                Script.FieldID fieldID = f.getFieldID();
+                depFieldIDs[index] = fieldID != null ? fieldID.getID(rs) : 0;
+                if (obj == null) {
+                    // Value is originally created by the owner closure
+                    values[index] = 0;
+                    sizes[index] = 0;
+                    return;
+                }
+            } else {
+                depClosures[index] = 0;
+                depFieldIDs[index] = 0;
+            }
+
+            ValueAndSize vs = new ValueAndSize(rs, obj);
+            values[index] = vs.value;
+            sizes[index] = vs.size;
+        }
+
+        /**
+         * Returns the future for the return value
+         *
+         * @return a future
+         */
+
+        public Future getReturn() {
+            if (mReturnFuture == null) {
+                mReturnFuture = new Future(this, null, mReturnValue);
+            }
+
+            return mReturnFuture;
+        }
+
+        /**
+         * Returns the future for a global variable
+         *
+         * @param field the field ID for the global variable
+         * @return a future
+         */
+
+        public Future getGlobal(Script.FieldID field) {
+            Future f = mGlobalFuture.get(field);
+
+            if (f == null) {
+                // If the field is not bound to this closure, this will return a future
+                // without an associated value (reference). So this is not working for
+                // cross-module (cross-script) linking in this case where a field not
+                // explicitly bound.
+                f = new Future(this, field, mBindings.get(field));
+                mGlobalFuture.put(field, f);
+            }
+
+            return f;
+        }
+
+        void setArg(int index, Object obj) {
+            mArgs[index] = obj;
+            ValueAndSize vs = new ValueAndSize(mRS, obj);
+            mRS.nClosureSetArg(getID(mRS), index, vs.value, vs.size);
+        }
+
+        void setGlobal(Script.FieldID fieldID, Object obj) {
+            mBindings.put(fieldID, obj);
+            ValueAndSize vs = new ValueAndSize(mRS, obj);
+            mRS.nClosureSetGlobal(getID(mRS), fieldID.getID(mRS), vs.value, vs.size);
+        }
+
+        private static final class ValueAndSize {
+            public ValueAndSize(RenderScript rs, Object obj) {
+                if (obj instanceof Allocation) {
+                    value = ((Allocation)obj).getID(rs);
+                    size = -1;
+                } else if (obj instanceof Boolean) {
+                    value = ((Boolean)obj).booleanValue() ? 1 : 0;
+                    size = 4;
+                } else if (obj instanceof Integer) {
+                    value = ((Integer)obj).longValue();
+                    size = 4;
+                } else if (obj instanceof Long) {
+                    value = ((Long)obj).longValue();
+                    size = 8;
+                } else if (obj instanceof Float) {
+                    value = ((Float)obj).longValue();
+                    size = 4;
+                } else if (obj instanceof Double) {
+                    value = ((Double)obj).longValue();
+                    size = 8;
+                }
+            }
+            public long value;
+            public int size;
+        }
+    }
+
+    /**
+     * An opaque class for futures
+     * <p>
+     * A future represents an output of a closure, either the return value of
+     * the function, or the value of a global variable written by the function.
+     * A future is created by calling the {@link Closure#getReturn}  or
+     * {@link Closure#getGlobal} method.
+     */
+
+    public static final class Future {
+        Closure mClosure;
+        Script.FieldID mFieldID;
+        Object mValue;
+
+        Future(Closure closure, Script.FieldID fieldID, Object value) {
+            mClosure = closure;
+            mFieldID = fieldID;
+            mValue = value;
+        }
+
+        Closure getClosure() { return mClosure; }
+        Script.FieldID getFieldID() { return mFieldID; }
+        Object getValue() { return mValue; }
+    }
+
+    /**
+     * An opaque class for unbound values (used for script group inputs)
+     * <p>
+     * Created by calling the {@link Builder2#addInput} method. The value
+     * is assigned in {@link ScriptGroup#execute(Object...)} method as
+     * one of its arguments. Arguments to the execute method should be in
+     * the same order as intputs are added using the addInput method.
+     */
+
+    public static final class Input {
+        // Either mFieldID or mArgIndex should be set but not both.
+        List<Pair<Closure, Script.FieldID>> mFieldID;
+        // -1 means unset. Legal values are 0 .. n-1, where n is the number of
+        // arguments for the referencing closure.
+        List<Pair<Closure, Integer>> mArgIndex;
+
+        Input() {
+            mFieldID = new ArrayList<Pair<Closure, Script.FieldID>>();
+            mArgIndex = new ArrayList<Pair<Closure, Integer>>();
+        }
+
+        void addReference(Closure closure, int index) {
+            mArgIndex.add(Pair.create(closure, Integer.valueOf(index)));
+        }
+
+        void addReference(Closure closure, Script.FieldID fieldID) {
+            mFieldID.add(Pair.create(closure, fieldID));
+        }
+
+        void set(Object value) {
+            for (Pair<Closure, Integer> p : mArgIndex) {
+                Closure closure = p.first;
+                int index = p.second.intValue();
+                closure.setArg(index, value);
+            }
+            for (Pair<Closure, Script.FieldID> p : mFieldID) {
+                Closure closure = p.first;
+                Script.FieldID fieldID = p.second;
+                closure.setGlobal(fieldID, value);
+            }
+        }
+    }
+
+    String mName;
+    List<Closure> mClosures;
+    List<Input> mInputs2;
+    Future[] mOutputs2;
+
+    private static final String TAG = "ScriptGroup2";
 
     ScriptGroup(long id, RenderScript rs) {
         super(id, rs);
     }
 
+    ScriptGroup(RenderScript rs, String name, List<Closure> closures,
+                List<Input> inputs, Future[] outputs) {
+        super(0, rs);
+
+        if (android.os.Build.VERSION.SDK_INT < MIN_API_VERSION && rs.isUseNative()) {
+            throw new RSRuntimeException("ScriptGroup2 not supported in this API level");
+        }
+        mName = name;
+        mClosures = closures;
+        mInputs2 = inputs;
+        mOutputs2 = outputs;
+
+        long[] closureIDs = new long[closures.size()];
+        for (int i = 0; i < closureIDs.length; i++) {
+            closureIDs[i] = closures.get(i).getID(rs);
+        }
+        String cachePath = rs.getApplicationContext().getCacheDir().toString();
+        long id = rs.nScriptGroup2Create(name, cachePath, closureIDs);
+        setID(id);
+    }
+
+    /**
+     * Executes a script group
+     *
+     * @param inputs inputs to the script group
+     * @return outputs of the script group as an array of objects
+     */
+
+    public Object[] execute(Object... inputs) {
+        if (inputs.length < mInputs2.size()) {
+            Log.e(TAG, this.toString() + " receives " + inputs.length + " inputs, " +
+                  "less than expected " + mInputs2.size());
+            return null;
+        }
+
+        if (inputs.length > mInputs2.size()) {
+            Log.i(TAG, this.toString() + " receives " + inputs.length + " inputs, " +
+                  "more than expected " + mInputs2.size());
+        }
+
+        for (int i = 0; i < mInputs2.size(); i++) {
+            Object obj = inputs[i];
+            if (obj instanceof Future || obj instanceof Input) {
+                Log.e(TAG, this.toString() + ": input " + i +
+                      " is a future or unbound value");
+                return null;
+            }
+            Input unbound = mInputs2.get(i);
+            unbound.set(obj);
+        }
+
+        mRS.nScriptGroup2Execute(getID(mRS));
+
+        Object[] outputObjs = new Object[mOutputs2.length];
+        int i = 0;
+        for (Future f : mOutputs2) {
+            outputObjs[i++] = f.getValue();
+        }
+        return outputObjs;
+    }
+
+    /**
+     * Represents a binding of a value to a global variable in a
+     * kernel or invocable function. Used in closure creation.
+     */
+
+    public static final class Binding {
+        public Script.FieldID mField;
+        public Object mValue;
+        public Binding(Script.FieldID field, Object value) {
+            mField = field;
+            mValue = value;
+        }
+    }
+
     /**
      * Sets an input of the ScriptGroup. This specifies an
      * Allocation to be used for kernels that require an input
      * Allocation provided from outside of the ScriptGroup.
      *
+     * @deprecated Set arguments to {@link #execute(Object...)} instead.
+     *
      * @param s The ID of the kernel where the allocation should be
      *          connected.
      * @param a The allocation to connect.
@@ -128,6 +506,8 @@
      * Allocation to be used for the kernels that require an output
      * Allocation visible after the ScriptGroup is executed.
      *
+     * @deprecated Use return value of {@link #execute(Object...)} instead.
+     *
      * @param s The ID of the kernel where the allocation should be
      *          connected.
      * @param a The allocation to connect.
@@ -153,6 +533,8 @@
      * If Incremental Support for intrinsics is needed, the execution
      * will take the naive path: execute kernels one by one in the
      * correct order.
+     *
+     * @deprecated Use {@link #execute} instead.
      */
     public void execute() {
         if (!mUseIncSupp) {
@@ -238,6 +620,8 @@
      * Once all connections are made, a call to {@link #create} will
      * return the ScriptGroup object.
      *
+     * @deprecated Use {@link Builder2} instead.
+     *
      */
     public static final class Builder {
         private RenderScript mRS;
@@ -591,6 +975,154 @@
 
     }
 
+    /**
+     * The builder class for creating script groups
+     * <p>
+     * A script group is created using closures (see class {@link Closure}).
+     * A closure is a function call to a kernel or
+     * invocable function. Each function argument or global variable accessed inside
+     * the function is bound to 1) a known value, 2) a script group input
+     * (see class {@link Input}), or 3) a
+     * future (see class {@link Future}).
+     * A future is the output of a closure, either the return value of the
+     * function or a global variable written by that function.
+     * <p>
+     * Closures are created using the {@link #addKernel} or {@link #addInvoke}
+     * methods.
+     * When a closure is created, futures from previously created closures
+     * can be used as its inputs.
+     * External script group inputs can be used as inputs to individual closures as well.
+     * An external script group input is created using the {@link #addInput} method.
+     * A script group is created by a call to the {@link #create} method, which
+     * accepts an array of futures as the outputs for the script group.
+     * <p>
+     * Closures in a script group can be evaluated in any order as long as the
+     * following conditions are met:
+     * 1) a closure must be evaluated before any other closures that take its
+     * futures as inputs;
+     * 2) all closures added before an invoke closure must be evaluated
+     * before it;
+     * and 3) all closures added after an invoke closure must be evaluated after
+     * it.
+     * As a special case, the order that the closures are added is a legal
+     * evaluation order. However, other evaluation orders are possible, including
+     * concurrently evaluating independent closures.
+     */
+
+    public static final class Builder2 {
+        RenderScript mRS;
+        List<Closure> mClosures;
+        List<Input> mInputs;
+        private static final String TAG = "ScriptGroup2.Builder";
+
+        public Builder2(RenderScript rs) {
+            mRS = rs;
+            mClosures = new ArrayList<Closure>();
+            mInputs = new ArrayList<Input>();
+        }
+
+        private Closure addKernelInternal(Script.KernelID k, Type returnType, Object[] args,
+                                         Map<Script.FieldID, Object> globalBindings) {
+            Closure c = new Closure(mRS, k, returnType, args, globalBindings);
+            mClosures.add(c);
+            return c;
+        }
+
+        private Closure addInvokeInternal(Script.InvokeID invoke, Object[] args,
+                                          Map<Script.FieldID, Object> globalBindings) {
+            Closure c = new Closure(mRS, invoke, args, globalBindings);
+            mClosures.add(c);
+            return c;
+        }
+
+        /**
+         * Adds a script group input
+         *
+         * @return a script group input, which can be used as an argument or a value to
+         *     a global variable for creating closures
+         */
+
+        public Input addInput() {
+            Input unbound = new Input();
+            mInputs.add(unbound);
+            return unbound;
+        }
+
+        /**
+         * Adds a closure for a kernel
+         *
+         * @param k Kernel ID for the kernel function
+         * @param argsAndBindings arguments followed by bindings for global variables
+         * @return a closure
+         */
+
+        public Closure addKernel(Script.KernelID k, Type returnType, Object... argsAndBindings) {
+            ArrayList<Object> args = new ArrayList<Object>();
+            Map<Script.FieldID, Object> bindingMap = new HashMap<Script.FieldID, Object>();
+            if (!seperateArgsAndBindings(argsAndBindings, args, bindingMap)) {
+                return null;
+            }
+            return addKernelInternal(k, returnType, args.toArray(), bindingMap);
+        }
+
+        /**
+         * Adds a closure for an invocable function
+         *
+         * @param invoke Invoke ID for the invocable function
+         * @param argsAndBindings arguments followed by bindings for global variables
+         * @return a closure
+         */
+
+        public Closure addInvoke(Script.InvokeID invoke, Object... argsAndBindings) {
+            ArrayList<Object> args = new ArrayList<Object>();
+            Map<Script.FieldID, Object> bindingMap = new HashMap<Script.FieldID, Object>();
+            if (!seperateArgsAndBindings(argsAndBindings, args, bindingMap)) {
+                return null;
+            }
+            return addInvokeInternal(invoke, args.toArray(), bindingMap);
+        }
+
+        /**
+         * Creates a script group
+         *
+         * @param name name for the script group. Legal names can only contain letters, digits,
+         *        '-', or '_'. The name can be no longer than 100 characters.
+         * @param outputs futures intended as outputs of the script group
+         * @return a script group
+         */
+
+        public ScriptGroup create(String name, Future... outputs) {
+            if (name == null || name.isEmpty() || name.length() > 100 ||
+                !name.equals(name.replaceAll("[^a-zA-Z0-9-]", "_"))) {
+                throw new RSIllegalArgumentException("invalid script group name");
+            }
+            ScriptGroup ret = new ScriptGroup(mRS, name, mClosures, mInputs, outputs);
+            return ret;
+        }
+
+        private boolean seperateArgsAndBindings(Object[] argsAndBindings,
+                                                ArrayList<Object> args,
+                                                Map<Script.FieldID, Object> bindingMap) {
+            int i;
+            for (i = 0; i < argsAndBindings.length; i++) {
+                if (argsAndBindings[i] instanceof Binding) {
+                    break;
+                }
+                args.add(argsAndBindings[i]);
+            }
+
+            for (; i < argsAndBindings.length; i++) {
+                if (!(argsAndBindings[i] instanceof Binding)) {
+                    return false;
+                }
+                Binding b = (Binding)argsAndBindings[i];
+                bindingMap.put(b.mField, b.mValue);
+            }
+
+            return true;
+        }
+
+    }
 
 }
 
diff --git a/v8/renderscript/java/src/android/support/v8/renderscript/ScriptGroup2.java b/v8/renderscript/java/src/android/support/v8/renderscript/ScriptGroup2.java
deleted file mode 100644
index cb2400a..0000000
--- a/v8/renderscript/java/src/android/support/v8/renderscript/ScriptGroup2.java
+++ /dev/null
@@ -1,460 +0,0 @@
-/*
- * Copyright (C) 2015 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- *      http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package android.support.v8.renderscript;
-
-import android.util.Log;
-import android.util.Pair;
-import java.util.ArrayList;
-import java.util.HashMap;
-import java.util.List;
-import java.util.Map;
-
-/**
-
-******************************
-You have tried to change the API from what has been previously approved.
-
-To make these errors go away, you have two choices:
-1) You can add "@hide" javadoc comments to the methods, etc. listed in the
-errors above.
-
-2) You can update current.txt by executing the following command:
-make update-api
-
-To submit the revised current.txt to the main Android repository,
-you will need approval.
-******************************
-
-@hide Pending Android public API approval.
-*/
-public class ScriptGroup2 extends BaseObj {
-    //FIXME: Change 23 to the codename when that is decided.
-    private static final int MIN_API_VERSION = 23;
-
-    public static class Closure extends BaseObj {
-        private Object[] mArgs;
-        private Allocation mReturnValue;
-        private Map<Script.FieldID, Object> mBindings;
-
-        private Future mReturnFuture;
-        private Map<Script.FieldID, Future> mGlobalFuture;
-
-        private FieldPacker mFP;
-
-        private static final String TAG = "Closure";
-
-        public Closure(long id, RenderScript rs) {
-            super(id, rs);
-        }
-
-        public Closure(RenderScript rs, Script.KernelID kernelID, Type returnType,
-                       Object[] args, Map<Script.FieldID, Object> globals) {
-            super(0, rs);
-
-            if (android.os.Build.VERSION.SDK_INT < MIN_API_VERSION && rs.isUseNative()) {
-                throw new RSRuntimeException("ScriptGroup2 not supported in this API level");
-            }
-
-            mArgs = args;
-            mReturnValue = Allocation.createTyped(rs, returnType);
-            mBindings = globals;
-            mGlobalFuture = new HashMap<Script.FieldID, Future>();
-
-            int numValues = args.length + globals.size();
-
-            long[] fieldIDs = new long[numValues];
-            long[] values = new long[numValues];
-            int[] sizes = new int[numValues];
-            long[] depClosures = new long[numValues];
-            long[] depFieldIDs = new long[numValues];
-
-            int i;
-            for (i = 0; i < args.length; i++) {
-                Object obj = args[i];
-                fieldIDs[i] = 0;
-                if (obj instanceof UnboundValue) {
-                    UnboundValue unbound = (UnboundValue)obj;
-                    unbound.addReference(this, i);
-                } else {
-                    retrieveValueAndDependenceInfo(rs, i, args[i], values, sizes,
-                                                   depClosures, depFieldIDs);
-                }
-            }
-
-            for (Map.Entry<Script.FieldID, Object> entry : globals.entrySet()) {
-                Object obj = entry.getValue();
-                Script.FieldID fieldID = entry.getKey();
-                fieldIDs[i] = fieldID.getID(rs);
-                if (obj instanceof UnboundValue) {
-                    UnboundValue unbound = (UnboundValue)obj;
-                    unbound.addReference(this, fieldID);
-                } else {
-                    retrieveValueAndDependenceInfo(rs, i, obj, values,
-                                                   sizes, depClosures, depFieldIDs);
-                }
-                i++;
-            }
-
-            long id = rs.nClosureCreate(kernelID.getID(rs), mReturnValue.getID(rs),
-                                        fieldIDs, values, sizes, depClosures, depFieldIDs);
-
-            setID(id);
-        }
-
-        public Closure(RenderScript rs, Script.InvokeID invokeID,
-                       Object[] args, Map<Script.FieldID, Object> globals) {
-            super(0, rs);
-
-            if (android.os.Build.VERSION.SDK_INT < MIN_API_VERSION && rs.isUseNative()) {
-                throw new RSRuntimeException("ScriptGroup2 not supported in this API level");
-            }
-
-            mFP = FieldPacker.createFieldPack(args);
-
-            mArgs = args;
-            mBindings = globals;
-            mGlobalFuture = new HashMap<Script.FieldID, Future>();
-
-            int numValues = globals.size();
-
-            long[] fieldIDs = new long[numValues];
-            long[] values = new long[numValues];
-            int[] sizes = new int[numValues];
-            long[] depClosures = new long[numValues];
-            long[] depFieldIDs = new long[numValues];
-
-            int i = 0;
-            for (Map.Entry<Script.FieldID, Object> entry : globals.entrySet()) {
-                Object obj = entry.getValue();
-                Script.FieldID fieldID = entry.getKey();
-                fieldIDs[i] = fieldID.getID(rs);
-                if (obj instanceof UnboundValue) {
-                    UnboundValue unbound = (UnboundValue)obj;
-                    unbound.addReference(this, fieldID);
-                } else {
-                    // TODO(yangni): Verify obj not a future.
-                    retrieveValueAndDependenceInfo(rs, i, obj, values,
-                                                   sizes, depClosures, depFieldIDs);
-                }
-                i++;
-            }
-
-            long id = rs.nInvokeClosureCreate(invokeID.getID(rs), mFP.getData(), fieldIDs,
-                                              values, sizes);
-
-            setID(id);
-        }
-
-        private static
-                void retrieveValueAndDependenceInfo(RenderScript rs,
-                                                    int index, Object obj,
-                                                    long[] values, int[] sizes,
-                                                    long[] depClosures,
-                                                    long[] depFieldIDs) {
-
-            if (obj instanceof Future) {
-                Future f = (Future)obj;
-                obj = f.getValue();
-                depClosures[index] = f.getClosure().getID(rs);
-                Script.FieldID fieldID = f.getFieldID();
-                depFieldIDs[index] = fieldID != null ? fieldID.getID(rs) : 0;
-                if (obj == null) {
-                    // Value is originally created by the owner closure
-                    values[index] = 0;
-                    sizes[index] = 0;
-                    return;
-                }
-            } else {
-                depClosures[index] = 0;
-                depFieldIDs[index] = 0;
-            }
-
-            ValueAndSize vs = new ValueAndSize(rs, obj);
-            values[index] = vs.value;
-            sizes[index] = vs.size;
-        }
-
-        public Future getReturn() {
-            if (mReturnFuture == null) {
-                mReturnFuture = new Future(this, null, mReturnValue);
-            }
-
-            return mReturnFuture;
-        }
-
-        public Future getGlobal(Script.FieldID field) {
-            Future f = mGlobalFuture.get(field);
-
-            if (f == null) {
-                // If the field is not bound to this closure, this will return a future
-                // without an associated value (reference). So this is not working for
-                // cross-module (cross-script) linking in this case where a field not
-                // explicitly bound.
-                f = new Future(this, field, mBindings.get(field));
-                mGlobalFuture.put(field, f);
-            }
-
-            return f;
-        }
-
-        void setArg(int index, Object obj) {
-            mArgs[index] = obj;
-            ValueAndSize vs = new ValueAndSize(mRS, obj);
-            mRS.nClosureSetArg(getID(mRS), index, vs.value, vs.size);
-        }
-
-        void setGlobal(Script.FieldID fieldID, Object obj) {
-            mBindings.put(fieldID, obj);
-            ValueAndSize vs = new ValueAndSize(mRS, obj);
-            mRS.nClosureSetGlobal(getID(mRS), fieldID.getID(mRS), vs.value, vs.size);
-        }
-
-        private static final class ValueAndSize {
-            public ValueAndSize(RenderScript rs, Object obj) {
-                if (obj instanceof Allocation) {
-                    value = ((Allocation)obj).getID(rs);
-                    size = -1;
-                } else if (obj instanceof Boolean) {
-                    value = ((Boolean)obj).booleanValue() ? 1 : 0;
-                    size = 4;
-                } else if (obj instanceof Integer) {
-                    value = ((Integer)obj).longValue();
-                    size = 4;
-                } else if (obj instanceof Long) {
-                    value = ((Long)obj).longValue();
-                    size = 8;
-                } else if (obj instanceof Float) {
-                    value = ((Float)obj).longValue();
-                    size = 4;
-                } else if (obj instanceof Double) {
-                    value = ((Double)obj).longValue();
-                    size = 8;
-                }
-            }
-            public long value;
-            public int size;
-        }
-    }
-
-    public static class Future {
-        Closure mClosure;
-        Script.FieldID mFieldID;
-        Object mValue;
-
-        Future(Closure closure, Script.FieldID fieldID, Object value) {
-            mClosure = closure;
-            mFieldID = fieldID;
-            mValue = value;
-        }
-
-        Closure getClosure() { return mClosure; }
-        Script.FieldID getFieldID() { return mFieldID; }
-        Object getValue() { return mValue; }
-    }
-
-    public static class UnboundValue {
-        // Either mFieldID or mArgIndex should be set but not both.
-        List<Pair<Closure, Script.FieldID>> mFieldID;
-        // -1 means unset. Legal values are 0 .. n-1, where n is the number of
-        // arguments for the referencing closure.
-        List<Pair<Closure, Integer>> mArgIndex;
-
-        UnboundValue() {
-            mFieldID = new ArrayList<Pair<Closure, Script.FieldID>>();
-            mArgIndex = new ArrayList<Pair<Closure, Integer>>();
-        }
-
-        void addReference(Closure closure, int index) {
-            mArgIndex.add(Pair.create(closure, Integer.valueOf(index)));
-        }
-
-        void addReference(Closure closure, Script.FieldID fieldID) {
-            mFieldID.add(Pair.create(closure, fieldID));
-        }
-
-        void set(Object value) {
-            for (Pair<Closure, Integer> p : mArgIndex) {
-                Closure closure = p.first;
-                int index = p.second.intValue();
-                closure.setArg(index, value);
-            }
-            for (Pair<Closure, Script.FieldID> p : mFieldID) {
-                Closure closure = p.first;
-                Script.FieldID fieldID = p.second;
-                closure.setGlobal(fieldID, value);
-            }
-        }
-    }
-
-    List<Closure> mClosures;
-    List<UnboundValue> mInputs;
-    Future[] mOutputs;
-
-    private static final String TAG = "ScriptGroup2";
-
-    public ScriptGroup2(long id, RenderScript rs) {
-        super(id, rs);
-    }
-
-    ScriptGroup2(RenderScript rs, List<Closure> closures,
-                 List<UnboundValue> inputs, Future[] outputs) {
-        super(0, rs);
-
-        if (android.os.Build.VERSION.SDK_INT < MIN_API_VERSION && rs.isUseNative()) {
-            throw new RSRuntimeException("ScriptGroup2 not supported in this API level");
-        }
-
-        mClosures = closures;
-        mInputs = inputs;
-        mOutputs = outputs;
-
-        long[] closureIDs = new long[closures.size()];
-        for (int i = 0; i < closureIDs.length; i++) {
-            closureIDs[i] = closures.get(i).getID(rs);
-        }
-        String cachePath = rs.getApplicationContext().getCacheDir().toString();
-        long id = rs.nScriptGroup2Create(cachePath, closureIDs);
-        setID(id);
-    }
-
-    public Object[] execute(Object... inputs) {
-        if (inputs.length < mInputs.size()) {
-            Log.e(TAG, this.toString() + " receives " + inputs.length + " inputs, " +
-                  "less than expected " + mInputs.size());
-            return null;
-        }
-
-        if (inputs.length > mInputs.size()) {
-            Log.i(TAG, this.toString() + " receives " + inputs.length + " inputs, " +
-                  "more than expected " + mInputs.size());
-        }
-
-        for (int i = 0; i < mInputs.size(); i++) {
-            Object obj = inputs[i];
-            if (obj instanceof Future || obj instanceof UnboundValue) {
-                Log.e(TAG, this.toString() + ": input " + i +
-                      " is a future or unbound value");
-                return null;
-            }
-            UnboundValue unbound = mInputs.get(i);
-            unbound.set(obj);
-        }
-
-        mRS.nScriptGroup2Execute(getID(mRS));
-
-        Object[] outputObjs = new Object[mOutputs.length];
-        int i = 0;
-        for (Future f : mOutputs) {
-            outputObjs[i++] = f.getValue();
-        }
-        return outputObjs;
-    }
-
-    /**
-       @hide Pending Android public API approval.
-    */
-    public static final class Binding {
-        public Script.FieldID mField;
-        public Object mValue;
-        public Binding(Script.FieldID field, Object value) {
-            mField = field;
-            mValue = value;
-        }
-    }
-
-    /**
-       @hide Pending Android public API approval.
-    */
-    public static final class Builder {
-        RenderScript mRS;
-        List<Closure> mClosures;
-        List<UnboundValue> mInputs;
-        private static final String TAG = "ScriptGroup2.Builder";
-
-        public Builder(RenderScript rs) {
-            mRS = rs;
-            mClosures = new ArrayList<Closure>();
-            mInputs = new ArrayList<UnboundValue>();
-        }
-
-        public Closure addKernel(Script.KernelID k, Type returnType, Object[] args,
-                                 Map<Script.FieldID, Object> globalBindings) {
-            Closure c = new Closure(mRS, k, returnType, args, globalBindings);
-            mClosures.add(c);
-            return c;
-        }
-
-        public Closure addInvoke(Script.InvokeID invoke, Object[] args,
-                                 Map<Script.FieldID, Object> globalBindings) {
-            Closure c = new Closure(mRS, invoke, args, globalBindings);
-            mClosures.add(c);
-            return c;
-        }
-
-        public UnboundValue addInput() {
-            UnboundValue unbound = new UnboundValue();
-            mInputs.add(unbound);
-            return unbound;
-        }
-
-        public Closure addKernel(Script.KernelID k, Type returnType, Object... argsAndBindings) {
-            ArrayList<Object> args = new ArrayList<Object>();
-            Map<Script.FieldID, Object> bindingMap = new HashMap<Script.FieldID, Object>();
-            if (!seperateArgsAndBindings(argsAndBindings, args, bindingMap)) {
-                return null;
-            }
-            return addKernel(k, returnType, args.toArray(), bindingMap);
-        }
-
-        public Closure addInvoke(Script.InvokeID invoke, Object... argsAndBindings) {
-            ArrayList<Object> args = new ArrayList<Object>();
-            Map<Script.FieldID, Object> bindingMap = new HashMap<Script.FieldID, Object>();
-            if (!seperateArgsAndBindings(argsAndBindings, args, bindingMap)) {
-                return null;
-            }
-            return addInvoke(invoke, args.toArray(), bindingMap);
-        }
-
-        public ScriptGroup2 create(Future... outputs) {
-            ScriptGroup2 ret = new ScriptGroup2(mRS, mClosures, mInputs, outputs);
-            return ret;
-        }
-
-        private boolean seperateArgsAndBindings(Object[] argsAndBindings,
-                                                ArrayList<Object> args,
-                                                Map<Script.FieldID, Object> bindingMap) {
-            int i;
-            for (i = 0; i < argsAndBindings.length; i++) {
-                if (argsAndBindings[i] instanceof Binding) {
-                    break;
-                }
-                args.add(argsAndBindings[i]);
-            }
-
-            for (; i < argsAndBindings.length; i++) {
-                if (!(argsAndBindings[i] instanceof Binding)) {
-                    return false;
-                }
-                Binding b = (Binding)argsAndBindings[i];
-                bindingMap.put(b.mField, b.mValue);
-            }
-
-            return true;
-        }
-
-    }
-}
diff --git a/v8/renderscript/java/src/android/support/v8/renderscript/ScriptIntrinsicHistogram.java b/v8/renderscript/java/src/android/support/v8/renderscript/ScriptIntrinsicHistogram.java
index 43ac015..3ed48f9 100644
--- a/v8/renderscript/java/src/android/support/v8/renderscript/ScriptIntrinsicHistogram.java
+++ b/v8/renderscript/java/src/android/support/v8/renderscript/ScriptIntrinsicHistogram.java
@@ -101,13 +101,11 @@
             throw new RSIllegalArgumentException(
                 "Input vector size must be >= output vector size.");
         }
-        if (mOut.getType().getElement().getVectorSize() == 3) {
-            throw new RSIllegalArgumentException(
-                "Output vector size should not be 3 for Input vector size 4.");
-        }
         if (!ain.getType().getElement().isCompatible(Element.U8(mRS)) &&
+            !ain.getType().getElement().isCompatible(Element.U8_2(mRS)) &&
+            !ain.getType().getElement().isCompatible(Element.U8_3(mRS)) &&
             !ain.getType().getElement().isCompatible(Element.U8_4(mRS))) {
-            throw new RSIllegalArgumentException("Output type must be U8 or U8_4.");
+            throw new RSIllegalArgumentException("Input type must be U8, U8_1, U8_2 or U8_4.");
         }
 
         forEach(0, ain, null, null, opt);
@@ -202,8 +200,10 @@
             throw new RSIllegalArgumentException("Output vector size must be one.");
         }
         if (!ain.getType().getElement().isCompatible(Element.U8(mRS)) &&
+            !ain.getType().getElement().isCompatible(Element.U8_2(mRS)) &&
+            !ain.getType().getElement().isCompatible(Element.U8_3(mRS)) &&
             !ain.getType().getElement().isCompatible(Element.U8_4(mRS))) {
-            throw new RSIllegalArgumentException("Output type must be U8 or U8_4.");
+            throw new RSIllegalArgumentException("Input type must be U8, U8_1, U8_2 or U8_4.");
         }
 
         forEach(1, ain, null, null, opt);
diff --git a/v8/renderscript/jni/android_renderscript_RenderScript.cpp b/v8/renderscript/jni/android_renderscript_RenderScript.cpp
index 0af0349..d22c502 100644
--- a/v8/renderscript/jni/android_renderscript_RenderScript.cpp
+++ b/v8/renderscript/jni/android_renderscript_RenderScript.cpp
@@ -435,8 +435,9 @@
 }
 
 static long
-nScriptGroup2Create(JNIEnv *_env, jobject _this, jlong con,
+nScriptGroup2Create(JNIEnv *_env, jobject _this, jlong con, jstring name,
                     jstring cacheDir, jlongArray closureArray) {
+  AutoJavaStringToUTF8 nameUTF(_env, name);
   AutoJavaStringToUTF8 cacheDirUTF(_env, cacheDir);
 
   jlong* jClosures = _env->GetLongArrayElements(closureArray, nullptr);
@@ -447,7 +448,8 @@
   }
 
   return (jlong)(uintptr_t)dispatchTab.ScriptGroup2Create(
-      (RsContext)con, cacheDirUTF.c_str(), cacheDirUTF.length(),
+      (RsContext)con, nameUTF.c_str(), nameUTF.length(),
+      cacheDirUTF.c_str(), cacheDirUTF.length(),
       closures, numClosures);
 }
 
@@ -1717,7 +1719,7 @@
 {"rsnScriptInvokeIDCreate",          "(JJI)J",                                (void*)nScriptInvokeIDCreate },
 {"rsnScriptFieldIDCreate",           "(JJIZ)J",                               (void*)nScriptFieldIDCreate },
 {"rsnScriptGroupCreate",             "(J[J[J[J[J[J)J",                        (void*)nScriptGroupCreate },
-{"rsnScriptGroup2Create",            "(JLjava/lang/String;[J)J",              (void*)nScriptGroup2Create },
+{"rsnScriptGroup2Create",            "(JLjava/lang/String;Ljava/lang/String;[J)J", (void*)nScriptGroup2Create },
 {"rsnScriptGroupSetInput",           "(JJJJ)V",                               (void*)nScriptGroupSetInput },
 {"rsnScriptGroupSetOutput",          "(JJJJ)V",                               (void*)nScriptGroupSetOutput },
 {"rsnScriptGroupExecute",            "(JJ)V",                                 (void*)nScriptGroupExecute },
diff --git a/v8/renderscript/rs_support/Android.mk b/v8/renderscript/rs_support/Android.mk
index 43952d5..75d2756 100644
--- a/v8/renderscript/rs_support/Android.mk
+++ b/v8/renderscript/rs_support/Android.mk
@@ -120,7 +120,6 @@
 	cpu_ref/rsCpuExecutable.cpp \
 	cpu_ref/rsCpuScript.cpp \
 	cpu_ref/rsCpuRuntimeMath.cpp \
-	cpu_ref/rsCpuRuntimeStubs.cpp \
 	cpu_ref/rsCpuScriptGroup.cpp \
 	cpu_ref/rsCpuScriptGroup2.cpp \
 	cpu_ref/rsCpuIntrinsic.cpp \
@@ -147,6 +146,7 @@
         cpu_ref/rsCpuIntrinsics_neon_Blend.S \
         cpu_ref/rsCpuIntrinsics_neon_Blur.S \
 	cpu_ref/rsCpuIntrinsics_neon_Convolve.S \
+	cpu_ref/rsCpuIntrinsics_neon_Resize.S \
         cpu_ref/rsCpuIntrinsics_neon_YuvToRGB.S
 endif
 
