static void wpa_driver_hostap_poll_client(void *priv, const u8 *own_addr, const u8 *addr, int qos) { struct ieee80211_hdr hdr; os_memset(&hdr, 0, sizeof(hdr)); /* * WLAN_FC_STYPE_NULLFUNC would be more appropriate, * but it is apparently not retried so TX Exc events * are not received for it. * This is the reason the driver overrides the default * handling. */ hdr.frame_control = IEEE80211_FC(WLAN_FC_TYPE_DATA, WLAN_FC_STYPE_DATA); hdr.frame_control |= host_to_le16(WLAN_FC_FROMDS); os_memcpy(hdr.IEEE80211_DA_FROMDS, addr, ETH_ALEN); os_memcpy(hdr.IEEE80211_BSSID_FROMDS, own_addr, ETH_ALEN); os_memcpy(hdr.IEEE80211_SA_FROMDS, own_addr, ETH_ALEN); hostap_send_mlme(priv, (u8 *)&hdr, sizeof(hdr), 0, 0, NULL, 0); }
int wnm_send_bss_transition_mgmt_query(struct wpa_supplicant *wpa_s, u8 query_reason) { u8 buf[1000], *pos; struct ieee80211_mgmt *mgmt; size_t len; int ret; wpa_printf(MSG_DEBUG, "WNM: Send BSS Transition Management Query to " MACSTR " query_reason=%u", MAC2STR(wpa_s->bssid), query_reason); mgmt = (struct ieee80211_mgmt *) buf; os_memset(&buf, 0, sizeof(buf)); os_memcpy(mgmt->da, wpa_s->bssid, ETH_ALEN); os_memcpy(mgmt->sa, wpa_s->own_addr, ETH_ALEN); os_memcpy(mgmt->bssid, wpa_s->bssid, ETH_ALEN); mgmt->frame_control = IEEE80211_FC(WLAN_FC_TYPE_MGMT, WLAN_FC_STYPE_ACTION); mgmt->u.action.category = WLAN_ACTION_WNM; mgmt->u.action.u.bss_tm_query.action = WNM_BSS_TRANS_MGMT_QUERY; mgmt->u.action.u.bss_tm_query.dialog_token = 1; mgmt->u.action.u.bss_tm_query.query_reason = query_reason; pos = mgmt->u.action.u.bss_tm_query.variable; len = pos - (u8 *) &mgmt->u.action.category; ret = wpa_drv_send_action(wpa_s, wpa_s->assoc_freq, 0, wpa_s->bssid, wpa_s->own_addr, wpa_s->bssid, &mgmt->u.action.category, len, 0); return ret; }
static int hostapd_wpa_auth_send_ft_action(void *ctx, const u8 *dst, const u8 *data, size_t data_len) { struct hostapd_data *hapd = ctx; int res; struct ieee80211_mgmt *m; size_t mlen; struct sta_info *sta; sta = ap_get_sta(hapd, dst); if (sta == NULL || sta->wpa_sm == NULL) return -1; m = os_zalloc(sizeof(*m) + data_len); if (m == NULL) return -1; mlen = ((u8 *) &m->u - (u8 *) m) + data_len; m->frame_control = IEEE80211_FC(WLAN_FC_TYPE_MGMT, WLAN_FC_STYPE_ACTION); os_memcpy(m->da, dst, ETH_ALEN); os_memcpy(m->sa, hapd->own_addr, ETH_ALEN); os_memcpy(m->bssid, hapd->own_addr, ETH_ALEN); os_memcpy(&m->u, data, data_len); res = hostapd_drv_send_mlme(hapd, (u8 *) m, mlen); os_free(m); return res; }
static int ibss_rsn_send_auth(struct ibss_rsn *ibss_rsn, const u8 *da, int seq) { struct ieee80211_mgmt auth; const size_t auth_length = IEEE80211_HDRLEN + sizeof(auth.u.auth); struct wpa_supplicant *wpa_s = ibss_rsn->wpa_s; if (wpa_s->driver->send_frame == NULL) return -1; os_memset(&auth, 0, sizeof(auth)); auth.frame_control = IEEE80211_FC(WLAN_FC_TYPE_MGMT, WLAN_FC_STYPE_AUTH); os_memcpy(auth.da, da, ETH_ALEN); os_memcpy(auth.sa, wpa_s->own_addr, ETH_ALEN); os_memcpy(auth.bssid, wpa_s->bssid, ETH_ALEN); auth.u.auth.auth_alg = host_to_le16(WLAN_AUTH_OPEN); auth.u.auth.auth_transaction = host_to_le16(seq); auth.u.auth.status_code = host_to_le16(WLAN_STATUS_SUCCESS); wpa_printf(MSG_DEBUG, "RSN: IBSS TX Auth frame (SEQ %d) to " MACSTR, seq, MAC2STR(da)); return wpa_s->driver->send_frame(wpa_s->drv_priv, (u8 *) &auth, auth_length, 0); }
static int hostapd_header_beacon(packet_element_t* p, u8* macaddr, u16 beacon_period) { struct ieee80211_mgmt* head=NULL; p->len = (u8)(int)&(head->u.beacon.variable[0]); head = (struct ieee80211_mgmt*)malloc(p->len); // FRAME CONTROL (2) : PROTOCOL=0 + TYPE=MNGT + SUBTYPE=BEACON, FROMDS, TODS.... head->frame_control = IEEE80211_FC(WLAN_FC_TYPE_MGMT, WLAN_FC_STYPE_BEACON); // FRAME DURATION (2) : 0 (typic for broadcast/multicast) head->duration = host_to_le16(0); // ADDR1 (6) = DA ( destination = broadcast) memcpy(head->da, broadcast_ether_addr, ETH_ALEN); // ADDR2 (6) = SA ( source = me) memcpy(head->sa, macaddr, ETH_ALEN); // ADDR3 (6) = BSSID ( me) memcpy(head->bssid, macaddr, ETH_ALEN); // SEQUENCE-CTRL (2) head->seq_ctrl = host_to_le16(0); // FRAME BODY FIXED ELEMENTS FOR BEACON // BEACON TIMESTAMP (8) memset(head->u.beacon.timestamp, 0, sizeof(head->u.beacon.timestamp)); //set by PHY ? // BEACON INTERVAL (2) head->u.beacon.beacon_int = host_to_le16(beacon_period); // BEACON CAPA (2) head->u.beacon.capab_info = host_to_le16(0x401); // TODO: check capabilities p->d = (u8*)head; return p->len; }
static int hostap_sta_deauth(void *priv, const u8 *own_addr, const u8 *addr, int reason) { struct hostap_driver_data *drv = priv; struct ieee80211_mgmt mgmt; if (is_broadcast_ether_addr(addr)) { /* * New Prism2.5/3 STA firmware versions seem to have issues * with this broadcast deauth frame. This gets the firmware in * odd state where nothing works correctly, so let's skip * sending this for the hostap driver. */ return 0; } memset(&mgmt, 0, sizeof(mgmt)); mgmt.frame_control = IEEE80211_FC(WLAN_FC_TYPE_MGMT, WLAN_FC_STYPE_DEAUTH); memcpy(mgmt.da, addr, ETH_ALEN); memcpy(mgmt.sa, own_addr, ETH_ALEN); memcpy(mgmt.bssid, own_addr, ETH_ALEN); mgmt.u.deauth.reason_code = host_to_le16(reason); return hostap_send_mlme(drv, (u8 *) &mgmt, IEEE80211_HDRLEN + sizeof(mgmt.u.deauth), 0, 0, NULL, 0); }
static void ieee802_11_sta_authenticate(void *eloop_ctx, void *timeout_ctx) { hostapd *hapd = eloop_ctx; struct ieee80211_mgmt mgmt; if (hapd->assoc_ap_state == WAIT_BEACON) hapd->assoc_ap_state = AUTHENTICATE; if (hapd->assoc_ap_state != AUTHENTICATE) return; printf("Authenticate with AP " MACSTR " SSID=", MAC2STR(hapd->conf->assoc_ap_addr)); ieee802_11_print_ssid((u8 *) hapd->assoc_ap_ssid, hapd->assoc_ap_ssid_len); printf(" (as station)\n"); memset(&mgmt, 0, sizeof(mgmt)); mgmt.frame_control = IEEE80211_FC(WLAN_FC_TYPE_MGMT, WLAN_FC_STYPE_AUTH); /* Request TX callback */ mgmt.frame_control |= host_to_le16(BIT(1)); memcpy(mgmt.da, hapd->conf->assoc_ap_addr, ETH_ALEN); memcpy(mgmt.sa, hapd->own_addr, ETH_ALEN); memcpy(mgmt.bssid, hapd->conf->assoc_ap_addr, ETH_ALEN); mgmt.u.auth.auth_alg = host_to_le16(WLAN_AUTH_OPEN); mgmt.u.auth.auth_transaction = host_to_le16(1); mgmt.u.auth.status_code = host_to_le16(0); if (hostapd_send_mgmt_frame(hapd, &mgmt, IEEE80211_HDRLEN + sizeof(mgmt.u.auth), 0) < 0) perror("ieee802_11_sta_authenticate: send"); /* Try to authenticate again, if this attempt fails or times out. */ eloop_register_timeout(5, 0, ieee802_11_sta_authenticate, hapd, NULL); }
int wnm_send_disassoc_imminent(struct hostapd_data *hapd, struct sta_info *sta, int disassoc_timer) { u8 buf[1000], *pos; struct ieee80211_mgmt *mgmt; os_memset(buf, 0, sizeof(buf)); mgmt = (struct ieee80211_mgmt *) buf; mgmt->frame_control = IEEE80211_FC(WLAN_FC_TYPE_MGMT, WLAN_FC_STYPE_ACTION); os_memcpy(mgmt->da, sta->addr, ETH_ALEN); os_memcpy(mgmt->sa, hapd->own_addr, ETH_ALEN); os_memcpy(mgmt->bssid, hapd->own_addr, ETH_ALEN); mgmt->u.action.category = WLAN_ACTION_WNM; mgmt->u.action.u.bss_tm_req.action = WNM_BSS_TRANS_MGMT_REQ; mgmt->u.action.u.bss_tm_req.dialog_token = 1; mgmt->u.action.u.bss_tm_req.req_mode = WNM_BSS_TM_REQ_DISASSOC_IMMINENT; mgmt->u.action.u.bss_tm_req.disassoc_timer = host_to_le16(disassoc_timer); mgmt->u.action.u.bss_tm_req.validity_interval = 0; pos = mgmt->u.action.u.bss_tm_req.variable; wpa_printf(MSG_DEBUG, "WNM: Send BSS Transition Management Request frame to indicate imminent disassociation (disassoc_timer=%d) to " MACSTR, disassoc_timer, MAC2STR(sta->addr)); if (hostapd_drv_send_mlme(hapd, buf, pos - buf, 0, NULL, 0) < 0) { wpa_printf(MSG_DEBUG, "Failed to send BSS Transition " "Management Request frame"); return -1; } return 0; }
/* MLME-SAQuery.request */ void ieee802_11_send_sa_query_req(struct hostapd_data *hapd, const u8 *addr, const u8 *trans_id) { struct ieee80211_mgmt mgmt; u8 *end; wpa_printf(MSG_DEBUG, "IEEE 802.11: Sending SA Query Request to " MACSTR, MAC2STR(addr)); wpa_hexdump(MSG_DEBUG, "IEEE 802.11: SA Query Transaction ID", trans_id, WLAN_SA_QUERY_TR_ID_LEN); os_memset(&mgmt, 0, sizeof(mgmt)); mgmt.frame_control = IEEE80211_FC(WLAN_FC_TYPE_MGMT, WLAN_FC_STYPE_ACTION); os_memcpy(mgmt.da, addr, ETH_ALEN); os_memcpy(mgmt.sa, hapd->own_addr, ETH_ALEN); os_memcpy(mgmt.bssid, hapd->own_addr, ETH_ALEN); mgmt.u.action.category = WLAN_ACTION_SA_QUERY; mgmt.u.action.u.sa_query_req.action = WLAN_SA_QUERY_REQUEST; os_memcpy(mgmt.u.action.u.sa_query_req.trans_id, trans_id, WLAN_SA_QUERY_TR_ID_LEN); end = mgmt.u.action.u.sa_query_req.trans_id + WLAN_SA_QUERY_TR_ID_LEN; if (hostapd_drv_send_mlme(hapd, &mgmt, end - (u8 *) &mgmt, 0) < 0) wpa_printf(MSG_INFO, "ieee802_11_send_sa_query_req: send failed"); }
int hostapd_ctrl_iface_disassociate(struct hostapd_data *hapd, const char *txtaddr) { u8 addr[ETH_ALEN]; struct sta_info *sta; const char *pos; u16 reason = WLAN_REASON_PREV_AUTH_NOT_VALID; wpa_dbg(hapd->msg_ctx, MSG_DEBUG, "CTRL_IFACE DISASSOCIATE %s", txtaddr); if (hwaddr_aton(txtaddr, addr)) return -1; pos = os_strstr(txtaddr, " test="); if (pos) { struct ieee80211_mgmt mgmt; int encrypt; if (hapd->driver->send_frame == NULL) return -1; pos += 6; encrypt = atoi(pos); os_memset(&mgmt, 0, sizeof(mgmt)); mgmt.frame_control = IEEE80211_FC(WLAN_FC_TYPE_MGMT, WLAN_FC_STYPE_DISASSOC); os_memcpy(mgmt.da, addr, ETH_ALEN); os_memcpy(mgmt.sa, hapd->own_addr, ETH_ALEN); os_memcpy(mgmt.bssid, hapd->own_addr, ETH_ALEN); mgmt.u.disassoc.reason_code = host_to_le16(WLAN_REASON_PREV_AUTH_NOT_VALID); if (hapd->driver->send_frame(hapd->drv_priv, (u8 *) &mgmt, IEEE80211_HDRLEN + sizeof(mgmt.u.deauth), encrypt) < 0) return -1; return 0; } #ifdef CONFIG_P2P_MANAGER pos = os_strstr(txtaddr, " p2p="); if (pos) { return p2p_manager_disconnect(hapd, WLAN_FC_STYPE_DISASSOC, atoi(pos + 5), addr); } #endif /* CONFIG_P2P_MANAGER */ pos = os_strstr(txtaddr, " reason="); if (pos) reason = atoi(pos + 8); hostapd_drv_sta_disassoc(hapd, addr, reason); sta = ap_get_sta(hapd, addr); if (sta) ap_sta_disassociate(hapd, sta, reason); else if (addr[0] == 0xff) hostapd_free_stas(hapd); return 0; }
/* FIXED LEN IE */ CWBool CW80211AssembleIEFrameControl(char * frame, int * offset, int frameType, int frameSubtype) { short int val = IEEE80211_FC(frameType, frameSubtype); CW_COPY_MEMORY(frame, &(val), LEN_IE_FRAME_CONTROL); (*offset) += LEN_IE_FRAME_CONTROL; return CW_TRUE; }
static void wnm_send_bss_transition_mgmt_resp( struct wpa_supplicant *wpa_s, u8 dialog_token, enum bss_trans_mgmt_status_code status, u8 delay, const u8 *target_bssid) { u8 buf[1000], *pos; struct ieee80211_mgmt *mgmt; size_t len; int res; wpa_printf(MSG_DEBUG, "WNM: Send BSS Transition Management Response " "to " MACSTR " dialog_token=%u status=%u delay=%d", MAC2STR(wpa_s->bssid), dialog_token, status, delay); if (!wpa_s->current_bss) { wpa_printf(MSG_DEBUG, "WNM: Current BSS not known - drop response"); return; } mgmt = (struct ieee80211_mgmt *) buf; os_memset(&buf, 0, sizeof(buf)); os_memcpy(mgmt->da, wpa_s->bssid, ETH_ALEN); os_memcpy(mgmt->sa, wpa_s->own_addr, ETH_ALEN); os_memcpy(mgmt->bssid, wpa_s->bssid, ETH_ALEN); mgmt->frame_control = IEEE80211_FC(WLAN_FC_TYPE_MGMT, WLAN_FC_STYPE_ACTION); mgmt->u.action.category = WLAN_ACTION_WNM; mgmt->u.action.u.bss_tm_resp.action = WNM_BSS_TRANS_MGMT_RESP; mgmt->u.action.u.bss_tm_resp.dialog_token = dialog_token; mgmt->u.action.u.bss_tm_resp.status_code = status; mgmt->u.action.u.bss_tm_resp.bss_termination_delay = delay; pos = mgmt->u.action.u.bss_tm_resp.variable; if (target_bssid) { os_memcpy(pos, target_bssid, ETH_ALEN); pos += ETH_ALEN; } else if (status == WNM_BSS_TM_ACCEPT) { /* * P802.11-REVmc clarifies that the Target BSSID field is always * present when status code is zero, so use a fake value here if * no BSSID is yet known. */ os_memset(pos, 0, ETH_ALEN); pos += ETH_ALEN; } len = pos - (u8 *) &mgmt->u.action.category; res = wpa_drv_send_action(wpa_s, wpa_s->assoc_freq, 0, wpa_s->bssid, wpa_s->own_addr, wpa_s->bssid, &mgmt->u.action.category, len, 0); if (res < 0) { wpa_printf(MSG_DEBUG, "WNM: Failed to send BSS Transition Management Response"); } }
static int ieee802_11_send_bss_trans_mgmt_request(struct hostapd_data *hapd, const u8 *addr, u8 dialog_token, const char *url) { struct ieee80211_mgmt *mgmt; size_t url_len, len; u8 *pos; int res; if (url) url_len = os_strlen(url); else url_len = 0; mgmt = os_zalloc(sizeof(*mgmt) + (url_len ? 1 + url_len : 0)); if (mgmt == NULL) return -1; os_memcpy(mgmt->da, addr, ETH_ALEN); os_memcpy(mgmt->sa, hapd->own_addr, ETH_ALEN); os_memcpy(mgmt->bssid, hapd->own_addr, ETH_ALEN); mgmt->frame_control = IEEE80211_FC(WLAN_FC_TYPE_MGMT, WLAN_FC_STYPE_ACTION); mgmt->u.action.category = WLAN_ACTION_WNM; mgmt->u.action.u.bss_tm_req.action = WNM_BSS_TRANS_MGMT_REQ; mgmt->u.action.u.bss_tm_req.dialog_token = dialog_token; mgmt->u.action.u.bss_tm_req.req_mode = 0; mgmt->u.action.u.bss_tm_req.disassoc_timer = host_to_le16(0); mgmt->u.action.u.bss_tm_req.validity_interval = 1; pos = mgmt->u.action.u.bss_tm_req.variable; if (url) { *pos++ += url_len; os_memcpy(pos, url, url_len); pos += url_len; } wpa_printf(MSG_DEBUG, "WNM: Send BSS Transition Management Request to " MACSTR " dialog_token=%u req_mode=0x%x disassoc_timer=%u " "validity_interval=%u", MAC2STR(addr), dialog_token, mgmt->u.action.u.bss_tm_req.req_mode, le_to_host16(mgmt->u.action.u.bss_tm_req.disassoc_timer), mgmt->u.action.u.bss_tm_req.validity_interval); len = pos - &mgmt->u.action.category; res = hostapd_drv_send_action(hapd, hapd->iface->freq, 0, mgmt->da, &mgmt->u.action.category, len); os_free(mgmt); return res; }
static int p2p_manager_disconnect(struct hostapd_data *hapd, u16 stype, u8 minor_reason_code, const u8 *addr) { struct ieee80211_mgmt *mgmt; int ret; u8 *pos; if (hapd->driver->send_frame == NULL) return -1; mgmt = os_zalloc(sizeof(*mgmt) + 100); if (mgmt == NULL) return -1; mgmt->frame_control = IEEE80211_FC(WLAN_FC_TYPE_MGMT, stype); wpa_dbg(hapd->msg_ctx, MSG_DEBUG, "P2P: Disconnect STA " MACSTR " with minor reason code %u (stype=%u (%s))", MAC2STR(addr), minor_reason_code, stype, fc2str(mgmt->frame_control)); os_memcpy(mgmt->da, addr, ETH_ALEN); os_memcpy(mgmt->sa, hapd->own_addr, ETH_ALEN); os_memcpy(mgmt->bssid, hapd->own_addr, ETH_ALEN); if (stype == WLAN_FC_STYPE_DEAUTH) { mgmt->u.deauth.reason_code = host_to_le16(WLAN_REASON_PREV_AUTH_NOT_VALID); pos = (u8 *) (&mgmt->u.deauth.reason_code + 1); } else { mgmt->u.disassoc.reason_code = host_to_le16(WLAN_REASON_PREV_AUTH_NOT_VALID); pos = (u8 *) (&mgmt->u.disassoc.reason_code + 1); } *pos++ = WLAN_EID_VENDOR_SPECIFIC; *pos++ = 4 + 3 + 1; WPA_PUT_BE32(pos, P2P_IE_VENDOR_TYPE); pos += 4; *pos++ = P2P_ATTR_MINOR_REASON_CODE; WPA_PUT_LE16(pos, 1); pos += 2; *pos++ = minor_reason_code; ret = hapd->driver->send_frame(hapd->drv_priv, (u8 *) mgmt, pos - (u8 *) mgmt, 1); os_free(mgmt); return ret < 0 ? -1 : 0; }
void ieee802_11_send_disassoc(hostapd *hapd, u8 *addr, u8 reason) { struct ieee80211_mgmt mgmt; memset(&mgmt, 0, sizeof(mgmt)); mgmt.frame_control = IEEE80211_FC(WLAN_FC_TYPE_MGMT, WLAN_FC_STYPE_DISASSOC); memcpy(mgmt.da, addr, ETH_ALEN); memcpy(mgmt.sa, hapd->own_addr, ETH_ALEN); memcpy(mgmt.bssid, hapd->own_addr, ETH_ALEN); mgmt.u.disassoc.reason_code = host_to_le16(reason); if (send(hapd->sock, &mgmt, IEEE80211_HDRLEN + sizeof(mgmt.u.disassoc), 0) < 0) perror("ieee802_11_send_disassoc: send"); }
static int hostap_sta_disassoc(void *priv, const u8 *addr, int reason) { struct hostap_driver_data *drv = priv; struct ieee80211_mgmt mgmt; memset(&mgmt, 0, sizeof(mgmt)); mgmt.frame_control = IEEE80211_FC(WLAN_FC_TYPE_MGMT, WLAN_FC_STYPE_DISASSOC); memcpy(mgmt.da, addr, ETH_ALEN); memcpy(mgmt.sa, drv->hapd->own_addr, ETH_ALEN); memcpy(mgmt.bssid, drv->hapd->own_addr, ETH_ALEN); mgmt.u.disassoc.reason_code = host_to_le16(reason); return hostap_send_mgmt_frame(drv, &mgmt, IEEE80211_HDRLEN + sizeof(mgmt.u.disassoc), 0); }
int wnm_send_ess_disassoc_imminent(struct hostapd_data *hapd, struct sta_info *sta, const char *url, int disassoc_timer) { u8 buf[1000], *pos; struct ieee80211_mgmt *mgmt; size_t url_len; os_memset(buf, 0, sizeof(buf)); mgmt = (struct ieee80211_mgmt *) buf; mgmt->frame_control = IEEE80211_FC(WLAN_FC_TYPE_MGMT, WLAN_FC_STYPE_ACTION); os_memcpy(mgmt->da, sta->addr, ETH_ALEN); os_memcpy(mgmt->sa, hapd->own_addr, ETH_ALEN); os_memcpy(mgmt->bssid, hapd->own_addr, ETH_ALEN); mgmt->u.action.category = WLAN_ACTION_WNM; mgmt->u.action.u.bss_tm_req.action = WNM_BSS_TRANS_MGMT_REQ; mgmt->u.action.u.bss_tm_req.dialog_token = 1; mgmt->u.action.u.bss_tm_req.req_mode = WNM_BSS_TM_REQ_DISASSOC_IMMINENT | WNM_BSS_TM_REQ_ESS_DISASSOC_IMMINENT; mgmt->u.action.u.bss_tm_req.disassoc_timer = host_to_le16(disassoc_timer); mgmt->u.action.u.bss_tm_req.validity_interval = 0x01; pos = mgmt->u.action.u.bss_tm_req.variable; /* Session Information URL */ url_len = os_strlen(url); if (url_len > 255) return -1; *pos++ = url_len; os_memcpy(pos, url, url_len); pos += url_len; if (hostapd_drv_send_mlme(hapd, buf, pos - buf, 0, NULL, 0) < 0) { wpa_printf(MSG_DEBUG, "Failed to send BSS Transition " "Management Request frame"); return -1; } if (disassoc_timer) { /* send disassociation frame after time-out */ set_disassoc_timer(hapd, sta, disassoc_timer); } return 0; }
static int hostap_sta_deauth(void *priv, const u8 *own_addr, const u8 *addr, int reason) { struct hostap_driver_data *drv = priv; struct ieee80211_mgmt mgmt; memset(&mgmt, 0, sizeof(mgmt)); mgmt.frame_control = IEEE80211_FC(WLAN_FC_TYPE_MGMT, WLAN_FC_STYPE_DEAUTH); memcpy(mgmt.da, addr, ETH_ALEN); memcpy(mgmt.sa, own_addr, ETH_ALEN); memcpy(mgmt.bssid, own_addr, ETH_ALEN); mgmt.u.deauth.reason_code = host_to_le16(reason); return hostap_send_mlme(drv, (u8 *) &mgmt, IEEE80211_HDRLEN + sizeof(mgmt.u.deauth)); }
static int hostap_send_eapol(void *priv, const u8 *addr, const u8 *data, size_t data_len, int encrypt, const u8 *own_addr) { struct hostap_driver_data *drv = priv; struct ieee80211_hdr *hdr; size_t len; u8 *pos; int res; len = sizeof(*hdr) + sizeof(rfc1042_header) + 2 + data_len; hdr = os_zalloc(len); if (hdr == NULL) { printf("malloc() failed for hostapd_send_data(len=%lu)\n", (unsigned long) len); return -1; } hdr->frame_control = IEEE80211_FC(WLAN_FC_TYPE_DATA, WLAN_FC_STYPE_DATA); hdr->frame_control |= host_to_le16(WLAN_FC_FROMDS); /* Request TX callback */ hdr->frame_control |= host_to_le16(BIT(1)); if (encrypt) hdr->frame_control |= host_to_le16(WLAN_FC_ISWEP); memcpy(hdr->IEEE80211_DA_FROMDS, addr, ETH_ALEN); memcpy(hdr->IEEE80211_BSSID_FROMDS, own_addr, ETH_ALEN); memcpy(hdr->IEEE80211_SA_FROMDS, own_addr, ETH_ALEN); pos = (u8 *) (hdr + 1); memcpy(pos, rfc1042_header, sizeof(rfc1042_header)); pos += sizeof(rfc1042_header); *((u16 *) pos) = htons(ETH_P_PAE); pos += 2; memcpy(pos, data, data_len); res = hostap_send_mgmt_frame(drv, (u8 *) hdr, len, 0); free(hdr); if (res < 0) { perror("hostapd_send_eapol: send"); printf("hostapd_send_eapol - packet len: %lu - failed\n", (unsigned long) len); } return res; }
void ieee802_11_send_deauth(hostapd *hapd, u8 *addr, u8 reason) { struct ieee80211_mgmt mgmt; memset(&mgmt, 0, sizeof(mgmt)); mgmt.frame_control = IEEE80211_FC(WLAN_FC_TYPE_MGMT, WLAN_FC_STYPE_DEAUTH); memcpy(mgmt.da, addr, ETH_ALEN); memcpy(mgmt.sa, hapd->own_addr, ETH_ALEN); memcpy(mgmt.bssid, hapd->own_addr, ETH_ALEN); mgmt.u.deauth.reason_code = host_to_le16(reason); if (hapd->driver.send_mgmt_frame && hapd->driver.send_mgmt_frame(hapd->driver.data, &mgmt, IEEE80211_HDRLEN + sizeof(mgmt.u.deauth), 0) < 0) perror("ieee802_11_send_deauth: send"); }
CWBool CW80211AssembleIEFrameControlData(char * frame, int * offset, int frameType, int frameSubtype, int toDS, int fromDS) { short int val = IEEE80211_FC(frameType, frameSubtype); if(toDS == 1) SETBIT(val,8); else CLEARBIT(val,8); if(fromDS == 1) SETBIT(val,9); else CLEARBIT(val,9); CW_COPY_MEMORY(frame, &(val), LEN_IE_FRAME_CONTROL); (*offset) += LEN_IE_FRAME_CONTROL; return CW_TRUE; }
static void build_mgmt_hdr(struct ieee80211_mgmt *mgmt, struct wlantest_bss *bss, struct wlantest_sta *sta, int sender_ap, int stype) { os_memset(mgmt, 0, 24); mgmt->frame_control = IEEE80211_FC(WLAN_FC_TYPE_MGMT, stype); if (sender_ap) { if (sta) os_memcpy(mgmt->da, sta->addr, ETH_ALEN); else os_memset(mgmt->da, 0xff, ETH_ALEN); os_memcpy(mgmt->sa, bss->bssid, ETH_ALEN); } else { os_memcpy(mgmt->da, bss->bssid, ETH_ALEN); os_memcpy(mgmt->sa, sta->addr, ETH_ALEN); } os_memcpy(mgmt->bssid, bss->bssid, ETH_ALEN); }
static void ieee802_11_sta_associate(void *eloop_ctx, void *timeout_ctx) { hostapd *hapd = eloop_ctx; u8 buf[256]; struct ieee80211_mgmt *mgmt = (struct ieee80211_mgmt *) buf; u8 *p; if (hapd->assoc_ap_state == AUTHENTICATE) hapd->assoc_ap_state = ASSOCIATE; if (hapd->assoc_ap_state != ASSOCIATE) return; printf("Associate with AP " MACSTR " SSID=", MAC2STR(hapd->conf->assoc_ap_addr)); ieee802_11_print_ssid(hapd->assoc_ap_ssid, hapd->assoc_ap_ssid_len); printf(" (as station)\n"); memset(mgmt, 0, sizeof(*mgmt)); mgmt->frame_control = IEEE80211_FC(WLAN_FC_TYPE_MGMT, WLAN_FC_STYPE_ASSOC_REQ); /* Request TX callback */ mgmt->frame_control |= host_to_le16(BIT(1)); memcpy(mgmt->da, hapd->conf->assoc_ap_addr, ETH_ALEN); memcpy(mgmt->sa, hapd->own_addr, ETH_ALEN); memcpy(mgmt->bssid, hapd->conf->assoc_ap_addr, ETH_ALEN); mgmt->u.assoc_req.capab_info = host_to_le16(0); mgmt->u.assoc_req.listen_interval = host_to_le16(1); p = &mgmt->u.assoc_req.variable[0]; *p++ = WLAN_EID_SSID; *p++ = hapd->assoc_ap_ssid_len; memcpy(p, hapd->assoc_ap_ssid, hapd->assoc_ap_ssid_len); p += hapd->assoc_ap_ssid_len; p = hostapd_eid_supp_rates(hapd, p); if (hapd->driver.send_mgmt_frame && hapd->driver.send_mgmt_frame(hapd->driver.send_mgmt_frame, mgmt, p - (u8 *) mgmt, 0) < 0) perror("ieee802_11_sta_associate: send"); /* Try to authenticate again, if this attempt fails or times out. */ eloop_register_timeout(5, 0, ieee802_11_sta_associate, hapd, NULL); }
static void send_auth_reply(hostapd *hapd, struct ieee80211_mgmt *mgmt, u16 auth_alg, u16 auth_transaction, u16 resp, u8 *challenge) { u8 buf[IEEE80211_HDRLEN + sizeof(mgmt->u.auth) + 2 + WLAN_AUTH_CHALLENGE_LEN]; struct ieee80211_mgmt *reply; size_t rlen; memset(buf, 0, sizeof(buf)); reply = (struct ieee80211_mgmt *) buf; reply->frame_control = IEEE80211_FC(WLAN_FC_TYPE_MGMT, WLAN_FC_STYPE_AUTH); /* Request TX callback */ reply->frame_control |= host_to_le16(BIT(1)); memcpy(reply->da, mgmt->sa, ETH_ALEN); memcpy(reply->sa, hapd->own_addr, ETH_ALEN); memcpy(reply->bssid, mgmt->bssid, ETH_ALEN); reply->u.auth.auth_alg = host_to_le16(auth_alg); reply->u.auth.auth_transaction = host_to_le16(auth_transaction); reply->u.auth.status_code = host_to_le16(resp); rlen = IEEE80211_HDRLEN + sizeof(reply->u.auth); if (auth_alg == WLAN_AUTH_SHARED_KEY && auth_transaction == 2 && challenge) { u8 *p = reply->u.auth.variable; *p++ = WLAN_EID_CHALLENGE; *p++ = WLAN_AUTH_CHALLENGE_LEN; memcpy(p, challenge, WLAN_AUTH_CHALLENGE_LEN); rlen += 2 + WLAN_AUTH_CHALLENGE_LEN; } else challenge = NULL; HOSTAPD_DEBUG(HOSTAPD_DEBUG_MINIMAL, "authentication reply: STA=" MACSTR " auth_alg=%d " "auth_transaction=%d resp=%d%s\n", MAC2STR(mgmt->sa), auth_alg, auth_transaction, resp, challenge ? " challenge" : ""); if (hapd->driver.send_mgmt_frame && hapd->driver.send_mgmt_frame(hapd->driver.data, reply, rlen, 0) < 0) perror("send_auth_reply: send"); }
static void send_deauth(struct hostapd_data *hapd, const u8 *addr, u16 reason_code) { int send_len; struct ieee80211_mgmt reply; os_memset(&reply, 0, sizeof(reply)); reply.frame_control = IEEE80211_FC(WLAN_FC_TYPE_MGMT, WLAN_FC_STYPE_DEAUTH); os_memcpy(reply.da, addr, ETH_ALEN); os_memcpy(reply.sa, hapd->own_addr, ETH_ALEN); os_memcpy(reply.bssid, hapd->own_addr, ETH_ALEN); send_len = IEEE80211_HDRLEN + sizeof(reply.u.deauth); reply.u.deauth.reason_code = host_to_le16(reason_code); if (hapd->drv.send_mgmt_frame(hapd, &reply, send_len) < 0) wpa_printf(MSG_INFO, "Failed to send deauth: %s", strerror(errno)); }
/** * mesh_send_path error - Sends a PERR mesh management frame * * @dst: broken destination * @dst_dsn: dsn of the broken destination * @ra: node this frame is addressed to */ int mesh_path_error_tx(u8 *dst, __le32 dst_dsn, u8 *ra, struct net_device *dev) { struct ieee80211_local *local = wdev_priv(dev->ieee80211_ptr); struct sk_buff *skb = dev_alloc_skb(local->hw.extra_tx_headroom + 400); struct ieee80211_mgmt *mgmt; u8 *pos; int ie_len; if (!skb) return -1; skb_reserve(skb, local->hw.extra_tx_headroom); /* 25 is the size of the common mgmt part (24) plus the size of the * common action part (1) */ mgmt = (struct ieee80211_mgmt *) skb_put(skb, 25 + sizeof(mgmt->u.action.u.mesh_action)); memset(mgmt, 0, 25 + sizeof(mgmt->u.action.u.mesh_action)); mgmt->frame_control = IEEE80211_FC(IEEE80211_FTYPE_MGMT, IEEE80211_STYPE_ACTION); memcpy(mgmt->da, ra, ETH_ALEN); memcpy(mgmt->sa, dev->dev_addr, ETH_ALEN); /* BSSID is left zeroed, wildcard value */ mgmt->u.action.category = MESH_PATH_SEL_CATEGORY; mgmt->u.action.u.mesh_action.action_code = MPATH_PERR; ie_len = 12; pos = skb_put(skb, 2 + ie_len); *pos++ = WLAN_EID_PERR; *pos++ = ie_len; /* mode flags, reserved */ *pos++ = 0; /* number of destinations */ *pos++ = 1; memcpy(pos, dst, ETH_ALEN); pos += ETH_ALEN; memcpy(pos, &dst_dsn, 4); ieee80211_sta_tx(dev, skb, 0); return 0; }
static int rtl871x_sta_deauth_ops(void *priv, const u8 *own_addr, const u8 *addr, int reason) { struct rtl871x_driver_data *drv = priv; struct ieee80211_mgmt mgmt; printf("+%s, " MACSTR " is deauth, reason=%d\n", __func__, MAC2STR(addr), reason); memset(&mgmt, 0, sizeof(mgmt)); mgmt.frame_control = IEEE80211_FC(WLAN_FC_TYPE_MGMT, WLAN_FC_STYPE_DEAUTH); memcpy(mgmt.da, addr, ETH_ALEN); memcpy(mgmt.sa, own_addr, ETH_ALEN); memcpy(mgmt.bssid, own_addr, ETH_ALEN); mgmt.u.deauth.reason_code = host_to_le16(reason); return rtl871x_send_mgmt_frame_ops(drv, &mgmt, IEEE80211_HDRLEN + sizeof(mgmt.u.deauth), 0); }
int from_8023_to_80211(unsigned char *inbuffer, int inlen, unsigned char *outbuffer, unsigned char *own_addr) { int indx = 0; struct ieee80211_hdr hdr; os_memset(&hdr, 0, sizeof(struct ieee80211_hdr)); hdr.frame_control = IEEE80211_FC(WLAN_FC_TYPE_DATA, WLAN_FC_STYPE_DATA) | host_to_le16(WLAN_FC_FROMDS); hdr.duration_id = 0; hdr.seq_ctrl = 0; os_memcpy(hdr.addr1, inbuffer, ETH_ALEN); os_memcpy(hdr.addr2, own_addr, ETH_ALEN); os_memcpy(hdr.addr3, inbuffer + ETH_ALEN, ETH_ALEN); os_memcpy(outbuffer + indx, &hdr, sizeof(hdr)); indx += sizeof(hdr); os_memcpy(outbuffer + indx, inbuffer, inlen); indx += inlen; return indx; }
static void hostapd_sa_query_request(struct hostapd_data *hapd, const struct ieee80211_mgmt *mgmt) { struct sta_info *sta; struct ieee80211_mgmt resp; u8 *end; wpa_printf(MSG_DEBUG, "IEEE 802.11: Received SA Query Request from " MACSTR, MAC2STR(mgmt->sa)); wpa_hexdump(MSG_DEBUG, "IEEE 802.11: SA Query Transaction ID", mgmt->u.action.u.sa_query_resp.trans_id, WLAN_SA_QUERY_TR_ID_LEN); sta = ap_get_sta(hapd, mgmt->sa); if (sta == NULL || !(sta->flags & WLAN_STA_ASSOC)) { wpa_printf(MSG_DEBUG, "IEEE 802.11: Ignore SA Query Request " "from unassociated STA " MACSTR, MAC2STR(mgmt->sa)); return; } wpa_printf(MSG_DEBUG, "IEEE 802.11: Sending SA Query Response to " MACSTR, MAC2STR(mgmt->sa)); os_memset(&resp, 0, sizeof(resp)); resp.frame_control = IEEE80211_FC(WLAN_FC_TYPE_MGMT, WLAN_FC_STYPE_ACTION); os_memcpy(resp.da, mgmt->sa, ETH_ALEN); os_memcpy(resp.sa, hapd->own_addr, ETH_ALEN); os_memcpy(resp.bssid, hapd->own_addr, ETH_ALEN); resp.u.action.category = WLAN_ACTION_SA_QUERY; resp.u.action.u.sa_query_req.action = WLAN_SA_QUERY_RESPONSE; os_memcpy(resp.u.action.u.sa_query_req.trans_id, mgmt->u.action.u.sa_query_req.trans_id, WLAN_SA_QUERY_TR_ID_LEN); end = resp.u.action.u.sa_query_req.trans_id + WLAN_SA_QUERY_TR_ID_LEN; if (hapd->drv.send_mgmt_frame(hapd, &resp, end - (u8 *) &resp) < 0) perror("hostapd_sa_query_request: send"); }
static void hostapd_rx_action(struct hostapd_data *hapd, struct rx_action *rx_action) { struct rx_mgmt rx_mgmt; u8 *buf; struct ieee80211_hdr *hdr; wpa_printf(MSG_DEBUG, "EVENT_RX_ACTION DA=" MACSTR " SA=" MACSTR " BSSID=" MACSTR " category=%u", MAC2STR(rx_action->da), MAC2STR(rx_action->sa), MAC2STR(rx_action->bssid), rx_action->category); wpa_hexdump(MSG_MSGDUMP, "Received action frame contents", rx_action->data, rx_action->len); buf = os_zalloc(24 + 1 + rx_action->len); if (buf == NULL) return; hdr = (struct ieee80211_hdr *) buf; hdr->frame_control = IEEE80211_FC(WLAN_FC_TYPE_MGMT, WLAN_FC_STYPE_ACTION); if (rx_action->category == WLAN_ACTION_SA_QUERY) { /* * Assume frame was protected; it would have been dropped if * not. */ hdr->frame_control |= host_to_le16(WLAN_FC_ISWEP); } os_memcpy(hdr->addr1, rx_action->da, ETH_ALEN); os_memcpy(hdr->addr2, rx_action->sa, ETH_ALEN); os_memcpy(hdr->addr3, rx_action->bssid, ETH_ALEN); buf[24] = rx_action->category; os_memcpy(buf + 24 + 1, rx_action->data, rx_action->len); os_memset(&rx_mgmt, 0, sizeof(rx_mgmt)); rx_mgmt.frame = buf; rx_mgmt.frame_len = 24 + 1 + rx_action->len; hostapd_mgmt_rx(hapd, &rx_mgmt); os_free(buf); }