1#!/usr/bin/env python3 2# 3# Copyright (C) 2019 The Android Open Source Project 4# 5# Licensed under the Apache License, Version 2.0 (the "License"); you may not 6# use this file except in compliance with the License. You may obtain a copy of 7# the License at 8# 9# http://www.apache.org/licenses/LICENSE-2.0 10# 11# Unless required by applicable law or agreed to in writing, software 12# distributed under the License is distributed on an "AS IS" BASIS, WITHOUT 13# WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the 14# License for the specific language governing permissions and limitations under 15# the License. 16""" 17Script for testing WiFi recovery after rebooting the AP. 18 19Override default number of iterations using the following 20parameter in the test config file. 21 22"beacon_loss_test_iterations": "5" 23""" 24 25import os 26import uuid 27import time 28 29from acts import asserts 30from acts import signals 31from acts import utils 32from acts.base_test import BaseTestClass 33from acts.controllers.ap_lib import hostapd_constants 34from acts.test_utils.abstract_devices.utils_lib.wlan_utils import disconnect 35from acts.test_utils.abstract_devices.utils_lib.wlan_utils import setup_ap 36from acts.test_utils.abstract_devices.utils_lib.wlan_utils import associate 37from acts.test_utils.abstract_devices.wlan_device import create_wlan_device 38from acts.test_utils.abstract_devices.wlan_device_lib.AbstractDeviceWlanDeviceBaseTest import AbstractDeviceWlanDeviceBaseTest 39from acts.utils import rand_ascii_str 40 41 42class BeaconLossTest(AbstractDeviceWlanDeviceBaseTest): 43 # Default number of test iterations here. 44 # Override using parameter in config file. 45 # Eg: "beacon_loss_test_iterations": "10" 46 num_of_iterations = 5 47 48 # Time to wait for AP to startup 49 wait_ap_startup_s = 15 50 51 # Default wait time in seconds for the AP radio to turn back on 52 wait_to_connect_after_ap_txon_s = 5 53 54 # Time to wait for device to disconnect after AP radio of 55 wait_after_ap_txoff_s = 15 56 57 # Time to wait for device to complete connection setup after 58 # given an associate command 59 wait_client_connection_setup_s = 15 60 61 def setup_class(self): 62 super().setup_class() 63 self.ssid = rand_ascii_str(10) 64 self.wlan_device = create_wlan_device(self.fuchsia_devices[0]) 65 self.ap = self.access_points[0] 66 self.num_of_iterations = int( 67 self.user_params.get("beacon_loss_test_iterations", 68 self.num_of_iterations)) 69 self.in_use_interface = None 70 71 def teardown_test(self): 72 disconnect(self.wlan_device) 73 self.wlan_device.reset_wifi() 74 # ensure radio is on, in case the test failed while the radio was off 75 self.ap.iwconfig.ap_iwconfig(self.in_use_interface, "txpower on") 76 self.ap.stop_all_aps() 77 78 def on_fail(self, test_name, begin_time): 79 super().on_fail(test_name, begin_time) 80 self.access_point.stop_all_aps() 81 82 def beacon_loss(self, channel): 83 setup_ap(access_point=self.ap, 84 profile_name='whirlwind', 85 channel=channel, 86 ssid=self.ssid) 87 time.sleep(self.wait_ap_startup_s) 88 if channel > 14: 89 self.in_use_interface = self.ap.wlan_5g 90 else: 91 self.in_use_interface = self.ap.wlan_2g 92 93 # TODO(b/144505723): [ACTS] update BeaconLossTest.py to handle client 94 # roaming, saved networks, etc. 95 self.log.info("sending associate command for ssid %s", self.ssid) 96 associate(client=self.wlan_device, ssid=self.ssid) 97 98 asserts.assert_true(self.wlan_device.is_connected(), 99 'Failed to connect.') 100 101 time.sleep(self.wait_client_connection_setup_s) 102 103 for _ in range(0, self.num_of_iterations): 104 # Turn off AP radio 105 self.log.info("turning off radio") 106 self.ap.iwconfig.ap_iwconfig(self.in_use_interface, "txpower off") 107 time.sleep(self.wait_after_ap_txoff_s) 108 109 # Did we disconnect from AP? 110 asserts.assert_false(self.wlan_device.is_connected(), 111 'Failed to disconnect.') 112 113 # Turn on AP radio 114 self.log.info("turning on radio") 115 self.ap.iwconfig.ap_iwconfig(self.in_use_interface, "txpower on") 116 time.sleep(self.wait_to_connect_after_ap_txon_s) 117 118 # Tell the client to connect 119 self.log.info("sending associate command for ssid %s" % self.ssid) 120 associate(client=self.wlan_device, ssid=self.ssid) 121 time.sleep(self.wait_client_connection_setup_s) 122 123 # Did we connect back to WiFi? 124 asserts.assert_true(self.wlan_device.is_connected(), 125 'Failed to connect back.') 126 127 return True 128 129 def test_beacon_loss_2g(self): 130 self.beacon_loss(channel=hostapd_constants.AP_DEFAULT_CHANNEL_2G) 131 132 def test_beacon_loss_5g(self): 133 self.beacon_loss(channel=hostapd_constants.AP_DEFAULT_CHANNEL_5G) 134