blob: abf5c7149c7312ebc75c979353ce917169ca7d94 [file] [log] [blame]
# Copyright (c) 2013 The Chromium OS Authors. All rights reserved.
# Use of this source code is governed by a BSD-style license that can be
# found in the LICENSE file.
import logging
import time
from autotest_lib.client.common_lib import error
from autotest_lib.client.common_lib.cros.network import xmlrpc_datatypes
from autotest_lib.server import site_linux_system
from autotest_lib.server.cros.network import hostap_config
from autotest_lib.server.cros.network import wifi_cell_test_base
class network_WiFi_VerifyRouter(wifi_cell_test_base.WiFiCellTestBase):
"""Test that a dual radio router can use both radios."""
version = 1
MAX_ASSOCIATION_RETRIES = 8 # Super lucky number. Not science.
def _connect(self, wifi_params):
assoc_result = xmlrpc_datatypes.deserialize(
self.context.client.shill.connect_wifi(wifi_params))
logging.info('Finished connection attempt to %s with times: '
'discovery=%.2f, association=%.2f, configuration=%.2f.',
wifi_params.ssid,
assoc_result.discovery_time,
assoc_result.association_time,
assoc_result.configuration_time)
return assoc_result.success
def _antenna_test(self, bitmap, channel):
"""Test to verify each antenna is working on given band.
Setup AP in each radio in given band, and run connection test with one
antenna active at a time, to verify each antenna in each radio is
working correctly for given band. Antenna can only be configured when
the wireless interface is down.
@param bitmap: int bitmask controlling which antennas to enable.
@param channel: int Wifi channel to conduct test on
"""
# Connect to AP with only one antenna active at a time
self.context.router.deconfig()
# Set the bitmasks to both antennas on before turning one off.
self.context.router.set_antenna_bitmap(3, 3)
# This seems to increase the probability that our association
# attempts pass. It is the very definition of a dark incantation.
time.sleep(5)
if bitmap != 3:
self.context.router.set_antenna_bitmap(bitmap, bitmap)
# Setup two APs in the same band
n_mode = hostap_config.HostapConfig.MODE_11N_MIXED
ap_config = hostap_config.HostapConfig(channel=channel, mode=n_mode)
self.context.configure(ap_config)
self.context.configure(ap_config, multi_interface=True)
failures = []
# Verify connectivity to both APs
for instance in range(2):
context_message = ('bitmap=%d, ap_instance=%d, channel=%d' %
(bitmap, instance, channel))
logging.info('Connecting to AP with settings %s.',
context_message)
client_conf = xmlrpc_datatypes.AssociationParameters(
ssid=self.context.router.get_ssid(instance=instance))
if self._connect(client_conf):
signal_level = self.context.client.wifi_signal_level
logging.info('Signal level for AP %d with bitmap %d is %d',
instance, bitmap, signal_level)
self.write_perf_keyval(
{'signal_for_ap_%d_bm_%d_ch_%d' %
(instance, bitmap, channel):
signal_level})
else:
failures.append(context_message)
# Don't automatically reconnect to this AP.
self.context.client.shill.disconnect(
self.context.router.get_ssid(instance=instance))
return failures
def cleanup(self):
"""Clean up after the test is completed
Perform additional cleanups after the test, the important thing is
to restore default antennas bitmap.
"""
self.context.router.deconfig()
self.context.router.set_default_antenna_bitmap()
super(network_WiFi_VerifyRouter, self).cleanup()
def run_once(self):
"""Set up two APs connect to both and then exit."""
self.context.router.require_capabilities(
[site_linux_system.LinuxSystem.CAPABILITY_MULTI_AP_SAME_BAND])
all_failures = []
# Run antenna test for 2GHz band and 5GHz band
for channel in (6, 149):
for bitmap in (3, 1, 2):
failures = set()
for attempt in range(self.MAX_ASSOCIATION_RETRIES):
new_failures = self._antenna_test(bitmap, channel)
if not new_failures:
break
failures.update(new_failures)
else:
all_failures += failures
if all_failures:
failure_message = ', '.join(
['(' + message + ')' for message in all_failures])
raise error.TestFail('Failed to connect when %s.' % failure_message)