Merge "[Thread] introduce TestTunNetworkUtils and use it in existing test cases" into main

This commit is contained in:
Handa Wang 2024-11-13 05:43:32 +00:00 • committed by Gerrit Code Review
commit 7175f59956
4 changed files with 108 additions and 80 deletions

View file

@ -58,6 +58,7 @@ import android.net.thread.utils.FullThreadDevice;
import android.net.thread.utils.InfraNetworkDevice;
import android.net.thread.utils.IntegrationTestUtils;
import android.net.thread.utils.OtDaemonController;
import android.net.thread.utils.TestTunNetworkUtils;
import android.net.thread.utils.ThreadFeatureCheckerRule;
import android.net.thread.utils.ThreadFeatureCheckerRule.RequiresIpv6MulticastRouting;
import android.net.thread.utils.ThreadFeatureCheckerRule.RequiresSimulationThreadDevice;
@ -160,6 +161,7 @@ public class BorderRoutingTest {
@After
public void tearDown() throws Exception {
mController.setTestNetworkAsUpstreamAndWait(null);
TestTunNetworkUtils.tearDownAllInfraNetworks();
mHandlerThread.quitSafely();
mHandlerThread.join();
@ -226,19 +228,13 @@ public class BorderRoutingTest {
FullThreadDevice ftd = mFtds.get(0);
joinNetworkAndWaitForOmr(ftd, DEFAULT_DATASET);
Inet6Address ftdOmr = ftd.getOmrAddress();
// Create a new infra network and let Thread prefer it
TestNetworkTracker oldInfraNetworkTracker = mInfraNetworkTracker;
try {
setUpInfraNetwork();
mInfraNetworkReader = newPacketReader(mInfraNetworkTracker.getTestIface(), mHandler);
startInfraDeviceAndWaitForOnLinkAddr();
setUpInfraNetwork();
mInfraNetworkReader = newPacketReader(mInfraNetworkTracker.getTestIface(), mHandler);
startInfraDeviceAndWaitForOnLinkAddr();
mInfraDevice.sendEchoRequest(ftd.getOmrAddress());
mInfraDevice.sendEchoRequest(ftd.getOmrAddress());
assertNotNull(pollForIcmpPacketOnInfraNetwork(ICMPV6_ECHO_REPLY_TYPE, ftdOmr));
} finally {
runAsShell(MANAGE_TEST_NETWORKS, () -> oldInfraNetworkTracker.teardown());
}
assertNotNull(pollForIcmpPacketOnInfraNetwork(ICMPV6_ECHO_REPLY_TYPE, ftdOmr));
}
@Test
@ -615,8 +611,6 @@ public class BorderRoutingTest {
subscribeMulticastAddressAndWait(ftd, GROUP_ADDR_SCOPE_5);
Inet6Address ftdOmr = ftd.getOmrAddress();
// Destroy infra link and re-create
tearDownInfraNetwork();
setUpInfraNetwork();
mInfraNetworkReader = newPacketReader(mInfraNetworkTracker.getTestIface(), mHandler);
startInfraDeviceAndWaitForOnLinkAddr();
@ -642,8 +636,6 @@ public class BorderRoutingTest {
joinNetworkAndWaitForOmr(ftd, DEFAULT_DATASET);
Inet6Address ftdOmr = ftd.getOmrAddress();
// Destroy infra link and re-create
tearDownInfraNetwork();
setUpInfraNetwork();
mInfraNetworkReader = newPacketReader(mInfraNetworkTracker.getTestIface(), mHandler);
startInfraDeviceAndWaitForOnLinkAddr();
@ -683,7 +675,7 @@ public class BorderRoutingTest {
@Test
public void nat64_withAilNat64Prefix_threadDevicePingIpv4InfraDevice_outboundPacketIsForwarded()
throws Exception {
tearDownInfraNetwork();
TestTunNetworkUtils.tearDownInfraNetwork(mInfraNetworkTracker);
LinkProperties lp = new LinkProperties();
// NAT64 feature requires the infra network to have an IPv4 default route.
lp.addRoute(
@ -701,7 +693,7 @@ public class BorderRoutingTest {
RouteInfo.RTN_UNICAST,
1500 /* mtu */));
lp.setNat64Prefix(AIL_NAT64_PREFIX);
mInfraNetworkTracker = IntegrationTestUtils.setUpInfraNetwork(mContext, mController, lp);
mInfraNetworkTracker = TestTunNetworkUtils.setUpInfraNetwork(mContext, mController, lp);
mInfraNetworkReader = newPacketReader(mInfraNetworkTracker.getTestIface(), mHandler);
FullThreadDevice ftd = mFtds.get(0);
joinNetworkAndWaitForOmr(ftd, DEFAULT_DATASET);
@ -717,16 +709,12 @@ public class BorderRoutingTest {
}
private void setUpInfraNetwork() throws Exception {
mInfraNetworkTracker = IntegrationTestUtils.setUpInfraNetwork(mContext, mController);
}
private void tearDownInfraNetwork() {
IntegrationTestUtils.tearDownInfraNetwork(mInfraNetworkTracker);
mInfraNetworkTracker = TestTunNetworkUtils.setUpInfraNetwork(mContext, mController);
}
private void startInfraDeviceAndWaitForOnLinkAddr() {
mInfraDevice =
IntegrationTestUtils.startInfraDeviceAndWaitForOnLinkAddr(mInfraNetworkReader);
TestTunNetworkUtils.startInfraDeviceAndWaitForOnLinkAddr(mInfraNetworkReader);
}
private void assertInfraLinkMemberOfGroup(Inet6Address address) throws Exception {

View file

@ -28,12 +28,10 @@ import android.net.thread.utils.IntegrationTestUtils.enableThreadAndJoinNetwork
import android.net.thread.utils.IntegrationTestUtils.joinNetworkAndWaitForOmr
import android.net.thread.utils.IntegrationTestUtils.leaveNetworkAndDisableThread
import android.net.thread.utils.IntegrationTestUtils.newPacketReader
import android.net.thread.utils.IntegrationTestUtils.setUpInfraNetwork
import android.net.thread.utils.IntegrationTestUtils.startInfraDeviceAndWaitForOnLinkAddr
import android.net.thread.utils.IntegrationTestUtils.tearDownInfraNetwork
import android.net.thread.utils.IntegrationTestUtils.waitFor
import android.net.thread.utils.OtDaemonController
import android.net.thread.utils.TestDnsServer
import android.net.thread.utils.TestTunNetworkUtils
import android.net.thread.utils.TestUdpEchoServer
import android.net.thread.utils.ThreadFeatureCheckerRule
import android.net.thread.utils.ThreadFeatureCheckerRule.RequiresSimulationThreadDevice
@ -128,11 +126,11 @@ class InternetAccessTest {
handler = Handler(handlerThread.looper)
ftds = ArrayList()
infraNetworkTracker = setUpInfraNetwork(context, controller)
infraNetworkTracker = TestTunNetworkUtils.setUpInfraNetwork(context, controller)
// Create an infra network device.
infraNetworkReader = newPacketReader(infraNetworkTracker.testIface, handler)
infraDevice = startInfraDeviceAndWaitForOnLinkAddr(infraNetworkReader)
infraDevice = TestTunNetworkUtils.startInfraDeviceAndWaitForOnLinkAddr(infraNetworkReader)
// Create a DNS server
dnsServer = TestDnsServer(infraNetworkReader, DNS_SERVER_ADDR, ANSWER_RECORDS)
@ -150,7 +148,7 @@ class InternetAccessTest {
@Throws(Exception::class)
fun tearDown() {
controller.setTestNetworkAsUpstreamAndWait(null)
tearDownInfraNetwork(infraNetworkTracker)
TestTunNetworkUtils.tearDownAllInfraNetworks()
dnsServer.stop()
udpEchoServer.stop()

View file

@ -649,57 +649,6 @@ object IntegrationTestUtils {
)
}
private fun defaultLinkProperties(): LinkProperties {
val lp = LinkProperties()
// TODO: use a fake DNS server
lp.setDnsServers(listOf(parseNumericAddress("8.8.8.8")))
// NAT64 feature requires the infra network to have an IPv4 default route.
lp.addRoute(
RouteInfo(
IpPrefix("0.0.0.0/0") /* destination */,
null /* gateway */,
null /* iface */,
RouteInfo.RTN_UNICAST, 1500 /* mtu */
)
)
return lp
}
@JvmStatic
@JvmOverloads
fun startInfraDeviceAndWaitForOnLinkAddr(
pollPacketReader: PollPacketReader,
macAddress: MacAddress = MacAddress.fromString("1:2:3:4:5:6")
): InfraNetworkDevice {
val infraDevice = InfraNetworkDevice(macAddress, pollPacketReader)
infraDevice.runSlaac(Duration.ofSeconds(60))
requireNotNull(infraDevice.ipv6Addr)
return infraDevice
}
@JvmStatic
@JvmOverloads
@Throws(java.lang.Exception::class)
fun setUpInfraNetwork(
context: Context,
controller: ThreadNetworkControllerWrapper,
lp: LinkProperties = defaultLinkProperties()
): TestNetworkTracker {
val infraNetworkTracker: TestNetworkTracker =
runAsShell(
MANAGE_TEST_NETWORKS,
supplier = { initTestNetwork(context, lp, setupTimeoutMs = 5000) })
val infraNetworkName: String = infraNetworkTracker.testIface.getInterfaceName()
controller.setTestNetworkAsUpstreamAndWait(infraNetworkName)
return infraNetworkTracker
}
@JvmStatic
fun tearDownInfraNetwork(testNetworkTracker: TestNetworkTracker) {
runAsShell(MANAGE_TEST_NETWORKS) { testNetworkTracker.teardown() }
}
/**
* Stop the ot-daemon by shell command.
*/

View file

@ -0,0 +1,93 @@
/*
* Copyright (C) 2024 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.thread.utils
import android.Manifest.permission.MANAGE_TEST_NETWORKS
import android.content.Context
import android.net.InetAddresses.parseNumericAddress
import android.net.IpPrefix
import android.net.LinkProperties
import android.net.MacAddress
import android.net.RouteInfo
import com.android.testutils.PollPacketReader
import com.android.testutils.TestNetworkTracker
import com.android.testutils.initTestNetwork
import com.android.testutils.runAsShell
import java.time.Duration
object TestTunNetworkUtils {
private val networkTrackers = mutableListOf<TestNetworkTracker>()
@JvmStatic
@JvmOverloads
fun setUpInfraNetwork(
context: Context,
controller: ThreadNetworkControllerWrapper,
lp: LinkProperties = defaultLinkProperties(),
): TestNetworkTracker {
val infraNetworkTracker: TestNetworkTracker =
runAsShell(
MANAGE_TEST_NETWORKS,
supplier = { initTestNetwork(context, lp, setupTimeoutMs = 5000) },
)
val infraNetworkName: String = infraNetworkTracker.testIface.getInterfaceName()
controller.setTestNetworkAsUpstreamAndWait(infraNetworkName)
networkTrackers.add(infraNetworkTracker)
return infraNetworkTracker
}
@JvmStatic
fun tearDownInfraNetwork(testNetworkTracker: TestNetworkTracker) {
runAsShell(MANAGE_TEST_NETWORKS) { testNetworkTracker.teardown() }
}
@JvmStatic
fun tearDownAllInfraNetworks() {
networkTrackers.forEach { tearDownInfraNetwork(it) }
networkTrackers.clear()
}
@JvmStatic
@JvmOverloads
fun startInfraDeviceAndWaitForOnLinkAddr(
pollPacketReader: PollPacketReader,
macAddress: MacAddress = MacAddress.fromString("1:2:3:4:5:6"),
): InfraNetworkDevice {
val infraDevice = InfraNetworkDevice(macAddress, pollPacketReader)
infraDevice.runSlaac(Duration.ofSeconds(60))
requireNotNull(infraDevice.ipv6Addr)
return infraDevice
}
private fun defaultLinkProperties(): LinkProperties {
val lp = LinkProperties()
// TODO: use a fake DNS server
lp.setDnsServers(listOf(parseNumericAddress("8.8.8.8")))
// NAT64 feature requires the infra network to have an IPv4 default route.
lp.addRoute(
RouteInfo(
IpPrefix("0.0.0.0/0") /* destination */,
null /* gateway */,
null /* iface */,
RouteInfo.RTN_UNICAST,
1500, /* mtu */
)
)
return lp
}
}