diff --git a/tests/cts/net/AndroidManifest.xml b/tests/cts/net/AndroidManifest.xml
index bca2d2c..001e294 100644
--- a/tests/cts/net/AndroidManifest.xml
+++ b/tests/cts/net/AndroidManifest.xml
@@ -20,6 +20,7 @@
 
     <uses-permission android:name="android.permission.ACCESS_NETWORK_STATE" />
     <uses-permission android:name="android.permission.ACCESS_WIFI_STATE" />
+    <uses-permission android:name="android.permission.ACCESS_COARSE_LOCATION" />
     <uses-permission android:name="android.permission.CHANGE_NETWORK_STATE" />
     <uses-permission android:name="android.permission.CHANGE_WIFI_STATE" />
     <uses-permission android:name="android.permission.DISABLE_KEYGUARD" />
diff --git a/tests/cts/net/jni/NativeMultinetworkJni.c b/tests/cts/net/jni/NativeMultinetworkJni.c
index 9a5ab9c..ad56b51 100644
--- a/tests/cts/net/jni/NativeMultinetworkJni.c
+++ b/tests/cts/net/jni/NativeMultinetworkJni.c
@@ -93,7 +93,8 @@
 void sockaddr_ntop(const struct sockaddr *sa, socklen_t salen, char *dst, const size_t size) {
     char addrstr[INET6_ADDRSTRLEN];
     char portstr[sizeof("65535")];
-    char buf[sizeof(addrstr) + sizeof(portstr) + sizeof("[]:")];
+    char buf[kSockaddrStrLen+1];
+
     int ret = getnameinfo(sa, salen,
                           addrstr, sizeof(addrstr),
                           portstr, sizeof(portstr),
@@ -106,7 +107,7 @@
         sprintf(buf, "???");
     }
 
-    strlcpy(dst, buf, (strlen(buf) < size - 1) ? strlen(buf) : size - 1);
+    strlcpy(dst, buf, size);
 }
 
 JNIEXPORT jint Java_android_net_cts_MultinetworkApiTest_runDatagramCheck(
@@ -122,9 +123,8 @@
     struct addrinfo *res = NULL;
     net_handle_t handle = (net_handle_t) nethandle;
 
-    // Quoth Ian Swett:
-    //     "QUIC always uses 80 and 443, but only 443 is used for secure(HTTPS) traffic."
-    int rval = android_getaddrinfofornetwork(handle, kHostname, "80", &kHints, &res);
+    static const char kPort[] = "443";
+    int rval = android_getaddrinfofornetwork(handle, kHostname, kPort, &kHints, &res);
     if (rval != 0) {
         ALOGD("android_getaddrinfofornetwork(%llu, %s) returned rval=%d errno=%d",
               handle, kHostname, rval, errno);
@@ -150,9 +150,9 @@
         return -errno;
     }
 
-    char addrstr[kSockaddrStrLen];
+    char addrstr[kSockaddrStrLen+1];
     sockaddr_ntop(res->ai_addr, res->ai_addrlen, addrstr, sizeof(addrstr));
-    ALOGD("Attempting connect() to %s...", addrstr);
+    ALOGD("Attempting connect() to %s ...", addrstr);
 
     rval = connect(fd, res->ai_addr, res->ai_addrlen);
     if (rval != 0) {
@@ -172,10 +172,12 @@
     ALOGD("... from %s", addrstr);
 
     // Don't let reads or writes block indefinitely.
-    const struct timeval timeo = { 5, 0 };  // 5 seconds
+    const struct timeval timeo = { 2, 0 };  // 2 seconds
     setsockopt(fd, SOL_SOCKET, SO_RCVTIMEO, &timeo, sizeof(timeo));
     setsockopt(fd, SOL_SOCKET, SO_SNDTIMEO, &timeo, sizeof(timeo));
 
+    // For reference see:
+    //     https://tools.ietf.org/html/draft-tsvwg-quic-protocol-01#section-6.1
     uint8_t quic_packet[] = {
         0x0c,                    // public flags: 64bit conn ID, 8bit sequence number
         0, 0, 0, 0, 0, 0, 0, 0,  // 64bit connection ID
@@ -186,19 +188,36 @@
 
     arc4random_buf(quic_packet + 1, 8);  // random connection ID
 
-    ssize_t sent = send(fd, quic_packet, sizeof(quic_packet), 0);
-    if (sent < (ssize_t)sizeof(quic_packet)) {
-        ALOGD("send(QUIC packet) returned sent=%zd, errno=%d", sent, errno);
-        close(fd);
-        return -errno;
-    }
-
     uint8_t response[1500];
-    ssize_t rcvd = recv(fd, response, sizeof(response), 0);
+    ssize_t sent, rcvd;
+    static const int MAX_RETRIES = 5;
+    int i, errnum = 0;
+
+    for (i = 0; i < MAX_RETRIES; i++) {
+        sent = send(fd, quic_packet, sizeof(quic_packet), 0);
+        if (sent < (ssize_t)sizeof(quic_packet)) {
+            errnum = errno;
+            ALOGD("send(QUIC packet) returned sent=%zd, errno=%d", sent, errnum);
+            close(fd);
+            return -errnum;
+        }
+
+        rcvd = recv(fd, response, sizeof(response), 0);
+        if (rcvd > 0) {
+            break;
+        } else {
+            errnum = errno;
+            ALOGD("[%d/%d] recv(QUIC response) returned rcvd=%zd, errno=%d",
+                  i + 1, MAX_RETRIES, rcvd, errnum);
+        }
+    }
     if (rcvd < sent) {
-        ALOGD("recv() returned rcvd=%zd, errno=%d", rcvd, errno);
+        ALOGD("QUIC UDP %s: sent=%zd but rcvd=%zd, errno=%d", kPort, sent, rcvd, errnum);
+        if (rcvd <= 0) {
+            ALOGD("Does this network block UDP port %s?", kPort);
+        }
         close(fd);
-        return -errno;
+        return -EPROTO;
     }
 
     int conn_id_cmp = memcmp(quic_packet + 1, response + 1, 8);
diff --git a/tests/cts/net/src/android/net/cts/ConnectivityManagerTest.java b/tests/cts/net/src/android/net/cts/ConnectivityManagerTest.java
index 34baac9..88dbd7c 100644
--- a/tests/cts/net/src/android/net/cts/ConnectivityManagerTest.java
+++ b/tests/cts/net/src/android/net/cts/ConnectivityManagerTest.java
@@ -16,6 +16,7 @@
 
 package android.net.cts;
 
+import android.app.PendingIntent;
 import android.content.BroadcastReceiver;
 import android.content.Context;
 import android.content.Intent;
@@ -32,6 +33,7 @@
 import android.net.wifi.WifiManager;
 import android.test.AndroidTestCase;
 import android.util.Log;
+import android.os.SystemProperties;
 
 import com.android.internal.telephony.PhoneConstants;
 
@@ -53,6 +55,10 @@
     public static final int TYPE_WIFI = ConnectivityManager.TYPE_WIFI;
     private static final int HOST_ADDRESS = 0x7f000001;// represent ip 127.0.0.1
 
+    // Action sent to ConnectivityActionReceiver when a network callback is sent via PendingIntent.
+    private static final String NETWORK_CALLBACK_ACTION =
+            "ConnectivityManagerTest.NetworkCallbackAction";
+
     // device could have only one interface: data, wifi.
     private static final int MIN_NUM_NETWORK_TYPES = 1;
 
@@ -61,7 +67,6 @@
     private PackageManager mPackageManager;
     private final HashMap<Integer, NetworkConfig> mNetworks =
             new HashMap<Integer, NetworkConfig>();
-    private final List<Integer>mProtectedNetworks = new ArrayList<Integer>();
 
     @Override
     protected void setUp() throws Exception {
@@ -73,20 +78,17 @@
         // Get com.android.internal.R.array.networkAttributes
         int resId = getContext().getResources().getIdentifier("networkAttributes", "array", "android");
         String[] naStrings = getContext().getResources().getStringArray(resId);
-
+        //TODO: What is the "correct" way to determine if this is a wifi only device?
+        boolean wifiOnly = SystemProperties.getBoolean("ro.radio.noril", false);
         for (String naString : naStrings) {
             try {
                 NetworkConfig n = new NetworkConfig(naString);
+                if (wifiOnly && ConnectivityManager.isNetworkTypeMobile(n.type)) {
+                    continue;
+                }
                 mNetworks.put(n.type, n);
             } catch (Exception e) {}
         }
-
-        // Get com.android.internal.R.array.config_protectedNetworks
-        resId = getContext().getResources().getIdentifier("config_protectedNetworks", "array", "android");
-        int[] protectedNetworks = getContext().getResources().getIntArray(resId);
-        for (int p : protectedNetworks) {
-            mProtectedNetworks.add(p);
-        }
     }
 
     public void testIsNetworkTypeValid() {
@@ -127,17 +129,18 @@
     public void testGetActiveNetworkInfo() {
         NetworkInfo ni = mCm.getActiveNetworkInfo();
 
-        assertTrue("You must have an active network connection to complete CTS", ni != null);
+        assertNotNull("You must have an active network connection to complete CTS", ni);
         assertTrue(ConnectivityManager.isNetworkTypeValid(ni.getType()));
         assertTrue(ni.getState() == State.CONNECTED);
     }
 
     public void testGetActiveNetwork() {
         Network network = mCm.getActiveNetwork();
-        assertTrue("You must have an active network connection to complete CTS", network != null);
+        assertNotNull("You must have an active network connection to complete CTS", network);
 
         NetworkInfo ni = mCm.getNetworkInfo(network);
-        assertTrue("Network returned from getActiveNetwork was invalid", ni != null);
+        assertNotNull("Network returned from getActiveNetwork was invalid", ni);
+
         // Similar to testGetActiveNetworkInfo above.
         assertTrue(ConnectivityManager.isNetworkTypeValid(ni.getType()));
         assertTrue(ni.getState() == State.CONNECTED);
@@ -179,6 +182,27 @@
         }
     }
 
+    private void assertStartUsingNetworkFeatureUnsupported(int networkType, String feature) {
+        try {
+            mCm.startUsingNetworkFeature(networkType, feature);
+            fail("startUsingNetworkFeature is no longer supported in the current API version");
+        } catch (UnsupportedOperationException expected) {}
+    }
+
+    private void assertStopUsingNetworkFeatureUnsupported(int networkType, String feature) {
+        try {
+            mCm.startUsingNetworkFeature(networkType, feature);
+            fail("stopUsingNetworkFeature is no longer supported in the current API version");
+        } catch (UnsupportedOperationException expected) {}
+    }
+
+    private void assertRequestRouteToHostUnsupported(int networkType, int hostAddress) {
+        try {
+            mCm.requestRouteToHost(networkType, hostAddress);
+            fail("requestRouteToHost is no longer supported in the current API version");
+        } catch (UnsupportedOperationException expected) {}
+    }
+
     public void testStartUsingNetworkFeature() {
 
         final String invalidateFeature = "invalidateFeature";
@@ -187,27 +211,9 @@
         final int wifiOnlyStartFailureCode = PhoneConstants.APN_REQUEST_FAILED;
         final int wifiOnlyStopFailureCode = -1;
 
-        NetworkInfo ni = mCm.getNetworkInfo(TYPE_MOBILE);
-        if (ni != null) {
-            assertEquals(PhoneConstants.APN_REQUEST_FAILED,
-                    mCm.startUsingNetworkFeature(TYPE_MOBILE, invalidateFeature));
-            assertEquals(failureCode, mCm.stopUsingNetworkFeature(TYPE_MOBILE,
-                    invalidateFeature));
-        } else {
-            assertEquals(wifiOnlyStartFailureCode, mCm.startUsingNetworkFeature(TYPE_MOBILE,
-                    invalidateFeature));
-            assertEquals(wifiOnlyStopFailureCode, mCm.stopUsingNetworkFeature(TYPE_MOBILE,
-                    invalidateFeature));
-        }
-
-        ni = mCm.getNetworkInfo(TYPE_WIFI);
-        if (ni != null) {
-            // Should return failure because MMS is not supported on WIFI.
-            assertEquals(PhoneConstants.APN_REQUEST_FAILED, mCm.startUsingNetworkFeature(TYPE_WIFI,
-                    mmsFeature));
-            assertEquals(failureCode, mCm.stopUsingNetworkFeature(TYPE_WIFI,
-                    mmsFeature));
-        }
+        assertStartUsingNetworkFeatureUnsupported(TYPE_MOBILE, invalidateFeature);
+        assertStopUsingNetworkFeatureUnsupported(TYPE_MOBILE, invalidateFeature);
+        assertStartUsingNetworkFeatureUnsupported(TYPE_WIFI, mmsFeature);
     }
 
     private boolean isSupported(int networkType) {
@@ -218,11 +224,6 @@
                (networkType == ConnectivityManager.TYPE_VPN);
     }
 
-    // true if only the system can turn it on
-    private boolean isNetworkProtected(int networkType) {
-        return mProtectedNetworks.contains(networkType);
-    }
-
     public void testIsNetworkSupported() {
         for (int type = -1; type <= ConnectivityManager.MAX_NETWORK_TYPE; type++) {
             boolean supported = mCm.isNetworkSupported(type);
@@ -236,82 +237,14 @@
 
     public void testRequestRouteToHost() {
         for (int type = -1 ; type <= ConnectivityManager.MAX_NETWORK_TYPE; type++) {
-            NetworkInfo ni = mCm.getNetworkInfo(type);
-            boolean expectToWork = isSupported(type) && !isNetworkProtected(type) &&
-                    ni != null && ni.isConnected();
-
-            try {
-                assertTrue("Network type " + type,
-                        mCm.requestRouteToHost(type, HOST_ADDRESS) == expectToWork);
-            } catch (Exception e) {
-                Log.d(TAG, "got exception in requestRouteToHost for type " + type);
-                assertFalse("Exception received for type " + type, expectToWork);
-            }
-
-            //TODO verify route table
+            assertRequestRouteToHostUnsupported(type, HOST_ADDRESS);
         }
-
-        assertFalse(mCm.requestRouteToHost(-1, HOST_ADDRESS));
     }
 
     public void testTest() {
         mCm.getBackgroundDataSetting();
     }
 
-    /** Test that hipri can be brought up when Wifi is enabled. */
-    public void testStartUsingNetworkFeature_enableHipri() throws Exception {
-        if (!mPackageManager.hasSystemFeature(PackageManager.FEATURE_TELEPHONY)
-                || !mPackageManager.hasSystemFeature(PackageManager.FEATURE_WIFI)) {
-            // This test requires a mobile data connection and WiFi.
-            return;
-        }
-
-        boolean isWifiEnabled = mWifiManager.isWifiEnabled();
-        boolean isWifiConnected = false;
-
-        NetworkInfo nwInfo = mCm.getNetworkInfo(ConnectivityManager.TYPE_WIFI);
-        if (nwInfo != null) {
-            isWifiConnected = nwInfo.isConnected();
-        }
-        try {
-            // Make sure WiFi is connected to an access point.
-            if (!isWifiConnected) {
-                connectToWifi();
-            }
-
-            // Register a receiver that will capture the connectivity change for hipri.
-            ConnectivityActionReceiver receiver =
-                    new ConnectivityActionReceiver(ConnectivityManager.TYPE_MOBILE_HIPRI);
-            IntentFilter filter = new IntentFilter();
-            filter.addAction(ConnectivityManager.CONNECTIVITY_ACTION);
-            mContext.registerReceiver(receiver, filter);
-
-            // Try to start using the hipri feature...
-            int result = mCm.startUsingNetworkFeature(ConnectivityManager.TYPE_MOBILE,
-                    FEATURE_ENABLE_HIPRI);
-            assertTrue("Couldn't start using the HIPRI feature.", result != -1);
-
-            // Check that the ConnectivityManager reported that it connected using hipri...
-            assertTrue("Couldn't connect using hipri...", receiver.waitForConnection());
-
-            assertTrue("Couldn't requestRouteToHost using HIPRI.",
-                    mCm.requestRouteToHost(ConnectivityManager.TYPE_MOBILE_HIPRI, HOST_ADDRESS));
-            // TODO check dns selection
-            // TODO check routes
-        } catch (InterruptedException e) {
-            fail("Broadcast receiver waiting for ConnectivityManager interrupted.");
-        } finally {
-            mCm.stopUsingNetworkFeature(ConnectivityManager.TYPE_MOBILE,
-                    FEATURE_ENABLE_HIPRI);
-            // TODO wait for HIPRI to go
-            // TODO check dns selection
-            // TODO check routes
-            if (!isWifiEnabled) {
-                mWifiManager.setWifiEnabled(false);
-            }
-        }
-    }
-
     /**
      * Exercises both registerNetworkCallback and unregisterNetworkCallback. This checks to
      * see if we get a callback for the TRANSPORT_WIFI transport type being available.
@@ -323,7 +256,7 @@
      */
     public void testRegisterNetworkCallback() {
         if (!mPackageManager.hasSystemFeature(PackageManager.FEATURE_WIFI)) {
-            Log.i(TAG, "testRegisterNetworkCallback cannot execute unless devices supports WiFi");
+            Log.i(TAG, "testRegisterNetworkCallback cannot execute unless device supports WiFi");
             return;
         }
 
@@ -353,47 +286,167 @@
             mCm.unregisterNetworkCallback(callback);
 
             // Return WiFI to its original enabled/disabled state.
-            mWifiManager.setWifiEnabled(previousWifiEnabledState);
+            if (!previousWifiEnabledState) {
+                disconnectFromWifi();
+            }
         }
     }
 
-    private void connectToWifi() throws InterruptedException {
-        ConnectivityActionReceiver receiver =
-                new ConnectivityActionReceiver(ConnectivityManager.TYPE_WIFI);
+    /**
+     * Tests both registerNetworkCallback and unregisterNetworkCallback similarly to
+     * {@link #testRegisterNetworkCallback} except that a {@code PendingIntent} is used instead
+     * of a {@code NetworkCallback}.
+     */
+    public void testRegisterNetworkCallback_withPendingIntent() {
+        if (!mPackageManager.hasSystemFeature(PackageManager.FEATURE_WIFI)) {
+            Log.i(TAG, "testRegisterNetworkCallback cannot execute unless device supports WiFi");
+            return;
+        }
+
+        // Create a ConnectivityActionReceiver that has an IntentFilter for our locally defined
+        // action, NETWORK_CALLBACK_ACTION.
+        IntentFilter filter = new IntentFilter();
+        filter.addAction(NETWORK_CALLBACK_ACTION);
+
+        ConnectivityActionReceiver receiver = new ConnectivityActionReceiver(
+                ConnectivityManager.TYPE_WIFI, NetworkInfo.State.CONNECTED);
+        mContext.registerReceiver(receiver, filter);
+
+        // Create a broadcast PendingIntent for NETWORK_CALLBACK_ACTION.
+        Intent intent = new Intent(NETWORK_CALLBACK_ACTION);
+        PendingIntent pendingIntent = PendingIntent.getBroadcast(
+                mContext, 0, intent, PendingIntent.FLAG_CANCEL_CURRENT);
+
+        // We will register for a WIFI network being available or lost.
+        NetworkRequest request = new NetworkRequest.Builder()
+                .addTransportType(NetworkCapabilities.TRANSPORT_WIFI)
+                .build();
+        mCm.registerNetworkCallback(request, pendingIntent);
+
+        boolean previousWifiEnabledState = mWifiManager.isWifiEnabled();
+
+        try {
+            // Make sure WiFi is connected to an access point to start with.
+            if (!previousWifiEnabledState) {
+                connectToWifi();
+            }
+
+            // Now we expect to get the Intent delivered notifying of the availability of the wifi
+            // network even if it was already connected as a state-based action when the callback
+            // is registered.
+            assertTrue("Did not receive expected Intent " + intent + " for TRANSPORT_WIFI",
+                    receiver.waitForState());
+        } catch (InterruptedException e) {
+            fail("Broadcast receiver or NetworkCallback wait was interrupted.");
+        } finally {
+            mCm.unregisterNetworkCallback(pendingIntent);
+            pendingIntent.cancel();
+            mContext.unregisterReceiver(receiver);
+
+            // Return WiFI to its original enabled/disabled state.
+            if (!previousWifiEnabledState) {
+                disconnectFromWifi();
+            }
+        }
+    }
+
+    /** Enable WiFi and wait for it to become connected to a network. */
+    private void connectToWifi() {
+        ConnectivityActionReceiver receiver = new ConnectivityActionReceiver(
+                ConnectivityManager.TYPE_WIFI, NetworkInfo.State.CONNECTED);
         IntentFilter filter = new IntentFilter();
         filter.addAction(ConnectivityManager.CONNECTIVITY_ACTION);
         mContext.registerReceiver(receiver, filter);
 
-        assertTrue(mWifiManager.setWifiEnabled(true));
-        assertTrue("Wifi must be configured to connect to an access point for this test.",
-                receiver.waitForConnection());
+        boolean connected = false;
+        try {
+            assertTrue(mWifiManager.setWifiEnabled(true));
+            connected = receiver.waitForState();
+        } catch (InterruptedException ex) {
+            fail("connectToWifi was interrupted");
+        } finally {
+            mContext.unregisterReceiver(receiver);
+        }
 
-        mContext.unregisterReceiver(receiver);
+        assertTrue("Wifi must be configured to connect to an access point for this test.",
+                connected);
     }
 
-    /** Receiver that captures the last connectivity change's network type and state. */
+    /** Disable WiFi and wait for it to become disconnected from the network. */
+    private void disconnectFromWifi() {
+        ConnectivityActionReceiver receiver = new ConnectivityActionReceiver(
+                ConnectivityManager.TYPE_WIFI, NetworkInfo.State.DISCONNECTED);
+        IntentFilter filter = new IntentFilter();
+        filter.addAction(ConnectivityManager.CONNECTIVITY_ACTION);
+        mContext.registerReceiver(receiver, filter);
+
+        boolean disconnected = false;
+        try {
+            assertTrue(mWifiManager.setWifiEnabled(false));
+            disconnected = receiver.waitForState();
+        } catch (InterruptedException ex) {
+            fail("disconnectFromWifi was interrupted");
+        } finally {
+            mContext.unregisterReceiver(receiver);
+        }
+
+        assertTrue("Wifi failed to reach DISCONNECTED state.", disconnected);
+    }
+
+    /**
+     * Receiver that captures the last connectivity change's network type and state. Recognizes
+     * both {@code CONNECTIVITY_ACTION} and {@code NETWORK_CALLBACK_ACTION} intents.
+     */
     private class ConnectivityActionReceiver extends BroadcastReceiver {
 
         private final CountDownLatch mReceiveLatch = new CountDownLatch(1);
 
         private final int mNetworkType;
+        private final NetworkInfo.State mNetState;
 
-        ConnectivityActionReceiver(int networkType) {
+        ConnectivityActionReceiver(int networkType, NetworkInfo.State netState) {
             mNetworkType = networkType;
+            mNetState = netState;
         }
 
         public void onReceive(Context context, Intent intent) {
-            NetworkInfo networkInfo = intent.getExtras()
-                    .getParcelable(ConnectivityManager.EXTRA_NETWORK_INFO);
+            String action = intent.getAction();
+            NetworkInfo networkInfo = null;
+
+            // When receiving ConnectivityManager.CONNECTIVITY_ACTION, the NetworkInfo parcelable
+            // is stored in EXTRA_NETWORK_INFO. With a NETWORK_CALLBACK_ACTION, the Network is
+            // sent in EXTRA_NETWORK and we need to ask the ConnectivityManager for the NetworkInfo.
+            if (ConnectivityManager.CONNECTIVITY_ACTION.equals(action)) {
+                networkInfo = intent.getExtras()
+                        .getParcelable(ConnectivityManager.EXTRA_NETWORK_INFO);
+                assertNotNull("ConnectivityActionReceiver expected EXTRA_NETWORK_INFO", networkInfo);
+            } else if (NETWORK_CALLBACK_ACTION.equals(action)) {
+                Network network = intent.getExtras()
+                        .getParcelable(ConnectivityManager.EXTRA_NETWORK);
+                assertNotNull("ConnectivityActionReceiver expected EXTRA_NETWORK", network);
+                networkInfo = mCm.getNetworkInfo(network);
+                if (networkInfo == null) {
+                    // When disconnecting, it seems like we get an intent sent with an invalid
+                    // Network; that is, by the time we call ConnectivityManager.getNetworkInfo(),
+                    // it is invalid. Ignore these.
+                    Log.i(TAG, "ConnectivityActionReceiver NETWORK_CALLBACK_ACTION ignoring "
+                            + "invalid network");
+                    return;
+                }
+            } else {
+                fail("ConnectivityActionReceiver received unxpected intent action: " + action);
+            }
+
+            assertNotNull("ConnectivityActionReceiver didn't find NetworkInfo", networkInfo);
             int networkType = networkInfo.getType();
             State networkState = networkInfo.getState();
             Log.i(TAG, "Network type: " + networkType + " state: " + networkState);
-            if (networkType == mNetworkType && networkInfo.getState() == State.CONNECTED) {
+            if (networkType == mNetworkType && networkInfo.getState() == mNetState) {
                 mReceiveLatch.countDown();
             }
         }
 
-        public boolean waitForConnection() throws InterruptedException {
+        public boolean waitForState() throws InterruptedException {
             return mReceiveLatch.await(30, TimeUnit.SECONDS);
         }
     }
@@ -402,7 +455,7 @@
      * Callback used in testRegisterNetworkCallback that allows caller to block on
      * {@code onAvailable}.
      */
-    private class TestNetworkCallback extends ConnectivityManager.NetworkCallback {
+    private static class TestNetworkCallback extends ConnectivityManager.NetworkCallback {
         private final CountDownLatch mAvailableLatch = new CountDownLatch(1);
 
         public boolean waitForAvailable() throws InterruptedException {
