Home | History | Annotate | Download | only in ap
      1 /*
      2  * hostapd / Callback functions for driver wrappers
      3  * Copyright (c) 2002-2009, Jouni Malinen <j (at) w1.fi>
      4  *
      5  * This software may be distributed under the terms of the BSD license.
      6  * See README for more details.
      7  */
      8 
      9 #include "utils/includes.h"
     10 
     11 #include "utils/common.h"
     12 #include "radius/radius.h"
     13 #include "drivers/driver.h"
     14 #include "common/ieee802_11_defs.h"
     15 #include "common/ieee802_11_common.h"
     16 #include "crypto/random.h"
     17 #include "p2p/p2p.h"
     18 #include "wps/wps.h"
     19 #include "wnm_ap.h"
     20 #include "hostapd.h"
     21 #include "ieee802_11.h"
     22 #include "sta_info.h"
     23 #include "accounting.h"
     24 #include "tkip_countermeasures.h"
     25 #include "ieee802_1x.h"
     26 #include "wpa_auth.h"
     27 #include "wps_hostapd.h"
     28 #include "ap_drv_ops.h"
     29 #include "ap_config.h"
     30 #include "hw_features.h"
     31 
     32 
     33 int hostapd_notif_assoc(struct hostapd_data *hapd, const u8 *addr,
     34 			const u8 *req_ies, size_t req_ies_len, int reassoc)
     35 {
     36 	struct sta_info *sta;
     37 	int new_assoc, res;
     38 	struct ieee802_11_elems elems;
     39 	const u8 *ie;
     40 	size_t ielen;
     41 #ifdef CONFIG_IEEE80211R
     42 	u8 buf[sizeof(struct ieee80211_mgmt) + 1024];
     43 	u8 *p = buf;
     44 #endif /* CONFIG_IEEE80211R */
     45 	u16 reason = WLAN_REASON_UNSPECIFIED;
     46 	u16 status = WLAN_STATUS_SUCCESS;
     47 
     48 	if (addr == NULL) {
     49 		/*
     50 		 * This could potentially happen with unexpected event from the
     51 		 * driver wrapper. This was seen at least in one case where the
     52 		 * driver ended up being set to station mode while hostapd was
     53 		 * running, so better make sure we stop processing such an
     54 		 * event here.
     55 		 */
     56 		wpa_printf(MSG_DEBUG, "hostapd_notif_assoc: Skip event with "
     57 			   "no address");
     58 		return -1;
     59 	}
     60 	random_add_randomness(addr, ETH_ALEN);
     61 
     62 	hostapd_logger(hapd, addr, HOSTAPD_MODULE_IEEE80211,
     63 		       HOSTAPD_LEVEL_INFO, "associated");
     64 
     65 	ieee802_11_parse_elems(req_ies, req_ies_len, &elems, 0);
     66 	if (elems.wps_ie) {
     67 		ie = elems.wps_ie - 2;
     68 		ielen = elems.wps_ie_len + 2;
     69 		wpa_printf(MSG_DEBUG, "STA included WPS IE in (Re)AssocReq");
     70 	} else if (elems.rsn_ie) {
     71 		ie = elems.rsn_ie - 2;
     72 		ielen = elems.rsn_ie_len + 2;
     73 		wpa_printf(MSG_DEBUG, "STA included RSN IE in (Re)AssocReq");
     74 	} else if (elems.wpa_ie) {
     75 		ie = elems.wpa_ie - 2;
     76 		ielen = elems.wpa_ie_len + 2;
     77 		wpa_printf(MSG_DEBUG, "STA included WPA IE in (Re)AssocReq");
     78 	} else {
     79 		ie = NULL;
     80 		ielen = 0;
     81 		wpa_printf(MSG_DEBUG, "STA did not include WPS/RSN/WPA IE in "
     82 			   "(Re)AssocReq");
     83 	}
     84 
     85 	sta = ap_get_sta(hapd, addr);
     86 	if (sta) {
     87 		accounting_sta_stop(hapd, sta);
     88 
     89 		/*
     90 		 * Make sure that the previously registered inactivity timer
     91 		 * will not remove the STA immediately.
     92 		 */
     93 		sta->timeout_next = STA_NULLFUNC;
     94 	} else {
     95 		sta = ap_sta_add(hapd, addr);
     96 		if (sta == NULL) {
     97 			hostapd_drv_sta_disassoc(hapd, addr,
     98 						 WLAN_REASON_DISASSOC_AP_BUSY);
     99 			return -1;
    100 		}
    101 	}
    102 	sta->flags &= ~(WLAN_STA_WPS | WLAN_STA_MAYBE_WPS | WLAN_STA_WPS2);
    103 
    104 #ifdef CONFIG_P2P
    105 	if (elems.p2p) {
    106 		wpabuf_free(sta->p2p_ie);
    107 		sta->p2p_ie = ieee802_11_vendor_ie_concat(req_ies, req_ies_len,
    108 							  P2P_IE_VENDOR_TYPE);
    109 	}
    110 #endif /* CONFIG_P2P */
    111 
    112 	if (hapd->conf->wpa) {
    113 		if (ie == NULL || ielen == 0) {
    114 #ifdef CONFIG_WPS
    115 			if (hapd->conf->wps_state) {
    116 				wpa_printf(MSG_DEBUG, "STA did not include "
    117 					   "WPA/RSN IE in (Re)Association "
    118 					   "Request - possible WPS use");
    119 				sta->flags |= WLAN_STA_MAYBE_WPS;
    120 				goto skip_wpa_check;
    121 			}
    122 #endif /* CONFIG_WPS */
    123 
    124 			wpa_printf(MSG_DEBUG, "No WPA/RSN IE from STA");
    125 			return -1;
    126 		}
    127 #ifdef CONFIG_WPS
    128 		if (hapd->conf->wps_state && ie[0] == 0xdd && ie[1] >= 4 &&
    129 		    os_memcmp(ie + 2, "\x00\x50\xf2\x04", 4) == 0) {
    130 			struct wpabuf *wps;
    131 			sta->flags |= WLAN_STA_WPS;
    132 			wps = ieee802_11_vendor_ie_concat(ie, ielen,
    133 							  WPS_IE_VENDOR_TYPE);
    134 			if (wps) {
    135 				if (wps_is_20(wps)) {
    136 					wpa_printf(MSG_DEBUG, "WPS: STA "
    137 						   "supports WPS 2.0");
    138 					sta->flags |= WLAN_STA_WPS2;
    139 				}
    140 				wpabuf_free(wps);
    141 			}
    142 			goto skip_wpa_check;
    143 		}
    144 #endif /* CONFIG_WPS */
    145 
    146 		if (sta->wpa_sm == NULL)
    147 			sta->wpa_sm = wpa_auth_sta_init(hapd->wpa_auth,
    148 							sta->addr);
    149 		if (sta->wpa_sm == NULL) {
    150 			wpa_printf(MSG_ERROR, "Failed to initialize WPA state "
    151 				   "machine");
    152 			return -1;
    153 		}
    154 		res = wpa_validate_wpa_ie(hapd->wpa_auth, sta->wpa_sm,
    155 					  ie, ielen,
    156 					  elems.mdie, elems.mdie_len);
    157 		if (res != WPA_IE_OK) {
    158 			wpa_printf(MSG_DEBUG, "WPA/RSN information element "
    159 				   "rejected? (res %u)", res);
    160 			wpa_hexdump(MSG_DEBUG, "IE", ie, ielen);
    161 			if (res == WPA_INVALID_GROUP) {
    162 				reason = WLAN_REASON_GROUP_CIPHER_NOT_VALID;
    163 				status = WLAN_STATUS_GROUP_CIPHER_NOT_VALID;
    164 			} else if (res == WPA_INVALID_PAIRWISE) {
    165 				reason = WLAN_REASON_PAIRWISE_CIPHER_NOT_VALID;
    166 				status = WLAN_STATUS_PAIRWISE_CIPHER_NOT_VALID;
    167 			} else if (res == WPA_INVALID_AKMP) {
    168 				reason = WLAN_REASON_AKMP_NOT_VALID;
    169 				status = WLAN_STATUS_AKMP_NOT_VALID;
    170 			}
    171 #ifdef CONFIG_IEEE80211W
    172 			else if (res == WPA_MGMT_FRAME_PROTECTION_VIOLATION) {
    173 				reason = WLAN_REASON_INVALID_IE;
    174 				status = WLAN_STATUS_INVALID_IE;
    175 			} else if (res == WPA_INVALID_MGMT_GROUP_CIPHER) {
    176 				reason = WLAN_REASON_GROUP_CIPHER_NOT_VALID;
    177 				status = WLAN_STATUS_GROUP_CIPHER_NOT_VALID;
    178 			}
    179 #endif /* CONFIG_IEEE80211W */
    180 			else {
    181 				reason = WLAN_REASON_INVALID_IE;
    182 				status = WLAN_STATUS_INVALID_IE;
    183 			}
    184 			goto fail;
    185 		}
    186 #ifdef CONFIG_IEEE80211W
    187 		if ((sta->flags & WLAN_STA_MFP) && !sta->sa_query_timed_out &&
    188 		    sta->sa_query_count > 0)
    189 			ap_check_sa_query_timeout(hapd, sta);
    190 		if ((sta->flags & WLAN_STA_MFP) && !sta->sa_query_timed_out &&
    191 		    (sta->auth_alg != WLAN_AUTH_FT)) {
    192 			/*
    193 			 * STA has already been associated with MFP and SA
    194 			 * Query timeout has not been reached. Reject the
    195 			 * association attempt temporarily and start SA Query,
    196 			 * if one is not pending.
    197 			 */
    198 
    199 			if (sta->sa_query_count == 0)
    200 				ap_sta_start_sa_query(hapd, sta);
    201 
    202 #ifdef CONFIG_IEEE80211R
    203 			status = WLAN_STATUS_ASSOC_REJECTED_TEMPORARILY;
    204 
    205 			p = hostapd_eid_assoc_comeback_time(hapd, sta, p);
    206 
    207 			hostapd_sta_assoc(hapd, addr, reassoc, status, buf,
    208 					  p - buf);
    209 #endif /* CONFIG_IEEE80211R */
    210 			return 0;
    211 		}
    212 
    213 		if (wpa_auth_uses_mfp(sta->wpa_sm))
    214 			sta->flags |= WLAN_STA_MFP;
    215 		else
    216 			sta->flags &= ~WLAN_STA_MFP;
    217 #endif /* CONFIG_IEEE80211W */
    218 
    219 #ifdef CONFIG_IEEE80211R
    220 		if (sta->auth_alg == WLAN_AUTH_FT) {
    221 			status = wpa_ft_validate_reassoc(sta->wpa_sm, req_ies,
    222 							 req_ies_len);
    223 			if (status != WLAN_STATUS_SUCCESS) {
    224 				if (status == WLAN_STATUS_INVALID_PMKID)
    225 					reason = WLAN_REASON_INVALID_IE;
    226 				if (status == WLAN_STATUS_INVALID_MDIE)
    227 					reason = WLAN_REASON_INVALID_IE;
    228 				if (status == WLAN_STATUS_INVALID_FTIE)
    229 					reason = WLAN_REASON_INVALID_IE;
    230 				goto fail;
    231 			}
    232 		}
    233 #endif /* CONFIG_IEEE80211R */
    234 	} else if (hapd->conf->wps_state) {
    235 #ifdef CONFIG_WPS
    236 		struct wpabuf *wps;
    237 		if (req_ies)
    238 			wps = ieee802_11_vendor_ie_concat(req_ies, req_ies_len,
    239 							  WPS_IE_VENDOR_TYPE);
    240 		else
    241 			wps = NULL;
    242 #ifdef CONFIG_WPS_STRICT
    243 		if (wps && wps_validate_assoc_req(wps) < 0) {
    244 			reason = WLAN_REASON_INVALID_IE;
    245 			status = WLAN_STATUS_INVALID_IE;
    246 			wpabuf_free(wps);
    247 			goto fail;
    248 		}
    249 #endif /* CONFIG_WPS_STRICT */
    250 		if (wps) {
    251 			sta->flags |= WLAN_STA_WPS;
    252 			if (wps_is_20(wps)) {
    253 				wpa_printf(MSG_DEBUG, "WPS: STA supports "
    254 					   "WPS 2.0");
    255 				sta->flags |= WLAN_STA_WPS2;
    256 			}
    257 		} else
    258 			sta->flags |= WLAN_STA_MAYBE_WPS;
    259 		wpabuf_free(wps);
    260 #endif /* CONFIG_WPS */
    261 	}
    262 #ifdef CONFIG_WPS
    263 skip_wpa_check:
    264 #endif /* CONFIG_WPS */
    265 
    266 #ifdef CONFIG_IEEE80211R
    267 	p = wpa_sm_write_assoc_resp_ies(sta->wpa_sm, buf, sizeof(buf),
    268 					sta->auth_alg, req_ies, req_ies_len);
    269 
    270 	hostapd_sta_assoc(hapd, addr, reassoc, status, buf, p - buf);
    271 #else /* CONFIG_IEEE80211R */
    272 	/* Keep compiler silent about unused variables */
    273 	if (status) {
    274 	}
    275 #endif /* CONFIG_IEEE80211R */
    276 
    277 	new_assoc = (sta->flags & WLAN_STA_ASSOC) == 0;
    278 	sta->flags |= WLAN_STA_AUTH | WLAN_STA_ASSOC;
    279 
    280 	if (reassoc && (sta->auth_alg == WLAN_AUTH_FT))
    281 		wpa_auth_sm_event(sta->wpa_sm, WPA_ASSOC_FT);
    282 	else
    283 		wpa_auth_sm_event(sta->wpa_sm, WPA_ASSOC);
    284 
    285 	hostapd_new_assoc_sta(hapd, sta, !new_assoc);
    286 
    287 	ieee802_1x_notify_port_enabled(sta->eapol_sm, 1);
    288 
    289 #ifdef CONFIG_P2P
    290 	if (req_ies) {
    291 		p2p_group_notif_assoc(hapd->p2p_group, sta->addr,
    292 				      req_ies, req_ies_len);
    293 	}
    294 #endif /* CONFIG_P2P */
    295 
    296 	return 0;
    297 
    298 fail:
    299 #ifdef CONFIG_IEEE80211R
    300 	hostapd_sta_assoc(hapd, addr, reassoc, status, buf, p - buf);
    301 #endif /* CONFIG_IEEE80211R */
    302 	hostapd_drv_sta_disassoc(hapd, sta->addr, reason);
    303 	ap_free_sta(hapd, sta);
    304 	return -1;
    305 }
    306 
    307 
    308 void hostapd_notif_disassoc(struct hostapd_data *hapd, const u8 *addr)
    309 {
    310 	struct sta_info *sta;
    311 
    312 	if (addr == NULL) {
    313 		/*
    314 		 * This could potentially happen with unexpected event from the
    315 		 * driver wrapper. This was seen at least in one case where the
    316 		 * driver ended up reporting a station mode event while hostapd
    317 		 * was running, so better make sure we stop processing such an
    318 		 * event here.
    319 		 */
    320 		wpa_printf(MSG_DEBUG, "hostapd_notif_disassoc: Skip event "
    321 			   "with no address");
    322 		return;
    323 	}
    324 
    325 	hostapd_logger(hapd, addr, HOSTAPD_MODULE_IEEE80211,
    326 		       HOSTAPD_LEVEL_INFO, "disassociated");
    327 
    328 	sta = ap_get_sta(hapd, addr);
    329 	if (sta == NULL) {
    330 		wpa_printf(MSG_DEBUG, "Disassociation notification for "
    331 			   "unknown STA " MACSTR, MAC2STR(addr));
    332 		return;
    333 	}
    334 
    335 	ap_sta_set_authorized(hapd, sta, 0);
    336 	sta->flags &= ~(WLAN_STA_AUTH | WLAN_STA_ASSOC);
    337 	wpa_auth_sm_event(sta->wpa_sm, WPA_DISASSOC);
    338 	sta->acct_terminate_cause = RADIUS_ACCT_TERMINATE_CAUSE_USER_REQUEST;
    339 	ieee802_1x_notify_port_enabled(sta->eapol_sm, 0);
    340 	ap_free_sta(hapd, sta);
    341 }
    342 
    343 
    344 void hostapd_event_sta_low_ack(struct hostapd_data *hapd, const u8 *addr)
    345 {
    346 	struct sta_info *sta = ap_get_sta(hapd, addr);
    347 
    348 	if (!sta || !hapd->conf->disassoc_low_ack)
    349 		return;
    350 
    351 	hostapd_logger(hapd, addr, HOSTAPD_MODULE_IEEE80211,
    352 		       HOSTAPD_LEVEL_INFO, "disconnected due to excessive "
    353 		       "missing ACKs");
    354 	hostapd_drv_sta_disassoc(hapd, addr, WLAN_REASON_DISASSOC_LOW_ACK);
    355 	if (sta)
    356 		ap_sta_disassociate(hapd, sta, WLAN_REASON_DISASSOC_LOW_ACK);
    357 }
    358 
    359 
    360 void hostapd_event_ch_switch(struct hostapd_data *hapd, int freq, int ht,
    361 			     int offset)
    362 {
    363 #ifdef NEED_AP_MLME
    364 	int channel;
    365 
    366 	hostapd_logger(hapd, NULL, HOSTAPD_MODULE_IEEE80211,
    367 		       HOSTAPD_LEVEL_INFO, "driver had channel switch: "
    368 		       "freq=%d, ht=%d, offset=%d", freq, ht, offset);
    369 
    370 	hapd->iface->freq = freq;
    371 
    372 	channel = hostapd_hw_get_channel(hapd, freq);
    373 	if (!channel) {
    374 		hostapd_logger(hapd, NULL, HOSTAPD_MODULE_IEEE80211,
    375 			       HOSTAPD_LEVEL_WARNING, "driver switched to "
    376 			       "bad channel!");
    377 		return;
    378 	}
    379 
    380 	hapd->iconf->channel = channel;
    381 	hapd->iconf->ieee80211n = ht;
    382 	hapd->iconf->secondary_channel = offset;
    383 #endif /* NEED_AP_MLME */
    384 }
    385 
    386 
    387 int hostapd_probe_req_rx(struct hostapd_data *hapd, const u8 *sa, const u8 *da,
    388 			 const u8 *bssid, const u8 *ie, size_t ie_len,
    389 			 int ssi_signal)
    390 {
    391 	size_t i;
    392 	int ret = 0;
    393 
    394 	if (sa == NULL || ie == NULL)
    395 		return -1;
    396 
    397 	random_add_randomness(sa, ETH_ALEN);
    398 	for (i = 0; hapd->probereq_cb && i < hapd->num_probereq_cb; i++) {
    399 		if (hapd->probereq_cb[i].cb(hapd->probereq_cb[i].ctx,
    400 					    sa, da, bssid, ie, ie_len,
    401 					    ssi_signal) > 0) {
    402 			ret = 1;
    403 			break;
    404 		}
    405 	}
    406 	return ret;
    407 }
    408 
    409 
    410 #ifdef HOSTAPD
    411 
    412 #ifdef CONFIG_IEEE80211R
    413 static void hostapd_notify_auth_ft_finish(void *ctx, const u8 *dst,
    414 					  const u8 *bssid,
    415 					  u16 auth_transaction, u16 status,
    416 					  const u8 *ies, size_t ies_len)
    417 {
    418 	struct hostapd_data *hapd = ctx;
    419 	struct sta_info *sta;
    420 
    421 	sta = ap_get_sta(hapd, dst);
    422 	if (sta == NULL)
    423 		return;
    424 
    425 	hostapd_logger(hapd, dst, HOSTAPD_MODULE_IEEE80211,
    426 		       HOSTAPD_LEVEL_DEBUG, "authentication OK (FT)");
    427 	sta->flags |= WLAN_STA_AUTH;
    428 
    429 	hostapd_sta_auth(hapd, dst, auth_transaction, status, ies, ies_len);
    430 }
    431 #endif /* CONFIG_IEEE80211R */
    432 
    433 
    434 static void hostapd_notif_auth(struct hostapd_data *hapd,
    435 			       struct auth_info *rx_auth)
    436 {
    437 	struct sta_info *sta;
    438 	u16 status = WLAN_STATUS_SUCCESS;
    439 	u8 resp_ies[2 + WLAN_AUTH_CHALLENGE_LEN];
    440 	size_t resp_ies_len = 0;
    441 
    442 	sta = ap_get_sta(hapd, rx_auth->peer);
    443 	if (!sta) {
    444 		sta = ap_sta_add(hapd, rx_auth->peer);
    445 		if (sta == NULL) {
    446 			status = WLAN_STATUS_UNSPECIFIED_FAILURE;
    447 			goto fail;
    448 		}
    449 	}
    450 	sta->flags &= ~WLAN_STA_PREAUTH;
    451 	ieee802_1x_notify_pre_auth(sta->eapol_sm, 0);
    452 #ifdef CONFIG_IEEE80211R
    453 	if (rx_auth->auth_type == WLAN_AUTH_FT && hapd->wpa_auth) {
    454 		sta->auth_alg = WLAN_AUTH_FT;
    455 		if (sta->wpa_sm == NULL)
    456 			sta->wpa_sm = wpa_auth_sta_init(hapd->wpa_auth,
    457 							sta->addr);
    458 		if (sta->wpa_sm == NULL) {
    459 			wpa_printf(MSG_DEBUG, "FT: Failed to initialize WPA "
    460 				   "state machine");
    461 			status = WLAN_STATUS_UNSPECIFIED_FAILURE;
    462 			goto fail;
    463 		}
    464 		wpa_ft_process_auth(sta->wpa_sm, rx_auth->bssid,
    465 				    rx_auth->auth_transaction, rx_auth->ies,
    466 				    rx_auth->ies_len,
    467 				    hostapd_notify_auth_ft_finish, hapd);
    468 		return;
    469 	}
    470 #endif /* CONFIG_IEEE80211R */
    471 fail:
    472 	hostapd_sta_auth(hapd, rx_auth->peer, rx_auth->auth_transaction + 1,
    473 			 status, resp_ies, resp_ies_len);
    474 }
    475 
    476 
    477 static void hostapd_action_rx(struct hostapd_data *hapd,
    478 			      struct rx_action *action)
    479 {
    480 	struct sta_info *sta;
    481 
    482         wpa_printf(MSG_DEBUG, "RX_ACTION cat %d action plen %d",
    483 		   action->category, (int) action->len);
    484 
    485 	sta = ap_get_sta(hapd, action->sa);
    486 	if (sta == NULL) {
    487 		wpa_printf(MSG_DEBUG, "%s: station not found", __func__);
    488 		return;
    489 	}
    490 #ifdef CONFIG_IEEE80211R
    491 	if (action->category == WLAN_ACTION_FT) {
    492 		wpa_printf(MSG_DEBUG, "%s: FT_ACTION length %d",
    493 			   __func__, (int) action->len);
    494 		wpa_ft_action_rx(sta->wpa_sm, action->data, action->len);
    495 	}
    496 #endif /* CONFIG_IEEE80211R */
    497 #ifdef CONFIG_IEEE80211W
    498 	if (action->category == WLAN_ACTION_SA_QUERY && action->len >= 4) {
    499 		wpa_printf(MSG_DEBUG, "%s: SA_QUERY_ACTION length %d",
    500 			   __func__, (int) action->len);
    501 		ieee802_11_sa_query_action(hapd, action->sa,
    502 					   *(action->data + 1),
    503 					   action->data + 2);
    504 	}
    505 #endif /* CONFIG_IEEE80211W */
    506 #ifdef CONFIG_IEEE80211V
    507 	if (action->category == WLAN_ACTION_WNM) {
    508 		wpa_printf(MSG_DEBUG, "%s: WNM_ACTION length %d",
    509 			   __func__, (int) action->len);
    510 		ieee802_11_rx_wnm_action_ap(hapd, action);
    511 	}
    512 #endif /* CONFIG_IEEE80211V */
    513 }
    514 
    515 
    516 #ifdef NEED_AP_MLME
    517 
    518 #define HAPD_BROADCAST ((struct hostapd_data *) -1)
    519 
    520 static struct hostapd_data * get_hapd_bssid(struct hostapd_iface *iface,
    521 					    const u8 *bssid)
    522 {
    523 	size_t i;
    524 
    525 	if (bssid == NULL)
    526 		return NULL;
    527 	if (bssid[0] == 0xff && bssid[1] == 0xff && bssid[2] == 0xff &&
    528 	    bssid[3] == 0xff && bssid[4] == 0xff && bssid[5] == 0xff)
    529 		return HAPD_BROADCAST;
    530 
    531 	for (i = 0; i < iface->num_bss; i++) {
    532 		if (os_memcmp(bssid, iface->bss[i]->own_addr, ETH_ALEN) == 0)
    533 			return iface->bss[i];
    534 	}
    535 
    536 	return NULL;
    537 }
    538 
    539 
    540 static void hostapd_rx_from_unknown_sta(struct hostapd_data *hapd,
    541 					const u8 *bssid, const u8 *addr,
    542 					int wds)
    543 {
    544 	hapd = get_hapd_bssid(hapd->iface, bssid);
    545 	if (hapd == NULL || hapd == HAPD_BROADCAST)
    546 		return;
    547 
    548 	ieee802_11_rx_from_unknown(hapd, addr, wds);
    549 }
    550 
    551 
    552 static void hostapd_mgmt_rx(struct hostapd_data *hapd, struct rx_mgmt *rx_mgmt)
    553 {
    554 	struct hostapd_iface *iface = hapd->iface;
    555 	const struct ieee80211_hdr *hdr;
    556 	const u8 *bssid;
    557 	struct hostapd_frame_info fi;
    558 
    559 	hdr = (const struct ieee80211_hdr *) rx_mgmt->frame;
    560 	bssid = get_hdr_bssid(hdr, rx_mgmt->frame_len);
    561 	if (bssid == NULL)
    562 		return;
    563 
    564 	hapd = get_hapd_bssid(iface, bssid);
    565 	if (hapd == NULL) {
    566 		u16 fc;
    567 		fc = le_to_host16(hdr->frame_control);
    568 
    569 		/*
    570 		 * Drop frames to unknown BSSIDs except for Beacon frames which
    571 		 * could be used to update neighbor information.
    572 		 */
    573 		if (WLAN_FC_GET_TYPE(fc) == WLAN_FC_TYPE_MGMT &&
    574 		    WLAN_FC_GET_STYPE(fc) == WLAN_FC_STYPE_BEACON)
    575 			hapd = iface->bss[0];
    576 		else
    577 			return;
    578 	}
    579 
    580 	os_memset(&fi, 0, sizeof(fi));
    581 	fi.datarate = rx_mgmt->datarate;
    582 	fi.ssi_signal = rx_mgmt->ssi_signal;
    583 
    584 	if (hapd == HAPD_BROADCAST) {
    585 		size_t i;
    586 		for (i = 0; i < iface->num_bss; i++)
    587 			ieee802_11_mgmt(iface->bss[i], rx_mgmt->frame,
    588 					rx_mgmt->frame_len, &fi);
    589 	} else
    590 		ieee802_11_mgmt(hapd, rx_mgmt->frame, rx_mgmt->frame_len, &fi);
    591 
    592 	random_add_randomness(&fi, sizeof(fi));
    593 }
    594 
    595 
    596 static void hostapd_rx_action(struct hostapd_data *hapd,
    597 			      struct rx_action *rx_action)
    598 {
    599 	struct rx_mgmt rx_mgmt;
    600 	u8 *buf;
    601 	struct ieee80211_hdr *hdr;
    602 
    603 	wpa_printf(MSG_DEBUG, "EVENT_RX_ACTION DA=" MACSTR " SA=" MACSTR
    604 		   " BSSID=" MACSTR " category=%u",
    605 		   MAC2STR(rx_action->da), MAC2STR(rx_action->sa),
    606 		   MAC2STR(rx_action->bssid), rx_action->category);
    607 	wpa_hexdump(MSG_MSGDUMP, "Received action frame contents",
    608 		    rx_action->data, rx_action->len);
    609 
    610 	buf = os_zalloc(24 + 1 + rx_action->len);
    611 	if (buf == NULL)
    612 		return;
    613 	hdr = (struct ieee80211_hdr *) buf;
    614 	hdr->frame_control = IEEE80211_FC(WLAN_FC_TYPE_MGMT,
    615 					  WLAN_FC_STYPE_ACTION);
    616 	if (rx_action->category == WLAN_ACTION_SA_QUERY) {
    617 		/*
    618 		 * Assume frame was protected; it would have been dropped if
    619 		 * not.
    620 		 */
    621 		hdr->frame_control |= host_to_le16(WLAN_FC_ISWEP);
    622 	}
    623 	os_memcpy(hdr->addr1, rx_action->da, ETH_ALEN);
    624 	os_memcpy(hdr->addr2, rx_action->sa, ETH_ALEN);
    625 	os_memcpy(hdr->addr3, rx_action->bssid, ETH_ALEN);
    626 	buf[24] = rx_action->category;
    627 	os_memcpy(buf + 24 + 1, rx_action->data, rx_action->len);
    628 	os_memset(&rx_mgmt, 0, sizeof(rx_mgmt));
    629 	rx_mgmt.frame = buf;
    630 	rx_mgmt.frame_len = 24 + 1 + rx_action->len;
    631 	hostapd_mgmt_rx(hapd, &rx_mgmt);
    632 	os_free(buf);
    633 }
    634 
    635 
    636 static void hostapd_mgmt_tx_cb(struct hostapd_data *hapd, const u8 *buf,
    637 			       size_t len, u16 stype, int ok)
    638 {
    639 	struct ieee80211_hdr *hdr;
    640 	hdr = (struct ieee80211_hdr *) buf;
    641 	hapd = get_hapd_bssid(hapd->iface, get_hdr_bssid(hdr, len));
    642 	if (hapd == NULL || hapd == HAPD_BROADCAST)
    643 		return;
    644 	ieee802_11_mgmt_cb(hapd, buf, len, stype, ok);
    645 }
    646 
    647 #endif /* NEED_AP_MLME */
    648 
    649 
    650 static int hostapd_event_new_sta(struct hostapd_data *hapd, const u8 *addr)
    651 {
    652 	struct sta_info *sta = ap_get_sta(hapd, addr);
    653 	if (sta)
    654 		return 0;
    655 
    656 	wpa_printf(MSG_DEBUG, "Data frame from unknown STA " MACSTR
    657 		   " - adding a new STA", MAC2STR(addr));
    658 	sta = ap_sta_add(hapd, addr);
    659 	if (sta) {
    660 		hostapd_new_assoc_sta(hapd, sta, 0);
    661 	} else {
    662 		wpa_printf(MSG_DEBUG, "Failed to add STA entry for " MACSTR,
    663 			   MAC2STR(addr));
    664 		return -1;
    665 	}
    666 
    667 	return 0;
    668 }
    669 
    670 
    671 static void hostapd_event_eapol_rx(struct hostapd_data *hapd, const u8 *src,
    672 				   const u8 *data, size_t data_len)
    673 {
    674 	struct hostapd_iface *iface = hapd->iface;
    675 	size_t j;
    676 
    677 	for (j = 0; j < iface->num_bss; j++) {
    678 		if (ap_get_sta(iface->bss[j], src)) {
    679 			hapd = iface->bss[j];
    680 			break;
    681 		}
    682 	}
    683 
    684 	ieee802_1x_receive(hapd, src, data, data_len);
    685 }
    686 
    687 
    688 void wpa_supplicant_event(void *ctx, enum wpa_event_type event,
    689 			  union wpa_event_data *data)
    690 {
    691 	struct hostapd_data *hapd = ctx;
    692 #ifndef CONFIG_NO_STDOUT_DEBUG
    693 	int level = MSG_DEBUG;
    694 
    695 	if (event == EVENT_RX_MGMT && data->rx_mgmt.frame &&
    696 	    data->rx_mgmt.frame_len >= 24) {
    697 		const struct ieee80211_hdr *hdr;
    698 		u16 fc;
    699 		hdr = (const struct ieee80211_hdr *) data->rx_mgmt.frame;
    700 		fc = le_to_host16(hdr->frame_control);
    701 		if (WLAN_FC_GET_TYPE(fc) == WLAN_FC_TYPE_MGMT &&
    702 		    WLAN_FC_GET_STYPE(fc) == WLAN_FC_STYPE_BEACON)
    703 			level = MSG_EXCESSIVE;
    704 	}
    705 
    706 	wpa_dbg(hapd->msg_ctx, level, "Event %s (%d) received",
    707 		event_to_string(event), event);
    708 #endif /* CONFIG_NO_STDOUT_DEBUG */
    709 
    710 	switch (event) {
    711 	case EVENT_MICHAEL_MIC_FAILURE:
    712 		michael_mic_failure(hapd, data->michael_mic_failure.src, 1);
    713 		break;
    714 	case EVENT_SCAN_RESULTS:
    715 		if (hapd->iface->scan_cb)
    716 			hapd->iface->scan_cb(hapd->iface);
    717 		break;
    718 #ifdef CONFIG_IEEE80211R
    719 	case EVENT_FT_RRB_RX:
    720 		wpa_ft_rrb_rx(hapd->wpa_auth, data->ft_rrb_rx.src,
    721 			      data->ft_rrb_rx.data, data->ft_rrb_rx.data_len);
    722 		break;
    723 #endif /* CONFIG_IEEE80211R */
    724 	case EVENT_WPS_BUTTON_PUSHED:
    725 		hostapd_wps_button_pushed(hapd, NULL);
    726 		break;
    727 #ifdef NEED_AP_MLME
    728 	case EVENT_TX_STATUS:
    729 		switch (data->tx_status.type) {
    730 		case WLAN_FC_TYPE_MGMT:
    731 			hostapd_mgmt_tx_cb(hapd, data->tx_status.data,
    732 					   data->tx_status.data_len,
    733 					   data->tx_status.stype,
    734 					   data->tx_status.ack);
    735 			break;
    736 		case WLAN_FC_TYPE_DATA:
    737 			hostapd_tx_status(hapd, data->tx_status.dst,
    738 					  data->tx_status.data,
    739 					  data->tx_status.data_len,
    740 					  data->tx_status.ack);
    741 			break;
    742 		}
    743 		break;
    744 	case EVENT_EAPOL_TX_STATUS:
    745 		hostapd_eapol_tx_status(hapd, data->eapol_tx_status.dst,
    746 					data->eapol_tx_status.data,
    747 					data->eapol_tx_status.data_len,
    748 					data->eapol_tx_status.ack);
    749 		break;
    750 	case EVENT_DRIVER_CLIENT_POLL_OK:
    751 		hostapd_client_poll_ok(hapd, data->client_poll.addr);
    752 		break;
    753 	case EVENT_RX_FROM_UNKNOWN:
    754 		hostapd_rx_from_unknown_sta(hapd, data->rx_from_unknown.bssid,
    755 					    data->rx_from_unknown.addr,
    756 					    data->rx_from_unknown.wds);
    757 		break;
    758 	case EVENT_RX_MGMT:
    759 		hostapd_mgmt_rx(hapd, &data->rx_mgmt);
    760 		break;
    761 #endif /* NEED_AP_MLME */
    762 	case EVENT_RX_PROBE_REQ:
    763 		if (data->rx_probe_req.sa == NULL ||
    764 		    data->rx_probe_req.ie == NULL)
    765 			break;
    766 		hostapd_probe_req_rx(hapd, data->rx_probe_req.sa,
    767 				     data->rx_probe_req.da,
    768 				     data->rx_probe_req.bssid,
    769 				     data->rx_probe_req.ie,
    770 				     data->rx_probe_req.ie_len,
    771 				     data->rx_probe_req.ssi_signal);
    772 		break;
    773 	case EVENT_NEW_STA:
    774 		hostapd_event_new_sta(hapd, data->new_sta.addr);
    775 		break;
    776 	case EVENT_EAPOL_RX:
    777 		hostapd_event_eapol_rx(hapd, data->eapol_rx.src,
    778 				       data->eapol_rx.data,
    779 				       data->eapol_rx.data_len);
    780 		break;
    781 	case EVENT_ASSOC:
    782 		hostapd_notif_assoc(hapd, data->assoc_info.addr,
    783 				    data->assoc_info.req_ies,
    784 				    data->assoc_info.req_ies_len,
    785 				    data->assoc_info.reassoc);
    786 		break;
    787 	case EVENT_DISASSOC:
    788 		if (data)
    789 			hostapd_notif_disassoc(hapd, data->disassoc_info.addr);
    790 		break;
    791 	case EVENT_DEAUTH:
    792 		if (data)
    793 			hostapd_notif_disassoc(hapd, data->deauth_info.addr);
    794 		break;
    795 	case EVENT_STATION_LOW_ACK:
    796 		if (!data)
    797 			break;
    798 		hostapd_event_sta_low_ack(hapd, data->low_ack.addr);
    799 		break;
    800 	case EVENT_RX_ACTION:
    801 		if (data->rx_action.da == NULL || data->rx_action.sa == NULL ||
    802 		    data->rx_action.bssid == NULL)
    803 			break;
    804 #ifdef NEED_AP_MLME
    805 		hostapd_rx_action(hapd, &data->rx_action);
    806 #endif /* NEED_AP_MLME */
    807 		hostapd_action_rx(hapd, &data->rx_action);
    808 		break;
    809 	case EVENT_AUTH:
    810 		hostapd_notif_auth(hapd, &data->auth);
    811 		break;
    812 	case EVENT_CH_SWITCH:
    813 		if (!data)
    814 			break;
    815 		hostapd_event_ch_switch(hapd, data->ch_switch.freq,
    816 					data->ch_switch.ht_enabled,
    817 					data->ch_switch.ch_offset);
    818 		break;
    819 	default:
    820 		wpa_printf(MSG_DEBUG, "Unknown event %d", event);
    821 		break;
    822 	}
    823 }
    824 
    825 #endif /* HOSTAPD */
    826