Merge "Remove wifi MAC addr access test" into nyc-dev
diff --git a/OldCtsTestCaseList.mk b/OldCtsTestCaseList.mk
index 1c6bd7f..d2eb85b 100644
--- a/OldCtsTestCaseList.mk
+++ b/OldCtsTestCaseList.mk
@@ -155,12 +155,12 @@
     CtsAppTestCases \
     CtsAppWidgetTestCases \
     CtsAssistTestCases \
-    CtsAutomotiveTestCases \
     CtsBluetoothTestCases \
     CtsBrowserTestCases \
     CtsCalendarcommon2TestCases \
     CtsCallLogTestCases \
     CtsCameraTestCases \
+    CtsCarTestCases \
     CtsContentTestCases \
     CtsDatabaseTestCases \
     CtsDisplayTestCases \
@@ -196,6 +196,7 @@
     CtsNetTestCasesLegacyApi22 \
     CtsNetTestCasesLegacyPermission22 \
     CtsNetSecConfigAttributeTestCases \
+    CtsNetSecConfigCleartextTrafficTestCases \
     CtsNetSecConfigBasicDebugDisabledTestCases \
     CtsNetSecConfigBasicDebugEnabledTestCases \
     CtsNetSecConfigBasicDomainConfigTestCases \
diff --git a/hostsidetests/appsecurity/src/android/appsecurity/cts/DocumentsTest.java b/hostsidetests/appsecurity/src/android/appsecurity/cts/DocumentsTest.java
index 25ee645..c2f17c53 100644
--- a/hostsidetests/appsecurity/src/android/appsecurity/cts/DocumentsTest.java
+++ b/hostsidetests/appsecurity/src/android/appsecurity/cts/DocumentsTest.java
@@ -109,6 +109,16 @@
                 "testOpenExternalDirectory_notAskedAgain");
     }
 
+    public void testOpenExternalDirectory_deniesOnceButAllowsAskingAgain() throws Exception {
+        runDeviceTests(CLIENT_PKG, ".DocumentsClientTest",
+                "testOpenExternalDirectory_deniesOnceButAllowsAskingAgain");
+    }
+
+    public void testOpenExternalDirectory_deniesOnceForAll() throws Exception {
+        runDeviceTests(CLIENT_PKG, ".DocumentsClientTest",
+                "testOpenExternalDirectory_deniesOnceForAll");
+    }
+
     public void testOpenExternalDirectory_userAcceptsNewDirectory() throws Exception {
         // TODO: figure out a better way to remove the directory.
         final String command = "rm -rf /sdcard/Pictures";
diff --git a/hostsidetests/appsecurity/test-apps/DocumentClient/src/com/android/cts/documentclient/DocumentsClientTest.java b/hostsidetests/appsecurity/test-apps/DocumentClient/src/com/android/cts/documentclient/DocumentsClientTest.java
index 69583a7..6c9108d 100644
--- a/hostsidetests/appsecurity/test-apps/DocumentClient/src/com/android/cts/documentclient/DocumentsClientTest.java
+++ b/hostsidetests/appsecurity/test-apps/DocumentClient/src/com/android/cts/documentclient/DocumentsClientTest.java
@@ -384,14 +384,10 @@
     public void testOpenExternalDirectory_userRejects() throws Exception {
         if (!supportedHardware()) return;
 
-        final String externalRoot = getExternalStorageDirectory().getPath();
-
         final StorageVolume primaryVolume = getPrimaryVolume();
 
         // Tests user clicking DENY button, for all valid directories.
         for (String directory : STANDARD_DIRECTORIES) {
-            final Uri uri = Uri.fromFile(new File(externalRoot, directory));
-
             final UiAlertDialog dialog = openExternalDirectoryValidPath(primaryVolume, directory);
             dialog.noButton.click();
             assertActivityFailed();
@@ -430,6 +426,56 @@
         assertNotEqual(grantedUri, grantedUri2);
     }
 
+    public void testOpenExternalDirectory_deniesOnceButAllowsAskingAgain() throws Exception {
+        if (!supportedHardware())
+            return;
+
+        for (StorageVolume volume : getVolumes()) {
+            // Rejects the first attempt...
+            UiAlertDialog dialog = openExternalDirectoryValidPath(volume, DIRECTORY_DCIM);
+            dialog.assertDoNotAskAgainVisibility(false);
+            dialog.noButton.click();
+            assertActivityFailed();
+
+            // ...and the second.
+            dialog = openExternalDirectoryValidPath(volume, DIRECTORY_DCIM);
+            dialog.assertDoNotAskAgainVisibility(true);
+            dialog.noButton.click();
+            assertActivityFailed();
+
+            // Third time is a charm...
+            userAcceptsOpenExternalDirectoryTest(volume, DIRECTORY_DCIM);
+        }
+    }
+
+    public void testOpenExternalDirectory_deniesOnceForAll() throws Exception {
+        if (!supportedHardware())
+            return;
+        for (StorageVolume volume : getVolumes()) {
+            // Rejects the first attempt...
+            UiAlertDialog dialog = openExternalDirectoryValidPath(volume, DIRECTORY_RINGTONES);
+            dialog.assertDoNotAskAgainVisibility(false);
+            dialog.noButton.click();
+            assertActivityFailed();
+
+            // ...and the second, checking the box
+            dialog = openExternalDirectoryValidPath(volume, DIRECTORY_RINGTONES);
+            UiObject checkbox = dialog.assertDoNotAskAgainVisibility(true);
+            assertTrue("checkbox should not be checkable", checkbox.isCheckable());
+            assertFalse("checkbox should not be checked", checkbox.isChecked());
+            checkbox.click();
+            assertTrue("checkbox should be checked", checkbox.isChecked()); // Sanity check
+            assertFalse("allow button should be disabled", dialog.yesButton.isEnabled());
+
+            dialog.noButton.click();
+            assertActivityFailed();
+
+            // Third strike out...
+            sendOpenExternalDirectoryIntent(volume, DIRECTORY_RINGTONES);
+            assertActivityFailed();
+        }
+    }
+
     private Uri userAcceptsOpenExternalDirectoryTest(StorageVolume volume, String directoryName)
             throws Exception {
         // Asserts dialog contain the proper message.
@@ -721,6 +767,7 @@
     }
 
     private final class UiAlertDialog {
+        final UiObject dialog;
         final UiObject messageText;
         final UiObject yesButton;
         final UiObject noButton;
@@ -729,11 +776,31 @@
             final String id = "android:id/parentPanel";
             boolean gotIt = mDevice.wait(Until.hasObject(By.res(id)), TIMEOUT);
             assertTrue("object with id '(" + id + "') not visible yet", gotIt);
-            final UiObject dialog = mDevice.findObject(new UiSelector().resourceId(id));
+            dialog = mDevice.findObject(new UiSelector().resourceId(id));
             assertTrue("object with id '(" + id + "') doesn't exist", dialog.exists());
-            messageText = dialog.getChild(new UiSelector().resourceId("android:id/message"));
+            messageText = dialog.getChild(
+                    new UiSelector().resourceId("com.android.documentsui:id/message"));
             yesButton = dialog.getChild(new UiSelector().resourceId("android:id/button1"));
             noButton  = dialog.getChild(new UiSelector().resourceId("android:id/button2"));
         }
+
+        private UiObject getDoNotAskAgainCheckBox() throws UiObjectNotFoundException {
+            return dialog.getChild(
+                    new UiSelector().resourceId("com.android.documentsui:id/do_not_ask_checkbox"));
+        }
+
+        UiObject assertDoNotAskAgainVisibility(boolean expectVisible) {
+            UiObject checkbox = null;
+            try {
+                checkbox = getDoNotAskAgainCheckBox();
+                assertEquals("Wrong value for 'DoNotAskAgain.exists()",
+                        expectVisible, checkbox.exists());
+            } catch (UiObjectNotFoundException e) {
+                if (expectVisible) {
+                    fail("'Do Not Ask Again' not found");
+                }
+            }
+            return checkbox;
+        }
     }
 }
diff --git a/hostsidetests/devicepolicy/app/DeviceOwner/src/com/android/cts/deviceowner/CreateAndManageUserTest.java b/hostsidetests/devicepolicy/app/DeviceOwner/src/com/android/cts/deviceowner/CreateAndManageUserTest.java
index 91663c7..391ef15 100644
--- a/hostsidetests/devicepolicy/app/DeviceOwner/src/com/android/cts/deviceowner/CreateAndManageUserTest.java
+++ b/hostsidetests/devicepolicy/app/DeviceOwner/src/com/android/cts/deviceowner/CreateAndManageUserTest.java
@@ -16,6 +16,7 @@
 
 package com.android.cts.deviceowner;
 
+import android.app.ActivityManager;
 import android.app.admin.DeviceAdminReceiver;
 import android.app.admin.DevicePolicyManager;
 import android.content.BroadcastReceiver;
@@ -46,6 +47,7 @@
     private static final int BROADCAST_TIMEOUT = 15_000;
     private static final int USER_SWITCH_DELAY = 10_000;
     private PackageManager mPackageManager;
+    private ActivityManager mActivityManager;
     private volatile boolean mReceived;
     private volatile boolean mTestProfileOwnerWasUsed;
     private volatile boolean mSetupComplete;
@@ -55,6 +57,7 @@
     protected void setUp() throws Exception {
         super.setUp();
         mPackageManager = mContext.getPackageManager();
+        mActivityManager = (ActivityManager) mContext.getSystemService(Context.ACTIVITY_SERVICE);
     }
 
     @Override
@@ -241,7 +244,11 @@
     }
 
     public void testCreateAndManageUser_DontSkipSetupWizard() {
-        createAndManageUserTest(0);
+        if (!mActivityManager.isRunningInTestHarness()) {
+            // In test harness, the setup wizard will be disabled by default, so this test is always
+            // failing.
+            createAndManageUserTest(0);
+        }
     }
 
     // createAndManageUser should circumvent the DISALLOW_ADD_USER restriction
diff --git a/hostsidetests/devicepolicy/app/PackageInstaller/src/com/android/cts/packageinstaller/ManualPackageInstallTest.java b/hostsidetests/devicepolicy/app/PackageInstaller/src/com/android/cts/packageinstaller/ManualPackageInstallTest.java
index 96affae..1bb797f 100644
--- a/hostsidetests/devicepolicy/app/PackageInstaller/src/com/android/cts/packageinstaller/ManualPackageInstallTest.java
+++ b/hostsidetests/devicepolicy/app/PackageInstaller/src/com/android/cts/packageinstaller/ManualPackageInstallTest.java
@@ -33,11 +33,11 @@
     private static final BySelector POPUP_BUTTON_SELECTOR = By
             .clazz(android.widget.Button.class.getName())
             .res("android:id/button1")
-            .pkg("com.google.android.packageinstaller");
-    private static final BySelector POPUP_TEXT_SELECTOR = By
-            .clazz(android.widget.TextView.class.getName())
-            .res("android:id/alertTitle")
-            .pkg("com.google.android.packageinstaller");
+            .pkg("com.android.settings");
+    private static final BySelector POPUP_IMAGE_SELECTOR = By
+            .clazz(android.widget.ImageView.class.getName())
+            .res("com.android.settings:id/admin_support_icon")
+            .pkg("com.android.settings");
     private static final BySelector INSTALL_BUTTON_SELECTOR = By
             .clazz(android.widget.Button.class.getName())
             .res("com.android.packageinstaller:id/ok_button")
@@ -106,9 +106,9 @@
     }
 
     private void automateDismissInstallBlockedDialog() {
-        mDevice.wait(Until.hasObject(POPUP_TEXT_SELECTOR), AUTOMATOR_WAIT_TIMEOUT);
-        UiObject2 text = mDevice.findObject(POPUP_TEXT_SELECTOR);
-        assertNotNull("Alert dialog not found", text);
+        mDevice.wait(Until.hasObject(POPUP_IMAGE_SELECTOR), AUTOMATOR_WAIT_TIMEOUT);
+        UiObject2 icon = mDevice.findObject(POPUP_IMAGE_SELECTOR);
+        assertNotNull("Policy transparency dialog icon not found", icon);
         // "OK" button only present in the dialog if it is blocked by policy.
         UiObject2 button = mDevice.findObject(POPUP_BUTTON_SELECTOR);
         assertNotNull("OK button not found", button);
diff --git a/tests/accessibility/src/android/view/accessibility/cts/AccessibilityManagerTest.java b/tests/accessibility/src/android/view/accessibility/cts/AccessibilityManagerTest.java
index bc88085..bb199b4 100644
--- a/tests/accessibility/src/android/view/accessibility/cts/AccessibilityManagerTest.java
+++ b/tests/accessibility/src/android/view/accessibility/cts/AccessibilityManagerTest.java
@@ -24,6 +24,7 @@
 import android.view.accessibility.AccessibilityEvent;
 import android.view.accessibility.AccessibilityManager;
 import android.view.accessibility.AccessibilityManager.AccessibilityStateChangeListener;
+import android.view.accessibility.AccessibilityManager.TouchExplorationStateChangeListener;
 
 import java.util.List;
 
@@ -63,6 +64,19 @@
         };
         assertTrue(mAccessibilityManager.addAccessibilityStateChangeListener(listener));
         assertTrue(mAccessibilityManager.removeAccessibilityStateChangeListener(listener));
+        assertFalse(mAccessibilityManager.removeAccessibilityStateChangeListener(listener));
+    }
+
+    public void testAddAndRemoveTouchExplorationStateChangeListener() throws Exception {
+        TouchExplorationStateChangeListener listener = new TouchExplorationStateChangeListener() {
+            @Override
+            public void onTouchExplorationStateChanged(boolean enabled) {
+                // Do nothing.
+            }
+        };
+        assertTrue(mAccessibilityManager.addTouchExplorationStateChangeListener(listener));
+        assertTrue(mAccessibilityManager.removeTouchExplorationStateChangeListener(listener));
+        assertFalse(mAccessibilityManager.removeTouchExplorationStateChangeListener(listener));
     }
 
     public void testIsTouchExplorationEnabled() throws Exception {
@@ -173,6 +187,10 @@
                 AccessibilityEvent.TYPE_VIEW_CLICKED));
     }
 
+    public void testTouchExplorationStateChanged() throws Exception {
+        waitForTouchExplorationEnabled();
+    }
+
     private void waitForAccessibilityEnabled() throws InterruptedException {
         final Object waitObject = new Object();
 
@@ -192,6 +210,29 @@
             }
         }
         mAccessibilityManager.removeAccessibilityStateChangeListener(listener);
-        assertTrue("Time out enabling accessibility", mAccessibilityManager.isEnabled());
+        assertTrue("Timed out enabling accessibility", mAccessibilityManager.isEnabled());
+    }
+
+    private void waitForTouchExplorationEnabled() throws InterruptedException {
+        final Object waitObject = new Object();
+
+        TouchExplorationStateChangeListener listener = new TouchExplorationStateChangeListener() {
+            @Override
+            public void onTouchExplorationStateChanged(boolean b) {
+                synchronized (waitObject) {
+                    waitObject.notifyAll();
+                }
+            }
+        };
+        mAccessibilityManager.addTouchExplorationStateChangeListener(listener);
+        long timeoutTime = System.currentTimeMillis() + WAIT_FOR_ACCESSIBILITY_ENABLED_TIMEOUT;
+        synchronized (waitObject) {
+            if (!mAccessibilityManager.isEnabled() && (System.currentTimeMillis() < timeoutTime)) {
+                waitObject.wait(timeoutTime - System.currentTimeMillis());
+            }
+        }
+        mAccessibilityManager.removeTouchExplorationStateChangeListener(listener);
+        assertTrue("Timed out enabling touch exploration",
+                mAccessibilityManager.isTouchExplorationEnabled());
     }
 }
diff --git a/tests/accessibility/src/android/view/accessibility/cts/AccessibilityNodeInfo_CollectionInfoTest.java b/tests/accessibility/src/android/view/accessibility/cts/AccessibilityNodeInfo_CollectionInfoTest.java
new file mode 100644
index 0000000..d64bd94
--- /dev/null
+++ b/tests/accessibility/src/android/view/accessibility/cts/AccessibilityNodeInfo_CollectionInfoTest.java
@@ -0,0 +1,46 @@
+/*
+ * Copyright (C) 2016 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package android.view.accessibility.cts;
+
+import android.test.AndroidTestCase;
+import android.test.suitebuilder.annotation.SmallTest;
+import android.view.accessibility.AccessibilityNodeInfo.CollectionInfo;
+
+/**
+ * Class for testing {@link CollectionInfo}.
+ */
+public class AccessibilityNodeInfo_CollectionInfoTest extends AndroidTestCase {
+
+    @SmallTest
+    public void testObtain() {
+        CollectionInfo c;
+
+        c = CollectionInfo.obtain(0, 1, true);
+        assertNotNull(c);
+        assertEquals(0, c.getRowCount());
+        assertEquals(1, c.getColumnCount());
+        assertTrue(c.isHierarchical());
+        assertEquals(CollectionInfo.SELECTION_MODE_NONE, c.getSelectionMode());
+
+        c = CollectionInfo.obtain(1, 2, true, CollectionInfo.SELECTION_MODE_MULTIPLE);
+        assertNotNull(c);
+        assertEquals(1, c.getRowCount());
+        assertEquals(2, c.getColumnCount());
+        assertTrue(c.isHierarchical());
+        assertEquals(CollectionInfo.SELECTION_MODE_MULTIPLE, c.getSelectionMode());
+    }
+}
diff --git a/tests/accessibility/src/android/view/accessibility/cts/AccessibilityNodeInfo_RangeInfoTest.java b/tests/accessibility/src/android/view/accessibility/cts/AccessibilityNodeInfo_RangeInfoTest.java
new file mode 100644
index 0000000..954d762
--- /dev/null
+++ b/tests/accessibility/src/android/view/accessibility/cts/AccessibilityNodeInfo_RangeInfoTest.java
@@ -0,0 +1,54 @@
+/*
+ * Copyright (C) 2016 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package android.view.accessibility.cts;
+
+import android.test.AndroidTestCase;
+import android.test.suitebuilder.annotation.SmallTest;
+import android.view.accessibility.AccessibilityNodeInfo;
+import android.view.accessibility.AccessibilityNodeInfo.RangeInfo;
+
+/**
+ * Class for testing {@link AccessibilityNodeInfo.RangeInfo}.
+ */
+public class AccessibilityNodeInfo_RangeInfoTest extends AndroidTestCase {
+
+    /** Allowed tolerance for floating point equality comparisons. */
+    public static final float FLOAT_TOLERANCE = 0.001f;
+
+    @SmallTest
+    public void testObtain() {
+        RangeInfo r;
+
+        r = RangeInfo.obtain(RangeInfo.RANGE_TYPE_INT, -100, 0, -50);
+        assertEquals(RangeInfo.RANGE_TYPE_INT, r.getType());
+        assertEquals(-100, r.getMin(), FLOAT_TOLERANCE);
+        assertEquals(0, r.getMax(), FLOAT_TOLERANCE);
+        assertEquals(-50, r.getCurrent(), FLOAT_TOLERANCE);
+
+        r = RangeInfo.obtain(RangeInfo.RANGE_TYPE_FLOAT, -1.5f, 1.5f, 0.0f);
+        assertEquals(RangeInfo.RANGE_TYPE_FLOAT, r.getType());
+        assertEquals(-1.5f, r.getMin(), FLOAT_TOLERANCE);
+        assertEquals(1.5f, r.getMax(), FLOAT_TOLERANCE);
+        assertEquals(0.0f, r.getCurrent(), FLOAT_TOLERANCE);
+
+        r = RangeInfo.obtain(RangeInfo.RANGE_TYPE_PERCENT, 0.0f, 100.0f, 50.0f);
+        assertEquals(RangeInfo.RANGE_TYPE_PERCENT, r.getType());
+        assertEquals(0.0f, r.getMin(), FLOAT_TOLERANCE);
+        assertEquals(100.0f, r.getMax(), FLOAT_TOLERANCE);
+        assertEquals(50.0f, r.getCurrent(), FLOAT_TOLERANCE);
+    }
+}
diff --git a/tests/accessibility/src/android/view/accessibility/cts/AccessibilityNodeProviderTest.java b/tests/accessibility/src/android/view/accessibility/cts/AccessibilityNodeProviderTest.java
new file mode 100644
index 0000000..eeee235
--- /dev/null
+++ b/tests/accessibility/src/android/view/accessibility/cts/AccessibilityNodeProviderTest.java
@@ -0,0 +1,38 @@
+/*
+ * Copyright (C) 2016 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package android.view.accessibility.cts;
+
+import android.test.AndroidTestCase;
+import android.test.suitebuilder.annotation.SmallTest;
+import android.view.accessibility.AccessibilityNodeProvider;
+
+/**
+ * Class for testing {@link AccessibilityNodeProvider}.
+ */
+public class AccessibilityNodeProviderTest extends AndroidTestCase {
+    @SmallTest
+    public void testDefaultBehavior() {
+        AccessibilityNodeProvider p = new AccessibilityNodeProvider() {
+            // Class is abstract, but has no abstract methods.
+        };
+
+        assertNull(p.createAccessibilityNodeInfo(0));
+        assertNull(p.findAccessibilityNodeInfosByText(null, 0));
+        assertNull(p.findFocus(0));
+        assertFalse(p.performAction(0, 0, null));
+    }
+}
diff --git a/tests/accessibility/src/android/view/accessibility/cts/AccessibilityWindowInfoTest.java b/tests/accessibility/src/android/view/accessibility/cts/AccessibilityWindowInfoTest.java
new file mode 100644
index 0000000..293feec
--- /dev/null
+++ b/tests/accessibility/src/android/view/accessibility/cts/AccessibilityWindowInfoTest.java
@@ -0,0 +1,90 @@
+/*
+ * Copyright (C) 2016 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package android.view.accessibility.cts;
+
+import android.graphics.Rect;
+import android.os.Parcel;
+import android.test.AndroidTestCase;
+import android.test.suitebuilder.annotation.SmallTest;
+import android.view.accessibility.AccessibilityWindowInfo;
+
+/**
+ * Class for testing {@link AccessibilityWindowInfo}.
+ */
+public class AccessibilityWindowInfoTest extends AndroidTestCase {
+
+    @SmallTest
+    public void testObtain() {
+        AccessibilityWindowInfo w1 = AccessibilityWindowInfo.obtain();
+        assertNotNull(w1);
+
+        AccessibilityWindowInfo w2 = AccessibilityWindowInfo.obtain(w1);
+        assertNotSame(w1, w2);
+        assertEquals(w1, w2);
+    }
+
+    @SmallTest
+    public void testParceling() {
+        Parcel parcel = Parcel.obtain();
+        AccessibilityWindowInfo w1 = AccessibilityWindowInfo.obtain();
+        w1.writeToParcel(parcel, 0);
+        parcel.setDataPosition(0);
+        AccessibilityWindowInfo w2 = AccessibilityWindowInfo.CREATOR.createFromParcel(parcel);
+        assertNotSame(w1, w2);
+        assertEquals(w1, w2);
+
+    }
+
+    @SmallTest
+    public void testDefaultValues() {
+        AccessibilityWindowInfo w = AccessibilityWindowInfo.obtain();
+        assertEquals(0, w.getChildCount());
+        assertEquals(-1, w.getType());
+        assertEquals(-1, w.getLayer());
+        assertEquals(-1, w.getId());
+        assertEquals(0, w.describeContents());
+        assertNull(w.getParent());
+        assertNull(w.getRoot());
+        assertFalse(w.isAccessibilityFocused());
+        assertFalse(w.isActive());
+        assertFalse(w.isFocused());
+
+        Rect rect = new Rect();
+        w.getBoundsInScreen(rect);
+        assertTrue(rect.isEmpty());
+
+        try {
+            w.getChild(0);
+            fail("Expected IndexOutOfBoundsException");
+        } catch (IndexOutOfBoundsException e) {
+            // Expected.
+        }
+    }
+
+    @SmallTest
+    public void testRecycle() {
+        AccessibilityWindowInfo w = AccessibilityWindowInfo.obtain();
+        w.recycle();
+
+        try {
+            w.recycle();
+            fail("Expected IllegalStateException");
+        } catch (IllegalStateException e) {
+            // Expected.
+        }
+    }
+}
diff --git a/tests/accessibility/src/android/view/accessibility/cts/CaptioningManagerTest.java b/tests/accessibility/src/android/view/accessibility/cts/CaptioningManagerTest.java
index 34beb59..997ee61 100644
--- a/tests/accessibility/src/android/view/accessibility/cts/CaptioningManagerTest.java
+++ b/tests/accessibility/src/android/view/accessibility/cts/CaptioningManagerTest.java
@@ -67,7 +67,9 @@
         putSecureSetting("accessibility_captioning_enabled", "1");
         assertTrue("Observed enabled change", listener.wasEnabledChangedCalled);
 
+        // Style change gets posted in a Runnable, so we need to wait for idle.
         putSecureSetting("accessibility_captioning_preset", "-1");
+        getInstrumentation().waitForIdleSync();
         assertTrue("Observed user style change", listener.wasUserStyleChangedCalled);
 
         putSecureSetting("accessibility_captioning_locale", "ja_JP");
diff --git a/tests/accessibility/src/android/view/accessibility/cts/SpeakingAccessibilityService.java b/tests/accessibility/src/android/view/accessibility/cts/SpeakingAccessibilityService.java
index afa08cd..219a2ff 100644
--- a/tests/accessibility/src/android/view/accessibility/cts/SpeakingAccessibilityService.java
+++ b/tests/accessibility/src/android/view/accessibility/cts/SpeakingAccessibilityService.java
@@ -17,6 +17,7 @@
 package android.view.accessibility.cts;
 
 import android.accessibilityservice.AccessibilityService;
+import android.accessibilityservice.AccessibilityServiceInfo;
 import android.view.accessibility.AccessibilityEvent;
 
 /**
@@ -34,6 +35,10 @@
 
     @Override
     protected void onServiceConnected() {
+        final AccessibilityServiceInfo info = getServiceInfo();
+        info.flags |= AccessibilityServiceInfo.FLAG_REQUEST_TOUCH_EXPLORATION_MODE;
+        setServiceInfo(info);
+
         synchronized (sWaitObjectForConnecting) {
             sConnectedInstance = this;
             sWaitObjectForConnecting.notifyAll();
diff --git a/tests/accessibility/src/android/view/accessibility/cts/VibratingAccessibilityService.java b/tests/accessibility/src/android/view/accessibility/cts/VibratingAccessibilityService.java
index 6bf522e..41edf9f 100644
--- a/tests/accessibility/src/android/view/accessibility/cts/VibratingAccessibilityService.java
+++ b/tests/accessibility/src/android/view/accessibility/cts/VibratingAccessibilityService.java
@@ -17,6 +17,7 @@
 package android.view.accessibility.cts;
 
 import android.accessibilityservice.AccessibilityService;
+import android.accessibilityservice.AccessibilityServiceInfo;
 import android.view.accessibility.AccessibilityEvent;
 
 /**
@@ -34,6 +35,10 @@
 
     @Override
     protected void onServiceConnected() {
+        final AccessibilityServiceInfo info = getServiceInfo();
+        info.flags |= AccessibilityServiceInfo.FLAG_REQUEST_TOUCH_EXPLORATION_MODE;
+        setServiceInfo(info);
+
         synchronized (sWaitObjectForConnecting) {
             sConnectedInstance = this;
             sWaitObjectForConnecting.notifyAll();
diff --git a/tests/app/src/android/app/cts/AlertDialog_BuilderCursorTest.java b/tests/app/src/android/app/cts/AlertDialog_BuilderCursorTest.java
new file mode 100644
index 0000000..6305adb
--- /dev/null
+++ b/tests/app/src/android/app/cts/AlertDialog_BuilderCursorTest.java
@@ -0,0 +1,261 @@
+/*
+ * Copyright (C) 2008 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package android.app.cts;
+
+import android.app.Activity;
+import android.app.AlertDialog;
+import android.app.AlertDialog.Builder;
+import android.app.Instrumentation;
+import android.app.stubs.DialogStubActivity;
+import android.content.ContentValues;
+import android.content.Context;
+import android.content.DialogInterface;
+import android.content.DialogInterface.OnClickListener;
+import android.content.DialogInterface.OnMultiChoiceClickListener;
+import android.cts.util.PollingCheck;
+import android.database.Cursor;
+import android.database.sqlite.SQLiteCursor;
+import android.database.sqlite.SQLiteDatabase;
+import android.support.test.InstrumentationRegistry;
+import android.test.ActivityInstrumentationTestCase2;
+import android.test.suitebuilder.annotation.MediumTest;
+import android.widget.ListView;
+
+import java.io.File;
+
+import static org.mockito.Mockito.*;
+
+@MediumTest
+public class AlertDialog_BuilderCursorTest
+        extends ActivityInstrumentationTestCase2<DialogStubActivity> {
+    private Builder mBuilder;
+    private Context mContext;
+    private Instrumentation mInstrumentation;
+    private AlertDialog mDialog;
+    private ListView mListView;
+
+    private static final String TEXT_COLUMN_NAME = "text";
+    private static final String CHECKED_COLUMN_NAME = "checked";
+
+    private String[] mTextContent;
+    private boolean[] mCheckedContent;
+
+    private String[] mProjectionWithChecked;
+    private String[] mProjectionWithoutChecked;
+
+    private SQLiteDatabase mDatabase;
+    private File mDatabaseFile;
+    private Cursor mCursor;
+
+    private OnClickListener mOnClickListener = mock(OnClickListener.class);
+
+    /**
+     * Multi-choice click listener that is registered on our {@link AlertDialog} when it's in
+     * multi-choide mode. Note that this needs to be a separate class that is also protected (not
+     * private) so that Mockito can "spy" on it.
+     */
+    protected class MultiChoiceClickListener implements OnMultiChoiceClickListener {
+        private boolean[] mCheckedTracker;
+
+        public MultiChoiceClickListener(boolean[] checkedTracker) {
+            mCheckedTracker = checkedTracker;
+        }
+
+        @Override
+        public void onClick(DialogInterface dialog, int which,
+                boolean isChecked) {
+            // Update the underlying database with the new checked
+            // state for the specific row
+            mCursor.moveToPosition(which);
+            ContentValues valuesToUpdate = new ContentValues();
+            valuesToUpdate.put(CHECKED_COLUMN_NAME, isChecked ? 1 : 0);
+            mDatabase.update("test", valuesToUpdate,
+                    TEXT_COLUMN_NAME + " = ?",
+                    new String[] { mCursor.getString(1) } );
+            mCursor.requery();
+            mCheckedTracker[which] = isChecked;
+        }
+    }
+
+    public AlertDialog_BuilderCursorTest() {
+        super("android.app.stubs", DialogStubActivity.class);
+    }
+
+    @Override
+    protected void setUp() throws Exception {
+        super.setUp();
+        mBuilder = null;
+        mInstrumentation = getInstrumentation();
+        mContext = getActivity();
+        final Activity activity = getActivity();
+        new PollingCheck() {
+            @Override
+            protected boolean check() {
+                return activity.hasWindowFocus();
+            }
+        }.run();
+        mListView = null;
+        mDialog = null;
+
+        // Local test data for the tests
+        mTextContent = new String[] { "Adele", "Beyonce", "Ciara", "Dido" };
+        mCheckedContent = new boolean[] { false, false, true, false };
+
+        // Two projections - one with "checked" column and one without
+        mProjectionWithChecked = new String[] {
+                "_id",                       // 0
+                TEXT_COLUMN_NAME,            // 1
+                CHECKED_COLUMN_NAME          // 2
+        };
+        mProjectionWithoutChecked = new String[] {
+                "_id",                       // 0
+                TEXT_COLUMN_NAME             // 1
+        };
+
+        File dbDir = mContext.getDir("tests", Context.MODE_PRIVATE);
+        mDatabaseFile = new File(dbDir, "database_alert_dialog_test.db");
+        if (mDatabaseFile.exists()) {
+            mDatabaseFile.delete();
+        }
+        mDatabase = SQLiteDatabase.openOrCreateDatabase(mDatabaseFile.getPath(), null);
+        assertNotNull(mDatabase);
+        // Create and populate a test table
+        mDatabase.execSQL(
+                "CREATE TABLE test (_id INTEGER PRIMARY KEY, " + TEXT_COLUMN_NAME +
+                        " TEXT, " + CHECKED_COLUMN_NAME + " INTEGER);");
+        for (int i = 0; i < mTextContent.length; i++) {
+            mDatabase.execSQL("INSERT INTO test (" + TEXT_COLUMN_NAME + ", " +
+                    CHECKED_COLUMN_NAME + ") VALUES ('" + mTextContent[i] + "', " +
+                    (mCheckedContent[i] ? "1" : "0") + ");");
+        }
+    }
+
+    @Override
+    protected void tearDown() throws Exception {
+        if (mCursor != null) {
+            // Close the cursor on the UI thread as the list view in the alert dialog
+            // will get notified of any change to the underlying cursor.
+            InstrumentationRegistry.getInstrumentation().runOnMainSync(new Runnable() {
+                @Override
+                public void run() {
+                    mCursor.close();
+                    mCursor = null;
+                }
+            });
+        }
+        if (mDatabase != null) {
+            mDatabase.close();
+        }
+        if (mDatabaseFile != null) {
+            mDatabaseFile.delete();
+        }
+
+        super.tearDown();
+    }
+
+    public void testSetCursor() throws Throwable {
+        // Use a projection without "checked" column
+        mCursor = mDatabase.query("test", mProjectionWithoutChecked,
+                null, null, null, null, null);
+        assertNotNull(mCursor);
+
+        runTestOnUiThread(new Runnable() {
+            public void run() {
+                mBuilder = new Builder(mContext);
+                mBuilder.setCursor(mCursor, mOnClickListener, TEXT_COLUMN_NAME);
+                mDialog = mBuilder.show();
+                mListView = mDialog.getListView();
+                mListView.performItemClick(null, 0, 0);
+            }
+        });
+        mInstrumentation.waitForIdleSync();
+        final SQLiteCursor selected = (SQLiteCursor) mListView.getSelectedItem();
+        assertEquals(mCursor.getString(1), selected.getString(1));
+        verify(mOnClickListener, times(1)).onClick(mDialog, 0);
+        verifyNoMoreInteractions(mOnClickListener);
+    }
+
+    public void testSetSingleChoiceItemsWithParamCursor() throws Throwable {
+        // Use a projection without "checked" column
+        mCursor = mDatabase.query("test", mProjectionWithoutChecked,
+                null, null, null, null, null);
+        assertNotNull(mCursor);
+
+        runTestOnUiThread(new Runnable() {
+            public void run() {
+                mBuilder = new Builder(mContext);
+                mBuilder.setSingleChoiceItems(mCursor, 0, TEXT_COLUMN_NAME, mOnClickListener);
+                mDialog = mBuilder.show();
+                mListView = mDialog.getListView();
+                mListView.performItemClick(null, 0, 0);
+            }
+        });
+        mInstrumentation.waitForIdleSync();
+        final SQLiteCursor selected = (SQLiteCursor) mListView.getSelectedItem();
+        assertEquals(mCursor.getString(1), selected.getString(1));
+        verify(mOnClickListener, times(1)).onClick(mDialog, 0);
+        verifyNoMoreInteractions(mOnClickListener);
+    }
+
+    public void testSetMultiChoiceItemsWithParamCursor() throws Throwable {
+        mCursor = mDatabase.query("test", mProjectionWithChecked,
+                null, null, null, null, null);
+        assertNotNull(mCursor);
+
+        final boolean[] checkedTracker = mCheckedContent.clone();
+        final OnMultiChoiceClickListener mockMultiChoiceClickListener =
+                spy(new MultiChoiceClickListener(checkedTracker));
+        runTestOnUiThread(new Runnable() {
+            public void run() {
+                mBuilder = new Builder(mContext);
+                mBuilder.setMultiChoiceItems(mCursor, CHECKED_COLUMN_NAME, TEXT_COLUMN_NAME,
+                        mockMultiChoiceClickListener);
+                mDialog = mBuilder.show();
+                mListView = mDialog.getListView();
+                mListView.performItemClick(null, 0, 0);
+            }
+        });
+        mInstrumentation.waitForIdleSync();
+
+        SQLiteCursor selected = (SQLiteCursor) mListView.getSelectedItem();
+        assertEquals(mCursor.getString(0), selected.getString(0));
+        verify(mockMultiChoiceClickListener, times(1)).onClick(mDialog, 0, true);
+        // Verify that our multi-choice listener was invoked to update our tracker array
+        assertTrue(checkedTracker[0]);
+        assertFalse(checkedTracker[1]);
+        assertTrue(checkedTracker[2]);
+        assertFalse(checkedTracker[3]);
+
+        runTestOnUiThread(new Runnable() {
+            public void run() {
+                mListView.performItemClick(null, 1, 1);
+            }
+        });
+        mInstrumentation.waitForIdleSync();
+
+        selected = (SQLiteCursor) mListView.getSelectedItem();
+        assertEquals(mCursor.getString(1), selected.getString(1));
+        verify(mockMultiChoiceClickListener, times(1)).onClick(mDialog, 1, true);
+        // Verify that our multi-choice listener was invoked to update our tracker array
+        assertTrue(checkedTracker[0]);
+        assertTrue(checkedTracker[1]);
+        assertTrue(checkedTracker[2]);
+        assertFalse(checkedTracker[3]);
+
+        verifyNoMoreInteractions(mockMultiChoiceClickListener);
+    }
+}
diff --git a/tests/app/src/android/app/cts/AlertDialog_BuilderTest.java b/tests/app/src/android/app/cts/AlertDialog_BuilderTest.java
index ff9d772..d13585a 100644
--- a/tests/app/src/android/app/cts/AlertDialog_BuilderTest.java
+++ b/tests/app/src/android/app/cts/AlertDialog_BuilderTest.java
@@ -22,8 +22,6 @@
 import android.app.Instrumentation;
 import android.app.stubs.DialogStubActivity;
 import android.app.stubs.R;
-import android.content.ContentResolver;
-import android.content.ContentValues;
 import android.content.Context;
 import android.content.DialogInterface;
 import android.content.DialogInterface.OnCancelListener;
@@ -33,10 +31,7 @@
 import android.content.DialogInterface.OnMultiChoiceClickListener;
 import android.content.res.TypedArray;
 import android.cts.util.PollingCheck;
-import android.database.Cursor;
-import android.database.CursorWrapper;
 import android.graphics.drawable.Drawable;
-import android.provider.Contacts.People;
 import android.test.ActivityInstrumentationTestCase2;
 import android.test.suitebuilder.annotation.SmallTest;
 import android.view.KeyEvent;
@@ -61,9 +56,6 @@
     private AlertDialog mDialog;
     private Button mButton;
     private CharSequence mSelectedItem;
-    private final String[] mPROJECTION = new String[] {
-            People._ID, People.NAME
-    };
 
     private View mView;
     private ListView mListView;
@@ -419,27 +411,6 @@
         assertEquals(adapter, mListView.getAdapter());
     }
 
-    public void testSetCursor() throws Throwable {
-        preparePeople();
-        final Cursor c = mContext.getContentResolver().query(People.CONTENT_URI, mPROJECTION, null,
-                null, null);
-
-        runTestOnUiThread(new Runnable() {
-            public void run() {
-                mBuilder = new AlertDialog.Builder(mContext);
-                mBuilder.setCursor(c, mOnClickListener, People.NAME);
-                mDialog = mBuilder.show();
-                mListView = mDialog.getListView();
-                mListView.performItemClick(null, 0, 0);
-            }
-        });
-        mInstrumentation.waitForIdleSync();
-        final CursorWrapper selected = (CursorWrapper)mListView.getSelectedItem();
-        assertEquals(c.getString(1), selected.getString(1));
-        verify(mOnClickListener, times(1)).onClick(mDialog, 0);
-        verifyNoMoreInteractions(mOnClickListener);
-    }
-
     public void testSetMultiChoiceItemsWithParamInt() throws Throwable {
 
         final CharSequence[] items = mContext.getResources().getTextArray(
@@ -488,30 +459,6 @@
         assertEquals(items[0], mListView.getItemAtPosition(0));
     }
 
-    public void testSetMultiChoiceItemsWithParamCursor() throws Throwable {
-        preparePeople();
-        final Cursor c = mContext.getContentResolver().query(People.CONTENT_URI, mPROJECTION, null,
-                null, null);
-
-        runTestOnUiThread(new Runnable() {
-            public void run() {
-                mBuilder = new AlertDialog.Builder(mContext);
-                mBuilder.setMultiChoiceItems(c, People.NAME, People.NAME,
-                        mOnMultiChoiceClickListener);
-                mDialog = mBuilder.show();
-                mListView = mDialog.getListView();
-                mListView.performItemClick(null, 0, 0);
-                mListView.performItemClick(null, 1, 0);
-            }
-        });
-        mInstrumentation.waitForIdleSync();
-        final CursorWrapper selected = (CursorWrapper)mListView.getSelectedItem();
-        assertEquals(c.getString(1), selected.getString(1));
-        verify(mOnMultiChoiceClickListener, times(1)).onClick(mDialog, 0, true);
-        verify(mOnMultiChoiceClickListener, times(1)).onClick(mDialog, 1, true);
-        verifyNoMoreInteractions(mOnMultiChoiceClickListener);
-    }
-
     public void testSetSingleChoiceItemsWithParamInt() throws Throwable {
         final CharSequence[] items = mContext.getResources().getTextArray(
                 R.array.difficultyLevel);
@@ -534,39 +481,6 @@
         verifyNoMoreInteractions(mOnClickListener);
     }
 
-    private void preparePeople() {
-        final ContentResolver mResolver = mContext.getContentResolver();
-        mResolver.delete(People.CONTENT_URI, null, null);
-        final ContentValues values = new ContentValues();
-        values.put(People._ID, "1");
-        values.put(People.NAME, "name");
-        mResolver.insert(People.CONTENT_URI, values);
-    }
-
-    public void testSetSingleChoiceItemsWithParamCursor() throws Throwable {
-        final String[] PROJECTION = new String[] {
-                People._ID, People.NAME
-        };
-        preparePeople();
-        final Cursor c = mContext.getContentResolver().query(People.CONTENT_URI, PROJECTION, null,
-                null, null);
-
-        runTestOnUiThread(new Runnable() {
-            public void run() {
-                mBuilder = new AlertDialog.Builder(mContext);
-                mBuilder.setSingleChoiceItems(c, 0, People.NAME, mOnClickListener);
-                mDialog = mBuilder.show();
-                mListView = mDialog.getListView();
-                mListView.performItemClick(null, 0, 0);
-            }
-        });
-        mInstrumentation.waitForIdleSync();
-        final CursorWrapper selected = (CursorWrapper)mListView.getSelectedItem();
-        assertEquals(c.getString(1), selected.getString(1));
-        verify(mOnClickListener, times(1)).onClick(mDialog, 0);
-        verifyNoMoreInteractions(mOnClickListener);
-    }
-
     public void testSetSingleChoiceItemsWithParamCharSequence() throws Throwable {
         final CharSequence[] items = mContext.getResources().getTextArray(
                 R.array.difficultyLevel);
diff --git a/tests/camera/AndroidTest.xml b/tests/camera/AndroidTest.xml
index df15689..b54e1a22 100644
--- a/tests/camera/AndroidTest.xml
+++ b/tests/camera/AndroidTest.xml
@@ -21,5 +21,7 @@
     <test class="com.android.tradefed.testtype.AndroidJUnitTest" >
         <option name="package" value="android.camera.cts" />
         <option name="runtime-hint" value="12m7s" />
+        <!-- test-timeout unit is ms, value = 30 min -->
+        <option name="test-timeout" value="1800000" />
     </test>
 </configuration>
diff --git a/tests/camera/src/android/hardware/camera2/cts/StillCaptureTest.java b/tests/camera/src/android/hardware/camera2/cts/StillCaptureTest.java
index ce229b1..a9b4ad2 100644
--- a/tests/camera/src/android/hardware/camera2/cts/StillCaptureTest.java
+++ b/tests/camera/src/android/hardware/camera2/cts/StillCaptureTest.java
@@ -402,7 +402,7 @@
                     continue;
                 }
                 takePictureTestByCamera(/*aeRegions*/null, /*awbRegions*/null, /*afRegions*/null,
-                        /*addAeTriggerCancel*/true, /*allocateBitmap*/true);
+                        /*addAeTriggerCancel*/false, /*allocateBitmap*/true);
             } finally {
                 closeDevice();
                 closeImageReader();
diff --git a/tests/expectations/knownfailures.txt b/tests/expectations/knownfailures.txt
index 185fc56..2d1443a 100644
--- a/tests/expectations/knownfailures.txt
+++ b/tests/expectations/knownfailures.txt
@@ -342,5 +342,22 @@
       "android.security.cts.MediaCryptoTest#testMediaCryptoWidevine"
   ],
   bug: 27218502
+},
+{
+  description: "Still investigating this, root cause unknown yet",
+  bug: 27578806,
+  names: ["com.android.cts.cpptools.RunAsHostTest#testRunAs"]
+},
+{
+  description: "Some SensorBatchingTest cases fails due to test imperection",
+  names: [
+      "android.hardware.cts.SensorBatchingTests#testGyroscope_fastest_batching",
+      "android.hardware.cts.SensorBatchingTests#testGravity_50hz_batching",
+      "android.hardware.cts.SensorBatchingTests#testGravity_fastest_batching",
+      "android.hardware.cts.SensorBatchingTests#testLinearAcceleration_50hz_batching",
+      "android.hardware.cts.SensorBatchingTests#testLinearAcceleration_fastest_batching",
+      "android.hardware.cts.SensorBatchingTests#testRotationVector_50hz_batching"
+      ],
+  bug: 27534791
 }
 ]
diff --git a/tests/tests/automotive/Android.mk b/tests/tests/car/Android.mk
similarity index 95%
rename from tests/tests/automotive/Android.mk
rename to tests/tests/car/Android.mk
index abef2ac..0138317 100644
--- a/tests/tests/automotive/Android.mk
+++ b/tests/tests/car/Android.mk
@@ -16,7 +16,7 @@
 
 include $(CLEAR_VARS)
 
-LOCAL_PACKAGE_NAME := CtsAutomotiveTestCases
+LOCAL_PACKAGE_NAME := CtsCarTestCases
 
 # Don't include this package in any target.
 LOCAL_MODULE_TAGS := optional
diff --git a/tests/tests/automotive/AndroidManifest.xml b/tests/tests/car/AndroidManifest.xml
similarity index 100%
rename from tests/tests/automotive/AndroidManifest.xml
rename to tests/tests/car/AndroidManifest.xml
diff --git a/tests/tests/automotive/AndroidTest.xml b/tests/tests/car/AndroidTest.xml
similarity index 87%
rename from tests/tests/automotive/AndroidTest.xml
rename to tests/tests/car/AndroidTest.xml
index b4af1f5..d82c101 100644
--- a/tests/tests/automotive/AndroidTest.xml
+++ b/tests/tests/car/AndroidTest.xml
@@ -16,9 +16,9 @@
 <configuration description="Config for CTS Automotive test cases">
     <target_preparer class="com.android.compatibility.common.tradefed.targetprep.ApkInstaller">
         <option name="cleanup-apks" value="true" />
-        <option name="test-file-name" value="CtsAutomotiveTestCases.apk" />
+        <option name="test-file-name" value="CtsCarTestCases.apk" />
     </target_preparer>
     <test class="com.android.tradefed.testtype.AndroidJUnitTest" >
-        <option name="package" value="android.support.car.cts" />
+        <option name="package" value="android.car.cts" />
     </test>
 </configuration>
diff --git a/tests/tests/automotive/src/android/car/cts/CarApiTestBase.java b/tests/tests/car/src/android/car/cts/CarApiTestBase.java
similarity index 100%
rename from tests/tests/automotive/src/android/car/cts/CarApiTestBase.java
rename to tests/tests/car/src/android/car/cts/CarApiTestBase.java
diff --git a/tests/tests/automotive/src/android/car/cts/CarAppContextManagerTest.java b/tests/tests/car/src/android/car/cts/CarAppContextManagerTest.java
similarity index 100%
rename from tests/tests/automotive/src/android/car/cts/CarAppContextManagerTest.java
rename to tests/tests/car/src/android/car/cts/CarAppContextManagerTest.java
diff --git a/tests/tests/automotive/src/android/car/cts/CarInfoManagerTest.java b/tests/tests/car/src/android/car/cts/CarInfoManagerTest.java
similarity index 100%
rename from tests/tests/automotive/src/android/car/cts/CarInfoManagerTest.java
rename to tests/tests/car/src/android/car/cts/CarInfoManagerTest.java
diff --git a/tests/tests/automotive/src/android/car/cts/CarPackageManagerTest.java b/tests/tests/car/src/android/car/cts/CarPackageManagerTest.java
similarity index 100%
rename from tests/tests/automotive/src/android/car/cts/CarPackageManagerTest.java
rename to tests/tests/car/src/android/car/cts/CarPackageManagerTest.java
diff --git a/tests/tests/automotive/src/android/car/cts/CarSensorManagerTest.java b/tests/tests/car/src/android/car/cts/CarSensorManagerTest.java
similarity index 100%
rename from tests/tests/automotive/src/android/car/cts/CarSensorManagerTest.java
rename to tests/tests/car/src/android/car/cts/CarSensorManagerTest.java
diff --git a/tests/tests/automotive/src/android/car/cts/CarTest.java b/tests/tests/car/src/android/car/cts/CarTest.java
similarity index 100%
rename from tests/tests/automotive/src/android/car/cts/CarTest.java
rename to tests/tests/car/src/android/car/cts/CarTest.java
diff --git a/tests/tests/automotive/src/android/car/cts/CarUiProviderTest.java b/tests/tests/car/src/android/car/cts/CarUiProviderTest.java
similarity index 100%
rename from tests/tests/automotive/src/android/car/cts/CarUiProviderTest.java
rename to tests/tests/car/src/android/car/cts/CarUiProviderTest.java
diff --git a/tests/tests/automotive/src/android/car/cts/ExceptionsTest.java b/tests/tests/car/src/android/car/cts/ExceptionsTest.java
similarity index 100%
rename from tests/tests/automotive/src/android/car/cts/ExceptionsTest.java
rename to tests/tests/car/src/android/car/cts/ExceptionsTest.java
diff --git a/tests/tests/content/res/color-land/testcolor_orientation.xml b/tests/tests/content/res/color-land/testcolor_orientation.xml
new file mode 100644
index 0000000..f9e285b
--- /dev/null
+++ b/tests/tests/content/res/color-land/testcolor_orientation.xml
@@ -0,0 +1,21 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<!--
+/*
+ * Copyright (C) 2016 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.
+ */
+-->
+<selector xmlns:android="http://schemas.android.com/apk/res/android">
+    <item android:color="@android:color/white" />
+</selector>
diff --git a/tests/tests/content/res/drawable/testcolor.xml b/tests/tests/content/res/color/testcolor.xml
similarity index 100%
rename from tests/tests/content/res/drawable/testcolor.xml
rename to tests/tests/content/res/color/testcolor.xml
diff --git a/tests/tests/content/res/color/testcolor_orientation.xml b/tests/tests/content/res/color/testcolor_orientation.xml
new file mode 100644
index 0000000..bef1ef6
--- /dev/null
+++ b/tests/tests/content/res/color/testcolor_orientation.xml
@@ -0,0 +1,21 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<!--
+/*
+ * Copyright (C) 2016 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.
+ */
+-->
+<selector xmlns:android="http://schemas.android.com/apk/res/android">
+    <item android:color="@android:color/black" />
+</selector>
diff --git a/tests/tests/content/res/color/testcolor_themed.xml b/tests/tests/content/res/color/testcolor_themed.xml
new file mode 100644
index 0000000..eee0526
--- /dev/null
+++ b/tests/tests/content/res/color/testcolor_themed.xml
@@ -0,0 +1,21 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<!--
+/*
+ * Copyright (C) 2016 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.
+ */
+-->
+<selector xmlns:android="http://schemas.android.com/apk/res/android">
+    <item android:color="?attr/themeColor" />
+</selector>
diff --git a/tests/tests/content/res/drawable/colordrawable_themed.xml b/tests/tests/content/res/drawable/colordrawable_themed.xml
new file mode 100644
index 0000000..eacbe65
--- /dev/null
+++ b/tests/tests/content/res/drawable/colordrawable_themed.xml
@@ -0,0 +1,20 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<!--
+/*
+ * Copyright (C) 2016 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.
+ */
+-->
+<color xmlns:android="http://schemas.android.com/apk/res/android"
+       android:color="?attr/themeColor" />
diff --git a/tests/tests/content/res/values/attrs.xml b/tests/tests/content/res/values/attrs.xml
index ac88ef6..12b731b 100644
--- a/tests/tests/content/res/values/attrs.xml
+++ b/tests/tests/content/res/values/attrs.xml
@@ -48,6 +48,9 @@
     <attr name="type14" format="string"/>
     <attr name="type15" format="reference"/>
     <attr name="type16" format="string"/>
+    <attr name="type17" format="reference|color"/>
+    <attr name="typeEmpty" format="reference"/>
+    <attr name="typeUndefined" format="reference"/>
     <declare-styleable name="style1">
         <attr name="type1"/>
         <attr name="type2"/>
@@ -65,6 +68,9 @@
         <attr name="type14"/>
         <attr name="type15"/>
         <attr name="type16"/>
+        <attr name="type17"/>
+        <attr name="typeEmpty"/>
+        <attr name="typeUndefined"/>
     </declare-styleable>
     <attr name="testEnum">
         <enum name="val1" value="1" />
diff --git a/tests/tests/content/res/values/styles.xml b/tests/tests/content/res/values/styles.xml
index b27968d..c6e4b1d 100644
--- a/tests/tests/content/res/values/styles.xml
+++ b/tests/tests/content/res/values/styles.xml
@@ -33,6 +33,9 @@
         <item name="type14">TypedArray Test!</item>
         <item name="type15">@array/difficultyLevel</item>
         <item name="type16">Typed Value!</item>
+        <item name="type17">@color/testcolor_orientation</item>
+        <item name="typeEmpty">@empty</item>
+        <item name="typeUndefined">@null</item>
     </style>
 
     <style name="TextViewWithoutColorAndAppearance">
diff --git a/tests/tests/content/src/android/content/res/cts/AssetFileDescriptorTest.java b/tests/tests/content/src/android/content/res/cts/AssetFileDescriptorTest.java
index e4a9500..f5dc5ca 100644
--- a/tests/tests/content/src/android/content/res/cts/AssetFileDescriptorTest.java
+++ b/tests/tests/content/src/android/content/res/cts/AssetFileDescriptorTest.java
@@ -24,9 +24,11 @@
 import java.util.Arrays;
 
 import android.content.res.AssetFileDescriptor;
+import android.os.Bundle;
 import android.os.Parcel;
 import android.os.ParcelFileDescriptor;
 import android.test.AndroidTestCase;
+import android.test.suitebuilder.annotation.SmallTest;
 
 public class AssetFileDescriptorTest extends AndroidTestCase {
     private static final long START_OFFSET = 0;
@@ -66,6 +68,31 @@
         getContext().deleteFile(FILE_NAME);
     }
 
+    @SmallTest
+    public void testConstructor() throws IOException {
+        ParcelFileDescriptor fd = ParcelFileDescriptor.open(
+                mFile, ParcelFileDescriptor.MODE_READ_WRITE);
+        AssetFileDescriptor assetFileDes;
+        Bundle extras;
+
+        assetFileDes = new AssetFileDescriptor(fd, START_OFFSET, LENGTH);
+        assertNotNull(assetFileDes);
+        assetFileDes.close();
+
+        extras = null;
+        assetFileDes = new AssetFileDescriptor(fd, START_OFFSET, LENGTH, extras);
+        assertEquals(extras, assetFileDes.getExtras());
+        assertNotNull(assetFileDes);
+        assetFileDes.close();
+
+        extras = new Bundle();
+        assetFileDes = new AssetFileDescriptor(fd, START_OFFSET, LENGTH, extras);
+        assertEquals(extras, assetFileDes.getExtras());
+        assertNotNull(assetFileDes);
+        assetFileDes.close();
+    }
+
+    @SmallTest
     public void testInputOutputStream() throws IOException {
         /*
          * test createOutputStream() and createInputStrean()
@@ -150,6 +177,7 @@
         }
     }
 
+    @SmallTest
     public void testMiscMethod() {
         // test getLength()
         assertEquals(LENGTH, mAssetFileDes.getLength());
diff --git a/tests/tests/content/src/android/content/res/cts/AssetManagerTest.java b/tests/tests/content/src/android/content/res/cts/AssetManagerTest.java
index b861264..4893ec1 100644
--- a/tests/tests/content/src/android/content/res/cts/AssetManagerTest.java
+++ b/tests/tests/content/src/android/content/res/cts/AssetManagerTest.java
@@ -26,6 +26,7 @@
 import android.content.res.Resources;
 import android.content.res.XmlResourceParser;
 import android.test.AndroidTestCase;
+import android.test.suitebuilder.annotation.SmallTest;
 import android.util.TypedValue;
 
 import java.io.BufferedReader;
@@ -45,6 +46,7 @@
         mAssets = mContext.getAssets();
     }
 
+    @SmallTest
     public void testAssetOperations() throws IOException, XmlPullParserException {
         final Resources res = getContext().getResources();
         final TypedValue value = new TypedValue();
@@ -117,7 +119,23 @@
 
     }
 
+    @SmallTest
+    public void testClose() throws IOException, XmlPullParserException {
+        final AssetManager assets = new AssetManager();
+        assets.close();
 
+        // Should no-op.
+        assets.close();
+
+        try {
+            assets.openXmlResourceParser("AndroidManifest.xml");
+            fail("Expected RuntimeException");
+        } catch (RuntimeException e) {
+            // Expected.
+        }
+    }
+
+    @SmallTest
     public void testGetNonSystemLocales() {
         // This is the list of locales built into this test package. It is basically the locales
         // specified in the Android.mk files (assuming they have corresponding resources), plus the
diff --git a/tests/tests/content/src/android/content/res/cts/ColorStateListTest.java b/tests/tests/content/src/android/content/res/cts/ColorStateListTest.java
index 2222ce4..2029b95 100644
--- a/tests/tests/content/src/android/content/res/cts/ColorStateListTest.java
+++ b/tests/tests/content/src/android/content/res/cts/ColorStateListTest.java
@@ -20,51 +20,110 @@
 import org.xmlpull.v1.XmlPullParser;
 import org.xmlpull.v1.XmlPullParserException;
 
+import android.content.pm.ActivityInfo;
 import android.content.res.ColorStateList;
 import android.content.res.Resources;
 import android.content.res.Resources.NotFoundException;
+import android.content.res.Resources.Theme;
 import android.graphics.Color;
 import android.os.Parcel;
 import android.test.AndroidTestCase;
 
 import android.content.cts.R;
-
+import android.test.suitebuilder.annotation.SmallTest;
 
 public class ColorStateListTest extends AndroidTestCase {
-    public void testColorStateList() throws NotFoundException, XmlPullParserException, IOException {
-        final int[][] state = new int[][] { { 0 }, { 0 } };
-        final int[] colors = new int[] { Color.RED, Color.BLUE };
-        ColorStateList c = new ColorStateList(state, colors);
+
+    @SmallTest
+    public void testConstructor() {
+        final int[][] state = new int[][]{{0}, {0}};
+        final int[] colors = new int[]{Color.RED, Color.BLUE};
+        final ColorStateList c = new ColorStateList(state, colors);
         assertTrue(c.isStateful());
         assertEquals(Color.RED, c.getDefaultColor());
+    }
 
-        final int alpha = 36;
-        final ColorStateList c1 = c.withAlpha(alpha);
-        assertNotSame(Color.RED, c1.getDefaultColor());
-        // check alpha
-        assertEquals(alpha, c1.getDefaultColor() >>> 24);
-        assertEquals(Color.RED & 0x00FF0000, c1.getDefaultColor() & 0x00FF0000);
-
-        final int xmlId = R.drawable.testcolor;
-        final int colorInXml = 0xFFA6C839;// this color value is define in testcolor.xml file.
+    @SmallTest
+    public void testCreateFromXml() throws Exception {
+        final int xmlId = R.color.testcolor;
+        final int colorInXml = 0xFFA6C839; // this color value is defined in testcolor.xml file.
         final Resources res = getContext().getResources();
-        c = ColorStateList.createFromXml(res, res.getXml(xmlId));
+        final ColorStateList c = ColorStateList.createFromXml(res, res.getXml(xmlId));
         assertEquals(colorInXml, c.getDefaultColor());
         assertEquals(0, c.describeContents());
         assertFalse(c.isStateful());
         assertNotNull(c.toString());
         assertEquals(colorInXml, c.getColorForState(new int[]{0}, 0));
+    }
 
-        c = ColorStateList.valueOf(Color.GRAY);
+    @SmallTest
+    public void testCreateFromXmlThemed() throws Exception {
+        final int xmlId = R.color.testcolor_themed;
+        final int colorInXml = Color.BLACK; // this color value is defined in styles.xml file.
+        final Resources res = getContext().getResources();
+        final Theme theme = res.newTheme();
+        theme.applyStyle(R.style.Theme_ThemedDrawableTest, true);
+        final ColorStateList c = ColorStateList.createFromXml(res, res.getXml(xmlId), theme);
+        assertEquals(colorInXml, c.getDefaultColor());
+        assertEquals(0, c.describeContents());
+        assertFalse(c.isStateful());
+        assertNotNull(c.toString());
+        assertEquals(colorInXml, c.getColorForState(new int[]{0}, 0));
+    }
+
+    @SmallTest
+    public void testGetChangingConfigurations() {
+        final Resources res = getContext().getResources();
+        ColorStateList c;
+
+        c = res.getColorStateList(R.color.testcolor, null);
+        assertEquals(c.getChangingConfigurations(), 0);
+
+        c = res.getColorStateList(R.color.testcolor_orientation, null);
+        assertEquals(ActivityInfo.CONFIG_ORIENTATION, c.getChangingConfigurations());
+    }
+
+    @SmallTest
+    public void testWithAlpha() {
+        final int[][] state = new int[][]{{0}, {0}};
+        final int[] colors = new int[]{Color.RED, Color.BLUE};
+        final ColorStateList c = new ColorStateList(state, colors);
+        final int alpha = 36;
+        final ColorStateList c1 = c.withAlpha(alpha);
+        assertNotSame(Color.RED, c1.getDefaultColor());
+        assertEquals(alpha, c1.getDefaultColor() >>> 24);
+        assertEquals(Color.RED & 0x00FF0000, c1.getDefaultColor() & 0x00FF0000);
+    }
+
+    @SmallTest
+    public void testValueOf() {
+        final ColorStateList c = ColorStateList.valueOf(Color.GRAY);
         assertEquals(Color.GRAY, c.getDefaultColor());
+    }
 
+    @SmallTest
+    public void testParcelable() {
+        final ColorStateList c = ColorStateList.valueOf(Color.GRAY);
         final Parcel parcel = Parcel.obtain();
         c.writeToParcel(parcel, 0);
         parcel.setDataPosition(0);
-        ColorStateList actual = ColorStateList.CREATOR.createFromParcel(parcel);
-        // can only compare the state and the default color. because no API to
-        // get every color of ColorStateList
+
+        final ColorStateList actual = ColorStateList.CREATOR.createFromParcel(parcel);
         assertEquals(c.isStateful(), actual.isStateful());
         assertEquals(c.getDefaultColor(), actual.getDefaultColor());
     }
+
+    @SmallTest
+    public void testIsOpaque() {
+        ColorStateList c;
+
+        c = ColorStateList.valueOf(Color.GRAY);
+        assertTrue(c.isOpaque());
+
+        c = ColorStateList.valueOf(0x80FFFFFF);
+        assertFalse(c.isOpaque());
+
+        c = ColorStateList.valueOf(Color.TRANSPARENT);
+        assertFalse(c.isOpaque());
+    }
 }
diff --git a/tests/tests/content/src/android/content/res/cts/ConfigurationTest.java b/tests/tests/content/src/android/content/res/cts/ConfigurationTest.java
index c1ee6c4..bc0f42e 100644
--- a/tests/tests/content/src/android/content/res/cts/ConfigurationTest.java
+++ b/tests/tests/content/src/android/content/res/cts/ConfigurationTest.java
@@ -403,6 +403,14 @@
         assertEquals(View.LAYOUT_DIRECTION_RTL, config.getLayoutDirection());
     }
 
+    public void testIsScreenRound() {
+        Configuration config = new Configuration();
+        assertFalse(config.isScreenRound());
+
+        config.screenLayout |= Configuration.SCREENLAYOUT_ROUND_YES;
+        assertTrue(config.isScreenRound());
+    }
+
     public void testFixUpLocaleList() {
         Configuration config = new Configuration();
 
diff --git a/tests/tests/content/src/android/content/res/cts/Resources_NotFoundExceptionTest.java b/tests/tests/content/src/android/content/res/cts/Resources_NotFoundExceptionTest.java
index 8fa8d7b..d75fcdd 100644
--- a/tests/tests/content/src/android/content/res/cts/Resources_NotFoundExceptionTest.java
+++ b/tests/tests/content/src/android/content/res/cts/Resources_NotFoundExceptionTest.java
@@ -23,41 +23,57 @@
 public class Resources_NotFoundExceptionTest extends TestCase {
 
     public void testNotFoundException() {
-        NotFoundException ne = null;
-        boolean isThrowed = false;
-        boolean isFinnalyRun = false;
+        NotFoundException ne;
+        boolean wasThrown;
+
+        wasThrown = false;
+        ne = new NotFoundException();
+
         try {
-            ne = new NotFoundException();
             throw ne;
         } catch (NotFoundException e) {
             // expected
             assertSame(ne, e);
-            isThrowed = true;
+            wasThrown = true;
         } finally {
-            if (!isThrowed) {
+            if (!wasThrown) {
                 fail("should throw out NotFoundException");
             }
-            isFinnalyRun = true;
         }
-        assertTrue(isFinnalyRun);
 
-        isThrowed = false;
-        isFinnalyRun = false;
         final String MESSAGE = "test";
+        wasThrown = false;
+        ne = new NotFoundException(MESSAGE);
+
         try {
-            ne = new NotFoundException(MESSAGE);
             throw ne;
         } catch (NotFoundException e) {
             // expected
             assertSame(ne, e);
             assertEquals(MESSAGE, e.getMessage());
-            isThrowed = true;
+            wasThrown = true;
         } finally {
-            if (!isThrowed) {
+            if (!wasThrown) {
                 fail("should throw out NotFoundException");
             }
-            isFinnalyRun = true;
         }
-        assertTrue(isFinnalyRun);
+
+        final Exception CAUSE = new NullPointerException();
+        wasThrown = false;
+        ne = new NotFoundException(MESSAGE, CAUSE);
+
+        try {
+            throw ne;
+        } catch (NotFoundException e) {
+            // expected
+            assertSame(ne, e);
+            assertEquals(MESSAGE, e.getMessage());
+            assertEquals(CAUSE, e.getCause());
+            wasThrown = true;
+        } finally {
+            if (!wasThrown) {
+                fail("should throw out NotFoundException");
+            }
+        }
     }
 }
diff --git a/tests/tests/content/src/android/content/res/cts/Resources_ThemeTest.java b/tests/tests/content/src/android/content/res/cts/Resources_ThemeTest.java
index 533b186..b7a621f 100644
--- a/tests/tests/content/src/android/content/res/cts/Resources_ThemeTest.java
+++ b/tests/tests/content/src/android/content/res/cts/Resources_ThemeTest.java
@@ -23,7 +23,10 @@
 import android.content.res.Resources;
 import android.content.res.TypedArray;
 import android.content.res.Resources.Theme;
+import android.graphics.Color;
+import android.graphics.drawable.ColorDrawable;
 import android.test.AndroidTestCase;
+import android.test.suitebuilder.annotation.SmallTest;
 import android.util.AttributeSet;
 import android.util.TypedValue;
 import android.util.Xml;
@@ -44,6 +47,7 @@
         mResTheme = getContext().getResources().newTheme();
     }
 
+    @SmallTest
     public void testSetMethods() {
         // call a native method, and have no way to get the style
         mResTheme.applyStyle(R.raw.testmp3, false);
@@ -54,6 +58,7 @@
         mResTheme.setTo(other);
     }
 
+    @SmallTest
     public void testObtainStyledAttributes() {
         final int[] attrs = new int[1];
         attrs[0] = R.raw.testmp3;
@@ -77,12 +82,14 @@
         testTypedArray.recycle();
     }
 
+    @SmallTest
     public void testResolveAttribute() {
         final TypedValue value = new TypedValue();
         getContext().getResources().getValue(R.raw.testmp3, value, true);
         assertFalse(mResTheme.resolveAttribute(R.raw.testmp3, value, false));
     }
 
+    @SmallTest
     public void testGetChangingConfigurations() {
         Resources.Theme theme = getContext().getResources().newTheme();
         assertEquals("Initial changing configuration mask is empty",
@@ -104,6 +111,7 @@
                 theme.getChangingConfigurations());
     }
 
+    @SmallTest
     public void testRebase() {
         Resources res = getContext().getResources();
         Configuration config = res.getConfiguration();
@@ -132,4 +140,21 @@
         assertEquals("Theme was rebased in RTL config", true, t.getBoolean(0, false));
         t.recycle();
     }
+
+    @SmallTest
+    public void testGetDrawable() {
+        final Resources res = getContext().getResources();
+        final Theme theme = res.newTheme();
+        theme.applyStyle(R.style.Theme_ThemedDrawableTest, true);
+
+        final ColorDrawable dr = (ColorDrawable) theme.getDrawable(R.drawable.colordrawable_themed);
+        assertEquals(Color.BLACK, dr.getColor());
+    }
+
+    @SmallTest
+    public void testGetResources() {
+        final Resources res = getContext().getResources();
+        final Theme theme = res.newTheme();
+        assertSame(res, theme.getResources());
+    }
 }
diff --git a/tests/tests/content/src/android/content/res/cts/TypedArrayTest.java b/tests/tests/content/src/android/content/res/cts/TypedArrayTest.java
index 2eb82a8..ee7449c 100644
--- a/tests/tests/content/src/android/content/res/cts/TypedArrayTest.java
+++ b/tests/tests/content/src/android/content/res/cts/TypedArrayTest.java
@@ -16,11 +16,11 @@
 
 package android.content.res.cts;
 
-import android.content.cts.R;
-
 import org.xmlpull.v1.XmlPullParserException;
 
+import android.content.cts.R;
 import android.content.cts.util.XmlUtils;
+import android.content.pm.ActivityInfo;
 import android.content.res.TypedArray;
 import android.content.res.XmlResourceParser;
 import android.test.AndroidTestCase;
@@ -30,12 +30,10 @@
 
 import java.io.IOException;
 
-
-public class TypedArrayTest extends AndroidTestCase{
-    private TypedArray mTypedArray;
+public class TypedArrayTest extends AndroidTestCase {
     private static final int DEFINT = -1;
     private static final float DEFFLOAT = -1.0f;
-    private static final int EXPECTEDCLOLOR = 0xff0000ff;
+    private static final int EXPECTED_COLOR = 0xff0000ff;
     private static final int EXPECTED_COLOR_STATE = 0xff00ff00;
     private static final float EXPECTED_DIMENSION = 0.75f;
     private static final int EXPECTED_PIXEL_OFFSET = 10;
@@ -47,20 +45,23 @@
     private static final String EXPECTED_STRING = "Hello, Android!";
     private static final String EXPECTED_TEXT = "TypedArray Test!";
     private static final String[] EXPECTED_TEXT_ARRAY = {"Easy", "Medium", "Hard"};
-    private static final int EXPETED_INDEX = 15;
+    private static final int EXPECTED_INDEX = 15;
     private static final TypedValue DEF_VALUE = new TypedValue();
-    private static final int EXPECTED_INDEX_COUNT = 16;
+    private static final int EXPECTED_INDEX_COUNT = 17;
     private static final String EXPTECTED_POS_DESCRIP = "<internal>";
-    private static final int EXPECTED_LENGTH = 16;
+    private static final int EXPECTED_LENGTH = 19;
     private static final String EXPECTED_NON_RESOURCE_STRING = "testNonResourcesString";
     private static final String XML_BEGIN = "resources";
     private static final int EXPECTED_INT_ATT = 86400;
+    private static final int EXPECTED_CHANGING_CONFIG =
+            ActivityInfo.CONFIG_ORIENTATION | ActivityInfo.CONFIG_LOCALE;
+
+    private TypedArray mTypedArray;
 
     @Override
     protected void setUp() throws Exception {
         super.setUp();
-        final int[] attrs = R.styleable.style1;
-        mTypedArray = getContext().getTheme().obtainStyledAttributes(R.style.Whatever, attrs);
+        mTypedArray = getContext().getTheme().obtainStyledAttributes(R.style.Whatever, R.styleable.style1);
     }
 
     @Override
@@ -69,85 +70,126 @@
         mTypedArray.recycle();
     }
 
-    /*
-     * Test all get attrs methods, all test value are in styles.xml and attrs.xml.
-     */
-    public void testAttrsMethod() {
-        // getBoolean test
-        assertTrue(mTypedArray.getBoolean(R.styleable.style1_type1, false));
-        assertFalse(mTypedArray.getBoolean(R.styleable.style1_type2, true));
+    public void testGetType() {
+        final TypedArray t = getContext().getTheme().obtainStyledAttributes(
+                R.style.Whatever, R.styleable.style1);
 
-        assertEquals(EXPECTEDCLOLOR, mTypedArray.getColor(R.styleable.style1_type3, DEFINT));
+        assertEquals(TypedValue.TYPE_INT_BOOLEAN, t.getType(R.styleable.style1_type1));
+        assertEquals(TypedValue.TYPE_INT_BOOLEAN, t.getType(R.styleable.style1_type2));
+        assertEquals(TypedValue.TYPE_INT_COLOR_ARGB8, t.getType(R.styleable.style1_type3));
+        assertEquals(TypedValue.TYPE_INT_COLOR_ARGB8, t.getType(R.styleable.style1_type4));
+        assertEquals(TypedValue.TYPE_DIMENSION, t.getType(R.styleable.style1_type5));
+        assertEquals(TypedValue.TYPE_DIMENSION, t.getType(R.styleable.style1_type6));
+        assertEquals(TypedValue.TYPE_DIMENSION, t.getType(R.styleable.style1_type7));
+        assertEquals(TypedValue.TYPE_STRING, t.getType(R.styleable.style1_type8));
+        assertEquals(TypedValue.TYPE_FLOAT, t.getType(R.styleable.style1_type9));
+        assertEquals(TypedValue.TYPE_FRACTION, t.getType(R.styleable.style1_type10));
+        assertEquals(TypedValue.TYPE_INT_DEC, t.getType(R.styleable.style1_type11));
+        assertEquals(TypedValue.TYPE_INT_DEC, t.getType(R.styleable.style1_type12));
+        assertEquals(TypedValue.TYPE_STRING, t.getType(R.styleable.style1_type13));
+        assertEquals(TypedValue.TYPE_STRING, t.getType(R.styleable.style1_type14));
+        assertEquals(TypedValue.TYPE_REFERENCE, t.getType(R.styleable.style1_type15));
+        assertEquals(TypedValue.TYPE_STRING, t.getType(R.styleable.style1_type16));
+        assertEquals(TypedValue.TYPE_NULL, t.getType(R.styleable.style1_typeEmpty));
+        assertEquals(TypedValue.TYPE_NULL, t.getType(R.styleable.style1_typeUndefined));
 
-        // getColorStateList test
-        final int[] set = new int[1];
-        set[0] = 0;
+        t.recycle();
+    }
+
+    public void testBasics() {
+        final TypedArray t = getContext().getTheme().obtainStyledAttributes(
+                R.style.Whatever, R.styleable.style1);
+
+        assertEquals(EXPECTED_CHANGING_CONFIG, t.getChangingConfigurations());
+        assertEquals(EXPECTED_INDEX_COUNT, t.getIndexCount());
+        assertEquals(EXPTECTED_POS_DESCRIP, t.getPositionDescription());
+        assertEquals(EXPECTED_LENGTH, t.length());
+        assertEquals(getContext().getResources(), t.getResources());
+        assertNotNull(t.toString());
+
+        t.recycle();
+    }
+
+    public void testGetAttributes() {
+        final TypedArray t = getContext().getTheme().obtainStyledAttributes(
+                R.style.Whatever, R.styleable.style1);
+
+        assertTrue(t.getBoolean(R.styleable.style1_type1, false));
+        assertFalse(t.getBoolean(R.styleable.style1_type2, true));
+
+        assertEquals(EXPECTED_COLOR,
+                t.getColor(R.styleable.style1_type3, DEFINT));
         assertEquals(EXPECTED_COLOR_STATE,
-                mTypedArray.getColorStateList(R.styleable.style1_type4).
-                getColorForState(set, DEFINT));
+                t.getColorStateList(R.styleable.style1_type4).getDefaultColor());
 
         // This get values equals attribute dimension value set in styles.xml
         // multiplied by the appropriate metric, the metric is unknown.
         assertEquals(EXPECTED_DIMENSION,
-                mTypedArray.getDimension(R.styleable.style1_type5, DEFFLOAT));
+                t.getDimension(R.styleable.style1_type5, DEFFLOAT));
+
         assertEquals(EXPECTED_PIXEL_OFFSET,
-                mTypedArray.getDimensionPixelOffset(R.styleable.style1_type6, DEFINT));
+                t.getDimensionPixelOffset(R.styleable.style1_type6, DEFINT));
         assertEquals(EXPECTED_LAYOUT_DIMENSION,
-                mTypedArray.getLayoutDimension(R.styleable.style1_type6, "type6"));
+                t.getLayoutDimension(R.styleable.style1_type6, "type6"));
         assertEquals(EXPECTED_LAYOUT_DIMENSION,
-                mTypedArray.getLayoutDimension(R.styleable.style1_type6, 0));
+                t.getLayoutDimension(R.styleable.style1_type6, 0));
+
         assertEquals(EXPECTED_PIXEL_SIZE,
-                mTypedArray.getDimensionPixelSize(R.styleable.style1_type7, DEFINT));
+                t.getDimensionPixelSize(R.styleable.style1_type7, DEFINT));
 
-        // getDrawable test
-        assertNotNull(mTypedArray.getDrawable(R.styleable.style1_type8));
-        // getResourceId test
-        assertEquals(R.drawable.pass,
-                mTypedArray.getResourceId(R.styleable.style1_type8, DEFINT));
+        assertNotNull(t.getDrawable(R.styleable.style1_type8));
+        assertEquals(R.drawable.pass, t.getResourceId(R.styleable.style1_type8, DEFINT));
 
-        assertEquals(EXPECTED_FLOAT, mTypedArray.getFloat(R.styleable.style1_type9, DEFFLOAT));
-
+        assertEquals(EXPECTED_FLOAT,
+                t.getFloat(R.styleable.style1_type9, DEFFLOAT));
         assertEquals(EXPECTED_FRACTION,
-                mTypedArray.getFraction(R.styleable.style1_type10, 10, 10, DEFFLOAT));
+                t.getFraction(R.styleable.style1_type10, 10, 10, DEFFLOAT));
+        assertEquals(EXPECTED_INT,
+                t.getInt(R.styleable.style1_type11, DEFINT));
+        assertEquals(EXPECTED_INT_ATT,
+                t.getInteger(R.styleable.style1_type12, DEFINT));
 
-        assertEquals(EXPECTED_INT, mTypedArray.getInt(R.styleable.style1_type11, DEFINT));
+        assertEquals(EXPECTED_STRING, t.getString(R.styleable.style1_type13));
+        assertNull(t.getNonResourceString(R.styleable.style1_type14));
+        assertEquals(EXPECTED_TEXT, t.getText(R.styleable.style1_type14));
 
-        assertEquals(EXPECTED_INT_ATT, mTypedArray.getInteger(R.styleable.style1_type12, DEFINT));
-
-        assertEquals(EXPECTED_STRING, mTypedArray.getString(R.styleable.style1_type13));
-
-        // getNonResourceString test
-        assertNull(mTypedArray.getNonResourceString(R.styleable.style1_type14));
-
-        assertEquals(EXPECTED_TEXT, mTypedArray.getText(R.styleable.style1_type14));
-
-        CharSequence[] textArray = mTypedArray.getTextArray(R.styleable.style1_type15);
+        final CharSequence[] textArray = t.getTextArray(R.styleable.style1_type15);
         assertEquals(EXPECTED_TEXT_ARRAY[0], textArray[0]);
         assertEquals(EXPECTED_TEXT_ARRAY[1], textArray[1]);
         assertEquals(EXPECTED_TEXT_ARRAY[2], textArray[2]);
 
-        // getIndex test
-        int index = mTypedArray.getIndex(R.styleable.style1_type16);
-        assertEquals(EXPETED_INDEX, index);
-        assertTrue(mTypedArray.getValue(index, DEF_VALUE));
-        // hasValue test
-        assertTrue(mTypedArray.hasValue(R.styleable.style1_type16));
+        final int index = t.getIndex(R.styleable.style1_type16);
+        assertEquals(EXPECTED_INDEX, index);
+        assertTrue(t.getValue(index, DEF_VALUE));
+    }
 
-        // peekValue test
-        assertNotNull(mTypedArray.peekValue(R.styleable.style1_type16));
+    public void testPeekValue() {
+        final TypedArray t = getContext().getTheme().obtainStyledAttributes(
+                R.style.Whatever, R.styleable.style1);
 
-        assertEquals(EXPECTED_INDEX_COUNT, mTypedArray.getIndexCount());
+        final TypedValue v = t.peekValue(R.styleable.style1_type11);
+        assertNotNull(v);
+        assertEquals(TypedValue.TYPE_INT_DEC, v.type);
+        assertEquals(EXPECTED_INT, v.data);
 
-        assertEquals(EXPTECTED_POS_DESCRIP,
-                mTypedArray.getPositionDescription());
+        t.recycle();
+    }
 
-        // getResources test
-        assertEquals(getContext().getResources(), mTypedArray.getResources());
+    public void testHasValue() {
+        final TypedArray t = getContext().getTheme().obtainStyledAttributes(
+                R.style.Whatever, R.styleable.style1);
 
-        assertEquals(EXPECTED_LENGTH, mTypedArray.length());
+        // hasValue()
+        assertTrue(t.hasValue(R.styleable.style1_type16));
+        assertFalse(t.hasValue(R.styleable.style1_typeEmpty));
+        assertFalse(t.hasValue(R.styleable.style1_typeUndefined));
 
-        // toString test
-        assertNotNull(mTypedArray.toString());
+        // hasValueOrEmpty()
+        assertTrue(t.hasValueOrEmpty(R.styleable.style1_type16));
+        assertTrue(t.hasValueOrEmpty(R.styleable.style1_typeEmpty));
+        assertFalse(t.hasValueOrEmpty(R.styleable.style1_typeUndefined));
+
+        t.recycle();
     }
 
     public void testRecycle() {
diff --git a/tests/tests/graphics/res/color/fill_gradient_linear.xml b/tests/tests/graphics/res/color/fill_gradient_linear.xml
index e0e3f03..d9b7497 100644
--- a/tests/tests/graphics/res/color/fill_gradient_linear.xml
+++ b/tests/tests/graphics/res/color/fill_gradient_linear.xml
@@ -18,8 +18,8 @@
 -->
 <gradient xmlns:android="http://schemas.android.com/apk/res/android"
           android:angle="90"
-          android:startColor="?android:attr/colorPrimary"
-          android:endColor="?android:attr/colorControlActivated"
+          android:startColor="?attr/themeColor"
+          android:endColor="#0f0"
           android:centerColor="#00ff0000"
           android:startX="0"
           android:startY="0"
diff --git a/tests/tests/graphics/res/color/fill_gradient_linear_item.xml b/tests/tests/graphics/res/color/fill_gradient_linear_item.xml
index cfb1236..c1fb560 100644
--- a/tests/tests/graphics/res/color/fill_gradient_linear_item.xml
+++ b/tests/tests/graphics/res/color/fill_gradient_linear_item.xml
@@ -18,15 +18,15 @@
 -->
 <gradient xmlns:android="http://schemas.android.com/apk/res/android"
           android:angle="90"
-          android:startColor="?android:attr/colorPrimary"
-          android:endColor="?android:attr/colorControlActivated"
+          android:startColor="?attr/themeColor"
+          android:endColor="#0f0"
           android:centerColor="#f00"
           android:startX="0"
           android:startY="0"
           android:endX="100"
           android:endY="100"
           android:type="linear">
-    <item android:offset="0.1" android:color="?android:attr/colorPrimary"/>
+    <item android:offset="0.1" android:color="?attr/themeColor"/>
     <item android:offset="0.4" android:color="#fff"/>
-    <item android:offset="0.9" android:color="?android:attr/colorControlActivated"/>
+    <item android:offset="0.9" android:color="#0f0"/>
 </gradient>
\ No newline at end of file
diff --git a/tests/tests/graphics/res/color/fill_gradient_linear_item_overlap.xml b/tests/tests/graphics/res/color/fill_gradient_linear_item_overlap.xml
index 18274b9..a5b261a 100644
--- a/tests/tests/graphics/res/color/fill_gradient_linear_item_overlap.xml
+++ b/tests/tests/graphics/res/color/fill_gradient_linear_item_overlap.xml
@@ -18,16 +18,16 @@
 -->
 <gradient xmlns:android="http://schemas.android.com/apk/res/android"
           android:angle="90"
-          android:startColor="?android:attr/colorPrimary"
-          android:endColor="?android:attr/colorControlActivated"
+          android:startColor="?attr/themeColor"
+          android:endColor="#0f0"
           android:centerColor="#f00"
           android:startX="0"
           android:startY="0"
           android:endX="100"
           android:endY="100"
           android:type="linear">
-    <item android:offset="0.1" android:color="?android:attr/colorPrimary"/>
+    <item android:offset="0.1" android:color="?attr/themeColor"/>
     <item android:offset="0.4" android:color="#f00"/>
     <item android:offset="0.4" android:color="#fff"/>
-    <item android:offset="0.9" android:color="?android:attr/colorControlActivated"/>
+    <item android:offset="0.9" android:color="#0f0"/>
 </gradient>
\ No newline at end of file
diff --git a/tests/tests/graphics/res/color/fill_gradient_radial.xml b/tests/tests/graphics/res/color/fill_gradient_radial.xml
index ef6fd70..389a0fc 100644
--- a/tests/tests/graphics/res/color/fill_gradient_radial.xml
+++ b/tests/tests/graphics/res/color/fill_gradient_radial.xml
@@ -18,10 +18,10 @@
 -->
 <gradient xmlns:android="http://schemas.android.com/apk/res/android"
           android:centerColor="#ff0000"
-          android:endColor="?android:attr/colorControlActivated"
+          android:endColor="#0f0"
           android:centerX="300"
           android:centerY="300"
           android:gradientRadius="100"
-          android:startColor="?android:attr/colorPrimary"
+          android:startColor="?attr/themeColor"
           android:type="radial">
 </gradient>
\ No newline at end of file
diff --git a/tests/tests/graphics/res/color/fill_gradient_radial_item.xml b/tests/tests/graphics/res/color/fill_gradient_radial_item.xml
index c6cea7c..2f116c9 100644
--- a/tests/tests/graphics/res/color/fill_gradient_radial_item.xml
+++ b/tests/tests/graphics/res/color/fill_gradient_radial_item.xml
@@ -24,7 +24,7 @@
           android:gradientRadius="100"
           android:startColor="#ffffffff"
           android:type="radial">
-    <item android:offset="0.1" android:color="?android:attr/colorPrimary"/>
+    <item android:offset="0.1" android:color="?attr/themeColor"/>
     <item android:offset="0.4" android:color="#fff"/>
-    <item android:offset="0.9" android:color="?android:attr/colorControlActivated"/>
+    <item android:offset="0.9" android:color="#0f0"/>
 </gradient>
\ No newline at end of file
diff --git a/tests/tests/graphics/res/color/fill_gradient_radial_item_short.xml b/tests/tests/graphics/res/color/fill_gradient_radial_item_short.xml
index fefbe9f..111d023 100644
--- a/tests/tests/graphics/res/color/fill_gradient_radial_item_short.xml
+++ b/tests/tests/graphics/res/color/fill_gradient_radial_item_short.xml
@@ -21,6 +21,6 @@
           android:centerY="300"
           android:gradientRadius="100"
           android:type="radial">
-    <item android:offset="0.1" android:color="?android:attr/colorPrimary"/>
-    <item android:offset="0.9" android:color="?android:attr/colorControlActivated"/>
+    <item android:offset="0.1" android:color="?attr/themeColor"/>
+    <item android:offset="0.9" android:color="#0f0"/>
 </gradient>
\ No newline at end of file
diff --git a/tests/tests/graphics/res/color/fill_gradient_sweep_item.xml b/tests/tests/graphics/res/color/fill_gradient_sweep_item.xml
index 332b9389..2a010c0 100644
--- a/tests/tests/graphics/res/color/fill_gradient_sweep_item.xml
+++ b/tests/tests/graphics/res/color/fill_gradient_sweep_item.xml
@@ -24,7 +24,7 @@
           android:gradientRadius="10"
           android:startColor="#ffffffff"
           android:type="sweep">
-    <item android:offset="0.1" android:color="?android:attr/colorPrimary"/>
+    <item android:offset="0.1" android:color="?attr/themeColor"/>
     <item android:offset="0.4" android:color="#fff"/>
-    <item android:offset="0.9" android:color="?android:attr/colorControlActivated"/>
+    <item android:offset="0.9" android:color="#0f0"/>
 </gradient>
diff --git a/tests/tests/graphics/res/color/fill_gradient_sweep_item_long.xml b/tests/tests/graphics/res/color/fill_gradient_sweep_item_long.xml
index 3931288..7b0bbef 100644
--- a/tests/tests/graphics/res/color/fill_gradient_sweep_item_long.xml
+++ b/tests/tests/graphics/res/color/fill_gradient_sweep_item_long.xml
@@ -22,9 +22,9 @@
           android:gradientRadius="10"
           android:type="sweep">
     <item android:offset="-0.3" android:color="#f00"/>
-    <item android:offset="0.1" android:color="?android:attr/colorPrimary"/>
+    <item android:offset="0.1" android:color="?attr/themeColor"/>
     <item android:offset="0.4" android:color="#0f0"/>
     <item android:offset="0.6" android:color="#00f"/>
-    <item android:offset="0.7" android:color="?android:attr/colorControlActivated"/>
+    <item android:offset="0.7" android:color="#0f0"/>
     <item android:offset="1.5" android:color="#00f"/>
 </gradient>
diff --git a/tests/tests/graphics/res/drawable-nodpi/vector_icon_gradient_1_golden.png b/tests/tests/graphics/res/drawable-nodpi/vector_icon_gradient_1_golden.png
index 638802f..d5288d1 100644
--- a/tests/tests/graphics/res/drawable-nodpi/vector_icon_gradient_1_golden.png
+++ b/tests/tests/graphics/res/drawable-nodpi/vector_icon_gradient_1_golden.png
Binary files differ
diff --git a/tests/tests/graphics/res/drawable-nodpi/vector_icon_gradient_2_golden.png b/tests/tests/graphics/res/drawable-nodpi/vector_icon_gradient_2_golden.png
index 1f248e3..54fbca7 100644
--- a/tests/tests/graphics/res/drawable-nodpi/vector_icon_gradient_2_golden.png
+++ b/tests/tests/graphics/res/drawable-nodpi/vector_icon_gradient_2_golden.png
Binary files differ
diff --git a/tests/tests/graphics/res/drawable-nodpi/vector_icon_gradient_3_golden.png b/tests/tests/graphics/res/drawable-nodpi/vector_icon_gradient_3_golden.png
index 085e72a..09fd92f 100644
--- a/tests/tests/graphics/res/drawable-nodpi/vector_icon_gradient_3_golden.png
+++ b/tests/tests/graphics/res/drawable-nodpi/vector_icon_gradient_3_golden.png
Binary files differ
diff --git a/tests/tests/graphics/src/android/graphics/cts/OutlineTest.java b/tests/tests/graphics/src/android/graphics/cts/OutlineTest.java
new file mode 100644
index 0000000..0dcff12
--- /dev/null
+++ b/tests/tests/graphics/src/android/graphics/cts/OutlineTest.java
@@ -0,0 +1,186 @@
+/*
+ * Copyright (C) 2016 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package android.graphics.cts;
+
+import android.graphics.Outline;
+import android.graphics.Path;
+import android.graphics.Rect;
+import android.test.suitebuilder.annotation.SmallTest;
+import junit.framework.TestCase;
+import org.junit.Test;
+
+@SmallTest
+public class OutlineTest extends TestCase {
+    @Test
+    public void testDefaults() {
+        Outline outline = new Outline();
+
+        assertEquals(0.0f, outline.getAlpha());
+        assertTrue(outline.isEmpty());
+        Rect outRect = new Rect();
+        assertFalse(outline.getRect(outRect));
+        assertTrue(outline.getRadius() < 0);
+    }
+
+    @Test
+    public void testGetSetAlpha() {
+        Outline outline = new Outline();
+
+        outline.setAlpha(1.0f);
+        assertEquals(1.0f, outline.getAlpha());
+
+        outline.setAlpha(0.0f);
+        assertEquals(0.0f, outline.getAlpha());
+
+        outline.setAlpha(0.45f);
+        assertEquals(0.45f, outline.getAlpha());
+
+        // define out of range getter/setter behavior: (note will be clamped in native when consumed)
+        outline.setAlpha(4f);
+        assertEquals(4f, outline.getAlpha());
+        outline.setAlpha(-30f);
+        assertEquals(-30f, outline.getAlpha());
+    }
+
+    @Test
+    public void testSetRect() {
+        Outline outline = new Outline();
+        Rect outRect = new Rect();
+
+        outline.setRect(0, 0, 0, 0);
+        assertTrue(outline.isEmpty());
+
+        outline.setRect(10, 5, 4, 5);
+        assertTrue(outline.isEmpty());
+
+        outline.setRect(new Rect());
+        assertTrue(outline.isEmpty());
+
+        outline.setRect(10, 10, 20, 20);
+        assertFalse(outline.isEmpty());
+        assertTrue(outline.getRect(outRect));
+        assertEquals(new Rect(10, 10, 20, 20), outRect);
+        assertTrue(outline.canClip());
+
+        outline.setRect(new Rect(10, 10, 20, 20));
+        assertFalse(outline.isEmpty());
+        assertTrue(outline.getRect(outRect));
+        assertEquals(new Rect(10, 10, 20, 20), outRect);
+        assertTrue(outline.canClip());
+    }
+
+    @Test
+    public void testSetRoundRect() {
+        Outline outline = new Outline();
+        Rect outRect = new Rect();
+
+        outline.setRoundRect(0, 0, 0, 0, 1f);
+        assertTrue(outline.isEmpty());
+
+        outline.setRoundRect(10, 5, 4, 5, 1f);
+        assertTrue(outline.isEmpty());
+
+        outline.setRoundRect(new Rect(), 1f);
+        assertTrue(outline.isEmpty());
+
+        outline.setRoundRect(10, 10, 20, 20, 5f);
+        assertFalse(outline.isEmpty());
+        assertTrue(outline.getRect(outRect));
+        assertEquals(new Rect(10, 10, 20, 20), outRect);
+        assertEquals(5f, outline.getRadius());
+        assertTrue(outline.canClip());
+
+        outline.setRoundRect(new Rect(10, 10, 20, 20), 4f);
+        assertFalse(outline.isEmpty());
+        assertTrue(outline.getRect(outRect));
+        assertEquals(new Rect(10, 10, 20, 20), outRect);
+        assertEquals(4f, outline.getRadius());
+        assertTrue(outline.canClip());
+    }
+
+    @Test
+    public void testSetOval() {
+        Outline outline = new Outline();
+
+        outline.setOval(0, 0, 0, 0);
+        assertTrue(outline.isEmpty());
+
+        outline.setOval(10, 5, 4, 5);
+        assertTrue(outline.isEmpty());
+
+        Rect outRect = new Rect();
+        outline.setOval(0, 0, 50, 51); // different x & y radii, so not round rect
+        assertFalse(outline.getRect(outRect)); // not round rect, doesn't work
+        assertFalse(outline.canClip()); // not round rect, doesn't work
+        assertFalse(outline.isEmpty());
+
+        outline.setOval(0, 0, 50, 50); // same x & y radii, so round rect
+        assertTrue(outline.getRect(outRect)); // is round rect, so works
+        assertTrue(outline.canClip()); // is round rect, so works
+        assertFalse(outline.isEmpty());
+    }
+
+    @Test
+    public void testSetConvexPath() {
+        Outline outline = new Outline();
+        Path path = new Path();
+
+        assertTrue(path.isEmpty());
+        outline.setConvexPath(path);
+        assertTrue(outline.isEmpty());
+
+        path.addCircle(50, 50, 50, Path.Direction.CW);
+        outline.setConvexPath(path);
+        assertFalse(outline.isEmpty());
+    }
+
+    @Test
+    public void testGetRectRadius() {
+        Outline outline = new Outline();
+
+        Rect outRect = new Rect();
+        outline.setRoundRect(15, 10, 45, 40, 30.0f);
+        assertEquals(30.0f, outline.getRadius());
+        assertTrue(outline.getRect(outRect));
+        assertEquals(new Rect(15, 10, 45, 40), outRect);
+
+        outline.setRect(5, 10, 15, 20);
+        assertEquals(0.0f, outline.getRadius());
+        assertTrue(outline.getRect(outRect));
+        assertEquals(new Rect(5, 10, 15, 20), outRect);
+
+        outline.setOval(0, 0, 50, 60);
+        assertTrue(outline.getRadius() < 0);
+        assertFalse(outline.getRect(outRect));
+    }
+
+    @Test
+    public void testOffset() {
+        Outline outline = new Outline();
+
+        Rect outRect = new Rect();
+        outline.setRoundRect(15, 10, 45, 40, 30.0f);
+        outline.offset(-15, -10);
+        assertTrue(outline.getRect(outRect));
+        assertEquals(new Rect(0, 0, 30, 30), outRect);
+
+        outline.setRect(5, 10, 15, 20);
+        outline.offset(-5, -10);
+        assertTrue(outline.getRect(outRect));
+        assertEquals(new Rect(0, 0, 10, 10), outRect);
+    }
+}
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 f174f01..ac1d9b3 100644
--- a/tests/tests/graphics/src/android/graphics/drawable/cts/VectorDrawableTest.java
+++ b/tests/tests/graphics/src/android/graphics/drawable/cts/VectorDrawableTest.java
@@ -197,7 +197,9 @@
                 throw new XmlPullParserException("No start tag found");
             }
 
-            mVectorDrawable.inflate(mResources, parser, attrs, mContext.getTheme());
+            Theme theme = mResources.newTheme();
+            theme.applyStyle(R.style.Theme_ThemedDrawableTest, true);
+            mVectorDrawable.inflate(mResources, parser, attrs, theme);
 
             if (stateSet != null) {
                 mVectorDrawable.setState(stateSet);
diff --git a/tests/tests/icu/resources/android/icu/cts/expectations/icu-known-failures.txt b/tests/tests/icu/resources/android/icu/cts/expectations/icu-known-failures.txt
index e667c08..b92e754 100644
--- a/tests/tests/icu/resources/android/icu/cts/expectations/icu-known-failures.txt
+++ b/tests/tests/icu/resources/android/icu/cts/expectations/icu-known-failures.txt
@@ -16,9 +16,9 @@
   bug: "27310873"
 },
 {
-  description: "Cannot find any classes to test because APK doesn't have entries for directories, android/icu/",
+  description: "Cannot find any classes to test because .class files are not treated as resources in APK",
   name: "android.icu.dev.test.serializable.CoverageTest",
-  bug: "27310873"
+  bug: "27666677"
 },
 {
   description: "Serialized forms have not been converted to use repackaged classes",
@@ -34,6 +34,21 @@
   description: "A completely empty test case",
   name: "android.icu.dev.test.duration.PeriodBuilderTest"
 },
+{
+  description: "Fails on host and on device in same way before and after packaging",
+  name: "android.icu.dev.test.bidi.TestCompatibility#testCompatibility",
+  bug: "23995372"
+},
+{
+  description: "Problem with negative multiplier, not a regression",
+  name: "android.icu.dev.test.format.NumberFormatTest#TestNonpositiveMultiplier",
+  bug: "19185440"
+},
+{
+  description: "Wrong case for exponent separator",
+  name: "android.icu.dev.test.format.PluralRulesTest#testOverUnderflow",
+  bug: "27566754"
+},
 // The following are known to be broken but the reason is not yet known. They are expected to
 // succeed and so will be run and will fail but that is intentional so that they do not get
 // forgotten and are investigated to determine whether it is correct behavior on Android or a bug
@@ -41,35 +56,12 @@
 {
   description: "Broken and not yet triaged",
   names: [
-    "android.icu.dev.test.bidi.TestCompatibility#testCompatibility",
-    "android.icu.dev.test.calendar.ChineseTest#TestCoverage",
-    "android.icu.dev.test.calendar.ChineseTest#TestInitWithCurrentTime",
-    "android.icu.dev.test.calendar.IBMCalendarTest#TestAddRollEra0AndEraBounds",
-    "android.icu.dev.test.duration.ICUDurationTest#TestBasics",
-    "android.icu.dev.test.format.DataDrivenFormatTest#TestConsistentPivot",
-    "android.icu.dev.test.format.DataDrivenFormatTest#TestDateFormatBasic",
-    "android.icu.dev.test.format.DateFormatRegressionTest#Test4073003",
-    "android.icu.dev.test.format.DateFormatRegressionTest#Test4151706",
-    "android.icu.dev.test.format.DateFormatRegressionTest#Test4182066",
-    "android.icu.dev.test.format.DateFormatTest#TestBadInput135",
-    "android.icu.dev.test.format.DateFormatTest#TestDotAndAtLeniency",
-    "android.icu.dev.test.format.DateFormatTest#TestGenericTime",
-    "android.icu.dev.test.format.DateFormatTest#TestPartialParse994",
-    "android.icu.dev.test.format.DateFormatTest#TestQuarters",
-    "android.icu.dev.test.format.DateFormatTest#TestSpaceParsing",
-    "android.icu.dev.test.format.DateFormatTest#TestTwoDigitYear",
-    "android.icu.dev.test.format.DateFormatTest#TestWhiteSpaceParsing",
     "android.icu.dev.test.format.NumberFormatTest#TestDataDrivenJDK",
-    "android.icu.dev.test.format.NumberFormatTest#TestNonpositiveMultiplier",
-    "android.icu.dev.test.format.PluralRulesTest#testOverUnderflow",
-    "android.icu.dev.test.timezone.TimeZoneBoundaryTest#TestStepwise",
-    "android.icu.dev.test.timezone.TimeZoneTest#TestObservesDaylightTime",
-    "android.icu.dev.test.util.CurrencyTest#TestGetKeywordValues"
   ],
   result: "SUCCESS"
 },
 {
-  description: "Broken due to warnings, not yet triaged",
+  description: "Collation rules data has been removed from ICU4J data on Android",
   names: [
     "android.icu.dev.test.collator.CollationCreationMethodTest#TestRuleVsLocaleCreationMonkey",
     "android.icu.dev.test.collator.CollationMiscTest#TestImport",
@@ -78,6 +70,6 @@
     "android.icu.dev.test.collator.CollationTest#TestDataDriven",
     "android.icu.dev.test.collator.G7CollationTest#TestG7Data"
   ],
-  result: "SUCCESS"
+  bug: "27552651"
 }
 ]
diff --git a/tests/tests/net/src/android/net/cts/TheaterModeTest.java b/tests/tests/net/src/android/net/cts/TheaterModeTest.java
new file mode 100644
index 0000000..10fca6f
--- /dev/null
+++ b/tests/tests/net/src/android/net/cts/TheaterModeTest.java
@@ -0,0 +1,84 @@
+/*
+ * Copyright (C) 2016 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package android.net.cts;
+
+import android.content.ContentResolver;
+import android.content.Context;
+import android.provider.Settings;
+import android.test.AndroidTestCase;
+import android.util.Log;
+
+import java.lang.Thread;
+
+public class TheaterModeTest extends AndroidTestCase {
+    private static final String TAG = "TheaterModeTest";
+    private static final String FEATURE_BLUETOOTH = "android.hardware.bluetooth";
+    private static final String FEATURE_WIFI = "android.hardware.wifi";
+    private static final int TIMEOUT_MS = 10 * 1000;
+    private boolean mHasFeature;
+    private Context mContext;
+    private ContentResolver resolver;
+
+    public void setup() {
+        mContext= getContext();
+        resolver = mContext.getContentResolver();
+        mHasFeature = (mContext.getPackageManager().hasSystemFeature(FEATURE_BLUETOOTH)
+                       || mContext.getPackageManager().hasSystemFeature(FEATURE_WIFI));
+    }
+
+    public void testTheaterMode() {
+        setup();
+        if (!mHasFeature) {
+            Log.i(TAG, "The device doesn't support network bluetooth or wifi feature");
+            return;
+        }
+
+        for (int testCount = 0; testCount < 2; testCount++) {
+            if (!doOneTest()) {
+                fail("Theater mode failed to change in " + TIMEOUT_MS + "msec");
+                return;
+            }
+        }
+    }
+
+    private boolean doOneTest() {
+        boolean theaterModeOn = isTheaterModeOn();
+
+        setTheaterModeOn(!theaterModeOn);
+        try {
+            Thread.sleep(TIMEOUT_MS);
+        } catch (InterruptedException e) {
+            Log.e(TAG, "Sleep time interrupted.", e);
+        }
+
+        if (theaterModeOn == isTheaterModeOn()) {
+            return false;
+        }
+        return true;
+    }
+
+    private void setTheaterModeOn(boolean enabling) {
+        // Change the system setting for theater mode
+        Settings.Global.putInt(resolver, Settings.Global.THEATER_MODE_ON, enabling ? 1 : 0);
+    }
+
+    private boolean isTheaterModeOn() {
+        // Read the system setting for theater mode
+        return Settings.Global.getInt(mContext.getContentResolver(),
+                                      Settings.Global.THEATER_MODE_ON, 0) != 0;
+    }
+}
diff --git a/tests/tests/automotive/Android.mk b/tests/tests/networksecurityconfig/networksecurityconfig-cleartext/Android.mk
similarity index 73%
copy from tests/tests/automotive/Android.mk
copy to tests/tests/networksecurityconfig/networksecurityconfig-cleartext/Android.mk
index abef2ac..df29b5f 100644
--- a/tests/tests/automotive/Android.mk
+++ b/tests/tests/networksecurityconfig/networksecurityconfig-cleartext/Android.mk
@@ -11,28 +11,24 @@
 # 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.
-
-LOCAL_PATH:= $(call my-dir)
+#
+LOCAL_PATH := $(call my-dir)
 
 include $(CLEAR_VARS)
+LOCAL_PACKAGE_NAME := CtsNetSecConfigCleartextTrafficTestCases
 
-LOCAL_PACKAGE_NAME := CtsAutomotiveTestCases
-
-# Don't include this package in any target.
-LOCAL_MODULE_TAGS := optional
-
-# When built, explicitly put it in the data partition.
+LOCAL_MODULE_TAGS := tests
 LOCAL_MODULE_PATH := $(TARGET_OUT_DATA_APPS)
 
-LOCAL_STATIC_JAVA_LIBRARIES := ctstestrunner
-
-LOCAL_JAVA_LIBRARIES := android.car
+LOCAL_STATIC_JAVA_LIBRARIES := ctstestrunner org.apache.http.legacy android-support-test
 
 LOCAL_SRC_FILES := $(call all-java-files-under, src)
+LOCAL_SRC_FILES += $(call all-java-files-under, ../src)
+
+LOCAL_RESOURCE_DIR := $(LOCAL_PATH)/res/
 
 # Tag this module as a cts test artifact
 LOCAL_COMPATIBILITY_SUITE := cts
 
 LOCAL_SDK_VERSION := current
-
 include $(BUILD_CTS_PACKAGE)
diff --git a/tests/tests/networksecurityconfig/networksecurityconfig-cleartext/AndroidManifest.xml b/tests/tests/networksecurityconfig/networksecurityconfig-cleartext/AndroidManifest.xml
new file mode 100644
index 0000000..dbb4770
--- /dev/null
+++ b/tests/tests/networksecurityconfig/networksecurityconfig-cleartext/AndroidManifest.xml
@@ -0,0 +1,34 @@
+<?xml version="1.0" encoding="utf-8"?>
+
+<!--
+ * Copyright (C) 2016 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.
+ -->
+
+<manifest xmlns:android="http://schemas.android.com/apk/res/android"
+        package="android.security.net.config.cts.CtsNetSecConfigCleartextTrafficTestCases">
+  <application>
+      <uses-library android:name="android.test.runner"/>
+      <meta-data android:name="android.security.net.config"
+                 android:resource="@xml/network_security_config" />
+  </application>
+
+  <uses-permission android:name="android.permission.INTERNET" />
+  <instrumentation android:name="android.support.test.runner.AndroidJUnitRunner"
+                   android:targetPackage="android.security.net.config.cts.CtsNetSecConfigCleartextTrafficTestCases"
+                   android:label="">
+        <meta-data android:name="listener"
+            android:value="com.android.cts.runner.CtsTestRunListener" />
+    </instrumentation>
+</manifest>
diff --git a/tests/tests/automotive/AndroidTest.xml b/tests/tests/networksecurityconfig/networksecurityconfig-cleartext/AndroidTest.xml
similarity index 75%
copy from tests/tests/automotive/AndroidTest.xml
copy to tests/tests/networksecurityconfig/networksecurityconfig-cleartext/AndroidTest.xml
index b4af1f5..9957342 100644
--- a/tests/tests/automotive/AndroidTest.xml
+++ b/tests/tests/networksecurityconfig/networksecurityconfig-cleartext/AndroidTest.xml
@@ -13,12 +13,12 @@
      See the License for the specific language governing permissions and
      limitations under the License.
 -->
-<configuration description="Config for CTS Automotive test cases">
+<configuration description="Config for CTS CtsNetSecConfigCleartextTraffic test cases">
     <target_preparer class="com.android.compatibility.common.tradefed.targetprep.ApkInstaller">
         <option name="cleanup-apks" value="true" />
-        <option name="test-file-name" value="CtsAutomotiveTestCases.apk" />
+        <option name="test-file-name" value="CtsNetSecConfigCleartextTrafficTestCases.apk" />
     </target_preparer>
     <test class="com.android.tradefed.testtype.AndroidJUnitTest" >
-        <option name="package" value="android.support.car.cts" />
+        <option name="package" value="android.security.net.config.cts.CtsNetSecConfigCleartextTrafficTestCases" />
     </test>
 </configuration>
diff --git a/tests/tests/networksecurityconfig/networksecurityconfig-cleartext/res/xml/network_security_config.xml b/tests/tests/networksecurityconfig/networksecurityconfig-cleartext/res/xml/network_security_config.xml
new file mode 100644
index 0000000..987b178
--- /dev/null
+++ b/tests/tests/networksecurityconfig/networksecurityconfig-cleartext/res/xml/network_security_config.xml
@@ -0,0 +1,9 @@
+<?xml version="1.0" encoding="utf-8"?>
+<network-security-config>
+  <domain-config cleartextTrafficPermitted="false">
+    <domain includeSubdomains="true">android.com</domain>
+    <domain-config cleartextTrafficPermitted="true">
+      <domain>developer.android.com</domain>
+    </domain-config>
+  </domain-config>
+</network-security-config>
diff --git a/tests/tests/networksecurityconfig/networksecurityconfig-cleartext/src/android/security/net/config/cts/CleartextPermittedTest.java b/tests/tests/networksecurityconfig/networksecurityconfig-cleartext/src/android/security/net/config/cts/CleartextPermittedTest.java
new file mode 100644
index 0000000..401b5ac
--- /dev/null
+++ b/tests/tests/networksecurityconfig/networksecurityconfig-cleartext/src/android/security/net/config/cts/CleartextPermittedTest.java
@@ -0,0 +1,43 @@
+/*
+ * Copyright (C) 2016 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package android.security.net.config.cts;
+
+import java.security.cert.CertificateException;
+import java.security.cert.X509Certificate;
+import javax.net.ssl.X509TrustManager;
+import junit.framework.TestCase;
+
+public class CleartextPermittedTest extends TestCase {
+    public void testDefaultAllowed() throws Exception {
+        TestUtils.assertCleartextConnectionSucceeds("google.com", 80);
+        TestUtils.assertTlsConnectionSucceeds("google.com", 443);
+    }
+
+    public void testCleartextBlocked() throws Exception {
+        TestUtils.assertCleartextConnectionFails("android.com", 80);
+        TestUtils.assertTlsConnectionSucceeds("android.com", 443);
+        // subdomains of android.com are also disallowed.
+        TestUtils.assertCleartextConnectionFails("www.android.com", 80);
+        TestUtils.assertTlsConnectionSucceeds("www.android.com", 443);
+    }
+
+    public void testNestedCleartextPermitted() throws Exception {
+        // developer.android.com is explicitly permitted.
+        TestUtils.assertCleartextConnectionSucceeds("developer.android.com", 80);
+        TestUtils.assertTlsConnectionSucceeds("developer.android.com", 443);
+    }
+}
diff --git a/tests/tests/networksecurityconfig/src/android/security/net/config/cts/TestUtils.java b/tests/tests/networksecurityconfig/src/android/security/net/config/cts/TestUtils.java
index 0952cd3..d114ab5 100644
--- a/tests/tests/networksecurityconfig/src/android/security/net/config/cts/TestUtils.java
+++ b/tests/tests/networksecurityconfig/src/android/security/net/config/cts/TestUtils.java
@@ -20,6 +20,7 @@
 
 import java.io.InputStream;
 import java.io.IOException;
+import java.net.HttpURLConnection;
 import java.net.Socket;
 import java.net.URL;
 import java.security.KeyStore;
@@ -28,7 +29,6 @@
 import java.security.cert.X509Certificate;
 import java.util.List;
 import java.util.ArrayList;
-import javax.net.ssl.HttpsURLConnection;
 import javax.net.ssl.SSLContext;
 import javax.net.ssl.SSLHandshakeException;
 import javax.net.ssl.TrustManager;
@@ -45,17 +45,26 @@
     private TestUtils() {
     }
 
-
     public static void assertTlsConnectionSucceeds(String host, int port) throws Exception {
         assertSslSocketSucceeds(host, port);
-        assertHttpClientHttpsSucceeds(host, port);
-        assertUrlConnectionHttpsSucceeds(host, port);
+        assertHttpClientSucceeds(host, port, true /* https */);
+        assertUrlConnectionSucceeds(host, port, true /* https */);
     }
 
     public static void assertTlsConnectionFails(String host, int port) throws Exception {
         assertSslSocketFails(host, port);
-        assertHttpClientHttpsFails(host, port);
-        assertUrlConnectionHttpsFails(host, port);
+        assertHttpClientFails(host, port, true /* https */);
+        assertUrlConnectionFails(host, port, true /* https */);
+    }
+
+    public static void assertCleartextConnectionSucceeds(String host, int port) throws Exception {
+        assertHttpClientSucceeds(host, port, false /* http */);
+        assertUrlConnectionSucceeds(host, port, false /* http */);
+    }
+
+    public static void assertCleartextConnectionFails(String host, int port) throws Exception {
+        assertHttpClientFails(host, port, false /* http */);
+        assertUrlConnectionFails(host, port, false /* http */);
     }
 
     public static X509TrustManager getDefaultTrustManager() throws Exception {
@@ -95,26 +104,27 @@
         s.getInputStream();
     }
 
-    private static void assertUrlConnectionHttpsFails(String host, int port)
+    private static void assertUrlConnectionFails(String host, int port, boolean https)
             throws Exception {
-        URL url = new URL("https://" + host + ":" + port);
-        HttpsURLConnection connection = (HttpsURLConnection) url.openConnection();
+        URL url = new URL((https ? "https://" : "http://") + host + ":" + port);
+        HttpURLConnection connection = (HttpURLConnection) url.openConnection();
         try {
             connection.getInputStream();
             fail("Connection to " + host + ":" + port + " succeeded");
-        } catch (SSLHandshakeException expected) {
+        } catch (IOException expected) {
         }
     }
 
-    private static void assertUrlConnectionHttpsSucceeds(String host, int port)
+    private static void assertUrlConnectionSucceeds(String host, int port, boolean https)
             throws Exception {
-        URL url = new URL("https://" + host + ":" + port);
-        HttpsURLConnection connection = (HttpsURLConnection) url.openConnection();
+        URL url = new URL((https ? "https://" : "http://") + host + ":" + port);
+        HttpURLConnection connection = (HttpURLConnection) url.openConnection();
         connection.getInputStream();
     }
 
-    private static void assertHttpClientHttpsSucceeds(String host, int port) throws Exception {
-        URL url = new URL("https://" + host + ":" + port);
+    private static void assertHttpClientSucceeds(String host, int port, boolean https)
+            throws Exception {
+        URL url = new URL((https ? "https://" : "http://") + host + ":" + port);
         AndroidHttpClient httpClient = AndroidHttpClient.newInstance(null);
         try {
             HttpResponse response = httpClient.execute(new HttpGet(url.toString()));
@@ -123,8 +133,9 @@
         }
     }
 
-    private static void assertHttpClientHttpsFails(String host, int port) throws Exception {
-        URL url = new URL("https://" + host + ":" + port);
+    private static void assertHttpClientFails(String host, int port, boolean https)
+            throws Exception {
+        URL url = new URL((https ? "https://" : "http://") + host + ":" + port);
         AndroidHttpClient httpClient = AndroidHttpClient.newInstance(null);
         try {
             HttpResponse response = httpClient.execute(new HttpGet(url.toString()));
diff --git a/tests/tests/telecom/src/android/telecom/cts/BaseTelecomTestWithMockServices.java b/tests/tests/telecom/src/android/telecom/cts/BaseTelecomTestWithMockServices.java
index 6810b71..8cf20bd 100644
--- a/tests/tests/telecom/src/android/telecom/cts/BaseTelecomTestWithMockServices.java
+++ b/tests/tests/telecom/src/android/telecom/cts/BaseTelecomTestWithMockServices.java
@@ -756,6 +756,24 @@
         );
     }
 
+    void assertDisconnectReason(final Connection connection, final String disconnectReason) {
+        waitUntilConditionIsTrueOrTimeout(
+                new Condition() {
+                    @Override
+                    public Object expected() {
+                        return disconnectReason;
+                    }
+
+                    @Override
+                    public Object actual() {
+                        return connection.getDisconnectCause().getReason();
+                    }
+                },
+                WAIT_FOR_STATE_CHANGE_TIMEOUT_MS,
+                "Connection should have been disconnected with reason: " + disconnectReason
+        );
+    }
+
     void assertConferenceState(final Conference conference, final int state) {
         waitUntilConditionIsTrueOrTimeout(
                 new Condition() {
diff --git a/tests/tests/telecom/src/android/telecom/cts/ExtendedInCallServiceTest.java b/tests/tests/telecom/src/android/telecom/cts/ExtendedInCallServiceTest.java
index 7d71c0f..fbda2a3 100644
--- a/tests/tests/telecom/src/android/telecom/cts/ExtendedInCallServiceTest.java
+++ b/tests/tests/telecom/src/android/telecom/cts/ExtendedInCallServiceTest.java
@@ -285,6 +285,29 @@
         assertConnectionState(connection, Connection.STATE_DISCONNECTED);
     }
 
+    public void testRejectIncomingCallWithMessage() {
+        if (!mShouldTestTelecom) {
+            return;
+        }
+        String disconnectReason = "Test reason for disconnect";
+
+        addAndVerifyNewIncomingCall(createTestNumber(), null);
+        final MockConnection connection = verifyConnectionForIncomingCall();
+
+        final MockInCallService inCallService = mInCallCallbacks.getService();
+
+        final Call call = inCallService.getLastCall();
+
+        assertCallState(call, Call.STATE_RINGING);
+        assertConnectionState(connection, Connection.STATE_RINGING);
+
+        call.reject(true, disconnectReason);
+
+        assertCallState(call, Call.STATE_DISCONNECTED);
+        assertConnectionState(connection, Connection.STATE_DISCONNECTED);
+        assertDisconnectReason(connection, disconnectReason);
+    }
+
     public void testCanAddCall_CannotAddForExistingDialingCall() {
         if (!mShouldTestTelecom) {
             return;
diff --git a/tests/tests/telecom/src/android/telecom/cts/MockConnection.java b/tests/tests/telecom/src/android/telecom/cts/MockConnection.java
index 9bb83a1..fe33a8d 100644
--- a/tests/tests/telecom/src/android/telecom/cts/MockConnection.java
+++ b/tests/tests/telecom/src/android/telecom/cts/MockConnection.java
@@ -70,6 +70,16 @@
     }
 
     @Override
+    public void onReject(String reason) {
+        super.onReject();
+        setDisconnected(new DisconnectCause(DisconnectCause.REJECTED, reason));
+        if (mRemoteConnection != null) {
+            mRemoteConnection.reject();
+        }
+        destroy();
+    }
+
+    @Override
     public void onHold() {
         super.onHold();
         setOnHold();
diff --git a/tests/tests/telecom/src/android/telecom/cts/MockConnectionService.java b/tests/tests/telecom/src/android/telecom/cts/MockConnectionService.java
index ad64e5c..48a1c94 100644
--- a/tests/tests/telecom/src/android/telecom/cts/MockConnectionService.java
+++ b/tests/tests/telecom/src/android/telecom/cts/MockConnectionService.java
@@ -73,6 +73,9 @@
             ConnectionRequest request) {
         final MockConnection connection = new MockConnection();
         connection.setAddress(request.getAddress(), CONNECTION_PRESENTATION);
+        connection.setConnectionCapabilities(
+                connection.getConnectionCapabilities() |
+                        Connection.CAPABILITY_CAN_SEND_RESPONSE_VIA_CONNECTION);
         connection.createMockVideoProvider();
         ((Connection) connection).setVideoState(request.getVideoState());
 
diff --git a/tests/tests/uirendering/src/android/uirendering/cts/testclasses/CanvasStateTests.java b/tests/tests/uirendering/src/android/uirendering/cts/testclasses/CanvasStateTests.java
index becc2f7..0e5fb0f 100644
--- a/tests/tests/uirendering/src/android/uirendering/cts/testclasses/CanvasStateTests.java
+++ b/tests/tests/uirendering/src/android/uirendering/cts/testclasses/CanvasStateTests.java
@@ -24,6 +24,9 @@
 import android.uirendering.cts.testinfrastructure.ActivityTestBase;
 import android.uirendering.cts.testinfrastructure.CanvasClient;
 
+import static org.junit.Assert.assertFalse;
+import static org.junit.Assert.assertTrue;
+
 /**
  * Tests of state query-able from canvas at draw time.
  *
diff --git a/tests/tests/uirendering/src/android/uirendering/cts/testclasses/ColorFilterAlphaTest.java b/tests/tests/uirendering/src/android/uirendering/cts/testclasses/ColorFilterAlphaTest.java
new file mode 100644
index 0000000..56ca467
--- /dev/null
+++ b/tests/tests/uirendering/src/android/uirendering/cts/testclasses/ColorFilterAlphaTest.java
@@ -0,0 +1,141 @@
+/*
+ * Copyright (C) 2016 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package android.uirendering.cts.testclasses;
+
+import android.graphics.Bitmap;
+import android.graphics.Canvas;
+import android.graphics.Paint;
+import android.graphics.Point;
+import android.graphics.PorterDuff;
+import android.graphics.PorterDuffXfermode;
+import android.graphics.PorterDuffColorFilter;
+import android.test.suitebuilder.annotation.MediumTest;
+import android.uirendering.cts.bitmapverifiers.SamplePointVerifier;
+import android.uirendering.cts.testinfrastructure.ActivityTestBase;
+import android.uirendering.cts.testinfrastructure.CanvasClient;
+import org.junit.Test;
+import org.junit.runner.RunWith;
+import org.junit.runners.Parameterized;
+
+import java.util.List;
+
+@RunWith(Parameterized.class)
+public class ColorFilterAlphaTest extends ActivityTestBase {
+    // We care about one point in each of the four rectangles of different alpha values, as well as
+    // the area outside the rectangles
+
+    public static final int FILTER_COLOR = 0xFFBB0000;
+
+    private static final Point[] TEST_POINTS = new Point[] {
+            new Point(9, 45),
+            new Point(27, 45),
+            new Point(45, 45),
+            new Point(63, 45),
+            new Point(81, 45)
+    };
+
+    private static Object[][] MODES_AND_EXPECTED_COLORS = new Object[][] {
+        { PorterDuff.Mode.DST, new int[] {
+                0xFFE6E6E6, 0xFFCCCCCC, 0xFFB3B3B3, 0xFF999999, 0xFFFFFFFF } },
+
+        { PorterDuff.Mode.SRC_OVER, new int[] {
+                0xFFBB0000, 0xFFBB0000, 0xFFBB0000, 0xFFBB0000, 0xFFBB0000 } },
+
+        { PorterDuff.Mode.DST_OVER, new int[] {
+                0xFFAF1A1A, 0xFFA33333, 0xFF984D4D, 0xFF8B6666, 0xFFBB0000 } },
+
+        { PorterDuff.Mode.SRC_IN, new int[] {
+                0xFFF1CCCC, 0xFFE49999, 0xFFD66666, 0xFFC83333, 0xFFFFFFFF } },
+
+        { PorterDuff.Mode.DST_IN, new int[] {
+                0xFFE6E6E6, 0xFFCCCCCC, 0xFFB3B3B3, 0xFF999999, 0xFFFFFFFF } },
+
+        { PorterDuff.Mode.SRC_OUT, new int[] {
+                0xFFC83333, 0xFFD66666, 0xFFE49999, 0xFFF1CCCC, 0xFFBB0000 } },
+
+        { PorterDuff.Mode.DST_OUT, new int[] {
+                0xFFFFFFFF, 0xFFFFFFFF, 0xFFFFFFFF, 0xFFFFFFFF, 0xFFFFFFFF } },
+
+        { PorterDuff.Mode.SRC_ATOP, new int[] {
+                0xFFF1CCCC, 0xFFE49999, 0xFFD66666, 0xFFC93333, 0xFFFFFFFF } },
+
+        { PorterDuff.Mode.DST_ATOP, new int[] {
+                0xFFB01A1A, 0xFFA33333, 0xFF984D4D, 0xFF8B6666, 0xFFBB0000 } },
+
+        { PorterDuff.Mode.XOR, new int[] {
+                0xFFC93333, 0xFFD66666, 0xFFE49999, 0xFFF1CCCC, 0xFFBB0000 } },
+
+        { PorterDuff.Mode.MULTIPLY, new int[] {
+                0xFFDFCCCC, 0xFFBE9999, 0xFF9E6666, 0xFF7E3333, 0xFFFFFFFF } },
+
+        { PorterDuff.Mode.SCREEN, new int[] {
+                0xFFC21A1A, 0xFFC93333, 0xFFD04D4D, 0xFFD66666, 0xFFBB0000 } },
+    };
+
+    @Parameterized.Parameters(name = "{0}")
+    public static List<XfermodeTest.Config> configs() {
+        return XfermodeTest.configs(MODES_AND_EXPECTED_COLORS);
+    }
+
+    private final XfermodeTest.Config mConfig;
+
+    public ColorFilterAlphaTest(XfermodeTest.Config config) {
+        mConfig = config;
+    }
+
+    private static final int[] BLOCK_COLORS = new int[] {
+            0x33808080,
+            0x66808080,
+            0x99808080,
+            0xCC808080,
+            0x00000000
+    };
+
+    private static Bitmap createMultiRectBitmap() {
+        Bitmap bitmap = Bitmap.createBitmap(TEST_WIDTH, TEST_HEIGHT, Bitmap.Config.ARGB_8888);
+        Canvas canvas = new Canvas(bitmap);
+        Paint paint = new Paint();
+        paint.setXfermode(new PorterDuffXfermode(PorterDuff.Mode.SRC));
+        final int blockCount = BLOCK_COLORS.length;
+        final int blockWidth = TEST_WIDTH / blockCount;
+        for (int i = 0 ; i < blockCount; i++) {
+            paint.setColor(BLOCK_COLORS[i]);
+            canvas.drawRect(i * blockWidth, 0, (i + 1) * blockWidth, TEST_HEIGHT, paint);
+        }
+        return bitmap;
+    }
+
+    private CanvasClient mCanvasClient = new CanvasClient() {
+        final Paint mPaint = new Paint();
+        private final Bitmap mBitmap = createMultiRectBitmap();
+
+        @Override
+        public void draw(Canvas canvas, int width, int height) {
+            mPaint.setColorFilter(new PorterDuffColorFilter(FILTER_COLOR, mConfig.mode));
+            canvas.drawBitmap(mBitmap, 0, 0, mPaint);
+        }
+    };
+
+    @Test
+    @MediumTest
+    public void test() {
+        createTest()
+                .addCanvasClient(mCanvasClient, mConfig.hardwareAccelerated)
+                .runWithVerifier(new SamplePointVerifier(TEST_POINTS, mConfig.expectedColors));
+    }
+}
+
+
diff --git a/tests/tests/uirendering/src/android/uirendering/cts/testclasses/LayerTests.java b/tests/tests/uirendering/src/android/uirendering/cts/testclasses/LayerTests.java
index a1338bc..30dbb03 100644
--- a/tests/tests/uirendering/src/android/uirendering/cts/testclasses/LayerTests.java
+++ b/tests/tests/uirendering/src/android/uirendering/cts/testclasses/LayerTests.java
@@ -23,15 +23,20 @@
 import android.graphics.Paint;
 import android.graphics.PorterDuff;
 import android.graphics.PorterDuffXfermode;
-import android.test.suitebuilder.annotation.SmallTest;
+import android.support.test.runner.AndroidJUnit4;
+import android.test.suitebuilder.annotation.MediumTest;
 import android.uirendering.cts.bitmapverifiers.ColorVerifier;
 import android.uirendering.cts.testinfrastructure.ActivityTestBase;
 import android.uirendering.cts.testinfrastructure.ViewInitializer;
 import android.view.View;
 import android.uirendering.cts.R;
+import org.junit.Test;
+import org.junit.runner.RunWith;
 
+@MediumTest
+@RunWith(AndroidJUnit4.class)
 public class LayerTests extends ActivityTestBase {
-    @SmallTest
+    @Test
     public void testLayerPaintAlpha() {
         // red channel full strength, other channels 75% strength
         // (since 25% alpha red subtracts from them)
@@ -53,7 +58,7 @@
                 .runWithVerifier(new ColorVerifier(expectedColor));
     }
 
-    @SmallTest
+    @Test
     public void testLayerPaintColorFilter() {
         // Red, fully desaturated. Note that it's not 255/3 in each channel.
         // See ColorMatrix#setSaturation()
@@ -73,7 +78,7 @@
                 .runWithVerifier(new ColorVerifier(expectedColor));
     }
 
-    @SmallTest
+    @Test
     public void testLayerPaintBlend() {
         // Red, drawn underneath opaque white, so output should be white.
         // TODO: consider doing more interesting blending test here
diff --git a/tests/tests/uirendering/src/android/uirendering/cts/testclasses/PathClippingTests.java b/tests/tests/uirendering/src/android/uirendering/cts/testclasses/PathClippingTests.java
index 8c00ecc..ae5f05d 100644
--- a/tests/tests/uirendering/src/android/uirendering/cts/testclasses/PathClippingTests.java
+++ b/tests/tests/uirendering/src/android/uirendering/cts/testclasses/PathClippingTests.java
@@ -34,6 +34,8 @@
 import android.webkit.WebView;
 import android.uirendering.cts.R;
 
+import static org.junit.Assert.assertNotNull;
+
 public class PathClippingTests extends ActivityTestBase {
     // draw circle with hole in it, with stroked circle
     static final CanvasClient sTorusDrawCanvasClient = new CanvasClient() {
diff --git a/tests/tests/uirendering/src/android/uirendering/cts/testclasses/ShadowTests.java b/tests/tests/uirendering/src/android/uirendering/cts/testclasses/ShadowTests.java
index 26c2402..bc76757 100644
--- a/tests/tests/uirendering/src/android/uirendering/cts/testclasses/ShadowTests.java
+++ b/tests/tests/uirendering/src/android/uirendering/cts/testclasses/ShadowTests.java
@@ -23,8 +23,22 @@
 
 import android.test.suitebuilder.annotation.SmallTest;
 import android.uirendering.cts.testinfrastructure.ActivityTestBase;
+import android.uirendering.cts.util.CompareUtils;
 
 public class ShadowTests extends ActivityTestBase {
+
+    private class GrayScaleVerifier extends SamplePointVerifier {
+        public GrayScaleVerifier(Point[] testPoints, int[] expectedColors, int tolerance) {
+            super(testPoints, expectedColors, tolerance) ;
+        }
+
+        @Override
+        protected boolean verifyPixel(int color, int expectedColor) {
+            return super.verifyPixel(color, expectedColor)
+                    && CompareUtils.verifyPixelGrayScale(color, 1);
+        }
+    }
+
     @SmallTest
     public void testShadowLayout() {
         int shadowColorValue = 0xDB;
@@ -32,8 +46,9 @@
         if (getActivity().getOnTv()) {
             shadowColorValue = 0xBB;
         }
-        // Use a higher threshold (36) than default value (20);
-        SamplePointVerifier verifier = new SamplePointVerifier(
+
+        // Use a higher threshold than default value (20), since we also double check gray scale;
+        GrayScaleVerifier verifier = new GrayScaleVerifier(
                 new Point[] {
                         // view area
                         new Point(25, 64),
@@ -48,7 +63,8 @@
                         Color.rgb(shadowColorValue, shadowColorValue, shadowColorValue),
                         Color.rgb(shadowColorValue, shadowColorValue, shadowColorValue),
                 },
-                36);
+                48);
+
         createTest()
                 .addLayout(R.layout.simple_shadow_layout, null, true/* HW only */)
                 .runWithVerifier(verifier);
diff --git a/tests/tests/uirendering/src/android/uirendering/cts/testclasses/SweepTests.java b/tests/tests/uirendering/src/android/uirendering/cts/testclasses/SweepTests.java
index 71b4f3f..f5f59b3 100644
--- a/tests/tests/uirendering/src/android/uirendering/cts/testclasses/SweepTests.java
+++ b/tests/tests/uirendering/src/android/uirendering/cts/testclasses/SweepTests.java
@@ -20,21 +20,16 @@
 import android.graphics.Color;
 import android.graphics.LinearGradient;
 import android.graphics.Paint;
-import android.graphics.Point;
-import android.graphics.PorterDuff;
-import android.graphics.PorterDuffXfermode;
 import android.graphics.Rect;
-import android.graphics.RectF;
 import android.graphics.Shader;
-import android.test.suitebuilder.annotation.SmallTest;
+import android.test.suitebuilder.annotation.MediumTest;
 import android.uirendering.cts.bitmapcomparers.BitmapComparer;
 import android.uirendering.cts.bitmapcomparers.MSSIMComparer;
-import android.uirendering.cts.bitmapverifiers.BitmapVerifier;
-import android.uirendering.cts.bitmapverifiers.SamplePointVerifier;
 import android.uirendering.cts.testinfrastructure.ActivityTestBase;
 import android.uirendering.cts.testinfrastructure.CanvasClient;
 import android.uirendering.cts.testinfrastructure.DisplayModifier;
 import android.uirendering.cts.testinfrastructure.ResourceModifier;
+import org.junit.Test;
 
 import java.util.LinkedHashMap;
 import java.util.Map;
@@ -42,222 +37,8 @@
 /**
  * Test cases of all combination of resource modifications.
  */
+@MediumTest
 public class SweepTests extends ActivityTestBase {
-    private static final String TAG = "SweepTests";
-
-    public static final int BG_COLOR = 0xFFFFFFFF;
-    public static final int DST_COLOR = 0xFFFFCC44;
-    public static final int SRC_COLOR = 0xFF66AAFF;
-    public static final int MULTIPLY_COLOR = 0xFF668844;
-    public static final int SCREEN_COLOR = 0xFFFFEEFF;
-
-    // These points are in pairs, the first being the lower left corner, the second is only in the
-    // Destination bitmap, the third is the intersection of the two bitmaps, and the fourth is in
-    // the Source bitmap.
-    private final static Point[] XFERMODE_TEST_POINTS = new Point[] {
-            new Point(1, 80), new Point(25, 25), new Point(35, 35), new Point(70, 70)
-    };
-
-    /**
-     * There are 4 locations we care about in any filter testing.
-     *
-     * 1) Both empty
-     * 2) Only src, dst empty
-     * 3) Both src + dst
-     * 4) Only dst, src empty
-     */
-    private final Map<PorterDuff.Mode, int[]> XFERMODE_COLOR_MAP = new LinkedHashMap<PorterDuff.Mode, int[]>() {
-        {
-            put(PorterDuff.Mode.SRC, new int[] {
-                    BG_COLOR, BG_COLOR, SRC_COLOR, SRC_COLOR
-            });
-
-            put(PorterDuff.Mode.DST, new int[] {
-                    BG_COLOR, DST_COLOR, DST_COLOR, BG_COLOR
-            });
-
-            put(PorterDuff.Mode.SRC_OVER, new int[] {
-                    BG_COLOR, DST_COLOR, SRC_COLOR, SRC_COLOR
-            });
-
-            put(PorterDuff.Mode.DST_OVER, new int[] {
-                    BG_COLOR, DST_COLOR, DST_COLOR, SRC_COLOR
-            });
-
-            put(PorterDuff.Mode.SRC_IN, new int[] {
-                    BG_COLOR, BG_COLOR, SRC_COLOR, BG_COLOR
-            });
-
-            put(PorterDuff.Mode.DST_IN, new int[] {
-                    BG_COLOR, BG_COLOR, DST_COLOR, BG_COLOR
-            });
-
-            put(PorterDuff.Mode.SRC_OUT, new int[] {
-                    BG_COLOR, BG_COLOR, BG_COLOR, SRC_COLOR
-            });
-
-            put(PorterDuff.Mode.DST_OUT, new int[] {
-                    BG_COLOR, DST_COLOR, BG_COLOR, BG_COLOR
-            });
-
-            put(PorterDuff.Mode.SRC_ATOP, new int[] {
-                    BG_COLOR, DST_COLOR, SRC_COLOR, BG_COLOR
-            });
-
-            put(PorterDuff.Mode.DST_ATOP, new int[] {
-                    BG_COLOR, BG_COLOR, DST_COLOR, SRC_COLOR
-            });
-
-            put(PorterDuff.Mode.XOR, new int[] {
-                    BG_COLOR, DST_COLOR, BG_COLOR, SRC_COLOR
-            });
-
-            put(PorterDuff.Mode.MULTIPLY, new int[] {
-                    BG_COLOR, BG_COLOR, MULTIPLY_COLOR, BG_COLOR
-            });
-
-            put(PorterDuff.Mode.SCREEN, new int[] {
-                    BG_COLOR, DST_COLOR, SCREEN_COLOR, SRC_COLOR
-            });
-        }
-    };
-
-    private final static DisplayModifier XFERMODE_MODIFIER = new DisplayModifier() {
-        private final RectF mSrcRect = new RectF(30, 30, 80, 80);
-        private final RectF mDstRect = new RectF(10, 10, 60, 60);
-        private final Bitmap mSrcBitmap = createSrc();
-        private final Bitmap mDstBitmap = createDst();
-
-        @Override
-        public void modifyDrawing(Paint paint, Canvas canvas) {
-            int sc = canvas.saveLayer(0, 0, TEST_WIDTH, TEST_HEIGHT, null);
-
-            canvas.drawBitmap(mDstBitmap, 0, 0, null);
-            canvas.drawBitmap(mSrcBitmap, 0, 0, paint);
-
-            canvas.restoreToCount(sc);
-        }
-
-        private Bitmap createSrc() {
-            Bitmap srcB = Bitmap.createBitmap(TEST_WIDTH, TEST_HEIGHT, Bitmap.Config.ARGB_8888);
-            Canvas srcCanvas = new Canvas(srcB);
-            Paint srcPaint = new Paint(Paint.ANTI_ALIAS_FLAG);
-            srcPaint.setColor(SRC_COLOR);
-            srcCanvas.drawRect(mSrcRect, srcPaint);
-            return srcB;
-        }
-
-        private Bitmap createDst() {
-            Bitmap dstB = Bitmap.createBitmap(TEST_WIDTH, TEST_HEIGHT, Bitmap.Config.ARGB_8888);
-            Canvas dstCanvas = new Canvas(dstB);
-            Paint dstPaint = new Paint(Paint.ANTI_ALIAS_FLAG);
-            dstPaint.setColor(DST_COLOR);
-            dstCanvas.drawOval(mDstRect, dstPaint);
-            return dstB;
-        }
-    };
-
-    // We care about one point in each of the four rectangles of different alpha values, as well as
-    // the area outside the rectangles
-    private final static Point[] COLOR_FILTER_ALPHA_POINTS = new Point[] {
-            new Point(9, 45),
-            new Point(27, 45),
-            new Point(45, 45),
-            new Point(63, 45),
-            new Point(81, 45)
-    };
-
-    public static final int FILTER_COLOR = 0xFFBB0000;
-    private final Map<PorterDuff.Mode, int[]> COLOR_FILTER_ALPHA_MAP
-            = new LinkedHashMap<PorterDuff.Mode, int[]>() {
-        {
-            put(PorterDuff.Mode.SRC, new int[] {
-                    FILTER_COLOR, FILTER_COLOR, FILTER_COLOR, FILTER_COLOR, FILTER_COLOR
-            });
-
-            put(PorterDuff.Mode.DST, new int[] {
-                    0xFFE6E6E6, 0xFFCCCCCC, 0xFFB3B3B3, 0xFF999999, 0xFFFFFFFF
-            });
-
-            put(PorterDuff.Mode.SRC_OVER, new int[] {
-                    0xFFBB0000, 0xFFBB0000, 0xFFBB0000, 0xFFBB0000, 0xFFBB0000
-            });
-
-            put(PorterDuff.Mode.DST_OVER, new int[] {
-                    0xFFAF1A1A, 0xFFA33333, 0xFF984D4D, 0xFF8B6666, 0xFFBB0000
-            });
-
-            put(PorterDuff.Mode.SRC_IN, new int[] {
-                    0xFFF1CCCC, 0xFFE49999, 0xFFD66666, 0xFFC83333, 0xFFFFFFFF
-            });
-
-            put(PorterDuff.Mode.DST_IN, new int[] {
-                    0xFFE6E6E6, 0xFFCCCCCC, 0xFFB3B3B3, 0xFF999999, 0xFFFFFFFF
-            });
-
-            put(PorterDuff.Mode.SRC_OUT, new int[] {
-                    0xFFC83333, 0xFFD66666, 0xFFE49999, 0xFFF1CCCC, 0xFFBB0000
-            });
-
-            put(PorterDuff.Mode.DST_OUT, new int[] {
-                    0xFFFFFFFF, 0xFFFFFFFF, 0xFFFFFFFF, 0xFFFFFFFF, 0xFFFFFFFF
-            });
-
-            put(PorterDuff.Mode.SRC_ATOP, new int[] {
-                    0xFFF1CCCC, 0xFFE49999, 0xFFD66666, 0xFFC93333, 0xFFFFFFFF
-            });
-
-            put(PorterDuff.Mode.DST_ATOP, new int[] {
-                    0xFFB01A1A, 0xFFA33333, 0xFF984D4D, 0xFF8B6666, 0xFFBB0000
-            });
-
-            put(PorterDuff.Mode.XOR, new int[] {
-                    0xFFC93333, 0xFFD66666, 0xFFE49999, 0xFFF1CCCC, 0xFFBB0000
-            });
-
-            put(PorterDuff.Mode.MULTIPLY, new int[] {
-                    0xFFDFCCCC, 0xFFBE9999, 0xFF9E6666, 0xFF7E3333, 0xFFFFFFFF
-            });
-
-            put(PorterDuff.Mode.SCREEN, new int[] {
-                    0xFFC21A1A, 0xFFC93333, 0xFFD04D4D, 0xFFD66666, 0xFFBB0000
-            });
-        }
-    };
-
-    /**
-     * Draws 5 blocks of different color/opacity to be blended against
-     */
-    private final static DisplayModifier COLOR_FILTER_ALPHA_MODIFIER = new DisplayModifier() {
-        private final int[] BLOCK_COLORS = new int[] {
-                0x33808080,
-                0x66808080,
-                0x99808080,
-                0xCC808080,
-                0x00000000
-        };
-
-        private final Bitmap mBitmap = createQuadRectBitmap();
-
-        public void modifyDrawing(Paint paint, Canvas canvas) {
-            canvas.drawBitmap(mBitmap, 0, 0, paint);
-        }
-
-        private Bitmap createQuadRectBitmap() {
-            Bitmap bitmap = Bitmap.createBitmap(TEST_WIDTH, TEST_HEIGHT, Bitmap.Config.ARGB_8888);
-            Canvas canvas = new Canvas(bitmap);
-            Paint paint = new Paint();
-            paint.setXfermode(new PorterDuffXfermode(PorterDuff.Mode.SRC));
-            final int blockCount = BLOCK_COLORS.length;
-            final int blockWidth = TEST_WIDTH / blockCount;
-            for (int i = 0 ; i < blockCount; i++) {
-                paint.setColor(BLOCK_COLORS[i]);
-                canvas.drawRect(i * blockWidth, 0, (i + 1) * blockWidth, TEST_HEIGHT, paint);
-            }
-            return bitmap;
-        }
-    };
-
     private final static DisplayModifier COLOR_FILTER_GRADIENT_MODIFIER = new DisplayModifier() {
         private final Rect mBounds = new Rect(30, 30, 150, 150);
         private final int[] mColors = new int[] {
@@ -299,54 +80,25 @@
             new MSSIMComparer(HIGH_THRESHOLD)
     };
 
-    @SmallTest
+    @Test
     public void testBasicDraws() {
-        sweepModifiersForMask(DisplayModifier.Accessor.SHAPES_MASK, null, DEFAULT_MSSIM_COMPARER,
-                null);
+        sweepModifiersForMask(DisplayModifier.Accessor.SHAPES_MASK, null, DEFAULT_MSSIM_COMPARER);
     }
 
-    @SmallTest
+    @Test
     public void testBasicShaders() {
         sweepModifiersForMask(DisplayModifier.Accessor.SHADER_MASK, mCircleDrawModifier,
-                DEFAULT_MSSIM_COMPARER, null);
+                DEFAULT_MSSIM_COMPARER);
     }
 
-    @SmallTest
+    @Test
     public void testColorFilterUsingGradient() {
         sweepModifiersForMask(DisplayModifier.Accessor.COLOR_FILTER_MASK,
-                COLOR_FILTER_GRADIENT_MODIFIER, DEFAULT_MSSIM_COMPARER, null);
-    }
-
-    @SmallTest
-    public void testColorFiltersAlphas() {
-        BitmapVerifier[] bitmapVerifiers =
-                new BitmapVerifier[DisplayModifier.PORTERDUFF_MODES.length];
-        int index = 0;
-        for (PorterDuff.Mode mode : DisplayModifier.PORTERDUFF_MODES) {
-            bitmapVerifiers[index] = new SamplePointVerifier(COLOR_FILTER_ALPHA_POINTS,
-                    COLOR_FILTER_ALPHA_MAP.get(mode));
-            index++;
-        }
-        sweepModifiersForMask(DisplayModifier.Accessor.COLOR_FILTER_MASK,
-                COLOR_FILTER_ALPHA_MODIFIER, null, bitmapVerifiers);
-    }
-
-    @SmallTest
-    public void testXfermodes() {
-        BitmapVerifier[] bitmapVerifiers =
-                new BitmapVerifier[DisplayModifier.PORTERDUFF_MODES.length];
-        int index = 0;
-        for (PorterDuff.Mode mode : DisplayModifier.PORTERDUFF_MODES) {
-            bitmapVerifiers[index] = new SamplePointVerifier(XFERMODE_TEST_POINTS,
-                    XFERMODE_COLOR_MAP.get(mode));
-            index++;
-        }
-        sweepModifiersForMask(DisplayModifier.Accessor.XFERMODE_MASK, XFERMODE_MODIFIER,
-                null, bitmapVerifiers);
+                COLOR_FILTER_GRADIENT_MODIFIER, DEFAULT_MSSIM_COMPARER);
     }
 
     protected void sweepModifiersForMask(int mask, final DisplayModifier drawOp,
-            BitmapComparer[] bitmapComparers, BitmapVerifier[] bitmapVerifiers) {
+                BitmapComparer[] bitmapComparers) {
         if ((mask & DisplayModifier.Accessor.ALL_OPTIONS_MASK) == 0) {
             throw new IllegalArgumentException("Attempt to test with a mask that is invalid");
         }
@@ -371,13 +123,8 @@
         // Create the test cases with each combination
         do {
             canvasClient.setDebugString(modifierAccessor.getDebugString());
-            if (bitmapComparers != null) {
-                int arrIndex = Math.min(index, bitmapComparers.length - 1);
-                createTest().addCanvasClient(canvasClient).runWithComparer(bitmapComparers[arrIndex]);
-            } else {
-                int arrIndex = Math.min(index, bitmapVerifiers.length - 1);
-                createTest().addCanvasClient(canvasClient).runWithVerifier(bitmapVerifiers[arrIndex]);
-            }
+            int arrIndex = Math.min(index, bitmapComparers.length - 1);
+            createTest().addCanvasClient(canvasClient).runWithComparer(bitmapComparers[arrIndex]);
             index++;
         } while (modifierAccessor.step());
     }
diff --git a/tests/tests/uirendering/src/android/uirendering/cts/testclasses/XfermodeTest.java b/tests/tests/uirendering/src/android/uirendering/cts/testclasses/XfermodeTest.java
new file mode 100644
index 0000000..857d3ab
--- /dev/null
+++ b/tests/tests/uirendering/src/android/uirendering/cts/testclasses/XfermodeTest.java
@@ -0,0 +1,182 @@
+/*
+ * Copyright (C) 2016 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package android.uirendering.cts.testclasses;
+
+import android.graphics.Bitmap;
+import android.graphics.Canvas;
+import android.graphics.Paint;
+import android.graphics.Point;
+import android.graphics.PorterDuff;
+import android.graphics.PorterDuffXfermode;
+import android.graphics.RectF;
+import android.test.suitebuilder.annotation.MediumTest;
+import android.uirendering.cts.bitmapverifiers.SamplePointVerifier;
+import android.uirendering.cts.testinfrastructure.ActivityTestBase;
+import android.uirendering.cts.testinfrastructure.CanvasClient;
+import org.junit.Test;
+import org.junit.runner.RunWith;
+import org.junit.runners.Parameterized;
+
+import java.util.ArrayList;
+import java.util.List;
+
+@RunWith(Parameterized.class)
+public class XfermodeTest extends ActivityTestBase {
+    /**
+     * There are 4 locations we care about in testing each filter:
+     *
+     * 1) Both empty
+     * 2) Only src, dst empty
+     * 3) Both src + dst
+     * 4) Only dst, src empty
+     */
+    private final static Point[] TEST_POINTS = new Point[] {
+            new Point(1, 80),
+            new Point(25, 25),
+            new Point(35, 35),
+            new Point(70, 70)
+    };
+
+    public static class Config {
+        final boolean hardwareAccelerated;
+        final PorterDuff.Mode mode;
+        final int[] expectedColors;
+
+        Config(boolean hardwareAccelerated, Object[] modeAndExpectedColors) {
+            this.hardwareAccelerated = hardwareAccelerated;
+            mode = (PorterDuff.Mode) modeAndExpectedColors[0];
+            expectedColors = (int[]) modeAndExpectedColors[1];
+        }
+
+        @Override
+        public String toString() {
+            return mode.name() + ", hardwareAccelerated=" + hardwareAccelerated;
+        }
+    };
+
+    public static List<XfermodeTest.Config> configs(Object[][] modesAndExpectedColors) {
+        List<XfermodeTest.Config> configs = new ArrayList<>();
+        for (boolean hardwareAccelerated : new boolean[] {false, true}) {
+            for (Object[] modeAndExpectedColors : modesAndExpectedColors) {
+                configs.add(new XfermodeTest.Config(hardwareAccelerated, modeAndExpectedColors));
+            }
+        }
+        return configs;
+    }
+
+    private static final int BG_COLOR = 0xFFFFFFFF;
+    private static final int DST_COLOR = 0xFFFFCC44;
+    private static final int SRC_COLOR = 0xFF66AAFF;
+    private static final int MULTIPLY_COLOR = 0xFF668844;
+    private static final int SCREEN_COLOR = 0xFFFFEEFF;
+
+    private static Object[][] MODES_AND_EXPECTED_COLORS = new Object[][] {
+        { PorterDuff.Mode.SRC, new int[] {
+                BG_COLOR, BG_COLOR, SRC_COLOR, SRC_COLOR } },
+
+        { PorterDuff.Mode.DST, new int[] {
+                BG_COLOR, DST_COLOR, DST_COLOR, BG_COLOR } },
+
+        { PorterDuff.Mode.SRC_OVER, new int[] {
+                BG_COLOR, DST_COLOR, SRC_COLOR, SRC_COLOR } },
+
+        { PorterDuff.Mode.DST_OVER, new int[] {
+                BG_COLOR, DST_COLOR, DST_COLOR, SRC_COLOR } },
+
+        { PorterDuff.Mode.SRC_IN, new int[] {
+                BG_COLOR, BG_COLOR, SRC_COLOR, BG_COLOR } },
+
+        { PorterDuff.Mode.DST_IN, new int[] {
+                BG_COLOR, BG_COLOR, DST_COLOR, BG_COLOR } },
+
+        { PorterDuff.Mode.SRC_OUT, new int[] {
+                BG_COLOR, BG_COLOR, BG_COLOR, SRC_COLOR } },
+
+        { PorterDuff.Mode.DST_OUT, new int[] {
+                BG_COLOR, DST_COLOR, BG_COLOR, BG_COLOR } },
+
+        { PorterDuff.Mode.SRC_ATOP, new int[] {
+                BG_COLOR, DST_COLOR, SRC_COLOR, BG_COLOR } },
+
+        { PorterDuff.Mode.DST_ATOP, new int[] {
+                BG_COLOR, BG_COLOR, DST_COLOR, SRC_COLOR } },
+
+        { PorterDuff.Mode.XOR, new int[] {
+                BG_COLOR, DST_COLOR, BG_COLOR, SRC_COLOR } },
+
+        { PorterDuff.Mode.MULTIPLY, new int[] {
+                BG_COLOR, BG_COLOR, MULTIPLY_COLOR, BG_COLOR } },
+
+        { PorterDuff.Mode.SCREEN, new int[] {
+                BG_COLOR, DST_COLOR, SCREEN_COLOR, SRC_COLOR } },
+    };
+
+    @Parameterized.Parameters(name = "{0}")
+    public static List<Config> configs() {
+        return configs(MODES_AND_EXPECTED_COLORS);
+    }
+
+    private final Config mConfig;
+
+    public XfermodeTest(Config config) {
+        mConfig = config;
+    }
+
+    private CanvasClient mCanvasClient = new CanvasClient() {
+        final Paint mPaint = new Paint();
+        private final RectF mSrcRect = new RectF(30, 30, 80, 80);
+        private final RectF mDstRect = new RectF(10, 10, 60, 60);
+        private final Bitmap mSrcBitmap = createSrc();
+        private final Bitmap mDstBitmap = createDst();
+
+        @Override
+        public void draw(Canvas canvas, int width, int height) {
+            int sc = canvas.saveLayer(0, 0, TEST_WIDTH, TEST_HEIGHT, null);
+
+            canvas.drawBitmap(mDstBitmap, 0, 0, null);
+            mPaint.setXfermode(new PorterDuffXfermode(mConfig.mode));
+            canvas.drawBitmap(mSrcBitmap, 0, 0, mPaint);
+
+            canvas.restoreToCount(sc);
+        }
+
+        private Bitmap createSrc() {
+            Bitmap srcB = Bitmap.createBitmap(TEST_WIDTH, TEST_HEIGHT, Bitmap.Config.ARGB_8888);
+            Canvas srcCanvas = new Canvas(srcB);
+            Paint srcPaint = new Paint(Paint.ANTI_ALIAS_FLAG);
+            srcPaint.setColor(SRC_COLOR);
+            srcCanvas.drawRect(mSrcRect, srcPaint);
+            return srcB;
+        }
+
+        private Bitmap createDst() {
+            Bitmap dstB = Bitmap.createBitmap(TEST_WIDTH, TEST_HEIGHT, Bitmap.Config.ARGB_8888);
+            Canvas dstCanvas = new Canvas(dstB);
+            Paint dstPaint = new Paint(Paint.ANTI_ALIAS_FLAG);
+            dstPaint.setColor(DST_COLOR);
+            dstCanvas.drawOval(mDstRect, dstPaint);
+            return dstB;
+        }
+    };
+
+    @Test
+    @MediumTest
+    public void test() {
+        createTest()
+                .addCanvasClient(mCanvasClient, mConfig.hardwareAccelerated)
+                .runWithVerifier(new SamplePointVerifier(TEST_POINTS, mConfig.expectedColors));
+    }
+}
diff --git a/tests/tests/uirendering/src/android/uirendering/cts/testinfrastructure/ActivityTestBase.java b/tests/tests/uirendering/src/android/uirendering/cts/testinfrastructure/ActivityTestBase.java
index 69cb688..f82bb40 100644
--- a/tests/tests/uirendering/src/android/uirendering/cts/testinfrastructure/ActivityTestBase.java
+++ b/tests/tests/uirendering/src/android/uirendering/cts/testinfrastructure/ActivityTestBase.java
@@ -16,11 +16,13 @@
 package android.uirendering.cts.testinfrastructure;
 
 import android.annotation.Nullable;
+import android.app.Activity;
+import android.app.Instrumentation;
 import android.graphics.Bitmap;
 import android.graphics.Point;
 import android.renderscript.Allocation;
 import android.renderscript.RenderScript;
-import android.test.ActivityInstrumentationTestCase2;
+import android.support.test.rule.ActivityTestRule;
 import android.uirendering.cts.bitmapcomparers.BitmapComparer;
 import android.uirendering.cts.bitmapverifiers.BitmapVerifier;
 import android.uirendering.cts.differencevisualizers.DifferenceVisualizer;
@@ -29,18 +31,23 @@
 import android.util.Log;
 
 import android.support.test.InstrumentationRegistry;
+import org.junit.After;
+import org.junit.Before;
+import org.junit.Rule;
+import org.junit.rules.TestName;
 
 import java.util.ArrayList;
 import java.util.Arrays;
 import java.util.List;
 
+import static org.junit.Assert.assertTrue;
+
 /**
  * This class contains the basis for the graphics hardware test classes. Contained within this class
  * are several methods that help with the execution of tests, and should be extended to gain the
  * functionality built in.
  */
-public abstract class ActivityTestBase extends
-        ActivityInstrumentationTestCase2<DrawActivity> {
+public abstract class ActivityTestBase {
     public static final String TAG = "ActivityTestBase";
     public static final boolean DEBUG = false;
     public static final boolean USE_RS = false;
@@ -57,12 +64,18 @@
     private RenderScript mRenderScript;
     private TestCaseBuilder mTestCaseBuilder;
 
+    @Rule
+    public ActivityTestRule<DrawActivity> mActivityRule = new ActivityTestRule<>(
+            DrawActivity.class);
+
+    @Rule
+    public TestName name = new TestName();
+
     /**
      * The default constructor creates the package name and sets the DrawActivity as the class that
      * we would use.
      */
     public ActivityTestBase() {
-        super(DrawActivity.class);
         mDifferenceVisualizer = new PassFailVisualizer();
 
         // Create a location for the files to be held, if it doesn't exist already
@@ -74,26 +87,27 @@
         }
     }
 
-    /**
-     * This method is called before each test case and should be called from the test class that
-     * extends this class.
-     */
-    @Override
+    protected DrawActivity getActivity() {
+        return mActivityRule.getActivity();
+    }
+
+    protected String getName() {
+        return name.getMethodName();
+    }
+
+    protected Instrumentation getInstrumentation() {
+        return InstrumentationRegistry.getInstrumentation();
+    }
+
+    @Before
     public void setUp() {
-        // As the way to access Instrumentation is changed in the new runner, we need to inject it
-        // manually into ActivityInstrumentationTestCase2. ActivityInstrumentationTestCase2 will
-        // be marked as deprecated and replaced with ActivityTestRule.
-        injectInstrumentation(InstrumentationRegistry.getInstrumentation());
         mDifferenceVisualizer = new PassFailVisualizer();
         if (USE_RS) {
             mRenderScript = RenderScript.create(getActivity().getApplicationContext());
         }
     }
 
-    /**
-     * This method will kill the activity so that it can be reset depending on the test.
-     */
-    @Override
+    @After
     public void tearDown() {
         if (mTestCaseBuilder != null) {
             List<TestCase> testCases = mTestCaseBuilder.getTestCases();
@@ -102,7 +116,6 @@
                 throw new IllegalStateException("Must have at least one test case");
             }
 
-
             for (TestCase testCase : testCases) {
                 if (!testCase.wasTestRan) {
                     Log.w(TAG, getName() + " not all of the tests ran");
@@ -111,16 +124,6 @@
             }
             mTestCaseBuilder = null;
         }
-
-        Runnable finishRunnable = new Runnable() {
-
-            @Override
-            public void run() {
-                getActivity().finish();
-            }
-        };
-
-        getActivity().runOnUiThread(finishRunnable);
     }
 
     public Bitmap takeScreenshot(Point testOffset) {
diff --git a/tests/tests/uirendering/src/android/uirendering/cts/util/CompareUtils.java b/tests/tests/uirendering/src/android/uirendering/cts/util/CompareUtils.java
index 4f246a4..c80a778 100644
--- a/tests/tests/uirendering/src/android/uirendering/cts/util/CompareUtils.java
+++ b/tests/tests/uirendering/src/android/uirendering/cts/util/CompareUtils.java
@@ -12,4 +12,17 @@
                 + Math.abs(Color.blue(color) - Color.blue(expectedColor));
         return diff <= threshold;
     }
+
+    /**
+     * @param threshold Per channel differences for R / G / B channel against the average of these 3
+     *                  channels. Should be less than 2 normally.
+     * @return True if the color is close enough to be a gray scale color.
+     */
+    public static boolean verifyPixelGrayScale(int color, int threshold) {
+        int average =  Color.red(color) + Color.green(color) + Color.blue(color);
+        average /= 3;
+        return Math.abs(Color.red(color) - average) <= threshold
+                && Math.abs(Color.green(color) - average) <= threshold
+                && Math.abs(Color.blue(color) - average) <= threshold;
+    }
 }
diff --git a/tests/tests/widget/res/layout/popupwindow.xml b/tests/tests/widget/res/layout/popupwindow.xml
index 7746da8..0c7b5e8 100644
--- a/tests/tests/widget/res/layout/popupwindow.xml
+++ b/tests/tests/widget/res/layout/popupwindow.xml
@@ -20,6 +20,14 @@
     android:layout_width="match_parent"
     android:layout_height="match_parent">
 
+    <android.widget.cts.MockViewForListPopupWindow
+        android:id="@+id/anchor_upper_left"
+        android:layout_width="10dp"
+        android:layout_height="10dp"
+        android:layout_alignParentTop="true"
+        android:layout_alignParentLeft="true"
+        android:background="#f0f" />
+
     <View android:id="@+id/anchor_upper"
         android:layout_width="10dp"
         android:layout_height="10dp"
diff --git a/tests/tests/widget/res/menu/popup_menu.xml b/tests/tests/widget/res/menu/popup_menu.xml
new file mode 100644
index 0000000..f50efc5
--- /dev/null
+++ b/tests/tests/widget/res/menu/popup_menu.xml
@@ -0,0 +1,36 @@
+<?xml version="1.0" encoding="utf-8"?>
+<!-- Copyright (C) 2016 Google Inc.
+
+     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.
+-->
+<menu xmlns:android="http://schemas.android.com/apk/res/android">
+    <item android:id="@+id/action_highlight"
+          android:title="@string/popup_menu_highlight" />
+    <item android:id="@+id/action_edit"
+          android:title="@string/popup_menu_edit" />
+    <item android:id="@+id/action_delete"
+          android:title="@string/popup_menu_delete" />
+    <item android:id="@+id/action_ignore"
+          android:title="@string/popup_menu_ignore" />
+    <item android:id="@+id/action_share"
+          android:title="@string/popup_menu_share">
+        <menu>
+            <item android:id="@+id/action_share_email"
+                  android:title="@string/popup_menu_share_email" />
+            <item android:id="@+id/action_share_circles"
+                  android:title="@string/popup_menu_share_circles" />
+        </menu>
+    </item>
+    <item android:id="@+id/action_print"
+          android:title="@string/popup_menu_print" />
+</menu>
diff --git a/tests/tests/widget/res/values/strings.xml b/tests/tests/widget/res/values/strings.xml
index 51d8708..d889772 100644
--- a/tests/tests/widget/res/values/strings.xml
+++ b/tests/tests/widget/res/values/strings.xml
@@ -177,4 +177,14 @@
 text, I would love to see the kind of devices you guys now use! Guys, maybe some devices need longer string!
 I think so, so how about double this string, like copy and paste! </string>
     <string name="rectangle200">"M 0,0 l 200,0 l 0, 200 l -200, 0 z"</string>
+
+    <string name="popup_show">Show popup</string>
+    <string name="popup_menu_highlight">Highlight</string>
+    <string name="popup_menu_edit">Edit</string>
+    <string name="popup_menu_delete">Delete</string>
+    <string name="popup_menu_ignore">Ignore</string>
+    <string name="popup_menu_share">Share</string>
+    <string name="popup_menu_share_email">Via email</string>
+    <string name="popup_menu_share_circles">To my circles</string>
+    <string name="popup_menu_print">Print</string>
 </resources>
diff --git a/tests/tests/widget/res/values/styles.xml b/tests/tests/widget/res/values/styles.xml
index 81925cc..14d575b 100644
--- a/tests/tests/widget/res/values/styles.xml
+++ b/tests/tests/widget/res/values/styles.xml
@@ -169,4 +169,5 @@
         <item name="android:windowSwipeToDismiss">false</item>
     </style>
 
+    <style name="PopupEmptyStyle" />
 </resources>
diff --git a/tests/tests/widget/src/android/widget/cts/FrameLayoutTest.java b/tests/tests/widget/src/android/widget/cts/FrameLayoutTest.java
index 1fc0cef..bdda79a 100644
--- a/tests/tests/widget/src/android/widget/cts/FrameLayoutTest.java
+++ b/tests/tests/widget/src/android/widget/cts/FrameLayoutTest.java
@@ -16,22 +16,19 @@
 
 package android.widget.cts;
 
-import android.content.res.ColorStateList;
-import android.cts.util.WidgetTestUtils;
-import android.graphics.Canvas;
-import android.graphics.Color;
-import android.graphics.ColorFilter;
-import android.graphics.PorterDuff;
-
-import android.widget.cts.R;
-
 import org.xmlpull.v1.XmlPullParser;
 import org.xmlpull.v1.XmlPullParserException;
 
 import android.app.Activity;
 import android.app.Instrumentation;
 import android.content.Context;
+import android.content.res.ColorStateList;
 import android.cts.util.PollingCheck;
+import android.cts.util.WidgetTestUtils;
+import android.graphics.Canvas;
+import android.graphics.Color;
+import android.graphics.ColorFilter;
+import android.graphics.PorterDuff;
 import android.graphics.Rect;
 import android.graphics.Region;
 import android.graphics.drawable.BitmapDrawable;
@@ -47,6 +44,8 @@
 import android.widget.FrameLayout.LayoutParams;
 import android.widget.LinearLayout;
 import android.widget.TextView;
+import android.widget.cts.R;
+import android.widget.cts.util.ViewTestUtils;
 
 import java.io.IOException;
 
@@ -88,12 +87,8 @@
         assertTrue(mFrameLayout.getWidth() > foreground.getIntrinsicWidth());
         assertNull(mFrameLayout.getForeground());
 
-        mActivity.runOnUiThread(new Runnable() {
-            public void run() {
-                mFrameLayout.setForeground(foreground);
-            }
-        });
-        mInstrumentation.waitForIdleSync();
+        ViewTestUtils.runOnMainAndDrawSync(mInstrumentation, mFrameLayout,
+                () -> mFrameLayout.setForeground(foreground));
         assertSame(foreground, mFrameLayout.getForeground());
         // check the default gravity FILL, it completely fills its container
         assertTrue(foreground.isVisible());
@@ -108,18 +103,16 @@
         assertEquals(mFrameLayout.getWidth(), rect.right - rect.left);
 
         // should get a new foreground again, because former foreground has been stretched
-        final BitmapDrawable newForeground
-                = (BitmapDrawable) mActivity.getResources().getDrawable(R.drawable.size_48x48);
+        final BitmapDrawable newForeground =
+                (BitmapDrawable) mActivity.getResources().getDrawable(R.drawable.size_48x48);
         compareScaledPixels(48, newForeground.getIntrinsicHeight());
         compareScaledPixels(48, newForeground.getIntrinsicWidth());
         assertTrue(mFrameLayout.getHeight() > newForeground.getIntrinsicHeight());
         assertTrue(mFrameLayout.getWidth() > foreground.getIntrinsicWidth());
 
-        mActivity.runOnUiThread(new Runnable() {
-            public void run() {
-                mFrameLayout.setForeground(newForeground);
-                mFrameLayout.setForegroundGravity(Gravity.CENTER);
-            }
+        ViewTestUtils.runOnMainAndDrawSync(mInstrumentation, mFrameLayout, () -> {
+            mFrameLayout.setForeground(newForeground);
+            mFrameLayout.setForegroundGravity(Gravity.CENTER);
         });
         mInstrumentation.waitForIdleSync();
         assertSame(newForeground, mFrameLayout.getForeground());
@@ -132,24 +125,19 @@
     }
 
     public void testGatherTransparentRegion() {
-        final LinearLayout container
-                = (LinearLayout) mActivity.findViewById(R.id.framelayout_container);
+        final LinearLayout container =
+                (LinearLayout) mActivity.findViewById(R.id.framelayout_container);
         final Drawable foreground = mActivity.getResources().getDrawable(R.drawable.size_48x48);
-        mActivity.runOnUiThread(new Runnable() {
-            public void run() {
-                mFrameLayout.setForeground(foreground);
-                mFrameLayout.setForegroundGravity(Gravity.CENTER);
-            }
+        ViewTestUtils.runOnMainAndDrawSync(mInstrumentation, mFrameLayout, () -> {
+            mFrameLayout.setForeground(foreground);
+            mFrameLayout.setForegroundGravity(Gravity.CENTER);
         });
         mInstrumentation.waitForIdleSync();
         Region region = new Region(foreground.getBounds());
         assertTrue(mFrameLayout.gatherTransparentRegion(region));
 
-        mActivity.runOnUiThread(new Runnable() {
-            public void run() {
-                container.requestTransparentRegion(mFrameLayout);
-            }
-        });
+        ViewTestUtils.runOnMainAndDrawSync(mInstrumentation, mFrameLayout,
+                () -> container.requestTransparentRegion(mFrameLayout));
         mInstrumentation.waitForIdleSync();
         region = new Region(foreground.getBounds());
         assertTrue(mFrameLayout.gatherTransparentRegion(region));
@@ -168,11 +156,9 @@
         assertEquals(textView.getMeasuredWidth(), frameLayout.getMeasuredWidth());
 
         // measureAll is false and text view is GONE, text view will NOT be measured
-        mActivity.runOnUiThread(new Runnable() {
-            public void run() {
-                textView.setVisibility(View.GONE);
-                frameLayout.requestLayout();
-            }
+        mActivity.runOnUiThread(() -> {
+            textView.setVisibility(View.GONE);
+            frameLayout.requestLayout();
         });
         mInstrumentation.waitForIdleSync();
         assertFalse(frameLayout.getConsiderGoneChildrenWhenMeasuring());
@@ -183,11 +169,9 @@
         assertEquals(button.getMeasuredWidth(), frameLayout.getMeasuredWidth());
 
         // measureAll is true and text view is GONE, text view will be measured
-        mActivity.runOnUiThread(new Runnable() {
-            public void run() {
-                frameLayout.setMeasureAllChildren(true);
-                frameLayout.requestLayout();
-            }
+        mActivity.runOnUiThread(() -> {
+            frameLayout.setMeasureAllChildren(true);
+            frameLayout.requestLayout();
         });
         mInstrumentation.waitForIdleSync();
         assertTrue(frameLayout.getConsiderGoneChildrenWhenMeasuring());
diff --git a/tests/tests/widget/src/android/widget/cts/ListPopupWindowTest.java b/tests/tests/widget/src/android/widget/cts/ListPopupWindowTest.java
index da5b9fe..1bdde5a 100644
--- a/tests/tests/widget/src/android/widget/cts/ListPopupWindowTest.java
+++ b/tests/tests/widget/src/android/widget/cts/ListPopupWindowTest.java
@@ -28,6 +28,7 @@
 import android.test.suitebuilder.annotation.SmallTest;
 import android.view.Display;
 import android.view.Gravity;
+import android.view.KeyEvent;
 import android.view.LayoutInflater;
 import android.view.MotionEvent;
 import android.view.View;
@@ -569,6 +570,44 @@
         verifyNoMoreInteractions(mPopupWindowBuilder.mOnItemSelectedListener);
     }
 
+    public void testNoDefaultDismissalWithBackButton() throws Throwable {
+        mPopupWindowBuilder = new Builder().withDismissListener();
+        mPopupWindowBuilder.show();
+
+        // Send BACK key event. As we don't have any custom code that dismisses ListPopupWindow,
+        // and ListPopupWindow doesn't track that system-level key event on its own, ListPopupWindow
+        // should stay visible
+        mInstrumentation.sendKeyDownUpSync(KeyEvent.KEYCODE_BACK);
+        verify(mPopupWindowBuilder.mOnDismissListener, never()).onDismiss();
+        assertTrue(mPopupWindow.isShowing());
+    }
+
+    public void testCustomDismissalWithBackButton() throws Throwable {
+        mPopupWindowBuilder = new Builder().withAnchor(R.id.anchor_upper_left)
+                .withDismissListener();
+        mPopupWindowBuilder.show();
+
+        // "Point" our custom extension of EditText to our ListPopupWindow
+        final MockViewForListPopupWindow anchor =
+                (MockViewForListPopupWindow) mPopupWindow.getAnchorView();
+        anchor.wireTo(mPopupWindow);
+        // Request focus on our EditText
+        runTestOnUiThread(new Runnable() {
+            @Override
+            public void run() {
+                anchor.requestFocus();
+            }
+        });
+        mInstrumentation.waitForIdleSync();
+
+        // Send BACK key event. As our custom extension of EditText calls
+        // ListPopupWindow.onKeyPreIme, the end result should be the dismissal of the
+        // ListPopupWindow
+        mInstrumentation.sendKeyDownUpSync(KeyEvent.KEYCODE_BACK);
+        verify(mPopupWindowBuilder.mOnDismissListener, times(1)).onDismiss();
+        assertFalse(mPopupWindow.isShowing());
+    }
+
     /**
      * Inner helper class to configure an instance of <code>ListPopupWindow</code> for the
      * specific test. The main reason for its existence is that once a popup window is shown
@@ -585,6 +624,7 @@
         private int mHorizontalOffset;
         private int mVerticalOffset;
         private int mDropDownGravity;
+        private int mAnchorId = R.id.anchor_upper;
 
         private boolean mHasWindowLayoutType;
         private int mWindowLayoutType;
@@ -600,6 +640,11 @@
             mPopupWindow = new ListPopupWindow(mActivity);
         }
 
+        public Builder withAnchor(int anchorId) {
+            mAnchorId = anchorId;
+            return this;
+        }
+
         public Builder ignoreContentWidth() {
             mIgnoreContentWidth = true;
             return this;
@@ -727,7 +772,7 @@
             };
 
             mPopupWindow.setAdapter(listPopupAdapter);
-            mPopupWindow.setAnchorView(mActivity.findViewById(R.id.anchor_upper));
+            mPopupWindow.setAnchorView(mActivity.findViewById(mAnchorId));
 
             // The following mock listeners have to be set before the call to show() as
             // they are set on the internally constructed drop down.
diff --git a/tests/tests/widget/src/android/widget/cts/MockViewForListPopupWindow.java b/tests/tests/widget/src/android/widget/cts/MockViewForListPopupWindow.java
new file mode 100644
index 0000000..8e280fe
--- /dev/null
+++ b/tests/tests/widget/src/android/widget/cts/MockViewForListPopupWindow.java
@@ -0,0 +1,48 @@
+/*
+ * Copyright (C) 2016 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package android.widget.cts;
+
+import android.content.Context;
+import android.util.AttributeSet;
+import android.view.KeyEvent;
+import android.widget.EditText;
+import android.widget.ListPopupWindow;
+
+public class MockViewForListPopupWindow extends EditText {
+    private ListPopupWindow mListPopupWindow;
+
+    public MockViewForListPopupWindow(Context context, AttributeSet attrs) {
+        super(context, attrs);
+    }
+
+    public MockViewForListPopupWindow(Context context) {
+        super(context);
+    }
+
+    public void wireTo(ListPopupWindow listPopupWindow) {
+        mListPopupWindow = listPopupWindow;
+    }
+
+    @Override
+    public boolean onKeyPreIme(int keyCode, KeyEvent event) {
+        if (mListPopupWindow != null) {
+            return mListPopupWindow.onKeyPreIme(keyCode, event);
+        }
+        return super.onKeyPreIme(keyCode, event);
+    }
+}
+
diff --git a/tests/tests/widget/src/android/widget/cts/PopupMenuTest.java b/tests/tests/widget/src/android/widget/cts/PopupMenuTest.java
index 206b794..8df2930 100644
--- a/tests/tests/widget/src/android/widget/cts/PopupMenuTest.java
+++ b/tests/tests/widget/src/android/widget/cts/PopupMenuTest.java
@@ -16,21 +16,32 @@
 
 package android.widget.cts;
 
-import static org.mockito.Mockito.*;
-
 import android.app.Activity;
 import android.app.Instrumentation;
+import android.os.SystemClock;
+import android.support.test.InstrumentationRegistry;
 import android.test.ActivityInstrumentationTestCase2;
+import android.test.suitebuilder.annotation.SmallTest;
 import android.view.Gravity;
+import android.view.Menu;
+import android.view.MenuInflater;
+import android.view.MenuItem;
+import android.view.MotionEvent;
+import android.view.SubMenu;
+import android.view.View;
 import android.widget.PopupMenu;
 
-import android.widget.cts.R;
+import static org.mockito.Mockito.*;
 
+@SmallTest
 public class PopupMenuTest extends
         ActivityInstrumentationTestCase2<MockPopupWindowCtsActivity> {
     private Instrumentation mInstrumentation;
     private Activity mActivity;
 
+    private Builder mBuilder;
+    private PopupMenu mPopupMenu;
+
     public PopupMenuTest() {
         super("android.widget.cts", MockPopupWindowCtsActivity.class);
     }
@@ -42,43 +53,255 @@
         mActivity = getActivity();
     }
 
-    public void testAccessGravity() {
-        PopupMenu popupMenu = new PopupMenu(mActivity,
-                mActivity.findViewById(R.id.anchor_middle_left));
-        assertEquals(Gravity.NO_GRAVITY, popupMenu.getGravity());
-
-        popupMenu.setGravity(Gravity.TOP);
-        assertEquals(Gravity.TOP, popupMenu.getGravity());
+    @Override
+    protected void tearDown() throws Exception {
+        if (mPopupMenu != null) {
+            try {
+                runTestOnUiThread(new Runnable() {
+                    @Override
+                    public void run() {
+                        mPopupMenu.dismiss();
+                    }
+                });
+            } catch (Throwable t) {
+                throw new RuntimeException(t);
+            }
+        }
+        super.tearDown();
     }
 
-    public void testOnDismissListener() {
-        final PopupMenu popupMenu = new PopupMenu(mActivity,
-                mActivity.findViewById(R.id.anchor_middle_left));
-        PopupMenu.OnDismissListener listener = mock(PopupMenu.OnDismissListener.class);
-        popupMenu.setOnDismissListener(listener);
+    private void verifyMenuContent() {
+        final Menu menu = mPopupMenu.getMenu();
+        assertEquals(6, menu.size());
+        assertEquals(R.id.action_highlight, menu.getItem(0).getItemId());
+        assertEquals(R.id.action_edit, menu.getItem(1).getItemId());
+        assertEquals(R.id.action_delete, menu.getItem(2).getItemId());
+        assertEquals(R.id.action_ignore, menu.getItem(3).getItemId());
+        assertEquals(R.id.action_share, menu.getItem(4).getItemId());
+        assertEquals(R.id.action_print, menu.getItem(5).getItemId());
 
-        mInstrumentation.runOnMainSync(new Runnable() {
-            public void run() {
-                popupMenu.show();
-            }
-        });
-        mInstrumentation.waitForIdleSync();
-        verify(listener, never()).onDismiss(popupMenu);
-
-        mInstrumentation.runOnMainSync(new Runnable() {
-            public void run() {
-                popupMenu.dismiss();
-            }
-        });
-        mInstrumentation.waitForIdleSync();
-        verify(listener, times(1)).onDismiss(popupMenu);
-
-        mInstrumentation.runOnMainSync(new Runnable() {
-            public void run() {
-                popupMenu.dismiss();
-            }
-        });
-        mInstrumentation.waitForIdleSync();
-        verify(listener, times(1)).onDismiss(popupMenu);
+        final SubMenu shareSubMenu = menu.getItem(4).getSubMenu();
+        assertNotNull(shareSubMenu);
+        assertEquals(2, shareSubMenu.size());
+        assertEquals(R.id.action_share_email, shareSubMenu.getItem(0).getItemId());
+        assertEquals(R.id.action_share_circles, shareSubMenu.getItem(1).getItemId());
     }
-}
+
+    public void testPopulateViaInflater() throws Throwable {
+        mBuilder = new Builder().inflateWithInflater(true);
+        runTestOnUiThread(new Runnable() {
+            public void run() {
+                mBuilder.show();
+            }
+        });
+        mInstrumentation.waitForIdleSync();
+
+        verifyMenuContent();
+    }
+
+    public void testDirectPopulate() throws Throwable {
+        mBuilder = new Builder().inflateWithInflater(false);
+        runTestOnUiThread(new Runnable() {
+            public void run() {
+                mBuilder.show();
+            }
+        });
+        mInstrumentation.waitForIdleSync();
+
+        verifyMenuContent();
+    }
+
+    public void testAccessGravity() throws Throwable {
+        mBuilder = new Builder();
+        runTestOnUiThread(new Runnable() {
+            public void run() {
+                mBuilder.show();
+            }
+        });
+
+        assertEquals(Gravity.NO_GRAVITY, mPopupMenu.getGravity());
+        mPopupMenu.setGravity(Gravity.TOP);
+        assertEquals(Gravity.TOP, mPopupMenu.getGravity());
+    }
+
+    public void testDismissalViaAPI() throws Throwable {
+        mBuilder = new Builder().withDismissListener();
+        runTestOnUiThread(new Runnable() {
+            public void run() {
+                mBuilder.show();
+            }
+        });
+
+        mInstrumentation.waitForIdleSync();
+        verify(mBuilder.mOnDismissListener, never()).onDismiss(mPopupMenu);
+
+        runTestOnUiThread(new Runnable() {
+            public void run() {
+                mPopupMenu.dismiss();
+            }
+        });
+        mInstrumentation.waitForIdleSync();
+        verify(mBuilder.mOnDismissListener, times(1)).onDismiss(mPopupMenu);
+
+        runTestOnUiThread(new Runnable() {
+            public void run() {
+                mPopupMenu.dismiss();
+            }
+        });
+        mInstrumentation.waitForIdleSync();
+        // Shouldn't have any more interactions with our dismiss listener since the menu was
+        // already dismissed when we called dismiss()
+        verifyNoMoreInteractions(mBuilder.mOnDismissListener);
+    }
+
+    public void testDismissalViaTouch() throws Throwable {
+        // Use empty popup style to remove all transitions from the popup. That way we don't
+        // need to synchronize with the popup window enter transition before proceeding to
+        // emulate a click outside the popup window bounds.
+        mBuilder = new Builder().withDismissListener()
+                .withPopupStyleAttr(R.style.PopupEmptyStyle);
+        runTestOnUiThread(new Runnable() {
+            public void run() {
+                mBuilder.show();
+            }
+        });
+        mInstrumentation.waitForIdleSync();
+
+        // Determine the location of the anchor on the screen so that we can emulate
+        // a tap outside of the popup bounds to dismiss the popup
+        final int[] anchorOnScreenXY = new int[2];
+        mBuilder.mAnchor.getLocationOnScreen(anchorOnScreenXY);
+
+        int emulatedTapX = anchorOnScreenXY[0] + 10;
+        int emulatedTapY = anchorOnScreenXY[1] - 20;
+
+        // The logic below uses Instrumentation to emulate a tap outside the bounds of the
+        // displayed popup menu. This tap is then treated by the framework to be "split" as
+        // the ACTION_OUTSIDE for the popup itself, as well as DOWN / MOVE / UP for the underlying
+        // view root if the popup is not modal.
+        // It is not correct to emulate these two sequences separately in the test, as it
+        // wouldn't emulate the user-facing interaction for this test. Note that usage
+        // of Instrumentation is necessary here since Espresso's actions operate at the level
+        // of view or data. Also, we don't want to use View.dispatchTouchEvent directly as
+        // that would require emulation of two separate sequences as well.
+
+        // Inject DOWN event
+        long downTime = SystemClock.uptimeMillis();
+        MotionEvent eventDown = MotionEvent.obtain(
+                downTime, downTime, MotionEvent.ACTION_DOWN, emulatedTapX, emulatedTapY, 1);
+        mInstrumentation.sendPointerSync(eventDown);
+
+        // Inject MOVE event
+        long moveTime = SystemClock.uptimeMillis();
+        MotionEvent eventMove = MotionEvent.obtain(
+                moveTime, moveTime, MotionEvent.ACTION_MOVE, emulatedTapX, emulatedTapY, 1);
+        mInstrumentation.sendPointerSync(eventMove);
+
+        // Inject UP event
+        long upTime = SystemClock.uptimeMillis();
+        MotionEvent eventUp = MotionEvent.obtain(
+                upTime, upTime, MotionEvent.ACTION_UP, emulatedTapX, emulatedTapY, 1);
+        mInstrumentation.sendPointerSync(eventUp);
+
+        // Wait for the system to process all events in the queue
+        mInstrumentation.waitForIdleSync();
+
+        // At this point our popup should have notified its dismiss listener
+        verify(mBuilder.mOnDismissListener, times(1)).onDismiss(mPopupMenu);
+    }
+
+    public void testSimpleMenuItemClickViaAPI() throws Throwable {
+        mBuilder = new Builder().withMenuItemClickListener().withDismissListener();
+        runTestOnUiThread(new Runnable() {
+            public void run() {
+                mBuilder.show();
+            }
+        });
+
+        // Verify that our menu item click listener hasn't been called yet
+        verify(mBuilder.mOnMenuItemClickListener, never()).onMenuItemClick(any(MenuItem.class));
+
+        InstrumentationRegistry.getInstrumentation().runOnMainSync(new Runnable() {
+            @Override
+            public void run() {
+                mPopupMenu.getMenu().performIdentifierAction(R.id.action_highlight, 0);
+            }
+        });
+
+        // Verify that our menu item click listener has been called with the expected menu item
+        verify(mBuilder.mOnMenuItemClickListener, times(1)).onMenuItemClick(
+                mPopupMenu.getMenu().findItem(R.id.action_highlight));
+
+        // Popup menu should be automatically dismissed on selecting an item
+        verify(mBuilder.mOnDismissListener, times(1)).onDismiss(mPopupMenu);
+    }
+
+    /**
+     * Inner helper class to configure an instance of {@link PopupMenu} for the specific test.
+     * The main reason for its existence is that once a popup menu is shown with the show() method,
+     * most of its configuration APIs are no-ops. This means that we can't add logic that is
+     * specific to a certain test once it's shown and we have a reference to a displayed
+     * {@link PopupMenu}.
+     */
+    public class Builder {
+        private boolean mHasDismissListener;
+        private boolean mHasMenuItemClickListener;
+        private boolean mInflateWithInflater;
+        private int mPopupStyleAttr = android.R.attr.popupMenuStyle;
+
+        private PopupMenu.OnMenuItemClickListener mOnMenuItemClickListener;
+        private PopupMenu.OnDismissListener mOnDismissListener;
+
+        private View mAnchor;
+
+        public Builder withMenuItemClickListener() {
+            mHasMenuItemClickListener = true;
+            return this;
+        }
+
+        public Builder withDismissListener() {
+            mHasDismissListener = true;
+            return this;
+        }
+
+        public Builder inflateWithInflater(boolean inflateWithInflater) {
+            mInflateWithInflater = inflateWithInflater;
+            return this;
+        }
+
+        public Builder withPopupStyleAttr(int popupStyleAttr) {
+            mPopupStyleAttr = popupStyleAttr;
+            return this;
+        }
+
+        private void configure() {
+            mAnchor = mActivity.findViewById(R.id.anchor_middle_left);
+            mPopupMenu = new PopupMenu(mActivity, mAnchor, Gravity.NO_GRAVITY, mPopupStyleAttr, 0);
+            if (mInflateWithInflater) {
+                final MenuInflater menuInflater = mPopupMenu.getMenuInflater();
+                menuInflater.inflate(R.menu.popup_menu, mPopupMenu.getMenu());
+            } else {
+                mPopupMenu.inflate(R.menu.popup_menu);
+            }
+
+            if (mHasMenuItemClickListener) {
+                // Register a mock listener to be notified when a menu item in our popup menu has
+                // been clicked.
+                mOnMenuItemClickListener = mock(PopupMenu.OnMenuItemClickListener.class);
+                mPopupMenu.setOnMenuItemClickListener(mOnMenuItemClickListener);
+            }
+
+            if (mHasDismissListener) {
+                // Register a mock listener to be notified when our popup menu is dismissed.
+                mOnDismissListener = mock(PopupMenu.OnDismissListener.class);
+                mPopupMenu.setOnDismissListener(mOnDismissListener);
+            }
+        }
+
+        public void show() {
+            configure();
+            // Show the popup menu
+            mPopupMenu.show();
+        }
+    }
+}
\ No newline at end of file
diff --git a/tests/tests/widget/src/android/widget/cts/util/ViewTestUtils.java b/tests/tests/widget/src/android/widget/cts/util/ViewTestUtils.java
index ca6c528..02ac28c 100644
--- a/tests/tests/widget/src/android/widget/cts/util/ViewTestUtils.java
+++ b/tests/tests/widget/src/android/widget/cts/util/ViewTestUtils.java
@@ -23,7 +23,7 @@
 import android.view.ViewTreeObserver;
 import android.view.ViewTreeObserver.OnDrawListener;
 
-import java.util.concurrent.Semaphore;
+import java.util.concurrent.CountDownLatch;
 import java.util.concurrent.TimeUnit;
 
 /**
@@ -41,34 +41,25 @@
      */
     public static void runOnMainAndDrawSync(Instrumentation instrumentation,
             final View view, final Runnable runner) {
-        final Semaphore token = new Semaphore(0);
-        final Runnable releaseToken = new Runnable() {
-            @Override
-            public void run() {
-                token.release();
-            }
-        };
+        final CountDownLatch latch = new CountDownLatch(1);
 
-        instrumentation.runOnMainSync(new Runnable() {
-            @Override
-            public void run() {
-                final ViewTreeObserver observer = view.getViewTreeObserver();
-                final OnDrawListener listener = new OnDrawListener() {
-                    @Override
-                    public void onDraw() {
-                        observer.removeOnDrawListener(this);
-                        view.post(releaseToken);
-                    }
-                };
+        instrumentation.runOnMainSync(() -> {
+            final ViewTreeObserver observer = view.getViewTreeObserver();
+            final OnDrawListener listener = new OnDrawListener() {
+                @Override
+                public void onDraw() {
+                    observer.removeOnDrawListener(this);
+                    view.post(() -> latch.countDown());
+                }
+            };
 
-                observer.addOnDrawListener(listener);
-                runner.run();
-            }
+            observer.addOnDrawListener(listener);
+            runner.run();
         });
 
         try {
             Assert.assertTrue("Expected draw pass occurred within 5 seconds",
-                    token.tryAcquire(5, TimeUnit.SECONDS));
+                    latch.await(5, TimeUnit.SECONDS));
         } catch (InterruptedException e) {
             throw new RuntimeException(e);
         }
diff --git a/tools/cts-tradefed/res/config/cts.xml b/tools/cts-tradefed/res/config/cts.xml
index 8104570..c54f355 100644
--- a/tools/cts-tradefed/res/config/cts.xml
+++ b/tools/cts-tradefed/res/config/cts.xml
@@ -27,7 +27,7 @@
     <option name="compatibility:exclude-filter" value="CtsSampleHostTestCases" />
 
     <!-- Exclude automotive only test cases for now -->
-    <option name="compatibility:exclude-filter" value="CtsAutomotiveTestCases" />
+    <option name="compatibility:exclude-filter" value="CtsCarTestCases" />
 
     <target_preparer class="com.android.compatibility.common.tradefed.targetprep.PropertyCheck">
         <option name="property-name" value="ro.build.type" />