Loading core/java/android/net/ConnectivityManager.java +20 −4 Original line number Diff line number Diff line Loading @@ -3158,11 +3158,11 @@ public class ConnectivityManager { } } /** {@hide} */ /** {@hide} - returns the factory serial number */ @UnsupportedAppUsage public void registerNetworkFactory(Messenger messenger, String name) { public int registerNetworkFactory(Messenger messenger, String name) { try { mService.registerNetworkFactory(messenger, name); return mService.registerNetworkFactory(messenger, name); } catch (RemoteException e) { throw e.rethrowFromSystemServer(); } Loading @@ -3178,6 +3178,10 @@ public class ConnectivityManager { } } // TODO : remove this method. It is a stopgap measure to help sheperding a number // of dependent changes that would conflict throughout the automerger graph. Having this // temporarily helps with the process of going through with all these dependent changes across // the entire tree. /** * @hide * Register a NetworkAgent with ConnectivityService. Loading @@ -3185,8 +3189,20 @@ public class ConnectivityManager { */ public int registerNetworkAgent(Messenger messenger, NetworkInfo ni, LinkProperties lp, NetworkCapabilities nc, int score, NetworkMisc misc) { return registerNetworkAgent(messenger, ni, lp, nc, score, misc, NetworkFactory.SerialNumber.NONE); } /** * @hide * Register a NetworkAgent with ConnectivityService. * @return NetID corresponding to NetworkAgent. */ public int registerNetworkAgent(Messenger messenger, NetworkInfo ni, LinkProperties lp, NetworkCapabilities nc, int score, NetworkMisc misc, int factorySerialNumber) { try { return mService.registerNetworkAgent(messenger, ni, lp, nc, score, misc); return mService.registerNetworkAgent(messenger, ni, lp, nc, score, misc, factorySerialNumber); } catch (RemoteException e) { throw e.rethrowFromSystemServer(); } Loading core/java/android/net/IConnectivityManager.aidl +2 −2 Original line number Diff line number Diff line Loading @@ -150,14 +150,14 @@ interface IConnectivityManager void setAirplaneMode(boolean enable); void registerNetworkFactory(in Messenger messenger, in String name); int registerNetworkFactory(in Messenger messenger, in String name); boolean requestBandwidthUpdate(in Network network); void unregisterNetworkFactory(in Messenger messenger); int registerNetworkAgent(in Messenger messenger, in NetworkInfo ni, in LinkProperties lp, in NetworkCapabilities nc, int score, in NetworkMisc misc); in NetworkCapabilities nc, int score, in NetworkMisc misc, in int factorySerialNumber); NetworkRequest requestNetwork(in NetworkCapabilities networkCapabilities, in Messenger messenger, int timeoutSec, in IBinder binder, int legacy); Loading core/java/android/net/NetworkAgent.java +20 −3 Original line number Diff line number Diff line Loading @@ -57,6 +57,7 @@ public abstract class NetworkAgent extends Handler { private static final long BW_REFRESH_MIN_WIN_MS = 500; private boolean mPollLceScheduled = false; private AtomicBoolean mPollLcePending = new AtomicBoolean(false); public final int mFactorySerialNumber; private static final int BASE = Protocol.BASE_NETWORK_AGENT; Loading Loading @@ -212,16 +213,31 @@ public abstract class NetworkAgent extends Handler { */ public static final int CMD_PREVENT_AUTOMATIC_RECONNECT = BASE + 15; // TODO : remove these two constructors. They are a stopgap measure to help sheperding a number // of dependent changes that would conflict throughout the automerger graph. Having these // temporarily helps with the process of going through with all these dependent changes across // the entire tree. public NetworkAgent(Looper looper, Context context, String logTag, NetworkInfo ni, NetworkCapabilities nc, LinkProperties lp, int score) { this(looper, context, logTag, ni, nc, lp, score, null); this(looper, context, logTag, ni, nc, lp, score, null, NetworkFactory.SerialNumber.NONE); } public NetworkAgent(Looper looper, Context context, String logTag, NetworkInfo ni, NetworkCapabilities nc, LinkProperties lp, int score, NetworkMisc misc) { this(looper, context, logTag, ni, nc, lp, score, misc, NetworkFactory.SerialNumber.NONE); } public NetworkAgent(Looper looper, Context context, String logTag, NetworkInfo ni, NetworkCapabilities nc, LinkProperties lp, int score, int factorySerialNumber) { this(looper, context, logTag, ni, nc, lp, score, null, factorySerialNumber); } public NetworkAgent(Looper looper, Context context, String logTag, NetworkInfo ni, NetworkCapabilities nc, LinkProperties lp, int score, NetworkMisc misc, int factorySerialNumber) { super(looper); LOG_TAG = logTag; mContext = context; mFactorySerialNumber = factorySerialNumber; if (ni == null || nc == null || lp == null) { throw new IllegalArgumentException(); } Loading @@ -230,7 +246,8 @@ public abstract class NetworkAgent extends Handler { ConnectivityManager cm = (ConnectivityManager)mContext.getSystemService( Context.CONNECTIVITY_SERVICE); netId = cm.registerNetworkAgent(new Messenger(this), new NetworkInfo(ni), new LinkProperties(lp), new NetworkCapabilities(nc), score, misc); new LinkProperties(lp), new NetworkCapabilities(nc), score, misc, factorySerialNumber); } @Override Loading core/java/android/net/NetworkFactory.java +112 −29 Original line number Diff line number Diff line Loading @@ -34,6 +34,7 @@ import com.android.internal.util.Protocol; import java.io.FileDescriptor; import java.io.PrintWriter; import java.util.ArrayList; import java.util.concurrent.atomic.AtomicInteger; /** * A NetworkFactory is an entity that creates NetworkAgent objects. Loading @@ -51,6 +52,20 @@ import java.util.ArrayList; * @hide **/ public class NetworkFactory extends Handler { /** @hide */ public static class SerialNumber { // Guard used by no network factory. public static final int NONE = -1; // A hardcoded serial number for NetworkAgents representing VPNs. These agents are // not created by any factory, so they use this constant for clarity instead of NONE. public static final int VPN = -2; private static final AtomicInteger sNetworkFactorySerialNumber = new AtomicInteger(1); /** Returns a unique serial number for a factory. */ public static final int nextSerialNumber() { return sNetworkFactorySerialNumber.getAndIncrement(); } } private static final boolean DBG = true; private static final boolean VDBG = false; Loading @@ -66,7 +81,7 @@ public class NetworkFactory extends Handler { * disregard any that it will never be able to service, for example * those requiring a different bearer. * msg.obj = NetworkRequest * msg.arg1 = score - the score of the any network currently satisfying this * msg.arg1 = score - the score of the network currently satisfying this * request. If this bearer knows in advance it cannot * exceed this score it should not try to connect, holding the request * for the future. Loading @@ -76,6 +91,8 @@ public class NetworkFactory extends Handler { * with the same NetworkRequest but an updated score. * Also, network conditions may change for this bearer * allowing for a better score in the future. * msg.arg2 = the serial number of the factory currently responsible for the * NetworkAgent handling this request, or SerialNumber.NONE if none. */ public static final int CMD_REQUEST_NETWORK = BASE; Loading Loading @@ -118,6 +135,7 @@ public class NetworkFactory extends Handler { private int mRefCount = 0; private Messenger mMessenger = null; private int mSerialNumber; @UnsupportedAppUsage public NetworkFactory(Looper looper, Context context, String logTag, Loading @@ -132,7 +150,8 @@ public class NetworkFactory extends Handler { if (DBG) log("Registering NetworkFactory"); if (mMessenger == null) { mMessenger = new Messenger(this); ConnectivityManager.from(mContext).registerNetworkFactory(mMessenger, LOG_TAG); mSerialNumber = ConnectivityManager.from(mContext).registerNetworkFactory(mMessenger, LOG_TAG); } } Loading Loading @@ -178,7 +197,7 @@ public class NetworkFactory extends Handler { break; } case CMD_REQUEST_NETWORK: { handleAddRequest((NetworkRequest)msg.obj, msg.arg1); handleAddRequest((NetworkRequest) msg.obj, msg.arg1, msg.arg2); break; } case CMD_CANCEL_REQUEST: { Loading @@ -200,11 +219,13 @@ public class NetworkFactory extends Handler { public final NetworkRequest request; public int score; public boolean requested; // do we have a request outstanding, limited by score public int factorySerialNumber; public NetworkRequestInfo(NetworkRequest request, int score) { NetworkRequestInfo(NetworkRequest request, int score, int factorySerialNumber) { this.request = request; this.score = score; this.requested = false; this.factorySerialNumber = factorySerialNumber; } @Override Loading @@ -213,16 +234,51 @@ public class NetworkFactory extends Handler { } } /** * Add a NetworkRequest that the bearer may want to attempt to satisfy. * @see #CMD_REQUEST_NETWORK * * @param request the request to handle. * @param score the score of the NetworkAgent currently satisfying this request. * @param servingFactorySerialNumber the serial number of the NetworkFactory that * created the NetworkAgent currently satisfying this request. */ // TODO : remove this method. It is a stopgap measure to help sheperding a number // of dependent changes that would conflict throughout the automerger graph. Having this // temporarily helps with the process of going through with all these dependent changes across // the entire tree. @VisibleForTesting protected void handleAddRequest(NetworkRequest request, int score) { handleAddRequest(request, score, SerialNumber.NONE); } /** * Add a NetworkRequest that the bearer may want to attempt to satisfy. * @see #CMD_REQUEST_NETWORK * * @param request the request to handle. * @param score the score of the NetworkAgent currently satisfying this request. * @param servingFactorySerialNumber the serial number of the NetworkFactory that * created the NetworkAgent currently satisfying this request. */ @VisibleForTesting protected void handleAddRequest(NetworkRequest request, int score, int servingFactorySerialNumber) { NetworkRequestInfo n = mNetworkRequests.get(request.requestId); if (n == null) { if (DBG) log("got request " + request + " with score " + score); n = new NetworkRequestInfo(request, score); if (DBG) { log("got request " + request + " with score " + score + " and serial " + servingFactorySerialNumber); } n = new NetworkRequestInfo(request, score, servingFactorySerialNumber); mNetworkRequests.put(n.request.requestId, n); } else { if (VDBG) log("new score " + score + " for exisiting request " + request); if (VDBG) { log("new score " + score + " for exisiting request " + request + " with serial " + servingFactorySerialNumber); } n.score = score; n.factorySerialNumber = servingFactorySerialNumber; } if (VDBG) log(" my score=" + mScore + ", my filter=" + mCapabilityFilter); Loading Loading @@ -272,16 +328,19 @@ public class NetworkFactory extends Handler { } private void evalRequest(NetworkRequestInfo n) { if (VDBG) log("evalRequest"); if (n.requested == false && n.score < mScore && n.request.networkCapabilities.satisfiedByNetworkCapabilities( mCapabilityFilter) && acceptRequest(n.request, n.score)) { if (VDBG) { log("evalRequest"); log(" n.requests = " + n.requested); log(" n.score = " + n.score); log(" mScore = " + mScore); log(" n.factorySerialNumber = " + n.factorySerialNumber); log(" mSerialNumber = " + mSerialNumber); } if (shouldNeedNetworkFor(n)) { if (VDBG) log(" needNetworkFor"); needNetworkFor(n.request, n.score); n.requested = true; } else if (n.requested == true && (n.score > mScore || n.request.networkCapabilities.satisfiedByNetworkCapabilities( mCapabilityFilter) == false || acceptRequest(n.request, n.score) == false)) { } else if (shouldReleaseNetworkFor(n)) { if (VDBG) log(" releaseNetworkFor"); releaseNetworkFor(n.request); n.requested = false; Loading @@ -290,10 +349,39 @@ public class NetworkFactory extends Handler { } } private boolean shouldNeedNetworkFor(NetworkRequestInfo n) { // If this request is already tracked, it doesn't qualify for need return !n.requested // If the score of this request is higher or equal to that of this factory and some // other factory is responsible for it, then this factory should not track the request // because it has no hope of satisfying it. && (n.score < mScore || n.factorySerialNumber == mSerialNumber) // If this factory can't satisfy the capability needs of this request, then it // should not be tracked. && n.request.networkCapabilities.satisfiedByNetworkCapabilities(mCapabilityFilter) // Finally if the concrete implementation of the factory rejects the request, then // don't track it. && acceptRequest(n.request, n.score); } private boolean shouldReleaseNetworkFor(NetworkRequestInfo n) { // Don't release a request that's not tracked. return n.requested // The request should be released if it can't be satisfied by this factory. That // means either of the following conditions are met : // - Its score is too high to be satisfied by this factory and it's not already // assigned to the factory // - This factory can't satisfy the capability needs of the request // - The concrete implementation of the factory rejects the request && ((n.score > mScore && n.factorySerialNumber != mSerialNumber) || !n.request.networkCapabilities.satisfiedByNetworkCapabilities( mCapabilityFilter) || !acceptRequest(n.request, n.score)); } private void evalRequests() { for (int i = 0; i < mNetworkRequests.size(); i++) { NetworkRequestInfo n = mNetworkRequests.valueAt(i); evalRequest(n); } } Loading Loading @@ -342,16 +430,6 @@ public class NetworkFactory extends Handler { if (--mRefCount == 0) stopNetwork(); } public void addNetworkRequest(NetworkRequest networkRequest, int score) { sendMessage(obtainMessage(CMD_REQUEST_NETWORK, new NetworkRequestInfo(networkRequest, score))); } public void removeNetworkRequest(NetworkRequest networkRequest) { sendMessage(obtainMessage(CMD_CANCEL_REQUEST, networkRequest)); } @UnsupportedAppUsage(maxTargetSdk = Build.VERSION_CODES.P, trackingBug = 115609023) public void setScoreFilter(int score) { sendMessage(obtainMessage(CMD_SET_SCORE, score, 0)); Loading @@ -366,6 +444,10 @@ public class NetworkFactory extends Handler { return mNetworkRequests.size(); } public int getSerialNumber() { return mSerialNumber; } protected void log(String s) { Log.d(LOG_TAG, s); } Loading @@ -383,10 +465,11 @@ public class NetworkFactory extends Handler { @Override public String toString() { StringBuilder sb = new StringBuilder("{").append(LOG_TAG).append(" - ScoreFilter="). append(mScore).append(", Filter=").append(mCapabilityFilter).append(", requests="). append(mNetworkRequests.size()).append(", refCount=").append(mRefCount). append("}"); StringBuilder sb = new StringBuilder("{").append(LOG_TAG).append(" - mSerialNumber=") .append(mSerialNumber).append(", ScoreFilter=") .append(mScore).append(", Filter=").append(mCapabilityFilter).append(", requests=") .append(mNetworkRequests.size()).append(", refCount=").append(mRefCount) .append("}"); return sb.toString(); } } services/core/java/com/android/server/ConnectivityService.java +62 −14 Original line number Diff line number Diff line Loading @@ -84,6 +84,7 @@ import android.net.Network; import android.net.NetworkAgent; import android.net.NetworkCapabilities; import android.net.NetworkConfig; import android.net.NetworkFactory; import android.net.NetworkInfo; import android.net.NetworkInfo.DetailedState; import android.net.NetworkMisc; Loading Loading @@ -2892,8 +2893,17 @@ public class ConnectivityService extends IConnectivityManager.Stub for (NetworkRequestInfo nri : mNetworkRequests.values()) { if (nri.request.isListen()) continue; NetworkAgentInfo nai = getNetworkForRequest(nri.request.requestId); ac.sendMessage(android.net.NetworkFactory.CMD_REQUEST_NETWORK, (nai != null ? nai.getCurrentScore() : 0), 0, nri.request); final int score; final int serial; if (nai != null) { score = nai.getCurrentScore(); serial = nai.factorySerialNumber; } else { score = 0; serial = NetworkFactory.SerialNumber.NONE; } ac.sendMessage(android.net.NetworkFactory.CMD_REQUEST_NETWORK, score, serial, nri.request); } } else { loge("Error connecting NetworkFactory"); Loading Loading @@ -2991,7 +3001,7 @@ public class ConnectivityService extends IConnectivityManager.Stub NetworkAgentInfo currentNetwork = getNetworkForRequest(request.requestId); if (currentNetwork != null && currentNetwork.network.netId == nai.network.netId) { clearNetworkForRequest(request.requestId); sendUpdatedScoreToFactories(request, 0); sendUpdatedScoreToFactories(request, null); } } nai.clearLingerState(); Loading Loading @@ -3068,7 +3078,7 @@ public class ConnectivityService extends IConnectivityManager.Stub } rematchAllNetworksAndRequests(null, 0); if (nri.request.isRequest() && getNetworkForRequest(nri.request.requestId) == null) { sendUpdatedScoreToFactories(nri.request, 0); sendUpdatedScoreToFactories(nri.request, null); } } Loading Loading @@ -4843,11 +4853,14 @@ public class ConnectivityService extends IConnectivityManager.Stub public final String name; public final Messenger messenger; public final AsyncChannel asyncChannel; public final int factorySerialNumber; public NetworkFactoryInfo(String name, Messenger messenger, AsyncChannel asyncChannel) { NetworkFactoryInfo(String name, Messenger messenger, AsyncChannel asyncChannel, int factorySerialNumber) { this.name = name; this.messenger = messenger; this.asyncChannel = asyncChannel; this.factorySerialNumber = factorySerialNumber; } } Loading Loading @@ -5208,10 +5221,12 @@ public class ConnectivityService extends IConnectivityManager.Stub } @Override public void registerNetworkFactory(Messenger messenger, String name) { public int registerNetworkFactory(Messenger messenger, String name) { enforceConnectivityInternalPermission(); NetworkFactoryInfo nfi = new NetworkFactoryInfo(name, messenger, new AsyncChannel()); NetworkFactoryInfo nfi = new NetworkFactoryInfo(name, messenger, new AsyncChannel(), NetworkFactory.SerialNumber.nextSerialNumber()); mHandler.sendMessage(mHandler.obtainMessage(EVENT_REGISTER_NETWORK_FACTORY, nfi)); return nfi.factorySerialNumber; } private void handleRegisterNetworkFactory(NetworkFactoryInfo nfi) { Loading Loading @@ -5316,9 +5331,35 @@ public class ConnectivityService extends IConnectivityManager.Stub return nri.request.requestId == mDefaultRequest.requestId; } // TODO : remove this method. It's a stopgap measure to help sheperding a number of dependent // changes that would conflict throughout the automerger graph. Having this method temporarily // helps with the process of going through with all these dependent changes across the entire // tree. public int registerNetworkAgent(Messenger messenger, NetworkInfo networkInfo, LinkProperties linkProperties, NetworkCapabilities networkCapabilities, int currentScore, NetworkMisc networkMisc) { return registerNetworkAgent(messenger, networkInfo, linkProperties, networkCapabilities, currentScore, networkMisc, NetworkFactory.SerialNumber.NONE); } /** * Register a new agent with ConnectivityService to handle a network. * * @param messenger a messenger for ConnectivityService to contact the agent asynchronously. * @param networkInfo the initial info associated with this network. It can be updated later : * see {@link #updateNetworkInfo}. * @param linkProperties the initial link properties of this network. They can be updated * later : see {@link #updateLinkProperties}. * @param networkCapabilities the initial capabilites of this network. They can be updated * later : see {@link #updateNetworkCapabilities}. * @param currentScore the initial score of the network. See * {@link NetworkAgentInfo#getCurrentScore}. * @param networkMisc metadata about the network. This is never updated. * @param factorySerialNumber the serial number of the factory owning this NetworkAgent. */ public int registerNetworkAgent(Messenger messenger, NetworkInfo networkInfo, LinkProperties linkProperties, NetworkCapabilities networkCapabilities, int currentScore, NetworkMisc networkMisc, int factorySerialNumber) { enforceConnectivityInternalPermission(); LinkProperties lp = new LinkProperties(linkProperties); Loading @@ -5328,7 +5369,8 @@ public class ConnectivityService extends IConnectivityManager.Stub final NetworkCapabilities nc = new NetworkCapabilities(networkCapabilities); final NetworkAgentInfo nai = new NetworkAgentInfo(messenger, new AsyncChannel(), new Network(reserveNetId()), new NetworkInfo(networkInfo), lp, nc, currentScore, mContext, mTrackerHandler, new NetworkMisc(networkMisc), this, mNetd, mNMS); mContext, mTrackerHandler, new NetworkMisc(networkMisc), this, mNetd, mNMS, factorySerialNumber); // Make sure the network capabilities reflect what the agent info says. nai.networkCapabilities = mixInCapabilities(nai, nc); final String extraInfo = networkInfo.getExtraInfo(); Loading Loading @@ -5755,17 +5797,23 @@ public class ConnectivityService extends IConnectivityManager.Stub NetworkRequest nr = nai.requestAt(i); // Don't send listening requests to factories. b/17393458 if (nr.isListen()) continue; sendUpdatedScoreToFactories(nr, nai.getCurrentScore()); sendUpdatedScoreToFactories(nr, nai); } } private void sendUpdatedScoreToFactories(NetworkRequest networkRequest, int score) { private void sendUpdatedScoreToFactories(NetworkRequest networkRequest, NetworkAgentInfo nai) { int score = 0; int serial = 0; if (nai != null) { score = nai.getCurrentScore(); serial = nai.factorySerialNumber; } if (VDBG || DDBG){ log("sending new Min Network Score(" + score + "): " + networkRequest.toString()); } for (NetworkFactoryInfo nfi : mNetworkFactoryInfos.values()) { nfi.asyncChannel.sendMessage(android.net.NetworkFactory.CMD_REQUEST_NETWORK, score, 0, networkRequest); nfi.asyncChannel.sendMessage(android.net.NetworkFactory.CMD_REQUEST_NETWORK, score, serial, networkRequest); } } Loading Loading @@ -6043,7 +6091,7 @@ public class ConnectivityService extends IConnectivityManager.Stub // TODO - this could get expensive if we have a lot of requests for this // network. Think about if there is a way to reduce this. Push // netid->request mapping to each factory? sendUpdatedScoreToFactories(nri.request, score); sendUpdatedScoreToFactories(nri.request, newNetwork); if (isDefaultRequest(nri)) { isNewDefault = true; oldDefaultNetwork = currentNetwork; Loading @@ -6067,7 +6115,7 @@ public class ConnectivityService extends IConnectivityManager.Stub newNetwork.removeRequest(nri.request.requestId); if (currentNetwork == newNetwork) { clearNetworkForRequest(nri.request.requestId); sendUpdatedScoreToFactories(nri.request, 0); sendUpdatedScoreToFactories(nri.request, null); } else { Slog.wtf(TAG, "BUG: Removing request " + nri.request.requestId + " from " + newNetwork.name() + Loading Loading
core/java/android/net/ConnectivityManager.java +20 −4 Original line number Diff line number Diff line Loading @@ -3158,11 +3158,11 @@ public class ConnectivityManager { } } /** {@hide} */ /** {@hide} - returns the factory serial number */ @UnsupportedAppUsage public void registerNetworkFactory(Messenger messenger, String name) { public int registerNetworkFactory(Messenger messenger, String name) { try { mService.registerNetworkFactory(messenger, name); return mService.registerNetworkFactory(messenger, name); } catch (RemoteException e) { throw e.rethrowFromSystemServer(); } Loading @@ -3178,6 +3178,10 @@ public class ConnectivityManager { } } // TODO : remove this method. It is a stopgap measure to help sheperding a number // of dependent changes that would conflict throughout the automerger graph. Having this // temporarily helps with the process of going through with all these dependent changes across // the entire tree. /** * @hide * Register a NetworkAgent with ConnectivityService. Loading @@ -3185,8 +3189,20 @@ public class ConnectivityManager { */ public int registerNetworkAgent(Messenger messenger, NetworkInfo ni, LinkProperties lp, NetworkCapabilities nc, int score, NetworkMisc misc) { return registerNetworkAgent(messenger, ni, lp, nc, score, misc, NetworkFactory.SerialNumber.NONE); } /** * @hide * Register a NetworkAgent with ConnectivityService. * @return NetID corresponding to NetworkAgent. */ public int registerNetworkAgent(Messenger messenger, NetworkInfo ni, LinkProperties lp, NetworkCapabilities nc, int score, NetworkMisc misc, int factorySerialNumber) { try { return mService.registerNetworkAgent(messenger, ni, lp, nc, score, misc); return mService.registerNetworkAgent(messenger, ni, lp, nc, score, misc, factorySerialNumber); } catch (RemoteException e) { throw e.rethrowFromSystemServer(); } Loading
core/java/android/net/IConnectivityManager.aidl +2 −2 Original line number Diff line number Diff line Loading @@ -150,14 +150,14 @@ interface IConnectivityManager void setAirplaneMode(boolean enable); void registerNetworkFactory(in Messenger messenger, in String name); int registerNetworkFactory(in Messenger messenger, in String name); boolean requestBandwidthUpdate(in Network network); void unregisterNetworkFactory(in Messenger messenger); int registerNetworkAgent(in Messenger messenger, in NetworkInfo ni, in LinkProperties lp, in NetworkCapabilities nc, int score, in NetworkMisc misc); in NetworkCapabilities nc, int score, in NetworkMisc misc, in int factorySerialNumber); NetworkRequest requestNetwork(in NetworkCapabilities networkCapabilities, in Messenger messenger, int timeoutSec, in IBinder binder, int legacy); Loading
core/java/android/net/NetworkAgent.java +20 −3 Original line number Diff line number Diff line Loading @@ -57,6 +57,7 @@ public abstract class NetworkAgent extends Handler { private static final long BW_REFRESH_MIN_WIN_MS = 500; private boolean mPollLceScheduled = false; private AtomicBoolean mPollLcePending = new AtomicBoolean(false); public final int mFactorySerialNumber; private static final int BASE = Protocol.BASE_NETWORK_AGENT; Loading Loading @@ -212,16 +213,31 @@ public abstract class NetworkAgent extends Handler { */ public static final int CMD_PREVENT_AUTOMATIC_RECONNECT = BASE + 15; // TODO : remove these two constructors. They are a stopgap measure to help sheperding a number // of dependent changes that would conflict throughout the automerger graph. Having these // temporarily helps with the process of going through with all these dependent changes across // the entire tree. public NetworkAgent(Looper looper, Context context, String logTag, NetworkInfo ni, NetworkCapabilities nc, LinkProperties lp, int score) { this(looper, context, logTag, ni, nc, lp, score, null); this(looper, context, logTag, ni, nc, lp, score, null, NetworkFactory.SerialNumber.NONE); } public NetworkAgent(Looper looper, Context context, String logTag, NetworkInfo ni, NetworkCapabilities nc, LinkProperties lp, int score, NetworkMisc misc) { this(looper, context, logTag, ni, nc, lp, score, misc, NetworkFactory.SerialNumber.NONE); } public NetworkAgent(Looper looper, Context context, String logTag, NetworkInfo ni, NetworkCapabilities nc, LinkProperties lp, int score, int factorySerialNumber) { this(looper, context, logTag, ni, nc, lp, score, null, factorySerialNumber); } public NetworkAgent(Looper looper, Context context, String logTag, NetworkInfo ni, NetworkCapabilities nc, LinkProperties lp, int score, NetworkMisc misc, int factorySerialNumber) { super(looper); LOG_TAG = logTag; mContext = context; mFactorySerialNumber = factorySerialNumber; if (ni == null || nc == null || lp == null) { throw new IllegalArgumentException(); } Loading @@ -230,7 +246,8 @@ public abstract class NetworkAgent extends Handler { ConnectivityManager cm = (ConnectivityManager)mContext.getSystemService( Context.CONNECTIVITY_SERVICE); netId = cm.registerNetworkAgent(new Messenger(this), new NetworkInfo(ni), new LinkProperties(lp), new NetworkCapabilities(nc), score, misc); new LinkProperties(lp), new NetworkCapabilities(nc), score, misc, factorySerialNumber); } @Override Loading
core/java/android/net/NetworkFactory.java +112 −29 Original line number Diff line number Diff line Loading @@ -34,6 +34,7 @@ import com.android.internal.util.Protocol; import java.io.FileDescriptor; import java.io.PrintWriter; import java.util.ArrayList; import java.util.concurrent.atomic.AtomicInteger; /** * A NetworkFactory is an entity that creates NetworkAgent objects. Loading @@ -51,6 +52,20 @@ import java.util.ArrayList; * @hide **/ public class NetworkFactory extends Handler { /** @hide */ public static class SerialNumber { // Guard used by no network factory. public static final int NONE = -1; // A hardcoded serial number for NetworkAgents representing VPNs. These agents are // not created by any factory, so they use this constant for clarity instead of NONE. public static final int VPN = -2; private static final AtomicInteger sNetworkFactorySerialNumber = new AtomicInteger(1); /** Returns a unique serial number for a factory. */ public static final int nextSerialNumber() { return sNetworkFactorySerialNumber.getAndIncrement(); } } private static final boolean DBG = true; private static final boolean VDBG = false; Loading @@ -66,7 +81,7 @@ public class NetworkFactory extends Handler { * disregard any that it will never be able to service, for example * those requiring a different bearer. * msg.obj = NetworkRequest * msg.arg1 = score - the score of the any network currently satisfying this * msg.arg1 = score - the score of the network currently satisfying this * request. If this bearer knows in advance it cannot * exceed this score it should not try to connect, holding the request * for the future. Loading @@ -76,6 +91,8 @@ public class NetworkFactory extends Handler { * with the same NetworkRequest but an updated score. * Also, network conditions may change for this bearer * allowing for a better score in the future. * msg.arg2 = the serial number of the factory currently responsible for the * NetworkAgent handling this request, or SerialNumber.NONE if none. */ public static final int CMD_REQUEST_NETWORK = BASE; Loading Loading @@ -118,6 +135,7 @@ public class NetworkFactory extends Handler { private int mRefCount = 0; private Messenger mMessenger = null; private int mSerialNumber; @UnsupportedAppUsage public NetworkFactory(Looper looper, Context context, String logTag, Loading @@ -132,7 +150,8 @@ public class NetworkFactory extends Handler { if (DBG) log("Registering NetworkFactory"); if (mMessenger == null) { mMessenger = new Messenger(this); ConnectivityManager.from(mContext).registerNetworkFactory(mMessenger, LOG_TAG); mSerialNumber = ConnectivityManager.from(mContext).registerNetworkFactory(mMessenger, LOG_TAG); } } Loading Loading @@ -178,7 +197,7 @@ public class NetworkFactory extends Handler { break; } case CMD_REQUEST_NETWORK: { handleAddRequest((NetworkRequest)msg.obj, msg.arg1); handleAddRequest((NetworkRequest) msg.obj, msg.arg1, msg.arg2); break; } case CMD_CANCEL_REQUEST: { Loading @@ -200,11 +219,13 @@ public class NetworkFactory extends Handler { public final NetworkRequest request; public int score; public boolean requested; // do we have a request outstanding, limited by score public int factorySerialNumber; public NetworkRequestInfo(NetworkRequest request, int score) { NetworkRequestInfo(NetworkRequest request, int score, int factorySerialNumber) { this.request = request; this.score = score; this.requested = false; this.factorySerialNumber = factorySerialNumber; } @Override Loading @@ -213,16 +234,51 @@ public class NetworkFactory extends Handler { } } /** * Add a NetworkRequest that the bearer may want to attempt to satisfy. * @see #CMD_REQUEST_NETWORK * * @param request the request to handle. * @param score the score of the NetworkAgent currently satisfying this request. * @param servingFactorySerialNumber the serial number of the NetworkFactory that * created the NetworkAgent currently satisfying this request. */ // TODO : remove this method. It is a stopgap measure to help sheperding a number // of dependent changes that would conflict throughout the automerger graph. Having this // temporarily helps with the process of going through with all these dependent changes across // the entire tree. @VisibleForTesting protected void handleAddRequest(NetworkRequest request, int score) { handleAddRequest(request, score, SerialNumber.NONE); } /** * Add a NetworkRequest that the bearer may want to attempt to satisfy. * @see #CMD_REQUEST_NETWORK * * @param request the request to handle. * @param score the score of the NetworkAgent currently satisfying this request. * @param servingFactorySerialNumber the serial number of the NetworkFactory that * created the NetworkAgent currently satisfying this request. */ @VisibleForTesting protected void handleAddRequest(NetworkRequest request, int score, int servingFactorySerialNumber) { NetworkRequestInfo n = mNetworkRequests.get(request.requestId); if (n == null) { if (DBG) log("got request " + request + " with score " + score); n = new NetworkRequestInfo(request, score); if (DBG) { log("got request " + request + " with score " + score + " and serial " + servingFactorySerialNumber); } n = new NetworkRequestInfo(request, score, servingFactorySerialNumber); mNetworkRequests.put(n.request.requestId, n); } else { if (VDBG) log("new score " + score + " for exisiting request " + request); if (VDBG) { log("new score " + score + " for exisiting request " + request + " with serial " + servingFactorySerialNumber); } n.score = score; n.factorySerialNumber = servingFactorySerialNumber; } if (VDBG) log(" my score=" + mScore + ", my filter=" + mCapabilityFilter); Loading Loading @@ -272,16 +328,19 @@ public class NetworkFactory extends Handler { } private void evalRequest(NetworkRequestInfo n) { if (VDBG) log("evalRequest"); if (n.requested == false && n.score < mScore && n.request.networkCapabilities.satisfiedByNetworkCapabilities( mCapabilityFilter) && acceptRequest(n.request, n.score)) { if (VDBG) { log("evalRequest"); log(" n.requests = " + n.requested); log(" n.score = " + n.score); log(" mScore = " + mScore); log(" n.factorySerialNumber = " + n.factorySerialNumber); log(" mSerialNumber = " + mSerialNumber); } if (shouldNeedNetworkFor(n)) { if (VDBG) log(" needNetworkFor"); needNetworkFor(n.request, n.score); n.requested = true; } else if (n.requested == true && (n.score > mScore || n.request.networkCapabilities.satisfiedByNetworkCapabilities( mCapabilityFilter) == false || acceptRequest(n.request, n.score) == false)) { } else if (shouldReleaseNetworkFor(n)) { if (VDBG) log(" releaseNetworkFor"); releaseNetworkFor(n.request); n.requested = false; Loading @@ -290,10 +349,39 @@ public class NetworkFactory extends Handler { } } private boolean shouldNeedNetworkFor(NetworkRequestInfo n) { // If this request is already tracked, it doesn't qualify for need return !n.requested // If the score of this request is higher or equal to that of this factory and some // other factory is responsible for it, then this factory should not track the request // because it has no hope of satisfying it. && (n.score < mScore || n.factorySerialNumber == mSerialNumber) // If this factory can't satisfy the capability needs of this request, then it // should not be tracked. && n.request.networkCapabilities.satisfiedByNetworkCapabilities(mCapabilityFilter) // Finally if the concrete implementation of the factory rejects the request, then // don't track it. && acceptRequest(n.request, n.score); } private boolean shouldReleaseNetworkFor(NetworkRequestInfo n) { // Don't release a request that's not tracked. return n.requested // The request should be released if it can't be satisfied by this factory. That // means either of the following conditions are met : // - Its score is too high to be satisfied by this factory and it's not already // assigned to the factory // - This factory can't satisfy the capability needs of the request // - The concrete implementation of the factory rejects the request && ((n.score > mScore && n.factorySerialNumber != mSerialNumber) || !n.request.networkCapabilities.satisfiedByNetworkCapabilities( mCapabilityFilter) || !acceptRequest(n.request, n.score)); } private void evalRequests() { for (int i = 0; i < mNetworkRequests.size(); i++) { NetworkRequestInfo n = mNetworkRequests.valueAt(i); evalRequest(n); } } Loading Loading @@ -342,16 +430,6 @@ public class NetworkFactory extends Handler { if (--mRefCount == 0) stopNetwork(); } public void addNetworkRequest(NetworkRequest networkRequest, int score) { sendMessage(obtainMessage(CMD_REQUEST_NETWORK, new NetworkRequestInfo(networkRequest, score))); } public void removeNetworkRequest(NetworkRequest networkRequest) { sendMessage(obtainMessage(CMD_CANCEL_REQUEST, networkRequest)); } @UnsupportedAppUsage(maxTargetSdk = Build.VERSION_CODES.P, trackingBug = 115609023) public void setScoreFilter(int score) { sendMessage(obtainMessage(CMD_SET_SCORE, score, 0)); Loading @@ -366,6 +444,10 @@ public class NetworkFactory extends Handler { return mNetworkRequests.size(); } public int getSerialNumber() { return mSerialNumber; } protected void log(String s) { Log.d(LOG_TAG, s); } Loading @@ -383,10 +465,11 @@ public class NetworkFactory extends Handler { @Override public String toString() { StringBuilder sb = new StringBuilder("{").append(LOG_TAG).append(" - ScoreFilter="). append(mScore).append(", Filter=").append(mCapabilityFilter).append(", requests="). append(mNetworkRequests.size()).append(", refCount=").append(mRefCount). append("}"); StringBuilder sb = new StringBuilder("{").append(LOG_TAG).append(" - mSerialNumber=") .append(mSerialNumber).append(", ScoreFilter=") .append(mScore).append(", Filter=").append(mCapabilityFilter).append(", requests=") .append(mNetworkRequests.size()).append(", refCount=").append(mRefCount) .append("}"); return sb.toString(); } }
services/core/java/com/android/server/ConnectivityService.java +62 −14 Original line number Diff line number Diff line Loading @@ -84,6 +84,7 @@ import android.net.Network; import android.net.NetworkAgent; import android.net.NetworkCapabilities; import android.net.NetworkConfig; import android.net.NetworkFactory; import android.net.NetworkInfo; import android.net.NetworkInfo.DetailedState; import android.net.NetworkMisc; Loading Loading @@ -2892,8 +2893,17 @@ public class ConnectivityService extends IConnectivityManager.Stub for (NetworkRequestInfo nri : mNetworkRequests.values()) { if (nri.request.isListen()) continue; NetworkAgentInfo nai = getNetworkForRequest(nri.request.requestId); ac.sendMessage(android.net.NetworkFactory.CMD_REQUEST_NETWORK, (nai != null ? nai.getCurrentScore() : 0), 0, nri.request); final int score; final int serial; if (nai != null) { score = nai.getCurrentScore(); serial = nai.factorySerialNumber; } else { score = 0; serial = NetworkFactory.SerialNumber.NONE; } ac.sendMessage(android.net.NetworkFactory.CMD_REQUEST_NETWORK, score, serial, nri.request); } } else { loge("Error connecting NetworkFactory"); Loading Loading @@ -2991,7 +3001,7 @@ public class ConnectivityService extends IConnectivityManager.Stub NetworkAgentInfo currentNetwork = getNetworkForRequest(request.requestId); if (currentNetwork != null && currentNetwork.network.netId == nai.network.netId) { clearNetworkForRequest(request.requestId); sendUpdatedScoreToFactories(request, 0); sendUpdatedScoreToFactories(request, null); } } nai.clearLingerState(); Loading Loading @@ -3068,7 +3078,7 @@ public class ConnectivityService extends IConnectivityManager.Stub } rematchAllNetworksAndRequests(null, 0); if (nri.request.isRequest() && getNetworkForRequest(nri.request.requestId) == null) { sendUpdatedScoreToFactories(nri.request, 0); sendUpdatedScoreToFactories(nri.request, null); } } Loading Loading @@ -4843,11 +4853,14 @@ public class ConnectivityService extends IConnectivityManager.Stub public final String name; public final Messenger messenger; public final AsyncChannel asyncChannel; public final int factorySerialNumber; public NetworkFactoryInfo(String name, Messenger messenger, AsyncChannel asyncChannel) { NetworkFactoryInfo(String name, Messenger messenger, AsyncChannel asyncChannel, int factorySerialNumber) { this.name = name; this.messenger = messenger; this.asyncChannel = asyncChannel; this.factorySerialNumber = factorySerialNumber; } } Loading Loading @@ -5208,10 +5221,12 @@ public class ConnectivityService extends IConnectivityManager.Stub } @Override public void registerNetworkFactory(Messenger messenger, String name) { public int registerNetworkFactory(Messenger messenger, String name) { enforceConnectivityInternalPermission(); NetworkFactoryInfo nfi = new NetworkFactoryInfo(name, messenger, new AsyncChannel()); NetworkFactoryInfo nfi = new NetworkFactoryInfo(name, messenger, new AsyncChannel(), NetworkFactory.SerialNumber.nextSerialNumber()); mHandler.sendMessage(mHandler.obtainMessage(EVENT_REGISTER_NETWORK_FACTORY, nfi)); return nfi.factorySerialNumber; } private void handleRegisterNetworkFactory(NetworkFactoryInfo nfi) { Loading Loading @@ -5316,9 +5331,35 @@ public class ConnectivityService extends IConnectivityManager.Stub return nri.request.requestId == mDefaultRequest.requestId; } // TODO : remove this method. It's a stopgap measure to help sheperding a number of dependent // changes that would conflict throughout the automerger graph. Having this method temporarily // helps with the process of going through with all these dependent changes across the entire // tree. public int registerNetworkAgent(Messenger messenger, NetworkInfo networkInfo, LinkProperties linkProperties, NetworkCapabilities networkCapabilities, int currentScore, NetworkMisc networkMisc) { return registerNetworkAgent(messenger, networkInfo, linkProperties, networkCapabilities, currentScore, networkMisc, NetworkFactory.SerialNumber.NONE); } /** * Register a new agent with ConnectivityService to handle a network. * * @param messenger a messenger for ConnectivityService to contact the agent asynchronously. * @param networkInfo the initial info associated with this network. It can be updated later : * see {@link #updateNetworkInfo}. * @param linkProperties the initial link properties of this network. They can be updated * later : see {@link #updateLinkProperties}. * @param networkCapabilities the initial capabilites of this network. They can be updated * later : see {@link #updateNetworkCapabilities}. * @param currentScore the initial score of the network. See * {@link NetworkAgentInfo#getCurrentScore}. * @param networkMisc metadata about the network. This is never updated. * @param factorySerialNumber the serial number of the factory owning this NetworkAgent. */ public int registerNetworkAgent(Messenger messenger, NetworkInfo networkInfo, LinkProperties linkProperties, NetworkCapabilities networkCapabilities, int currentScore, NetworkMisc networkMisc, int factorySerialNumber) { enforceConnectivityInternalPermission(); LinkProperties lp = new LinkProperties(linkProperties); Loading @@ -5328,7 +5369,8 @@ public class ConnectivityService extends IConnectivityManager.Stub final NetworkCapabilities nc = new NetworkCapabilities(networkCapabilities); final NetworkAgentInfo nai = new NetworkAgentInfo(messenger, new AsyncChannel(), new Network(reserveNetId()), new NetworkInfo(networkInfo), lp, nc, currentScore, mContext, mTrackerHandler, new NetworkMisc(networkMisc), this, mNetd, mNMS); mContext, mTrackerHandler, new NetworkMisc(networkMisc), this, mNetd, mNMS, factorySerialNumber); // Make sure the network capabilities reflect what the agent info says. nai.networkCapabilities = mixInCapabilities(nai, nc); final String extraInfo = networkInfo.getExtraInfo(); Loading Loading @@ -5755,17 +5797,23 @@ public class ConnectivityService extends IConnectivityManager.Stub NetworkRequest nr = nai.requestAt(i); // Don't send listening requests to factories. b/17393458 if (nr.isListen()) continue; sendUpdatedScoreToFactories(nr, nai.getCurrentScore()); sendUpdatedScoreToFactories(nr, nai); } } private void sendUpdatedScoreToFactories(NetworkRequest networkRequest, int score) { private void sendUpdatedScoreToFactories(NetworkRequest networkRequest, NetworkAgentInfo nai) { int score = 0; int serial = 0; if (nai != null) { score = nai.getCurrentScore(); serial = nai.factorySerialNumber; } if (VDBG || DDBG){ log("sending new Min Network Score(" + score + "): " + networkRequest.toString()); } for (NetworkFactoryInfo nfi : mNetworkFactoryInfos.values()) { nfi.asyncChannel.sendMessage(android.net.NetworkFactory.CMD_REQUEST_NETWORK, score, 0, networkRequest); nfi.asyncChannel.sendMessage(android.net.NetworkFactory.CMD_REQUEST_NETWORK, score, serial, networkRequest); } } Loading Loading @@ -6043,7 +6091,7 @@ public class ConnectivityService extends IConnectivityManager.Stub // TODO - this could get expensive if we have a lot of requests for this // network. Think about if there is a way to reduce this. Push // netid->request mapping to each factory? sendUpdatedScoreToFactories(nri.request, score); sendUpdatedScoreToFactories(nri.request, newNetwork); if (isDefaultRequest(nri)) { isNewDefault = true; oldDefaultNetwork = currentNetwork; Loading @@ -6067,7 +6115,7 @@ public class ConnectivityService extends IConnectivityManager.Stub newNetwork.removeRequest(nri.request.requestId); if (currentNetwork == newNetwork) { clearNetworkForRequest(nri.request.requestId); sendUpdatedScoreToFactories(nri.request, 0); sendUpdatedScoreToFactories(nri.request, null); } else { Slog.wtf(TAG, "BUG: Removing request " + nri.request.requestId + " from " + newNetwork.name() + Loading