Merge "Add ability to include/exclude tests from buildCts.py."
diff --git a/tests/res/drawable/vector_icon_clip_path_1.xml b/tests/res/drawable/vector_icon_clip_path_1.xml
new file mode 100644
index 0000000..5b4c4ab
--- /dev/null
+++ b/tests/res/drawable/vector_icon_clip_path_1.xml
@@ -0,0 +1,77 @@
+<!--
+ Copyright (C) 2014 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.
+-->
+<vector xmlns:android="http://schemas.android.com/apk/res/android" >
+
+    <size
+        android:height="64dp"
+        android:width="64dp" />
+
+    <viewport
+        android:viewportHeight="12.25"
+        android:viewportWidth="7.30625" />
+
+    <group
+        android:pivotX="3.65"
+        android:pivotY="6.125"
+        android:rotation="-30" >
+        <path
+            android:name="clip1"
+            android:clipToPath="true"
+            android:pathData="
+                M 0, 6.125
+                l 7.3, 0
+                l 0, 12.25
+                l -7.3, 0
+                z" />
+    </group>
+    <group>
+        <path
+            android:name="one"
+            android:fill="#ff88ff"
+            android:pathData="M 1.215625,9.5l 1.9375,0.0 0.0,-6.671875 -2.109375,0.421875 0.0,-1.078125
+                l 2.09375,-0.421875 1.1874998,0.0 0.0,7.75 1.9375,0.0 0.0,1.0
+                l -5.046875,0.0 0.0,-1.0Z" />
+    </group>
+    <group
+        android:pivotX="3.65"
+        android:pivotY="6.125"
+        android:rotation="-30" >
+        <path
+            android:name="clip2"
+            android:clipToPath="true"
+            android:pathData="
+                M 0, 0
+                l 7.3, 0
+                l 0, 6.125
+                l -7.3, 0
+                z" />
+    </group>
+    <group>
+        <path
+            android:name="two"
+            android:fill="#ff88ff"
+            android:pathData="M 2.534375,9.6875l 4.140625,0.0 0.0,1.0 -5.5625,0.0 0.0,-1.0q 0.671875,-0.6875 1.828125,-1.859375
+                        q 1.1718752,-1.1875 1.4687502,-1.53125 0.578125,-0.625 0.796875,-1.0625
+                        q 0.234375,-0.453125 0.234375,-0.875 0.0,-0.703125 -0.5,-1.140625
+                        q -0.484375,-0.4375 -1.2656252,-0.4375 -0.5625,0.0 -1.1875,0.1875
+                        q -0.609375,0.1875 -1.3125,0.59375l 0.0,-1.203125q 0.71875,-0.28125 1.328125,-0.421875
+                        q 0.625,-0.15625 1.140625,-0.15625 1.3593752,0.0 2.1718752,0.6875
+                        q 0.8125,0.671875 0.8125,1.8125 0.0,0.53125 -0.203125,1.015625
+                        q -0.203125,0.484375 -0.734375,1.140625 -0.15625,0.171875 -0.9375,0.984375
+                        q -0.78125024,0.8125 -2.2187502,2.265625Z" />
+    </group>
+
+</vector>
\ No newline at end of file
diff --git a/tests/res/drawable/vector_icon_clip_path_1_golden.png b/tests/res/drawable/vector_icon_clip_path_1_golden.png
new file mode 100644
index 0000000..78dddaa
--- /dev/null
+++ b/tests/res/drawable/vector_icon_clip_path_1_golden.png
Binary files differ
diff --git a/tests/res/drawable/vector_icon_transformation_1.xml b/tests/res/drawable/vector_icon_transformation_1.xml
new file mode 100644
index 0000000..116d77e
--- /dev/null
+++ b/tests/res/drawable/vector_icon_transformation_1.xml
@@ -0,0 +1,41 @@
+<!--
+ Copyright (C) 2014 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.
+-->
+<vector xmlns:android="http://schemas.android.com/apk/res/android" >
+
+    <size
+        android:height="64dp"
+        android:width="64dp" />
+
+    <viewport
+        android:viewportHeight="500"
+        android:viewportWidth="800" />
+
+    <group
+        android:pivotX="90"
+        android:pivotY="100"
+        android:rotation="20">
+        <path
+            android:name="pie2"
+            android:pathData="M200,350 l 50,-25
+           a25,12 -30 0,1 100,-50 l 50,-25
+           a25,25 -30 0,1 100,-50 l 50,-25
+           a25,37 -30 0,1 100,-50 l 50,-25
+           a25,50 -30 0,1 100,-50 l 50,-25"
+            android:stroke="#FF00FF00"
+            android:strokeWidth="10" />
+    </group>
+
+</vector>
diff --git a/tests/res/drawable/vector_icon_transformation_1_golden.png b/tests/res/drawable/vector_icon_transformation_1_golden.png
new file mode 100644
index 0000000..6f659c3
--- /dev/null
+++ b/tests/res/drawable/vector_icon_transformation_1_golden.png
Binary files differ
diff --git a/tests/res/drawable/vector_icon_transformation_2.xml b/tests/res/drawable/vector_icon_transformation_2.xml
new file mode 100644
index 0000000..ae85d9b
--- /dev/null
+++ b/tests/res/drawable/vector_icon_transformation_2.xml
@@ -0,0 +1,51 @@
+<!--
+ Copyright (C) 2014 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.
+-->
+<vector xmlns:android="http://schemas.android.com/apk/res/android" >
+
+    <size
+        android:height="64dp"
+        android:width="64dp" />
+
+    <viewport
+        android:viewportHeight="200"
+        android:viewportWidth="200" />
+
+    <group>
+        <path
+            android:name="background1"
+            android:pathData="M 0,0 l 100,0 l 0, 100 l -100, 0 z"
+            android:fill="#FF000000"/>
+        <path
+            android:name="background2"
+            android:pathData="M 100,100 l 100,0 l 0, 100 l -100, 0 z"
+            android:fill="#FF000000"/>
+    </group>
+    <group
+        android:pivotX="100"
+        android:pivotY="100"
+        android:rotation="90"
+        android:scaleX="0.75"
+        android:scaleY="0.5"
+        android:translateX="0.0"
+        android:translateY="100.0">
+        <path
+            android:name="twoLines"
+            android:pathData="M 100,10 v 90 M 10,100 h 90"
+            android:stroke="#FF00FF00"
+            android:strokeWidth="10" />
+    </group>
+
+</vector>
\ No newline at end of file
diff --git a/tests/res/drawable/vector_icon_transformation_2_golden.png b/tests/res/drawable/vector_icon_transformation_2_golden.png
new file mode 100644
index 0000000..e0e14f3
--- /dev/null
+++ b/tests/res/drawable/vector_icon_transformation_2_golden.png
Binary files differ
diff --git a/tests/res/drawable/vector_icon_transformation_3.xml b/tests/res/drawable/vector_icon_transformation_3.xml
new file mode 100644
index 0000000..e0013e7
--- /dev/null
+++ b/tests/res/drawable/vector_icon_transformation_3.xml
@@ -0,0 +1,51 @@
+<!--
+ Copyright (C) 2014 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.
+-->
+<vector xmlns:android="http://schemas.android.com/apk/res/android" >
+
+    <size
+        android:height="64dp"
+        android:width="64dp" />
+
+    <viewport
+        android:viewportHeight="200"
+        android:viewportWidth="200" />
+
+    <group>
+        <path
+            android:name="background1"
+            android:pathData="M 0,0 l 100,0 l 0, 100 l -100, 0 z"
+            android:fill="#FF000000"/>
+        <path
+            android:name="background2"
+            android:pathData="M 100,100 l 100,0 l 0, 100 l -100, 0 z"
+            android:fill="#FF000000"/>
+    </group>
+    <group
+        android:pivotX="0"
+        android:pivotY="0"
+        android:rotation="90"
+        android:scaleX="0.75"
+        android:scaleY="0.5"
+        android:translateX="100.0"
+        android:translateY="100.0">
+        <path
+            android:name="twoLines"
+            android:pathData="M 100,10 v 90 M 10,100 h 90"
+            android:stroke="#FF00FF00"
+            android:strokeWidth="10" />
+    </group>
+
+</vector>
\ No newline at end of file
diff --git a/tests/res/drawable/vector_icon_transformation_3_golden.png b/tests/res/drawable/vector_icon_transformation_3_golden.png
new file mode 100644
index 0000000..b6798c2
--- /dev/null
+++ b/tests/res/drawable/vector_icon_transformation_3_golden.png
Binary files differ
diff --git a/tests/tests/display/src/android/display/cts/VirtualDisplayTest.java b/tests/tests/display/src/android/display/cts/VirtualDisplayTest.java
index f452f50..f2f859a 100644
--- a/tests/tests/display/src/android/display/cts/VirtualDisplayTest.java
+++ b/tests/tests/display/src/android/display/cts/VirtualDisplayTest.java
@@ -29,6 +29,7 @@
 import android.os.Bundle;
 import android.os.Handler;
 import android.os.Looper;
+import android.os.HandlerThread;
 import android.os.SystemClock;
 import android.test.AndroidTestCase;
 import android.util.DisplayMetrics;
@@ -72,6 +73,8 @@
     private ImageReader mImageReader;
     private Surface mSurface;
     private ImageListener mImageListener;
+    private HandlerThread mCheckThread;
+    private Handler mCheckHandler;
 
     @Override
     protected void setUp() throws Exception {
@@ -80,11 +83,15 @@
         mDisplayManager = (DisplayManager)mContext.getSystemService(Context.DISPLAY_SERVICE);
         mHandler = new Handler(Looper.getMainLooper());
         mImageListener = new ImageListener();
+        // thread for image checking
+        mCheckThread = new HandlerThread("TestHandler");
+        mCheckThread.start();
+        mCheckHandler = new Handler(mCheckThread.getLooper());
 
         mImageReaderLock.lock();
         try {
             mImageReader = ImageReader.newInstance(WIDTH, HEIGHT, PixelFormat.RGBA_8888, 2);
-            mImageReader.setOnImageAvailableListener(mImageListener, mHandler);
+            mImageReader.setOnImageAvailableListener(mImageListener, mCheckHandler);
             mSurface = mImageReader.getSurface();
         } finally {
             mImageReaderLock.unlock();
@@ -94,7 +101,6 @@
     @Override
     protected void tearDown() throws Exception {
         super.tearDown();
-
         mImageReaderLock.lock();
         try {
             mImageReader.close();
@@ -103,6 +109,7 @@
         } finally {
             mImageReaderLock.unlock();
         }
+        mCheckThread.quit();
     }
 
     /**
diff --git a/tests/tests/graphics/src/android/graphics/drawable/cts/VectorDrawableTest.java b/tests/tests/graphics/src/android/graphics/drawable/cts/VectorDrawableTest.java
index 94c87cb..45a14d7 100644
--- a/tests/tests/graphics/src/android/graphics/drawable/cts/VectorDrawableTest.java
+++ b/tests/tests/graphics/src/android/graphics/drawable/cts/VectorDrawableTest.java
@@ -49,6 +49,10 @@
             R.drawable.vector_icon_repeated_st,
             R.drawable.vector_icon_repeated_a_1,
             R.drawable.vector_icon_repeated_a_2,
+            R.drawable.vector_icon_clip_path_1,
+            R.drawable.vector_icon_transformation_1,
+            R.drawable.vector_icon_transformation_2,
+            R.drawable.vector_icon_transformation_3,
     };
 
     private int[] mGoldenImages = new int[] {
@@ -63,6 +67,10 @@
             R.drawable.vector_icon_repeated_st_golden,
             R.drawable.vector_icon_repeated_a_1_golden,
             R.drawable.vector_icon_repeated_a_2_golden,
+            R.drawable.vector_icon_clip_path_1_golden,
+            R.drawable.vector_icon_transformation_1_golden,
+            R.drawable.vector_icon_transformation_2_golden,
+            R.drawable.vector_icon_transformation_3_golden,
     };
 
     private static final int IMAGE_WIDTH = 64;
@@ -130,11 +138,16 @@
         // Save the image to the disk.
         FileOutputStream out = null;
         try {
+            String outputFolder = "/sdcard/temp/";
+            File folder = new File(outputFolder);
+            if (!folder.exists()) {
+                folder.mkdir();
+            }
             String originalFilePath = mResources.getString(resIds[index]);
             File originalFile = new File(originalFilePath);
             String fileFullName = originalFile.getName();
             String fileTitle = fileFullName.substring(0, fileFullName.lastIndexOf("."));
-            String outputFilename = "/sdcard/temp/" + fileTitle + "_golden.png";
+            String outputFilename = outputFolder + fileTitle + "_golden.png";
             File outputFile = new File(outputFilename);
             if (!outputFile.exists()) {
                 outputFile.createNewFile();
diff --git a/tests/tests/hardware/src/android/hardware/camera2/cts/AllocationTest.java b/tests/tests/hardware/src/android/hardware/camera2/cts/AllocationTest.java
index f09b1f1..8baecac 100644
--- a/tests/tests/hardware/src/android/hardware/camera2/cts/AllocationTest.java
+++ b/tests/tests/hardware/src/android/hardware/camera2/cts/AllocationTest.java
@@ -33,6 +33,8 @@
 import android.hardware.camera2.CaptureRequest;
 import android.hardware.camera2.CaptureResult;
 import android.hardware.camera2.TotalCaptureResult;
+import android.hardware.camera2.params.ColorSpaceTransform;
+import android.hardware.camera2.params.RggbChannelVector;
 import android.util.Size;
 import android.hardware.camera2.cts.helpers.MaybeNull;
 import android.hardware.camera2.cts.helpers.StaticMetadata;
@@ -149,14 +151,15 @@
 
         // Identity transform
         request.set(CaptureRequest.COLOR_CORRECTION_TRANSFORM,
-            new Rational[] {
+            new ColorSpaceTransform(new Rational[] {
                 ONE, ZERO, ZERO,
                 ZERO, ONE, ZERO,
                 ZERO, ZERO, ONE
-            });
+            }));
 
         // Identity gains
-        request.set(CaptureRequest.COLOR_CORRECTION_GAINS, new float[] { 1.0f, 1.0f, 1.0f, 1.0f });
+        request.set(CaptureRequest.COLOR_CORRECTION_GAINS,
+                new RggbChannelVector(1.0f, 1.0f, 1.0f, 1.0f ));
         request.set(CaptureRequest.TONEMAP_MODE, CaptureRequest.TONEMAP_MODE_FAST);
     }
 
diff --git a/tests/tests/hardware/src/android/hardware/camera2/cts/CameraCharacteristicsTest.java b/tests/tests/hardware/src/android/hardware/camera2/cts/CameraCharacteristicsTest.java
index ac5c889..effb6ba 100644
--- a/tests/tests/hardware/src/android/hardware/camera2/cts/CameraCharacteristicsTest.java
+++ b/tests/tests/hardware/src/android/hardware/camera2/cts/CameraCharacteristicsTest.java
@@ -287,7 +287,7 @@
         }
     }
 
-    public void testCameraCharacteristicsAndroidControlMaxRegions() throws Exception {
+    public void testCameraCharacteristicsAndroidControlMaxRegionsAe() throws Exception {
         String[] ids = mCameraManager.getCameraIdList();
         for (int i = 0; i < ids.length; i++) {
             CameraCharacteristics props = mCameraManager.getCameraCharacteristics(ids[i]);
@@ -296,14 +296,60 @@
 
             {
 
-                assertNotNull("Invalid property: android.control.maxRegions",
-                        props.get(CameraCharacteristics.CONTROL_MAX_REGIONS));
+                assertNotNull("Invalid property: android.control.maxRegionsAe",
+                        props.get(CameraCharacteristics.CONTROL_MAX_REGIONS_AE));
 
                 List<Key<?>> allKeys = props.getKeys();
                 assertNotNull(String.format("Can't get camera characteristics keys from: ID %s",
                         ids[i], props));
-                assertTrue("Key not in keys list: android.control.maxRegions", allKeys.contains(
-                        CameraCharacteristics.CONTROL_MAX_REGIONS));
+                assertTrue("Key not in keys list: android.control.maxRegionsAe", allKeys.contains(
+                        CameraCharacteristics.CONTROL_MAX_REGIONS_AE));
+
+            }
+
+        }
+    }
+
+    public void testCameraCharacteristicsAndroidControlMaxRegionsAwb() throws Exception {
+        String[] ids = mCameraManager.getCameraIdList();
+        for (int i = 0; i < ids.length; i++) {
+            CameraCharacteristics props = mCameraManager.getCameraCharacteristics(ids[i]);
+            assertNotNull(String.format("Can't get camera characteristics from: ID %s", ids[i]),
+                                        props);
+
+            {
+
+                assertNotNull("Invalid property: android.control.maxRegionsAwb",
+                        props.get(CameraCharacteristics.CONTROL_MAX_REGIONS_AWB));
+
+                List<Key<?>> allKeys = props.getKeys();
+                assertNotNull(String.format("Can't get camera characteristics keys from: ID %s",
+                        ids[i], props));
+                assertTrue("Key not in keys list: android.control.maxRegionsAwb", allKeys.contains(
+                        CameraCharacteristics.CONTROL_MAX_REGIONS_AWB));
+
+            }
+
+        }
+    }
+
+    public void testCameraCharacteristicsAndroidControlMaxRegionsAf() throws Exception {
+        String[] ids = mCameraManager.getCameraIdList();
+        for (int i = 0; i < ids.length; i++) {
+            CameraCharacteristics props = mCameraManager.getCameraCharacteristics(ids[i]);
+            assertNotNull(String.format("Can't get camera characteristics from: ID %s", ids[i]),
+                                        props);
+
+            {
+
+                assertNotNull("Invalid property: android.control.maxRegionsAf",
+                        props.get(CameraCharacteristics.CONTROL_MAX_REGIONS_AF));
+
+                List<Key<?>> allKeys = props.getKeys();
+                assertNotNull(String.format("Can't get camera characteristics keys from: ID %s",
+                        ids[i], props));
+                assertTrue("Key not in keys list: android.control.maxRegionsAf", allKeys.contains(
+                        CameraCharacteristics.CONTROL_MAX_REGIONS_AF));
 
             }
 
@@ -567,29 +613,6 @@
         }
     }
 
-    public void testCameraCharacteristicsAndroidLensInfoShadingMapSize() throws Exception {
-        String[] ids = mCameraManager.getCameraIdList();
-        for (int i = 0; i < ids.length; i++) {
-            CameraCharacteristics props = mCameraManager.getCameraCharacteristics(ids[i]);
-            assertNotNull(String.format("Can't get camera characteristics from: ID %s", ids[i]),
-                                        props);
-
-            {
-
-                assertNotNull("Invalid property: android.lens.info.shadingMapSize",
-                        props.get(CameraCharacteristics.LENS_INFO_SHADING_MAP_SIZE));
-
-                List<Key<?>> allKeys = props.getKeys();
-                assertNotNull(String.format("Can't get camera characteristics keys from: ID %s",
-                        ids[i], props));
-                assertTrue("Key not in keys list: android.lens.info.shadingMapSize", allKeys.contains(
-                        CameraCharacteristics.LENS_INFO_SHADING_MAP_SIZE));
-
-            }
-
-        }
-    }
-
     public void testCameraCharacteristicsAndroidLensInfoFocusDistanceCalibration() throws Exception {
         String[] ids = mCameraManager.getCameraIdList();
         for (int i = 0; i < ids.length; i++) {
@@ -636,7 +659,7 @@
         }
     }
 
-    public void testCameraCharacteristicsAndroidRequestMaxNumOutputStreams() throws Exception {
+    public void testCameraCharacteristicsAndroidRequestMaxNumOutputRaw() throws Exception {
         String[] ids = mCameraManager.getCameraIdList();
         for (int i = 0; i < ids.length; i++) {
             CameraCharacteristics props = mCameraManager.getCameraCharacteristics(ids[i]);
@@ -645,14 +668,60 @@
 
             {
 
-                assertNotNull("Invalid property: android.request.maxNumOutputStreams",
-                        props.get(CameraCharacteristics.REQUEST_MAX_NUM_OUTPUT_STREAMS));
+                assertNotNull("Invalid property: android.request.maxNumOutputRaw",
+                        props.get(CameraCharacteristics.REQUEST_MAX_NUM_OUTPUT_RAW));
 
                 List<Key<?>> allKeys = props.getKeys();
                 assertNotNull(String.format("Can't get camera characteristics keys from: ID %s",
                         ids[i], props));
-                assertTrue("Key not in keys list: android.request.maxNumOutputStreams", allKeys.contains(
-                        CameraCharacteristics.REQUEST_MAX_NUM_OUTPUT_STREAMS));
+                assertTrue("Key not in keys list: android.request.maxNumOutputRaw", allKeys.contains(
+                        CameraCharacteristics.REQUEST_MAX_NUM_OUTPUT_RAW));
+
+            }
+
+        }
+    }
+
+    public void testCameraCharacteristicsAndroidRequestMaxNumOutputProc() throws Exception {
+        String[] ids = mCameraManager.getCameraIdList();
+        for (int i = 0; i < ids.length; i++) {
+            CameraCharacteristics props = mCameraManager.getCameraCharacteristics(ids[i]);
+            assertNotNull(String.format("Can't get camera characteristics from: ID %s", ids[i]),
+                                        props);
+
+            {
+
+                assertNotNull("Invalid property: android.request.maxNumOutputProc",
+                        props.get(CameraCharacteristics.REQUEST_MAX_NUM_OUTPUT_PROC));
+
+                List<Key<?>> allKeys = props.getKeys();
+                assertNotNull(String.format("Can't get camera characteristics keys from: ID %s",
+                        ids[i], props));
+                assertTrue("Key not in keys list: android.request.maxNumOutputProc", allKeys.contains(
+                        CameraCharacteristics.REQUEST_MAX_NUM_OUTPUT_PROC));
+
+            }
+
+        }
+    }
+
+    public void testCameraCharacteristicsAndroidRequestMaxNumOutputProcStalling() throws Exception {
+        String[] ids = mCameraManager.getCameraIdList();
+        for (int i = 0; i < ids.length; i++) {
+            CameraCharacteristics props = mCameraManager.getCameraCharacteristics(ids[i]);
+            assertNotNull(String.format("Can't get camera characteristics from: ID %s", ids[i]),
+                                        props);
+
+            {
+
+                assertNotNull("Invalid property: android.request.maxNumOutputProcStalling",
+                        props.get(CameraCharacteristics.REQUEST_MAX_NUM_OUTPUT_PROC_STALLING));
+
+                List<Key<?>> allKeys = props.getKeys();
+                assertNotNull(String.format("Can't get camera characteristics keys from: ID %s",
+                        ids[i], props));
+                assertTrue("Key not in keys list: android.request.maxNumOutputProcStalling", allKeys.contains(
+                        CameraCharacteristics.REQUEST_MAX_NUM_OUTPUT_PROC_STALLING));
 
             }
 
diff --git a/tests/tests/hardware/src/android/hardware/camera2/cts/CameraDeviceTest.java b/tests/tests/hardware/src/android/hardware/camera2/cts/CameraDeviceTest.java
index d7cacd3..d61f667 100644
--- a/tests/tests/hardware/src/android/hardware/camera2/cts/CameraDeviceTest.java
+++ b/tests/tests/hardware/src/android/hardware/camera2/cts/CameraDeviceTest.java
@@ -32,6 +32,7 @@
 import android.hardware.camera2.cts.testcases.Camera2AndroidTestCase;
 import android.os.SystemClock;
 import android.util.Log;
+import android.util.Range;
 import android.view.Surface;
 
 import com.android.ex.camera2.blocking.BlockingStateListener;
@@ -639,30 +640,20 @@
 
     private void checkFpsRange(CaptureRequest.Builder request, int template,
             CameraCharacteristics props) {
-        CaptureRequest.Key<int[]> fpsRangeKey = CONTROL_AE_TARGET_FPS_RANGE;
-        int[] fpsRange;
+        CaptureRequest.Key<Range<Integer>> fpsRangeKey = CONTROL_AE_TARGET_FPS_RANGE;
+        Range<Integer> fpsRange;
         if ((fpsRange = mCollector.expectKeyValueNotNull(request, fpsRangeKey)) == null) {
             return;
         }
 
-        // TODO: Use generated array dimensions
-        final int CONTROL_AE_TARGET_FPS_RANGE_SIZE = 2;
-        final int CONTROL_AE_TARGET_FPS_RANGE_MIN = 0;
-        final int CONTROL_AE_TARGET_FPS_RANGE_MAX = 1;
-
-        String cause = "Failed with fps range size check";
-        if (!mCollector.expectEquals(cause, CONTROL_AE_TARGET_FPS_RANGE_SIZE, fpsRange.length)) {
-            return;
-        }
-
-        int minFps = fpsRange[CONTROL_AE_TARGET_FPS_RANGE_MIN];
-        int maxFps = fpsRange[CONTROL_AE_TARGET_FPS_RANGE_MAX];
-        int[] availableFpsRange = props
+        int minFps = fpsRange.getLower();
+        int maxFps = fpsRange.getUpper();
+        Range<Integer>[] availableFpsRange = props
                 .get(CameraCharacteristics.CONTROL_AE_AVAILABLE_TARGET_FPS_RANGES);
         boolean foundRange = false;
-        for (int i = 0; i < availableFpsRange.length; i += CONTROL_AE_TARGET_FPS_RANGE_SIZE) {
-            if (minFps == availableFpsRange[i + CONTROL_AE_TARGET_FPS_RANGE_MIN]
-                    && maxFps == availableFpsRange[i + CONTROL_AE_TARGET_FPS_RANGE_MAX]) {
+        for (int i = 0; i < availableFpsRange.length; i += 1) {
+            if (minFps == availableFpsRange[i].getLower()
+                    && maxFps == availableFpsRange[i].getUpper()) {
                 foundRange = true;
                 break;
             }
@@ -700,7 +691,7 @@
         }
 
         int targetAfMode = CaptureRequest.CONTROL_AF_MODE_AUTO;
-        byte[] availableAfMode = props.get(CameraCharacteristics.CONTROL_AF_AVAILABLE_MODES);
+        int[] availableAfMode = props.get(CameraCharacteristics.CONTROL_AF_AVAILABLE_MODES);
         if (template == CameraDevice.TEMPLATE_PREVIEW ||
                 template == CameraDevice.TEMPLATE_STILL_CAPTURE ||
                 template == CameraDevice.TEMPLATE_ZERO_SHUTTER_LAG) {
@@ -808,7 +799,7 @@
             mCollector.expectKeyValueNotNull(request, LENS_FOCAL_LENGTH);
         }
 
-        byte[] availableOIS =
+        int[] availableOIS =
                 props.get(CameraCharacteristics.LENS_INFO_AVAILABLE_OPTICAL_STABILIZATION);
         if (availableOIS.length > 1) {
             mCollector.expectKeyValueNotNull(request, LENS_OPTICAL_STABILIZATION_MODE);
@@ -835,26 +826,26 @@
                     request, COLOR_CORRECTION_MODE,
                     CaptureRequest.COLOR_CORRECTION_MODE_TRANSFORM_MATRIX);
 
-            List<Byte> availableEdgeModes =
+            List<Integer> availableEdgeModes =
                     Arrays.asList(toObject(mStaticInfo.getAvailableEdgeModesChecked()));
-            if (availableEdgeModes.contains((byte) CaptureRequest.EDGE_MODE_HIGH_QUALITY)) {
+            if (availableEdgeModes.contains(CaptureRequest.EDGE_MODE_HIGH_QUALITY)) {
                 mCollector.expectKeyValueEquals(request, EDGE_MODE,
                         CaptureRequest.EDGE_MODE_HIGH_QUALITY);
-            } else if (availableEdgeModes.contains((byte) CaptureRequest.EDGE_MODE_FAST)) {
+            } else if (availableEdgeModes.contains(CaptureRequest.EDGE_MODE_FAST)) {
                 mCollector.expectKeyValueEquals(request, EDGE_MODE, CaptureRequest.EDGE_MODE_FAST);
             } else {
                 mCollector.expectKeyValueEquals(request, EDGE_MODE, CaptureRequest.EDGE_MODE_OFF);
             }
 
-            List<Byte> availableNoiseReductionModes =
+            List<Integer> availableNoiseReductionModes =
                     Arrays.asList(toObject(mStaticInfo.getAvailableNoiseReductionModesChecked()));
             if (availableNoiseReductionModes
-                    .contains((byte) CaptureRequest.NOISE_REDUCTION_MODE_HIGH_QUALITY)) {
+                    .contains(CaptureRequest.NOISE_REDUCTION_MODE_HIGH_QUALITY)) {
                 mCollector.expectKeyValueEquals(
                         request, NOISE_REDUCTION_MODE,
                         CaptureRequest.NOISE_REDUCTION_MODE_HIGH_QUALITY);
             } else if (availableNoiseReductionModes
-                    .contains((byte) CaptureRequest.NOISE_REDUCTION_MODE_FAST)) {
+                    .contains(CaptureRequest.NOISE_REDUCTION_MODE_FAST)) {
                 mCollector.expectKeyValueEquals(
                         request, NOISE_REDUCTION_MODE, CaptureRequest.NOISE_REDUCTION_MODE_FAST);
             } else {
@@ -862,9 +853,9 @@
                         request, NOISE_REDUCTION_MODE, CaptureRequest.NOISE_REDUCTION_MODE_OFF);
             }
 
-            List<Byte> availableToneMapModes =
+            List<Integer> availableToneMapModes =
                     Arrays.asList(toObject(mStaticInfo.getAvailableToneMapModesChecked()));
-            if (availableToneMapModes.contains((byte) CaptureRequest.TONEMAP_MODE_HIGH_QUALITY)) {
+            if (availableToneMapModes.contains(CaptureRequest.TONEMAP_MODE_HIGH_QUALITY)) {
                 mCollector.expectKeyValueEquals(request, TONEMAP_MODE,
                         CaptureRequest.TONEMAP_MODE_HIGH_QUALITY);
             } else {
diff --git a/tests/tests/hardware/src/android/hardware/camera2/cts/CameraTestUtils.java b/tests/tests/hardware/src/android/hardware/camera2/cts/CameraTestUtils.java
index e157b4c..52a486f 100644
--- a/tests/tests/hardware/src/android/hardware/camera2/cts/CameraTestUtils.java
+++ b/tests/tests/hardware/src/android/hardware/camera2/cts/CameraTestUtils.java
@@ -31,6 +31,7 @@
 import android.hardware.camera2.CaptureResult;
 import android.hardware.camera2.TotalCaptureResult;
 import android.util.Size;
+import android.hardware.camera2.params.MeteringRectangle;
 import android.hardware.camera2.params.StreamConfigurationMap;
 import android.media.Image;
 import android.media.ImageReader;
@@ -881,21 +882,22 @@
     /**
      * Calculate output 3A region from the intersection of input 3A region and cropped region.
      *
-     * @param requestRegion The input 3A region [xmin, ymin, xmax, ymax, weight]
+     * @param requestRegions The input 3A regions
      * @param cropRect The cropped region
-     * @return expected 3A region output in capture result
+     * @return expected 3A regions output in capture result
      */
-    public static int[] getExpectedOutputRegion(int[] requestRegion, Rect cropRect){
-        Rect requestRect = new Rect(requestRegion[0], requestRegion[1],
-                requestRegion[2], requestRegion[3]);
-        Rect resultRect = new Rect();
-        assertTrue("Input 3A region must intersect cropped region",
-                    resultRect.setIntersect(requestRect, cropRect));
-        return new int[] {
-                resultRect.left,
-                resultRect.top,
-                resultRect.right,
-                resultRect.bottom,
-                requestRegion[4]};
+    public static MeteringRectangle[] getExpectedOutputRegion(
+            MeteringRectangle[] requestRegions, Rect cropRect){
+        MeteringRectangle[] resultRegions = new MeteringRectangle[requestRegions.length];
+        for (int i = 0; i < requestRegions.length; i++) {
+            Rect requestRect = requestRegions[i].getRect();
+            Rect resultRect = new Rect();
+            assertTrue("Input 3A region must intersect cropped region",
+                        resultRect.setIntersect(requestRect, cropRect));
+            resultRegions[i] = new MeteringRectangle(
+                    resultRect,
+                    requestRegions[i].getMeteringWeight());
+        }
+        return resultRegions;
     }
 }
diff --git a/tests/tests/hardware/src/android/hardware/camera2/cts/CaptureRequestTest.java b/tests/tests/hardware/src/android/hardware/camera2/cts/CaptureRequestTest.java
index add91a4..aa548ed 100644
--- a/tests/tests/hardware/src/android/hardware/camera2/cts/CaptureRequestTest.java
+++ b/tests/tests/hardware/src/android/hardware/camera2/cts/CaptureRequestTest.java
@@ -29,8 +29,15 @@
 import android.hardware.camera2.CaptureResult;
 import android.hardware.camera2.cts.CameraTestUtils.SimpleCaptureListener;
 import android.hardware.camera2.cts.testcases.Camera2SurfaceViewTestCase;
+import android.hardware.camera2.params.ColorSpaceTransform;
 import android.hardware.camera2.params.Face;
+import android.hardware.camera2.params.LensShadingMap;
+import android.hardware.camera2.params.MeteringRectangle;
+import android.hardware.camera2.params.RggbChannelVector;
+import android.hardware.camera2.params.TonemapCurve;
+
 import android.util.Log;
+import android.util.Range;
 import android.util.Rational;
 import android.util.Size;
 
@@ -93,7 +100,6 @@
     private final int INDEX_ALGORITHM_AE = 0;
     private final int INDEX_ALGORITHM_AWB = 1;
     private final int INDEX_ALGORITHM_AF = 2;
-    private final int LENGTH_ALGORITHM_REGION = 5;
 
     @Override
     protected void setUp() throws Exception {
@@ -186,14 +192,13 @@
                 requestBuilder.set(CaptureRequest.STATISTICS_LENS_SHADING_MAP_MODE,
                         STATISTICS_LENS_SHADING_MAP_MODE_ON);
 
-                Size mapSz = mStaticInfo.getCharacteristics().get(LENS_INFO_SHADING_MAP_SIZE);
                 Size previewSz =
                         getMaxPreviewSize(mCamera.getId(), mCameraManager, PREVIEW_SIZE_BOUND);
 
                 listener = new SimpleCaptureListener();
                 startPreview(requestBuilder, previewSz, listener);
 
-                verifyShadingMap(listener, NUM_FRAMES_VERIFIED, mapSz, SHADING_MODE_OFF);
+                verifyShadingMap(listener, NUM_FRAMES_VERIFIED, SHADING_MODE_OFF);
 
                 // Shading map mode FAST, lensShadingMapMode ON, camera device
                 // should output valid maps.
@@ -203,7 +208,7 @@
                 startPreview(requestBuilder, previewSz, listener);
 
                 // Allow at most one lock OFF state as the exposure is changed once.
-                verifyShadingMap(listener, NUM_FRAMES_VERIFIED, mapSz, SHADING_MODE_FAST);
+                verifyShadingMap(listener, NUM_FRAMES_VERIFIED, SHADING_MODE_FAST);
 
                 // Shading map mode HIGH_QUALITY, lensShadingMapMode ON, camera device
                 // should output valid maps.
@@ -212,7 +217,7 @@
                 listener = new SimpleCaptureListener();
                 startPreview(requestBuilder, previewSz, listener);
 
-                verifyShadingMap(listener, NUM_FRAMES_VERIFIED, mapSz, SHADING_MODE_HIGH_QUALITY);
+                verifyShadingMap(listener, NUM_FRAMES_VERIFIED, SHADING_MODE_HIGH_QUALITY);
 
                 stopPreview();
             } finally {
@@ -237,12 +242,12 @@
                     continue;
                 }
 
-                byte[] modes = mStaticInfo.getAeAvailableAntiBandingModesChecked();
+                int[] modes = mStaticInfo.getAeAvailableAntiBandingModesChecked();
 
                 Size previewSz =
                         getMaxPreviewSize(mCamera.getId(), mCameraManager, PREVIEW_SIZE_BOUND);
 
-                for (byte mode : modes) {
+                for (int mode : modes) {
                     antiBandingTestByMode(previewSz, mode);
                 }
             } finally {
@@ -278,8 +283,8 @@
                 updatePreviewSurface(maxPreviewSz);
 
                 // Test aeMode and lock
-                byte[] aeModes = mStaticInfo.getAeAvailableModesChecked();
-                for (byte mode : aeModes) {
+                int[] aeModes = mStaticInfo.getAeAvailableModesChecked();
+                for (int mode : aeModes) {
                     aeModeAndLockTestByMode(mode);
                 }
             } finally {
@@ -542,12 +547,12 @@
         Size maxPrevSize = mOrderedPreviewSizes.get(0);
         CaptureRequest.Builder requestBuilder =
                 mCamera.createCaptureRequest(CameraDevice.TEMPLATE_PREVIEW);
-        byte[] availableModes = mStaticInfo.getAvailableNoiseReductionModesChecked();
+        int[] availableModes = mStaticInfo.getAvailableNoiseReductionModesChecked();
         SimpleCaptureListener resultListener = new SimpleCaptureListener();
         startPreview(requestBuilder, maxPrevSize, resultListener);
 
-        for (byte mode : availableModes) {
-            requestBuilder.set(CaptureRequest.NOISE_REDUCTION_MODE, (int)mode);
+        for (int mode : availableModes) {
+            requestBuilder.set(CaptureRequest.NOISE_REDUCTION_MODE, mode);
             resultListener = new SimpleCaptureListener();
             mCamera.setRepeatingRequest(requestBuilder.build(), resultListener, mHandler);
 
@@ -659,14 +664,14 @@
      */
     private void edgeModesTestByCamera() throws Exception {
         Size maxPrevSize = mOrderedPreviewSizes.get(0);
-        byte[] edgeModes = mStaticInfo.getAvailableEdgeModesChecked();
+        int[] edgeModes = mStaticInfo.getAvailableEdgeModesChecked();
         CaptureRequest.Builder requestBuilder =
                 mCamera.createCaptureRequest(CameraDevice.TEMPLATE_PREVIEW);
         SimpleCaptureListener resultListener = new SimpleCaptureListener();
         startPreview(requestBuilder, maxPrevSize, resultListener);
 
-        for (byte mode : edgeModes) {
-            requestBuilder.set(CaptureRequest.EDGE_MODE, (int)mode);
+        for (int mode : edgeModes) {
+            requestBuilder.set(CaptureRequest.EDGE_MODE, mode);
             resultListener = new SimpleCaptureListener();
             mCamera.setRepeatingRequest(requestBuilder.build(), resultListener, mHandler);
 
@@ -706,12 +711,15 @@
 
         // TRANSFORM_MATRIX mode
         // Only test unit gain and identity transform
-        float[] UNIT_GAIN = {1.0f, 1.0f, 1.0f, 1.0f};
-        Rational[] IDENTITY_TRANSFORM = {
+        RggbChannelVector UNIT_GAIN = new RggbChannelVector(1.0f, 1.0f, 1.0f, 1.0f);
+
+        ColorSpaceTransform IDENTITY_TRANSFORM = new ColorSpaceTransform(
+            new Rational[] {
                 ONE_R, ZERO_R, ZERO_R,
                 ZERO_R, ONE_R, ZERO_R,
                 ZERO_R, ZERO_R, ONE_R
-        };
+            });
+
         manualRequestBuilder.set(CaptureRequest.CONTROL_MODE, CaptureRequest.CONTROL_MODE_OFF);
         manualRequestBuilder.set(CaptureRequest.COLOR_CORRECTION_MODE,
                 CaptureRequest.COLOR_CORRECTION_MODE_TRANSFORM_MATRIX);
@@ -720,11 +728,11 @@
         request = manualRequestBuilder.build();
         mCamera.capture(request, listener, mHandler);
         result = listener.getCaptureResultForRequest(request, NUM_RESULTS_WAIT_TIMEOUT);
-        float[] gains = result.get(CaptureResult.COLOR_CORRECTION_GAINS);
-        Rational[] transform = result.get(CaptureResult.COLOR_CORRECTION_TRANSFORM);
+        RggbChannelVector gains = result.get(CaptureResult.COLOR_CORRECTION_GAINS);
+        ColorSpaceTransform transform = result.get(CaptureResult.COLOR_CORRECTION_TRANSFORM);
         validateColorCorrectionResult(result);
         mCollector.expectEquals("Color correction gain result/request mismatch",
-                CameraTestUtils.toObject(UNIT_GAIN), CameraTestUtils.toObject(gains));
+                UNIT_GAIN, gains);
         mCollector.expectEquals("Color correction gain result/request mismatch",
                 IDENTITY_TRANSFORM, transform);
 
@@ -748,27 +756,24 @@
     }
 
     private void validateColorCorrectionResult(CaptureResult result) {
-        float[] ZERO_GAINS = {0, 0, 0, 0};
+        final RggbChannelVector ZERO_GAINS = new RggbChannelVector(0, 0, 0, 0);
         final int TRANSFORM_SIZE = 9;
         Rational[] zeroTransform = new Rational[TRANSFORM_SIZE];
         Arrays.fill(zeroTransform, ZERO_R);
+        final ColorSpaceTransform ZERO_TRANSFORM = new ColorSpaceTransform(zeroTransform);
 
-        float[] resultGain;
+        RggbChannelVector resultGain;
         if ((resultGain = mCollector.expectKeyValueNotNull(result,
                 CaptureResult.COLOR_CORRECTION_GAINS)) != null) {
-            mCollector.expectEquals("Color correction gain size in incorrect",
-                    ZERO_GAINS.length, resultGain.length);
             mCollector.expectKeyValueNotEquals(result,
                     CaptureResult.COLOR_CORRECTION_GAINS, ZERO_GAINS);
         }
 
-        Rational[] resultTransform;
+        ColorSpaceTransform resultTransform;
         if ((resultTransform = mCollector.expectKeyValueNotNull(result,
                 CaptureResult.COLOR_CORRECTION_TRANSFORM)) != null) {
-            mCollector.expectEquals("Color correction transform size is incorrect",
-                    zeroTransform.length, resultTransform.length);
             mCollector.expectKeyValueNotEquals(result,
-                    CaptureResult.COLOR_CORRECTION_TRANSFORM, zeroTransform);
+                    CaptureResult.COLOR_CORRECTION_TRANSFORM, ZERO_TRANSFORM);
         }
     }
 
@@ -1101,19 +1106,18 @@
      * Verify shading map for different shading modes.
      */
     private void verifyShadingMap(SimpleCaptureListener listener, int numFramesVerified,
-            Size mapSize, int shadingMode) throws Exception {
-        int numElementsInMap = mapSize.getWidth() * mapSize.getHeight() * RGGB_COLOR_CHANNEL_COUNT;
-        float[] unityMap = new float[numElementsInMap];
-        Arrays.fill(unityMap, 1.0f);
+            int shadingMode) throws Exception {
 
         for (int i = 0; i < numFramesVerified; i++) {
             CaptureResult result = listener.getCaptureResult(WAIT_FOR_RESULT_TIMEOUT_MS);
             mCollector.expectEquals("Shading mode result doesn't match request",
                     shadingMode, result.get(CaptureResult.SHADING_MODE));
-            float[] map = result.get(CaptureResult.STATISTICS_LENS_SHADING_MAP);
+            LensShadingMap mapObj = result.get(CaptureResult.STATISTICS_LENS_SHADING_CORRECTION_MAP);
+            assertNotNull("Map object must not be null", mapObj);
+            int numElementsInMap = mapObj.getGainFactorCount();
+            float[] map = new float[numElementsInMap];
+            mapObj.copyGainFactors(map, /*offset*/0);
             assertNotNull("Map must not be null", map);
-            assertTrue("Map size " + map.length + " must be " + numElementsInMap,
-                    map.length == numElementsInMap);
             assertFalse(String.format(
                     "Map size %d should be less than %d", numElementsInMap, MAX_SHADING_MAP_SIZE),
                     numElementsInMap >= MAX_SHADING_MAP_SIZE);
@@ -1135,6 +1139,8 @@
                 assertEquals("Number of value in the map is " + badValueCnt + " out of "
                         + numElementsInMap, /*expected*/0, /*actual*/badValueCnt);
             } else if (shadingMode == CaptureRequest.SHADING_MODE_OFF) {
+                float[] unityMap = new float[numElementsInMap];
+                Arrays.fill(unityMap, 1.0f);
                 // shading mode is OFF, expect to receive a unity map.
                 assertTrue("Result map " + Arrays.toString(map) + " must be an unity map",
                         Arrays.equals(unityMap, map));
@@ -1151,15 +1157,15 @@
         if (!mStaticInfo.isHardwareLevelFull()) {
             return;
         }
-        byte[] faceDetectModes = mStaticInfo.getAvailableFaceDetectModesChecked();
+        int[] faceDetectModes = mStaticInfo.getAvailableFaceDetectModesChecked();
 
         SimpleCaptureListener listener;
         CaptureRequest.Builder requestBuilder =
                 mCamera.createCaptureRequest(CameraDevice.TEMPLATE_PREVIEW);
 
         Size maxPreviewSz = mOrderedPreviewSizes.get(0); // Max preview size.
-        for (byte mode : faceDetectModes) {
-            requestBuilder.set(CaptureRequest.STATISTICS_FACE_DETECT_MODE, (int)mode);
+        for (int mode : faceDetectModes) {
+            requestBuilder.set(CaptureRequest.STATISTICS_FACE_DETECT_MODE, mode);
             if (VERBOSE) {
                 Log.v(TAG, "Start testing face detection mode " + mode);
             }
@@ -1272,17 +1278,17 @@
 
         Size maxPreviewSz = mOrderedPreviewSizes.get(0); // Max preview size.
 
-        byte[] toneMapModes = mStaticInfo.getAvailableToneMapModesChecked();
-        for (byte mode : toneMapModes) {
-            requestBuilder.set(CaptureRequest.TONEMAP_MODE, (int)mode);
+        int[] toneMapModes = mStaticInfo.getAvailableToneMapModesChecked();
+        for (int mode : toneMapModes) {
+            requestBuilder.set(CaptureRequest.TONEMAP_MODE, mode);
             if (VERBOSE) {
                 Log.v(TAG, "Testing tonemap mode " + mode);
             }
 
             if (mode == CaptureRequest.TONEMAP_MODE_CONTRAST_CURVE) {
-                requestBuilder.set(CaptureRequest.TONEMAP_CURVE_RED, TONEMAP_CURVE_LINEAR);
-                requestBuilder.set(CaptureRequest.TONEMAP_CURVE_GREEN, TONEMAP_CURVE_LINEAR);
-                requestBuilder.set(CaptureRequest.TONEMAP_CURVE_BLUE, TONEMAP_CURVE_LINEAR);
+                TonemapCurve tcLinear = new TonemapCurve(
+                        TONEMAP_CURVE_LINEAR, TONEMAP_CURVE_LINEAR, TONEMAP_CURVE_LINEAR);
+                requestBuilder.set(CaptureRequest.TONEMAP_CURVE, tcLinear);
                 // Create a new listener for each run to avoid the results from one run spill
                 // into another run.
                 listener = new SimpleCaptureListener();
@@ -1290,9 +1296,9 @@
                 verifyToneMapModeResults(listener, NUM_FRAMES_VERIFIED, mode,
                         TONEMAP_CURVE_LINEAR);
 
-                requestBuilder.set(CaptureRequest.TONEMAP_CURVE_RED, TONEMAP_CURVE_SRGB);
-                requestBuilder.set(CaptureRequest.TONEMAP_CURVE_GREEN, TONEMAP_CURVE_SRGB);
-                requestBuilder.set(CaptureRequest.TONEMAP_CURVE_BLUE, TONEMAP_CURVE_SRGB);
+                TonemapCurve tcSrgb = new TonemapCurve(
+                        TONEMAP_CURVE_SRGB, TONEMAP_CURVE_SRGB, TONEMAP_CURVE_SRGB);
+                requestBuilder.set(CaptureRequest.TONEMAP_CURVE, tcSrgb);
                 // Create a new listener for each run to avoid the results from one run spill
                 // into another run.
                 listener = new SimpleCaptureListener();
@@ -1335,18 +1341,16 @@
             CaptureResult result = listener.getCaptureResult(WAIT_FOR_RESULT_TIMEOUT_MS);
             mCollector.expectEquals("Capture result tonemap mode should match request", tonemapMode,
                     result.get(CaptureResult.TONEMAP_MODE));
-            float[] mapRed = result.get(CaptureResult.TONEMAP_CURVE_RED);
-            float[] mapGreen = result.get(CaptureResult.TONEMAP_CURVE_GREEN);
-            float[] mapBlue = result.get(CaptureResult.TONEMAP_CURVE_BLUE);
-            boolean redAvailable =
-                    mCollector.expectTrue("Tonemap curve red shouldn't be null for mode "
-                            + tonemapMode, mapRed != null);
-            boolean greenAvailable =
-                    mCollector.expectTrue("Tonemap curve red shouldn't be null for mode "
-                            + tonemapMode, mapGreen != null);
-            boolean blueAvailable =
-                    mCollector.expectTrue("Tonemap curve red shouldn't be null for mode "
-                            + tonemapMode, mapBlue != null);
+            TonemapCurve tc = getValueNotNull(result, CaptureResult.TONEMAP_CURVE);
+            int pointCount = tc.getPointCount(TonemapCurve.CHANNEL_RED);
+            float[] mapRed = new float[pointCount * TonemapCurve.POINT_SIZE];
+            pointCount = tc.getPointCount(TonemapCurve.CHANNEL_GREEN);
+            float[] mapGreen = new float[pointCount * TonemapCurve.POINT_SIZE];
+            pointCount = tc.getPointCount(TonemapCurve.CHANNEL_BLUE);
+            float[] mapBlue = new float[pointCount * TonemapCurve.POINT_SIZE];
+            tc.copyColorCurve(TonemapCurve.CHANNEL_RED, mapRed, 0);
+            tc.copyColorCurve(TonemapCurve.CHANNEL_GREEN, mapGreen, 0);
+            tc.copyColorCurve(TonemapCurve.CHANNEL_BLUE, mapBlue, 0);
             if (tonemapMode == CaptureResult.TONEMAP_MODE_CONTRAST_CURVE) {
                 /**
                  * TODO: need figure out a good way to measure the difference
@@ -1356,24 +1360,18 @@
             }
 
             // Tonemap curve result availability and basic sanity check for all modes.
-            if (redAvailable) {
-                mCollector.expectValuesInRange("Tonemap curve red values are out of range",
-                        CameraTestUtils.toObject(mapRed), /*min*/ZERO, /*max*/ONE);
-                mCollector.expectInRange("Tonemap curve red length is out of range",
-                        mapRed.length, MIN_TONEMAP_CURVE_POINTS, maxCurvePoints * 2);
-            }
-            if (greenAvailable) {
-                mCollector.expectValuesInRange("Tonemap curve green values are out of range",
-                        CameraTestUtils.toObject(mapGreen), /*min*/ZERO, /*max*/ONE);
-                mCollector.expectInRange("Tonemap curve green length is out of range",
-                        mapGreen.length, MIN_TONEMAP_CURVE_POINTS, maxCurvePoints * 2);
-            }
-            if (blueAvailable) {
-                mCollector.expectValuesInRange("Tonemap curve blue values are out of range",
-                        CameraTestUtils.toObject(mapBlue), /*min*/ZERO, /*max*/ONE);
-                mCollector.expectInRange("Tonemap curve blue length is out of range",
-                        mapBlue.length, MIN_TONEMAP_CURVE_POINTS, maxCurvePoints * 2);
-            }
+            mCollector.expectValuesInRange("Tonemap curve red values are out of range",
+                    CameraTestUtils.toObject(mapRed), /*min*/ZERO, /*max*/ONE);
+            mCollector.expectInRange("Tonemap curve red length is out of range",
+                    mapRed.length, MIN_TONEMAP_CURVE_POINTS, maxCurvePoints * 2);
+            mCollector.expectValuesInRange("Tonemap curve green values are out of range",
+                    CameraTestUtils.toObject(mapGreen), /*min*/ZERO, /*max*/ONE);
+            mCollector.expectInRange("Tonemap curve green length is out of range",
+                    mapGreen.length, MIN_TONEMAP_CURVE_POINTS, maxCurvePoints * 2);
+            mCollector.expectValuesInRange("Tonemap curve blue values are out of range",
+                    CameraTestUtils.toObject(mapBlue), /*min*/ZERO, /*max*/ONE);
+            mCollector.expectInRange("Tonemap curve blue length is out of range",
+                    mapBlue.length, MIN_TONEMAP_CURVE_POINTS, maxCurvePoints * 2);
         }
     }
 
@@ -1386,20 +1384,20 @@
      * </p>
      */
     private void awbModeAndLockTestByCamera() throws Exception {
-        byte[] awbModes = mStaticInfo.getAwbAvailableModesChecked();
+        int[] awbModes = mStaticInfo.getAwbAvailableModesChecked();
         Size maxPreviewSize = mOrderedPreviewSizes.get(0);
         CaptureRequest.Builder requestBuilder =
                 mCamera.createCaptureRequest(CameraDevice.TEMPLATE_PREVIEW);
         startPreview(requestBuilder, maxPreviewSize, /*listener*/null);
 
-        for (byte mode : awbModes) {
+        for (int mode : awbModes) {
             SimpleCaptureListener listener;
-            requestBuilder.set(CaptureRequest.CONTROL_AWB_MODE, (int)mode);
+            requestBuilder.set(CaptureRequest.CONTROL_AWB_MODE, mode);
             listener = new SimpleCaptureListener();
             mCamera.setRepeatingRequest(requestBuilder.build(), listener, mHandler);
 
             // Verify AWB mode in capture result.
-            verifyCaptureResultForKey(CaptureResult.CONTROL_AWB_MODE, (int)mode, listener,
+            verifyCaptureResultForKey(CaptureResult.CONTROL_AWB_MODE, mode, listener,
                     NUM_FRAMES_VERIFIED);
 
             // Verify color correction transform and gains stay unchanged after a lock.
@@ -1415,19 +1413,20 @@
     private void verifyAwbCaptureResultUnchanged(SimpleCaptureListener listener,
             int numFramesVerified) {
         CaptureResult result = listener.getCaptureResult(WAIT_FOR_RESULT_TIMEOUT_MS);
-        float[] lockedGains = getValueNotNull(result, CaptureResult.COLOR_CORRECTION_GAINS);
-        Rational[] lockedTransform =
+        RggbChannelVector lockedGains =
+                getValueNotNull(result, CaptureResult.COLOR_CORRECTION_GAINS);
+        ColorSpaceTransform lockedTransform =
                 getValueNotNull(result, CaptureResult.COLOR_CORRECTION_TRANSFORM);
 
         for (int i = 0; i < numFramesVerified; i++) {
             result = listener.getCaptureResult(WAIT_FOR_RESULT_TIMEOUT_MS);
             validateColorCorrectionResult(result);
 
-            float[] gains = getValueNotNull(result, CaptureResult.COLOR_CORRECTION_GAINS);
-            Rational[] transform =
+            RggbChannelVector gains = getValueNotNull(result, CaptureResult.COLOR_CORRECTION_GAINS);
+            ColorSpaceTransform transform =
                     getValueNotNull(result, CaptureResult.COLOR_CORRECTION_TRANSFORM);
             mCollector.expectEquals("Color correction gains should remain unchanged after awb lock",
-                    toObject(lockedGains), toObject(gains));
+                    lockedGains, gains);
             mCollector.expectEquals("Color correction transform should remain unchanged after"
                     + " awb lock", lockedTransform, transform);
         }
@@ -1443,20 +1442,20 @@
      * </p>
      */
     private void afModeTestByCamera() throws Exception {
-        byte[] afModes = mStaticInfo.getAfAvailableModesChecked();
+        int[] afModes = mStaticInfo.getAfAvailableModesChecked();
         Size maxPreviewSize = mOrderedPreviewSizes.get(0);
         CaptureRequest.Builder requestBuilder =
                 mCamera.createCaptureRequest(CameraDevice.TEMPLATE_PREVIEW);
         startPreview(requestBuilder, maxPreviewSize, /*listener*/null);
 
-        for (byte mode : afModes) {
+        for (int mode : afModes) {
             SimpleCaptureListener listener;
-            requestBuilder.set(CaptureRequest.CONTROL_AF_MODE, (int)mode);
+            requestBuilder.set(CaptureRequest.CONTROL_AF_MODE, mode);
             listener = new SimpleCaptureListener();
             mCamera.setRepeatingRequest(requestBuilder.build(), listener, mHandler);
 
             // Verify AF mode in capture result.
-            verifyCaptureResultForKey(CaptureResult.CONTROL_AF_MODE, (int)mode, listener,
+            verifyCaptureResultForKey(CaptureResult.CONTROL_AF_MODE, mode, listener,
                     NUM_FRAMES_VERIFIED);
 
             // Verify AF can finish a scan for CONTROL_AF_MODE_CONTINUOUS_* modes
@@ -1476,17 +1475,17 @@
      */
     private void stabilizationTestByCamera() throws Exception {
         // video stabilization test.
-        byte[] videoStabModes = mStaticInfo.getAvailableVideoStabilizationModesChecked();
-        byte[] opticalStabModes = mStaticInfo.getAvailableOpticalStabilizationChecked();
+        int[] videoStabModes = mStaticInfo.getAvailableVideoStabilizationModesChecked();
+        int[] opticalStabModes = mStaticInfo.getAvailableOpticalStabilizationChecked();
         Size maxPreviewSize = mOrderedPreviewSizes.get(0);
         CaptureRequest.Builder requestBuilder =
                 mCamera.createCaptureRequest(CameraDevice.TEMPLATE_PREVIEW);
         SimpleCaptureListener listener = new SimpleCaptureListener();
         startPreview(requestBuilder, maxPreviewSize, listener);
 
-        for ( byte mode : videoStabModes) {
+        for (int mode : videoStabModes) {
             listener = new SimpleCaptureListener();
-            requestBuilder.set(CaptureRequest.CONTROL_VIDEO_STABILIZATION_MODE, (int) mode);
+            requestBuilder.set(CaptureRequest.CONTROL_VIDEO_STABILIZATION_MODE, mode);
             mCamera.setRepeatingRequest(requestBuilder.build(), listener, mHandler);
             // TODO: enable below code when b/14059883 is fixed.
             /*
@@ -1518,7 +1517,7 @@
         final float maxZoom = mStaticInfo.getAvailableMaxDigitalZoomChecked();
         final Rect activeArraySize = mStaticInfo.getActiveArraySizeChecked();
         Rect[] cropRegions = new Rect[ZOOM_STEPS];
-        int [][] expectRegions = new int[ZOOM_STEPS][];
+        MeteringRectangle[][] expectRegions = new MeteringRectangle[ZOOM_STEPS][];
         Size maxPreviewSize = mOrderedPreviewSizes.get(0);
         CaptureRequest.Builder requestBuilder =
                 mCamera.createCaptureRequest(CameraDevice.TEMPLATE_PREVIEW);
@@ -1528,16 +1527,12 @@
 
         // Set algorithm regions to full active region
         // TODO: test more different 3A regions
-        final int[] algoDefaultRegion = new int[] {
-            0, // xmin
-            0, // ymin
-            activeArraySize.width() - 1,  // xmax
-            activeArraySize.height() - 1, // ymax
-            1, // weight
-        };
+        final MeteringRectangle[] defaultMeteringRect = new MeteringRectangle[] {
+                new MeteringRectangle (
+                        0, 0, activeArraySize.width(), activeArraySize.height(), 1)};
 
         for (int algo = 0; algo < NUM_ALGORITHMS; algo++) {
-            update3aRegion(requestBuilder, algo,  algoDefaultRegion);
+            update3aRegion(requestBuilder, algo,  defaultMeteringRect);
         }
 
         for (PointF center : TEST_ZOOM_CENTERS) {
@@ -1551,7 +1546,7 @@
                 requestBuilder.set(CaptureRequest.SCALER_CROP_REGION, cropRegions[i]);
                 requests[i] = requestBuilder.build();
                 expectRegions[i] = getExpectedOutputRegion(
-                        /*requestRegion*/algoDefaultRegion,
+                        /*requestRegion*/defaultMeteringRect,
                         /*cropRect*/     cropRegions[i]);
                 mCamera.capture(requests[i], listener, mHandler);
             }
@@ -1564,7 +1559,7 @@
                  Rect cropRegion = getValueNotNull(result, CaptureResult.SCALER_CROP_REGION);
                  // Verify Output 3A region is intersection of input 3A region and crop region
                  for (int algo = 0; algo < NUM_ALGORITHMS; algo++) {
-                     validate3aRegion(result,algo,  expectRegions[i]);
+                     validate3aRegion(result, algo, expectRegions[i]);
                  }
                  mCollector.expectEquals(" Request and result crop region should match",
                          cropRegions[i], cropRegion);
@@ -1575,7 +1570,7 @@
     }
 
     private void sceneModeTestByCamera() throws Exception {
-        byte[] sceneModes = mStaticInfo.getAvailableSceneModesChecked();
+        int[] sceneModes = mStaticInfo.getAvailableSceneModesChecked();
         Size maxPreviewSize = mOrderedPreviewSizes.get(0);
         CaptureRequest.Builder requestBuilder =
                 mCamera.createCaptureRequest(CameraDevice.TEMPLATE_PREVIEW);
@@ -1583,8 +1578,8 @@
         requestBuilder.set(CaptureRequest.CONTROL_MODE, CaptureRequest.CONTROL_MODE_USE_SCENE_MODE);
         startPreview(requestBuilder, maxPreviewSize, listener);
 
-        for(byte mode : sceneModes) {
-            requestBuilder.set(CaptureRequest.CONTROL_SCENE_MODE, (int)mode);
+        for(int mode : sceneModes) {
+            requestBuilder.set(CaptureRequest.CONTROL_SCENE_MODE, mode);
             listener = new SimpleCaptureListener();
             mCamera.setRepeatingRequest(requestBuilder.build(), listener, mHandler);
             // Enable below check  when b/14059883 is fixed.
@@ -1599,7 +1594,7 @@
     }
 
     private void effectModeTestByCamera() throws Exception {
-        byte[] effectModes = mStaticInfo.getAvailableEffectModesChecked();
+        int[] effectModes = mStaticInfo.getAvailableEffectModesChecked();
         Size maxPreviewSize = mOrderedPreviewSizes.get(0);
         CaptureRequest.Builder requestBuilder =
                 mCamera.createCaptureRequest(CameraDevice.TEMPLATE_PREVIEW);
@@ -1607,8 +1602,8 @@
         SimpleCaptureListener listener = new SimpleCaptureListener();
         startPreview(requestBuilder, maxPreviewSize, listener);
 
-        for(byte mode : effectModes) {
-            requestBuilder.set(CaptureRequest.CONTROL_EFFECT_MODE, (int)mode);
+        for(int mode : effectModes) {
+            requestBuilder.set(CaptureRequest.CONTROL_EFFECT_MODE, mode);
             listener = new SimpleCaptureListener();
             mCamera.setRepeatingRequest(requestBuilder.build(), listener, mHandler);
             // Enable below check  when b/14059883 is fixed.
@@ -1820,26 +1815,24 @@
      */
     private void verifyFpsNotSlowDown(CaptureRequest.Builder requestBuilder,
             int numFramesVerified)  throws Exception {
-        int[] fpsRanges = mStaticInfo.getAeAvailableTargetFpsRangesChecked();
+        Range<Integer>[] fpsRanges = mStaticInfo.getAeAvailableTargetFpsRangesChecked();
         boolean antiBandingOffIsSupported = mStaticInfo.isAntiBandingOffModeSupported();
-        final int FPS_RANGE_SIZE = 2;
-        int[] fpsRange = new int[FPS_RANGE_SIZE];
+        Range<Integer> fpsRange;
         SimpleCaptureListener resultListener;
 
-        for (int i = 0; i < fpsRanges.length; i += FPS_RANGE_SIZE) {
-            fpsRange[0] = fpsRanges[i];
-            fpsRange[1] = fpsRanges[i + 1];
+        for (int i = 0; i < fpsRanges.length; i += 1) {
+            fpsRange = fpsRanges[i];
             Size previewSz = getMaxPreviewSizeForFpsRange(fpsRange);
             // If unable to find a preview size, then log the failure, and skip this run.
             if (!mCollector.expectTrue(String.format(
-                    "Unable to find a preview size supporting given fps range [%d, %d]",
-                    fpsRange[0], fpsRange[1]), previewSz != null)) {
+                    "Unable to find a preview size supporting given fps range %s",
+                    fpsRange), previewSz != null)) {
                 continue;
             }
 
             if (VERBOSE) {
-                Log.v(TAG, String.format("Test fps range [%d, %d] for preview size %s",
-                        fpsRange[0], fpsRange[1], previewSz.toString()));
+                Log.v(TAG, String.format("Test fps range %s for preview size %s",
+                        fpsRange, previewSz.toString()));
             }
             requestBuilder.set(CaptureRequest.CONTROL_AE_TARGET_FPS_RANGE, fpsRange);
             // Turn off auto antibanding to avoid exposure time and frame duration interference
@@ -1858,7 +1851,7 @@
             resultListener = new SimpleCaptureListener();
             startPreview(requestBuilder, previewSz, resultListener);
             long[] frameDurationRange =
-                    new long[]{(long) (1e9 / fpsRange[1]), (long) (1e9 / fpsRange[0])};
+                    new long[]{(long) (1e9 / fpsRange.getUpper()), (long) (1e9 / fpsRange.getLower())};
             for (int j = 0; j < numFramesVerified; j++) {
                 CaptureResult result =
                         resultListener.getCaptureResult(WAIT_FOR_RESULT_TIMEOUT_MS);
@@ -1929,28 +1922,28 @@
      * if the specified 3A region is not supported by camera device.
      * @param requestBuilder The request to be updated
      * @param algoIdx The index to the algorithm. (AE: 0, AWB: 1, AF: 2)
-     * @param region The 3A region to be set
+     * @param regions The 3A regions to be set
      */
-    private void update3aRegion(CaptureRequest.Builder requestBuilder, int algoIdx, int[] region)
+    private void update3aRegion(
+            CaptureRequest.Builder requestBuilder, int algoIdx, MeteringRectangle[] regions)
     {
         int[] maxRegions = mStaticInfo.get3aMaxRegionsChecked();
 
-        if (region.length == 0 ||
-                region.length % LENGTH_ALGORITHM_REGION != 0) {
+        if (regions == null || regions.length == 0) {
             throw new IllegalArgumentException("Invalid input 3A region!");
         }
 
-        if (maxRegions[algoIdx] * LENGTH_ALGORITHM_REGION >= region.length)
+        if (maxRegions[algoIdx] >= regions.length)
         {
             switch (algoIdx) {
                 case INDEX_ALGORITHM_AE:
-                    requestBuilder.set(CaptureRequest.CONTROL_AE_REGIONS, region);
+                    requestBuilder.set(CaptureRequest.CONTROL_AE_REGIONS, regions);
                     break;
                 case INDEX_ALGORITHM_AWB:
-                    requestBuilder.set(CaptureRequest.CONTROL_AWB_REGIONS, region);
+                    requestBuilder.set(CaptureRequest.CONTROL_AWB_REGIONS, regions);
                     break;
                 case INDEX_ALGORITHM_AF:
-                    requestBuilder.set(CaptureRequest.CONTROL_AF_REGIONS, region);
+                    requestBuilder.set(CaptureRequest.CONTROL_AF_REGIONS, regions);
                     break;
                 default:
                     throw new IllegalArgumentException("Unknown 3A Algorithm!");
@@ -1963,17 +1956,13 @@
      * supported. Do nothing if the specified 3A region is not supported by camera device.
      * @param result The capture result to be validated
      * @param algoIdx The index to the algorithm. (AE: 0, AWB: 1, AF: 2)
-     * @param expectRegion The 3A region expected
+     * @param expectRegion The 3A regions expected in capture result
      */
-    private void validate3aRegion(CaptureResult result, int algoIdx, int[] expectRegion)
+    private void validate3aRegion(
+            CaptureResult result, int algoIdx, MeteringRectangle[] expectRegion)
     {
         int[] maxRegions = mStaticInfo.get3aMaxRegionsChecked();
-        int[] actualRegion;
-
-        if (expectRegion.length == 0 ||
-                expectRegion.length % LENGTH_ALGORITHM_REGION != 0) {
-            throw new IllegalArgumentException("Invalid expected 3A region!");
-        }
+        MeteringRectangle[] actualRegion;
 
         if (maxRegions[algoIdx] > 0)
         {
@@ -1993,8 +1982,7 @@
             mCollector.expectEquals(
                     "Expected 3A region: " + Arrays.toString(expectRegion) +
                     " does not match actual one: " + Arrays.toString(actualRegion),
-                    toObject(expectRegion),
-                    toObject(actualRegion));
+                    expectRegion, actualRegion);
         }
     }
 }
diff --git a/tests/tests/hardware/src/android/hardware/camera2/cts/CaptureResultTest.java b/tests/tests/hardware/src/android/hardware/camera2/cts/CaptureResultTest.java
index a66debe..dd7439f 100644
--- a/tests/tests/hardware/src/android/hardware/camera2/cts/CaptureResultTest.java
+++ b/tests/tests/hardware/src/android/hardware/camera2/cts/CaptureResultTest.java
@@ -111,7 +111,7 @@
                 requestBuilder.addTarget(mReaderSurface);
 
                 // Enable face detection if supported
-                byte[] faceModes = mStaticInfo.getAvailableFaceDetectModesChecked();
+                int[] faceModes = mStaticInfo.getAvailableFaceDetectModesChecked();
                 for (int i = 0; i < faceModes.length; i++) {
                     if (faceModes[i] == CameraMetadata.STATISTICS_FACE_DETECT_MODE_FULL) {
                         if (VERBOSE) {
@@ -241,9 +241,7 @@
         resultKeys.add(CaptureResult.FLASH_MODE);
         resultKeys.add(CaptureResult.FLASH_STATE);
         resultKeys.add(CaptureResult.HOT_PIXEL_MODE);
-        resultKeys.add(CaptureResult.JPEG_GPS_COORDINATES);
-        resultKeys.add(CaptureResult.JPEG_GPS_PROCESSING_METHOD);
-        resultKeys.add(CaptureResult.JPEG_GPS_TIMESTAMP);
+        resultKeys.add(CaptureResult.JPEG_GPS_LOCATION);
         resultKeys.add(CaptureResult.JPEG_ORIENTATION);
         resultKeys.add(CaptureResult.JPEG_QUALITY);
         resultKeys.add(CaptureResult.JPEG_THUMBNAIL_QUALITY);
@@ -271,13 +269,11 @@
         resultKeys.add(CaptureResult.STATISTICS_FACE_DETECT_MODE);
         resultKeys.add(CaptureResult.STATISTICS_HOT_PIXEL_MAP_MODE);
         resultKeys.add(CaptureResult.STATISTICS_FACES);
-        resultKeys.add(CaptureResult.STATISTICS_LENS_SHADING_MAP);
+        resultKeys.add(CaptureResult.STATISTICS_LENS_SHADING_CORRECTION_MAP);
         resultKeys.add(CaptureResult.STATISTICS_SCENE_FLICKER);
         resultKeys.add(CaptureResult.STATISTICS_HOT_PIXEL_MAP);
         resultKeys.add(CaptureResult.STATISTICS_LENS_SHADING_MAP_MODE);
-        resultKeys.add(CaptureResult.TONEMAP_CURVE_BLUE);
-        resultKeys.add(CaptureResult.TONEMAP_CURVE_GREEN);
-        resultKeys.add(CaptureResult.TONEMAP_CURVE_RED);
+        resultKeys.add(CaptureResult.TONEMAP_CURVE);
         resultKeys.add(CaptureResult.TONEMAP_MODE);
         resultKeys.add(CaptureResult.BLACK_LEVEL_LOCK);
 
diff --git a/tests/tests/hardware/src/android/hardware/camera2/cts/RecordingTest.java b/tests/tests/hardware/src/android/hardware/camera2/cts/RecordingTest.java
index ab9cddc..43031da 100644
--- a/tests/tests/hardware/src/android/hardware/camera2/cts/RecordingTest.java
+++ b/tests/tests/hardware/src/android/hardware/camera2/cts/RecordingTest.java
@@ -32,6 +32,7 @@
 import android.os.SystemClock;
 import android.test.suitebuilder.annotation.LargeTest;
 import android.util.Log;
+import android.util.Range;
 import android.view.SurfaceHolder;
 import android.view.Surface;
 
@@ -327,7 +328,7 @@
         CaptureRequest.Builder recordingRequestBuilder =
                 mCamera.createCaptureRequest(CameraDevice.TEMPLATE_RECORD);
         // Make sure camera output frame rate is set to correct value.
-        int[] fpsRange = {VIDEO_FRAME_RATE, VIDEO_FRAME_RATE};
+        Range<Integer> fpsRange = Range.create(VIDEO_FRAME_RATE, VIDEO_FRAME_RATE);
         recordingRequestBuilder.set(CaptureRequest.CONTROL_AE_TARGET_FPS_RANGE, fpsRange);
         recordingRequestBuilder.addTarget(mRecordingSurface);
         recordingRequestBuilder.addTarget(mPreviewSurface);
diff --git a/tests/tests/hardware/src/android/hardware/camera2/cts/StillCaptureTest.java b/tests/tests/hardware/src/android/hardware/camera2/cts/StillCaptureTest.java
index 9f0af9b..7daf859 100644
--- a/tests/tests/hardware/src/android/hardware/camera2/cts/StillCaptureTest.java
+++ b/tests/tests/hardware/src/android/hardware/camera2/cts/StillCaptureTest.java
@@ -23,22 +23,27 @@
 import android.hardware.camera2.CameraDevice;
 import android.hardware.camera2.CaptureRequest;
 import android.hardware.camera2.CaptureResult;
+import android.location.Location;
+import android.location.LocationManager;
 import android.util.Size;
 import android.hardware.camera2.cts.CameraTestUtils.SimpleCaptureListener;
 import android.hardware.camera2.cts.CameraTestUtils.SimpleImageReaderListener;
 import android.hardware.camera2.cts.helpers.Camera2Focuser;
 import android.hardware.camera2.cts.testcases.Camera2SurfaceViewTestCase;
+import android.hardware.camera2.params.MeteringRectangle;
 import android.media.ExifInterface;
 import android.media.Image;
 import android.os.Build;
 import android.os.ConditionVariable;
 import android.util.Log;
+import android.util.Range;
 import android.util.Rational;
 
 import com.android.ex.camera2.exceptions.TimeoutRuntimeException;
 
 import java.text.ParseException;
 import java.text.SimpleDateFormat;
+import java.util.ArrayList;
 import java.util.Arrays;
 import java.util.Date;
 import java.util.List;
@@ -46,7 +51,7 @@
 public class StillCaptureTest extends Camera2SurfaceViewTestCase {
     private static final String TAG = "StillCaptureTest";
     private static final boolean VERBOSE = Log.isLoggable(TAG, Log.VERBOSE);
-    private static final boolean DEBUG = Log.isLoggable(TAG, Log.DEBUG);;
+    private static final boolean DEBUG = Log.isLoggable(TAG, Log.DEBUG);
     private static final String JPEG_FILE_NAME = DEBUG_FILE_NAME_BASE + "/test.jpeg";
     // 60 second to accommodate the possible long exposure time.
     private static final int EXIF_DATETIME_ERROR_MARGIN_SEC = 60;
@@ -54,32 +59,39 @@
     // TODO: exposure time error margin need to be scaled with exposure time.
     private static final float EXIF_EXPOSURE_TIME_ERROR_MARGIN_SEC = 0.002f;
     private static final float EXIF_APERTURE_ERROR_MARGIN = 0.001f;
+    private static final Location sTestLocation0 = new Location(LocationManager.GPS_PROVIDER);
+    private static final Location sTestLocation1 = new Location(LocationManager.GPS_PROVIDER);
+    private static final Location sTestLocation2 = new Location(LocationManager.NETWORK_PROVIDER);
+    static {
+        sTestLocation0.setTime(1199145600L);
+        sTestLocation0.setLatitude(37.736071);
+        sTestLocation0.setLongitude(-122.441983);
+        sTestLocation0.setAltitude(21.0);
+
+        sTestLocation1.setTime(1199145601L);
+        sTestLocation1.setLatitude(0.736071);
+        sTestLocation1.setLongitude(0.441983);
+        sTestLocation1.setAltitude(1.0);
+
+        sTestLocation2.setTime(1199145602L);
+        sTestLocation2.setLatitude(-89.736071);
+        sTestLocation2.setLongitude(-179.441983);
+        sTestLocation2.setAltitude(100000.0);
+    }
     // Exif test data vectors.
     private static final ExifTestData[] EXIF_TEST_DATA = {
             new ExifTestData(
-                    /* coords */new double[] {
-                            37.736071, -122.441983, 21.0
-                    },
-                    /* procMethod */"GPS NETWORK HYBRID ARE ALL FINE.",
-                    /* timestamp */1199145600L,
+                    /*gpsLocation*/ sTestLocation0,
                     /* orientation */90,
                     /* jpgQuality */(byte) 80,
                     /* thumbQuality */(byte) 75),
             new ExifTestData(
-                    /* coords */new double[] {
-                            0.736071, 0.441983, 1.0
-                    },
-                    /* procMethod */"GPS",
-                    /* timestamp */1199145601L,
+                    /*gpsLocation*/ sTestLocation1,
                     /* orientation */180,
                     /* jpgQuality */(byte) 90,
                     /* thumbQuality */(byte) 85),
             new ExifTestData(
-                    /* coords */new double[] {
-                            -89.736071, -179.441983, 100000.0
-                    },
-                    /* procMethod */"NETWORK",
-                    /* timestamp */1199145602L,
+                    /*gpsLocation*/ sTestLocation2,
                     /* orientation */270,
                     /* jpgQuality */(byte) 100,
                     /* thumbQuality */(byte) 100)
@@ -254,9 +266,9 @@
                     continue;
                 }
 
-                int[][] aeRegions = get3ATestRegionsForCamera();
-                for (int i = 0; i < aeRegions.length; i++) {
-                    takePictureTestByCamera(aeRegions[i], /*awbRegions*/null, /*afRegions*/null);
+                ArrayList<MeteringRectangle[]> aeRegionTestCases = get3ARegionTestCasesForCamera();
+                for (MeteringRectangle[] aeRegions : aeRegionTestCases) {
+                    takePictureTestByCamera(aeRegions, /*awbRegions*/null, /*afRegions*/null);
                 }
             } finally {
                 closeDevice();
@@ -279,9 +291,9 @@
                     continue;
                 }
 
-                int[][] awbRegions = get3ATestRegionsForCamera();
-                for (int i = 0; i < awbRegions.length; i++) {
-                    takePictureTestByCamera(/*aeRegions*/null, awbRegions[i], /*afRegions*/null);
+                ArrayList<MeteringRectangle[]> awbRegionTestCases = get3ARegionTestCasesForCamera();
+                for (MeteringRectangle[] awbRegions : awbRegionTestCases) {
+                    takePictureTestByCamera(/*aeRegions*/null, awbRegions, /*afRegions*/null);
                 }
             } finally {
                 closeDevice();
@@ -304,9 +316,9 @@
                     continue;
                 }
 
-                int[][] afRegions = get3ATestRegionsForCamera();
-                for (int i = 0; i < afRegions.length; i++) {
-                    takePictureTestByCamera(/*aeRegions*/null, /*awbRegions*/null, afRegions[i]);
+                ArrayList<MeteringRectangle[]> afRegionTestCases = get3ARegionTestCasesForCamera();
+                for (MeteringRectangle[] afRegions : afRegionTestCases) {
+                    takePictureTestByCamera(/*aeRegions*/null, /*awbRegions*/null, afRegions);
                 }
             } finally {
                 closeDevice();
@@ -381,8 +393,10 @@
      * @param awbRegions AWB regions for this capture
      * @param afRegions AF regions for this capture
      */
-    private void takePictureTestByCamera(int[] aeRegions, int[] awbRegions, int[] afRegions)
-            throws Exception {
+    private void takePictureTestByCamera(
+            MeteringRectangle[] aeRegions, MeteringRectangle[] awbRegions,
+            MeteringRectangle[] afRegions) throws Exception {
+
         boolean hasFocuser = mStaticInfo.hasFocuser();
 
         Size maxStillSz = mOrderedStillSizes.get(0);
@@ -459,10 +473,10 @@
                 previewRequest.get(CaptureRequest.CONTROL_AWB_MODE),
                 result.get(CaptureResult.CONTROL_AWB_MODE));
         if (canSetAwbRegion) {
-            int[] resultAwbRegions = getValueNotNull(result, CaptureResult.CONTROL_AWB_REGIONS);
+            MeteringRectangle[] resultAwbRegions =
+                    getValueNotNull(result, CaptureResult.CONTROL_AWB_REGIONS);
             mCollector.expectEquals("AWB regions in result and request should be same",
-                    toObject(awbRegions),
-                    toObject(resultAwbRegions));
+                    awbRegions, resultAwbRegions);
         }
 
         /**
@@ -486,10 +500,10 @@
                 previewRequest.get(CaptureRequest.CONTROL_AE_MODE),
                 result.get(CaptureResult.CONTROL_AE_MODE));
         if (canSetAeRegion) {
-            int[] resultAeRegions = getValueNotNull(result, CaptureResult.CONTROL_AE_REGIONS);
+            MeteringRectangle[] resultAeRegions =
+                    getValueNotNull(result, CaptureResult.CONTROL_AE_REGIONS);
             mCollector.expectEquals("AE regions in result and request should be same",
-                    toObject(aeRegions),
-                    toObject(resultAeRegions));
+                    aeRegions, resultAeRegions);
         }
 
         /**
@@ -504,10 +518,10 @@
                 stillRequest.get(CaptureRequest.CONTROL_AF_MODE),
                 result.get(CaptureResult.CONTROL_AF_MODE));
         if (canSetAfRegion) {
-            int[] resultAfRegions = getValueNotNull(result, CaptureResult.CONTROL_AF_REGIONS);
+            MeteringRectangle[] resultAfRegions =
+                    getValueNotNull(result, CaptureResult.CONTROL_AF_REGIONS);
             mCollector.expectEquals("AF regions in result and request should be same",
-                    toObject(afRegions),
-                    toObject(resultAfRegions));
+                    afRegions, resultAfRegions);
         }
 
         if (hasFocuser) {
@@ -535,10 +549,10 @@
         SimpleAutoFocusListener afListener = new SimpleAutoFocusListener();
         Camera2Focuser focuser = new Camera2Focuser(mCamera, mPreviewSurface, afListener,
                 mStaticInfo.getCharacteristics(), mHandler);
-        int[][] testAfRegions = get3ATestRegionsForCamera();
+        ArrayList<MeteringRectangle[]> testAfRegions = get3ARegionTestCasesForCamera();
 
-        for (int i = 0; i < testAfRegions.length; i++) {
-            focuser.touchForAutoFocus(testAfRegions[i]);
+        for (MeteringRectangle[] afRegions : testAfRegions) {
+            focuser.touchForAutoFocus(afRegions);
             afListener.waitForAutoFocusDone(WAIT_FOR_FOCUS_DONE_TIMEOUT_MS);
             focuser.cancelAutoFocus();
         }
@@ -616,6 +630,15 @@
         // TODO: validate DNG metadata tags.
     }
 
+    private static boolean areGpsFieldsEqual(Location a, Location b) {
+        if (a == null || b == null) {
+            return false;
+        }
+
+        return a.getTime() == b.getTime() && a.getLatitude() == b.getLatitude() &&
+                a.getLongitude() == b.getLongitude() && a.getAltitude() == b.getAltitude() &&
+                a.getProvider() == b.getProvider();
+    }
     /**
      * Issue a Jpeg capture and validate the exif information.
      * <p>
@@ -661,10 +684,7 @@
              *   present and semantically correct.
              */
             stillBuilder.set(CaptureRequest.JPEG_THUMBNAIL_SIZE, testThumbnailSizes[i]);
-            stillBuilder.set(CaptureRequest.JPEG_GPS_COORDINATES, EXIF_TEST_DATA[i].gpsCoordinates);
-            stillBuilder.set(CaptureRequest.JPEG_GPS_PROCESSING_METHOD,
-                    EXIF_TEST_DATA[i].gpsProcessingMethod);
-            stillBuilder.set(CaptureRequest.JPEG_GPS_TIMESTAMP, EXIF_TEST_DATA[i].gpsTimeStamp);
+            stillBuilder.set(CaptureRequest.JPEG_GPS_LOCATION, EXIF_TEST_DATA[i].gpsLocation);
             stillBuilder.set(CaptureRequest.JPEG_ORIENTATION, EXIF_TEST_DATA[i].jpegOrientation);
             stillBuilder.set(CaptureRequest.JPEG_QUALITY, EXIF_TEST_DATA[i].jpegQuality);
             stillBuilder.set(CaptureRequest.JPEG_THUMBNAIL_QUALITY,
@@ -674,15 +694,9 @@
             mCollector.expectEquals("JPEG thumbnail size request set and get should match",
                     testThumbnailSizes[i],
                     stillBuilder.get(CaptureRequest.JPEG_THUMBNAIL_SIZE));
-            mCollector.expectEquals("GPS coordinates request set and get should match.",
-                    toObject(EXIF_TEST_DATA[i].gpsCoordinates),
-                    toObject(stillBuilder.get(CaptureRequest.JPEG_GPS_COORDINATES)));
-            mCollector.expectEquals("GPS processing method request set and get should match",
-                    EXIF_TEST_DATA[i].gpsProcessingMethod,
-                    stillBuilder.get(CaptureRequest.JPEG_GPS_PROCESSING_METHOD));
-            mCollector.expectEquals("GPS time stamp request set and get should match",
-                    EXIF_TEST_DATA[i].gpsTimeStamp,
-                    stillBuilder.get(CaptureRequest.JPEG_GPS_TIMESTAMP));
+            mCollector.expectTrue("GPS locations request set and get should match.",
+                    areGpsFieldsEqual(EXIF_TEST_DATA[i].gpsLocation,
+                            stillBuilder.get(CaptureRequest.JPEG_GPS_LOCATION)));
             mCollector.expectEquals("JPEG orientation request set and get should match",
                     EXIF_TEST_DATA[i].jpegOrientation,
                     stillBuilder.get(CaptureRequest.JPEG_ORIENTATION));
@@ -719,18 +733,12 @@
             mCollector.expectEquals("JPEG thumbnail size result and request should match",
                     testThumbnailSizes[i],
                     stillResult.get(CaptureResult.JPEG_THUMBNAIL_SIZE));
-            CaptureResult.Key<double[]> gpsCoordsKey = CaptureResult.JPEG_GPS_COORDINATES;
-            if (mCollector.expectKeyValueNotNull(stillResult, gpsCoordsKey) != null) {
-                mCollector.expectEquals("GPS coordinates result and request should match.",
-                        toObject(EXIF_TEST_DATA[i].gpsCoordinates),
-                        toObject(stillResult.get(gpsCoordsKey)));
+            if (mCollector.expectKeyValueNotNull(stillResult, CaptureResult.JPEG_GPS_LOCATION) !=
+                    null) {
+                mCollector.expectTrue("GPS location result and request should match.",
+                        areGpsFieldsEqual(EXIF_TEST_DATA[i].gpsLocation,
+                                stillResult.get(CaptureResult.JPEG_GPS_LOCATION)));
             }
-            mCollector.expectEquals("GPS processing method result and request should match",
-                    EXIF_TEST_DATA[i].gpsProcessingMethod,
-                    stillResult.get(CaptureResult.JPEG_GPS_PROCESSING_METHOD));
-            mCollector.expectEquals("GPS time stamp result and request should match",
-                    EXIF_TEST_DATA[i].gpsTimeStamp,
-                    stillResult.get(CaptureResult.JPEG_GPS_TIMESTAMP));
             mCollector.expectEquals("JPEG orientation result and request should match",
                     EXIF_TEST_DATA[i].jpegOrientation,
                     stillResult.get(CaptureResult.JPEG_ORIENTATION));
@@ -942,18 +950,14 @@
      * Immutable class wrapping the exif test data.
      */
     private static class ExifTestData {
-        public final double[] gpsCoordinates;
-        public final String gpsProcessingMethod;
-        public final long gpsTimeStamp;
+        public final Location gpsLocation;
         public final int jpegOrientation;
         public final byte jpegQuality;
         public final byte thumbnailQuality;
 
-        public ExifTestData(double[] coords, String procMethod, long timeStamp, int orientation,
+        public ExifTestData(Location location, int orientation,
                 byte jpgQuality, byte thumbQuality) {
-            gpsCoordinates = coords;
-            gpsProcessingMethod = procMethod;
-            gpsTimeStamp = timeStamp;
+            gpsLocation = location;
             jpegOrientation = orientation;
             jpegQuality = jpgQuality;
             thumbnailQuality = thumbQuality;
@@ -961,10 +965,10 @@
     }
 
     private void aeCompensationTestByCamera() throws Exception {
-        int[] compensationRange = mStaticInfo.getAeCompensationRangeChecked();
+        Range<Integer> compensationRange = mStaticInfo.getAeCompensationRangeChecked();
         Rational step = mStaticInfo.getAeCompensationStepChecked();
         int stepsPerEv = (int) Math.round(1.0 / step.toFloat());
-        int numSteps = (compensationRange[1] - compensationRange[0]) / stepsPerEv;
+        int numSteps = (compensationRange.getUpper() - compensationRange.getLower()) / stepsPerEv;
 
         Size maxStillSz = mOrderedStillSizes.get(0);
         Size maxPreviewSz = mOrderedPreviewSizes.get(0);
@@ -993,7 +997,7 @@
                 maxStillSz, resultListener, numSteps, imageListener);
 
         for (int i = 0; i <= numSteps; i++) {
-            int exposureCompensation = i * stepsPerEv + compensationRange[0];
+            int exposureCompensation = i * stepsPerEv + compensationRange.getLower();
 
             // Wait for AE to be stabilized before capture: CONVERGED or FLASH_REQUIRED.
             waitForAeStable(resultListener);
@@ -1072,10 +1076,8 @@
 
     private long getMaxExposureValue(CaptureRequest.Builder request, long maxExposureTimeUs,
                 long maxSensitivity)  throws Exception {
-        int[] fpsRange = request.get(CaptureRequest.CONTROL_AE_TARGET_FPS_RANGE);
-        mCollector.expectEquals("Length of CaptureResult FPS range must be 2",
-                2, fpsRange.length);
-        long maxFrameDurationUs = Math.round(1000000.0 / fpsRange[0]);
+        Range<Integer> fpsRange = request.get(CaptureRequest.CONTROL_AE_TARGET_FPS_RANGE);
+        long maxFrameDurationUs = Math.round(1000000.0 / fpsRange.getLower());
         long currentMaxExposureTimeUs = Math.min(maxFrameDurationUs, maxExposureTimeUs);
         return currentMaxExposureTimeUs * maxSensitivity;
     }
@@ -1206,71 +1208,89 @@
     }
 
     /**
-     * Get 5 3A test square regions, one is at center, the other four are at corners of
+     * Get 5 3A region test cases, each with one square region in it.
+     * The first one is at center, the other four are at corners of
      * active array rectangle.
      *
      * @return array of test 3A regions
      */
-    private int[][] get3ATestRegionsForCamera() {
+    private ArrayList<MeteringRectangle[]> get3ARegionTestCasesForCamera() {
         final int TEST_3A_REGION_NUM = 5;
-        final int NUM_ELEMENT_IN_REGION = 5;
         final int DEFAULT_REGION_WEIGHT = 30;
         final int DEFAULT_REGION_SCALE_RATIO = 8;
-        int[][] regions = new int[TEST_3A_REGION_NUM][NUM_ELEMENT_IN_REGION];
+        ArrayList<MeteringRectangle[]> testCases =
+                new ArrayList<MeteringRectangle[]>(TEST_3A_REGION_NUM);
         final Rect activeArraySize = mStaticInfo.getActiveArraySizeChecked();
-        int regionWidth = activeArraySize.width() / DEFAULT_REGION_SCALE_RATIO;
-        int regionHeight = activeArraySize.height() / DEFAULT_REGION_SCALE_RATIO;
+        int regionWidth = activeArraySize.width() / DEFAULT_REGION_SCALE_RATIO - 1;
+        int regionHeight = activeArraySize.height() / DEFAULT_REGION_SCALE_RATIO - 1;
         int centerX = activeArraySize.width() / 2;
         int centerY = activeArraySize.height() / 2;
         int bottomRightX = activeArraySize.width() - 1;
         int bottomRightY = activeArraySize.height() - 1;
 
         // Center region
-        int i = 0;
-        regions[i][0] = centerX - regionWidth / 2;       // xmin
-        regions[i][1] = centerY - regionHeight / 2;      // ymin
-        regions[i][2] = centerX + regionWidth / 2 - 1;   // xmax
-        regions[i][3] = centerY + regionHeight / 2 - 1;  // ymax
-        regions[i][4] = DEFAULT_REGION_WEIGHT;
-        i++;
+        testCases.add(
+                new MeteringRectangle[] {
+                    new MeteringRectangle(
+                            centerX - regionWidth / 2,  // x
+                            centerY - regionHeight / 2, // y
+                            regionWidth,                // width
+                            regionHeight,               // height
+                            DEFAULT_REGION_WEIGHT)});
 
         // Upper left corner
-        regions[i][0] = 0;                // xmin
-        regions[i][1] = 0;                // ymin
-        regions[i][2] = regionWidth - 1;  // xmax
-        regions[i][3] = regionHeight - 1; // ymax
-        regions[i][4] = DEFAULT_REGION_WEIGHT;
-        i++;
+        testCases.add(
+                new MeteringRectangle[] {
+                    new MeteringRectangle(
+                            0,                // x
+                            0,                // y
+                            regionWidth,      // width
+                            regionHeight,     // height
+                            DEFAULT_REGION_WEIGHT)});
 
         // Upper right corner
-        regions[i][0] = activeArraySize.width() - regionWidth; // xmin
-        regions[i][1] = 0;                                     // ymin
-        regions[i][2] = bottomRightX;                          // xmax
-        regions[i][3] = regionHeight - 1;                      // ymax
-        regions[i][4] = DEFAULT_REGION_WEIGHT;
-        i++;
+        testCases.add(
+                new MeteringRectangle[] {
+                    new MeteringRectangle(
+                            bottomRightX - regionWidth, // x
+                            0,                          // y
+                            regionWidth,                // width
+                            regionHeight,               // height
+                            DEFAULT_REGION_WEIGHT)});
 
         // Bootom left corner
-        regions[i][0] = 0;                                       // xmin
-        regions[i][1] = activeArraySize.height() - regionHeight; // ymin
-        regions[i][2] = regionWidth - 1;                         // xmax
-        regions[i][3] = bottomRightY;                            // ymax
-        regions[i][4] = DEFAULT_REGION_WEIGHT;
-        i++;
+        testCases.add(
+                new MeteringRectangle[] {
+                    new MeteringRectangle(
+                            0,                           // x
+                            bottomRightY - regionHeight, // y
+                            regionWidth,                 // width
+                            regionHeight,                // height
+                            DEFAULT_REGION_WEIGHT)});
 
         // Bootom right corner
-        regions[i][0] = activeArraySize.width() - regionWidth;   // xmin
-        regions[i][1] = activeArraySize.height() - regionHeight; // ymin
-        regions[i][2] = bottomRightX;                            // xmax
-        regions[i][3] = bottomRightY;                            // ymax
-        regions[i][4] = DEFAULT_REGION_WEIGHT;
-        i++;
+        testCases.add(
+                new MeteringRectangle[] {
+                    new MeteringRectangle(
+                            bottomRightX - regionWidth,  // x
+                            bottomRightY - regionHeight, // y
+                            regionWidth,                 // width
+                            regionHeight,                // height
+                            DEFAULT_REGION_WEIGHT)});
 
         if (VERBOSE) {
-            Log.v(TAG, "Generated test regions are: " + Arrays.deepToString(regions));
+            StringBuilder sb = new StringBuilder();
+            for (MeteringRectangle[] mr : testCases) {
+                sb.append("{");
+                sb.append(Arrays.toString(mr));
+                sb.append("}, ");
+            }
+            if (sb.length() > 1)
+                sb.setLength(sb.length() - 2); // Remove the redundant comma and space at the end
+            Log.v(TAG, "Generated test regions are: " + sb.toString());
         }
 
-        return regions;
+        return testCases;
     }
 
     private boolean isRegionsSupportedFor3A(int index) {
diff --git a/tests/tests/hardware/src/android/hardware/camera2/cts/SurfaceViewPreviewTest.java b/tests/tests/hardware/src/android/hardware/camera2/cts/SurfaceViewPreviewTest.java
index d569fab..37b6357 100644
--- a/tests/tests/hardware/src/android/hardware/camera2/cts/SurfaceViewPreviewTest.java
+++ b/tests/tests/hardware/src/android/hardware/camera2/cts/SurfaceViewPreviewTest.java
@@ -28,6 +28,7 @@
 import android.hardware.camera2.cts.CameraTestUtils.SimpleCaptureListener;
 import android.hardware.camera2.cts.testcases.Camera2SurfaceViewTestCase;
 import android.util.Log;
+import android.util.Range;
 
 import org.mockito.ArgumentCaptor;
 import org.mockito.ArgumentMatcher;
@@ -122,17 +123,16 @@
     private void previewFpsRangeTestByCamera() throws Exception {
         final int FPS_RANGE_SIZE = 2;
         Size maxPreviewSz = mOrderedPreviewSizes.get(0);
-        int[] fpsRanges = mStaticInfo.getAeAvailableTargetFpsRangesChecked();
+        Range<Integer>[] fpsRanges = mStaticInfo.getAeAvailableTargetFpsRangesChecked();
         boolean antiBandingOffIsSupported = mStaticInfo.isAntiBandingOffModeSupported();
-        int[] fpsRange = new int[FPS_RANGE_SIZE];
+        Range<Integer> fpsRange;
         CaptureRequest.Builder requestBuilder =
                 mCamera.createCaptureRequest(CameraDevice.TEMPLATE_PREVIEW);
         SimpleCaptureListener resultListener = new SimpleCaptureListener();
         startPreview(requestBuilder, maxPreviewSz, resultListener);
 
-        for (int i = 0; i < fpsRanges.length; i += FPS_RANGE_SIZE) {
-            fpsRange[0] = fpsRanges[i];
-            fpsRange[1] = fpsRanges[i + 1];
+        for (int i = 0; i < fpsRanges.length; i += 1) {
+            fpsRange = fpsRanges[i];
 
             requestBuilder.set(CaptureRequest.CONTROL_AE_TARGET_FPS_RANGE, fpsRange);
             // Turn off auto antibanding to avoid exposure time and frame duration interference
@@ -159,11 +159,11 @@
     }
 
     private void verifyPreviewTargetFpsRange(SimpleCaptureListener resultListener,
-            int numFramesVerified, int[] fpsRange, Size previewSz) {
+            int numFramesVerified, Range<Integer> fpsRange, Size previewSz) {
         CaptureResult result = resultListener.getCaptureResult(WAIT_FOR_RESULT_TIMEOUT_MS);
         long frameDuration = getValueNotNull(result, CaptureResult.SENSOR_FRAME_DURATION);
         long[] frameDurationRange =
-                new long[]{(long) (1e9 / fpsRange[1]), (long) (1e9 / fpsRange[0])};
+                new long[]{(long) (1e9 / fpsRange.getUpper()), (long) (1e9 / fpsRange.getLower())};
         mCollector.expectInRange(
                 "Frame duration must be in the range of " + Arrays.toString(frameDurationRange),
                 frameDuration, (long) (frameDurationRange[0] * (1 - FRAME_DURATION_ERROR_MARGIN)),
diff --git a/tests/tests/hardware/src/android/hardware/camera2/cts/helpers/Camera2Focuser.java b/tests/tests/hardware/src/android/hardware/camera2/cts/helpers/Camera2Focuser.java
index b1fd4a1..ff4af2d 100644
--- a/tests/tests/hardware/src/android/hardware/camera2/cts/helpers/Camera2Focuser.java
+++ b/tests/tests/hardware/src/android/hardware/camera2/cts/helpers/Camera2Focuser.java
@@ -21,6 +21,7 @@
 import android.hardware.camera2.CameraCharacteristics;
 import android.hardware.camera2.CameraDevice;
 import android.hardware.camera2.CameraDevice.CaptureListener;
+import android.hardware.camera2.params.MeteringRectangle;
 import android.hardware.camera2.CaptureRequest;
 import android.hardware.camera2.CaptureResult;
 import android.hardware.camera2.TotalCaptureResult;
@@ -50,11 +51,10 @@
     private final AutoFocusListener mAutoFocusListener;
     private final CameraDevice mCamera;
     private final Surface mRequestSurface;
-    private final int AF_REGION_NUM_ELEMENTS = 5;
     private final CameraCharacteristics mStaticInfo;
 
     private int mAfRun = 0;
-    private int[] mAfRegions; // int x AF_REGION_NUM_ELEMENTS array.
+    private MeteringRectangle[] mAfRegions;
     private boolean mLocked = false;
     private boolean mSuccess = false;
     private CaptureRequest.Builder mRepeatingBuilder;
@@ -165,7 +165,8 @@
      * array size is used if afRegions is null.
      * @throws CameraAccessException
      */
-    public synchronized void touchForAutoFocus(int[] afRegions) throws CameraAccessException {
+    public synchronized void touchForAutoFocus(MeteringRectangle[] afRegions)
+            throws CameraAccessException {
         startAutoFocusLocked(/*active*/true, afRegions);
     }
 
@@ -182,7 +183,8 @@
      *            array size is used if afRegions is null.
      * @throws CameraAccessException
      */
-    public synchronized void startAutoFocus(int[] afRegions) throws CameraAccessException {
+    public synchronized void startAutoFocus(MeteringRectangle[] afRegions)
+            throws CameraAccessException {
         startAutoFocusLocked(/*forceActive*/false, afRegions);
     }
 
@@ -222,7 +224,9 @@
         return mRepeatingBuilder.get(CaptureRequest.CONTROL_AF_MODE);
     }
 
-    private void startAutoFocusLocked(boolean forceActive, int[] afRegions) throws CameraAccessException {
+    private void startAutoFocusLocked(
+            boolean forceActive, MeteringRectangle[] afRegions) throws CameraAccessException {
+
         setAfRegions(afRegions);
         mAfRun++;
 
@@ -282,9 +286,6 @@
      * @throws CameraAccessException
      */
     private CaptureRequest.Builder createRequestBuilder() throws CameraAccessException {
-        if (mAfRegions == null) {
-            throw new IllegalStateException("AF regions are not initialized yet");
-        }
         CaptureRequest.Builder requestBuilder =
                 mCamera.createCaptureRequest(CameraDevice.TEMPLATE_PREVIEW);
 
@@ -298,17 +299,16 @@
      * Set AF regions, fall back to default region if afRegions is null.
      *
      * @param afRegions The AF regions to set
-     * @throws IllegalArgumentException if the region is malformed (length is 0
-     *             or not multiple times of {@value #AF_REGION_NUM_ELEMENTS}).
+     * @throws IllegalArgumentException if the region is malformed (length is 0).
      */
-    private void setAfRegions(int[] afRegions) {
+    private void setAfRegions(MeteringRectangle[] afRegions) {
         if (afRegions == null) {
             setDefaultAfRegions();
             return;
         }
         // Throw IAE if AF regions are malformed.
-        if (afRegions.length % AF_REGION_NUM_ELEMENTS != 0 || afRegions.length == 0) {
-            throw new IllegalArgumentException("afRegions is malformed, length: " + afRegions.length);
+        if (afRegions.length == 0) {
+            throw new IllegalArgumentException("afRegions is malformed, length: 0");
         }
 
         mAfRegions = afRegions;
@@ -325,7 +325,8 @@
 
         // Initialize AF regions with all zeros, meaning that it is up to camera device to device
         // the regions used by AF.
-        mAfRegions = new int[]{0, 0, 0, 0, 0};
+        mAfRegions = new MeteringRectangle[] {
+                new MeteringRectangle(0, 0, 0, 0, 0)};
     }
     private CaptureListener createCaptureListener() {
 
diff --git a/tests/tests/hardware/src/android/hardware/camera2/cts/helpers/StaticMetadata.java b/tests/tests/hardware/src/android/hardware/camera2/cts/helpers/StaticMetadata.java
index e99d64a..76f79f7 100644
--- a/tests/tests/hardware/src/android/hardware/camera2/cts/helpers/StaticMetadata.java
+++ b/tests/tests/hardware/src/android/hardware/camera2/cts/helpers/StaticMetadata.java
@@ -21,10 +21,12 @@
 import android.hardware.camera2.CameraCharacteristics;
 import android.hardware.camera2.CameraCharacteristics.Key;
 import android.hardware.camera2.CameraMetadata;
+import android.util.Range;
 import android.util.Size;
 import android.hardware.camera2.cts.CameraTestUtils;
 import android.hardware.camera2.params.StreamConfigurationMap;
 import android.util.Log;
+import android.util.Range;
 import android.util.Rational;
 
 import junit.framework.Assert;
@@ -309,12 +311,12 @@
      *
      * @return The array contains available anti-banding modes.
      */
-    public byte[] getAeAvailableAntiBandingModesChecked() {
-        Key<byte[]> key = CameraCharacteristics.CONTROL_AE_AVAILABLE_ANTIBANDING_MODES;
-        byte[] modes = getValueFromKeyNonNull(key);
+    public int[] getAeAvailableAntiBandingModesChecked() {
+        Key<int[]> key = CameraCharacteristics.CONTROL_AE_AVAILABLE_ANTIBANDING_MODES;
+        int[] modes = getValueFromKeyNonNull(key);
 
         boolean foundAuto = false;
-        for (byte mode : modes) {
+        for (int mode : modes) {
             checkTrueForKey(key, "mode value " + mode + " is out if range",
                     mode >= CameraMetadata.CONTROL_AE_ANTIBANDING_MODE_OFF ||
                     mode <= CameraMetadata.CONTROL_AE_ANTIBANDING_MODE_AUTO);
@@ -335,10 +337,10 @@
      * @return true if antibanding OFF mode is supported, false otherwise.
      */
     public boolean isAntiBandingOffModeSupported() {
-        List<Byte> antiBandingModes =
+        List<Integer> antiBandingModes =
                 Arrays.asList(CameraTestUtils.toObject(getAeAvailableAntiBandingModesChecked()));
 
-        return antiBandingModes.contains((byte)CameraMetadata.CONTROL_AE_ANTIBANDING_MODE_OFF);
+        return antiBandingModes.contains(CameraMetadata.CONTROL_AE_ANTIBANDING_MODE_OFF);
     }
 
     public Boolean getFlashInfoChecked() {
@@ -445,20 +447,20 @@
      *
      * @return The non-null array of available face detection modes
      */
-    public byte[] getAvailableFaceDetectModesChecked() {
-        Key<byte[]> key = CameraCharacteristics.STATISTICS_INFO_AVAILABLE_FACE_DETECT_MODES;
-        byte[] modes = getValueFromKeyNonNull(key);
+    public int[] getAvailableFaceDetectModesChecked() {
+        Key<int[]> key = CameraCharacteristics.STATISTICS_INFO_AVAILABLE_FACE_DETECT_MODES;
+        int[] modes = getValueFromKeyNonNull(key);
 
         if (modes == null) {
-            return new byte[0];
+            return new int[0];
         }
 
-        List<Byte> modeList = Arrays.asList(CameraTestUtils.toObject(modes));
+        List<Integer> modeList = Arrays.asList(CameraTestUtils.toObject(modes));
         checkTrueForKey(key, "Array should contain OFF mode",
-                modeList.contains((byte)CameraMetadata.STATISTICS_FACE_DETECT_MODE_OFF));
+                modeList.contains(CameraMetadata.STATISTICS_FACE_DETECT_MODE_OFF));
         checkElementDistinct(key, modeList);
-        checkArrayValuesInRange(key, modes, (byte)CameraMetadata.STATISTICS_FACE_DETECT_MODE_OFF,
-                (byte)CameraMetadata.STATISTICS_FACE_DETECT_MODE_FULL);
+        checkArrayValuesInRange(key, modes, CameraMetadata.STATISTICS_FACE_DETECT_MODE_OFF,
+                CameraMetadata.STATISTICS_FACE_DETECT_MODE_FULL);
 
         return modes;
     }
@@ -476,9 +478,9 @@
             return 0;
         }
 
-        List<Byte> faceDetectModes =
+        List<Integer> faceDetectModes =
                 Arrays.asList(CameraTestUtils.toObject(getAvailableFaceDetectModesChecked()));
-        if (faceDetectModes.contains((byte)CameraMetadata.STATISTICS_FACE_DETECT_MODE_OFF) &&
+        if (faceDetectModes.contains(CameraMetadata.STATISTICS_FACE_DETECT_MODE_OFF) &&
                 faceDetectModes.size() == 1) {
             checkTrueForKey(key, " value must be 0 if only OFF mode is supported in "
                     + "availableFaceDetectionModes", count == 0);
@@ -497,26 +499,26 @@
      *
      * @return the availalbe tone map modes
      */
-    public byte[] getAvailableToneMapModesChecked() {
-        Key<byte[]> key = CameraCharacteristics.TONEMAP_AVAILABLE_TONE_MAP_MODES;
-        byte[] modes = getValueFromKeyNonNull(key);
+    public int[] getAvailableToneMapModesChecked() {
+        Key<int[]> key = CameraCharacteristics.TONEMAP_AVAILABLE_TONE_MAP_MODES;
+        int[] modes = getValueFromKeyNonNull(key);
 
         if (modes == null) {
-            return new byte[0];
+            return new int[0];
         }
 
-        List<Byte> modeList = Arrays.asList(CameraTestUtils.toObject(modes));
+        List<Integer> modeList = Arrays.asList(CameraTestUtils.toObject(modes));
         checkTrueForKey(key, " Camera devices must always support FAST mode",
-                modeList.contains((byte)CameraMetadata.TONEMAP_MODE_FAST));
+                modeList.contains(CameraMetadata.TONEMAP_MODE_FAST));
         if (isHardwareLevelFull()) {
             checkTrueForKey(key, "Full-capability camera devices must support"
                     + "CONTRAST_CURVE mode",
-                    modeList.contains((byte)CameraMetadata.TONEMAP_MODE_CONTRAST_CURVE) &&
-                    modeList.contains((byte)CameraMetadata.TONEMAP_MODE_FAST));
+                    modeList.contains(CameraMetadata.TONEMAP_MODE_CONTRAST_CURVE) &&
+                    modeList.contains(CameraMetadata.TONEMAP_MODE_FAST));
         }
         checkElementDistinct(key, modeList);
-        checkArrayValuesInRange(key, modes, (byte)CameraMetadata.TONEMAP_MODE_CONTRAST_CURVE,
-                (byte)CameraMetadata.TONEMAP_MODE_HIGH_QUALITY);
+        checkArrayValuesInRange(key, modes, CameraMetadata.TONEMAP_MODE_CONTRAST_CURVE,
+                CameraMetadata.TONEMAP_MODE_HIGH_QUALITY);
 
         return modes;
     }
@@ -534,9 +536,9 @@
             return 0;
         }
 
-        List<Byte> modeList =
+        List<Integer> modeList =
                 Arrays.asList(CameraTestUtils.toObject(getAvailableToneMapModesChecked()));
-        if (modeList.contains((byte)CameraMetadata.TONEMAP_MODE_CONTRAST_CURVE)) {
+        if (modeList.contains(CameraMetadata.TONEMAP_MODE_CONTRAST_CURVE)) {
             checkTrueForKey(key, "Full-capability camera device must support maxCurvePoints "
                     + ">= " + TONEMAP_MAX_CURVE_POINTS_AT_LEAST,
                     count >= TONEMAP_MAX_CURVE_POINTS_AT_LEAST);
@@ -687,12 +689,14 @@
      * @return The value reported by the camera device or the defaultValue otherwise.
      */
     public int getSensitivityMinimumOrDefault(int defaultValue) {
-        return getArrayElementOrDefault(
-                CameraCharacteristics.SENSOR_INFO_SENSITIVITY_RANGE,
-                defaultValue,
-                "minimum",
-                SENSOR_INFO_SENSITIVITY_RANGE_MIN,
-                SENSOR_INFO_SENSITIVITY_RANGE_SIZE);
+        Range<Integer> range = getValueFromKeyNonNull(
+                CameraCharacteristics.SENSOR_INFO_SENSITIVITY_RANGE);
+        if (range == null) {
+            failKeyCheck(CameraCharacteristics.SENSOR_INFO_SENSITIVITY_RANGE,
+                    "had no valid minimum value; using default of " + defaultValue);
+            return defaultValue;
+        }
+        return range.getLower();
     }
 
     /**
@@ -718,12 +722,14 @@
      * @return The value reported by the camera device or the defaultValue otherwise.
      */
     public int getSensitivityMaximumOrDefault(int defaultValue) {
-        return getArrayElementOrDefault(
-                CameraCharacteristics.SENSOR_INFO_SENSITIVITY_RANGE,
-                defaultValue,
-                "maximum",
-                SENSOR_INFO_SENSITIVITY_RANGE_MAX,
-                SENSOR_INFO_SENSITIVITY_RANGE_SIZE);
+        Range<Integer> range = getValueFromKeyNonNull(
+                CameraCharacteristics.SENSOR_INFO_SENSITIVITY_RANGE);
+        if (range == null) {
+            failKeyCheck(CameraCharacteristics.SENSOR_INFO_SENSITIVITY_RANGE,
+                    "had no valid maximum value; using default of " + defaultValue);
+            return defaultValue;
+        }
+        return range.getUpper();
     }
 
     /**
@@ -736,12 +742,14 @@
      * @return The value reported by the camera device or the defaultValue otherwise.
      */
     public long getExposureMinimumOrDefault(long defaultValue) {
-        return getArrayElementOrDefault(
-                CameraCharacteristics.SENSOR_INFO_EXPOSURE_TIME_RANGE,
-                defaultValue,
-                "minimum",
-                SENSOR_INFO_EXPOSURE_TIME_RANGE_MIN,
-                SENSOR_INFO_EXPOSURE_TIME_RANGE_SIZE);
+        Range<Long> range = getValueFromKeyNonNull(
+                CameraCharacteristics.SENSOR_INFO_EXPOSURE_TIME_RANGE);
+        if (range == null) {
+            failKeyCheck(CameraCharacteristics.SENSOR_INFO_EXPOSURE_TIME_RANGE,
+                    "had no valid minimum value; using default of " + defaultValue);
+            return defaultValue;
+        }
+        return range.getLower();
     }
 
     /**
@@ -767,12 +775,14 @@
      * @return The value reported by the camera device or the defaultValue otherwise.
      */
     public long getExposureMaximumOrDefault(long defaultValue) {
-        return getArrayElementOrDefault(
-                CameraCharacteristics.SENSOR_INFO_EXPOSURE_TIME_RANGE,
-                defaultValue,
-                "maximum",
-                SENSOR_INFO_EXPOSURE_TIME_RANGE_MAX,
-                SENSOR_INFO_EXPOSURE_TIME_RANGE_SIZE);
+        Range<Long> range = getValueFromKeyNonNull(
+                CameraCharacteristics.SENSOR_INFO_EXPOSURE_TIME_RANGE);
+        if (range == null) {
+            failKeyCheck(CameraCharacteristics.SENSOR_INFO_EXPOSURE_TIME_RANGE,
+                    "had no valid maximum value; using default of " + defaultValue);
+            return defaultValue;
+        }
+        return range.getUpper();
     }
 
     /**
@@ -796,14 +806,14 @@
      * have to abort the execution even the aeMode list is invalid.</p>
      * @return AE available modes
      */
-    public byte[] getAeAvailableModesChecked() {
-        Key<byte[]> modesKey = CameraCharacteristics.CONTROL_AE_AVAILABLE_MODES;
-        byte[] modes = getValueFromKeyNonNull(modesKey);
+    public int[] getAeAvailableModesChecked() {
+        Key<int[]> modesKey = CameraCharacteristics.CONTROL_AE_AVAILABLE_MODES;
+        int[] modes = getValueFromKeyNonNull(modesKey);
         if (modes == null) {
-            modes = new byte[0];
+            modes = new int[0];
         }
         List<Integer> modeList = new ArrayList<Integer>();
-        for (byte mode : modes) {
+        for (int mode : modes) {
             modeList.add((int)(mode));
         }
         checkTrueForKey(modesKey, "value is empty", !modeList.isEmpty());
@@ -842,7 +852,7 @@
         checkTrueForKey(modesKey, "Full capability device must have OFF mode", condition);
 
         // Boundary check.
-        for (byte mode : modes) {
+        for (int mode : modes) {
             checkTrueForKey(modesKey, "Value " + mode + " is out of bound",
                     mode >= CameraMetadata.CONTROL_AE_MODE_OFF
                     && mode <= CameraMetadata.CONTROL_AE_MODE_ON_AUTO_FLASH_REDEYE);
@@ -857,21 +867,21 @@
      * @return array that contains available AWB modes, empty array if awbAvailableModes is
      * unavailable.
      */
-    public byte[] getAwbAvailableModesChecked() {
-        Key<byte[]> key =
+    public int[] getAwbAvailableModesChecked() {
+        Key<int[]> key =
                 CameraCharacteristics.CONTROL_AWB_AVAILABLE_MODES;
-        byte[] awbModes = getValueFromKeyNonNull(key);
+        int[] awbModes = getValueFromKeyNonNull(key);
 
         if (awbModes == null) {
-            return new byte[0];
+            return new int[0];
         }
 
-        List<Byte> modesList = Arrays.asList(CameraTestUtils.toObject(awbModes));
+        List<Integer> modesList = Arrays.asList(CameraTestUtils.toObject(awbModes));
         checkTrueForKey(key, " All camera devices must support AUTO mode",
-                modesList.contains((byte)CameraMetadata.CONTROL_AWB_MODE_AUTO));
+                modesList.contains(CameraMetadata.CONTROL_AWB_MODE_AUTO));
         if (isHardwareLevelFull()) {
             checkTrueForKey(key, " Full capability camera devices must support OFF mode",
-                    modesList.contains((byte)CameraMetadata.CONTROL_AWB_MODE_OFF));
+                    modesList.contains(CameraMetadata.CONTROL_AWB_MODE_OFF));
         }
 
         return awbModes;
@@ -883,21 +893,21 @@
      * @return array that contains available AF modes, empty array if afAvailableModes is
      * unavailable.
      */
-    public byte[] getAfAvailableModesChecked() {
-        Key<byte[]> key =
+    public int[] getAfAvailableModesChecked() {
+        Key<int[]> key =
                 CameraCharacteristics.CONTROL_AF_AVAILABLE_MODES;
-        byte[] afModes = getValueFromKeyNonNull(key);
+        int[] afModes = getValueFromKeyNonNull(key);
 
         if (afModes == null) {
-            return new byte[0];
+            return new int[0];
         }
 
-        List<Byte> modesList = Arrays.asList(CameraTestUtils.toObject(afModes));
+        List<Integer> modesList = Arrays.asList(CameraTestUtils.toObject(afModes));
         checkTrueForKey(key, " All camera devices must support OFF mode",
-                modesList.contains((byte)CameraMetadata.CONTROL_AF_MODE_OFF));
+                modesList.contains(CameraMetadata.CONTROL_AF_MODE_OFF));
         if (hasFocuser()) {
             checkTrueForKey(key, " Camera devices that have focuser units must support AUTO mode",
-                    modesList.contains((byte)CameraMetadata.CONTROL_AF_MODE_AUTO));
+                    modesList.contains(CameraMetadata.CONTROL_AF_MODE_AUTO));
         }
 
         return afModes;
@@ -984,27 +994,24 @@
      *
      * @return Empty int array if aeAvailableTargetFpsRanges is invalid.
      */
-    public int[] getAeAvailableTargetFpsRangesChecked() {
-        final int NUM_ELEMENTS_IN_FPS_RANGE = 2;
-        Key<int[]> key =
+    @SuppressWarnings("raw")
+    public Range<Integer>[] getAeAvailableTargetFpsRangesChecked() {
+        Key<Range<Integer>[]> key =
                 CameraCharacteristics.CONTROL_AE_AVAILABLE_TARGET_FPS_RANGES;
-        int[] fpsRanges = getValueFromKeyNonNull(key);
+        Range<Integer>[] fpsRanges = getValueFromKeyNonNull(key);
 
         if (fpsRanges == null) {
-            return new int[0];
+            return new Range[0];
         }
 
-        checkTrueForKey(key, "array length is invalid", fpsRanges.length
-                % NUM_ELEMENTS_IN_FPS_RANGE == 0);
         // Round down to 2 boundary if it is not integer times of 2, to avoid array out of bound
         // in case the above check fails.
-        int fpsRangeLength = (fpsRanges.length / NUM_ELEMENTS_IN_FPS_RANGE)
-                * NUM_ELEMENTS_IN_FPS_RANGE;
+        int fpsRangeLength = fpsRanges.length;
         int minFps, maxFps;
         long maxFrameDuration = getMaxFrameDurationChecked();
-        for (int i = 0; i < fpsRangeLength; i += NUM_ELEMENTS_IN_FPS_RANGE) {
-            minFps = fpsRanges[i];
-            maxFps = fpsRanges[i + 1];
+        for (int i = 0; i < fpsRangeLength; i += 1) {
+            minFps = fpsRanges[i].getLower();
+            maxFps = fpsRanges[i].getUpper();
             checkTrueForKey(key, " min fps must be no larger than max fps!",
                     minFps > 0 && maxFps >= minFps);
             long maxDuration = (long) (1e9 / minFps);
@@ -1063,40 +1070,40 @@
         return minDurationMap;
     }
 
-    public byte[] getAvailableEdgeModesChecked() {
-        Key<byte[]> key = CameraCharacteristics.EDGE_AVAILABLE_EDGE_MODES;
-        byte[] edgeModes = getValueFromKeyNonNull(key);
+    public int[] getAvailableEdgeModesChecked() {
+        Key<int[]> key = CameraCharacteristics.EDGE_AVAILABLE_EDGE_MODES;
+        int[] edgeModes = getValueFromKeyNonNull(key);
 
         if (edgeModes == null) {
-            return new byte[0];
+            return new int[0];
         }
 
         // Full device should always include OFF and FAST
         if (isHardwareLevelFull()) {
-            List<Byte> modeList = Arrays.asList(CameraTestUtils.toObject(edgeModes));
+            List<Integer> modeList = Arrays.asList(CameraTestUtils.toObject(edgeModes));
             checkTrueForKey(key, "Full device must contain OFF and FAST edge modes",
-                    modeList.contains((byte)CameraMetadata.EDGE_MODE_OFF) &&
-                    modeList.contains((byte)CameraMetadata.EDGE_MODE_FAST));
+                    modeList.contains(CameraMetadata.EDGE_MODE_OFF) &&
+                    modeList.contains(CameraMetadata.EDGE_MODE_FAST));
         }
 
         return edgeModes;
     }
 
-    public byte[] getAvailableNoiseReductionModesChecked() {
-        Key<byte[]> key =
+    public int[] getAvailableNoiseReductionModesChecked() {
+        Key<int[]> key =
                 CameraCharacteristics.NOISE_REDUCTION_AVAILABLE_NOISE_REDUCTION_MODES;
-        byte[] noiseReductionModes = getValueFromKeyNonNull(key);
+        int[] noiseReductionModes = getValueFromKeyNonNull(key);
 
         if (noiseReductionModes == null) {
-            return new byte[0];
+            return new int[0];
         }
 
         // Full device should always include OFF and FAST
         if (isHardwareLevelFull()) {
-            List<Byte> modeList = Arrays.asList(CameraTestUtils.toObject(noiseReductionModes));
+            List<Integer> modeList = Arrays.asList(CameraTestUtils.toObject(noiseReductionModes));
             checkTrueForKey(key, "Full device must contain OFF and FAST noise reduction modes",
-                    modeList.contains((byte)CameraMetadata.NOISE_REDUCTION_MODE_OFF) &&
-                    modeList.contains((byte)CameraMetadata.NOISE_REDUCTION_MODE_FAST));
+                    modeList.contains(CameraMetadata.NOISE_REDUCTION_MODE_OFF) &&
+                    modeList.contains(CameraMetadata.NOISE_REDUCTION_MODE_FAST));
         }
 
         return noiseReductionModes;
@@ -1126,26 +1133,21 @@
      *
      * @return default value if the value is null or malformed.
      */
-    public int[] getAeCompensationRangeChecked() {
-        Key<int[]> key =
+    public Range<Integer> getAeCompensationRangeChecked() {
+        Key<Range<Integer>> key =
                 CameraCharacteristics.CONTROL_AE_COMPENSATION_RANGE;
-        int[] compensationRange = getValueFromKeyNonNull(key);
+        Range<Integer> compensationRange = getValueFromKeyNonNull(key);
         float compensationStep = getAeCompensationStepChecked().toFloat();
-        final int[] DEFAULT_RANGE = new int[] {
+        final Range<Integer> DEFAULT_RANGE = Range.create(
                 (int)(CONTROL_AE_COMPENSATION_RANGE_DEFAULT_MIN / compensationStep),
-                (int)(CONTROL_AE_COMPENSATION_RANGE_DEFAULT_MAX / compensationStep)};
+                (int)(CONTROL_AE_COMPENSATION_RANGE_DEFAULT_MAX / compensationStep));
         if (compensationRange == null) {
             return DEFAULT_RANGE;
         }
 
-        checkTrueForKey(key, " value must have 2 elements", compensationRange.length == 2);
-        if (compensationRange.length != 2) {
-            return DEFAULT_RANGE;
-        }
-
-        checkTrueForKey(key, " range value must be at least " + Arrays.toString(DEFAULT_RANGE),
-               compensationRange[0] <= DEFAULT_RANGE[0] &&
-               compensationRange[1] >= DEFAULT_RANGE[1]);
+        checkTrueForKey(key, " range value must be at least " + DEFAULT_RANGE,
+               compensationRange.getLower() <= DEFAULT_RANGE.getLower() &&
+               compensationRange.getUpper() >= DEFAULT_RANGE.getUpper());
 
         return compensationRange;
     }
@@ -1155,21 +1157,21 @@
      *
      * @return available video stabilization modes, empty array if it is unavailable.
      */
-    public byte[] getAvailableVideoStabilizationModesChecked() {
-        Key<byte[]> key =
+    public int[] getAvailableVideoStabilizationModesChecked() {
+        Key<int[]> key =
                 CameraCharacteristics.CONTROL_AVAILABLE_VIDEO_STABILIZATION_MODES;
-        byte[] modes = getValueFromKeyNonNull(key);
+        int[] modes = getValueFromKeyNonNull(key);
 
         if (modes == null) {
-            return new byte[0];
+            return new int[0];
         }
 
-        List<Byte> modeList = Arrays.asList(CameraTestUtils.toObject(modes));
+        List<Integer> modeList = Arrays.asList(CameraTestUtils.toObject(modes));
         checkTrueForKey(key, " All device should support OFF mode",
-                modeList.contains((byte)CameraMetadata.CONTROL_VIDEO_STABILIZATION_MODE_OFF));
+                modeList.contains(CameraMetadata.CONTROL_VIDEO_STABILIZATION_MODE_OFF));
         checkArrayValuesInRange(key, modes,
-                (byte)CameraMetadata.CONTROL_VIDEO_STABILIZATION_MODE_OFF,
-                (byte)CameraMetadata.CONTROL_VIDEO_STABILIZATION_MODE_ON);
+                CameraMetadata.CONTROL_VIDEO_STABILIZATION_MODE_OFF,
+                CameraMetadata.CONTROL_VIDEO_STABILIZATION_MODE_ON);
 
         return modes;
     }
@@ -1179,18 +1181,18 @@
      *
      * @return available optical stabilization modes, empty array if it is unavailable.
      */
-    public byte[] getAvailableOpticalStabilizationChecked() {
-        Key<byte[]> key =
+    public int[] getAvailableOpticalStabilizationChecked() {
+        Key<int[]> key =
                 CameraCharacteristics.LENS_INFO_AVAILABLE_OPTICAL_STABILIZATION;
-        byte[] modes = getValueFromKeyNonNull(key);
+        int[] modes = getValueFromKeyNonNull(key);
 
         if (modes == null) {
-            return new byte[0];
+            return new int[0];
         }
 
         checkArrayValuesInRange(key, modes,
-                (byte)CameraMetadata.LENS_OPTICAL_STABILIZATION_MODE_OFF,
-                (byte)CameraMetadata.LENS_OPTICAL_STABILIZATION_MODE_ON);
+                CameraMetadata.LENS_OPTICAL_STABILIZATION_MODE_OFF,
+                CameraMetadata.LENS_OPTICAL_STABILIZATION_MODE_ON);
 
         return modes;
     }
@@ -1214,38 +1216,38 @@
         return maxZoom;
     }
 
-    public byte[] getAvailableSceneModesChecked() {
-        Key<byte[]> key =
+    public int[] getAvailableSceneModesChecked() {
+        Key<int[]> key =
                 CameraCharacteristics.CONTROL_AVAILABLE_SCENE_MODES;
-        byte[] modes = getValueFromKeyNonNull(key);
+        int[] modes = getValueFromKeyNonNull(key);
 
         if (modes == null) {
-            return new byte[0];
+            return new int[0];
         }
 
-        List<Byte> modeList = Arrays.asList(CameraTestUtils.toObject(modes));
+        List<Integer> modeList = Arrays.asList(CameraTestUtils.toObject(modes));
         // FACE_PRIORITY must be included if face detection is supported.
         if (getMaxFaceCountChecked() > 0) {
             checkTrueForKey(key, " FACE_PRIORITY must be included if face detection is supported",
-                    modeList.contains((byte)CameraMetadata.CONTROL_SCENE_MODE_FACE_PRIORITY));
+                    modeList.contains(CameraMetadata.CONTROL_SCENE_MODE_FACE_PRIORITY));
         }
 
         return modes;
     }
 
-    public byte[] getAvailableEffectModesChecked() {
-        Key<byte[]> key =
+    public int[] getAvailableEffectModesChecked() {
+        Key<int[]> key =
                 CameraCharacteristics.CONTROL_AVAILABLE_EFFECTS;
-        byte[] modes = getValueFromKeyNonNull(key);
+        int[] modes = getValueFromKeyNonNull(key);
 
         if (modes == null) {
-            return new byte[0];
+            return new int[0];
         }
 
-        List<Byte> modeList = Arrays.asList(CameraTestUtils.toObject(modes));
+        List<Integer> modeList = Arrays.asList(CameraTestUtils.toObject(modes));
         // OFF must be included.
         checkTrueForKey(key, " OFF must be included",
-                modeList.contains((byte)CameraMetadata.CONTROL_EFFECT_MODE_OFF));
+                modeList.contains(CameraMetadata.CONTROL_EFFECT_MODE_OFF));
 
         return modes;
     }
diff --git a/tests/tests/hardware/src/android/hardware/camera2/cts/testcases/Camera2SurfaceViewTestCase.java b/tests/tests/hardware/src/android/hardware/camera2/cts/testcases/Camera2SurfaceViewTestCase.java
index 7470f24..a169f7e 100644
--- a/tests/tests/hardware/src/android/hardware/camera2/cts/testcases/Camera2SurfaceViewTestCase.java
+++ b/tests/tests/hardware/src/android/hardware/camera2/cts/testcases/Camera2SurfaceViewTestCase.java
@@ -37,6 +37,7 @@
 import android.hardware.camera2.CaptureRequest;
 import android.hardware.camera2.CaptureResult;
 import android.util.Size;
+import android.util.Range;
 import android.hardware.camera2.CameraDevice.CaptureListener;
 import android.hardware.camera2.cts.Camera2SurfaceViewStubActivity;
 import android.hardware.camera2.cts.CameraTestUtils;
@@ -523,8 +524,8 @@
      * @param fpsRange The fps range the returned size must support.
      * @return max size that support the given fps range.
      */
-    protected Size getMaxPreviewSizeForFpsRange(int[] fpsRange) {
-        if (fpsRange == null || fpsRange[0] <= 0 || fpsRange[1] <= 0) {
+    protected Size getMaxPreviewSizeForFpsRange(Range<Integer> fpsRange) {
+        if (fpsRange == null || fpsRange.getLower() <= 0 || fpsRange.getUpper() <= 0) {
             throw new IllegalArgumentException("Invalid fps range argument");
         }
         if (mOrderedPreviewSizes == null || mMinPreviewFrameDurationMap == null) {
@@ -533,7 +534,7 @@
         }
 
         long[] frameDurationRange =
-                new long[]{(long) (1e9 / fpsRange[1]), (long) (1e9 / fpsRange[0])};
+                new long[]{(long) (1e9 / fpsRange.getUpper()), (long) (1e9 / fpsRange.getLower())};
         for (Size size : mOrderedPreviewSizes) {
             long minDuration = mMinPreviewFrameDurationMap.get(size);
             if (minDuration <= frameDurationRange[0]) {
diff --git a/tests/tests/media/libmediandkjni/native-media-jni.cpp b/tests/tests/media/libmediandkjni/native-media-jni.cpp
index 9adc887..51d2cf2 100644
--- a/tests/tests/media/libmediandkjni/native-media-jni.cpp
+++ b/tests/tests/media/libmediandkjni/native-media-jni.cpp
@@ -129,7 +129,7 @@
         sizes.add(n);
         sizes.add(AMediaExtractor_getSampleTrackIndex(ex));
         sizes.add(AMediaExtractor_getSampleFlags(ex));
-        sizes.add(AMediaExtractor_getSampletime(ex));
+        sizes.add(AMediaExtractor_getSampleTime(ex));
         AMediaExtractor_advance(ex);
     }
 
@@ -279,7 +279,7 @@
                     ALOGV("EOS");
                     //break;
                 }
-                int64_t presentationTimeUs = AMediaExtractor_getSampletime(ex);
+                int64_t presentationTimeUs = AMediaExtractor_getSampleTime(ex);
 
                 AMediaCodec_queueInputBuffer(codec[t], bufidx, 0, sampleSize, presentationTimeUs,
                         sawInputEOS[t] ? AMEDIACODEC_BUFFER_FLAG_END_OF_STREAM : 0);
@@ -421,7 +421,7 @@
                 sawInputEOS = true;
                 ALOGV("EOS");
             }
-            int64_t presentationTimeUs = AMediaExtractor_getSampletime(ex);
+            int64_t presentationTimeUs = AMediaExtractor_getSampleTime(ex);
 
             AMediaCodec_queueInputBuffer(codec, bufidx, 0, sampleSize, presentationTimeUs,
                     sawInputEOS ? AMEDIACODEC_BUFFER_FLAG_END_OF_STREAM : 0);
@@ -504,7 +504,7 @@
         }
         info.offset = 0;
         info.size = n;
-        info.presentationTimeUs = AMediaExtractor_getSampletime(ex);
+        info.presentationTimeUs = AMediaExtractor_getSampleTime(ex);
         info.flags = AMediaExtractor_getSampleFlags(ex);
 
         size_t idx = (size_t) AMediaExtractor_getSampleTrackIndex(ex);