Merge "Cleaning EthernetNetworkFactoryTest Unprovisioned"
diff --git a/service-t/src/com/android/server/ethernet/EthernetNetworkFactory.java b/service-t/src/com/android/server/ethernet/EthernetNetworkFactory.java
index 875fc10..ef3abba 100644
--- a/service-t/src/com/android/server/ethernet/EthernetNetworkFactory.java
+++ b/service-t/src/com/android/server/ethernet/EthernetNetworkFactory.java
@@ -19,7 +19,9 @@
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;
import android.net.EthernetNetworkSpecifier;
import android.net.IEthernetNetworkManagementListener;
@@ -49,6 +51,7 @@
import android.util.Log;
import android.util.SparseArray;
+import com.android.connectivity.resources.R;
import com.android.internal.annotations.VisibleForTesting;
import com.android.internal.util.IndentingPrintWriter;
import com.android.net.module.util.InterfaceParams;
@@ -69,6 +72,8 @@
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<>();
@@ -94,6 +99,27 @@
public InterfaceParams getNetworkInterfaceByName(String name) {
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;
+ }
}
public static class ConfigurationException extends AndroidRuntimeException {
@@ -207,7 +233,8 @@
* Update a network's configuration and restart it if necessary.
*
* @param ifaceName the interface name of the network to be updated.
- * @param ipConfig the desired {@link IpConfiguration} for the given network.
+ * @param ipConfig the desired {@link IpConfiguration} for the given network or null. If
+ * {@code null} is passed, the existing IpConfiguration is not updated.
* @param capabilities the desired {@link NetworkCapabilities} for the given network. If
* {@code null} is passed, then the network's current
* {@link NetworkCapabilities} will be used in support of existing APIs as
@@ -217,7 +244,7 @@
*/
@VisibleForTesting(visibility = VisibleForTesting.Visibility.PACKAGE)
protected void updateInterface(@NonNull final String ifaceName,
- @NonNull final IpConfiguration ipConfig,
+ @Nullable final IpConfiguration ipConfig,
@Nullable final NetworkCapabilities capabilities,
@Nullable final IEthernetNetworkManagementListener listener) {
if (!hasInterface(ifaceName)) {
@@ -473,7 +500,7 @@
mLegacyType = getLegacyType(mCapabilities);
}
- void updateInterface(@NonNull final IpConfiguration ipConfig,
+ void updateInterface(@Nullable final IpConfiguration ipConfig,
@Nullable final NetworkCapabilities capabilities,
@Nullable final IEthernetNetworkManagementListener listener) {
if (DBG) {
@@ -484,7 +511,9 @@
);
}
- mIpConfig = ipConfig;
+ if (null != ipConfig){
+ mIpConfig = ipConfig;
+ }
if (null != capabilities) {
setCapabilities(capabilities);
}
@@ -518,8 +547,7 @@
mIpClientCallback.awaitIpClientStart();
if (sTcpBufferSizes == null) {
- sTcpBufferSizes = mContext.getResources().getString(
- com.android.internal.R.string.config_ethernet_tcp_buffers);
+ sTcpBufferSizes = mDeps.getTcpBufferSizesFromResource(mContext);
}
provisionIpClient(mIpClient, mIpConfig, sTcpBufferSizes);
}
diff --git a/service-t/src/com/android/server/ethernet/EthernetService.java b/service-t/src/com/android/server/ethernet/EthernetService.java
index e6fee9e..d405fd5 100644
--- a/service-t/src/com/android/server/ethernet/EthernetService.java
+++ b/service-t/src/com/android/server/ethernet/EthernetService.java
@@ -21,45 +21,27 @@
import android.os.Handler;
import android.os.HandlerThread;
import android.os.IBinder;
-import android.util.Log;
-import com.android.server.SystemService;
import java.util.Objects;
-public final class EthernetService extends SystemService {
-
+// TODO: consider renaming EthernetServiceImpl to EthernetService and deleting this file.
+public final class EthernetService {
private static final String TAG = "EthernetService";
private static final String THREAD_NAME = "EthernetServiceThread";
- private final EthernetServiceImpl mImpl;
- public EthernetService(Context context) {
- super(context);
- final HandlerThread handlerThread = new HandlerThread(THREAD_NAME);
- handlerThread.start();
- final Handler handler = handlerThread.getThreadHandler();
- final EthernetNetworkFactory factory = new EthernetNetworkFactory(handler, context);
- mImpl = new EthernetServiceImpl(
- context, handler,
- new EthernetTracker(context, handler, factory, getNetd(context)));
- }
-
- private INetd getNetd(Context context) {
+ private static INetd getNetd(Context context) {
final INetd netd =
INetd.Stub.asInterface((IBinder) context.getSystemService(Context.NETD_SERVICE));
Objects.requireNonNull(netd, "could not get netd instance");
return netd;
}
- @Override
- public void onStart() {
- Log.i(TAG, "Registering service " + Context.ETHERNET_SERVICE);
- publishBinderService(Context.ETHERNET_SERVICE, mImpl);
- }
-
- @Override
- public void onBootPhase(int phase) {
- if (phase == SystemService.PHASE_SYSTEM_SERVICES_READY) {
- mImpl.start();
- }
+ public static EthernetServiceImpl create(Context context) {
+ final HandlerThread handlerThread = new HandlerThread(THREAD_NAME);
+ handlerThread.start();
+ final Handler handler = new Handler(handlerThread.getLooper());
+ final EthernetNetworkFactory factory = new EthernetNetworkFactory(handler, context);
+ return new EthernetServiceImpl(context, handler,
+ new EthernetTracker(context, handler, factory, getNetd(context)));
}
}
diff --git a/service-t/src/com/android/server/ethernet/EthernetTracker.java b/service-t/src/com/android/server/ethernet/EthernetTracker.java
index ea241e1..074c81b 100644
--- a/service-t/src/com/android/server/ethernet/EthernetTracker.java
+++ b/service-t/src/com/android/server/ethernet/EthernetTracker.java
@@ -23,6 +23,8 @@
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;
import android.net.IEthernetNetworkManagementListener;
@@ -80,6 +82,7 @@
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,
@@ -102,6 +105,7 @@
private final Handler mHandler;
private final EthernetNetworkFactory mFactory;
private final EthernetConfigStore mConfigStore;
+ private final Dependencies mDeps;
private final RemoteCallbackList<IEthernetServiceListener> mListeners =
new RemoteCallbackList<>();
@@ -123,19 +127,72 @@
}
}
+ 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;
+ }
+
+ 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;
+ }
+ }
+
EthernetTracker(@NonNull final Context context, @NonNull final Handler handler,
@NonNull final EthernetNetworkFactory factory, @NonNull final INetd netd) {
+ this(context, handler, factory, netd, new Dependencies());
+ }
+
+ @VisibleForTesting
+ EthernetTracker(@NonNull final Context context, @NonNull final Handler handler,
+ @NonNull final EthernetNetworkFactory factory, @NonNull final INetd netd,
+ @NonNull final Dependencies deps) {
mContext = context;
mHandler = handler;
mFactory = factory;
mNetd = netd;
+ mDeps = deps;
// Interface match regex.
updateIfaceMatchRegexp();
// Read default Ethernet interface configuration from resources
- final String[] interfaceConfigs = context.getResources().getStringArray(
- com.android.internal.R.array.config_ethernet_interfaces);
+ final String[] interfaceConfigs = mDeps.getInterfaceConfigFromResource(context);
for (String strConfig : interfaceConfigs) {
parseEthernetConfig(strConfig);
}
@@ -232,15 +289,20 @@
@VisibleForTesting(visibility = PACKAGE)
protected void updateConfiguration(@NonNull final String iface,
- @NonNull final IpConfiguration ipConfig,
+ @Nullable final IpConfiguration ipConfig,
@Nullable final NetworkCapabilities capabilities,
@Nullable final IEthernetNetworkManagementListener listener) {
if (DBG) {
Log.i(TAG, "updateConfiguration, iface: " + iface + ", capabilities: " + capabilities
+ ", ipConfig: " + ipConfig);
}
- final IpConfiguration localIpConfig = new IpConfiguration(ipConfig);
- writeIpConfiguration(iface, localIpConfig);
+
+ final IpConfiguration localIpConfig = ipConfig == null
+ ? null : new IpConfiguration(ipConfig);
+ if (ipConfig != null) {
+ writeIpConfiguration(iface, localIpConfig);
+ }
+
if (null != capabilities) {
mNetworkCapabilities.put(iface, capabilities);
}
@@ -735,8 +797,7 @@
}
private void updateIfaceMatchRegexp() {
- final String match = mContext.getResources().getString(
- com.android.internal.R.string.config_ethernet_iface_regex);
+ final String match = mDeps.getInterfaceRegexFromResource(mContext);
mIfaceMatch = mIncludeTestInterfaces
? "(" + match + "|" + TEST_IFACE_REGEXP + ")"
: match;
diff --git a/tests/ethernet/Android.bp b/tests/ethernet/Android.bp
index 28b13c5..6cfebdc 100644
--- a/tests/ethernet/Android.bp
+++ b/tests/ethernet/Android.bp
@@ -17,10 +17,17 @@
default_applicable_licenses: ["Android-Apache-2.0"],
}
+// TODO: merge the tests into service-connectivity tests after
+// ethernet service migration completes. So far just import the
+// ethernet service source to fix the dependencies.
android_test {
name: "EthernetServiceTests",
- srcs: ["java/**/*.java"],
+ srcs: [
+ ":ethernet-service-updatable-sources",
+ ":services.connectivity-ethernet-sources",
+ "java/**/*.java",
+ ],
certificate: "platform",
platform_apis: true,
@@ -29,11 +36,13 @@
"android.test.runner",
"android.test.base",
"android.test.mock",
+ "framework-connectivity.impl",
+ "framework-connectivity-t.impl",
+ "ServiceConnectivityResources",
],
static_libs: [
"androidx.test.rules",
- "ethernet-service",
"frameworks-base-testutils",
"mockito-target-minus-junit4",
"net-tests-utils",
diff --git a/tests/ethernet/java/com/android/server/ethernet/EthernetNetworkFactoryTest.java b/tests/ethernet/java/com/android/server/ethernet/EthernetNetworkFactoryTest.java
index 28fcf3e..e256add 100644
--- a/tests/ethernet/java/com/android/server/ethernet/EthernetNetworkFactoryTest.java
+++ b/tests/ethernet/java/com/android/server/ethernet/EthernetNetworkFactoryTest.java
@@ -63,7 +63,7 @@
import androidx.test.filters.SmallTest;
import androidx.test.runner.AndroidJUnit4;
-import com.android.internal.R;
+import com.android.connectivity.resources.R;
import com.android.net.module.util.InterfaceParams;
import com.android.testutils.DevSdkIgnoreRule;
@@ -174,8 +174,7 @@
}
private void setupContext() {
- when(mContext.getResources()).thenReturn(mResources);
- when(mResources.getString(R.string.config_ethernet_tcp_buffers)).thenReturn("");
+ when(mDeps.getTcpBufferSizesFromResource(eq(mContext))).thenReturn("");
}
@After
@@ -771,4 +770,28 @@
verifyNoStopOrStart();
assertFailedListener(listener, "can't be updated as it is not available");
}
+
+ @Test
+ public void testUpdateInterfaceWithNullIpConfiguration() throws Exception {
+ initEthernetNetworkFactory();
+ createAndVerifyProvisionedInterface(TEST_IFACE);
+
+ final IpConfiguration initialIpConfig = createStaticIpConfig();
+ mNetFactory.updateInterface(TEST_IFACE, initialIpConfig, null /*capabilities*/,
+ null /*listener*/);
+ triggerOnProvisioningSuccess();
+ verifyRestart(initialIpConfig);
+
+ // TODO: have verifyXyz functions clear invocations.
+ clearInvocations(mDeps);
+ clearInvocations(mIpClient);
+ clearInvocations(mNetworkAgent);
+
+
+ // verify that sending a null ipConfig does not update the current ipConfig.
+ mNetFactory.updateInterface(TEST_IFACE, null /*ipConfig*/, null /*capabilities*/,
+ null /*listener*/);
+ triggerOnProvisioningSuccess();
+ verifyRestart(initialIpConfig);
+ }
}
diff --git a/tests/ethernet/java/com/android/server/ethernet/EthernetServiceImplTest.java b/tests/ethernet/java/com/android/server/ethernet/EthernetServiceImplTest.java
index 175a97d..2131f7f 100644
--- a/tests/ethernet/java/com/android/server/ethernet/EthernetServiceImplTest.java
+++ b/tests/ethernet/java/com/android/server/ethernet/EthernetServiceImplTest.java
@@ -60,6 +60,10 @@
new EthernetNetworkUpdateRequest.Builder()
.setIpConfiguration(new IpConfiguration())
.build();
+ private static final EthernetNetworkUpdateRequest UPDATE_REQUEST_WITHOUT_IP_CONFIG =
+ new EthernetNetworkUpdateRequest.Builder()
+ .setNetworkCapabilities(new NetworkCapabilities.Builder().build())
+ .build();
private static final IEthernetNetworkManagementListener NULL_LISTENER = null;
private EthernetServiceImpl mEthernetServiceImpl;
@Mock private Context mContext;
@@ -276,6 +280,15 @@
}
@Test
+ public void testUpdateConfigurationAcceptsRequestWithNullIpConfiguration() {
+ mEthernetServiceImpl.updateConfiguration(TEST_IFACE, UPDATE_REQUEST_WITHOUT_IP_CONFIG,
+ NULL_LISTENER);
+ verify(mEthernetTracker).updateConfiguration(eq(TEST_IFACE),
+ eq(UPDATE_REQUEST_WITHOUT_IP_CONFIG.getIpConfiguration()),
+ eq(UPDATE_REQUEST_WITHOUT_IP_CONFIG.getNetworkCapabilities()), isNull());
+ }
+
+ @Test
public void testUpdateConfigurationRejectsInvalidTestRequest() {
enableTestInterface();
assertThrows(IllegalArgumentException.class, () -> {
diff --git a/tests/ethernet/java/com/android/server/ethernet/EthernetTrackerTest.java b/tests/ethernet/java/com/android/server/ethernet/EthernetTrackerTest.java
index d86cc0f..ef70d94 100644
--- a/tests/ethernet/java/com/android/server/ethernet/EthernetTrackerTest.java
+++ b/tests/ethernet/java/com/android/server/ethernet/EthernetTrackerTest.java
@@ -27,7 +27,6 @@
import static org.mockito.ArgumentMatchers.anyBoolean;
import static org.mockito.ArgumentMatchers.anyString;
import static org.mockito.ArgumentMatchers.eq;
-import static org.mockito.Mockito.doReturn;
import static org.mockito.Mockito.verify;
import static org.mockito.Mockito.when;
@@ -48,7 +47,7 @@
import androidx.test.filters.SmallTest;
import androidx.test.runner.AndroidJUnit4;
-import com.android.internal.R;
+import com.android.connectivity.resources.R;
import com.android.testutils.HandlerUtils;
import org.junit.After;
@@ -73,7 +72,7 @@
@Mock private Context mContext;
@Mock private EthernetNetworkFactory mFactory;
@Mock private INetd mNetd;
- @Mock Resources mResources;
+ @Mock private EthernetTracker.Dependencies mDeps;
@Before
public void setUp() throws RemoteException {
@@ -83,7 +82,8 @@
when(mNetd.interfaceGetList()).thenReturn(new String[0]);
mHandlerThread = new HandlerThread(THREAD_NAME);
mHandlerThread.start();
- tracker = new EthernetTracker(mContext, mHandlerThread.getThreadHandler(), mFactory, mNetd);
+ tracker = new EthernetTracker(mContext, mHandlerThread.getThreadHandler(), mFactory, mNetd,
+ mDeps);
}
@After
@@ -92,9 +92,8 @@
}
private void initMockResources() {
- doReturn("").when(mResources).getString(R.string.config_ethernet_iface_regex);
- doReturn(new String[0]).when(mResources).getStringArray(R.array.config_ethernet_interfaces);
- doReturn(mResources).when(mContext).getResources();
+ when(mDeps.getInterfaceRegexFromResource(eq(mContext))).thenReturn("");
+ when(mDeps.getInterfaceConfigFromResource(eq(mContext))).thenReturn(new String[0]);
}
private void waitForIdle() {