diff options
| author | 2020-01-21 12:41:11 +0000 | |
|---|---|---|
| committer | 2020-01-21 12:41:11 +0000 | |
| commit | a1cbcd6e00208d29708e024a441cf682e27e41b6 (patch) | |
| tree | c1bb00724fb0f95501d297f219c17afaabba078b | |
| parent | dbbdc8b6f44ffbdb5a5a8d14346a2eae7206bd18 (diff) | |
| parent | 709c6fb8a9ca56fc2ad0cef0d66a05f44f5eec12 (diff) | |
Merge changes I904d87c0,I9ef468a1 am: 85768e2dc3 am: 709c6fb8a9
Change-Id: I253587aca8cb272d0bf9576a84c5c7d5a0bb342a
| -rw-r--r-- | services/core/java/com/android/server/ConnectivityService.java | 129 | 
1 files changed, 83 insertions, 46 deletions
diff --git a/services/core/java/com/android/server/ConnectivityService.java b/services/core/java/com/android/server/ConnectivityService.java index 83adec675caf..29f9e58a5d8a 100644 --- a/services/core/java/com/android/server/ConnectivityService.java +++ b/services/core/java/com/android/server/ConnectivityService.java @@ -5791,6 +5791,19 @@ public class ConnectivityService extends IConnectivityManager.Stub          return INetd.PERMISSION_NONE;      } +    private void updateNetworkPermissions(@NonNull final NetworkAgentInfo nai, +            @NonNull final NetworkCapabilities newNc) { +        final int oldPermission = getNetworkPermission(nai.networkCapabilities); +        final int newPermission = getNetworkPermission(newNc); +        if (oldPermission != newPermission && nai.created && !nai.isVPN()) { +            try { +                mNMS.setNetworkPermission(nai.network.netId, newPermission); +            } catch (RemoteException e) { +                loge("Exception in setNetworkPermission: " + e); +            } +        } +    } +      /**       * Augments the NetworkCapabilities passed in by a NetworkAgent with capabilities that are       * maintained here that the NetworkAgent is not aware of (e.g., validated, captive portal, @@ -5862,21 +5875,11 @@ public class ConnectivityService extends IConnectivityManager.Stub       * @param nai the network having its capabilities updated.       * @param nc the new network capabilities.       */ -    private void updateCapabilities(int oldScore, NetworkAgentInfo nai, NetworkCapabilities nc) { +    private void updateCapabilities(final int oldScore, @NonNull final NetworkAgentInfo nai, +            @NonNull final NetworkCapabilities nc) {          NetworkCapabilities newNc = mixInCapabilities(nai, nc); -          if (Objects.equals(nai.networkCapabilities, newNc)) return; - -        final int oldPermission = getNetworkPermission(nai.networkCapabilities); -        final int newPermission = getNetworkPermission(newNc); -        if (oldPermission != newPermission && nai.created && !nai.isVPN()) { -            try { -                mNMS.setNetworkPermission(nai.network.netId, newPermission); -            } catch (RemoteException e) { -                loge("Exception in setNetworkPermission: " + e); -            } -        } - +        updateNetworkPermissions(nai, newNc);          final NetworkCapabilities prevNc = nai.getAndSetNetworkCapabilities(newNc);          updateUids(nai, prevNc, newNc); @@ -6241,6 +6244,30 @@ public class ConnectivityService extends IConnectivityManager.Stub          }      } +    // An accumulator class to gather the list of changes that result from a rematch. +    // TODO : enrich to represent an entire set of changes to apply. +    private static class NetworkReassignment { +        static class NetworkBgStatePair { +            @NonNull final NetworkAgentInfo mNetwork; +            final boolean mOldBackground; +            NetworkBgStatePair(@NonNull final NetworkAgentInfo network, +                    final boolean oldBackground) { +                mNetwork = network; +                mOldBackground = oldBackground; +            } +        } + +        @NonNull private final Set<NetworkBgStatePair> mRematchedNetworks = new ArraySet<>(); + +        @NonNull Iterable<NetworkBgStatePair> getRematchedNetworks() { +            return mRematchedNetworks; +        } + +        void addRematchedNetwork(@NonNull final NetworkBgStatePair network) { +            mRematchedNetworks.add(network); +        } +    } +      private ArrayMap<NetworkRequestInfo, NetworkAgentInfo> computeRequestReassignmentForNetwork(              @NonNull final NetworkAgentInfo newNetwork) {          final int score = newNetwork.getCurrentScore(); @@ -6286,8 +6313,8 @@ public class ConnectivityService extends IConnectivityManager.Stub      //   needed. A network is needed if it is the best network for      //   one or more NetworkRequests, or if it is a VPN.      // -    // - Tears down newNetwork if it just became validated -    //   but turns out to be unneeded. +    // - Writes into the passed reassignment object all changes that should be done for +    //   rematching this network with all requests, to be applied later.      //      // NOTE: This function only adds NetworkRequests that "newNetwork" could satisfy,      // it does not remove NetworkRequests that other Networks could better satisfy. @@ -6295,15 +6322,22 @@ public class ConnectivityService extends IConnectivityManager.Stub      // This function should be used when possible instead of {@code rematchAllNetworksAndRequests}      // as it performs better by a factor of the number of Networks.      // +    // TODO : stop writing to the passed reassignment. This is temporarily more useful, but +    // it's unidiomatic Java and it's hard to read. +    // +    // @param changes a currently-building list of changes to write to      // @param newNetwork is the network to be matched against NetworkRequests.      // @param now the time the rematch starts, as returned by SystemClock.elapsedRealtime(); -    private void rematchNetworkAndRequests(NetworkAgentInfo newNetwork, long now) { +    private void rematchNetworkAndRequests(@NonNull final NetworkReassignment changes, +            @NonNull final NetworkAgentInfo newNetwork, final long now) {          ensureRunningOnConnectivityServiceThread();          if (!newNetwork.everConnected) return;          boolean isNewDefault = false;          NetworkAgentInfo oldDefaultNetwork = null; -        final boolean wasBackgroundNetwork = newNetwork.isBackgroundNetwork(); +        changes.addRematchedNetwork(new NetworkReassignment.NetworkBgStatePair(newNetwork, +                newNetwork.isBackgroundNetwork())); +          final int score = newNetwork.getCurrentScore();          if (VDBG || DDBG) log("rematching " + newNetwork.name()); @@ -6406,39 +6440,12 @@ public class ConnectivityService extends IConnectivityManager.Stub          if (newNetwork.getCurrentScore() != score) {              Slog.wtf(TAG, String.format(                      "BUG: %s changed score during rematch: %d -> %d", -                   newNetwork.name(), score, newNetwork.getCurrentScore())); +                    newNetwork.name(), score, newNetwork.getCurrentScore()));          }          // Notify requested networks are available after the default net is switched, but          // before LegacyTypeTracker sends legacy broadcasts          for (NetworkRequestInfo nri : addedRequests) notifyNetworkAvailable(newNetwork, nri); - -        // Finally, process listen requests and update capabilities if the background state has -        // changed for this network. For consistency with previous behavior, send onLost callbacks -        // before onAvailable. -        processNewlyLostListenRequests(newNetwork); - -        // Maybe the network changed background states. Update its capabilities. -        final boolean backgroundChanged = wasBackgroundNetwork != newNetwork.isBackgroundNetwork(); -        if (backgroundChanged) { -            final NetworkCapabilities newNc = mixInCapabilities(newNetwork, -                    newNetwork.networkCapabilities); - -            final int oldPermission = getNetworkPermission(newNetwork.networkCapabilities); -            final int newPermission = getNetworkPermission(newNc); -            if (oldPermission != newPermission) { -                try { -                    mNMS.setNetworkPermission(newNetwork.network.netId, newPermission); -                } catch (RemoteException e) { -                    loge("Exception in setNetworkPermission: " + e); -                } -            } - -            newNetwork.getAndSetNetworkCapabilities(newNc); -            notifyNetworkCallbacks(newNetwork, ConnectivityManager.CALLBACK_CAP_CHANGED); -        } - -        processNewlySatisfiedListenRequests(newNetwork);      }      /** @@ -6460,12 +6467,24 @@ public class ConnectivityService extends IConnectivityManager.Stub          // scoring network and then a higher scoring network, which could produce multiple          // callbacks.          Arrays.sort(nais); +        final NetworkReassignment changes = new NetworkReassignment();          for (final NetworkAgentInfo nai : nais) { -            rematchNetworkAndRequests(nai, now); +            rematchNetworkAndRequests(changes, nai, now);          }          final NetworkAgentInfo newDefaultNetwork = getDefaultNetwork(); +        for (final NetworkReassignment.NetworkBgStatePair event : changes.getRematchedNetworks()) { +            // Process listen requests and update capabilities if the background state has +            // changed for this network. For consistency with previous behavior, send onLost +            // callbacks before onAvailable. +            processNewlyLostListenRequests(event.mNetwork); +            if (event.mOldBackground != event.mNetwork.isBackgroundNetwork()) { +                applyBackgroundChangeForRematch(event.mNetwork); +            } +            processNewlySatisfiedListenRequests(event.mNetwork); +        } +          for (final NetworkAgentInfo nai : nais) {              // Rematching may have altered the linger state of some networks, so update all linger              // timers. updateLingerState reads the state from the network agent and does nothing @@ -6497,6 +6516,24 @@ public class ConnectivityService extends IConnectivityManager.Stub          }      } +    /** +     * Apply a change in background state resulting from rematching networks with requests. +     * +     * During rematch, a network may change background states by starting to satisfy or stopping +     * to satisfy a foreground request. Listens don't count for this. When a network changes +     * background states, its capabilities need to be updated and callbacks fired for the +     * capability change. +     * +     * @param nai The network that changed background states +     */ +    private void applyBackgroundChangeForRematch(@NonNull final NetworkAgentInfo nai) { +        final NetworkCapabilities newNc = mixInCapabilities(nai, nai.networkCapabilities); +        if (Objects.equals(nai.networkCapabilities, newNc)) return; +        updateNetworkPermissions(nai, newNc); +        nai.getAndSetNetworkCapabilities(newNc); +        notifyNetworkCallbacks(nai, ConnectivityManager.CALLBACK_CAP_CHANGED); +    } +      private void updateLegacyTypeTrackerAndVpnLockdownForRematch(              @Nullable final NetworkAgentInfo oldDefaultNetwork,              @Nullable final NetworkAgentInfo newDefaultNetwork,  |