def run_reboot_test(self, settings):
        """Runs a reboot test based on a given config.
            1. Setups up a network, associates the dut, and saves the network.
            2. Verifies the dut receives ip address(es).
            3. Verifies traffic between DUT and AP (IPerf client and server).
            4. Reboots (hard or soft) the device (dut or ap).
                - If the ap was rebooted, setup the same network again.
            5. Wait for reassociation or timeout.
            6. If reassocation occurs:
                - Verifies the dut receives ip address(es).
                - Verifies traffic between DUT and AP (IPerf client and server).
            7. Logs time to reconnect (or failure to reconnect)
            8. If stress testing, repeats steps 4 - 7 for N loops.

        Args:
            settings: dictionary containing the following values:
                reboot_device: string ('dut' or 'ap') of the device to reboot.
                reboot_type: string ('soft' or 'hard') of how to reboot the
                    reboot_device.
                band: string ('2g' or '5g') of band to setup.
                ipv4: True if using ipv4 (dhcp), else False.
                ipv6: True if using ipv6 (radvd), else False.

                Optional:
                    interrupt: if True, the DUT will be pinging the AP in a
                        parallel process when the reboot occurs. This is used to
                        compare reconnect times when idle to active.
                    test_name: name of the test, used when stress testing.
                    loops: number of times to perform test, used when stress
                        testing.

        Raises:
            ValueError, if ipv4 and ipv6 are both False
            ValueError, if band is not '2g' or '5g'
            ValueError, if reboot_device is not 'dut' or 'ap'
            ValueError, if reboot_type is not 'soft' or 'hard'

        """
        loops = settings.get('loops', 1)
        passed_count = 0
        ipv4 = settings['ipv4']
        ipv6 = settings['ipv6']
        reboot_device = settings['reboot_device']
        reboot_type = settings['reboot_type']
        band = settings['band']
        interrupt = settings.get('interrupt', None)

        # Validate test settings.
        if not ipv4 and not ipv6:
            raise ValueError('Either ipv4, ipv6, or both must be True.')
        if reboot_device != DUT and reboot_device != AP:
            raise ValueError('Invalid reboot device: %s' % reboot_device)
        if reboot_type != SOFT and reboot_type != HARD:
            raise ValueError('Invalid reboot type: %s' % reboot_type)
        if band != BAND_2G and band != BAND_5G:
            raise ValueError('Invalid band: %s' % band)

        self.setup_save_and_connect_to_network(self.ssid,
                                               band,
                                               ipv4=ipv4,
                                               ipv6=ipv6)
        self.wait_for_dut_network_connection(self.ssid)

        dut_test_interface = self.iperf_client_on_dut.test_interface
        if ipv4:
            self.wait_until_dut_gets_ipv4_addr(dut_test_interface)
        if ipv6:
            self.wait_until_dut_gets_ipv6_addr(dut_test_interface)

        self.iperf_server_on_ap = self.setup_iperf_server_on_ap(band)
        self.iperf_server_on_ap.start()

        if ipv4:
            self.verify_traffic_between_dut_and_ap(self.iperf_server_on_ap,
                                                   self.iperf_client_on_dut)
        if ipv6:
            self.verify_traffic_between_dut_and_ap(self.iperf_server_on_ap,
                                                   self.iperf_client_on_dut,
                                                   ip_version=IPV6)

        # Looping reboots for stress testing
        for run in range(loops):
            run += 1
            self.log.info('Starting run %s of %s.' % (run, loops))

            # Ping from DUT to AP during AP reboot
            if interrupt:
                if ipv4:
                    self.start_dut_ping_process(self.iperf_server_on_ap)
                if ipv6:
                    self.start_dut_ping_process(self.iperf_server_on_ap,
                                                ip_version=IPV6)

            # DUT reboots
            if reboot_device == DUT:
                if type(self.iperf_client_on_dut
                        ) == iperf_client.IPerfClientOverSsh:
                    self.iperf_client_on_dut.close_ssh()
                if reboot_type == SOFT:
                    self.dut.device.reboot()
                elif reboot_type == HARD:
                    self.dut.hard_power_cycle(self.pdu_devices)

            # AP reboots
            elif reboot_device == AP:
                if reboot_type == SOFT:
                    self.log.info('Cleanly stopping ap.')
                    self.access_point.stop_all_aps()
                elif reboot_type == HARD:
                    self.iperf_server_on_ap.close_ssh()
                    self.access_point.hard_power_cycle(self.pdu_devices)
                self.setup_ap(self.ssid, band, ipv4=ipv4, ipv6=ipv6)

            self.prepare_dut_for_reconnection()
            uptime = time.time()
            try:
                self.wait_for_dut_network_connection(self.ssid)
                time_to_reconnect = time.time() - uptime
                if ipv4:
                    self.wait_until_dut_gets_ipv4_addr(dut_test_interface)
                if ipv6:
                    self.wait_until_dut_gets_ipv6_addr(dut_test_interface)
                self.iperf_server_on_ap.start()

                if ipv4:
                    self.verify_traffic_between_dut_and_ap(
                        self.iperf_server_on_ap, self.iperf_client_on_dut)
                if ipv6:
                    self.verify_traffic_between_dut_and_ap(
                        self.iperf_server_on_ap,
                        self.iperf_client_on_dut,
                        ip_version=IPV6)

            except ConnectionError as err:
                self.log_and_continue(run, error=err)
            else:
                passed_count += 1
                self.log_and_continue(run, time_to_reconnect=time_to_reconnect)

        if passed_count == loops:
            asserts.explicit_pass(
                'Test Summary: device successfully reconnected to network %s '
                '%s/%s times.' % (self.ssid, passed_count, loops))

        else:
            asserts.fail(
                'Test Summary: device failed reconnection test. Reconnected to '
                'network %s %s/%s times.' % (self.ssid, passed_count, loops))
示例#2
0
 def wait_channel_ready(self):
     future = grpc.channel_ready_future(self.grpc_channel)
     try:
         future.result(timeout=self.WAIT_CHANNEL_READY_TIMEOUT_SECONDS)
     except grpc.FutureTimeoutError:
         asserts.fail("[%s] wait channel ready timeout" % self.label)
示例#3
0
 def test_func(self):
     asserts.fail(MSG_EXPECTED_EXCEPTION, extras=MOCK_EXTRA)
     never_call()
示例#4
0
    def test_ipv6_tethering(self):
        """ IPv6 tethering test

        Steps:
            1. Start wifi tethering on hotspot device
            2. Verify IPv6 address on hotspot device (VZW & TMO only)
            3. Connect tethered device to hotspot device
            4. Verify IPv6 address on the client's link properties (VZW only)
            5. Verify ping on client using ping6 which should pass (VZW only)
            6. Disable mobile data on provider and verify that link properties
               does not have IPv6 address and default route (VZW only)
        """
        # Start wifi tethering on the hotspot device
        wutils.toggle_wifi_off_and_on(self.hotspot_device)
        self._start_wifi_tethering()

        # Verify link properties on hotspot device
        self.log.info("Check IPv6 properties on the hotspot device. "
                      "Verizon & T-mobile should have IPv6 in link properties")
        self._verify_ipv6_tethering(self.hotspot_device)

        # Connect the client to the SSID
        wutils.wifi_connect(self.tethered_devices[0], self.network)

        # Need to wait atleast 2 seconds for IPv6 address to
        # show up in the link properties
        time.sleep(WAIT_TIME)

        # Verify link properties on tethered device
        self.log.info("Check IPv6 properties on the tethered device. "
                      "Device should have IPv6 if carrier is Verizon")
        self._verify_ipv6_tethering(self.tethered_devices[0])

        # Verify ping6 on tethered device
        ping_result = self._verify_ping(self.tethered_devices[0],
                                        wutils.DEFAULT_PING_ADDR, True)
        if self._supports_ipv6_tethering(self.hotspot_device):
            asserts.assert_true(ping_result, "Ping6 failed on the client")
        else:
            asserts.assert_true(not ping_result, "Ping6 failed as expected")

        # Disable mobile data on hotspot device
        # and verify the link properties on tethered device
        self.log.info("Disabling mobile data to verify ipv6 default route")
        self.hotspot_device.droid.telephonyToggleDataConnection(False)
        asserts.assert_equal(
            self.hotspot_device.droid.telephonyGetDataConnectionState(),
            tel_defines.DATA_STATE_CONNECTED, "Could not disable cell data")

        time.sleep(
            WAIT_TIME)  # wait until the IPv6 is removed from link properties

        result = self.tethered_devices[
            0].droid.connectivityHasIPv6DefaultRoute()
        self.hotspot_device.droid.telephonyToggleDataConnection(True)
        if result:
            asserts.fail(
                "Found IPv6 default route in link properties:Data off")
        self.log.info("Did not find IPv6 address in link properties")

        # Disable wifi tethering
        wutils.stop_wifi_tethering(self.hotspot_device)
示例#5
0
    def pass_fail_check_rssi_accuracy(self, postprocessed_results,
                                      rssi_under_test, absolute_accuracy):
        """Check the test result and decide if it passed or failed.

        Checks the RSSI test result and compares and compute its deviation from
        the predicted RSSI. This computation is done for all reported RSSI
        values. The test fails if any of the RSSI values specified in
        rssi_under_test have an average error beyond what is specified in the
        configuration file.

        Args:
            postprocessed_results: compiled arrays of RSSI measurements
            rssi_under_test: list of RSSIs under test, i.e., can cause test to
            fail
            absolute_accuracy: boolean indicating whether to look at absolute
            RSSI accuracy, or centered RSSI accuracy. Centered accuracy is
            computed after systematic RSSI shifts are removed.
        """
        test_failed = False
        test_message = ""
        if absolute_accuracy:
            error_type = "absolute"
        else:
            error_type = "centered"

        for key, val in postprocessed_results.items():
            # Compute the error metrics ignoring invalid RSSI readings
            # If all readings invalid, set error to RSSI_ERROR_VAL
            if "rssi" in key and "predicted" not in key:
                filtered_error = [x for x in val["error"] if not math.isnan(x)]
                if filtered_error:
                    avg_shift = statistics.mean(filtered_error)
                    if absolute_accuracy:
                        avg_error = statistics.mean(
                            [abs(x) for x in filtered_error])
                    else:
                        avg_error = statistics.mean(
                            [abs(x - avg_shift) for x in filtered_error])
                else:
                    avg_error = RSSI_ERROR_VAL
                    avg_shift = RSSI_ERROR_VAL
                rssi_failure = (avg_error > self.test_params["abs_tolerance"]
                                ) or math.isnan(avg_error)
                if rssi_failure and key in rssi_under_test:
                    test_message = test_message + (
                        "{} failed. Average {} error is {:.2f} dB. "
                        "Average shift is {:.2f} dB.\n").format(
                            key, error_type, avg_error, avg_shift)
                    test_failed = True
                elif rssi_failure:
                    test_message = test_message + (
                        "{} failed (ignored). Average {} error is {:.2f} dB. "
                        "Average shift is {:.2f} dB.\n").format(
                            key, error_type, avg_error, avg_shift)
                else:
                    test_message = test_message + (
                        "{} passed. Average {} error is {:.2f} dB. "
                        "Average shift is {:.2f} dB.\n").format(
                            key, error_type, avg_error, avg_shift)

        if test_failed:
            asserts.fail(test_message)
        asserts.explicit_pass(test_message)
示例#6
0
 def test_something(self):
     asserts.fail(MSG_EXPECTED_EXCEPTION, extras=MOCK_EXTRA)
示例#7
0
    def run_iperf_max_ndi_aware_only(self, sec_configs, results):
        """Measure iperf performance on multiple NDPs between 2 devices using
    different security configurations (and hence different NDIs). Test with
    Aware enabled and no infrastructure connection - i.e. device is not
    associated to an AP.

    The security configuration can be:
    - None: open
    - String: passphrase
    - otherwise: PMK (byte array)

    Args:
      sec_configs: list of security configurations
      results: Dictionary into which to place test results.
    """
        init_dut = self.android_devices[0]
        init_dut.pretty_name = "Initiator"
        resp_dut = self.android_devices[1]
        resp_dut.pretty_name = "Responder"

        asserts.skip_if(
            init_dut.aware_capabilities[aconsts.CAP_MAX_NDI_INTERFACES] <
            len(sec_configs)
            or resp_dut.aware_capabilities[aconsts.CAP_MAX_NDI_INTERFACES] <
            len(sec_configs),
            "Initiator or Responder do not support multiple NDIs")

        init_id, init_mac = autils.attach_with_identity(init_dut)
        resp_id, resp_mac = autils.attach_with_identity(resp_dut)

        # wait for for devices to synchronize with each other - there are no other
        # mechanisms to make sure this happens for OOB discovery (except retrying
        # to execute the data-path request)
        time.sleep(autils.WAIT_FOR_CLUSTER)

        resp_req_keys = []
        init_req_keys = []
        resp_aware_ifs = []
        init_aware_ifs = []
        resp_aware_ipv6s = []
        init_aware_ipv6s = []

        for sec in sec_configs:
            # Responder: request network
            resp_req_key = autils.request_network(
                resp_dut,
                autils.get_network_specifier(resp_dut, resp_id,
                                             aconsts.DATA_PATH_RESPONDER,
                                             init_mac, sec))
            resp_req_keys.append(resp_req_key)

            # Initiator: request network
            init_req_key = autils.request_network(
                init_dut,
                autils.get_network_specifier(init_dut, init_id,
                                             aconsts.DATA_PATH_INITIATOR,
                                             resp_mac, sec))
            init_req_keys.append(init_req_key)

            # Wait for network
            init_net_event = autils.wait_for_event_with_keys(
                init_dut, cconsts.EVENT_NETWORK_CALLBACK, autils.EVENT_TIMEOUT,
                (cconsts.NETWORK_CB_KEY_EVENT,
                 cconsts.NETWORK_CB_LINK_PROPERTIES_CHANGED),
                (cconsts.NETWORK_CB_KEY_ID, init_req_key))
            resp_net_event = autils.wait_for_event_with_keys(
                resp_dut, cconsts.EVENT_NETWORK_CALLBACK, autils.EVENT_TIMEOUT,
                (cconsts.NETWORK_CB_KEY_EVENT,
                 cconsts.NETWORK_CB_LINK_PROPERTIES_CHANGED),
                (cconsts.NETWORK_CB_KEY_ID, resp_req_key))

            resp_aware_ifs.append(
                resp_net_event["data"][cconsts.NETWORK_CB_KEY_INTERFACE_NAME])
            init_aware_ifs.append(
                init_net_event["data"][cconsts.NETWORK_CB_KEY_INTERFACE_NAME])

            resp_aware_ipv6s.append(
                autils.get_ipv6_addr(resp_dut, resp_aware_ifs[-1]))
            init_aware_ipv6s.append(
                autils.get_ipv6_addr(init_dut, init_aware_ifs[-1]))

        self.log.info("Initiator interfaces/ipv6: %s / %s", init_aware_ifs,
                      init_aware_ipv6s)
        self.log.info("Responder interfaces/ipv6: %s / %s", resp_aware_ifs,
                      resp_aware_ipv6s)

        # create threads, start them, and wait for all to finish
        base_port = 5000
        q = queue.Queue()
        threads = []
        for i in range(len(sec_configs)):
            threads.append(
                threading.Thread(target=self.run_iperf,
                                 args=(q, init_dut, resp_dut,
                                       resp_aware_ifs[i], init_aware_ipv6s[i],
                                       base_port + i)))

        for thread in threads:
            thread.start()

        for thread in threads:
            thread.join()

        # release requests
        for resp_req_key in resp_req_keys:
            resp_dut.droid.connectivityUnregisterNetworkCallback(resp_req_key)
        for init_req_key in init_req_keys:
            init_dut.droid.connectivityUnregisterNetworkCallback(init_req_key)

        # collect data
        for i in range(len(sec_configs)):
            results[i] = {}
            result, data = q.get()
            asserts.assert_true(
                result, "Failure starting/running iperf3 in client mode")
            self.log.debug(pprint.pformat(data))
            data_json = json.loads("".join(data))
            if "error" in data_json:
                asserts.fail("iperf run failed: %s" % data_json["error"],
                             extras=data_json)
            results[i]["tx_rate"] = data_json["end"]["sum_sent"][
                "bits_per_second"]
            results[i]["rx_rate"] = data_json["end"]["sum_received"][
                "bits_per_second"]
            self.log.info("iPerf3: Sent = %d bps Received = %d bps",
                          results[i]["tx_rate"], results[i]["rx_rate"])
    def run(self, test_names=None):
        """Runs test cases within a test class by the order they appear in the
        execution list.

        One of these test cases lists will be executed, shown here in priority
        order:
        1. The test_names list, which is passed from cmd line. Invalid names
           are guarded by cmd line arg parsing.
        2. The self.tests list defined in test class. Invalid names are
           ignored.
        3. All function that matches test case naming convention in the test
           class.

        Args:
            test_names: A list of string that are test case names requested in
                cmd line.

        Returns:
            The test results object of this class.
        """
        self.log.info("==========> %s <==========", self.TAG)
        # Devise the actual test cases to run in the test class.
        if not test_names:
            if self.tests:
                # Specified by run list in class.
                test_names = list(self.tests)
            else:
                # No test case specified by user, execute all in the test class
                test_names = self._get_all_test_names()
        self.results.requested = test_names
        tests = self._get_test_funcs(test_names)
        # A TestResultRecord used for when setup_class fails.
        class_record = records.TestResultRecord("setup_class", self.TAG)
        class_record.test_begin()
        # Setup for the class.
        try:
            if self._setup_class() is False:
                asserts.fail("Failed to setup %s." % self.TAG)
        except Exception as e:
            self.log.exception("Failed to setup %s.", self.TAG)
            class_record.test_fail(e)
            self._exec_procedure_func(self._on_fail, class_record)
            self._exec_func(self.teardown_class)
            self.results.fail_class(class_record)
            return self.results
        # Run tests in order.
        try:
            for test_name, test_func in tests:
                self.exec_one_testcase(test_name, test_func, self.cli_args)
            return self.results
        except signals.TestAbortClass:
            return self.results
        except signals.TestAbortAll as e:
            # Piggy-back test results on this exception object so we don't lose
            # results from this test class.
            setattr(e, "results", self.results)
            raise e
        finally:
            self._exec_func(self.teardown_class)
            self.log.info("Summary for test class %s: %s", self.TAG,
                          self.results.summary_str())
示例#9
0
    def test_nan_data_path(self):
        """Perform NAN configuration, discovery, data-path setup, and data
        transfer.

        Configuration: 2 devices, one acting as Publisher (P) and the
        other as Subscriber (S)

        Logical steps:
          * P & S initiate NAN clustering (if not already up)
          * P & S wait for NAN connection confirmation
          * P starts publishing
          * S starts subscribing
          * S waits for a match (discovery) notification
          * S sends a message to P
          * P waits for message
          * P creates a NAN network to S as RESPONDER
          * P sends a message to S
          * S waits for message
          * S creates a NAN network to P as INITIATOR (order important!)
          * Both P & S wait for events confirming network set up
          * P registers NSD service
          * S discovers NSD service and obtains P's IP address
          * run iperf3 between P (server) and S (client)
          * unregister network callback on S
        """
        # Configure Test
        self.publisher = self.android_devices[0]
        self.subscriber = self.android_devices[1]

        sub2pub_msg = "Get ready!"
        pub2sub_msg = "Ready!"
        test_token = "Token / <some magic string>"

        # Start Test
        pub_connect_id = self.exec_connect(self.publisher,
                                           self.config_request1, "publisher")
        sub_connect_id = self.exec_connect(self.subscriber,
                                           self.config_request2, "subscriber")

        # Discovery: publish + subscribe + wait for match
        pub_id = self.publisher.droid.wifiNanPublish(pub_connect_id,
                                                     self.publish_config)
        sub_id = self.subscriber.droid.wifiNanSubscribe(
            sub_connect_id, self.subscribe_config)

        def filter_callbacks(event, key, name):
            return event['data'][key] == name

        try:
            event_sub_match = self.subscriber.ed.pop_event(
                nan_const.SESSION_CB_ON_SERVICE_DISCOVERED, EVENT_TIMEOUT)
            self.log.info('%s: %s', nan_const.SESSION_CB_ON_SERVICE_DISCOVERED,
                          event_sub_match['data'])
        except queue.Empty:
            asserts.fail('Timed out while waiting for %s on Subscriber' %
                         nan_const.SESSION_CB_ON_SERVICE_DISCOVERED)
        self.log.debug(event_sub_match)

        # S sends message to P
        self.reliable_tx(self.subscriber, sub_id,
                         event_sub_match['data']['peerId'], sub2pub_msg)

        try:
            event_pub_rx = self.publisher.ed.pop_event(
                nan_const.SESSION_CB_ON_MESSAGE_RECEIVED, EVENT_TIMEOUT)
        except queue.Empty:
            asserts.fail('Timed out while waiting for %s on publisher' %
                         nan_const.SESSION_CB_ON_MESSAGE_RECEIVED)
        self.log.info('%s: %s', nan_const.SESSION_CB_ON_MESSAGE_RECEIVED,
                      event_pub_rx['data'])
        asserts.assert_equal(event_pub_rx['data']['messageAsString'],
                             sub2pub_msg,
                             "Subscriber -> publisher message corrupted")

        # P requests a NAN network as RESPONDER
        pub_ns = self.publisher.droid.wifiNanCreateNetworkSpecifier(
            nan_const.DATA_PATH_RESPONDER, pub_id,
            event_pub_rx['data']['peerId'], test_token)
        self.log.info("Publisher network specifier - '%s'", pub_ns)
        self.network_req['NetworkSpecifier'] = pub_ns
        pub_req_key = self.publisher.droid.connectivityRequestNetwork(
            self.network_req)

        # P sends message to S
        self.reliable_tx(self.publisher, pub_id,
                         event_pub_rx['data']['peerId'], pub2sub_msg)

        try:
            event_sub_rx = self.subscriber.ed.pop_event(
                nan_const.SESSION_CB_ON_MESSAGE_RECEIVED, EVENT_TIMEOUT)
        except queue.Empty:
            asserts.fail('Timed out while waiting for %s on subscriber' %
                         nan_const.SESSION_CB_ON_MESSAGE_RECEIVED)
        self.log.info('%s: %s', nan_const.SESSION_CB_ON_MESSAGE_RECEIVED,
                      event_sub_rx['data'])
        asserts.assert_equal(event_sub_rx['data']['messageAsString'],
                             pub2sub_msg,
                             "Publisher -> subscriber message corrupted")

        # S requests a NAN network as INITIATOR
        sub_ns = self.subscriber.droid.wifiNanCreateNetworkSpecifier(
            nan_const.DATA_PATH_INITIATOR, sub_id,
            event_sub_rx['data']['peerId'], test_token)
        self.log.info("Subscriber network specifier - '%s'", sub_ns)
        self.network_req['NetworkSpecifier'] = sub_ns
        sub_req_key = self.subscriber.droid.connectivityRequestNetwork(
            self.network_req)

        # Wait until both S and P get confirmation that network formed
        try:
            event_network = self.subscriber.ed.wait_for_event(
                con_const.EVENT_NETWORK_CALLBACK,
                filter_callbacks,
                EVENT_TIMEOUT,
                key=con_const.NETWORK_CB_KEY_EVENT,
                name=con_const.NETWORK_CB_LINK_PROPERTIES_CHANGED)
            self.log.info('Subscriber %s: %s',
                          con_const.EVENT_NETWORK_CALLBACK,
                          event_network['data'])
        except queue.Empty:
            asserts.fail('Timed out while waiting for %s/%s on Subscriber' %
                         (con_const.EVENT_NETWORK_CALLBACK,
                          con_const.NETWORK_CB_LINK_PROPERTIES_CHANGED))
        self.log.debug(event_network)
        sub_nan_if = event_network['data']['interfaceName']

        try:
            event_network = self.publisher.ed.wait_for_event(
                con_const.EVENT_NETWORK_CALLBACK,
                filter_callbacks,
                EVENT_TIMEOUT,
                key=con_const.NETWORK_CB_KEY_EVENT,
                name=con_const.NETWORK_CB_LINK_PROPERTIES_CHANGED)
            self.log.info('Publisher %s: %s', con_const.EVENT_NETWORK_CALLBACK,
                          event_network['data'])
        except queue.Empty:
            asserts.fail('Timed out while waiting for %s/%s on Publisher' %
                         (con_const.EVENT_NETWORK_CALLBACK,
                          con_const.NETWORK_CB_LINK_PROPERTIES_CHANGED))
        self.log.debug(event_network)

        try:
            # P registers NSD service (i.e. starts publishing)
            nsd_reg = self.publisher.droid.nsdRegisterService(
                self.nsd_service_info)
            try:
                event_nsd = self.publisher.ed.wait_for_event(
                    nsd_const.REG_LISTENER_EVENT,
                    filter_callbacks,
                    EVENT_TIMEOUT,
                    key=nsd_const.REG_LISTENER_CALLBACK,
                    name=nsd_const.REG_LISTENER_EVENT_ON_SERVICE_REGISTERED)
                self.log.info(
                    'Publisher %s: %s',
                    nsd_const.REG_LISTENER_EVENT_ON_SERVICE_REGISTERED,
                    event_nsd['data'])
            except queue.Empty:
                asserts.fail(
                    'Timed out while waiting for %s on Publisher' %
                    nsd_const.REG_LISTENER_EVENT_ON_SERVICE_REGISTERED)

            # S starts NSD discovery
            nsd_discovery = self.subscriber.droid.nsdDiscoverServices(
                self.nsd_service_info[nsd_const.NSD_SERVICE_INFO_SERVICE_TYPE])
            try:
                event_nsd = self.subscriber.ed.wait_for_event(
                    nsd_const.DISCOVERY_LISTENER_EVENT,
                    filter_callbacks,
                    EVENT_TIMEOUT,
                    key=nsd_const.DISCOVERY_LISTENER_DATA_CALLBACK,
                    name=nsd_const.DISCOVERY_LISTENER_EVENT_ON_SERVICE_FOUND)
                self.log.info(
                    'Subscriber %s: %s',
                    nsd_const.DISCOVERY_LISTENER_EVENT_ON_SERVICE_FOUND,
                    event_nsd['data'])
            except queue.Empty:
                asserts.fail(
                    'Timed out while waiting for %s on Subscriber' %
                    nsd_const.DISCOVERY_LISTENER_EVENT_ON_SERVICE_FOUND)

            # S resolves IP address of P from NSD service discovery
            self.subscriber.droid.nsdResolveService(event_nsd['data'])
            try:
                event_nsd = self.subscriber.ed.wait_for_event(
                    nsd_const.RESOLVE_LISTENER_EVENT,
                    filter_callbacks,
                    EVENT_TIMEOUT,
                    key=nsd_const.RESOLVE_LISTENER_DATA_CALLBACK,
                    name=nsd_const.RESOLVE_LISTENER_EVENT_ON_SERVICE_RESOLVED)
                self.log.info(
                    'Subscriber %s: %s',
                    nsd_const.RESOLVE_LISTENER_EVENT_ON_SERVICE_RESOLVED,
                    event_nsd['data'])
            except queue.Empty:
                asserts.fail(
                    'Timed out while waiting for %s on Subscriber' %
                    nsd_const.RESOLVE_LISTENER_EVENT_ON_SERVICE_RESOLVED)

            # mDNS returns first character as '/' - strip out to get clean IPv6
            pub_ipv6_from_nsd = event_nsd['data'][
                nsd_const.NSD_SERVICE_INFO_HOST][1:]
        finally:
            # Stop NSD
            if nsd_reg is not None:
                self.publisher.droid.nsdUnregisterService(nsd_reg)
            if nsd_discovery is not None:
                self.subscriber.droid.nsdStopServiceDiscovery(nsd_discovery)

        # P starts iPerf server
        result, data = self.publisher.run_iperf_server("-D")
        asserts.assert_true(result, "Can't start iperf3 server")

        # S starts iPerf client
        result, data = self.subscriber.run_iperf_client(
            "%s%%%s" % (pub_ipv6_from_nsd, sub_nan_if), "-6 -J")
        self.log.debug(data)
        asserts.assert_true(result,
                            "Failure starting/running iperf3 in client mode")
        self.log.debug(pprint.pformat(data))
        data_json = json.loads(''.join(data))
        self.log.info('iPerf3: Sent = %d bps Received = %d bps',
                      data_json['end']['sum_sent']['bits_per_second'],
                      data_json['end']['sum_received']['bits_per_second'])

        # S terminates data-path (only have to do on one end)
        self.subscriber.droid.connectivityUnregisterNetworkCallback(
            sub_req_key)
示例#10
0
    def run_iperf_max_ndp_aware_only(self, results):
        """Measure iperf performance on the max number of concurrent OOB NDPs, with
    Aware enabled and no infrastructure connection - i.e. device is not
    associated to an AP.

    Note: the test requires MAX_NDP + 1 devices to be validated. If these are
    not available the test will fail.

    Args:
      results: Dictionary into which to place test results.
    """
        dut = self.android_devices[0]

        # get max NDP: using first available device (assumes all devices are the
        # same)
        max_ndp = dut.aware_capabilities[aconsts.CAP_MAX_NDP_SESSIONS]
        asserts.assert_true(
            len(self.android_devices) > max_ndp,
            'Needed %d devices to run the test, have %d' %
            (max_ndp + 1, len(self.android_devices)))

        # create all NDPs
        dut_aware_if = None
        dut_ipv6 = None
        peers_aware_ifs = []
        peers_ipv6s = []
        dut_requests = []
        peers_requests = []
        for i in range(max_ndp):
            (init_req_key, resp_req_key, init_aware_if, resp_aware_if,
             init_ipv6,
             resp_ipv6) = autils.create_oob_ndp(dut,
                                                self.android_devices[i + 1])
            self.log.info("Interface names: I=%s, R=%s", init_aware_if,
                          resp_aware_if)
            self.log.info("Interface addresses (IPv6): I=%s, R=%s", init_ipv6,
                          resp_ipv6)

            dut_requests.append(init_req_key)
            peers_requests.append(resp_req_key)
            if dut_aware_if is None:
                dut_aware_if = init_aware_if
            else:
                asserts.assert_equal(
                    dut_aware_if, init_aware_if,
                    "DUT (Initiator) interface changed on subsequent NDPs!?")
            if dut_ipv6 is None:
                dut_ipv6 = init_ipv6
            else:
                asserts.assert_equal(
                    dut_ipv6, init_ipv6,
                    "DUT (Initiator) IPv6 changed on subsequent NDPs!?")
            peers_aware_ifs.append(resp_aware_if)
            peers_ipv6s.append(resp_ipv6)

        # create threads, start them, and wait for all to finish
        base_port = 5000
        q = queue.Queue()
        threads = []
        for i in range(max_ndp):
            threads.append(
                threading.Thread(target=self.run_iperf,
                                 args=(q, dut, self.android_devices[i + 1],
                                       peers_aware_ifs[i], dut_ipv6,
                                       base_port + i)))

        for thread in threads:
            thread.start()

        for thread in threads:
            thread.join()

        # cleanup
        for i in range(max_ndp):
            dut.droid.connectivityUnregisterNetworkCallback(dut_requests[i])
            self.android_devices[
                i + 1].droid.connectivityUnregisterNetworkCallback(
                    peers_requests[i])

        # collect data
        for i in range(max_ndp):
            results[i] = {}
            result, data = q.get()
            asserts.assert_true(
                result, "Failure starting/running iperf3 in client mode")
            self.log.debug(pprint.pformat(data))
            data_json = json.loads("".join(data))
            if "error" in data_json:
                asserts.fail("iperf run failed: %s" % data_json["error"],
                             extras=data_json)
            results[i]["tx_rate"] = data_json["end"]["sum_sent"][
                "bits_per_second"]
            results[i]["rx_rate"] = data_json["end"]["sum_received"][
                "bits_per_second"]
            self.log.info("iPerf3: Sent = %d bps Received = %d bps",
                          results[i]["tx_rate"], results[i]["rx_rate"])
示例#11
0
    def test_nan_messaging(self):
        """Perform NAN configuration, discovery, and large message exchange.

        Configuration: 2 devices, one acting as Publisher (P) and the
        other as Subscriber (S)

        Logical steps:
          * P & S initiate NAN clustering (if not already up)
          * P & S wait for NAN connection confirmation
          * P starts publishing
          * S starts subscribing
          * S waits for a match (discovery) notification
          * S sends XX messages to P
          * S confirms that all XXX messages were transmitted
          * P confirms that all XXX messages are received
        """
        self.publisher = self.android_devices[0]
        self.subscriber = self.android_devices[1]
        num_async_messages = 100

        # Start Test
        pub_connect_id = self.exec_connect(self.publisher,
                                           self.config_request1, "publisher")
        sub_connect_id = self.exec_connect(self.subscriber,
                                           self.config_request2, "subscriber")

        pub_id = self.publisher.droid.wifiNanPublish(pub_connect_id,
                                                     self.publish_config)
        sub_id = self.subscriber.droid.wifiNanSubscribe(
            sub_connect_id, self.subscribe_config)

        try:
            event_sub_match = self.subscriber.ed.pop_event(
                nan_const.SESSION_CB_ON_SERVICE_DISCOVERED, EVENT_TIMEOUT)
            self.log.info('%s: %s', nan_const.SESSION_CB_ON_SERVICE_DISCOVERED,
                          event_sub_match['data'])
        except queue.Empty:
            asserts.fail('Timed out while waiting for %s on Subscriber' %
                         nan_const.SESSION_CB_ON_SERVICE_DISCOVERED)
        self.log.debug(event_sub_match)

        # send all messages at once
        for i in range(num_async_messages):
            self.msg_id = self.msg_id + 1
            self.subscriber.droid.wifiNanSendMessage(
                sub_id, event_sub_match['data']['peerId'], "msg %s" % i,
                self.msg_id, nan_const.MAX_TX_RETRIES)

        # wait for all messages to be transmitted correctly
        num_tx_ok = 0
        num_tx_fail = 0
        events_regex = '%s|%s' % (nan_const.SESSION_CB_ON_MESSAGE_SEND_FAILED,
                                  nan_const.SESSION_CB_ON_MESSAGE_SENT)
        while (num_tx_ok + num_tx_fail) < num_async_messages:
            try:
                events = self.subscriber.ed.pop_events(events_regex,
                                                       EVENT_TIMEOUT)

                for event in events:
                    if event['name'] == nan_const.SESSION_CB_ON_MESSAGE_SENT:
                        num_tx_ok = num_tx_ok + 1
                    if event[
                            'name'] == nan_const.SESSION_CB_ON_MESSAGE_SEND_FAILED:
                        num_tx_fail = num_tx_fail + 1
            except queue.Empty:
                self.log.warning(
                    'Timed out while waiting for %s on Subscriber'
                    ' - %d events received', events_regex,
                    num_tx_ok + num_tx_fail)
                break
        self.log.info('Transmission stats: %d success, %d fail', num_tx_ok,
                      num_tx_fail)

        # validate that all messages are received (not just the correct
        # number of messages - since on occassion there may be duplicates
        # received).
        num_received = 0
        num_unique_received = 0
        messages = {}
        while num_unique_received != num_async_messages:
            try:
                event = self.publisher.ed.pop_event(
                    nan_const.SESSION_CB_ON_MESSAGE_RECEIVED, EVENT_TIMEOUT)
                msg = event['data']['messageAsString']
                num_received = num_received + 1
                if msg not in messages:
                    num_unique_received = num_unique_received + 1
                    messages[msg] = 0
                messages[msg] = messages[msg] + 1
                self.log.debug('%s: %s',
                               nan_const.SESSION_CB_ON_MESSAGE_RECEIVED, msg)
            except queue.Empty:
                asserts.fail('Timed out while waiting for %s on Publisher: %d '
                             'messages received, %d unique message' %
                             (nan_const.SESSION_CB_ON_MESSAGE_RECEIVED,
                              num_received, num_unique_received))
        self.log.info('Reception stats: %d received (%d unique)', num_received,
                      num_unique_received)
        if num_received > num_unique_received:
            self.log.info('%d duplicate receptions of %d messages: %s',
                          num_received - num_unique_received, num_received,
                          messages)

        self.publisher.droid.wifiNanDestroyDiscoverySession(pub_id)
        self.subscriber.droid.wifiNanDestroyDiscoverySession(sub_id)
示例#12
0
    def run_nan_discovery_session(self, discovery_config):
        """Perform NAN configuration, discovery, and message exchange.

        Configuration: 2 devices, one acting as Publisher (P) and the
        other as Subscriber (S)

        Logical steps:
          * P & S initiate NAN clustering (if not already up)
          * P & S wait for NAN connection confirmation
          * P starts publishing
          * S starts subscribing
          * S waits for a match (discovery) notification
          * S sends a message to P, confirming that sent successfully
          * P waits for a message and confirms that received (uncorrupted)
          * P sends a message to S, confirming that sent successfully
          * S waits for a message and confirms that received (uncorrupted)

        Args:
            discovery_configs: Array of (publish_config, subscribe_config)

        Returns:
            True if discovery succeeds, else false.
        """
        # Configure Test
        self.publisher = self.android_devices[0]
        self.subscriber = self.android_devices[1]

        sub2pub_msg = "How are you doing? 你好嗎?"
        pub2sub_msg = "Doing ok - thanks! 做的不錯 - 謝謝!"

        # Start Test
        pub_connect_id = self.exec_connect(self.publisher,
                                           self.config_request1, "publisher")
        sub_connect_id = self.exec_connect(self.subscriber,
                                           self.config_request2, "subscriber")

        try:
            pub_id = self.publisher.droid.wifiNanPublish(
                pub_connect_id, discovery_config[0])
            sub_id = self.subscriber.droid.wifiNanSubscribe(
                sub_connect_id, discovery_config[1])

            try:
                event_sub_match = self.subscriber.ed.pop_event(
                    nan_const.SESSION_CB_ON_SERVICE_DISCOVERED, EVENT_TIMEOUT)
                self.log.info('%s: %s',
                              nan_const.SESSION_CB_ON_SERVICE_DISCOVERED,
                              event_sub_match['data'])
            except queue.Empty:
                asserts.fail('Timed out while waiting for %s on Subscriber' %
                             nan_const.SESSION_CB_ON_SERVICE_DISCOVERED)
            self.log.debug(event_sub_match)

            self.reliable_tx(self.subscriber, sub_id,
                             event_sub_match['data']['peerId'], sub2pub_msg)

            try:
                event_pub_rx = self.publisher.ed.pop_event(
                    nan_const.SESSION_CB_ON_MESSAGE_RECEIVED, EVENT_TIMEOUT)
                self.log.info('%s: %s',
                              nan_const.SESSION_CB_ON_MESSAGE_RECEIVED,
                              event_pub_rx['data'])
                asserts.assert_equal(
                    event_pub_rx['data']['messageAsString'], sub2pub_msg,
                    "Subscriber -> publisher message corrupted")
            except queue.Empty:
                asserts.fail('Timed out while waiting for %s on publisher' %
                             nan_const.SESSION_CB_ON_MESSAGE_RECEIVED)

            self.reliable_tx(self.publisher, pub_id,
                             event_pub_rx['data']['peerId'], pub2sub_msg)

            try:
                event_sub_rx = self.subscriber.ed.pop_event(
                    nan_const.SESSION_CB_ON_MESSAGE_RECEIVED, EVENT_TIMEOUT)
                self.log.info('%s: %s',
                              nan_const.SESSION_CB_ON_MESSAGE_RECEIVED,
                              event_sub_rx['data'])
                asserts.assert_equal(
                    event_sub_rx['data']['messageAsString'], pub2sub_msg,
                    "Publisher -> subscriber message corrupted")
            except queue.Empty:
                asserts.fail('Timed out while waiting for %s on subscriber' %
                             nan_const.SESSION_CB_ON_MESSAGE_RECEIVED)
        finally:
            self.publisher.droid.wifiNanDestroyDiscoverySession(pub_id)
            self.subscriber.droid.wifiNanDestroyDiscoverySession(sub_id)
示例#13
0
  def start_dpp_as_initiator_enrollee(self,
                                      security,
                                      use_mac,
                                      cause_timeout=False,
                                      invalid_config=False):
    """ Test Easy Connect (DPP) as initiator enrollee.

                1. Enable wifi, if needed
                2. Start DPP as responder-configurator on helper device
                3. Start DPP as initiator enrollee on dut
                4. Check if configuration received successfully
                5. Delete the URI from helper device
                6. Remove the config.

        Args:
            security: Security type, a string "SAE" or "PSK"
            use_mac: A boolean indicating whether to use the device's MAC
              address (if True) or use a Broadcast (if False).
            cause_timeout: Intentionally don't start the responder to cause a
              timeout
            invalid_config: Responder to intentionally send malformed
              configuration
    """
    if not self.dut.droid.wifiIsEasyConnectSupported():
      self.log.warning("Easy Connect is not supported on device!")
      return

    wutils.wifi_toggle_state(self.dut, True)

    if use_mac:
      mac = autils.get_mac_addr(self.helper_dev, "wlan0")
    else:
      mac = None

    # Generate a URI with default info and channel
    uri_id = self.gen_uri(self.helper_dev, mac=mac)

    # Get the URI. This is equal to scanning a QR code
    configurator_uri = self.get_uri(self.helper_dev, uri_id)

    if not cause_timeout:
      # Start DPP as an configurator-responder for STA on helper device
      ssid = self.start_responder_configurator(
          self.helper_dev, security=security, invalid_config=invalid_config)
    else:
      self.log.info(
          "Not starting a responder configurator on helper device, on purpose")
      ssid = self.DPP_TEST_SSID_PREFIX + utils.rand_ascii_str(8)

    self.log.info("Starting DPP in Enrollee-Initiator mode")

    # Start DPP as enrollee-initiator on dut
    self.dut.droid.startEasyConnectAsEnrolleeInitiator(configurator_uri)

    network_id = 0

    start_time = time.time()
    while time.time() < start_time + self.DPP_TEST_TIMEOUT:
      dut_event = self.dut.ed.pop_event(self.DPP_TEST_EVENT_DPP_CALLBACK,
                                        self.DPP_TEST_TIMEOUT)
      if dut_event[self.DPP_TEST_EVENT_DATA][
          self.DPP_TEST_MESSAGE_TYPE] == self.DPP_TEST_EVENT_ENROLLEE_SUCCESS:
        if cause_timeout or invalid_config:
          asserts.fail(
              "Unexpected DPP success, status code: %s" %
              dut_event[self.DPP_TEST_EVENT_DATA][self.DPP_TEST_MESSAGE_STATUS])
        else:
          self.dut.log.info("DPP Configuration received success")
          network_id = dut_event[self.DPP_TEST_EVENT_DATA][
              self.DPP_TEST_MESSAGE_NETWORK_ID]
          self.dut.log.info("NetworkID: %d" % network_id)
        break
      if dut_event[self.DPP_TEST_EVENT_DATA][
          self
          .DPP_TEST_MESSAGE_TYPE] == self.DPP_TEST_EVENT_CONFIGURATOR_SUCCESS:
        asserts.fail(
            "DPP failure, unexpected result: %s" %
            dut_event[self.DPP_TEST_EVENT_DATA][self.DPP_TEST_MESSAGE_STATUS])
        break
      if dut_event[self.DPP_TEST_EVENT_DATA][
          self.DPP_TEST_MESSAGE_TYPE] == self.DPP_TEST_EVENT_PROGRESS:
        self.dut.log.info("DPP progress event")
        val = dut_event[self.DPP_TEST_EVENT_DATA][self.DPP_TEST_MESSAGE_STATUS]
        if val == 0:
          self.dut.log.info("DPP Authentication success")
        elif val == 1:
          self.dut.log.info("DPP Response pending")
        continue
      if dut_event[self.DPP_TEST_EVENT_DATA][
          self.DPP_TEST_MESSAGE_TYPE] == self.DPP_TEST_EVENT_FAILURE:
        if cause_timeout or invalid_config:
          self.dut.log.info(
              "Error %s occurred, as expected" %
              dut_event[self.DPP_TEST_EVENT_DATA][self.DPP_TEST_MESSAGE_STATUS])
        else:
          asserts.fail(
              "DPP failure, status code: %s" %
              dut_event[self.DPP_TEST_EVENT_DATA][self.DPP_TEST_MESSAGE_STATUS])
        break
      asserts.fail("Unknown message received")

    # Clear all pending events.
    self.dut.ed.clear_all_events()

    # Stop responder
    self.stop_responder(self.helper_dev)

    # Delete URI
    self.del_uri(self.helper_dev, uri_id)

    if not (invalid_config or cause_timeout):
      # Check that the saved network is what we expect
      asserts.assert_true(
          self.check_network_config_saved(ssid, security, network_id),
          "Could not find the expected network: %s" % ssid)

      asserts.assert_true(
          self.forget_network(network_id),
          "Test network not deleted from configured networks.")
示例#14
0
  def start_dpp_as_initiator_configurator(self,
                                          security,
                                          use_mac,
                                          responder_chan="81/1",
                                          responder_freq=2412,
                                          net_role=DPP_TEST_NETWORK_ROLE_STA,
                                          cause_timeout=False,
                                          fail_authentication=False,
                                          invalid_uri=False):
    """ Test Easy Connect (DPP) as initiator configurator.

                1. Enable wifi, if needed
                2. Create and save a random config.
                3. Generate a URI using the helper device
                4. Start DPP as responder-enrollee on helper device
                5. Start DPP as initiator configurator on dut
                6. Check if configurator sent successfully
                7. Delete the URI from helper device
                8. Remove the config.

        Args:
            security: Security type, a string "SAE" or "PSK"
            use_mac: A boolean indicating whether to use the device's MAC
              address (if True) or use a Broadcast (if False).
            responder_chan: Responder channel to specify in the URI
            responder_freq: Frequency that the Responder would actually listen on.
              Note: To succeed, there must be a correlation between responder_chan, which is what
              the URI advertises, and responder_freq which is the actual frequency. See:
              https://en.wikipedia.org/wiki/List_of_WLAN_channels
            net_role: Network role, a string "sta" or "ap"
            cause_timeout: Intentionally don't start the responder to cause a
              timeout
            fail_authentication: Fail authentication by corrupting the
              responder's key
            invalid_uri: Use garbage string instead of a URI
    """
    if not self.dut.droid.wifiIsEasyConnectSupported():
      self.log.warning("Easy Connect is not supported on device!")
      return

    wutils.wifi_toggle_state(self.dut, True)
    test_network_id = self.create_and_save_wifi_network_config(security)

    if use_mac:
      mac = autils.get_mac_addr(self.helper_dev, "wlan0")
    else:
      mac = None

    if invalid_uri:
      enrollee_uri = "dskjgnkdjfgnkdsjfgnsDFGDIFGKDSJFGFDbgjdsnbkjdfnkbgsdfgFDSGSDfgesouhgureho" \
                     "iu3ht98368903434089ut4958763094u0934ujg094j5oifegjfds"
    else:
      # Generate a URI with default info and channel
      uri_id = self.gen_uri(self.helper_dev, chan=responder_chan, mac=mac)

      # Get the URI. This is equal to scanning a QR code
      enrollee_uri = self.get_uri(self.helper_dev, uri_id)

      # Corrupt the responder key if required
      if fail_authentication:
        enrollee_uri = enrollee_uri[:80] + "DeAdBeeF" + enrollee_uri[88:]
        self.log.info("Corrupted enrollee URI: %s" % enrollee_uri)

    if not cause_timeout:
      # Start DPP as an enrolle-responder for STA on helper device
      self.start_responder_enrollee(self.helper_dev, freq=responder_freq, net_role=net_role)
    else:
      self.log.info("Not starting DPP responder on purpose")

    self.log.info("Starting DPP in Configurator-Initiator mode")

    # Start DPP as configurator-initiator on dut
    self.dut.droid.startEasyConnectAsConfiguratorInitiator(enrollee_uri,
                                                   test_network_id, net_role)

    start_time = time.time()
    while time.time() < start_time + self.DPP_TEST_TIMEOUT:
      dut_event = self.dut.ed.pop_event(self.DPP_TEST_EVENT_DPP_CALLBACK,
                                        self.DPP_TEST_TIMEOUT)
      if dut_event[self.DPP_TEST_EVENT_DATA][self.DPP_TEST_MESSAGE_TYPE] \
              == self.DPP_TEST_EVENT_ENROLLEE_SUCCESS:
        asserts.fail("DPP failure, unexpected result!")
        break
      if dut_event[self.DPP_TEST_EVENT_DATA][
          self
          .DPP_TEST_MESSAGE_TYPE] == self.DPP_TEST_EVENT_CONFIGURATOR_SUCCESS:
        if cause_timeout or fail_authentication or invalid_uri:
          asserts.fail(
              "Unexpected DPP success, status code: %s" %
              dut_event[self.DPP_TEST_EVENT_DATA][self.DPP_TEST_MESSAGE_STATUS])
        else:
          val = dut_event[self.DPP_TEST_EVENT_DATA][
              self.DPP_TEST_MESSAGE_STATUS]
          if val == 0:
            self.dut.log.info("DPP Configuration sent success")
        break
      if dut_event[self.DPP_TEST_EVENT_DATA][
          self.DPP_TEST_MESSAGE_TYPE] == self.DPP_TEST_EVENT_PROGRESS:
        self.dut.log.info("DPP progress event")
        val = dut_event[self.DPP_TEST_EVENT_DATA][self.DPP_TEST_MESSAGE_STATUS]
        if val == 0:
          self.dut.log.info("DPP Authentication success")
        elif val == 1:
          self.dut.log.info("DPP Response pending")
        continue
      if dut_event[self.DPP_TEST_EVENT_DATA][
          self.DPP_TEST_MESSAGE_TYPE] == self.DPP_TEST_EVENT_FAILURE:
        if cause_timeout or fail_authentication or invalid_uri:
          self.dut.log.info(
              "Error %s occurred, as expected" %
              dut_event[self.DPP_TEST_EVENT_DATA][self.DPP_TEST_MESSAGE_STATUS])
        else:
          asserts.fail(
              "DPP failure, status code: %s" %
              dut_event[self.DPP_TEST_EVENT_DATA][self.DPP_TEST_MESSAGE_STATUS])
        break

    # Clear all pending events.
    self.dut.ed.clear_all_events()

    # Stop responder
    self.stop_responder(self.helper_dev)

    if not invalid_uri:
      # Delete URI
      self.del_uri(self.helper_dev, uri_id)

    asserts.assert_true(
        self.forget_network(test_network_id),
        "Test network not deleted from configured networks.")
示例#15
0
  def start_responder_configurator(self,
                                   device,
                                   freq=2412,
                                   net_role=DPP_TEST_NETWORK_ROLE_STA,
                                   security=DPP_TEST_SECURITY_SAE,
                                   invalid_config=False):
    """Start a responder on helper device

           Args:
               device: Device object
               freq: Frequency to listen on
               net_role: Network role to configure
               security: Security type: SAE or PSK
               invalid_config: Send invalid configuration (negative test)

            Returns:
                ssid: SSID name of the network to be configured

        """
    if not net_role or (net_role != self.DPP_TEST_NETWORK_ROLE_STA and
                        net_role != self.DPP_TEST_NETWORK_ROLE_AP):
      asserts.fail("start_responder: Must specify net_role sta or ap")

    self.log.info("Starting Responder in Configurator mode, frequency %sMHz" % freq)

    conf = "conf=%s-" % net_role

    use_psk = False

    if security == self.DPP_TEST_SECURITY_SAE:
      if not self.dut.droid.wifiIsWpa3SaeSupported():
        self.log.warning("SAE not supported on device! reverting to PSK")
        security = self.DPP_TEST_SECURITY_PSK_PASSPHRASE

    if security == self.DPP_TEST_SECURITY_SAE:
      conf += self.WPA_SUPPLICANT_SECURITY_SAE
    elif security == self.DPP_TEST_SECURITY_PSK_PASSPHRASE:
      conf += self.WPA_SUPPLICANT_SECURITY_PSK
    else:
      conf += self.WPA_SUPPLICANT_SECURITY_PSK
      use_psk = True

    ssid = self.DPP_TEST_SSID_PREFIX + utils.rand_ascii_str(8)
    self.log.debug("SSID = %s" % ssid)

    ssid_encoded = binascii.hexlify(ssid.encode()).decode()

    if use_psk:
      psk = utils.rand_ascii_str(16)
      if not invalid_config:
        psk_encoded = binascii.b2a_hex(psk.encode()).decode()
      else:
        # Use the psk as is without hex encoding, will make it invalid
        psk_encoded = psk
      self.log.debug("PSK = %s" % psk)
    else:
      password = utils.rand_ascii_str(8)
      if not invalid_config:
        password_encoded = binascii.b2a_hex(password.encode()).decode()
      else:
        # Use the password as is without hex encoding, will make it invalid
        password_encoded = password
      self.log.debug("Password = %s" % password)

    conf += " ssid=%s" % ssid_encoded

    if password:  # SAE password or PSK passphrase
      conf += " pass=%s" % password_encoded
    else:  # PSK
      conf += " psk=%s" % psk_encoded

    # Stop responder first
    self.stop_responder(device)

    cmd = "wpa_cli set dpp_configurator_params guard=1 %s" % conf
    device.log.debug("Command used: %s" % cmd)
    result = self.helper_dev.adb.shell(cmd)
    if "FAIL" in result:
      asserts.fail(
          "start_responder_configurator: Failure. Command used: %s" % cmd)

    cmd = "wpa_cli DPP_LISTEN %d role=configurator netrole=%s" % (freq,
                                                                  net_role)
    device.log.debug("Command used: %s" % cmd)
    result = self.helper_dev.adb.shell(cmd)
    if "FAIL" in result:
      asserts.fail(
          "start_responder_configurator: Failure. Command used: %s" % cmd)

    device.log.info("Started responder in configurator mode")
    return ssid