1# Protected management frames tests 2# Copyright (c) 2013-2024, Jouni Malinen <j@w1.fi> 3# 4# This software may be distributed under the terms of the BSD license. 5# See README for more details. 6 7from remotehost import remote_compatible 8import binascii 9import os 10import time 11import logging 12logger = logging.getLogger() 13 14import hwsim_utils 15import hostapd 16from utils import * 17from wlantest import Wlantest 18from wpasupplicant import WpaSupplicant 19from test_eap_proto import rx_msg, tx_msg, proxy_msg 20 21@remote_compatible 22def test_ap_pmf_required(dev, apdev): 23 """WPA2-PSK AP with PMF required""" 24 ssid = "test-pmf-required" 25 params = hostapd.wpa2_params(ssid=ssid, passphrase="12345678") 26 params["wpa_key_mgmt"] = "WPA-PSK-SHA256" 27 params["ieee80211w"] = "2" 28 hapd = hostapd.add_ap(apdev[0], params) 29 Wlantest.setup(hapd) 30 wt = Wlantest() 31 wt.flush() 32 wt.add_passphrase("12345678") 33 key_mgmt = hapd.get_config()['key_mgmt'] 34 if key_mgmt.split(' ')[0] != "WPA-PSK-SHA256": 35 raise Exception("Unexpected GET_CONFIG(key_mgmt): " + key_mgmt) 36 dev[0].connect(ssid, psk="12345678", ieee80211w="1", 37 key_mgmt="WPA-PSK WPA-PSK-SHA256", proto="WPA2", 38 scan_freq="2412") 39 if "[WPA2-PSK-SHA256-CCMP]" not in dev[0].request("SCAN_RESULTS"): 40 raise Exception("Scan results missing RSN element info") 41 hwsim_utils.test_connectivity(dev[0], hapd) 42 dev[1].connect(ssid, psk="12345678", ieee80211w="2", 43 key_mgmt="WPA-PSK WPA-PSK-SHA256", proto="WPA2", 44 scan_freq="2412") 45 hwsim_utils.test_connectivity(dev[1], hapd) 46 if "OK" not in hapd.request("SA_QUERY " + dev[0].own_addr()): 47 raise Exception("SA_QUERY failed") 48 if "OK" not in hapd.request("SA_QUERY " + dev[1].own_addr()): 49 raise Exception("SA_QUERY failed") 50 if "FAIL" not in hapd.request("SA_QUERY foo"): 51 raise Exception("Invalid SA_QUERY accepted") 52 wt.require_ap_pmf_mandatory(apdev[0]['bssid']) 53 wt.require_sta_pmf(apdev[0]['bssid'], dev[0].p2p_interface_addr()) 54 wt.require_sta_pmf_mandatory(apdev[0]['bssid'], dev[1].p2p_interface_addr()) 55 time.sleep(0.1) 56 if wt.get_sta_counter("valid_saqueryresp_tx", apdev[0]['bssid'], 57 dev[0].p2p_interface_addr()) < 1: 58 raise Exception("STA did not reply to SA Query") 59 if wt.get_sta_counter("valid_saqueryresp_tx", apdev[0]['bssid'], 60 dev[1].p2p_interface_addr()) < 1: 61 raise Exception("STA did not reply to SA Query") 62 63def start_ocv_ap(apdev): 64 ssid = "test-pmf-required" 65 params = hostapd.wpa2_params(ssid=ssid, passphrase="12345678") 66 params["wpa_key_mgmt"] = "WPA-PSK-SHA256" 67 params["ieee80211w"] = "2" 68 params["ocv"] = "1" 69 try: 70 hapd = hostapd.add_ap(apdev, params) 71 except Exception as e: 72 if "Failed to set hostapd parameter ocv" in str(e): 73 raise HwsimSkip("OCV not supported") 74 raise 75 76 Wlantest.setup(hapd) 77 wt = Wlantest() 78 wt.flush() 79 wt.add_passphrase("12345678") 80 81 return hapd, ssid, wt 82 83@remote_compatible 84def test_ocv_sa_query(dev, apdev): 85 """Test SA Query with OCV""" 86 hapd, ssid, wt = start_ocv_ap(apdev[0]) 87 dev[0].connect(ssid, psk="12345678", ieee80211w="1", ocv="1", 88 key_mgmt="WPA-PSK WPA-PSK-SHA256", proto="WPA2", 89 scan_freq="2412") 90 hapd.wait_sta() # wait so we can actually request SA_QUERY 91 # Test that client can handle SA Query with OCI element 92 if "OK" not in hapd.request("SA_QUERY " + dev[0].own_addr()): 93 raise Exception("SA_QUERY failed") 94 ev = hapd.wait_event(["OCV-FAILURE"], timeout=0.1) 95 if ev: 96 raise Exception("Unexpected OCV failure reported") 97 if wt.get_sta_counter("valid_saqueryresp_tx", apdev[0]['bssid'], 98 dev[0].own_addr()) < 1: 99 raise Exception("STA did not reply to SA Query") 100 101 # Test that AP can handle SA Query with OCI element 102 if "OK" not in dev[0].request("UNPROT_DEAUTH"): 103 raise Exception("Triggering SA Query from the STA failed") 104 ev = dev[0].wait_event(["CTRL-EVENT-DISCONNECTED"], timeout=3) 105 if ev is not None: 106 raise Exception("SA Query from the STA failed") 107 108@remote_compatible 109def test_ocv_sa_query_csa(dev, apdev): 110 """Test SA Query with OCV after channel switch""" 111 hapd, ssid, wt = start_ocv_ap(apdev[0]) 112 dev[0].connect(ssid, psk="12345678", ieee80211w="1", ocv="1", 113 key_mgmt="WPA-PSK WPA-PSK-SHA256", proto="WPA2", 114 scan_freq="2412") 115 116 hapd.request("CHAN_SWITCH 5 2437 ht") 117 time.sleep(1) 118 if wt.get_sta_counter("valid_saqueryreq_tx", apdev[0]['bssid'], 119 dev[0].own_addr()) < 1: 120 raise Exception("STA did not start SA Query after channel switch") 121 122 ev = dev[0].wait_event(["CTRL-EVENT-DISCONNECTED"], timeout=16) 123 if ev is not None: 124 raise Exception("Unexpected disconnection") 125 126def test_ocv_sa_query_csa_no_resp(dev, apdev): 127 """Test SA Query with OCV after channel switch getting no response""" 128 hapd, ssid, wt = start_ocv_ap(apdev[0]) 129 dev[0].connect(ssid, psk="12345678", ieee80211w="1", ocv="1", 130 key_mgmt="WPA-PSK WPA-PSK-SHA256", proto="WPA2", 131 scan_freq="2412") 132 133 hapd.set("ext_mgmt_frame_handling", "1") 134 hapd.request("CHAN_SWITCH 5 2437 ht") 135 ev = dev[0].wait_event(["CTRL-EVENT-DISCONNECTED"], timeout=5) 136 if ev is None: 137 raise Exception("Disconnection after CSA not reported") 138 if "locally_generated=1" not in ev: 139 raise Exception("Unexpectedly disconnected by AP: " + ev) 140 141def test_ocv_sa_query_csa_missing(dev, apdev): 142 """Test SA Query with OCV missing after channel switch""" 143 hapd, ssid, wt = start_ocv_ap(apdev[0]) 144 dev[0].connect(ssid, psk="12345678", ieee80211w="1", ocv="1", 145 key_mgmt="WPA-PSK WPA-PSK-SHA256", proto="WPA2", 146 scan_freq="2412") 147 hapd.wait_sta() # wait so kernel won't drop deauth frame (MFP) 148 hapd.set("ext_mgmt_frame_handling", "1") 149 dev[0].request("DISCONNECT") 150 dev[0].wait_disconnected() 151 ev = hapd.wait_event(['MGMT-RX'], timeout=5) 152 if ev is None: 153 raise Exception("Deauthentication frame RX not reported") 154 hapd.set("ext_mgmt_frame_handling", "0") 155 hapd.request("CHAN_SWITCH 5 2437 ht") 156 ev = hapd.wait_event(["AP-STA-DISCONNECTED"], timeout=20) 157 if ev is None: 158 raise Exception("No disconnection event received from hostapd") 159 160@remote_compatible 161def test_ap_pmf_optional(dev, apdev): 162 """WPA2-PSK AP with PMF optional""" 163 ssid = "test-pmf-optional" 164 params = hostapd.wpa2_params(ssid=ssid, passphrase="12345678") 165 params["wpa_key_mgmt"] = "WPA-PSK" 166 params["ieee80211w"] = "1" 167 hapd = hostapd.add_ap(apdev[0], params) 168 Wlantest.setup(hapd) 169 wt = Wlantest() 170 wt.flush() 171 wt.add_passphrase("12345678") 172 dev[0].connect(ssid, psk="12345678", ieee80211w="1", 173 key_mgmt="WPA-PSK WPA-PSK-SHA256", proto="WPA2", 174 scan_freq="2412") 175 hwsim_utils.test_connectivity(dev[0], hapd) 176 dev[1].connect(ssid, psk="12345678", ieee80211w="2", 177 key_mgmt="WPA-PSK WPA-PSK-SHA256", proto="WPA2", 178 scan_freq="2412") 179 hwsim_utils.test_connectivity(dev[1], hapd) 180 wt.require_ap_pmf_optional(apdev[0]['bssid']) 181 wt.require_sta_pmf(apdev[0]['bssid'], dev[0].p2p_interface_addr()) 182 wt.require_sta_pmf_mandatory(apdev[0]['bssid'], dev[1].p2p_interface_addr()) 183 184@remote_compatible 185def test_ap_pmf_optional_2akm(dev, apdev): 186 """WPA2-PSK AP with PMF optional (2 AKMs)""" 187 ssid = "test-pmf-optional-2akm" 188 params = hostapd.wpa2_params(ssid=ssid, passphrase="12345678") 189 params["wpa_key_mgmt"] = "WPA-PSK WPA-PSK-SHA256" 190 params["ieee80211w"] = "1" 191 hapd = hostapd.add_ap(apdev[0], params) 192 Wlantest.setup(hapd) 193 wt = Wlantest() 194 wt.flush() 195 wt.add_passphrase("12345678") 196 dev[0].connect(ssid, psk="12345678", ieee80211w="1", 197 key_mgmt="WPA-PSK WPA-PSK-SHA256", proto="WPA2", 198 scan_freq="2412") 199 hwsim_utils.test_connectivity(dev[0], hapd) 200 dev[1].connect(ssid, psk="12345678", ieee80211w="2", 201 key_mgmt="WPA-PSK WPA-PSK-SHA256", proto="WPA2", 202 scan_freq="2412") 203 hwsim_utils.test_connectivity(dev[1], hapd) 204 wt.require_ap_pmf_optional(apdev[0]['bssid']) 205 wt.require_sta_pmf(apdev[0]['bssid'], dev[0].p2p_interface_addr()) 206 wt.require_sta_key_mgmt(apdev[0]['bssid'], dev[0].p2p_interface_addr(), 207 "PSK-SHA256") 208 wt.require_sta_pmf_mandatory(apdev[0]['bssid'], dev[1].p2p_interface_addr()) 209 wt.require_sta_key_mgmt(apdev[0]['bssid'], dev[1].p2p_interface_addr(), 210 "PSK-SHA256") 211 212@remote_compatible 213def test_ap_pmf_negative(dev, apdev): 214 """WPA2-PSK AP without PMF (negative test)""" 215 ssid = "test-pmf-negative" 216 params = hostapd.wpa2_params(ssid=ssid, passphrase="12345678") 217 hapd = hostapd.add_ap(apdev[0], params) 218 Wlantest.setup(hapd) 219 wt = Wlantest() 220 wt.flush() 221 wt.add_passphrase("12345678") 222 dev[0].connect(ssid, psk="12345678", ieee80211w="1", 223 key_mgmt="WPA-PSK WPA-PSK-SHA256", proto="WPA2", 224 scan_freq="2412") 225 hwsim_utils.test_connectivity(dev[0], hapd) 226 try: 227 dev[1].connect(ssid, psk="12345678", ieee80211w="2", 228 key_mgmt="WPA-PSK WPA-PSK-SHA256", proto="WPA2", 229 scan_freq="2412") 230 hwsim_utils.test_connectivity(dev[1], hapd) 231 raise Exception("PMF required STA connected to no PMF AP") 232 except Exception as e: 233 logger.debug("Ignore expected exception: " + str(e)) 234 wt.require_ap_no_pmf(apdev[0]['bssid']) 235 236@remote_compatible 237def test_ap_pmf_assoc_comeback(dev, apdev): 238 """WPA2-PSK AP with PMF association comeback""" 239 run_ap_pmf_assoc_comeback(dev, apdev) 240 241def test_ap_pmf_assoc_comeback_10000tu(dev, apdev): 242 """WPA2-PSK AP with PMF association comeback (10000 TUs)""" 243 run_ap_pmf_assoc_comeback(dev, apdev, comeback=10000) 244 245def run_ap_pmf_assoc_comeback(dev, apdev, comeback=None): 246 ssid = "assoc-comeback" 247 params = hostapd.wpa2_params(ssid=ssid, passphrase="12345678") 248 params["wpa_key_mgmt"] = "WPA-PSK-SHA256" 249 params["ieee80211w"] = "2" 250 if comeback is not None: 251 params["assoc_sa_query_max_timeout"] = str(comeback) 252 hapd = hostapd.add_ap(apdev[0], params) 253 Wlantest.setup(hapd) 254 wt = Wlantest() 255 wt.flush() 256 wt.add_passphrase("12345678") 257 dev[0].connect(ssid, psk="12345678", ieee80211w="1", 258 key_mgmt="WPA-PSK WPA-PSK-SHA256", proto="WPA2", 259 scan_freq="2412") 260 hapd.wait_sta(wait_4way_hs=True) 261 hapd.set("ext_mgmt_frame_handling", "1") 262 dev[0].request("DISCONNECT") 263 dev[0].wait_disconnected(timeout=10) 264 ev = hapd.wait_event(["MGMT-RX"], timeout=1) 265 if ev is None: 266 raise Exception("Deauthentication frame RX not reported") 267 hapd.set("ext_mgmt_frame_handling", "0") 268 dev[0].request("REASSOCIATE") 269 dev[0].wait_connected(timeout=20, error="Timeout on re-connection") 270 hapd.wait_4way_hs() 271 if wt.get_sta_counter("assocresp_comeback", apdev[0]['bssid'], 272 dev[0].p2p_interface_addr()) < 1: 273 raise Exception("AP did not use association comeback request") 274 275def test_ap_pmf_assoc_comeback_in_wpas(dev, apdev): 276 """WPA2-PSK AP with PMF association comeback in wpa_supplicant""" 277 ssid = "assoc-comeback" 278 params = hostapd.wpa2_params(ssid=ssid, passphrase="12345678") 279 params["wpa_key_mgmt"] = "WPA-PSK-SHA256" 280 params["ieee80211w"] = "2" 281 params["test_assoc_comeback_type"] = "255" 282 hapd = hostapd.add_ap(apdev[0], params) 283 284 dev[0].set("test_assoc_comeback_type", "255") 285 dev[0].connect(ssid, psk="12345678", ieee80211w="1", 286 key_mgmt="WPA-PSK WPA-PSK-SHA256", proto="WPA2", 287 scan_freq="2412") 288 hapd.wait_sta(wait_4way_hs=True) 289 hapd.set("ext_mgmt_frame_handling", "1") 290 dev[0].request("DISCONNECT") 291 dev[0].wait_disconnected(timeout=10) 292 ev = hapd.wait_event(["MGMT-RX"], timeout=1) 293 if ev is None: 294 raise Exception("Deauthentication frame RX not reported") 295 hapd.set("ext_mgmt_frame_handling", "0") 296 dev[0].request("REASSOCIATE") 297 ev = dev[0].wait_event(["CTRL-EVENT-ASSOC-REJECT"], timeout=10) 298 if ev is None or "status_code=30" not in ev: 299 raise Exception("Association comeback not requested") 300 ev = dev[0].wait_event(["CTRL-EVENT-CONNECTED", 301 "CTRL-EVENT-ASSOC-REJECT"], timeout=10) 302 if ev is None: 303 raise Exception("Association not reported") 304 if "CTRL-EVENT-ASSOC-REJECT" in ev: 305 raise Exception("Unexpected association rejection: " + ev) 306 hapd.wait_4way_hs() 307 308 hapd.set("ext_mgmt_frame_handling", "1") 309 dev[0].request("DISCONNECT") 310 dev[0].wait_disconnected(timeout=10) 311 ev = hapd.wait_event(["MGMT-RX"], timeout=1) 312 if ev is None: 313 raise Exception("Deauthentication frame RX not reported") 314 hapd.set("ext_mgmt_frame_handling", "0") 315 dev[0].set("test_assoc_comeback_type", "254") 316 dev[0].request("REASSOCIATE") 317 ev = dev[0].wait_event(["CTRL-EVENT-ASSOC-REJECT"], timeout=10) 318 if ev is None or "status_code=30" not in ev: 319 raise Exception("Association comeback not requested") 320 ev = dev[0].wait_event(["SME: Temporary assoc reject: missing association comeback time", 321 "CTRL-EVENT-CONNECTED", 322 "CTRL-EVENT-ASSOC-REJECT"], timeout=10) 323 if ev is None: 324 raise Exception("Association not reported") 325 if "SME: Temporary assoc reject: missing association comeback time" not in ev: 326 raise Exception("Unexpected result: " + ev) 327 dev[0].wait_connected(timeout=20, error="Timeout on re-connection with misbehaving AP") 328 hapd.wait_4way_hs() 329 330@remote_compatible 331def test_ap_pmf_assoc_comeback2(dev, apdev): 332 """WPA2-PSK AP with PMF association comeback (using DROP_SA)""" 333 ssid = "assoc-comeback" 334 params = hostapd.wpa2_params(ssid=ssid, passphrase="12345678") 335 params["wpa_key_mgmt"] = "WPA-PSK" 336 params["ieee80211w"] = "1" 337 hapd = hostapd.add_ap(apdev[0], params) 338 Wlantest.setup(hapd) 339 wt = Wlantest() 340 wt.flush() 341 wt.add_passphrase("12345678") 342 dev[0].connect(ssid, psk="12345678", ieee80211w="2", 343 key_mgmt="WPA-PSK", proto="WPA2", scan_freq="2412") 344 if "OK" not in dev[0].request("DROP_SA"): 345 raise Exception("DROP_SA failed") 346 dev[0].request("REASSOCIATE") 347 dev[0].wait_connected(timeout=10, error="Timeout on re-connection") 348 if wt.get_sta_counter("reassocresp_comeback", apdev[0]['bssid'], 349 dev[0].p2p_interface_addr()) < 1: 350 raise Exception("AP did not use reassociation comeback request") 351 352@remote_compatible 353def test_ap_pmf_assoc_comeback3(dev, apdev): 354 """WPA2-PSK AP with PMF association comeback (using radio_disabled)""" 355 drv_flags = dev[0].get_driver_status_field("capa.flags") 356 if int(drv_flags, 0) & 0x20 == 0: 357 raise HwsimSkip("Driver does not support radio_disabled") 358 ssid = "assoc-comeback" 359 params = hostapd.wpa2_params(ssid=ssid, passphrase="12345678") 360 params["wpa_key_mgmt"] = "WPA-PSK" 361 params["ieee80211w"] = "1" 362 hapd = hostapd.add_ap(apdev[0], params) 363 Wlantest.setup(hapd) 364 wt = Wlantest() 365 wt.flush() 366 wt.add_passphrase("12345678") 367 dev[0].connect(ssid, psk="12345678", ieee80211w="2", 368 key_mgmt="WPA-PSK", proto="WPA2", scan_freq="2412") 369 dev[0].set("radio_disabled", "1") 370 dev[0].set("radio_disabled", "0") 371 dev[0].request("REASSOCIATE") 372 dev[0].wait_connected(timeout=10, error="Timeout on re-connection") 373 if wt.get_sta_counter("assocresp_comeback", apdev[0]['bssid'], 374 dev[0].own_addr()) < 1: 375 raise Exception("AP did not use reassociation comeback request") 376 377@remote_compatible 378def test_ap_pmf_assoc_comeback_wps(dev, apdev): 379 """WPA2-PSK AP with PMF association comeback (WPS)""" 380 ssid = "assoc-comeback" 381 appin = "12345670" 382 params = hostapd.wpa2_params(ssid=ssid, passphrase="12345678") 383 params["wpa_key_mgmt"] = "WPA-PSK-SHA256" 384 params["ieee80211w"] = "2" 385 params["eap_server"] = "1" 386 params["wps_state"] = "2" 387 params["ap_pin"] = appin 388 hapd = hostapd.add_ap(apdev[0], params) 389 Wlantest.setup(hapd) 390 wt = Wlantest() 391 wt.flush() 392 wt.add_passphrase("12345678") 393 dev[0].connect(ssid, psk="12345678", ieee80211w="1", 394 key_mgmt="WPA-PSK WPA-PSK-SHA256", proto="WPA2", 395 scan_freq="2412") 396 hapd.wait_sta(wait_4way_hs=True) 397 hapd.set("ext_mgmt_frame_handling", "1") 398 dev[0].request("DISCONNECT") 399 dev[0].wait_disconnected(timeout=10) 400 ev = hapd.wait_event(["MGMT-RX"], timeout=1) 401 if ev is None: 402 raise Exception("Deauthentication frame RX not reported") 403 hapd.set("ext_mgmt_frame_handling", "0") 404 dev[0].wps_reg(apdev[0]['bssid'], appin) 405 hapd.wait_4way_hs() 406 if wt.get_sta_counter("assocresp_comeback", apdev[0]['bssid'], 407 dev[0].p2p_interface_addr()) < 1: 408 raise Exception("AP did not use association comeback request") 409 410def test_ap_pmf_ap_dropping_sa(dev, apdev): 411 """WPA2-PSK PMF AP dropping SA""" 412 ssid = "pmf" 413 params = hostapd.wpa2_params(ssid=ssid, passphrase="12345678") 414 params["wpa_key_mgmt"] = "WPA-PSK-SHA256" 415 params["ieee80211w"] = "2" 416 hapd = hostapd.add_ap(apdev[0], params) 417 bssid = hapd.own_addr() 418 Wlantest.setup(hapd) 419 wt = Wlantest() 420 wt.flush() 421 wt.add_passphrase("12345678") 422 dev[0].connect(ssid, psk="12345678", ieee80211w="2", 423 key_mgmt="WPA-PSK-SHA256", proto="WPA2", scan_freq="2412") 424 addr0 = dev[0].own_addr() 425 dev[0].dump_monitor() 426 hapd.wait_sta() 427 # Drop SA and association at the AP locally without notifying the STA. This 428 # results in the STA getting unprotected Deauthentication frames when trying 429 # to transmit the next Class 3 frame. 430 if "OK" not in hapd.request("DEAUTHENTICATE " + addr0 + " tx=0"): 431 raise Exception("DEAUTHENTICATE command failed") 432 ev = dev[0].wait_event(["CTRL-EVENT-DISCONNECTED"], timeout=1) 433 if ev is not None: 434 raise Exception("Unexpected disconnection event after DEAUTHENTICATE tx=0: " + ev) 435 dev[0].request("DATA_TEST_CONFIG 1") 436 dev[0].request("DATA_TEST_TX " + bssid + " " + addr0) 437 ev = dev[0].wait_event(["CTRL-EVENT-DISCONNECTED"], timeout=5) 438 dev[0].request("DATA_TEST_CONFIG 0") 439 if ev is None or "locally_generated=1" not in ev: 440 raise Exception("Locally generated disconnection not reported") 441 442def test_ap_pmf_valid_broadcast_deauth(dev, apdev): 443 """WPA2-PSK PMF AP sending valid broadcast deauth without dropping SA""" 444 run_ap_pmf_valid(dev, apdev, False, True) 445 446def test_ap_pmf_valid_broadcast_disassoc(dev, apdev): 447 """WPA2-PSK PMF AP sending valid broadcast disassoc without dropping SA""" 448 run_ap_pmf_valid(dev, apdev, True, True) 449 450def test_ap_pmf_valid_unicast_deauth(dev, apdev): 451 """WPA2-PSK PMF AP sending valid unicast deauth without dropping SA""" 452 run_ap_pmf_valid(dev, apdev, False, False) 453 454def test_ap_pmf_valid_unicast_disassoc(dev, apdev): 455 """WPA2-PSK PMF AP sending valid unicast disassoc without dropping SA""" 456 run_ap_pmf_valid(dev, apdev, True, False) 457 458def run_ap_pmf_valid(dev, apdev, disassociate, broadcast): 459 ssid = "pmf" 460 params = hostapd.wpa2_params(ssid=ssid, passphrase="12345678") 461 params["wpa_key_mgmt"] = "WPA-PSK-SHA256" 462 params["ieee80211w"] = "2" 463 hapd = hostapd.add_ap(apdev[0], params) 464 bssid = hapd.own_addr() 465 Wlantest.setup(hapd) 466 wt = Wlantest() 467 wt.flush() 468 wt.add_passphrase("12345678") 469 dev[0].connect(ssid, psk="12345678", ieee80211w="2", 470 key_mgmt="WPA-PSK-SHA256", proto="WPA2", scan_freq="2412") 471 addr0 = dev[0].own_addr() 472 dev[0].dump_monitor() 473 hapd.wait_sta() 474 cmd = "DISASSOCIATE " if disassociate else "DEAUTHENTICATE " 475 cmd += "ff:ff:ff:ff:ff:ff" if broadcast else addr0 476 cmd += " test=1" 477 if "OK" not in hapd.request(cmd): 478 raise Exception("hostapd command failed") 479 sta = hapd.get_sta(addr0) 480 if not sta: 481 raise Exception("STA entry lost") 482 ev = dev[0].wait_event(["CTRL-EVENT-DISCONNECTED"], timeout=5) 483 if ev is None: 484 raise Exception("Disconnection not reported") 485 if "locally_generated=1" in ev: 486 raise Exception("Unexpected locally generated disconnection") 487 488 # Wait for SA Query procedure to fail and association comeback to succeed 489 dev[0].wait_connected() 490 491def start_wpas_ap(ssid): 492 wpas = WpaSupplicant(global_iface='/tmp/wpas-wlan5') 493 wpas.interface_add("wlan5", drv_params="use_monitor=1") 494 id = wpas.add_network() 495 wpas.set_network(id, "mode", "2") 496 wpas.set_network_quoted(id, "ssid", ssid) 497 wpas.set_network(id, "proto", "WPA2") 498 wpas.set_network(id, "key_mgmt", "WPA-PSK-SHA256") 499 wpas.set_network(id, "ieee80211w", "2") 500 wpas.set_network_quoted(id, "psk", "12345678") 501 wpas.set_network(id, "pairwise", "CCMP") 502 wpas.set_network(id, "group", "CCMP") 503 wpas.set_network(id, "frequency", "2412") 504 wpas.set_network(id, "scan_freq", "2412") 505 wpas.connect_network(id) 506 wpas.dump_monitor() 507 return wpas 508 509def test_ap_pmf_sta_sa_query(dev, apdev): 510 """WPA2-PSK AP with station using SA Query""" 511 ssid = "assoc-comeback" 512 addr = dev[0].own_addr() 513 514 wpas = start_wpas_ap(ssid) 515 bssid = wpas.own_addr() 516 517 Wlantest.setup(wpas) 518 wt = Wlantest() 519 wt.flush() 520 wt.add_passphrase("12345678") 521 522 dev[0].connect(ssid, psk="12345678", ieee80211w="1", 523 key_mgmt="WPA-PSK WPA-PSK-SHA256", proto="WPA2", 524 scan_freq="2412") 525 wpas.dump_monitor() 526 wpas.request("DEAUTHENTICATE " + addr + " test=0") 527 wpas.dump_monitor() 528 wpas.request("DISASSOCIATE " + addr + " test=0") 529 wpas.dump_monitor() 530 ev = dev[0].wait_event(["CTRL-EVENT-DISCONNECTED"], timeout=1) 531 if ev is not None: 532 raise Exception("Unexpected disconnection") 533 534 wpas.request("DEAUTHENTICATE " + addr + " reason=6 test=0") 535 wpas.dump_monitor() 536 wpas.request("DISASSOCIATE " + addr + " reason=7 test=0") 537 wpas.dump_monitor() 538 ev = dev[0].wait_event(["CTRL-EVENT-DISCONNECTED"], timeout=1) 539 if ev is not None: 540 raise Exception("Unexpected disconnection") 541 if wt.get_sta_counter("valid_saqueryreq_tx", bssid, addr) < 1: 542 raise Exception("STA did not send SA Query") 543 if wt.get_sta_counter("valid_saqueryresp_rx", bssid, addr) < 1: 544 raise Exception("AP did not reply to SA Query") 545 wpas.dump_monitor() 546 547def test_ap_pmf_sta_sa_query_no_response(dev, apdev): 548 """WPA2-PSK AP with station using SA Query and getting no response""" 549 ssid = "assoc-comeback" 550 addr = dev[0].own_addr() 551 552 wpas = start_wpas_ap(ssid) 553 bssid = wpas.own_addr() 554 555 dev[0].connect(ssid, psk="12345678", ieee80211w="1", 556 key_mgmt="WPA-PSK WPA-PSK-SHA256", proto="WPA2", 557 scan_freq="2412") 558 wpas.dump_monitor() 559 wpas.request("DEAUTHENTICATE " + addr + " test=0") 560 wpas.dump_monitor() 561 wpas.request("DISASSOCIATE " + addr + " test=0") 562 wpas.dump_monitor() 563 ev = dev[0].wait_event(["CTRL-EVENT-DISCONNECTED"], timeout=1) 564 if ev is not None: 565 raise Exception("Unexpected disconnection") 566 567 wpas.request("SET ext_mgmt_frame_handling 1") 568 wpas.request("DEAUTHENTICATE " + addr + " reason=6 test=0") 569 wpas.dump_monitor() 570 wpas.request("DISASSOCIATE " + addr + " reason=7 test=0") 571 wpas.dump_monitor() 572 dev[0].wait_disconnected() 573 wpas.dump_monitor() 574 wpas.request("SET ext_mgmt_frame_handling 0") 575 dev[0].wait_connected() 576 wpas.dump_monitor() 577 578def test_ap_pmf_sta_unprot_deauth_burst(dev, apdev): 579 """WPA2-PSK AP with station receiving burst of unprotected Deauthentication frames""" 580 ssid = "deauth-attack" 581 addr = dev[0].own_addr() 582 583 wpas = start_wpas_ap(ssid) 584 bssid = wpas.own_addr() 585 586 Wlantest.setup(wpas) 587 wt = Wlantest() 588 wt.flush() 589 wt.add_passphrase("12345678") 590 591 dev[0].connect(ssid, psk="12345678", ieee80211w="1", 592 key_mgmt="WPA-PSK WPA-PSK-SHA256", proto="WPA2", 593 scan_freq="2412") 594 595 for i in range(0, 10): 596 wpas.request("DEAUTHENTICATE " + addr + " reason=6 test=0") 597 wpas.request("DISASSOCIATE " + addr + " reason=7 test=0") 598 ev = dev[0].wait_event(["CTRL-EVENT-DISCONNECTED"], timeout=1) 599 if ev is not None: 600 raise Exception("Unexpected disconnection") 601 num_req = wt.get_sta_counter("valid_saqueryreq_tx", bssid, addr) 602 num_resp = wt.get_sta_counter("valid_saqueryresp_rx", bssid, addr) 603 if num_req < 1: 604 raise Exception("STA did not send SA Query") 605 if num_resp < 1: 606 raise Exception("AP did not reply to SA Query") 607 if num_req > 1: 608 raise Exception("STA initiated too many SA Query procedures (%d)" % num_req) 609 610 time.sleep(10) 611 for i in range(0, 5): 612 wpas.request("DEAUTHENTICATE " + addr + " reason=6 test=0") 613 wpas.request("DISASSOCIATE " + addr + " reason=7 test=0") 614 ev = dev[0].wait_event(["CTRL-EVENT-DISCONNECTED"], timeout=1) 615 if ev is not None: 616 raise Exception("Unexpected disconnection") 617 num_req = wt.get_sta_counter("valid_saqueryreq_tx", bssid, addr) 618 num_resp = wt.get_sta_counter("valid_saqueryresp_rx", bssid, addr) 619 if num_req != 2 or num_resp != 2: 620 raise Exception("Unexpected number of SA Query procedures (req=%d resp=%d)" % (num_req, num_resp)) 621 622def test_ap_pmf_sta_sa_query_oom(dev, apdev): 623 """WPA2-PSK AP with station using SA Query (OOM)""" 624 ssid = "assoc-comeback" 625 addr = dev[0].own_addr() 626 wpas = start_wpas_ap(ssid) 627 dev[0].connect(ssid, psk="12345678", ieee80211w="1", 628 key_mgmt="WPA-PSK WPA-PSK-SHA256", proto="WPA2", 629 scan_freq="2412") 630 with alloc_fail(dev[0], 1, "=sme_sa_query_timer"): 631 wpas.request("DEAUTHENTICATE " + addr + " reason=6 test=0") 632 wait_fail_trigger(dev[0], "GET_ALLOC_FAIL") 633 dev[0].request("DISCONNECT") 634 wpas.request("DISCONNECT") 635 dev[0].wait_disconnected() 636 637def test_ap_pmf_sta_sa_query_local_failure(dev, apdev): 638 """WPA2-PSK AP with station using SA Query (local failure)""" 639 ssid = "assoc-comeback" 640 addr = dev[0].own_addr() 641 wpas = start_wpas_ap(ssid) 642 dev[0].connect(ssid, psk="12345678", ieee80211w="1", 643 key_mgmt="WPA-PSK WPA-PSK-SHA256", proto="WPA2", 644 scan_freq="2412") 645 with fail_test(dev[0], 1, "os_get_random;sme_sa_query_timer"): 646 wpas.request("DEAUTHENTICATE " + addr + " reason=6 test=0") 647 wait_fail_trigger(dev[0], "GET_FAIL") 648 dev[0].request("DISCONNECT") 649 wpas.request("DISCONNECT") 650 dev[0].wait_disconnected() 651 652def test_ap_pmf_sta_sa_query_hostapd(dev, apdev): 653 """WPA2-PSK AP with station using SA Query (hostapd)""" 654 ssid = "assoc-comeback" 655 passphrase = "12345678" 656 addr = dev[0].own_addr() 657 658 params = hostapd.wpa2_params(ssid=ssid, passphrase=passphrase, 659 wpa_key_mgmt="WPA-PSK-SHA256", 660 ieee80211w="2") 661 hapd = hostapd.add_ap(apdev[0], params) 662 bssid = hapd.own_addr() 663 664 Wlantest.setup(hapd) 665 wt = Wlantest() 666 wt.flush() 667 wt.add_passphrase("12345678") 668 669 dev[0].connect(ssid, psk=passphrase, ieee80211w="2", 670 key_mgmt="WPA-PSK-SHA256", proto="WPA2", 671 scan_freq="2412") 672 hapd.wait_sta() 673 if "OK" not in hapd.request("DEAUTHENTICATE " + addr + " test=0") or \ 674 "OK" not in hapd.request("DISASSOCIATE " + addr + " test=0"): 675 raise Exception("Failed to send unprotected disconnection messages") 676 ev = dev[0].wait_event(["CTRL-EVENT-DISCONNECTED"], timeout=1) 677 if ev is not None: 678 raise Exception("Unexpected disconnection") 679 680 if "OK" not in hapd.request("DEAUTHENTICATE " + addr + " reason=6 test=0") or \ 681 "OK" not in hapd.request("DISASSOCIATE " + addr + " reason=7 test=0"): 682 raise Exception("Failed to send unprotected disconnection messages (2)") 683 ev = dev[0].wait_event(["CTRL-EVENT-DISCONNECTED"], timeout=1) 684 if ev is not None: 685 raise Exception("Unexpected disconnection") 686 if wt.get_sta_counter("valid_saqueryreq_tx", bssid, addr) < 1: 687 raise Exception("STA did not send SA Query") 688 if wt.get_sta_counter("valid_saqueryresp_rx", bssid, addr) < 1: 689 raise Exception("AP did not reply to SA Query") 690 691def test_ap_pmf_sta_sa_query_no_response_hostapd(dev, apdev): 692 """WPA2-PSK AP with station using SA Query and getting no response (hostapd)""" 693 ssid = "assoc-comeback" 694 passphrase = "12345678" 695 addr = dev[0].own_addr() 696 697 params = hostapd.wpa2_params(ssid=ssid, passphrase=passphrase, 698 wpa_key_mgmt="WPA-PSK-SHA256", 699 ieee80211w="2") 700 hapd = hostapd.add_ap(apdev[0], params) 701 bssid = hapd.own_addr() 702 703 Wlantest.setup(hapd) 704 wt = Wlantest() 705 wt.flush() 706 wt.add_passphrase("12345678") 707 708 dev[0].connect(ssid, psk=passphrase, ieee80211w="2", 709 key_mgmt="WPA-PSK-SHA256", proto="WPA2", 710 scan_freq="2412") 711 hapd.wait_sta() 712 hapd.set("ext_mgmt_frame_handling", "1") 713 if "OK" not in hapd.request("DEAUTHENTICATE " + addr + " reason=6 test=0") or \ 714 "OK" not in hapd.request("DISASSOCIATE " + addr + " reason=7 test=0"): 715 raise Exception("Failed to send unprotected disconnection messages") 716 dev[0].wait_disconnected() 717 hapd.set("ext_mgmt_frame_handling", "0") 718 if wt.get_sta_counter("valid_saqueryreq_tx", bssid, addr) < 1: 719 raise Exception("STA did not send SA Query") 720 if wt.get_sta_counter("valid_saqueryresp_rx", bssid, addr) > 0: 721 raise Exception("AP replied to SA Query") 722 dev[0].wait_connected() 723 724def test_ap_pmf_sta_unprot_deauth_burst_hostapd(dev, apdev): 725 """WPA2-PSK AP with station receiving burst of unprotected Deauthentication frames (hostapd)""" 726 ssid = "deauth-attack" 727 passphrase = "12345678" 728 addr = dev[0].own_addr() 729 730 params = hostapd.wpa2_params(ssid=ssid, passphrase=passphrase, 731 wpa_key_mgmt="WPA-PSK-SHA256", 732 ieee80211w="2") 733 hapd = hostapd.add_ap(apdev[0], params) 734 bssid = hapd.own_addr() 735 736 Wlantest.setup(hapd) 737 wt = Wlantest() 738 wt.flush() 739 wt.add_passphrase("12345678") 740 741 dev[0].connect(ssid, psk=passphrase, ieee80211w="2", 742 key_mgmt="WPA-PSK-SHA256", proto="WPA2", 743 scan_freq="2412") 744 hapd.wait_sta() 745 for i in range(10): 746 if "OK" not in hapd.request("DEAUTHENTICATE " + addr + " reason=6 test=0") or \ 747 "OK" not in hapd.request("DISASSOCIATE " + addr + " reason=7 test=0"): 748 raise Exception("Failed to send unprotected disconnection messages") 749 ev = dev[0].wait_event(["CTRL-EVENT-DISCONNECTED"], timeout=1) 750 if ev is not None: 751 raise Exception("Unexpected disconnection") 752 num_req = wt.get_sta_counter("valid_saqueryreq_tx", bssid, addr) 753 num_resp = wt.get_sta_counter("valid_saqueryresp_rx", bssid, addr) 754 if num_req < 1: 755 raise Exception("STA did not send SA Query") 756 if num_resp < 1: 757 raise Exception("AP did not reply to SA Query") 758 if num_req > 1: 759 raise Exception("STA initiated too many SA Query procedures (%d)" % num_req) 760 761 time.sleep(10) 762 for i in range(5): 763 if "OK" not in hapd.request("DEAUTHENTICATE " + addr + " reason=6 test=0") or \ 764 "OK" not in hapd.request("DISASSOCIATE " + addr + " reason=7 test=0"): 765 raise Exception("Failed to send unprotected disconnection messages") 766 ev = dev[0].wait_event(["CTRL-EVENT-DISCONNECTED"], timeout=1) 767 if ev is not None: 768 raise Exception("Unexpected disconnection") 769 num_req = wt.get_sta_counter("valid_saqueryreq_tx", bssid, addr) 770 num_resp = wt.get_sta_counter("valid_saqueryresp_rx", bssid, addr) 771 if num_req != 2 or num_resp != 2: 772 raise Exception("Unexpected number of SA Query procedures (req=%d resp=%d)" % (num_req, num_resp)) 773 774def test_ap_pmf_required_eap(dev, apdev): 775 """WPA2-EAP AP with PMF required""" 776 ssid = "test-pmf-required-eap" 777 params = hostapd.wpa2_eap_params(ssid=ssid) 778 params["wpa_key_mgmt"] = "WPA-EAP-SHA256" 779 params["ieee80211w"] = "2" 780 hapd = hostapd.add_ap(apdev[0], params) 781 key_mgmt = hapd.get_config()['key_mgmt'] 782 if key_mgmt.split(' ')[0] != "WPA-EAP-SHA256": 783 raise Exception("Unexpected GET_CONFIG(key_mgmt): " + key_mgmt) 784 dev[0].connect("test-pmf-required-eap", key_mgmt="WPA-EAP-SHA256", 785 ieee80211w="2", eap="PSK", identity="psk.user@example.com", 786 password_hex="0123456789abcdef0123456789abcdef", 787 scan_freq="2412") 788 dev[1].connect("test-pmf-required-eap", key_mgmt="WPA-EAP WPA-EAP-SHA256", 789 ieee80211w="1", eap="PSK", identity="psk.user@example.com", 790 password_hex="0123456789abcdef0123456789abcdef", 791 scan_freq="2412") 792 793def test_ap_pmf_optional_eap(dev, apdev): 794 """WPA2EAP AP with PMF optional""" 795 params = hostapd.wpa2_eap_params(ssid="test-wpa2-eap") 796 params["ieee80211w"] = "1" 797 hapd = hostapd.add_ap(apdev[0], params) 798 dev[0].connect("test-wpa2-eap", key_mgmt="WPA-EAP", eap="TTLS", 799 identity="pap user", anonymous_identity="ttls", 800 password="password", 801 ca_cert="auth_serv/ca.pem", phase2="auth=PAP", 802 ieee80211w="1", scan_freq="2412") 803 dev[1].connect("test-wpa2-eap", key_mgmt="WPA-EAP WPA-EAP-SHA256", 804 eap="TTLS", identity="pap user", anonymous_identity="ttls", 805 password="password", 806 ca_cert="auth_serv/ca.pem", phase2="auth=PAP", 807 ieee80211w="2", scan_freq="2412") 808 809@remote_compatible 810def test_ap_pmf_required_sha1(dev, apdev): 811 """WPA2-PSK AP with PMF required with SHA1 AKM""" 812 ssid = "test-pmf-required-sha1" 813 params = hostapd.wpa2_params(ssid=ssid, passphrase="12345678") 814 params["wpa_key_mgmt"] = "WPA-PSK" 815 params["ieee80211w"] = "2" 816 hapd = hostapd.add_ap(apdev[0], params) 817 Wlantest.setup(hapd) 818 wt = Wlantest() 819 wt.flush() 820 wt.add_passphrase("12345678") 821 key_mgmt = hapd.get_config()['key_mgmt'] 822 if key_mgmt.split(' ')[0] != "WPA-PSK": 823 raise Exception("Unexpected GET_CONFIG(key_mgmt): " + key_mgmt) 824 dev[0].connect(ssid, psk="12345678", ieee80211w="2", 825 key_mgmt="WPA-PSK", proto="WPA2", scan_freq="2412") 826 if "[WPA2-PSK-CCMP]" not in dev[0].request("SCAN_RESULTS"): 827 raise Exception("Scan results missing RSN element info") 828 hwsim_utils.test_connectivity(dev[0], hapd) 829 830@remote_compatible 831def test_ap_pmf_toggle(dev, apdev): 832 """WPA2-PSK AP with PMF optional and changing PMF on reassociation""" 833 try: 834 _test_ap_pmf_toggle(dev, apdev) 835 finally: 836 dev[0].request("SET reassoc_same_bss_optim 0") 837 838def _test_ap_pmf_toggle(dev, apdev): 839 ssid = "test-pmf-optional" 840 params = hostapd.wpa2_params(ssid=ssid, passphrase="12345678") 841 params["wpa_key_mgmt"] = "WPA-PSK" 842 params["ieee80211w"] = "1" 843 params["assoc_sa_query_max_timeout"] = "1" 844 params["assoc_sa_query_retry_timeout"] = "1" 845 hapd = hostapd.add_ap(apdev[0], params) 846 Wlantest.setup(hapd) 847 wt = Wlantest() 848 wt.flush() 849 wt.add_passphrase("12345678") 850 bssid = apdev[0]['bssid'] 851 addr = dev[0].own_addr() 852 dev[0].request("SET reassoc_same_bss_optim 1") 853 id = dev[0].connect(ssid, psk="12345678", ieee80211w="1", 854 key_mgmt="WPA-PSK WPA-PSK-SHA256", proto="WPA2", 855 scan_freq="2412") 856 wt.require_ap_pmf_optional(bssid) 857 wt.require_sta_pmf(bssid, addr) 858 sta = hapd.get_sta(addr) 859 if '[MFP]' not in sta['flags']: 860 raise Exception("MFP flag not present for STA") 861 862 dev[0].set_network(id, "ieee80211w", "0") 863 dev[0].request("REASSOCIATE") 864 dev[0].wait_connected() 865 wt.require_sta_no_pmf(bssid, addr) 866 sta = hapd.get_sta(addr) 867 if '[MFP]' in sta['flags']: 868 raise Exception("MFP flag unexpectedly present for STA") 869 err, data = hapd.cmd_execute(['iw', 'dev', apdev[0]['ifname'], 'station', 870 'get', addr]) 871 if "yes" in [l for l in data.splitlines() if "MFP" in l][0]: 872 raise Exception("Kernel STA entry had MFP enabled") 873 874 dev[0].set_network(id, "ieee80211w", "1") 875 dev[0].request("REASSOCIATE") 876 dev[0].wait_connected() 877 wt.require_sta_pmf(bssid, addr) 878 sta = hapd.get_sta(addr) 879 if '[MFP]' not in sta['flags']: 880 raise Exception("MFP flag not present for STA") 881 err, data = hapd.cmd_execute(['iw', 'dev', apdev[0]['ifname'], 'station', 882 'get', addr]) 883 if "yes" not in [l for l in data.splitlines() if "MFP" in l][0]: 884 raise Exception("Kernel STA entry did not have MFP enabled") 885 886@remote_compatible 887def test_ap_pmf_required_sta_no_pmf(dev, apdev): 888 """WPA2-PSK AP with PMF required and PMF disabled on STA""" 889 ssid = "test-pmf-required" 890 params = hostapd.wpa2_params(ssid=ssid, passphrase="12345678") 891 params["wpa_key_mgmt"] = "WPA-PSK-SHA256" 892 params["ieee80211w"] = "2" 893 hapd = hostapd.add_ap(apdev[0], params) 894 895 # Disable PMF on the station and try to connect 896 dev[0].connect(ssid, psk="12345678", ieee80211w="0", 897 key_mgmt="WPA-PSK WPA-PSK-SHA256", proto="WPA2", 898 scan_freq="2412", wait_connect=False) 899 ev = dev[0].wait_event(["CTRL-EVENT-NETWORK-NOT-FOUND", 900 "CTRL-EVENT-ASSOC-REJECT"], timeout=2) 901 if ev is None: 902 raise Exception("No connection result") 903 if "CTRL-EVENT-ASSOC-REJECT" in ev: 904 raise Exception("Tried to connect to PMF required AP without PMF enabled") 905 dev[0].request("REMOVE_NETWORK all") 906 907def test_ap_pmf_inject_auth(dev, apdev): 908 """WPA2-PSK AP with PMF and Authentication frame injection""" 909 ssid = "test-pmf" 910 params = hostapd.wpa2_params(ssid=ssid, passphrase="12345678") 911 params["wpa_key_mgmt"] = "WPA-PSK-SHA256" 912 params["ieee80211w"] = "2" 913 hapd = hostapd.add_ap(apdev[0], params) 914 dev[0].connect(ssid, psk="12345678", ieee80211w="2", 915 key_mgmt="WPA-PSK-SHA256", proto="WPA2", 916 scan_freq="2412") 917 hapd.wait_sta() 918 hwsim_utils.test_connectivity(dev[0], hapd) 919 920 bssid = hapd.own_addr().replace(':', '') 921 addr = dev[0].own_addr().replace(':', '') 922 923 # Inject an unprotected Authentication frame claiming to be from the 924 # associated STA, from another STA, from the AP's own address, from all 925 # zeros and all ones addresses, and from a multicast address. 926 hapd.request("SET ext_mgmt_frame_handling 1") 927 failed = False 928 addresses = [ addr, "021122334455", bssid, 6*"00", 6*"ff", 6*"01" ] 929 for a in addresses: 930 auth = "b0003a01" + bssid + a + bssid + '1000000001000000' 931 res = hapd.request("MGMT_RX_PROCESS freq=2412 datarate=0 ssi_signal=-30 frame=%s" % auth) 932 if "OK" not in res: 933 failed = True 934 hapd.request("SET ext_mgmt_frame_handling 0") 935 if failed: 936 raise Exception("MGMT_RX_PROCESS failed") 937 time.sleep(0.1) 938 939 ev = dev[0].wait_event(["CTRL-EVENT-DISCONNECTED"], timeout=0.1) 940 if ev: 941 raise Exception("Unexpected disconnection reported on the STA") 942 943 # Verify that original association is still functional. 944 hwsim_utils.test_connectivity(dev[0], hapd) 945 946 # Inject an unprotected Association Request frame (with and without RSNE) 947 # claiming to be from the set of test addresses. 948 hapd.request("SET ext_mgmt_frame_handling 1") 949 for a in addresses: 950 assoc = "00003a01" + bssid + a + bssid + '2000' + '31040500' + '0008746573742d706d66' + '010802040b160c121824' + '301a0100000fac040100000fac040100000fac06c0000000000fac06' 951 res = hapd.request("MGMT_RX_PROCESS freq=2412 datarate=0 ssi_signal=-30 frame=%s" % assoc) 952 if "OK" not in res: 953 failed = True 954 955 assoc = "00003a01" + bssid + a + bssid + '2000' + '31040500' + '0008746573742d706d66' + '010802040b160c121824' + '3000' 956 res = hapd.request("MGMT_RX_PROCESS freq=2412 datarate=0 ssi_signal=-30 frame=%s" % assoc) 957 if "OK" not in res: 958 failed = True 959 960 assoc = "00003a01" + bssid + a + bssid + '2000' + '31040500' + '0008746573742d706d66' + '010802040b160c121824' 961 res = hapd.request("MGMT_RX_PROCESS freq=2412 datarate=0 ssi_signal=-30 frame=%s" % assoc) 962 if "OK" not in res: 963 failed = True 964 hapd.request("SET ext_mgmt_frame_handling 0") 965 if failed: 966 raise Exception("MGMT_RX_PROCESS failed") 967 time.sleep(5) 968 969 ev = dev[0].wait_event(["CTRL-EVENT-DISCONNECTED"], timeout=0.1) 970 if ev: 971 raise Exception("Unexpected disconnection reported on the STA") 972 973 # Verify that original association is still functional. 974 hwsim_utils.test_connectivity(dev[0], hapd) 975 976def test_ap_pmf_inject_assoc(dev, apdev): 977 """WPA2-PSK with PMF and Association Request frame injection""" 978 run_ap_pmf_inject_assoc(dev, apdev, False) 979 980def test_ap_pmf_inject_assoc_wps(dev, apdev): 981 """WPA2-PSK/WPS with PMF and Association Request frame injection""" 982 run_ap_pmf_inject_assoc(dev, apdev, True) 983 984def inject_assoc_req(hapd, addr, frame): 985 hapd.set("ext_mgmt_frame_handling", "1") 986 res = hapd.request("MGMT_RX_PROCESS freq=2412 datarate=0 ssi_signal=-30 frame=%s" % frame) 987 if "OK" not in res: 988 raise Exception("MGMT_RX_PROCESS failed") 989 hapd.set("ext_mgmt_frame_handling", "0") 990 sta = hapd.get_sta(addr) 991 if "[MFP]" not in sta['flags']: 992 raise Exception("MFP flag removed") 993 if sta["AKMSuiteSelector"] != '00-0f-ac-6': 994 raise Exception("AKMSuiteSelector value changed") 995 996def run_ap_pmf_inject_assoc(dev, apdev, wps): 997 ssid = "test-pmf" 998 params = hostapd.wpa2_params(ssid=ssid, passphrase="12345678") 999 params["wpa_key_mgmt"] = "WPA-PSK WPA-PSK-SHA256" 1000 params["ieee80211w"] = "1" 1001 if wps: 1002 params["eap_server"] = "1" 1003 params["wps_state"] = "2" 1004 1005 hapd = hostapd.add_ap(apdev[0], params) 1006 dev[0].connect(ssid, psk="12345678", ieee80211w="2", 1007 key_mgmt="WPA-PSK-SHA256", proto="WPA2", 1008 scan_freq="2412") 1009 hapd.wait_sta() 1010 sta = hapd.get_sta(dev[0].own_addr()) 1011 if "[MFP]" not in sta['flags']: 1012 raise Exception("MFP flag not reported") 1013 if sta["AKMSuiteSelector"] != '00-0f-ac-6': 1014 raise Exception("Incorrect AKMSuiteSelector value") 1015 1016 bssid = hapd.own_addr().replace(':', '') 1017 addr = dev[0].own_addr().replace(':', '') 1018 1019 # Inject unprotected Association Request frames 1020 assoc1 = "00003a01" + bssid + addr + bssid + '2000' + '31040500' + '0008746573742d706d66' + '010802040b160c121824' + '30140100000fac040100000fac040100000fac020000' 1021 assoc2 = "00003a01" + bssid + addr + bssid + '2000' + '31040500' + '0008746573742d706d66' + '010802040b160c121824' + '30140100000fac040100000fac040100000fac060000' 1022 assoc3 = "00003a01" + bssid + addr + bssid + '2000' + '31040500' + '0008746573742d706d66' + '010802040b160c121824' 1023 1024 inject_assoc_req(hapd, dev[0].own_addr(), assoc1) 1025 time.sleep(0.1) 1026 inject_assoc_req(hapd, dev[0].own_addr(), assoc1) 1027 time.sleep(0.1) 1028 inject_assoc_req(hapd, dev[0].own_addr(), assoc2) 1029 time.sleep(0.1) 1030 inject_assoc_req(hapd, dev[0].own_addr(), assoc3) 1031 time.sleep(0.1) 1032 inject_assoc_req(hapd, dev[0].own_addr(), assoc2) 1033 1034 ev = dev[0].wait_event(["CTRL-EVENT-DISCONNECTED"], timeout=5.1) 1035 if ev: 1036 raise Exception("Unexpected disconnection reported on the STA") 1037 ev = hapd.wait_event(["AP-STA-DISCONNECTED"], timeout=0.1) 1038 if ev: 1039 raise Exception("Unexpected disconnection event received from hostapd") 1040 1041 # Verify that original association is still functional. 1042 hwsim_utils.test_connectivity(dev[0], hapd) 1043 1044def test_ap_pmf_inject_data(dev, apdev): 1045 """WPA2-PSK AP with PMF and Data frame injection""" 1046 try: 1047 run_ap_pmf_inject_data(dev, apdev) 1048 finally: 1049 stop_monitor(apdev[1]["ifname"]) 1050 1051def run_ap_pmf_inject_data(dev, apdev): 1052 ssid = "test-pmf" 1053 params = hostapd.wpa2_params(ssid=ssid, passphrase="12345678") 1054 params["wpa_key_mgmt"] = "WPA-PSK-SHA256" 1055 params["ieee80211w"] = "2" 1056 hapd = hostapd.add_ap(apdev[0], params) 1057 dev[0].connect(ssid, psk="12345678", ieee80211w="2", 1058 key_mgmt="WPA-PSK-SHA256", proto="WPA2", 1059 scan_freq="2412") 1060 hapd.wait_sta() 1061 hwsim_utils.test_connectivity(dev[0], hapd) 1062 1063 sock = start_monitor(apdev[1]["ifname"]) 1064 radiotap = radiotap_build() 1065 1066 bssid = hapd.own_addr().replace(':', '') 1067 addr = dev[0].own_addr().replace(':', '') 1068 1069 # Inject Data frame with A2=broadcast, A2=multicast, A2=BSSID, A2=STA, and 1070 # A2=unknown unicast 1071 addresses = [ 6*"ff", 6*"01", bssid, addr, "020102030405" ] 1072 for a in addresses: 1073 frame = binascii.unhexlify("48010000" + bssid + a + bssid + "0000") 1074 sock.send(radiotap + frame) 1075 1076 time.sleep(0.1) 1077 ev = dev[0].wait_event(["CTRL-EVENT-DISCONNECTED"], timeout=0.1) 1078 if ev: 1079 raise Exception("Unexpected disconnection reported on the STA") 1080 hwsim_utils.test_connectivity(dev[0], hapd) 1081 1082def test_ap_pmf_inject_msg1(dev, apdev): 1083 """WPA2-PSK AP with PMF and EAPOL-Key msg 1/4 injection""" 1084 try: 1085 run_ap_pmf_inject_msg1(dev, apdev) 1086 finally: 1087 stop_monitor(apdev[1]["ifname"]) 1088 1089def test_ap_pmf_inject_msg1_no_pmf(dev, apdev): 1090 """WPA2-PSK AP without PMF and EAPOL-Key msg 1/4 injection""" 1091 try: 1092 run_ap_pmf_inject_msg1(dev, apdev, pmf=False) 1093 finally: 1094 stop_monitor(apdev[1]["ifname"]) 1095 1096def run_ap_pmf_inject_msg1(dev, apdev, pmf=True): 1097 ssid = "test-pmf" 1098 params = hostapd.wpa2_params(ssid=ssid, passphrase="12345678") 1099 params["wpa_key_mgmt"] = "WPA-PSK-SHA256" 1100 if pmf: 1101 params["ieee80211w"] = "2" 1102 hapd = hostapd.add_ap(apdev[0], params) 1103 dev[0].connect(ssid, psk="12345678", ieee80211w="2" if pmf else "0", 1104 key_mgmt="WPA-PSK-SHA256", proto="WPA2", 1105 scan_freq="2412") 1106 hapd.wait_sta() 1107 1108 sock = start_monitor(apdev[1]["ifname"]) 1109 radiotap = radiotap_build() 1110 1111 bssid = hapd.own_addr().replace(':', '') 1112 addr = dev[0].own_addr().replace(':', '') 1113 1114 # Inject unprotected EAPOL-Key msg 1/4 with an invalid KDE 1115 f = "88020000" + addr + bssid + bssid + "0000" + "0700" 1116 f += "aaaa03000000" + "888e" 1117 f += "0203006602008b00100000000000000005bcb714da6f98f817b88948485c26ef052922b795814819f1889ae01e11b486910000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000007" + "dd33000fac0400" 1118 frame = binascii.unhexlify(f) 1119 sock.send(radiotap + frame) 1120 1121 ev = dev[0].wait_event(["CTRL-EVENT-DISCONNECTED"], timeout=0.5) 1122 if ev: 1123 raise Exception("Unexpected disconnection reported on the STA") 1124 hwsim_utils.test_connectivity(dev[0], hapd) 1125 state = dev[0].get_status_field("wpa_state") 1126 if state != "COMPLETED": 1127 raise Exception("Unexpected wpa_state: " + state) 1128 1129def test_ap_pmf_inject_eap(dev, apdev): 1130 """WPA2-EAP AP with PMF and EAP frame injection""" 1131 try: 1132 run_ap_pmf_inject_eap(dev, apdev) 1133 finally: 1134 stop_monitor(apdev[1]["ifname"]) 1135 1136def run_ap_pmf_inject_eap(dev, apdev, pmf=True): 1137 ssid = "test-pmf-eap" 1138 params = hostapd.wpa2_eap_params(ssid=ssid) 1139 params["wpa_key_mgmt"] = "WPA-EAP-SHA256" 1140 params["ieee80211w"] = "2" 1141 hapd = hostapd.add_ap(apdev[0], params) 1142 dev[0].connect(ssid, key_mgmt="WPA-EAP-SHA256", 1143 ieee80211w="2", eap="PSK", identity="psk.user@example.com", 1144 password_hex="0123456789abcdef0123456789abcdef", 1145 scan_freq="2412") 1146 hapd.wait_sta() 1147 dev[0].dump_monitor() 1148 hapd.dump_monitor() 1149 1150 sock = start_monitor(apdev[1]["ifname"]) 1151 radiotap = radiotap_build() 1152 1153 bssid = hapd.own_addr().replace(':', '') 1154 addr = dev[0].own_addr().replace(':', '') 1155 1156 disconnected = False 1157 eap_start = False 1158 eap_failure = False 1159 ap_disconnected = False 1160 1161 # Inject various unexpected unprotected EAPOL frames to the STA 1162 f = "88020000" + addr + bssid + bssid + "0000" + "0700" 1163 f += "aaaa03000000" + "888e" 1164 tests = [] 1165 for i in range(101): 1166 tests += [ "02000005012d000501" ] # EAP-Request/Identity 1167 for i in range(101): 1168 tests += [ "02000022012e00222f00862406a9b45782fee8a62e837457d1367365727665722e77312e6669" ] # EAP-Request/PSK 1169 tests += [ "0200000404780004" ] # EAP-Failure 1170 tests += [ "0200000403780004" ] # EAP-Success 1171 tests += [ "02000006057800060100" ] # EAP-Initiate 1172 tests += [ "0200000406780004" ] # EAP-Finish 1173 tests += [ "0200000400780004" ] # EAP-? 1174 tests += [ "02020000" ] # EAPOL-Logoff 1175 tests += [ "02010000" ] # EAPOL-Start 1176 for t in tests: 1177 dev[0].note("Inject " + t) 1178 frame = binascii.unhexlify(f + t) 1179 sock.send(radiotap + frame) 1180 for i in range(2): 1181 ev = dev[0].wait_event(["CTRL-EVENT-DISCONNECTED", 1182 "CTRL-EVENT-EAP-STARTED", 1183 "CTRL-EVENT-EAP-FAILURE"], 1184 timeout=0.0001) 1185 if ev is None: 1186 break 1187 if "CTRL-EVENT-DISCONNECTED" in ev: 1188 disconnected = True 1189 if "CTRL-EVENT-EAP-START" in ev: 1190 eap_start = True 1191 if "CTRL-EVENT-EAP-FAILURE" in ev: 1192 eap_failure = True 1193 dev[0].dump_monitor(mon=False) 1194 dev[0].dump_monitor() 1195 ev = hapd.wait_event(["AP-STA-DISCONNECTED"], timeout=0.1) 1196 if ev: 1197 ap_disconnected = True 1198 if disconnected or eap_start or eap_failure or ap_disconnected: 1199 raise Exception("Unexpected event:%s%s%s%s" % 1200 (" disconnected" if disconnected else "", 1201 " eap_start" if eap_start else "", 1202 " eap_failure" if eap_failure else "", 1203 " ap_disconnected" if ap_disconnected else "")) 1204 hwsim_utils.test_connectivity(dev[0], hapd) 1205 state = dev[0].get_status_field("wpa_state") 1206 if state != "COMPLETED": 1207 raise Exception("Unexpected wpa_state: " + state) 1208 1209 dev[0].dump_monitor() 1210 hapd.dump_monitor() 1211 1212 # Inject various unexpected unprotected EAPOL frames to the AP 1213 f = "88010000" + bssid + addr + bssid + "0000" + "0700" 1214 f += "aaaa03000000" + "888e" 1215 tests = [] 1216 tests += [ "02020000" ] # EAPOL-Logoff 1217 for i in range(10): 1218 tests += [ "02010000" ] # EAPOL-Start 1219 for t in tests: 1220 hapd.note("Inject " + t) 1221 frame = binascii.unhexlify(f + t) 1222 sock.send(radiotap + frame) 1223 for i in range(2): 1224 ev = dev[0].wait_event(["CTRL-EVENT-DISCONNECTED", 1225 "CTRL-EVENT-EAP-STARTED", 1226 "CTRL-EVENT-EAP-FAILURE"], 1227 timeout=0.0001) 1228 if ev is None: 1229 break 1230 if "CTRL-EVENT-DISCONNECTED" in ev: 1231 disconnected = True 1232 if "CTRL-EVENT-EAP-START" in ev: 1233 eap_start = True 1234 if "CTRL-EVENT-EAP-FAILURE" in ev: 1235 eap_failure = True 1236 dev[0].dump_monitor(mon=False) 1237 dev[0].dump_monitor() 1238 ev = hapd.wait_event(["AP-STA-DISCONNECTED"], timeout=0.1) 1239 if ev: 1240 ap_disconnected = True 1241 hapd.dump_monitor() 1242 if disconnected or eap_start or eap_failure or ap_disconnected: 1243 raise Exception("Unexpected event(2):%s%s%s%s" % 1244 (" disconnected" if disconnected else "", 1245 " eap_start" if eap_start else "", 1246 " eap_failure" if eap_failure else "", 1247 " ap_disconnected" if ap_disconnected else "")) 1248 hwsim_utils.test_connectivity(dev[0], hapd) 1249 state = dev[0].get_status_field("wpa_state") 1250 if state != "COMPLETED": 1251 raise Exception("Unexpected wpa_state(2): " + state) 1252 1253def test_ap_pmf_tkip_reject(dev, apdev): 1254 """Mixed mode BSS and MFP-enabled AP rejecting TKIP""" 1255 skip_without_tkip(dev[0]) 1256 params = hostapd.wpa2_params(ssid="test-pmf", passphrase="12345678") 1257 params['wpa'] = '3' 1258 params["ieee80211w"] = "1" 1259 params["wpa_pairwise"] = "TKIP CCMP" 1260 params["rsn_pairwise"] = "TKIP CCMP" 1261 hostapd.add_ap(apdev[0], params) 1262 1263 dev[0].connect("test-pmf", psk="12345678", pairwise="CCMP", ieee80211w="2", 1264 scan_freq="2412") 1265 dev[0].dump_monitor() 1266 1267 dev[1].connect("test-pmf", psk="12345678", proto="WPA", pairwise="TKIP", 1268 ieee80211w="0", scan_freq="2412") 1269 dev[1].dump_monitor() 1270 1271 dev[2].connect("test-pmf", psk="12345678", pairwise="TKIP", 1272 ieee80211w="2", scan_freq="2412", wait_connect=False) 1273 ev = dev[2].wait_event(["CTRL-EVENT-CONNECTED", 1274 "CTRL-EVENT-ASSOC-REJECT"], timeout=10) 1275 if ev is None: 1276 raise Exception("No connection result reported") 1277 if "CTRL-EVENT-ASSOC-REJECT" not in ev: 1278 raise Exception("MFP + TKIP connection was not rejected") 1279 if "status_code=31" not in ev: 1280 raise Exception("Unexpected status code in rejection: " + ev) 1281 dev[2].request("DISCONNECT") 1282 dev[2].dump_monitor() 1283 1284def test_ap_pmf_sa_query_timeout(dev, apdev): 1285 """SA Query timeout""" 1286 ssid = "test-pmf-required" 1287 params = hostapd.wpa2_params(ssid=ssid, passphrase="12345678") 1288 params["wpa_key_mgmt"] = "WPA-PSK-SHA256" 1289 params["ieee80211w"] = "2" 1290 hapd = hostapd.add_ap(apdev[0], params) 1291 dev[0].connect(ssid, psk="12345678", ieee80211w="2", 1292 key_mgmt="WPA-PSK-SHA256", proto="WPA2", 1293 scan_freq="2412") 1294 1295 hapd.set("ext_mgmt_frame_handling", "1") 1296 if "OK" not in dev[0].request("UNPROT_DEAUTH"): 1297 raise Exception("Triggering SA Query from the STA failed") 1298 ev = dev[0].wait_event(["CTRL-EVENT-DISCONNECTED"], timeout=2) 1299 if ev is None: 1300 raise Exception("No disconnection on SA Query timeout seen") 1301 hapd.set("ext_mgmt_frame_handling", "0") 1302 dev[0].wait_connected() 1303 dev[0].dump_monitor() 1304 1305 hapd.set("ext_mgmt_frame_handling", "1") 1306 if "OK" not in dev[0].request("UNPROT_DEAUTH"): 1307 raise Exception("Triggering SA Query from the STA failed") 1308 ev = hapd.mgmt_rx() 1309 hapd.set("ext_mgmt_frame_handling", "0") 1310 dev[0].request("DISCONNECT") 1311 dev[0].wait_disconnected() 1312 dev[0].request("RECONNECT") 1313 dev[0].wait_connected() 1314 hapd.set("ext_mgmt_frame_handling", "1") 1315 ev = dev[0].wait_event(["CTRL-EVENT-DISCONNECTED"], timeout=1.5) 1316 if ev is not None: 1317 raise Exception("Unexpected disconnection after reconnection seen") 1318 1319def mac80211_read_key(keydir): 1320 vals = {} 1321 for name in os.listdir(keydir): 1322 try: 1323 with open(os.path.join(keydir, name)) as f: 1324 vals[name] = f.read().strip() 1325 except OSError as e: 1326 pass 1327 return vals 1328 1329def check_mac80211_bigtk(dev, hapd): 1330 sta_key = None 1331 ap_key = None 1332 1333 phy = dev.get_driver_status_field("phyname") 1334 keys = "/sys/kernel/debug/ieee80211/%s/keys" % phy 1335 try: 1336 for key in os.listdir(keys): 1337 keydir = os.path.join(keys, key) 1338 vals = mac80211_read_key(keydir) 1339 keyidx = int(vals['keyidx']) 1340 if keyidx == 6 or keyidx == 7: 1341 sta_key = vals; 1342 break 1343 except OSError as e: 1344 raise HwsimSkip("debugfs not supported in mac80211 (STA)") 1345 1346 phy = hapd.get_driver_status_field("phyname") 1347 keys = "/sys/kernel/debug/ieee80211/%s/keys" % phy 1348 try: 1349 for key in os.listdir(keys): 1350 keydir = os.path.join(keys, key) 1351 vals = mac80211_read_key(keydir) 1352 keyidx = int(vals['keyidx']) 1353 if keyidx == 6 or keyidx == 7: 1354 ap_key = vals; 1355 break 1356 except OSError as e: 1357 raise HwsimSkip("debugfs not supported in mac80211 (AP)") 1358 1359 if not sta_key: 1360 raise Exception("Could not find STA key information from debugfs") 1361 logger.info("STA key: " + str(sta_key)) 1362 1363 if not ap_key: 1364 raise Exception("Could not find AP key information from debugfs") 1365 logger.info("AP key: " + str(ap_key)) 1366 1367 if sta_key['key'] != ap_key['key']: 1368 raise Exception("AP and STA BIGTK mismatch") 1369 1370 if sta_key['keyidx'] != ap_key['keyidx']: 1371 raise Exception("AP and STA BIGTK keyidx mismatch") 1372 1373 if sta_key['algorithm'] != ap_key['algorithm']: 1374 raise Exception("AP and STA BIGTK algorithm mismatch") 1375 1376 replays = int(sta_key['replays']) 1377 icverrors = int(sta_key['icverrors']) 1378 if replays > 0 or icverrors > 0: 1379 raise Exception("STA reported errors: replays=%d icverrors=%d" % replays, icverrors) 1380 1381 rx_spec = int(sta_key['rx_spec'], base=16) 1382 if rx_spec < 3: 1383 raise Exception("STA did not update BIGTK receive counter sufficiently") 1384 1385 tx_spec = int(ap_key['tx_spec'], base=16) 1386 if tx_spec < 3: 1387 raise Exception("AP did not update BIGTK BIPN sufficiently") 1388 1389def test_ap_pmf_beacon_protection_bip(dev, apdev): 1390 """WPA2-PSK Beacon protection (BIP)""" 1391 run_ap_pmf_beacon_protection(dev, apdev, "AES-128-CMAC") 1392 1393def test_ap_pmf_beacon_protection_bip_cmac_256(dev, apdev): 1394 """WPA2-PSK Beacon protection (BIP-CMAC-256)""" 1395 run_ap_pmf_beacon_protection(dev, apdev, "BIP-CMAC-256") 1396 1397def test_ap_pmf_beacon_protection_bip_gmac_128(dev, apdev): 1398 """WPA2-PSK Beacon protection (BIP-GMAC-128)""" 1399 run_ap_pmf_beacon_protection(dev, apdev, "BIP-GMAC-128") 1400 1401def test_ap_pmf_beacon_protection_bip_gmac_256(dev, apdev): 1402 """WPA2-PSK Beacon protection (BIP-GMAC-256)""" 1403 run_ap_pmf_beacon_protection(dev, apdev, "BIP-GMAC-256") 1404 1405def run_ap_pmf_beacon_protection(dev, apdev, cipher): 1406 ssid = "test-beacon-prot" 1407 params = hostapd.wpa2_params(ssid=ssid, passphrase="12345678") 1408 params["wpa_key_mgmt"] = "WPA-PSK-SHA256" 1409 params["ieee80211w"] = "2" 1410 params["beacon_prot"] = "1" 1411 params["group_mgmt_cipher"] = cipher 1412 try: 1413 hapd = hostapd.add_ap(apdev[0], params) 1414 except Exception as e: 1415 if "Failed to enable hostapd interface" in str(e): 1416 raise HwsimSkip("Beacon protection not supported") 1417 raise 1418 1419 bssid = hapd.own_addr() 1420 1421 Wlantest.setup(hapd) 1422 wt = Wlantest() 1423 wt.flush() 1424 wt.add_passphrase("12345678") 1425 1426 dev[0].flush_scan_cache() 1427 1428 # STA with Beacon protection enabled 1429 dev[0].connect(ssid, psk="12345678", ieee80211w="2", beacon_prot="1", 1430 key_mgmt="WPA-PSK-SHA256", proto="WPA2", scan_freq="2412") 1431 if dev[0].get_status_field("bigtk_set") != "1": 1432 raise Exception("bigtk_set=1 not indicated") 1433 1434 # STA with Beacon protection disabled 1435 dev[1].connect(ssid, psk="12345678", ieee80211w="2", 1436 key_mgmt="WPA-PSK-SHA256", proto="WPA2", scan_freq="2412") 1437 if dev[1].get_status_field("bigtk_set") == "1": 1438 raise Exception("Unexpected bigtk_set=1 indication") 1439 1440 time.sleep(1) 1441 check_mac80211_bigtk(dev[0], hapd) 1442 1443 valid_bip = wt.get_bss_counter('valid_bip_mmie', bssid) 1444 invalid_bip = wt.get_bss_counter('invalid_bip_mmie', bssid) 1445 missing_bip = wt.get_bss_counter('missing_bip_mmie', bssid) 1446 logger.info("wlantest BIP counters: valid=%d invalid=%d missing=%d" % (valid_bip, invalid_bip, missing_bip)) 1447 if valid_bip < 0 or invalid_bip > 0 or missing_bip > 0: 1448 raise Exception("Unexpected wlantest BIP counters: valid=%d invalid=%d missing=%d" % (valid_bip, invalid_bip, missing_bip)) 1449 1450 ev = dev[0].wait_event(["CTRL-EVENT-BEACON-LOSS"], timeout=10) 1451 if ev is not None: 1452 raise Exception("Beacon loss detected") 1453 1454 # Verify that the SSID has been successfully verified from a protected 1455 # Beacon frame. 1456 if dev[0].get_status_field("ssid_verified") != "1": 1457 raise Exception("ssid_verified=1 not in STATUS") 1458 1459def test_ap_pmf_beacon_protection_mismatch(dev, apdev): 1460 """WPA2-PSK Beacon protection MIC mismatch""" 1461 run_ap_pmf_beacon_protection_mismatch(dev, apdev, False) 1462 1463def test_ap_pmf_beacon_protection_missing(dev, apdev): 1464 """WPA2-PSK Beacon protection MME missing""" 1465 run_ap_pmf_beacon_protection_mismatch(dev, apdev, True) 1466 1467def run_ap_pmf_beacon_protection_mismatch(dev, apdev, clear): 1468 ssid = "test-beacon-prot" 1469 params = hostapd.wpa2_params(ssid=ssid, passphrase="12345678") 1470 params["wpa_key_mgmt"] = "WPA-PSK-SHA256" 1471 params["ieee80211w"] = "2" 1472 params["beacon_prot"] = "1" 1473 params["group_mgmt_cipher"] = "AES-128-CMAC" 1474 try: 1475 hapd = hostapd.add_ap(apdev[0], params) 1476 except Exception as e: 1477 if "Failed to enable hostapd interface" in str(e): 1478 raise HwsimSkip("Beacon protection not supported") 1479 raise 1480 1481 bssid = hapd.own_addr() 1482 1483 Wlantest.setup(hapd) 1484 wt = Wlantest() 1485 wt.flush() 1486 wt.add_passphrase("12345678") 1487 1488 dev[0].connect(ssid, psk="12345678", ieee80211w="2", beacon_prot="1", 1489 key_mgmt="WPA-PSK-SHA256", proto="WPA2", scan_freq="2412") 1490 1491 WPA_ALG_NONE = 0 1492 WPA_ALG_IGTK = 4 1493 KEY_FLAG_DEFAULT = 0x02 1494 KEY_FLAG_TX = 0x08 1495 KEY_FLAG_GROUP = 0x10 1496 KEY_FLAG_GROUP_TX_DEFAULT = KEY_FLAG_GROUP | KEY_FLAG_TX | KEY_FLAG_DEFAULT 1497 1498 addr = "ff:ff:ff:ff:ff:ff" 1499 1500 if clear: 1501 res = hapd.request("SET_KEY %d %s %d %d %s %s %d" % (WPA_ALG_NONE, addr, 6, 1, 6*"00", "", KEY_FLAG_GROUP)) 1502 else: 1503 res = hapd.request("SET_KEY %d %s %d %d %s %s %d" % (WPA_ALG_IGTK, addr, 6, 1, 6*"00", 16*"00", KEY_FLAG_GROUP_TX_DEFAULT)) 1504 if "OK" not in res: 1505 raise Exception("SET_KEY failed") 1506 1507 ev = dev[0].wait_event(["CTRL-EVENT-UNPROT-BEACON"], timeout=5) 1508 if ev is None: 1509 raise Exception("Unprotected Beacon frame not reported") 1510 1511 ev = dev[0].wait_event(["CTRL-EVENT-BEACON-LOSS"], timeout=5) 1512 if ev is None: 1513 raise Exception("Beacon loss not reported") 1514 1515 ev = hapd.wait_event(["CTRL-EVENT-UNPROT-BEACON"], timeout=5) 1516 if ev is None: 1517 raise Exception("WNM-Notification Request frame not reported") 1518 1519def test_ap_pmf_beacon_protection_reconnect(dev, apdev): 1520 """Beacon protection and reconnection""" 1521 ssid = "test-beacon-prot" 1522 params = hostapd.wpa2_params(ssid=ssid, passphrase="12345678") 1523 params["wpa_key_mgmt"] = "WPA-PSK-SHA256" 1524 params["ieee80211w"] = "2" 1525 params["beacon_prot"] = "1" 1526 params["group_mgmt_cipher"] = "AES-128-CMAC" 1527 try: 1528 hapd = hostapd.add_ap(apdev[0], params) 1529 except Exception as e: 1530 if "Failed to enable hostapd interface" in str(e): 1531 raise HwsimSkip("Beacon protection not supported") 1532 raise 1533 1534 dev[0].connect(ssid, psk="12345678", ieee80211w="2", beacon_prot="1", 1535 key_mgmt="WPA-PSK-SHA256", proto="WPA2", scan_freq="2412") 1536 dev[0].request("DISCONNECT") 1537 dev[0].wait_disconnected() 1538 dev[0].request("RECONNECT") 1539 dev[0].wait_connected() 1540 time.sleep(1) 1541 check_mac80211_bigtk(dev[0], hapd) 1542 ev = dev[0].wait_event(["CTRL-EVENT-BEACON-LOSS"], timeout=5) 1543 if ev is not None: 1544 raise Exception("Beacon loss detected") 1545 1546def test_ap_pmf_beacon_protection_unicast(dev, apdev): 1547 """WPA2-PSK Beacon protection (BIP) and unicast Beacon frame""" 1548 try: 1549 run_ap_pmf_beacon_protection_unicast(dev, apdev) 1550 finally: 1551 stop_monitor(apdev[1]["ifname"]) 1552 1553def run_ap_pmf_beacon_protection_unicast(dev, apdev): 1554 cipher = "AES-128-CMAC" 1555 ssid = "test-beacon-prot" 1556 params = hostapd.wpa2_params(ssid=ssid, passphrase="12345678") 1557 params["wpa_key_mgmt"] = "WPA-PSK-SHA256" 1558 params["ieee80211w"] = "2" 1559 params["beacon_prot"] = "1" 1560 params["group_mgmt_cipher"] = cipher 1561 try: 1562 hapd = hostapd.add_ap(apdev[0], params) 1563 except Exception as e: 1564 if "Failed to enable hostapd interface" in str(e): 1565 raise HwsimSkip("Beacon protection not supported") 1566 raise 1567 1568 bssid = hapd.own_addr() 1569 1570 Wlantest.setup(hapd) 1571 wt = Wlantest() 1572 wt.flush() 1573 wt.add_passphrase("12345678") 1574 1575 # STA with Beacon protection enabled 1576 dev[0].connect(ssid, psk="12345678", ieee80211w="2", beacon_prot="1", 1577 key_mgmt="WPA-PSK-SHA256", proto="WPA2", scan_freq="2412") 1578 hapd.wait_sta() 1579 1580 sock = start_monitor(apdev[1]["ifname"]) 1581 radiotap = radiotap_build() 1582 1583 bssid = hapd.own_addr().replace(':', '') 1584 addr = dev[0].own_addr().replace(':', '') 1585 1586 h = "80000000" + addr + bssid + bssid + "0000" 1587 h += "c0a0260d27090600"+ "6400" + "1104" 1588 h += "0010746573742d626561636f6e2d70726f74" 1589 h += "010882848b960c121824" 1590 h += "03010" 1591 h += "1050400020000" 1592 h += "2a0104" 1593 h += "32043048606c" 1594 h += "30140100000fac040100000fac040100000fac06cc00" 1595 h += "3b025100" 1596 h += "2d1a0c001bffff000000000000000000000100000000000000000000" 1597 h += "3d1601000000000000000000000000000000000000000000" 1598 h += "7f0b0400000200000040000010" 1599 h += "dd180050f2020101010003a4000027a4000042435e0062322f00" 1600 1601 frame = binascii.unhexlify(h) 1602 h += "4c1006002100000000002b8fab24bcef3bb1" #MME 1603 frame2 = binascii.unhexlify(h) 1604 1605 sock.send(radiotap + frame) 1606 ev = dev[0].wait_event(["CTRL-EVENT-UNPROT-BEACON"], timeout=5) 1607 if ev is None: 1608 raise Exception("Unprotected beacon was not reported") 1609 if hapd.own_addr() not in ev: 1610 raise Exception("Unexpected BSSID in unproted beacon indication") 1611 1612 time.sleep(10.1) 1613 sock.send(radiotap + frame2) 1614 ev = dev[0].wait_event(["CTRL-EVENT-UNPROT-BEACON"], timeout=5) 1615 if ev is None: 1616 raise Exception("Unprotected beacon was not reported") 1617 if hapd.own_addr() not in ev: 1618 raise Exception("Unexpected BSSID in unproted beacon indication") 1619 1620def test_ap_pmf_sta_global_require(dev, apdev): 1621 """WPA2-PSK AP with PMF optional and wpa_supplicant pmf=2""" 1622 ssid = "test-pmf-optional" 1623 params = hostapd.wpa2_params(ssid=ssid, passphrase="12345678") 1624 params["wpa_key_mgmt"] = "WPA-PSK" 1625 params["ieee80211w"] = "1" 1626 hapd = hostapd.add_ap(apdev[0], params) 1627 try: 1628 dev[0].set("pmf", "2") 1629 dev[0].connect(ssid, psk="12345678", 1630 key_mgmt="WPA-PSK WPA-PSK-SHA256", proto="WPA2", 1631 scan_freq="2412") 1632 pmf = dev[0].get_status_field("pmf") 1633 if pmf != "1": 1634 raise Exception("Unexpected PMF state: " + str(pmf)) 1635 finally: 1636 dev[0].set("pmf", "0") 1637 1638def test_ap_pmf_sta_global_require2(dev, apdev): 1639 """WPA2-PSK AP with PMF optional and wpa_supplicant pmf=2 (2)""" 1640 ssid = "test-pmf-optional" 1641 params = hostapd.wpa2_params(ssid=ssid, passphrase="12345678") 1642 params["wpa_key_mgmt"] = "WPA-PSK" 1643 params["ieee80211w"] = "0" 1644 hapd = hostapd.add_ap(apdev[0], params) 1645 bssid = hapd.own_addr() 1646 try: 1647 dev[0].scan_for_bss(bssid, freq=2412) 1648 dev[0].set("pmf", "2") 1649 dev[0].connect(ssid, psk="12345678", 1650 key_mgmt="WPA-PSK WPA-PSK-SHA256", proto="WPA2", 1651 scan_freq="2412", wait_connect=False) 1652 ev = dev[0].wait_event(["CTRL-EVENT-CONNECTED", 1653 "CTRL-EVENT-NETWORK-NOT-FOUND"], timeout=10) 1654 if ev is None: 1655 raise Exception("Connection result not reported") 1656 if "CTRL-EVENT-CONNECTED" in ev: 1657 raise Exception("Unexpected connection") 1658 finally: 1659 dev[0].set("pmf", "0") 1660 1661def test_ap_pmf_drop_robust_mgmt_prior_to_keys_installation(dev, apdev): 1662 """Drop non protected Robust Action frames prior to keys installation""" 1663 ssid = "test-pmf-required" 1664 passphrase = '12345678' 1665 params = hostapd.wpa2_params(ssid=ssid, passphrase=passphrase) 1666 params['delay_eapol_tx'] = '1' 1667 params['ieee80211w'] = '2' 1668 params['wpa_pairwise_update_count'] = '5' 1669 hapd = hostapd.add_ap(apdev[0], params, wait_enabled=False) 1670 1671 # Spectrum management with Channel Switch element 1672 msg = {'fc': 0x00d0, 1673 'sa': hapd.own_addr(), 1674 'da': dev[0].own_addr(), 1675 'bssid': hapd.own_addr(), 1676 'payload': binascii.unhexlify('00042503000608') 1677 } 1678 1679 dev[0].connect(ssid, psk=passphrase, scan_freq='2412', ieee80211w='1', 1680 wait_connect=False) 1681 1682 # wait for the first delay before sending the frame 1683 ev = hapd.wait_event(['DELAY-EAPOL-TX-1'], timeout=10) 1684 if ev is None: 1685 raise Exception("EAPOL is not delayed") 1686 1687 # send the Action frame while connecting (prior to keys installation) 1688 hapd.mgmt_tx(msg) 1689 1690 dev[0].wait_connected(timeout=10, error="Timeout on connection") 1691 hapd.wait_sta() 1692 hwsim_utils.test_connectivity(dev[0], hapd) 1693 1694 # Verify no channel switch event 1695 ev = dev[0].wait_event(['CTRL-EVENT-STARTED-CHANNEL-SWITCH'], timeout=5) 1696 if ev is not None: 1697 raise Exception("Unexpected CSA prior to keys installation") 1698 1699 # Send the frame after keys installation and verify channel switch event 1700 hapd.mgmt_tx(msg) 1701 ev = dev[0].wait_event(['CTRL-EVENT-STARTED-CHANNEL-SWITCH'], timeout=5) 1702 if ev is None: 1703 raise Exception("Expected CSA handling after keys installation") 1704 1705def test_ap_pmf_eapol_logoff(dev, apdev): 1706 """WPA2-EAP AP with PMF required and EAPOL-Logoff""" 1707 ssid = "test-pmf-required-eap" 1708 params = hostapd.wpa2_eap_params(ssid=ssid) 1709 params["wpa_key_mgmt"] = "WPA-EAP-SHA256" 1710 params["ieee80211w"] = "2" 1711 hapd = hostapd.add_ap(apdev[0], params) 1712 hapd.request("SET ext_eapol_frame_io 1") 1713 1714 dev[0].set("ext_eapol_frame_io", "1") 1715 dev[0].connect("test-pmf-required-eap", key_mgmt="WPA-EAP-SHA256", 1716 ieee80211w="2", eap="PSK", identity="psk.user@example.com", 1717 password_hex="0123456789abcdef0123456789abcdef", 1718 scan_freq="2412", wait_connect=False) 1719 1720 # EAP-Request/Identity 1721 proxy_msg(hapd, dev[0]) 1722 1723 # EAP-Response/Identity RX 1724 msg = rx_msg(dev[0]) 1725 # EAPOL-Logoff TX (inject) 1726 tx_msg(dev[0], hapd, "02020000") 1727 # EAP-Response/Identity TX (proxy previously received) 1728 tx_msg(dev[0], hapd, msg) 1729 1730 # Verify that the 10 ms timeout for deauthenticating STA after EAP-Failure 1731 # is not used in this sequence with the EAPOL-Logoff message before the 1732 # successful authentication. 1733 ev = dev[0].wait_event(["CTRL-EVENT-DISCONNECTED"], timeout=0.03) 1734 if ev: 1735 raise Exception("Unexpected disconnection") 1736 1737 # EAP-Request/Identity 1738 proxy_msg(hapd, dev[0]) 1739 # EAP-Response/Identity 1740 proxy_msg(dev[0], hapd) 1741 1742 # EAP-PSK 1743 proxy_msg(hapd, dev[0]) 1744 proxy_msg(dev[0], hapd) 1745 proxy_msg(hapd, dev[0]) 1746 proxy_msg(dev[0], hapd) 1747 proxy_msg(hapd, dev[0]) 1748 1749 # 4-way handshake 1750 proxy_msg(hapd, dev[0]) 1751 proxy_msg(dev[0], hapd) 1752 proxy_msg(hapd, dev[0]) 1753 proxy_msg(dev[0], hapd) 1754 1755 ev = hapd.wait_event(["EAPOL-4WAY-HS-COMPLETED"], timeout=1) 1756 if ev is None: 1757 raise Exception("4-way handshake did not complete successfully") 1758 dev[0].wait_connected(timeout=0.1) 1759 hapd.wait_sta() 1760 1761 # Verify that the STA gets disconnected when the EAPOL-Logoff message is 1762 # sent after successful authentication. 1763 1764 # EAPOL-Logoff TX (inject) 1765 tx_msg(dev[0], hapd, "02020000") 1766 hapd.request("SET ext_eapol_frame_io 0") 1767 dev[0].set("ext_eapol_frame_io", "0") 1768 ev = dev[0].wait_disconnected(timeout=1) 1769 if "reason=23" not in ev: 1770 raise Exception("Unexpected disconnection reason: " + ev) 1771