Enhance global settings for carrier-specific "avoid bad WiFi" behavior
Previously, the "avoid bad WiFi" global setting was limited to a single boolean value (0 or 1), preventing granular control for multiple carriers. This commit introduces support for carrier-aware "avoid bad WiFi" configurations using a new, extensible format: "subId1,value1;subId2,value2;...". This allows different `subId`s (carriers) to have their own specific "avoid bad WiFi" settings. Flag: EXEMPT mainline Bug: 410976315 Test: atest ConnectivityCoverageTests:android.net.connectivity.com.android.server.connectivity.MultinetworkPolicyTrackerTest Change-Id: I118cff67c0c632778f73649999ee63e6f0e6fb17
This commit is contained in:
parent
92e23acebb
commit
cbdfd9f54b
2 changed files with 99 additions and 13 deletions
|
|
@ -20,6 +20,10 @@ import static android.content.pm.PackageManager.FEATURE_TELEPHONY_SUBSCRIPTION;
|
|||
import static android.net.ConnectivitySettingsManager.NETWORK_AVOID_BAD_WIFI;
|
||||
import static android.net.ConnectivitySettingsManager.NETWORK_METERED_MULTIPATH_PREFERENCE;
|
||||
|
||||
import static com.android.net.module.util.ConnectivitySettingsUtils.convertCarrierAwareSettingsStringToMap;
|
||||
import static com.android.net.module.util.ConnectivitySettingsUtils.getNetworkAvoidBadWifiSetting;
|
||||
import static com.android.net.module.util.ConnectivitySettingsUtils.getNetworkLegacyGlobalAvoidBadWifiSetting;
|
||||
|
||||
import android.annotation.IntDef;
|
||||
import android.annotation.NonNull;
|
||||
import android.annotation.Nullable;
|
||||
|
|
@ -57,6 +61,7 @@ import java.lang.annotation.Retention;
|
|||
import java.lang.annotation.RetentionPolicy;
|
||||
import java.util.Arrays;
|
||||
import java.util.List;
|
||||
import java.util.Map;
|
||||
import java.util.concurrent.Executor;
|
||||
import java.util.concurrent.RejectedExecutionException;
|
||||
|
||||
|
|
@ -508,6 +513,54 @@ public class MultinetworkPolicyTracker {
|
|||
mHandler.post(() -> updateAvoidBadWifiFromCarrierConfig(subId, config));
|
||||
}
|
||||
|
||||
/**
|
||||
* Determines whether the device should avoid bad Wi-Fi connections based on a hierarchical
|
||||
* preference for settings.
|
||||
*
|
||||
* This method checks for the "avoid bad Wi-Fi" setting by first looking for a
|
||||
* **carrier-aware setting** via {@code NETWORK_CARRIER_AWARE_AVOID_BAD_WIFI}.
|
||||
* If this setting is present and contains a value for the {@code mActiveSubId},
|
||||
* that value is used.
|
||||
* If {@code mActiveSubId} isn't explicitly found in the map, then fall back to the
|
||||
* **legacy global setting** {@code NETWORK_AVOID_BAD_WIFI}.
|
||||
*
|
||||
* If the carrier-aware setting isn't available (i.e., it's {@code null}), the method then
|
||||
* falls back to the **legacy global setting** {@code NETWORK_AVOID_BAD_WIFI}.
|
||||
* This setting is considered {@code true} if its value is anything other than "0",
|
||||
* and {@code false} if it is "0".
|
||||
*
|
||||
* Finally, if neither of the above settings is available (meaning both are {@code null}),
|
||||
* the method retrieves the setting from a **local cache** using
|
||||
* {@code readAvoidBadWifiFromCache(mActiveSubId)}.
|
||||
* This is done to avoid potential IPC issues or blocking.
|
||||
*
|
||||
* @return {@code true} if the device should avoid bad Wi-Fi based on the highest priority
|
||||
* available setting, {@code false} otherwise.
|
||||
*/
|
||||
private boolean getAvoidBadWifiInternal() {
|
||||
final String carrierAwareSetting =
|
||||
getNetworkAvoidBadWifiSetting(mContext);
|
||||
if (carrierAwareSetting != null) {
|
||||
final Map<Integer, Boolean> settingMap =
|
||||
convertCarrierAwareSettingsStringToMap(carrierAwareSetting);
|
||||
if (settingMap.containsKey(mActiveSubId)) {
|
||||
return settingMap.get(mActiveSubId);
|
||||
}
|
||||
}
|
||||
|
||||
// if NETWORK_CARRIER_AWARE_AVOID_BAD_WIFI is not set,
|
||||
// check NETWORK_AVOID_BAD_WIFI setting for backward compatible
|
||||
final String setting =
|
||||
getNetworkLegacyGlobalAvoidBadWifiSetting(mContext);
|
||||
if (setting != null) {
|
||||
return !setting.equals("0");
|
||||
}
|
||||
|
||||
// Retrieve the avoid bad Wi-Fi setting from the local cache to avoid potential
|
||||
// issues or blocking from the IPC call getAvoidBadWifiCarrierConfigForSubId().
|
||||
return readAvoidBadWifiFromCache(mActiveSubId);
|
||||
}
|
||||
|
||||
/**
|
||||
* Updates the "avoid bad Wi-Fi" setting.
|
||||
* Depending on whether the carrier config feature is enabled, this method uses different logic:
|
||||
|
|
@ -535,14 +588,7 @@ public class MultinetworkPolicyTracker {
|
|||
// and mAvoidBadWifiFromCarrierConfigFeature is a trunk stable flag
|
||||
// that only exists in 25Q4+
|
||||
mActivelyPreferBadWifi = true;
|
||||
final String settingAvoidBadWifiStr = readAvoidBadWifiFromSettings();
|
||||
if (settingAvoidBadWifiStr != null) {
|
||||
mAvoidBadWifi = "1".equals(settingAvoidBadWifiStr);
|
||||
} else {
|
||||
// Retrieve the avoid bad Wi-Fi setting from the local cache to avoid potential
|
||||
// issues or blocking from the IPC call getAvoidBadWifiCarrierConfigForSubId().
|
||||
mAvoidBadWifi = readAvoidBadWifiFromCache(mActiveSubId);
|
||||
}
|
||||
mAvoidBadWifi = getAvoidBadWifiInternal();
|
||||
return mAvoidBadWifi != prevAvoid;
|
||||
case FROM_RESOURCE:
|
||||
final boolean settingAvoidBadWifi = "1".equals(readAvoidBadWifiFromSettings());
|
||||
|
|
|
|||
|
|
@ -23,6 +23,7 @@ import android.net.ConnectivityManager.MULTIPATH_PREFERENCE_HANDOVER
|
|||
import android.net.ConnectivityManager.MULTIPATH_PREFERENCE_PERFORMANCE
|
||||
import android.net.ConnectivityManager.MULTIPATH_PREFERENCE_RELIABILITY
|
||||
import android.net.ConnectivitySettingsManager.NETWORK_AVOID_BAD_WIFI
|
||||
import android.net.ConnectivitySettingsManager.NETWORK_CARRIER_AWARE_AVOID_BAD_WIFI
|
||||
import android.net.ConnectivitySettingsManager.NETWORK_METERED_MULTIPATH_PREFERENCE
|
||||
import android.net.platform.flags.Flags.FLAG_AVOID_BAD_WIFI_FROM_CARRIER_CONFIG
|
||||
import android.os.Build
|
||||
|
|
@ -310,8 +311,8 @@ class MultinetworkPolicyTrackerTest(private val supportCarrierConfigManager: Boo
|
|||
@DevSdkIgnoreRule.IgnoreUpTo(Build.VERSION_CODES.BAKLAVA)
|
||||
fun testAvoidBadWifiWithGlobalSetting() {
|
||||
val activeSubId = 1000
|
||||
// Mock the initial global setting to false
|
||||
Settings.Global.putString(resolver, NETWORK_AVOID_BAD_WIFI, "0")
|
||||
// Mock the initial NETWORK_CARRIER_AWARE_AVOID_BAD_WIFI setting to false
|
||||
Settings.Global.putString(resolver, NETWORK_CARRIER_AWARE_AVOID_BAD_WIFI, "$activeSubId,0")
|
||||
// Mock the initial carrier configuration to return true
|
||||
trackerDependencies.setAvoidBadWifiCarrierConfigForSubId(activeSubId, true)
|
||||
|
||||
|
|
@ -330,12 +331,51 @@ class MultinetworkPolicyTrackerTest(private val supportCarrierConfigManager: Boo
|
|||
assertFalse(tracker.avoidBadWifi)
|
||||
assertTrue(tracker.activelyPreferBadWifi)
|
||||
|
||||
// Mock the initial global setting to true
|
||||
Settings.Global.putString(resolver, NETWORK_AVOID_BAD_WIFI, "1")
|
||||
// Mock the NETWORK_CARRIER_AWARE_AVOID_BAD_WIFI setting to true
|
||||
Settings.Global.putString(resolver, NETWORK_CARRIER_AWARE_AVOID_BAD_WIFI, "$activeSubId,1")
|
||||
// Mock the initial carrier configuration to return false
|
||||
trackerDependencies.setAvoidBadWifiCarrierConfigForSubId(activeSubId, false)
|
||||
|
||||
// Assert that the tracker's avoidBadWifi flag is true based on global setting
|
||||
// Assert that the tracker's avoidBadWifi flag is true based on carrier aware setting
|
||||
assertTrue(tracker.updateAvoidBadWifi())
|
||||
assertTrue(tracker.avoidBadWifi)
|
||||
assertTrue(tracker.activelyPreferBadWifi)
|
||||
|
||||
val testSubId = 1001
|
||||
// Mock the NETWORK_CARRIER_AWARE_AVOID_BAD_WIFI setting to multiple carrier setting
|
||||
Settings.Global.putString(
|
||||
resolver,
|
||||
NETWORK_CARRIER_AWARE_AVOID_BAD_WIFI,
|
||||
"$activeSubId, 0;$testSubId, 1"
|
||||
)
|
||||
|
||||
// Assert that the tracker's avoidBadWifi flag is false based on carrier aware setting
|
||||
assertTrue(tracker.updateAvoidBadWifi())
|
||||
assertFalse(tracker.avoidBadWifi)
|
||||
assertTrue(tracker.activelyPreferBadWifi)
|
||||
|
||||
// Simulate a change in the active data subscription ID to testSubId.
|
||||
listener.onActiveDataSubscriptionIdChanged(testSubId)
|
||||
|
||||
// Assert that the tracker's avoidBadWifi flag is true based on carrier aware setting
|
||||
assertTrue(tracker.avoidBadWifi)
|
||||
assertTrue(tracker.activelyPreferBadWifi)
|
||||
|
||||
// Unset NETWORK_CARRIER_AWARE_AVOID_BAD_WIFI setting,
|
||||
// it check NETWORK_AVOID_BAD_WIFI setting for backward compatible
|
||||
Settings.Global.putString(resolver, NETWORK_CARRIER_AWARE_AVOID_BAD_WIFI, null)
|
||||
// Mock the NETWORK_AVOID_BAD_WIFI setting to setting
|
||||
Settings.Global.putString(resolver, NETWORK_AVOID_BAD_WIFI, "0")
|
||||
|
||||
// Assert that the tracker's avoidBadWifi flag is true based on setting
|
||||
assertTrue(tracker.updateAvoidBadWifi())
|
||||
assertFalse(tracker.avoidBadWifi)
|
||||
assertTrue(tracker.activelyPreferBadWifi)
|
||||
|
||||
// Mock the NETWORK_AVOID_BAD_WIFI setting to setting
|
||||
Settings.Global.putString(resolver, NETWORK_AVOID_BAD_WIFI, "1")
|
||||
|
||||
// Assert that the tracker's avoidBadWifi flag is true based on setting
|
||||
assertTrue(tracker.updateAvoidBadWifi())
|
||||
assertTrue(tracker.avoidBadWifi)
|
||||
assertTrue(tracker.activelyPreferBadWifi)
|
||||
|
|
|
|||
Loading…
Reference in a new issue