OSDN Git Service

[CS] Unregister callback as part of onUnavailable dispatch
authorEtan Cohen <etancohen@google.com>
Tue, 16 Apr 2019 22:07:55 +0000 (15:07 -0700)
committerEtan Cohen <etancohen@google.com>
Thu, 9 May 2019 03:57:54 +0000 (03:57 +0000)
The onUnavailable semantics promise that it is equivalent to calling
the unregister callback method. But - it doesn't unregister the callback
allowing it to be reused. Fixed.

Additionally, modified the unregisterNetworkCallback method to not fail
on duplicate unregistration (since a callback could now self
unregister). Instead simply print a log.

Bug: 130651445
Test: atest ConnectivityServiceTest
Merged-In: I4c54b003a733eb0b1e4fd8674ed13081b1bef8e3
Change-Id: I4c54b003a733eb0b1e4fd8674ed13081b1bef8e3

core/java/android/net/ConnectivityManager.java
tests/net/java/com/android/server/ConnectivityServiceTest.java

index 0e10de8..a69ca99 100644 (file)
@@ -3449,6 +3449,10 @@ public class ConnectivityManager {
             final NetworkCallback callback;
             synchronized (sCallbacks) {
                 callback = sCallbacks.get(request);
+                if (message.what == CALLBACK_UNAVAIL) {
+                    sCallbacks.remove(request);
+                    callback.networkRequest = ALREADY_UNREGISTERED;
+                }
             }
             if (DBG) {
                 Log.d(TAG, getCallbackName(message.what) + " for network " + network);
@@ -3995,8 +3999,10 @@ public class ConnectivityManager {
         synchronized (sCallbacks) {
             Preconditions.checkArgument(networkCallback.networkRequest != null,
                     "NetworkCallback was not registered");
-            Preconditions.checkArgument(networkCallback.networkRequest != ALREADY_UNREGISTERED,
-                    "NetworkCallback was already unregistered");
+            if (networkCallback.networkRequest == ALREADY_UNREGISTERED) {
+                Log.d(TAG, "NetworkCallback was already unregistered");
+                return;
+            }
             for (Map.Entry<NetworkRequest, NetworkCallback> e : sCallbacks.entrySet()) {
                 if (e.getValue() == networkCallback) {
                     reqs.add(e.getKey());
index 363ac9c..0ef56e5 100644 (file)
@@ -3854,6 +3854,9 @@ public class ConnectivityServiceTest {
         networkCallback.expectCallback(CallbackState.UNAVAILABLE, null);
         testFactory.waitForRequests();
 
+        // unregister network callback - a no-op, but should not fail
+        mCm.unregisterNetworkCallback(networkCallback);
+
         testFactory.unregister();
         handlerThread.quit();
     }