Merge "[CLATJ#27] Use ClatdCoordinator since T+ devices"
diff --git a/Tethering/src/com/android/networkstack/tethering/EntitlementManager.java b/Tethering/src/com/android/networkstack/tethering/EntitlementManager.java
index 844efde..adc95ab 100644
--- a/Tethering/src/com/android/networkstack/tethering/EntitlementManager.java
+++ b/Tethering/src/com/android/networkstack/tethering/EntitlementManager.java
@@ -34,7 +34,6 @@
 import static android.net.TetheringManager.TETHER_ERROR_PROVISIONING_FAILED;
 
 import static com.android.networkstack.apishim.ConstantsShim.ACTION_TETHER_UNSUPPORTED_CARRIER_UI;
-import static com.android.networkstack.apishim.ConstantsShim.KEY_CARRIER_SUPPORTS_TETHERING_BOOL;
 
 import android.app.AlarmManager;
 import android.app.PendingIntent;
@@ -48,12 +47,10 @@
 import android.os.Bundle;
 import android.os.Handler;
 import android.os.Parcel;
-import android.os.PersistableBundle;
 import android.os.ResultReceiver;
 import android.os.SystemClock;
 import android.os.SystemProperties;
 import android.provider.Settings;
-import android.telephony.CarrierConfigManager;
 import android.util.SparseIntArray;
 
 import com.android.internal.annotations.VisibleForTesting;
@@ -307,13 +304,13 @@
         if (SystemProperties.getBoolean(DISABLE_PROVISIONING_SYSPROP_KEY, false)) {
             return TETHERING_PROVISIONING_NOT_REQUIRED;
         }
-        // TODO: Find a way to avoid get carrier config twice.
-        if (carrierConfigAffirmsCarrierNotSupport(config)) {
+
+        if (!config.isCarrierSupportTethering) {
             // To block tethering, behave as if running provisioning check and failed.
             return TETHERING_PROVISIONING_CARRIER_UNSUPPORT;
         }
 
-        if (carrierConfigAffirmsEntitlementCheckNotRequired(config)) {
+        if (!config.isCarrierConfigAffirmsEntitlementCheckRequired) {
             return TETHERING_PROVISIONING_NOT_REQUIRED;
         }
         return (config.provisioningApp.length == 2)
@@ -380,57 +377,6 @@
     }
 
     /**
-     * Get carrier configuration bundle.
-     * @param config an object that encapsulates the various tethering configuration elements.
-     * */
-    public PersistableBundle getCarrierConfig(final TetheringConfiguration config) {
-        final CarrierConfigManager configManager = mContext
-                .getSystemService(CarrierConfigManager.class);
-        if (configManager == null) return null;
-
-        final PersistableBundle carrierConfig = configManager.getConfigForSubId(
-                config.activeDataSubId);
-
-        if (CarrierConfigManager.isConfigForIdentifiedCarrier(carrierConfig)) {
-            return carrierConfig;
-        }
-
-        return null;
-    }
-
-    // The logic here is aimed solely at confirming that a CarrierConfig exists
-    // and affirms that entitlement checks are not required.
-    //
-    // TODO: find a better way to express this, or alter the checking process
-    // entirely so that this is more intuitive.
-    // TODO: Find a way to avoid using getCarrierConfig everytime.
-    private boolean carrierConfigAffirmsEntitlementCheckNotRequired(
-            final TetheringConfiguration config) {
-        // Check carrier config for entitlement checks
-        final PersistableBundle carrierConfig = getCarrierConfig(config);
-        if (carrierConfig == null) return false;
-
-        // A CarrierConfigManager was found and it has a config.
-        final boolean isEntitlementCheckRequired = carrierConfig.getBoolean(
-                CarrierConfigManager.KEY_REQUIRE_ENTITLEMENT_CHECKS_BOOL);
-        return !isEntitlementCheckRequired;
-    }
-
-    private boolean carrierConfigAffirmsCarrierNotSupport(final TetheringConfiguration config) {
-        if (!SdkLevel.isAtLeastT()) {
-            return false;
-        }
-        // Check carrier config for entitlement checks
-        final PersistableBundle carrierConfig = getCarrierConfig(config);
-        if (carrierConfig == null) return false;
-
-        // A CarrierConfigManager was found and it has a config.
-        final boolean mIsCarrierSupport = carrierConfig.getBoolean(
-                KEY_CARRIER_SUPPORTS_TETHERING_BOOL, true);
-        return !mIsCarrierSupport;
-    }
-
-    /**
      * Run no UI tethering provisioning check.
      * @param type tethering type from TetheringManager.TETHERING_{@code *}
      * @param subId default data subscription ID.
@@ -479,7 +425,7 @@
 
     private void runTetheringProvisioning(
             boolean showProvisioningUi, int downstreamType, final TetheringConfiguration config) {
-        if (carrierConfigAffirmsCarrierNotSupport(config)) {
+        if (!config.isCarrierSupportTethering) {
             mListener.onTetherProvisioningFailed(downstreamType, "Carrier does not support.");
             if (showProvisioningUi) {
                 showCarrierUnsupportedDialog();
@@ -497,7 +443,7 @@
     }
 
     private void showCarrierUnsupportedDialog() {
-        // This is only used when carrierConfigAffirmsCarrierNotSupport() is true.
+        // This is only used when TetheringConfiguration.isCarrierSupportTethering is false.
         if (!SdkLevel.isAtLeastT()) {
             return;
         }
diff --git a/Tethering/src/com/android/networkstack/tethering/Tethering.java b/Tethering/src/com/android/networkstack/tethering/Tethering.java
index 4504829..44935fc 100644
--- a/Tethering/src/com/android/networkstack/tethering/Tethering.java
+++ b/Tethering/src/com/android/networkstack/tethering/Tethering.java
@@ -482,7 +482,7 @@
             // To avoid launching unexpected provisioning checks, ignore re-provisioning
             // when no CarrierConfig loaded yet. Assume reevaluateSimCardProvisioning()
             // will be triggered again when CarrierConfig is loaded.
-            if (mEntitlementMgr.getCarrierConfig(mConfig) != null) {
+            if (TetheringConfiguration.getCarrierConfig(mContext, subId) != null) {
                 mEntitlementMgr.reevaluateSimCardProvisioning(mConfig);
             } else {
                 mLog.log("IGNORED reevaluate provisioning, no carrier config loaded");
diff --git a/Tethering/src/com/android/networkstack/tethering/TetheringConfiguration.java b/Tethering/src/com/android/networkstack/tethering/TetheringConfiguration.java
index f9f3ed9..7c36054 100644
--- a/Tethering/src/com/android/networkstack/tethering/TetheringConfiguration.java
+++ b/Tethering/src/com/android/networkstack/tethering/TetheringConfiguration.java
@@ -24,14 +24,17 @@
 import static android.provider.DeviceConfig.NAMESPACE_CONNECTIVITY;
 
 import static com.android.net.module.util.DeviceConfigUtils.TETHERING_MODULE_NAME;
+import static com.android.networkstack.apishim.ConstantsShim.KEY_CARRIER_SUPPORTS_TETHERING_BOOL;
 
 import android.content.ContentResolver;
 import android.content.Context;
 import android.content.res.Resources;
 import android.net.TetheringConfigurationParcel;
 import android.net.util.SharedLog;
+import android.os.PersistableBundle;
 import android.provider.DeviceConfig;
 import android.provider.Settings;
+import android.telephony.CarrierConfigManager;
 import android.telephony.SubscriptionManager;
 import android.telephony.TelephonyManager;
 import android.text.TextUtils;
@@ -142,6 +145,9 @@
     public final int provisioningCheckPeriod;
     public final String provisioningResponse;
 
+    public final boolean isCarrierSupportTethering;
+    public final boolean isCarrierConfigAffirmsEntitlementCheckRequired;
+
     public final int activeDataSubId;
 
     private final boolean mEnableLegacyDhcpServer;
@@ -207,6 +213,11 @@
         provisioningResponse = getResourceString(res,
                 R.string.config_mobile_hotspot_provision_response);
 
+        PersistableBundle carrierConfigs = getCarrierConfig(ctx, activeDataSubId);
+        isCarrierSupportTethering = carrierConfigAffirmsCarrierSupport(carrierConfigs);
+        isCarrierConfigAffirmsEntitlementCheckRequired =
+                carrierConfigAffirmsEntitlementCheckRequired(carrierConfigs);
+
         mOffloadPollInterval = getResourceInteger(res,
                 R.integer.config_tether_offload_poll_interval,
                 DEFAULT_TETHER_OFFLOAD_POLL_INTERVAL_MS);
@@ -329,6 +340,10 @@
         pw.print("provisioningAppNoUi: ");
         pw.println(provisioningAppNoUi);
 
+        pw.println("isCarrierSupportTethering: " + isCarrierSupportTethering);
+        pw.println("isCarrierConfigAffirmsEntitlementCheckRequired: "
+                + isCarrierConfigAffirmsEntitlementCheckRequired);
+
         pw.print("enableBpfOffload: ");
         pw.println(mEnableBpfOffload);
 
@@ -361,6 +376,9 @@
                 toIntArray(preferredUpstreamIfaceTypes)));
         sj.add(String.format("provisioningApp:%s", makeString(provisioningApp)));
         sj.add(String.format("provisioningAppNoUi:%s", provisioningAppNoUi));
+        sj.add(String.format("isCarrierSupportTethering:%s", isCarrierSupportTethering));
+        sj.add(String.format("isCarrierConfigAffirmsEntitlementCheckRequired:%s",
+                isCarrierConfigAffirmsEntitlementCheckRequired));
         sj.add(String.format("enableBpfOffload:%s", mEnableBpfOffload));
         sj.add(String.format("enableLegacyDhcpServer:%s", mEnableLegacyDhcpServer));
         return String.format("TetheringConfiguration{%s}", sj.toString());
@@ -596,6 +614,39 @@
         return result;
     }
 
+    private static boolean carrierConfigAffirmsEntitlementCheckRequired(
+            PersistableBundle carrierConfig) {
+        if (carrierConfig == null) {
+            return true;
+        }
+        return carrierConfig.getBoolean(
+                CarrierConfigManager.KEY_REQUIRE_ENTITLEMENT_CHECKS_BOOL, true);
+    }
+
+    private static boolean carrierConfigAffirmsCarrierSupport(PersistableBundle carrierConfig) {
+        if (!SdkLevel.isAtLeastT() || carrierConfig == null) {
+            return true;
+        }
+        return carrierConfig.getBoolean(KEY_CARRIER_SUPPORTS_TETHERING_BOOL, true);
+    }
+
+    /**
+     * Get carrier configuration bundle.
+     */
+    public static PersistableBundle getCarrierConfig(Context context, int activeDataSubId) {
+        final CarrierConfigManager configManager =
+                context.getSystemService(CarrierConfigManager.class);
+        if (configManager == null) {
+            return null;
+        }
+
+        final PersistableBundle carrierConfig = configManager.getConfigForSubId(activeDataSubId);
+        if (CarrierConfigManager.isConfigForIdentifiedCarrier(carrierConfig)) {
+            return carrierConfig;
+        }
+        return null;
+    }
+
     /**
      * Convert this TetheringConfiguration to a TetheringConfigurationParcel.
      */
diff --git a/Tethering/tests/unit/src/com/android/networkstack/tethering/EntitlementManagerTest.java b/Tethering/tests/unit/src/com/android/networkstack/tethering/EntitlementManagerTest.java
index 690ff71..01d7b4b 100644
--- a/Tethering/tests/unit/src/com/android/networkstack/tethering/EntitlementManagerTest.java
+++ b/Tethering/tests/unit/src/com/android/networkstack/tethering/EntitlementManagerTest.java
@@ -304,33 +304,6 @@
     }
 
     @Test
-    public void toleratesCarrierConfigManagerMissing() {
-        setupForRequiredProvisioning();
-        mockService(Context.CARRIER_CONFIG_SERVICE, CarrierConfigManager.class, null);
-        mConfig = new FakeTetheringConfiguration(mMockContext, mLog, INVALID_SUBSCRIPTION_ID);
-        // Couldn't get the CarrierConfigManager, but still had a declared provisioning app.
-        // Therefore provisioning still be required.
-        assertTrue(mEnMgr.isTetherProvisioningRequired(mConfig));
-    }
-
-    @Test
-    public void toleratesCarrierConfigMissing() {
-        setupForRequiredProvisioning();
-        when(mCarrierConfigManager.getConfig()).thenReturn(null);
-        mConfig = new FakeTetheringConfiguration(mMockContext, mLog, INVALID_SUBSCRIPTION_ID);
-        // We still have a provisioning app configured, so still require provisioning.
-        assertTrue(mEnMgr.isTetherProvisioningRequired(mConfig));
-    }
-
-    @Test
-    public void toleratesCarrierConfigNotLoaded() {
-        setupForRequiredProvisioning();
-        mCarrierConfig.putBoolean(CarrierConfigManager.KEY_CARRIER_CONFIG_APPLIED_BOOL, false);
-        // We still have a provisioning app configured, so still require provisioning.
-        assertTrue(mEnMgr.isTetherProvisioningRequired(mConfig));
-    }
-
-    @Test
     public void provisioningNotRequiredWhenAppNotFound() {
         setupForRequiredProvisioning();
         when(mResources.getStringArray(R.array.config_mobile_hotspot_provision_app))
@@ -706,8 +679,8 @@
     @IgnoreUpTo(SC_V2)
     public void requestLatestTetheringEntitlementResult_carrierDoesNotSupport_noProvisionCount()
             throws Exception {
-        setupForRequiredProvisioning();
         setupCarrierConfig(false);
+        setupForRequiredProvisioning();
         mEnMgr.fakeEntitlementResult = TETHER_ERROR_NO_ERROR;
         ResultReceiver receiver = new ResultReceiver(null) {
             @Override
@@ -735,6 +708,7 @@
         mEnMgr.notifyUpstream(false);
         mLooper.dispatchAll();
         setupCarrierConfig(false);
+        mConfig = new FakeTetheringConfiguration(mMockContext, mLog, INVALID_SUBSCRIPTION_ID);
         mEnMgr.reevaluateSimCardProvisioning(mConfig);
 
         // Turn on upstream.
@@ -749,8 +723,8 @@
     @IgnoreUpTo(SC_V2)
     public void startProvisioningIfNeeded_carrierUnsupport()
             throws Exception {
-        setupForRequiredProvisioning();
         setupCarrierConfig(false);
+        setupForRequiredProvisioning();
         mEnMgr.startProvisioningIfNeeded(TETHERING_WIFI, true);
         verify(mTetherProvisioningFailedListener, never())
                 .onTetherProvisioningFailed(TETHERING_WIFI, "Carrier does not support.");
diff --git a/Tethering/tests/unit/src/com/android/networkstack/tethering/TetheringConfigurationTest.java b/Tethering/tests/unit/src/com/android/networkstack/tethering/TetheringConfigurationTest.java
index 7fcf2b2..3190f35 100644
--- a/Tethering/tests/unit/src/com/android/networkstack/tethering/TetheringConfigurationTest.java
+++ b/Tethering/tests/unit/src/com/android/networkstack/tethering/TetheringConfigurationTest.java
@@ -22,10 +22,13 @@
 import static android.net.ConnectivityManager.TYPE_MOBILE_HIPRI;
 import static android.net.ConnectivityManager.TYPE_WIFI;
 import static android.provider.DeviceConfig.NAMESPACE_CONNECTIVITY;
+import static android.telephony.CarrierConfigManager.KEY_CARRIER_CONFIG_APPLIED_BOOL;
+import static android.telephony.CarrierConfigManager.KEY_REQUIRE_ENTITLEMENT_CHECKS_BOOL;
 import static android.telephony.SubscriptionManager.INVALID_SUBSCRIPTION_ID;
 
 import static com.android.dx.mockito.inline.extended.ExtendedMockito.doReturn;
 import static com.android.dx.mockito.inline.extended.ExtendedMockito.mockitoSession;
+import static com.android.networkstack.apishim.ConstantsShim.KEY_CARRIER_SUPPORTS_TETHERING_BOOL;
 import static com.android.networkstack.tethering.TetheringConfiguration.TETHER_FORCE_USB_FUNCTIONS;
 import static com.android.networkstack.tethering.TetheringConfiguration.TETHER_USB_NCM_FUNCTION;
 import static com.android.networkstack.tethering.TetheringConfiguration.TETHER_USB_RNDIS_FUNCTION;
@@ -46,8 +49,10 @@
 import android.content.res.Resources;
 import android.net.util.SharedLog;
 import android.os.Build;
+import android.os.PersistableBundle;
 import android.provider.DeviceConfig;
 import android.provider.Settings;
+import android.telephony.CarrierConfigManager;
 import android.telephony.TelephonyManager;
 import android.test.mock.MockContentResolver;
 
@@ -56,6 +61,7 @@
 
 import com.android.internal.util.test.BroadcastInterceptingContext;
 import com.android.internal.util.test.FakeSettingsProvider;
+import com.android.modules.utils.build.SdkLevel;
 import com.android.net.module.util.DeviceConfigUtils;
 import com.android.testutils.DevSdkIgnoreRule;
 import com.android.testutils.DevSdkIgnoreRule.IgnoreAfter;
@@ -88,6 +94,7 @@
     private static final long TEST_PACKAGE_VERSION = 1234L;
     @Mock private ApplicationInfo mApplicationInfo;
     @Mock private Context mContext;
+    @Mock private CarrierConfigManager mCarrierConfigManager;
     @Mock private TelephonyManager mTelephonyManager;
     @Mock private Resources mResources;
     @Mock private Resources mResourcesForSubId;
@@ -97,6 +104,7 @@
     private boolean mHasTelephonyManager;
     private MockitoSession mMockingSession;
     private MockContentResolver mContentResolver;
+    private final PersistableBundle mCarrierConfig = new PersistableBundle();
 
     private class MockTetheringConfiguration extends TetheringConfiguration {
         MockTetheringConfiguration(Context ctx, SharedLog log, int id) {
@@ -474,6 +482,56 @@
                 PROVISIONING_APP_RESPONSE);
     }
 
+    private <T> void mockService(String serviceName, Class<T> serviceClass, T service) {
+        when(mMockContext.getSystemServiceName(serviceClass)).thenReturn(serviceName);
+        when(mMockContext.getSystemService(serviceName)).thenReturn(service);
+    }
+
+    @Test
+    public void testGetCarrierConfigBySubId_noCarrierConfigManager_configsAreDefault() {
+        // Act like the CarrierConfigManager is present and ready unless told otherwise.
+        mockService(Context.CARRIER_CONFIG_SERVICE,
+                CarrierConfigManager.class, null);
+        final TetheringConfiguration cfg = new TetheringConfiguration(
+                mMockContext, mLog, INVALID_SUBSCRIPTION_ID);
+
+        assertTrue(cfg.isCarrierSupportTethering);
+        assertTrue(cfg.isCarrierConfigAffirmsEntitlementCheckRequired);
+    }
+
+    @Test
+    public void testGetCarrierConfigBySubId_carrierConfigMissing_configsAreDefault() {
+        // Act like the CarrierConfigManager is present and ready unless told otherwise.
+        mockService(Context.CARRIER_CONFIG_SERVICE,
+                CarrierConfigManager.class, mCarrierConfigManager);
+        when(mCarrierConfigManager.getConfigForSubId(anyInt())).thenReturn(null);
+        final TetheringConfiguration cfg = new TetheringConfiguration(
+                mMockContext, mLog, INVALID_SUBSCRIPTION_ID);
+
+        assertTrue(cfg.isCarrierSupportTethering);
+        assertTrue(cfg.isCarrierConfigAffirmsEntitlementCheckRequired);
+    }
+
+    @Test
+    public void testGetCarrierConfigBySubId_hasConfigs_carrierUnsupportAndCheckNotRequired() {
+        mockService(Context.CARRIER_CONFIG_SERVICE,
+                CarrierConfigManager.class, mCarrierConfigManager);
+        mCarrierConfig.putBoolean(KEY_CARRIER_CONFIG_APPLIED_BOOL, true);
+        mCarrierConfig.putBoolean(KEY_REQUIRE_ENTITLEMENT_CHECKS_BOOL, false);
+        mCarrierConfig.putBoolean(KEY_CARRIER_SUPPORTS_TETHERING_BOOL, false);
+        when(mCarrierConfigManager.getConfigForSubId(anyInt())).thenReturn(mCarrierConfig);
+        final TetheringConfiguration cfg = new TetheringConfiguration(
+                mMockContext, mLog, INVALID_SUBSCRIPTION_ID);
+
+        if (SdkLevel.isAtLeastT()) {
+            assertFalse(cfg.isCarrierSupportTethering);
+        } else {
+            assertTrue(cfg.isCarrierSupportTethering);
+        }
+        assertFalse(cfg.isCarrierConfigAffirmsEntitlementCheckRequired);
+
+    }
+
     @Test
     public void testEnableLegacyWifiP2PAddress() throws Exception {
         final TetheringConfiguration defaultCfg = new TetheringConfiguration(
diff --git a/service-t/src/com/android/server/ethernet/EthernetNetworkFactory.java b/service-t/src/com/android/server/ethernet/EthernetNetworkFactory.java
index eb22f78..fe27335 100644
--- a/service-t/src/com/android/server/ethernet/EthernetNetworkFactory.java
+++ b/service-t/src/com/android/server/ethernet/EthernetNetworkFactory.java
@@ -19,7 +19,6 @@
 import android.annotation.NonNull;
 import android.annotation.Nullable;
 import android.content.Context;
-import android.content.res.Resources;
 import android.net.ConnectivityManager;
 import android.net.ConnectivityResources;
 import android.net.EthernetManager;
@@ -71,8 +70,6 @@
 
     private final static int NETWORK_SCORE = 70;
     private static final String NETWORK_TYPE = "Ethernet";
-    private static final String LEGACY_TCP_BUFFER_SIZES =
-            "524288,1048576,3145728,524288,1048576,2097152";
 
     private final ConcurrentHashMap<String, NetworkInterfaceState> mTrackingInterfaces =
             new ConcurrentHashMap<>();
@@ -99,25 +96,9 @@
             return InterfaceParams.getByName(name);
         }
 
-        // TODO: remove legacy resource fallback after migrating its overlays.
-        private String getPlatformTcpBufferSizes(Context context) {
-            final Resources r = context.getResources();
-            final int resId = r.getIdentifier("config_ethernet_tcp_buffers", "string",
-                    context.getPackageName());
-            return r.getString(resId);
-        }
-
         public String getTcpBufferSizesFromResource(Context context) {
-            final String tcpBufferSizes;
-            final String platformTcpBufferSizes = getPlatformTcpBufferSizes(context);
-            if (!LEGACY_TCP_BUFFER_SIZES.equals(platformTcpBufferSizes)) {
-                // Platform resource is not the historical default: use the overlay.
-                tcpBufferSizes = platformTcpBufferSizes;
-            } else {
-                final ConnectivityResources resources = new ConnectivityResources(context);
-                tcpBufferSizes = resources.get().getString(R.string.config_ethernet_tcp_buffers);
-            }
-            return tcpBufferSizes;
+            final ConnectivityResources resources = new ConnectivityResources(context);
+            return resources.get().getString(R.string.config_ethernet_tcp_buffers);
         }
     }
 
diff --git a/service-t/src/com/android/server/ethernet/EthernetTracker.java b/service-t/src/com/android/server/ethernet/EthernetTracker.java
index 693d91a..e9053dd 100644
--- a/service-t/src/com/android/server/ethernet/EthernetTracker.java
+++ b/service-t/src/com/android/server/ethernet/EthernetTracker.java
@@ -25,7 +25,6 @@
 import android.annotation.NonNull;
 import android.annotation.Nullable;
 import android.content.Context;
-import android.content.res.Resources;
 import android.net.ConnectivityResources;
 import android.net.EthernetManager;
 import android.net.IEthernetServiceListener;
@@ -86,7 +85,6 @@
     private static final boolean DBG = EthernetNetworkFactory.DBG;
 
     private static final String TEST_IFACE_REGEXP = TEST_TAP_PREFIX + "\\d+";
-    private static final String LEGACY_IFACE_REGEXP = "eth\\d";
 
     /**
      * Interface names we track. This is a product-dependent regular expression, plus,
@@ -134,48 +132,16 @@
     }
 
     public static class Dependencies {
-        // TODO: remove legacy resource fallback after migrating its overlays.
-        private String getPlatformRegexResource(Context context) {
-            final Resources r = context.getResources();
-            final int resId =
-                r.getIdentifier("config_ethernet_iface_regex", "string", context.getPackageName());
-            return r.getString(resId);
-        }
-
-        // TODO: remove legacy resource fallback after migrating its overlays.
-        private String[] getPlatformInterfaceConfigs(Context context) {
-            final Resources r = context.getResources();
-            final int resId = r.getIdentifier("config_ethernet_interfaces", "array",
-                    context.getPackageName());
-            return r.getStringArray(resId);
-        }
-
         public String getInterfaceRegexFromResource(Context context) {
-            final String platformRegex = getPlatformRegexResource(context);
-            final String match;
-            if (!LEGACY_IFACE_REGEXP.equals(platformRegex)) {
-                // Platform resource is not the historical default: use the overlay
-                match = platformRegex;
-            } else {
-                final ConnectivityResources resources = new ConnectivityResources(context);
-                match = resources.get().getString(
-                        com.android.connectivity.resources.R.string.config_ethernet_iface_regex);
-            }
-            return match;
+            final ConnectivityResources resources = new ConnectivityResources(context);
+            return resources.get().getString(
+                    com.android.connectivity.resources.R.string.config_ethernet_iface_regex);
         }
 
         public String[] getInterfaceConfigFromResource(Context context) {
-            final String[] platformInterfaceConfigs = getPlatformInterfaceConfigs(context);
-            final String[] interfaceConfigs;
-            if (platformInterfaceConfigs.length != 0) {
-                // Platform resource is not the historical default: use the overlay
-                interfaceConfigs = platformInterfaceConfigs;
-            } else {
-                final ConnectivityResources resources = new ConnectivityResources(context);
-                interfaceConfigs = resources.get().getStringArray(
-                        com.android.connectivity.resources.R.array.config_ethernet_interfaces);
-            }
-            return interfaceConfigs;
+            final ConnectivityResources resources = new ConnectivityResources(context);
+            return resources.get().getStringArray(
+                    com.android.connectivity.resources.R.array.config_ethernet_interfaces);
         }
     }
 
diff --git a/service/src/com/android/server/connectivity/PermissionMonitor.java b/service/src/com/android/server/connectivity/PermissionMonitor.java
index 62b3add..c02d9cf 100755
--- a/service/src/com/android/server/connectivity/PermissionMonitor.java
+++ b/service/src/com/android/server/connectivity/PermissionMonitor.java
@@ -134,7 +134,9 @@
 
     // Store appIds traffic permissions for each user.
     // Keys are users, Values are SparseArrays where each entry maps an appId to the permissions
-    // that appId has within that user.
+    // that appId has within that user. The permissions are a bitmask of PERMISSION_INTERNET and
+    // PERMISSION_UPDATE_DEVICE_STATS, or 0 (PERMISSION_NONE) if the app has neither of those
+    // permissions. They can never be PERMISSION_UNINSTALLED.
     @GuardedBy("this")
     private final Map<UserHandle, SparseIntArray> mUsersTrafficPermissions = new ArrayMap<>();
 
@@ -545,17 +547,21 @@
 
         // Remove appIds traffic permission that belongs to the user
         final SparseIntArray removedUserAppIds = mUsersTrafficPermissions.remove(user);
-        // Generate appIds from left users.
+        // Generate appIds from the remaining users.
         final SparseIntArray appIds = makeAppIdsTrafficPermForAllUsers();
+
+        if (removedUserAppIds == null) {
+            Log.wtf(TAG, "onUserRemoved: Receive unknown user=" + user);
+            return;
+        }
+
         // Clear permission on those appIds belong to this user only, set the permission to
         // PERMISSION_UNINSTALLED.
-        if (removedUserAppIds != null) {
-            for (int i = 0; i < removedUserAppIds.size(); i++) {
-                final int appId = removedUserAppIds.keyAt(i);
-                // Need to clear permission if the removed appId is not found in the array.
-                if (appIds.indexOfKey(appId) < 0) {
-                    appIds.put(appId, PERMISSION_UNINSTALLED);
-                }
+        for (int i = 0; i < removedUserAppIds.size(); i++) {
+            final int appId = removedUserAppIds.keyAt(i);
+            // Need to clear permission if the removed appId is not found in the array.
+            if (appIds.indexOfKey(appId) < 0) {
+                appIds.put(appId, PERMISSION_UNINSTALLED);
             }
         }
         sendAppIdsTrafficPermission(appIds);
@@ -650,7 +656,6 @@
     }
 
     private synchronized void updateAppIdTrafficPermission(int uid) {
-        final int appId = UserHandle.getAppId(uid);
         final int uidTrafficPerm = getTrafficPermissionForUid(uid);
         final SparseIntArray userTrafficPerms =
                 mUsersTrafficPermissions.get(UserHandle.getUserHandleForUid(uid));
@@ -661,6 +666,7 @@
         // Do not put PERMISSION_UNINSTALLED into the array. If no package left on the uid
         // (PERMISSION_UNINSTALLED), remove the appId from the array. Otherwise, update the latest
         // permission to the appId.
+        final int appId = UserHandle.getAppId(uid);
         if (uidTrafficPerm == PERMISSION_UNINSTALLED) {
             userTrafficPerms.delete(appId);
         } else {
@@ -984,10 +990,6 @@
      */
     @VisibleForTesting
     void sendAppIdsTrafficPermission(SparseIntArray netdPermissionsAppIds) {
-        if (mNetd == null) {
-            Log.e(TAG, "Failed to get the netd service");
-            return;
-        }
         final ArrayList<Integer> allPermissionAppIds = new ArrayList<>();
         final ArrayList<Integer> internetPermissionAppIds = new ArrayList<>();
         final ArrayList<Integer> updateStatsPermissionAppIds = new ArrayList<>();
diff --git a/tests/common/AndroidTest_Coverage.xml b/tests/common/AndroidTest_Coverage.xml
index d4898b2..48d26b8 100644
--- a/tests/common/AndroidTest_Coverage.xml
+++ b/tests/common/AndroidTest_Coverage.xml
@@ -14,7 +14,8 @@
 -->
 <configuration description="Runs coverage tests for Connectivity">
     <target_preparer class="com.android.tradefed.targetprep.TestAppInstallSetup">
-        <option name="test-file-name" value="ConnectivityCoverageTests.apk" />
+      <option name="test-file-name" value="ConnectivityCoverageTests.apk" />
+      <option name="install-arg" value="-t" />
     </target_preparer>
 
     <option name="test-tag" value="ConnectivityCoverageTests" />
diff --git a/tests/unit/AndroidManifest.xml b/tests/unit/AndroidManifest.xml
index 887f171..54e1cd0 100644
--- a/tests/unit/AndroidManifest.xml
+++ b/tests/unit/AndroidManifest.xml
@@ -50,7 +50,7 @@
     <uses-permission android:name="android.permission.NETWORK_STATS_PROVIDER" />
     <uses-permission android:name="android.permission.CONTROL_OEM_PAID_NETWORK_PREFERENCE" />
 
-    <application>
+    <application android:testOnly="true">
         <uses-library android:name="android.test.runner" />
         <uses-library android:name="android.net.ipsec.ike" />
         <activity
diff --git a/tests/unit/AndroidTest.xml b/tests/unit/AndroidTest.xml
index 939ae49..2d32e55 100644
--- a/tests/unit/AndroidTest.xml
+++ b/tests/unit/AndroidTest.xml
@@ -15,7 +15,8 @@
 -->
 <configuration description="Runs Frameworks Networking Tests.">
     <target_preparer class="com.android.tradefed.targetprep.TestAppInstallSetup">
-        <option name="test-file-name" value="FrameworksNetTests.apk" />
+      <option name="test-file-name" value="FrameworksNetTests.apk" />
+      <option name="install-arg" value="-t" />
     </target_preparer>
 
     <option name="test-suite-tag" value="apct" />