#!/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 sys
import os
import time
import re
import random
import string
import subprocess
import pexpect
import pexpect.popen_spawn
import signal
import inspect
import weakref

# ----------------------------------------------------------------------------------------------------------------------
# Constants

JOIN_TYPE_ROUTER = 'router'
JOIN_TYPE_END_DEVICE = 'ed'
JOIN_TYPE_SLEEPY_END_DEVICE = 'sed'
JOIN_TYPE_REED = 'reed'

# for use as `radios` parameter in `Node.__init__()`
RADIO_15_4 = "-15.4"
RADIO_TREL = "-trel"
RADIO_15_4_TREL = "-15.4-trel"

# ----------------------------------------------------------------------------------------------------------------------


def _log(text, new_line=True, flush=True):
    sys.stdout.write(text)
    if new_line:
        sys.stdout.write('\n')
    if flush:
        sys.stdout.flush()


# ----------------------------------------------------------------------------------------------------------------------
# CliError class


class CliError(Exception):

    def __init__(self, error_code, message):
        self._error_code = error_code
        self._message = message

    @property
    def error_code(self):
        return self._error_code

    @property
    def message(self):
        return self._message


# ----------------------------------------------------------------------------------------------------------------------
# Node class


class Node(object):
    """ An OT CLI instance """

    # defines the default verbosity setting (can be changed per `Node`)
    _VERBOSE = os.getenv('TORANJ_VERBOSE', 'no').lower() in ['true', '1', 't', 'y', 'yes', 'on']

    _SPEED_UP_FACTOR = 1  # defines the default time speed up factor

    # Determine whether to save logs in a file.
    _SAVE_LOGS = True

    # name of  log file (if _SAVE_LOGS is `True`)
    _LOG_FNAME = 'ot-logs'

    _OT_BUILDDIR = os.getenv('top_builddir', '../../..')

    _OT_CLI_FTD = '%s/examples/apps/cli/ot-cli-ftd' % _OT_BUILDDIR

    _WAIT_TIME = 10

    _START_INDEX = 1
    _cur_index = _START_INDEX

    _all_nodes = weakref.WeakSet()

    def __init__(self, radios='', index=None, verbose=_VERBOSE):
        """Creates a new `Node` instance"""

        if index is None:
            index = Node._cur_index
            Node._cur_index += 1

        self._index = index
        self._verbose = verbose

        cmd = f'{self._OT_CLI_FTD}{radios} --time-speed={self._SPEED_UP_FACTOR} '

        if Node._SAVE_LOGS:
            log_file_name = self._LOG_FNAME + str(index) + '.log'
            cmd = cmd + f'--log-file={log_file_name} '

        cmd = cmd + f'{self._index}'

        if self._verbose:
            _log(f'$ Node{index}.__init__() cmd: `{cmd}`')

        self._cli_process = pexpect.popen_spawn.PopenSpawn(cmd)
        Node._all_nodes.add(self)

    def __del__(self):
        self._finalize()

    def __repr__(self):
        return f'Node(index={self._index})'

    @property
    def index(self):
        return self._index

    # ------------------------------------------------------------------------------------------------------------------
    # Executing a `cli` command

    def cli(self, *args):
        """ Issues a CLI command on the given node and returns the resulting output.

            The returned result is a list of strings (with `\r\n` removed) as outputted by the CLI.
            If executing the command fails, `CliError` is raised with error code and error message.
        """

        cmd = ' '.join([f'{arg}' for arg in args if arg is not None]).strip()

        if self._verbose:
            _log(f'$ Node{self._index}.cli(\'{cmd}\')', new_line=False)

        self._cli_process.send(cmd + '\n')
        index = self._cli_process.expect(['(.*)Done\r\n', '.*Error (\d+):(.*)\r\n'])

        if index == 0:
            result = [
                line for line in self._cli_process.match.group(1).decode().splitlines()
                if not self._is_ot_logg_line(line) if not line.strip().endswith(cmd)
            ]

            if self._verbose:
                if len(result) > 1:
                    _log(':')
                    for line in result:
                        _log('     ' + line)
                elif len(result) == 1:
                    _log(f' -> {result[0]}')
                else:
                    _log('')

            return result
        else:
            match = self._cli_process.match
            e = CliError(int(match.group(1).decode()), match.group(2).decode().strip())
            if self._verbose:
                _log(f': Error {e.message} ({e.error_code})')
            raise e

    def _is_ot_logg_line(self, line):
        return any(level in line for level in [' [D] ', ' [I] ', ' [N] ', ' [W] ', ' [C] ', ' [-] '])

    def _cli_no_output(self, cmd, *args):
        outputs = self.cli(cmd, *args)
        verify(len(outputs) == 0)

    def _cli_single_output(self, cmd, *args, expected_outputs=None):
        outputs = self.cli(cmd, *args)
        verify(len(outputs) == 1)
        verify((expected_outputs is None) or (outputs[0] in expected_outputs))
        return outputs[0]

    def _finalize(self):
        if self._cli_process.proc.poll() is None:
            if self._verbose:
                _log(f'$ Node{self.index} terminating')
            self._cli_process.send('exit\n')
            self._cli_process.wait()

    # ------------------------------------------------------------------------------------------------------------------
    # cli commands

    def get_state(self):
        return self._cli_single_output('state', expected_outputs=['detached', 'child', 'router', 'leader', 'disabled'])

    def get_version(self):
        return self._cli_single_output('version')

    def get_channel(self):
        return self._cli_single_output('channel')

    def set_channel(self, channel):
        self._cli_no_output('channel', channel)

    def get_ext_addr(self):
        return self._cli_single_output('extaddr')

    def set_ext_addr(self, ext_addr):
        self._cli_no_output('extaddr', ext_addr)

    def get_ext_panid(self):
        return self._cli_single_output('extpanid')

    def set_ext_panid(self, ext_panid):
        self._cli_no_output('extpanid', ext_panid)

    def get_mode(self):
        return self._cli_single_output('mode')

    def set_mode(self, mode):
        self._cli_no_output('mode', mode)

    def get_network_key(self):
        return self._cli_single_output('networkkey')

    def set_network_key(self, networkkey):
        self._cli_no_output('networkkey', networkkey)

    def get_network_name(self):
        return self._cli_single_output('networkname')

    def set_network_name(self, network_name):
        self._cli_no_output('networkname', network_name)

    def get_panid(self):
        return self._cli_single_output('panid')

    def set_panid(self, panid):
        self._cli_no_output('panid', panid)

    def get_router_upgrade_threshold(self):
        return self._cli_single_output('routerupgradethreshold')

    def set_router_upgrade_threshold(self, threshold):
        self._cli_no_output('routerupgradethreshold', threshold)

    def get_router_selection_jitter(self):
        return self._cli_single_output('routerselectionjitter')

    def set_router_selection_jitter(self, jitter):
        self._cli_no_output('routerselectionjitter', jitter)

    def get_router_eligible(self):
        return self._cli_single_output('routereligible')

    def set_router_eligible(self, enable):
        self._cli_no_output('routereligible', enable)

    def get_context_reuse_delay(self):
        return self._cli_single_output('contextreusedelay')

    def set_context_reuse_delay(self, delay):
        self._cli_no_output('contextreusedelay', delay)

    def interface_up(self):
        self._cli_no_output('ifconfig up')

    def interface_down(self):
        self._cli_no_output('ifconfig down')

    def get_interface_state(self):
        return self._cli_single_output('ifconfig')

    def thread_start(self):
        self._cli_no_output('thread start')

    def thread_stop(self):
        self._cli_no_output('thread stop')

    def get_rloc16(self):
        return self._cli_single_output('rloc16')

    def get_ip_addrs(self):
        return self.cli('ipaddr')

    def add_ip_addr(self, address):
        self._cli_no_output('ipaddr add', address)

    def remove_ip_addr(self, address):
        self._cli_no_output('ipaddr del', address)

    def get_mleid_ip_addr(self):
        return self._cli_single_output('ipaddr mleid')

    def get_linklocal_ip_addr(self):
        return self._cli_single_output('ipaddr linklocal')

    def get_rloc_ip_addr(self):
        return self._cli_single_output('ipaddr rloc')

    def get_mesh_local_prefix(self):
        return self._cli_single_output('prefix meshlocal')

    def get_ip_maddrs(self):
        return self.cli('ipmaddr')

    def add_ip_maddr(self, maddr):
        return self._cli_no_output('ipmaddr add', maddr)

    def get_pollperiod(self):
        return self._cli_single_output('pollperiod')

    def set_pollperiod(self, period):
        self._cli_no_output('pollperiod', period)

    def get_partition_id(self):
        return self._cli_single_output('partitionid')

    def get_nexthop(self, rloc16):
        return self._cli_single_output('nexthop', rloc16)

    def get_parent_info(self):
        outputs = self.cli('parent')
        result = {}
        for line in outputs:
            fields = line.split(':')
            result[fields[0].strip()] = fields[1].strip()
        return result

    def get_child_table(self):
        return Node.parse_table(self.cli('child table'))

    def get_neighbor_table(self):
        return Node.parse_table(self.cli('neighbor table'))

    def get_router_table(self):
        return Node.parse_table(self.cli('router table'))

    def get_eidcache(self):
        return self.cli('eidcache')

    def get_vendor_name(self):
        return self._cli_single_output('vendor name')

    def set_vendor_name(self, name):
        self._cli_no_output('vendor name', name)

    def get_vendor_model(self):
        return self._cli_single_output('vendor model')

    def set_vendor_model(self, model):
        self._cli_no_output('vendor model', model)

    def get_vendor_sw_version(self):
        return self._cli_single_output('vendor swversion')

    def set_vendor_sw_version(self, version):
        return self._cli_no_output('vendor swversion', version)

    #- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
    # netdata

    def get_netdata(self):
        outputs = self.cli('netdata show')
        outputs = [line.strip() for line in outputs]
        routes_index = outputs.index('Routes:')
        services_index = outputs.index('Services:')
        contexts_index = outputs.index('Contexts:')
        result = {}
        result['prefixes'] = outputs[1:routes_index]
        result['routes'] = outputs[routes_index + 1:services_index]
        result['services'] = outputs[services_index + 1:contexts_index]
        result['contexts'] = outputs[contexts_index + 1:]

        return result

    def get_netdata_prefixes(self):
        return self.get_netdata()['prefixes']

    def get_netdata_routes(self):
        return self.get_netdata()['routes']

    def get_netdata_services(self):
        return self.get_netdata()['services']

    def get_netdata_contexts(self):
        return self.get_netdata()['contexts']

    def get_netdata_versions(self):
        leaderdata = Node.parse_list(self.cli('leaderdata'))
        return (int(leaderdata['Data Version']), int(leaderdata['Stable Data Version']))

    def get_netdata_length(self):
        return self._cli_single_output('netdata length')

    def add_prefix(self, prefix, flags=None, prf=None):
        return self._cli_no_output('prefix add', prefix, flags, prf)

    def add_route(self, prefix, flags=None, prf=None):
        return self._cli_no_output('route add', prefix, flags, prf)

    def remove_prefix(self, prefix):
        return self._cli_no_output('prefix remove', prefix)

    def register_netdata(self):
        self._cli_no_output('netdata register')

    def get_netdata_full(self):
        return self._cli_single_output('netdata full')

    def reset_netdata_full(self):
        self._cli_no_output('netdata full reset')

    #- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
    # ping and counters

    def ping(self, address, size=0, count=1, verify_success=True):
        outputs = self.cli('ping', address, size, count)
        m = re.match(r'(\d+) packets transmitted, (\d+) packets received.', outputs[-1].strip())
        verify(m is not None)
        verify(int(m.group(1)) == count)
        if verify_success:
            verify(int(m.group(2)) == count)

    def get_mle_counter(self):
        return self.cli('counters mle')

    def get_br_counter_unicast_outbound_packets(self):
        outputs = self.cli('counters br')
        for line in outputs:
            m = re.match(r'Outbound Unicast: Packets (\d+) Bytes (\d+)', line.strip())
            if m is not None:
                counter = int(m.group(1))
                break
        else:
            verify(False)
        return counter

    #- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
    # Misc

    def get_mle_adv_imax(self):
        return self._cli_single_output('mleadvimax')

    #- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
    # UDP

    def udp_open(self):
        self._cli_no_output('udp open')

    def udp_close(self):
        self._cli_no_output('udp close')

    def udp_bind(self, address, port):
        self._cli_no_output('udp bind', address, port)

    def udp_send(self, address, port, text):
        self._cli_no_output('udp send', address, port, '-t', text)

    #- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
    # multiradio

    def multiradio_get_radios(self):
        return self._cli_single_output('multiradio')

    def multiradio_get_neighbor_list(self):
        return self.cli('multiradio neighbor list')

    #- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
    # SRP client

    def srp_client_start(self, server_address, server_port):
        self._cli_no_output('srp client start', server_address, server_port)

    def srp_client_stop(self):
        self._cli_no_output('srp client stop')

    def srp_client_get_state(self):
        return self._cli_single_output('srp client state', expected_outputs=['Enabled', 'Disabled'])

    def srp_client_get_auto_start_mode(self):
        return self._cli_single_output('srp client autostart', expected_outputs=['Enabled', 'Disabled'])

    def srp_client_enable_auto_start_mode(self):
        self._cli_no_output('srp client autostart enable')

    def srp_client_disable_auto_start_mode(self):
        self._cli_no_output('srp client autostart disable')

    def srp_client_get_server_address(self):
        return self._cli_single_output('srp client server address')

    def srp_client_get_server_port(self):
        return self._cli_single_output('srp client server port')

    def srp_client_get_host_state(self):
        return self._cli_single_output('srp client host state')

    def srp_client_set_host_name(self, name):
        self._cli_no_output('srp client host name', name)

    def srp_client_get_host_name(self):
        return self._cli_single_output('srp client host name')

    def srp_client_remove_host(self, remove_key=False, send_unreg_to_server=False):
        self._cli_no_output('srp client host remove', int(remove_key), int(send_unreg_to_server))

    def srp_client_clear_host(self):
        self._cli_no_output('srp client host clear')

    def srp_client_enable_auto_host_address(self):
        self._cli_no_output('srp client host address auto')

    def srp_client_set_host_address(self, *addrs):
        self._cli_no_output('srp client host address', *addrs)

    def srp_client_get_host_address(self):
        return self.cli('srp client host address')

    def srp_client_add_service(self,
                               instance_name,
                               service_name,
                               port,
                               priority=0,
                               weight=0,
                               txt_entries=[],
                               lease=0,
                               key_lease=0):
        txt_record = "".join(self._encode_txt_entry(entry) for entry in txt_entries)
        self._cli_no_output('srp client service add', instance_name, service_name, port, priority, weight, txt_record,
                            lease, key_lease)

    def srp_client_remove_service(self, instance_name, service_name):
        self._cli_no_output('srp client service remove', instance_name, service_name)

    def srp_client_clear_service(self, instance_name, service_name):
        self._cli_no_output('srp client service clear', instance_name, service_name)

    def srp_client_get_services(self):
        outputs = self.cli('srp client service')
        return [self._parse_srp_client_service(line) for line in outputs]

    def _encode_txt_entry(self, entry):
        """Encodes the TXT entry to the DNS-SD TXT record format as a HEX string.

           Example usage:
           self._encode_txt_entries(['abc'])     -> '03616263'
           self._encode_txt_entries(['def='])    -> '046465663d'
           self._encode_txt_entries(['xyz=XYZ']) -> '0778797a3d58595a'
        """
        return '{:02x}'.format(len(entry)) + "".join("{:02x}".format(ord(c)) for c in entry)

    def _parse_srp_client_service(self, line):
        """Parse one line of srp service list into a dictionary which
           maps string keys to string values.

           Example output for input
           'instance:\"%s\", name:\"%s\", state:%s, port:%d, priority:%d, weight:%d"'
           {
               'instance': 'my-service',
               'name': '_ipps._udp',
               'state': 'ToAdd',
               'port': '12345',
               'priority': '0',
               'weight': '0'
           }

           Note that value of 'port', 'priority' and 'weight' are represented
           as strings but not integers.
        """
        key_values = [word.strip().split(':') for word in line.split(', ')]
        return {key_value[0].strip(): key_value[1].strip('"') for key_value in key_values}

    #- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
    # SRP server

    def srp_server_get_state(self):
        return self._cli_single_output('srp server state', expected_outputs=['disabled', 'running', 'stopped'])

    def srp_server_get_addr_mode(self):
        return self._cli_single_output('srp server addrmode', expected_outputs=['unicast', 'anycast'])

    def srp_server_set_addr_mode(self, mode):
        self._cli_no_output('srp server addrmode', mode)

    def srp_server_get_anycast_seq_num(self):
        return self._cli_single_output('srp server seqnum')

    def srp_server_set_anycast_seq_num(self, seqnum):
        self._cli_no_output('srp server seqnum', seqnum)

    def srp_server_enable(self):
        self._cli_no_output('srp server enable')

    def srp_server_disable(self):
        self._cli_no_output('srp server disable')

    def srp_server_set_lease(self, min_lease, max_lease, min_key_lease, max_key_lease):
        self._cli_no_output('srp server lease', min_lease, max_lease, min_key_lease, max_key_lease)

    def srp_server_get_hosts(self):
        """Returns the host list on the SRP server as a list of property
           dictionary.

           Example output:
           [{
               'fullname': 'my-host.default.service.arpa.',
               'name': 'my-host',
               'deleted': 'false',
               'addresses': ['2001::1', '2001::2']
           }]
        """
        outputs = self.cli('srp server host')
        host_list = []
        while outputs:
            host = {}
            host['fullname'] = outputs.pop(0).strip()
            host['name'] = host['fullname'].split('.')[0]
            host['deleted'] = outputs.pop(0).strip().split(':')[1].strip()
            if host['deleted'] == 'true':
                host_list.append(host)
                continue
            addresses = outputs.pop(0).strip().split('[')[1].strip(' ]').split(',')
            map(str.strip, addresses)
            host['addresses'] = [addr for addr in addresses if addr]
            host_list.append(host)
        return host_list

    def srp_server_get_host(self, host_name):
        """Returns host on the SRP server that matches given host name.

           Example usage:
           self.srp_server_get_host("my-host")
        """
        for host in self.srp_server_get_hosts():
            if host_name == host['name']:
                return host

    def srp_server_get_services(self):
        """Returns the service list on the SRP server as a list of property
           dictionary.

           Example output:
           [{
               'fullname': 'my-service._ipps._tcp.default.service.arpa.',
               'instance': 'my-service',
               'name': '_ipps._tcp',
               'deleted': 'false',
               'port': '12345',
               'priority': '0',
               'weight': '0',
               'ttl': '7200',
               'lease': '7200',
               'key-lease', '1209600',
               'TXT': ['abc=010203'],
               'host_fullname': 'my-host.default.service.arpa.',
               'host': 'my-host',
               'addresses': ['2001::1', '2001::2']
           }]

           Note that the TXT data is output as a HEX string.
        """
        outputs = self.cli('srp server service')
        service_list = []
        while outputs:
            service = {}
            service['fullname'] = outputs.pop(0).strip()
            name_labels = service['fullname'].split('.')
            service['instance'] = name_labels[0]
            service['name'] = '.'.join(name_labels[1:3])
            service['deleted'] = outputs.pop(0).strip().split(':')[1].strip()
            if service['deleted'] == 'true':
                service_list.append(service)
                continue
            # 'subtypes', port', 'priority', 'weight', 'ttl', 'lease', 'key-lease'
            for i in range(0, 7):
                key_value = outputs.pop(0).strip().split(':')
                service[key_value[0].strip()] = key_value[1].strip()
            txt_entries = outputs.pop(0).strip().split('[')[1].strip(' ]').split(',')
            txt_entries = map(str.strip, txt_entries)
            service['TXT'] = [txt for txt in txt_entries if txt]
            service['host_fullname'] = outputs.pop(0).strip().split(':')[1].strip()
            service['host'] = service['host_fullname'].split('.')[0]
            addresses = outputs.pop(0).strip().split('[')[1].strip(' ]').split(',')
            addresses = map(str.strip, addresses)
            service['addresses'] = [addr for addr in addresses if addr]
            service_list.append(service)
        return service_list

    def srp_server_get_service(self, instance_name, service_name):
        """Returns service on the SRP server that matches given instance
           name and service name.

           Example usage:
           self.srp_server_get_service("my-service", "_ipps._tcp")
        """
        for service in self.srp_server_get_services():
            if (instance_name == service['instance'] and service_name == service['name']):
                return service

    #- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
    # br

    def br_init(self, if_inex, is_running):
        self._cli_no_output('br init', if_inex, is_running)

    def br_enable(self):
        self._cli_no_output('br enable')

    def br_disable(self):
        self._cli_no_output('br disable')

    def br_get_state(self):
        return self._cli_single_output('br state')

    def br_get_routeprf(self):
        return self._cli_single_output('br routeprf')

    def br_set_routeprf(self, prf):
        self._cli_no_output('br routeprf', prf)

    def br_clear_routeprf(self):
        self._cli_no_output('br routeprf clear')

    # ------------------------------------------------------------------------------------------------------------------
    # Helper methods

    def form(self, network_name=None, network_key=None, channel=None, panid=0x1234, xpanid=None):
        self._cli_no_output('dataset init new')
        self._cli_no_output('dataset panid', panid)
        if network_name is not None:
            self._cli_no_output('dataset networkname', network_name)
        if network_key is not None:
            self._cli_no_output('dataset networkkey', network_key)
        if channel is not None:
            self._cli_no_output('dataset channel', channel)
        if xpanid is not None:
            self._cli_no_output('dataset extpanid', xpanid)
        self._cli_no_output('dataset commit active')
        self.set_mode('rdn')
        self.interface_up()
        self.thread_start()
        verify_within(_check_node_is_leader, self._WAIT_TIME, arg=self)

    def join(self, node, type=JOIN_TYPE_ROUTER):
        self._cli_no_output('dataset clear')
        self._cli_no_output('dataset networkname', node.get_network_name())
        self._cli_no_output('dataset networkkey', node.get_network_key())
        self._cli_no_output('dataset channel', node.get_channel())
        self._cli_no_output('dataset panid', node.get_panid())
        self._cli_no_output('dataset commit active')
        if type == JOIN_TYPE_END_DEVICE:
            self.set_mode('rn')
        elif type == JOIN_TYPE_SLEEPY_END_DEVICE:
            self.set_mode('-')
        elif type == JOIN_TYPE_REED:
            self.set_mode('rdn')
            self.set_router_eligible('disable')
        else:
            self.set_mode('rdn')
            self.set_router_selection_jitter(1)
        self.interface_up()
        self.thread_start()
        if type == JOIN_TYPE_ROUTER:
            verify_within(_check_node_is_router, self._WAIT_TIME, arg=self)
        else:
            verify_within(_check_node_is_child, self._WAIT_TIME, arg=self)

    def allowlist_node(self, node):
        """Adds a given node to the allowlist of `self` and enables allowlisting on `self`"""
        self._cli_no_output('macfilter addr add', node.get_ext_addr())
        self._cli_no_output('macfilter addr allowlist')

    def un_allowlist_node(self, node):
        """Removes a given node (of node `Node) from the allowlist"""
        self._cli_no_output('macfilter addr remove', node.get_ext_addr())

    def set_macfilter_lqi_to_node(self, node, lqi):
        self._cli_no_output('macfilter rss add-lqi', node.get_ext_addr(), lqi)

    # ------------------------------------------------------------------------------------------------------------------
    # Radio nodeidfilter

    def nodeidfilter_clear(self, node):
        self._cli_no_output('nodeidfilter clear')

    def nodeidfilter_allow(self, node):
        self._cli_no_output('nodeidfilter allow', node.index)

    def nodeidfilter_deny(self, node):
        self._cli_no_output('nodeidfilter deny', node.index)

    # ------------------------------------------------------------------------------------------------------------------
    # Parsing helpers

    @classmethod
    def parse_table(cls, table_lines):
        verify(len(table_lines) >= 2)
        headers = cls.split_table_row(table_lines[0])
        info = []
        for row in table_lines[2:]:
            if row.strip() == '':
                continue
            fields = cls.split_table_row(row)
            verify(len(fields) == len(headers))
            info.append({headers[i]: fields[i] for i in range(len(fields))})
        return info

    @classmethod
    def split_table_row(cls, row):
        return [field.strip() for field in row.strip().split('|')[1:-1]]

    @classmethod
    def parse_list(cls, list_lines):
        result = {}
        for line in list_lines:
            fields = line.split(':', 1)
            result[fields[0].strip()] = fields[1].strip()
        return result

    @classmethod
    def parse_multiradio_neighbor_entry(cls, line):
        # Example: "ExtAddr:42aa94ad67229f14, RLOC16:0x9400, Radios:[15.4(245), TREL(255)]"
        result = {}
        for field in line.split(', ', 2):
            key_value = field.split(':')
            result[key_value[0]] = key_value[1]
        radios = {}
        for item in result['Radios'][1:-1].split(','):
            name, prf = item.strip().split('(')
            verify(prf.endswith(')'))
            radios[name] = int(prf[:-1])
        result['Radios'] = radios
        return result

    # ------------------------------------------------------------------------------------------------------------------
    # class methods

    @classmethod
    def finalize_all_nodes(cls):
        """Finalizes all previously created `Node` instances (stops the CLI process)"""
        for node in Node._all_nodes:
            node._finalize()

    @classmethod
    def set_time_speedup_factor(cls, factor):
        """Sets up the time speed up factor - should be set before creating any `Node` objects"""
        if len(Node._all_nodes) != 0:
            raise Node._NodeError('set_time_speedup_factor() cannot be called after creating a `Node`')
        Node._SPEED_UP_FACTOR = factor


def _check_node_is_leader(node):
    verify(node.get_state() == 'leader')


def _check_node_is_router(node):
    verify(node.get_state() == 'router')


def _check_node_is_child(node):
    verify(node.get_state() == 'child')


# ----------------------------------------------------------------------------------------------------------------------


class VerifyError(Exception):
    pass


_is_in_verify_within = False


def verify(condition):
    """Verifies that a `condition` is true, otherwise raises a VerifyError"""
    global _is_in_verify_within
    if not condition:
        calling_frame = inspect.currentframe().f_back
        error_message = 'verify() failed at line {} in "{}"'.format(calling_frame.f_lineno,
                                                                    calling_frame.f_code.co_filename)
        if not _is_in_verify_within:
            print(error_message)
        raise VerifyError(error_message)


def verify_within(condition_checker_func, wait_time, arg=None, delay_time=0.1):
    """Verifies that a given function `condition_checker_func` passes successfully within a given wait timeout.
       `wait_time` is maximum time waiting for condition_checker to pass (in seconds).
       `arg` is optional parameter and if it s not None, will be passed to `condition_checker_func()`
       `delay_time` specifies a delay interval added between failed attempts (in seconds).
    """
    global _is_in_verify_within
    start_time = time.time()
    old_is_in_verify_within = _is_in_verify_within
    _is_in_verify_within = True
    while True:
        try:
            if arg is None:
                condition_checker_func()
            else:
                condition_checker_func(arg)
        except VerifyError as e:
            if time.time() - start_time > wait_time:
                print('Took too long to pass the condition ({}>{} sec)'.format(time.time() - start_time, wait_time))
                print(e.message)
                raise e
        except BaseException:
            raise
        else:
            break
        if delay_time != 0:
            time.sleep(delay_time)
    _is_in_verify_within = old_is_in_verify_within
