Merge changes I9bccc558,Ifd855571 am: fbef749cda
Original change: https://android-review.googlesource.com/c/platform/packages/modules/Connectivity/+/2319858 Change-Id: I7ae6719f2f0b04576d1184ada42620611263841a Signed-off-by: Automerger Merge Worker <android-build-automerger-merge-worker@system.gserviceaccount.com>
This commit is contained in:
@@ -67,16 +67,13 @@ import static org.junit.Assert.fail;
|
||||
import static org.junit.Assume.assumeFalse;
|
||||
import static org.junit.Assume.assumeTrue;
|
||||
|
||||
import android.app.UiAutomation;
|
||||
import android.content.Context;
|
||||
import android.content.pm.PackageManager;
|
||||
import android.net.EthernetManager.TetheredInterfaceCallback;
|
||||
import android.net.EthernetManager.TetheredInterfaceRequest;
|
||||
import android.net.TetheringManager.StartTetheringCallback;
|
||||
import android.net.TetheringManager.TetheringEventCallback;
|
||||
import android.net.TetheringManager.TetheringRequest;
|
||||
import android.net.TetheringTester.TetheredDevice;
|
||||
import android.net.cts.util.CtsNetUtils;
|
||||
import android.os.Build;
|
||||
import android.os.Handler;
|
||||
import android.os.HandlerThread;
|
||||
@@ -88,7 +85,6 @@ import android.util.Pair;
|
||||
|
||||
import androidx.annotation.NonNull;
|
||||
import androidx.annotation.Nullable;
|
||||
import androidx.test.InstrumentationRegistry;
|
||||
import androidx.test.filters.MediumTest;
|
||||
import androidx.test.runner.AndroidJUnit4;
|
||||
|
||||
@@ -143,17 +139,12 @@ import java.util.concurrent.TimeoutException;
|
||||
|
||||
@RunWith(AndroidJUnit4.class)
|
||||
@MediumTest
|
||||
public class EthernetTetheringTest {
|
||||
public class EthernetTetheringTest extends EthernetTetheringTestBase {
|
||||
@Rule
|
||||
public final DevSdkIgnoreRule mIgnoreRule = new DevSdkIgnoreRule();
|
||||
|
||||
private static final String TAG = EthernetTetheringTest.class.getSimpleName();
|
||||
private static final int TIMEOUT_MS = 5000;
|
||||
// Used to check if any tethering interface is available. Choose 200ms to be request timeout
|
||||
// because the average interface requested time on cuttlefish@acloud is around 10ms.
|
||||
// See TetheredInterfaceRequester.getInterface, isInterfaceForTetheringAvailable.
|
||||
private static final int AVAILABLE_TETHER_IFACE_REQUEST_TIMEOUT_MS = 200;
|
||||
private static final int TETHER_REACHABILITY_ATTEMPTS = 20;
|
||||
|
||||
private static final int DUMP_POLLING_MAX_RETRY = 100;
|
||||
private static final int DUMP_POLLING_INTERVAL_MS = 50;
|
||||
// Kernel treats a confirmed UDP connection which active after two seconds as stream mode.
|
||||
@@ -168,35 +159,14 @@ public class EthernetTetheringTest {
|
||||
// Per TX UDP packet size: ethhdr (14) + iphdr (20) + udphdr (8) + payload (2) = 44 bytes.
|
||||
private static final int TX_UDP_PACKET_SIZE = 44;
|
||||
private static final int TX_UDP_PACKET_COUNT = 123;
|
||||
private static final long WAIT_RA_TIMEOUT_MS = 2000;
|
||||
|
||||
private static final MacAddress TEST_MAC = MacAddress.fromString("1:2:3:4:5:6");
|
||||
private static final LinkAddress TEST_IP4_ADDR = new LinkAddress("10.0.0.1/24");
|
||||
private static final LinkAddress TEST_IP6_ADDR = new LinkAddress("2001:db8:1::101/64");
|
||||
private static final InetAddress TEST_IP4_DNS = parseNumericAddress("8.8.8.8");
|
||||
private static final InetAddress TEST_IP6_DNS = parseNumericAddress("2001:db8:1::888");
|
||||
private static final IpPrefix TEST_NAT64PREFIX = new IpPrefix("64:ff9b::/96");
|
||||
private static final Inet6Address REMOTE_NAT64_ADDR =
|
||||
(Inet6Address) parseNumericAddress("64:ff9b::808:808");
|
||||
private static final Inet6Address REMOTE_IP6_ADDR =
|
||||
(Inet6Address) parseNumericAddress("2002:db8:1::515:ca");
|
||||
private static final ByteBuffer TEST_REACHABILITY_PAYLOAD =
|
||||
ByteBuffer.wrap(new byte[] { (byte) 0x55, (byte) 0xaa });
|
||||
private static final ByteBuffer EMPTY_PAYLOAD = ByteBuffer.wrap(new byte[0]);
|
||||
|
||||
private static final short DNS_PORT = 53;
|
||||
private static final short WINDOW = (short) 0x2000;
|
||||
private static final short URGENT_POINTER = 0;
|
||||
|
||||
private static final String DUMPSYS_TETHERING_RAWMAP_ARG = "bpfRawMap";
|
||||
private static final String DUMPSYS_RAWMAP_ARG_STATS = "--stats";
|
||||
private static final String DUMPSYS_RAWMAP_ARG_UPSTREAM4 = "--upstream4";
|
||||
private static final String LINE_DELIMITER = "\\n";
|
||||
|
||||
// version=6, traffic class=0x0, flowlabel=0x0;
|
||||
private static final int VERSION_TRAFFICCLASS_FLOWLABEL = 0x60000000;
|
||||
private static final short HOP_LIMIT = 0x40;
|
||||
|
||||
private static final short ICMPECHO_CODE = 0x0;
|
||||
private static final short ICMPECHO_ID = 0x0;
|
||||
private static final short ICMPECHO_SEQ = 0x0;
|
||||
@@ -261,27 +231,9 @@ public class EthernetTetheringTest {
|
||||
(byte) 0x01, (byte) 0x02, (byte) 0x03, (byte) 0x04 /* Address: 1.2.3.4 */
|
||||
};
|
||||
|
||||
private final Context mContext = InstrumentationRegistry.getContext();
|
||||
private final EthernetManager mEm = mContext.getSystemService(EthernetManager.class);
|
||||
private final TetheringManager mTm = mContext.getSystemService(TetheringManager.class);
|
||||
private final PackageManager mPackageManager = mContext.getPackageManager();
|
||||
private final CtsNetUtils mCtsNetUtils = new CtsNetUtils(mContext);
|
||||
|
||||
private TestNetworkInterface mDownstreamIface;
|
||||
private HandlerThread mHandlerThread;
|
||||
private Handler mHandler;
|
||||
private TapPacketReader mDownstreamReader;
|
||||
private TapPacketReader mUpstreamReader;
|
||||
|
||||
private TetheredInterfaceRequester mTetheredInterfaceRequester;
|
||||
private MyTetheringEventCallback mTetheringEventCallback;
|
||||
|
||||
private UiAutomation mUiAutomation =
|
||||
InstrumentationRegistry.getInstrumentation().getUiAutomation();
|
||||
private boolean mRunTests;
|
||||
|
||||
private TestNetworkTracker mUpstreamTracker;
|
||||
|
||||
@Before
|
||||
public void setUp() throws Exception {
|
||||
mHandlerThread = new HandlerThread(getClass().getSimpleName());
|
||||
@@ -295,6 +247,30 @@ public class EthernetTetheringTest {
|
||||
mTetheredInterfaceRequester = new TetheredInterfaceRequester(mHandler, mEm);
|
||||
}
|
||||
|
||||
private void maybeStopTapPacketReader(final TapPacketReader tapPacketReader)
|
||||
throws Exception {
|
||||
if (tapPacketReader != null) {
|
||||
TapPacketReader reader = tapPacketReader;
|
||||
mHandler.post(() -> reader.stop());
|
||||
}
|
||||
}
|
||||
|
||||
private void maybeCloseTestInterface(final TestNetworkInterface testInterface)
|
||||
throws Exception {
|
||||
if (testInterface != null) {
|
||||
testInterface.getFileDescriptor().close();
|
||||
Log.d(TAG, "Deleted test interface " + testInterface.getInterfaceName());
|
||||
}
|
||||
}
|
||||
|
||||
private void maybeUnregisterTetheringEventCallback(final MyTetheringEventCallback callback)
|
||||
throws Exception {
|
||||
if (callback != null) {
|
||||
callback.awaitInterfaceUntethered();
|
||||
callback.unregister();
|
||||
}
|
||||
}
|
||||
|
||||
private void cleanUp() throws Exception {
|
||||
setPreferTestNetworks(false);
|
||||
|
||||
@@ -310,24 +286,19 @@ public class EthernetTetheringTest {
|
||||
mUpstreamReader = null;
|
||||
}
|
||||
|
||||
if (mDownstreamReader != null) {
|
||||
TapPacketReader reader = mDownstreamReader;
|
||||
mHandler.post(() -> reader.stop());
|
||||
maybeStopTapPacketReader(mDownstreamReader);
|
||||
mDownstreamReader = null;
|
||||
}
|
||||
|
||||
// To avoid flaky which caused by the next test started but the previous interface is not
|
||||
// untracked from EthernetTracker yet. Just delete the test interface without explicitly
|
||||
// calling TetheringManager#stopTethering could let EthernetTracker untrack the test
|
||||
// interface from server mode before tethering stopped. Thus, awaitInterfaceUntethered
|
||||
// could not only make sure tethering is stopped but also guarantee the test interface is
|
||||
// untracked from EthernetTracker.
|
||||
maybeDeleteTestInterface();
|
||||
if (mTetheringEventCallback != null) {
|
||||
mTetheringEventCallback.awaitInterfaceUntethered();
|
||||
mTetheringEventCallback.unregister();
|
||||
maybeCloseTestInterface(mDownstreamIface);
|
||||
mDownstreamIface = null;
|
||||
maybeUnregisterTetheringEventCallback(mTetheringEventCallback);
|
||||
mTetheringEventCallback = null;
|
||||
}
|
||||
|
||||
runAsShell(NETWORK_SETTINGS, () -> mTetheredInterfaceRequester.release());
|
||||
setIncludeTestInterfaces(false);
|
||||
}
|
||||
@@ -383,26 +354,50 @@ public class EthernetTetheringTest {
|
||||
});
|
||||
}
|
||||
|
||||
private String getTetheredInterface() throws Exception {
|
||||
return mTetheredInterfaceRequester.getInterface();
|
||||
}
|
||||
|
||||
private CompletableFuture<String> requestTetheredInterface() throws Exception {
|
||||
return mTetheredInterfaceRequester.requestInterface();
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testVirtualEthernetAlreadyExists() throws Exception {
|
||||
// This test requires manipulating packets. Skip if there is a physical Ethernet connected.
|
||||
assumeFalse(isInterfaceForTetheringAvailable());
|
||||
|
||||
mDownstreamIface = createTestInterface();
|
||||
// This must be done now because as soon as setIncludeTestInterfaces(true) is called, the
|
||||
// interface will be placed in client mode, which will delete the link-local address.
|
||||
// At that point NetworkInterface.getByName() will cease to work on the interface, because
|
||||
// starting in R NetworkInterface can no longer see interfaces without IP addresses.
|
||||
int mtu = getMTU(mDownstreamIface);
|
||||
TestNetworkInterface downstreamIface = null;
|
||||
MyTetheringEventCallback tetheringEventCallback = null;
|
||||
TapPacketReader downstreamReader = null;
|
||||
|
||||
try {
|
||||
downstreamIface = createTestInterface();
|
||||
// This must be done now because as soon as setIncludeTestInterfaces(true) is called,
|
||||
// the interface will be placed in client mode, which will delete the link-local
|
||||
// address. At that point NetworkInterface.getByName() will cease to work on the
|
||||
// interface, because starting in R NetworkInterface can no longer see interfaces
|
||||
// without IP addresses.
|
||||
int mtu = getMTU(downstreamIface);
|
||||
|
||||
Log.d(TAG, "Including test interfaces");
|
||||
setIncludeTestInterfaces(true);
|
||||
|
||||
final String iface = mTetheredInterfaceRequester.getInterface();
|
||||
final String iface = getTetheredInterface();
|
||||
assertEquals("TetheredInterfaceCallback for unexpected interface",
|
||||
mDownstreamIface.getInterfaceName(), iface);
|
||||
downstreamIface.getInterfaceName(), iface);
|
||||
|
||||
checkVirtualEthernet(mDownstreamIface, mtu);
|
||||
// Check virtual ethernet.
|
||||
FileDescriptor fd = downstreamIface.getFileDescriptor().getFileDescriptor();
|
||||
downstreamReader = makePacketReader(fd, mtu);
|
||||
tetheringEventCallback = enableEthernetTethering(downstreamIface.getInterfaceName(),
|
||||
null /* any upstream */);
|
||||
checkTetheredClientCallbacks(downstreamReader, tetheringEventCallback);
|
||||
} finally {
|
||||
maybeStopTapPacketReader(downstreamReader);
|
||||
maybeCloseTestInterface(downstreamIface);
|
||||
maybeUnregisterTetheringEventCallback(tetheringEventCallback);
|
||||
}
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -410,17 +405,32 @@ public class EthernetTetheringTest {
|
||||
// This test requires manipulating packets. Skip if there is a physical Ethernet connected.
|
||||
assumeFalse(isInterfaceForTetheringAvailable());
|
||||
|
||||
CompletableFuture<String> futureIface = mTetheredInterfaceRequester.requestInterface();
|
||||
CompletableFuture<String> futureIface = requestTetheredInterface();
|
||||
|
||||
setIncludeTestInterfaces(true);
|
||||
|
||||
mDownstreamIface = createTestInterface();
|
||||
TestNetworkInterface downstreamIface = null;
|
||||
MyTetheringEventCallback tetheringEventCallback = null;
|
||||
TapPacketReader downstreamReader = null;
|
||||
|
||||
try {
|
||||
downstreamIface = createTestInterface();
|
||||
|
||||
final String iface = futureIface.get(TIMEOUT_MS, TimeUnit.MILLISECONDS);
|
||||
assertEquals("TetheredInterfaceCallback for unexpected interface",
|
||||
mDownstreamIface.getInterfaceName(), iface);
|
||||
downstreamIface.getInterfaceName(), iface);
|
||||
|
||||
checkVirtualEthernet(mDownstreamIface, getMTU(mDownstreamIface));
|
||||
// Check virtual ethernet.
|
||||
FileDescriptor fd = downstreamIface.getFileDescriptor().getFileDescriptor();
|
||||
downstreamReader = makePacketReader(fd, getMTU(downstreamIface));
|
||||
tetheringEventCallback = enableEthernetTethering(downstreamIface.getInterfaceName(),
|
||||
null /* any upstream */);
|
||||
checkTetheredClientCallbacks(downstreamReader, tetheringEventCallback);
|
||||
} finally {
|
||||
maybeStopTapPacketReader(downstreamReader);
|
||||
maybeCloseTestInterface(downstreamIface);
|
||||
maybeUnregisterTetheringEventCallback(tetheringEventCallback);
|
||||
}
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -429,11 +439,16 @@ public class EthernetTetheringTest {
|
||||
|
||||
setIncludeTestInterfaces(true);
|
||||
|
||||
mDownstreamIface = createTestInterface();
|
||||
TestNetworkInterface downstreamIface = null;
|
||||
MyTetheringEventCallback tetheringEventCallback = null;
|
||||
TapPacketReader downstreamReader = null;
|
||||
|
||||
final String iface = mTetheredInterfaceRequester.getInterface();
|
||||
try {
|
||||
downstreamIface = createTestInterface();
|
||||
|
||||
final String iface = getTetheredInterface();
|
||||
assertEquals("TetheredInterfaceCallback for unexpected interface",
|
||||
mDownstreamIface.getInterfaceName(), iface);
|
||||
downstreamIface.getInterfaceName(), iface);
|
||||
|
||||
assertInvalidStaticIpv4Request(iface, null, null);
|
||||
assertInvalidStaticIpv4Request(iface, "2001:db8::1/64", "2001:db8:2::/64");
|
||||
@@ -445,18 +460,18 @@ public class EthernetTetheringTest {
|
||||
|
||||
final String localAddr = "192.0.2.3/28";
|
||||
final String clientAddr = "192.0.2.2/28";
|
||||
mTetheringEventCallback = enableEthernetTethering(iface,
|
||||
tetheringEventCallback = enableEthernetTethering(iface,
|
||||
requestWithStaticIpv4(localAddr, clientAddr), null /* any upstream */);
|
||||
|
||||
mTetheringEventCallback.awaitInterfaceTethered();
|
||||
tetheringEventCallback.awaitInterfaceTethered();
|
||||
assertInterfaceHasIpAddress(iface, localAddr);
|
||||
|
||||
byte[] client1 = MacAddress.fromString("1:2:3:4:5:6").toByteArray();
|
||||
byte[] client2 = MacAddress.fromString("a:b:c:d:e:f").toByteArray();
|
||||
|
||||
FileDescriptor fd = mDownstreamIface.getFileDescriptor().getFileDescriptor();
|
||||
mDownstreamReader = makePacketReader(fd, getMTU(mDownstreamIface));
|
||||
TetheringTester tester = new TetheringTester(mDownstreamReader);
|
||||
FileDescriptor fd = downstreamIface.getFileDescriptor().getFileDescriptor();
|
||||
downstreamReader = makePacketReader(fd, getMTU(downstreamIface));
|
||||
TetheringTester tester = new TetheringTester(downstreamReader);
|
||||
DhcpResults dhcpResults = tester.runDhcp(client1);
|
||||
assertEquals(new LinkAddress(clientAddr), dhcpResults.ipAddress);
|
||||
|
||||
@@ -464,7 +479,11 @@ public class EthernetTetheringTest {
|
||||
tester.runDhcp(client2);
|
||||
fail("Only one client should get an IP address");
|
||||
} catch (TimeoutException expected) { }
|
||||
|
||||
} finally {
|
||||
maybeStopTapPacketReader(downstreamReader);
|
||||
maybeCloseTestInterface(downstreamIface);
|
||||
maybeUnregisterTetheringEventCallback(tetheringEventCallback);
|
||||
}
|
||||
}
|
||||
|
||||
private static void waitForRouterAdvertisement(TapPacketReader reader, String iface,
|
||||
@@ -510,26 +529,36 @@ public class EthernetTetheringTest {
|
||||
|
||||
setIncludeTestInterfaces(true);
|
||||
|
||||
mDownstreamIface = createTestInterface();
|
||||
TestNetworkInterface downstreamIface = null;
|
||||
MyTetheringEventCallback tetheringEventCallback = null;
|
||||
TapPacketReader downstreamReader = null;
|
||||
|
||||
final String iface = mTetheredInterfaceRequester.getInterface();
|
||||
try {
|
||||
downstreamIface = createTestInterface();
|
||||
|
||||
final String iface = getTetheredInterface();
|
||||
assertEquals("TetheredInterfaceCallback for unexpected interface",
|
||||
mDownstreamIface.getInterfaceName(), iface);
|
||||
downstreamIface.getInterfaceName(), iface);
|
||||
|
||||
final TetheringRequest request = new TetheringRequest.Builder(TETHERING_ETHERNET)
|
||||
.setConnectivityScope(CONNECTIVITY_SCOPE_LOCAL).build();
|
||||
mTetheringEventCallback = enableEthernetTethering(iface, request,
|
||||
tetheringEventCallback = enableEthernetTethering(iface, request,
|
||||
null /* any upstream */);
|
||||
mTetheringEventCallback.awaitInterfaceLocalOnly();
|
||||
tetheringEventCallback.awaitInterfaceLocalOnly();
|
||||
|
||||
// makePacketReader only works after tethering is started, because until then the interface
|
||||
// does not have an IP address, and unprivileged apps cannot see interfaces without IP
|
||||
// addresses. This shouldn't be flaky because the TAP interface will buffer all packets even
|
||||
// before the reader is started.
|
||||
mDownstreamReader = makePacketReader(mDownstreamIface);
|
||||
// makePacketReader only works after tethering is started, because until then the
|
||||
// interface does not have an IP address, and unprivileged apps cannot see interfaces
|
||||
// without IP addresses. This shouldn't be flaky because the TAP interface will buffer
|
||||
// all packets even before the reader is started.
|
||||
downstreamReader = makePacketReader(downstreamIface);
|
||||
|
||||
waitForRouterAdvertisement(mDownstreamReader, iface, WAIT_RA_TIMEOUT_MS);
|
||||
waitForRouterAdvertisement(downstreamReader, iface, WAIT_RA_TIMEOUT_MS);
|
||||
expectLocalOnlyAddresses(iface);
|
||||
} finally {
|
||||
maybeStopTapPacketReader(downstreamReader);
|
||||
maybeCloseTestInterface(downstreamIface);
|
||||
maybeUnregisterTetheringEventCallback(tetheringEventCallback);
|
||||
}
|
||||
}
|
||||
|
||||
private boolean isAdbOverNetwork() {
|
||||
@@ -546,12 +575,16 @@ public class EthernetTetheringTest {
|
||||
// from client mode to server mode. See b/160389275.
|
||||
assumeFalse(isAdbOverNetwork());
|
||||
|
||||
MyTetheringEventCallback tetheringEventCallback = null;
|
||||
try {
|
||||
// Get an interface to use.
|
||||
final String iface = mTetheredInterfaceRequester.getInterface();
|
||||
final String iface = getTetheredInterface();
|
||||
|
||||
// Enable Ethernet tethering and check that it starts.
|
||||
mTetheringEventCallback = enableEthernetTethering(iface, null /* any upstream */);
|
||||
|
||||
tetheringEventCallback = enableEthernetTethering(iface, null /* any upstream */);
|
||||
} finally {
|
||||
maybeUnregisterTetheringEventCallback(tetheringEventCallback);
|
||||
}
|
||||
// There is nothing more we can do on a physical interface without connecting an actual
|
||||
// client, which is not possible in this test.
|
||||
}
|
||||
@@ -810,15 +843,8 @@ public class EthernetTetheringTest {
|
||||
return reader;
|
||||
}
|
||||
|
||||
private void checkVirtualEthernet(TestNetworkInterface iface, int mtu) throws Exception {
|
||||
FileDescriptor fd = iface.getFileDescriptor().getFileDescriptor();
|
||||
mDownstreamReader = makePacketReader(fd, mtu);
|
||||
mTetheringEventCallback = enableEthernetTethering(iface.getInterfaceName(),
|
||||
null /* any upstream */);
|
||||
checkTetheredClientCallbacks(mDownstreamReader);
|
||||
}
|
||||
|
||||
private void checkTetheredClientCallbacks(TapPacketReader packetReader) throws Exception {
|
||||
private void checkTetheredClientCallbacks(final TapPacketReader packetReader,
|
||||
final MyTetheringEventCallback tetheringEventCallback) throws Exception {
|
||||
// Create a fake client.
|
||||
byte[] clientMacAddr = new byte[6];
|
||||
new Random().nextBytes(clientMacAddr);
|
||||
@@ -826,7 +852,7 @@ public class EthernetTetheringTest {
|
||||
TetheringTester tester = new TetheringTester(packetReader);
|
||||
DhcpResults dhcpResults = tester.runDhcp(clientMacAddr);
|
||||
|
||||
final Collection<TetheredClient> clients = mTetheringEventCallback.awaitClientConnected();
|
||||
final Collection<TetheredClient> clients = tetheringEventCallback.awaitClientConnected();
|
||||
assertEquals(1, clients.size());
|
||||
final TetheredClient client = clients.iterator().next();
|
||||
|
||||
@@ -945,14 +971,6 @@ public class EthernetTetheringTest {
|
||||
return iface;
|
||||
}
|
||||
|
||||
private void maybeDeleteTestInterface() throws Exception {
|
||||
if (mDownstreamIface != null) {
|
||||
mDownstreamIface.getFileDescriptor().close();
|
||||
Log.d(TAG, "Deleted test interface " + mDownstreamIface.getInterfaceName());
|
||||
mDownstreamIface = null;
|
||||
}
|
||||
}
|
||||
|
||||
private TestNetworkTracker createTestUpstream(final List<LinkAddress> addresses,
|
||||
final List<InetAddress> dnses) throws Exception {
|
||||
setPreferTestNetworks(true);
|
||||
@@ -1002,22 +1020,6 @@ public class EthernetTetheringTest {
|
||||
// remote ip public ip private ip
|
||||
// 8.8.8.8:443 <Upstream ip>:9876 <TetheredDevice ip>:9876
|
||||
//
|
||||
private static final Inet4Address REMOTE_IP4_ADDR =
|
||||
(Inet4Address) parseNumericAddress("8.8.8.8");
|
||||
// Used by public port and private port. Assume port 9876 has not been used yet before the
|
||||
// testing that public port and private port are the same in the testing. Note that NAT port
|
||||
// forwarding could be different between private port and public port.
|
||||
// TODO: move to the start of test class.
|
||||
private static final short LOCAL_PORT = 9876;
|
||||
private static final short REMOTE_PORT = 433;
|
||||
private static final byte TYPE_OF_SERVICE = 0;
|
||||
private static final short ID = 27149;
|
||||
private static final short FLAGS_AND_FRAGMENT_OFFSET = (short) 0x4000; // flags=DF, offset=0
|
||||
private static final byte TIME_TO_LIVE = (byte) 0x40;
|
||||
private static final ByteBuffer RX_PAYLOAD =
|
||||
ByteBuffer.wrap(new byte[] { (byte) 0x12, (byte) 0x34 });
|
||||
private static final ByteBuffer TX_PAYLOAD =
|
||||
ByteBuffer.wrap(new byte[] { (byte) 0x56, (byte) 0x78 });
|
||||
|
||||
private short getEthType(@NonNull final InetAddress srcIp, @NonNull final InetAddress dstIp) {
|
||||
return isAddressIpv4(srcIp, dstIp) ? (short) ETHER_TYPE_IPV4 : (short) ETHER_TYPE_IPV6;
|
||||
|
||||
@@ -0,0 +1,115 @@
|
||||
/*
|
||||
* Copyright (C) 2022 The Android Open Source Project
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
package android.net;
|
||||
|
||||
import static android.net.InetAddresses.parseNumericAddress;
|
||||
|
||||
import android.app.UiAutomation;
|
||||
import android.content.Context;
|
||||
import android.content.pm.PackageManager;
|
||||
import android.net.cts.util.CtsNetUtils;
|
||||
import android.os.Handler;
|
||||
import android.os.HandlerThread;
|
||||
|
||||
import androidx.test.platform.app.InstrumentationRegistry;
|
||||
|
||||
import com.android.testutils.TapPacketReader;
|
||||
import com.android.testutils.TestNetworkTracker;
|
||||
|
||||
import java.net.Inet4Address;
|
||||
import java.net.Inet6Address;
|
||||
import java.net.InetAddress;
|
||||
import java.nio.ByteBuffer;
|
||||
|
||||
/**
|
||||
* TODO: Common variables or methods shared between CtsEthernetTetheringTest and
|
||||
* MtsEthernetTetheringTest.
|
||||
*/
|
||||
public abstract class EthernetTetheringTestBase {
|
||||
private static final String TAG = EthernetTetheringTestBase.class.getSimpleName();
|
||||
|
||||
protected static final int TIMEOUT_MS = 5000;
|
||||
// Used to check if any tethering interface is available. Choose 200ms to be request timeout
|
||||
// because the average interface requested time on cuttlefish@acloud is around 10ms.
|
||||
// See TetheredInterfaceRequester.getInterface, isInterfaceForTetheringAvailable.
|
||||
protected static final int AVAILABLE_TETHER_IFACE_REQUEST_TIMEOUT_MS = 200;
|
||||
protected static final int TETHER_REACHABILITY_ATTEMPTS = 20;
|
||||
protected static final long WAIT_RA_TIMEOUT_MS = 2000;
|
||||
|
||||
// Address and NAT prefix definition.
|
||||
protected static final MacAddress TEST_MAC = MacAddress.fromString("1:2:3:4:5:6");
|
||||
protected static final LinkAddress TEST_IP4_ADDR = new LinkAddress("10.0.0.1/24");
|
||||
protected static final LinkAddress TEST_IP6_ADDR = new LinkAddress("2001:db8:1::101/64");
|
||||
protected static final InetAddress TEST_IP4_DNS = parseNumericAddress("8.8.8.8");
|
||||
protected static final InetAddress TEST_IP6_DNS = parseNumericAddress("2001:db8:1::888");
|
||||
|
||||
protected static final Inet4Address REMOTE_IP4_ADDR =
|
||||
(Inet4Address) parseNumericAddress("8.8.8.8");
|
||||
protected static final Inet6Address REMOTE_IP6_ADDR =
|
||||
(Inet6Address) parseNumericAddress("2002:db8:1::515:ca");
|
||||
protected static final Inet6Address REMOTE_NAT64_ADDR =
|
||||
(Inet6Address) parseNumericAddress("64:ff9b::808:808");
|
||||
protected static final IpPrefix TEST_NAT64PREFIX = new IpPrefix("64:ff9b::/96");
|
||||
|
||||
// IPv4 header definition.
|
||||
protected static final short ID = 27149;
|
||||
protected static final short FLAGS_AND_FRAGMENT_OFFSET = (short) 0x4000; // flags=DF, offset=0
|
||||
protected static final byte TIME_TO_LIVE = (byte) 0x40;
|
||||
protected static final byte TYPE_OF_SERVICE = 0;
|
||||
|
||||
// IPv6 header definition.
|
||||
protected static final short HOP_LIMIT = 0x40;
|
||||
// version=6, traffic class=0x0, flowlabel=0x0;
|
||||
protected static final int VERSION_TRAFFICCLASS_FLOWLABEL = 0x60000000;
|
||||
|
||||
// UDP and TCP header definition.
|
||||
// LOCAL_PORT is used by public port and private port. Assume port 9876 has not been used yet
|
||||
// before the testing that public port and private port are the same in the testing. Note that
|
||||
// NAT port forwarding could be different between private port and public port.
|
||||
protected static final short LOCAL_PORT = 9876;
|
||||
protected static final short REMOTE_PORT = 433;
|
||||
protected static final short WINDOW = (short) 0x2000;
|
||||
protected static final short URGENT_POINTER = 0;
|
||||
|
||||
// Payload definition.
|
||||
protected static final ByteBuffer EMPTY_PAYLOAD = ByteBuffer.wrap(new byte[0]);
|
||||
protected static final ByteBuffer TEST_REACHABILITY_PAYLOAD =
|
||||
ByteBuffer.wrap(new byte[] { (byte) 0x55, (byte) 0xaa });
|
||||
protected static final ByteBuffer RX_PAYLOAD =
|
||||
ByteBuffer.wrap(new byte[] { (byte) 0x12, (byte) 0x34 });
|
||||
protected static final ByteBuffer TX_PAYLOAD =
|
||||
ByteBuffer.wrap(new byte[] { (byte) 0x56, (byte) 0x78 });
|
||||
|
||||
protected final Context mContext = InstrumentationRegistry.getInstrumentation().getContext();
|
||||
protected final EthernetManager mEm = mContext.getSystemService(EthernetManager.class);
|
||||
protected final TetheringManager mTm = mContext.getSystemService(TetheringManager.class);
|
||||
protected final PackageManager mPackageManager = mContext.getPackageManager();
|
||||
protected final CtsNetUtils mCtsNetUtils = new CtsNetUtils(mContext);
|
||||
protected final UiAutomation mUiAutomation =
|
||||
InstrumentationRegistry.getInstrumentation().getUiAutomation();
|
||||
|
||||
// Late initialization in setUp()
|
||||
protected boolean mRunTests;
|
||||
protected HandlerThread mHandlerThread;
|
||||
protected Handler mHandler;
|
||||
|
||||
// Late initialization in initTetheringTester().
|
||||
protected TapPacketReader mUpstreamReader;
|
||||
protected TestNetworkTracker mUpstreamTracker;
|
||||
protected TestNetworkInterface mDownstreamIface;
|
||||
protected TapPacketReader mDownstreamReader;
|
||||
}
|
||||
Reference in New Issue
Block a user