Merge "AbstractVerifierTest: adapt tests to reflect that tabs are preserved by the DN parser" am: 31cf2dfd30 am: 5982f2bc9a
am: fc9df7044f

* commit 'fc9df7044f0aa6c860fc0e11f510b1aa10fd8b24':
  AbstractVerifierTest: adapt tests to reflect that tabs are preserved by the DN parser
diff --git a/tests/cts/hostside/Android.mk b/tests/cts/hostside/Android.mk
index 6637d61..b4e1e3d 100644
--- a/tests/cts/hostside/Android.mk
+++ b/tests/cts/hostside/Android.mk
@@ -21,10 +21,15 @@
 
 LOCAL_MODULE := CtsHostsideNetworkTests
 
-LOCAL_JAVA_LIBRARIES := cts-tradefed tradefed-prebuilt
+LOCAL_JAVA_LIBRARIES := cts-tradefed_v2 compatibility-host-util tradefed-prebuilt
+
+LOCAL_STATIC_JAVA_LIBRARIES := cts-migration-lib
 
 LOCAL_CTS_TEST_PACKAGE := android.net.hostsidenetwork
 
+# Tag this module as a cts_v2 test artifact
+LOCAL_COMPATIBILITY_SUITE := cts_v2
+
 include $(BUILD_CTS_HOST_JAVA_LIBRARY)
 
 # Build the test APKs using their own makefiles
diff --git a/tests/cts/hostside/AndroidTest.xml b/tests/cts/hostside/AndroidTest.xml
new file mode 100644
index 0000000..4b6994a
--- /dev/null
+++ b/tests/cts/hostside/AndroidTest.xml
@@ -0,0 +1,20 @@
+<?xml version="1.0" encoding="utf-8"?>
+<!-- Copyright (C) 2015 The Android Open Source Project
+
+     Licensed under the Apache License, Version 2.0 (the "License");
+     you may not use this file except in compliance with the License.
+     You may obtain a copy of the License at
+
+          http://www.apache.org/licenses/LICENSE-2.0
+
+     Unless required by applicable law or agreed to in writing, software
+     distributed under the License is distributed on an "AS IS" BASIS,
+     WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+     See the License for the specific language governing permissions and
+     limitations under the License.
+-->
+<configuration description="Config for CTS net host test cases">
+    <test class="com.android.compatibility.common.tradefed.testtype.JarHostTest" >
+        <option name="jar" value="CtsHostsideNetworkTests.jar" />
+    </test>
+</configuration>
diff --git a/tests/cts/hostside/app/Android.mk b/tests/cts/hostside/app/Android.mk
index 055287a..b64c4c9 100644
--- a/tests/cts/hostside/app/Android.mk
+++ b/tests/cts/hostside/app/Android.mk
@@ -29,4 +29,7 @@
 LOCAL_PROGUARD_ENABLED := disabled
 LOCAL_DEX_PREOPT := false
 
+# Tag this module as a cts_v2 test artifact
+LOCAL_COMPATIBILITY_SUITE := cts_v2
+
 include $(BUILD_CTS_SUPPORT_PACKAGE)
diff --git a/tests/cts/hostside/app/src/com/android/cts/net/hostside/ConnectivityManagerTest.java b/tests/cts/hostside/app/src/com/android/cts/net/hostside/ConnectivityManagerTest.java
new file mode 100644
index 0000000..5d3812c
--- /dev/null
+++ b/tests/cts/hostside/app/src/com/android/cts/net/hostside/ConnectivityManagerTest.java
@@ -0,0 +1,77 @@
+/*
+ * 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 com.android.cts.net.hostside;
+
+import static android.net.ConnectivityManager.RESTRICT_BACKGROUND_STATUS_DISABLED;
+import static android.net.ConnectivityManager.RESTRICT_BACKGROUND_STATUS_ENABLED;
+import static android.net.ConnectivityManager.RESTRICT_BACKGROUND_STATUS_WHITELISTED;
+import android.app.Activity;
+import android.net.ConnectivityManager;
+import android.test.InstrumentationTestCase;
+import android.util.Log;
+
+/**
+ * Tests for the {@link ConnectivityManager} API.
+ *
+ * <p>These tests rely on a host-side test to use {@code adb shell cmd netpolicy} to put the device
+ * in the proper state. In fact, they're more like "assertions" than tests per se - the real test
+ * logic is done on {@code HostsideNetworkTests}.
+ */
+public class ConnectivityManagerTest extends InstrumentationTestCase {
+    private static final String TAG = "ConnectivityManagerTest";
+
+    private ConnectivityManager mCM;
+
+    @Override
+    public void setUp() throws Exception {
+        super.setUp();
+        mCM = (ConnectivityManager) getInstrumentation().getContext().getSystemService(
+                Activity.CONNECTIVITY_SERVICE);
+    }
+
+    public void testGetRestrictBackgroundStatus_disabled() {
+        assertRestrictBackgroundStatus(RESTRICT_BACKGROUND_STATUS_DISABLED);
+    }
+
+    public void testGetRestrictBackgroundStatus_whitelisted() {
+        assertRestrictBackgroundStatus(RESTRICT_BACKGROUND_STATUS_WHITELISTED);
+    }
+
+    public void testGetRestrictBackgroundStatus_enabled() {
+        assertRestrictBackgroundStatus(RESTRICT_BACKGROUND_STATUS_ENABLED);
+    }
+
+    private void assertRestrictBackgroundStatus(int expectedStatus) {
+        final String expected = toString(expectedStatus);
+        Log.d(TAG, getName() + " (expecting " + expected + ")");
+        final int actualStatus = mCM.getRestrictBackgroundStatus();
+        assertEquals("wrong status", expected, toString(actualStatus));
+    }
+
+    private String toString(int status) {
+        switch (status) {
+            case RESTRICT_BACKGROUND_STATUS_DISABLED:
+                return "DISABLED";
+            case RESTRICT_BACKGROUND_STATUS_WHITELISTED:
+                return "WHITELISTED";
+            case RESTRICT_BACKGROUND_STATUS_ENABLED:
+                return "ENABLED";
+            default:
+                return "UNKNOWN_STATUS_" + status;
+        }
+    }
+}
diff --git a/tests/cts/hostside/src/com/android/cts/net/HostsideNetworkTests.java b/tests/cts/hostside/src/com/android/cts/net/HostsideNetworkTests.java
index a7698f3..dd2424c 100644
--- a/tests/cts/hostside/src/com/android/cts/net/HostsideNetworkTests.java
+++ b/tests/cts/hostside/src/com/android/cts/net/HostsideNetworkTests.java
@@ -16,7 +16,8 @@
 
 package com.android.cts.net;
 
-import com.android.cts.tradefed.build.CtsBuildHelper;
+import com.android.cts.migration.MigrationHelper;
+import com.android.ddmlib.Log;
 import com.android.ddmlib.testrunner.RemoteAndroidTestRunner;
 import com.android.ddmlib.testrunner.TestIdentifier;
 import com.android.ddmlib.testrunner.TestResult;
@@ -24,22 +25,25 @@
 import com.android.ddmlib.testrunner.TestRunResult;
 import com.android.tradefed.build.IBuildInfo;
 import com.android.tradefed.device.DeviceNotAvailableException;
+import com.android.tradefed.result.CollectingTestListener;
 import com.android.tradefed.testtype.DeviceTestCase;
 import com.android.tradefed.testtype.IAbi;
 import com.android.tradefed.testtype.IAbiReceiver;
 import com.android.tradefed.testtype.IBuildReceiver;
-import com.android.tradefed.device.DeviceNotAvailableException;
-import com.android.tradefed.device.ITestDevice;
-import com.android.tradefed.result.CollectingTestListener;
 
+import java.io.FileNotFoundException;
 import java.util.Map;
+import java.util.regex.Matcher;
+import java.util.regex.Pattern;
 
 public class HostsideNetworkTests extends DeviceTestCase implements IAbiReceiver, IBuildReceiver {
+    private static final boolean DEBUG = false;
+    private static final String TAG = "HostsideNetworkTests";
     private static final String TEST_PKG = "com.android.cts.net.hostside";
     private static final String TEST_APK = "CtsHostsideNetworkTestsApp.apk";
 
     private IAbi mAbi;
-    private CtsBuildHelper mCtsBuild;
+    private IBuildInfo mCtsBuild;
 
     @Override
     public void setAbi(IAbi abi) {
@@ -48,7 +52,7 @@
 
     @Override
     public void setBuild(IBuildInfo buildInfo) {
-        mCtsBuild = CtsBuildHelper.createBuildHelper(buildInfo);
+        mCtsBuild = buildInfo;
     }
 
     @Override
@@ -58,27 +62,130 @@
         assertNotNull(mAbi);
         assertNotNull(mCtsBuild);
 
-        getDevice().uninstallPackage(TEST_PKG);
-
-        assertNull(getDevice().installPackage(mCtsBuild.getTestApp(TEST_APK), false));
+        setRestrictBackground(false);
+        uninstallTestPackage(false);
+        installTestPackage();
     }
 
     @Override
     protected void tearDown() throws Exception {
         super.tearDown();
 
-        getDevice().uninstallPackage(TEST_PKG);
+        uninstallTestPackage(false);
+        setRestrictBackground(false);
     }
 
     public void testVpn() throws Exception {
-        runDeviceTests(TEST_PKG, ".VpnTest");
+        runDeviceTests(TEST_PKG, TEST_PKG + ".VpnTest");
+    }
+
+    public void testConnectivityManager_getRestrictBackgroundStatus_disabled() throws Exception {
+        final int uid = getUid(TEST_PKG);
+        removeRestrictBackgroundWhitelist(uid);
+        assertRestrictBackgroundStatusDisabled();
+        // Sanity check: make sure status is always disabled, never whitelisted
+        addRestrictBackgroundWhitelist(uid);
+        assertRestrictBackgroundStatusDisabled();
+    }
+
+    public void testConnectivityManager_getRestrictBackgroundStatus_whitelisted() throws Exception {
+        final int uid = getUid(TEST_PKG);
+        setRestrictBackground(true);
+        addRestrictBackgroundWhitelist(uid);
+        assertRestrictBackgroundStatusWhitelisted();
+    }
+
+    public void testConnectivityManager_getRestrictBackgroundStatus_enabled() throws Exception {
+        final int uid = getUid(TEST_PKG);
+        setRestrictBackground(true);
+        removeRestrictBackgroundWhitelist(uid);
+        assertRestrictBackgroundStatusEnabled();
+    }
+
+    public void testConnectivityManager_getRestrictBackgroundStatus_uninstall() throws Exception {
+        final int uid = getUid(TEST_PKG);
+
+        addRestrictBackgroundWhitelist(uid);
+        assertRestrictBackgroundWhitelist(uid, true);
+
+        uninstallTestPackage(true);
+        assertPackageUninstalled(TEST_PKG);
+        assertRestrictBackgroundWhitelist(uid, false);
+
+        installTestPackage();
+        final int newUid = getUid(TEST_PKG);
+        assertRestrictBackgroundWhitelist(uid, false);
+        assertRestrictBackgroundWhitelist(newUid, false);
+    }
+
+    private void installTestPackage() throws DeviceNotAvailableException, FileNotFoundException {
+        assertNull(getDevice().installPackage(
+                MigrationHelper.getTestFile(mCtsBuild, TEST_APK), false));
+    }
+
+    private void uninstallTestPackage(boolean shouldSucceed) throws DeviceNotAvailableException {
+        final String result = getDevice().uninstallPackage(TEST_PKG);
+        if (shouldSucceed) {
+            assertNull("uninstallPackage failed: " + result, result);
+        }
+    }
+
+    private void assertPackageUninstalled(String packageName) throws DeviceNotAvailableException {
+        final String command = "cmd package list packages -f " + packageName;
+        final int max_tries = 5;
+        for (int i = 1; i <= max_tries; i++) {
+            final String result = runCommand(command);
+            if (result.trim().isEmpty()) {
+                return;
+            }
+            i++;
+            Log.v(TAG, "Package " + packageName + " not uninstalled yet (" + result
+                    + "); sleeping 1s before polling again");
+            try {
+                Thread.sleep(1000);
+            } catch (InterruptedException e) {
+                Thread.currentThread().interrupt();
+            }
+        }
+        fail("Package '" + packageName + "' not uinstalled after " + max_tries + " seconds");
+    }
+
+    private void assertRestrictBackgroundStatusDisabled() throws DeviceNotAvailableException {
+        runDeviceTests(TEST_PKG, TEST_PKG + ".ConnectivityManagerTest",
+                "testGetRestrictBackgroundStatus_disabled");
+    }
+
+    private void assertRestrictBackgroundStatusWhitelisted() throws DeviceNotAvailableException {
+        runDeviceTests(TEST_PKG, TEST_PKG + ".ConnectivityManagerTest",
+                "testGetRestrictBackgroundStatus_whitelisted");
+    }
+
+    private void assertRestrictBackgroundStatusEnabled() throws DeviceNotAvailableException {
+        runDeviceTests(TEST_PKG, TEST_PKG + ".ConnectivityManagerTest",
+                "testGetRestrictBackgroundStatus_enabled");
     }
 
     public void runDeviceTests(String packageName, String testClassName)
-           throws DeviceNotAvailableException {
+            throws DeviceNotAvailableException {
+        runDeviceTests(packageName, testClassName, null);
+    }
+
+    public void runDeviceTests(String packageName, String testClassName, String methodName)
+            throws DeviceNotAvailableException {
         RemoteAndroidTestRunner testRunner = new RemoteAndroidTestRunner(packageName,
                 "android.support.test.runner.AndroidJUnitRunner", getDevice().getIDevice());
 
+        if (testClassName != null) {
+            // TODO: figure out why testRunner.setMethodName() / testRunner.setClassName() doesn't
+            // work
+            final StringBuilder runOptions = new StringBuilder("-e class ").append(testClassName);
+            if (methodName != null) {
+                runOptions.append('#').append(methodName);
+            }
+            Log.i(TAG, "Setting runOptions() as " + runOptions);
+            testRunner.setRunOptions(runOptions.toString());
+        }
+
         final CollectingTestListener listener = new CollectingTestListener();
         getDevice().runInstrumentationTests(testRunner, listener);
 
@@ -102,4 +209,57 @@
             throw new AssertionError(errorBuilder.toString());
         }
     }
+
+    private static final Pattern UID_PATTERN =
+            Pattern.compile(".*userId=([0-9]+)$", Pattern.MULTILINE);
+
+    private int getUid(String packageName) throws DeviceNotAvailableException {
+        final String output = runCommand("dumpsys package " + packageName);
+        final Matcher matcher = UID_PATTERN.matcher(output);
+        while (matcher.find()) {
+            final String match = matcher.group(1);
+            return Integer.parseInt(match);
+        }
+        throw new RuntimeException("Did not find regexp '" + UID_PATTERN + "' on adb output\n"
+                + output);
+    }
+
+    private void addRestrictBackgroundWhitelist(int uid) throws DeviceNotAvailableException {
+        runCommand("cmd netpolicy add restrict-background-whitelist " + uid);
+        assertRestrictBackgroundWhitelist(uid, true);
+    }
+
+    private void removeRestrictBackgroundWhitelist(int uid) throws DeviceNotAvailableException {
+        runCommand("cmd netpolicy remove restrict-background-whitelist " + uid);
+        assertRestrictBackgroundWhitelist(uid, false);
+    }
+
+    private void assertRestrictBackgroundWhitelist(int uid, boolean expected)
+            throws DeviceNotAvailableException {
+        final String output = runCommand("cmd netpolicy list restrict-background-whitelist ");
+        // TODO: use MoreAsserts
+        if (expected) {
+            assertTrue("Did not find uid '" + uid + "' on '" + output + "'",
+                    output.contains(Integer.toString(uid)));
+        } else {
+            assertFalse("Found uid '" + uid + "' on '" + output + "'",
+                    output.contains(Integer.toString(uid)));
+        }
+    }
+
+    private void setRestrictBackground(boolean enabled) throws DeviceNotAvailableException {
+        runCommand("cmd netpolicy set restrict-background " + enabled);
+        final String output = runCommand("cmd netpolicy get restrict-background ").trim();
+        final String expectedSuffix = enabled ? "enabled" : "disabled";
+        // TODO: use MoreAsserts?
+        assertTrue("output '" + output + "' should end with '" + expectedSuffix + "'",
+                output.endsWith(expectedSuffix));
+    }
+
+    private String runCommand(String command) throws DeviceNotAvailableException {
+        Log.d(TAG, "Command: '" + command + "'");
+        final String output = getDevice().executeShellCommand(command);
+        if (DEBUG) Log.v(TAG, "Output: " + output.trim());
+        return output;
+    }
 }
diff --git a/tests/cts/net/Android.mk b/tests/cts/net/Android.mk
index 56729b6..608ea47 100644
--- a/tests/cts/net/Android.mk
+++ b/tests/cts/net/Android.mk
@@ -40,6 +40,9 @@
 # uncomment when b/13249961 is fixed
 #LOCAL_SDK_VERSION := current
 
+# Tag this module as a cts_v2 test artifact
+LOCAL_COMPATIBILITY_SUITE := cts_v2
+
 include $(BUILD_CTS_PACKAGE)
 
 include $(call all-makefiles-under,$(LOCAL_PATH))
diff --git a/tests/cts/net/AndroidManifest.xml b/tests/cts/net/AndroidManifest.xml
index 001e294..2bc8216 100644
--- a/tests/cts/net/AndroidManifest.xml
+++ b/tests/cts/net/AndroidManifest.xml
@@ -16,7 +16,7 @@
  -->
 
 <manifest xmlns:android="http://schemas.android.com/apk/res/android"
-    package="com.android.cts.net">
+    package="android.net.cts">
 
     <uses-permission android:name="android.permission.ACCESS_NETWORK_STATE" />
     <uses-permission android:name="android.permission.ACCESS_WIFI_STATE" />
@@ -35,7 +35,7 @@
     </application>
 
     <instrumentation android:name="android.support.test.runner.AndroidJUnitRunner"
-                     android:targetPackage="com.android.cts.net"
+                     android:targetPackage="android.net.cts"
                      android:label="CTS tests of android.net">
         <meta-data android:name="listener"
             android:value="com.android.cts.runner.CtsTestRunListener" />
diff --git a/tests/cts/net/AndroidTest.xml b/tests/cts/net/AndroidTest.xml
new file mode 100644
index 0000000..dc80339
--- /dev/null
+++ b/tests/cts/net/AndroidTest.xml
@@ -0,0 +1,25 @@
+<!-- Copyright (C) 2015 The Android Open Source Project
+
+     Licensed under the Apache License, Version 2.0 (the "License");
+     you may not use this file except in compliance with the License.
+     You may obtain a copy of the License at
+
+          http://www.apache.org/licenses/LICENSE-2.0
+
+     Unless required by applicable law or agreed to in writing, software
+     distributed under the License is distributed on an "AS IS" BASIS,
+     WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+     See the License for the specific language governing permissions and
+     limitations under the License.
+-->
+<configuration description="Config for CTS Net test cases">
+    <target_preparer class="com.android.compatibility.common.tradefed.targetprep.WifiCheck" />
+    <target_preparer class="com.android.compatibility.common.tradefed.targetprep.ApkInstaller">
+        <option name="cleanup-apks" value="true" />
+        <option name="test-file-name" value="CtsNetTestCases.apk" />
+    </target_preparer>
+    <test class="com.android.tradefed.testtype.AndroidJUnitTest" >
+        <option name="package" value="android.net.cts" />
+        <option name="runtime-hint" value="9m4s" />
+    </test>
+</configuration>