Merge changes I6eca0331,I346323cb am: c9af6cf307 am: 63dde898b5
Original change: https://android-review.googlesource.com/c/platform/frameworks/base/+/2320254 Change-Id: I07980f3dd02ac55b437c3c45e3e4bea50a1a7292 Signed-off-by: Automerger Merge Worker <android-build-automerger-merge-worker@system.gserviceaccount.com>
This commit is contained in:
@@ -353,6 +353,11 @@ public final class VcnCellUnderlyingNetworkTemplate extends VcnUnderlyingNetwork
|
|||||||
return mCapabilitiesMatchCriteria.get(NET_CAPABILITY_RCS);
|
return mCapabilitiesMatchCriteria.get(NET_CAPABILITY_RCS);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/** @hide */
|
||||||
|
public Map<Integer, Integer> getCapabilitiesMatchCriteria() {
|
||||||
|
return Collections.unmodifiableMap(new HashMap<>(mCapabilitiesMatchCriteria));
|
||||||
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public int hashCode() {
|
public int hashCode() {
|
||||||
return Objects.hash(
|
return Objects.hash(
|
||||||
|
|||||||
@@ -15,6 +15,7 @@
|
|||||||
*/
|
*/
|
||||||
package com.android.server.vcn.routeselection;
|
package com.android.server.vcn.routeselection;
|
||||||
|
|
||||||
|
import static android.net.NetworkCapabilities.NET_CAPABILITY_INTERNET;
|
||||||
import static android.net.NetworkCapabilities.NET_CAPABILITY_NOT_METERED;
|
import static android.net.NetworkCapabilities.NET_CAPABILITY_NOT_METERED;
|
||||||
import static android.net.NetworkCapabilities.NET_CAPABILITY_NOT_ROAMING;
|
import static android.net.NetworkCapabilities.NET_CAPABILITY_NOT_ROAMING;
|
||||||
import static android.net.NetworkCapabilities.TRANSPORT_CELLULAR;
|
import static android.net.NetworkCapabilities.TRANSPORT_CELLULAR;
|
||||||
@@ -45,6 +46,7 @@ import com.android.server.vcn.TelephonySubscriptionTracker.TelephonySubscription
|
|||||||
import com.android.server.vcn.VcnContext;
|
import com.android.server.vcn.VcnContext;
|
||||||
|
|
||||||
import java.util.List;
|
import java.util.List;
|
||||||
|
import java.util.Map;
|
||||||
import java.util.Objects;
|
import java.util.Objects;
|
||||||
import java.util.Set;
|
import java.util.Set;
|
||||||
|
|
||||||
@@ -69,9 +71,23 @@ class NetworkPriorityClassifier {
|
|||||||
@VisibleForTesting(visibility = Visibility.PRIVATE)
|
@VisibleForTesting(visibility = Visibility.PRIVATE)
|
||||||
static final int WIFI_EXIT_RSSI_THRESHOLD_DEFAULT = -74;
|
static final int WIFI_EXIT_RSSI_THRESHOLD_DEFAULT = -74;
|
||||||
|
|
||||||
/** Priority for any other networks (including unvalidated, etc) */
|
/**
|
||||||
|
* Priority for networks that VCN can fall back to.
|
||||||
|
*
|
||||||
|
* <p>If none of the network candidates are validated or match any template, VCN will fall back
|
||||||
|
* to any INTERNET network.
|
||||||
|
*/
|
||||||
@VisibleForTesting(visibility = Visibility.PRIVATE)
|
@VisibleForTesting(visibility = Visibility.PRIVATE)
|
||||||
static final int PRIORITY_ANY = Integer.MAX_VALUE;
|
static final int PRIORITY_FALLBACK = Integer.MAX_VALUE;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Priority for networks that cannot be selected as VCN's underlying networks.
|
||||||
|
*
|
||||||
|
* <p>VCN MUST never select a non-INTERNET network that are unvalidated or fail to match any
|
||||||
|
* template as the underlying network.
|
||||||
|
*/
|
||||||
|
@VisibleForTesting(visibility = Visibility.PRIVATE)
|
||||||
|
static final int PRIORITY_INVALID = -1;
|
||||||
|
|
||||||
/** Gives networks a priority class, based on configured VcnGatewayConnectionConfig */
|
/** Gives networks a priority class, based on configured VcnGatewayConnectionConfig */
|
||||||
public static int calculatePriorityClass(
|
public static int calculatePriorityClass(
|
||||||
@@ -86,12 +102,12 @@ class NetworkPriorityClassifier {
|
|||||||
|
|
||||||
if (networkRecord.isBlocked) {
|
if (networkRecord.isBlocked) {
|
||||||
logWtf("Network blocked for System Server: " + networkRecord.network);
|
logWtf("Network blocked for System Server: " + networkRecord.network);
|
||||||
return PRIORITY_ANY;
|
return PRIORITY_INVALID;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (snapshot == null) {
|
if (snapshot == null) {
|
||||||
logWtf("Got null snapshot");
|
logWtf("Got null snapshot");
|
||||||
return PRIORITY_ANY;
|
return PRIORITY_INVALID;
|
||||||
}
|
}
|
||||||
|
|
||||||
int priorityIndex = 0;
|
int priorityIndex = 0;
|
||||||
@@ -108,7 +124,13 @@ class NetworkPriorityClassifier {
|
|||||||
}
|
}
|
||||||
priorityIndex++;
|
priorityIndex++;
|
||||||
}
|
}
|
||||||
return PRIORITY_ANY;
|
|
||||||
|
final NetworkCapabilities caps = networkRecord.networkCapabilities;
|
||||||
|
if (caps.hasCapability(NET_CAPABILITY_INTERNET)
|
||||||
|
|| (vcnContext.isInTestMode() && caps.hasTransport(TRANSPORT_TEST))) {
|
||||||
|
return PRIORITY_FALLBACK;
|
||||||
|
}
|
||||||
|
return PRIORITY_INVALID;
|
||||||
}
|
}
|
||||||
|
|
||||||
@VisibleForTesting(visibility = Visibility.PRIVATE)
|
@VisibleForTesting(visibility = Visibility.PRIVATE)
|
||||||
@@ -297,6 +319,18 @@ class NetworkPriorityClassifier {
|
|||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
for (Map.Entry<Integer, Integer> entry :
|
||||||
|
networkPriority.getCapabilitiesMatchCriteria().entrySet()) {
|
||||||
|
final int cap = entry.getKey();
|
||||||
|
final int matchCriteria = entry.getValue();
|
||||||
|
|
||||||
|
if (matchCriteria == MATCH_REQUIRED && !caps.hasCapability(cap)) {
|
||||||
|
return false;
|
||||||
|
} else if (matchCriteria == MATCH_FORBIDDEN && caps.hasCapability(cap)) {
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -16,6 +16,9 @@
|
|||||||
|
|
||||||
package com.android.server.vcn.routeselection;
|
package com.android.server.vcn.routeselection;
|
||||||
|
|
||||||
|
import static android.net.vcn.VcnUnderlyingNetworkTemplate.MATCH_ANY;
|
||||||
|
import static android.net.vcn.VcnUnderlyingNetworkTemplate.MATCH_FORBIDDEN;
|
||||||
|
import static android.net.vcn.VcnUnderlyingNetworkTemplate.MATCH_REQUIRED;
|
||||||
import static android.telephony.TelephonyCallback.ActiveDataSubscriptionIdListener;
|
import static android.telephony.TelephonyCallback.ActiveDataSubscriptionIdListener;
|
||||||
|
|
||||||
import static com.android.server.VcnManagementService.LOCAL_LOG;
|
import static com.android.server.VcnManagementService.LOCAL_LOG;
|
||||||
@@ -32,6 +35,7 @@ import android.net.Network;
|
|||||||
import android.net.NetworkCapabilities;
|
import android.net.NetworkCapabilities;
|
||||||
import android.net.NetworkRequest;
|
import android.net.NetworkRequest;
|
||||||
import android.net.TelephonyNetworkSpecifier;
|
import android.net.TelephonyNetworkSpecifier;
|
||||||
|
import android.net.vcn.VcnCellUnderlyingNetworkTemplate;
|
||||||
import android.net.vcn.VcnGatewayConnectionConfig;
|
import android.net.vcn.VcnGatewayConnectionConfig;
|
||||||
import android.net.vcn.VcnUnderlyingNetworkTemplate;
|
import android.net.vcn.VcnUnderlyingNetworkTemplate;
|
||||||
import android.os.Handler;
|
import android.os.Handler;
|
||||||
@@ -40,6 +44,7 @@ import android.os.ParcelUuid;
|
|||||||
import android.telephony.TelephonyCallback;
|
import android.telephony.TelephonyCallback;
|
||||||
import android.telephony.TelephonyManager;
|
import android.telephony.TelephonyManager;
|
||||||
import android.util.ArrayMap;
|
import android.util.ArrayMap;
|
||||||
|
import android.util.ArraySet;
|
||||||
import android.util.Slog;
|
import android.util.Slog;
|
||||||
|
|
||||||
import com.android.internal.annotations.VisibleForTesting;
|
import com.android.internal.annotations.VisibleForTesting;
|
||||||
@@ -49,6 +54,7 @@ import com.android.server.vcn.VcnContext;
|
|||||||
import com.android.server.vcn.util.LogUtils;
|
import com.android.server.vcn.util.LogUtils;
|
||||||
|
|
||||||
import java.util.ArrayList;
|
import java.util.ArrayList;
|
||||||
|
import java.util.Collections;
|
||||||
import java.util.List;
|
import java.util.List;
|
||||||
import java.util.Map;
|
import java.util.Map;
|
||||||
import java.util.Objects;
|
import java.util.Objects;
|
||||||
@@ -126,6 +132,63 @@ public class UnderlyingNetworkController {
|
|||||||
registerOrUpdateNetworkRequests();
|
registerOrUpdateNetworkRequests();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
private static class CapabilityMatchCriteria {
|
||||||
|
public final int capability;
|
||||||
|
public final int matchCriteria;
|
||||||
|
|
||||||
|
CapabilityMatchCriteria(int capability, int matchCriteria) {
|
||||||
|
this.capability = capability;
|
||||||
|
this.matchCriteria = matchCriteria;
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public int hashCode() {
|
||||||
|
return Objects.hash(capability, matchCriteria);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public boolean equals(@Nullable Object other) {
|
||||||
|
if (!(other instanceof CapabilityMatchCriteria)) {
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
final CapabilityMatchCriteria rhs = (CapabilityMatchCriteria) other;
|
||||||
|
return capability == rhs.capability && matchCriteria == rhs.matchCriteria;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
private static Set<Set<CapabilityMatchCriteria>> dedupAndGetCapRequirementsForCell(
|
||||||
|
VcnGatewayConnectionConfig connectionConfig) {
|
||||||
|
final Set<Set<CapabilityMatchCriteria>> dedupedCapsMatchSets = new ArraySet<>();
|
||||||
|
|
||||||
|
for (VcnUnderlyingNetworkTemplate template :
|
||||||
|
connectionConfig.getVcnUnderlyingNetworkPriorities()) {
|
||||||
|
if (template instanceof VcnCellUnderlyingNetworkTemplate) {
|
||||||
|
final Set<CapabilityMatchCriteria> capsMatchSet = new ArraySet<>();
|
||||||
|
|
||||||
|
for (Map.Entry<Integer, Integer> entry :
|
||||||
|
((VcnCellUnderlyingNetworkTemplate) template)
|
||||||
|
.getCapabilitiesMatchCriteria()
|
||||||
|
.entrySet()) {
|
||||||
|
|
||||||
|
final int capability = entry.getKey();
|
||||||
|
final int matchCriteria = entry.getValue();
|
||||||
|
if (matchCriteria != MATCH_ANY) {
|
||||||
|
capsMatchSet.add(new CapabilityMatchCriteria(capability, matchCriteria));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
dedupedCapsMatchSets.add(capsMatchSet);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
dedupedCapsMatchSets.add(
|
||||||
|
Collections.singleton(
|
||||||
|
new CapabilityMatchCriteria(
|
||||||
|
NetworkCapabilities.NET_CAPABILITY_INTERNET, MATCH_REQUIRED)));
|
||||||
|
return dedupedCapsMatchSets;
|
||||||
|
}
|
||||||
|
|
||||||
private void registerOrUpdateNetworkRequests() {
|
private void registerOrUpdateNetworkRequests() {
|
||||||
NetworkCallback oldRouteSelectionCallback = mRouteSelectionCallback;
|
NetworkCallback oldRouteSelectionCallback = mRouteSelectionCallback;
|
||||||
NetworkCallback oldWifiCallback = mWifiBringupCallback;
|
NetworkCallback oldWifiCallback = mWifiBringupCallback;
|
||||||
@@ -158,11 +221,14 @@ public class UnderlyingNetworkController {
|
|||||||
getWifiNetworkRequest(), mWifiBringupCallback, mHandler);
|
getWifiNetworkRequest(), mWifiBringupCallback, mHandler);
|
||||||
|
|
||||||
for (final int subId : mLastSnapshot.getAllSubIdsInGroup(mSubscriptionGroup)) {
|
for (final int subId : mLastSnapshot.getAllSubIdsInGroup(mSubscriptionGroup)) {
|
||||||
|
for (Set<CapabilityMatchCriteria> capsMatchCriteria :
|
||||||
|
dedupAndGetCapRequirementsForCell(mConnectionConfig)) {
|
||||||
final NetworkBringupCallback cb = new NetworkBringupCallback();
|
final NetworkBringupCallback cb = new NetworkBringupCallback();
|
||||||
mCellBringupCallbacks.add(cb);
|
mCellBringupCallbacks.add(cb);
|
||||||
|
|
||||||
mConnectivityManager.requestBackgroundNetwork(
|
mConnectivityManager.requestBackgroundNetwork(
|
||||||
getCellNetworkRequestForSubId(subId), cb, mHandler);
|
getCellNetworkRequestForSubId(subId, capsMatchCriteria), cb, mHandler);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
mRouteSelectionCallback = null;
|
mRouteSelectionCallback = null;
|
||||||
@@ -214,6 +280,13 @@ public class UnderlyingNetworkController {
|
|||||||
.build();
|
.build();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
private NetworkRequest.Builder getBaseWifiNetworkRequestBuilder() {
|
||||||
|
return getBaseNetworkRequestBuilder()
|
||||||
|
.addTransportType(NetworkCapabilities.TRANSPORT_WIFI)
|
||||||
|
.addCapability(NetworkCapabilities.NET_CAPABILITY_INTERNET)
|
||||||
|
.setSubscriptionIds(mLastSnapshot.getAllSubIdsInGroup(mSubscriptionGroup));
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Builds the WiFi bringup request
|
* Builds the WiFi bringup request
|
||||||
*
|
*
|
||||||
@@ -224,10 +297,7 @@ public class UnderlyingNetworkController {
|
|||||||
* but will NEVER bring up a Carrier WiFi network itself.
|
* but will NEVER bring up a Carrier WiFi network itself.
|
||||||
*/
|
*/
|
||||||
private NetworkRequest getWifiNetworkRequest() {
|
private NetworkRequest getWifiNetworkRequest() {
|
||||||
return getBaseNetworkRequestBuilder()
|
return getBaseWifiNetworkRequestBuilder().build();
|
||||||
.addTransportType(NetworkCapabilities.TRANSPORT_WIFI)
|
|
||||||
.setSubscriptionIds(mLastSnapshot.getAllSubIdsInGroup(mSubscriptionGroup))
|
|
||||||
.build();
|
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -238,9 +308,7 @@ public class UnderlyingNetworkController {
|
|||||||
* pace to effectively select a short-lived WiFi offload network.
|
* pace to effectively select a short-lived WiFi offload network.
|
||||||
*/
|
*/
|
||||||
private NetworkRequest getWifiEntryRssiThresholdNetworkRequest() {
|
private NetworkRequest getWifiEntryRssiThresholdNetworkRequest() {
|
||||||
return getBaseNetworkRequestBuilder()
|
return getBaseWifiNetworkRequestBuilder()
|
||||||
.addTransportType(NetworkCapabilities.TRANSPORT_WIFI)
|
|
||||||
.setSubscriptionIds(mLastSnapshot.getAllSubIdsInGroup(mSubscriptionGroup))
|
|
||||||
// Ensure wifi updates signal strengths when crossing this threshold.
|
// Ensure wifi updates signal strengths when crossing this threshold.
|
||||||
.setSignalStrength(getWifiEntryRssiThreshold(mCarrierConfig))
|
.setSignalStrength(getWifiEntryRssiThreshold(mCarrierConfig))
|
||||||
.build();
|
.build();
|
||||||
@@ -254,9 +322,7 @@ public class UnderlyingNetworkController {
|
|||||||
* pace to effectively select away from a failing WiFi network.
|
* pace to effectively select away from a failing WiFi network.
|
||||||
*/
|
*/
|
||||||
private NetworkRequest getWifiExitRssiThresholdNetworkRequest() {
|
private NetworkRequest getWifiExitRssiThresholdNetworkRequest() {
|
||||||
return getBaseNetworkRequestBuilder()
|
return getBaseWifiNetworkRequestBuilder()
|
||||||
.addTransportType(NetworkCapabilities.TRANSPORT_WIFI)
|
|
||||||
.setSubscriptionIds(mLastSnapshot.getAllSubIdsInGroup(mSubscriptionGroup))
|
|
||||||
// Ensure wifi updates signal strengths when crossing this threshold.
|
// Ensure wifi updates signal strengths when crossing this threshold.
|
||||||
.setSignalStrength(getWifiExitRssiThreshold(mCarrierConfig))
|
.setSignalStrength(getWifiExitRssiThreshold(mCarrierConfig))
|
||||||
.build();
|
.build();
|
||||||
@@ -273,11 +339,25 @@ public class UnderlyingNetworkController {
|
|||||||
* <p>Since this request MUST make it to the TelephonyNetworkFactory, subIds are not specified
|
* <p>Since this request MUST make it to the TelephonyNetworkFactory, subIds are not specified
|
||||||
* in the NetworkCapabilities, but rather in the TelephonyNetworkSpecifier.
|
* in the NetworkCapabilities, but rather in the TelephonyNetworkSpecifier.
|
||||||
*/
|
*/
|
||||||
private NetworkRequest getCellNetworkRequestForSubId(int subId) {
|
private NetworkRequest getCellNetworkRequestForSubId(
|
||||||
return getBaseNetworkRequestBuilder()
|
int subId, Set<CapabilityMatchCriteria> capsMatchCriteria) {
|
||||||
|
final NetworkRequest.Builder nrBuilder =
|
||||||
|
getBaseNetworkRequestBuilder()
|
||||||
.addTransportType(NetworkCapabilities.TRANSPORT_CELLULAR)
|
.addTransportType(NetworkCapabilities.TRANSPORT_CELLULAR)
|
||||||
.setNetworkSpecifier(new TelephonyNetworkSpecifier(subId))
|
.setNetworkSpecifier(new TelephonyNetworkSpecifier(subId));
|
||||||
.build();
|
|
||||||
|
for (CapabilityMatchCriteria capMatchCriteria : capsMatchCriteria) {
|
||||||
|
final int cap = capMatchCriteria.capability;
|
||||||
|
final int matchCriteria = capMatchCriteria.matchCriteria;
|
||||||
|
|
||||||
|
if (matchCriteria == MATCH_REQUIRED) {
|
||||||
|
nrBuilder.addCapability(cap);
|
||||||
|
} else if (matchCriteria == MATCH_FORBIDDEN) {
|
||||||
|
nrBuilder.addForbiddenCapability(cap);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
return nrBuilder.build();
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -285,7 +365,6 @@ public class UnderlyingNetworkController {
|
|||||||
*/
|
*/
|
||||||
private NetworkRequest.Builder getBaseNetworkRequestBuilder() {
|
private NetworkRequest.Builder getBaseNetworkRequestBuilder() {
|
||||||
return new NetworkRequest.Builder()
|
return new NetworkRequest.Builder()
|
||||||
.addCapability(NetworkCapabilities.NET_CAPABILITY_INTERNET)
|
|
||||||
.removeCapability(NetworkCapabilities.NET_CAPABILITY_TRUSTED)
|
.removeCapability(NetworkCapabilities.NET_CAPABILITY_TRUSTED)
|
||||||
.removeCapability(NetworkCapabilities.NET_CAPABILITY_NOT_RESTRICTED)
|
.removeCapability(NetworkCapabilities.NET_CAPABILITY_NOT_RESTRICTED)
|
||||||
.removeCapability(NetworkCapabilities.NET_CAPABILITY_NOT_VCN_MANAGED);
|
.removeCapability(NetworkCapabilities.NET_CAPABILITY_NOT_VCN_MANAGED);
|
||||||
@@ -356,7 +435,7 @@ public class UnderlyingNetworkController {
|
|||||||
if (!allNetworkPriorities.isEmpty()) {
|
if (!allNetworkPriorities.isEmpty()) {
|
||||||
allNetworkPriorities += ", ";
|
allNetworkPriorities += ", ";
|
||||||
}
|
}
|
||||||
allNetworkPriorities += record.network + ": " + record.getPriorityClass();
|
allNetworkPriorities += record.network + ": " + record.priorityClass;
|
||||||
}
|
}
|
||||||
logInfo(
|
logInfo(
|
||||||
"Selected network changed to "
|
"Selected network changed to "
|
||||||
@@ -393,19 +472,22 @@ public class UnderlyingNetworkController {
|
|||||||
|
|
||||||
private TreeSet<UnderlyingNetworkRecord> getSortedUnderlyingNetworks() {
|
private TreeSet<UnderlyingNetworkRecord> getSortedUnderlyingNetworks() {
|
||||||
TreeSet<UnderlyingNetworkRecord> sorted =
|
TreeSet<UnderlyingNetworkRecord> sorted =
|
||||||
new TreeSet<>(
|
new TreeSet<>(UnderlyingNetworkRecord.getComparator());
|
||||||
UnderlyingNetworkRecord.getComparator(
|
|
||||||
|
for (UnderlyingNetworkRecord.Builder builder :
|
||||||
|
mUnderlyingNetworkRecordBuilders.values()) {
|
||||||
|
if (builder.isValid()) {
|
||||||
|
final UnderlyingNetworkRecord record =
|
||||||
|
builder.build(
|
||||||
mVcnContext,
|
mVcnContext,
|
||||||
mConnectionConfig.getVcnUnderlyingNetworkPriorities(),
|
mConnectionConfig.getVcnUnderlyingNetworkPriorities(),
|
||||||
mSubscriptionGroup,
|
mSubscriptionGroup,
|
||||||
mLastSnapshot,
|
mLastSnapshot,
|
||||||
mCurrentRecord,
|
mCurrentRecord,
|
||||||
mCarrierConfig));
|
mCarrierConfig);
|
||||||
|
if (record.priorityClass != NetworkPriorityClassifier.PRIORITY_INVALID) {
|
||||||
for (UnderlyingNetworkRecord.Builder builder :
|
sorted.add(record);
|
||||||
mUnderlyingNetworkRecordBuilders.values()) {
|
}
|
||||||
if (builder.isValid()) {
|
|
||||||
sorted.add(builder.build());
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -42,37 +42,33 @@ import java.util.Objects;
|
|||||||
* @hide
|
* @hide
|
||||||
*/
|
*/
|
||||||
public class UnderlyingNetworkRecord {
|
public class UnderlyingNetworkRecord {
|
||||||
private static final int PRIORITY_CLASS_INVALID = Integer.MAX_VALUE;
|
|
||||||
|
|
||||||
@NonNull public final Network network;
|
@NonNull public final Network network;
|
||||||
@NonNull public final NetworkCapabilities networkCapabilities;
|
@NonNull public final NetworkCapabilities networkCapabilities;
|
||||||
@NonNull public final LinkProperties linkProperties;
|
@NonNull public final LinkProperties linkProperties;
|
||||||
public final boolean isBlocked;
|
public final boolean isBlocked;
|
||||||
|
public final boolean isSelected;
|
||||||
private int mPriorityClass = PRIORITY_CLASS_INVALID;
|
public final int priorityClass;
|
||||||
|
|
||||||
@VisibleForTesting(visibility = Visibility.PRIVATE)
|
@VisibleForTesting(visibility = Visibility.PRIVATE)
|
||||||
public UnderlyingNetworkRecord(
|
public UnderlyingNetworkRecord(
|
||||||
@NonNull Network network,
|
@NonNull Network network,
|
||||||
@NonNull NetworkCapabilities networkCapabilities,
|
@NonNull NetworkCapabilities networkCapabilities,
|
||||||
@NonNull LinkProperties linkProperties,
|
@NonNull LinkProperties linkProperties,
|
||||||
boolean isBlocked) {
|
boolean isBlocked,
|
||||||
this.network = network;
|
|
||||||
this.networkCapabilities = networkCapabilities;
|
|
||||||
this.linkProperties = linkProperties;
|
|
||||||
this.isBlocked = isBlocked;
|
|
||||||
}
|
|
||||||
|
|
||||||
private int getOrCalculatePriorityClass(
|
|
||||||
VcnContext vcnContext,
|
VcnContext vcnContext,
|
||||||
List<VcnUnderlyingNetworkTemplate> underlyingNetworkTemplates,
|
List<VcnUnderlyingNetworkTemplate> underlyingNetworkTemplates,
|
||||||
ParcelUuid subscriptionGroup,
|
ParcelUuid subscriptionGroup,
|
||||||
TelephonySubscriptionSnapshot snapshot,
|
TelephonySubscriptionSnapshot snapshot,
|
||||||
UnderlyingNetworkRecord currentlySelected,
|
UnderlyingNetworkRecord currentlySelected,
|
||||||
PersistableBundleWrapper carrierConfig) {
|
PersistableBundleWrapper carrierConfig) {
|
||||||
// Never changes after the underlying network record is created.
|
this.network = network;
|
||||||
if (mPriorityClass == PRIORITY_CLASS_INVALID) {
|
this.networkCapabilities = networkCapabilities;
|
||||||
mPriorityClass =
|
this.linkProperties = linkProperties;
|
||||||
|
this.isBlocked = isBlocked;
|
||||||
|
|
||||||
|
this.isSelected = isSelected(this.network, currentlySelected);
|
||||||
|
|
||||||
|
priorityClass =
|
||||||
NetworkPriorityClassifier.calculatePriorityClass(
|
NetworkPriorityClassifier.calculatePriorityClass(
|
||||||
vcnContext,
|
vcnContext,
|
||||||
this,
|
this,
|
||||||
@@ -83,12 +79,21 @@ public class UnderlyingNetworkRecord {
|
|||||||
carrierConfig);
|
carrierConfig);
|
||||||
}
|
}
|
||||||
|
|
||||||
return mPriorityClass;
|
@VisibleForTesting(visibility = Visibility.PRIVATE)
|
||||||
}
|
public UnderlyingNetworkRecord(
|
||||||
|
@NonNull Network network,
|
||||||
|
@NonNull NetworkCapabilities networkCapabilities,
|
||||||
|
@NonNull LinkProperties linkProperties,
|
||||||
|
boolean isBlocked,
|
||||||
|
boolean isSelected,
|
||||||
|
int priorityClass) {
|
||||||
|
this.network = network;
|
||||||
|
this.networkCapabilities = networkCapabilities;
|
||||||
|
this.linkProperties = linkProperties;
|
||||||
|
this.isBlocked = isBlocked;
|
||||||
|
this.isSelected = isSelected;
|
||||||
|
|
||||||
// Used in UnderlyingNetworkController
|
this.priorityClass = priorityClass;
|
||||||
int getPriorityClass() {
|
|
||||||
return mPriorityClass;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
@@ -108,40 +113,32 @@ public class UnderlyingNetworkRecord {
|
|||||||
return Objects.hash(network, networkCapabilities, linkProperties, isBlocked);
|
return Objects.hash(network, networkCapabilities, linkProperties, isBlocked);
|
||||||
}
|
}
|
||||||
|
|
||||||
static Comparator<UnderlyingNetworkRecord> getComparator(
|
/** Returns if two records are equal including their priority classes. */
|
||||||
VcnContext vcnContext,
|
public static boolean isEqualIncludingPriorities(
|
||||||
List<VcnUnderlyingNetworkTemplate> underlyingNetworkTemplates,
|
UnderlyingNetworkRecord left, UnderlyingNetworkRecord right) {
|
||||||
ParcelUuid subscriptionGroup,
|
if (left != null && right != null) {
|
||||||
TelephonySubscriptionSnapshot snapshot,
|
return left.equals(right)
|
||||||
UnderlyingNetworkRecord currentlySelected,
|
&& left.isSelected == right.isSelected
|
||||||
PersistableBundleWrapper carrierConfig) {
|
&& left.priorityClass == right.priorityClass;
|
||||||
|
}
|
||||||
|
|
||||||
|
return left == right;
|
||||||
|
}
|
||||||
|
|
||||||
|
static Comparator<UnderlyingNetworkRecord> getComparator() {
|
||||||
return (left, right) -> {
|
return (left, right) -> {
|
||||||
final int leftIndex =
|
final int leftIndex = left.priorityClass;
|
||||||
left.getOrCalculatePriorityClass(
|
final int rightIndex = right.priorityClass;
|
||||||
vcnContext,
|
|
||||||
underlyingNetworkTemplates,
|
|
||||||
subscriptionGroup,
|
|
||||||
snapshot,
|
|
||||||
currentlySelected,
|
|
||||||
carrierConfig);
|
|
||||||
final int rightIndex =
|
|
||||||
right.getOrCalculatePriorityClass(
|
|
||||||
vcnContext,
|
|
||||||
underlyingNetworkTemplates,
|
|
||||||
subscriptionGroup,
|
|
||||||
snapshot,
|
|
||||||
currentlySelected,
|
|
||||||
carrierConfig);
|
|
||||||
|
|
||||||
// In the case of networks in the same priority class, prioritize based on other
|
// In the case of networks in the same priority class, prioritize based on other
|
||||||
// criteria (eg. actively selected network, link metrics, etc)
|
// criteria (eg. actively selected network, link metrics, etc)
|
||||||
if (leftIndex == rightIndex) {
|
if (leftIndex == rightIndex) {
|
||||||
// TODO: Improve the strategy of network selection when both UnderlyingNetworkRecord
|
// TODO: Improve the strategy of network selection when both UnderlyingNetworkRecord
|
||||||
// fall into the same priority class.
|
// fall into the same priority class.
|
||||||
if (isSelected(left, currentlySelected)) {
|
if (left.isSelected) {
|
||||||
return -1;
|
return -1;
|
||||||
}
|
}
|
||||||
if (isSelected(left, currentlySelected)) {
|
if (right.isSelected) {
|
||||||
return 1;
|
return 1;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -150,11 +147,11 @@ public class UnderlyingNetworkRecord {
|
|||||||
}
|
}
|
||||||
|
|
||||||
private static boolean isSelected(
|
private static boolean isSelected(
|
||||||
UnderlyingNetworkRecord recordToCheck, UnderlyingNetworkRecord currentlySelected) {
|
Network networkToCheck, UnderlyingNetworkRecord currentlySelected) {
|
||||||
if (currentlySelected == null) {
|
if (currentlySelected == null) {
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
if (currentlySelected.network == recordToCheck.network) {
|
if (currentlySelected.network.equals(networkToCheck)) {
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
return false;
|
return false;
|
||||||
@@ -172,16 +169,8 @@ public class UnderlyingNetworkRecord {
|
|||||||
pw.println("UnderlyingNetworkRecord:");
|
pw.println("UnderlyingNetworkRecord:");
|
||||||
pw.increaseIndent();
|
pw.increaseIndent();
|
||||||
|
|
||||||
final int priorityIndex =
|
pw.println("priorityClass: " + priorityClass);
|
||||||
getOrCalculatePriorityClass(
|
pw.println("isSelected: " + isSelected);
|
||||||
vcnContext,
|
|
||||||
underlyingNetworkTemplates,
|
|
||||||
subscriptionGroup,
|
|
||||||
snapshot,
|
|
||||||
currentlySelected,
|
|
||||||
carrierConfig);
|
|
||||||
|
|
||||||
pw.println("Priority index: " + priorityIndex);
|
|
||||||
pw.println("mNetwork: " + network);
|
pw.println("mNetwork: " + network);
|
||||||
pw.println("mNetworkCapabilities: " + networkCapabilities);
|
pw.println("mNetworkCapabilities: " + networkCapabilities);
|
||||||
pw.println("mLinkProperties: " + linkProperties);
|
pw.println("mLinkProperties: " + linkProperties);
|
||||||
@@ -198,8 +187,6 @@ public class UnderlyingNetworkRecord {
|
|||||||
boolean mIsBlocked;
|
boolean mIsBlocked;
|
||||||
boolean mWasIsBlockedSet;
|
boolean mWasIsBlockedSet;
|
||||||
|
|
||||||
@Nullable private UnderlyingNetworkRecord mCached;
|
|
||||||
|
|
||||||
Builder(@NonNull Network network) {
|
Builder(@NonNull Network network) {
|
||||||
mNetwork = network;
|
mNetwork = network;
|
||||||
}
|
}
|
||||||
@@ -211,7 +198,6 @@ public class UnderlyingNetworkRecord {
|
|||||||
|
|
||||||
void setNetworkCapabilities(@NonNull NetworkCapabilities networkCapabilities) {
|
void setNetworkCapabilities(@NonNull NetworkCapabilities networkCapabilities) {
|
||||||
mNetworkCapabilities = networkCapabilities;
|
mNetworkCapabilities = networkCapabilities;
|
||||||
mCached = null;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
@Nullable
|
@Nullable
|
||||||
@@ -221,32 +207,40 @@ public class UnderlyingNetworkRecord {
|
|||||||
|
|
||||||
void setLinkProperties(@NonNull LinkProperties linkProperties) {
|
void setLinkProperties(@NonNull LinkProperties linkProperties) {
|
||||||
mLinkProperties = linkProperties;
|
mLinkProperties = linkProperties;
|
||||||
mCached = null;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
void setIsBlocked(boolean isBlocked) {
|
void setIsBlocked(boolean isBlocked) {
|
||||||
mIsBlocked = isBlocked;
|
mIsBlocked = isBlocked;
|
||||||
mWasIsBlockedSet = true;
|
mWasIsBlockedSet = true;
|
||||||
mCached = null;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
boolean isValid() {
|
boolean isValid() {
|
||||||
return mNetworkCapabilities != null && mLinkProperties != null && mWasIsBlockedSet;
|
return mNetworkCapabilities != null && mLinkProperties != null && mWasIsBlockedSet;
|
||||||
}
|
}
|
||||||
|
|
||||||
UnderlyingNetworkRecord build() {
|
UnderlyingNetworkRecord build(
|
||||||
|
VcnContext vcnContext,
|
||||||
|
List<VcnUnderlyingNetworkTemplate> underlyingNetworkTemplates,
|
||||||
|
ParcelUuid subscriptionGroup,
|
||||||
|
TelephonySubscriptionSnapshot snapshot,
|
||||||
|
UnderlyingNetworkRecord currentlySelected,
|
||||||
|
PersistableBundleWrapper carrierConfig) {
|
||||||
if (!isValid()) {
|
if (!isValid()) {
|
||||||
throw new IllegalArgumentException(
|
throw new IllegalArgumentException(
|
||||||
"Called build before UnderlyingNetworkRecord was valid");
|
"Called build before UnderlyingNetworkRecord was valid");
|
||||||
}
|
}
|
||||||
|
|
||||||
if (mCached == null) {
|
return new UnderlyingNetworkRecord(
|
||||||
mCached =
|
mNetwork,
|
||||||
new UnderlyingNetworkRecord(
|
mNetworkCapabilities,
|
||||||
mNetwork, mNetworkCapabilities, mLinkProperties, mIsBlocked);
|
mLinkProperties,
|
||||||
}
|
mIsBlocked,
|
||||||
|
vcnContext,
|
||||||
return mCached;
|
underlyingNetworkTemplates,
|
||||||
|
subscriptionGroup,
|
||||||
|
snapshot,
|
||||||
|
currentlySelected,
|
||||||
|
carrierConfig);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -32,7 +32,8 @@ public class VcnCellUnderlyingNetworkTemplateTest extends VcnUnderlyingNetworkTe
|
|||||||
private static final Set<String> ALLOWED_PLMN_IDS = new HashSet<>();
|
private static final Set<String> ALLOWED_PLMN_IDS = new HashSet<>();
|
||||||
private static final Set<Integer> ALLOWED_CARRIER_IDS = new HashSet<>();
|
private static final Set<Integer> ALLOWED_CARRIER_IDS = new HashSet<>();
|
||||||
|
|
||||||
private static VcnCellUnderlyingNetworkTemplate.Builder getTestNetworkTemplateBuilder() {
|
// Public for use in UnderlyingNetworkControllerTest
|
||||||
|
public static VcnCellUnderlyingNetworkTemplate.Builder getTestNetworkTemplateBuilder() {
|
||||||
return new VcnCellUnderlyingNetworkTemplate.Builder()
|
return new VcnCellUnderlyingNetworkTemplate.Builder()
|
||||||
.setMetered(MATCH_FORBIDDEN)
|
.setMetered(MATCH_FORBIDDEN)
|
||||||
.setMinUpstreamBandwidthKbps(
|
.setMinUpstreamBandwidthKbps(
|
||||||
|
|||||||
@@ -100,14 +100,20 @@ public class VcnGatewayConnectionConfigTest {
|
|||||||
EXPOSED_CAPS);
|
EXPOSED_CAPS);
|
||||||
}
|
}
|
||||||
|
|
||||||
// Public for use in VcnGatewayConnectionTest
|
// Public for use in UnderlyingNetworkControllerTest
|
||||||
public static VcnGatewayConnectionConfig buildTestConfig() {
|
public static VcnGatewayConnectionConfig buildTestConfig(
|
||||||
|
List<VcnUnderlyingNetworkTemplate> nwTemplates) {
|
||||||
final VcnGatewayConnectionConfig.Builder builder =
|
final VcnGatewayConnectionConfig.Builder builder =
|
||||||
newBuilder().setVcnUnderlyingNetworkPriorities(UNDERLYING_NETWORK_TEMPLATES);
|
newBuilder().setVcnUnderlyingNetworkPriorities(nwTemplates);
|
||||||
|
|
||||||
return buildTestConfigWithExposedCaps(builder, EXPOSED_CAPS);
|
return buildTestConfigWithExposedCaps(builder, EXPOSED_CAPS);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Public for use in VcnGatewayConnectionTest
|
||||||
|
public static VcnGatewayConnectionConfig buildTestConfig() {
|
||||||
|
return buildTestConfig(UNDERLYING_NETWORK_TEMPLATES);
|
||||||
|
}
|
||||||
|
|
||||||
private static VcnGatewayConnectionConfig.Builder newBuilder() {
|
private static VcnGatewayConnectionConfig.Builder newBuilder() {
|
||||||
// Append a unique identifier to the name prefix to guarantee that all created
|
// Append a unique identifier to the name prefix to guarantee that all created
|
||||||
// VcnGatewayConnectionConfigs have a unique name (required by VcnConfig).
|
// VcnGatewayConnectionConfigs have a unique name (required by VcnConfig).
|
||||||
|
|||||||
@@ -143,9 +143,9 @@ public class VcnGatewayConnectionTest extends VcnGatewayConnectionTestBase {
|
|||||||
capBuilder.setLinkDownstreamBandwidthKbps(TEST_DOWNSTREAM_BANDWIDTH);
|
capBuilder.setLinkDownstreamBandwidthKbps(TEST_DOWNSTREAM_BANDWIDTH);
|
||||||
capBuilder.setAdministratorUids(new int[] {TEST_UID});
|
capBuilder.setAdministratorUids(new int[] {TEST_UID});
|
||||||
final Network underlyingNetwork = mock(Network.class, CALLS_REAL_METHODS);
|
final Network underlyingNetwork = mock(Network.class, CALLS_REAL_METHODS);
|
||||||
UnderlyingNetworkRecord record = new UnderlyingNetworkRecord(
|
UnderlyingNetworkRecord record =
|
||||||
underlyingNetwork,
|
getTestNetworkRecord(
|
||||||
capBuilder.build(), new LinkProperties(), false);
|
underlyingNetwork, capBuilder.build(), new LinkProperties(), false);
|
||||||
final NetworkCapabilities vcnCaps =
|
final NetworkCapabilities vcnCaps =
|
||||||
VcnGatewayConnection.buildNetworkCapabilities(
|
VcnGatewayConnection.buildNetworkCapabilities(
|
||||||
VcnGatewayConnectionConfigTest.buildTestConfig(),
|
VcnGatewayConnectionConfigTest.buildTestConfig(),
|
||||||
@@ -211,7 +211,7 @@ public class VcnGatewayConnectionTest extends VcnGatewayConnectionTestBase {
|
|||||||
doReturn(TEST_DNS_ADDRESSES).when(childSessionConfig).getInternalDnsServers();
|
doReturn(TEST_DNS_ADDRESSES).when(childSessionConfig).getInternalDnsServers();
|
||||||
|
|
||||||
UnderlyingNetworkRecord record =
|
UnderlyingNetworkRecord record =
|
||||||
new UnderlyingNetworkRecord(
|
getTestNetworkRecord(
|
||||||
mock(Network.class, CALLS_REAL_METHODS),
|
mock(Network.class, CALLS_REAL_METHODS),
|
||||||
new NetworkCapabilities.Builder().build(),
|
new NetworkCapabilities.Builder().build(),
|
||||||
underlyingLp,
|
underlyingLp,
|
||||||
|
|||||||
@@ -109,9 +109,23 @@ public class VcnGatewayConnectionTestBase {
|
|||||||
protected static final long ELAPSED_REAL_TIME = 123456789L;
|
protected static final long ELAPSED_REAL_TIME = 123456789L;
|
||||||
protected static final String TEST_IPSEC_TUNNEL_IFACE = "IPSEC_IFACE";
|
protected static final String TEST_IPSEC_TUNNEL_IFACE = "IPSEC_IFACE";
|
||||||
|
|
||||||
|
protected static UnderlyingNetworkRecord getTestNetworkRecord(
|
||||||
|
Network network,
|
||||||
|
NetworkCapabilities networkCapabilities,
|
||||||
|
LinkProperties linkProperties,
|
||||||
|
boolean isBlocked) {
|
||||||
|
return new UnderlyingNetworkRecord(
|
||||||
|
network,
|
||||||
|
networkCapabilities,
|
||||||
|
linkProperties,
|
||||||
|
isBlocked,
|
||||||
|
false /* isSelected */,
|
||||||
|
0 /* priorityClass */);
|
||||||
|
}
|
||||||
|
|
||||||
protected static final String TEST_TCP_BUFFER_SIZES_1 = "1,2,3,4";
|
protected static final String TEST_TCP_BUFFER_SIZES_1 = "1,2,3,4";
|
||||||
protected static final UnderlyingNetworkRecord TEST_UNDERLYING_NETWORK_RECORD_1 =
|
protected static final UnderlyingNetworkRecord TEST_UNDERLYING_NETWORK_RECORD_1 =
|
||||||
new UnderlyingNetworkRecord(
|
getTestNetworkRecord(
|
||||||
mock(Network.class, CALLS_REAL_METHODS),
|
mock(Network.class, CALLS_REAL_METHODS),
|
||||||
new NetworkCapabilities(),
|
new NetworkCapabilities(),
|
||||||
new LinkProperties(),
|
new LinkProperties(),
|
||||||
@@ -124,7 +138,7 @@ public class VcnGatewayConnectionTestBase {
|
|||||||
|
|
||||||
protected static final String TEST_TCP_BUFFER_SIZES_2 = "2,3,4,5";
|
protected static final String TEST_TCP_BUFFER_SIZES_2 = "2,3,4,5";
|
||||||
protected static final UnderlyingNetworkRecord TEST_UNDERLYING_NETWORK_RECORD_2 =
|
protected static final UnderlyingNetworkRecord TEST_UNDERLYING_NETWORK_RECORD_2 =
|
||||||
new UnderlyingNetworkRecord(
|
getTestNetworkRecord(
|
||||||
mock(Network.class, CALLS_REAL_METHODS),
|
mock(Network.class, CALLS_REAL_METHODS),
|
||||||
new NetworkCapabilities(),
|
new NetworkCapabilities(),
|
||||||
new LinkProperties(),
|
new LinkProperties(),
|
||||||
|
|||||||
@@ -16,6 +16,7 @@
|
|||||||
|
|
||||||
package com.android.server.vcn.routeselection;
|
package com.android.server.vcn.routeselection;
|
||||||
|
|
||||||
|
import static android.net.NetworkCapabilities.NET_CAPABILITY_INTERNET;
|
||||||
import static android.net.vcn.VcnUnderlyingNetworkTemplate.MATCH_FORBIDDEN;
|
import static android.net.vcn.VcnUnderlyingNetworkTemplate.MATCH_FORBIDDEN;
|
||||||
import static android.net.vcn.VcnUnderlyingNetworkTemplate.MATCH_REQUIRED;
|
import static android.net.vcn.VcnUnderlyingNetworkTemplate.MATCH_REQUIRED;
|
||||||
import static android.net.vcn.VcnUnderlyingNetworkTemplateTestBase.TEST_MIN_ENTRY_DOWNSTREAM_BANDWIDTH_KBPS;
|
import static android.net.vcn.VcnUnderlyingNetworkTemplateTestBase.TEST_MIN_ENTRY_DOWNSTREAM_BANDWIDTH_KBPS;
|
||||||
@@ -24,8 +25,8 @@ import static android.net.vcn.VcnUnderlyingNetworkTemplateTestBase.TEST_MIN_EXIT
|
|||||||
import static android.net.vcn.VcnUnderlyingNetworkTemplateTestBase.TEST_MIN_EXIT_UPSTREAM_BANDWIDTH_KBPS;
|
import static android.net.vcn.VcnUnderlyingNetworkTemplateTestBase.TEST_MIN_EXIT_UPSTREAM_BANDWIDTH_KBPS;
|
||||||
|
|
||||||
import static com.android.server.vcn.VcnTestUtils.setupSystemService;
|
import static com.android.server.vcn.VcnTestUtils.setupSystemService;
|
||||||
import static com.android.server.vcn.routeselection.NetworkPriorityClassifier.PRIORITY_ANY;
|
import static com.android.server.vcn.routeselection.NetworkPriorityClassifier.PRIORITY_FALLBACK;
|
||||||
import static com.android.server.vcn.routeselection.NetworkPriorityClassifier.calculatePriorityClass;
|
import static com.android.server.vcn.routeselection.NetworkPriorityClassifier.PRIORITY_INVALID;
|
||||||
import static com.android.server.vcn.routeselection.NetworkPriorityClassifier.checkMatchesCellPriorityRule;
|
import static com.android.server.vcn.routeselection.NetworkPriorityClassifier.checkMatchesCellPriorityRule;
|
||||||
import static com.android.server.vcn.routeselection.NetworkPriorityClassifier.checkMatchesPriorityRule;
|
import static com.android.server.vcn.routeselection.NetworkPriorityClassifier.checkMatchesPriorityRule;
|
||||||
import static com.android.server.vcn.routeselection.NetworkPriorityClassifier.checkMatchesWifiPriorityRule;
|
import static com.android.server.vcn.routeselection.NetworkPriorityClassifier.checkMatchesWifiPriorityRule;
|
||||||
@@ -48,6 +49,7 @@ import android.net.TelephonyNetworkSpecifier;
|
|||||||
import android.net.vcn.VcnCellUnderlyingNetworkTemplate;
|
import android.net.vcn.VcnCellUnderlyingNetworkTemplate;
|
||||||
import android.net.vcn.VcnGatewayConnectionConfig;
|
import android.net.vcn.VcnGatewayConnectionConfig;
|
||||||
import android.net.vcn.VcnManager;
|
import android.net.vcn.VcnManager;
|
||||||
|
import android.net.vcn.VcnUnderlyingNetworkTemplate;
|
||||||
import android.net.vcn.VcnWifiUnderlyingNetworkTemplate;
|
import android.net.vcn.VcnWifiUnderlyingNetworkTemplate;
|
||||||
import android.os.ParcelUuid;
|
import android.os.ParcelUuid;
|
||||||
import android.os.PersistableBundle;
|
import android.os.PersistableBundle;
|
||||||
@@ -64,6 +66,8 @@ import org.junit.Test;
|
|||||||
import org.mockito.Mock;
|
import org.mockito.Mock;
|
||||||
import org.mockito.MockitoAnnotations;
|
import org.mockito.MockitoAnnotations;
|
||||||
|
|
||||||
|
import java.util.Collections;
|
||||||
|
import java.util.List;
|
||||||
import java.util.Set;
|
import java.util.Set;
|
||||||
import java.util.UUID;
|
import java.util.UUID;
|
||||||
|
|
||||||
@@ -102,6 +106,7 @@ public class NetworkPriorityClassifierTest {
|
|||||||
private static final NetworkCapabilities CELL_NETWORK_CAPABILITIES =
|
private static final NetworkCapabilities CELL_NETWORK_CAPABILITIES =
|
||||||
new NetworkCapabilities.Builder()
|
new NetworkCapabilities.Builder()
|
||||||
.addCapability(NetworkCapabilities.NET_CAPABILITY_INTERNET)
|
.addCapability(NetworkCapabilities.NET_CAPABILITY_INTERNET)
|
||||||
|
.addCapability(NetworkCapabilities.NET_CAPABILITY_DUN)
|
||||||
.addTransportType(NetworkCapabilities.TRANSPORT_CELLULAR)
|
.addTransportType(NetworkCapabilities.TRANSPORT_CELLULAR)
|
||||||
.setSubscriptionIds(Set.of(SUB_ID))
|
.setSubscriptionIds(Set.of(SUB_ID))
|
||||||
.setNetworkSpecifier(TEL_NETWORK_SPECIFIER)
|
.setNetworkSpecifier(TEL_NETWORK_SPECIFIER)
|
||||||
@@ -135,25 +140,35 @@ public class NetworkPriorityClassifierTest {
|
|||||||
false /* isInTestMode */));
|
false /* isInTestMode */));
|
||||||
doNothing().when(mVcnContext).ensureRunningOnLooperThread();
|
doNothing().when(mVcnContext).ensureRunningOnLooperThread();
|
||||||
|
|
||||||
mWifiNetworkRecord =
|
|
||||||
new UnderlyingNetworkRecord(
|
|
||||||
mNetwork,
|
|
||||||
WIFI_NETWORK_CAPABILITIES,
|
|
||||||
LINK_PROPERTIES,
|
|
||||||
false /* isBlocked */);
|
|
||||||
|
|
||||||
mCellNetworkRecord =
|
|
||||||
new UnderlyingNetworkRecord(
|
|
||||||
mNetwork,
|
|
||||||
CELL_NETWORK_CAPABILITIES,
|
|
||||||
LINK_PROPERTIES,
|
|
||||||
false /* isBlocked */);
|
|
||||||
|
|
||||||
setupSystemService(
|
setupSystemService(
|
||||||
mockContext, mTelephonyManager, Context.TELEPHONY_SERVICE, TelephonyManager.class);
|
mockContext, mTelephonyManager, Context.TELEPHONY_SERVICE, TelephonyManager.class);
|
||||||
when(mTelephonyManager.createForSubscriptionId(SUB_ID)).thenReturn(mTelephonyManager);
|
when(mTelephonyManager.createForSubscriptionId(SUB_ID)).thenReturn(mTelephonyManager);
|
||||||
when(mTelephonyManager.getNetworkOperator()).thenReturn(PLMN_ID);
|
when(mTelephonyManager.getNetworkOperator()).thenReturn(PLMN_ID);
|
||||||
when(mTelephonyManager.getSimSpecificCarrierId()).thenReturn(CARRIER_ID);
|
when(mTelephonyManager.getSimSpecificCarrierId()).thenReturn(CARRIER_ID);
|
||||||
|
|
||||||
|
mWifiNetworkRecord =
|
||||||
|
getTestNetworkRecord(
|
||||||
|
WIFI_NETWORK_CAPABILITIES,
|
||||||
|
VcnGatewayConnectionConfig.DEFAULT_UNDERLYING_NETWORK_TEMPLATES);
|
||||||
|
mCellNetworkRecord =
|
||||||
|
getTestNetworkRecord(
|
||||||
|
CELL_NETWORK_CAPABILITIES,
|
||||||
|
VcnGatewayConnectionConfig.DEFAULT_UNDERLYING_NETWORK_TEMPLATES);
|
||||||
|
}
|
||||||
|
|
||||||
|
private UnderlyingNetworkRecord getTestNetworkRecord(
|
||||||
|
NetworkCapabilities nc, List<VcnUnderlyingNetworkTemplate> underlyingNetworkTemplates) {
|
||||||
|
return new UnderlyingNetworkRecord(
|
||||||
|
mNetwork,
|
||||||
|
nc,
|
||||||
|
LINK_PROPERTIES,
|
||||||
|
false /* isBlocked */,
|
||||||
|
mVcnContext,
|
||||||
|
underlyingNetworkTemplates,
|
||||||
|
SUB_GROUP,
|
||||||
|
mSubscriptionSnapshot,
|
||||||
|
null /* currentlySelected */,
|
||||||
|
null /* carrierConfig */);
|
||||||
}
|
}
|
||||||
|
|
||||||
@Test
|
@Test
|
||||||
@@ -490,37 +505,72 @@ public class NetworkPriorityClassifierTest {
|
|||||||
mSubscriptionSnapshot));
|
mSubscriptionSnapshot));
|
||||||
}
|
}
|
||||||
|
|
||||||
private void verifyCalculatePriorityClass(
|
private void verifyMatchCellWithRequiredCapabilities(
|
||||||
UnderlyingNetworkRecord networkRecord, int expectedIndex) {
|
VcnCellUnderlyingNetworkTemplate template, boolean expectMatch) {
|
||||||
final int priorityIndex =
|
assertEquals(
|
||||||
calculatePriorityClass(
|
expectMatch,
|
||||||
|
checkMatchesCellPriorityRule(
|
||||||
mVcnContext,
|
mVcnContext,
|
||||||
networkRecord,
|
template,
|
||||||
VcnGatewayConnectionConfig.DEFAULT_UNDERLYING_NETWORK_TEMPLATES,
|
mCellNetworkRecord,
|
||||||
SUB_GROUP,
|
SUB_GROUP,
|
||||||
mSubscriptionSnapshot,
|
mSubscriptionSnapshot));
|
||||||
null /* currentlySelected */,
|
}
|
||||||
null /* carrierConfig */);
|
|
||||||
|
|
||||||
assertEquals(expectedIndex, priorityIndex);
|
@Test
|
||||||
|
public void testMatchCell() {
|
||||||
|
final VcnCellUnderlyingNetworkTemplate template =
|
||||||
|
getCellNetworkPriorityBuilder().setInternet(MATCH_REQUIRED).build();
|
||||||
|
verifyMatchCellWithRequiredCapabilities(template, true /* expectMatch */);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void testMatchCellFail_RequiredCapabilitiesMissing() {
|
||||||
|
final VcnCellUnderlyingNetworkTemplate template =
|
||||||
|
getCellNetworkPriorityBuilder().setCbs(MATCH_REQUIRED).build();
|
||||||
|
verifyMatchCellWithRequiredCapabilities(template, false /* expectMatch */);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void testMatchCellFail_ForbiddenCapabilitiesFound() {
|
||||||
|
final VcnCellUnderlyingNetworkTemplate template =
|
||||||
|
getCellNetworkPriorityBuilder().setDun(MATCH_FORBIDDEN).build();
|
||||||
|
verifyMatchCellWithRequiredCapabilities(template, false /* expectMatch */);
|
||||||
}
|
}
|
||||||
|
|
||||||
@Test
|
@Test
|
||||||
public void testCalculatePriorityClass() throws Exception {
|
public void testCalculatePriorityClass() throws Exception {
|
||||||
verifyCalculatePriorityClass(mCellNetworkRecord, 2);
|
assertEquals(2, mCellNetworkRecord.priorityClass);
|
||||||
|
}
|
||||||
|
|
||||||
|
private void checkCalculatePriorityClassFailToMatchAny(
|
||||||
|
boolean hasInternet, int expectedPriorityClass) throws Exception {
|
||||||
|
final List<VcnUnderlyingNetworkTemplate> templatesRequireDun =
|
||||||
|
Collections.singletonList(
|
||||||
|
new VcnCellUnderlyingNetworkTemplate.Builder()
|
||||||
|
.setDun(MATCH_REQUIRED)
|
||||||
|
.build());
|
||||||
|
|
||||||
|
final NetworkCapabilities.Builder ncBuilder =
|
||||||
|
new NetworkCapabilities.Builder()
|
||||||
|
.addTransportType(NetworkCapabilities.TRANSPORT_CELLULAR);
|
||||||
|
if (hasInternet) {
|
||||||
|
ncBuilder.addCapability(NET_CAPABILITY_INTERNET);
|
||||||
|
}
|
||||||
|
|
||||||
|
final UnderlyingNetworkRecord nonDunNetworkRecord =
|
||||||
|
getTestNetworkRecord(ncBuilder.build(), templatesRequireDun);
|
||||||
|
|
||||||
|
assertEquals(expectedPriorityClass, nonDunNetworkRecord.priorityClass);
|
||||||
}
|
}
|
||||||
|
|
||||||
@Test
|
@Test
|
||||||
public void testCalculatePriorityClassFailToMatchAny() throws Exception {
|
public void testCalculatePriorityClassFailToMatchAny_InternetNetwork() throws Exception {
|
||||||
final NetworkCapabilities nc =
|
checkCalculatePriorityClassFailToMatchAny(true /* hasInternet */, PRIORITY_FALLBACK);
|
||||||
new NetworkCapabilities.Builder()
|
}
|
||||||
.addTransportType(NetworkCapabilities.TRANSPORT_WIFI)
|
|
||||||
.setSignalStrength(WIFI_RSSI_LOW)
|
|
||||||
.setSsid(SSID)
|
|
||||||
.build();
|
|
||||||
final UnderlyingNetworkRecord wifiNetworkRecord =
|
|
||||||
new UnderlyingNetworkRecord(mNetwork, nc, LINK_PROPERTIES, false /* isBlocked */);
|
|
||||||
|
|
||||||
verifyCalculatePriorityClass(wifiNetworkRecord, PRIORITY_ANY);
|
@Test
|
||||||
|
public void testCalculatePriorityClassFailToMatchAny_NonInternetNetwork() throws Exception {
|
||||||
|
checkCalculatePriorityClassFailToMatchAny(false /* hasInternet */, PRIORITY_INVALID);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -16,18 +16,29 @@
|
|||||||
|
|
||||||
package com.android.server.vcn.routeselection;
|
package com.android.server.vcn.routeselection;
|
||||||
|
|
||||||
|
import static android.net.NetworkCapabilities.NET_CAPABILITY_CBS;
|
||||||
|
import static android.net.NetworkCapabilities.NET_CAPABILITY_DUN;
|
||||||
|
import static android.net.NetworkCapabilities.NET_CAPABILITY_INTERNET;
|
||||||
|
import static android.net.NetworkCapabilities.NET_CAPABILITY_MMS;
|
||||||
|
import static android.net.vcn.VcnCellUnderlyingNetworkTemplate.MATCH_ANY;
|
||||||
|
import static android.net.vcn.VcnCellUnderlyingNetworkTemplate.MATCH_FORBIDDEN;
|
||||||
|
import static android.net.vcn.VcnCellUnderlyingNetworkTemplate.MATCH_REQUIRED;
|
||||||
|
|
||||||
import static com.android.server.vcn.VcnTestUtils.setupSystemService;
|
import static com.android.server.vcn.VcnTestUtils.setupSystemService;
|
||||||
import static com.android.server.vcn.routeselection.NetworkPriorityClassifier.WIFI_ENTRY_RSSI_THRESHOLD_DEFAULT;
|
import static com.android.server.vcn.routeselection.NetworkPriorityClassifier.WIFI_ENTRY_RSSI_THRESHOLD_DEFAULT;
|
||||||
import static com.android.server.vcn.routeselection.NetworkPriorityClassifier.WIFI_EXIT_RSSI_THRESHOLD_DEFAULT;
|
import static com.android.server.vcn.routeselection.NetworkPriorityClassifier.WIFI_EXIT_RSSI_THRESHOLD_DEFAULT;
|
||||||
|
|
||||||
import static org.junit.Assert.assertEquals;
|
import static org.junit.Assert.assertEquals;
|
||||||
|
import static org.junit.Assert.assertFalse;
|
||||||
import static org.junit.Assert.assertNotEquals;
|
import static org.junit.Assert.assertNotEquals;
|
||||||
|
import static org.junit.Assert.assertTrue;
|
||||||
import static org.mockito.ArgumentMatchers.any;
|
import static org.mockito.ArgumentMatchers.any;
|
||||||
import static org.mockito.ArgumentMatchers.eq;
|
import static org.mockito.ArgumentMatchers.eq;
|
||||||
import static org.mockito.Mockito.any;
|
import static org.mockito.Mockito.any;
|
||||||
import static org.mockito.Mockito.doNothing;
|
import static org.mockito.Mockito.doNothing;
|
||||||
import static org.mockito.Mockito.eq;
|
import static org.mockito.Mockito.eq;
|
||||||
import static org.mockito.Mockito.mock;
|
import static org.mockito.Mockito.mock;
|
||||||
|
import static org.mockito.Mockito.never;
|
||||||
import static org.mockito.Mockito.reset;
|
import static org.mockito.Mockito.reset;
|
||||||
import static org.mockito.Mockito.spy;
|
import static org.mockito.Mockito.spy;
|
||||||
import static org.mockito.Mockito.times;
|
import static org.mockito.Mockito.times;
|
||||||
@@ -42,7 +53,10 @@ import android.net.Network;
|
|||||||
import android.net.NetworkCapabilities;
|
import android.net.NetworkCapabilities;
|
||||||
import android.net.NetworkRequest;
|
import android.net.NetworkRequest;
|
||||||
import android.net.TelephonyNetworkSpecifier;
|
import android.net.TelephonyNetworkSpecifier;
|
||||||
|
import android.net.vcn.VcnCellUnderlyingNetworkTemplate;
|
||||||
|
import android.net.vcn.VcnCellUnderlyingNetworkTemplateTest;
|
||||||
import android.net.vcn.VcnGatewayConnectionConfigTest;
|
import android.net.vcn.VcnGatewayConnectionConfigTest;
|
||||||
|
import android.net.vcn.VcnUnderlyingNetworkTemplate;
|
||||||
import android.os.ParcelUuid;
|
import android.os.ParcelUuid;
|
||||||
import android.os.test.TestLooper;
|
import android.os.test.TestLooper;
|
||||||
import android.telephony.CarrierConfigManager;
|
import android.telephony.CarrierConfigManager;
|
||||||
@@ -64,7 +78,10 @@ import org.mockito.Captor;
|
|||||||
import org.mockito.Mock;
|
import org.mockito.Mock;
|
||||||
import org.mockito.MockitoAnnotations;
|
import org.mockito.MockitoAnnotations;
|
||||||
|
|
||||||
|
import java.util.ArrayList;
|
||||||
import java.util.Arrays;
|
import java.util.Arrays;
|
||||||
|
import java.util.Collections;
|
||||||
|
import java.util.List;
|
||||||
import java.util.Set;
|
import java.util.Set;
|
||||||
import java.util.UUID;
|
import java.util.UUID;
|
||||||
|
|
||||||
@@ -95,11 +112,39 @@ public class UnderlyingNetworkControllerTest {
|
|||||||
.addTransportType(NetworkCapabilities.TRANSPORT_CELLULAR)
|
.addTransportType(NetworkCapabilities.TRANSPORT_CELLULAR)
|
||||||
.build();
|
.build();
|
||||||
|
|
||||||
|
private static final NetworkCapabilities DUN_NETWORK_CAPABILITIES =
|
||||||
|
new NetworkCapabilities.Builder()
|
||||||
|
.addCapability(NetworkCapabilities.NET_CAPABILITY_DUN)
|
||||||
|
.addCapability(NetworkCapabilities.NET_CAPABILITY_NOT_METERED)
|
||||||
|
.addTransportType(NetworkCapabilities.TRANSPORT_CELLULAR)
|
||||||
|
.removeCapability(NetworkCapabilities.NET_CAPABILITY_TRUSTED)
|
||||||
|
.build();
|
||||||
|
|
||||||
|
private static final NetworkCapabilities CBS_NETWORK_CAPABILITIES =
|
||||||
|
new NetworkCapabilities.Builder()
|
||||||
|
.addCapability(NetworkCapabilities.NET_CAPABILITY_CBS)
|
||||||
|
.addCapability(NetworkCapabilities.NET_CAPABILITY_NOT_METERED)
|
||||||
|
.addTransportType(NetworkCapabilities.TRANSPORT_CELLULAR)
|
||||||
|
.removeCapability(NetworkCapabilities.NET_CAPABILITY_TRUSTED)
|
||||||
|
.build();
|
||||||
|
|
||||||
private static final LinkProperties INITIAL_LINK_PROPERTIES =
|
private static final LinkProperties INITIAL_LINK_PROPERTIES =
|
||||||
getLinkPropertiesWithName("initial_iface");
|
getLinkPropertiesWithName("initial_iface");
|
||||||
private static final LinkProperties UPDATED_LINK_PROPERTIES =
|
private static final LinkProperties UPDATED_LINK_PROPERTIES =
|
||||||
getLinkPropertiesWithName("updated_iface");
|
getLinkPropertiesWithName("updated_iface");
|
||||||
|
|
||||||
|
private static final VcnCellUnderlyingNetworkTemplate CELL_TEMPLATE_DUN =
|
||||||
|
new VcnCellUnderlyingNetworkTemplate.Builder()
|
||||||
|
.setInternet(MATCH_ANY)
|
||||||
|
.setDun(MATCH_REQUIRED)
|
||||||
|
.build();
|
||||||
|
|
||||||
|
private static final VcnCellUnderlyingNetworkTemplate CELL_TEMPLATE_CBS =
|
||||||
|
new VcnCellUnderlyingNetworkTemplate.Builder()
|
||||||
|
.setInternet(MATCH_ANY)
|
||||||
|
.setCbs(MATCH_REQUIRED)
|
||||||
|
.build();
|
||||||
|
|
||||||
@Mock private Context mContext;
|
@Mock private Context mContext;
|
||||||
@Mock private VcnNetworkProvider mVcnNetworkProvider;
|
@Mock private VcnNetworkProvider mVcnNetworkProvider;
|
||||||
@Mock private ConnectivityManager mConnectivityManager;
|
@Mock private ConnectivityManager mConnectivityManager;
|
||||||
@@ -201,6 +246,107 @@ public class UnderlyingNetworkControllerTest {
|
|||||||
any());
|
any());
|
||||||
}
|
}
|
||||||
|
|
||||||
|
private void verifyRequestBackgroundNetwork(
|
||||||
|
ConnectivityManager cm,
|
||||||
|
int expectedSubId,
|
||||||
|
Set<Integer> expectedRequiredCaps,
|
||||||
|
Set<Integer> expectedForbiddenCaps) {
|
||||||
|
verify(cm)
|
||||||
|
.requestBackgroundNetwork(
|
||||||
|
eq(
|
||||||
|
getCellRequestForSubId(
|
||||||
|
expectedSubId,
|
||||||
|
expectedRequiredCaps,
|
||||||
|
expectedForbiddenCaps)),
|
||||||
|
any(NetworkBringupCallback.class),
|
||||||
|
any());
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void testNetworkCallbacksRegisteredOnStartupForNonInternetCapabilities() {
|
||||||
|
final ConnectivityManager cm = mock(ConnectivityManager.class);
|
||||||
|
setupSystemService(mContext, cm, Context.CONNECTIVITY_SERVICE, ConnectivityManager.class);
|
||||||
|
|
||||||
|
// Build network templates
|
||||||
|
final List<VcnUnderlyingNetworkTemplate> networkTemplates = new ArrayList();
|
||||||
|
|
||||||
|
networkTemplates.add(
|
||||||
|
VcnCellUnderlyingNetworkTemplateTest.getTestNetworkTemplateBuilder()
|
||||||
|
.setDun(MATCH_REQUIRED)
|
||||||
|
.setInternet(MATCH_ANY)
|
||||||
|
.build());
|
||||||
|
|
||||||
|
networkTemplates.add(
|
||||||
|
VcnCellUnderlyingNetworkTemplateTest.getTestNetworkTemplateBuilder()
|
||||||
|
.setMms(MATCH_REQUIRED)
|
||||||
|
.setCbs(MATCH_FORBIDDEN)
|
||||||
|
.setInternet(MATCH_ANY)
|
||||||
|
.build());
|
||||||
|
|
||||||
|
// Start UnderlyingNetworkController
|
||||||
|
new UnderlyingNetworkController(
|
||||||
|
mVcnContext,
|
||||||
|
VcnGatewayConnectionConfigTest.buildTestConfig(networkTemplates),
|
||||||
|
SUB_GROUP,
|
||||||
|
mSubscriptionSnapshot,
|
||||||
|
mNetworkControllerCb);
|
||||||
|
|
||||||
|
// Verifications
|
||||||
|
for (final int subId : INITIAL_SUB_IDS) {
|
||||||
|
verifyRequestBackgroundNetwork(
|
||||||
|
cm,
|
||||||
|
subId,
|
||||||
|
Collections.singleton(NET_CAPABILITY_INTERNET),
|
||||||
|
Collections.emptySet());
|
||||||
|
verifyRequestBackgroundNetwork(
|
||||||
|
cm, subId, Collections.singleton(NET_CAPABILITY_DUN), Collections.emptySet());
|
||||||
|
verifyRequestBackgroundNetwork(
|
||||||
|
cm,
|
||||||
|
subId,
|
||||||
|
Collections.singleton(NET_CAPABILITY_MMS),
|
||||||
|
Collections.singleton(NET_CAPABILITY_CBS));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void testNetworkCallbacksRegisteredOnStartupWithDedupedtCapabilities() {
|
||||||
|
final ConnectivityManager cm = mock(ConnectivityManager.class);
|
||||||
|
setupSystemService(mContext, cm, Context.CONNECTIVITY_SERVICE, ConnectivityManager.class);
|
||||||
|
|
||||||
|
// Build network templates
|
||||||
|
final List<VcnUnderlyingNetworkTemplate> networkTemplates = new ArrayList();
|
||||||
|
final VcnCellUnderlyingNetworkTemplate.Builder builder =
|
||||||
|
new VcnCellUnderlyingNetworkTemplate.Builder()
|
||||||
|
.setMms(MATCH_REQUIRED)
|
||||||
|
.setCbs(MATCH_FORBIDDEN)
|
||||||
|
.setInternet(MATCH_ANY);
|
||||||
|
|
||||||
|
networkTemplates.add(builder.setMetered(MATCH_REQUIRED).build());
|
||||||
|
networkTemplates.add(builder.setMetered(MATCH_FORBIDDEN).build());
|
||||||
|
|
||||||
|
// Start UnderlyingNetworkController
|
||||||
|
new UnderlyingNetworkController(
|
||||||
|
mVcnContext,
|
||||||
|
VcnGatewayConnectionConfigTest.buildTestConfig(networkTemplates),
|
||||||
|
SUB_GROUP,
|
||||||
|
mSubscriptionSnapshot,
|
||||||
|
mNetworkControllerCb);
|
||||||
|
|
||||||
|
// Verifications
|
||||||
|
for (final int subId : INITIAL_SUB_IDS) {
|
||||||
|
verifyRequestBackgroundNetwork(
|
||||||
|
cm,
|
||||||
|
subId,
|
||||||
|
Collections.singleton(NET_CAPABILITY_INTERNET),
|
||||||
|
Collections.emptySet());
|
||||||
|
verifyRequestBackgroundNetwork(
|
||||||
|
cm,
|
||||||
|
subId,
|
||||||
|
Collections.singleton(NET_CAPABILITY_MMS),
|
||||||
|
Collections.singleton(NET_CAPABILITY_CBS));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
private void verifyNetworkRequestsRegistered(Set<Integer> expectedSubIds) {
|
private void verifyNetworkRequestsRegistered(Set<Integer> expectedSubIds) {
|
||||||
verify(mConnectivityManager)
|
verify(mConnectivityManager)
|
||||||
.requestBackgroundNetwork(
|
.requestBackgroundNetwork(
|
||||||
@@ -210,8 +356,13 @@ public class UnderlyingNetworkControllerTest {
|
|||||||
for (final int subId : expectedSubIds) {
|
for (final int subId : expectedSubIds) {
|
||||||
verify(mConnectivityManager)
|
verify(mConnectivityManager)
|
||||||
.requestBackgroundNetwork(
|
.requestBackgroundNetwork(
|
||||||
eq(getCellRequestForSubId(subId)),
|
eq(
|
||||||
any(NetworkBringupCallback.class), any());
|
getCellRequestForSubId(
|
||||||
|
subId,
|
||||||
|
Collections.singleton(NET_CAPABILITY_INTERNET),
|
||||||
|
Collections.emptySet())),
|
||||||
|
any(NetworkBringupCallback.class),
|
||||||
|
any());
|
||||||
}
|
}
|
||||||
|
|
||||||
verify(mConnectivityManager)
|
verify(mConnectivityManager)
|
||||||
@@ -253,6 +404,7 @@ public class UnderlyingNetworkControllerTest {
|
|||||||
private NetworkRequest getWifiRequest(Set<Integer> netCapsSubIds) {
|
private NetworkRequest getWifiRequest(Set<Integer> netCapsSubIds) {
|
||||||
return getExpectedRequestBase()
|
return getExpectedRequestBase()
|
||||||
.addTransportType(NetworkCapabilities.TRANSPORT_WIFI)
|
.addTransportType(NetworkCapabilities.TRANSPORT_WIFI)
|
||||||
|
.addCapability(NetworkCapabilities.NET_CAPABILITY_INTERNET)
|
||||||
.setSubscriptionIds(netCapsSubIds)
|
.setSubscriptionIds(netCapsSubIds)
|
||||||
.build();
|
.build();
|
||||||
}
|
}
|
||||||
@@ -261,6 +413,7 @@ public class UnderlyingNetworkControllerTest {
|
|||||||
// TODO (b/187991063): Add tests for carrier-config based thresholds
|
// TODO (b/187991063): Add tests for carrier-config based thresholds
|
||||||
return getExpectedRequestBase()
|
return getExpectedRequestBase()
|
||||||
.addTransportType(NetworkCapabilities.TRANSPORT_WIFI)
|
.addTransportType(NetworkCapabilities.TRANSPORT_WIFI)
|
||||||
|
.addCapability(NetworkCapabilities.NET_CAPABILITY_INTERNET)
|
||||||
.setSubscriptionIds(netCapsSubIds)
|
.setSubscriptionIds(netCapsSubIds)
|
||||||
.setSignalStrength(WIFI_ENTRY_RSSI_THRESHOLD_DEFAULT)
|
.setSignalStrength(WIFI_ENTRY_RSSI_THRESHOLD_DEFAULT)
|
||||||
.build();
|
.build();
|
||||||
@@ -270,16 +423,27 @@ public class UnderlyingNetworkControllerTest {
|
|||||||
// TODO (b/187991063): Add tests for carrier-config based thresholds
|
// TODO (b/187991063): Add tests for carrier-config based thresholds
|
||||||
return getExpectedRequestBase()
|
return getExpectedRequestBase()
|
||||||
.addTransportType(NetworkCapabilities.TRANSPORT_WIFI)
|
.addTransportType(NetworkCapabilities.TRANSPORT_WIFI)
|
||||||
|
.addCapability(NetworkCapabilities.NET_CAPABILITY_INTERNET)
|
||||||
.setSubscriptionIds(netCapsSubIds)
|
.setSubscriptionIds(netCapsSubIds)
|
||||||
.setSignalStrength(WIFI_EXIT_RSSI_THRESHOLD_DEFAULT)
|
.setSignalStrength(WIFI_EXIT_RSSI_THRESHOLD_DEFAULT)
|
||||||
.build();
|
.build();
|
||||||
}
|
}
|
||||||
|
|
||||||
private NetworkRequest getCellRequestForSubId(int subId) {
|
private NetworkRequest getCellRequestForSubId(
|
||||||
return getExpectedRequestBase()
|
int subId, Set<Integer> requiredCaps, Set<Integer> forbiddenCaps) {
|
||||||
|
final NetworkRequest.Builder nqBuilder =
|
||||||
|
getExpectedRequestBase()
|
||||||
.addTransportType(NetworkCapabilities.TRANSPORT_CELLULAR)
|
.addTransportType(NetworkCapabilities.TRANSPORT_CELLULAR)
|
||||||
.setNetworkSpecifier(new TelephonyNetworkSpecifier(subId))
|
.setNetworkSpecifier(new TelephonyNetworkSpecifier(subId));
|
||||||
.build();
|
|
||||||
|
for (int cap : requiredCaps) {
|
||||||
|
nqBuilder.addCapability(cap);
|
||||||
|
}
|
||||||
|
for (int cap : forbiddenCaps) {
|
||||||
|
nqBuilder.addForbiddenCapability(cap);
|
||||||
|
}
|
||||||
|
|
||||||
|
return nqBuilder.build();
|
||||||
}
|
}
|
||||||
|
|
||||||
private NetworkRequest getRouteSelectionRequest(Set<Integer> netCapsSubIds) {
|
private NetworkRequest getRouteSelectionRequest(Set<Integer> netCapsSubIds) {
|
||||||
@@ -301,7 +465,6 @@ public class UnderlyingNetworkControllerTest {
|
|||||||
private NetworkRequest.Builder getExpectedRequestBase() {
|
private NetworkRequest.Builder getExpectedRequestBase() {
|
||||||
final NetworkRequest.Builder builder =
|
final NetworkRequest.Builder builder =
|
||||||
new NetworkRequest.Builder()
|
new NetworkRequest.Builder()
|
||||||
.addCapability(NetworkCapabilities.NET_CAPABILITY_INTERNET)
|
|
||||||
.removeCapability(NetworkCapabilities.NET_CAPABILITY_TRUSTED)
|
.removeCapability(NetworkCapabilities.NET_CAPABILITY_TRUSTED)
|
||||||
.removeCapability(NetworkCapabilities.NET_CAPABILITY_NOT_RESTRICTED)
|
.removeCapability(NetworkCapabilities.NET_CAPABILITY_NOT_RESTRICTED)
|
||||||
.removeCapability(NetworkCapabilities.NET_CAPABILITY_NOT_VCN_MANAGED);
|
.removeCapability(NetworkCapabilities.NET_CAPABILITY_NOT_VCN_MANAGED);
|
||||||
@@ -321,29 +484,55 @@ public class UnderlyingNetworkControllerTest {
|
|||||||
.unregisterNetworkCallback(any(UnderlyingNetworkListener.class));
|
.unregisterNetworkCallback(any(UnderlyingNetworkListener.class));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
private static UnderlyingNetworkRecord getTestNetworkRecord(
|
||||||
|
Network network,
|
||||||
|
NetworkCapabilities networkCapabilities,
|
||||||
|
LinkProperties linkProperties,
|
||||||
|
boolean isBlocked) {
|
||||||
|
return new UnderlyingNetworkRecord(
|
||||||
|
network,
|
||||||
|
networkCapabilities,
|
||||||
|
linkProperties,
|
||||||
|
isBlocked,
|
||||||
|
false /* isSelected */,
|
||||||
|
0 /* priorityClass */);
|
||||||
|
}
|
||||||
|
|
||||||
@Test
|
@Test
|
||||||
public void testUnderlyingNetworkRecordEquals() {
|
public void testUnderlyingNetworkRecordEquals() {
|
||||||
UnderlyingNetworkRecord recordA =
|
UnderlyingNetworkRecord recordA =
|
||||||
new UnderlyingNetworkRecord(
|
getTestNetworkRecord(
|
||||||
mNetwork,
|
mNetwork,
|
||||||
INITIAL_NETWORK_CAPABILITIES,
|
INITIAL_NETWORK_CAPABILITIES,
|
||||||
INITIAL_LINK_PROPERTIES,
|
INITIAL_LINK_PROPERTIES,
|
||||||
false /* isBlocked */);
|
false /* isBlocked */);
|
||||||
UnderlyingNetworkRecord recordB =
|
UnderlyingNetworkRecord recordB =
|
||||||
new UnderlyingNetworkRecord(
|
getTestNetworkRecord(
|
||||||
mNetwork,
|
mNetwork,
|
||||||
INITIAL_NETWORK_CAPABILITIES,
|
INITIAL_NETWORK_CAPABILITIES,
|
||||||
INITIAL_LINK_PROPERTIES,
|
INITIAL_LINK_PROPERTIES,
|
||||||
false /* isBlocked */);
|
false /* isBlocked */);
|
||||||
UnderlyingNetworkRecord recordC =
|
UnderlyingNetworkRecord recordC =
|
||||||
new UnderlyingNetworkRecord(
|
new UnderlyingNetworkRecord(
|
||||||
|
mNetwork,
|
||||||
|
INITIAL_NETWORK_CAPABILITIES,
|
||||||
|
INITIAL_LINK_PROPERTIES,
|
||||||
|
false /* isBlocked */,
|
||||||
|
true /* isSelected */,
|
||||||
|
-1 /* priorityClass */);
|
||||||
|
UnderlyingNetworkRecord recordD =
|
||||||
|
getTestNetworkRecord(
|
||||||
mNetwork,
|
mNetwork,
|
||||||
UPDATED_NETWORK_CAPABILITIES,
|
UPDATED_NETWORK_CAPABILITIES,
|
||||||
UPDATED_LINK_PROPERTIES,
|
UPDATED_LINK_PROPERTIES,
|
||||||
false /* isBlocked */);
|
false /* isBlocked */);
|
||||||
|
|
||||||
assertEquals(recordA, recordB);
|
assertEquals(recordA, recordB);
|
||||||
assertNotEquals(recordA, recordC);
|
assertEquals(recordA, recordC);
|
||||||
|
assertNotEquals(recordA, recordD);
|
||||||
|
|
||||||
|
assertTrue(UnderlyingNetworkRecord.isEqualIncludingPriorities(recordA, recordB));
|
||||||
|
assertFalse(UnderlyingNetworkRecord.isEqualIncludingPriorities(recordA, recordC));
|
||||||
}
|
}
|
||||||
|
|
||||||
@Test
|
@Test
|
||||||
@@ -366,6 +555,10 @@ public class UnderlyingNetworkControllerTest {
|
|||||||
.build();
|
.build();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
private void verifyOnSelectedUnderlyingNetworkChanged(UnderlyingNetworkRecord expectedRecord) {
|
||||||
|
verify(mNetworkControllerCb).onSelectedUnderlyingNetworkChanged(eq(expectedRecord));
|
||||||
|
}
|
||||||
|
|
||||||
private UnderlyingNetworkListener verifyRegistrationOnAvailableAndGetCallback(
|
private UnderlyingNetworkListener verifyRegistrationOnAvailableAndGetCallback(
|
||||||
NetworkCapabilities networkCapabilities) {
|
NetworkCapabilities networkCapabilities) {
|
||||||
verify(mConnectivityManager)
|
verify(mConnectivityManager)
|
||||||
@@ -384,12 +577,12 @@ public class UnderlyingNetworkControllerTest {
|
|||||||
cb.onBlockedStatusChanged(mNetwork, false /* isFalse */);
|
cb.onBlockedStatusChanged(mNetwork, false /* isFalse */);
|
||||||
|
|
||||||
UnderlyingNetworkRecord expectedRecord =
|
UnderlyingNetworkRecord expectedRecord =
|
||||||
new UnderlyingNetworkRecord(
|
getTestNetworkRecord(
|
||||||
mNetwork,
|
mNetwork,
|
||||||
responseNetworkCaps,
|
responseNetworkCaps,
|
||||||
INITIAL_LINK_PROPERTIES,
|
INITIAL_LINK_PROPERTIES,
|
||||||
false /* isBlocked */);
|
false /* isBlocked */);
|
||||||
verify(mNetworkControllerCb).onSelectedUnderlyingNetworkChanged(eq(expectedRecord));
|
verifyOnSelectedUnderlyingNetworkChanged(expectedRecord);
|
||||||
return cb;
|
return cb;
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -402,12 +595,12 @@ public class UnderlyingNetworkControllerTest {
|
|||||||
cb.onCapabilitiesChanged(mNetwork, responseNetworkCaps);
|
cb.onCapabilitiesChanged(mNetwork, responseNetworkCaps);
|
||||||
|
|
||||||
UnderlyingNetworkRecord expectedRecord =
|
UnderlyingNetworkRecord expectedRecord =
|
||||||
new UnderlyingNetworkRecord(
|
getTestNetworkRecord(
|
||||||
mNetwork,
|
mNetwork,
|
||||||
responseNetworkCaps,
|
responseNetworkCaps,
|
||||||
INITIAL_LINK_PROPERTIES,
|
INITIAL_LINK_PROPERTIES,
|
||||||
false /* isBlocked */);
|
false /* isBlocked */);
|
||||||
verify(mNetworkControllerCb).onSelectedUnderlyingNetworkChanged(eq(expectedRecord));
|
verifyOnSelectedUnderlyingNetworkChanged(expectedRecord);
|
||||||
}
|
}
|
||||||
|
|
||||||
@Test
|
@Test
|
||||||
@@ -417,12 +610,12 @@ public class UnderlyingNetworkControllerTest {
|
|||||||
cb.onLinkPropertiesChanged(mNetwork, UPDATED_LINK_PROPERTIES);
|
cb.onLinkPropertiesChanged(mNetwork, UPDATED_LINK_PROPERTIES);
|
||||||
|
|
||||||
UnderlyingNetworkRecord expectedRecord =
|
UnderlyingNetworkRecord expectedRecord =
|
||||||
new UnderlyingNetworkRecord(
|
getTestNetworkRecord(
|
||||||
mNetwork,
|
mNetwork,
|
||||||
buildResponseNwCaps(INITIAL_NETWORK_CAPABILITIES, INITIAL_SUB_IDS),
|
buildResponseNwCaps(INITIAL_NETWORK_CAPABILITIES, INITIAL_SUB_IDS),
|
||||||
UPDATED_LINK_PROPERTIES,
|
UPDATED_LINK_PROPERTIES,
|
||||||
false /* isBlocked */);
|
false /* isBlocked */);
|
||||||
verify(mNetworkControllerCb).onSelectedUnderlyingNetworkChanged(eq(expectedRecord));
|
verifyOnSelectedUnderlyingNetworkChanged(expectedRecord);
|
||||||
}
|
}
|
||||||
|
|
||||||
@Test
|
@Test
|
||||||
@@ -434,18 +627,16 @@ public class UnderlyingNetworkControllerTest {
|
|||||||
cb.onCapabilitiesChanged(mNetwork, responseNetworkCaps);
|
cb.onCapabilitiesChanged(mNetwork, responseNetworkCaps);
|
||||||
|
|
||||||
UnderlyingNetworkRecord expectedRecord =
|
UnderlyingNetworkRecord expectedRecord =
|
||||||
new UnderlyingNetworkRecord(
|
getTestNetworkRecord(
|
||||||
mNetwork,
|
mNetwork,
|
||||||
responseNetworkCaps,
|
responseNetworkCaps,
|
||||||
INITIAL_LINK_PROPERTIES,
|
INITIAL_LINK_PROPERTIES,
|
||||||
false /* isBlocked */);
|
false /* isBlocked */);
|
||||||
verify(mNetworkControllerCb, times(1))
|
verifyOnSelectedUnderlyingNetworkChanged(expectedRecord);
|
||||||
.onSelectedUnderlyingNetworkChanged(eq(expectedRecord));
|
|
||||||
// onSelectedUnderlyingNetworkChanged() won't be fired twice if network capabilities doesn't
|
// onSelectedUnderlyingNetworkChanged() won't be fired twice if network capabilities doesn't
|
||||||
// change.
|
// change.
|
||||||
cb.onCapabilitiesChanged(mNetwork, responseNetworkCaps);
|
cb.onCapabilitiesChanged(mNetwork, responseNetworkCaps);
|
||||||
verify(mNetworkControllerCb, times(1))
|
verifyOnSelectedUnderlyingNetworkChanged(expectedRecord);
|
||||||
.onSelectedUnderlyingNetworkChanged(eq(expectedRecord));
|
|
||||||
}
|
}
|
||||||
|
|
||||||
@Test
|
@Test
|
||||||
@@ -458,18 +649,16 @@ public class UnderlyingNetworkControllerTest {
|
|||||||
cb.onCapabilitiesChanged(mNetwork, responseNetworkCaps);
|
cb.onCapabilitiesChanged(mNetwork, responseNetworkCaps);
|
||||||
|
|
||||||
UnderlyingNetworkRecord expectedRecord =
|
UnderlyingNetworkRecord expectedRecord =
|
||||||
new UnderlyingNetworkRecord(
|
getTestNetworkRecord(
|
||||||
mNetwork,
|
mNetwork,
|
||||||
responseNetworkCaps,
|
responseNetworkCaps,
|
||||||
INITIAL_LINK_PROPERTIES,
|
INITIAL_LINK_PROPERTIES,
|
||||||
false /* isBlocked */);
|
false /* isBlocked */);
|
||||||
verify(mNetworkControllerCb, times(1))
|
verifyOnSelectedUnderlyingNetworkChanged(expectedRecord);
|
||||||
.onSelectedUnderlyingNetworkChanged(eq(expectedRecord));
|
|
||||||
// onSelectedUnderlyingNetworkChanged() won't be fired twice if network capabilities doesn't
|
// onSelectedUnderlyingNetworkChanged() won't be fired twice if network capabilities doesn't
|
||||||
// change.
|
// change.
|
||||||
cb.onCapabilitiesChanged(mNetwork, responseNetworkCaps);
|
cb.onCapabilitiesChanged(mNetwork, responseNetworkCaps);
|
||||||
verify(mNetworkControllerCb, times(1))
|
verifyOnSelectedUnderlyingNetworkChanged(expectedRecord);
|
||||||
.onSelectedUnderlyingNetworkChanged(eq(expectedRecord));
|
|
||||||
}
|
}
|
||||||
|
|
||||||
@Test
|
@Test
|
||||||
@@ -478,13 +667,7 @@ public class UnderlyingNetworkControllerTest {
|
|||||||
|
|
||||||
cb.onBlockedStatusChanged(mNetwork, true /* isBlocked */);
|
cb.onBlockedStatusChanged(mNetwork, true /* isBlocked */);
|
||||||
|
|
||||||
UnderlyingNetworkRecord expectedRecord =
|
verifyOnSelectedUnderlyingNetworkChanged(null);
|
||||||
new UnderlyingNetworkRecord(
|
|
||||||
mNetwork,
|
|
||||||
buildResponseNwCaps(INITIAL_NETWORK_CAPABILITIES, INITIAL_SUB_IDS),
|
|
||||||
INITIAL_LINK_PROPERTIES,
|
|
||||||
true /* isBlocked */);
|
|
||||||
verify(mNetworkControllerCb).onSelectedUnderlyingNetworkChanged(eq(expectedRecord));
|
|
||||||
}
|
}
|
||||||
|
|
||||||
@Test
|
@Test
|
||||||
@@ -520,5 +703,132 @@ public class UnderlyingNetworkControllerTest {
|
|||||||
verify(mNetworkControllerCb, times(1)).onSelectedUnderlyingNetworkChanged(any());
|
verify(mNetworkControllerCb, times(1)).onSelectedUnderlyingNetworkChanged(any());
|
||||||
}
|
}
|
||||||
|
|
||||||
// TODO (b/187991063): Add tests for network prioritization
|
private UnderlyingNetworkListener setupControllerAndGetNetworkListener(
|
||||||
|
List<VcnUnderlyingNetworkTemplate> networkTemplates) {
|
||||||
|
final ConnectivityManager cm = mock(ConnectivityManager.class);
|
||||||
|
setupSystemService(mContext, cm, Context.CONNECTIVITY_SERVICE, ConnectivityManager.class);
|
||||||
|
|
||||||
|
new UnderlyingNetworkController(
|
||||||
|
mVcnContext,
|
||||||
|
VcnGatewayConnectionConfigTest.buildTestConfig(networkTemplates),
|
||||||
|
SUB_GROUP,
|
||||||
|
mSubscriptionSnapshot,
|
||||||
|
mNetworkControllerCb);
|
||||||
|
|
||||||
|
verify(cm)
|
||||||
|
.registerNetworkCallback(
|
||||||
|
eq(getRouteSelectionRequest(INITIAL_SUB_IDS)),
|
||||||
|
mUnderlyingNetworkListenerCaptor.capture(),
|
||||||
|
any());
|
||||||
|
|
||||||
|
return mUnderlyingNetworkListenerCaptor.getValue();
|
||||||
|
}
|
||||||
|
|
||||||
|
private UnderlyingNetworkRecord bringupNetworkAndGetRecord(
|
||||||
|
UnderlyingNetworkListener cb,
|
||||||
|
NetworkCapabilities requestNetworkCaps,
|
||||||
|
List<VcnUnderlyingNetworkTemplate> underlyingNetworkTemplates,
|
||||||
|
UnderlyingNetworkRecord currentlySelected) {
|
||||||
|
final Network network = mock(Network.class);
|
||||||
|
final NetworkCapabilities responseNetworkCaps =
|
||||||
|
buildResponseNwCaps(requestNetworkCaps, INITIAL_SUB_IDS);
|
||||||
|
|
||||||
|
cb.onAvailable(network);
|
||||||
|
cb.onCapabilitiesChanged(network, responseNetworkCaps);
|
||||||
|
cb.onLinkPropertiesChanged(network, INITIAL_LINK_PROPERTIES);
|
||||||
|
cb.onBlockedStatusChanged(network, false /* isFalse */);
|
||||||
|
return new UnderlyingNetworkRecord(
|
||||||
|
network,
|
||||||
|
responseNetworkCaps,
|
||||||
|
INITIAL_LINK_PROPERTIES,
|
||||||
|
false /* isBlocked */,
|
||||||
|
mVcnContext,
|
||||||
|
underlyingNetworkTemplates,
|
||||||
|
SUB_GROUP,
|
||||||
|
mSubscriptionSnapshot,
|
||||||
|
currentlySelected,
|
||||||
|
null /* carrierConfig */);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void testSelectMorePreferredNetwork() {
|
||||||
|
final List<VcnUnderlyingNetworkTemplate> networkTemplates = new ArrayList();
|
||||||
|
networkTemplates.add(CELL_TEMPLATE_DUN);
|
||||||
|
networkTemplates.add(CELL_TEMPLATE_CBS);
|
||||||
|
|
||||||
|
UnderlyingNetworkListener cb = setupControllerAndGetNetworkListener(networkTemplates);
|
||||||
|
|
||||||
|
// Bring up CBS network
|
||||||
|
final UnderlyingNetworkRecord cbsNetworkRecord =
|
||||||
|
bringupNetworkAndGetRecord(
|
||||||
|
cb,
|
||||||
|
CBS_NETWORK_CAPABILITIES,
|
||||||
|
networkTemplates,
|
||||||
|
null /* currentlySelected */);
|
||||||
|
verify(mNetworkControllerCb).onSelectedUnderlyingNetworkChanged(eq(cbsNetworkRecord));
|
||||||
|
|
||||||
|
// Bring up DUN network
|
||||||
|
final UnderlyingNetworkRecord dunNetworkRecord =
|
||||||
|
bringupNetworkAndGetRecord(
|
||||||
|
cb, DUN_NETWORK_CAPABILITIES, networkTemplates, cbsNetworkRecord);
|
||||||
|
verify(mNetworkControllerCb).onSelectedUnderlyingNetworkChanged(eq(dunNetworkRecord));
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void testNeverSelectLessPreferredNetwork() {
|
||||||
|
final List<VcnUnderlyingNetworkTemplate> networkTemplates = new ArrayList();
|
||||||
|
networkTemplates.add(CELL_TEMPLATE_DUN);
|
||||||
|
networkTemplates.add(CELL_TEMPLATE_CBS);
|
||||||
|
|
||||||
|
UnderlyingNetworkListener cb = setupControllerAndGetNetworkListener(networkTemplates);
|
||||||
|
|
||||||
|
// Bring up DUN network
|
||||||
|
final UnderlyingNetworkRecord dunNetworkRecord =
|
||||||
|
bringupNetworkAndGetRecord(
|
||||||
|
cb,
|
||||||
|
DUN_NETWORK_CAPABILITIES,
|
||||||
|
networkTemplates,
|
||||||
|
null /* currentlySelected */);
|
||||||
|
verify(mNetworkControllerCb).onSelectedUnderlyingNetworkChanged(eq(dunNetworkRecord));
|
||||||
|
|
||||||
|
// Bring up CBS network
|
||||||
|
final UnderlyingNetworkRecord cbsNetworkRecord =
|
||||||
|
bringupNetworkAndGetRecord(
|
||||||
|
cb, CBS_NETWORK_CAPABILITIES, networkTemplates, dunNetworkRecord);
|
||||||
|
verify(mNetworkControllerCb, never())
|
||||||
|
.onSelectedUnderlyingNetworkChanged(eq(cbsNetworkRecord));
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void testFailtoMatchTemplateAndFallBackToInternetNetwork() {
|
||||||
|
final List<VcnUnderlyingNetworkTemplate> networkTemplates = new ArrayList();
|
||||||
|
|
||||||
|
networkTemplates.add(
|
||||||
|
new VcnCellUnderlyingNetworkTemplate.Builder().setDun(MATCH_REQUIRED).build());
|
||||||
|
UnderlyingNetworkListener cb = setupControllerAndGetNetworkListener(networkTemplates);
|
||||||
|
|
||||||
|
// Bring up an Internet network without DUN capability
|
||||||
|
final UnderlyingNetworkRecord networkRecord =
|
||||||
|
bringupNetworkAndGetRecord(
|
||||||
|
cb,
|
||||||
|
INITIAL_NETWORK_CAPABILITIES,
|
||||||
|
networkTemplates,
|
||||||
|
null /* currentlySelected */);
|
||||||
|
verify(mNetworkControllerCb).onSelectedUnderlyingNetworkChanged(eq(networkRecord));
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void testFailtoMatchTemplateAndNeverFallBackToNonInternetNetwork() {
|
||||||
|
final List<VcnUnderlyingNetworkTemplate> networkTemplates = new ArrayList();
|
||||||
|
|
||||||
|
networkTemplates.add(
|
||||||
|
new VcnCellUnderlyingNetworkTemplate.Builder().setDun(MATCH_REQUIRED).build());
|
||||||
|
UnderlyingNetworkListener cb = setupControllerAndGetNetworkListener(networkTemplates);
|
||||||
|
|
||||||
|
bringupNetworkAndGetRecord(
|
||||||
|
cb, CBS_NETWORK_CAPABILITIES, networkTemplates, null /* currentlySelected */);
|
||||||
|
|
||||||
|
verify(mNetworkControllerCb, never())
|
||||||
|
.onSelectedUnderlyingNetworkChanged(any(UnderlyingNetworkRecord.class));
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
Reference in New Issue
Block a user