Snap for 6497471 from 1fe85bb60c590f8ffd15dc57a932342bb1fd289f to mainline-release

Change-Id: I6d810cfb1b7bce5ef1430f0140b0c3e9df7d733b
This commit is contained in:
android-build-team Robot
2020-05-15 07:03:45 +00:00
8 changed files with 121 additions and 52 deletions

View File

@@ -48,6 +48,7 @@ import android.os.Looper;
import android.os.Message;
import android.os.Messenger;
import android.os.ParcelFileDescriptor;
import android.os.PersistableBundle;
import android.os.Process;
import android.os.RemoteException;
import android.os.ResultReceiver;
@@ -4693,4 +4694,28 @@ public class ConnectivityManager {
Log.d(TAG, "StackLog:" + sb.toString());
}
}
/**
* Simulates a Data Stall for the specified Network.
*
* <p>The caller must be the owner of the specified Network.
*
* @param detectionMethod The detection method used to identify the Data Stall.
* @param timestampMillis The timestamp at which the stall 'occurred', in milliseconds.
* @param network The Network for which a Data Stall is being simluated.
* @param extras The PersistableBundle of extras included in the Data Stall notification.
* @throws SecurityException if the caller is not the owner of the given network.
* @hide
*/
@TestApi
@RequiresPermission(anyOf = {android.Manifest.permission.MANAGE_TEST_NETWORKS,
android.Manifest.permission.NETWORK_STACK})
public void simulateDataStall(int detectionMethod, long timestampMillis,
@NonNull Network network, @NonNull PersistableBundle extras) {
try {
mService.simulateDataStall(detectionMethod, timestampMillis, network, extras);
} catch (RemoteException e) {
e.rethrowFromSystemServer();
}
}
}

View File

@@ -18,6 +18,7 @@ package android.net;
import android.app.PendingIntent;
import android.net.ConnectionInfo;
import android.net.ConnectivityDiagnosticsManager;
import android.net.IConnectivityDiagnosticsCallback;
import android.net.LinkProperties;
import android.net.Network;
@@ -33,6 +34,7 @@ import android.os.Bundle;
import android.os.IBinder;
import android.os.Messenger;
import android.os.ParcelFileDescriptor;
import android.os.PersistableBundle;
import android.os.ResultReceiver;
import com.android.internal.net.LegacyVpnInfo;
@@ -227,4 +229,7 @@ interface IConnectivityManager
void unregisterConnectivityDiagnosticsCallback(in IConnectivityDiagnosticsCallback callback);
IBinder startOrGetTestNetworkService();
void simulateDataStall(int detectionMethod, long timestampMillis, in Network network,
in PersistableBundle extras);
}

View File

@@ -677,16 +677,27 @@ public final class NetworkCapabilities implements Parcelable {
* restrictions.
* @hide
*/
public void restrictCapabilitesForTestNetwork() {
public void restrictCapabilitesForTestNetwork(int creatorUid) {
final long originalCapabilities = mNetworkCapabilities;
final NetworkSpecifier originalSpecifier = mNetworkSpecifier;
final int originalSignalStrength = mSignalStrength;
final int originalOwnerUid = getOwnerUid();
final int[] originalAdministratorUids = getAdministratorUids();
clearAll();
// Reset the transports to only contain TRANSPORT_TEST.
mTransportTypes = (1 << TRANSPORT_TEST);
mNetworkCapabilities = originalCapabilities & TEST_NETWORKS_ALLOWED_CAPABILITIES;
mNetworkSpecifier = originalSpecifier;
mSignalStrength = originalSignalStrength;
// Only retain the owner and administrator UIDs if they match the app registering the remote
// caller that registered the network.
if (originalOwnerUid == creatorUid) {
setOwnerUid(creatorUid);
}
if (ArrayUtils.contains(originalAdministratorUids, creatorUid)) {
setAdministratorUids(new int[] {creatorUid});
}
}
/**

View File

@@ -2740,7 +2740,7 @@ public class ConnectivityService extends IConnectivityManager.Stub
// the Messenger, but if this ever changes, not making a defensive copy
// here will give attack vectors to clients using this code path.
networkCapabilities = new NetworkCapabilities(networkCapabilities);
networkCapabilities.restrictCapabilitesForTestNetwork();
networkCapabilities.restrictCapabilitesForTestNetwork(nai.creatorUid);
}
updateCapabilities(nai.getCurrentScore(), nai, networkCapabilities);
break;
@@ -3087,10 +3087,6 @@ public class ConnectivityService extends IConnectivityManager.Stub
@Override
public void notifyDataStallSuspected(DataStallReportParcelable p) {
final Message msg = mConnectivityDiagnosticsHandler.obtainMessage(
ConnectivityDiagnosticsHandler.EVENT_DATA_STALL_SUSPECTED,
p.detectionMethod, mNetId, p.timestampMillis);
final PersistableBundle extras = new PersistableBundle();
switch (p.detectionMethod) {
case DETECTION_METHOD_DNS_EVENTS:
@@ -3105,12 +3101,9 @@ public class ConnectivityService extends IConnectivityManager.Stub
log("Unknown data stall detection method, ignoring: " + p.detectionMethod);
return;
}
msg.setData(new Bundle(extras));
// NetworkStateTrackerHandler currently doesn't take any actions based on data
// stalls so send the message directly to ConnectivityDiagnosticsHandler and avoid
// the cost of going through two handlers.
mConnectivityDiagnosticsHandler.sendMessage(msg);
proxyDataStallToConnectivityDiagnosticsHandler(
p.detectionMethod, mNetId, p.timestampMillis, extras);
}
@Override
@@ -3124,6 +3117,19 @@ public class ConnectivityService extends IConnectivityManager.Stub
}
}
private void proxyDataStallToConnectivityDiagnosticsHandler(int detectionMethod, int netId,
long timestampMillis, @NonNull PersistableBundle extras) {
final Message msg = mConnectivityDiagnosticsHandler.obtainMessage(
ConnectivityDiagnosticsHandler.EVENT_DATA_STALL_SUSPECTED,
detectionMethod, netId, timestampMillis);
msg.setData(new Bundle(extras));
// NetworkStateTrackerHandler currently doesn't take any actions based on data
// stalls so send the message directly to ConnectivityDiagnosticsHandler and avoid
// the cost of going through two handlers.
mConnectivityDiagnosticsHandler.sendMessage(msg);
}
private boolean networkRequiresPrivateDnsValidation(NetworkAgentInfo nai) {
return isPrivateDnsValidationRequired(nai.networkCapabilities);
}
@@ -5859,7 +5865,7 @@ public class ConnectivityService extends IConnectivityManager.Stub
// the call to mixInCapabilities below anyway, but sanitizing here means the NAI never
// sees capabilities that may be malicious, which might prevent mistakes in the future.
networkCapabilities = new NetworkCapabilities(networkCapabilities);
networkCapabilities.restrictCapabilitesForTestNetwork();
networkCapabilities.restrictCapabilitesForTestNetwork(Binder.getCallingUid());
} else {
enforceNetworkFactoryPermission();
}
@@ -5872,7 +5878,7 @@ public class ConnectivityService extends IConnectivityManager.Stub
final NetworkAgentInfo nai = new NetworkAgentInfo(messenger, new AsyncChannel(),
new Network(mNetIdManager.reserveNetId()), new NetworkInfo(networkInfo), lp, nc,
currentScore, mContext, mTrackerHandler, new NetworkAgentConfig(networkAgentConfig),
this, mNetd, mDnsResolver, mNMS, providerId);
this, mNetd, mDnsResolver, mNMS, providerId, Binder.getCallingUid());
// Make sure the LinkProperties and NetworkCapabilities reflect what the agent info says.
nai.getAndSetNetworkCapabilities(mixInCapabilities(nai, nc));
@@ -8154,4 +8160,24 @@ public class ConnectivityService extends IConnectivityManager.Stub
0,
callback));
}
@Override
public void simulateDataStall(int detectionMethod, long timestampMillis,
@NonNull Network network, @NonNull PersistableBundle extras) {
enforceAnyPermissionOf(android.Manifest.permission.MANAGE_TEST_NETWORKS,
android.Manifest.permission.NETWORK_STACK);
final NetworkCapabilities nc = getNetworkCapabilitiesInternal(network);
if (!nc.hasTransport(TRANSPORT_TEST)) {
throw new SecurityException("Data Stall simluation is only possible for test networks");
}
final NetworkAgentInfo nai = getNetworkAgentInfoForNetwork(network);
if (nai == null || nai.creatorUid != Binder.getCallingUid()) {
throw new SecurityException("Data Stall simulation is only possible for network "
+ "creators");
}
proxyDataStallToConnectivityDiagnosticsHandler(
detectionMethod, network.netId, timestampMillis, extras);
}
}

View File

@@ -317,39 +317,34 @@ class TestNetworkService extends ITestNetworkManager.Stub {
"Cannot create network for non ipsec, non-testtun interface");
}
// Setup needs to be done with NETWORK_STACK privileges.
int callingUid = Binder.getCallingUid();
Binder.withCleanCallingIdentity(
() -> {
try {
mNMS.setInterfaceUp(iface);
try {
// This requires NETWORK_STACK privileges.
Binder.withCleanCallingIdentity(() -> mNMS.setInterfaceUp(iface));
// Synchronize all accesses to mTestNetworkTracker to prevent the case
// where:
// 1. TestNetworkAgent successfully binds to death of binder
// 2. Before it is added to the mTestNetworkTracker, binder dies,
// binderDied() is called (on a different thread)
// 3. This thread is pre-empted, put() is called after remove()
synchronized (mTestNetworkTracker) {
TestNetworkAgent agent =
registerTestNetworkAgent(
mHandler.getLooper(),
mContext,
iface,
lp,
isMetered,
callingUid,
administratorUids,
binder);
// Synchronize all accesses to mTestNetworkTracker to prevent the case where:
// 1. TestNetworkAgent successfully binds to death of binder
// 2. Before it is added to the mTestNetworkTracker, binder dies, binderDied() is called
// (on a different thread)
// 3. This thread is pre-empted, put() is called after remove()
synchronized (mTestNetworkTracker) {
TestNetworkAgent agent =
registerTestNetworkAgent(
mHandler.getLooper(),
mContext,
iface,
lp,
isMetered,
Binder.getCallingUid(),
administratorUids,
binder);
mTestNetworkTracker.put(agent.getNetwork().netId, agent);
}
} catch (SocketException e) {
throw new UncheckedIOException(e);
} catch (RemoteException e) {
throw e.rethrowFromSystemServer();
}
});
mTestNetworkTracker.put(agent.getNetwork().netId, agent);
}
} catch (SocketException e) {
throw new UncheckedIOException(e);
} catch (RemoteException e) {
throw e.rethrowFromSystemServer();
}
}
/** Teardown a test network */

View File

@@ -168,6 +168,9 @@ public class NetworkAgentInfo implements Comparable<NetworkAgentInfo> {
// Obtained by ConnectivityService and merged into NetworkAgent-provided information.
public CaptivePortalData captivePortalData;
// The UID of the remote entity that created this Network.
public final int creatorUid;
// Networks are lingered when they become unneeded as a result of their NetworkRequests being
// satisfied by a higher-scoring network. so as to allow communication to wrap up before the
// network is taken down. This usually only happens to the default network. Lingering ends with
@@ -268,7 +271,8 @@ public class NetworkAgentInfo implements Comparable<NetworkAgentInfo> {
public NetworkAgentInfo(Messenger messenger, AsyncChannel ac, Network net, NetworkInfo info,
LinkProperties lp, NetworkCapabilities nc, int score, Context context,
Handler handler, NetworkAgentConfig config, ConnectivityService connService, INetd netd,
IDnsResolver dnsResolver, INetworkManagementService nms, int factorySerialNumber) {
IDnsResolver dnsResolver, INetworkManagementService nms, int factorySerialNumber,
int creatorUid) {
this.messenger = messenger;
asyncChannel = ac;
network = net;
@@ -282,6 +286,7 @@ public class NetworkAgentInfo implements Comparable<NetworkAgentInfo> {
mHandler = handler;
networkAgentConfig = config;
this.factorySerialNumber = factorySerialNumber;
this.creatorUid = creatorUid;
}
/**

View File

@@ -75,6 +75,7 @@ import static android.net.NetworkPolicyManager.RULE_NONE;
import static android.net.NetworkPolicyManager.RULE_REJECT_ALL;
import static android.net.NetworkPolicyManager.RULE_REJECT_METERED;
import static android.net.RouteInfo.RTN_UNREACHABLE;
import static android.os.Process.INVALID_UID;
import static android.system.OsConstants.IPPROTO_TCP;
import static com.android.server.ConnectivityServiceTestUtilsKt.transportToLegacyType;
@@ -6945,7 +6946,7 @@ public class ConnectivityServiceTest {
final NetworkAgentInfo naiWithoutUid =
new NetworkAgentInfo(
null, null, null, null, null, new NetworkCapabilities(), 0,
mServiceContext, null, null, mService, null, null, null, 0);
mServiceContext, null, null, mService, null, null, null, 0, INVALID_UID);
mServiceContext.setPermission(
android.Manifest.permission.NETWORK_STACK, PERMISSION_GRANTED);
@@ -6961,7 +6962,7 @@ public class ConnectivityServiceTest {
final NetworkAgentInfo naiWithoutUid =
new NetworkAgentInfo(
null, null, null, null, null, new NetworkCapabilities(), 0,
mServiceContext, null, null, mService, null, null, null, 0);
mServiceContext, null, null, mService, null, null, null, 0, INVALID_UID);
mServiceContext.setPermission(android.Manifest.permission.NETWORK_STACK, PERMISSION_DENIED);
@@ -6977,7 +6978,7 @@ public class ConnectivityServiceTest {
final NetworkAgentInfo naiWithoutUid =
new NetworkAgentInfo(
null, null, null, null, null, new NetworkCapabilities(), 0,
mServiceContext, null, null, mService, null, null, null, 0);
mServiceContext, null, null, mService, null, null, null, 0, INVALID_UID);
mServiceContext.setPermission(android.Manifest.permission.NETWORK_STACK, PERMISSION_DENIED);
@@ -6994,7 +6995,7 @@ public class ConnectivityServiceTest {
final NetworkAgentInfo naiWithoutUid =
new NetworkAgentInfo(
null, null, network, null, null, new NetworkCapabilities(), 0,
mServiceContext, null, null, mService, null, null, null, 0);
mServiceContext, null, null, mService, null, null, null, 0, INVALID_UID);
setupLocationPermissions(Build.VERSION_CODES.Q, true, AppOpsManager.OPSTR_FINE_LOCATION,
Manifest.permission.ACCESS_FINE_LOCATION);
@@ -7028,7 +7029,7 @@ public class ConnectivityServiceTest {
final NetworkAgentInfo naiWithUid =
new NetworkAgentInfo(
null, null, null, null, null, nc, 0, mServiceContext, null, null,
mService, null, null, null, 0);
mService, null, null, null, 0, INVALID_UID);
setupLocationPermissions(Build.VERSION_CODES.Q, true, AppOpsManager.OPSTR_FINE_LOCATION,
Manifest.permission.ACCESS_FINE_LOCATION);
@@ -7050,7 +7051,7 @@ public class ConnectivityServiceTest {
final NetworkAgentInfo naiWithUid =
new NetworkAgentInfo(
null, null, null, null, null, nc, 0, mServiceContext, null, null,
mService, null, null, null, 0);
mService, null, null, null, 0, INVALID_UID);
setupLocationPermissions(Build.VERSION_CODES.Q, true, AppOpsManager.OPSTR_FINE_LOCATION,
Manifest.permission.ACCESS_FINE_LOCATION);

View File

@@ -38,6 +38,7 @@ import android.net.Network;
import android.net.NetworkCapabilities;
import android.net.NetworkInfo;
import android.net.NetworkProvider;
import android.os.Binder;
import android.os.INetworkManagementService;
import android.text.format.DateUtils;
@@ -354,7 +355,7 @@ public class LingerMonitorTest {
caps.addTransportType(transport);
NetworkAgentInfo nai = new NetworkAgentInfo(null, null, new Network(netId), info, null,
caps, 50, mCtx, null, null /* config */, mConnService, mNetd, mDnsResolver, mNMS,
NetworkProvider.ID_NONE);
NetworkProvider.ID_NONE, Binder.getCallingUid());
nai.everValidated = true;
return nai;
}