mirror of
https://github.com/espressif/openthread.git
synced 2026-07-29 15:17:47 +00:00
[tests] support testing commissioning (#3441)
Add support for testing commissioning process, including: 1. Add DTLS, Thread Discovery and commissioning messages(JOIN_FIN.req etc) parsing; 2. Support parsing log from UART response, and construct decrypted messages; 3. Common commands for commissioning related verification;
This commit is contained in:
@@ -45,6 +45,8 @@ class otCli:
|
||||
self.verbose = int(float(os.getenv('VERBOSE', 0)))
|
||||
self.node_type = os.getenv('NODE_TYPE', 'sim')
|
||||
self.simulator = simulator
|
||||
if self.simulator:
|
||||
self.simulator.add_node(self)
|
||||
|
||||
mode = os.environ.get('USE_MTD') is '1' and is_mtd and 'mtd' or 'ftd'
|
||||
|
||||
@@ -152,6 +154,56 @@ class otCli:
|
||||
self.pexpect.expect(pexpect.EOF)
|
||||
self.pexpect = None
|
||||
|
||||
def read_cert_messages_in_commissioning_log(self, timeout=-1):
|
||||
"""Get the log of the traffic after DTLS handshake.
|
||||
"""
|
||||
format_str = br"=+?\[\[THCI\].*?type=%s.*?\].*?=+?[\s\S]+?-{40,}"
|
||||
join_fin_req = format_str % br"JOIN_FIN\.req"
|
||||
join_fin_rsp = format_str % br"JOIN_FIN\.rsp"
|
||||
dummy_format_str = br"\[THCI\].*?type=%s.*?"
|
||||
join_ent_ntf = dummy_format_str % br"JOIN_ENT\.ntf"
|
||||
join_ent_rsp = dummy_format_str % br"JOIN_ENT\.rsp"
|
||||
pattern = (b"(" + join_fin_req + b")|(" + join_fin_rsp + b")|("+ join_ent_ntf + b")|(" + join_ent_rsp + b")")
|
||||
|
||||
messages = []
|
||||
# There are at most 4 cert messages both for joiner and commissioner
|
||||
for _ in range(0, 4):
|
||||
try:
|
||||
self._expect(pattern, timeout=timeout)
|
||||
log = self.pexpect.match.group(0)
|
||||
messages.append(self._extract_cert_message(log))
|
||||
except:
|
||||
break
|
||||
return messages
|
||||
|
||||
def _extract_cert_message(self, log):
|
||||
res = re.search(br"direction=\w+", log)
|
||||
assert res
|
||||
direction = res.group(0).split(b'=')[1].strip()
|
||||
|
||||
res = re.search(br"type=\S+", log)
|
||||
assert res
|
||||
type = res.group(0).split(b'=')[1].strip()
|
||||
|
||||
payload = bytearray([])
|
||||
payload_len = 0
|
||||
if type in [b"JOIN_FIN.req", b"JOIN_FIN.rsp"]:
|
||||
res = re.search(br"len=\d+", log)
|
||||
assert res
|
||||
payload_len = int(res.group(0).split(b'=')[1].strip())
|
||||
|
||||
hex_pattern = br"\|(\s([0-9a-fA-F]{2}|\.\.))+?\s+?\|"
|
||||
while True:
|
||||
res = re.search(hex_pattern, log)
|
||||
if not res:
|
||||
break
|
||||
data = [int(hex, 16) for hex in res.group(0)[1:-1].split(b' ') if hex and hex != b'..']
|
||||
payload += bytearray(data)
|
||||
log = log[res.end()-1:]
|
||||
|
||||
assert len(payload) == payload_len
|
||||
return (direction, type, payload)
|
||||
|
||||
def send_command(self, cmd, go=True):
|
||||
print("%d: %s" % (self.nodeid, cmd))
|
||||
self.pexpect.send(cmd + '\n')
|
||||
@@ -164,7 +216,7 @@ class otCli:
|
||||
self._expect('Commands:')
|
||||
commands = []
|
||||
while True:
|
||||
i = self._expect(['Done', '(\S+)'])
|
||||
i = self._expect(['Done', r'(\S+)'])
|
||||
if i != 0:
|
||||
commands.append(self.pexpect.match.groups()[0])
|
||||
else:
|
||||
@@ -280,7 +332,7 @@ class otCli:
|
||||
|
||||
def get_channel(self):
|
||||
self.send_command('channel')
|
||||
i = self._expect('(\d+)\r?\n')
|
||||
i = self._expect(r'(\d+)\r?\n')
|
||||
if i == 0:
|
||||
channel = int(self.pexpect.match.groups()[0])
|
||||
self._expect('Done')
|
||||
@@ -306,7 +358,7 @@ class otCli:
|
||||
|
||||
def get_key_sequence_counter(self):
|
||||
self.send_command('keysequence counter')
|
||||
i = self._expect('(\d+)\r?\n')
|
||||
i = self._expect(r'(\d+)\r?\n')
|
||||
if i == 0:
|
||||
key_sequence_counter = int(self.pexpect.match.groups()[0])
|
||||
self._expect('Done')
|
||||
@@ -330,7 +382,7 @@ class otCli:
|
||||
def get_network_name(self):
|
||||
self.send_command('networkname')
|
||||
while True:
|
||||
i = self._expect(['Done', '(\S+)'])
|
||||
i = self._expect(['Done', r'(\S+)'])
|
||||
if i != 0:
|
||||
network_name = self.pexpect.match.groups()[0].decode('utf-8')
|
||||
else:
|
||||
@@ -357,7 +409,7 @@ class otCli:
|
||||
|
||||
def get_partition_id(self):
|
||||
self.send_command('leaderpartitionid')
|
||||
i = self._expect('(\d+)\r?\n')
|
||||
i = self._expect(r'(\d+)\r?\n')
|
||||
if i == 0:
|
||||
weight = self.pexpect.match.groups()[0]
|
||||
self._expect('Done')
|
||||
@@ -397,7 +449,7 @@ class otCli:
|
||||
|
||||
def get_timeout(self):
|
||||
self.send_command('childtimeout')
|
||||
i = self._expect('(\d+)\r?\n')
|
||||
i = self._expect(r'(\d+)\r?\n')
|
||||
if i == 0:
|
||||
timeout = self.pexpect.match.groups()[0]
|
||||
self._expect('Done')
|
||||
@@ -415,7 +467,7 @@ class otCli:
|
||||
|
||||
def get_weight(self):
|
||||
self.send_command('leaderweight')
|
||||
i = self._expect('(\d+)\r?\n')
|
||||
i = self._expect(r'(\d+)\r?\n')
|
||||
if i == 0:
|
||||
weight = self.pexpect.match.groups()[0]
|
||||
self._expect('Done')
|
||||
@@ -436,7 +488,7 @@ class otCli:
|
||||
self.send_command('ipaddr')
|
||||
|
||||
while True:
|
||||
i = self._expect(['(\S+(:\S*)+)\r?\n', 'Done'])
|
||||
i = self._expect([r'(\S+(:\S*)+)\r?\n', 'Done'])
|
||||
if i == 0:
|
||||
addrs.append(self.pexpect.match.groups()[0].decode("utf-8"))
|
||||
elif i == 1:
|
||||
@@ -464,7 +516,7 @@ class otCli:
|
||||
self.send_command('eidcache')
|
||||
|
||||
while True:
|
||||
i = self._expect(['([a-fA-F0-9\:]+) ([a-fA-F0-9]+)\r?\n', 'Done'])
|
||||
i = self._expect([r'([a-fA-F0-9\:]+) ([a-fA-F0-9]+)\r?\n', 'Done'])
|
||||
if i == 0:
|
||||
eid = self.pexpect.match.groups()[0].decode("utf-8")
|
||||
rloc = self.pexpect.match.groups()[1].decode("utf-8")
|
||||
@@ -553,7 +605,7 @@ class otCli:
|
||||
|
||||
def get_context_reuse_delay(self):
|
||||
self.send_command('contextreusedelay')
|
||||
i = self._expect('(\d+)\r?\n')
|
||||
i = self._expect(r'(\d+)\r?\n')
|
||||
if i == 0:
|
||||
timeout = self.pexpect.match.groups()[0]
|
||||
self._expect('Done')
|
||||
@@ -617,7 +669,7 @@ class otCli:
|
||||
|
||||
results = []
|
||||
while True:
|
||||
i = self._expect(['\|\s(\S+)\s+\|\s(\S+)\s+\|\s([0-9a-fA-F]{4})\s\|\s([0-9a-fA-F]{16})\s\|\s(\d+)\r?\n',
|
||||
i = self._expect([r'\|\s(\S+)\s+\|\s(\S+)\s+\|\s([0-9a-fA-F]{4})\s\|\s([0-9a-fA-F]{16})\s\|\s(\d+)\r?\n',
|
||||
'Done'])
|
||||
if i == 0:
|
||||
results.append(self.pexpect.match.groups())
|
||||
@@ -640,7 +692,7 @@ class otCli:
|
||||
try:
|
||||
responders = {}
|
||||
while len(responders) < num_responses:
|
||||
i = self._expect(['from (\S+):'])
|
||||
i = self._expect([r'from (\S+):'])
|
||||
if i == 0:
|
||||
responders[self.pexpect.match.groups()[0]] = 1
|
||||
self._expect('\n')
|
||||
|
||||
Reference in New Issue
Block a user