def run_once(self, host=None, wifi_iface=None, wifi_ssid=None):
        """Check that a given wifi interface is properly configured.

        @param host: a host object representing the DUT.
        @param wifi_iface: Name of the wifi interface to test; None means we'll
                           try to detect at least one that works.
        @param wifi_ssid: Name of the SSID we want the interface to be
                          connected to; None means any.

        @raise TestFail: The test failed.
        """
        err_iface = ('No interface is' if wifi_iface is None else
                     'Interface %s is not' % wifi_iface)

        # First check link status and SSID.
        iw = iw_runner.IwRunner(remote_host=host)
        active_ifaces = []
        try:
            iw_ifaces = [
                iface_tuple.if_name for iface_tuple in iw.list_interfaces()
            ]
            if wifi_iface is not None:
                if wifi_iface not in iw_ifaces:
                    raise error.TestFail('Interface %s not listed by iw' %
                                         wifi_iface)
                test_ifaces = [wifi_iface]
            else:
                test_ifaces = iw_ifaces

            for iface in test_ifaces:
                iface_ssid = iw.get_link_value(iface, 'SSID')
                if (iface_ssid is not None
                        and (wifi_ssid is None or iface_ssid == wifi_ssid)):
                    active_ifaces.append(iface)
        except error.AutoservRunError:
            raise error.TestFail('Failed to run iw')

        if not active_ifaces:
            err_ssid = 'any SSID' if wifi_ssid is None else 'SSID ' + wifi_ssid
            raise error.TestFail('%s connected to %s' % (err_iface, err_ssid))

        logging.info('Active wifi interfaces: %s', ', '.join(active_ifaces))

        # Then check IPv4 connectivity.
        try:
            ifconfig_output = host.run_output('ifconfig').splitlines()
        except error.AutoservRunError:
            raise error.TestFail('Failed to run ifconfig')

        ifconfig_dict = self.get_ifconfig_dict(ifconfig_output)
        connected_ifaces = [
            iface for iface in active_ifaces if any([
                'inet addr:' in line for line in ifconfig_dict.get(iface, [])
            ])
        ]
        if not connected_ifaces:
            raise error.TestFail('%s IPv4 connected' % err_iface)

        logging.info('IPv4 connected wifi interfaces: %s',
                     ', '.join(connected_ifaces))
Beispiel #2
0
    def run_once(self):
        """Body of the test."""

        get_assoc_params = lambda conf: xmlrpc_datatypes.AssociationParameters(
            ssid=self.context.router.get_ssid(instance=0), bgscan_config=conf)
        get_ping_config = lambda period: ping_runner.PingConfig(
            self.context.get_wifi_addr(),
            interval=self.PING_INTERVAL_SECONDS,
            count=int(period / self.PING_INTERVAL_SECONDS))
        self.context.configure(self._config_first_ap)
        bgscan_config = xmlrpc_datatypes.BgscanConfiguration(
            short_interval=self.CONFIGURED_BGSCAN_INTERVAL_SECONDS,
            long_interval=self.CONFIGURED_BGSCAN_INTERVAL_SECONDS,
            method=xmlrpc_datatypes.BgscanConfiguration.SCAN_METHOD_SIMPLE)
        self.context.assert_connect_wifi(get_assoc_params(bgscan_config))
        logging.info('Pinging router with background scans for %d seconds.',
                     self.BGSCAN_SAMPLE_PERIOD_SECONDS)
        result_bgscan = self.context.client.ping(
            get_ping_config(self.BGSCAN_SAMPLE_PERIOD_SECONDS))
        logging.info('Ping statistics with bgscan: %r', result_bgscan)
        # Bring up a second AP, make sure that it shows up in bgscans.
        self._config_second_ap.ssid = self.context.router.get_ssid()
        self.context.configure(self._config_second_ap, multi_interface=True)
        logging.info('Without a ping running, ensure that bgscans succeed.')
        ap_mac = self.context.router.get_hostapd_mac(ap_num=1)
        logging.debug('Looking for BSS %s', ap_mac)
        iw = iw_runner.IwRunner(remote_host=self.context.client.host)

        utils.poll_for_condition(
            condition=lambda: self._find_bss_matching_mac_addr(iw, ap_mac),
            exception=error.TestFail(
                'Background scans should detect new BSSes '
                'within an associated ESS.'),
            timeout=self.BGSCAN_SAMPLE_PERIOD_SECONDS,
            sleep_interval=1)

        self.context.router.deconfig_aps(instance=1)
        self.context.client.shill.disconnect(
            self.context.router.get_ssid(instance=0))
        # Reconfigure AP, so the new bgscan setting can be correctly applied.
        self.context.configure(self._config_first_ap)
        # Gather some statistics about ping latencies without scanning going on.
        self.context.assert_connect_wifi(get_assoc_params(None))
        logging.info('Pinging router without background scans for %d seconds.',
                     self.NO_BGSCAN_SAMPLE_PERIOD_SECONDS)
        result_no_bgscan = self.context.client.ping(
            get_ping_config(self.NO_BGSCAN_SAMPLE_PERIOD_SECONDS))
        logging.info('Ping statistics without bgscan: %r', result_no_bgscan)
        if result_no_bgscan.max_latency > self.THRESHOLD_BASELINE_LATENCY_MS:
            raise error.TestFail('RTT latency is too high even without '
                                 'background scans: %f' %
                                 result_no_bgscan.max_latency)

        if (result_bgscan.max_latency >
                self.LATENCY_MARGIN_MS + result_no_bgscan.avg_latency):
            raise error.TestFail(
                'Significant difference in rtt due to bgscan: '
                '%.1f > %.1f + %d' %
                (result_bgscan.max_latency, result_no_bgscan.avg_latency,
                 self.LATENCY_MARGIN_MS))
Beispiel #3
0
    def prepare_work_client(self, work_client_machine):
        """Prepare the SSHHost object into WiFiClient object

        @param work_client_machine: a SSHHost object to be wrapped

        """
        work_client_host = hosts.create_host(work_client_machine.hostname)
        # All packet captures in chaos lab have dual NICs. Let us use phy1 to
        # be a radio dedicated for work client
        iw = iw_runner.IwRunner(remote_host=work_client_host)
        phys = iw.list_phys()
        devs = iw.list_interfaces(desired_if_type='managed')
        if len(devs) > 0:
            logging.debug('Removing interfaces in work host machine %s', devs)
            for i in range(len(devs)):
                iw.remove_interface(devs[i].if_name)
        if len(phys) > 1:
            logging.debug('Adding interfaces in work host machine')
            iw.add_interface('phy1', 'work0', 'managed')
            logging.debug('Interfaces in work client %s', iw.list_interfaces())
        elif len(phys) == 1:
            raise error.TestError('Not enough phys available to create a'
                                  'work client interface %s.' %
                                   work_client_host.hostname)
        self.work_client = wifi_client.WiFiClient(
                work_client_host, './debug', False)
        # Make the host object easily accessible
        self.host = self.work_client.host
    def get_highest_mcs_rate(self, frequency):
        """
        Get the highest MCS index supported by the DUT on |frequency|.

        @param frequency: int frequency to look for supported MCS rates.
        @return int highest rate supported.

        """
        # Figure out the highest MCS index supported by this hardware.
        phys = iw_runner.IwRunner(
            remote_host=self.context.client.host).list_phys()
        if len(phys) != 1:
            raise error.TestFail('Test expects a single PHY, but we got %d' %
                                 len(phys))

        phy = phys[0]
        bands = [band for band in phy.bands if frequency in band.frequencies]
        if len(bands) != 1:
            raise error.TestFail('Test expects a single possible band for a '
                                 'given frequency, but this device has %d '
                                 'such bands.' % len(bands))

        # 32 is a special low throughput, high resilience mode.  Ignore it.
        possible_indices = filter(lambda x: x != 32, bands[0].mcs_indices)

        if not possible_indices:
            raise error.TestFail('No possible MCS indices on frequency %d' %
                                 frequency)

        return max(possible_indices)
Beispiel #5
0
    def count_mismatched_phy_configs(cls, dut_host, expected_channel_configs):
        """Verifies that phys on the DUT place the expected restrictions on
        channels.

        Compares the restrictions reported by the running system to
        the restrictions in |expected_channel_configs|. Returns a
        count of the number of mismatches.

        Note that this method deliberately ignores channels that are
        reported by the running system, but not mentioned in
        |expected_channel_configs|. This allows us to program the
        control file with "spot checks", rather than an exhaustive
        list of channels.

        @param dut_host The host object for the DUT.
        @param expected_channel_configs A channel_infos list.
        @return int count of mismatches

        """
        actual_channel_expectations = cls.phy_list_to_channel_expectations(
            iw_runner.IwRunner(dut_host).list_phys())
        mismatches = 0
        for expected_config in expected_channel_configs:
            channel = expected_config['chnum']
            expected = expected_config['expect']
            actual = actual_channel_expectations[channel]
            if actual != expected:
                logging.error(
                    'Expected phy config for channel %d of |%s|, but got |%s|.',
                    channel, expected, actual)
                mismatches += 1
        return mismatches
Beispiel #6
0
 def test_station_link_key(self):
     """Test a link key is extracted from station link information."""
     host = self.host(self.STATION_LINK_INFORMATION)
     runner = iw_runner.IwRunner(remote_host=host)
     self.assertEquals(
         runner.get_link_value(self.STATION_LINK_INFORMATION,
                               iw_runner.IW_LINK_KEY_FREQUENCY),
         self.STATION_LINK_FREQ)
Beispiel #7
0
 def test_multiple_ssids(self):
     """Test with multiple networks with the same ssids."""
     scan_output = self.HT40_ABOVE + self.HT20 + self.NO_HT + self.HT20_2
     host = self.host(scan_output + self.SCAN_TIME_OUTPUT)
     runner = iw_runner.IwRunner(remote_host=host)
     networks = runner.wait_for_scan_result('wlan 0',
                                            ssids=[self.HT20_2_IW_BSS.ssid])
     for iw_bss_1, iw_bss_2 in zip([self.HT20_IW_BSS, self.HT20_2_IW_BSS],
                                   networks):
         self.verify_values(iw_bss_1, iw_bss_2)
Beispiel #8
0
    def search_by_bss(self, scan_output, test_iw_bss):
        """

        @param scan_output: the output of the scan as a string
        @param test_iw_bss: an IWBss object

        Uses the runner to search for a network by bss.
        """
        host = self.host(scan_output + self.SCAN_TIME_OUTPUT)
        runner = iw_runner.IwRunner(remote_host=host)
        network = runner.wait_for_scan_result('wlan0', bsses=[test_iw_bss.bss])
        self.verify_values(test_iw_bss, network[0])
    def dut_sees_bss(self, bssid):
        """
        Check if a DUT can see a BSS in scan results.

        @param bssid: string bssid of AP we expect to see in scan results.
        @return True iff scan results from DUT include the specified BSS.

        """
        runner = iw_runner.IwRunner(remote_host=self.context.client.host)
        is_requested_bss = lambda iw_bss: iw_bss.bss == bssid
        scan_results = runner.scan(self.context.client.wifi_if)
        return scan_results and filter(is_requested_bss, scan_results)
Beispiel #10
0
    def run_once(self):
        """Test main loop"""
        self._iw = iw_runner.IwRunner()
        initial_regdomain = self._iw.get_regulatory_domain()
        logging.info('Initial regulatory domain is %s', initial_regdomain)

        domain_list = self.get_regulatory_domains()
        if not domain_list:
            raise error.TestFail('Did not get a domain list from the database')

        for domain in domain_list:
            self.assert_set_regulatory_domain(domain)
        self.assert_set_regulatory_domain(initial_regdomain)
    def __setup(self):
        """Set up this system.

        Can be used either to complete initialization of a LinuxSystem object,
        or to re-establish a good state after a reboot.

        """
        # Command locations.
        cmd_iw = path_utils.must_be_installed('/usr/sbin/iw', host=self.host)
        self.cmd_ip = path_utils.must_be_installed('/usr/sbin/ip',
                                                   host=self.host)
        self.cmd_readlink = '%s -l' % path_utils.must_be_installed(
            '/bin/ls', host=self.host)

        self._packet_capturer = packet_capturer.get_packet_capturer(
            self.host,
            host_description=self.role,
            cmd_ip=self.cmd_ip,
            cmd_iw=cmd_iw,
            ignore_failures=True)
        self.iw_runner = iw_runner.IwRunner(remote_host=self.host,
                                            command_iw=cmd_iw)

        self._phy_list = None
        self.phys_for_frequency, self.phy_bus_type = self._get_phy_info()
        logging.debug('Current regulatory domain %r',
                      self.iw_runner.get_regulatory_domain())
        self._interfaces = []
        self._brif_index = 0
        for interface in self.iw_runner.list_interfaces():
            if self.inherit_interfaces:
                self._interfaces.append(
                    NetDev(inherited=True,
                           if_name=interface.if_name,
                           if_type=interface.if_type,
                           phy=interface.phy))
            else:
                self.iw_runner.remove_interface(interface.if_name)

        self._wlanifs_in_use = []
        self._local_macs_in_use = set()
        self._capture_interface = None
        self._board = None
        # Some uses of LinuxSystem don't use the interface allocation facility.
        # Don't force us to remove all the existing interfaces if this facility
        # is not desired.
        self._wlanifs_initialized = False
        self._capabilities = None
        self._ping_runner = ping_runner.PingRunner(host=self.host)
        self._bridge_interface = None
        self._virtual_ethernet_pair = None
Beispiel #12
0
    def assert_scanning_fails(cls, client, scan_freq):
        """Initiates a single-channel scan, and verifies that it fails.

        @param client The WiFiClient object for the DUT.
        @param scan_freq The frequency (in MHz) on which to scan.
        """
        client.claim_wifi_if()  # Stop shill/supplicant scans.
        try:
            # We use IwRunner directly here, because WiFiClient.scan()
            # wants a scan to succeed, while we want the scan to fail.
            if iw_runner.IwRunner(client.host).timed_scan(
                    client.wifi_if, [scan_freq], [cls.MISSING_SSID]):
                # We should have got None, to represent failure.
                raise error.TestFail(
                    'Scan succeeded (and was expected to fail).')
        finally:
            client.release_wifi_if()
Beispiel #13
0
    def run_once(self):
        """Configures a DUT to behave as if it was manufactured for a
        particular region. Then verifies that the DUT connects, or
        fails to connect, per expectations.

        """
        num_failures = 0
        try:
            self.fake_up_region(self.region_name)
            self.assert_equal(
                'country code',
                iw_runner.IwRunner(self.host).get_regulatory_domain(),
                self.expected_country_code)
            num_mismatches = self.count_mismatched_phy_configs(
                self.host, self.channel_infos)
            if num_mismatches:
                raise error.TestFail(
                    '%d phy configs were not as expected (see below)' %
                    num_mismatches)
            wifi_context = wifi_test_context_manager.WiFiTestContextManager(
                self.__class__.__name__, self.host, self.cmdline_args,
                self.debugdir)
            with wifi_context:
                wifi_context.router.reboot(timeout=self.REBOOT_TIMEOUT_SECS)
                for channel_config in self.channel_infos:
                    try:
                        self.test_channel(wifi_context, channel_config)
                    except error.TestFail as e:
                        # Log the error, but keep going. This way, we
                        # get a full report of channels where behavior
                        # differs from expectations.
                        logging.error('Verification failed for |%s|: %s',
                                      self.region_name, channel_config)
                        logging.error(e)
                        num_failures += 1
        finally:
            if num_failures:
                raise error.TestFail(
                    'Verification failed for %d channel configs (see below)' %
                    num_failures)
            self.host.run(self.VPD_CLEAN_COMMAND)
            self.host.reboot(timeout=self.REBOOT_TIMEOUT_SECS, wait=True)
    def run(self,
            job,
            batch_size=7,
            tries=10,
            capturer_hostname=None,
            conn_worker=None,
            work_client_hostname=None,
            disabled_sysinfo=False):
        """Executes Chaos test.

        @param job: an Autotest job object.
        @param batch_size: an integer, max number of APs to lock in one batch.
        @param tries: an integer, number of iterations to run per AP.
        @param capturer_hostname: a string or None, hostname or IP of capturer.
        @param conn_worker: ConnectionWorkerAbstract or None, to run extra
                            work after successful connection.
        @param work_client_hostname: a string or None, hostname of work client
        @param disabled_sysinfo: a bool, disable collection of logs from DUT.


        @raises TestError: Issues locking VM webdriver instance
        """

        lock_manager = host_lock_manager.HostLockManager()
        webdriver_master = hosts.SSHHost(MASTERNAME, user='******')
        with host_lock_manager.HostsLockedBy(lock_manager):
            capture_host = utils.allocate_packet_capturer(
                lock_manager, hostname=capturer_hostname)
            # Cleanup and reboot packet capturer before the test.
            utils.sanitize_client(capture_host)
            capturer = site_linux_system.LinuxSystem(capture_host, {},
                                                     'packet_capturer')

            # Run iw scan and abort if more than allowed number of APs are up.
            iw_command = iw_runner.IwRunner(capture_host)
            start_time = time.time()
            logging.info('Performing a scan with a max timeout of 30 seconds.')
            while time.time() - start_time <= ap_constants.MAX_SCAN_TIMEOUT:
                networks = iw_command.scan('wlan0')
                if networks is None:
                    if (time.time() -
                            start_time == ap_constants.MAX_SCAN_TIMEOUT):
                        raise error.TestError(
                            'Packet capturer is not responding to scans. Check'
                            'device and re-run test')
                    continue
                elif len(networks) < ap_constants.MAX_SSID_COUNT:
                    break
                elif len(networks) >= ap_constants.MAX_SSID_COUNT:
                    raise error.TestError(
                        'Probably someone is already running a'
                        'chaos test?!')

            if conn_worker is not None:
                work_client_machine = utils.allocate_packet_capturer(
                    lock_manager, hostname=work_client_hostname)
                conn_worker.prepare_work_client(work_client_machine)

            webdriver_instance = utils.allocate_webdriver_instance(
                lock_manager)
            self._ap_spec._webdriver_hostname = webdriver_instance

            # If a test is cancelled or aborted the VM may be left on.  Always
            # turn of the VM to return it to a clean state.
            try:
                logging.info('Always power off VM %s', webdriver_instance)
                utils.power_off_VM(webdriver_master, webdriver_instance)
            except:
                logging.debug('VM was already off, ignoring.')

            logging.info('Starting up VM %s', webdriver_instance)
            utils.power_on_VM(webdriver_master, webdriver_instance)

            batch_locker = ap_batch_locker.ApBatchLocker(
                lock_manager,
                self._ap_spec,
                ap_test_type=ap_constants.AP_TEST_TYPE_CHAOS)

            while batch_locker.has_more_aps():
                # Work around crbug.com/358716
                utils.sanitize_client(self._host)
                healthy_dut = True

                with contextlib.closing(
                        wifi_client.WiFiClient(
                            hosts.create_host(self._host.hostname), './debug',
                            False)) as client:

                    aps = batch_locker.get_ap_batch(batch_size=batch_size)
                    if not aps:
                        logging.info('No more APs to test.')
                        break

                    # Power down all of the APs because some can get grumpy
                    # if they are configured several times and remain on.
                    # User the cartridge to down group power downs and
                    # configurations.
                    utils.power_down_aps(aps, self._broken_pdus)
                    utils.configure_aps(aps, self._ap_spec, self._broken_pdus)

                    aps = utils.filter_quarantined_and_config_failed_aps(
                        aps, batch_locker, job, self._broken_pdus)

                    for ap in aps:
                        # http://crbug.com/306687
                        if ap.ssid == None:
                            logging.error('The SSID was not set for the AP:%s',
                                          ap)

                        healthy_dut = utils.is_dut_healthy(client, ap)

                        if not healthy_dut:
                            logging.error('DUT is not healthy, rebooting.')
                            batch_locker.unlock_and_reclaim_aps()
                            break

                        networks = utils.return_available_networks(
                            ap, capturer, job, self._ap_spec)

                        if networks is None:
                            # If scan returned no networks, iw scan failed.
                            # Reboot the packet capturer device and
                            # reconfigure the capturer.
                            batch_locker.unlock_and_reclaim_ap(ap.host_name)
                            logging.error('Packet capture is not healthy, '
                                          'rebooting.')
                            capturer.host.reboot()
                            capturer = site_linux_system.LinuxSystem(
                                capture_host, {}, 'packet_capturer')
                            continue
                        if networks == list():
                            # Packet capturer did not find the SSID in scan or
                            # there was a security mismatch.
                            utils.release_ap(ap, batch_locker,
                                             self._broken_pdus)
                            continue

                        assoc_params = ap.get_association_parameters()

                        if not utils.is_conn_worker_healthy(
                                conn_worker, ap, assoc_params, job):
                            utils.release_ap(ap, batch_locker,
                                             self._broken_pdus)
                            continue

                        name = ap.name
                        kernel_ver = self._host.get_kernel_ver()
                        firmware_ver = utils.get_firmware_ver(self._host)
                        if not firmware_ver:
                            firmware_ver = "Unknown"

                        debug_dict = {
                            '+++PARSE DATA+++': '+++PARSE DATA+++',
                            'SSID': ap._ssid,
                            'DUT': client.wifi_mac,
                            'AP Info': ap.name,
                            'kernel_version': kernel_ver,
                            'wifi_firmware_version': firmware_ver
                        }
                        debug_string = pprint.pformat(debug_dict)

                        logging.info(
                            'Waiting %d seconds for the AP dhcp '
                            'server', ap.dhcp_delay)
                        time.sleep(ap.dhcp_delay)

                        result = job.run_test(
                            self._test,
                            capturer=capturer,
                            capturer_frequency=networks[0].frequency,
                            capturer_ht_type=networks[0].ht,
                            host=self._host,
                            assoc_params=assoc_params,
                            client=client,
                            tries=tries,
                            debug_info=debug_string,
                            # Copy all logs from the system
                            disabled_sysinfo=disabled_sysinfo,
                            conn_worker=conn_worker,
                            tag=ap.ssid if conn_worker is None else '%s.%s' %
                            (conn_worker.name, ap.ssid))

                        utils.release_ap(ap, batch_locker, self._broken_pdus)

                        if conn_worker is not None:
                            conn_worker.cleanup()

                    if not healthy_dut:
                        continue

                batch_locker.unlock_aps()
            capturer.close()
            logging.info('Powering off VM %s', webdriver_instance)
            utils.power_off_VM(webdriver_master, webdriver_instance)
            lock_manager.unlock(webdriver_instance)

            if self._broken_pdus:
                logging.info('PDU is down!!!\nThe following PDUs are down:\n')
                pprint.pprint(self._broken_pdus)
Beispiel #15
0
 def test_station_dump(self):
     """Test parsing of a station dump."""
     host = self.host(self.STATION_DUMP_INFORMATION)
     runner = iw_runner.IwRunner(remote_host=host)
     self.assertEquals(runner.get_station_dump(self.STATION_DUMP_IFACE),
                       self.STATION_DUMP_INFORMATION_PARSED)
Beispiel #16
0
 def test_vht_supported(self):
     """Test VHT support parsing."""
     host = self.host(self.VHT_IW_INFO)
     runner = iw_runner.IwRunner(remote_host=host)
     self.assertEquals(runner.vht_supported(), True)
Beispiel #17
0
    def run_once(self):
        """Body of the test."""
        get_assoc_params = lambda conf: xmlrpc_datatypes.AssociationParameters(
            ssid=self.context.router.get_ssid(instance=0), bgscan_config=conf)
        get_ping_config = lambda period: ping_runner.PingConfig(
            self.context.get_wifi_addr(),
            interval=self.PING_INTERVAL_SECONDS,
            count=int(period / self.PING_INTERVAL_SECONDS))
        self.context.configure(hostap_config.HostapConfig(channel=1))
        bgscan_config = xmlrpc_datatypes.BgscanConfiguration(
            short_interval=self.CONFIGURED_BGSCAN_INTERVAL_SECONDS,
            long_interval=self.CONFIGURED_BGSCAN_INTERVAL_SECONDS,
            method=xmlrpc_datatypes.BgscanConfiguration.SCAN_METHOD_SIMPLE)
        self.context.assert_connect_wifi(get_assoc_params(bgscan_config))
        logging.info('Pinging router with background scans for %d seconds.',
                     self.BGSCAN_SAMPLE_PERIOD_SECONDS)
        result_bgscan = self.context.client.ping(
            get_ping_config(self.BGSCAN_SAMPLE_PERIOD_SECONDS))
        logging.info('Ping statistics with bgscan: %r', result_bgscan)
        # Bring up a second AP, make sure that it shows up in bgscans.
        self.context.configure(hostap_config.HostapConfig(
            channel=11, min_streams=1, ssid=self.context.router.get_ssid()),
                               multi_interface=True)
        logging.info('Without a ping running, ensure that bgscans succeed.')
        ap_mac = self.context.router.get_hostapd_mac(ap_num=1)
        logging.debug('Looking for BSS %s', ap_mac)
        iw = iw_runner.IwRunner(remote_host=self.context.client.host)
        start_time = time.time()
        while time.time() - start_time < self.BGSCAN_SAMPLE_PERIOD_SECONDS:
            bsses = iw.scan_dump(self.context.client.wifi_if)
            logging.debug('Found BSSes: %r', bsses)
            if filter(lambda bss: bss.bss == ap_mac, bsses):
                break

            time.sleep(1)
        else:
            raise error.TestFail('Background scans should detect new BSSes '
                                 'within an associated ESS.')

        self.context.router.deconfig_aps(instance=1)
        self.context.client.shill.disconnect(
            self.context.router.get_ssid(instance=0))
        # Reconfigure AP, so the new bgscan setting can be correctly applied.
        self.context.configure(hostap_config.HostapConfig(channel=1))
        # Gather some statistics about ping latencies without scanning going on.
        self.context.assert_connect_wifi(get_assoc_params(None))
        logging.info('Pinging router without background scans for %d seconds.',
                     self.NO_BGSCAN_SAMPLE_PERIOD_SECONDS)
        result_no_bgscan = self.context.client.ping(
            get_ping_config(self.NO_BGSCAN_SAMPLE_PERIOD_SECONDS))
        logging.info('Ping statistics without bgscan: %r', result_no_bgscan)
        if result_no_bgscan.max_latency > self.THRESHOLD_BASELINE_LATENCY_MS:
            raise error.TestFail('RTT latency is too high even without '
                                 'background scans: %f' %
                                 result_no_bgscan.max_latency)

        # Dwell time for scanning is usually configured to be around 100 ms,
        # since this is also the standard beacon interval.  Tolerate spikes in
        # latency up to 200 ms as a way of asking that our PHY be servicing
        # foreground traffic regularly during background scans.
        if (result_bgscan.max_latency >
                self.LATENCY_MARGIN_MS + result_no_bgscan.avg_latency):
            raise error.TestFail(
                'Significant difference in rtt due to bgscan: '
                '%.1f > %.1f + %d' %
                (result_bgscan.max_latency, result_no_bgscan.avg_latency,
                 self.LATENCY_MARGIN_MS))
    def run(self,
            job,
            batch_size=10,
            tries=10,
            capturer_hostname=None,
            conn_worker=None,
            work_client_hostname=None,
            disabled_sysinfo=False):
        """Executes Chaos test.

        @param job: an Autotest job object.
        @param batch_size: an integer, max number of APs to lock in one batch.
        @param tries: an integer, number of iterations to run per AP.
        @param capturer_hostname: a string or None, hostname or IP of capturer.
        @param conn_worker: ConnectionWorkerAbstract or None, to run extra
                            work after successful connection.
        @param work_client_hostname: a string or None, hostname of work client
        @param disabled_sysinfo: a bool, disable collection of logs from DUT.


        @raises TestError: Packet capture DUT may be down or another test may be
                           running in the chamber.
        """

        lock_manager = host_lock_manager.HostLockManager()
        host_prefix = self._host.hostname.split('-')[0]
        if ap_constants.CASEY5 in host_prefix:
            test_type = ap_constants.AP_TEST_TYPE_CASEY5
        elif ap_constants.CASEY7 in host_prefix:
            test_type = ap_constants.AP_TEST_TYPE_CASEY7
        else:
            test_type = None

        with host_lock_manager.HostsLockedBy(lock_manager):
            capture_host = utils.allocate_packet_capturer(
                lock_manager, hostname=capturer_hostname, prefix=host_prefix)
            # Cleanup and reboot packet capturer before the test.
            utils.sanitize_client(capture_host)
            capturer = site_linux_system.LinuxSystem(capture_host, {},
                                                     'packet_capturer')

            # Run iw scan and abort if more than allowed number of APs are up.
            iw_command = iw_runner.IwRunner(capture_host)
            start_time = time.time()
            logging.info('Performing a scan with a max timeout of 30 seconds.')
            capture_interface = 'wlan0'
            capturer_info = capture_host.run('cat /etc/lsb-release',
                                             ignore_status=True,
                                             timeout=5).stdout
            if 'whirlwind' in capturer_info:
                # Use the dual band aux radio for scanning networks.
                capture_interface = 'wlan2'
            while time.time() - start_time <= ap_constants.MAX_SCAN_TIMEOUT:
                networks = iw_command.scan(capture_interface)
                if networks is None:
                    if (time.time() -
                            start_time == ap_constants.MAX_SCAN_TIMEOUT):
                        raise error.TestError(
                            'Packet capturer is not responding to scans. Check'
                            'device and re-run test')
                    continue
                elif len(networks) < ap_constants.MAX_SSID_COUNT:
                    break
                elif len(networks) >= ap_constants.MAX_SSID_COUNT:
                    raise error.TestError(
                        'Probably someone is already running a '
                        'chaos test?!')

            if conn_worker is not None:
                work_client_machine = utils.allocate_packet_capturer(
                    lock_manager, hostname=work_client_hostname)
                conn_worker.prepare_work_client(work_client_machine)

            batch_locker = ap_batch_locker.ApBatchLocker(
                lock_manager, self._ap_spec, ap_test_type=test_type)

            while batch_locker.has_more_aps():
                # Work around for CrOS devices only:crbug.com/358716
                # Do not reboot Android devices:b/27977927
                if self._host.get_os_type() != adb_host.OS_TYPE_ANDROID:
                    utils.sanitize_client(self._host)
                healthy_dut = True

                with contextlib.closing(
                        wifi_client.WiFiClient(
                            hosts.create_host(
                                {
                                    'hostname': self._host.hostname,
                                    'afe_host': self._host._afe_host
                                },
                                host_class=self._host.__class__), './debug',
                            False)) as client:

                    aps = batch_locker.get_ap_batch(batch_size=batch_size)
                    if not aps:
                        logging.info('No more APs to test.')
                        break

                    utils.configure_aps(aps, self._ap_spec)

                    aps = utils.filter_quarantined_and_config_failed_aps(
                        aps, batch_locker, job)

                    for ap in aps:
                        # http://crbug.com/306687
                        if ap.ssid == None:
                            logging.error('The SSID was not set for the AP:%s',
                                          ap)

                        healthy_dut = utils.is_dut_healthy(client, ap)

                        if not healthy_dut:
                            logging.error('DUT is not healthy, rebooting.')
                            batch_locker.unlock_and_reclaim_aps()
                            break

                        networks = utils.return_available_networks(
                            ap, capturer, job, self._ap_spec)

                        if networks is None:
                            # If scan returned no networks, iw scan failed.
                            # Reboot the packet capturer device and
                            # reconfigure the capturer.
                            batch_locker.unlock_and_reclaim_ap(ap.host_name)
                            logging.error('Packet capture is not healthy, '
                                          'rebooting.')
                            capturer.host.reboot()
                            capturer = site_linux_system.LinuxSystem(
                                capture_host, {}, 'packet_capturer')
                            continue
                        if networks == list():
                            # Packet capturer did not find the SSID in scan or
                            # there was a security mismatch.
                            utils.release_ap(ap, batch_locker)
                            continue

                        assoc_params = ap.get_association_parameters()

                        if not utils.is_conn_worker_healthy(
                                conn_worker, ap, assoc_params, job):
                            utils.release_ap(ap, batch_locker)
                            continue

                        name = ap.name
                        kernel_ver = self._host.get_kernel_ver()
                        firmware_ver = utils.get_firmware_ver(self._host)
                        if not firmware_ver:
                            firmware_ver = "Unknown"

                        debug_dict = {
                            '+++PARSE DATA+++': '+++PARSE DATA+++',
                            'SSID': ap._ssid,
                            'DUT': client.wifi_mac,
                            'AP Info': ap.name,
                            'kernel_version': kernel_ver,
                            'wifi_firmware_version': firmware_ver
                        }
                        debug_string = pprint.pformat(debug_dict)

                        logging.info(
                            'Waiting %d seconds for the AP dhcp '
                            'server', ap.dhcp_delay)
                        time.sleep(ap.dhcp_delay)

                        result = job.run_test(
                            self._test,
                            capturer=capturer,
                            capturer_frequency=networks[0].frequency,
                            capturer_ht_type=networks[0].ht,
                            host=self._host,
                            assoc_params=assoc_params,
                            client=client,
                            tries=tries,
                            debug_info=debug_string,
                            # Copy all logs from the system
                            disabled_sysinfo=disabled_sysinfo,
                            conn_worker=conn_worker,
                            tag=ap.ssid if conn_worker is None else '%s.%s' %
                            (conn_worker.name, ap.ssid))

                        utils.release_ap(ap, batch_locker)

                        if conn_worker is not None:
                            conn_worker.cleanup()

                    if not healthy_dut:
                        continue

                batch_locker.unlock_aps()

            capturer.close()

            factory = ap_configurator_factory.APConfiguratorFactory(test_type)
            factory.turn_off_all_routers([])
Beispiel #19
0
 def test_he_supported(self):
     """Test HE support parsing."""
     host = self.host(self.HE_IW_INFO)
     runner = iw_runner.IwRunner(remote_host=host)
     self.assertEquals(runner.he_supported(), True)
Beispiel #20
0
    def run(self, job, batch_size=10, tries=10, capturer_hostname=None,
            conn_worker=None, work_client_hostname=None,
            disabled_sysinfo=False):
        """Executes Chaos test.

        @param job: an Autotest job object.
        @param batch_size: an integer, max number of APs to lock in one batch.
        @param tries: an integer, number of iterations to run per AP.
        @param capturer_hostname: a string or None, hostname or IP of capturer.
        @param conn_worker: ConnectionWorkerAbstract or None, to run extra
                            work after successful connection.
        @param work_client_hostname: a string or None, hostname of work client
        @param disabled_sysinfo: a bool, disable collection of logs from DUT.


        @raises TestError: Issues locking VM webdriver instance
        """

        lock_manager = host_lock_manager.HostLockManager()
        webdriver_master = hosts.SSHHost(MASTERNAME, user='******')
        host_prefix = self._host.hostname.split('-')[0]
        with host_lock_manager.HostsLockedBy(lock_manager):
            capture_host = utils.allocate_packet_capturer(
                    lock_manager, hostname=capturer_hostname,
                    prefix=host_prefix)
            # Cleanup and reboot packet capturer before the test.
            utils.sanitize_client(capture_host)
            capturer = site_linux_system.LinuxSystem(capture_host, {},
                                                     'packet_capturer')

            # Run iw scan and abort if more than allowed number of APs are up.
            iw_command = iw_runner.IwRunner(capture_host)
            start_time = time.time()
            logging.info('Performing a scan with a max timeout of 30 seconds.')
            capture_interface = 'wlan0'
            capturer_info = capture_host.run('cat /etc/lsb-release',
                                             ignore_status=True, timeout=5).stdout
            if 'whirlwind' in capturer_info:
                # Use the dual band aux radio for scanning networks.
                capture_interface = 'wlan2'
            while time.time() - start_time <= ap_constants.MAX_SCAN_TIMEOUT:
                networks = iw_command.scan(capture_interface)
                if networks is None:
                    if (time.time() - start_time ==
                            ap_constants.MAX_SCAN_TIMEOUT):
                        raise error.TestError(
                            'Packet capturer is not responding to scans. Check'
                            'device and re-run test')
                    continue
                elif len(networks) < ap_constants.MAX_SSID_COUNT:
                    break
                elif len(networks) >= ap_constants.MAX_SSID_COUNT:
                    raise error.TestError(
                        'Probably someone is already running a '
                        'chaos test?!')

            if conn_worker is not None:
                work_client_machine = utils.allocate_packet_capturer(
                        lock_manager, hostname=work_client_hostname)
                conn_worker.prepare_work_client(work_client_machine)

            # Lock VM. If on, power off; always power on. Then create a tunnel.
            webdriver_instance = utils.allocate_webdriver_instance(lock_manager)

            if utils.is_VM_running(webdriver_master, webdriver_instance):
                logging.info('VM %s was on; powering off for a clean instance',
                             webdriver_instance)
                utils.power_off_VM(webdriver_master, webdriver_instance)
                logging.info('Allow VM time to gracefully shut down')
                time.sleep(5)

            logging.info('Starting up VM %s', webdriver_instance)
            utils.power_on_VM(webdriver_master, webdriver_instance)
            logging.info('Allow VM time to power on before creating a tunnel.')
            time.sleep(30)

            if not client_utils.host_is_in_lab_zone(webdriver_instance.hostname):
                self._ap_spec._webdriver_hostname = webdriver_instance.hostname
            else:
                # If in the lab then port forwarding must be done so webdriver
                # connection will be over localhost.
                self._ap_spec._webdriver_hostname = 'localhost'
                webdriver_tunnel = webdriver_instance.create_ssh_tunnel(
                                                WEBDRIVER_PORT, WEBDRIVER_PORT)
                logging.info('Wait for tunnel to be created.')
                for i in range(3):
                    time.sleep(10)
                    results = client_utils.run('lsof -i:%s' % WEBDRIVER_PORT,
                                             ignore_status=True)
                    if results:
                        break
                if not results:
                    raise error.TestError(
                            'Unable to listen to WEBDRIVER_PORT: %s', results)

            batch_locker = ap_batch_locker.ApBatchLocker(
                    lock_manager, self._ap_spec,
                    ap_test_type=ap_constants.AP_TEST_TYPE_CHAOS)

            while batch_locker.has_more_aps():
                # Work around for CrOS devices only:crbug.com/358716
                utils.sanitize_client(self._host)
                healthy_dut = True

                with contextlib.closing(wifi_client.WiFiClient(
                    hosts.create_host(
                            {
                                    'hostname' : self._host.hostname,
                                    'afe_host' : self._host._afe_host,
                                    'host_info_store':
                                            self._host.host_info_store,
                            },
                            host_class=self._host.__class__,
                    ),
                    './debug',
                    False,
                )) as client:

                    aps = batch_locker.get_ap_batch(batch_size=batch_size)
                    if not aps:
                        logging.info('No more APs to test.')
                        break

                    # Power down all of the APs because some can get grumpy
                    # if they are configured several times and remain on.
                    # User the cartridge to down group power downs and
                    # configurations.
                    utils.power_down_aps(aps, self._broken_pdus)
                    utils.configure_aps(aps, self._ap_spec, self._broken_pdus)

                    aps = utils.filter_quarantined_and_config_failed_aps(aps,
                            batch_locker, job, self._broken_pdus)

                    for ap in aps:
                        # http://crbug.com/306687
                        if ap.ssid == None:
                            logging.error('The SSID was not set for the AP:%s',
                                          ap)

                        healthy_dut = utils.is_dut_healthy(client, ap)

                        if not healthy_dut:
                            logging.error('DUT is not healthy, rebooting.')
                            batch_locker.unlock_and_reclaim_aps()
                            break

                        networks = utils.return_available_networks(
                                ap, capturer, job, self._ap_spec)

                        if networks is None:
                            # If scan returned no networks, iw scan failed.
                            # Reboot the packet capturer device and
                            # reconfigure the capturer.
                            batch_locker.unlock_and_reclaim_ap(ap.host_name)
                            logging.error('Packet capture is not healthy, '
                                          'rebooting.')
                            capturer.host.reboot()
                            capturer = site_linux_system.LinuxSystem(
                                           capture_host, {},'packet_capturer')
                            continue
                        if networks == list():
                           # Packet capturer did not find the SSID in scan or
                           # there was a security mismatch.
                           utils.release_ap(ap, batch_locker, self._broken_pdus)
                           continue

                        assoc_params = ap.get_association_parameters()

                        if not utils.is_conn_worker_healthy(
                                conn_worker, ap, assoc_params, job):
                            utils.release_ap(
                                    ap, batch_locker, self._broken_pdus)
                            continue

                        name = ap.name
                        kernel_ver = self._host.get_kernel_ver()
                        firmware_ver = utils.get_firmware_ver(self._host)
                        if not firmware_ver:
                            firmware_ver = "Unknown"

                        debug_dict = {'+++PARSE DATA+++': '+++PARSE DATA+++',
                                      'SSID': ap._ssid,
                                      'DUT': client.wifi_mac,
                                      'AP Info': ap.name,
                                      'kernel_version': kernel_ver,
                                      'wifi_firmware_version': firmware_ver}
                        debug_string = pprint.pformat(debug_dict)

                        logging.info('Waiting %d seconds for the AP dhcp '
                                     'server', ap.dhcp_delay)
                        time.sleep(ap.dhcp_delay)

                        result = job.run_test(self._test,
                                     capturer=capturer,
                                     capturer_frequency=networks[0].frequency,
                                     capturer_ht_type=networks[0].ht,
                                     host=self._host,
                                     assoc_params=assoc_params,
                                     client=client,
                                     tries=tries,
                                     debug_info=debug_string,
                                     # Copy all logs from the system
                                     disabled_sysinfo=disabled_sysinfo,
                                     conn_worker=conn_worker,
                                     tag=ap.ssid if conn_worker is None else
                                         '%s.%s' % (conn_worker.name, ap.ssid))

                        utils.release_ap(ap, batch_locker, self._broken_pdus)

                        if conn_worker is not None:
                            conn_worker.cleanup()

                    if not healthy_dut:
                        continue

                batch_locker.unlock_aps()

            if webdriver_tunnel:
                webdriver_instance.disconnect_ssh_tunnel(webdriver_tunnel,
                                                         WEBDRIVER_PORT)
                webdriver_instance.close()
            capturer.close()
            logging.info('Powering off VM %s', webdriver_instance)
            utils.power_off_VM(webdriver_master, webdriver_instance)
            lock_manager.unlock(webdriver_instance.hostname)

            if self._broken_pdus:
                logging.info('PDU is down!!!\nThe following PDUs are down:\n')
                pprint.pprint(self._broken_pdus)

            factory = ap_configurator_factory.APConfiguratorFactory(
                    ap_constants.AP_TEST_TYPE_CHAOS)
            factory.turn_off_all_routers(self._broken_pdus)
    def run_once(self,
                 host=None,
                 ssid=None,
                 passphrase=None,
                 wifi_iface=None,
                 wifi_ssid=None):
        """Check that a given wifi interface is properly configured.

        @param host: a host object representing the DUT.
        @param ssid: A string representing the ssid to connect to.
        @param passphrase: A string representing the passphrase to the ssid.
        @param wifi_iface: Name of the wifi interface to test; None means we'll
                           try to detect at least one that works.
        @param wifi_ssid: Name of the SSID we want the interface to be
                          connected to; None means any.

        @raise TestFail: The test failed.
        """
        self.host = host
        if afe_utils.host_in_lab(host):
            ssid = site_utils.get_wireless_ssid(host.hostname)
            passphrase = global_config.global_config.get_config_value(
                'CLIENT', 'wireless_password', default=None)
        with host_utils.connect_to_ssid(host, ssid, passphrase):
            err_iface = ('No interface is' if wifi_iface is None else
                         'Interface %s is not' % wifi_iface)

            # First check link status and SSID.
            iw = iw_runner.IwRunner(remote_host=host)
            active_ifaces = []
            try:
                iw_ifaces = [
                    iface_tuple.if_name
                    for iface_tuple in iw.list_interfaces()
                ]
                if wifi_iface is not None:
                    if wifi_iface not in iw_ifaces:
                        raise error.TestFail('Interface %s not listed by iw' %
                                             wifi_iface)
                    test_ifaces = [wifi_iface]
                else:
                    test_ifaces = iw_ifaces

                for iface in test_ifaces:
                    iface_ssid = iw.get_link_value(iface, 'SSID')
                    if (iface_ssid is not None and
                        (wifi_ssid is None or iface_ssid == wifi_ssid)):
                        active_ifaces.append(iface)
            except error.GenericHostRunError:
                raise error.TestFail('Failed to run iw')

            if not active_ifaces:
                err_ssid = 'any SSID' if wifi_ssid is None else ('SSID ' +
                                                                 wifi_ssid)
                raise error.TestFail('%s connected to %s' %
                                     (err_iface, err_ssid))

            logging.info('Active wifi interfaces: %s',
                         ', '.join(active_ifaces))

            # Then check IPv4 connectivity.
            try:
                ifconfig_output = host.run_output('ifconfig').splitlines()
            except error.GenericHostRunError:
                raise error.TestFail('Failed to run ifconfig')

            ifconfig_dict = self.get_ifconfig_dict(ifconfig_output)
            connected_ifaces = [
                iface for iface in active_ifaces if any([
                    'inet addr:' in line
                    for line in ifconfig_dict.get(iface, [])
                ])
            ]
            if not connected_ifaces:
                raise error.TestFail('%s IPv4 connected' % err_iface)

            logging.info('IPv4 connected wifi interfaces: %s',
                         ', '.join(connected_ifaces))
Beispiel #22
0
 def test_radio_information(self):
     """Test radio information parsing."""
     host = self.host(self.INFO_AP_MODE)
     runner = iw_runner.IwRunner(remote_host=host)
     self.assertEquals(runner.get_radio_config(self.INFO_IFACE),
                       self.RADIO_CONFIG_AP_MODE)
Beispiel #23
0
 def test_fragmentation_threshold(self):
     """Test fragmentation threshold parsing."""
     host = self.host(self.PHY_INFO_FRAGMENTATION)
     runner = iw_runner.IwRunner(remote_host=host)
     self.assertEquals(runner.get_fragmentation_threshold(self.INFO_PHY),
                       self.PHY_FRAGMENTATION_THRESHOLD)
Beispiel #24
0
 def test_operating_mode_station(self):
     """Test STA operating mode parsing."""
     host = self.host(self.INFO_STA_MODE)
     runner = iw_runner.IwRunner(remote_host=host)
     self.assertEquals(runner.get_operating_mode(self.INFO_IFACE),
                       iw_runner.DEV_MODE_STATION)
Beispiel #25
0
 def test_operating_mode_ap(self):
     """Test AP operating mode parsing."""
     host = self.host(self.INFO_AP_MODE)
     runner = iw_runner.IwRunner(remote_host=host)
     self.assertEquals(runner.get_operating_mode(self.INFO_IFACE),
                       iw_runner.DEV_MODE_AP)
Beispiel #26
0
 def test_operating_mode_mesh(self):
     """Test mesh operating mode parsing."""
     host = self.host(self.INFO_MESH_MODE)
     runner = iw_runner.IwRunner(remote_host=host)
     self.assertEquals(runner.get_operating_mode(self.INFO_IFACE),
                       iw_runner.DEV_MODE_MESH_POINT)
Beispiel #27
0
    def run_once(self, host):
        helper = privet_helper.PrivetHelper(host=host)
        logging.info('Looking for privet bootstrapping network from DUT.')
        scan_interface = self._router.get_wlanif(2437, 'managed')
        self._router.host.run('%s link set %s up' %
                              (self._router.cmd_ip, scan_interface))
        start_time = time.time()
        privet_bss = None
        while time.time() - start_time < PRIVET_AP_STARTUP_TIMEOUT_SECONDS:
            bss_list = self._router.iw_runner.scan(scan_interface)
            for bss in bss_list or []:
                if helper.is_softap_ssid(bss.ssid):
                    privet_bss = bss
        if privet_bss is None:
            raise error.TestFail('Device did not start soft AP in time.')
        self._router.release_interface(scan_interface)

        # Get the netblock of the interface running the AP.
        dut_iw_runner = iw_runner.IwRunner(remote_host=host)
        devs = dut_iw_runner.list_interfaces(desired_if_type='AP')
        if not devs:
            raise error.TestFail('No AP devices on DUT?')
        ap_interface = interface.Interface(devs[0].if_name, host=host)
        ap_netblock = netblock.from_addr(ap_interface.ipv4_address_and_prefix)

        # Set up an AP on the router in the 5Ghz range with WPA2 security.
        wpa_config = xmlrpc_security_types.WPAConfig(
                psk=PASSPHRASE,
                wpa_mode=xmlrpc_security_types.WPAConfig.MODE_PURE_WPA2,
                wpa2_ciphers=[xmlrpc_security_types.WPAConfig.CIPHER_CCMP])
        router_conf = hostap_config.HostapConfig(
                frequency=5240, security_config=wpa_config,
                mode=hostap_config.HostapConfig.MODE_11N_PURE)
        self._router.hostap_configure(router_conf)

        # Connect the other interface on the router to the AP on the client
        # at a hardcoded IP address.
        self._router.configure_managed_station(
                privet_bss.ssid, privet_bss.frequency,
                ap_netblock.get_addr_in_block(200))
        station_interface = self._router.get_station_interface(instance=0)
        logging.debug('Set up station on %s', station_interface)
        self._router.ping(ping_runner.PingConfig(ap_netblock.addr, count=3))

        logging.info('Looking for privet webserver in mDNS records.')
        start_time = time.time()
        while time.time() - start_time < PRIVET_MDNS_RECORD_TIMEOUT_SECONDS:
            all_records = avahi_utils.avahi_browse(host=self._router.host)
            records = [record for record in all_records
                       if (record.interface == station_interface and
                           record.record_type == '_privet._tcp')]
            if records:
                break
            time.sleep(POLLING_PERIOD)
        if not records:
            raise error.TestFail('Did not find privet mDNS records in time.')
        if len(records) > 1:
            raise error.TestFail('Should not see multiple privet records.')
        privet_record = records[0]
        # TODO(wiley) pull the HTTPs port number out of the /info API.
        helper = privet_helper.PrivetdHelper(
                host=self._router.host,
                hostname=privet_record.address,
                http_port=int(privet_record.port))
        helper.ping_server()

        # Now configure the client with WiFi credentials.
        auth_token = helper.privet_auth()
        ssid = self._router.get_ssid()
        data = helper.setup_add_wifi_credentials(ssid, PASSPHRASE)
        helper.setup_start(data, auth_token)

        logging.info('Waiting for DUT to connect to router network.')
        start_time = time.time()
        # Wait for the DUT to take down the AP.
        while time.time() - start_time < PRIVET_CONNECT_TIMEOUT_SECONDS:
            if not dut_iw_runner.list_interfaces(desired_if_type='AP'):
                break
            time.sleep(POLLING_PERIOD)
        else:
            raise error.TestFail('Timeout waiting for DUT to take down AP.')

        # But we should be able to ping the client from the router's AP.
        while time.time() - start_time < PRIVET_CONNECT_TIMEOUT_SECONDS:
            if dut_iw_runner.list_interfaces(desired_if_type='managed'):
                break
            time.sleep(POLLING_PERIOD)
        else:
            raise error.TestFail('Timeout waiting for DUT managerd interface.')

        while time.time() - start_time < PRIVET_CONNECT_TIMEOUT_SECONDS:
            devs = dut_iw_runner.list_interfaces(desired_if_type='managed')
            if devs:
                managed_interface = interface.Interface(devs[0].if_name,
                                                        host=host)
                # Check if we have an IP yet.
                if managed_interface.ipv4_address_and_prefix:
                    break
            time.sleep(POLLING_PERIOD)
        else:
            raise error.TestFail('Timeout waiting for DUT managerd interface.')

        managed_netblock = netblock.from_addr(
                managed_interface.ipv4_address_and_prefix)
        while time.time() - start_time < PRIVET_CONNECT_TIMEOUT_SECONDS:
            PING_COUNT = 3
            result = self._router.ping(
                    ping_runner.PingConfig(managed_netblock.addr,
                                           ignore_result=True,
                                           count=PING_COUNT))
            if result.received == PING_COUNT:
                break
            time.sleep(POLLING_PERIOD)
        else:
            raise error.TestFail('Timeout before ping was successful.')

        # And buffet should think it is online as well.
        helper = privet_helper.PrivetdHelper(
                host=host, hostname=managed_netblock.addr,
                http_port=int(privet_record.port))
        helper.ping_server()
        if not helper.wifi_setup_was_successful(ssid, auth_token):
            raise error.TestFail('Device claims to be offline, but is online.')
Beispiel #28
0
 def test_station_bssid(self):
     """Test parsing of the bssid of a station-mode link."""
     host = self.host(self.STATION_LINK_INFORMATION)
     runner = iw_runner.IwRunner(remote_host=host)
     self.assertEquals(runner.get_current_bssid(self.STATION_LINK_IFACE),
                       self.STATION_LINK_BSSID)