[ST01] Attributes data usage of test network by specifier

Currently, data usage of all test networks are all attributed to
the same NetworkIdentity, which does not allow services to
distinguish upload & download traffic of different test networks.

Thus, this CL put specifier that comes along with
TestNetworkAgent into wifiNetworkKey field to build different
NetworkIdentity to attribute data usage to different for
individual networks. And allow querying test network usage with
wifiNetworkKeys.

Bug: 139774492
Test: atest FrameworksNetTests
      atest android.net.cts.ConnectivityManagerTest
Change-Id: I1bb38fd20781eaf3105735440a04b27bef36fcae
This commit is contained in:
Junyu Lai
2022-07-25 16:31:59 +08:00
parent d407328dd4
commit c9f1ca62d9
5 changed files with 149 additions and 21 deletions

View File

@@ -85,6 +85,12 @@ public class NetworkIdentity {
private static final long SUPPORTED_OEM_MANAGED_TYPES = OEM_PAID | OEM_PRIVATE;
// Need to be synchronized with ConnectivityManager.
// TODO: Use {@code ConnectivityManager#*} when visible.
static final int TYPE_TEST = 18;
private static final int MAX_NETWORK_TYPE = TYPE_TEST;
private static final int MIN_NETWORK_TYPE = TYPE_MOBILE;
final int mType;
final int mRatType;
final int mSubId;
@@ -346,11 +352,6 @@ public class NetworkIdentity {
* Builder class for {@link NetworkIdentity}.
*/
public static final class Builder {
// Need to be synchronized with ConnectivityManager.
// TODO: Use {@link ConnectivityManager#MAX_NETWORK_TYPE} when this file is in the module.
private static final int MAX_NETWORK_TYPE = 18; // TYPE_TEST
private static final int MIN_NETWORK_TYPE = TYPE_MOBILE;
private int mType;
private int mRatType;
private String mSubscriberId;
@@ -413,6 +414,12 @@ public class NetworkIdentity {
final WifiInfo info = (WifiInfo) transportInfo;
setWifiNetworkKey(info.getNetworkKey());
}
} else if (mType == TYPE_TEST) {
final NetworkSpecifier ns = snapshot.getNetworkCapabilities().getNetworkSpecifier();
if (ns instanceof TestNetworkSpecifier) {
// Reuse the wifi network key field to identify individual test networks.
setWifiNetworkKey(((TestNetworkSpecifier) ns).getInterfaceName());
}
}
return this;
}
@@ -574,7 +581,7 @@ public class NetworkIdentity {
}
// Assert non-wifi network cannot have a wifi network key.
if (mType != TYPE_WIFI && mWifiNetworkKey != null) {
if (mType != TYPE_WIFI && mType != TYPE_TEST && mWifiNetworkKey != null) {
throw new IllegalArgumentException("Invalid wifi network key for type " + mType);
}
}

View File

@@ -50,6 +50,7 @@ import android.os.Parcelable;
import android.text.TextUtils;
import android.util.ArraySet;
import com.android.internal.annotations.VisibleForTesting;
import com.android.net.module.util.CollectionUtils;
import com.android.net.module.util.NetworkIdentityUtils;
import com.android.net.module.util.NetworkStatsUtils;
@@ -114,6 +115,14 @@ public final class NetworkTemplate implements Parcelable {
* may offer non-cellular networks like WiFi, which will be matched by this rule.
*/
public static final int MATCH_CARRIER = 10;
/**
* Match rule to match networks with {@link ConnectivityManager#TYPE_TEST} as the legacy
* network type.
*
* @hide
*/
@VisibleForTesting
public static final int MATCH_TEST = 11;
// TODO: Remove this and replace all callers with WIFI_NETWORK_KEY_ALL.
/** @hide */
@@ -176,6 +185,7 @@ public final class NetworkTemplate implements Parcelable {
case MATCH_BLUETOOTH:
case MATCH_PROXY:
case MATCH_CARRIER:
case MATCH_TEST:
return true;
default:
@@ -666,6 +676,8 @@ public final class NetworkTemplate implements Parcelable {
return matchesProxy(ident);
case MATCH_CARRIER:
return matchesCarrier(ident);
case MATCH_TEST:
return matchesTest(ident);
default:
// We have no idea what kind of network template we are, so we
// just claim not to match anything.
@@ -776,6 +788,17 @@ public final class NetworkTemplate implements Parcelable {
&& CollectionUtils.contains(mMatchSubscriberIds, ident.mSubscriberId);
}
/**
* Check if matches test network. If the wifiNetworkKeys in the template is specified, Then it
* will only match a network containing any of the specified the wifi network key. Otherwise,
* all test networks would be matched.
*/
private boolean matchesTest(NetworkIdentity ident) {
return ident.mType == NetworkIdentity.TYPE_TEST
&& ((CollectionUtils.isEmpty(mMatchWifiNetworkKeys)
|| CollectionUtils.contains(mMatchWifiNetworkKeys, ident.mWifiNetworkKey)));
}
private boolean matchesMobileWildcard(NetworkIdentity ident) {
if (ident.mType == TYPE_WIMAX) {
return true;
@@ -829,6 +852,8 @@ public final class NetworkTemplate implements Parcelable {
return "PROXY";
case MATCH_CARRIER:
return "CARRIER";
case MATCH_TEST:
return "TEST";
default:
return "UNKNOWN(" + matchRule + ")";
}
@@ -1079,7 +1104,9 @@ public final class NetworkTemplate implements Parcelable {
}
private void validateWifiNetworkKeys() {
if (mMatchRule != MATCH_WIFI && !mMatchWifiNetworkKeys.isEmpty()) {
// Also allow querying test networks which use wifi network key as identifier.
if (mMatchRule != MATCH_WIFI && mMatchRule != MATCH_TEST
&& !mMatchWifiNetworkKeys.isEmpty()) {
throw new IllegalArgumentException("Trying to build non wifi match rule: "
+ mMatchRule + " with wifi network keys");
}