diff --git a/script/test b/script/test index be9433166..69a657201 100755 --- a/script/test +++ b/script/test @@ -245,8 +245,6 @@ do_cert_suite() export PYTHONPATH=tests/scripts/thread-cert export VIRTUAL_TIME - sudo modprobe ip6table_filter - python3 tests/scripts/thread-cert/run_cert_suite.py --multiply "${MULTIPLY:-1}" "$@" exit 0 } diff --git a/src/posix/platform/CMakeLists.txt b/src/posix/platform/CMakeLists.txt index 203e7f089..0e06d4eb2 100644 --- a/src/posix/platform/CMakeLists.txt +++ b/src/posix/platform/CMakeLists.txt @@ -67,7 +67,6 @@ add_library(openthread-posix backbone.cpp daemon.cpp entropy.cpp - firewall.cpp hdlc_interface.cpp infra_if.cpp logging.cpp @@ -83,7 +82,6 @@ add_library(openthread-posix system.cpp trel_udp6.cpp udp.cpp - utils.cpp virtual_time.cpp ) diff --git a/src/posix/platform/Makefile.am b/src/posix/platform/Makefile.am index 90bb59d32..7a2c72339 100644 --- a/src/posix/platform/Makefile.am +++ b/src/posix/platform/Makefile.am @@ -48,7 +48,6 @@ libopenthread_posix_a_SOURCES = \ backbone.cpp \ daemon.cpp \ entropy.cpp \ - firewall.cpp \ hdlc_interface.cpp \ infra_if.cpp \ logging.cpp \ @@ -64,7 +63,6 @@ libopenthread_posix_a_SOURCES = \ system.cpp \ trel_udp6.cpp \ udp.cpp \ - utils.cpp \ virtual_time.cpp \ $(NULL) diff --git a/src/posix/platform/firewall.cpp b/src/posix/platform/firewall.cpp deleted file mode 100644 index 65ef5a687..000000000 --- a/src/posix/platform/firewall.cpp +++ /dev/null @@ -1,132 +0,0 @@ -/* - * Copyright (c) 2021, The OpenThread Authors. - * All rights reserved. - * - * Redistribution and use in source and binary forms, with or without - * modification, are permitted provided that the following conditions are met: - * 1. Redistributions of source code must retain the above copyright - * notice, this list of conditions and the following disclaimer. - * 2. Redistributions in binary form must reproduce the above copyright - * notice, this list of conditions and the following disclaimer in the - * documentation and/or other materials provided with the distribution. - * 3. Neither the name of the copyright holder nor the - * names of its contributors may be used to endorse or promote products - * derived from this software without specific prior written permission. - * - * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" - * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE - * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE - * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE - * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR - * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF - * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS - * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN - * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) - * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE - * POSSIBILITY OF SUCH DAMAGE. - */ - -/** - * @file - * @brief - * This file includes the implementation of OTBR firewall. - */ - -#include "firewall.hpp" - -#include - -#include "common/code_utils.hpp" -#include "openthread/netdata.h" -#include "posix/platform/utils.hpp" - -namespace ot { -namespace Posix { - -#if defined(__linux__) && OPENTHREAD_POSIX_CONFIG_FIREWALL_ENABLE - -#if !OPENTHREAD_CONFIG_BORDER_ROUTER_ENABLE || !OPENTHREAD_CONFIG_PLATFORM_NETIF_ENABLE -#error Configurations 'OPENTHREAD_CONFIG_BORDER_ROUTER_ENABLE' and 'OPENTHREAD_CONFIG_PLATFORM_NETIF_ENABLE' are required. -#endif - -static const char kIpsetCommand[] = "ipset"; -static const char kIngressDenySrcIpSet[] = "otbr-ingress-deny-src"; -static const char kIngressDenySrcSwapIpSet[] = "otbr-ingress-deny-src-swap"; -static const char kIngressAllowDstIpSet[] = "otbr-ingress-allow-dst"; -static const char kIngressAllowDstSwapIpSet[] = "otbr-ingress-allow-dst-swap"; - -class IpSetManager -{ -public: - otError FlushIpSet(const char *aName); - otError AddToIpSet(const char *aSetName, const char *aAddress); - otError SwapIpSets(const char *aSetName1, const char *aSetName2); -}; - -inline otError IpSetManager::FlushIpSet(const char *aName) -{ - return ExecuteCommand("%s flush %s", kIpsetCommand, aName); -} - -inline otError IpSetManager::AddToIpSet(const char *aSetName, const char *aAddress) -{ - return ExecuteCommand("%s add %s %s -exist", kIpsetCommand, aSetName, aAddress); -} - -inline otError IpSetManager::SwapIpSets(const char *aSetName1, const char *aSetName2) -{ - return ExecuteCommand("%s swap %s %s", kIpsetCommand, aSetName1, aSetName2); -} - -void UpdateIpSets(otInstance *aInstance) -{ - otError error = OT_ERROR_NONE; - otNetworkDataIterator iterator = OT_NETWORK_DATA_ITERATOR_INIT; - otBorderRouterConfig config; - otIp6Prefix prefix; - char prefixBuf[OT_IP6_PREFIX_STRING_SIZE]; - IpSetManager ipSetManager; - - // 1. Flush the '*-swap' ipsets - SuccessOrExit(error = ipSetManager.FlushIpSet(kIngressAllowDstSwapIpSet)); - SuccessOrExit(error = ipSetManager.FlushIpSet(kIngressDenySrcSwapIpSet)); - - // 2. Update otbr-deny-src-swap - while (otNetDataGetNextOnMeshPrefix(aInstance, &iterator, &config) == OT_ERROR_NONE) - { - if (config.mDp) - { - continue; - } - otIp6PrefixToString(&config.mPrefix, prefixBuf, sizeof(prefixBuf)); - SuccessOrExit(error = ipSetManager.AddToIpSet(kIngressDenySrcSwapIpSet, prefixBuf)); - } - memcpy(prefix.mPrefix.mFields.m8, otThreadGetMeshLocalPrefix(aInstance)->m8, - sizeof(otThreadGetMeshLocalPrefix(aInstance)->m8)); - prefix.mLength = OT_IP6_PREFIX_BITSIZE; - otIp6PrefixToString(&prefix, prefixBuf, sizeof(prefixBuf)); - SuccessOrExit(error = ipSetManager.AddToIpSet(kIngressDenySrcSwapIpSet, prefixBuf)); - - // 3. Update otbr-allow-dst-swap - iterator = OT_NETWORK_DATA_ITERATOR_INIT; - while (otNetDataGetNextOnMeshPrefix(aInstance, &iterator, &config) == OT_ERROR_NONE) - { - otIp6PrefixToString(&config.mPrefix, prefixBuf, sizeof(prefixBuf)); - SuccessOrExit(error = ipSetManager.AddToIpSet(kIngressAllowDstSwapIpSet, prefixBuf)); - } - - // 4. Swap ipsets to let them take effect - SuccessOrExit(error = ipSetManager.SwapIpSets(kIngressDenySrcSwapIpSet, kIngressDenySrcIpSet)); - SuccessOrExit(error = ipSetManager.SwapIpSets(kIngressAllowDstSwapIpSet, kIngressAllowDstIpSet)); - -exit: - if (error != OT_ERROR_NONE) - { - otLogWarnPlat("Failed to update ipsets: %s", otThreadErrorToString(error)); - } -} - -#endif // defined(__linux__) && OPENTHREAD_POSIX_CONFIG_FIREWALL_ENABLE - -} // namespace Posix -} // namespace ot diff --git a/src/posix/platform/firewall.hpp b/src/posix/platform/firewall.hpp deleted file mode 100644 index bfbef6273..000000000 --- a/src/posix/platform/firewall.hpp +++ /dev/null @@ -1,49 +0,0 @@ -/* - * Copyright (c) 2021, The OpenThread Authors. - * All rights reserved. - * - * Redistribution and use in source and binary forms, with or without - * modification, are permitted provided that the following conditions are met: - * 1. Redistributions of source code must retain the above copyright - * notice, this list of conditions and the following disclaimer. - * 2. Redistributions in binary form must reproduce the above copyright - * notice, this list of conditions and the following disclaimer in the - * documentation and/or other materials provided with the distribution. - * 3. Neither the name of the copyright holder nor the - * names of its contributors may be used to endorse or promote products - * derived from this software without specific prior written permission. - * - * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" - * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE - * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE - * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE - * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR - * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF - * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS - * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN - * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) - * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE - * POSSIBILITY OF SUCH DAMAGE. - */ - -#ifndef OT_POSIX_PLATFORM_FIREWALL_HPP_ -#define OT_POSIX_PLATFORM_FIREWALL_HPP_ - -#include "posix/platform/openthread-posix-config.h" - -#include "common/logging.hpp" -#include "openthread/thread.h" - -namespace ot { -namespace Posix { - -#if OPENTHREAD_POSIX_CONFIG_FIREWALL_ENABLE - -void UpdateIpSets(otInstance *aInstance); - -#endif - -} // namespace Posix -} // namespace ot - -#endif // OT_POSIX_PLATFORM_FIREWALL_HPP_ diff --git a/src/posix/platform/netif.cpp b/src/posix/platform/netif.cpp index 02e5bc539..9d886d7d6 100644 --- a/src/posix/platform/netif.cpp +++ b/src/posix/platform/netif.cpp @@ -163,9 +163,6 @@ unsigned int otSysGetThreadNetifIndex(void) } #if OPENTHREAD_CONFIG_PLATFORM_NETIF_ENABLE -#if OPENTHREAD_POSIX_CONFIG_FIREWALL_ENABLE -#include "firewall.hpp" -#endif #include "posix/platform/ip6_utils.hpp" using namespace ot::Posix::Ip6Utils; @@ -749,12 +746,6 @@ void platformNetifStateChange(otInstance *aInstance, otChangedFlags aFlags) UpdateExternalRoutes(aInstance); } #endif -#if OPENTHREAD_POSIX_CONFIG_FIREWALL_ENABLE - if (OT_CHANGED_THREAD_NETDATA & aFlags) - { - ot::Posix::UpdateIpSets(aInstance); - } -#endif } static void processReceive(otMessage *aMessage, void *aContext) diff --git a/src/posix/platform/openthread-posix-config.h b/src/posix/platform/openthread-posix-config.h index dfdfdb913..9bd6d70f6 100644 --- a/src/posix/platform/openthread-posix-config.h +++ b/src/posix/platform/openthread-posix-config.h @@ -187,31 +187,6 @@ #define OPENTHREAD_POSIX_CONFIG_MAX_EXTERNAL_ROUTE_NUM 8 #endif -/** - * @def OPENTHREAD_POSIX_CONFIG_FIREWALL_ENABLE - * - * Define as 1 to enable firewall. - * - * The rules are implemented using ip6tables and ipset. The rules are as follows. - * - * ip6tables -A $OTBR_FORWARD_CHAIN -m set --match-set otbr-deny-src src -p ip -j DROP - * ip6tables -A $OTBR_FORWARD_CHAIN -m set --match-set otbr-allow-dst dst -p ip -j ACCEPT - * ip6tables -A $OTBR_FORWARD_CHAIN -m pkttype --pkt-type unicast -p ip -j DROP - * ip6tables -A $OTBR_FORWARD_CHAIN -p ip -j ACCEPT - * - */ -#ifdef __linux__ -#if OPENTHREAD_CONFIG_BORDER_ROUTER_ENABLE & OPENTHREAD_CONFIG_PLATFORM_NETIF_ENABLE -#ifndef OPENTHREAD_POSIX_CONFIG_FIREWALL_ENABLE -#define OPENTHREAD_POSIX_CONFIG_FIREWALL_ENABLE 1 -#endif -#endif -#endif - -#ifndef OPENTHREAD_POSIX_CONFIG_FIREWALL_ENABLE -#define OPENTHREAD_POSIX_CONFIG_FIREWALL_ENABLE 0 -#endif - #ifdef __APPLE__ /** diff --git a/src/posix/platform/system.cpp b/src/posix/platform/system.cpp index b029373c2..8b78f9be5 100644 --- a/src/posix/platform/system.cpp +++ b/src/posix/platform/system.cpp @@ -49,7 +49,6 @@ #include "common/code_utils.hpp" #include "common/debug.hpp" #include "posix/platform/daemon.hpp" -#include "posix/platform/firewall.hpp" #include "posix/platform/infra_if.hpp" #include "posix/platform/mainloop.hpp" #include "posix/platform/radio_url.hpp" diff --git a/src/posix/platform/utils.cpp b/src/posix/platform/utils.cpp deleted file mode 100644 index a7322198e..000000000 --- a/src/posix/platform/utils.cpp +++ /dev/null @@ -1,88 +0,0 @@ -/* - * Copyright (c) 2021, The OpenThread Authors. - * All rights reserved. - * - * Redistribution and use in source and binary forms, with or without - * modification, are permitted provided that the following conditions are met: - * 1. Redistributions of source code must retain the above copyright - * notice, this list of conditions and the following disclaimer. - * 2. Redistributions in binary form must reproduce the above copyright - * notice, this list of conditions and the following disclaimer in the - * documentation and/or other materials provided with the distribution. - * 3. Neither the name of the copyright holder nor the - * names of its contributors may be used to endorse or promote products - * derived from this software without specific prior written permission. - * - * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" - * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE - * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE - * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE - * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR - * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF - * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS - * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN - * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) - * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE - * POSSIBILITY OF SUCH DAMAGE. - */ - -/** - * @file - * The file implements POSIX system utilities. - */ - -#include "utils.hpp" - -#include -#include -#include - -#include "common/code_utils.hpp" -#include "common/logging.hpp" - -namespace ot { -namespace Posix { - -enum -{ - kSystemCommandMaxLength = 1024, ///< Max length of a system call command. - kOutputBufferSize = 256, ///< Buffer size of command output. -}; - -otError ExecuteCommand(const char *aFormat, ...) -{ - char cmd[kSystemCommandMaxLength]; - char buf[kOutputBufferSize]; - va_list args; - FILE * file; - int exitCode; - otError error = OT_ERROR_NONE; - - va_start(args, aFormat); - vsnprintf(cmd, sizeof(cmd), aFormat, args); - va_end(args); - - file = popen(cmd, "r"); - VerifyOrExit(file != nullptr, error = OT_ERROR_FAILED); - while (fgets(buf, sizeof(buf), file)) - { - size_t length = strlen(buf); - if (buf[length] == '\n') - { - buf[length] = '\0'; - } - otLogInfoPlat("%s", buf); - } - exitCode = pclose(file); - otLogInfoPlat("Execute command `%s` = %d", cmd, exitCode); - VerifyOrExit(exitCode == 0, error = OT_ERROR_FAILED); -exit: - if (error != OT_ERROR_NONE && errno != 0) - { - otLogInfoPlat("Got an error when executing command `%s`: `%s`", cmd, strerror(errno)); - } - return error; -} - -} // namespace Posix -} // namespace ot diff --git a/src/posix/platform/utils.hpp b/src/posix/platform/utils.hpp deleted file mode 100644 index 0ffcc904d..000000000 --- a/src/posix/platform/utils.hpp +++ /dev/null @@ -1,51 +0,0 @@ -/* - * Copyright (c) 2021, The OpenThread Authors. - * All rights reserved. - * - * Redistribution and use in source and binary forms, with or without - * modification, are permitted provided that the following conditions are met: - * 1. Redistributions of source code must retain the above copyright - * notice, this list of conditions and the following disclaimer. - * 2. Redistributions in binary form must reproduce the above copyright - * notice, this list of conditions and the following disclaimer in the - * documentation and/or other materials provided with the distribution. - * 3. Neither the name of the copyright holder nor the - * names of its contributors may be used to endorse or promote products - * derived from this software without specific prior written permission. - * - * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" - * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE - * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE - * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE - * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR - * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF - * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS - * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN - * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) - * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE - * POSSIBILITY OF SUCH DAMAGE. - */ - -#ifndef OT_POSIX_PLATFORM_UTILS_HPP_ -#define OT_POSIX_PLATFORM_UTILS_HPP_ - -#include "openthread/error.h" - -namespace ot { -namespace Posix { - -/** - * This method formats a system command to execute. - * - * @param[in] aFormat A pointer to the format string. - * @param[in] ... Arguments for the format specification. - * - * @returns The command exit code. - * - */ -otError ExecuteCommand(const char *aFormat, ...); - -} // namespace Posix -} // namespace ot - -#endif // OT_POSIX_PLATFORM_UTILS_HPP_ diff --git a/tests/scripts/thread-cert/border_router/test_firewall.py b/tests/scripts/thread-cert/border_router/test_firewall.py deleted file mode 100644 index 03b90b96a..000000000 --- a/tests/scripts/thread-cert/border_router/test_firewall.py +++ /dev/null @@ -1,269 +0,0 @@ -#!/usr/bin/env python3 -# -# Copyright (c) 2021, The OpenThread Authors. -# All rights reserved. -# -# Redistribution and use in source and binary forms, with or without -# modification, are permitted provided that the following conditions are met: -# 1. Redistributions of source code must retain the above copyright -# notice, this list of conditions and the following disclaimer. -# 2. Redistributions in binary form must reproduce the above copyright -# notice, this list of conditions and the following disclaimer in the -# documentation and/or other materials provided with the distribution. -# 3. Neither the name of the copyright holder nor the -# names of its contributors may be used to endorse or promote products -# derived from this software without specific prior written permission. -# -# THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 'AS IS' -# AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE -# IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE -# ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE -# LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR -# CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF -# SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS -# INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN -# CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) -# ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE -# POSSIBILITY OF SUCH DAMAGE. -# -import logging -import unittest -import ipaddress - -import config -import pktverify -import pktverify.packet_verifier -from pktverify.consts import MA1 -import thread_cert - -# Test description: -# This test verifies the functionality of firewall. OTBR will only -# forward specific kinds of packets between the infra interface and the thread -# interface. -# -# Topology: -# ----------------(eth)---------------------- -# | | -# BR1 (Leader) HOST -# | -# ROUTER1 - -BR1 = 1 -ROUTER1 = 2 -HOST = 3 - - -class Firewall(thread_cert.TestCase): - USE_MESSAGE_FACTORY = False - - TOPOLOGY = { - BR1: { - 'name': 'BR_1', - 'allowlist': [ROUTER1], - 'is_otbr': True, - 'version': '1.2', - }, - ROUTER1: { - 'name': 'Router_1', - 'allowlist': [BR1], - 'version': '1.2', - }, - HOST: { - 'name': 'Host', - 'is_host': True, - } - } - - def test(self): - br1 = self.nodes[BR1] - self.br1 = br1 - router1 = self.nodes[ROUTER1] - host = self.nodes[HOST] - - br1.start() - self.simulator.go(5) - self.assertEqual('leader', br1.get_state()) - - router1.start() - host.start(start_radvd=True) - self.simulator.go(5) - self.assertEqual('router', router1.get_state()) - - br1.set_domain_prefix(config.DOMAIN_PREFIX, 'prosD') - br1.register_netdata() - - router1.add_ipmaddr(MA1) - router1.register_netdata() - - self.simulator.go(5) - - def host_ping_ether(dest, interface, ttl=10, add_interface=False, add_route=False, gateway=None): - if add_interface: - host.bash(f'ip -6 addr add {interface}/64 dev {host.ETH_DEV} scope global') - route = str(ipaddress.IPv6Network(f'{interface}/64', strict=False)) - host.bash(f'ip -6 route del {route} dev {host.ETH_DEV}') - if add_route: - host.bash(f'ip -6 route add {dest} dev {host.ETH_DEV} via {gateway}') - self.simulator.go(2) - result = host.ping_ether(dest, ttl=ttl, interface=interface) - if add_route: - host.bash(f'ip -6 route del {dest}') - if add_interface: - host.bash(f'ip -6 addr del {interface}/64 dev {host.ETH_DEV} scope global') - self.simulator.go(1) - return result - - # 1. Host pings router1's OMR from host's infra address. - self.assertTrue(host_ping_ether(router1.get_ip6_address(config.ADDRESS_TYPE.OMR)[0], interface=host.ETH_DEV)) - - # 2. Host pings router1's DUA from host's infra address. - self.assertTrue(host_ping_ether(router1.get_ip6_address(config.ADDRESS_TYPE.DUA), interface=host.ETH_DEV)) - - # 3. Host pings router1's OMR from router1's RLOC. - self.assertFalse( - host_ping_ether(router1.get_ip6_address(config.ADDRESS_TYPE.OMR)[0], - interface=router1.get_rloc(), - add_interface=True)) - - # 4. Host pings router1's OMR from BR1's OMR. - self.assertFalse( - host_ping_ether(router1.get_ip6_address(config.ADDRESS_TYPE.OMR)[0], - interface=br1.get_ip6_address(config.ADDRESS_TYPE.OMR)[0], - add_interface=True)) - - # 5. Host pings router1's OMR from router1's MLE-ID. - self.assertFalse( - host_ping_ether(router1.get_ip6_address(config.ADDRESS_TYPE.OMR)[0], - interface=router1.get_mleid(), - add_interface=True)) - - host.bash(f'ip -6 route add {config.MESH_LOCAL_PREFIX} dev {host.ETH_DEV}') - self.simulator.go(5) - - # 6. Host pings router1's RLOC from host's ULA address. - self.assertFalse( - host_ping_ether(router1.get_rloc(), - interface=host.get_ip6_address(config.ADDRESS_TYPE.ONLINK_ULA)[0], - add_route=True, - gateway=br1.get_ip6_address(config.ADDRESS_TYPE.BACKBONE_GUA))) - - # 7. Host pings router1's MLE-ID from host's ULA address. - self.assertFalse( - host_ping_ether(router1.get_mleid(), - interface=host.get_ip6_address(config.ADDRESS_TYPE.ONLINK_ULA)[0], - add_route=True, - gateway=br1.get_ip6_address(config.ADDRESS_TYPE.BACKBONE_GUA))) - - # 8. Host pings router1's link-local address from host's infra address. - self.assertFalse( - host_ping_ether(router1.get_linklocal(), - interface=host.ETH_DEV, - add_route=True, - gateway=br1.get_ip6_address(config.ADDRESS_TYPE.BACKBONE_GUA))) - - # 9. Host pings MA1 from host's ULA address. - self.assertTrue(host_ping_ether(MA1, ttl=10, - interface=host.get_ip6_address(config.ADDRESS_TYPE.ONLINK_ULA)[0])) - - # 10. Host pings MA1 from router1's RLOC. - self.assertFalse(host_ping_ether(MA1, ttl=10, interface=router1.get_rloc(), add_interface=True)) - - # 11. Host pings MA1 from router1's OMR. - self.assertFalse( - host_ping_ether(MA1, - ttl=10, - interface=router1.get_ip6_address(config.ADDRESS_TYPE.OMR)[0], - add_interface=True)) - - # 12. Host pings MA1 from router1's MLE-ID. - self.assertFalse(host_ping_ether(MA1, ttl=10, interface=router1.get_mleid(), add_interface=True)) - - self.collect_ipaddrs() - self.collect_rlocs() - self.collect_rloc16s() - self.collect_extra_vars() - self.collect_omrs() - self.collect_duas() - - def verify(self, pv: pktverify.packet_verifier.PacketVerifier): - pkts = pv.pkts - vars = pv.vars - pv.summary.show() - logging.info(f'vars = {vars}') - - pv.verify_attached('Router_1', 'BR_1') - - # 1. Host pings router1's OMR from host's infra address. - _pkt = pkts.filter_eth_src(vars['Host_ETH']).filter_ipv6_dst( - vars['Router_1_OMR'][0]).filter_ping_request().must_next() - pkts.filter_wpan_src64(vars['BR_1']).filter_wpan_dst16( - vars['Router_1_RLOC16']).filter_ping_request(identifier=_pkt.icmpv6.echo.identifier).must_next() - - # 2. Host pings router1's DUA from host's infra address. - _pkt = pkts.filter_eth_src(vars['Host_ETH']).filter_ipv6_dst( - vars['Router_1_DUA']).filter_ping_request().must_next() - pkts.filter_wpan_src64(vars['BR_1']).filter_wpan_dst16( - vars['Router_1_RLOC16']).filter_ping_request(identifier=_pkt.icmpv6.echo.identifier).must_next() - - # 3. Host pings router1's OMR from router1's RLOC. - _pkt = pkts.filter_eth_src(vars['Host_ETH']).filter_ipv6_src_dst( - vars['Router_1_RLOC'], vars['Router_1_OMR'][0]).filter_ping_request().must_next() - pkts.filter_wpan_src64(vars['BR_1']).filter_wpan_dst16( - vars['Router_1_RLOC16']).filter_ping_request(identifier=_pkt.icmpv6.echo.identifier).must_not_next() - - # 4. Host pings router1's OMR from BR1's OMR. - _pkt = pkts.filter_eth_src(vars['Host_ETH']).filter_ipv6_src_dst( - vars['BR_1_OMR'][0], vars['Router_1_OMR'][0]).filter_ping_request().must_next() - pkts.filter_wpan_src64(vars['BR_1']).filter_wpan_dst64( - vars['Router_1']).filter_ping_request(identifier=_pkt.icmpv6.echo.identifier).must_not_next() - - # 5. Host pings router1's OMR from router1's MLE-ID. - _pkt = pkts.filter_eth_src(vars['Host_ETH']).filter_ipv6_src_dst( - vars['Router_1_MLEID'], vars['Router_1_OMR'][0]).filter_ping_request().must_next() - pkts.filter_wpan_src64(vars['BR_1']).filter_wpan_dst16( - vars['Router_1_RLOC16']).filter_ping_request(identifier=_pkt.icmpv6.echo.identifier).must_not_next() - - # 6. Host pings router1's RLOC from host's ULA address. - _pkt = pkts.filter_eth_src(vars['Host_ETH']).filter_ipv6_dst( - vars['Router_1_RLOC']).filter_ping_request().must_next() - pkts.filter_wpan_src64(vars['BR_1']).filter_wpan_dst16( - vars['Router_1_RLOC16']).filter_ping_request(identifier=_pkt.icmpv6.echo.identifier).must_not_next() - - # 7. Host pings router1's MLE-ID from host's ULA address. - _pkt = pkts.filter_eth_src(vars['Host_ETH']).filter_ipv6_dst( - vars['Router_1_MLEID']).filter_ping_request().must_next() - pkts.filter_wpan_src64(vars['BR_1']).filter_wpan_dst16( - vars['Router_1_RLOC16']).filter_ping_request(identifier=_pkt.icmpv6.echo.identifier).must_not_next() - - # 8. Host pings router1's link-local address from host's infra address. - _pkt = pkts.filter_eth_src(vars['Host_ETH']).filter_ipv6_dst( - vars['Router_1_LLA']).filter_ping_request().must_next() - pkts.filter_wpan_src64(vars['BR_1']).filter_wpan_dst16( - vars['Router_1_RLOC16']).filter_ping_request(identifier=_pkt.icmpv6.echo.identifier).must_not_next() - - # 9. Host pings MA1 from host's ULA address. - _pkt = pkts.filter_eth_src(vars['Host_ETH']).filter_ipv6_dst(MA1).filter_ping_request().must_next() - pkts.filter_wpan_src64( - vars['BR_1']).filter_AMPLFMA().filter_ping_request(identifier=_pkt.icmpv6.echo.identifier).must_next() - - # 10. Host pings MA1 from router1's RLOC. - _pkt = pkts.filter_eth_src(vars['Host_ETH']).filter_ipv6_src_dst(vars['Router_1_RLOC'], - MA1).filter_ping_request().must_next() - pkts.filter_wpan_src64( - vars['BR_1']).filter_AMPLFMA().filter_ping_request(identifier=_pkt.icmpv6.echo.identifier).must_not_next() - - # 11. Host pings MA1 from router1's OMR. - _pkt = pkts.filter_eth_src(vars['Host_ETH']).filter_ipv6_src_dst(vars['Router_1_OMR'][0], - MA1).filter_ping_request().must_next() - pkts.filter_wpan_src64( - vars['BR_1']).filter_AMPLFMA().filter_ping_request(identifier=_pkt.icmpv6.echo.identifier).must_not_next() - - # 12. Host pings MA1 from router1's MLE-ID. - _pkt = pkts.filter_eth_src(vars['Host_ETH']).filter_ipv6_src_dst(vars['Router_1_MLEID'], - MA1).filter_ping_request().must_next() - pkts.filter_wpan_src64( - vars['BR_1']).filter_AMPLFMA().filter_ping_request(identifier=_pkt.icmpv6.echo.identifier).must_not_next() - - -if __name__ == '__main__': - unittest.main() diff --git a/tests/scripts/thread-cert/node.py b/tests/scripts/thread-cert/node.py index cc6c87e65..4c5811c4c 100755 --- a/tests/scripts/thread-cert/node.py +++ b/tests/scripts/thread-cert/node.py @@ -1657,7 +1657,7 @@ class NodeImpl: omr_addrs = [] for addr in self.get_addrs(): for prefix in prefixes: - if (addr.startswith(prefix)) and (addr != self.__getDua()): + if (addr.startswith(prefix)): omr_addrs.append(addr) break diff --git a/tests/scripts/thread-cert/pktverify/packet_verifier.py b/tests/scripts/thread-cert/pktverify/packet_verifier.py index c78ec7e0b..5c02166c1 100644 --- a/tests/scripts/thread-cert/pktverify/packet_verifier.py +++ b/tests/scripts/thread-cert/pktverify/packet_verifier.py @@ -157,14 +157,6 @@ class PacketVerifier(object): key = self.test_info.get_node_name(i) + '_RLOC' self._vars[key] = rloc - for i, omr in self.test_info.omrs.items(): - key = self.test_info.get_node_name(i) + '_OMR' - self._vars[key] = omr - - for i, dua in self.test_info.duas.items(): - key = self.test_info.get_node_name(i) + '_DUA' - self._vars[key] = dua - if self.test_info.leader_aloc: self._vars['LEADER_ALOC'] = self.test_info.leader_aloc diff --git a/tests/scripts/thread-cert/pktverify/test_info.py b/tests/scripts/thread-cert/pktverify/test_info.py index 937929b0b..c44f52ab5 100644 --- a/tests/scripts/thread-cert/pktverify/test_info.py +++ b/tests/scripts/thread-cert/pktverify/test_info.py @@ -53,8 +53,6 @@ class TestInfo(object): self.mleids = {int(k): Ipv6Addr(v) for k, v in test_info.get('mleids', {}).items()} self.rlocs = {int(k): Ipv6Addr(v) for k, v in test_info.get('rlocs', {}).items()} self.rloc16s = self._convert_hex_values(self._convert_keys_to_ints(test_info.get('rloc16s', {}))) - self.omrs = {int(k): [Ipv6Addr(x) for x in l] for k, l in test_info.get('omrs', {}).items()} - self.duas = {int(k): Ipv6Addr(v) for k, v in test_info.get('duas', {}).items()} self.extra_vars = test_info.get('extra_vars', {}) self.leader_aloc = Ipv6Addr(test_info.get('leader_aloc')) if 'leader_aloc' in test_info else '' diff --git a/tests/scripts/thread-cert/run_cert_suite.py b/tests/scripts/thread-cert/run_cert_suite.py index 512ab815d..a3b7d5755 100755 --- a/tests/scripts/thread-cert/run_cert_suite.py +++ b/tests/scripts/thread-cert/run_cert_suite.py @@ -94,6 +94,8 @@ def cleanup_backbone_env(): def setup_backbone_env(): + bash('sudo modprobe ip6table_filter') + if THREAD_VERSION != '1.2': raise RuntimeError('Backbone tests only work with THREAD_VERSION=1.2') diff --git a/tests/scripts/thread-cert/thread_cert.py b/tests/scripts/thread-cert/thread_cert.py index 7b22446c0..dbbddc731 100755 --- a/tests/scripts/thread-cert/thread_cert.py +++ b/tests/scripts/thread-cert/thread_cert.py @@ -351,32 +351,6 @@ class TestCase(NcpSupportMixin, unittest.TestCase): test_info['rlocs'][i] = node.get_rloc() - def collect_omrs(self): - if not self._do_packet_verification: - return - - test_info = self._test_info - test_info['omrs'] = {} - - for i, node in self.nodes.items(): - if node.is_host: - continue - - test_info['omrs'][i] = node.get_ip6_address(config.ADDRESS_TYPE.OMR) - - def collect_duas(self): - if not self._do_packet_verification: - return - - test_info = self._test_info - test_info['duas'] = {} - - for i, node in self.nodes.items(): - if node.is_host: - continue - - test_info['duas'][i] = node.get_ip6_address(config.ADDRESS_TYPE.DUA) - def collect_leader_aloc(self, node): if not self._do_packet_verification: return