]>
git.ipfire.org Git - thirdparty/hostap.git/blob - tests/hwsim/test_scan.py
2 # Copyright (c) 2013, Jouni Malinen <j@w1.fi>
4 # This software may be distributed under the terms of the BSD license.
5 # See README for more details.
9 logger
= logging
.getLogger()
15 def check_scan(dev
, params
, other_started
=False):
18 id = dev
.request("SCAN " + params
)
20 raise Exception("Failed to start scan")
24 ev
= dev
.wait_event(["CTRL-EVENT-SCAN-STARTED"])
26 raise Exception("Other scan did not start")
27 if "id=" + str(id) in ev
:
28 raise Exception("Own scan id unexpectedly included in start event")
30 ev
= dev
.wait_event(["CTRL-EVENT-SCAN-RESULTS"])
32 raise Exception("Other scan did not complete")
33 if "id=" + str(id) in ev
:
34 raise Exception("Own scan id unexpectedly included in completed event")
36 ev
= dev
.wait_event(["CTRL-EVENT-SCAN-STARTED"])
38 raise Exception("Scan did not start")
39 if "id=" + str(id) not in ev
:
40 raise Exception("Scan id not included in start event")
42 ev
= dev
.wait_event(["CTRL-EVENT-SCAN-RESULTS"])
44 raise Exception("Scan did not complete")
45 if "id=" + str(id) not in ev
:
46 raise Exception("Scan id not included in completed event")
48 def check_scan_retry(dev
, params
, bssid
):
50 check_scan(dev
, "freq=2412-2462,5180 use_id=1")
51 if int(dev
.get_bss(bssid
)['age']) <= 1:
53 raise Exception("Unexpectedly old BSS entry")
55 def test_scan(dev
, apdev
):
56 """Control interface behavior on scan parameters"""
57 hostapd
.add_ap(apdev
[0]['ifname'], { "ssid": "test-scan" })
58 bssid
= apdev
[0]['bssid']
60 logger
.info("Full scan")
61 check_scan(dev
[0], "use_id=1")
63 logger
.info("Limited channel scan")
64 check_scan_retry(dev
[0], "freq=2412-2462,5180 use_id=1", bssid
)
66 # wait long enough to allow next scans to be verified not to find the AP
69 logger
.info("Passive single-channel scan")
70 check_scan(dev
[0], "freq=2457 passive=1 use_id=1")
71 logger
.info("Active single-channel scan")
72 check_scan(dev
[0], "freq=2452 passive=0 use_id=1")
73 if int(dev
[0].get_bss(bssid
)['age']) < 2:
74 raise Exception("Unexpectedly updated BSS entry")
76 logger
.info("Active single-channel scan on AP's operating channel")
77 check_scan_retry(dev
[0], "freq=2412 passive=0 use_id=1", bssid
)
79 def test_scan_only(dev
, apdev
):
80 """Control interface behavior on scan parameters with type=only"""
81 hostapd
.add_ap(apdev
[0]['ifname'], { "ssid": "test-scan" })
82 bssid
= apdev
[0]['bssid']
84 logger
.info("Full scan")
85 check_scan(dev
[0], "type=only use_id=1")
87 logger
.info("Limited channel scan")
88 check_scan_retry(dev
[0], "type=only freq=2412-2462,5180 use_id=1", bssid
)
90 # wait long enough to allow next scans to be verified not to find the AP
93 logger
.info("Passive single-channel scan")
94 check_scan(dev
[0], "type=only freq=2457 passive=1 use_id=1")
95 logger
.info("Active single-channel scan")
96 check_scan(dev
[0], "type=only freq=2452 passive=0 use_id=1")
97 if int(dev
[0].get_bss(bssid
)['age']) < 2:
98 raise Exception("Unexpectedly updated BSS entry")
100 logger
.info("Active single-channel scan on AP's operating channel")
101 check_scan_retry(dev
[0], "type=only freq=2412 passive=0 use_id=1", bssid
)
103 def test_scan_external_trigger(dev
, apdev
):
104 """Avoid operations during externally triggered scan"""
105 hostapd
.add_ap(apdev
[0]['ifname'], { "ssid": "test-scan" })
106 bssid
= apdev
[0]['bssid']
107 subprocess
.call(['sudo', 'iw', dev
[0].ifname
, 'scan', 'trigger'])
108 check_scan(dev
[0], "use_id=1", other_started
=True)
110 def test_scan_bss_expiration_count(dev
, apdev
):
111 """BSS entry expiration based on scan results without match"""
112 if "FAIL" not in dev
[0].request("BSS_EXPIRE_COUNT 0"):
113 raise Exception("Invalid BSS_EXPIRE_COUNT accepted")
114 if "OK" not in dev
[0].request("BSS_EXPIRE_COUNT 2"):
115 raise Exception("BSS_EXPIRE_COUNT failed")
116 hapd
= hostapd
.add_ap(apdev
[0]['ifname'], { "ssid": "test-scan" })
117 bssid
= apdev
[0]['bssid']
118 dev
[0].scan(freq
="2412", only_new
=True)
119 if bssid
not in dev
[0].request("SCAN_RESULTS"):
120 raise Exception("BSS not found in initial scan")
121 hapd
.request("DISABLE")
122 dev
[0].scan(freq
="2412", only_new
=True)
123 if bssid
not in dev
[0].request("SCAN_RESULTS"):
124 raise Exception("BSS not found in first scan without match")
125 dev
[0].scan(freq
="2412", only_new
=True)
126 if bssid
in dev
[0].request("SCAN_RESULTS"):
127 raise Exception("BSS found after two scans without match")
129 def test_scan_bss_expiration_age(dev
, apdev
):
130 """BSS entry expiration based on age"""
132 if "FAIL" not in dev
[0].request("BSS_EXPIRE_AGE COUNT 9"):
133 raise Exception("Invalid BSS_EXPIRE_AGE accepted")
134 if "OK" not in dev
[0].request("BSS_EXPIRE_AGE 10"):
135 raise Exception("BSS_EXPIRE_AGE failed")
136 hapd
= hostapd
.add_ap(apdev
[0]['ifname'], { "ssid": "test-scan" })
137 bssid
= apdev
[0]['bssid']
138 dev
[0].scan(freq
="2412")
139 if bssid
not in dev
[0].request("SCAN_RESULTS"):
140 raise Exception("BSS not found in initial scan")
141 hapd
.request("DISABLE")
142 logger
.info("Waiting for BSS entry to expire")
144 if bssid
not in dev
[0].request("SCAN_RESULTS"):
145 raise Exception("BSS expired too quickly")
146 ev
= dev
[0].wait_event(["CTRL-EVENT-BSS-REMOVED"], timeout
=15)
148 raise Exception("BSS entry expiration timed out")
149 if bssid
in dev
[0].request("SCAN_RESULTS"):
150 raise Exception("BSS not removed after expiration time")
152 dev
[0].request("BSS_EXPIRE_AGE 180")
154 def test_scan_filter(dev
, apdev
):
155 """Filter scan results based on SSID"""
157 if "OK" not in dev
[0].request("SET filter_ssids 1"):
158 raise Exception("SET failed")
159 dev
[0].connect("test-scan", key_mgmt
="NONE", only_add_network
=True)
160 hostapd
.add_ap(apdev
[0]['ifname'], { "ssid": "test-scan" })
161 bssid
= apdev
[0]['bssid']
162 hostapd
.add_ap(apdev
[1]['ifname'], { "ssid": "test-scan2" })
163 bssid2
= apdev
[1]['bssid']
164 dev
[0].scan(freq
="2412", only_new
=True)
165 if bssid
not in dev
[0].request("SCAN_RESULTS"):
166 raise Exception("BSS not found in scan results")
167 if bssid2
in dev
[0].request("SCAN_RESULTS"):
168 raise Exception("Unexpected BSS found in scan results")
170 dev
[0].request("SET filter_ssids 0")
172 def test_scan_int(dev
, apdev
):
173 """scan interval configuration"""
175 if "FAIL" not in dev
[0].request("SCAN_INTERVAL -1"):
176 raise Exception("Accepted invalid scan interval")
177 if "OK" not in dev
[0].request("SCAN_INTERVAL 1"):
178 raise Exception("Failed to set scan interval")
179 dev
[0].connect("not-used", key_mgmt
="NONE", scan_freq
="2412",
182 for i
in range(0, 3):
183 logger
.info("Waiting for scan to start")
184 start
= os
.times()[4]
185 ev
= dev
[0].wait_event(["CTRL-EVENT-SCAN-STARTED"], timeout
=5)
187 raise Exception("did not start a scan")
189 times
[i
] = stop
- start
190 logger
.info("Waiting for scan to complete")
191 ev
= dev
[0].wait_event(["CTRL-EVENT-SCAN-RESULTS"], 10)
193 raise Exception("did not complete a scan")
195 if times
[0] > 1 or times
[1] < 0.5 or times
[1] > 1.5 or times
[2] < 0.5 or times
[2] > 1.5:
196 raise Exception("Unexpected scan timing: " + str(times
))
198 dev
[0].request("SCAN_INTERVAL 5")
200 def test_scan_bss_operations(dev
, apdev
):
201 """Control interface behavior on BSS parameters"""
202 hostapd
.add_ap(apdev
[0]['ifname'], { "ssid": "test-scan" })
203 bssid
= apdev
[0]['bssid']
204 hostapd
.add_ap(apdev
[1]['ifname'], { "ssid": "test2-scan" })
205 bssid2
= apdev
[1]['bssid']
207 dev
[0].scan(freq
="2412")
208 dev
[0].scan(freq
="2412")
209 dev
[0].scan(freq
="2412")
211 id1
= dev
[0].request("BSS FIRST MASK=0x1").splitlines()[0].split('=')[1]
212 id2
= dev
[0].request("BSS LAST MASK=0x1").splitlines()[0].split('=')[1]
214 res
= dev
[0].request("BSS RANGE=ALL MASK=0x20001")
215 if "id=" + id1
not in res
:
216 raise Exception("Missing BSS " + id1
)
217 if "id=" + id2
not in res
:
218 raise Exception("Missing BSS " + id2
)
219 if "====" not in res
:
220 raise Exception("Missing delim")
221 if "####" not in res
:
222 raise Exception("Missing end")
224 res
= dev
[0].request("BSS RANGE=ALL MASK=0x1").splitlines()
226 raise Exception("Unexpected result")
227 res
= dev
[0].request("BSS FIRST MASK=0x1")
228 if "id=" + id1
not in res
:
229 raise Exception("Unexpected result: " + res
)
230 res
= dev
[0].request("BSS LAST MASK=0x1")
231 if "id=" + id2
not in res
:
232 raise Exception("Unexpected result: " + res
)
233 res
= dev
[0].request("BSS ID-" + id1
+ " MASK=0x1")
234 if "id=" + id1
not in res
:
235 raise Exception("Unexpected result: " + res
)
236 res
= dev
[0].request("BSS NEXT-" + id1
+ " MASK=0x1")
237 if "id=" + id2
not in res
:
238 raise Exception("Unexpected result: " + res
)
240 if len(dev
[0].request("BSS RANGE=" + id2
+ " MASK=0x1").splitlines()) != 0:
241 raise Exception("Unexpected RANGE=1 result")
242 if len(dev
[0].request("BSS RANGE=" + id1
+ "- MASK=0x1").splitlines()) != 2:
243 raise Exception("Unexpected RANGE=0- result")
244 if len(dev
[0].request("BSS RANGE=-" + id2
+ " MASK=0x1").splitlines()) != 2:
245 raise Exception("Unexpected RANGE=-1 result")
246 if len(dev
[0].request("BSS RANGE=" + id1
+ "-" + id2
+ " MASK=0x1").splitlines()) != 2:
247 raise Exception("Unexpected RANGE=0-1 result")
248 if len(dev
[0].request("BSS RANGE=" + id2
+ "-" + id2
+ " MASK=0x1").splitlines()) != 1:
249 raise Exception("Unexpected RANGE=1-1 result")
250 if len(dev
[0].request("BSS RANGE=" + str(int(id2
) + 1) + "-" + str(int(id2
) + 10) + " MASK=0x1").splitlines()) != 0:
251 raise Exception("Unexpected RANGE=2-10 result")
252 if len(dev
[0].request("BSS RANGE=0-" + str(int(id2
) + 10) + " MASK=0x1").splitlines()) != 2:
253 raise Exception("Unexpected RANGE=0-10 result")