Allow USE_RESTRICTED_NETWORKS for registerSystemDefaultNetworkCallback

Some callers (e.g. iwlan) need to learn about system default
network but they cannot have NETWORK_SETTINGS permission.
To allow them to use this API but prevent from misuse by
unprivileged apps, enforce USE_RESTRICTED_NETWORKS for this API.

Test: atest com.android.server.ConnectivityServiceTest#testRegisterPrivilegedDefaultCallbacksRequireNetworkSettings android.net.cts.ConnectivityManagerTest#testRegisterNetworkCallback
Fix: 242456635
Change-Id: I80ab27445af874328c9c0f4814a8fbf035ae5df4
This commit is contained in:
Junyu Lai
2022-10-28 15:42:00 +08:00
parent 3e7778805b
commit aa4ad8c2d1
5 changed files with 29 additions and 4 deletions

View File

@@ -15,7 +15,7 @@ package android.net {
method @Nullable @RequiresPermission(anyOf={android.net.NetworkStack.PERMISSION_MAINLINE_NETWORK_STACK, android.Manifest.permission.NETWORK_STACK, android.Manifest.permission.NETWORK_SETTINGS}) public android.net.LinkProperties getRedactedLinkPropertiesForPackage(@NonNull android.net.LinkProperties, int, @NonNull String); method @Nullable @RequiresPermission(anyOf={android.net.NetworkStack.PERMISSION_MAINLINE_NETWORK_STACK, android.Manifest.permission.NETWORK_STACK, android.Manifest.permission.NETWORK_SETTINGS}) public android.net.LinkProperties getRedactedLinkPropertiesForPackage(@NonNull android.net.LinkProperties, int, @NonNull String);
method @Nullable @RequiresPermission(anyOf={android.net.NetworkStack.PERMISSION_MAINLINE_NETWORK_STACK, android.Manifest.permission.NETWORK_STACK, android.Manifest.permission.NETWORK_SETTINGS}) public android.net.NetworkCapabilities getRedactedNetworkCapabilitiesForPackage(@NonNull android.net.NetworkCapabilities, int, @NonNull String); method @Nullable @RequiresPermission(anyOf={android.net.NetworkStack.PERMISSION_MAINLINE_NETWORK_STACK, android.Manifest.permission.NETWORK_STACK, android.Manifest.permission.NETWORK_SETTINGS}) public android.net.NetworkCapabilities getRedactedNetworkCapabilitiesForPackage(@NonNull android.net.NetworkCapabilities, int, @NonNull String);
method @RequiresPermission(anyOf={android.net.NetworkStack.PERMISSION_MAINLINE_NETWORK_STACK, android.Manifest.permission.NETWORK_SETTINGS}) public void registerDefaultNetworkCallbackForUid(int, @NonNull android.net.ConnectivityManager.NetworkCallback, @NonNull android.os.Handler); method @RequiresPermission(anyOf={android.net.NetworkStack.PERMISSION_MAINLINE_NETWORK_STACK, android.Manifest.permission.NETWORK_SETTINGS}) public void registerDefaultNetworkCallbackForUid(int, @NonNull android.net.ConnectivityManager.NetworkCallback, @NonNull android.os.Handler);
method @RequiresPermission(anyOf={android.net.NetworkStack.PERMISSION_MAINLINE_NETWORK_STACK, android.Manifest.permission.NETWORK_SETTINGS}) public void registerSystemDefaultNetworkCallback(@NonNull android.net.ConnectivityManager.NetworkCallback, @NonNull android.os.Handler); method @RequiresPermission(anyOf={android.net.NetworkStack.PERMISSION_MAINLINE_NETWORK_STACK, android.Manifest.permission.NETWORK_SETTINGS, android.Manifest.permission.CONNECTIVITY_USE_RESTRICTED_NETWORKS}) public void registerSystemDefaultNetworkCallback(@NonNull android.net.ConnectivityManager.NetworkCallback, @NonNull android.os.Handler);
method @RequiresPermission(anyOf={android.Manifest.permission.NETWORK_SETTINGS, android.Manifest.permission.NETWORK_STACK, android.net.NetworkStack.PERMISSION_MAINLINE_NETWORK_STACK}) public void removeUidFromMeteredNetworkAllowList(int); method @RequiresPermission(anyOf={android.Manifest.permission.NETWORK_SETTINGS, android.Manifest.permission.NETWORK_STACK, android.net.NetworkStack.PERMISSION_MAINLINE_NETWORK_STACK}) public void removeUidFromMeteredNetworkAllowList(int);
method @RequiresPermission(anyOf={android.Manifest.permission.NETWORK_SETTINGS, android.Manifest.permission.NETWORK_STACK, android.net.NetworkStack.PERMISSION_MAINLINE_NETWORK_STACK}) public void removeUidFromMeteredNetworkDenyList(int); method @RequiresPermission(anyOf={android.Manifest.permission.NETWORK_SETTINGS, android.Manifest.permission.NETWORK_STACK, android.net.NetworkStack.PERMISSION_MAINLINE_NETWORK_STACK}) public void removeUidFromMeteredNetworkDenyList(int);
method @RequiresPermission(anyOf={android.Manifest.permission.NETWORK_SETTINGS, android.Manifest.permission.NETWORK_STACK, android.net.NetworkStack.PERMISSION_MAINLINE_NETWORK_STACK}) public void replaceFirewallChain(int, @NonNull int[]); method @RequiresPermission(anyOf={android.Manifest.permission.NETWORK_SETTINGS, android.Manifest.permission.NETWORK_STACK, android.net.NetworkStack.PERMISSION_MAINLINE_NETWORK_STACK}) public void replaceFirewallChain(int, @NonNull int[]);

View File

@@ -4786,7 +4786,8 @@ public class ConnectivityManager {
@SuppressLint({"ExecutorRegistration", "PairedRegistration"}) @SuppressLint({"ExecutorRegistration", "PairedRegistration"})
@RequiresPermission(anyOf = { @RequiresPermission(anyOf = {
NetworkStack.PERMISSION_MAINLINE_NETWORK_STACK, NetworkStack.PERMISSION_MAINLINE_NETWORK_STACK,
android.Manifest.permission.NETWORK_SETTINGS}) android.Manifest.permission.NETWORK_SETTINGS,
android.Manifest.permission.CONNECTIVITY_USE_RESTRICTED_NETWORKS})
public void registerSystemDefaultNetworkCallback(@NonNull NetworkCallback networkCallback, public void registerSystemDefaultNetworkCallback(@NonNull NetworkCallback networkCallback,
@NonNull Handler handler) { @NonNull Handler handler) {
CallbackHandler cbHandler = new CallbackHandler(handler); CallbackHandler cbHandler = new CallbackHandler(handler);

View File

@@ -2800,6 +2800,13 @@ public class ConnectivityService extends IConnectivityManager.Stub
NetworkStack.PERMISSION_MAINLINE_NETWORK_STACK); NetworkStack.PERMISSION_MAINLINE_NETWORK_STACK);
} }
private void enforceSettingsOrUseRestrictedNetworksPermission() {
enforceAnyPermissionOf(mContext,
android.Manifest.permission.NETWORK_SETTINGS,
NetworkStack.PERMISSION_MAINLINE_NETWORK_STACK,
Manifest.permission.CONNECTIVITY_USE_RESTRICTED_NETWORKS);
}
private void enforceNetworkFactoryPermission() { private void enforceNetworkFactoryPermission() {
// TODO: Check for the BLUETOOTH_STACK permission once that is in the API surface. // TODO: Check for the BLUETOOTH_STACK permission once that is in the API surface.
if (UserHandle.getAppId(getCallingUid()) == Process.BLUETOOTH_UID) return; if (UserHandle.getAppId(getCallingUid()) == Process.BLUETOOTH_UID) return;
@@ -6592,7 +6599,7 @@ public class ConnectivityService extends IConnectivityManager.Stub
enforceAccessPermission(); enforceAccessPermission();
break; break;
case TRACK_SYSTEM_DEFAULT: case TRACK_SYSTEM_DEFAULT:
enforceSettingsPermission(); enforceSettingsOrUseRestrictedNetworksPermission();
networkCapabilities = new NetworkCapabilities(defaultNc); networkCapabilities = new NetworkCapabilities(defaultNc);
break; break;
case BACKGROUND_REQUEST: case BACKGROUND_REQUEST:

View File

@@ -1044,12 +1044,22 @@ public class ConnectivityManagerTest {
final TestNetworkCallback bestMatchingCallback = new TestNetworkCallback(); final TestNetworkCallback bestMatchingCallback = new TestNetworkCallback();
final Handler h = new Handler(Looper.getMainLooper()); final Handler h = new Handler(Looper.getMainLooper());
if (TestUtils.shouldTestSApis()) { if (TestUtils.shouldTestSApis()) {
assertThrows(SecurityException.class, () ->
registerSystemDefaultNetworkCallback(systemDefaultCallback, h));
runWithShellPermissionIdentity(() -> { runWithShellPermissionIdentity(() -> {
registerSystemDefaultNetworkCallback(systemDefaultCallback, h); registerSystemDefaultNetworkCallback(systemDefaultCallback, h);
registerDefaultNetworkCallbackForUid(Process.myUid(), perUidCallback, h); registerDefaultNetworkCallbackForUid(Process.myUid(), perUidCallback, h);
}, NETWORK_SETTINGS); }, NETWORK_SETTINGS);
registerBestMatchingNetworkCallback(makeDefaultRequest(), bestMatchingCallback, h); registerBestMatchingNetworkCallback(makeDefaultRequest(), bestMatchingCallback, h);
} }
if (TestUtils.shouldTestTApis()) {
// Verify registerSystemDefaultNetworkCallback can be accessed via
// CONNECTIVITY_USE_RESTRICTED_NETWORKS permission.
final TestNetworkCallback systemDefaultCallback2 = new TestNetworkCallback();
runWithShellPermissionIdentity(() ->
registerSystemDefaultNetworkCallback(systemDefaultCallback2, h),
CONNECTIVITY_USE_RESTRICTED_NETWORKS);
}
Network wifiNetwork = null; Network wifiNetwork = null;
mCtsNetUtils.ensureWifiConnected(); mCtsNetUtils.ensureWifiConnected();

View File

@@ -5121,9 +5121,10 @@ public class ConnectivityServiceTest {
} }
@Test @Test
public void testRegisterPrivilegedDefaultCallbacksRequireNetworkSettings() throws Exception { public void testRegisterPrivilegedDefaultCallbacksRequirePermissions() throws Exception {
mCellNetworkAgent = new TestNetworkAgentWrapper(TRANSPORT_CELLULAR); mCellNetworkAgent = new TestNetworkAgentWrapper(TRANSPORT_CELLULAR);
mCellNetworkAgent.connect(false /* validated */); mCellNetworkAgent.connect(false /* validated */);
mServiceContext.setPermission(CONNECTIVITY_USE_RESTRICTED_NETWORKS, PERMISSION_DENIED);
final Handler handler = new Handler(ConnectivityThread.getInstanceLooper()); final Handler handler = new Handler(ConnectivityThread.getInstanceLooper());
final TestNetworkCallback callback = new TestNetworkCallback(); final TestNetworkCallback callback = new TestNetworkCallback();
@@ -5134,6 +5135,12 @@ public class ConnectivityServiceTest {
() -> mCm.registerDefaultNetworkCallbackForUid(APP1_UID, callback, handler)); () -> mCm.registerDefaultNetworkCallbackForUid(APP1_UID, callback, handler));
callback.assertNoCallback(); callback.assertNoCallback();
mServiceContext.setPermission(CONNECTIVITY_USE_RESTRICTED_NETWORKS, PERMISSION_GRANTED);
mCm.registerSystemDefaultNetworkCallback(callback, handler);
mServiceContext.setPermission(CONNECTIVITY_USE_RESTRICTED_NETWORKS, PERMISSION_DENIED);
callback.expectAvailableCallbacksUnvalidated(mCellNetworkAgent);
mCm.unregisterNetworkCallback(callback);
mServiceContext.setPermission(NETWORK_SETTINGS, PERMISSION_GRANTED); mServiceContext.setPermission(NETWORK_SETTINGS, PERMISSION_GRANTED);
mCm.registerSystemDefaultNetworkCallback(callback, handler); mCm.registerSystemDefaultNetworkCallback(callback, handler);
callback.expectAvailableCallbacksUnvalidated(mCellNetworkAgent); callback.expectAvailableCallbacksUnvalidated(mCellNetworkAgent);