From 1ba69deb309425ce45d1b597aa080d218ad762ac Mon Sep 17 00:00:00 2001 From: Jonathan Hui Date: Tue, 25 Sep 2018 13:32:14 -0700 Subject: [PATCH] [coaps] add functional tests for psk and x509 (#3096) --- tests/scripts/thread-cert/Makefile.am | 3 + tests/scripts/thread-cert/node.py | 21 ++++++ tests/scripts/thread-cert/node_cli.py | 65 ++++++++++++++++ tests/scripts/thread-cert/test_coaps.py | 98 +++++++++++++++++++++++++ 4 files changed, 187 insertions(+) create mode 100755 tests/scripts/thread-cert/test_coaps.py diff --git a/tests/scripts/thread-cert/Makefile.am b/tests/scripts/thread-cert/Makefile.am index be6200fb2..c134dadd4 100644 --- a/tests/scripts/thread-cert/Makefile.am +++ b/tests/scripts/thread-cert/Makefile.am @@ -139,6 +139,7 @@ EXTRA_DIST = \ sniffer.py \ sniffer_transport.py \ test_coap.py \ + test_coaps.py \ test_common.py \ test_crypto.py \ test_diag.py \ @@ -156,6 +157,7 @@ check_PROGRAMS = \ check_SCRIPTS = \ test_coap.py \ + test_coaps.py \ test_common.py \ test_crypto.py \ test_ipv6.py \ @@ -274,6 +276,7 @@ TESTS = \ $(NULL) XFAIL_NCP_TESTS = \ + test_coaps.py \ test_diag.py \ test_service.py \ Cert_5_2_05_AddressQuery.py \ diff --git a/tests/scripts/thread-cert/node.py b/tests/scripts/thread-cert/node.py index bfc896bd3..e3c7d7866 100755 --- a/tests/scripts/thread-cert/node.py +++ b/tests/scripts/thread-cert/node.py @@ -275,5 +275,26 @@ class Node: self.interface.send_mgmt_pending_set(pending_timestamp, active_timestamp, delay_timer, channel, panid, master_key, mesh_local, network_name) + def coaps_start_psk(self, psk, pskIdentity): + self.interface.coaps_start_psk(psk, pskIdentity) + + def coaps_start_x509(self): + self.interface.coaps_start_x509() + + def coaps_set_resource_path(self, path): + self.interface.coaps_set_resource_path(path) + + def coaps_stop(self): + self.interface.coaps_stop() + + def coaps_connect(self, ipaddr): + self.interface.coaps_connect(ipaddr) + + def coaps_disconnect(self): + self.interface.coaps_disconnect() + + def coaps_get(self): + self.interface.coaps_get() + if __name__ == '__main__': unittest.main() diff --git a/tests/scripts/thread-cert/node_cli.py b/tests/scripts/thread-cert/node_cli.py index 9138558a6..0d54ec2e2 100644 --- a/tests/scripts/thread-cert/node_cli.py +++ b/tests/scripts/thread-cert/node_cli.py @@ -776,3 +776,68 @@ class otCli: self.send_command(cmd) self._expect('Done') + + def coaps_start_psk(self, psk, pskIdentity): + cmd = 'coaps set psk ' + psk + ' ' + pskIdentity + self.send_command(cmd) + self._expect('Done') + + cmd = 'coaps start' + self.send_command(cmd) + self._expect('Done') + + def coaps_start_x509(self): + cmd = 'coaps set x509' + self.send_command(cmd) + self._expect('Done') + + cmd = 'coaps start' + self.send_command(cmd) + self._expect('Done') + + def coaps_set_resource_path(self, path): + cmd = 'coaps resource ' + path + self.send_command(cmd) + self._expect('Done') + + def coaps_stop(self): + cmd = 'coaps stop' + self.send_command(cmd) + + if isinstance(self.simulator, simulator.VirtualTime): + self.simulator.go(5) + timeout = 1 + else: + timeout = 5 + + self._expect('Done', timeout=timeout) + + def coaps_connect(self, ipaddr): + cmd = 'coaps connect ' + ipaddr + self.send_command(cmd) + + if isinstance(self.simulator, simulator.VirtualTime): + self.simulator.go(5) + timeout = 1 + else: + timeout = 5 + + self._expect('CoAP Secure connected!', timeout=timeout) + + def coaps_disconnect(self): + cmd = 'coaps disconnect' + self.send_command(cmd) + self._expect('Done') + self.simulator.go(5) + + def coaps_get(self): + cmd = 'coaps get test' + self.send_command(cmd) + + if isinstance(self.simulator, simulator.VirtualTime): + self.simulator.go(5) + timeout = 1 + else: + timeout = 5 + + self._expect('Received coap secure response', timeout=timeout) diff --git a/tests/scripts/thread-cert/test_coaps.py b/tests/scripts/thread-cert/test_coaps.py new file mode 100755 index 000000000..285f91b49 --- /dev/null +++ b/tests/scripts/thread-cert/test_coaps.py @@ -0,0 +1,98 @@ +#!/usr/bin/env python +# +# Copyright (c) 2018, 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 time +import unittest + +import config +import mle +import network_layer +import node + +LEADER = 1 +ROUTER = 2 + + +class TestCoaps(unittest.TestCase): + + def setUp(self): + self.simulator = config.create_default_simulator() + + self.nodes = {} + for i in range(1, 3): + self.nodes[i] = node.Node(i, simulator=self.simulator) + + self.nodes[LEADER].set_panid(0xface) + self.nodes[LEADER].set_mode('rsdn') + self.nodes[LEADER].add_whitelist(self.nodes[ROUTER].get_addr64()) + self.nodes[LEADER].enable_whitelist() + + self.nodes[ROUTER].set_panid(0xface) + self.nodes[ROUTER].set_mode('rsdn') + self.nodes[ROUTER].add_whitelist(self.nodes[LEADER].get_addr64()) + self.nodes[ROUTER].enable_whitelist() + self.nodes[ROUTER].set_router_selection_jitter(1) + + def tearDown(self): + for node in list(self.nodes.values()): + node.stop() + node.destroy() + self.simulator.stop() + + def test(self): + self.nodes[LEADER].start() + self.simulator.go(5) + self.assertEqual(self.nodes[LEADER].get_state(), 'leader') + + self.nodes[ROUTER].start() + self.simulator.go(5) + self.assertEqual(self.nodes[ROUTER].get_state(), 'router') + + mleid = self.nodes[LEADER].get_ip6_address(config.ADDRESS_TYPE.ML_EID) + + self.nodes[LEADER].coaps_start_psk('psk', 'pskIdentity') + self.nodes[LEADER].coaps_set_resource_path('test') + self.nodes[ROUTER].coaps_start_psk('psk', 'pskIdentity') + self.nodes[ROUTER].coaps_connect(mleid) + self.nodes[ROUTER].coaps_get() + self.nodes[ROUTER].coaps_disconnect() + self.nodes[ROUTER].coaps_stop() + self.nodes[LEADER].coaps_stop() + + self.nodes[LEADER].coaps_start_x509() + #self.nodes[LEADER].coaps_set_resource_path('test') + self.nodes[ROUTER].coaps_start_x509() + self.nodes[ROUTER].coaps_connect(mleid) + self.nodes[ROUTER].coaps_get() + self.nodes[ROUTER].coaps_disconnect() + self.nodes[ROUTER].coaps_stop() + self.nodes[LEADER].coaps_stop() + +if __name__ == '__main__': + unittest.main()