Merge "[BR01.1] Support BpfNetMapsReader" into main
This commit is contained in:
@@ -95,6 +95,7 @@ android_library {
|
||||
],
|
||||
static_libs: [
|
||||
"NetworkStackApiCurrentShims",
|
||||
"net-utils-device-common-struct",
|
||||
],
|
||||
apex_available: ["com.android.tethering"],
|
||||
lint: { strict_updatability_linting: true },
|
||||
@@ -109,6 +110,7 @@ android_library {
|
||||
],
|
||||
static_libs: [
|
||||
"NetworkStackApiStableShims",
|
||||
"net-utils-device-common-struct",
|
||||
],
|
||||
apex_available: ["com.android.tethering"],
|
||||
lint: { strict_updatability_linting: true },
|
||||
|
||||
@@ -25,6 +25,7 @@ build = ["TrunkStable.bp"]
|
||||
// as the above target may not exist
|
||||
// depending on the branch
|
||||
|
||||
// The library requires the final artifact to contain net-utils-device-common-struct.
|
||||
java_library {
|
||||
name: "connectivity-net-module-utils-bpf",
|
||||
srcs: [
|
||||
@@ -40,8 +41,9 @@ java_library {
|
||||
libs: [
|
||||
"androidx.annotation_annotation",
|
||||
"framework-connectivity.stubs.module_lib",
|
||||
],
|
||||
static_libs: [
|
||||
// For libraries which are statically linked in framework-connectivity, do not
|
||||
// statically link here because callers of this library might already have a static
|
||||
// version linked.
|
||||
"net-utils-device-common-struct",
|
||||
],
|
||||
apex_available: [
|
||||
|
||||
@@ -101,7 +101,7 @@ java_defaults {
|
||||
"framework-connectivity-javastream-protos",
|
||||
],
|
||||
impl_only_static_libs: [
|
||||
"net-utils-device-common-struct",
|
||||
"net-utils-device-common-bpf",
|
||||
],
|
||||
libs: [
|
||||
"androidx.annotation_annotation",
|
||||
@@ -130,7 +130,7 @@ java_library {
|
||||
// to generate the SDK stubs.
|
||||
// Even if the library is included in "impl_only_static_libs" of defaults. This is still
|
||||
// needed because java_library which doesn't understand "impl_only_static_libs".
|
||||
"net-utils-device-common-struct",
|
||||
"net-utils-device-common-bpf",
|
||||
],
|
||||
libs: [
|
||||
// This cannot be in the defaults clause above because if it were, it would be used
|
||||
|
||||
179
framework/src/android/net/BpfNetMapsReader.java
Normal file
179
framework/src/android/net/BpfNetMapsReader.java
Normal file
@@ -0,0 +1,179 @@
|
||||
/*
|
||||
* Copyright (C) 2023 The Android Open Source Project
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
package android.net;
|
||||
|
||||
import static android.net.BpfNetMapsConstants.CONFIGURATION_MAP_PATH;
|
||||
import static android.net.BpfNetMapsConstants.UID_OWNER_MAP_PATH;
|
||||
import static android.net.BpfNetMapsConstants.UID_RULES_CONFIGURATION_KEY;
|
||||
import static android.net.BpfNetMapsUtils.getMatchByFirewallChain;
|
||||
import static android.net.BpfNetMapsUtils.isFirewallAllowList;
|
||||
import static android.net.BpfNetMapsUtils.throwIfPreT;
|
||||
import static android.net.ConnectivityManager.FIREWALL_RULE_ALLOW;
|
||||
import static android.net.ConnectivityManager.FIREWALL_RULE_DENY;
|
||||
|
||||
import android.annotation.NonNull;
|
||||
import android.annotation.RequiresApi;
|
||||
import android.os.Build;
|
||||
import android.os.ServiceSpecificException;
|
||||
import android.system.ErrnoException;
|
||||
import android.system.Os;
|
||||
|
||||
import com.android.internal.annotations.VisibleForTesting;
|
||||
import com.android.modules.utils.build.SdkLevel;
|
||||
import com.android.net.module.util.BpfMap;
|
||||
import com.android.net.module.util.IBpfMap;
|
||||
import com.android.net.module.util.Struct;
|
||||
import com.android.net.module.util.Struct.S32;
|
||||
import com.android.net.module.util.Struct.U32;
|
||||
|
||||
/**
|
||||
* A helper class to *read* java BpfMaps.
|
||||
* @hide
|
||||
*/
|
||||
@RequiresApi(Build.VERSION_CODES.TIRAMISU) // BPF maps were only mainlined in T
|
||||
public class BpfNetMapsReader {
|
||||
// Locally store the handle of bpf maps. The FileDescriptors are statically cached inside the
|
||||
// BpfMap implementation.
|
||||
|
||||
// Bpf map to store various networking configurations, the format of the value is different
|
||||
// for different keys. See BpfNetMapsConstants#*_CONFIGURATION_KEY for keys.
|
||||
private final IBpfMap<S32, U32> mConfigurationMap;
|
||||
// Bpf map to store per uid traffic control configurations.
|
||||
// See {@link UidOwnerValue} for more detail.
|
||||
private final IBpfMap<S32, UidOwnerValue> mUidOwnerMap;
|
||||
private final Dependencies mDeps;
|
||||
|
||||
public BpfNetMapsReader() {
|
||||
this(new Dependencies());
|
||||
}
|
||||
|
||||
@VisibleForTesting
|
||||
public BpfNetMapsReader(@NonNull Dependencies deps) {
|
||||
if (!SdkLevel.isAtLeastT()) {
|
||||
throw new UnsupportedOperationException(
|
||||
BpfNetMapsReader.class.getSimpleName() + " is not supported below Android T");
|
||||
}
|
||||
mDeps = deps;
|
||||
mConfigurationMap = mDeps.getConfigurationMap();
|
||||
mUidOwnerMap = mDeps.getUidOwnerMap();
|
||||
}
|
||||
|
||||
/**
|
||||
* Dependencies of BpfNetMapReader, for injection in tests.
|
||||
*/
|
||||
@VisibleForTesting
|
||||
public static class Dependencies {
|
||||
/** Get the configuration map. */
|
||||
public IBpfMap<S32, U32> getConfigurationMap() {
|
||||
try {
|
||||
return new BpfMap<>(CONFIGURATION_MAP_PATH, BpfMap.BPF_F_RDONLY,
|
||||
S32.class, U32.class);
|
||||
} catch (ErrnoException e) {
|
||||
throw new IllegalStateException("Cannot open configuration map", e);
|
||||
}
|
||||
}
|
||||
|
||||
/** Get the uid owner map. */
|
||||
public IBpfMap<S32, UidOwnerValue> getUidOwnerMap() {
|
||||
try {
|
||||
return new BpfMap<>(UID_OWNER_MAP_PATH, BpfMap.BPF_F_RDONLY,
|
||||
S32.class, UidOwnerValue.class);
|
||||
} catch (ErrnoException e) {
|
||||
throw new IllegalStateException("Cannot open uid owner map", e);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Get the specified firewall chain's status.
|
||||
*
|
||||
* @param chain target chain
|
||||
* @return {@code true} if chain is enabled, {@code false} if chain is not enabled.
|
||||
* @throws UnsupportedOperationException if called on pre-T devices.
|
||||
* @throws ServiceSpecificException in case of failure, with an error code indicating the
|
||||
* cause of the failure.
|
||||
*/
|
||||
public boolean isChainEnabled(final int chain) {
|
||||
return isChainEnabled(mConfigurationMap, chain);
|
||||
}
|
||||
|
||||
/**
|
||||
* Get firewall rule of specified firewall chain on specified uid.
|
||||
*
|
||||
* @param chain target chain
|
||||
* @param uid target uid
|
||||
* @return either {@link ConnectivityManager#FIREWALL_RULE_ALLOW} or
|
||||
* {@link ConnectivityManager#FIREWALL_RULE_DENY}.
|
||||
* @throws UnsupportedOperationException if called on pre-T devices.
|
||||
* @throws ServiceSpecificException in case of failure, with an error code indicating the
|
||||
* cause of the failure.
|
||||
*/
|
||||
public int getUidRule(final int chain, final int uid) {
|
||||
return getUidRule(mUidOwnerMap, chain, uid);
|
||||
}
|
||||
|
||||
/**
|
||||
* Get the specified firewall chain's status.
|
||||
*
|
||||
* @param configurationMap target configurationMap
|
||||
* @param chain target chain
|
||||
* @return {@code true} if chain is enabled, {@code false} if chain is not enabled.
|
||||
* @throws UnsupportedOperationException if called on pre-T devices.
|
||||
* @throws ServiceSpecificException in case of failure, with an error code indicating the
|
||||
* cause of the failure.
|
||||
*/
|
||||
public static boolean isChainEnabled(
|
||||
final IBpfMap<Struct.S32, Struct.U32> configurationMap, final int chain) {
|
||||
throwIfPreT("isChainEnabled is not available on pre-T devices");
|
||||
|
||||
final long match = getMatchByFirewallChain(chain);
|
||||
try {
|
||||
final Struct.U32 config = configurationMap.getValue(UID_RULES_CONFIGURATION_KEY);
|
||||
return (config.val & match) != 0;
|
||||
} catch (ErrnoException e) {
|
||||
throw new ServiceSpecificException(e.errno,
|
||||
"Unable to get firewall chain status: " + Os.strerror(e.errno));
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Get firewall rule of specified firewall chain on specified uid.
|
||||
*
|
||||
* @param uidOwnerMap target uidOwnerMap.
|
||||
* @param chain target chain.
|
||||
* @param uid target uid.
|
||||
* @return either FIREWALL_RULE_ALLOW or FIREWALL_RULE_DENY
|
||||
* @throws UnsupportedOperationException if called on pre-T devices.
|
||||
* @throws ServiceSpecificException in case of failure, with an error code indicating the
|
||||
* cause of the failure.
|
||||
*/
|
||||
public static int getUidRule(final IBpfMap<Struct.S32, UidOwnerValue> uidOwnerMap,
|
||||
final int chain, final int uid) {
|
||||
throwIfPreT("getUidRule is not available on pre-T devices");
|
||||
|
||||
final long match = getMatchByFirewallChain(chain);
|
||||
final boolean isAllowList = isFirewallAllowList(chain);
|
||||
try {
|
||||
final UidOwnerValue uidMatch = uidOwnerMap.getValue(new Struct.S32(uid));
|
||||
final boolean isMatchEnabled = uidMatch != null && (uidMatch.rule & match) != 0;
|
||||
return isMatchEnabled == isAllowList ? FIREWALL_RULE_ALLOW : FIREWALL_RULE_DENY;
|
||||
} catch (ErrnoException e) {
|
||||
throw new ServiceSpecificException(e.errno,
|
||||
"Unable to get uid rule status: " + Os.strerror(e.errno));
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -39,6 +39,8 @@ import static android.system.OsConstants.EINVAL;
|
||||
import android.os.ServiceSpecificException;
|
||||
import android.util.Pair;
|
||||
|
||||
import com.android.modules.utils.build.SdkLevel;
|
||||
|
||||
import java.util.StringJoiner;
|
||||
|
||||
/**
|
||||
@@ -124,4 +126,15 @@ public class BpfNetMapsUtils {
|
||||
}
|
||||
return sj.toString();
|
||||
}
|
||||
|
||||
public static final boolean PRE_T = !SdkLevel.isAtLeastT();
|
||||
|
||||
/**
|
||||
* Throw UnsupportedOperationException if SdkLevel is before T.
|
||||
*/
|
||||
public static void throwIfPreT(final String msg) {
|
||||
if (PRE_T) {
|
||||
throw new UnsupportedOperationException(msg);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright (C) 2022 The Android Open Source Project
|
||||
* Copyright (C) 2023 The Android Open Source Project
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
@@ -14,11 +14,15 @@
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
package com.android.server;
|
||||
package android.net;
|
||||
|
||||
import com.android.net.module.util.Struct;
|
||||
|
||||
/** Value type for per uid traffic control configuration map */
|
||||
/**
|
||||
* Value type for per uid traffic control configuration map.
|
||||
*
|
||||
* @hide
|
||||
*/
|
||||
public class UidOwnerValue extends Struct {
|
||||
// Allowed interface index. Only applicable if IIF_MATCH is set in the rule bitmask below.
|
||||
@Field(order = 0, type = Type.S32)
|
||||
@@ -188,7 +188,6 @@ java_library {
|
||||
"dnsresolver_aidl_interface-V11-java",
|
||||
"modules-utils-shell-command-handler",
|
||||
"net-utils-device-common",
|
||||
"net-utils-device-common-bpf",
|
||||
"net-utils-device-common-ip",
|
||||
"net-utils-device-common-netlink",
|
||||
"net-utils-services-common",
|
||||
|
||||
@@ -26,6 +26,7 @@ import static android.net.BpfNetMapsConstants.PENALTY_BOX_MATCH;
|
||||
import static android.net.BpfNetMapsConstants.UID_OWNER_MAP_PATH;
|
||||
import static android.net.BpfNetMapsConstants.UID_PERMISSION_MAP_PATH;
|
||||
import static android.net.BpfNetMapsConstants.UID_RULES_CONFIGURATION_KEY;
|
||||
import static android.net.BpfNetMapsUtils.PRE_T;
|
||||
import static android.net.BpfNetMapsUtils.getMatchByFirewallChain;
|
||||
import static android.net.BpfNetMapsUtils.matchToString;
|
||||
import static android.net.ConnectivityManager.FIREWALL_CHAIN_DOZABLE;
|
||||
@@ -51,7 +52,9 @@ import static com.android.server.ConnectivityStatsLog.NETWORK_BPF_MAP_INFO;
|
||||
|
||||
import android.app.StatsManager;
|
||||
import android.content.Context;
|
||||
import android.net.BpfNetMapsReader;
|
||||
import android.net.INetd;
|
||||
import android.net.UidOwnerValue;
|
||||
import android.os.Build;
|
||||
import android.os.RemoteException;
|
||||
import android.os.ServiceSpecificException;
|
||||
@@ -92,7 +95,6 @@ import java.util.StringJoiner;
|
||||
* {@hide}
|
||||
*/
|
||||
public class BpfNetMaps {
|
||||
private static final boolean PRE_T = !SdkLevel.isAtLeastT();
|
||||
static {
|
||||
if (!PRE_T) {
|
||||
System.loadLibrary("service-connectivity");
|
||||
@@ -298,6 +300,7 @@ public class BpfNetMaps {
|
||||
}
|
||||
|
||||
/** Constructor used after T that doesn't need to use netd anymore. */
|
||||
@RequiresApi(Build.VERSION_CODES.TIRAMISU)
|
||||
public BpfNetMaps(final Context context) {
|
||||
this(context, null);
|
||||
|
||||
@@ -420,6 +423,7 @@ public class BpfNetMaps {
|
||||
* @throws ServiceSpecificException in case of failure, with an error code indicating the
|
||||
* cause of the failure.
|
||||
*/
|
||||
@RequiresApi(Build.VERSION_CODES.TIRAMISU)
|
||||
public void addNaughtyApp(final int uid) {
|
||||
throwIfPreT("addNaughtyApp is not available on pre-T devices");
|
||||
|
||||
@@ -438,6 +442,7 @@ public class BpfNetMaps {
|
||||
* @throws ServiceSpecificException in case of failure, with an error code indicating the
|
||||
* cause of the failure.
|
||||
*/
|
||||
@RequiresApi(Build.VERSION_CODES.TIRAMISU)
|
||||
public void removeNaughtyApp(final int uid) {
|
||||
throwIfPreT("removeNaughtyApp is not available on pre-T devices");
|
||||
|
||||
@@ -456,6 +461,7 @@ public class BpfNetMaps {
|
||||
* @throws ServiceSpecificException in case of failure, with an error code indicating the
|
||||
* cause of the failure.
|
||||
*/
|
||||
@RequiresApi(Build.VERSION_CODES.TIRAMISU)
|
||||
public void addNiceApp(final int uid) {
|
||||
throwIfPreT("addNiceApp is not available on pre-T devices");
|
||||
|
||||
@@ -474,6 +480,7 @@ public class BpfNetMaps {
|
||||
* @throws ServiceSpecificException in case of failure, with an error code indicating the
|
||||
* cause of the failure.
|
||||
*/
|
||||
@RequiresApi(Build.VERSION_CODES.TIRAMISU)
|
||||
public void removeNiceApp(final int uid) {
|
||||
throwIfPreT("removeNiceApp is not available on pre-T devices");
|
||||
|
||||
@@ -494,6 +501,7 @@ public class BpfNetMaps {
|
||||
* @throws ServiceSpecificException in case of failure, with an error code indicating the
|
||||
* cause of the failure.
|
||||
*/
|
||||
@RequiresApi(Build.VERSION_CODES.TIRAMISU)
|
||||
public void setChildChain(final int childChain, final boolean enable) {
|
||||
throwIfPreT("setChildChain is not available on pre-T devices");
|
||||
|
||||
@@ -523,18 +531,14 @@ public class BpfNetMaps {
|
||||
* @throws UnsupportedOperationException if called on pre-T devices.
|
||||
* @throws ServiceSpecificException in case of failure, with an error code indicating the
|
||||
* cause of the failure.
|
||||
*
|
||||
* @deprecated Use {@link BpfNetMapsReader#isChainEnabled} instead.
|
||||
*/
|
||||
// TODO: Migrate the callers to use {@link BpfNetMapsReader#isChainEnabled} instead.
|
||||
@Deprecated
|
||||
@RequiresApi(Build.VERSION_CODES.TIRAMISU)
|
||||
public boolean isChainEnabled(final int childChain) {
|
||||
throwIfPreT("isChainEnabled is not available on pre-T devices");
|
||||
|
||||
final long match = getMatchByFirewallChain(childChain);
|
||||
try {
|
||||
final U32 config = sConfigurationMap.getValue(UID_RULES_CONFIGURATION_KEY);
|
||||
return (config.val & match) != 0;
|
||||
} catch (ErrnoException e) {
|
||||
throw new ServiceSpecificException(e.errno,
|
||||
"Unable to get firewall chain status: " + Os.strerror(e.errno));
|
||||
}
|
||||
return BpfNetMapsReader.isChainEnabled(sConfigurationMap, childChain);
|
||||
}
|
||||
|
||||
private Set<Integer> asSet(final int[] uids) {
|
||||
@@ -554,6 +558,7 @@ public class BpfNetMaps {
|
||||
* @throws UnsupportedOperationException if called on pre-T devices.
|
||||
* @throws IllegalArgumentException if {@code chain} is not a valid chain.
|
||||
*/
|
||||
@RequiresApi(Build.VERSION_CODES.TIRAMISU)
|
||||
public void replaceUidChain(final int chain, final int[] uids) {
|
||||
throwIfPreT("replaceUidChain is not available on pre-T devices");
|
||||
|
||||
@@ -638,6 +643,7 @@ public class BpfNetMaps {
|
||||
* @throws ServiceSpecificException in case of failure, with an error code indicating the
|
||||
* cause of the failure.
|
||||
*/
|
||||
@RequiresApi(Build.VERSION_CODES.TIRAMISU)
|
||||
public void setUidRule(final int childChain, final int uid, final int firewallRule) {
|
||||
throwIfPreT("setUidRule is not available on pre-T devices");
|
||||
|
||||
@@ -667,20 +673,12 @@ public class BpfNetMaps {
|
||||
* @throws UnsupportedOperationException if called on pre-T devices.
|
||||
* @throws ServiceSpecificException in case of failure, with an error code indicating the
|
||||
* cause of the failure.
|
||||
*
|
||||
* @deprecated use {@link BpfNetMapsReader#getUidRule} instead.
|
||||
*/
|
||||
// TODO: Migrate the callers to use {@link BpfNetMapsReader#getUidRule} instead.
|
||||
public int getUidRule(final int childChain, final int uid) {
|
||||
throwIfPreT("isUidChainEnabled is not available on pre-T devices");
|
||||
|
||||
final long match = getMatchByFirewallChain(childChain);
|
||||
final boolean isAllowList = isFirewallAllowList(childChain);
|
||||
try {
|
||||
final UidOwnerValue uidMatch = sUidOwnerMap.getValue(new S32(uid));
|
||||
final boolean isMatchEnabled = uidMatch != null && (uidMatch.rule & match) != 0;
|
||||
return isMatchEnabled == isAllowList ? FIREWALL_RULE_ALLOW : FIREWALL_RULE_DENY;
|
||||
} catch (ErrnoException e) {
|
||||
throw new ServiceSpecificException(e.errno,
|
||||
"Unable to get uid rule status: " + Os.strerror(e.errno));
|
||||
}
|
||||
return BpfNetMapsReader.getUidRule(sUidOwnerMap, childChain, uid);
|
||||
}
|
||||
|
||||
private Set<Integer> getUidsMatchEnabled(final int childChain) throws ErrnoException {
|
||||
@@ -830,6 +828,7 @@ public class BpfNetMaps {
|
||||
* @throws ServiceSpecificException in case of failure, with an error code indicating the
|
||||
* cause of the failure.
|
||||
*/
|
||||
@RequiresApi(Build.VERSION_CODES.TIRAMISU)
|
||||
public void updateUidLockdownRule(final int uid, final boolean add) {
|
||||
throwIfPreT("updateUidLockdownRule is not available on pre-T devices");
|
||||
|
||||
@@ -852,6 +851,7 @@ public class BpfNetMaps {
|
||||
* @throws ServiceSpecificException in case of failure, with an error code indicating the
|
||||
* cause of the failure.
|
||||
*/
|
||||
@RequiresApi(Build.VERSION_CODES.TIRAMISU)
|
||||
public void swapActiveStatsMap() {
|
||||
throwIfPreT("swapActiveStatsMap is not available on pre-T devices");
|
||||
|
||||
@@ -927,6 +927,7 @@ public class BpfNetMaps {
|
||||
}
|
||||
|
||||
/** Register callback for statsd to pull atom. */
|
||||
@RequiresApi(Build.VERSION_CODES.TIRAMISU)
|
||||
public void setPullAtomCallback(final Context context) {
|
||||
throwIfPreT("setPullAtomCallback is not available on pre-T devices");
|
||||
|
||||
@@ -1016,6 +1017,7 @@ public class BpfNetMaps {
|
||||
* @throws IOException when file descriptor is invalid.
|
||||
* @throws ServiceSpecificException when the method is called on an unsupported device.
|
||||
*/
|
||||
@RequiresApi(Build.VERSION_CODES.TIRAMISU)
|
||||
public void dump(final IndentingPrintWriter pw, final FileDescriptor fd, boolean verbose)
|
||||
throws IOException, ServiceSpecificException {
|
||||
if (PRE_T) {
|
||||
|
||||
@@ -181,6 +181,8 @@ java_library {
|
||||
},
|
||||
}
|
||||
|
||||
// The net-utils-device-common-netlink library requires the callers to contain
|
||||
// net-utils-device-common-struct.
|
||||
java_library {
|
||||
name: "net-utils-device-common-netlink",
|
||||
srcs: [
|
||||
@@ -192,12 +194,13 @@ java_library {
|
||||
"//packages/modules/Connectivity:__subpackages__",
|
||||
"//packages/modules/NetworkStack:__subpackages__",
|
||||
],
|
||||
static_libs: [
|
||||
"net-utils-device-common-struct",
|
||||
],
|
||||
libs: [
|
||||
"androidx.annotation_annotation",
|
||||
"framework-connectivity.stubs.module_lib",
|
||||
// For libraries which are statically linked in framework-connectivity, do not
|
||||
// statically link here because callers of this library might already have a static
|
||||
// version linked.
|
||||
"net-utils-device-common-struct",
|
||||
],
|
||||
apex_available: [
|
||||
"com.android.tethering",
|
||||
@@ -209,6 +212,8 @@ java_library {
|
||||
},
|
||||
}
|
||||
|
||||
// The net-utils-device-common-ip library requires the callers to contain
|
||||
// net-utils-device-common-struct.
|
||||
java_library {
|
||||
// TODO : this target should probably be folded into net-utils-device-common
|
||||
name: "net-utils-device-common-ip",
|
||||
|
||||
@@ -38,6 +38,7 @@ java_library {
|
||||
"net-utils-device-common",
|
||||
"net-utils-device-common-async",
|
||||
"net-utils-device-common-netlink",
|
||||
"net-utils-device-common-struct",
|
||||
"net-utils-device-common-wear",
|
||||
"modules-utils-build_system",
|
||||
],
|
||||
|
||||
@@ -43,6 +43,8 @@ import java.util.concurrent.ConcurrentHashMap;
|
||||
public class TestBpfMap<K extends Struct, V extends Struct> implements IBpfMap<K, V> {
|
||||
private final ConcurrentHashMap<K, V> mMap = new ConcurrentHashMap<>();
|
||||
|
||||
public TestBpfMap() {}
|
||||
|
||||
// TODO: Remove this constructor
|
||||
public TestBpfMap(final Class<K> key, final Class<V> value) {
|
||||
}
|
||||
|
||||
69
tests/unit/java/android/net/BpfNetMapsReaderTest.kt
Normal file
69
tests/unit/java/android/net/BpfNetMapsReaderTest.kt
Normal file
@@ -0,0 +1,69 @@
|
||||
/*
|
||||
* Copyright (C) 2023 The Android Open Source Project
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
package android.net
|
||||
|
||||
import android.net.BpfNetMapsConstants.UID_RULES_CONFIGURATION_KEY
|
||||
import android.net.BpfNetMapsUtils.getMatchByFirewallChain
|
||||
import android.os.Build
|
||||
import com.android.net.module.util.IBpfMap
|
||||
import com.android.net.module.util.Struct.S32
|
||||
import com.android.net.module.util.Struct.U32
|
||||
import com.android.testutils.DevSdkIgnoreRule.IgnoreUpTo
|
||||
import com.android.testutils.DevSdkIgnoreRunner
|
||||
import com.android.testutils.TestBpfMap
|
||||
import kotlin.test.assertFalse
|
||||
import kotlin.test.assertTrue
|
||||
import org.junit.Test
|
||||
import org.junit.runner.RunWith
|
||||
|
||||
// pre-T devices does not support Bpf.
|
||||
@RunWith(DevSdkIgnoreRunner::class)
|
||||
@IgnoreUpTo(Build.VERSION_CODES.S_V2)
|
||||
class BpfNetMapsReaderTest {
|
||||
private val testConfigurationMap: IBpfMap<S32, U32> = TestBpfMap()
|
||||
private val testUidOwnerMap: IBpfMap<S32, UidOwnerValue> = TestBpfMap()
|
||||
private val bpfNetMapsReader = BpfNetMapsReader(
|
||||
TestDependencies(testConfigurationMap, testUidOwnerMap))
|
||||
|
||||
class TestDependencies(
|
||||
private val configMap: IBpfMap<S32, U32>,
|
||||
private val uidOwnerMap: IBpfMap<S32, UidOwnerValue>
|
||||
) : BpfNetMapsReader.Dependencies() {
|
||||
override fun getConfigurationMap() = configMap
|
||||
override fun getUidOwnerMap() = uidOwnerMap
|
||||
}
|
||||
|
||||
private fun doTestIsChainEnabled(chain: Int) {
|
||||
testConfigurationMap.updateEntry(
|
||||
UID_RULES_CONFIGURATION_KEY,
|
||||
U32(getMatchByFirewallChain(chain))
|
||||
)
|
||||
assertTrue(bpfNetMapsReader.isChainEnabled(chain))
|
||||
testConfigurationMap.updateEntry(UID_RULES_CONFIGURATION_KEY, U32(0))
|
||||
assertFalse(bpfNetMapsReader.isChainEnabled(chain))
|
||||
}
|
||||
|
||||
@Test
|
||||
@Throws(Exception::class)
|
||||
fun testIsChainEnabled() {
|
||||
doTestIsChainEnabled(ConnectivityManager.FIREWALL_CHAIN_DOZABLE)
|
||||
doTestIsChainEnabled(ConnectivityManager.FIREWALL_CHAIN_STANDBY)
|
||||
doTestIsChainEnabled(ConnectivityManager.FIREWALL_CHAIN_POWERSAVE)
|
||||
doTestIsChainEnabled(ConnectivityManager.FIREWALL_CHAIN_RESTRICTED)
|
||||
doTestIsChainEnabled(ConnectivityManager.FIREWALL_CHAIN_LOW_POWER_STANDBY)
|
||||
}
|
||||
}
|
||||
@@ -66,6 +66,7 @@ import android.app.StatsManager;
|
||||
import android.content.Context;
|
||||
import android.net.BpfNetMapsUtils;
|
||||
import android.net.INetd;
|
||||
import android.net.UidOwnerValue;
|
||||
import android.os.Build;
|
||||
import android.os.ServiceSpecificException;
|
||||
import android.system.ErrnoException;
|
||||
|
||||
Reference in New Issue
Block a user