Matrix, fixed function, surface config tests.

Change-Id: I3f1f6a1d527b252fa9daf92e58f22001252676c1
diff --git a/tests/assets/sphere.a3d b/tests/assets/sphere.a3d
new file mode 100644
index 0000000..3d78b01
--- /dev/null
+++ b/tests/assets/sphere.a3d
Binary files differ
diff --git a/tests/res/raw/samplefont.ttf b/tests/res/raw/samplefont.ttf
new file mode 100644
index 0000000..49f1c62
--- /dev/null
+++ b/tests/res/raw/samplefont.ttf
Binary files differ
diff --git a/tests/tests/renderscript/src/android/renderscript/cts/ExceptionTest.java b/tests/tests/renderscript/src/android/renderscript/cts/ExceptionTest.java
index 5a24245..3a9df46 100644
--- a/tests/tests/renderscript/src/android/renderscript/cts/ExceptionTest.java
+++ b/tests/tests/renderscript/src/android/renderscript/cts/ExceptionTest.java
@@ -19,6 +19,7 @@
 import android.renderscript.RSIllegalArgumentException;
 import android.renderscript.RSInvalidStateException;
 import android.renderscript.RSRuntimeException;
+import android.renderscript.RSDriverException;
 
 import android.test.AndroidTestCase;
 
@@ -41,5 +42,11 @@
         } catch (RSRuntimeException e) {
             assertEquals(e.getMessage(), "RE");
         }
+
+        try {
+            throw new RSDriverException("DE");
+        } catch (RSDriverException e) {
+            assertEquals(e.getMessage(), "DE");
+        }
     }
 }
diff --git a/tests/tests/renderscript/src/android/renderscript/cts/FileA3DTest.java b/tests/tests/renderscript/src/android/renderscript/cts/FileA3DTest.java
index bc14953..ccd7d9d 100644
--- a/tests/tests/renderscript/src/android/renderscript/cts/FileA3DTest.java
+++ b/tests/tests/renderscript/src/android/renderscript/cts/FileA3DTest.java
@@ -29,6 +29,11 @@
         assertTrue(model != null);
     }
 
+    public void testCreateFromAsset() {
+        FileA3D model = FileA3D.createFromAsset(mRS, mRes.getAssets(), "sphere.a3d");
+        assertTrue(model != null);
+    }
+
     public void testGetIndexEntryCount() {
         FileA3D model = FileA3D.createFromResource(mRS, mRes, R.raw.sphere);
         assertTrue(model != null);
diff --git a/tests/tests/renderscript/src/android/renderscript/cts/FontTest.java b/tests/tests/renderscript/src/android/renderscript/cts/FontTest.java
index 2e212e2..e2405e8 100644
--- a/tests/tests/renderscript/src/android/renderscript/cts/FontTest.java
+++ b/tests/tests/renderscript/src/android/renderscript/cts/FontTest.java
@@ -17,6 +17,7 @@
 package android.renderscript.cts;
 
 import java.io.File;
+import com.android.cts.stub.R;
 
 import android.os.Environment;
 import android.renderscript.Font;
@@ -83,5 +84,9 @@
         // Make sure no new enums are added
         assertEquals(4, Font.Style.values().length);
     }
+
+    public void testCreateFromResource() {
+        assertTrue(Font.createFromResource(mRS, mRes, R.raw.samplefont, 8) != null);
+    }
 }
 
diff --git a/tests/tests/renderscript/src/android/renderscript/cts/Matrix2fTest.java b/tests/tests/renderscript/src/android/renderscript/cts/Matrix2fTest.java
new file mode 100755
index 0000000..1daa83a
--- /dev/null
+++ b/tests/tests/renderscript/src/android/renderscript/cts/Matrix2fTest.java
@@ -0,0 +1,180 @@
+/*
+ * Copyright (C) 2011 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.renderscript.cts;
+import android.renderscript.Matrix2f;
+
+public class Matrix2fTest extends RSBaseCompute {
+
+    final float delta = 0.00001f;
+    final float[] setData = {
+            1.0f, 2.0f,
+            3.0f, 4.0f
+        };
+
+    void checkIdentity(Matrix2f m, float delta) {
+        for (int i = 0; i < 2; i ++) {
+            for (int j = 0; j < 2; j ++) {
+                if (i == j) {
+                    assertEquals(1.0f, m.getArray()[i*2 + j], delta);
+                } else {
+                    assertEquals(0.0f, m.getArray()[i*2 + j], delta);
+                }
+            }
+        }
+    }
+
+    String getString(float[] array) {
+        StringBuilder builder = new StringBuilder();
+        for (int i = 0; i < 2; i ++) {
+            builder.append("[");
+            for (int j = 0; j < 2; j ++) {
+                builder.append(array[i*2 + j]);
+                builder.append(" ");
+            }
+            builder.append("]");
+        }
+        return builder.toString();
+    }
+
+    void checkData(Matrix2f m, float[] data, float delta) {
+        for (int i = 0; i < data.length; i ++) {
+            assertEquals(data[i], m.getArray()[i], delta);
+        }
+    }
+
+    void checkData(Matrix2f m, float[] data) {
+        String s1 = getString(m.getArray());
+        String s2 = getString(data);
+        assertEquals(s2, s1);
+    }
+
+    public void testCreation() {
+        Matrix2f m = new Matrix2f();
+        assertTrue(m.getArray() != null);
+        checkIdentity(m, 0.0f);
+
+        m = new Matrix2f(setData);
+        checkData(m, setData);
+    }
+
+    public void testGet() {
+
+        Matrix2f m = new Matrix2f(setData);
+
+        for (int i = 0; i < 2; i ++) {
+            for (int j = 0; j < 2; j ++) {
+                assertEquals(setData[i*2 + j], m.get(i, j), 0.0f);
+            }
+        }
+    }
+
+    public void testSet() {
+        Matrix2f m = new Matrix2f();
+        for (int i = 0; i < 2; i ++) {
+            for (int j = 0; j < 2; j ++) {
+                float valToSet = setData[i*2 + j];
+                m.set(i, j, valToSet);
+                assertEquals(valToSet, m.get(i, j), 0.0f);
+            }
+        }
+    }
+
+    public void testLoadIdentity() {
+        Matrix2f m = new Matrix2f(setData);
+        m.loadIdentity();
+        checkIdentity(m, 0.0f);
+    }
+
+    public void testLoad() {
+        Matrix2f m1 = new Matrix2f();
+        Matrix2f m2 = new Matrix2f(setData);
+
+        m1.load(m2);
+        checkData(m1, setData);
+    }
+
+    public void testLoadScale() {
+        float[] expectedData = {
+            2.0f, 0.0f,
+            0.0f, 3.0f
+        };
+
+        Matrix2f m = new Matrix2f(setData);
+        m.loadScale(2.0f, 3.0f);
+        checkData(m, expectedData);
+    }
+
+    public void testMultiply() {
+        float[] lhsData = {
+            1.0f, 1.0f,
+            1.0f, 1.0f
+        };
+
+        float[] rhsData = {
+            2.0f, 2.0f,
+            3.0f, 3.0f
+        };
+
+        float[] expected = {
+            2.0f*2.0f, 2.0f*2.0f,
+            2.0f*3.0f, 2.0f*3.0f
+        };
+
+        // Due to column major nature of OpenGL,
+        // left hand side and right hand side
+        // are reversed. Premultiplying by row major
+        // and post multiplying by column major
+        // are the same. So lhs and rhs get reversed here.
+        Matrix2f lhs = new Matrix2f(lhsData);
+        Matrix2f rhs = new Matrix2f(rhsData);
+        Matrix2f loadMul = new Matrix2f();
+
+        loadMul.loadMultiply(lhs, rhs);
+        checkData(loadMul, expected);
+
+        lhs.multiply(rhs);
+        checkData(lhs, expected);
+    }
+
+    public void testScale() {
+        float[] expectedData = new float[setData.length];
+        System.arraycopy(setData, 0, expectedData, 0, setData.length);
+        float scaleX = 2.0f;
+        float scaleY = 3.0f;
+        expectedData[0] *= scaleX;
+        expectedData[1] *= scaleX;
+        expectedData[2] *= scaleY;
+        expectedData[3] *= scaleY;
+
+        Matrix2f m = new Matrix2f(setData);
+        m.scale(scaleX, scaleY);
+        checkData(m, expectedData);
+    }
+
+    public void testTranspose() {
+        float[] expectedData = new float[setData.length];
+        System.arraycopy(setData, 0, expectedData, 0, setData.length);
+        float temp = expectedData[1];
+        expectedData[1] = expectedData[2];
+        expectedData[2] = temp;
+
+        Matrix2f m = new Matrix2f(setData);
+        m.transpose();
+
+        checkData(m, expectedData);
+    }
+}
diff --git a/tests/tests/renderscript/src/android/renderscript/cts/Matrix3fTest.java b/tests/tests/renderscript/src/android/renderscript/cts/Matrix3fTest.java
new file mode 100755
index 0000000..f817cab
--- /dev/null
+++ b/tests/tests/renderscript/src/android/renderscript/cts/Matrix3fTest.java
@@ -0,0 +1,229 @@
+/*
+ * Copyright (C) 2011 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.renderscript.cts;
+import android.renderscript.Matrix3f;
+
+public class Matrix3fTest extends RSBaseCompute {
+
+    final float delta = 0.00001f;
+    final float[] setData = {
+            1.0f, 2.0f, 3.0f,
+            4.0f, 5.0f, 6.0f,
+            7.0f, 8.0f, 9.0f
+        };
+
+    void checkIdentity(Matrix3f m, float delta) {
+        for (int i = 0; i < 3; i ++) {
+            for (int j = 0; j < 3; j ++) {
+                if (i == j) {
+                    assertEquals(1.0f, m.getArray()[i*3 + j], delta);
+                } else {
+                    assertEquals(0.0f, m.getArray()[i*3 + j], delta);
+                }
+            }
+        }
+    }
+
+    String getString(float[] array) {
+        StringBuilder builder = new StringBuilder();
+        for (int i = 0; i < 3; i ++) {
+            builder.append("[");
+            for (int j = 0; j < 3; j ++) {
+                builder.append(array[i*3 + j]);
+                builder.append(" ");
+            }
+            builder.append("]");
+        }
+        return builder.toString();
+    }
+
+    void checkData(Matrix3f m, float[] data, float delta) {
+        for (int i = 0; i < data.length; i ++) {
+            assertEquals(data[i], m.getArray()[i], delta);
+        }
+    }
+
+    void checkData(Matrix3f m, float[] data) {
+        String s1 = getString(m.getArray());
+        String s2 = getString(data);
+        assertEquals(s2, s1);
+    }
+
+    public void testCreation() {
+        Matrix3f m = new Matrix3f();
+        assertTrue(m.getArray() != null);
+        checkIdentity(m, 0.0f);
+
+        m = new Matrix3f(setData);
+        checkData(m, setData);
+    }
+
+    public void testGet() {
+
+        Matrix3f m = new Matrix3f(setData);
+
+        for (int i = 0; i < 3; i ++) {
+            for (int j = 0; j < 3; j ++) {
+                assertEquals(setData[i*3 + j], m.get(i, j), 0.0f);
+            }
+        }
+    }
+
+    public void testSet() {
+        Matrix3f m = new Matrix3f();
+        for (int i = 0; i < 3; i ++) {
+            for (int j = 0; j < 3; j ++) {
+                float valToSet = setData[i*3 + j];
+                m.set(i, j, valToSet);
+                assertEquals(valToSet, m.get(i, j), 0.0f);
+            }
+        }
+    }
+
+    public void testLoadIdentity() {
+        Matrix3f m = new Matrix3f(setData);
+        m.loadIdentity();
+        checkIdentity(m, 0.0f);
+    }
+
+    public void testLoad() {
+        Matrix3f m1 = new Matrix3f();
+        Matrix3f m2 = new Matrix3f(setData);
+
+        m1.load(m2);
+        checkData(m1, setData);
+    }
+
+    public void testLoadScale() {
+        float[] expectedData = {
+            2.0f, 0.0f, 0.0f,
+            0.0f, 3.0f, 0.0f,
+            0.0f, 0.0f, 4.0f,
+        };
+        float[] expectedData2 = {
+            2.0f, 0.0f, 0.0f,
+            0.0f, 3.0f, 0.0f,
+            0.0f, 0.0f, 1.0f,
+        };
+
+        Matrix3f m = new Matrix3f(setData);
+        m.loadScale(2.0f, 3.0f, 4.0f);
+        checkData(m, expectedData);
+
+        m = new Matrix3f(setData);
+        m.loadScale(2.0f, 3.0f);
+        checkData(m, expectedData2);
+    }
+
+    public void testLoadTranslate() {
+        float[] expectedData = {
+            1.0f, 0.0f, 0.0f,
+            0.0f, 1.0f, 0.0f,
+            2.0f, 3.0f, 1.0f,
+        };
+
+        Matrix3f m = new Matrix3f(setData);
+        m.loadTranslate(2.0f, 3.0f);
+        checkData(m, expectedData);
+    }
+
+    public void testScale() {
+        float[] expectedData = new float[setData.length];
+        System.arraycopy(setData, 0, expectedData, 0, setData.length);
+        float scaleX = 2.0f;
+        float scaleY = 3.0f;
+        float scaleZ = 4.0f;
+        expectedData[0] *= scaleX;
+        expectedData[1] *= scaleX;
+        expectedData[2] *= scaleX;
+        expectedData[3] *= scaleY;
+        expectedData[4] *= scaleY;
+        expectedData[5] *= scaleY;
+        expectedData[6] *= scaleZ;
+        expectedData[7] *= scaleZ;
+        expectedData[8] *= scaleZ;
+
+        Matrix3f m = new Matrix3f(setData);
+        m.scale(scaleX, scaleY, scaleZ);
+        checkData(m, expectedData);
+
+        System.arraycopy(setData, 0, expectedData, 0, setData.length);
+        expectedData[0] *= scaleX;
+        expectedData[1] *= scaleX;
+        expectedData[2] *= scaleX;
+        expectedData[3] *= scaleY;
+        expectedData[4] *= scaleY;
+        expectedData[5] *= scaleY;
+
+        m = new Matrix3f(setData);
+        m.scale(scaleX, scaleY);
+        checkData(m, expectedData);
+    }
+
+    public void testMultiply() {
+        float[] lhsData = {
+            1.0f, 1.0f, 1.0f,
+            1.0f, 1.0f, 1.0f,
+            1.0f, 1.0f, 1.0f
+        };
+
+        float[] rhsData = {
+            2.0f, 2.0f, 2.0f,
+            3.0f, 3.0f, 3.0f,
+            4.0f, 4.0f, 4.0f
+        };
+
+        float[] expected = {
+            3.0f*2.0f, 3.0f*2.0f, 3.0f*2.0f,
+            3.0f*3.0f, 3.0f*3.0f, 3.0f*3.0f,
+            3.0f*4.0f, 3.0f*4.0f, 3.0f*4.0f
+        };
+
+        // Due to column major nature of OpenGL,
+        // left hand side and right hand side
+        // are reversed. Premultiplying by row major
+        // and post multiplying by column major
+        // are the same. So lhs and rhs get reversed here.
+        Matrix3f lhs = new Matrix3f(lhsData);
+        Matrix3f rhs = new Matrix3f(rhsData);
+        Matrix3f loadMul = new Matrix3f();
+
+        loadMul.loadMultiply(lhs, rhs);
+        checkData(loadMul, expected);
+
+        lhs.multiply(rhs);
+        checkData(lhs, expected);
+    }
+
+    public void testTranspose() {
+        float[] expectedData = new float[setData.length];
+        System.arraycopy(setData, 0, expectedData, 0, setData.length);
+
+        for(int i = 0; i < 2; i++) {
+            for(int j = i + 1; j < 3; j++) {
+                float temp = expectedData[i*3 + j];
+                expectedData[i*3 + j] = expectedData[j*3 + i];
+                expectedData[j*3 + i] = temp;
+            }
+        }
+
+        Matrix3f m = new Matrix3f(setData);
+        m.transpose();
+
+        checkData(m, expectedData);
+    }
+}
diff --git a/tests/tests/renderscript/src/android/renderscript/cts/Matrix4fTest.java b/tests/tests/renderscript/src/android/renderscript/cts/Matrix4fTest.java
new file mode 100755
index 0000000..8678578
--- /dev/null
+++ b/tests/tests/renderscript/src/android/renderscript/cts/Matrix4fTest.java
@@ -0,0 +1,233 @@
+/*
+ * Copyright (C) 2011 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.renderscript.cts;
+import android.renderscript.Matrix4f;
+
+public class Matrix4fTest extends RSBaseCompute {
+
+    final float delta = 0.00001f;
+    final float[] setData = {
+            1.0f, 2.0f, 3.0f, 4.0f,
+            5.0f, 6.0f, 7.0f, 8.0f,
+            9.0f, 10.0f, 11.0f, 12.0f,
+            13.0f, 14.0f, 15.0f, 16.0f
+        };
+
+    void checkIdentity(Matrix4f m, float delta) {
+        for (int i = 0; i < 4; i ++) {
+            for (int j = 0; j < 4; j ++) {
+                if (i == j) {
+                    assertEquals(1.0f, m.getArray()[i*4 + j], delta);
+                } else {
+                    assertEquals(0.0f, m.getArray()[i*4 + j], delta);
+                }
+            }
+        }
+    }
+
+    String getString(float[] array) {
+        StringBuilder builder = new StringBuilder();
+        for (int i = 0; i < 4; i ++) {
+            builder.append("[");
+            for (int j = 0; j < 4; j ++) {
+                builder.append(array[i*4 + j]);
+                builder.append(" ");
+            }
+            builder.append("]");
+        }
+        return builder.toString();
+    }
+
+    void checkData(Matrix4f m, float[] data, float delta) {
+        for (int i = 0; i < data.length; i ++) {
+            assertEquals(data[i], m.getArray()[i], delta);
+        }
+    }
+
+    void checkData(Matrix4f m, float[] data) {
+        String s1 = getString(m.getArray());
+        String s2 = getString(data);
+        assertEquals(s2, s1);
+    }
+
+    public void testCreation() {
+        Matrix4f m = new Matrix4f();
+        assertTrue(m.getArray() != null);
+        checkIdentity(m, 0.0f);
+
+
+        m = new Matrix4f(setData);
+        checkData(m, setData);
+    }
+
+    public void testGet() {
+
+        Matrix4f m = new Matrix4f(setData);
+
+        for (int i = 0; i < 4; i ++) {
+            for (int j = 0; j < 4; j ++) {
+                assertEquals(setData[i*4 + j], m.get(i, j), 0.0f);
+            }
+        }
+    }
+
+    public void testSet() {
+        Matrix4f m = new Matrix4f();
+        for (int i = 0; i < 4; i ++) {
+            for (int j = 0; j < 4; j ++) {
+                float valToSet = setData[i*4 + j];
+                m.set(i, j, valToSet);
+                assertEquals(valToSet, m.get(i, j), 0.0f);
+            }
+        }
+    }
+
+    public void testLoadIdentity() {
+        Matrix4f m = new Matrix4f(setData);
+        m.loadIdentity();
+        checkIdentity(m, 0.0f);
+    }
+
+    public void testLoad() {
+        Matrix4f m1 = new Matrix4f();
+        Matrix4f m2 = new Matrix4f(setData);
+
+        m1.load(m2);
+        checkData(m1, setData);
+    }
+
+    public void testLoadScale() {
+        float[] expectedData = {
+            2.0f, 0.0f, 0.0f, 0.0f,
+            0.0f, 3.0f, 0.0f, 0.0f,
+            0.0f, 0.0f, 4.0f, 0.0f,
+            0.0f, 0.0f, 0.0f, 1.0f
+        };
+
+        Matrix4f m = new Matrix4f(setData);
+        m.loadScale(2.0f, 3.0f, 4.0f);
+        checkData(m, expectedData);
+    }
+
+    public void testLoadTranslate() {
+        float[] expectedData = {
+            1.0f, 0.0f, 0.0f, 0.0f,
+            0.0f, 1.0f, 0.0f, 0.0f,
+            0.0f, 0.0f, 1.0f, 0.0f,
+            2.0f, 3.0f, 4.0f, 1.0f
+        };
+
+        Matrix4f m = new Matrix4f(setData);
+        m.loadTranslate(2.0f, 3.0f, 4.0f);
+        checkData(m, expectedData);
+    }
+
+    public void testScale() {
+        float[] expectedData = new float[setData.length];
+        System.arraycopy(setData, 0, expectedData, 0, setData.length);
+        float scaleX = 2.0f;
+        float scaleY = 3.0f;
+        float scaleZ = 4.0f;
+        expectedData[0] *= scaleX;
+        expectedData[1] *= scaleX;
+        expectedData[2] *= scaleX;
+        expectedData[3] *= scaleX;
+        expectedData[4] *= scaleY;
+        expectedData[5] *= scaleY;
+        expectedData[6] *= scaleY;
+        expectedData[7] *= scaleY;
+        expectedData[8] *= scaleZ;
+        expectedData[9] *= scaleZ;
+        expectedData[10] *= scaleZ;
+        expectedData[11] *= scaleZ;
+
+        Matrix4f m = new Matrix4f(setData);
+        m.scale(scaleX, scaleY, scaleZ);
+        checkData(m, expectedData);
+    }
+
+    public void testTranspose() {
+        float[] expectedData = new float[setData.length];
+        System.arraycopy(setData, 0, expectedData, 0, setData.length);
+
+        for(int i = 0; i < 3; i++) {
+            for(int j = i + 1; j < 4; j++) {
+                float temp = expectedData[i*4 + j];
+                expectedData[i*4 + j] = expectedData[j*4 + i];
+                expectedData[j*4 + i] = temp;
+            }
+        }
+
+        Matrix4f m = new Matrix4f(setData);
+        m.transpose();
+
+        checkData(m, expectedData);
+    }
+
+    public void testMultiply() {
+        float[] lhsData = {
+            1.0f, 1.0f, 1.0f, 1.0f,
+            1.0f, 1.0f, 1.0f, 1.0f,
+            1.0f, 1.0f, 1.0f, 1.0f,
+            1.0f, 1.0f, 1.0f, 1.0f
+        };
+
+        float[] rhsData = {
+            2.0f, 2.0f, 2.0f, 2.0f,
+            3.0f, 3.0f, 3.0f, 3.0f,
+            4.0f, 4.0f, 4.0f, 4.0f,
+            5.0f, 5.0f, 5.0f, 5.0f
+        };
+
+        float[] expected = {
+            4.0f*2.0f, 4.0f*2.0f, 4.0f*2.0f, 4.0f*2.0f,
+            4.0f*3.0f, 4.0f*3.0f, 4.0f*3.0f, 4.0f*3.0f,
+            4.0f*4.0f, 4.0f*4.0f, 4.0f*4.0f, 4.0f*4.0f,
+            4.0f*5.0f, 4.0f*5.0f, 4.0f*5.0f, 4.0f*5.0f
+        };
+
+        // Due to column major nature of OpenGL,
+        // left hand side and right hand side
+        // are reversed. Premultiplying by row major
+        // and post multiplying by column major
+        // are the same. So lhs and rhs get reversed here.
+        Matrix4f lhs = new Matrix4f(lhsData);
+        Matrix4f rhs = new Matrix4f(rhsData);
+        Matrix4f loadMul = new Matrix4f();
+
+        loadMul.loadMultiply(lhs, rhs);
+        checkData(loadMul, expected);
+
+        lhs.multiply(rhs);
+        checkData(lhs, expected);
+    }
+
+    public void testInverse() {
+        Matrix4f m = new Matrix4f();
+        assertTrue(m.inverse());
+        checkIdentity(m, delta);
+
+        m = new Matrix4f();
+        m.scale(2.0f, 2.0f, 2.0f);
+        m.translate(5.0f, 6.0f, 7.0f);
+
+        Matrix4f m2 = new Matrix4f(m.getArray());
+        assertTrue(m2.inverse());
+        m.multiply(m2);
+        checkIdentity(m, delta);
+    }
+}
diff --git a/tests/tests/renderscript/src/android/renderscript/cts/ProgramFragmentFixedFunctionTest.java b/tests/tests/renderscript/src/android/renderscript/cts/ProgramFragmentFixedFunctionTest.java
new file mode 100644
index 0000000..ac54b74
--- /dev/null
+++ b/tests/tests/renderscript/src/android/renderscript/cts/ProgramFragmentFixedFunctionTest.java
@@ -0,0 +1,110 @@
+/*
+ * Copyright (C) 2011 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.renderscript.cts;
+
+import com.android.cts.stub.R;
+import android.renderscript.Element;
+import android.renderscript.Type;
+import android.renderscript.Allocation;
+import android.renderscript.Sampler;
+import android.renderscript.ProgramFragment;
+import android.renderscript.ProgramFragmentFixedFunction;
+import android.renderscript.ProgramFragmentFixedFunction.Builder;
+
+public class ProgramFragmentFixedFunctionTest extends RSBaseGraphics {
+
+    ScriptC_graphics_runner mScript;
+
+    Allocation mTex2D;
+
+    @Override
+    protected void setUp() throws Exception {
+        super.setUp();
+
+        Type.Builder typeB = new Type.Builder(mRS, Element.RGB_888(mRS));
+        typeB.setX(8).setY(8);
+        mTex2D = Allocation.createTyped(mRS, typeB.create(),
+                                        Allocation.USAGE_SCRIPT |
+                                        Allocation.USAGE_GRAPHICS_TEXTURE);
+
+        mScript = new ScriptC_graphics_runner(mRS, mRes, R.raw.graphics_runner);
+        mRS.bindRootScript(mScript);
+    }
+
+    @Override
+    protected void tearDown() throws Exception {
+        mRS.bindRootScript(null);
+        super.tearDown();
+    }
+
+    void testProgramFragmentFixedFunctionBuilder(boolean testBind) {
+        ProgramFragmentFixedFunction.Builder b;
+        for (int tCount = 0; tCount <= Builder.MAX_TEXTURE; tCount ++) {
+            for (int varC = 0; varC <= 1; varC++) {
+                for (int pSprite = 0; pSprite <= 1; pSprite++) {
+                    for (Builder.EnvMode env : Builder.EnvMode.values()) {
+                        for (Builder.Format format : Builder.Format.values()) {
+                            b = new ProgramFragmentFixedFunction.Builder(mRS);
+                            b.setVaryingColor(varC == 1);
+                            b.setPointSpriteTexCoordinateReplacement(pSprite == 1);
+                            for (int t = 0; t < tCount; t++) {
+                                b.setTexture(env, format, t);
+                            }
+
+                            ProgramFragment pf = b.create();
+                            assertTrue(pf != null);
+                            for (int t = 0; t < tCount; t++) {
+                                pf.bindTexture(mTex2D, t);
+                                pf.bindSampler(Sampler.CLAMP_NEAREST(mRS), t);
+                            }
+                            if (testBind) {
+                                mScript.invoke_testProgramFragment(pf);
+                            }
+                        }
+                    }
+                }
+            }
+        }
+    }
+
+    public void testProgramFragmentFixedFunctionBuilder() {
+        testProgramFragmentFixedFunctionBuilder(false);
+        testProgramFragmentFixedFunctionBuilder(true);
+    }
+
+    public void testBuilderEnvMode() {
+        assertEquals(Builder.EnvMode.DECAL, Builder.EnvMode.valueOf("DECAL"));
+        assertEquals(Builder.EnvMode.MODULATE, Builder.EnvMode.valueOf("MODULATE"));
+        assertEquals(Builder.EnvMode.REPLACE, Builder.EnvMode.valueOf("REPLACE"));
+
+        // Make sure no new enums are added
+        assertEquals(3, Builder.EnvMode.values().length);
+    }
+
+    public void testBuilderFormat() {
+        assertEquals(Builder.Format.ALPHA, Builder.Format.valueOf("ALPHA"));
+        assertEquals(Builder.Format.LUMINANCE_ALPHA, Builder.Format.valueOf("LUMINANCE_ALPHA"));
+        assertEquals(Builder.Format.RGB, Builder.Format.valueOf("RGB"));
+        assertEquals(Builder.Format.RGBA, Builder.Format.valueOf("RGBA"));
+
+        // Make sure no new enums are added
+        assertEquals(4, Builder.Format.values().length);
+    }
+
+}
+
+
diff --git a/tests/tests/renderscript/src/android/renderscript/cts/ProgramFragmentTest.java b/tests/tests/renderscript/src/android/renderscript/cts/ProgramFragmentTest.java
index 00e9a9f..d6a7f0d 100644
--- a/tests/tests/renderscript/src/android/renderscript/cts/ProgramFragmentTest.java
+++ b/tests/tests/renderscript/src/android/renderscript/cts/ProgramFragmentTest.java
@@ -166,12 +166,14 @@
         pf = buildShader(null, constInput, simpleUni);
         if (testBind) {
             mScript.invoke_testProgramFragment(pf);
+            mRS.bindProgramFragment(pf);
         }
 
         constInput[0] = mConstComplex;
         pf = buildShader(null, constInput, multiUni);
         if (testBind) {
             mScript.invoke_testProgramFragment(pf);
+            mRS.bindProgramFragment(pf);
         }
 
         Allocation[] textures = new Allocation[2];
@@ -180,6 +182,7 @@
         pf = buildShader(textures, constInput, simpleUniTex);
         if (testBind) {
             mScript.invoke_testProgramFragment(pf);
+            mRS.bindProgramFragment(pf);
         }
 
         constInput = new Allocation[2];
@@ -188,6 +191,7 @@
         pf = buildShader(null, constInput, multiUni);
         if (testBind) {
             mScript.invoke_testProgramFragment(pf);
+            mRS.bindProgramFragment(pf);
         }
     }
 
diff --git a/tests/tests/renderscript/src/android/renderscript/cts/ProgramRasterTest.java b/tests/tests/renderscript/src/android/renderscript/cts/ProgramRasterTest.java
index 98644af..befa926 100644
--- a/tests/tests/renderscript/src/android/renderscript/cts/ProgramRasterTest.java
+++ b/tests/tests/renderscript/src/android/renderscript/cts/ProgramRasterTest.java
@@ -29,7 +29,9 @@
             b.setPointSpriteEnabled(pSprite);
             for (CullMode cull : CullMode.values()) {
                 b.setCullMode(cull);
-                b.create();
+                ProgramRaster pr = b.create();
+                assertTrue(pr != null);
+                mRS.bindProgramRaster(pr);
             }
         }
     }
@@ -48,5 +50,3 @@
         assertEquals(3, CullMode.values().length);
     }
 }
-
-
diff --git a/tests/tests/renderscript/src/android/renderscript/cts/ProgramStoreTest.java b/tests/tests/renderscript/src/android/renderscript/cts/ProgramStoreTest.java
index a78a7d1..b7f5eff 100644
--- a/tests/tests/renderscript/src/android/renderscript/cts/ProgramStoreTest.java
+++ b/tests/tests/renderscript/src/android/renderscript/cts/ProgramStoreTest.java
@@ -36,7 +36,9 @@
                             boolean isDither = (dither == 1);
                             pb.setDitherEnabled(isDither);
                             pb.setColorMaskEnabled(isR, isG, isB, isA);
-                            pb.create();
+                            ProgramStore ps = pb.create();
+                            assertTrue(ps != null);
+                            mRS.bindProgramStore(ps);
                         }
                     }
                 }
diff --git a/tests/tests/renderscript/src/android/renderscript/cts/ProgramVertexFixedFunctionTest.java b/tests/tests/renderscript/src/android/renderscript/cts/ProgramVertexFixedFunctionTest.java
new file mode 100644
index 0000000..0adab9a
--- /dev/null
+++ b/tests/tests/renderscript/src/android/renderscript/cts/ProgramVertexFixedFunctionTest.java
@@ -0,0 +1,93 @@
+/*
+ * Copyright (C) 2011 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.renderscript.cts;
+
+import com.android.cts.stub.R;
+
+import android.renderscript.ProgramVertexFixedFunction;
+import android.renderscript.ProgramVertexFixedFunction.Builder;
+import android.renderscript.ScriptC;
+import android.renderscript.Matrix4f;
+
+public class ProgramVertexFixedFunctionTest extends RSBaseGraphics {
+
+    ScriptC_graphics_runner mScript;
+
+    @Override
+    protected void setUp() throws Exception {
+        super.setUp();
+        mScript = new ScriptC_graphics_runner(mRS, mRes, R.raw.graphics_runner);
+        mRS.bindRootScript(mScript);
+    }
+
+    @Override
+    protected void tearDown() throws Exception {
+        mRS.bindRootScript(null);
+        super.tearDown();
+    }
+
+    public void testConstants() {
+        ProgramVertexFixedFunction.Constants pva;
+        for (int isM = 0; isM <= 1; isM++) {
+            for (int isP = 0; isP <= 1; isP++) {
+                for (int isT = 0; isT <= 1; isT++) {
+                    pva = new ProgramVertexFixedFunction.Constants(mRS);
+                    if (isM == 1) {
+                        pva.setModelview(new Matrix4f());
+                    }
+                    if (isP == 1) {
+                        pva.setProjection(new Matrix4f());
+                    }
+                    if (isT == 1) {
+                        pva.setTexture(new Matrix4f());
+                    }
+                    pva.destroy();
+                }
+            }
+        }
+    }
+
+    void testProgramVertexFixedFunctionBuilder(boolean testBind) {
+        ProgramVertexFixedFunction.Constants pva;
+        pva = new ProgramVertexFixedFunction.Constants(mRS);
+
+        ProgramVertexFixedFunction.Builder b;
+        b = new ProgramVertexFixedFunction.Builder(mRS);
+        b.setTextureMatrixEnable(false);
+        ProgramVertexFixedFunction pv = b.create();
+        assertTrue(pv != null);
+        pv.bindConstants(pva);
+        if (testBind) {
+            mScript.invoke_testProgramVertex(pv);
+        }
+        pv.destroy();
+        b.setTextureMatrixEnable(true);
+        pv = b.create();
+        assertTrue(pv != null);
+        pv.bindConstants(pva);
+        if (testBind) {
+            mScript.invoke_testProgramVertex(pv);
+        }
+        pv.destroy();
+    }
+
+    public void testProgramVertexFixedFunctionBuilder() {
+        testProgramVertexFixedFunctionBuilder(false);
+        testProgramVertexFixedFunctionBuilder(true);
+    }
+
+}
diff --git a/tests/tests/renderscript/src/android/renderscript/cts/ProgramVertexTest.java b/tests/tests/renderscript/src/android/renderscript/cts/ProgramVertexTest.java
index 5d6d8d3..0a5c60e 100644
--- a/tests/tests/renderscript/src/android/renderscript/cts/ProgramVertexTest.java
+++ b/tests/tests/renderscript/src/android/renderscript/cts/ProgramVertexTest.java
@@ -165,18 +165,21 @@
         ProgramVertex pv = buildShader(inputs, null, simpleAttr);
         if (testBind) {
             mScript.invoke_testProgramVertex(pv);
+            mRS.bindProgramVertex(pv);
         }
 
         inputs[0] = mAttrPosNormTexElem;
         pv = buildShader(inputs, null, multiAttr);
         if (testBind) {
             mScript.invoke_testProgramVertex(pv);
+            mRS.bindProgramVertex(pv);
         }
 
         inputs[0] = mAttrExtra;
         pv = buildShader(inputs, null, multiAttr2);
         if (testBind) {
             mScript.invoke_testProgramVertex(pv);
+            mRS.bindProgramVertex(pv);
         }
 
         // Now with constant inputs
@@ -186,6 +189,7 @@
         pv = buildShader(inputs, constInput, simpleAttrSimpleUni);
         if (testBind) {
             mScript.invoke_testProgramVertex(pv);
+            mRS.bindProgramVertex(pv);
         }
 
         inputs[0] = mAttrPosNormTexElem;
@@ -193,6 +197,7 @@
         pv = buildShader(inputs, constInput, multiAttrMultiUni);
         if (testBind) {
             mScript.invoke_testProgramVertex(pv);
+            mRS.bindProgramVertex(pv);
         }
 
         // Now with multiple input and const structs
@@ -203,6 +208,7 @@
         pv = buildShader(inputs, constInput, multiAttrMultiUni);
         if (testBind) {
             mScript.invoke_testProgramVertex(pv);
+            mRS.bindProgramVertex(pv);
         }
 
         inputs = new Element[2];
@@ -211,6 +217,7 @@
         pv = buildShader(inputs, null, multiAttr);
         if (testBind) {
             mScript.invoke_testProgramVertex(pv);
+            mRS.bindProgramVertex(pv);
         }
 
         constInput[0] = mConstMatrix;
@@ -220,6 +227,7 @@
         pv = buildShader(inputs, constInput, multiAttrMultiUni);
         if (testBind) {
             mScript.invoke_testProgramVertex(pv);
+            mRS.bindProgramVertex(pv);
         }
     }
 
diff --git a/tests/tests/renderscript/src/android/renderscript/cts/SurfaceConfigTest.java b/tests/tests/renderscript/src/android/renderscript/cts/SurfaceConfigTest.java
new file mode 100644
index 0000000..94d784e
--- /dev/null
+++ b/tests/tests/renderscript/src/android/renderscript/cts/SurfaceConfigTest.java
@@ -0,0 +1,154 @@
+/*
+ * Copyright (C) 2011 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.renderscript.cts;
+import android.test.AndroidTestCase;
+
+import android.renderscript.RSIllegalArgumentException;
+import android.renderscript.RenderScriptGL.SurfaceConfig;
+
+public class SurfaceConfigTest extends AndroidTestCase {
+
+    public void testSimpleCreate() {
+        SurfaceConfig sc = new SurfaceConfig();
+    }
+
+    public void testSetColor() {
+        SurfaceConfig sc = new SurfaceConfig();
+        try {
+            sc.setColor(-1, 8);
+            fail("should throw RSIllegalArgumentException.");
+        } catch (RSIllegalArgumentException e) {
+        }
+        sc = new SurfaceConfig();
+        try {
+            sc.setColor(9, 8);
+            fail("should throw RSIllegalArgumentException.");
+        } catch (RSIllegalArgumentException e) {
+        }
+        sc = new SurfaceConfig();
+        try {
+            sc.setColor(5, -1);
+            fail("should throw RSIllegalArgumentException.");
+        } catch (RSIllegalArgumentException e) {
+        }
+        sc = new SurfaceConfig();
+        sc.setColor(5, 8);
+        sc = new SurfaceConfig();
+        sc.setColor(8, 8);
+    }
+
+    public void testSetAlpha() {
+        SurfaceConfig sc = new SurfaceConfig();
+        try {
+            sc.setAlpha(-1, 8);
+            fail("should throw RSIllegalArgumentException.");
+        } catch (RSIllegalArgumentException e) {
+        }
+        sc = new SurfaceConfig();
+        try {
+            sc.setAlpha(9, 8);
+            fail("should throw RSIllegalArgumentException.");
+        } catch (RSIllegalArgumentException e) {
+        }
+        sc = new SurfaceConfig();
+        try {
+            sc.setAlpha(0, -1);
+            fail("should throw RSIllegalArgumentException.");
+        } catch (RSIllegalArgumentException e) {
+        }
+        sc = new SurfaceConfig();
+        sc.setAlpha(0, 8);
+        sc = new SurfaceConfig();
+        sc.setAlpha(8, 8);
+    }
+
+    public void testSetDepth() {
+        SurfaceConfig sc = new SurfaceConfig();
+        try {
+            sc.setDepth(-1, 8);
+            fail("should throw RSIllegalArgumentException.");
+        } catch (RSIllegalArgumentException e) {
+        }
+        sc = new SurfaceConfig();
+        try {
+            sc.setDepth(45, 8);
+            fail("should throw RSIllegalArgumentException.");
+        } catch (RSIllegalArgumentException e) {
+        }
+        sc = new SurfaceConfig();
+        try {
+            sc.setDepth(0, -1);
+            fail("should throw RSIllegalArgumentException.");
+        } catch (RSIllegalArgumentException e) {
+        }
+        sc = new SurfaceConfig();
+        sc.setDepth(0, 16);
+        sc = new SurfaceConfig();
+        sc.setDepth(16, 24);
+        sc = new SurfaceConfig();
+        sc.setDepth(24, 24);
+    }
+
+    public void testSetSamples() {
+        SurfaceConfig sc = new SurfaceConfig();
+        try {
+            sc.setSamples(-1, 8, 1.0f);
+            fail("should throw RSIllegalArgumentException.");
+        } catch (RSIllegalArgumentException e) {
+        }
+        sc = new SurfaceConfig();
+        try {
+            sc.setSamples(45, 8, 1.0f);
+            fail("should throw RSIllegalArgumentException.");
+        } catch (RSIllegalArgumentException e) {
+        }
+        sc = new SurfaceConfig();
+        try {
+            sc.setSamples(1, -1, 1.0f);
+            fail("should throw RSIllegalArgumentException.");
+        } catch (RSIllegalArgumentException e) {
+        }
+        sc = new SurfaceConfig();
+        try {
+            sc.setSamples(1, 1, -1.0f);
+            fail("should throw RSIllegalArgumentException.");
+        } catch (RSIllegalArgumentException e) {
+        }
+        sc = new SurfaceConfig();
+        try {
+            sc.setSamples(1, 1, 10.0f);
+            fail("should throw RSIllegalArgumentException.");
+        } catch (RSIllegalArgumentException e) {
+        }
+        sc = new SurfaceConfig();
+        sc.setSamples(1, 4, 1.0f);
+        sc = new SurfaceConfig();
+        sc.setSamples(4, 32, 1.0f);
+        sc = new SurfaceConfig();
+        sc.setSamples(4, 64, 0.5f);
+    }
+
+    public void testCopyConstructor() {
+        SurfaceConfig sc = new SurfaceConfig();
+        sc.setAlpha(1, 7);
+        sc.setColor(5, 8);
+        sc.setDepth(0, 16);
+        sc.setSamples(1, 4, 0.71f);
+        SurfaceConfig sc2 = new SurfaceConfig(sc);
+    }
+
+}