Make firewall bpf code multi-user aware

The check is_system_uid should mirror the definition of core_uids in
UserHandle.isCore until it is available to be read from mainline code.
isUidNetworkingBlocked should also do the same.

Test: All existing tests should pass.
Test: atest CtsHostsideNetworkPolicyTests
Test: atest FrameworksNetTests

Bug: 348316140
Change-Id: Id5e01289b301a725b162ef249062e0f2806876dc
This commit is contained in:
Suprabh Shukla 2024-06-20 17:07:13 -07:00
commit 3d00262fe7
3 changed files with 33 additions and 4 deletions

View file

@ -270,5 +270,5 @@ static inline bool isBlockedByUidRules(BpfConfig enabledRules, uint32_t uidRules
static inline bool is_system_uid(uint32_t uid) {
// MIN_SYSTEM_UID is AID_ROOT == 0, so uint32_t is *always* >= 0
// MAX_SYSTEM_UID is AID_NOBODY == 9999, while AID_APP_START == 10000
return (uid < AID_APP_START);
return ((uid % AID_USER_OFFSET) < AID_APP_START);
}

View file

@ -68,6 +68,7 @@ import static android.system.OsConstants.EINVAL;
import android.os.Build;
import android.os.Process;
import android.os.ServiceSpecificException;
import android.os.UserHandle;
import android.system.ErrnoException;
import android.system.Os;
import android.util.Pair;
@ -330,9 +331,9 @@ public class BpfNetMapsUtils {
) {
throwIfPreT("isUidBlockedByFirewallChains is not available on pre-T devices");
// System uid is not blocked by firewall chains, see bpf_progs/netd.c
// TODO: use UserHandle.isCore() once it is accessible
if (uid < Process.FIRST_APPLICATION_UID) {
// System uids are not blocked by firewall chains, see bpf_progs/netd.c
// TODO: b/348513058 - use UserHandle.isCore() once it is accessible
if (UserHandle.getAppId(uid) < Process.FIRST_APPLICATION_UID) {
return false;
}

View file

@ -87,7 +87,9 @@ import android.net.INetd;
import android.net.InetAddresses;
import android.net.UidOwnerValue;
import android.os.Build;
import android.os.Process;
import android.os.ServiceSpecificException;
import android.os.UserHandle;
import android.system.ErrnoException;
import android.util.ArraySet;
import android.util.IndentingPrintWriter;
@ -1249,6 +1251,32 @@ public final class BpfNetMapsTest {
);
}
@Test
@IgnoreUpTo(Build.VERSION_CODES.S_V2)
public void testIsUidNetworkingBlockedForCoreUids() throws Exception {
final long allowlistMatch = BACKGROUND_MATCH; // Enable any allowlist match.
mConfigurationMap.updateEntry(UID_RULES_CONFIGURATION_KEY, new U32(allowlistMatch));
// Verify that a normal uid that is not on this chain is indeed blocked.
assertTrue(BpfNetMapsUtils.isUidNetworkingBlocked(TEST_UID, false, mConfigurationMap,
mUidOwnerMap, mDataSaverEnabledMap));
final int[] coreAids = new int[] {
Process.ROOT_UID,
Process.SYSTEM_UID,
Process.FIRST_APPLICATION_UID - 10,
Process.FIRST_APPLICATION_UID - 1,
};
// Core appIds are not on the chain but should still be allowed on any user.
for (int userId = 0; userId < 20; userId++) {
for (final int aid : coreAids) {
final int uid = UserHandle.getUid(userId, aid);
assertFalse(BpfNetMapsUtils.isUidNetworkingBlocked(uid, false, mConfigurationMap,
mUidOwnerMap, mDataSaverEnabledMap));
}
}
}
private void doTestIsUidRestrictedOnMeteredNetworks(
final long enabledMatches,
final long uidRules,