xref: /openbsd/sys/net80211/ieee80211_output.c (revision 54fbbda3)
1 /*	$OpenBSD: ieee80211_output.c,v 1.140 2024/09/01 03:09:00 jsg Exp $	*/
2 /*	$NetBSD: ieee80211_output.c,v 1.13 2004/05/31 11:02:55 dyoung Exp $	*/
3 
4 /*-
5  * Copyright (c) 2001 Atsushi Onoe
6  * Copyright (c) 2002, 2003 Sam Leffler, Errno Consulting
7  * Copyright (c) 2007-2009 Damien Bergamini
8  * All rights reserved.
9  *
10  * Redistribution and use in source and binary forms, with or without
11  * modification, are permitted provided that the following conditions
12  * are met:
13  * 1. Redistributions of source code must retain the above copyright
14  *    notice, this list of conditions and the following disclaimer.
15  * 2. Redistributions in binary form must reproduce the above copyright
16  *    notice, this list of conditions and the following disclaimer in the
17  *    documentation and/or other materials provided with the distribution.
18  * 3. The name of the author may not be used to endorse or promote products
19  *    derived from this software without specific prior written permission.
20  *
21  * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
22  * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
23  * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
24  * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
25  * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
26  * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
27  * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
28  * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
29  * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
30  * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
31  */
32 
33 #include "bpfilter.h"
34 #include "vlan.h"
35 
36 #include <sys/param.h>
37 #include <sys/systm.h>
38 #include <sys/mbuf.h>
39 #include <sys/kernel.h>
40 #include <sys/socket.h>
41 #include <sys/sockio.h>
42 #include <sys/endian.h>
43 #include <sys/errno.h>
44 #include <sys/sysctl.h>
45 
46 #include <net/if.h>
47 #include <net/if_dl.h>
48 #include <net/if_media.h>
49 #include <net/if_llc.h>
50 #include <net/bpf.h>
51 
52 #include <netinet/in.h>
53 #include <netinet/if_ether.h>
54 #include <netinet/ip.h>
55 #ifdef INET6
56 #include <netinet/ip6.h>
57 #endif
58 
59 #if NVLAN > 0
60 #include <net/if_vlan_var.h>
61 #endif
62 
63 #include <net80211/ieee80211_var.h>
64 #include <net80211/ieee80211_priv.h>
65 
66 int	ieee80211_mgmt_output(struct ifnet *, struct ieee80211_node *,
67 	    struct mbuf *, int);
68 int	ieee80211_can_use_ampdu(struct ieee80211com *,
69 	    struct ieee80211_node *);
70 u_int8_t *ieee80211_add_rsn_body(u_int8_t *, struct ieee80211com *,
71 	    const struct ieee80211_node *, int);
72 struct	mbuf *ieee80211_getmgmt(int, int, u_int);
73 struct	mbuf *ieee80211_get_probe_req(struct ieee80211com *,
74 	    struct ieee80211_node *);
75 #ifndef IEEE80211_STA_ONLY
76 struct	mbuf *ieee80211_get_probe_resp(struct ieee80211com *);
77 #endif
78 struct	mbuf *ieee80211_get_auth(struct ieee80211com *,
79 	    struct ieee80211_node *, u_int16_t, u_int16_t);
80 struct	mbuf *ieee80211_get_deauth(struct ieee80211com *,
81 	    struct ieee80211_node *, u_int16_t);
82 struct	mbuf *ieee80211_get_assoc_req(struct ieee80211com *,
83 	    struct ieee80211_node *, int);
84 #ifndef IEEE80211_STA_ONLY
85 struct	mbuf *ieee80211_get_assoc_resp(struct ieee80211com *,
86 	    struct ieee80211_node *, u_int16_t);
87 #endif
88 struct	mbuf *ieee80211_get_disassoc(struct ieee80211com *,
89 	    struct ieee80211_node *, u_int16_t);
90 struct	mbuf *ieee80211_get_addba_req(struct ieee80211com *,
91 	    struct ieee80211_node *, u_int8_t);
92 struct	mbuf *ieee80211_get_addba_resp(struct ieee80211com *,
93 	    struct ieee80211_node *, u_int8_t, u_int8_t, u_int16_t);
94 struct	mbuf *ieee80211_get_delba(struct ieee80211com *,
95 	    struct ieee80211_node *, u_int8_t, u_int8_t, u_int16_t);
96 uint8_t *ieee80211_add_wme_info(uint8_t *, struct ieee80211com *);
97 #ifndef IEEE80211_STA_ONLY
98 uint8_t *ieee80211_add_wme_param(uint8_t *, struct ieee80211com *);
99 #endif
100 struct	mbuf *ieee80211_get_sa_query(struct ieee80211com *,
101 	    struct ieee80211_node *, u_int8_t);
102 struct	mbuf *ieee80211_get_action(struct ieee80211com *,
103 	    struct ieee80211_node *, u_int8_t, u_int8_t, int);
104 
105 /*
106  * IEEE 802.11 output routine. Normally this will directly call the
107  * Ethernet output routine because 802.11 encapsulation is called
108  * later by the driver. This function can be used to send raw frames
109  * if the mbuf has been tagged with a 802.11 data link type.
110  */
111 int
ieee80211_output(struct ifnet * ifp,struct mbuf * m,struct sockaddr * dst,struct rtentry * rt)112 ieee80211_output(struct ifnet *ifp, struct mbuf *m, struct sockaddr *dst,
113     struct rtentry *rt)
114 {
115 	struct ieee80211_frame *wh;
116 	struct m_tag *mtag;
117 	int error = 0;
118 
119 	/* Interface has to be up and running */
120 	if ((ifp->if_flags & (IFF_UP | IFF_RUNNING)) !=
121 	    (IFF_UP | IFF_RUNNING)) {
122 		error = ENETDOWN;
123 		goto bad;
124 	}
125 
126 	/* Try to get the DLT from a mbuf tag */
127 	if ((mtag = m_tag_find(m, PACKET_TAG_DLT, NULL)) != NULL) {
128 		struct ieee80211com *ic = (void *)ifp;
129 		u_int dlt = *(u_int *)(mtag + 1);
130 
131 		/* Fallback to ethernet for non-802.11 linktypes */
132 		if (!(dlt == DLT_IEEE802_11 || dlt == DLT_IEEE802_11_RADIO))
133 			goto fallback;
134 
135 		if (m->m_pkthdr.len < sizeof(struct ieee80211_frame_min))
136 			return (EINVAL);
137 		wh = mtod(m, struct ieee80211_frame *);
138 		if ((wh->i_fc[0] & IEEE80211_FC0_VERSION_MASK) !=
139 		    IEEE80211_FC0_VERSION_0)
140 			return (EINVAL);
141 		if (!(ic->ic_caps & IEEE80211_C_RAWCTL) &&
142 		    (wh->i_fc[0] & IEEE80211_FC0_TYPE_MASK) ==
143 		    IEEE80211_FC0_TYPE_CTL)
144 			return (EINVAL);
145 
146 		return (if_enqueue(ifp, m));
147 	}
148 
149  fallback:
150 	return (ether_output(ifp, m, dst, rt));
151 
152  bad:
153 	m_freem(m);
154 	return (error);
155 }
156 
157 const char *
ieee80211_action_name(struct ieee80211_frame * wh)158 ieee80211_action_name(struct ieee80211_frame *wh)
159 {
160 	const u_int8_t *frm = (const uint8_t *)&wh[1];
161 	const char *categ_ba_name[3] = { "addba_req", "addba_resp", "delba" };
162 
163 	if (frm[0] == IEEE80211_CATEG_BA && frm[1] < nitems(categ_ba_name))
164 		return categ_ba_name[frm[1]];
165 
166 	return "action";
167 }
168 
169 /*
170  * Send a management frame to the specified node.  The node pointer
171  * must have a reference as the pointer will be passed to the driver
172  * and potentially held for a long time.  If the frame is successfully
173  * dispatched to the driver, then it is responsible for freeing the
174  * reference (and potentially free'ing up any associated storage).
175  */
176 int
ieee80211_mgmt_output(struct ifnet * ifp,struct ieee80211_node * ni,struct mbuf * m,int type)177 ieee80211_mgmt_output(struct ifnet *ifp, struct ieee80211_node *ni,
178     struct mbuf *m, int type)
179 {
180 	struct ieee80211com *ic = (void *)ifp;
181 	struct ieee80211_frame *wh;
182 
183 	if (ni == NULL)
184 		panic("null node");
185 	ni->ni_inact = 0;
186 
187 	/*
188 	 * We want to pass the node down to the driver's start
189 	 * routine.  We could stick this in an m_tag and tack that
190 	 * on to the mbuf.  However that's rather expensive to do
191 	 * for every frame so instead we stuff it in a special pkthdr
192 	 * field.
193 	 */
194 	M_PREPEND(m, sizeof(struct ieee80211_frame), M_DONTWAIT);
195 	if (m == NULL)
196 		return ENOMEM;
197 	m->m_pkthdr.ph_cookie = ni;
198 
199 	wh = mtod(m, struct ieee80211_frame *);
200 	wh->i_fc[0] = IEEE80211_FC0_VERSION_0 | IEEE80211_FC0_TYPE_MGT | type;
201 	wh->i_fc[1] = IEEE80211_FC1_DIR_NODS;
202 	*(u_int16_t *)&wh->i_dur[0] = 0;
203 	*(u_int16_t *)&wh->i_seq[0] =
204 	    htole16(ni->ni_txseq << IEEE80211_SEQ_SEQ_SHIFT);
205 	ni->ni_txseq = (ni->ni_txseq + 1) & 0xfff;
206 	IEEE80211_ADDR_COPY(wh->i_addr1, ni->ni_macaddr);
207 	IEEE80211_ADDR_COPY(wh->i_addr2, ic->ic_myaddr);
208 	IEEE80211_ADDR_COPY(wh->i_addr3, ni->ni_bssid);
209 
210 	/* check if protection is required for this mgmt frame */
211 	if ((ic->ic_caps & IEEE80211_C_MFP) &&
212 	    (type == IEEE80211_FC0_SUBTYPE_DISASSOC ||
213 	     type == IEEE80211_FC0_SUBTYPE_DEAUTH ||
214 	     type == IEEE80211_FC0_SUBTYPE_ACTION)) {
215 		/*
216 		 * Hack: we should not set the Protected bit in outgoing
217 		 * group management frames, however it is used as an
218 		 * indication to the drivers that they must encrypt the
219 		 * frame.  Drivers should clear this bit from group
220 		 * management frames (software crypto code will do it).
221 		 * XXX could use an mbuf flag..
222 		 */
223 		if (IEEE80211_IS_MULTICAST(wh->i_addr1) ||
224 		    (ni->ni_flags & IEEE80211_NODE_TXMGMTPROT))
225 			wh->i_fc[1] |= IEEE80211_FC1_PROTECTED;
226 	}
227 
228 	if (ifp->if_flags & IFF_DEBUG) {
229 		/* avoid to print too many frames */
230 		if (
231 #ifndef IEEE80211_STA_ONLY
232 		    ic->ic_opmode == IEEE80211_M_IBSS ||
233 #endif
234 #ifdef IEEE80211_DEBUG
235 		    ieee80211_debug > 1 ||
236 #endif
237 		    (type & IEEE80211_FC0_SUBTYPE_MASK) !=
238 		    IEEE80211_FC0_SUBTYPE_PROBE_RESP) {
239 			const char *subtype_name;
240 			if ((type & IEEE80211_FC0_SUBTYPE_MASK) ==
241 			    IEEE80211_FC0_SUBTYPE_ACTION)
242 				subtype_name = ieee80211_action_name(wh);
243 			else
244 				subtype_name = ieee80211_mgt_subtype_name[
245 				    (type & IEEE80211_FC0_SUBTYPE_MASK) >>
246 				    IEEE80211_FC0_SUBTYPE_SHIFT];
247 			printf("%s: sending %s to %s on channel %u mode %s\n",
248 			    ifp->if_xname, subtype_name,
249 			    ether_sprintf(ni->ni_macaddr),
250 			    ieee80211_chan2ieee(ic, ni->ni_chan),
251 			    ieee80211_phymode_name[ic->ic_curmode]);
252 		}
253 	}
254 
255 #ifndef IEEE80211_STA_ONLY
256 	if (ic->ic_opmode == IEEE80211_M_HOSTAP &&
257 	    ieee80211_pwrsave(ic, m, ni) != 0)
258 		return 0;
259 #endif
260 	mq_enqueue(&ic->ic_mgtq, m);
261 	ifp->if_timer = 1;
262 	if_start(ifp);
263 	return 0;
264 }
265 
266 /*-
267  * EDCA tables are computed using the following formulas:
268  *
269  * 1) EDCATable (non-AP QSTA)
270  *
271  * AC     CWmin 	   CWmax	   AIFSN  TXOP limit(ms)
272  * -------------------------------------------------------------
273  * AC_BK  aCWmin	   aCWmax	   7	  0
274  * AC_BE  aCWmin	   aCWmax	   3	  0
275  * AC_VI  (aCWmin+1)/2-1   aCWmin	   2	  agn=3.008 b=6.016 others=0
276  * AC_VO  (aCWmin+1)/4-1   (aCWmin+1)/2-1  2	  agn=1.504 b=3.264 others=0
277  *
278  * 2) QAPEDCATable (QAP)
279  *
280  * AC     CWmin 	   CWmax	   AIFSN  TXOP limit(ms)
281  * -------------------------------------------------------------
282  * AC_BK  aCWmin	   aCWmax	   7	  0
283  * AC_BE  aCWmin	   4*(aCWmin+1)-1  3	  0
284  * AC_VI  (aCWmin+1)/2-1   aCWmin	   1	  agn=3.008 b=6.016 others=0
285  * AC_VO  (aCWmin+1)/4-1   (aCWmin+1)/2-1  1	  agn=1.504 b=3.264 others=0
286  *
287  * and the following aCWmin/aCWmax values:
288  *
289  * PHY		aCWmin	aCWmax
290  * ---------------------------
291  * 11A		15	1023
292  * 11B  	31	1023
293  * 11G		15*	1023	(*) aCWmin(1)
294  * 11N		15	1023
295  */
296 const struct ieee80211_edca_ac_params
297     ieee80211_edca_table[IEEE80211_MODE_MAX][EDCA_NUM_AC] = {
298 	[IEEE80211_MODE_11B] = {
299 		[EDCA_AC_BK] = { 5, 10, 7,   0 },
300 		[EDCA_AC_BE] = { 5, 10, 3,   0 },
301 		[EDCA_AC_VI] = { 4,  5, 2, 188 },
302 		[EDCA_AC_VO] = { 3,  4, 2, 102 }
303 	},
304 	[IEEE80211_MODE_11A] = {
305 		[EDCA_AC_BK] = { 4, 10, 7,   0 },
306 		[EDCA_AC_BE] = { 4, 10, 3,   0 },
307 		[EDCA_AC_VI] = { 3,  4, 2,  94 },
308 		[EDCA_AC_VO] = { 2,  3, 2,  47 }
309 	},
310 	[IEEE80211_MODE_11G] = {
311 		[EDCA_AC_BK] = { 4, 10, 7,   0 },
312 		[EDCA_AC_BE] = { 4, 10, 3,   0 },
313 		[EDCA_AC_VI] = { 3,  4, 2,  94 },
314 		[EDCA_AC_VO] = { 2,  3, 2,  47 }
315 	},
316 	[IEEE80211_MODE_11N] = {
317 		[EDCA_AC_BK] = { 4, 10, 7,   0 },
318 		[EDCA_AC_BE] = { 4, 10, 3,   0 },
319 		[EDCA_AC_VI] = { 3,  4, 2,  94 },
320 		[EDCA_AC_VO] = { 2,  3, 2,  47 }
321 	},
322 	[IEEE80211_MODE_11AC] = {
323 		[EDCA_AC_BK] = { 4, 10, 7,   0 },
324 		[EDCA_AC_BE] = { 4, 10, 3,   0 },
325 		[EDCA_AC_VI] = { 3,  4, 2,  94 },
326 		[EDCA_AC_VO] = { 2,  3, 2,  47 }
327 	},
328 };
329 
330 #ifndef IEEE80211_STA_ONLY
331 const struct ieee80211_edca_ac_params
332     ieee80211_qap_edca_table[IEEE80211_MODE_MAX][EDCA_NUM_AC] = {
333 	[IEEE80211_MODE_11B] = {
334 		[EDCA_AC_BK] = { 5, 10, 7,   0 },
335 		[EDCA_AC_BE] = { 5,  7, 3,   0 },
336 		[EDCA_AC_VI] = { 4,  5, 1, 188 },
337 		[EDCA_AC_VO] = { 3,  4, 1, 102 }
338 	},
339 	[IEEE80211_MODE_11A] = {
340 		[EDCA_AC_BK] = { 4, 10, 7,   0 },
341 		[EDCA_AC_BE] = { 4,  6, 3,   0 },
342 		[EDCA_AC_VI] = { 3,  4, 1,  94 },
343 		[EDCA_AC_VO] = { 2,  3, 1,  47 }
344 	},
345 	[IEEE80211_MODE_11G] = {
346 		[EDCA_AC_BK] = { 4, 10, 7,   0 },
347 		[EDCA_AC_BE] = { 4,  6, 3,   0 },
348 		[EDCA_AC_VI] = { 3,  4, 1,  94 },
349 		[EDCA_AC_VO] = { 2,  3, 1,  47 }
350 	},
351 	[IEEE80211_MODE_11N] = {
352 		[EDCA_AC_BK] = { 4, 10, 7,   0 },
353 		[EDCA_AC_BE] = { 4,  6, 3,   0 },
354 		[EDCA_AC_VI] = { 3,  4, 1,  94 },
355 		[EDCA_AC_VO] = { 2,  3, 1,  47 }
356 	},
357 	[IEEE80211_MODE_11AC] = {
358 		[EDCA_AC_BK] = { 4, 10, 7,   0 },
359 		[EDCA_AC_BE] = { 4,  6, 3,   0 },
360 		[EDCA_AC_VI] = { 3,  4, 1,  94 },
361 		[EDCA_AC_VO] = { 2,  3, 1,  47 }
362 	},
363 };
364 #endif	/* IEEE80211_STA_ONLY */
365 
366 /*
367  * Return the EDCA Access Category to be used for transmitting a frame with
368  * user-priority `up'.
369  */
370 enum ieee80211_edca_ac
ieee80211_up_to_ac(struct ieee80211com * ic,int up)371 ieee80211_up_to_ac(struct ieee80211com *ic, int up)
372 {
373 	/* see Table 9-1 */
374 	static const enum ieee80211_edca_ac up_to_ac[] = {
375 		EDCA_AC_BE,	/* BE */
376 		EDCA_AC_BK,	/* BK */
377 		EDCA_AC_BK,	/* -- */
378 		EDCA_AC_BE,	/* EE */
379 		EDCA_AC_VI,	/* CL */
380 		EDCA_AC_VI,	/* VI */
381 		EDCA_AC_VO,	/* VO */
382 		EDCA_AC_VO	/* NC */
383 	};
384 	enum ieee80211_edca_ac ac;
385 
386 	ac = (up <= 7) ? up_to_ac[up] : EDCA_AC_BE;
387 
388 #ifndef IEEE80211_STA_ONLY
389 	if (ic->ic_opmode == IEEE80211_M_HOSTAP)
390 		return ac;
391 #endif
392 	/*
393 	 * We do not support the admission control procedure defined in
394 	 * IEEE Std 802.11-2012 section 9.19.4.2.3. The spec says that
395 	 * non-AP QSTAs that don't support this procedure shall use EDCA
396 	 * parameters of a lower priority AC that does not require
397 	 * admission control.
398 	 */
399 	while (ac != EDCA_AC_BK && ic->ic_edca_ac[ac].ac_acm) {
400 		switch (ac) {
401 		case EDCA_AC_BK:
402 			/* can't get there */
403 			break;
404 		case EDCA_AC_BE:
405 			/* BE shouldn't require admission control */
406 			ac = EDCA_AC_BK;
407 			break;
408 		case EDCA_AC_VI:
409 			ac = EDCA_AC_BE;
410 			break;
411 		case EDCA_AC_VO:
412 			ac = EDCA_AC_VI;
413 			break;
414 		}
415 	}
416 	return ac;
417 }
418 
419 /*
420  * Get mbuf's user-priority: if mbuf is not VLAN tagged, select user-priority
421  * based on the DSCP (Differentiated Services Codepoint) field.
422  */
423 int
ieee80211_classify(struct ieee80211com * ic,struct mbuf * m)424 ieee80211_classify(struct ieee80211com *ic, struct mbuf *m)
425 {
426 	struct ether_header eh;
427 	u_int8_t ds_field;
428 #if NVLAN > 0
429 	if (m->m_flags & M_VLANTAG)	/* use VLAN 802.1D user-priority */
430 		return EVL_PRIOFTAG(m->m_pkthdr.ether_vtag);
431 #endif
432 	m_copydata(m, 0, sizeof(eh), (caddr_t)&eh);
433 	if (eh.ether_type == htons(ETHERTYPE_IP)) {
434 		struct ip ip;
435 		m_copydata(m, sizeof(eh), sizeof(ip), (caddr_t)&ip);
436 		if (ip.ip_v != 4)
437 			return 0;
438 		ds_field = ip.ip_tos;
439 	}
440 #ifdef INET6
441 	else if (eh.ether_type == htons(ETHERTYPE_IPV6)) {
442 		struct ip6_hdr ip6;
443 		u_int32_t flowlabel;
444 		m_copydata(m, sizeof(eh), sizeof(ip6), (caddr_t)&ip6);
445 		flowlabel = ntohl(ip6.ip6_flow);
446 		if ((flowlabel >> 28) != 6)
447 			return 0;
448 		ds_field = (flowlabel >> 20) & 0xff;
449 	}
450 #endif	/* INET6 */
451 	else	/* neither IPv4 nor IPv6 */
452 		return 0;
453 
454 	/*
455 	 * Map Differentiated Services Codepoint field (see RFC2474).
456 	 * Preserves backward compatibility with IP Precedence field.
457 	 */
458 	switch (ds_field & 0xfc) {
459 	case IPTOS_PREC_PRIORITY:
460 		return EDCA_AC_VI;
461 	case IPTOS_PREC_IMMEDIATE:
462 		return EDCA_AC_BK;
463 	case IPTOS_PREC_FLASH:
464 	case IPTOS_PREC_FLASHOVERRIDE:
465 	case IPTOS_PREC_CRITIC_ECP:
466 	case IPTOS_PREC_INTERNETCONTROL:
467 	case IPTOS_PREC_NETCONTROL:
468 		return EDCA_AC_VO;
469 	default:
470 		return EDCA_AC_BE;
471 	}
472 }
473 
474 int
ieee80211_can_use_ampdu(struct ieee80211com * ic,struct ieee80211_node * ni)475 ieee80211_can_use_ampdu(struct ieee80211com *ic, struct ieee80211_node *ni)
476 {
477 	return (ni->ni_flags & IEEE80211_NODE_HT) &&
478 	    (ic->ic_caps & IEEE80211_C_TX_AMPDU) &&
479 	    !(ic->ic_opmode == IEEE80211_M_STA && ni != ic->ic_bss) &&
480 	    /*
481 	     * Don't use A-MPDU on non-encrypted networks. There are devices
482 	     * with buggy firmware which allow an attacker to inject 802.11
483 	     * frames into a wifi network by embedding rogue A-MPDU subframes
484 	     * in an arbitrary data payload (e.g. PNG images) which may end
485 	     * up appearing as actual frames after de-aggregation by a buggy
486 	     * device; see https://github.com/rpp0/aggr-inject for details.
487 	     * WPA2 prevents this injection attack since the attacker would
488 	     * need to inject frames which get decrypted correctly.
489 	     */
490 	    ((ic->ic_flags & IEEE80211_F_RSNON) &&
491 	      (ni->ni_rsnprotos & IEEE80211_PROTO_RSN));
492 }
493 
494 void
ieee80211_tx_compressed_bar(struct ieee80211com * ic,struct ieee80211_node * ni,int tid,uint16_t ssn)495 ieee80211_tx_compressed_bar(struct ieee80211com *ic, struct ieee80211_node *ni,
496     int tid, uint16_t ssn)
497 {
498 	struct ifnet *ifp = &ic->ic_if;
499 	struct mbuf *m;
500 
501 	m = ieee80211_get_compressed_bar(ic, ni, tid, ssn);
502 	if (m == NULL)
503 		return;
504 
505 	ieee80211_ref_node(ni);
506 	if (mq_enqueue(&ic->ic_mgtq, m) == 0)
507 		if_start(ifp);
508 	else
509 		ieee80211_release_node(ic, ni);
510 }
511 
512 /*
513  * Encapsulate an outbound data frame.  The mbuf chain is updated and
514  * a reference to the destination node is returned.  If an error is
515  * encountered NULL is returned and the node reference will also be NULL.
516  *
517  * NB: The caller is responsible for free'ing a returned node reference.
518  *     The convention is ic_bss is not reference counted; the caller must
519  *     maintain that.
520  */
521 struct mbuf *
ieee80211_encap(struct ifnet * ifp,struct mbuf * m,struct ieee80211_node ** pni)522 ieee80211_encap(struct ifnet *ifp, struct mbuf *m, struct ieee80211_node **pni)
523 {
524 	struct ieee80211com *ic = (void *)ifp;
525 	struct ether_header eh;
526 	struct ieee80211_frame *wh;
527 	struct ieee80211_node *ni = NULL;
528 	struct llc *llc;
529 	struct m_tag *mtag;
530 	u_int8_t *addr;
531 	u_int dlt, hdrlen;
532 	int addqos, tid;
533 
534 	/* Handle raw frames if mbuf is tagged as 802.11 */
535 	if ((mtag = m_tag_find(m, PACKET_TAG_DLT, NULL)) != NULL) {
536 		dlt = *(u_int *)(mtag + 1);
537 
538 		if (!(dlt == DLT_IEEE802_11 || dlt == DLT_IEEE802_11_RADIO))
539 			goto fallback;
540 
541 		wh = mtod(m, struct ieee80211_frame *);
542 		switch (wh->i_fc[1] & IEEE80211_FC1_DIR_MASK) {
543 		case IEEE80211_FC1_DIR_NODS:
544 		case IEEE80211_FC1_DIR_FROMDS:
545 			addr = wh->i_addr1;
546 			break;
547 		case IEEE80211_FC1_DIR_DSTODS:
548 		case IEEE80211_FC1_DIR_TODS:
549 			addr = wh->i_addr3;
550 			break;
551 		default:
552 			goto bad;
553 		}
554 
555 		ni = ieee80211_find_txnode(ic, addr);
556 		if (ni == NULL)
557 			ni = ieee80211_ref_node(ic->ic_bss);
558 		if (ni == NULL) {
559 			printf("%s: no node for dst %s, "
560 			    "discard raw tx frame\n", ifp->if_xname,
561 			    ether_sprintf(addr));
562 			ic->ic_stats.is_tx_nonode++;
563 			goto bad;
564 		}
565 		ni->ni_inact = 0;
566 
567 		*pni = ni;
568 		return (m);
569 	}
570 
571  fallback:
572 	if (ic->ic_opmode == IEEE80211_M_MONITOR)
573 		goto bad;
574 
575 	if (m->m_len < sizeof(struct ether_header)) {
576 		m = m_pullup(m, sizeof(struct ether_header));
577 		if (m == NULL) {
578 			ic->ic_stats.is_tx_nombuf++;
579 			goto bad;
580 		}
581 	}
582 	memcpy(&eh, mtod(m, caddr_t), sizeof(struct ether_header));
583 
584 	ni = ieee80211_find_txnode(ic, eh.ether_dhost);
585 	if (ni == NULL) {
586 		DPRINTF(("no node for dst %s, discard frame\n",
587 		    ether_sprintf(eh.ether_dhost)));
588 		ic->ic_stats.is_tx_nonode++;
589 		goto bad;
590 	}
591 
592 #ifndef IEEE80211_STA_ONLY
593 	if (ic->ic_opmode == IEEE80211_M_HOSTAP && ni != ic->ic_bss &&
594 	    ni->ni_state != IEEE80211_STA_ASSOC) {
595 		ic->ic_stats.is_tx_nonode++;
596 		goto bad;
597 	}
598 #endif
599 
600 	if ((ic->ic_flags & IEEE80211_F_RSNON) &&
601 	    !ni->ni_port_valid &&
602 	    eh.ether_type != htons(ETHERTYPE_EAPOL)) {
603 		DPRINTF(("port not valid: %s\n",
604 		    ether_sprintf(eh.ether_dhost)));
605 		ic->ic_stats.is_tx_noauth++;
606 		goto bad;
607 	}
608 
609 	if ((ic->ic_flags & IEEE80211_F_COUNTERM) &&
610 	    ni->ni_rsncipher == IEEE80211_CIPHER_TKIP)
611 		/* XXX TKIP countermeasures! */;
612 
613 	ni->ni_inact = 0;
614 
615 	if ((ic->ic_flags & IEEE80211_F_QOS) &&
616 	    (ni->ni_flags & IEEE80211_NODE_QOS) &&
617 	    /* do not QoS-encapsulate EAPOL frames */
618 	    eh.ether_type != htons(ETHERTYPE_EAPOL)) {
619 		struct ieee80211_tx_ba *ba;
620 		tid = ieee80211_classify(ic, m);
621 		ba = &ni->ni_tx_ba[tid];
622 		/* We use QoS data frames for aggregation only. */
623 		if (ba->ba_state != IEEE80211_BA_AGREED) {
624 			hdrlen = sizeof(struct ieee80211_frame);
625 			addqos = 0;
626 			if (ieee80211_can_use_ampdu(ic, ni))
627 				ieee80211_node_trigger_addba_req(ni, tid);
628 		} else {
629 			hdrlen = sizeof(struct ieee80211_qosframe);
630 			addqos = 1;
631 		}
632 	} else {
633 		hdrlen = sizeof(struct ieee80211_frame);
634 		addqos = 0;
635 	}
636 	m_adj(m, sizeof(struct ether_header) - LLC_SNAPFRAMELEN);
637 	llc = mtod(m, struct llc *);
638 	llc->llc_dsap = llc->llc_ssap = LLC_SNAP_LSAP;
639 	llc->llc_control = LLC_UI;
640 	llc->llc_snap.org_code[0] = 0;
641 	llc->llc_snap.org_code[1] = 0;
642 	llc->llc_snap.org_code[2] = 0;
643 	llc->llc_snap.ether_type = eh.ether_type;
644 	M_PREPEND(m, hdrlen, M_DONTWAIT);
645 	if (m == NULL) {
646 		ic->ic_stats.is_tx_nombuf++;
647 		goto bad;
648 	}
649 	wh = mtod(m, struct ieee80211_frame *);
650 	wh->i_fc[0] = IEEE80211_FC0_VERSION_0 | IEEE80211_FC0_TYPE_DATA;
651 	*(u_int16_t *)&wh->i_dur[0] = 0;
652 	if (addqos) {
653 		struct ieee80211_qosframe *qwh =
654 		    (struct ieee80211_qosframe *)wh;
655 		u_int16_t qos = tid;
656 
657 		if (ic->ic_tid_noack & (1 << tid))
658 			qos |= IEEE80211_QOS_ACK_POLICY_NOACK;
659 		else {
660 			/* Use HT immediate block-ack. */
661 			qos |= IEEE80211_QOS_ACK_POLICY_NORMAL;
662 		}
663 		qwh->i_fc[0] |= IEEE80211_FC0_SUBTYPE_QOS;
664 		*(u_int16_t *)qwh->i_qos = htole16(qos);
665 		*(u_int16_t *)qwh->i_seq =
666 		    htole16(ni->ni_qos_txseqs[tid] << IEEE80211_SEQ_SEQ_SHIFT);
667 		ni->ni_qos_txseqs[tid] = (ni->ni_qos_txseqs[tid] + 1) & 0xfff;
668 	} else {
669 		*(u_int16_t *)&wh->i_seq[0] =
670 		    htole16(ni->ni_txseq << IEEE80211_SEQ_SEQ_SHIFT);
671 		ni->ni_txseq = (ni->ni_txseq + 1) & 0xfff;
672 	}
673 	switch (ic->ic_opmode) {
674 	case IEEE80211_M_STA:
675 		wh->i_fc[1] = IEEE80211_FC1_DIR_TODS;
676 		IEEE80211_ADDR_COPY(wh->i_addr1, ni->ni_bssid);
677 		IEEE80211_ADDR_COPY(wh->i_addr2, eh.ether_shost);
678 		IEEE80211_ADDR_COPY(wh->i_addr3, eh.ether_dhost);
679 		break;
680 #ifndef IEEE80211_STA_ONLY
681 	case IEEE80211_M_IBSS:
682 	case IEEE80211_M_AHDEMO:
683 		wh->i_fc[1] = IEEE80211_FC1_DIR_NODS;
684 		IEEE80211_ADDR_COPY(wh->i_addr1, eh.ether_dhost);
685 		IEEE80211_ADDR_COPY(wh->i_addr2, eh.ether_shost);
686 		IEEE80211_ADDR_COPY(wh->i_addr3, ic->ic_bss->ni_bssid);
687 		break;
688 	case IEEE80211_M_HOSTAP:
689 		wh->i_fc[1] = IEEE80211_FC1_DIR_FROMDS;
690 		IEEE80211_ADDR_COPY(wh->i_addr1, eh.ether_dhost);
691 		IEEE80211_ADDR_COPY(wh->i_addr2, ni->ni_bssid);
692 		IEEE80211_ADDR_COPY(wh->i_addr3, eh.ether_shost);
693 		break;
694 #endif
695 	default:
696 		/* should not get there */
697 		goto bad;
698 	}
699 
700 	if ((ic->ic_flags & IEEE80211_F_WEPON) ||
701 	    ((ic->ic_flags & IEEE80211_F_RSNON) &&
702 	     (ni->ni_flags & IEEE80211_NODE_TXPROT)))
703 		wh->i_fc[1] |= IEEE80211_FC1_PROTECTED;
704 
705 #ifndef IEEE80211_STA_ONLY
706 	if (ic->ic_opmode == IEEE80211_M_HOSTAP &&
707 	    ieee80211_pwrsave(ic, m, ni) != 0) {
708 		*pni = NULL;
709 		return NULL;
710 	}
711 #endif
712 	*pni = ni;
713 	return m;
714 bad:
715 	m_freem(m);
716 	if (ni != NULL)
717 		ieee80211_release_node(ic, ni);
718 	*pni = NULL;
719 	return NULL;
720 }
721 
722 /*
723  * Add a Capability Information field to a frame (see 7.3.1.4).
724  */
725 u_int8_t *
ieee80211_add_capinfo(u_int8_t * frm,struct ieee80211com * ic,const struct ieee80211_node * ni)726 ieee80211_add_capinfo(u_int8_t *frm, struct ieee80211com *ic,
727     const struct ieee80211_node *ni)
728 {
729 	u_int16_t capinfo;
730 
731 #ifndef IEEE80211_STA_ONLY
732 	if (ic->ic_opmode == IEEE80211_M_IBSS)
733 		capinfo = IEEE80211_CAPINFO_IBSS;
734 	else if (ic->ic_opmode == IEEE80211_M_HOSTAP)
735 		capinfo = IEEE80211_CAPINFO_ESS;
736 	else
737 #endif
738 		capinfo = 0;
739 #ifndef IEEE80211_STA_ONLY
740 	if (ic->ic_opmode == IEEE80211_M_HOSTAP &&
741 	    (ic->ic_flags & (IEEE80211_F_WEPON | IEEE80211_F_RSNON)))
742 		capinfo |= IEEE80211_CAPINFO_PRIVACY;
743 #endif
744 	/* NB: some 11a AP's reject the request when short preamble is set */
745 	if ((ic->ic_flags & IEEE80211_F_SHPREAMBLE) &&
746 	    IEEE80211_IS_CHAN_2GHZ(ni->ni_chan))
747 		capinfo |= IEEE80211_CAPINFO_SHORT_PREAMBLE;
748 	if (ic->ic_flags & IEEE80211_F_SHSLOT)
749 		capinfo |= IEEE80211_CAPINFO_SHORT_SLOTTIME;
750 	LE_WRITE_2(frm, capinfo);
751 	return frm + 2;
752 }
753 
754 /*
755  * Add an SSID element to a frame (see 7.3.2.1).
756  */
757 u_int8_t *
ieee80211_add_ssid(u_int8_t * frm,const u_int8_t * ssid,u_int len)758 ieee80211_add_ssid(u_int8_t *frm, const u_int8_t *ssid, u_int len)
759 {
760 	*frm++ = IEEE80211_ELEMID_SSID;
761 	*frm++ = len;
762 	memcpy(frm, ssid, len);
763 	return frm + len;
764 }
765 
766 /*
767  * Add a supported rates element to a frame (see 7.3.2.2).
768  */
769 u_int8_t *
ieee80211_add_rates(u_int8_t * frm,const struct ieee80211_rateset * rs)770 ieee80211_add_rates(u_int8_t *frm, const struct ieee80211_rateset *rs)
771 {
772 	int nrates;
773 
774 	*frm++ = IEEE80211_ELEMID_RATES;
775 	nrates = min(rs->rs_nrates, IEEE80211_RATE_SIZE);
776 	*frm++ = nrates;
777 	memcpy(frm, rs->rs_rates, nrates);
778 	return frm + nrates;
779 }
780 
781 #ifndef IEEE80211_STA_ONLY
782 /*
783  * Add a DS Parameter Set element to a frame (see 7.3.2.4).
784  */
785 u_int8_t *
ieee80211_add_ds_params(u_int8_t * frm,struct ieee80211com * ic,const struct ieee80211_node * ni)786 ieee80211_add_ds_params(u_int8_t *frm, struct ieee80211com *ic,
787     const struct ieee80211_node *ni)
788 {
789 	*frm++ = IEEE80211_ELEMID_DSPARMS;
790 	*frm++ = 1;
791 	*frm++ = ieee80211_chan2ieee(ic, ni->ni_chan);
792 	return frm;
793 }
794 
795 /*
796  * Add a TIM element to a frame (see 7.3.2.6 and Annex L).
797  */
798 u_int8_t *
ieee80211_add_tim(u_int8_t * frm,struct ieee80211com * ic)799 ieee80211_add_tim(u_int8_t *frm, struct ieee80211com *ic)
800 {
801 	u_int i, offset = 0, len;
802 
803 	/* find first non-zero octet in the virtual bit map */
804 	for (i = 0; i < ic->ic_tim_len && ic->ic_tim_bitmap[i] == 0; i++)
805 		;
806 
807 	/* clear the lsb as it is reserved for the broadcast indication bit */
808 	if (i < ic->ic_tim_len)
809 		offset = i & ~1;
810 
811 	/* find last non-zero octet in the virtual bit map */
812 	for (i = ic->ic_tim_len - 1; i > 0 && ic->ic_tim_bitmap[i] == 0; i--)
813 		;
814 
815 	len = i - offset + 1;
816 
817 	*frm++ = IEEE80211_ELEMID_TIM;
818 	*frm++ = len + 3;		/* length */
819 	*frm++ = ic->ic_dtim_count;	/* DTIM count */
820 	*frm++ = ic->ic_dtim_period;	/* DTIM period */
821 
822 	/* Bitmap Control */
823 	*frm = offset;
824 	/* set broadcast/multicast indication bit if necessary */
825 	if (ic->ic_dtim_count == 0 && ic->ic_tim_mcast_pending)
826 		*frm |= 0x01;
827 	frm++;
828 
829 	/* Partial Virtual Bitmap */
830 	memcpy(frm, &ic->ic_tim_bitmap[offset], len);
831 	return frm + len;
832 }
833 
834 /*
835  * Add an IBSS Parameter Set element to a frame (see 7.3.2.7).
836  */
837 u_int8_t *
ieee80211_add_ibss_params(u_int8_t * frm,const struct ieee80211_node * ni)838 ieee80211_add_ibss_params(u_int8_t *frm, const struct ieee80211_node *ni)
839 {
840 	*frm++ = IEEE80211_ELEMID_IBSSPARMS;
841 	*frm++ = 2;
842 	LE_WRITE_2(frm, 0);	/* TODO: ATIM window */
843 	return frm + 2;
844 }
845 
846 /*
847  * Add an EDCA Parameter Set element to a frame (see 7.3.2.29).
848  */
849 u_int8_t *
ieee80211_add_edca_params(u_int8_t * frm,struct ieee80211com * ic)850 ieee80211_add_edca_params(u_int8_t *frm, struct ieee80211com *ic)
851 {
852 	const struct ieee80211_edca_ac_params *edca;
853 	int aci;
854 
855 	*frm++ = IEEE80211_ELEMID_EDCAPARMS;
856 	*frm++ = 18;	/* length */
857 	*frm++ = 0;	/* QoS Info */
858 	*frm++ = 0;	/* reserved */
859 
860 	/* setup AC Parameter Records */
861 	edca = ieee80211_edca_table[ic->ic_curmode];
862 	for (aci = 0; aci < EDCA_NUM_AC; aci++) {
863 		const struct ieee80211_edca_ac_params *ac = &edca[aci];
864 
865 		*frm++ = (aci << 5) | ((ac->ac_acm & 0x1) << 4) |
866 			 (ac->ac_aifsn & 0xf);
867 		*frm++ = (ac->ac_ecwmax << 4) |
868 			 (ac->ac_ecwmin & 0xf);
869 		LE_WRITE_2(frm, ac->ac_txoplimit); frm += 2;
870 	}
871 	return frm;
872 }
873 
874 /*
875  * Add an ERP element to a frame (see 7.3.2.13).
876  */
877 u_int8_t *
ieee80211_add_erp(u_int8_t * frm,struct ieee80211com * ic)878 ieee80211_add_erp(u_int8_t *frm, struct ieee80211com *ic)
879 {
880 	u_int8_t erp;
881 	int nonerpsta = 0;
882 
883 	*frm++ = IEEE80211_ELEMID_ERP;
884 	*frm++ = 1;
885 	erp = 0;
886 	/*
887 	 * The NonERP_Present bit shall be set to 1 when a NonERP STA
888 	 * is associated with the BSS.
889 	 */
890 	ieee80211_iterate_nodes(ic, ieee80211_count_nonerpsta, &nonerpsta);
891 	if (nonerpsta != 0)
892 		erp |= IEEE80211_ERP_NON_ERP_PRESENT;
893 	/*
894 	 * If one or more NonERP STAs are associated in the BSS, the
895 	 * Use_Protection bit shall be set to 1 in transmitted ERP
896 	 * Information Elements.
897 	 */
898 	if (ic->ic_flags & IEEE80211_F_USEPROT)
899 		erp |= IEEE80211_ERP_USE_PROTECTION;
900 	/*
901 	 * The Barker_Preamble_Mode bit shall be set to 1 by the ERP
902 	 * Information Element sender if one or more associated NonERP
903 	 * STAs are not short preamble capable.
904 	 */
905 	if (!(ic->ic_flags & IEEE80211_F_SHPREAMBLE))
906 		erp |= IEEE80211_ERP_BARKER_MODE;
907 	*frm++ = erp;
908 	return frm;
909 }
910 #endif	/* IEEE80211_STA_ONLY */
911 
912 /*
913  * Add a QoS Capability element to a frame (see 7.3.2.35).
914  */
915 u_int8_t *
ieee80211_add_qos_capability(u_int8_t * frm,struct ieee80211com * ic)916 ieee80211_add_qos_capability(u_int8_t *frm, struct ieee80211com *ic)
917 {
918 	*frm++ = IEEE80211_ELEMID_QOS_CAP;
919 	*frm++ = 1;
920 	*frm++ = 0;	/* QoS Info */
921 	return frm;
922 }
923 
924 /*
925  * Add a Wifi-Alliance WME (aka WMM) info element to a frame.
926  * WME is a requirement for Wifi-Alliance compliance and some
927  * 11n APs will not negotiate HT if this element is missing.
928  */
929 uint8_t *
ieee80211_add_wme_info(uint8_t * frm,struct ieee80211com * ic)930 ieee80211_add_wme_info(uint8_t *frm, struct ieee80211com *ic)
931 {
932 	*frm++ = IEEE80211_ELEMID_VENDOR;
933 	*frm++ = 7;
934 	memcpy(frm, MICROSOFT_OUI, 3); frm += 3;
935 	*frm++ = 2; /* OUI type */
936 	*frm++ = 0; /* OUI subtype */
937 	*frm++ = 1; /* version */
938 	*frm++ = 0; /* info */
939 
940 	return frm;
941 }
942 
943 #ifndef IEEE80211_STA_ONLY
944 /*
945  * Add a Wifi-Alliance WMM (aka WME) parameter element to a frame.
946  */
947 uint8_t *
ieee80211_add_wme_param(uint8_t * frm,struct ieee80211com * ic)948 ieee80211_add_wme_param(uint8_t *frm, struct ieee80211com *ic)
949 {
950 	const struct ieee80211_edca_ac_params *edca;
951 	int aci;
952 
953 	*frm++ = IEEE80211_ELEMID_VENDOR;
954 	*frm++ = 24;
955 	memcpy(frm, MICROSOFT_OUI, 3); frm += 3;
956 	*frm++ = 2; /* OUI type */
957 	*frm++ = 1; /* OUI subtype */
958 	*frm++ = 1; /* version */
959 	*frm++ = 0; /* info */
960 	*frm++ = 0; /* reserved */
961 
962 	/* setup AC Parameter Records */
963 	edca = ieee80211_edca_table[ic->ic_curmode];
964 	for (aci = 0; aci < EDCA_NUM_AC; aci++) {
965 		const struct ieee80211_edca_ac_params *ac = &edca[aci];
966 
967 		*frm++ = (aci << 5) | ((ac->ac_acm & 0x1) << 4) |
968 			 (ac->ac_aifsn & 0xf);
969 		*frm++ = (ac->ac_ecwmax << 4) |
970 			 (ac->ac_ecwmin & 0xf);
971 		LE_WRITE_2(frm, ac->ac_txoplimit); frm += 2;
972 	}
973 
974 	return frm;
975 }
976 #endif
977 
978 /*
979  * Add an RSN element to a frame (see 802.11-2012 8.4.2.27)
980  */
981 u_int8_t *
ieee80211_add_rsn_body(u_int8_t * frm,struct ieee80211com * ic,const struct ieee80211_node * ni,int wpa)982 ieee80211_add_rsn_body(u_int8_t *frm, struct ieee80211com *ic,
983     const struct ieee80211_node *ni, int wpa)
984 {
985 	const u_int8_t *oui = wpa ? MICROSOFT_OUI : IEEE80211_OUI;
986 	u_int8_t *pcount;
987 	u_int16_t count, rsncaps;
988 
989 	/* write Version field */
990 	LE_WRITE_2(frm, 1); frm += 2;
991 
992 	/* write Group Data Cipher Suite field (see 802.11-2012 Table 8-99) */
993 	memcpy(frm, oui, 3); frm += 3;
994 	switch (ni->ni_rsngroupcipher) {
995 	case IEEE80211_CIPHER_WEP40:
996 		*frm++ = 1;
997 		break;
998 	case IEEE80211_CIPHER_TKIP:
999 		*frm++ = 2;
1000 		break;
1001 	case IEEE80211_CIPHER_CCMP:
1002 		*frm++ = 4;
1003 		break;
1004 	case IEEE80211_CIPHER_WEP104:
1005 		*frm++ = 5;
1006 		break;
1007 	default:
1008 		/* can't get there */
1009 		panic("invalid group data cipher!");
1010 	}
1011 
1012 	pcount = frm; frm += 2;
1013 	count = 0;
1014 	/* write Pairwise Cipher Suite List */
1015 	if (ni->ni_rsnciphers & IEEE80211_CIPHER_USEGROUP) {
1016 		memcpy(frm, oui, 3); frm += 3;
1017 		*frm++ = 0;
1018 		count++;
1019 	}
1020 	if (ni->ni_rsnciphers & IEEE80211_CIPHER_TKIP) {
1021 		memcpy(frm, oui, 3); frm += 3;
1022 		*frm++ = 2;
1023 		count++;
1024 	}
1025 	if (ni->ni_rsnciphers & IEEE80211_CIPHER_CCMP) {
1026 		memcpy(frm, oui, 3); frm += 3;
1027 		*frm++ = 4;
1028 		count++;
1029 	}
1030 	/* write Pairwise Cipher Suite Count field */
1031 	LE_WRITE_2(pcount, count);
1032 
1033 	pcount = frm; frm += 2;
1034 	count = 0;
1035 	/* write AKM Suite List (see Table 20dc) */
1036 	if (ni->ni_rsnakms & IEEE80211_AKM_8021X) {
1037 		memcpy(frm, oui, 3); frm += 3;
1038 		*frm++ = 1;
1039 		count++;
1040 	}
1041 	if (ni->ni_rsnakms & IEEE80211_AKM_PSK) {
1042 		memcpy(frm, oui, 3); frm += 3;
1043 		*frm++ = 2;
1044 		count++;
1045 	}
1046 	if (!wpa && (ni->ni_rsnakms & IEEE80211_AKM_SHA256_8021X)) {
1047 		memcpy(frm, oui, 3); frm += 3;
1048 		*frm++ = 5;
1049 		count++;
1050 	}
1051 	if (!wpa && (ni->ni_rsnakms & IEEE80211_AKM_SHA256_PSK)) {
1052 		memcpy(frm, oui, 3); frm += 3;
1053 		*frm++ = 6;
1054 		count++;
1055 	}
1056 	/* write AKM Suite List Count field */
1057 	LE_WRITE_2(pcount, count);
1058 
1059 	if (wpa)
1060 		return frm;
1061 
1062 	/* write RSN Capabilities field */
1063 	rsncaps = (ni->ni_rsncaps & (IEEE80211_RSNCAP_PTKSA_RCNT_MASK |
1064 	    IEEE80211_RSNCAP_GTKSA_RCNT_MASK));
1065 	if (ic->ic_caps & IEEE80211_C_MFP) {
1066 		rsncaps |= IEEE80211_RSNCAP_MFPC;
1067 		if (ic->ic_flags & IEEE80211_F_MFPR)
1068 			rsncaps |= IEEE80211_RSNCAP_MFPR;
1069 	}
1070 	if (ic->ic_flags & IEEE80211_F_PBAR)
1071 		rsncaps |= IEEE80211_RSNCAP_PBAC;
1072 	LE_WRITE_2(frm, rsncaps); frm += 2;
1073 
1074 	if (ni->ni_flags & IEEE80211_NODE_PMKID) {
1075 		/* write PMKID Count field */
1076 		LE_WRITE_2(frm, 1); frm += 2;
1077 		/* write PMKID List (only 1) */
1078 		memcpy(frm, ni->ni_pmkid, IEEE80211_PMKID_LEN);
1079 		frm += IEEE80211_PMKID_LEN;
1080 	}
1081 
1082 	if (!(ic->ic_caps & IEEE80211_C_MFP))
1083 		return frm;
1084 
1085 	if ((ni->ni_flags & IEEE80211_NODE_PMKID) == 0) {
1086 		/* no PMKID (PMKID Count=0) */
1087 		LE_WRITE_2(frm, 0); frm += 2;
1088 	}
1089 
1090 	/* write Group Integrity Cipher Suite field */
1091 	memcpy(frm, oui, 3); frm += 3;
1092 	switch (ic->ic_rsngroupmgmtcipher) {
1093 	case IEEE80211_CIPHER_BIP:
1094 		*frm++ = 6;
1095 		break;
1096 	default:
1097 		/* can't get there */
1098 		panic("invalid integrity group cipher!");
1099 	}
1100 	return frm;
1101 }
1102 
1103 u_int8_t *
ieee80211_add_rsn(u_int8_t * frm,struct ieee80211com * ic,const struct ieee80211_node * ni)1104 ieee80211_add_rsn(u_int8_t *frm, struct ieee80211com *ic,
1105     const struct ieee80211_node *ni)
1106 {
1107 	u_int8_t *plen;
1108 
1109 	*frm++ = IEEE80211_ELEMID_RSN;
1110 	plen = frm++;	/* length filled in later */
1111 	frm = ieee80211_add_rsn_body(frm, ic, ni, 0);
1112 
1113 	/* write length field */
1114 	*plen = frm - plen - 1;
1115 	return frm;
1116 }
1117 
1118 /*
1119  * Add a vendor-specific WPA element to a frame.
1120  * This is required for compatibility with Wi-Fi Alliance WPA.
1121  */
1122 u_int8_t *
ieee80211_add_wpa(u_int8_t * frm,struct ieee80211com * ic,const struct ieee80211_node * ni)1123 ieee80211_add_wpa(u_int8_t *frm, struct ieee80211com *ic,
1124     const struct ieee80211_node *ni)
1125 {
1126 	u_int8_t *plen;
1127 
1128 	*frm++ = IEEE80211_ELEMID_VENDOR;
1129 	plen = frm++;	/* length filled in later */
1130 	memcpy(frm, MICROSOFT_OUI, 3); frm += 3;
1131 	*frm++ = 1;	/* WPA */
1132 	frm = ieee80211_add_rsn_body(frm, ic, ni, 1);
1133 
1134 	/* write length field */
1135 	*plen = frm - plen - 1;
1136 	return frm;
1137 }
1138 
1139 /*
1140  * Add an extended supported rates element to a frame (see 7.3.2.14).
1141  */
1142 u_int8_t *
ieee80211_add_xrates(u_int8_t * frm,const struct ieee80211_rateset * rs)1143 ieee80211_add_xrates(u_int8_t *frm, const struct ieee80211_rateset *rs)
1144 {
1145 	int nrates;
1146 
1147 	KASSERT(rs->rs_nrates > IEEE80211_RATE_SIZE);
1148 
1149 	*frm++ = IEEE80211_ELEMID_XRATES;
1150 	nrates = rs->rs_nrates - IEEE80211_RATE_SIZE;
1151 	*frm++ = nrates;
1152 	memcpy(frm, rs->rs_rates + IEEE80211_RATE_SIZE, nrates);
1153 	return frm + nrates;
1154 }
1155 
1156 /*
1157  * Add an HT Capabilities element to a frame (see 7.3.2.57).
1158  */
1159 u_int8_t *
ieee80211_add_htcaps(u_int8_t * frm,struct ieee80211com * ic)1160 ieee80211_add_htcaps(u_int8_t *frm, struct ieee80211com *ic)
1161 {
1162 	*frm++ = IEEE80211_ELEMID_HTCAPS;
1163 	*frm++ = 26;
1164 	LE_WRITE_2(frm, ic->ic_htcaps); frm += 2;
1165 	*frm++ = ic->ic_ampdu_params;
1166 	memcpy(frm, ic->ic_sup_mcs, 10); frm += 10;
1167 	LE_WRITE_2(frm, (ic->ic_max_rxrate & IEEE80211_MCS_RX_RATE_HIGH));
1168 	frm += 2;
1169 	*frm++ = ic->ic_tx_mcs_set;
1170 	*frm++ = 0; /* reserved */
1171 	*frm++ = 0; /* reserved */
1172 	*frm++ = 0; /* reserved */
1173 	LE_WRITE_2(frm, ic->ic_htxcaps); frm += 2;
1174 	LE_WRITE_4(frm, ic->ic_txbfcaps); frm += 4;
1175 	*frm++ = ic->ic_aselcaps;
1176 	return frm;
1177 }
1178 
1179 #ifndef IEEE80211_STA_ONLY
1180 /*
1181  * Add an HT Operation element to a frame (see 7.3.2.58).
1182  */
1183 u_int8_t *
ieee80211_add_htop(u_int8_t * frm,struct ieee80211com * ic)1184 ieee80211_add_htop(u_int8_t *frm, struct ieee80211com *ic)
1185 {
1186 	*frm++ = IEEE80211_ELEMID_HTOP;
1187 	*frm++ = 22;
1188 	*frm++ = ieee80211_chan2ieee(ic, ic->ic_bss->ni_chan);
1189 	*frm++ = ic->ic_bss->ni_htop0;
1190 	LE_WRITE_2(frm, ic->ic_bss->ni_htop1); frm += 2;
1191 	LE_WRITE_2(frm, ic->ic_bss->ni_htop2); frm += 2;
1192 	memset(frm, 0, 16); frm += 16;
1193 	return frm;
1194 }
1195 #endif	/* !IEEE80211_STA_ONLY */
1196 
1197 /*
1198  * Add a VHT Capabilities element to a frame (see 802.11ac-2013 8.4.2.160.2).
1199  */
1200 u_int8_t *
ieee80211_add_vhtcaps(u_int8_t * frm,struct ieee80211com * ic)1201 ieee80211_add_vhtcaps(u_int8_t *frm, struct ieee80211com *ic)
1202 {
1203 	*frm++ = IEEE80211_ELEMID_VHTCAPS;
1204 	*frm++ = 12;
1205 	LE_WRITE_4(frm, ic->ic_vhtcaps); frm += 4;
1206 	LE_WRITE_2(frm, ic->ic_vht_rxmcs); frm += 2;
1207 	LE_WRITE_2(frm, ic->ic_vht_rx_max_lgi_mbit_s); frm += 2;
1208 	LE_WRITE_2(frm, ic->ic_vht_txmcs); frm += 2;
1209 	LE_WRITE_2(frm, ic->ic_vht_tx_max_lgi_mbit_s); frm += 2;
1210 	return frm;
1211 }
1212 
1213 #ifndef IEEE80211_STA_ONLY
1214 /*
1215  * Add a Timeout Interval element to a frame (see 7.3.2.49).
1216  */
1217 u_int8_t *
ieee80211_add_tie(u_int8_t * frm,u_int8_t type,u_int32_t value)1218 ieee80211_add_tie(u_int8_t *frm, u_int8_t type, u_int32_t value)
1219 {
1220 	*frm++ = IEEE80211_ELEMID_TIE;
1221 	*frm++ = 5;	/* length */
1222 	*frm++ = type;	/* Timeout Interval type */
1223 	LE_WRITE_4(frm, value);
1224 	return frm + 4;
1225 }
1226 #endif
1227 
1228 struct mbuf *
ieee80211_getmgmt(int flags,int type,u_int pktlen)1229 ieee80211_getmgmt(int flags, int type, u_int pktlen)
1230 {
1231 	struct mbuf *m;
1232 
1233 	/* reserve space for 802.11 header */
1234 	pktlen += sizeof(struct ieee80211_frame);
1235 
1236 	if (pktlen > MCLBYTES)
1237 		panic("management frame too large: %u", pktlen);
1238 	MGETHDR(m, flags, type);
1239 	if (m == NULL)
1240 		return NULL;
1241 	if (pktlen > MHLEN) {
1242 		MCLGET(m, flags);
1243 		if (!(m->m_flags & M_EXT))
1244 			return m_free(m);
1245 	}
1246 	m->m_data += sizeof(struct ieee80211_frame);
1247 	return m;
1248 }
1249 
1250 /*-
1251  * Probe request frame format:
1252  * [tlv] SSID
1253  * [tlv] Supported rates
1254  * [tlv] Extended Supported Rates (802.11g)
1255  * [tlv] HT Capabilities (802.11n)
1256  */
1257 struct mbuf *
ieee80211_get_probe_req(struct ieee80211com * ic,struct ieee80211_node * ni)1258 ieee80211_get_probe_req(struct ieee80211com *ic, struct ieee80211_node *ni)
1259 {
1260 	const struct ieee80211_rateset *rs =
1261 	    &ic->ic_sup_rates[ieee80211_chan2mode(ic, ni->ni_chan)];
1262 	struct mbuf *m;
1263 	u_int8_t *frm;
1264 
1265 	m = ieee80211_getmgmt(M_DONTWAIT, MT_DATA,
1266 	    2 + ic->ic_des_esslen +
1267 	    2 + min(rs->rs_nrates, IEEE80211_RATE_SIZE) +
1268 	    ((rs->rs_nrates > IEEE80211_RATE_SIZE) ?
1269 		2 + rs->rs_nrates - IEEE80211_RATE_SIZE : 0) +
1270 	    ((ic->ic_flags & IEEE80211_F_HTON) ? 28 + 9 : 0) +
1271 	    ((ic->ic_flags & IEEE80211_F_VHTON) ? 14 : 0));
1272 	if (m == NULL)
1273 		return NULL;
1274 
1275 	frm = mtod(m, u_int8_t *);
1276 	frm = ieee80211_add_ssid(frm, ic->ic_des_essid, ic->ic_des_esslen);
1277 	frm = ieee80211_add_rates(frm, rs);
1278 	if (rs->rs_nrates > IEEE80211_RATE_SIZE)
1279 		frm = ieee80211_add_xrates(frm, rs);
1280 	if (ic->ic_flags & IEEE80211_F_HTON) {
1281 		frm = ieee80211_add_htcaps(frm, ic);
1282 		frm = ieee80211_add_wme_info(frm, ic);
1283 	}
1284 	if (ic->ic_flags & IEEE80211_F_VHTON)
1285 		frm = ieee80211_add_htcaps(frm, ic);
1286 
1287 	m->m_pkthdr.len = m->m_len = frm - mtod(m, u_int8_t *);
1288 
1289 	return m;
1290 }
1291 
1292 #ifndef IEEE80211_STA_ONLY
1293 /*-
1294  * Probe response frame format:
1295  * [8]   Timestamp
1296  * [2]   Beacon interval
1297  * [2]   Capability
1298  * [tlv] Service Set Identifier (SSID)
1299  * [tlv] Supported rates
1300  * [tlv] DS Parameter Set (802.11g)
1301  * [tlv] ERP Information (802.11g)
1302  * [tlv] Extended Supported Rates (802.11g)
1303  * [tlv] RSN (802.11i)
1304  * [tlv] EDCA Parameter Set (802.11e)
1305  * [tlv] HT Capabilities (802.11n)
1306  * [tlv] HT Operation (802.11n)
1307  */
1308 struct mbuf *
ieee80211_get_probe_resp(struct ieee80211com * ic)1309 ieee80211_get_probe_resp(struct ieee80211com *ic)
1310 {
1311 	const struct ieee80211_rateset *rs = &ic->ic_bss->ni_rates;
1312 	struct mbuf *m;
1313 	u_int8_t *frm;
1314 
1315 	m = ieee80211_getmgmt(M_DONTWAIT, MT_DATA,
1316 	    8 + 2 + 2 +
1317 	    2 + ic->ic_bss->ni_esslen +
1318 	    2 + min(rs->rs_nrates, IEEE80211_RATE_SIZE) +
1319 	    2 + 1 +
1320 	    ((ic->ic_opmode == IEEE80211_M_IBSS) ? 2 + 2 : 0) +
1321 	    ((ic->ic_curmode == IEEE80211_MODE_11G) ? 2 + 1 : 0) +
1322 	    ((rs->rs_nrates > IEEE80211_RATE_SIZE) ?
1323 		2 + rs->rs_nrates - IEEE80211_RATE_SIZE : 0) +
1324 	    (((ic->ic_flags & IEEE80211_F_RSNON) &&
1325 	      (ic->ic_bss->ni_rsnprotos & IEEE80211_PROTO_RSN)) ?
1326 		2 + IEEE80211_RSNIE_MAXLEN : 0) +
1327 	    ((ic->ic_flags & IEEE80211_F_QOS) ? 2 + 18 : 0) +
1328 	    (((ic->ic_flags & IEEE80211_F_RSNON) &&
1329 	      (ic->ic_bss->ni_rsnprotos & IEEE80211_PROTO_WPA)) ?
1330 		2 + IEEE80211_WPAIE_MAXLEN : 0) +
1331 	    ((ic->ic_flags & IEEE80211_F_HTON) ? 28 + 24 + 26 : 0));
1332 	if (m == NULL)
1333 		return NULL;
1334 
1335 	frm = mtod(m, u_int8_t *);
1336 	memset(frm, 0, 8); frm += 8;	/* timestamp is set by hardware */
1337 	LE_WRITE_2(frm, ic->ic_bss->ni_intval); frm += 2;
1338 	frm = ieee80211_add_capinfo(frm, ic, ic->ic_bss);
1339 	frm = ieee80211_add_ssid(frm, ic->ic_bss->ni_essid,
1340 	    ic->ic_bss->ni_esslen);
1341 	frm = ieee80211_add_rates(frm, rs);
1342 	frm = ieee80211_add_ds_params(frm, ic, ic->ic_bss);
1343 	if (ic->ic_opmode == IEEE80211_M_IBSS)
1344 		frm = ieee80211_add_ibss_params(frm, ic->ic_bss);
1345 	if (ic->ic_curmode == IEEE80211_MODE_11G)
1346 		frm = ieee80211_add_erp(frm, ic);
1347 	if (rs->rs_nrates > IEEE80211_RATE_SIZE)
1348 		frm = ieee80211_add_xrates(frm, rs);
1349 	if ((ic->ic_flags & IEEE80211_F_RSNON) &&
1350 	    (ic->ic_bss->ni_rsnprotos & IEEE80211_PROTO_RSN))
1351 		frm = ieee80211_add_rsn(frm, ic, ic->ic_bss);
1352 	if (ic->ic_flags & IEEE80211_F_QOS)
1353 		frm = ieee80211_add_edca_params(frm, ic);
1354 	if ((ic->ic_flags & IEEE80211_F_RSNON) &&
1355 	    (ic->ic_bss->ni_rsnprotos & IEEE80211_PROTO_WPA))
1356 		frm = ieee80211_add_wpa(frm, ic, ic->ic_bss);
1357 	if (ic->ic_flags & IEEE80211_F_HTON) {
1358 		frm = ieee80211_add_htcaps(frm, ic);
1359 		frm = ieee80211_add_htop(frm, ic);
1360 		frm = ieee80211_add_wme_param(frm, ic);
1361 	}
1362 
1363 	m->m_pkthdr.len = m->m_len = frm - mtod(m, u_int8_t *);
1364 
1365 	return m;
1366 }
1367 #endif	/* IEEE80211_STA_ONLY */
1368 
1369 /*-
1370  * Authentication frame format:
1371  * [2] Authentication algorithm number
1372  * [2] Authentication transaction sequence number
1373  * [2] Status code
1374  */
1375 struct mbuf *
ieee80211_get_auth(struct ieee80211com * ic,struct ieee80211_node * ni,u_int16_t status,u_int16_t seq)1376 ieee80211_get_auth(struct ieee80211com *ic, struct ieee80211_node *ni,
1377     u_int16_t status, u_int16_t seq)
1378 {
1379 	struct mbuf *m;
1380 	u_int8_t *frm;
1381 
1382 	MGETHDR(m, M_DONTWAIT, MT_DATA);
1383 	if (m == NULL)
1384 		return NULL;
1385 	m_align(m, 2 * 3);
1386 	m->m_pkthdr.len = m->m_len = 2 * 3;
1387 
1388 	frm = mtod(m, u_int8_t *);
1389 	LE_WRITE_2(frm, IEEE80211_AUTH_ALG_OPEN); frm += 2;
1390 	LE_WRITE_2(frm, seq); frm += 2;
1391 	LE_WRITE_2(frm, status);
1392 
1393 	return m;
1394 }
1395 
1396 /*-
1397  * Deauthentication frame format:
1398  * [2] Reason code
1399  */
1400 struct mbuf *
ieee80211_get_deauth(struct ieee80211com * ic,struct ieee80211_node * ni,u_int16_t reason)1401 ieee80211_get_deauth(struct ieee80211com *ic, struct ieee80211_node *ni,
1402     u_int16_t reason)
1403 {
1404 	struct mbuf *m;
1405 
1406 	MGETHDR(m, M_DONTWAIT, MT_DATA);
1407 	if (m == NULL)
1408 		return NULL;
1409 	m_align(m, 2);
1410 	m->m_pkthdr.len = m->m_len = 2;
1411 
1412 	*mtod(m, u_int16_t *) = htole16(reason);
1413 
1414 	return m;
1415 }
1416 
1417 /*-
1418  * (Re)Association request frame format:
1419  * [2]   Capability information
1420  * [2]   Listen interval
1421  * [6*]  Current AP address (Reassociation only)
1422  * [tlv] SSID
1423  * [tlv] Supported rates
1424  * [tlv] Extended Supported Rates (802.11g)
1425  * [tlv] RSN (802.11i)
1426  * [tlv] QoS Capability (802.11e)
1427  * [tlv] HT Capabilities (802.11n)
1428  */
1429 struct mbuf *
ieee80211_get_assoc_req(struct ieee80211com * ic,struct ieee80211_node * ni,int type)1430 ieee80211_get_assoc_req(struct ieee80211com *ic, struct ieee80211_node *ni,
1431     int type)
1432 {
1433 	const struct ieee80211_rateset *rs = &ni->ni_rates;
1434 	struct mbuf *m;
1435 	u_int8_t *frm;
1436 	u_int16_t capinfo;
1437 
1438 	m = ieee80211_getmgmt(M_DONTWAIT, MT_DATA,
1439 	    2 + 2 +
1440 	    ((type == IEEE80211_FC0_SUBTYPE_REASSOC_REQ) ?
1441 		IEEE80211_ADDR_LEN : 0) +
1442 	    2 + ni->ni_esslen +
1443 	    2 + min(rs->rs_nrates, IEEE80211_RATE_SIZE) +
1444 	    ((rs->rs_nrates > IEEE80211_RATE_SIZE) ?
1445 		2 + rs->rs_nrates - IEEE80211_RATE_SIZE : 0) +
1446 	    (((ic->ic_flags & IEEE80211_F_RSNON) &&
1447 	      (ni->ni_rsnprotos & IEEE80211_PROTO_RSN)) ?
1448 		2 + IEEE80211_RSNIE_MAXLEN : 0) +
1449 	    ((ni->ni_flags & IEEE80211_NODE_QOS) ? 2 + 1 : 0) +
1450 	    (((ic->ic_flags & IEEE80211_F_RSNON) &&
1451 	      (ni->ni_rsnprotos & IEEE80211_PROTO_WPA)) ?
1452 		2 + IEEE80211_WPAIE_MAXLEN : 0) +
1453 	    ((ic->ic_flags & IEEE80211_F_HTON) ? 28 + 9 : 0) +
1454 	    ((ic->ic_flags & IEEE80211_F_VHTON) ? 14 : 0));
1455 	if (m == NULL)
1456 		return NULL;
1457 
1458 	frm = mtod(m, u_int8_t *);
1459 	capinfo = IEEE80211_CAPINFO_ESS;
1460 	if (ic->ic_flags & IEEE80211_F_WEPON)
1461 		capinfo |= IEEE80211_CAPINFO_PRIVACY;
1462 	if ((ic->ic_flags & IEEE80211_F_SHPREAMBLE) &&
1463 	    IEEE80211_IS_CHAN_2GHZ(ni->ni_chan))
1464 		capinfo |= IEEE80211_CAPINFO_SHORT_PREAMBLE;
1465 	if (ic->ic_caps & IEEE80211_C_SHSLOT)
1466 		capinfo |= IEEE80211_CAPINFO_SHORT_SLOTTIME;
1467 	LE_WRITE_2(frm, capinfo); frm += 2;
1468 	LE_WRITE_2(frm, ic->ic_lintval); frm += 2;
1469 	if (type == IEEE80211_FC0_SUBTYPE_REASSOC_REQ) {
1470 		IEEE80211_ADDR_COPY(frm, ic->ic_bss->ni_bssid);
1471 		frm += IEEE80211_ADDR_LEN;
1472 	}
1473 	frm = ieee80211_add_ssid(frm, ni->ni_essid, ni->ni_esslen);
1474 	frm = ieee80211_add_rates(frm, rs);
1475 	if (rs->rs_nrates > IEEE80211_RATE_SIZE)
1476 		frm = ieee80211_add_xrates(frm, rs);
1477 	if ((ic->ic_flags & IEEE80211_F_RSNON) &&
1478 	    (ni->ni_rsnprotos & IEEE80211_PROTO_RSN))
1479 		frm = ieee80211_add_rsn(frm, ic, ni);
1480 	if (ni->ni_flags & IEEE80211_NODE_QOS)
1481 		frm = ieee80211_add_qos_capability(frm, ic);
1482 	if ((ic->ic_flags & IEEE80211_F_RSNON) &&
1483 	    (ni->ni_rsnprotos & IEEE80211_PROTO_WPA))
1484 		frm = ieee80211_add_wpa(frm, ic, ni);
1485 	if (ic->ic_flags & IEEE80211_F_HTON) {
1486 		frm = ieee80211_add_htcaps(frm, ic);
1487 		frm = ieee80211_add_wme_info(frm, ic);
1488 	}
1489 	if (ic->ic_flags & IEEE80211_F_VHTON)
1490 		frm = ieee80211_add_vhtcaps(frm, ic);
1491 
1492 	m->m_pkthdr.len = m->m_len = frm - mtod(m, u_int8_t *);
1493 
1494 	return m;
1495 }
1496 
1497 #ifndef IEEE80211_STA_ONLY
1498 /*-
1499  * (Re)Association response frame format:
1500  * [2]   Capability information
1501  * [2]   Status code
1502  * [2]   Association ID (AID)
1503  * [tlv] Supported rates
1504  * [tlv] Extended Supported Rates (802.11g)
1505  * [tlv] EDCA Parameter Set (802.11e)
1506  * [tlv] Timeout Interval (802.11w)
1507  * [tlv] HT Capabilities (802.11n)
1508  * [tlv] HT Operation (802.11n)
1509  */
1510 struct mbuf *
ieee80211_get_assoc_resp(struct ieee80211com * ic,struct ieee80211_node * ni,u_int16_t status)1511 ieee80211_get_assoc_resp(struct ieee80211com *ic, struct ieee80211_node *ni,
1512     u_int16_t status)
1513 {
1514 	const struct ieee80211_rateset *rs = &ni->ni_rates;
1515 	struct mbuf *m;
1516 	u_int8_t *frm;
1517 
1518 	m = ieee80211_getmgmt(M_DONTWAIT, MT_DATA,
1519 	    2 + 2 + 2 +
1520 	    2 + min(rs->rs_nrates, IEEE80211_RATE_SIZE) +
1521 	    ((rs->rs_nrates > IEEE80211_RATE_SIZE) ?
1522 		2 + rs->rs_nrates - IEEE80211_RATE_SIZE : 0) +
1523 	    ((ni->ni_flags & IEEE80211_NODE_QOS) ? 2 + 18 : 0) +
1524 	    ((status == IEEE80211_STATUS_TRY_AGAIN_LATER) ? 2 + 7 : 0) +
1525 	    ((ic->ic_flags & IEEE80211_F_HTON) ? 28 + 24 + 26 : 0));
1526 	if (m == NULL)
1527 		return NULL;
1528 
1529 	frm = mtod(m, u_int8_t *);
1530 	frm = ieee80211_add_capinfo(frm, ic, ni);
1531 	LE_WRITE_2(frm, status); frm += 2;
1532 	if (status == IEEE80211_STATUS_SUCCESS)
1533 		LE_WRITE_2(frm, ni->ni_associd);
1534 	else
1535 		LE_WRITE_2(frm, 0);
1536 	frm += 2;
1537 	frm = ieee80211_add_rates(frm, rs);
1538 	if (rs->rs_nrates > IEEE80211_RATE_SIZE)
1539 		frm = ieee80211_add_xrates(frm, rs);
1540 	if (ni->ni_flags & IEEE80211_NODE_QOS)
1541 		frm = ieee80211_add_edca_params(frm, ic);
1542 	if ((ni->ni_flags & IEEE80211_NODE_MFP) &&
1543 	    status == IEEE80211_STATUS_TRY_AGAIN_LATER) {
1544 		/* Association Comeback Time */
1545 		frm = ieee80211_add_tie(frm, 3, 1000 /* XXX */);
1546 	}
1547 	if (ic->ic_flags & IEEE80211_F_HTON) {
1548 		frm = ieee80211_add_htcaps(frm, ic);
1549 		frm = ieee80211_add_htop(frm, ic);
1550 		frm = ieee80211_add_wme_param(frm, ic);
1551 	}
1552 
1553 	m->m_pkthdr.len = m->m_len = frm - mtod(m, u_int8_t *);
1554 
1555 	return m;
1556 }
1557 #endif	/* IEEE80211_STA_ONLY */
1558 
1559 /*-
1560  * Disassociation frame format:
1561  * [2] Reason code
1562  */
1563 struct mbuf *
ieee80211_get_disassoc(struct ieee80211com * ic,struct ieee80211_node * ni,u_int16_t reason)1564 ieee80211_get_disassoc(struct ieee80211com *ic, struct ieee80211_node *ni,
1565     u_int16_t reason)
1566 {
1567 	struct mbuf *m;
1568 
1569 	MGETHDR(m, M_DONTWAIT, MT_DATA);
1570 	if (m == NULL)
1571 		return NULL;
1572 	m_align(m, 2);
1573 	m->m_pkthdr.len = m->m_len = 2;
1574 
1575 	*mtod(m, u_int16_t *) = htole16(reason);
1576 
1577 	return m;
1578 }
1579 
1580 /*-
1581  * ADDBA Request frame format:
1582  * [1] Category
1583  * [1] Action
1584  * [1] Dialog Token
1585  * [2] Block Ack Parameter Set
1586  * [2] Block Ack Timeout Value
1587  * [2] Block Ack Starting Sequence Control
1588  */
1589 struct mbuf *
ieee80211_get_addba_req(struct ieee80211com * ic,struct ieee80211_node * ni,u_int8_t tid)1590 ieee80211_get_addba_req(struct ieee80211com *ic, struct ieee80211_node *ni,
1591     u_int8_t tid)
1592 {
1593 	struct ieee80211_tx_ba *ba = &ni->ni_tx_ba[tid];
1594 	struct mbuf *m;
1595 	u_int8_t *frm;
1596 
1597 	m = ieee80211_getmgmt(M_DONTWAIT, MT_DATA, 9);
1598 	if (m == NULL)
1599 		return m;
1600 
1601 	frm = mtod(m, u_int8_t *);
1602 	*frm++ = IEEE80211_CATEG_BA;
1603 	*frm++ = IEEE80211_ACTION_ADDBA_REQ;
1604 	*frm++ = ba->ba_token;
1605 	LE_WRITE_2(frm, ba->ba_params); frm += 2;
1606 	LE_WRITE_2(frm, ba->ba_timeout_val / IEEE80211_DUR_TU); frm += 2;
1607 	LE_WRITE_2(frm, ba->ba_winstart << IEEE80211_SEQ_SEQ_SHIFT); frm += 2;
1608 
1609 	m->m_pkthdr.len = m->m_len = frm - mtod(m, u_int8_t *);
1610 
1611 	return m;
1612 }
1613 
1614 /* Move Tx BA window forward to the specified SSN. */
1615 void
ieee80211_output_ba_move_window(struct ieee80211com * ic,struct ieee80211_node * ni,uint8_t tid,uint16_t ssn)1616 ieee80211_output_ba_move_window(struct ieee80211com *ic,
1617     struct ieee80211_node *ni, uint8_t tid, uint16_t ssn)
1618 {
1619 	struct ieee80211_tx_ba *ba = &ni->ni_tx_ba[tid];
1620 	uint16_t s = ba->ba_winstart;
1621 
1622 	while (SEQ_LT(s, ssn) && ba->ba_bitmap) {
1623 		s = (s + 1) % 0xfff;
1624 		ba->ba_bitmap >>= 1;
1625 	}
1626 
1627 	ba->ba_winstart = (ssn & 0xfff);
1628 	ba->ba_winend = (ba->ba_winstart + ba->ba_winsize - 1) & 0xfff;
1629 }
1630 
1631 /*
1632  * Move Tx BA window forward up to the first hole in the bitmap
1633  * or up to the specified SSN, whichever comes first.
1634  * After calling this function, frames before the start of the
1635  * potentially changed BA window should be discarded.
1636  */
1637 void
ieee80211_output_ba_move_window_to_first_unacked(struct ieee80211com * ic,struct ieee80211_node * ni,uint8_t tid,uint16_t ssn)1638 ieee80211_output_ba_move_window_to_first_unacked(struct ieee80211com *ic,
1639     struct ieee80211_node *ni, uint8_t tid, uint16_t ssn)
1640 {
1641 	struct ieee80211_tx_ba *ba = &ni->ni_tx_ba[tid];
1642 	uint16_t s = ba->ba_winstart;
1643 	uint64_t bitmap = ba->ba_bitmap;
1644 	int can_move_window = 0;
1645 
1646 	while (bitmap && SEQ_LT(s, ssn)) {
1647 		if ((bitmap & 1) == 0)
1648 			break;
1649 		s = (s + 1) % 0xfff;
1650 		bitmap >>= 1;
1651 		can_move_window = 1;
1652 	}
1653 
1654 	if (can_move_window)
1655 		ieee80211_output_ba_move_window(ic, ni, tid, s);
1656 }
1657 
1658 /* Record an ACK for a frame with a given SSN within the Tx BA window. */
1659 void
ieee80211_output_ba_record_ack(struct ieee80211com * ic,struct ieee80211_node * ni,uint8_t tid,uint16_t ssn)1660 ieee80211_output_ba_record_ack(struct ieee80211com *ic,
1661     struct ieee80211_node *ni, uint8_t tid, uint16_t ssn)
1662 {
1663 	struct ieee80211_tx_ba *ba = &ni->ni_tx_ba[tid];
1664 	int i = 0;
1665 	uint16_t s = ba->ba_winstart;
1666 
1667 	KASSERT(!SEQ_LT(ssn, ba->ba_winstart));
1668 	KASSERT(!SEQ_LT(ba->ba_winend, ssn));
1669 
1670 	while (SEQ_LT(s, ssn)) {
1671 		s = (s + 1) % 0xfff;
1672 		i++;
1673 	}
1674 	if (i < ba->ba_winsize)
1675 		ba->ba_bitmap |= (1 << i);
1676 }
1677 
1678 /*-
1679  * ADDBA Response frame format:
1680  * [1] Category
1681  * [1] Action
1682  * [1] Dialog Token
1683  * [2] Status Code
1684  * [2] Block Ack Parameter Set
1685  * [2] Block Ack Timeout Value
1686  */
1687 struct mbuf *
ieee80211_get_addba_resp(struct ieee80211com * ic,struct ieee80211_node * ni,u_int8_t tid,u_int8_t token,u_int16_t status)1688 ieee80211_get_addba_resp(struct ieee80211com *ic, struct ieee80211_node *ni,
1689     u_int8_t tid, u_int8_t token, u_int16_t status)
1690 {
1691 	struct ieee80211_rx_ba *ba = &ni->ni_rx_ba[tid];
1692 	struct mbuf *m;
1693 	u_int8_t *frm;
1694 	u_int16_t params;
1695 
1696 	m = ieee80211_getmgmt(M_DONTWAIT, MT_DATA, 9);
1697 	if (m == NULL)
1698 		return m;
1699 
1700 	frm = mtod(m, u_int8_t *);
1701 	*frm++ = IEEE80211_CATEG_BA;
1702 	*frm++ = IEEE80211_ACTION_ADDBA_RESP;
1703 	*frm++ = token;
1704 	LE_WRITE_2(frm, status); frm += 2;
1705 	if (status == 0)
1706 		params = ba->ba_params;
1707 	else
1708 		params = tid << IEEE80211_ADDBA_TID_SHIFT;
1709 	LE_WRITE_2(frm, params); frm += 2;
1710 	if (status == 0)
1711 		LE_WRITE_2(frm, ba->ba_timeout_val / IEEE80211_DUR_TU);
1712 	else
1713 		LE_WRITE_2(frm, 0);
1714 	frm += 2;
1715 
1716 	m->m_pkthdr.len = m->m_len = frm - mtod(m, u_int8_t *);
1717 
1718 	return m;
1719 }
1720 
1721 /*-
1722  * DELBA frame format:
1723  * [1] Category
1724  * [1] Action
1725  * [2] DELBA Parameter Set
1726  * [2] Reason Code
1727  */
1728 struct mbuf *
ieee80211_get_delba(struct ieee80211com * ic,struct ieee80211_node * ni,u_int8_t tid,u_int8_t dir,u_int16_t reason)1729 ieee80211_get_delba(struct ieee80211com *ic, struct ieee80211_node *ni,
1730     u_int8_t tid, u_int8_t dir, u_int16_t reason)
1731 {
1732 	struct mbuf *m;
1733 	u_int8_t *frm;
1734 	u_int16_t params;
1735 
1736 	m = ieee80211_getmgmt(M_DONTWAIT, MT_DATA, 6);
1737 	if (m == NULL)
1738 		return m;
1739 
1740 	frm = mtod(m, u_int8_t *);
1741 	*frm++ = IEEE80211_CATEG_BA;
1742 	*frm++ = IEEE80211_ACTION_DELBA;
1743 	params = tid << 12;
1744 	if (dir)
1745 		params |= IEEE80211_DELBA_INITIATOR;
1746 	LE_WRITE_2(frm, params); frm += 2;
1747 	LE_WRITE_2(frm, reason); frm += 2;
1748 
1749 	m->m_pkthdr.len = m->m_len = frm - mtod(m, u_int8_t *);
1750 
1751 	return m;
1752 }
1753 
1754 /*-
1755  * SA Query Request/Response frame format:
1756  * [1]  Category
1757  * [1]  Action
1758  * [16] Transaction Identifier
1759  */
1760 struct mbuf *
ieee80211_get_sa_query(struct ieee80211com * ic,struct ieee80211_node * ni,u_int8_t action)1761 ieee80211_get_sa_query(struct ieee80211com *ic, struct ieee80211_node *ni,
1762     u_int8_t action)
1763 {
1764 	struct mbuf *m;
1765 	u_int8_t *frm;
1766 
1767 	m = ieee80211_getmgmt(M_DONTWAIT, MT_DATA, 4);
1768 	if (m == NULL)
1769 		return NULL;
1770 
1771 	frm = mtod(m, u_int8_t *);
1772 	*frm++ = IEEE80211_CATEG_SA_QUERY;
1773 	*frm++ = action;	/* ACTION_SA_QUERY_REQ/RESP */
1774 	LE_WRITE_2(frm, ni->ni_sa_query_trid); frm += 2;
1775 
1776 	m->m_pkthdr.len = m->m_len = frm - mtod(m, u_int8_t *);
1777 
1778 	return m;
1779 }
1780 
1781 struct mbuf *
ieee80211_get_action(struct ieee80211com * ic,struct ieee80211_node * ni,u_int8_t categ,u_int8_t action,int arg)1782 ieee80211_get_action(struct ieee80211com *ic, struct ieee80211_node *ni,
1783     u_int8_t categ, u_int8_t action, int arg)
1784 {
1785 	struct mbuf *m = NULL;
1786 
1787 	switch (categ) {
1788 	case IEEE80211_CATEG_BA:
1789 		switch (action) {
1790 		case IEEE80211_ACTION_ADDBA_REQ:
1791 			m = ieee80211_get_addba_req(ic, ni, arg & 0xffff);
1792 			break;
1793 		case IEEE80211_ACTION_ADDBA_RESP:
1794 			m = ieee80211_get_addba_resp(ic, ni, arg & 0xff,
1795 			    arg >> 8, arg >> 16);
1796 			break;
1797 		case IEEE80211_ACTION_DELBA:
1798 			m = ieee80211_get_delba(ic, ni, arg & 0xff, arg >> 8,
1799 			    arg >> 16);
1800 			break;
1801 		}
1802 		break;
1803 	case IEEE80211_CATEG_SA_QUERY:
1804 		switch (action) {
1805 #ifndef IEEE80211_STA_ONLY
1806 		case IEEE80211_ACTION_SA_QUERY_REQ:
1807 #endif
1808 		case IEEE80211_ACTION_SA_QUERY_RESP:
1809 			m = ieee80211_get_sa_query(ic, ni, action);
1810 			break;
1811 		}
1812 		break;
1813 	}
1814 	return m;
1815 }
1816 
1817 /*
1818  * Send a management frame.  The node is for the destination (or ic_bss
1819  * when in station mode).  Nodes other than ic_bss have their reference
1820  * count bumped to reflect our use for an indeterminate time.
1821  */
1822 int
ieee80211_send_mgmt(struct ieee80211com * ic,struct ieee80211_node * ni,int type,int arg1,int arg2)1823 ieee80211_send_mgmt(struct ieee80211com *ic, struct ieee80211_node *ni,
1824     int type, int arg1, int arg2)
1825 {
1826 #define	senderr(_x, _v)	do { ic->ic_stats._v++; ret = _x; goto bad; } while (0)
1827 	struct ifnet *ifp = &ic->ic_if;
1828 	struct mbuf *m;
1829 	int ret, timer;
1830 
1831 	if (ni == NULL)
1832 		panic("null node");
1833 
1834 	/*
1835 	 * Hold a reference on the node so it doesn't go away until after
1836 	 * the xmit is complete all the way in the driver.  On error we
1837 	 * will remove our reference.
1838 	 */
1839 	ieee80211_ref_node(ni);
1840 	timer = 0;
1841 	switch (type) {
1842 	case IEEE80211_FC0_SUBTYPE_PROBE_REQ:
1843 		if ((m = ieee80211_get_probe_req(ic, ni)) == NULL)
1844 			senderr(ENOMEM, is_tx_nombuf);
1845 
1846 		timer = IEEE80211_TRANS_WAIT;
1847 		break;
1848 #ifndef IEEE80211_STA_ONLY
1849 	case IEEE80211_FC0_SUBTYPE_PROBE_RESP:
1850 		if ((m = ieee80211_get_probe_resp(ic)) == NULL)
1851 			senderr(ENOMEM, is_tx_nombuf);
1852 		break;
1853 #endif
1854 	case IEEE80211_FC0_SUBTYPE_AUTH:
1855 		m = ieee80211_get_auth(ic, ni, arg1 >> 16, arg1 & 0xffff);
1856 		if (m == NULL)
1857 			senderr(ENOMEM, is_tx_nombuf);
1858 
1859 		if (ic->ic_opmode == IEEE80211_M_STA)
1860 			timer = IEEE80211_TRANS_WAIT;
1861 		break;
1862 
1863 	case IEEE80211_FC0_SUBTYPE_DEAUTH:
1864 		if ((m = ieee80211_get_deauth(ic, ni, arg1)) == NULL)
1865 			senderr(ENOMEM, is_tx_nombuf);
1866 #ifndef IEEE80211_STA_ONLY
1867 		if ((ifp->if_flags & IFF_DEBUG) &&
1868 		    (ic->ic_opmode == IEEE80211_M_HOSTAP ||
1869 		    ic->ic_opmode == IEEE80211_M_IBSS))
1870 			printf("%s: station %s deauthenticate (reason %d)\n",
1871 			    ifp->if_xname, ether_sprintf(ni->ni_macaddr),
1872 			    arg1);
1873 #endif
1874 		break;
1875 
1876 	case IEEE80211_FC0_SUBTYPE_ASSOC_REQ:
1877 	case IEEE80211_FC0_SUBTYPE_REASSOC_REQ:
1878 		if ((m = ieee80211_get_assoc_req(ic, ni, type)) == NULL)
1879 			senderr(ENOMEM, is_tx_nombuf);
1880 
1881 		timer = IEEE80211_TRANS_WAIT;
1882 		break;
1883 #ifndef IEEE80211_STA_ONLY
1884 	case IEEE80211_FC0_SUBTYPE_ASSOC_RESP:
1885 	case IEEE80211_FC0_SUBTYPE_REASSOC_RESP:
1886 		if ((m = ieee80211_get_assoc_resp(ic, ni, arg1)) == NULL)
1887 			senderr(ENOMEM, is_tx_nombuf);
1888 		break;
1889 #endif
1890 	case IEEE80211_FC0_SUBTYPE_DISASSOC:
1891 		if ((m = ieee80211_get_disassoc(ic, ni, arg1)) == NULL)
1892 			senderr(ENOMEM, is_tx_nombuf);
1893 #ifndef IEEE80211_STA_ONLY
1894 		if ((ifp->if_flags & IFF_DEBUG) &&
1895 		    (ic->ic_opmode == IEEE80211_M_HOSTAP ||
1896 		    ic->ic_opmode == IEEE80211_M_IBSS))
1897 			printf("%s: station %s disassociate (reason %d)\n",
1898 			    ifp->if_xname, ether_sprintf(ni->ni_macaddr),
1899 			    arg1);
1900 #endif
1901 		break;
1902 
1903 	case IEEE80211_FC0_SUBTYPE_ACTION:
1904 		m = ieee80211_get_action(ic, ni, arg1 >> 16, arg1 & 0xffff,
1905 		    arg2);
1906 		if (m == NULL)
1907 			senderr(ENOMEM, is_tx_nombuf);
1908 		break;
1909 
1910 	default:
1911 		DPRINTF(("invalid mgmt frame type %u\n", type));
1912 		senderr(EINVAL, is_tx_unknownmgt);
1913 		/* NOTREACHED */
1914 	}
1915 
1916 	ret = ieee80211_mgmt_output(ifp, ni, m, type);
1917 	if (ret == 0) {
1918 		if (timer)
1919 			ic->ic_mgt_timer = timer;
1920 	} else {
1921 bad:
1922 		ieee80211_release_node(ic, ni);
1923 	}
1924 	return ret;
1925 #undef senderr
1926 }
1927 
1928 /*
1929  * Build a RTS (Request To Send) control frame (see 7.2.1.1).
1930  */
1931 struct mbuf *
ieee80211_get_rts(struct ieee80211com * ic,const struct ieee80211_frame * wh,u_int16_t dur)1932 ieee80211_get_rts(struct ieee80211com *ic, const struct ieee80211_frame *wh,
1933     u_int16_t dur)
1934 {
1935 	struct ieee80211_frame_rts *rts;
1936 	struct mbuf *m;
1937 
1938 	MGETHDR(m, M_DONTWAIT, MT_DATA);
1939 	if (m == NULL)
1940 		return NULL;
1941 
1942 	m->m_pkthdr.len = m->m_len = sizeof(struct ieee80211_frame_rts);
1943 
1944 	rts = mtod(m, struct ieee80211_frame_rts *);
1945 	rts->i_fc[0] = IEEE80211_FC0_VERSION_0 | IEEE80211_FC0_TYPE_CTL |
1946 	    IEEE80211_FC0_SUBTYPE_RTS;
1947 	rts->i_fc[1] = IEEE80211_FC1_DIR_NODS;
1948 	*(u_int16_t *)rts->i_dur = htole16(dur);
1949 	IEEE80211_ADDR_COPY(rts->i_ra, wh->i_addr1);
1950 	IEEE80211_ADDR_COPY(rts->i_ta, wh->i_addr2);
1951 
1952 	return m;
1953 }
1954 
1955 /*
1956  * Build a CTS-to-self (Clear To Send) control frame (see 7.2.1.2).
1957  */
1958 struct mbuf *
ieee80211_get_cts_to_self(struct ieee80211com * ic,u_int16_t dur)1959 ieee80211_get_cts_to_self(struct ieee80211com *ic, u_int16_t dur)
1960 {
1961 	struct ieee80211_frame_cts *cts;
1962 	struct mbuf *m;
1963 
1964 	MGETHDR(m, M_DONTWAIT, MT_DATA);
1965 	if (m == NULL)
1966 		return NULL;
1967 
1968 	m->m_pkthdr.len = m->m_len = sizeof(struct ieee80211_frame_cts);
1969 
1970 	cts = mtod(m, struct ieee80211_frame_cts *);
1971 	cts->i_fc[0] = IEEE80211_FC0_VERSION_0 | IEEE80211_FC0_TYPE_CTL |
1972 	    IEEE80211_FC0_SUBTYPE_CTS;
1973 	cts->i_fc[1] = IEEE80211_FC1_DIR_NODS;
1974 	*(u_int16_t *)cts->i_dur = htole16(dur);
1975 	IEEE80211_ADDR_COPY(cts->i_ra, ic->ic_myaddr);
1976 
1977 	return m;
1978 }
1979 
1980 /*
1981  * Build a compressed Block Ack Request control frame.
1982  */
1983 struct mbuf *
ieee80211_get_compressed_bar(struct ieee80211com * ic,struct ieee80211_node * ni,int tid,uint16_t ssn)1984 ieee80211_get_compressed_bar(struct ieee80211com *ic,
1985     struct ieee80211_node *ni, int tid, uint16_t ssn)
1986 {
1987 	struct ieee80211_frame_min *wh;
1988 	uint8_t *frm;
1989 	uint16_t ctl;
1990 	struct mbuf *m;
1991 
1992 	MGETHDR(m, M_DONTWAIT, MT_DATA);
1993 	if (m == NULL)
1994 		return NULL;
1995 
1996 	m->m_pkthdr.len = m->m_len = sizeof(struct ieee80211_frame_min) +
1997 	    sizeof(ctl) + sizeof(ssn);
1998 
1999 	wh = mtod(m, struct ieee80211_frame_min *);
2000 	wh->i_fc[0] = IEEE80211_FC0_VERSION_0 | IEEE80211_FC0_TYPE_CTL |
2001 	    IEEE80211_FC0_SUBTYPE_BAR;
2002 	wh->i_fc[1] = IEEE80211_FC1_DIR_NODS;
2003 	*(u_int16_t *)wh->i_dur = 0;
2004 	IEEE80211_ADDR_COPY(wh->i_addr1, ni->ni_macaddr);
2005 	IEEE80211_ADDR_COPY(wh->i_addr2, ic->ic_myaddr);
2006 	frm = (uint8_t *)&wh[1];
2007 
2008 	ctl = IEEE80211_BA_COMPRESSED | (tid << IEEE80211_BA_TID_INFO_SHIFT);
2009 	LE_WRITE_2(frm, ctl);
2010 	frm += 2;
2011 
2012 	LE_WRITE_2(frm, ssn << IEEE80211_SEQ_SEQ_SHIFT);
2013 	frm += 2;
2014 
2015 	m->m_pkthdr.len = m->m_len = frm - mtod(m, u_int8_t *);
2016 	m->m_pkthdr.ph_cookie = ni;
2017 
2018 	return m;
2019 }
2020 
2021 #ifndef IEEE80211_STA_ONLY
2022 /*-
2023  * Beacon frame format:
2024  * [8]   Timestamp
2025  * [2]   Beacon interval
2026  * [2]   Capability
2027  * [tlv] Service Set Identifier (SSID)
2028  * [tlv] Supported rates
2029  * [tlv] DS Parameter Set (802.11g)
2030  * [tlv] IBSS Parameter Set
2031  * [tlv] Traffic Indication Map (TIM)
2032  * [tlv] ERP Information (802.11g)
2033  * [tlv] Extended Supported Rates (802.11g)
2034  * [tlv] RSN (802.11i)
2035  * [tlv] EDCA Parameter Set (802.11e)
2036  * [tlv] HT Capabilities (802.11n)
2037  * [tlv] HT Operation (802.11n)
2038  */
2039 struct mbuf *
ieee80211_beacon_alloc(struct ieee80211com * ic,struct ieee80211_node * ni)2040 ieee80211_beacon_alloc(struct ieee80211com *ic, struct ieee80211_node *ni)
2041 {
2042 	const struct ieee80211_rateset *rs = &ni->ni_rates;
2043 	struct ieee80211_frame *wh;
2044 	struct mbuf *m;
2045 	u_int8_t *frm;
2046 
2047 	m = ieee80211_getmgmt(M_DONTWAIT, MT_DATA,
2048 	    8 + 2 + 2 +
2049 	    2 + ((ic->ic_userflags & IEEE80211_F_HIDENWID) ?
2050 	    0 : ni->ni_esslen) +
2051 	    2 + min(rs->rs_nrates, IEEE80211_RATE_SIZE) +
2052 	    2 + 1 +
2053 	    2 + ((ic->ic_opmode == IEEE80211_M_IBSS) ? 2 : 254) +
2054 	    ((ic->ic_curmode == IEEE80211_MODE_11G) ? 2 + 1 : 0) +
2055 	    ((rs->rs_nrates > IEEE80211_RATE_SIZE) ?
2056 		2 + rs->rs_nrates - IEEE80211_RATE_SIZE : 0) +
2057 	    (((ic->ic_flags & IEEE80211_F_RSNON) &&
2058 	      (ni->ni_rsnprotos & IEEE80211_PROTO_RSN)) ?
2059 		2 + IEEE80211_RSNIE_MAXLEN : 0) +
2060 	    ((ic->ic_flags & IEEE80211_F_QOS) ? 2 + 18 : 0) +
2061 	    (((ic->ic_flags & IEEE80211_F_RSNON) &&
2062 	      (ni->ni_rsnprotos & IEEE80211_PROTO_WPA)) ?
2063 		2 + IEEE80211_WPAIE_MAXLEN : 0) +
2064 	    ((ic->ic_flags & IEEE80211_F_HTON) ? 28 + 24 + 26 : 0));
2065 	if (m == NULL)
2066 		return NULL;
2067 
2068 	M_PREPEND(m, sizeof(struct ieee80211_frame), M_DONTWAIT);
2069 	if (m == NULL)
2070 		return NULL;
2071 	wh = mtod(m, struct ieee80211_frame *);
2072 	wh->i_fc[0] = IEEE80211_FC0_VERSION_0 | IEEE80211_FC0_TYPE_MGT |
2073 	    IEEE80211_FC0_SUBTYPE_BEACON;
2074 	wh->i_fc[1] = IEEE80211_FC1_DIR_NODS;
2075 	*(u_int16_t *)wh->i_dur = 0;
2076 	IEEE80211_ADDR_COPY(wh->i_addr1, etherbroadcastaddr);
2077 	IEEE80211_ADDR_COPY(wh->i_addr2, ic->ic_myaddr);
2078 	IEEE80211_ADDR_COPY(wh->i_addr3, ni->ni_bssid);
2079 	*(u_int16_t *)wh->i_seq = 0;
2080 
2081 	frm = (u_int8_t *)&wh[1];
2082 	memset(frm, 0, 8); frm += 8;	/* timestamp is set by hardware */
2083 	LE_WRITE_2(frm, ni->ni_intval); frm += 2;
2084 	frm = ieee80211_add_capinfo(frm, ic, ni);
2085 	if (ic->ic_userflags & IEEE80211_F_HIDENWID)
2086 		frm = ieee80211_add_ssid(frm, NULL, 0);
2087 	else
2088 		frm = ieee80211_add_ssid(frm, ni->ni_essid, ni->ni_esslen);
2089 	frm = ieee80211_add_rates(frm, rs);
2090 	frm = ieee80211_add_ds_params(frm, ic, ni);
2091 	if (ic->ic_opmode == IEEE80211_M_IBSS)
2092 		frm = ieee80211_add_ibss_params(frm, ni);
2093 	else
2094 		frm = ieee80211_add_tim(frm, ic);
2095 	if (ic->ic_curmode == IEEE80211_MODE_11G)
2096 		frm = ieee80211_add_erp(frm, ic);
2097 	if (rs->rs_nrates > IEEE80211_RATE_SIZE)
2098 		frm = ieee80211_add_xrates(frm, rs);
2099 	if ((ic->ic_flags & IEEE80211_F_RSNON) &&
2100 	    (ni->ni_rsnprotos & IEEE80211_PROTO_RSN))
2101 		frm = ieee80211_add_rsn(frm, ic, ni);
2102 	if (ic->ic_flags & IEEE80211_F_QOS)
2103 		frm = ieee80211_add_edca_params(frm, ic);
2104 	if ((ic->ic_flags & IEEE80211_F_RSNON) &&
2105 	    (ni->ni_rsnprotos & IEEE80211_PROTO_WPA))
2106 		frm = ieee80211_add_wpa(frm, ic, ni);
2107 	if (ic->ic_flags & IEEE80211_F_HTON) {
2108 		frm = ieee80211_add_htcaps(frm, ic);
2109 		frm = ieee80211_add_htop(frm, ic);
2110 		frm = ieee80211_add_wme_param(frm, ic);
2111 	}
2112 
2113 	m->m_pkthdr.len = m->m_len = frm - mtod(m, u_int8_t *);
2114 	m->m_pkthdr.ph_cookie = ni;
2115 
2116 	return m;
2117 }
2118 
2119 /*
2120  * Check if an outgoing MSDU or management frame should be buffered into
2121  * the AP for power management.  Return 1 if the frame was buffered into
2122  * the AP, or 0 if the frame shall be transmitted immediately.
2123  */
2124 int
ieee80211_pwrsave(struct ieee80211com * ic,struct mbuf * m,struct ieee80211_node * ni)2125 ieee80211_pwrsave(struct ieee80211com *ic, struct mbuf *m,
2126     struct ieee80211_node *ni)
2127 {
2128 	const struct ieee80211_frame *wh;
2129 	int pssta = 0;
2130 
2131 	KASSERT(ic->ic_opmode == IEEE80211_M_HOSTAP);
2132 	if (!(ic->ic_caps & IEEE80211_C_APPMGT))
2133 		return 0;
2134 
2135 	wh = mtod(m, struct ieee80211_frame *);
2136 	if (IEEE80211_IS_MULTICAST(wh->i_addr1)) {
2137 		/*
2138 		 * Buffer group addressed MSDUs with the Order bit clear
2139 		 * if any associated STAs are in PS mode.
2140 		 */
2141 		ieee80211_iterate_nodes(ic, ieee80211_count_pssta, &pssta);
2142 		if ((wh->i_fc[1] & IEEE80211_FC1_ORDER) || pssta == 0)
2143 			return 0;
2144 		ic->ic_tim_mcast_pending = 1;
2145 	} else {
2146 		/*
2147 		 * Buffer MSDUs, A-MSDUs or management frames destined for
2148 		 * PS STAs.
2149 		 */
2150 		if (ni->ni_pwrsave == IEEE80211_PS_AWAKE ||
2151 		    (wh->i_fc[0] & IEEE80211_FC0_TYPE_MASK) ==
2152 		    IEEE80211_FC0_TYPE_CTL)
2153 			return 0;
2154 		if (mq_empty(&ni->ni_savedq))
2155 			(*ic->ic_set_tim)(ic, ni->ni_associd, 1);
2156 	}
2157 	/* NB: ni == ic->ic_bss for broadcast/multicast */
2158 	/*
2159 	 * Similar to ieee80211_mgmt_output, store the node in a
2160 	 * special pkthdr field.
2161 	 */
2162 	m->m_pkthdr.ph_cookie = ni;
2163 	mq_enqueue(&ni->ni_savedq, m);
2164 	return 1;
2165 }
2166 #endif	/* IEEE80211_STA_ONLY */
2167