xref: /freebsd/sys/dev/mwl/if_mwl.c (revision 0957b409)
1 /*-
2  * SPDX-License-Identifier: BSD-2-Clause-FreeBSD
3  *
4  * Copyright (c) 2007-2009 Sam Leffler, Errno Consulting
5  * Copyright (c) 2007-2008 Marvell Semiconductor, Inc.
6  * All rights reserved.
7  *
8  * Redistribution and use in source and binary forms, with or without
9  * modification, are permitted provided that the following conditions
10  * are met:
11  * 1. Redistributions of source code must retain the above copyright
12  *    notice, this list of conditions and the following disclaimer,
13  *    without modification.
14  * 2. Redistributions in binary form must reproduce at minimum a disclaimer
15  *    similar to the "NO WARRANTY" disclaimer below ("Disclaimer") and any
16  *    redistribution must be conditioned upon including a substantially
17  *    similar Disclaimer requirement for further binary redistribution.
18  *
19  * NO WARRANTY
20  * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
21  * ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
22  * LIMITED TO, THE IMPLIED WARRANTIES OF NONINFRINGEMENT, MERCHANTIBILITY
23  * AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL
24  * THE COPYRIGHT HOLDERS OR CONTRIBUTORS BE LIABLE FOR SPECIAL, EXEMPLARY,
25  * OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
26  * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
27  * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER
28  * IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
29  * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
30  * THE POSSIBILITY OF SUCH DAMAGES.
31  */
32 
33 #include <sys/cdefs.h>
34 __FBSDID("$FreeBSD$");
35 
36 /*
37  * Driver for the Marvell 88W8363 Wireless LAN controller.
38  */
39 
40 #include "opt_inet.h"
41 #include "opt_mwl.h"
42 #include "opt_wlan.h"
43 
44 #include <sys/param.h>
45 #include <sys/systm.h>
46 #include <sys/sysctl.h>
47 #include <sys/mbuf.h>
48 #include <sys/malloc.h>
49 #include <sys/lock.h>
50 #include <sys/mutex.h>
51 #include <sys/kernel.h>
52 #include <sys/socket.h>
53 #include <sys/sockio.h>
54 #include <sys/errno.h>
55 #include <sys/callout.h>
56 #include <sys/bus.h>
57 #include <sys/endian.h>
58 #include <sys/kthread.h>
59 #include <sys/taskqueue.h>
60 
61 #include <machine/bus.h>
62 
63 #include <net/if.h>
64 #include <net/if_var.h>
65 #include <net/if_dl.h>
66 #include <net/if_media.h>
67 #include <net/if_types.h>
68 #include <net/if_arp.h>
69 #include <net/ethernet.h>
70 #include <net/if_llc.h>
71 
72 #include <net/bpf.h>
73 
74 #include <net80211/ieee80211_var.h>
75 #include <net80211/ieee80211_input.h>
76 #include <net80211/ieee80211_regdomain.h>
77 
78 #ifdef INET
79 #include <netinet/in.h>
80 #include <netinet/if_ether.h>
81 #endif /* INET */
82 
83 #include <dev/mwl/if_mwlvar.h>
84 #include <dev/mwl/mwldiag.h>
85 
86 /* idiomatic shorthands: MS = mask+shift, SM = shift+mask */
87 #define	MS(v,x)	(((v) & x) >> x##_S)
88 #define	SM(v,x)	(((v) << x##_S) & x)
89 
90 static struct ieee80211vap *mwl_vap_create(struct ieee80211com *,
91 		    const char [IFNAMSIZ], int, enum ieee80211_opmode, int,
92 		    const uint8_t [IEEE80211_ADDR_LEN],
93 		    const uint8_t [IEEE80211_ADDR_LEN]);
94 static void	mwl_vap_delete(struct ieee80211vap *);
95 static int	mwl_setupdma(struct mwl_softc *);
96 static int	mwl_hal_reset(struct mwl_softc *sc);
97 static int	mwl_init(struct mwl_softc *);
98 static void	mwl_parent(struct ieee80211com *);
99 static int	mwl_reset(struct ieee80211vap *, u_long);
100 static void	mwl_stop(struct mwl_softc *);
101 static void	mwl_start(struct mwl_softc *);
102 static int	mwl_transmit(struct ieee80211com *, struct mbuf *);
103 static int	mwl_raw_xmit(struct ieee80211_node *, struct mbuf *,
104 			const struct ieee80211_bpf_params *);
105 static int	mwl_media_change(struct ifnet *);
106 static void	mwl_watchdog(void *);
107 static int	mwl_ioctl(struct ieee80211com *, u_long, void *);
108 static void	mwl_radar_proc(void *, int);
109 static void	mwl_chanswitch_proc(void *, int);
110 static void	mwl_bawatchdog_proc(void *, int);
111 static int	mwl_key_alloc(struct ieee80211vap *,
112 			struct ieee80211_key *,
113 			ieee80211_keyix *, ieee80211_keyix *);
114 static int	mwl_key_delete(struct ieee80211vap *,
115 			const struct ieee80211_key *);
116 static int	mwl_key_set(struct ieee80211vap *,
117 			const struct ieee80211_key *);
118 static int	_mwl_key_set(struct ieee80211vap *,
119 			const struct ieee80211_key *,
120 			const uint8_t mac[IEEE80211_ADDR_LEN]);
121 static int	mwl_mode_init(struct mwl_softc *);
122 static void	mwl_update_mcast(struct ieee80211com *);
123 static void	mwl_update_promisc(struct ieee80211com *);
124 static void	mwl_updateslot(struct ieee80211com *);
125 static int	mwl_beacon_setup(struct ieee80211vap *);
126 static void	mwl_beacon_update(struct ieee80211vap *, int);
127 #ifdef MWL_HOST_PS_SUPPORT
128 static void	mwl_update_ps(struct ieee80211vap *, int);
129 static int	mwl_set_tim(struct ieee80211_node *, int);
130 #endif
131 static int	mwl_dma_setup(struct mwl_softc *);
132 static void	mwl_dma_cleanup(struct mwl_softc *);
133 static struct ieee80211_node *mwl_node_alloc(struct ieee80211vap *,
134 		    const uint8_t [IEEE80211_ADDR_LEN]);
135 static void	mwl_node_cleanup(struct ieee80211_node *);
136 static void	mwl_node_drain(struct ieee80211_node *);
137 static void	mwl_node_getsignal(const struct ieee80211_node *,
138 			int8_t *, int8_t *);
139 static void	mwl_node_getmimoinfo(const struct ieee80211_node *,
140 			struct ieee80211_mimo_info *);
141 static int	mwl_rxbuf_init(struct mwl_softc *, struct mwl_rxbuf *);
142 static void	mwl_rx_proc(void *, int);
143 static void	mwl_txq_init(struct mwl_softc *sc, struct mwl_txq *, int);
144 static int	mwl_tx_setup(struct mwl_softc *, int, int);
145 static int	mwl_wme_update(struct ieee80211com *);
146 static void	mwl_tx_cleanupq(struct mwl_softc *, struct mwl_txq *);
147 static void	mwl_tx_cleanup(struct mwl_softc *);
148 static uint16_t	mwl_calcformat(uint8_t rate, const struct ieee80211_node *);
149 static int	mwl_tx_start(struct mwl_softc *, struct ieee80211_node *,
150 			     struct mwl_txbuf *, struct mbuf *);
151 static void	mwl_tx_proc(void *, int);
152 static int	mwl_chan_set(struct mwl_softc *, struct ieee80211_channel *);
153 static void	mwl_draintxq(struct mwl_softc *);
154 static void	mwl_cleartxq(struct mwl_softc *, struct ieee80211vap *);
155 static int	mwl_recv_action(struct ieee80211_node *,
156 			const struct ieee80211_frame *,
157 			const uint8_t *, const uint8_t *);
158 static int	mwl_addba_request(struct ieee80211_node *,
159 			struct ieee80211_tx_ampdu *, int dialogtoken,
160 			int baparamset, int batimeout);
161 static int	mwl_addba_response(struct ieee80211_node *,
162 			struct ieee80211_tx_ampdu *, int status,
163 			int baparamset, int batimeout);
164 static void	mwl_addba_stop(struct ieee80211_node *,
165 			struct ieee80211_tx_ampdu *);
166 static int	mwl_startrecv(struct mwl_softc *);
167 static MWL_HAL_APMODE mwl_getapmode(const struct ieee80211vap *,
168 			struct ieee80211_channel *);
169 static int	mwl_setapmode(struct ieee80211vap *, struct ieee80211_channel*);
170 static void	mwl_scan_start(struct ieee80211com *);
171 static void	mwl_scan_end(struct ieee80211com *);
172 static void	mwl_set_channel(struct ieee80211com *);
173 static int	mwl_peerstadb(struct ieee80211_node *,
174 			int aid, int staid, MWL_HAL_PEERINFO *pi);
175 static int	mwl_localstadb(struct ieee80211vap *);
176 static int	mwl_newstate(struct ieee80211vap *, enum ieee80211_state, int);
177 static int	allocstaid(struct mwl_softc *sc, int aid);
178 static void	delstaid(struct mwl_softc *sc, int staid);
179 static void	mwl_newassoc(struct ieee80211_node *, int);
180 static void	mwl_agestations(void *);
181 static int	mwl_setregdomain(struct ieee80211com *,
182 			struct ieee80211_regdomain *, int,
183 			struct ieee80211_channel []);
184 static void	mwl_getradiocaps(struct ieee80211com *, int, int *,
185 			struct ieee80211_channel []);
186 static int	mwl_getchannels(struct mwl_softc *);
187 
188 static void	mwl_sysctlattach(struct mwl_softc *);
189 static void	mwl_announce(struct mwl_softc *);
190 
191 SYSCTL_NODE(_hw, OID_AUTO, mwl, CTLFLAG_RD, 0, "Marvell driver parameters");
192 
193 static	int mwl_rxdesc = MWL_RXDESC;		/* # rx desc's to allocate */
194 SYSCTL_INT(_hw_mwl, OID_AUTO, rxdesc, CTLFLAG_RW, &mwl_rxdesc,
195 	    0, "rx descriptors allocated");
196 static	int mwl_rxbuf = MWL_RXBUF;		/* # rx buffers to allocate */
197 SYSCTL_INT(_hw_mwl, OID_AUTO, rxbuf, CTLFLAG_RWTUN, &mwl_rxbuf,
198 	    0, "rx buffers allocated");
199 static	int mwl_txbuf = MWL_TXBUF;		/* # tx buffers to allocate */
200 SYSCTL_INT(_hw_mwl, OID_AUTO, txbuf, CTLFLAG_RWTUN, &mwl_txbuf,
201 	    0, "tx buffers allocated");
202 static	int mwl_txcoalesce = 8;		/* # tx packets to q before poking f/w*/
203 SYSCTL_INT(_hw_mwl, OID_AUTO, txcoalesce, CTLFLAG_RWTUN, &mwl_txcoalesce,
204 	    0, "tx buffers to send at once");
205 static	int mwl_rxquota = MWL_RXBUF;		/* # max buffers to process */
206 SYSCTL_INT(_hw_mwl, OID_AUTO, rxquota, CTLFLAG_RWTUN, &mwl_rxquota,
207 	    0, "max rx buffers to process per interrupt");
208 static	int mwl_rxdmalow = 3;			/* # min buffers for wakeup */
209 SYSCTL_INT(_hw_mwl, OID_AUTO, rxdmalow, CTLFLAG_RWTUN, &mwl_rxdmalow,
210 	    0, "min free rx buffers before restarting traffic");
211 
212 #ifdef MWL_DEBUG
213 static	int mwl_debug = 0;
214 SYSCTL_INT(_hw_mwl, OID_AUTO, debug, CTLFLAG_RWTUN, &mwl_debug,
215 	    0, "control debugging printfs");
216 enum {
217 	MWL_DEBUG_XMIT		= 0x00000001,	/* basic xmit operation */
218 	MWL_DEBUG_XMIT_DESC	= 0x00000002,	/* xmit descriptors */
219 	MWL_DEBUG_RECV		= 0x00000004,	/* basic recv operation */
220 	MWL_DEBUG_RECV_DESC	= 0x00000008,	/* recv descriptors */
221 	MWL_DEBUG_RESET		= 0x00000010,	/* reset processing */
222 	MWL_DEBUG_BEACON 	= 0x00000020,	/* beacon handling */
223 	MWL_DEBUG_INTR		= 0x00000040,	/* ISR */
224 	MWL_DEBUG_TX_PROC	= 0x00000080,	/* tx ISR proc */
225 	MWL_DEBUG_RX_PROC	= 0x00000100,	/* rx ISR proc */
226 	MWL_DEBUG_KEYCACHE	= 0x00000200,	/* key cache management */
227 	MWL_DEBUG_STATE		= 0x00000400,	/* 802.11 state transitions */
228 	MWL_DEBUG_NODE		= 0x00000800,	/* node management */
229 	MWL_DEBUG_RECV_ALL	= 0x00001000,	/* trace all frames (beacons) */
230 	MWL_DEBUG_TSO		= 0x00002000,	/* TSO processing */
231 	MWL_DEBUG_AMPDU		= 0x00004000,	/* BA stream handling */
232 	MWL_DEBUG_ANY		= 0xffffffff
233 };
234 #define	IS_BEACON(wh) \
235     ((wh->i_fc[0] & (IEEE80211_FC0_TYPE_MASK|IEEE80211_FC0_SUBTYPE_MASK)) == \
236 	 (IEEE80211_FC0_TYPE_MGT|IEEE80211_FC0_SUBTYPE_BEACON))
237 #define	IFF_DUMPPKTS_RECV(sc, wh) \
238     ((sc->sc_debug & MWL_DEBUG_RECV) && \
239       ((sc->sc_debug & MWL_DEBUG_RECV_ALL) || !IS_BEACON(wh)))
240 #define	IFF_DUMPPKTS_XMIT(sc) \
241 	(sc->sc_debug & MWL_DEBUG_XMIT)
242 
243 #define	DPRINTF(sc, m, fmt, ...) do {				\
244 	if (sc->sc_debug & (m))					\
245 		printf(fmt, __VA_ARGS__);			\
246 } while (0)
247 #define	KEYPRINTF(sc, hk, mac) do {				\
248 	if (sc->sc_debug & MWL_DEBUG_KEYCACHE)			\
249 		mwl_keyprint(sc, __func__, hk, mac);		\
250 } while (0)
251 static	void mwl_printrxbuf(const struct mwl_rxbuf *bf, u_int ix);
252 static	void mwl_printtxbuf(const struct mwl_txbuf *bf, u_int qnum, u_int ix);
253 #else
254 #define	IFF_DUMPPKTS_RECV(sc, wh)	0
255 #define	IFF_DUMPPKTS_XMIT(sc)		0
256 #define	DPRINTF(sc, m, fmt, ...)	do { (void )sc; } while (0)
257 #define	KEYPRINTF(sc, k, mac)		do { (void )sc; } while (0)
258 #endif
259 
260 static MALLOC_DEFINE(M_MWLDEV, "mwldev", "mwl driver dma buffers");
261 
262 /*
263  * Each packet has fixed front matter: a 2-byte length
264  * of the payload, followed by a 4-address 802.11 header
265  * (regardless of the actual header and always w/o any
266  * QoS header).  The payload then follows.
267  */
268 struct mwltxrec {
269 	uint16_t fwlen;
270 	struct ieee80211_frame_addr4 wh;
271 } __packed;
272 
273 /*
274  * Read/Write shorthands for accesses to BAR 0.  Note
275  * that all BAR 1 operations are done in the "hal" and
276  * there should be no reference to them here.
277  */
278 #ifdef MWL_DEBUG
279 static __inline uint32_t
280 RD4(struct mwl_softc *sc, bus_size_t off)
281 {
282 	return bus_space_read_4(sc->sc_io0t, sc->sc_io0h, off);
283 }
284 #endif
285 
286 static __inline void
287 WR4(struct mwl_softc *sc, bus_size_t off, uint32_t val)
288 {
289 	bus_space_write_4(sc->sc_io0t, sc->sc_io0h, off, val);
290 }
291 
292 int
293 mwl_attach(uint16_t devid, struct mwl_softc *sc)
294 {
295 	struct ieee80211com *ic = &sc->sc_ic;
296 	struct mwl_hal *mh;
297 	int error = 0;
298 
299 	DPRINTF(sc, MWL_DEBUG_ANY, "%s: devid 0x%x\n", __func__, devid);
300 
301 	/*
302 	 * Setup the RX free list lock early, so it can be consistently
303 	 * removed.
304 	 */
305 	MWL_RXFREE_INIT(sc);
306 
307 	mh = mwl_hal_attach(sc->sc_dev, devid,
308 	    sc->sc_io1h, sc->sc_io1t, sc->sc_dmat);
309 	if (mh == NULL) {
310 		device_printf(sc->sc_dev, "unable to attach HAL\n");
311 		error = EIO;
312 		goto bad;
313 	}
314 	sc->sc_mh = mh;
315 	/*
316 	 * Load firmware so we can get setup.  We arbitrarily
317 	 * pick station firmware; we'll re-load firmware as
318 	 * needed so setting up the wrong mode isn't a big deal.
319 	 */
320 	if (mwl_hal_fwload(mh, NULL) != 0) {
321 		device_printf(sc->sc_dev, "unable to setup builtin firmware\n");
322 		error = EIO;
323 		goto bad1;
324 	}
325 	if (mwl_hal_gethwspecs(mh, &sc->sc_hwspecs) != 0) {
326 		device_printf(sc->sc_dev, "unable to fetch h/w specs\n");
327 		error = EIO;
328 		goto bad1;
329 	}
330 	error = mwl_getchannels(sc);
331 	if (error != 0)
332 		goto bad1;
333 
334 	sc->sc_txantenna = 0;		/* h/w default */
335 	sc->sc_rxantenna = 0;		/* h/w default */
336 	sc->sc_invalid = 0;		/* ready to go, enable int handling */
337 	sc->sc_ageinterval = MWL_AGEINTERVAL;
338 
339 	/*
340 	 * Allocate tx+rx descriptors and populate the lists.
341 	 * We immediately push the information to the firmware
342 	 * as otherwise it gets upset.
343 	 */
344 	error = mwl_dma_setup(sc);
345 	if (error != 0) {
346 		device_printf(sc->sc_dev, "failed to setup descriptors: %d\n",
347 		    error);
348 		goto bad1;
349 	}
350 	error = mwl_setupdma(sc);	/* push to firmware */
351 	if (error != 0)			/* NB: mwl_setupdma prints msg */
352 		goto bad1;
353 
354 	callout_init(&sc->sc_timer, 1);
355 	callout_init_mtx(&sc->sc_watchdog, &sc->sc_mtx, 0);
356 	mbufq_init(&sc->sc_snd, ifqmaxlen);
357 
358 	sc->sc_tq = taskqueue_create("mwl_taskq", M_NOWAIT,
359 		taskqueue_thread_enqueue, &sc->sc_tq);
360 	taskqueue_start_threads(&sc->sc_tq, 1, PI_NET,
361 		"%s taskq", device_get_nameunit(sc->sc_dev));
362 
363 	TASK_INIT(&sc->sc_rxtask, 0, mwl_rx_proc, sc);
364 	TASK_INIT(&sc->sc_radartask, 0, mwl_radar_proc, sc);
365 	TASK_INIT(&sc->sc_chanswitchtask, 0, mwl_chanswitch_proc, sc);
366 	TASK_INIT(&sc->sc_bawatchdogtask, 0, mwl_bawatchdog_proc, sc);
367 
368 	/* NB: insure BK queue is the lowest priority h/w queue */
369 	if (!mwl_tx_setup(sc, WME_AC_BK, MWL_WME_AC_BK)) {
370 		device_printf(sc->sc_dev,
371 		    "unable to setup xmit queue for %s traffic!\n",
372 		     ieee80211_wme_acnames[WME_AC_BK]);
373 		error = EIO;
374 		goto bad2;
375 	}
376 	if (!mwl_tx_setup(sc, WME_AC_BE, MWL_WME_AC_BE) ||
377 	    !mwl_tx_setup(sc, WME_AC_VI, MWL_WME_AC_VI) ||
378 	    !mwl_tx_setup(sc, WME_AC_VO, MWL_WME_AC_VO)) {
379 		/*
380 		 * Not enough hardware tx queues to properly do WME;
381 		 * just punt and assign them all to the same h/w queue.
382 		 * We could do a better job of this if, for example,
383 		 * we allocate queues when we switch from station to
384 		 * AP mode.
385 		 */
386 		if (sc->sc_ac2q[WME_AC_VI] != NULL)
387 			mwl_tx_cleanupq(sc, sc->sc_ac2q[WME_AC_VI]);
388 		if (sc->sc_ac2q[WME_AC_BE] != NULL)
389 			mwl_tx_cleanupq(sc, sc->sc_ac2q[WME_AC_BE]);
390 		sc->sc_ac2q[WME_AC_BE] = sc->sc_ac2q[WME_AC_BK];
391 		sc->sc_ac2q[WME_AC_VI] = sc->sc_ac2q[WME_AC_BK];
392 		sc->sc_ac2q[WME_AC_VO] = sc->sc_ac2q[WME_AC_BK];
393 	}
394 	TASK_INIT(&sc->sc_txtask, 0, mwl_tx_proc, sc);
395 
396 	ic->ic_softc = sc;
397 	ic->ic_name = device_get_nameunit(sc->sc_dev);
398 	/* XXX not right but it's not used anywhere important */
399 	ic->ic_phytype = IEEE80211_T_OFDM;
400 	ic->ic_opmode = IEEE80211_M_STA;
401 	ic->ic_caps =
402 		  IEEE80211_C_STA		/* station mode supported */
403 		| IEEE80211_C_HOSTAP		/* hostap mode */
404 		| IEEE80211_C_MONITOR		/* monitor mode */
405 #if 0
406 		| IEEE80211_C_IBSS		/* ibss, nee adhoc, mode */
407 		| IEEE80211_C_AHDEMO		/* adhoc demo mode */
408 #endif
409 		| IEEE80211_C_MBSS		/* mesh point link mode */
410 		| IEEE80211_C_WDS		/* WDS supported */
411 		| IEEE80211_C_SHPREAMBLE	/* short preamble supported */
412 		| IEEE80211_C_SHSLOT		/* short slot time supported */
413 		| IEEE80211_C_WME		/* WME/WMM supported */
414 		| IEEE80211_C_BURST		/* xmit bursting supported */
415 		| IEEE80211_C_WPA		/* capable of WPA1+WPA2 */
416 		| IEEE80211_C_BGSCAN		/* capable of bg scanning */
417 		| IEEE80211_C_TXFRAG		/* handle tx frags */
418 		| IEEE80211_C_TXPMGT		/* capable of txpow mgt */
419 		| IEEE80211_C_DFS		/* DFS supported */
420 		;
421 
422 	ic->ic_htcaps =
423 		  IEEE80211_HTCAP_SMPS_ENA	/* SM PS mode enabled */
424 		| IEEE80211_HTCAP_CHWIDTH40	/* 40MHz channel width */
425 		| IEEE80211_HTCAP_SHORTGI20	/* short GI in 20MHz */
426 		| IEEE80211_HTCAP_SHORTGI40	/* short GI in 40MHz */
427 		| IEEE80211_HTCAP_RXSTBC_2STREAM/* 1-2 spatial streams */
428 #if MWL_AGGR_SIZE == 7935
429 		| IEEE80211_HTCAP_MAXAMSDU_7935	/* max A-MSDU length */
430 #else
431 		| IEEE80211_HTCAP_MAXAMSDU_3839	/* max A-MSDU length */
432 #endif
433 #if 0
434 		| IEEE80211_HTCAP_PSMP		/* PSMP supported */
435 		| IEEE80211_HTCAP_40INTOLERANT	/* 40MHz intolerant */
436 #endif
437 		/* s/w capabilities */
438 		| IEEE80211_HTC_HT		/* HT operation */
439 		| IEEE80211_HTC_AMPDU		/* tx A-MPDU */
440 		| IEEE80211_HTC_AMSDU		/* tx A-MSDU */
441 		| IEEE80211_HTC_SMPS		/* SMPS available */
442 		;
443 
444 	/*
445 	 * Mark h/w crypto support.
446 	 * XXX no way to query h/w support.
447 	 */
448 	ic->ic_cryptocaps |= IEEE80211_CRYPTO_WEP
449 			  |  IEEE80211_CRYPTO_AES_CCM
450 			  |  IEEE80211_CRYPTO_TKIP
451 			  |  IEEE80211_CRYPTO_TKIPMIC
452 			  ;
453 	/*
454 	 * Transmit requires space in the packet for a special
455 	 * format transmit record and optional padding between
456 	 * this record and the payload.  Ask the net80211 layer
457 	 * to arrange this when encapsulating packets so we can
458 	 * add it efficiently.
459 	 */
460 	ic->ic_headroom = sizeof(struct mwltxrec) -
461 		sizeof(struct ieee80211_frame);
462 
463 	IEEE80211_ADDR_COPY(ic->ic_macaddr, sc->sc_hwspecs.macAddr);
464 
465 	/* call MI attach routine. */
466 	ieee80211_ifattach(ic);
467 	ic->ic_setregdomain = mwl_setregdomain;
468 	ic->ic_getradiocaps = mwl_getradiocaps;
469 	/* override default methods */
470 	ic->ic_raw_xmit = mwl_raw_xmit;
471 	ic->ic_newassoc = mwl_newassoc;
472 	ic->ic_updateslot = mwl_updateslot;
473 	ic->ic_update_mcast = mwl_update_mcast;
474 	ic->ic_update_promisc = mwl_update_promisc;
475 	ic->ic_wme.wme_update = mwl_wme_update;
476 	ic->ic_transmit = mwl_transmit;
477 	ic->ic_ioctl = mwl_ioctl;
478 	ic->ic_parent = mwl_parent;
479 
480 	ic->ic_node_alloc = mwl_node_alloc;
481 	sc->sc_node_cleanup = ic->ic_node_cleanup;
482 	ic->ic_node_cleanup = mwl_node_cleanup;
483 	sc->sc_node_drain = ic->ic_node_drain;
484 	ic->ic_node_drain = mwl_node_drain;
485 	ic->ic_node_getsignal = mwl_node_getsignal;
486 	ic->ic_node_getmimoinfo = mwl_node_getmimoinfo;
487 
488 	ic->ic_scan_start = mwl_scan_start;
489 	ic->ic_scan_end = mwl_scan_end;
490 	ic->ic_set_channel = mwl_set_channel;
491 
492 	sc->sc_recv_action = ic->ic_recv_action;
493 	ic->ic_recv_action = mwl_recv_action;
494 	sc->sc_addba_request = ic->ic_addba_request;
495 	ic->ic_addba_request = mwl_addba_request;
496 	sc->sc_addba_response = ic->ic_addba_response;
497 	ic->ic_addba_response = mwl_addba_response;
498 	sc->sc_addba_stop = ic->ic_addba_stop;
499 	ic->ic_addba_stop = mwl_addba_stop;
500 
501 	ic->ic_vap_create = mwl_vap_create;
502 	ic->ic_vap_delete = mwl_vap_delete;
503 
504 	ieee80211_radiotap_attach(ic,
505 	    &sc->sc_tx_th.wt_ihdr, sizeof(sc->sc_tx_th),
506 		MWL_TX_RADIOTAP_PRESENT,
507 	    &sc->sc_rx_th.wr_ihdr, sizeof(sc->sc_rx_th),
508 		MWL_RX_RADIOTAP_PRESENT);
509 	/*
510 	 * Setup dynamic sysctl's now that country code and
511 	 * regdomain are available from the hal.
512 	 */
513 	mwl_sysctlattach(sc);
514 
515 	if (bootverbose)
516 		ieee80211_announce(ic);
517 	mwl_announce(sc);
518 	return 0;
519 bad2:
520 	mwl_dma_cleanup(sc);
521 bad1:
522 	mwl_hal_detach(mh);
523 bad:
524 	MWL_RXFREE_DESTROY(sc);
525 	sc->sc_invalid = 1;
526 	return error;
527 }
528 
529 int
530 mwl_detach(struct mwl_softc *sc)
531 {
532 	struct ieee80211com *ic = &sc->sc_ic;
533 
534 	MWL_LOCK(sc);
535 	mwl_stop(sc);
536 	MWL_UNLOCK(sc);
537 	/*
538 	 * NB: the order of these is important:
539 	 * o call the 802.11 layer before detaching the hal to
540 	 *   insure callbacks into the driver to delete global
541 	 *   key cache entries can be handled
542 	 * o reclaim the tx queue data structures after calling
543 	 *   the 802.11 layer as we'll get called back to reclaim
544 	 *   node state and potentially want to use them
545 	 * o to cleanup the tx queues the hal is called, so detach
546 	 *   it last
547 	 * Other than that, it's straightforward...
548 	 */
549 	ieee80211_ifdetach(ic);
550 	callout_drain(&sc->sc_watchdog);
551 	mwl_dma_cleanup(sc);
552 	MWL_RXFREE_DESTROY(sc);
553 	mwl_tx_cleanup(sc);
554 	mwl_hal_detach(sc->sc_mh);
555 	mbufq_drain(&sc->sc_snd);
556 
557 	return 0;
558 }
559 
560 /*
561  * MAC address handling for multiple BSS on the same radio.
562  * The first vap uses the MAC address from the EEPROM.  For
563  * subsequent vap's we set the U/L bit (bit 1) in the MAC
564  * address and use the next six bits as an index.
565  */
566 static void
567 assign_address(struct mwl_softc *sc, uint8_t mac[IEEE80211_ADDR_LEN], int clone)
568 {
569 	int i;
570 
571 	if (clone && mwl_hal_ismbsscapable(sc->sc_mh)) {
572 		/* NB: we only do this if h/w supports multiple bssid */
573 		for (i = 0; i < 32; i++)
574 			if ((sc->sc_bssidmask & (1<<i)) == 0)
575 				break;
576 		if (i != 0)
577 			mac[0] |= (i << 2)|0x2;
578 	} else
579 		i = 0;
580 	sc->sc_bssidmask |= 1<<i;
581 	if (i == 0)
582 		sc->sc_nbssid0++;
583 }
584 
585 static void
586 reclaim_address(struct mwl_softc *sc, const uint8_t mac[IEEE80211_ADDR_LEN])
587 {
588 	int i = mac[0] >> 2;
589 	if (i != 0 || --sc->sc_nbssid0 == 0)
590 		sc->sc_bssidmask &= ~(1<<i);
591 }
592 
593 static struct ieee80211vap *
594 mwl_vap_create(struct ieee80211com *ic, const char name[IFNAMSIZ], int unit,
595     enum ieee80211_opmode opmode, int flags,
596     const uint8_t bssid[IEEE80211_ADDR_LEN],
597     const uint8_t mac0[IEEE80211_ADDR_LEN])
598 {
599 	struct mwl_softc *sc = ic->ic_softc;
600 	struct mwl_hal *mh = sc->sc_mh;
601 	struct ieee80211vap *vap, *apvap;
602 	struct mwl_hal_vap *hvap;
603 	struct mwl_vap *mvp;
604 	uint8_t mac[IEEE80211_ADDR_LEN];
605 
606 	IEEE80211_ADDR_COPY(mac, mac0);
607 	switch (opmode) {
608 	case IEEE80211_M_HOSTAP:
609 	case IEEE80211_M_MBSS:
610 		if ((flags & IEEE80211_CLONE_MACADDR) == 0)
611 			assign_address(sc, mac, flags & IEEE80211_CLONE_BSSID);
612 		hvap = mwl_hal_newvap(mh, MWL_HAL_AP, mac);
613 		if (hvap == NULL) {
614 			if ((flags & IEEE80211_CLONE_MACADDR) == 0)
615 				reclaim_address(sc, mac);
616 			return NULL;
617 		}
618 		break;
619 	case IEEE80211_M_STA:
620 		if ((flags & IEEE80211_CLONE_MACADDR) == 0)
621 			assign_address(sc, mac, flags & IEEE80211_CLONE_BSSID);
622 		hvap = mwl_hal_newvap(mh, MWL_HAL_STA, mac);
623 		if (hvap == NULL) {
624 			if ((flags & IEEE80211_CLONE_MACADDR) == 0)
625 				reclaim_address(sc, mac);
626 			return NULL;
627 		}
628 		/* no h/w beacon miss support; always use s/w */
629 		flags |= IEEE80211_CLONE_NOBEACONS;
630 		break;
631 	case IEEE80211_M_WDS:
632 		hvap = NULL;		/* NB: we use associated AP vap */
633 		if (sc->sc_napvaps == 0)
634 			return NULL;	/* no existing AP vap */
635 		break;
636 	case IEEE80211_M_MONITOR:
637 		hvap = NULL;
638 		break;
639 	case IEEE80211_M_IBSS:
640 	case IEEE80211_M_AHDEMO:
641 	default:
642 		return NULL;
643 	}
644 
645 	mvp = malloc(sizeof(struct mwl_vap), M_80211_VAP, M_WAITOK | M_ZERO);
646 	mvp->mv_hvap = hvap;
647 	if (opmode == IEEE80211_M_WDS) {
648 		/*
649 		 * WDS vaps must have an associated AP vap; find one.
650 		 * XXX not right.
651 		 */
652 		TAILQ_FOREACH(apvap, &ic->ic_vaps, iv_next)
653 			if (apvap->iv_opmode == IEEE80211_M_HOSTAP) {
654 				mvp->mv_ap_hvap = MWL_VAP(apvap)->mv_hvap;
655 				break;
656 			}
657 		KASSERT(mvp->mv_ap_hvap != NULL, ("no ap vap"));
658 	}
659 	vap = &mvp->mv_vap;
660 	ieee80211_vap_setup(ic, vap, name, unit, opmode, flags, bssid);
661 	/* override with driver methods */
662 	mvp->mv_newstate = vap->iv_newstate;
663 	vap->iv_newstate = mwl_newstate;
664 	vap->iv_max_keyix = 0;	/* XXX */
665 	vap->iv_key_alloc = mwl_key_alloc;
666 	vap->iv_key_delete = mwl_key_delete;
667 	vap->iv_key_set = mwl_key_set;
668 #ifdef MWL_HOST_PS_SUPPORT
669 	if (opmode == IEEE80211_M_HOSTAP || opmode == IEEE80211_M_MBSS) {
670 		vap->iv_update_ps = mwl_update_ps;
671 		mvp->mv_set_tim = vap->iv_set_tim;
672 		vap->iv_set_tim = mwl_set_tim;
673 	}
674 #endif
675 	vap->iv_reset = mwl_reset;
676 	vap->iv_update_beacon = mwl_beacon_update;
677 
678 	/* override max aid so sta's cannot assoc when we're out of sta id's */
679 	vap->iv_max_aid = MWL_MAXSTAID;
680 	/* override default A-MPDU rx parameters */
681 	vap->iv_ampdu_rxmax = IEEE80211_HTCAP_MAXRXAMPDU_64K;
682 	vap->iv_ampdu_density = IEEE80211_HTCAP_MPDUDENSITY_4;
683 
684 	/* complete setup */
685 	ieee80211_vap_attach(vap, mwl_media_change, ieee80211_media_status,
686 	    mac);
687 
688 	switch (vap->iv_opmode) {
689 	case IEEE80211_M_HOSTAP:
690 	case IEEE80211_M_MBSS:
691 	case IEEE80211_M_STA:
692 		/*
693 		 * Setup sta db entry for local address.
694 		 */
695 		mwl_localstadb(vap);
696 		if (vap->iv_opmode == IEEE80211_M_HOSTAP ||
697 		    vap->iv_opmode == IEEE80211_M_MBSS)
698 			sc->sc_napvaps++;
699 		else
700 			sc->sc_nstavaps++;
701 		break;
702 	case IEEE80211_M_WDS:
703 		sc->sc_nwdsvaps++;
704 		break;
705 	default:
706 		break;
707 	}
708 	/*
709 	 * Setup overall operating mode.
710 	 */
711 	if (sc->sc_napvaps)
712 		ic->ic_opmode = IEEE80211_M_HOSTAP;
713 	else if (sc->sc_nstavaps)
714 		ic->ic_opmode = IEEE80211_M_STA;
715 	else
716 		ic->ic_opmode = opmode;
717 
718 	return vap;
719 }
720 
721 static void
722 mwl_vap_delete(struct ieee80211vap *vap)
723 {
724 	struct mwl_vap *mvp = MWL_VAP(vap);
725 	struct mwl_softc *sc = vap->iv_ic->ic_softc;
726 	struct mwl_hal *mh = sc->sc_mh;
727 	struct mwl_hal_vap *hvap = mvp->mv_hvap;
728 	enum ieee80211_opmode opmode = vap->iv_opmode;
729 
730 	/* XXX disallow ap vap delete if WDS still present */
731 	if (sc->sc_running) {
732 		/* quiesce h/w while we remove the vap */
733 		mwl_hal_intrset(mh, 0);		/* disable interrupts */
734 	}
735 	ieee80211_vap_detach(vap);
736 	switch (opmode) {
737 	case IEEE80211_M_HOSTAP:
738 	case IEEE80211_M_MBSS:
739 	case IEEE80211_M_STA:
740 		KASSERT(hvap != NULL, ("no hal vap handle"));
741 		(void) mwl_hal_delstation(hvap, vap->iv_myaddr);
742 		mwl_hal_delvap(hvap);
743 		if (opmode == IEEE80211_M_HOSTAP || opmode == IEEE80211_M_MBSS)
744 			sc->sc_napvaps--;
745 		else
746 			sc->sc_nstavaps--;
747 		/* XXX don't do it for IEEE80211_CLONE_MACADDR */
748 		reclaim_address(sc, vap->iv_myaddr);
749 		break;
750 	case IEEE80211_M_WDS:
751 		sc->sc_nwdsvaps--;
752 		break;
753 	default:
754 		break;
755 	}
756 	mwl_cleartxq(sc, vap);
757 	free(mvp, M_80211_VAP);
758 	if (sc->sc_running)
759 		mwl_hal_intrset(mh, sc->sc_imask);
760 }
761 
762 void
763 mwl_suspend(struct mwl_softc *sc)
764 {
765 
766 	MWL_LOCK(sc);
767 	mwl_stop(sc);
768 	MWL_UNLOCK(sc);
769 }
770 
771 void
772 mwl_resume(struct mwl_softc *sc)
773 {
774 	int error = EDOOFUS;
775 
776 	MWL_LOCK(sc);
777 	if (sc->sc_ic.ic_nrunning > 0)
778 		error = mwl_init(sc);
779 	MWL_UNLOCK(sc);
780 
781 	if (error == 0)
782 		ieee80211_start_all(&sc->sc_ic);	/* start all vap's */
783 }
784 
785 void
786 mwl_shutdown(void *arg)
787 {
788 	struct mwl_softc *sc = arg;
789 
790 	MWL_LOCK(sc);
791 	mwl_stop(sc);
792 	MWL_UNLOCK(sc);
793 }
794 
795 /*
796  * Interrupt handler.  Most of the actual processing is deferred.
797  */
798 void
799 mwl_intr(void *arg)
800 {
801 	struct mwl_softc *sc = arg;
802 	struct mwl_hal *mh = sc->sc_mh;
803 	uint32_t status;
804 
805 	if (sc->sc_invalid) {
806 		/*
807 		 * The hardware is not ready/present, don't touch anything.
808 		 * Note this can happen early on if the IRQ is shared.
809 		 */
810 		DPRINTF(sc, MWL_DEBUG_ANY, "%s: invalid; ignored\n", __func__);
811 		return;
812 	}
813 	/*
814 	 * Figure out the reason(s) for the interrupt.
815 	 */
816 	mwl_hal_getisr(mh, &status);		/* NB: clears ISR too */
817 	if (status == 0)			/* must be a shared irq */
818 		return;
819 
820 	DPRINTF(sc, MWL_DEBUG_INTR, "%s: status 0x%x imask 0x%x\n",
821 	    __func__, status, sc->sc_imask);
822 	if (status & MACREG_A2HRIC_BIT_RX_RDY)
823 		taskqueue_enqueue(sc->sc_tq, &sc->sc_rxtask);
824 	if (status & MACREG_A2HRIC_BIT_TX_DONE)
825 		taskqueue_enqueue(sc->sc_tq, &sc->sc_txtask);
826 	if (status & MACREG_A2HRIC_BIT_BA_WATCHDOG)
827 		taskqueue_enqueue(sc->sc_tq, &sc->sc_bawatchdogtask);
828 	if (status & MACREG_A2HRIC_BIT_OPC_DONE)
829 		mwl_hal_cmddone(mh);
830 	if (status & MACREG_A2HRIC_BIT_MAC_EVENT) {
831 		;
832 	}
833 	if (status & MACREG_A2HRIC_BIT_ICV_ERROR) {
834 		/* TKIP ICV error */
835 		sc->sc_stats.mst_rx_badtkipicv++;
836 	}
837 	if (status & MACREG_A2HRIC_BIT_QUEUE_EMPTY) {
838 		/* 11n aggregation queue is empty, re-fill */
839 		;
840 	}
841 	if (status & MACREG_A2HRIC_BIT_QUEUE_FULL) {
842 		;
843 	}
844 	if (status & MACREG_A2HRIC_BIT_RADAR_DETECT) {
845 		/* radar detected, process event */
846 		taskqueue_enqueue(sc->sc_tq, &sc->sc_radartask);
847 	}
848 	if (status & MACREG_A2HRIC_BIT_CHAN_SWITCH) {
849 		/* DFS channel switch */
850 		taskqueue_enqueue(sc->sc_tq, &sc->sc_chanswitchtask);
851 	}
852 }
853 
854 static void
855 mwl_radar_proc(void *arg, int pending)
856 {
857 	struct mwl_softc *sc = arg;
858 	struct ieee80211com *ic = &sc->sc_ic;
859 
860 	DPRINTF(sc, MWL_DEBUG_ANY, "%s: radar detected, pending %u\n",
861 	    __func__, pending);
862 
863 	sc->sc_stats.mst_radardetect++;
864 	/* XXX stop h/w BA streams? */
865 
866 	IEEE80211_LOCK(ic);
867 	ieee80211_dfs_notify_radar(ic, ic->ic_curchan);
868 	IEEE80211_UNLOCK(ic);
869 }
870 
871 static void
872 mwl_chanswitch_proc(void *arg, int pending)
873 {
874 	struct mwl_softc *sc = arg;
875 	struct ieee80211com *ic = &sc->sc_ic;
876 
877 	DPRINTF(sc, MWL_DEBUG_ANY, "%s: channel switch notice, pending %u\n",
878 	    __func__, pending);
879 
880 	IEEE80211_LOCK(ic);
881 	sc->sc_csapending = 0;
882 	ieee80211_csa_completeswitch(ic);
883 	IEEE80211_UNLOCK(ic);
884 }
885 
886 static void
887 mwl_bawatchdog(const MWL_HAL_BASTREAM *sp)
888 {
889 	struct ieee80211_node *ni = sp->data[0];
890 
891 	/* send DELBA and drop the stream */
892 	ieee80211_ampdu_stop(ni, sp->data[1], IEEE80211_REASON_UNSPECIFIED);
893 }
894 
895 static void
896 mwl_bawatchdog_proc(void *arg, int pending)
897 {
898 	struct mwl_softc *sc = arg;
899 	struct mwl_hal *mh = sc->sc_mh;
900 	const MWL_HAL_BASTREAM *sp;
901 	uint8_t bitmap, n;
902 
903 	sc->sc_stats.mst_bawatchdog++;
904 
905 	if (mwl_hal_getwatchdogbitmap(mh, &bitmap) != 0) {
906 		DPRINTF(sc, MWL_DEBUG_AMPDU,
907 		    "%s: could not get bitmap\n", __func__);
908 		sc->sc_stats.mst_bawatchdog_failed++;
909 		return;
910 	}
911 	DPRINTF(sc, MWL_DEBUG_AMPDU, "%s: bitmap 0x%x\n", __func__, bitmap);
912 	if (bitmap == 0xff) {
913 		n = 0;
914 		/* disable all ba streams */
915 		for (bitmap = 0; bitmap < 8; bitmap++) {
916 			sp = mwl_hal_bastream_lookup(mh, bitmap);
917 			if (sp != NULL) {
918 				mwl_bawatchdog(sp);
919 				n++;
920 			}
921 		}
922 		if (n == 0) {
923 			DPRINTF(sc, MWL_DEBUG_AMPDU,
924 			    "%s: no BA streams found\n", __func__);
925 			sc->sc_stats.mst_bawatchdog_empty++;
926 		}
927 	} else if (bitmap != 0xaa) {
928 		/* disable a single ba stream */
929 		sp = mwl_hal_bastream_lookup(mh, bitmap);
930 		if (sp != NULL) {
931 			mwl_bawatchdog(sp);
932 		} else {
933 			DPRINTF(sc, MWL_DEBUG_AMPDU,
934 			    "%s: no BA stream %d\n", __func__, bitmap);
935 			sc->sc_stats.mst_bawatchdog_notfound++;
936 		}
937 	}
938 }
939 
940 /*
941  * Convert net80211 channel to a HAL channel.
942  */
943 static void
944 mwl_mapchan(MWL_HAL_CHANNEL *hc, const struct ieee80211_channel *chan)
945 {
946 	hc->channel = chan->ic_ieee;
947 
948 	*(uint32_t *)&hc->channelFlags = 0;
949 	if (IEEE80211_IS_CHAN_2GHZ(chan))
950 		hc->channelFlags.FreqBand = MWL_FREQ_BAND_2DOT4GHZ;
951 	else if (IEEE80211_IS_CHAN_5GHZ(chan))
952 		hc->channelFlags.FreqBand = MWL_FREQ_BAND_5GHZ;
953 	if (IEEE80211_IS_CHAN_HT40(chan)) {
954 		hc->channelFlags.ChnlWidth = MWL_CH_40_MHz_WIDTH;
955 		if (IEEE80211_IS_CHAN_HT40U(chan))
956 			hc->channelFlags.ExtChnlOffset = MWL_EXT_CH_ABOVE_CTRL_CH;
957 		else
958 			hc->channelFlags.ExtChnlOffset = MWL_EXT_CH_BELOW_CTRL_CH;
959 	} else
960 		hc->channelFlags.ChnlWidth = MWL_CH_20_MHz_WIDTH;
961 	/* XXX 10MHz channels */
962 }
963 
964 /*
965  * Inform firmware of our tx/rx dma setup.  The BAR 0
966  * writes below are for compatibility with older firmware.
967  * For current firmware we send this information with a
968  * cmd block via mwl_hal_sethwdma.
969  */
970 static int
971 mwl_setupdma(struct mwl_softc *sc)
972 {
973 	int error, i;
974 
975 	sc->sc_hwdma.rxDescRead = sc->sc_rxdma.dd_desc_paddr;
976 	WR4(sc, sc->sc_hwspecs.rxDescRead, sc->sc_hwdma.rxDescRead);
977 	WR4(sc, sc->sc_hwspecs.rxDescWrite, sc->sc_hwdma.rxDescRead);
978 
979 	for (i = 0; i < MWL_NUM_TX_QUEUES-MWL_NUM_ACK_QUEUES; i++) {
980 		struct mwl_txq *txq = &sc->sc_txq[i];
981 		sc->sc_hwdma.wcbBase[i] = txq->dma.dd_desc_paddr;
982 		WR4(sc, sc->sc_hwspecs.wcbBase[i], sc->sc_hwdma.wcbBase[i]);
983 	}
984 	sc->sc_hwdma.maxNumTxWcb = mwl_txbuf;
985 	sc->sc_hwdma.maxNumWCB = MWL_NUM_TX_QUEUES-MWL_NUM_ACK_QUEUES;
986 
987 	error = mwl_hal_sethwdma(sc->sc_mh, &sc->sc_hwdma);
988 	if (error != 0) {
989 		device_printf(sc->sc_dev,
990 		    "unable to setup tx/rx dma; hal status %u\n", error);
991 		/* XXX */
992 	}
993 	return error;
994 }
995 
996 /*
997  * Inform firmware of tx rate parameters.
998  * Called after a channel change.
999  */
1000 static int
1001 mwl_setcurchanrates(struct mwl_softc *sc)
1002 {
1003 	struct ieee80211com *ic = &sc->sc_ic;
1004 	const struct ieee80211_rateset *rs;
1005 	MWL_HAL_TXRATE rates;
1006 
1007 	memset(&rates, 0, sizeof(rates));
1008 	rs = ieee80211_get_suprates(ic, ic->ic_curchan);
1009 	/* rate used to send management frames */
1010 	rates.MgtRate = rs->rs_rates[0] & IEEE80211_RATE_VAL;
1011 	/* rate used to send multicast frames */
1012 	rates.McastRate = rates.MgtRate;
1013 
1014 	return mwl_hal_settxrate_auto(sc->sc_mh, &rates);
1015 }
1016 
1017 /*
1018  * Inform firmware of tx rate parameters.  Called whenever
1019  * user-settable params change and after a channel change.
1020  */
1021 static int
1022 mwl_setrates(struct ieee80211vap *vap)
1023 {
1024 	struct mwl_vap *mvp = MWL_VAP(vap);
1025 	struct ieee80211_node *ni = vap->iv_bss;
1026 	const struct ieee80211_txparam *tp = ni->ni_txparms;
1027 	MWL_HAL_TXRATE rates;
1028 
1029 	KASSERT(vap->iv_state == IEEE80211_S_RUN, ("state %d", vap->iv_state));
1030 
1031 	/*
1032 	 * Update the h/w rate map.
1033 	 * NB: 0x80 for MCS is passed through unchanged
1034 	 */
1035 	memset(&rates, 0, sizeof(rates));
1036 	/* rate used to send management frames */
1037 	rates.MgtRate = tp->mgmtrate;
1038 	/* rate used to send multicast frames */
1039 	rates.McastRate = tp->mcastrate;
1040 
1041 	/* while here calculate EAPOL fixed rate cookie */
1042 	mvp->mv_eapolformat = htole16(mwl_calcformat(rates.MgtRate, ni));
1043 
1044 	return mwl_hal_settxrate(mvp->mv_hvap,
1045 	    tp->ucastrate != IEEE80211_FIXED_RATE_NONE ?
1046 		RATE_FIXED : RATE_AUTO, &rates);
1047 }
1048 
1049 /*
1050  * Setup a fixed xmit rate cookie for EAPOL frames.
1051  */
1052 static void
1053 mwl_seteapolformat(struct ieee80211vap *vap)
1054 {
1055 	struct mwl_vap *mvp = MWL_VAP(vap);
1056 	struct ieee80211_node *ni = vap->iv_bss;
1057 	enum ieee80211_phymode mode;
1058 	uint8_t rate;
1059 
1060 	KASSERT(vap->iv_state == IEEE80211_S_RUN, ("state %d", vap->iv_state));
1061 
1062 	mode = ieee80211_chan2mode(ni->ni_chan);
1063 	/*
1064 	 * Use legacy rates when operating a mixed HT+non-HT bss.
1065 	 * NB: this may violate POLA for sta and wds vap's.
1066 	 */
1067 	if (mode == IEEE80211_MODE_11NA &&
1068 	    (vap->iv_flags_ht & IEEE80211_FHT_PUREN) == 0)
1069 		rate = vap->iv_txparms[IEEE80211_MODE_11A].mgmtrate;
1070 	else if (mode == IEEE80211_MODE_11NG &&
1071 	    (vap->iv_flags_ht & IEEE80211_FHT_PUREN) == 0)
1072 		rate = vap->iv_txparms[IEEE80211_MODE_11G].mgmtrate;
1073 	else
1074 		rate = vap->iv_txparms[mode].mgmtrate;
1075 
1076 	mvp->mv_eapolformat = htole16(mwl_calcformat(rate, ni));
1077 }
1078 
1079 /*
1080  * Map SKU+country code to region code for radar bin'ing.
1081  */
1082 static int
1083 mwl_map2regioncode(const struct ieee80211_regdomain *rd)
1084 {
1085 	switch (rd->regdomain) {
1086 	case SKU_FCC:
1087 	case SKU_FCC3:
1088 		return DOMAIN_CODE_FCC;
1089 	case SKU_CA:
1090 		return DOMAIN_CODE_IC;
1091 	case SKU_ETSI:
1092 	case SKU_ETSI2:
1093 	case SKU_ETSI3:
1094 		if (rd->country == CTRY_SPAIN)
1095 			return DOMAIN_CODE_SPAIN;
1096 		if (rd->country == CTRY_FRANCE || rd->country == CTRY_FRANCE2)
1097 			return DOMAIN_CODE_FRANCE;
1098 		/* XXX force 1.3.1 radar type */
1099 		return DOMAIN_CODE_ETSI_131;
1100 	case SKU_JAPAN:
1101 		return DOMAIN_CODE_MKK;
1102 	case SKU_ROW:
1103 		return DOMAIN_CODE_DGT;	/* Taiwan */
1104 	case SKU_APAC:
1105 	case SKU_APAC2:
1106 	case SKU_APAC3:
1107 		return DOMAIN_CODE_AUS;	/* Australia */
1108 	}
1109 	/* XXX KOREA? */
1110 	return DOMAIN_CODE_FCC;			/* XXX? */
1111 }
1112 
1113 static int
1114 mwl_hal_reset(struct mwl_softc *sc)
1115 {
1116 	struct ieee80211com *ic = &sc->sc_ic;
1117 	struct mwl_hal *mh = sc->sc_mh;
1118 
1119 	mwl_hal_setantenna(mh, WL_ANTENNATYPE_RX, sc->sc_rxantenna);
1120 	mwl_hal_setantenna(mh, WL_ANTENNATYPE_TX, sc->sc_txantenna);
1121 	mwl_hal_setradio(mh, 1, WL_AUTO_PREAMBLE);
1122 	mwl_hal_setwmm(sc->sc_mh, (ic->ic_flags & IEEE80211_F_WME) != 0);
1123 	mwl_chan_set(sc, ic->ic_curchan);
1124 	/* NB: RF/RA performance tuned for indoor mode */
1125 	mwl_hal_setrateadaptmode(mh, 0);
1126 	mwl_hal_setoptimizationlevel(mh,
1127 	    (ic->ic_flags & IEEE80211_F_BURST) != 0);
1128 
1129 	mwl_hal_setregioncode(mh, mwl_map2regioncode(&ic->ic_regdomain));
1130 
1131 	mwl_hal_setaggampduratemode(mh, 1, 80);		/* XXX */
1132 	mwl_hal_setcfend(mh, 0);			/* XXX */
1133 
1134 	return 1;
1135 }
1136 
1137 static int
1138 mwl_init(struct mwl_softc *sc)
1139 {
1140 	struct mwl_hal *mh = sc->sc_mh;
1141 	int error = 0;
1142 
1143 	MWL_LOCK_ASSERT(sc);
1144 
1145 	/*
1146 	 * Stop anything previously setup.  This is safe
1147 	 * whether this is the first time through or not.
1148 	 */
1149 	mwl_stop(sc);
1150 
1151 	/*
1152 	 * Push vap-independent state to the firmware.
1153 	 */
1154 	if (!mwl_hal_reset(sc)) {
1155 		device_printf(sc->sc_dev, "unable to reset hardware\n");
1156 		return EIO;
1157 	}
1158 
1159 	/*
1160 	 * Setup recv (once); transmit is already good to go.
1161 	 */
1162 	error = mwl_startrecv(sc);
1163 	if (error != 0) {
1164 		device_printf(sc->sc_dev, "unable to start recv logic\n");
1165 		return error;
1166 	}
1167 
1168 	/*
1169 	 * Enable interrupts.
1170 	 */
1171 	sc->sc_imask = MACREG_A2HRIC_BIT_RX_RDY
1172 		     | MACREG_A2HRIC_BIT_TX_DONE
1173 		     | MACREG_A2HRIC_BIT_OPC_DONE
1174 #if 0
1175 		     | MACREG_A2HRIC_BIT_MAC_EVENT
1176 #endif
1177 		     | MACREG_A2HRIC_BIT_ICV_ERROR
1178 		     | MACREG_A2HRIC_BIT_RADAR_DETECT
1179 		     | MACREG_A2HRIC_BIT_CHAN_SWITCH
1180 #if 0
1181 		     | MACREG_A2HRIC_BIT_QUEUE_EMPTY
1182 #endif
1183 		     | MACREG_A2HRIC_BIT_BA_WATCHDOG
1184 		     | MACREQ_A2HRIC_BIT_TX_ACK
1185 		     ;
1186 
1187 	sc->sc_running = 1;
1188 	mwl_hal_intrset(mh, sc->sc_imask);
1189 	callout_reset(&sc->sc_watchdog, hz, mwl_watchdog, sc);
1190 
1191 	return 0;
1192 }
1193 
1194 static void
1195 mwl_stop(struct mwl_softc *sc)
1196 {
1197 
1198 	MWL_LOCK_ASSERT(sc);
1199 	if (sc->sc_running) {
1200 		/*
1201 		 * Shutdown the hardware and driver.
1202 		 */
1203 		sc->sc_running = 0;
1204 		callout_stop(&sc->sc_watchdog);
1205 		sc->sc_tx_timer = 0;
1206 		mwl_draintxq(sc);
1207 	}
1208 }
1209 
1210 static int
1211 mwl_reset_vap(struct ieee80211vap *vap, int state)
1212 {
1213 	struct mwl_hal_vap *hvap = MWL_VAP(vap)->mv_hvap;
1214 	struct ieee80211com *ic = vap->iv_ic;
1215 
1216 	if (state == IEEE80211_S_RUN)
1217 		mwl_setrates(vap);
1218 	/* XXX off by 1? */
1219 	mwl_hal_setrtsthreshold(hvap, vap->iv_rtsthreshold);
1220 	/* XXX auto? 20/40 split? */
1221 	mwl_hal_sethtgi(hvap, (vap->iv_flags_ht &
1222 	    (IEEE80211_FHT_SHORTGI20|IEEE80211_FHT_SHORTGI40)) ? 1 : 0);
1223 	mwl_hal_setnprot(hvap, ic->ic_htprotmode == IEEE80211_PROT_NONE ?
1224 	    HTPROTECT_NONE : HTPROTECT_AUTO);
1225 	/* XXX txpower cap */
1226 
1227 	/* re-setup beacons */
1228 	if (state == IEEE80211_S_RUN &&
1229 	    (vap->iv_opmode == IEEE80211_M_HOSTAP ||
1230 	     vap->iv_opmode == IEEE80211_M_MBSS ||
1231 	     vap->iv_opmode == IEEE80211_M_IBSS)) {
1232 		mwl_setapmode(vap, vap->iv_bss->ni_chan);
1233 		mwl_hal_setnprotmode(hvap,
1234 		    MS(ic->ic_curhtprotmode, IEEE80211_HTINFO_OPMODE));
1235 		return mwl_beacon_setup(vap);
1236 	}
1237 	return 0;
1238 }
1239 
1240 /*
1241  * Reset the hardware w/o losing operational state.
1242  * Used to reset or reload hardware state for a vap.
1243  */
1244 static int
1245 mwl_reset(struct ieee80211vap *vap, u_long cmd)
1246 {
1247 	struct mwl_hal_vap *hvap = MWL_VAP(vap)->mv_hvap;
1248 	int error = 0;
1249 
1250 	if (hvap != NULL) {			/* WDS, MONITOR, etc. */
1251 		struct ieee80211com *ic = vap->iv_ic;
1252 		struct mwl_softc *sc = ic->ic_softc;
1253 		struct mwl_hal *mh = sc->sc_mh;
1254 
1255 		/* XXX handle DWDS sta vap change */
1256 		/* XXX do we need to disable interrupts? */
1257 		mwl_hal_intrset(mh, 0);		/* disable interrupts */
1258 		error = mwl_reset_vap(vap, vap->iv_state);
1259 		mwl_hal_intrset(mh, sc->sc_imask);
1260 	}
1261 	return error;
1262 }
1263 
1264 /*
1265  * Allocate a tx buffer for sending a frame.  The
1266  * packet is assumed to have the WME AC stored so
1267  * we can use it to select the appropriate h/w queue.
1268  */
1269 static struct mwl_txbuf *
1270 mwl_gettxbuf(struct mwl_softc *sc, struct mwl_txq *txq)
1271 {
1272 	struct mwl_txbuf *bf;
1273 
1274 	/*
1275 	 * Grab a TX buffer and associated resources.
1276 	 */
1277 	MWL_TXQ_LOCK(txq);
1278 	bf = STAILQ_FIRST(&txq->free);
1279 	if (bf != NULL) {
1280 		STAILQ_REMOVE_HEAD(&txq->free, bf_list);
1281 		txq->nfree--;
1282 	}
1283 	MWL_TXQ_UNLOCK(txq);
1284 	if (bf == NULL)
1285 		DPRINTF(sc, MWL_DEBUG_XMIT,
1286 		    "%s: out of xmit buffers on q %d\n", __func__, txq->qnum);
1287 	return bf;
1288 }
1289 
1290 /*
1291  * Return a tx buffer to the queue it came from.  Note there
1292  * are two cases because we must preserve the order of buffers
1293  * as it reflects the fixed order of descriptors in memory
1294  * (the firmware pre-fetches descriptors so we cannot reorder).
1295  */
1296 static void
1297 mwl_puttxbuf_head(struct mwl_txq *txq, struct mwl_txbuf *bf)
1298 {
1299 	bf->bf_m = NULL;
1300 	bf->bf_node = NULL;
1301 	MWL_TXQ_LOCK(txq);
1302 	STAILQ_INSERT_HEAD(&txq->free, bf, bf_list);
1303 	txq->nfree++;
1304 	MWL_TXQ_UNLOCK(txq);
1305 }
1306 
1307 static void
1308 mwl_puttxbuf_tail(struct mwl_txq *txq, struct mwl_txbuf *bf)
1309 {
1310 	bf->bf_m = NULL;
1311 	bf->bf_node = NULL;
1312 	MWL_TXQ_LOCK(txq);
1313 	STAILQ_INSERT_TAIL(&txq->free, bf, bf_list);
1314 	txq->nfree++;
1315 	MWL_TXQ_UNLOCK(txq);
1316 }
1317 
1318 static int
1319 mwl_transmit(struct ieee80211com *ic, struct mbuf *m)
1320 {
1321 	struct mwl_softc *sc = ic->ic_softc;
1322 	int error;
1323 
1324 	MWL_LOCK(sc);
1325 	if (!sc->sc_running) {
1326 		MWL_UNLOCK(sc);
1327 		return (ENXIO);
1328 	}
1329 	error = mbufq_enqueue(&sc->sc_snd, m);
1330 	if (error) {
1331 		MWL_UNLOCK(sc);
1332 		return (error);
1333 	}
1334 	mwl_start(sc);
1335 	MWL_UNLOCK(sc);
1336 	return (0);
1337 }
1338 
1339 static void
1340 mwl_start(struct mwl_softc *sc)
1341 {
1342 	struct ieee80211_node *ni;
1343 	struct mwl_txbuf *bf;
1344 	struct mbuf *m;
1345 	struct mwl_txq *txq = NULL;	/* XXX silence gcc */
1346 	int nqueued;
1347 
1348 	MWL_LOCK_ASSERT(sc);
1349 	if (!sc->sc_running || sc->sc_invalid)
1350 		return;
1351 	nqueued = 0;
1352 	while ((m = mbufq_dequeue(&sc->sc_snd)) != NULL) {
1353 		/*
1354 		 * Grab the node for the destination.
1355 		 */
1356 		ni = (struct ieee80211_node *) m->m_pkthdr.rcvif;
1357 		KASSERT(ni != NULL, ("no node"));
1358 		m->m_pkthdr.rcvif = NULL;	/* committed, clear ref */
1359 		/*
1360 		 * Grab a TX buffer and associated resources.
1361 		 * We honor the classification by the 802.11 layer.
1362 		 */
1363 		txq = sc->sc_ac2q[M_WME_GETAC(m)];
1364 		bf = mwl_gettxbuf(sc, txq);
1365 		if (bf == NULL) {
1366 			m_freem(m);
1367 			ieee80211_free_node(ni);
1368 #ifdef MWL_TX_NODROP
1369 			sc->sc_stats.mst_tx_qstop++;
1370 			break;
1371 #else
1372 			DPRINTF(sc, MWL_DEBUG_XMIT,
1373 			    "%s: tail drop on q %d\n", __func__, txq->qnum);
1374 			sc->sc_stats.mst_tx_qdrop++;
1375 			continue;
1376 #endif /* MWL_TX_NODROP */
1377 		}
1378 
1379 		/*
1380 		 * Pass the frame to the h/w for transmission.
1381 		 */
1382 		if (mwl_tx_start(sc, ni, bf, m)) {
1383 			if_inc_counter(ni->ni_vap->iv_ifp,
1384 			    IFCOUNTER_OERRORS, 1);
1385 			mwl_puttxbuf_head(txq, bf);
1386 			ieee80211_free_node(ni);
1387 			continue;
1388 		}
1389 		nqueued++;
1390 		if (nqueued >= mwl_txcoalesce) {
1391 			/*
1392 			 * Poke the firmware to process queued frames;
1393 			 * see below about (lack of) locking.
1394 			 */
1395 			nqueued = 0;
1396 			mwl_hal_txstart(sc->sc_mh, 0/*XXX*/);
1397 		}
1398 	}
1399 	if (nqueued) {
1400 		/*
1401 		 * NB: We don't need to lock against tx done because
1402 		 * this just prods the firmware to check the transmit
1403 		 * descriptors.  The firmware will also start fetching
1404 		 * descriptors by itself if it notices new ones are
1405 		 * present when it goes to deliver a tx done interrupt
1406 		 * to the host. So if we race with tx done processing
1407 		 * it's ok.  Delivering the kick here rather than in
1408 		 * mwl_tx_start is an optimization to avoid poking the
1409 		 * firmware for each packet.
1410 		 *
1411 		 * NB: the queue id isn't used so 0 is ok.
1412 		 */
1413 		mwl_hal_txstart(sc->sc_mh, 0/*XXX*/);
1414 	}
1415 }
1416 
1417 static int
1418 mwl_raw_xmit(struct ieee80211_node *ni, struct mbuf *m,
1419 	const struct ieee80211_bpf_params *params)
1420 {
1421 	struct ieee80211com *ic = ni->ni_ic;
1422 	struct mwl_softc *sc = ic->ic_softc;
1423 	struct mwl_txbuf *bf;
1424 	struct mwl_txq *txq;
1425 
1426 	if (!sc->sc_running || sc->sc_invalid) {
1427 		m_freem(m);
1428 		return ENETDOWN;
1429 	}
1430 	/*
1431 	 * Grab a TX buffer and associated resources.
1432 	 * Note that we depend on the classification
1433 	 * by the 802.11 layer to get to the right h/w
1434 	 * queue.  Management frames must ALWAYS go on
1435 	 * queue 1 but we cannot just force that here
1436 	 * because we may receive non-mgt frames.
1437 	 */
1438 	txq = sc->sc_ac2q[M_WME_GETAC(m)];
1439 	bf = mwl_gettxbuf(sc, txq);
1440 	if (bf == NULL) {
1441 		sc->sc_stats.mst_tx_qstop++;
1442 		m_freem(m);
1443 		return ENOBUFS;
1444 	}
1445 	/*
1446 	 * Pass the frame to the h/w for transmission.
1447 	 */
1448 	if (mwl_tx_start(sc, ni, bf, m)) {
1449 		mwl_puttxbuf_head(txq, bf);
1450 
1451 		return EIO;		/* XXX */
1452 	}
1453 	/*
1454 	 * NB: We don't need to lock against tx done because
1455 	 * this just prods the firmware to check the transmit
1456 	 * descriptors.  The firmware will also start fetching
1457 	 * descriptors by itself if it notices new ones are
1458 	 * present when it goes to deliver a tx done interrupt
1459 	 * to the host. So if we race with tx done processing
1460 	 * it's ok.  Delivering the kick here rather than in
1461 	 * mwl_tx_start is an optimization to avoid poking the
1462 	 * firmware for each packet.
1463 	 *
1464 	 * NB: the queue id isn't used so 0 is ok.
1465 	 */
1466 	mwl_hal_txstart(sc->sc_mh, 0/*XXX*/);
1467 	return 0;
1468 }
1469 
1470 static int
1471 mwl_media_change(struct ifnet *ifp)
1472 {
1473 	struct ieee80211vap *vap = ifp->if_softc;
1474 	int error;
1475 
1476 	error = ieee80211_media_change(ifp);
1477 	/* NB: only the fixed rate can change and that doesn't need a reset */
1478 	if (error == ENETRESET) {
1479 		mwl_setrates(vap);
1480 		error = 0;
1481 	}
1482 	return error;
1483 }
1484 
1485 #ifdef MWL_DEBUG
1486 static void
1487 mwl_keyprint(struct mwl_softc *sc, const char *tag,
1488 	const MWL_HAL_KEYVAL *hk, const uint8_t mac[IEEE80211_ADDR_LEN])
1489 {
1490 	static const char *ciphers[] = {
1491 		"WEP",
1492 		"TKIP",
1493 		"AES-CCM",
1494 	};
1495 	int i, n;
1496 
1497 	printf("%s: [%u] %-7s", tag, hk->keyIndex, ciphers[hk->keyTypeId]);
1498 	for (i = 0, n = hk->keyLen; i < n; i++)
1499 		printf(" %02x", hk->key.aes[i]);
1500 	printf(" mac %s", ether_sprintf(mac));
1501 	if (hk->keyTypeId == KEY_TYPE_ID_TKIP) {
1502 		printf(" %s", "rxmic");
1503 		for (i = 0; i < sizeof(hk->key.tkip.rxMic); i++)
1504 			printf(" %02x", hk->key.tkip.rxMic[i]);
1505 		printf(" txmic");
1506 		for (i = 0; i < sizeof(hk->key.tkip.txMic); i++)
1507 			printf(" %02x", hk->key.tkip.txMic[i]);
1508 	}
1509 	printf(" flags 0x%x\n", hk->keyFlags);
1510 }
1511 #endif
1512 
1513 /*
1514  * Allocate a key cache slot for a unicast key.  The
1515  * firmware handles key allocation and every station is
1516  * guaranteed key space so we are always successful.
1517  */
1518 static int
1519 mwl_key_alloc(struct ieee80211vap *vap, struct ieee80211_key *k,
1520 	ieee80211_keyix *keyix, ieee80211_keyix *rxkeyix)
1521 {
1522 	struct mwl_softc *sc = vap->iv_ic->ic_softc;
1523 
1524 	if (k->wk_keyix != IEEE80211_KEYIX_NONE ||
1525 	    (k->wk_flags & IEEE80211_KEY_GROUP)) {
1526 		if (!(&vap->iv_nw_keys[0] <= k &&
1527 		      k < &vap->iv_nw_keys[IEEE80211_WEP_NKID])) {
1528 			/* should not happen */
1529 			DPRINTF(sc, MWL_DEBUG_KEYCACHE,
1530 				"%s: bogus group key\n", __func__);
1531 			return 0;
1532 		}
1533 		/* give the caller what they requested */
1534 		*keyix = *rxkeyix = ieee80211_crypto_get_key_wepidx(vap, k);
1535 	} else {
1536 		/*
1537 		 * Firmware handles key allocation.
1538 		 */
1539 		*keyix = *rxkeyix = 0;
1540 	}
1541 	return 1;
1542 }
1543 
1544 /*
1545  * Delete a key entry allocated by mwl_key_alloc.
1546  */
1547 static int
1548 mwl_key_delete(struct ieee80211vap *vap, const struct ieee80211_key *k)
1549 {
1550 	struct mwl_softc *sc = vap->iv_ic->ic_softc;
1551 	struct mwl_hal_vap *hvap = MWL_VAP(vap)->mv_hvap;
1552 	MWL_HAL_KEYVAL hk;
1553 	const uint8_t bcastaddr[IEEE80211_ADDR_LEN] =
1554 	    { 0xff, 0xff, 0xff, 0xff, 0xff, 0xff };
1555 
1556 	if (hvap == NULL) {
1557 		if (vap->iv_opmode != IEEE80211_M_WDS) {
1558 			/* XXX monitor mode? */
1559 			DPRINTF(sc, MWL_DEBUG_KEYCACHE,
1560 			    "%s: no hvap for opmode %d\n", __func__,
1561 			    vap->iv_opmode);
1562 			return 0;
1563 		}
1564 		hvap = MWL_VAP(vap)->mv_ap_hvap;
1565 	}
1566 
1567 	DPRINTF(sc, MWL_DEBUG_KEYCACHE, "%s: delete key %u\n",
1568 	    __func__, k->wk_keyix);
1569 
1570 	memset(&hk, 0, sizeof(hk));
1571 	hk.keyIndex = k->wk_keyix;
1572 	switch (k->wk_cipher->ic_cipher) {
1573 	case IEEE80211_CIPHER_WEP:
1574 		hk.keyTypeId = KEY_TYPE_ID_WEP;
1575 		break;
1576 	case IEEE80211_CIPHER_TKIP:
1577 		hk.keyTypeId = KEY_TYPE_ID_TKIP;
1578 		break;
1579 	case IEEE80211_CIPHER_AES_CCM:
1580 		hk.keyTypeId = KEY_TYPE_ID_AES;
1581 		break;
1582 	default:
1583 		/* XXX should not happen */
1584 		DPRINTF(sc, MWL_DEBUG_KEYCACHE, "%s: unknown cipher %d\n",
1585 		    __func__, k->wk_cipher->ic_cipher);
1586 		return 0;
1587 	}
1588 	return (mwl_hal_keyreset(hvap, &hk, bcastaddr) == 0);	/*XXX*/
1589 }
1590 
1591 static __inline int
1592 addgroupflags(MWL_HAL_KEYVAL *hk, const struct ieee80211_key *k)
1593 {
1594 	if (k->wk_flags & IEEE80211_KEY_GROUP) {
1595 		if (k->wk_flags & IEEE80211_KEY_XMIT)
1596 			hk->keyFlags |= KEY_FLAG_TXGROUPKEY;
1597 		if (k->wk_flags & IEEE80211_KEY_RECV)
1598 			hk->keyFlags |= KEY_FLAG_RXGROUPKEY;
1599 		return 1;
1600 	} else
1601 		return 0;
1602 }
1603 
1604 /*
1605  * Set the key cache contents for the specified key.  Key cache
1606  * slot(s) must already have been allocated by mwl_key_alloc.
1607  */
1608 static int
1609 mwl_key_set(struct ieee80211vap *vap, const struct ieee80211_key *k)
1610 {
1611 	return (_mwl_key_set(vap, k, k->wk_macaddr));
1612 }
1613 
1614 static int
1615 _mwl_key_set(struct ieee80211vap *vap, const struct ieee80211_key *k,
1616 	const uint8_t mac[IEEE80211_ADDR_LEN])
1617 {
1618 #define	GRPXMIT	(IEEE80211_KEY_XMIT | IEEE80211_KEY_GROUP)
1619 /* NB: static wep keys are marked GROUP+tx/rx; GTK will be tx or rx */
1620 #define	IEEE80211_IS_STATICKEY(k) \
1621 	(((k)->wk_flags & (GRPXMIT|IEEE80211_KEY_RECV)) == \
1622 	 (GRPXMIT|IEEE80211_KEY_RECV))
1623 	struct mwl_softc *sc = vap->iv_ic->ic_softc;
1624 	struct mwl_hal_vap *hvap = MWL_VAP(vap)->mv_hvap;
1625 	const struct ieee80211_cipher *cip = k->wk_cipher;
1626 	const uint8_t *macaddr;
1627 	MWL_HAL_KEYVAL hk;
1628 
1629 	KASSERT((k->wk_flags & IEEE80211_KEY_SWCRYPT) == 0,
1630 		("s/w crypto set?"));
1631 
1632 	if (hvap == NULL) {
1633 		if (vap->iv_opmode != IEEE80211_M_WDS) {
1634 			/* XXX monitor mode? */
1635 			DPRINTF(sc, MWL_DEBUG_KEYCACHE,
1636 			    "%s: no hvap for opmode %d\n", __func__,
1637 			    vap->iv_opmode);
1638 			return 0;
1639 		}
1640 		hvap = MWL_VAP(vap)->mv_ap_hvap;
1641 	}
1642 	memset(&hk, 0, sizeof(hk));
1643 	hk.keyIndex = k->wk_keyix;
1644 	switch (cip->ic_cipher) {
1645 	case IEEE80211_CIPHER_WEP:
1646 		hk.keyTypeId = KEY_TYPE_ID_WEP;
1647 		hk.keyLen = k->wk_keylen;
1648 		if (k->wk_keyix == vap->iv_def_txkey)
1649 			hk.keyFlags = KEY_FLAG_WEP_TXKEY;
1650 		if (!IEEE80211_IS_STATICKEY(k)) {
1651 			/* NB: WEP is never used for the PTK */
1652 			(void) addgroupflags(&hk, k);
1653 		}
1654 		break;
1655 	case IEEE80211_CIPHER_TKIP:
1656 		hk.keyTypeId = KEY_TYPE_ID_TKIP;
1657 		hk.key.tkip.tsc.high = (uint32_t)(k->wk_keytsc >> 16);
1658 		hk.key.tkip.tsc.low = (uint16_t)k->wk_keytsc;
1659 		hk.keyFlags = KEY_FLAG_TSC_VALID | KEY_FLAG_MICKEY_VALID;
1660 		hk.keyLen = k->wk_keylen + IEEE80211_MICBUF_SIZE;
1661 		if (!addgroupflags(&hk, k))
1662 			hk.keyFlags |= KEY_FLAG_PAIRWISE;
1663 		break;
1664 	case IEEE80211_CIPHER_AES_CCM:
1665 		hk.keyTypeId = KEY_TYPE_ID_AES;
1666 		hk.keyLen = k->wk_keylen;
1667 		if (!addgroupflags(&hk, k))
1668 			hk.keyFlags |= KEY_FLAG_PAIRWISE;
1669 		break;
1670 	default:
1671 		/* XXX should not happen */
1672 		DPRINTF(sc, MWL_DEBUG_KEYCACHE, "%s: unknown cipher %d\n",
1673 		    __func__, k->wk_cipher->ic_cipher);
1674 		return 0;
1675 	}
1676 	/*
1677 	 * NB: tkip mic keys get copied here too; the layout
1678 	 *     just happens to match that in ieee80211_key.
1679 	 */
1680 	memcpy(hk.key.aes, k->wk_key, hk.keyLen);
1681 
1682 	/*
1683 	 * Locate address of sta db entry for writing key;
1684 	 * the convention unfortunately is somewhat different
1685 	 * than how net80211, hostapd, and wpa_supplicant think.
1686 	 */
1687 	if (vap->iv_opmode == IEEE80211_M_STA) {
1688 		/*
1689 		 * NB: keys plumbed before the sta reaches AUTH state
1690 		 * will be discarded or written to the wrong sta db
1691 		 * entry because iv_bss is meaningless.  This is ok
1692 		 * (right now) because we handle deferred plumbing of
1693 		 * WEP keys when the sta reaches AUTH state.
1694 		 */
1695 		macaddr = vap->iv_bss->ni_bssid;
1696 		if ((k->wk_flags & IEEE80211_KEY_GROUP) == 0) {
1697 			/* XXX plumb to local sta db too for static key wep */
1698 			mwl_hal_keyset(hvap, &hk, vap->iv_myaddr);
1699 		}
1700 	} else if (vap->iv_opmode == IEEE80211_M_WDS &&
1701 	    vap->iv_state != IEEE80211_S_RUN) {
1702 		/*
1703 		 * Prior to RUN state a WDS vap will not it's BSS node
1704 		 * setup so we will plumb the key to the wrong mac
1705 		 * address (it'll be our local address).  Workaround
1706 		 * this for the moment by grabbing the correct address.
1707 		 */
1708 		macaddr = vap->iv_des_bssid;
1709 	} else if ((k->wk_flags & GRPXMIT) == GRPXMIT)
1710 		macaddr = vap->iv_myaddr;
1711 	else
1712 		macaddr = mac;
1713 	KEYPRINTF(sc, &hk, macaddr);
1714 	return (mwl_hal_keyset(hvap, &hk, macaddr) == 0);
1715 #undef IEEE80211_IS_STATICKEY
1716 #undef GRPXMIT
1717 }
1718 
1719 /*
1720  * Set the multicast filter contents into the hardware.
1721  * XXX f/w has no support; just defer to the os.
1722  */
1723 static void
1724 mwl_setmcastfilter(struct mwl_softc *sc)
1725 {
1726 #if 0
1727 	struct ether_multi *enm;
1728 	struct ether_multistep estep;
1729 	uint8_t macs[IEEE80211_ADDR_LEN*MWL_HAL_MCAST_MAX];/* XXX stack use */
1730 	uint8_t *mp;
1731 	int nmc;
1732 
1733 	mp = macs;
1734 	nmc = 0;
1735 	ETHER_FIRST_MULTI(estep, &sc->sc_ec, enm);
1736 	while (enm != NULL) {
1737 		/* XXX Punt on ranges. */
1738 		if (nmc == MWL_HAL_MCAST_MAX ||
1739 		    !IEEE80211_ADDR_EQ(enm->enm_addrlo, enm->enm_addrhi)) {
1740 			ifp->if_flags |= IFF_ALLMULTI;
1741 			return;
1742 		}
1743 		IEEE80211_ADDR_COPY(mp, enm->enm_addrlo);
1744 		mp += IEEE80211_ADDR_LEN, nmc++;
1745 		ETHER_NEXT_MULTI(estep, enm);
1746 	}
1747 	ifp->if_flags &= ~IFF_ALLMULTI;
1748 	mwl_hal_setmcast(sc->sc_mh, nmc, macs);
1749 #endif
1750 }
1751 
1752 static int
1753 mwl_mode_init(struct mwl_softc *sc)
1754 {
1755 	struct ieee80211com *ic = &sc->sc_ic;
1756 	struct mwl_hal *mh = sc->sc_mh;
1757 
1758 	mwl_hal_setpromisc(mh, ic->ic_promisc > 0);
1759 	mwl_setmcastfilter(sc);
1760 
1761 	return 0;
1762 }
1763 
1764 /*
1765  * Callback from the 802.11 layer after a multicast state change.
1766  */
1767 static void
1768 mwl_update_mcast(struct ieee80211com *ic)
1769 {
1770 	struct mwl_softc *sc = ic->ic_softc;
1771 
1772 	mwl_setmcastfilter(sc);
1773 }
1774 
1775 /*
1776  * Callback from the 802.11 layer after a promiscuous mode change.
1777  * Note this interface does not check the operating mode as this
1778  * is an internal callback and we are expected to honor the current
1779  * state (e.g. this is used for setting the interface in promiscuous
1780  * mode when operating in hostap mode to do ACS).
1781  */
1782 static void
1783 mwl_update_promisc(struct ieee80211com *ic)
1784 {
1785 	struct mwl_softc *sc = ic->ic_softc;
1786 
1787 	mwl_hal_setpromisc(sc->sc_mh, ic->ic_promisc > 0);
1788 }
1789 
1790 /*
1791  * Callback from the 802.11 layer to update the slot time
1792  * based on the current setting.  We use it to notify the
1793  * firmware of ERP changes and the f/w takes care of things
1794  * like slot time and preamble.
1795  */
1796 static void
1797 mwl_updateslot(struct ieee80211com *ic)
1798 {
1799 	struct mwl_softc *sc = ic->ic_softc;
1800 	struct mwl_hal *mh = sc->sc_mh;
1801 	int prot;
1802 
1803 	/* NB: can be called early; suppress needless cmds */
1804 	if (!sc->sc_running)
1805 		return;
1806 
1807 	/*
1808 	 * Calculate the ERP flags.  The firwmare will use
1809 	 * this to carry out the appropriate measures.
1810 	 */
1811 	prot = 0;
1812 	if (IEEE80211_IS_CHAN_ANYG(ic->ic_curchan)) {
1813 		if ((ic->ic_flags & IEEE80211_F_SHSLOT) == 0)
1814 			prot |= IEEE80211_ERP_NON_ERP_PRESENT;
1815 		if (ic->ic_flags & IEEE80211_F_USEPROT)
1816 			prot |= IEEE80211_ERP_USE_PROTECTION;
1817 		if (ic->ic_flags & IEEE80211_F_USEBARKER)
1818 			prot |= IEEE80211_ERP_LONG_PREAMBLE;
1819 	}
1820 
1821 	DPRINTF(sc, MWL_DEBUG_RESET,
1822 	    "%s: chan %u MHz/flags 0x%x %s slot, (prot 0x%x ic_flags 0x%x)\n",
1823 	    __func__, ic->ic_curchan->ic_freq, ic->ic_curchan->ic_flags,
1824 	    ic->ic_flags & IEEE80211_F_SHSLOT ? "short" : "long", prot,
1825 	    ic->ic_flags);
1826 
1827 	mwl_hal_setgprot(mh, prot);
1828 }
1829 
1830 /*
1831  * Setup the beacon frame.
1832  */
1833 static int
1834 mwl_beacon_setup(struct ieee80211vap *vap)
1835 {
1836 	struct mwl_hal_vap *hvap = MWL_VAP(vap)->mv_hvap;
1837 	struct ieee80211_node *ni = vap->iv_bss;
1838 	struct mbuf *m;
1839 
1840 	m = ieee80211_beacon_alloc(ni);
1841 	if (m == NULL)
1842 		return ENOBUFS;
1843 	mwl_hal_setbeacon(hvap, mtod(m, const void *), m->m_len);
1844 	m_free(m);
1845 
1846 	return 0;
1847 }
1848 
1849 /*
1850  * Update the beacon frame in response to a change.
1851  */
1852 static void
1853 mwl_beacon_update(struct ieee80211vap *vap, int item)
1854 {
1855 	struct mwl_hal_vap *hvap = MWL_VAP(vap)->mv_hvap;
1856 	struct ieee80211com *ic = vap->iv_ic;
1857 
1858 	KASSERT(hvap != NULL, ("no beacon"));
1859 	switch (item) {
1860 	case IEEE80211_BEACON_ERP:
1861 		mwl_updateslot(ic);
1862 		break;
1863 	case IEEE80211_BEACON_HTINFO:
1864 		mwl_hal_setnprotmode(hvap,
1865 		    MS(ic->ic_curhtprotmode, IEEE80211_HTINFO_OPMODE));
1866 		break;
1867 	case IEEE80211_BEACON_CAPS:
1868 	case IEEE80211_BEACON_WME:
1869 	case IEEE80211_BEACON_APPIE:
1870 	case IEEE80211_BEACON_CSA:
1871 		break;
1872 	case IEEE80211_BEACON_TIM:
1873 		/* NB: firmware always forms TIM */
1874 		return;
1875 	}
1876 	/* XXX retain beacon frame and update */
1877 	mwl_beacon_setup(vap);
1878 }
1879 
1880 static void
1881 mwl_load_cb(void *arg, bus_dma_segment_t *segs, int nsegs, int error)
1882 {
1883 	bus_addr_t *paddr = (bus_addr_t*) arg;
1884 	KASSERT(error == 0, ("error %u on bus_dma callback", error));
1885 	*paddr = segs->ds_addr;
1886 }
1887 
1888 #ifdef MWL_HOST_PS_SUPPORT
1889 /*
1890  * Handle power save station occupancy changes.
1891  */
1892 static void
1893 mwl_update_ps(struct ieee80211vap *vap, int nsta)
1894 {
1895 	struct mwl_vap *mvp = MWL_VAP(vap);
1896 
1897 	if (nsta == 0 || mvp->mv_last_ps_sta == 0)
1898 		mwl_hal_setpowersave_bss(mvp->mv_hvap, nsta);
1899 	mvp->mv_last_ps_sta = nsta;
1900 }
1901 
1902 /*
1903  * Handle associated station power save state changes.
1904  */
1905 static int
1906 mwl_set_tim(struct ieee80211_node *ni, int set)
1907 {
1908 	struct ieee80211vap *vap = ni->ni_vap;
1909 	struct mwl_vap *mvp = MWL_VAP(vap);
1910 
1911 	if (mvp->mv_set_tim(ni, set)) {		/* NB: state change */
1912 		mwl_hal_setpowersave_sta(mvp->mv_hvap,
1913 		    IEEE80211_AID(ni->ni_associd), set);
1914 		return 1;
1915 	} else
1916 		return 0;
1917 }
1918 #endif /* MWL_HOST_PS_SUPPORT */
1919 
1920 static int
1921 mwl_desc_setup(struct mwl_softc *sc, const char *name,
1922 	struct mwl_descdma *dd,
1923 	int nbuf, size_t bufsize, int ndesc, size_t descsize)
1924 {
1925 	uint8_t *ds;
1926 	int error;
1927 
1928 	DPRINTF(sc, MWL_DEBUG_RESET,
1929 	    "%s: %s DMA: %u bufs (%ju) %u desc/buf (%ju)\n",
1930 	    __func__, name, nbuf, (uintmax_t) bufsize,
1931 	    ndesc, (uintmax_t) descsize);
1932 
1933 	dd->dd_name = name;
1934 	dd->dd_desc_len = nbuf * ndesc * descsize;
1935 
1936 	/*
1937 	 * Setup DMA descriptor area.
1938 	 */
1939 	error = bus_dma_tag_create(bus_get_dma_tag(sc->sc_dev),	/* parent */
1940 		       PAGE_SIZE, 0,		/* alignment, bounds */
1941 		       BUS_SPACE_MAXADDR_32BIT,	/* lowaddr */
1942 		       BUS_SPACE_MAXADDR,	/* highaddr */
1943 		       NULL, NULL,		/* filter, filterarg */
1944 		       dd->dd_desc_len,		/* maxsize */
1945 		       1,			/* nsegments */
1946 		       dd->dd_desc_len,		/* maxsegsize */
1947 		       BUS_DMA_ALLOCNOW,	/* flags */
1948 		       NULL,			/* lockfunc */
1949 		       NULL,			/* lockarg */
1950 		       &dd->dd_dmat);
1951 	if (error != 0) {
1952 		device_printf(sc->sc_dev, "cannot allocate %s DMA tag\n", dd->dd_name);
1953 		return error;
1954 	}
1955 
1956 	/* allocate descriptors */
1957 	error = bus_dmamem_alloc(dd->dd_dmat, (void**) &dd->dd_desc,
1958 				 BUS_DMA_NOWAIT | BUS_DMA_COHERENT,
1959 				 &dd->dd_dmamap);
1960 	if (error != 0) {
1961 		device_printf(sc->sc_dev, "unable to alloc memory for %u %s descriptors, "
1962 			"error %u\n", nbuf * ndesc, dd->dd_name, error);
1963 		goto fail1;
1964 	}
1965 
1966 	error = bus_dmamap_load(dd->dd_dmat, dd->dd_dmamap,
1967 				dd->dd_desc, dd->dd_desc_len,
1968 				mwl_load_cb, &dd->dd_desc_paddr,
1969 				BUS_DMA_NOWAIT);
1970 	if (error != 0) {
1971 		device_printf(sc->sc_dev, "unable to map %s descriptors, error %u\n",
1972 			dd->dd_name, error);
1973 		goto fail2;
1974 	}
1975 
1976 	ds = dd->dd_desc;
1977 	memset(ds, 0, dd->dd_desc_len);
1978 	DPRINTF(sc, MWL_DEBUG_RESET,
1979 	    "%s: %s DMA map: %p (%lu) -> 0x%jx (%lu)\n",
1980 	    __func__, dd->dd_name, ds, (u_long) dd->dd_desc_len,
1981 	    (uintmax_t) dd->dd_desc_paddr, /*XXX*/ (u_long) dd->dd_desc_len);
1982 
1983 	return 0;
1984 fail2:
1985 	bus_dmamem_free(dd->dd_dmat, dd->dd_desc, dd->dd_dmamap);
1986 fail1:
1987 	bus_dma_tag_destroy(dd->dd_dmat);
1988 	memset(dd, 0, sizeof(*dd));
1989 	return error;
1990 #undef DS2PHYS
1991 }
1992 
1993 static void
1994 mwl_desc_cleanup(struct mwl_softc *sc, struct mwl_descdma *dd)
1995 {
1996 	bus_dmamap_unload(dd->dd_dmat, dd->dd_dmamap);
1997 	bus_dmamem_free(dd->dd_dmat, dd->dd_desc, dd->dd_dmamap);
1998 	bus_dma_tag_destroy(dd->dd_dmat);
1999 
2000 	memset(dd, 0, sizeof(*dd));
2001 }
2002 
2003 /*
2004  * Construct a tx q's free list.  The order of entries on
2005  * the list must reflect the physical layout of tx descriptors
2006  * because the firmware pre-fetches descriptors.
2007  *
2008  * XXX might be better to use indices into the buffer array.
2009  */
2010 static void
2011 mwl_txq_reset(struct mwl_softc *sc, struct mwl_txq *txq)
2012 {
2013 	struct mwl_txbuf *bf;
2014 	int i;
2015 
2016 	bf = txq->dma.dd_bufptr;
2017 	STAILQ_INIT(&txq->free);
2018 	for (i = 0; i < mwl_txbuf; i++, bf++)
2019 		STAILQ_INSERT_TAIL(&txq->free, bf, bf_list);
2020 	txq->nfree = i;
2021 }
2022 
2023 #define	DS2PHYS(_dd, _ds) \
2024 	((_dd)->dd_desc_paddr + ((caddr_t)(_ds) - (caddr_t)(_dd)->dd_desc))
2025 
2026 static int
2027 mwl_txdma_setup(struct mwl_softc *sc, struct mwl_txq *txq)
2028 {
2029 	int error, bsize, i;
2030 	struct mwl_txbuf *bf;
2031 	struct mwl_txdesc *ds;
2032 
2033 	error = mwl_desc_setup(sc, "tx", &txq->dma,
2034 			mwl_txbuf, sizeof(struct mwl_txbuf),
2035 			MWL_TXDESC, sizeof(struct mwl_txdesc));
2036 	if (error != 0)
2037 		return error;
2038 
2039 	/* allocate and setup tx buffers */
2040 	bsize = mwl_txbuf * sizeof(struct mwl_txbuf);
2041 	bf = malloc(bsize, M_MWLDEV, M_NOWAIT | M_ZERO);
2042 	if (bf == NULL) {
2043 		device_printf(sc->sc_dev, "malloc of %u tx buffers failed\n",
2044 			mwl_txbuf);
2045 		return ENOMEM;
2046 	}
2047 	txq->dma.dd_bufptr = bf;
2048 
2049 	ds = txq->dma.dd_desc;
2050 	for (i = 0; i < mwl_txbuf; i++, bf++, ds += MWL_TXDESC) {
2051 		bf->bf_desc = ds;
2052 		bf->bf_daddr = DS2PHYS(&txq->dma, ds);
2053 		error = bus_dmamap_create(sc->sc_dmat, BUS_DMA_NOWAIT,
2054 				&bf->bf_dmamap);
2055 		if (error != 0) {
2056 			device_printf(sc->sc_dev, "unable to create dmamap for tx "
2057 				"buffer %u, error %u\n", i, error);
2058 			return error;
2059 		}
2060 	}
2061 	mwl_txq_reset(sc, txq);
2062 	return 0;
2063 }
2064 
2065 static void
2066 mwl_txdma_cleanup(struct mwl_softc *sc, struct mwl_txq *txq)
2067 {
2068 	struct mwl_txbuf *bf;
2069 	int i;
2070 
2071 	bf = txq->dma.dd_bufptr;
2072 	for (i = 0; i < mwl_txbuf; i++, bf++) {
2073 		KASSERT(bf->bf_m == NULL, ("mbuf on free list"));
2074 		KASSERT(bf->bf_node == NULL, ("node on free list"));
2075 		if (bf->bf_dmamap != NULL)
2076 			bus_dmamap_destroy(sc->sc_dmat, bf->bf_dmamap);
2077 	}
2078 	STAILQ_INIT(&txq->free);
2079 	txq->nfree = 0;
2080 	if (txq->dma.dd_bufptr != NULL) {
2081 		free(txq->dma.dd_bufptr, M_MWLDEV);
2082 		txq->dma.dd_bufptr = NULL;
2083 	}
2084 	if (txq->dma.dd_desc_len != 0)
2085 		mwl_desc_cleanup(sc, &txq->dma);
2086 }
2087 
2088 static int
2089 mwl_rxdma_setup(struct mwl_softc *sc)
2090 {
2091 	int error, jumbosize, bsize, i;
2092 	struct mwl_rxbuf *bf;
2093 	struct mwl_jumbo *rbuf;
2094 	struct mwl_rxdesc *ds;
2095 	caddr_t data;
2096 
2097 	error = mwl_desc_setup(sc, "rx", &sc->sc_rxdma,
2098 			mwl_rxdesc, sizeof(struct mwl_rxbuf),
2099 			1, sizeof(struct mwl_rxdesc));
2100 	if (error != 0)
2101 		return error;
2102 
2103 	/*
2104 	 * Receive is done to a private pool of jumbo buffers.
2105 	 * This allows us to attach to mbuf's and avoid re-mapping
2106 	 * memory on each rx we post.  We allocate a large chunk
2107 	 * of memory and manage it in the driver.  The mbuf free
2108 	 * callback method is used to reclaim frames after sending
2109 	 * them up the stack.  By default we allocate 2x the number of
2110 	 * rx descriptors configured so we have some slop to hold
2111 	 * us while frames are processed.
2112 	 */
2113 	if (mwl_rxbuf < 2*mwl_rxdesc) {
2114 		device_printf(sc->sc_dev,
2115 		    "too few rx dma buffers (%d); increasing to %d\n",
2116 		    mwl_rxbuf, 2*mwl_rxdesc);
2117 		mwl_rxbuf = 2*mwl_rxdesc;
2118 	}
2119 	jumbosize = roundup(MWL_AGGR_SIZE, PAGE_SIZE);
2120 	sc->sc_rxmemsize = mwl_rxbuf*jumbosize;
2121 
2122 	error = bus_dma_tag_create(sc->sc_dmat,	/* parent */
2123 		       PAGE_SIZE, 0,		/* alignment, bounds */
2124 		       BUS_SPACE_MAXADDR_32BIT,	/* lowaddr */
2125 		       BUS_SPACE_MAXADDR,	/* highaddr */
2126 		       NULL, NULL,		/* filter, filterarg */
2127 		       sc->sc_rxmemsize,	/* maxsize */
2128 		       1,			/* nsegments */
2129 		       sc->sc_rxmemsize,	/* maxsegsize */
2130 		       BUS_DMA_ALLOCNOW,	/* flags */
2131 		       NULL,			/* lockfunc */
2132 		       NULL,			/* lockarg */
2133 		       &sc->sc_rxdmat);
2134 	if (error != 0) {
2135 		device_printf(sc->sc_dev, "could not create rx DMA tag\n");
2136 		return error;
2137 	}
2138 
2139 	error = bus_dmamem_alloc(sc->sc_rxdmat, (void**) &sc->sc_rxmem,
2140 				 BUS_DMA_NOWAIT | BUS_DMA_COHERENT,
2141 				 &sc->sc_rxmap);
2142 	if (error != 0) {
2143 		device_printf(sc->sc_dev, "could not alloc %ju bytes of rx DMA memory\n",
2144 		    (uintmax_t) sc->sc_rxmemsize);
2145 		return error;
2146 	}
2147 
2148 	error = bus_dmamap_load(sc->sc_rxdmat, sc->sc_rxmap,
2149 				sc->sc_rxmem, sc->sc_rxmemsize,
2150 				mwl_load_cb, &sc->sc_rxmem_paddr,
2151 				BUS_DMA_NOWAIT);
2152 	if (error != 0) {
2153 		device_printf(sc->sc_dev, "could not load rx DMA map\n");
2154 		return error;
2155 	}
2156 
2157 	/*
2158 	 * Allocate rx buffers and set them up.
2159 	 */
2160 	bsize = mwl_rxdesc * sizeof(struct mwl_rxbuf);
2161 	bf = malloc(bsize, M_MWLDEV, M_NOWAIT | M_ZERO);
2162 	if (bf == NULL) {
2163 		device_printf(sc->sc_dev, "malloc of %u rx buffers failed\n", bsize);
2164 		return error;
2165 	}
2166 	sc->sc_rxdma.dd_bufptr = bf;
2167 
2168 	STAILQ_INIT(&sc->sc_rxbuf);
2169 	ds = sc->sc_rxdma.dd_desc;
2170 	for (i = 0; i < mwl_rxdesc; i++, bf++, ds++) {
2171 		bf->bf_desc = ds;
2172 		bf->bf_daddr = DS2PHYS(&sc->sc_rxdma, ds);
2173 		/* pre-assign dma buffer */
2174 		bf->bf_data = ((uint8_t *)sc->sc_rxmem) + (i*jumbosize);
2175 		/* NB: tail is intentional to preserve descriptor order */
2176 		STAILQ_INSERT_TAIL(&sc->sc_rxbuf, bf, bf_list);
2177 	}
2178 
2179 	/*
2180 	 * Place remainder of dma memory buffers on the free list.
2181 	 */
2182 	SLIST_INIT(&sc->sc_rxfree);
2183 	for (; i < mwl_rxbuf; i++) {
2184 		data = ((uint8_t *)sc->sc_rxmem) + (i*jumbosize);
2185 		rbuf = MWL_JUMBO_DATA2BUF(data);
2186 		SLIST_INSERT_HEAD(&sc->sc_rxfree, rbuf, next);
2187 		sc->sc_nrxfree++;
2188 	}
2189 	return 0;
2190 }
2191 #undef DS2PHYS
2192 
2193 static void
2194 mwl_rxdma_cleanup(struct mwl_softc *sc)
2195 {
2196 	if (sc->sc_rxmem_paddr != 0) {
2197 		bus_dmamap_unload(sc->sc_rxdmat, sc->sc_rxmap);
2198 		sc->sc_rxmem_paddr = 0;
2199 	}
2200 	if (sc->sc_rxmem != NULL) {
2201 		bus_dmamem_free(sc->sc_rxdmat, sc->sc_rxmem, sc->sc_rxmap);
2202 		sc->sc_rxmem = NULL;
2203 	}
2204 	if (sc->sc_rxdma.dd_bufptr != NULL) {
2205 		free(sc->sc_rxdma.dd_bufptr, M_MWLDEV);
2206 		sc->sc_rxdma.dd_bufptr = NULL;
2207 	}
2208 	if (sc->sc_rxdma.dd_desc_len != 0)
2209 		mwl_desc_cleanup(sc, &sc->sc_rxdma);
2210 }
2211 
2212 static int
2213 mwl_dma_setup(struct mwl_softc *sc)
2214 {
2215 	int error, i;
2216 
2217 	error = mwl_rxdma_setup(sc);
2218 	if (error != 0) {
2219 		mwl_rxdma_cleanup(sc);
2220 		return error;
2221 	}
2222 
2223 	for (i = 0; i < MWL_NUM_TX_QUEUES; i++) {
2224 		error = mwl_txdma_setup(sc, &sc->sc_txq[i]);
2225 		if (error != 0) {
2226 			mwl_dma_cleanup(sc);
2227 			return error;
2228 		}
2229 	}
2230 	return 0;
2231 }
2232 
2233 static void
2234 mwl_dma_cleanup(struct mwl_softc *sc)
2235 {
2236 	int i;
2237 
2238 	for (i = 0; i < MWL_NUM_TX_QUEUES; i++)
2239 		mwl_txdma_cleanup(sc, &sc->sc_txq[i]);
2240 	mwl_rxdma_cleanup(sc);
2241 }
2242 
2243 static struct ieee80211_node *
2244 mwl_node_alloc(struct ieee80211vap *vap, const uint8_t mac[IEEE80211_ADDR_LEN])
2245 {
2246 	struct ieee80211com *ic = vap->iv_ic;
2247 	struct mwl_softc *sc = ic->ic_softc;
2248 	const size_t space = sizeof(struct mwl_node);
2249 	struct mwl_node *mn;
2250 
2251 	mn = malloc(space, M_80211_NODE, M_NOWAIT|M_ZERO);
2252 	if (mn == NULL) {
2253 		/* XXX stat+msg */
2254 		return NULL;
2255 	}
2256 	DPRINTF(sc, MWL_DEBUG_NODE, "%s: mn %p\n", __func__, mn);
2257 	return &mn->mn_node;
2258 }
2259 
2260 static void
2261 mwl_node_cleanup(struct ieee80211_node *ni)
2262 {
2263 	struct ieee80211com *ic = ni->ni_ic;
2264         struct mwl_softc *sc = ic->ic_softc;
2265 	struct mwl_node *mn = MWL_NODE(ni);
2266 
2267 	DPRINTF(sc, MWL_DEBUG_NODE, "%s: ni %p ic %p staid %d\n",
2268 	    __func__, ni, ni->ni_ic, mn->mn_staid);
2269 
2270 	if (mn->mn_staid != 0) {
2271 		struct ieee80211vap *vap = ni->ni_vap;
2272 
2273 		if (mn->mn_hvap != NULL) {
2274 			if (vap->iv_opmode == IEEE80211_M_STA)
2275 				mwl_hal_delstation(mn->mn_hvap, vap->iv_myaddr);
2276 			else
2277 				mwl_hal_delstation(mn->mn_hvap, ni->ni_macaddr);
2278 		}
2279 		/*
2280 		 * NB: legacy WDS peer sta db entry is installed using
2281 		 * the associate ap's hvap; use it again to delete it.
2282 		 * XXX can vap be NULL?
2283 		 */
2284 		else if (vap->iv_opmode == IEEE80211_M_WDS &&
2285 		    MWL_VAP(vap)->mv_ap_hvap != NULL)
2286 			mwl_hal_delstation(MWL_VAP(vap)->mv_ap_hvap,
2287 			    ni->ni_macaddr);
2288 		delstaid(sc, mn->mn_staid);
2289 		mn->mn_staid = 0;
2290 	}
2291 	sc->sc_node_cleanup(ni);
2292 }
2293 
2294 /*
2295  * Reclaim rx dma buffers from packets sitting on the ampdu
2296  * reorder queue for a station.  We replace buffers with a
2297  * system cluster (if available).
2298  */
2299 static void
2300 mwl_ampdu_rxdma_reclaim(struct ieee80211_rx_ampdu *rap)
2301 {
2302 #if 0
2303 	int i, n, off;
2304 	struct mbuf *m;
2305 	void *cl;
2306 
2307 	n = rap->rxa_qframes;
2308 	for (i = 0; i < rap->rxa_wnd && n > 0; i++) {
2309 		m = rap->rxa_m[i];
2310 		if (m == NULL)
2311 			continue;
2312 		n--;
2313 		/* our dma buffers have a well-known free routine */
2314 		if ((m->m_flags & M_EXT) == 0 ||
2315 		    m->m_ext.ext_free != mwl_ext_free)
2316 			continue;
2317 		/*
2318 		 * Try to allocate a cluster and move the data.
2319 		 */
2320 		off = m->m_data - m->m_ext.ext_buf;
2321 		if (off + m->m_pkthdr.len > MCLBYTES) {
2322 			/* XXX no AMSDU for now */
2323 			continue;
2324 		}
2325 		cl = pool_cache_get_paddr(&mclpool_cache, 0,
2326 		    &m->m_ext.ext_paddr);
2327 		if (cl != NULL) {
2328 			/*
2329 			 * Copy the existing data to the cluster, remove
2330 			 * the rx dma buffer, and attach the cluster in
2331 			 * its place.  Note we preserve the offset to the
2332 			 * data so frames being bridged can still prepend
2333 			 * their headers without adding another mbuf.
2334 			 */
2335 			memcpy((caddr_t) cl + off, m->m_data, m->m_pkthdr.len);
2336 			MEXTREMOVE(m);
2337 			MEXTADD(m, cl, MCLBYTES, 0, NULL, &mclpool_cache);
2338 			/* setup mbuf like _MCLGET does */
2339 			m->m_flags |= M_CLUSTER | M_EXT_RW;
2340 			_MOWNERREF(m, M_EXT | M_CLUSTER);
2341 			/* NB: m_data is clobbered by MEXTADDR, adjust */
2342 			m->m_data += off;
2343 		}
2344 	}
2345 #endif
2346 }
2347 
2348 /*
2349  * Callback to reclaim resources.  We first let the
2350  * net80211 layer do it's thing, then if we are still
2351  * blocked by a lack of rx dma buffers we walk the ampdu
2352  * reorder q's to reclaim buffers by copying to a system
2353  * cluster.
2354  */
2355 static void
2356 mwl_node_drain(struct ieee80211_node *ni)
2357 {
2358 	struct ieee80211com *ic = ni->ni_ic;
2359         struct mwl_softc *sc = ic->ic_softc;
2360 	struct mwl_node *mn = MWL_NODE(ni);
2361 
2362 	DPRINTF(sc, MWL_DEBUG_NODE, "%s: ni %p vap %p staid %d\n",
2363 	    __func__, ni, ni->ni_vap, mn->mn_staid);
2364 
2365 	/* NB: call up first to age out ampdu q's */
2366 	sc->sc_node_drain(ni);
2367 
2368 	/* XXX better to not check low water mark? */
2369 	if (sc->sc_rxblocked && mn->mn_staid != 0 &&
2370 	    (ni->ni_flags & IEEE80211_NODE_HT)) {
2371 		uint8_t tid;
2372 		/*
2373 		 * Walk the reorder q and reclaim rx dma buffers by copying
2374 		 * the packet contents into clusters.
2375 		 */
2376 		for (tid = 0; tid < WME_NUM_TID; tid++) {
2377 			struct ieee80211_rx_ampdu *rap;
2378 
2379 			rap = &ni->ni_rx_ampdu[tid];
2380 			if ((rap->rxa_flags & IEEE80211_AGGR_XCHGPEND) == 0)
2381 				continue;
2382 			if (rap->rxa_qframes)
2383 				mwl_ampdu_rxdma_reclaim(rap);
2384 		}
2385 	}
2386 }
2387 
2388 static void
2389 mwl_node_getsignal(const struct ieee80211_node *ni, int8_t *rssi, int8_t *noise)
2390 {
2391 	*rssi = ni->ni_ic->ic_node_getrssi(ni);
2392 #ifdef MWL_ANT_INFO_SUPPORT
2393 #if 0
2394 	/* XXX need to smooth data */
2395 	*noise = -MWL_NODE_CONST(ni)->mn_ai.nf;
2396 #else
2397 	*noise = -95;		/* XXX */
2398 #endif
2399 #else
2400 	*noise = -95;		/* XXX */
2401 #endif
2402 }
2403 
2404 /*
2405  * Convert Hardware per-antenna rssi info to common format:
2406  * Let a1, a2, a3 represent the amplitudes per chain
2407  * Let amax represent max[a1, a2, a3]
2408  * Rssi1_dBm = RSSI_dBm + 20*log10(a1/amax)
2409  * Rssi1_dBm = RSSI_dBm + 20*log10(a1) - 20*log10(amax)
2410  * We store a table that is 4*20*log10(idx) - the extra 4 is to store or
2411  * maintain some extra precision.
2412  *
2413  * Values are stored in .5 db format capped at 127.
2414  */
2415 static void
2416 mwl_node_getmimoinfo(const struct ieee80211_node *ni,
2417 	struct ieee80211_mimo_info *mi)
2418 {
2419 #define	CVT(_dst, _src) do {						\
2420 	(_dst) = rssi + ((logdbtbl[_src] - logdbtbl[rssi_max]) >> 2);	\
2421 	(_dst) = (_dst) > 64 ? 127 : ((_dst) << 1);			\
2422 } while (0)
2423 	static const int8_t logdbtbl[32] = {
2424 	       0,   0,  24,  38,  48,  56,  62,  68,
2425 	      72,  76,  80,  83,  86,  89,  92,  94,
2426 	      96,  98, 100, 102, 104, 106, 107, 109,
2427 	     110, 112, 113, 115, 116, 117, 118, 119
2428 	};
2429 	const struct mwl_node *mn = MWL_NODE_CONST(ni);
2430 	uint8_t rssi = mn->mn_ai.rsvd1/2;		/* XXX */
2431 	uint32_t rssi_max;
2432 
2433 	rssi_max = mn->mn_ai.rssi_a;
2434 	if (mn->mn_ai.rssi_b > rssi_max)
2435 		rssi_max = mn->mn_ai.rssi_b;
2436 	if (mn->mn_ai.rssi_c > rssi_max)
2437 		rssi_max = mn->mn_ai.rssi_c;
2438 
2439 	CVT(mi->ch[0].rssi[0], mn->mn_ai.rssi_a);
2440 	CVT(mi->ch[1].rssi[0], mn->mn_ai.rssi_b);
2441 	CVT(mi->ch[2].rssi[0], mn->mn_ai.rssi_c);
2442 
2443 	mi->ch[0].noise[0] = mn->mn_ai.nf_a;
2444 	mi->ch[1].noise[0] = mn->mn_ai.nf_b;
2445 	mi->ch[2].noise[0] = mn->mn_ai.nf_c;
2446 #undef CVT
2447 }
2448 
2449 static __inline void *
2450 mwl_getrxdma(struct mwl_softc *sc)
2451 {
2452 	struct mwl_jumbo *buf;
2453 	void *data;
2454 
2455 	/*
2456 	 * Allocate from jumbo pool.
2457 	 */
2458 	MWL_RXFREE_LOCK(sc);
2459 	buf = SLIST_FIRST(&sc->sc_rxfree);
2460 	if (buf == NULL) {
2461 		DPRINTF(sc, MWL_DEBUG_ANY,
2462 		    "%s: out of rx dma buffers\n", __func__);
2463 		sc->sc_stats.mst_rx_nodmabuf++;
2464 		data = NULL;
2465 	} else {
2466 		SLIST_REMOVE_HEAD(&sc->sc_rxfree, next);
2467 		sc->sc_nrxfree--;
2468 		data = MWL_JUMBO_BUF2DATA(buf);
2469 	}
2470 	MWL_RXFREE_UNLOCK(sc);
2471 	return data;
2472 }
2473 
2474 static __inline void
2475 mwl_putrxdma(struct mwl_softc *sc, void *data)
2476 {
2477 	struct mwl_jumbo *buf;
2478 
2479 	/* XXX bounds check data */
2480 	MWL_RXFREE_LOCK(sc);
2481 	buf = MWL_JUMBO_DATA2BUF(data);
2482 	SLIST_INSERT_HEAD(&sc->sc_rxfree, buf, next);
2483 	sc->sc_nrxfree++;
2484 	MWL_RXFREE_UNLOCK(sc);
2485 }
2486 
2487 static int
2488 mwl_rxbuf_init(struct mwl_softc *sc, struct mwl_rxbuf *bf)
2489 {
2490 	struct mwl_rxdesc *ds;
2491 
2492 	ds = bf->bf_desc;
2493 	if (bf->bf_data == NULL) {
2494 		bf->bf_data = mwl_getrxdma(sc);
2495 		if (bf->bf_data == NULL) {
2496 			/* mark descriptor to be skipped */
2497 			ds->RxControl = EAGLE_RXD_CTRL_OS_OWN;
2498 			/* NB: don't need PREREAD */
2499 			MWL_RXDESC_SYNC(sc, ds, BUS_DMASYNC_PREWRITE);
2500 			sc->sc_stats.mst_rxbuf_failed++;
2501 			return ENOMEM;
2502 		}
2503 	}
2504 	/*
2505 	 * NB: DMA buffer contents is known to be unmodified
2506 	 *     so there's no need to flush the data cache.
2507 	 */
2508 
2509 	/*
2510 	 * Setup descriptor.
2511 	 */
2512 	ds->QosCtrl = 0;
2513 	ds->RSSI = 0;
2514 	ds->Status = EAGLE_RXD_STATUS_IDLE;
2515 	ds->Channel = 0;
2516 	ds->PktLen = htole16(MWL_AGGR_SIZE);
2517 	ds->SQ2 = 0;
2518 	ds->pPhysBuffData = htole32(MWL_JUMBO_DMA_ADDR(sc, bf->bf_data));
2519 	/* NB: don't touch pPhysNext, set once */
2520 	ds->RxControl = EAGLE_RXD_CTRL_DRIVER_OWN;
2521 	MWL_RXDESC_SYNC(sc, ds, BUS_DMASYNC_PREREAD | BUS_DMASYNC_PREWRITE);
2522 
2523 	return 0;
2524 }
2525 
2526 static void
2527 mwl_ext_free(struct mbuf *m)
2528 {
2529 	struct mwl_softc *sc = m->m_ext.ext_arg1;
2530 
2531 	/* XXX bounds check data */
2532 	mwl_putrxdma(sc, m->m_ext.ext_buf);
2533 	/*
2534 	 * If we were previously blocked by a lack of rx dma buffers
2535 	 * check if we now have enough to restart rx interrupt handling.
2536 	 * NB: we know we are called at splvm which is above splnet.
2537 	 */
2538 	if (sc->sc_rxblocked && sc->sc_nrxfree > mwl_rxdmalow) {
2539 		sc->sc_rxblocked = 0;
2540 		mwl_hal_intrset(sc->sc_mh, sc->sc_imask);
2541 	}
2542 }
2543 
2544 struct mwl_frame_bar {
2545 	u_int8_t	i_fc[2];
2546 	u_int8_t	i_dur[2];
2547 	u_int8_t	i_ra[IEEE80211_ADDR_LEN];
2548 	u_int8_t	i_ta[IEEE80211_ADDR_LEN];
2549 	/* ctl, seq, FCS */
2550 } __packed;
2551 
2552 /*
2553  * Like ieee80211_anyhdrsize, but handles BAR frames
2554  * specially so the logic below to piece the 802.11
2555  * header together works.
2556  */
2557 static __inline int
2558 mwl_anyhdrsize(const void *data)
2559 {
2560 	const struct ieee80211_frame *wh = data;
2561 
2562 	if ((wh->i_fc[0]&IEEE80211_FC0_TYPE_MASK) == IEEE80211_FC0_TYPE_CTL) {
2563 		switch (wh->i_fc[0] & IEEE80211_FC0_SUBTYPE_MASK) {
2564 		case IEEE80211_FC0_SUBTYPE_CTS:
2565 		case IEEE80211_FC0_SUBTYPE_ACK:
2566 			return sizeof(struct ieee80211_frame_ack);
2567 		case IEEE80211_FC0_SUBTYPE_BAR:
2568 			return sizeof(struct mwl_frame_bar);
2569 		}
2570 		return sizeof(struct ieee80211_frame_min);
2571 	} else
2572 		return ieee80211_hdrsize(data);
2573 }
2574 
2575 static void
2576 mwl_handlemicerror(struct ieee80211com *ic, const uint8_t *data)
2577 {
2578 	const struct ieee80211_frame *wh;
2579 	struct ieee80211_node *ni;
2580 
2581 	wh = (const struct ieee80211_frame *)(data + sizeof(uint16_t));
2582 	ni = ieee80211_find_rxnode(ic, (const struct ieee80211_frame_min *) wh);
2583 	if (ni != NULL) {
2584 		ieee80211_notify_michael_failure(ni->ni_vap, wh, 0);
2585 		ieee80211_free_node(ni);
2586 	}
2587 }
2588 
2589 /*
2590  * Convert hardware signal strength to rssi.  The value
2591  * provided by the device has the noise floor added in;
2592  * we need to compensate for this but we don't have that
2593  * so we use a fixed value.
2594  *
2595  * The offset of 8 is good for both 2.4 and 5GHz.  The LNA
2596  * offset is already set as part of the initial gain.  This
2597  * will give at least +/- 3dB for 2.4GHz and +/- 5dB for 5GHz.
2598  */
2599 static __inline int
2600 cvtrssi(uint8_t ssi)
2601 {
2602 	int rssi = (int) ssi + 8;
2603 	/* XXX hack guess until we have a real noise floor */
2604 	rssi = 2*(87 - rssi);	/* NB: .5 dBm units */
2605 	return (rssi < 0 ? 0 : rssi > 127 ? 127 : rssi);
2606 }
2607 
2608 static void
2609 mwl_rx_proc(void *arg, int npending)
2610 {
2611 	struct mwl_softc *sc = arg;
2612 	struct ieee80211com *ic = &sc->sc_ic;
2613 	struct mwl_rxbuf *bf;
2614 	struct mwl_rxdesc *ds;
2615 	struct mbuf *m;
2616 	struct ieee80211_qosframe *wh;
2617 	struct ieee80211_node *ni;
2618 	struct mwl_node *mn;
2619 	int off, len, hdrlen, pktlen, rssi, ntodo;
2620 	uint8_t *data, status;
2621 	void *newdata;
2622 	int16_t nf;
2623 
2624 	DPRINTF(sc, MWL_DEBUG_RX_PROC, "%s: pending %u rdptr 0x%x wrptr 0x%x\n",
2625 	    __func__, npending, RD4(sc, sc->sc_hwspecs.rxDescRead),
2626 	    RD4(sc, sc->sc_hwspecs.rxDescWrite));
2627 	nf = -96;			/* XXX */
2628 	bf = sc->sc_rxnext;
2629 	for (ntodo = mwl_rxquota; ntodo > 0; ntodo--) {
2630 		if (bf == NULL)
2631 			bf = STAILQ_FIRST(&sc->sc_rxbuf);
2632 		ds = bf->bf_desc;
2633 		data = bf->bf_data;
2634 		if (data == NULL) {
2635 			/*
2636 			 * If data allocation failed previously there
2637 			 * will be no buffer; try again to re-populate it.
2638 			 * Note the firmware will not advance to the next
2639 			 * descriptor with a dma buffer so we must mimic
2640 			 * this or we'll get out of sync.
2641 			 */
2642 			DPRINTF(sc, MWL_DEBUG_ANY,
2643 			    "%s: rx buf w/o dma memory\n", __func__);
2644 			(void) mwl_rxbuf_init(sc, bf);
2645 			sc->sc_stats.mst_rx_dmabufmissing++;
2646 			break;
2647 		}
2648 		MWL_RXDESC_SYNC(sc, ds,
2649 		    BUS_DMASYNC_POSTREAD | BUS_DMASYNC_POSTWRITE);
2650 		if (ds->RxControl != EAGLE_RXD_CTRL_DMA_OWN)
2651 			break;
2652 #ifdef MWL_DEBUG
2653 		if (sc->sc_debug & MWL_DEBUG_RECV_DESC)
2654 			mwl_printrxbuf(bf, 0);
2655 #endif
2656 		status = ds->Status;
2657 		if (status & EAGLE_RXD_STATUS_DECRYPT_ERR_MASK) {
2658 			counter_u64_add(ic->ic_ierrors, 1);
2659 			sc->sc_stats.mst_rx_crypto++;
2660 			/*
2661 			 * NB: Check EAGLE_RXD_STATUS_GENERAL_DECRYPT_ERR
2662 			 *     for backwards compatibility.
2663 			 */
2664 			if (status != EAGLE_RXD_STATUS_GENERAL_DECRYPT_ERR &&
2665 			    (status & EAGLE_RXD_STATUS_TKIP_MIC_DECRYPT_ERR)) {
2666 				/*
2667 				 * MIC error, notify upper layers.
2668 				 */
2669 				bus_dmamap_sync(sc->sc_rxdmat, sc->sc_rxmap,
2670 				    BUS_DMASYNC_POSTREAD);
2671 				mwl_handlemicerror(ic, data);
2672 				sc->sc_stats.mst_rx_tkipmic++;
2673 			}
2674 			/* XXX too painful to tap packets */
2675 			goto rx_next;
2676 		}
2677 		/*
2678 		 * Sync the data buffer.
2679 		 */
2680 		len = le16toh(ds->PktLen);
2681 		bus_dmamap_sync(sc->sc_rxdmat, sc->sc_rxmap, BUS_DMASYNC_POSTREAD);
2682 		/*
2683 		 * The 802.11 header is provided all or in part at the front;
2684 		 * use it to calculate the true size of the header that we'll
2685 		 * construct below.  We use this to figure out where to copy
2686 		 * payload prior to constructing the header.
2687 		 */
2688 		hdrlen = mwl_anyhdrsize(data + sizeof(uint16_t));
2689 		off = sizeof(uint16_t) + sizeof(struct ieee80211_frame_addr4);
2690 
2691 		/* calculate rssi early so we can re-use for each aggregate */
2692 		rssi = cvtrssi(ds->RSSI);
2693 
2694 		pktlen = hdrlen + (len - off);
2695 		/*
2696 		 * NB: we know our frame is at least as large as
2697 		 * IEEE80211_MIN_LEN because there is a 4-address
2698 		 * frame at the front.  Hence there's no need to
2699 		 * vet the packet length.  If the frame in fact
2700 		 * is too small it should be discarded at the
2701 		 * net80211 layer.
2702 		 */
2703 
2704 		/*
2705 		 * Attach dma buffer to an mbuf.  We tried
2706 		 * doing this based on the packet size (i.e.
2707 		 * copying small packets) but it turns out to
2708 		 * be a net loss.  The tradeoff might be system
2709 		 * dependent (cache architecture is important).
2710 		 */
2711 		MGETHDR(m, M_NOWAIT, MT_DATA);
2712 		if (m == NULL) {
2713 			DPRINTF(sc, MWL_DEBUG_ANY,
2714 			    "%s: no rx mbuf\n", __func__);
2715 			sc->sc_stats.mst_rx_nombuf++;
2716 			goto rx_next;
2717 		}
2718 		/*
2719 		 * Acquire the replacement dma buffer before
2720 		 * processing the frame.  If we're out of dma
2721 		 * buffers we disable rx interrupts and wait
2722 		 * for the free pool to reach mlw_rxdmalow buffers
2723 		 * before starting to do work again.  If the firmware
2724 		 * runs out of descriptors then it will toss frames
2725 		 * which is better than our doing it as that can
2726 		 * starve our processing.  It is also important that
2727 		 * we always process rx'd frames in case they are
2728 		 * A-MPDU as otherwise the host's view of the BA
2729 		 * window may get out of sync with the firmware.
2730 		 */
2731 		newdata = mwl_getrxdma(sc);
2732 		if (newdata == NULL) {
2733 			/* NB: stat+msg in mwl_getrxdma */
2734 			m_free(m);
2735 			/* disable RX interrupt and mark state */
2736 			mwl_hal_intrset(sc->sc_mh,
2737 			    sc->sc_imask &~ MACREG_A2HRIC_BIT_RX_RDY);
2738 			sc->sc_rxblocked = 1;
2739 			ieee80211_drain(ic);
2740 			/* XXX check rxblocked and immediately start again? */
2741 			goto rx_stop;
2742 		}
2743 		bf->bf_data = newdata;
2744 		/*
2745 		 * Attach the dma buffer to the mbuf;
2746 		 * mwl_rxbuf_init will re-setup the rx
2747 		 * descriptor using the replacement dma
2748 		 * buffer we just installed above.
2749 		 */
2750 		m_extadd(m, data, MWL_AGGR_SIZE, mwl_ext_free, sc, NULL, 0,
2751 		    EXT_NET_DRV);
2752 		m->m_data += off - hdrlen;
2753 		m->m_pkthdr.len = m->m_len = pktlen;
2754 		/* NB: dma buffer assumed read-only */
2755 
2756 		/*
2757 		 * Piece 802.11 header together.
2758 		 */
2759 		wh = mtod(m, struct ieee80211_qosframe *);
2760 		/* NB: don't need to do this sometimes but ... */
2761 		/* XXX special case so we can memcpy after m_devget? */
2762 		ovbcopy(data + sizeof(uint16_t), wh, hdrlen);
2763 		if (IEEE80211_QOS_HAS_SEQ(wh))
2764 			*(uint16_t *)ieee80211_getqos(wh) = ds->QosCtrl;
2765 		/*
2766 		 * The f/w strips WEP header but doesn't clear
2767 		 * the WEP bit; mark the packet with M_WEP so
2768 		 * net80211 will treat the data as decrypted.
2769 		 * While here also clear the PWR_MGT bit since
2770 		 * power save is handled by the firmware and
2771 		 * passing this up will potentially cause the
2772 		 * upper layer to put a station in power save
2773 		 * (except when configured with MWL_HOST_PS_SUPPORT).
2774 		 */
2775 		if (wh->i_fc[1] & IEEE80211_FC1_PROTECTED)
2776 			m->m_flags |= M_WEP;
2777 #ifdef MWL_HOST_PS_SUPPORT
2778 		wh->i_fc[1] &= ~IEEE80211_FC1_PROTECTED;
2779 #else
2780 		wh->i_fc[1] &= ~(IEEE80211_FC1_PROTECTED |
2781 		    IEEE80211_FC1_PWR_MGT);
2782 #endif
2783 
2784 		if (ieee80211_radiotap_active(ic)) {
2785 			struct mwl_rx_radiotap_header *tap = &sc->sc_rx_th;
2786 
2787 			tap->wr_flags = 0;
2788 			tap->wr_rate = ds->Rate;
2789 			tap->wr_antsignal = rssi + nf;
2790 			tap->wr_antnoise = nf;
2791 		}
2792 		if (IFF_DUMPPKTS_RECV(sc, wh)) {
2793 			ieee80211_dump_pkt(ic, mtod(m, caddr_t),
2794 			    len, ds->Rate, rssi);
2795 		}
2796 		/* dispatch */
2797 		ni = ieee80211_find_rxnode(ic,
2798 		    (const struct ieee80211_frame_min *) wh);
2799 		if (ni != NULL) {
2800 			mn = MWL_NODE(ni);
2801 #ifdef MWL_ANT_INFO_SUPPORT
2802 			mn->mn_ai.rssi_a = ds->ai.rssi_a;
2803 			mn->mn_ai.rssi_b = ds->ai.rssi_b;
2804 			mn->mn_ai.rssi_c = ds->ai.rssi_c;
2805 			mn->mn_ai.rsvd1 = rssi;
2806 #endif
2807 			/* tag AMPDU aggregates for reorder processing */
2808 			if (ni->ni_flags & IEEE80211_NODE_HT)
2809 				m->m_flags |= M_AMPDU;
2810 			(void) ieee80211_input(ni, m, rssi, nf);
2811 			ieee80211_free_node(ni);
2812 		} else
2813 			(void) ieee80211_input_all(ic, m, rssi, nf);
2814 rx_next:
2815 		/* NB: ignore ENOMEM so we process more descriptors */
2816 		(void) mwl_rxbuf_init(sc, bf);
2817 		bf = STAILQ_NEXT(bf, bf_list);
2818 	}
2819 rx_stop:
2820 	sc->sc_rxnext = bf;
2821 
2822 	if (mbufq_first(&sc->sc_snd) != NULL) {
2823 		/* NB: kick fw; the tx thread may have been preempted */
2824 		mwl_hal_txstart(sc->sc_mh, 0);
2825 		mwl_start(sc);
2826 	}
2827 }
2828 
2829 static void
2830 mwl_txq_init(struct mwl_softc *sc, struct mwl_txq *txq, int qnum)
2831 {
2832 	struct mwl_txbuf *bf, *bn;
2833 	struct mwl_txdesc *ds;
2834 
2835 	MWL_TXQ_LOCK_INIT(sc, txq);
2836 	txq->qnum = qnum;
2837 	txq->txpri = 0;	/* XXX */
2838 #if 0
2839 	/* NB: q setup by mwl_txdma_setup XXX */
2840 	STAILQ_INIT(&txq->free);
2841 #endif
2842 	STAILQ_FOREACH(bf, &txq->free, bf_list) {
2843 		bf->bf_txq = txq;
2844 
2845 		ds = bf->bf_desc;
2846 		bn = STAILQ_NEXT(bf, bf_list);
2847 		if (bn == NULL)
2848 			bn = STAILQ_FIRST(&txq->free);
2849 		ds->pPhysNext = htole32(bn->bf_daddr);
2850 	}
2851 	STAILQ_INIT(&txq->active);
2852 }
2853 
2854 /*
2855  * Setup a hardware data transmit queue for the specified
2856  * access control.  We record the mapping from ac's
2857  * to h/w queues for use by mwl_tx_start.
2858  */
2859 static int
2860 mwl_tx_setup(struct mwl_softc *sc, int ac, int mvtype)
2861 {
2862 	struct mwl_txq *txq;
2863 
2864 	if (ac >= nitems(sc->sc_ac2q)) {
2865 		device_printf(sc->sc_dev, "AC %u out of range, max %zu!\n",
2866 			ac, nitems(sc->sc_ac2q));
2867 		return 0;
2868 	}
2869 	if (mvtype >= MWL_NUM_TX_QUEUES) {
2870 		device_printf(sc->sc_dev, "mvtype %u out of range, max %u!\n",
2871 			mvtype, MWL_NUM_TX_QUEUES);
2872 		return 0;
2873 	}
2874 	txq = &sc->sc_txq[mvtype];
2875 	mwl_txq_init(sc, txq, mvtype);
2876 	sc->sc_ac2q[ac] = txq;
2877 	return 1;
2878 }
2879 
2880 /*
2881  * Update WME parameters for a transmit queue.
2882  */
2883 static int
2884 mwl_txq_update(struct mwl_softc *sc, int ac)
2885 {
2886 #define	MWL_EXPONENT_TO_VALUE(v)	((1<<v)-1)
2887 	struct ieee80211com *ic = &sc->sc_ic;
2888 	struct chanAccParams chp;
2889 	struct mwl_txq *txq = sc->sc_ac2q[ac];
2890 	struct wmeParams *wmep;
2891 	struct mwl_hal *mh = sc->sc_mh;
2892 	int aifs, cwmin, cwmax, txoplim;
2893 
2894 	ieee80211_wme_ic_getparams(ic, &chp);
2895 	wmep = &chp.cap_wmeParams[ac];
2896 
2897 	aifs = wmep->wmep_aifsn;
2898 	/* XXX in sta mode need to pass log values for cwmin/max */
2899 	cwmin = MWL_EXPONENT_TO_VALUE(wmep->wmep_logcwmin);
2900 	cwmax = MWL_EXPONENT_TO_VALUE(wmep->wmep_logcwmax);
2901 	txoplim = wmep->wmep_txopLimit;		/* NB: units of 32us */
2902 
2903 	if (mwl_hal_setedcaparams(mh, txq->qnum, cwmin, cwmax, aifs, txoplim)) {
2904 		device_printf(sc->sc_dev, "unable to update hardware queue "
2905 			"parameters for %s traffic!\n",
2906 			ieee80211_wme_acnames[ac]);
2907 		return 0;
2908 	}
2909 	return 1;
2910 #undef MWL_EXPONENT_TO_VALUE
2911 }
2912 
2913 /*
2914  * Callback from the 802.11 layer to update WME parameters.
2915  */
2916 static int
2917 mwl_wme_update(struct ieee80211com *ic)
2918 {
2919 	struct mwl_softc *sc = ic->ic_softc;
2920 
2921 	return !mwl_txq_update(sc, WME_AC_BE) ||
2922 	    !mwl_txq_update(sc, WME_AC_BK) ||
2923 	    !mwl_txq_update(sc, WME_AC_VI) ||
2924 	    !mwl_txq_update(sc, WME_AC_VO) ? EIO : 0;
2925 }
2926 
2927 /*
2928  * Reclaim resources for a setup queue.
2929  */
2930 static void
2931 mwl_tx_cleanupq(struct mwl_softc *sc, struct mwl_txq *txq)
2932 {
2933 	/* XXX hal work? */
2934 	MWL_TXQ_LOCK_DESTROY(txq);
2935 }
2936 
2937 /*
2938  * Reclaim all tx queue resources.
2939  */
2940 static void
2941 mwl_tx_cleanup(struct mwl_softc *sc)
2942 {
2943 	int i;
2944 
2945 	for (i = 0; i < MWL_NUM_TX_QUEUES; i++)
2946 		mwl_tx_cleanupq(sc, &sc->sc_txq[i]);
2947 }
2948 
2949 static int
2950 mwl_tx_dmasetup(struct mwl_softc *sc, struct mwl_txbuf *bf, struct mbuf *m0)
2951 {
2952 	struct mbuf *m;
2953 	int error;
2954 
2955 	/*
2956 	 * Load the DMA map so any coalescing is done.  This
2957 	 * also calculates the number of descriptors we need.
2958 	 */
2959 	error = bus_dmamap_load_mbuf_sg(sc->sc_dmat, bf->bf_dmamap, m0,
2960 				     bf->bf_segs, &bf->bf_nseg,
2961 				     BUS_DMA_NOWAIT);
2962 	if (error == EFBIG) {
2963 		/* XXX packet requires too many descriptors */
2964 		bf->bf_nseg = MWL_TXDESC+1;
2965 	} else if (error != 0) {
2966 		sc->sc_stats.mst_tx_busdma++;
2967 		m_freem(m0);
2968 		return error;
2969 	}
2970 	/*
2971 	 * Discard null packets and check for packets that
2972 	 * require too many TX descriptors.  We try to convert
2973 	 * the latter to a cluster.
2974 	 */
2975 	if (error == EFBIG) {		/* too many desc's, linearize */
2976 		sc->sc_stats.mst_tx_linear++;
2977 #if MWL_TXDESC > 1
2978 		m = m_collapse(m0, M_NOWAIT, MWL_TXDESC);
2979 #else
2980 		m = m_defrag(m0, M_NOWAIT);
2981 #endif
2982 		if (m == NULL) {
2983 			m_freem(m0);
2984 			sc->sc_stats.mst_tx_nombuf++;
2985 			return ENOMEM;
2986 		}
2987 		m0 = m;
2988 		error = bus_dmamap_load_mbuf_sg(sc->sc_dmat, bf->bf_dmamap, m0,
2989 					     bf->bf_segs, &bf->bf_nseg,
2990 					     BUS_DMA_NOWAIT);
2991 		if (error != 0) {
2992 			sc->sc_stats.mst_tx_busdma++;
2993 			m_freem(m0);
2994 			return error;
2995 		}
2996 		KASSERT(bf->bf_nseg <= MWL_TXDESC,
2997 		    ("too many segments after defrag; nseg %u", bf->bf_nseg));
2998 	} else if (bf->bf_nseg == 0) {		/* null packet, discard */
2999 		sc->sc_stats.mst_tx_nodata++;
3000 		m_freem(m0);
3001 		return EIO;
3002 	}
3003 	DPRINTF(sc, MWL_DEBUG_XMIT, "%s: m %p len %u\n",
3004 		__func__, m0, m0->m_pkthdr.len);
3005 	bus_dmamap_sync(sc->sc_dmat, bf->bf_dmamap, BUS_DMASYNC_PREWRITE);
3006 	bf->bf_m = m0;
3007 
3008 	return 0;
3009 }
3010 
3011 static __inline int
3012 mwl_cvtlegacyrate(int rate)
3013 {
3014 	switch (rate) {
3015 	case 2:	 return 0;
3016 	case 4:	 return 1;
3017 	case 11: return 2;
3018 	case 22: return 3;
3019 	case 44: return 4;
3020 	case 12: return 5;
3021 	case 18: return 6;
3022 	case 24: return 7;
3023 	case 36: return 8;
3024 	case 48: return 9;
3025 	case 72: return 10;
3026 	case 96: return 11;
3027 	case 108:return 12;
3028 	}
3029 	return 0;
3030 }
3031 
3032 /*
3033  * Calculate fixed tx rate information per client state;
3034  * this value is suitable for writing to the Format field
3035  * of a tx descriptor.
3036  */
3037 static uint16_t
3038 mwl_calcformat(uint8_t rate, const struct ieee80211_node *ni)
3039 {
3040 	uint16_t fmt;
3041 
3042 	fmt = SM(3, EAGLE_TXD_ANTENNA)
3043 	    | (IEEE80211_IS_CHAN_HT40D(ni->ni_chan) ?
3044 		EAGLE_TXD_EXTCHAN_LO : EAGLE_TXD_EXTCHAN_HI);
3045 	if (rate & IEEE80211_RATE_MCS) {	/* HT MCS */
3046 		fmt |= EAGLE_TXD_FORMAT_HT
3047 		    /* NB: 0x80 implicitly stripped from ucastrate */
3048 		    | SM(rate, EAGLE_TXD_RATE);
3049 		/* XXX short/long GI may be wrong; re-check */
3050 		if (IEEE80211_IS_CHAN_HT40(ni->ni_chan)) {
3051 			fmt |= EAGLE_TXD_CHW_40
3052 			    | (ni->ni_htcap & IEEE80211_HTCAP_SHORTGI40 ?
3053 			        EAGLE_TXD_GI_SHORT : EAGLE_TXD_GI_LONG);
3054 		} else {
3055 			fmt |= EAGLE_TXD_CHW_20
3056 			    | (ni->ni_htcap & IEEE80211_HTCAP_SHORTGI20 ?
3057 			        EAGLE_TXD_GI_SHORT : EAGLE_TXD_GI_LONG);
3058 		}
3059 	} else {			/* legacy rate */
3060 		fmt |= EAGLE_TXD_FORMAT_LEGACY
3061 		    | SM(mwl_cvtlegacyrate(rate), EAGLE_TXD_RATE)
3062 		    | EAGLE_TXD_CHW_20
3063 		    /* XXX iv_flags & IEEE80211_F_SHPREAMBLE? */
3064 		    | (ni->ni_capinfo & IEEE80211_CAPINFO_SHORT_PREAMBLE ?
3065 			EAGLE_TXD_PREAMBLE_SHORT : EAGLE_TXD_PREAMBLE_LONG);
3066 	}
3067 	return fmt;
3068 }
3069 
3070 static int
3071 mwl_tx_start(struct mwl_softc *sc, struct ieee80211_node *ni, struct mwl_txbuf *bf,
3072     struct mbuf *m0)
3073 {
3074 	struct ieee80211com *ic = &sc->sc_ic;
3075 	struct ieee80211vap *vap = ni->ni_vap;
3076 	int error, iswep, ismcast;
3077 	int hdrlen, copyhdrlen, pktlen;
3078 	struct mwl_txdesc *ds;
3079 	struct mwl_txq *txq;
3080 	struct ieee80211_frame *wh;
3081 	struct mwltxrec *tr;
3082 	struct mwl_node *mn;
3083 	uint16_t qos;
3084 #if MWL_TXDESC > 1
3085 	int i;
3086 #endif
3087 
3088 	wh = mtod(m0, struct ieee80211_frame *);
3089 	iswep = wh->i_fc[1] & IEEE80211_FC1_PROTECTED;
3090 	ismcast = IEEE80211_IS_MULTICAST(wh->i_addr1);
3091 	hdrlen = ieee80211_anyhdrsize(wh);
3092 	copyhdrlen = hdrlen;
3093 	pktlen = m0->m_pkthdr.len;
3094 	if (IEEE80211_QOS_HAS_SEQ(wh)) {
3095 		qos = *(uint16_t *)ieee80211_getqos(wh);
3096 		if (IEEE80211_IS_DSTODS(wh))
3097 			copyhdrlen -= sizeof(qos);
3098 	} else
3099 		qos = 0;
3100 
3101 	if (iswep) {
3102 		const struct ieee80211_cipher *cip;
3103 		struct ieee80211_key *k;
3104 
3105 		/*
3106 		 * Construct the 802.11 header+trailer for an encrypted
3107 		 * frame. The only reason this can fail is because of an
3108 		 * unknown or unsupported cipher/key type.
3109 		 *
3110 		 * NB: we do this even though the firmware will ignore
3111 		 *     what we've done for WEP and TKIP as we need the
3112 		 *     ExtIV filled in for CCMP and this also adjusts
3113 		 *     the headers which simplifies our work below.
3114 		 */
3115 		k = ieee80211_crypto_encap(ni, m0);
3116 		if (k == NULL) {
3117 			/*
3118 			 * This can happen when the key is yanked after the
3119 			 * frame was queued.  Just discard the frame; the
3120 			 * 802.11 layer counts failures and provides
3121 			 * debugging/diagnostics.
3122 			 */
3123 			m_freem(m0);
3124 			return EIO;
3125 		}
3126 		/*
3127 		 * Adjust the packet length for the crypto additions
3128 		 * done during encap and any other bits that the f/w
3129 		 * will add later on.
3130 		 */
3131 		cip = k->wk_cipher;
3132 		pktlen += cip->ic_header + cip->ic_miclen + cip->ic_trailer;
3133 
3134 		/* packet header may have moved, reset our local pointer */
3135 		wh = mtod(m0, struct ieee80211_frame *);
3136 	}
3137 
3138 	if (ieee80211_radiotap_active_vap(vap)) {
3139 		sc->sc_tx_th.wt_flags = 0;	/* XXX */
3140 		if (iswep)
3141 			sc->sc_tx_th.wt_flags |= IEEE80211_RADIOTAP_F_WEP;
3142 #if 0
3143 		sc->sc_tx_th.wt_rate = ds->DataRate;
3144 #endif
3145 		sc->sc_tx_th.wt_txpower = ni->ni_txpower;
3146 		sc->sc_tx_th.wt_antenna = sc->sc_txantenna;
3147 
3148 		ieee80211_radiotap_tx(vap, m0);
3149 	}
3150 	/*
3151 	 * Copy up/down the 802.11 header; the firmware requires
3152 	 * we present a 2-byte payload length followed by a
3153 	 * 4-address header (w/o QoS), followed (optionally) by
3154 	 * any WEP/ExtIV header (but only filled in for CCMP).
3155 	 * We are assured the mbuf has sufficient headroom to
3156 	 * prepend in-place by the setup of ic_headroom in
3157 	 * mwl_attach.
3158 	 */
3159 	if (hdrlen < sizeof(struct mwltxrec)) {
3160 		const int space = sizeof(struct mwltxrec) - hdrlen;
3161 		if (M_LEADINGSPACE(m0) < space) {
3162 			/* NB: should never happen */
3163 			device_printf(sc->sc_dev,
3164 			    "not enough headroom, need %d found %zd, "
3165 			    "m_flags 0x%x m_len %d\n",
3166 			    space, M_LEADINGSPACE(m0), m0->m_flags, m0->m_len);
3167 			ieee80211_dump_pkt(ic,
3168 			    mtod(m0, const uint8_t *), m0->m_len, 0, -1);
3169 			m_freem(m0);
3170 			sc->sc_stats.mst_tx_noheadroom++;
3171 			return EIO;
3172 		}
3173 		M_PREPEND(m0, space, M_NOWAIT);
3174 	}
3175 	tr = mtod(m0, struct mwltxrec *);
3176 	if (wh != (struct ieee80211_frame *) &tr->wh)
3177 		ovbcopy(wh, &tr->wh, hdrlen);
3178 	/*
3179 	 * Note: the "firmware length" is actually the length
3180 	 * of the fully formed "802.11 payload".  That is, it's
3181 	 * everything except for the 802.11 header.  In particular
3182 	 * this includes all crypto material including the MIC!
3183 	 */
3184 	tr->fwlen = htole16(pktlen - hdrlen);
3185 
3186 	/*
3187 	 * Load the DMA map so any coalescing is done.  This
3188 	 * also calculates the number of descriptors we need.
3189 	 */
3190 	error = mwl_tx_dmasetup(sc, bf, m0);
3191 	if (error != 0) {
3192 		/* NB: stat collected in mwl_tx_dmasetup */
3193 		DPRINTF(sc, MWL_DEBUG_XMIT,
3194 		    "%s: unable to setup dma\n", __func__);
3195 		return error;
3196 	}
3197 	bf->bf_node = ni;			/* NB: held reference */
3198 	m0 = bf->bf_m;				/* NB: may have changed */
3199 	tr = mtod(m0, struct mwltxrec *);
3200 	wh = (struct ieee80211_frame *)&tr->wh;
3201 
3202 	/*
3203 	 * Formulate tx descriptor.
3204 	 */
3205 	ds = bf->bf_desc;
3206 	txq = bf->bf_txq;
3207 
3208 	ds->QosCtrl = qos;			/* NB: already little-endian */
3209 #if MWL_TXDESC == 1
3210 	/*
3211 	 * NB: multiframes should be zero because the descriptors
3212 	 *     are initialized to zero.  This should handle the case
3213 	 *     where the driver is built with MWL_TXDESC=1 but we are
3214 	 *     using firmware with multi-segment support.
3215 	 */
3216 	ds->PktPtr = htole32(bf->bf_segs[0].ds_addr);
3217 	ds->PktLen = htole16(bf->bf_segs[0].ds_len);
3218 #else
3219 	ds->multiframes = htole32(bf->bf_nseg);
3220 	ds->PktLen = htole16(m0->m_pkthdr.len);
3221 	for (i = 0; i < bf->bf_nseg; i++) {
3222 		ds->PktPtrArray[i] = htole32(bf->bf_segs[i].ds_addr);
3223 		ds->PktLenArray[i] = htole16(bf->bf_segs[i].ds_len);
3224 	}
3225 #endif
3226 	/* NB: pPhysNext, DataRate, and SapPktInfo setup once, don't touch */
3227 	ds->Format = 0;
3228 	ds->pad = 0;
3229 	ds->ack_wcb_addr = 0;
3230 
3231 	mn = MWL_NODE(ni);
3232 	/*
3233 	 * Select transmit rate.
3234 	 */
3235 	switch (wh->i_fc[0] & IEEE80211_FC0_TYPE_MASK) {
3236 	case IEEE80211_FC0_TYPE_MGT:
3237 		sc->sc_stats.mst_tx_mgmt++;
3238 		/* fall thru... */
3239 	case IEEE80211_FC0_TYPE_CTL:
3240 		/* NB: assign to BE q to avoid bursting */
3241 		ds->TxPriority = MWL_WME_AC_BE;
3242 		break;
3243 	case IEEE80211_FC0_TYPE_DATA:
3244 		if (!ismcast) {
3245 			const struct ieee80211_txparam *tp = ni->ni_txparms;
3246 			/*
3247 			 * EAPOL frames get forced to a fixed rate and w/o
3248 			 * aggregation; otherwise check for any fixed rate
3249 			 * for the client (may depend on association state).
3250 			 */
3251 			if (m0->m_flags & M_EAPOL) {
3252 				const struct mwl_vap *mvp = MWL_VAP_CONST(vap);
3253 				ds->Format = mvp->mv_eapolformat;
3254 				ds->pad = htole16(
3255 				    EAGLE_TXD_FIXED_RATE | EAGLE_TXD_DONT_AGGR);
3256 			} else if (tp->ucastrate != IEEE80211_FIXED_RATE_NONE) {
3257 				/* XXX pre-calculate per node */
3258 				ds->Format = htole16(
3259 				    mwl_calcformat(tp->ucastrate, ni));
3260 				ds->pad = htole16(EAGLE_TXD_FIXED_RATE);
3261 			}
3262 			/* NB: EAPOL frames will never have qos set */
3263 			if (qos == 0)
3264 				ds->TxPriority = txq->qnum;
3265 #if MWL_MAXBA > 3
3266 			else if (mwl_bastream_match(&mn->mn_ba[3], qos))
3267 				ds->TxPriority = mn->mn_ba[3].txq;
3268 #endif
3269 #if MWL_MAXBA > 2
3270 			else if (mwl_bastream_match(&mn->mn_ba[2], qos))
3271 				ds->TxPriority = mn->mn_ba[2].txq;
3272 #endif
3273 #if MWL_MAXBA > 1
3274 			else if (mwl_bastream_match(&mn->mn_ba[1], qos))
3275 				ds->TxPriority = mn->mn_ba[1].txq;
3276 #endif
3277 #if MWL_MAXBA > 0
3278 			else if (mwl_bastream_match(&mn->mn_ba[0], qos))
3279 				ds->TxPriority = mn->mn_ba[0].txq;
3280 #endif
3281 			else
3282 				ds->TxPriority = txq->qnum;
3283 		} else
3284 			ds->TxPriority = txq->qnum;
3285 		break;
3286 	default:
3287 		device_printf(sc->sc_dev, "bogus frame type 0x%x (%s)\n",
3288 			wh->i_fc[0] & IEEE80211_FC0_TYPE_MASK, __func__);
3289 		sc->sc_stats.mst_tx_badframetype++;
3290 		m_freem(m0);
3291 		return EIO;
3292 	}
3293 
3294 	if (IFF_DUMPPKTS_XMIT(sc))
3295 		ieee80211_dump_pkt(ic,
3296 		    mtod(m0, const uint8_t *)+sizeof(uint16_t),
3297 		    m0->m_len - sizeof(uint16_t), ds->DataRate, -1);
3298 
3299 	MWL_TXQ_LOCK(txq);
3300 	ds->Status = htole32(EAGLE_TXD_STATUS_FW_OWNED);
3301 	STAILQ_INSERT_TAIL(&txq->active, bf, bf_list);
3302 	MWL_TXDESC_SYNC(txq, ds, BUS_DMASYNC_PREREAD | BUS_DMASYNC_PREWRITE);
3303 
3304 	sc->sc_tx_timer = 5;
3305 	MWL_TXQ_UNLOCK(txq);
3306 
3307 	return 0;
3308 }
3309 
3310 static __inline int
3311 mwl_cvtlegacyrix(int rix)
3312 {
3313 	static const int ieeerates[] =
3314 	    { 2, 4, 11, 22, 44, 12, 18, 24, 36, 48, 72, 96, 108 };
3315 	return (rix < nitems(ieeerates) ? ieeerates[rix] : 0);
3316 }
3317 
3318 /*
3319  * Process completed xmit descriptors from the specified queue.
3320  */
3321 static int
3322 mwl_tx_processq(struct mwl_softc *sc, struct mwl_txq *txq)
3323 {
3324 #define	EAGLE_TXD_STATUS_MCAST \
3325 	(EAGLE_TXD_STATUS_MULTICAST_TX | EAGLE_TXD_STATUS_BROADCAST_TX)
3326 	struct ieee80211com *ic = &sc->sc_ic;
3327 	struct mwl_txbuf *bf;
3328 	struct mwl_txdesc *ds;
3329 	struct ieee80211_node *ni;
3330 	struct mwl_node *an;
3331 	int nreaped;
3332 	uint32_t status;
3333 
3334 	DPRINTF(sc, MWL_DEBUG_TX_PROC, "%s: tx queue %u\n", __func__, txq->qnum);
3335 	for (nreaped = 0;; nreaped++) {
3336 		MWL_TXQ_LOCK(txq);
3337 		bf = STAILQ_FIRST(&txq->active);
3338 		if (bf == NULL) {
3339 			MWL_TXQ_UNLOCK(txq);
3340 			break;
3341 		}
3342 		ds = bf->bf_desc;
3343 		MWL_TXDESC_SYNC(txq, ds,
3344 		    BUS_DMASYNC_POSTREAD | BUS_DMASYNC_POSTWRITE);
3345 		if (ds->Status & htole32(EAGLE_TXD_STATUS_FW_OWNED)) {
3346 			MWL_TXQ_UNLOCK(txq);
3347 			break;
3348 		}
3349 		STAILQ_REMOVE_HEAD(&txq->active, bf_list);
3350 		MWL_TXQ_UNLOCK(txq);
3351 
3352 #ifdef MWL_DEBUG
3353 		if (sc->sc_debug & MWL_DEBUG_XMIT_DESC)
3354 			mwl_printtxbuf(bf, txq->qnum, nreaped);
3355 #endif
3356 		ni = bf->bf_node;
3357 		if (ni != NULL) {
3358 			an = MWL_NODE(ni);
3359 			status = le32toh(ds->Status);
3360 			if (status & EAGLE_TXD_STATUS_OK) {
3361 				uint16_t Format = le16toh(ds->Format);
3362 				uint8_t txant = MS(Format, EAGLE_TXD_ANTENNA);
3363 
3364 				sc->sc_stats.mst_ant_tx[txant]++;
3365 				if (status & EAGLE_TXD_STATUS_OK_RETRY)
3366 					sc->sc_stats.mst_tx_retries++;
3367 				if (status & EAGLE_TXD_STATUS_OK_MORE_RETRY)
3368 					sc->sc_stats.mst_tx_mretries++;
3369 				if (txq->qnum >= MWL_WME_AC_VO)
3370 					ic->ic_wme.wme_hipri_traffic++;
3371 				ni->ni_txrate = MS(Format, EAGLE_TXD_RATE);
3372 				if ((Format & EAGLE_TXD_FORMAT_HT) == 0) {
3373 					ni->ni_txrate = mwl_cvtlegacyrix(
3374 					    ni->ni_txrate);
3375 				} else
3376 					ni->ni_txrate |= IEEE80211_RATE_MCS;
3377 				sc->sc_stats.mst_tx_rate = ni->ni_txrate;
3378 			} else {
3379 				if (status & EAGLE_TXD_STATUS_FAILED_LINK_ERROR)
3380 					sc->sc_stats.mst_tx_linkerror++;
3381 				if (status & EAGLE_TXD_STATUS_FAILED_XRETRY)
3382 					sc->sc_stats.mst_tx_xretries++;
3383 				if (status & EAGLE_TXD_STATUS_FAILED_AGING)
3384 					sc->sc_stats.mst_tx_aging++;
3385 				if (bf->bf_m->m_flags & M_FF)
3386 					sc->sc_stats.mst_ff_txerr++;
3387 			}
3388 			if (bf->bf_m->m_flags & M_TXCB)
3389 				/* XXX strip fw len in case header inspected */
3390 				m_adj(bf->bf_m, sizeof(uint16_t));
3391 			ieee80211_tx_complete(ni, bf->bf_m,
3392 			    (status & EAGLE_TXD_STATUS_OK) == 0);
3393 		} else
3394 			m_freem(bf->bf_m);
3395 		ds->Status = htole32(EAGLE_TXD_STATUS_IDLE);
3396 
3397 		bus_dmamap_sync(sc->sc_dmat, bf->bf_dmamap,
3398 		    BUS_DMASYNC_POSTWRITE);
3399 		bus_dmamap_unload(sc->sc_dmat, bf->bf_dmamap);
3400 
3401 		mwl_puttxbuf_tail(txq, bf);
3402 	}
3403 	return nreaped;
3404 #undef EAGLE_TXD_STATUS_MCAST
3405 }
3406 
3407 /*
3408  * Deferred processing of transmit interrupt; special-cased
3409  * for four hardware queues, 0-3.
3410  */
3411 static void
3412 mwl_tx_proc(void *arg, int npending)
3413 {
3414 	struct mwl_softc *sc = arg;
3415 	int nreaped;
3416 
3417 	/*
3418 	 * Process each active queue.
3419 	 */
3420 	nreaped = 0;
3421 	if (!STAILQ_EMPTY(&sc->sc_txq[0].active))
3422 		nreaped += mwl_tx_processq(sc, &sc->sc_txq[0]);
3423 	if (!STAILQ_EMPTY(&sc->sc_txq[1].active))
3424 		nreaped += mwl_tx_processq(sc, &sc->sc_txq[1]);
3425 	if (!STAILQ_EMPTY(&sc->sc_txq[2].active))
3426 		nreaped += mwl_tx_processq(sc, &sc->sc_txq[2]);
3427 	if (!STAILQ_EMPTY(&sc->sc_txq[3].active))
3428 		nreaped += mwl_tx_processq(sc, &sc->sc_txq[3]);
3429 
3430 	if (nreaped != 0) {
3431 		sc->sc_tx_timer = 0;
3432 		if (mbufq_first(&sc->sc_snd) != NULL) {
3433 			/* NB: kick fw; the tx thread may have been preempted */
3434 			mwl_hal_txstart(sc->sc_mh, 0);
3435 			mwl_start(sc);
3436 		}
3437 	}
3438 }
3439 
3440 static void
3441 mwl_tx_draintxq(struct mwl_softc *sc, struct mwl_txq *txq)
3442 {
3443 	struct ieee80211_node *ni;
3444 	struct mwl_txbuf *bf;
3445 	u_int ix;
3446 
3447 	/*
3448 	 * NB: this assumes output has been stopped and
3449 	 *     we do not need to block mwl_tx_tasklet
3450 	 */
3451 	for (ix = 0;; ix++) {
3452 		MWL_TXQ_LOCK(txq);
3453 		bf = STAILQ_FIRST(&txq->active);
3454 		if (bf == NULL) {
3455 			MWL_TXQ_UNLOCK(txq);
3456 			break;
3457 		}
3458 		STAILQ_REMOVE_HEAD(&txq->active, bf_list);
3459 		MWL_TXQ_UNLOCK(txq);
3460 #ifdef MWL_DEBUG
3461 		if (sc->sc_debug & MWL_DEBUG_RESET) {
3462 			struct ieee80211com *ic = &sc->sc_ic;
3463 			const struct mwltxrec *tr =
3464 			    mtod(bf->bf_m, const struct mwltxrec *);
3465 			mwl_printtxbuf(bf, txq->qnum, ix);
3466 			ieee80211_dump_pkt(ic, (const uint8_t *)&tr->wh,
3467 				bf->bf_m->m_len - sizeof(tr->fwlen), 0, -1);
3468 		}
3469 #endif /* MWL_DEBUG */
3470 		bus_dmamap_unload(sc->sc_dmat, bf->bf_dmamap);
3471 		ni = bf->bf_node;
3472 		if (ni != NULL) {
3473 			/*
3474 			 * Reclaim node reference.
3475 			 */
3476 			ieee80211_free_node(ni);
3477 		}
3478 		m_freem(bf->bf_m);
3479 
3480 		mwl_puttxbuf_tail(txq, bf);
3481 	}
3482 }
3483 
3484 /*
3485  * Drain the transmit queues and reclaim resources.
3486  */
3487 static void
3488 mwl_draintxq(struct mwl_softc *sc)
3489 {
3490 	int i;
3491 
3492 	for (i = 0; i < MWL_NUM_TX_QUEUES; i++)
3493 		mwl_tx_draintxq(sc, &sc->sc_txq[i]);
3494 	sc->sc_tx_timer = 0;
3495 }
3496 
3497 #ifdef MWL_DIAGAPI
3498 /*
3499  * Reset the transmit queues to a pristine state after a fw download.
3500  */
3501 static void
3502 mwl_resettxq(struct mwl_softc *sc)
3503 {
3504 	int i;
3505 
3506 	for (i = 0; i < MWL_NUM_TX_QUEUES; i++)
3507 		mwl_txq_reset(sc, &sc->sc_txq[i]);
3508 }
3509 #endif /* MWL_DIAGAPI */
3510 
3511 /*
3512  * Clear the transmit queues of any frames submitted for the
3513  * specified vap.  This is done when the vap is deleted so we
3514  * don't potentially reference the vap after it is gone.
3515  * Note we cannot remove the frames; we only reclaim the node
3516  * reference.
3517  */
3518 static void
3519 mwl_cleartxq(struct mwl_softc *sc, struct ieee80211vap *vap)
3520 {
3521 	struct mwl_txq *txq;
3522 	struct mwl_txbuf *bf;
3523 	int i;
3524 
3525 	for (i = 0; i < MWL_NUM_TX_QUEUES; i++) {
3526 		txq = &sc->sc_txq[i];
3527 		MWL_TXQ_LOCK(txq);
3528 		STAILQ_FOREACH(bf, &txq->active, bf_list) {
3529 			struct ieee80211_node *ni = bf->bf_node;
3530 			if (ni != NULL && ni->ni_vap == vap) {
3531 				bf->bf_node = NULL;
3532 				ieee80211_free_node(ni);
3533 			}
3534 		}
3535 		MWL_TXQ_UNLOCK(txq);
3536 	}
3537 }
3538 
3539 static int
3540 mwl_recv_action(struct ieee80211_node *ni, const struct ieee80211_frame *wh,
3541 	const uint8_t *frm, const uint8_t *efrm)
3542 {
3543 	struct mwl_softc *sc = ni->ni_ic->ic_softc;
3544 	const struct ieee80211_action *ia;
3545 
3546 	ia = (const struct ieee80211_action *) frm;
3547 	if (ia->ia_category == IEEE80211_ACTION_CAT_HT &&
3548 	    ia->ia_action == IEEE80211_ACTION_HT_MIMOPWRSAVE) {
3549 		const struct ieee80211_action_ht_mimopowersave *mps =
3550 		    (const struct ieee80211_action_ht_mimopowersave *) ia;
3551 
3552 		mwl_hal_setmimops(sc->sc_mh, ni->ni_macaddr,
3553 		    mps->am_control & IEEE80211_A_HT_MIMOPWRSAVE_ENA,
3554 		    MS(mps->am_control, IEEE80211_A_HT_MIMOPWRSAVE_MODE));
3555 		return 0;
3556 	} else
3557 		return sc->sc_recv_action(ni, wh, frm, efrm);
3558 }
3559 
3560 static int
3561 mwl_addba_request(struct ieee80211_node *ni, struct ieee80211_tx_ampdu *tap,
3562 	int dialogtoken, int baparamset, int batimeout)
3563 {
3564 	struct mwl_softc *sc = ni->ni_ic->ic_softc;
3565 	struct ieee80211vap *vap = ni->ni_vap;
3566 	struct mwl_node *mn = MWL_NODE(ni);
3567 	struct mwl_bastate *bas;
3568 
3569 	bas = tap->txa_private;
3570 	if (bas == NULL) {
3571 		const MWL_HAL_BASTREAM *sp;
3572 		/*
3573 		 * Check for a free BA stream slot.
3574 		 */
3575 #if MWL_MAXBA > 3
3576 		if (mn->mn_ba[3].bastream == NULL)
3577 			bas = &mn->mn_ba[3];
3578 		else
3579 #endif
3580 #if MWL_MAXBA > 2
3581 		if (mn->mn_ba[2].bastream == NULL)
3582 			bas = &mn->mn_ba[2];
3583 		else
3584 #endif
3585 #if MWL_MAXBA > 1
3586 		if (mn->mn_ba[1].bastream == NULL)
3587 			bas = &mn->mn_ba[1];
3588 		else
3589 #endif
3590 #if MWL_MAXBA > 0
3591 		if (mn->mn_ba[0].bastream == NULL)
3592 			bas = &mn->mn_ba[0];
3593 		else
3594 #endif
3595 		{
3596 			/* sta already has max BA streams */
3597 			/* XXX assign BA stream to highest priority tid */
3598 			DPRINTF(sc, MWL_DEBUG_AMPDU,
3599 			    "%s: already has max bastreams\n", __func__);
3600 			sc->sc_stats.mst_ampdu_reject++;
3601 			return 0;
3602 		}
3603 		/* NB: no held reference to ni */
3604 		sp = mwl_hal_bastream_alloc(MWL_VAP(vap)->mv_hvap,
3605 		    (baparamset & IEEE80211_BAPS_POLICY_IMMEDIATE) != 0,
3606 		    ni->ni_macaddr, tap->txa_tid, ni->ni_htparam,
3607 		    ni, tap);
3608 		if (sp == NULL) {
3609 			/*
3610 			 * No available stream, return 0 so no
3611 			 * a-mpdu aggregation will be done.
3612 			 */
3613 			DPRINTF(sc, MWL_DEBUG_AMPDU,
3614 			    "%s: no bastream available\n", __func__);
3615 			sc->sc_stats.mst_ampdu_nostream++;
3616 			return 0;
3617 		}
3618 		DPRINTF(sc, MWL_DEBUG_AMPDU, "%s: alloc bastream %p\n",
3619 		    __func__, sp);
3620 		/* NB: qos is left zero so we won't match in mwl_tx_start */
3621 		bas->bastream = sp;
3622 		tap->txa_private = bas;
3623 	}
3624 	/* fetch current seq# from the firmware; if available */
3625 	if (mwl_hal_bastream_get_seqno(sc->sc_mh, bas->bastream,
3626 	    vap->iv_opmode == IEEE80211_M_STA ? vap->iv_myaddr : ni->ni_macaddr,
3627 	    &tap->txa_start) != 0)
3628 		tap->txa_start = 0;
3629 	return sc->sc_addba_request(ni, tap, dialogtoken, baparamset, batimeout);
3630 }
3631 
3632 static int
3633 mwl_addba_response(struct ieee80211_node *ni, struct ieee80211_tx_ampdu *tap,
3634 	int code, int baparamset, int batimeout)
3635 {
3636 	struct mwl_softc *sc = ni->ni_ic->ic_softc;
3637 	struct mwl_bastate *bas;
3638 
3639 	bas = tap->txa_private;
3640 	if (bas == NULL) {
3641 		/* XXX should not happen */
3642 		DPRINTF(sc, MWL_DEBUG_AMPDU,
3643 		    "%s: no BA stream allocated, TID %d\n",
3644 		    __func__, tap->txa_tid);
3645 		sc->sc_stats.mst_addba_nostream++;
3646 		return 0;
3647 	}
3648 	if (code == IEEE80211_STATUS_SUCCESS) {
3649 		struct ieee80211vap *vap = ni->ni_vap;
3650 		int bufsiz, error;
3651 
3652 		/*
3653 		 * Tell the firmware to setup the BA stream;
3654 		 * we know resources are available because we
3655 		 * pre-allocated one before forming the request.
3656 		 */
3657 		bufsiz = MS(baparamset, IEEE80211_BAPS_BUFSIZ);
3658 		if (bufsiz == 0)
3659 			bufsiz = IEEE80211_AGGR_BAWMAX;
3660 		error = mwl_hal_bastream_create(MWL_VAP(vap)->mv_hvap,
3661 		    bas->bastream, bufsiz, bufsiz, tap->txa_start);
3662 		if (error != 0) {
3663 			/*
3664 			 * Setup failed, return immediately so no a-mpdu
3665 			 * aggregation will be done.
3666 			 */
3667 			mwl_hal_bastream_destroy(sc->sc_mh, bas->bastream);
3668 			mwl_bastream_free(bas);
3669 			tap->txa_private = NULL;
3670 
3671 			DPRINTF(sc, MWL_DEBUG_AMPDU,
3672 			    "%s: create failed, error %d, bufsiz %d TID %d "
3673 			    "htparam 0x%x\n", __func__, error, bufsiz,
3674 			    tap->txa_tid, ni->ni_htparam);
3675 			sc->sc_stats.mst_bacreate_failed++;
3676 			return 0;
3677 		}
3678 		/* NB: cache txq to avoid ptr indirect */
3679 		mwl_bastream_setup(bas, tap->txa_tid, bas->bastream->txq);
3680 		DPRINTF(sc, MWL_DEBUG_AMPDU,
3681 		    "%s: bastream %p assigned to txq %d TID %d bufsiz %d "
3682 		    "htparam 0x%x\n", __func__, bas->bastream,
3683 		    bas->txq, tap->txa_tid, bufsiz, ni->ni_htparam);
3684 	} else {
3685 		/*
3686 		 * Other side NAK'd us; return the resources.
3687 		 */
3688 		DPRINTF(sc, MWL_DEBUG_AMPDU,
3689 		    "%s: request failed with code %d, destroy bastream %p\n",
3690 		    __func__, code, bas->bastream);
3691 		mwl_hal_bastream_destroy(sc->sc_mh, bas->bastream);
3692 		mwl_bastream_free(bas);
3693 		tap->txa_private = NULL;
3694 	}
3695 	/* NB: firmware sends BAR so we don't need to */
3696 	return sc->sc_addba_response(ni, tap, code, baparamset, batimeout);
3697 }
3698 
3699 static void
3700 mwl_addba_stop(struct ieee80211_node *ni, struct ieee80211_tx_ampdu *tap)
3701 {
3702 	struct mwl_softc *sc = ni->ni_ic->ic_softc;
3703 	struct mwl_bastate *bas;
3704 
3705 	bas = tap->txa_private;
3706 	if (bas != NULL) {
3707 		DPRINTF(sc, MWL_DEBUG_AMPDU, "%s: destroy bastream %p\n",
3708 		    __func__, bas->bastream);
3709 		mwl_hal_bastream_destroy(sc->sc_mh, bas->bastream);
3710 		mwl_bastream_free(bas);
3711 		tap->txa_private = NULL;
3712 	}
3713 	sc->sc_addba_stop(ni, tap);
3714 }
3715 
3716 /*
3717  * Setup the rx data structures.  This should only be
3718  * done once or we may get out of sync with the firmware.
3719  */
3720 static int
3721 mwl_startrecv(struct mwl_softc *sc)
3722 {
3723 	if (!sc->sc_recvsetup) {
3724 		struct mwl_rxbuf *bf, *prev;
3725 		struct mwl_rxdesc *ds;
3726 
3727 		prev = NULL;
3728 		STAILQ_FOREACH(bf, &sc->sc_rxbuf, bf_list) {
3729 			int error = mwl_rxbuf_init(sc, bf);
3730 			if (error != 0) {
3731 				DPRINTF(sc, MWL_DEBUG_RECV,
3732 					"%s: mwl_rxbuf_init failed %d\n",
3733 					__func__, error);
3734 				return error;
3735 			}
3736 			if (prev != NULL) {
3737 				ds = prev->bf_desc;
3738 				ds->pPhysNext = htole32(bf->bf_daddr);
3739 			}
3740 			prev = bf;
3741 		}
3742 		if (prev != NULL) {
3743 			ds = prev->bf_desc;
3744 			ds->pPhysNext =
3745 			    htole32(STAILQ_FIRST(&sc->sc_rxbuf)->bf_daddr);
3746 		}
3747 		sc->sc_recvsetup = 1;
3748 	}
3749 	mwl_mode_init(sc);		/* set filters, etc. */
3750 	return 0;
3751 }
3752 
3753 static MWL_HAL_APMODE
3754 mwl_getapmode(const struct ieee80211vap *vap, struct ieee80211_channel *chan)
3755 {
3756 	MWL_HAL_APMODE mode;
3757 
3758 	if (IEEE80211_IS_CHAN_HT(chan)) {
3759 		if (vap->iv_flags_ht & IEEE80211_FHT_PUREN)
3760 			mode = AP_MODE_N_ONLY;
3761 		else if (IEEE80211_IS_CHAN_5GHZ(chan))
3762 			mode = AP_MODE_AandN;
3763 		else if (vap->iv_flags & IEEE80211_F_PUREG)
3764 			mode = AP_MODE_GandN;
3765 		else
3766 			mode = AP_MODE_BandGandN;
3767 	} else if (IEEE80211_IS_CHAN_ANYG(chan)) {
3768 		if (vap->iv_flags & IEEE80211_F_PUREG)
3769 			mode = AP_MODE_G_ONLY;
3770 		else
3771 			mode = AP_MODE_MIXED;
3772 	} else if (IEEE80211_IS_CHAN_B(chan))
3773 		mode = AP_MODE_B_ONLY;
3774 	else if (IEEE80211_IS_CHAN_A(chan))
3775 		mode = AP_MODE_A_ONLY;
3776 	else
3777 		mode = AP_MODE_MIXED;		/* XXX should not happen? */
3778 	return mode;
3779 }
3780 
3781 static int
3782 mwl_setapmode(struct ieee80211vap *vap, struct ieee80211_channel *chan)
3783 {
3784 	struct mwl_hal_vap *hvap = MWL_VAP(vap)->mv_hvap;
3785 	return mwl_hal_setapmode(hvap, mwl_getapmode(vap, chan));
3786 }
3787 
3788 /*
3789  * Set/change channels.
3790  */
3791 static int
3792 mwl_chan_set(struct mwl_softc *sc, struct ieee80211_channel *chan)
3793 {
3794 	struct mwl_hal *mh = sc->sc_mh;
3795 	struct ieee80211com *ic = &sc->sc_ic;
3796 	MWL_HAL_CHANNEL hchan;
3797 	int maxtxpow;
3798 
3799 	DPRINTF(sc, MWL_DEBUG_RESET, "%s: chan %u MHz/flags 0x%x\n",
3800 	    __func__, chan->ic_freq, chan->ic_flags);
3801 
3802 	/*
3803 	 * Convert to a HAL channel description with
3804 	 * the flags constrained to reflect the current
3805 	 * operating mode.
3806 	 */
3807 	mwl_mapchan(&hchan, chan);
3808 	mwl_hal_intrset(mh, 0);		/* disable interrupts */
3809 #if 0
3810 	mwl_draintxq(sc);		/* clear pending tx frames */
3811 #endif
3812 	mwl_hal_setchannel(mh, &hchan);
3813 	/*
3814 	 * Tx power is cap'd by the regulatory setting and
3815 	 * possibly a user-set limit.  We pass the min of
3816 	 * these to the hal to apply them to the cal data
3817 	 * for this channel.
3818 	 * XXX min bound?
3819 	 */
3820 	maxtxpow = 2*chan->ic_maxregpower;
3821 	if (maxtxpow > ic->ic_txpowlimit)
3822 		maxtxpow = ic->ic_txpowlimit;
3823 	mwl_hal_settxpower(mh, &hchan, maxtxpow / 2);
3824 	/* NB: potentially change mcast/mgt rates */
3825 	mwl_setcurchanrates(sc);
3826 
3827 	/*
3828 	 * Update internal state.
3829 	 */
3830 	sc->sc_tx_th.wt_chan_freq = htole16(chan->ic_freq);
3831 	sc->sc_rx_th.wr_chan_freq = htole16(chan->ic_freq);
3832 	if (IEEE80211_IS_CHAN_A(chan)) {
3833 		sc->sc_tx_th.wt_chan_flags = htole16(IEEE80211_CHAN_A);
3834 		sc->sc_rx_th.wr_chan_flags = htole16(IEEE80211_CHAN_A);
3835 	} else if (IEEE80211_IS_CHAN_ANYG(chan)) {
3836 		sc->sc_tx_th.wt_chan_flags = htole16(IEEE80211_CHAN_G);
3837 		sc->sc_rx_th.wr_chan_flags = htole16(IEEE80211_CHAN_G);
3838 	} else {
3839 		sc->sc_tx_th.wt_chan_flags = htole16(IEEE80211_CHAN_B);
3840 		sc->sc_rx_th.wr_chan_flags = htole16(IEEE80211_CHAN_B);
3841 	}
3842 	sc->sc_curchan = hchan;
3843 	mwl_hal_intrset(mh, sc->sc_imask);
3844 
3845 	return 0;
3846 }
3847 
3848 static void
3849 mwl_scan_start(struct ieee80211com *ic)
3850 {
3851 	struct mwl_softc *sc = ic->ic_softc;
3852 
3853 	DPRINTF(sc, MWL_DEBUG_STATE, "%s\n", __func__);
3854 }
3855 
3856 static void
3857 mwl_scan_end(struct ieee80211com *ic)
3858 {
3859 	struct mwl_softc *sc = ic->ic_softc;
3860 
3861 	DPRINTF(sc, MWL_DEBUG_STATE, "%s\n", __func__);
3862 }
3863 
3864 static void
3865 mwl_set_channel(struct ieee80211com *ic)
3866 {
3867 	struct mwl_softc *sc = ic->ic_softc;
3868 
3869 	(void) mwl_chan_set(sc, ic->ic_curchan);
3870 }
3871 
3872 /*
3873  * Handle a channel switch request.  We inform the firmware
3874  * and mark the global state to suppress various actions.
3875  * NB: we issue only one request to the fw; we may be called
3876  * multiple times if there are multiple vap's.
3877  */
3878 static void
3879 mwl_startcsa(struct ieee80211vap *vap)
3880 {
3881 	struct ieee80211com *ic = vap->iv_ic;
3882 	struct mwl_softc *sc = ic->ic_softc;
3883 	MWL_HAL_CHANNEL hchan;
3884 
3885 	if (sc->sc_csapending)
3886 		return;
3887 
3888 	mwl_mapchan(&hchan, ic->ic_csa_newchan);
3889 	/* 1 =>'s quiet channel */
3890 	mwl_hal_setchannelswitchie(sc->sc_mh, &hchan, 1, ic->ic_csa_count);
3891 	sc->sc_csapending = 1;
3892 }
3893 
3894 /*
3895  * Plumb any static WEP key for the station.  This is
3896  * necessary as we must propagate the key from the
3897  * global key table of the vap to each sta db entry.
3898  */
3899 static void
3900 mwl_setanywepkey(struct ieee80211vap *vap, const uint8_t mac[IEEE80211_ADDR_LEN])
3901 {
3902 	if ((vap->iv_flags & (IEEE80211_F_PRIVACY|IEEE80211_F_WPA)) ==
3903 		IEEE80211_F_PRIVACY &&
3904 	    vap->iv_def_txkey != IEEE80211_KEYIX_NONE &&
3905 	    vap->iv_nw_keys[vap->iv_def_txkey].wk_keyix != IEEE80211_KEYIX_NONE)
3906 		(void) _mwl_key_set(vap, &vap->iv_nw_keys[vap->iv_def_txkey],
3907 				    mac);
3908 }
3909 
3910 static int
3911 mwl_peerstadb(struct ieee80211_node *ni, int aid, int staid, MWL_HAL_PEERINFO *pi)
3912 {
3913 #define	WME(ie) ((const struct ieee80211_wme_info *) ie)
3914 	struct ieee80211vap *vap = ni->ni_vap;
3915 	struct mwl_hal_vap *hvap;
3916 	int error;
3917 
3918 	if (vap->iv_opmode == IEEE80211_M_WDS) {
3919 		/*
3920 		 * WDS vap's do not have a f/w vap; instead they piggyback
3921 		 * on an AP vap and we must install the sta db entry and
3922 		 * crypto state using that AP's handle (the WDS vap has none).
3923 		 */
3924 		hvap = MWL_VAP(vap)->mv_ap_hvap;
3925 	} else
3926 		hvap = MWL_VAP(vap)->mv_hvap;
3927 	error = mwl_hal_newstation(hvap, ni->ni_macaddr,
3928 	    aid, staid, pi,
3929 	    ni->ni_flags & (IEEE80211_NODE_QOS | IEEE80211_NODE_HT),
3930 	    ni->ni_ies.wme_ie != NULL ? WME(ni->ni_ies.wme_ie)->wme_info : 0);
3931 	if (error == 0) {
3932 		/*
3933 		 * Setup security for this station.  For sta mode this is
3934 		 * needed even though do the same thing on transition to
3935 		 * AUTH state because the call to mwl_hal_newstation
3936 		 * clobbers the crypto state we setup.
3937 		 */
3938 		mwl_setanywepkey(vap, ni->ni_macaddr);
3939 	}
3940 	return error;
3941 #undef WME
3942 }
3943 
3944 static void
3945 mwl_setglobalkeys(struct ieee80211vap *vap)
3946 {
3947 	struct ieee80211_key *wk;
3948 
3949 	wk = &vap->iv_nw_keys[0];
3950 	for (; wk < &vap->iv_nw_keys[IEEE80211_WEP_NKID]; wk++)
3951 		if (wk->wk_keyix != IEEE80211_KEYIX_NONE)
3952 			(void) _mwl_key_set(vap, wk, vap->iv_myaddr);
3953 }
3954 
3955 /*
3956  * Convert a legacy rate set to a firmware bitmask.
3957  */
3958 static uint32_t
3959 get_rate_bitmap(const struct ieee80211_rateset *rs)
3960 {
3961 	uint32_t rates;
3962 	int i;
3963 
3964 	rates = 0;
3965 	for (i = 0; i < rs->rs_nrates; i++)
3966 		switch (rs->rs_rates[i] & IEEE80211_RATE_VAL) {
3967 		case 2:	  rates |= 0x001; break;
3968 		case 4:	  rates |= 0x002; break;
3969 		case 11:  rates |= 0x004; break;
3970 		case 22:  rates |= 0x008; break;
3971 		case 44:  rates |= 0x010; break;
3972 		case 12:  rates |= 0x020; break;
3973 		case 18:  rates |= 0x040; break;
3974 		case 24:  rates |= 0x080; break;
3975 		case 36:  rates |= 0x100; break;
3976 		case 48:  rates |= 0x200; break;
3977 		case 72:  rates |= 0x400; break;
3978 		case 96:  rates |= 0x800; break;
3979 		case 108: rates |= 0x1000; break;
3980 		}
3981 	return rates;
3982 }
3983 
3984 /*
3985  * Construct an HT firmware bitmask from an HT rate set.
3986  */
3987 static uint32_t
3988 get_htrate_bitmap(const struct ieee80211_htrateset *rs)
3989 {
3990 	uint32_t rates;
3991 	int i;
3992 
3993 	rates = 0;
3994 	for (i = 0; i < rs->rs_nrates; i++) {
3995 		if (rs->rs_rates[i] < 16)
3996 			rates |= 1<<rs->rs_rates[i];
3997 	}
3998 	return rates;
3999 }
4000 
4001 /*
4002  * Craft station database entry for station.
4003  * NB: use host byte order here, the hal handles byte swapping.
4004  */
4005 static MWL_HAL_PEERINFO *
4006 mkpeerinfo(MWL_HAL_PEERINFO *pi, const struct ieee80211_node *ni)
4007 {
4008 	const struct ieee80211vap *vap = ni->ni_vap;
4009 
4010 	memset(pi, 0, sizeof(*pi));
4011 	pi->LegacyRateBitMap = get_rate_bitmap(&ni->ni_rates);
4012 	pi->CapInfo = ni->ni_capinfo;
4013 	if (ni->ni_flags & IEEE80211_NODE_HT) {
4014 		/* HT capabilities, etc */
4015 		pi->HTCapabilitiesInfo = ni->ni_htcap;
4016 		/* XXX pi.HTCapabilitiesInfo */
4017 	        pi->MacHTParamInfo = ni->ni_htparam;
4018 		pi->HTRateBitMap = get_htrate_bitmap(&ni->ni_htrates);
4019 		pi->AddHtInfo.ControlChan = ni->ni_htctlchan;
4020 		pi->AddHtInfo.AddChan = ni->ni_ht2ndchan;
4021 		pi->AddHtInfo.OpMode = ni->ni_htopmode;
4022 		pi->AddHtInfo.stbc = ni->ni_htstbc;
4023 
4024 		/* constrain according to local configuration */
4025 		if ((vap->iv_flags_ht & IEEE80211_FHT_SHORTGI40) == 0)
4026 			pi->HTCapabilitiesInfo &= ~IEEE80211_HTCAP_SHORTGI40;
4027 		if ((vap->iv_flags_ht & IEEE80211_FHT_SHORTGI20) == 0)
4028 			pi->HTCapabilitiesInfo &= ~IEEE80211_HTCAP_SHORTGI20;
4029 		if (ni->ni_chw != 40)
4030 			pi->HTCapabilitiesInfo &= ~IEEE80211_HTCAP_CHWIDTH40;
4031 	}
4032 	return pi;
4033 }
4034 
4035 /*
4036  * Re-create the local sta db entry for a vap to ensure
4037  * up to date WME state is pushed to the firmware.  Because
4038  * this resets crypto state this must be followed by a
4039  * reload of any keys in the global key table.
4040  */
4041 static int
4042 mwl_localstadb(struct ieee80211vap *vap)
4043 {
4044 #define	WME(ie) ((const struct ieee80211_wme_info *) ie)
4045 	struct mwl_hal_vap *hvap = MWL_VAP(vap)->mv_hvap;
4046 	struct ieee80211_node *bss;
4047 	MWL_HAL_PEERINFO pi;
4048 	int error;
4049 
4050 	switch (vap->iv_opmode) {
4051 	case IEEE80211_M_STA:
4052 		bss = vap->iv_bss;
4053 		error = mwl_hal_newstation(hvap, vap->iv_myaddr, 0, 0,
4054 		    vap->iv_state == IEEE80211_S_RUN ?
4055 			mkpeerinfo(&pi, bss) : NULL,
4056 		    (bss->ni_flags & (IEEE80211_NODE_QOS | IEEE80211_NODE_HT)),
4057 		    bss->ni_ies.wme_ie != NULL ?
4058 			WME(bss->ni_ies.wme_ie)->wme_info : 0);
4059 		if (error == 0)
4060 			mwl_setglobalkeys(vap);
4061 		break;
4062 	case IEEE80211_M_HOSTAP:
4063 	case IEEE80211_M_MBSS:
4064 		error = mwl_hal_newstation(hvap, vap->iv_myaddr,
4065 		    0, 0, NULL, vap->iv_flags & IEEE80211_F_WME, 0);
4066 		if (error == 0)
4067 			mwl_setglobalkeys(vap);
4068 		break;
4069 	default:
4070 		error = 0;
4071 		break;
4072 	}
4073 	return error;
4074 #undef WME
4075 }
4076 
4077 static int
4078 mwl_newstate(struct ieee80211vap *vap, enum ieee80211_state nstate, int arg)
4079 {
4080 	struct mwl_vap *mvp = MWL_VAP(vap);
4081 	struct mwl_hal_vap *hvap = mvp->mv_hvap;
4082 	struct ieee80211com *ic = vap->iv_ic;
4083 	struct ieee80211_node *ni = NULL;
4084 	struct mwl_softc *sc = ic->ic_softc;
4085 	struct mwl_hal *mh = sc->sc_mh;
4086 	enum ieee80211_state ostate = vap->iv_state;
4087 	int error;
4088 
4089 	DPRINTF(sc, MWL_DEBUG_STATE, "%s: %s: %s -> %s\n",
4090 	    vap->iv_ifp->if_xname, __func__,
4091 	    ieee80211_state_name[ostate], ieee80211_state_name[nstate]);
4092 
4093 	callout_stop(&sc->sc_timer);
4094 	/*
4095 	 * Clear current radar detection state.
4096 	 */
4097 	if (ostate == IEEE80211_S_CAC) {
4098 		/* stop quiet mode radar detection */
4099 		mwl_hal_setradardetection(mh, DR_CHK_CHANNEL_AVAILABLE_STOP);
4100 	} else if (sc->sc_radarena) {
4101 		/* stop in-service radar detection */
4102 		mwl_hal_setradardetection(mh, DR_DFS_DISABLE);
4103 		sc->sc_radarena = 0;
4104 	}
4105 	/*
4106 	 * Carry out per-state actions before doing net80211 work.
4107 	 */
4108 	if (nstate == IEEE80211_S_INIT) {
4109 		/* NB: only ap+sta vap's have a fw entity */
4110 		if (hvap != NULL)
4111 			mwl_hal_stop(hvap);
4112 	} else if (nstate == IEEE80211_S_SCAN) {
4113 		mwl_hal_start(hvap);
4114 		/* NB: this disables beacon frames */
4115 		mwl_hal_setinframode(hvap);
4116 	} else if (nstate == IEEE80211_S_AUTH) {
4117 		/*
4118 		 * Must create a sta db entry in case a WEP key needs to
4119 		 * be plumbed.  This entry will be overwritten if we
4120 		 * associate; otherwise it will be reclaimed on node free.
4121 		 */
4122 		ni = vap->iv_bss;
4123 		MWL_NODE(ni)->mn_hvap = hvap;
4124 		(void) mwl_peerstadb(ni, 0, 0, NULL);
4125 	} else if (nstate == IEEE80211_S_CSA) {
4126 		/* XXX move to below? */
4127 		if (vap->iv_opmode == IEEE80211_M_HOSTAP ||
4128 		    vap->iv_opmode == IEEE80211_M_MBSS)
4129 			mwl_startcsa(vap);
4130 	} else if (nstate == IEEE80211_S_CAC) {
4131 		/* XXX move to below? */
4132 		/* stop ap xmit and enable quiet mode radar detection */
4133 		mwl_hal_setradardetection(mh, DR_CHK_CHANNEL_AVAILABLE_START);
4134 	}
4135 
4136 	/*
4137 	 * Invoke the parent method to do net80211 work.
4138 	 */
4139 	error = mvp->mv_newstate(vap, nstate, arg);
4140 
4141 	/*
4142 	 * Carry out work that must be done after net80211 runs;
4143 	 * this work requires up to date state (e.g. iv_bss).
4144 	 */
4145 	if (error == 0 && nstate == IEEE80211_S_RUN) {
4146 		/* NB: collect bss node again, it may have changed */
4147 		ni = vap->iv_bss;
4148 
4149 		DPRINTF(sc, MWL_DEBUG_STATE,
4150 		    "%s: %s(RUN): iv_flags 0x%08x bintvl %d bssid %s "
4151 		    "capinfo 0x%04x chan %d\n",
4152 		    vap->iv_ifp->if_xname, __func__, vap->iv_flags,
4153 		    ni->ni_intval, ether_sprintf(ni->ni_bssid), ni->ni_capinfo,
4154 		    ieee80211_chan2ieee(ic, ic->ic_curchan));
4155 
4156 		/*
4157 		 * Recreate local sta db entry to update WME/HT state.
4158 		 */
4159 		mwl_localstadb(vap);
4160 		switch (vap->iv_opmode) {
4161 		case IEEE80211_M_HOSTAP:
4162 		case IEEE80211_M_MBSS:
4163 			if (ostate == IEEE80211_S_CAC) {
4164 				/* enable in-service radar detection */
4165 				mwl_hal_setradardetection(mh,
4166 				    DR_IN_SERVICE_MONITOR_START);
4167 				sc->sc_radarena = 1;
4168 			}
4169 			/*
4170 			 * Allocate and setup the beacon frame
4171 			 * (and related state).
4172 			 */
4173 			error = mwl_reset_vap(vap, IEEE80211_S_RUN);
4174 			if (error != 0) {
4175 				DPRINTF(sc, MWL_DEBUG_STATE,
4176 				    "%s: beacon setup failed, error %d\n",
4177 				    __func__, error);
4178 				goto bad;
4179 			}
4180 			/* NB: must be after setting up beacon */
4181 			mwl_hal_start(hvap);
4182 			break;
4183 		case IEEE80211_M_STA:
4184 			DPRINTF(sc, MWL_DEBUG_STATE, "%s: %s: aid 0x%x\n",
4185 			    vap->iv_ifp->if_xname, __func__, ni->ni_associd);
4186 			/*
4187 			 * Set state now that we're associated.
4188 			 */
4189 			mwl_hal_setassocid(hvap, ni->ni_bssid, ni->ni_associd);
4190 			mwl_setrates(vap);
4191 			mwl_hal_setrtsthreshold(hvap, vap->iv_rtsthreshold);
4192 			if ((vap->iv_flags & IEEE80211_F_DWDS) &&
4193 			    sc->sc_ndwdsvaps++ == 0)
4194 				mwl_hal_setdwds(mh, 1);
4195 			break;
4196 		case IEEE80211_M_WDS:
4197 			DPRINTF(sc, MWL_DEBUG_STATE, "%s: %s: bssid %s\n",
4198 			    vap->iv_ifp->if_xname, __func__,
4199 			    ether_sprintf(ni->ni_bssid));
4200 			mwl_seteapolformat(vap);
4201 			break;
4202 		default:
4203 			break;
4204 		}
4205 		/*
4206 		 * Set CS mode according to operating channel;
4207 		 * this mostly an optimization for 5GHz.
4208 		 *
4209 		 * NB: must follow mwl_hal_start which resets csmode
4210 		 */
4211 		if (IEEE80211_IS_CHAN_5GHZ(ic->ic_bsschan))
4212 			mwl_hal_setcsmode(mh, CSMODE_AGGRESSIVE);
4213 		else
4214 			mwl_hal_setcsmode(mh, CSMODE_AUTO_ENA);
4215 		/*
4216 		 * Start timer to prod firmware.
4217 		 */
4218 		if (sc->sc_ageinterval != 0)
4219 			callout_reset(&sc->sc_timer, sc->sc_ageinterval*hz,
4220 			    mwl_agestations, sc);
4221 	} else if (nstate == IEEE80211_S_SLEEP) {
4222 		/* XXX set chip in power save */
4223 	} else if ((vap->iv_flags & IEEE80211_F_DWDS) &&
4224 	    --sc->sc_ndwdsvaps == 0)
4225 		mwl_hal_setdwds(mh, 0);
4226 bad:
4227 	return error;
4228 }
4229 
4230 /*
4231  * Manage station id's; these are separate from AID's
4232  * as AID's may have values out of the range of possible
4233  * station id's acceptable to the firmware.
4234  */
4235 static int
4236 allocstaid(struct mwl_softc *sc, int aid)
4237 {
4238 	int staid;
4239 
4240 	if (!(0 < aid && aid < MWL_MAXSTAID) || isset(sc->sc_staid, aid)) {
4241 		/* NB: don't use 0 */
4242 		for (staid = 1; staid < MWL_MAXSTAID; staid++)
4243 			if (isclr(sc->sc_staid, staid))
4244 				break;
4245 	} else
4246 		staid = aid;
4247 	setbit(sc->sc_staid, staid);
4248 	return staid;
4249 }
4250 
4251 static void
4252 delstaid(struct mwl_softc *sc, int staid)
4253 {
4254 	clrbit(sc->sc_staid, staid);
4255 }
4256 
4257 /*
4258  * Setup driver-specific state for a newly associated node.
4259  * Note that we're called also on a re-associate, the isnew
4260  * param tells us if this is the first time or not.
4261  */
4262 static void
4263 mwl_newassoc(struct ieee80211_node *ni, int isnew)
4264 {
4265 	struct ieee80211vap *vap = ni->ni_vap;
4266         struct mwl_softc *sc = vap->iv_ic->ic_softc;
4267 	struct mwl_node *mn = MWL_NODE(ni);
4268 	MWL_HAL_PEERINFO pi;
4269 	uint16_t aid;
4270 	int error;
4271 
4272 	aid = IEEE80211_AID(ni->ni_associd);
4273 	if (isnew) {
4274 		mn->mn_staid = allocstaid(sc, aid);
4275 		mn->mn_hvap = MWL_VAP(vap)->mv_hvap;
4276 	} else {
4277 		mn = MWL_NODE(ni);
4278 		/* XXX reset BA stream? */
4279 	}
4280 	DPRINTF(sc, MWL_DEBUG_NODE, "%s: mac %s isnew %d aid %d staid %d\n",
4281 	    __func__, ether_sprintf(ni->ni_macaddr), isnew, aid, mn->mn_staid);
4282 	error = mwl_peerstadb(ni, aid, mn->mn_staid, mkpeerinfo(&pi, ni));
4283 	if (error != 0) {
4284 		DPRINTF(sc, MWL_DEBUG_NODE,
4285 		    "%s: error %d creating sta db entry\n",
4286 		    __func__, error);
4287 		/* XXX how to deal with error? */
4288 	}
4289 }
4290 
4291 /*
4292  * Periodically poke the firmware to age out station state
4293  * (power save queues, pending tx aggregates).
4294  */
4295 static void
4296 mwl_agestations(void *arg)
4297 {
4298 	struct mwl_softc *sc = arg;
4299 
4300 	mwl_hal_setkeepalive(sc->sc_mh);
4301 	if (sc->sc_ageinterval != 0)		/* NB: catch dynamic changes */
4302 		callout_schedule(&sc->sc_timer, sc->sc_ageinterval*hz);
4303 }
4304 
4305 static const struct mwl_hal_channel *
4306 findhalchannel(const MWL_HAL_CHANNELINFO *ci, int ieee)
4307 {
4308 	int i;
4309 
4310 	for (i = 0; i < ci->nchannels; i++) {
4311 		const struct mwl_hal_channel *hc = &ci->channels[i];
4312 		if (hc->ieee == ieee)
4313 			return hc;
4314 	}
4315 	return NULL;
4316 }
4317 
4318 static int
4319 mwl_setregdomain(struct ieee80211com *ic, struct ieee80211_regdomain *rd,
4320 	int nchan, struct ieee80211_channel chans[])
4321 {
4322 	struct mwl_softc *sc = ic->ic_softc;
4323 	struct mwl_hal *mh = sc->sc_mh;
4324 	const MWL_HAL_CHANNELINFO *ci;
4325 	int i;
4326 
4327 	for (i = 0; i < nchan; i++) {
4328 		struct ieee80211_channel *c = &chans[i];
4329 		const struct mwl_hal_channel *hc;
4330 
4331 		if (IEEE80211_IS_CHAN_2GHZ(c)) {
4332 			mwl_hal_getchannelinfo(mh, MWL_FREQ_BAND_2DOT4GHZ,
4333 			    IEEE80211_IS_CHAN_HT40(c) ?
4334 				MWL_CH_40_MHz_WIDTH : MWL_CH_20_MHz_WIDTH, &ci);
4335 		} else if (IEEE80211_IS_CHAN_5GHZ(c)) {
4336 			mwl_hal_getchannelinfo(mh, MWL_FREQ_BAND_5GHZ,
4337 			    IEEE80211_IS_CHAN_HT40(c) ?
4338 				MWL_CH_40_MHz_WIDTH : MWL_CH_20_MHz_WIDTH, &ci);
4339 		} else {
4340 			device_printf(sc->sc_dev,
4341 			    "%s: channel %u freq %u/0x%x not 2.4/5GHz\n",
4342 			    __func__, c->ic_ieee, c->ic_freq, c->ic_flags);
4343 			return EINVAL;
4344 		}
4345 		/*
4346 		 * Verify channel has cal data and cap tx power.
4347 		 */
4348 		hc = findhalchannel(ci, c->ic_ieee);
4349 		if (hc != NULL) {
4350 			if (c->ic_maxpower > 2*hc->maxTxPow)
4351 				c->ic_maxpower = 2*hc->maxTxPow;
4352 			goto next;
4353 		}
4354 		if (IEEE80211_IS_CHAN_HT40(c)) {
4355 			/*
4356 			 * Look for the extension channel since the
4357 			 * hal table only has the primary channel.
4358 			 */
4359 			hc = findhalchannel(ci, c->ic_extieee);
4360 			if (hc != NULL) {
4361 				if (c->ic_maxpower > 2*hc->maxTxPow)
4362 					c->ic_maxpower = 2*hc->maxTxPow;
4363 				goto next;
4364 			}
4365 		}
4366 		device_printf(sc->sc_dev,
4367 		    "%s: no cal data for channel %u ext %u freq %u/0x%x\n",
4368 		    __func__, c->ic_ieee, c->ic_extieee,
4369 		    c->ic_freq, c->ic_flags);
4370 		return EINVAL;
4371 	next:
4372 		;
4373 	}
4374 	return 0;
4375 }
4376 
4377 #define	IEEE80211_CHAN_HTG	(IEEE80211_CHAN_HT|IEEE80211_CHAN_G)
4378 #define	IEEE80211_CHAN_HTA	(IEEE80211_CHAN_HT|IEEE80211_CHAN_A)
4379 
4380 static void
4381 addht40channels(struct ieee80211_channel chans[], int maxchans, int *nchans,
4382 	const MWL_HAL_CHANNELINFO *ci, int flags)
4383 {
4384 	int i, error;
4385 
4386 	for (i = 0; i < ci->nchannels; i++) {
4387 		const struct mwl_hal_channel *hc = &ci->channels[i];
4388 
4389 		error = ieee80211_add_channel_ht40(chans, maxchans, nchans,
4390 		    hc->ieee, hc->maxTxPow, flags);
4391 		if (error != 0 && error != ENOENT)
4392 			break;
4393 	}
4394 }
4395 
4396 static void
4397 addchannels(struct ieee80211_channel chans[], int maxchans, int *nchans,
4398 	const MWL_HAL_CHANNELINFO *ci, const uint8_t bands[])
4399 {
4400 	int i, error;
4401 
4402 	error = 0;
4403 	for (i = 0; i < ci->nchannels && error == 0; i++) {
4404 		const struct mwl_hal_channel *hc = &ci->channels[i];
4405 
4406 		error = ieee80211_add_channel(chans, maxchans, nchans,
4407 		    hc->ieee, hc->freq, hc->maxTxPow, 0, bands);
4408 	}
4409 }
4410 
4411 static void
4412 getchannels(struct mwl_softc *sc, int maxchans, int *nchans,
4413 	struct ieee80211_channel chans[])
4414 {
4415 	const MWL_HAL_CHANNELINFO *ci;
4416 	uint8_t bands[IEEE80211_MODE_BYTES];
4417 
4418 	/*
4419 	 * Use the channel info from the hal to craft the
4420 	 * channel list.  Note that we pass back an unsorted
4421 	 * list; the caller is required to sort it for us
4422 	 * (if desired).
4423 	 */
4424 	*nchans = 0;
4425 	if (mwl_hal_getchannelinfo(sc->sc_mh,
4426 	    MWL_FREQ_BAND_2DOT4GHZ, MWL_CH_20_MHz_WIDTH, &ci) == 0) {
4427 		memset(bands, 0, sizeof(bands));
4428 		setbit(bands, IEEE80211_MODE_11B);
4429 		setbit(bands, IEEE80211_MODE_11G);
4430 		setbit(bands, IEEE80211_MODE_11NG);
4431 		addchannels(chans, maxchans, nchans, ci, bands);
4432 	}
4433 	if (mwl_hal_getchannelinfo(sc->sc_mh,
4434 	    MWL_FREQ_BAND_5GHZ, MWL_CH_20_MHz_WIDTH, &ci) == 0) {
4435 		memset(bands, 0, sizeof(bands));
4436 		setbit(bands, IEEE80211_MODE_11A);
4437 		setbit(bands, IEEE80211_MODE_11NA);
4438 		addchannels(chans, maxchans, nchans, ci, bands);
4439 	}
4440 	if (mwl_hal_getchannelinfo(sc->sc_mh,
4441 	    MWL_FREQ_BAND_2DOT4GHZ, MWL_CH_40_MHz_WIDTH, &ci) == 0)
4442 		addht40channels(chans, maxchans, nchans, ci, IEEE80211_CHAN_HTG);
4443 	if (mwl_hal_getchannelinfo(sc->sc_mh,
4444 	    MWL_FREQ_BAND_5GHZ, MWL_CH_40_MHz_WIDTH, &ci) == 0)
4445 		addht40channels(chans, maxchans, nchans, ci, IEEE80211_CHAN_HTA);
4446 }
4447 
4448 static void
4449 mwl_getradiocaps(struct ieee80211com *ic,
4450 	int maxchans, int *nchans, struct ieee80211_channel chans[])
4451 {
4452 	struct mwl_softc *sc = ic->ic_softc;
4453 
4454 	getchannels(sc, maxchans, nchans, chans);
4455 }
4456 
4457 static int
4458 mwl_getchannels(struct mwl_softc *sc)
4459 {
4460 	struct ieee80211com *ic = &sc->sc_ic;
4461 
4462 	/*
4463 	 * Use the channel info from the hal to craft the
4464 	 * channel list for net80211.  Note that we pass up
4465 	 * an unsorted list; net80211 will sort it for us.
4466 	 */
4467 	memset(ic->ic_channels, 0, sizeof(ic->ic_channels));
4468 	ic->ic_nchans = 0;
4469 	getchannels(sc, IEEE80211_CHAN_MAX, &ic->ic_nchans, ic->ic_channels);
4470 
4471 	ic->ic_regdomain.regdomain = SKU_DEBUG;
4472 	ic->ic_regdomain.country = CTRY_DEFAULT;
4473 	ic->ic_regdomain.location = 'I';
4474 	ic->ic_regdomain.isocc[0] = ' ';	/* XXX? */
4475 	ic->ic_regdomain.isocc[1] = ' ';
4476 	return (ic->ic_nchans == 0 ? EIO : 0);
4477 }
4478 #undef IEEE80211_CHAN_HTA
4479 #undef IEEE80211_CHAN_HTG
4480 
4481 #ifdef MWL_DEBUG
4482 static void
4483 mwl_printrxbuf(const struct mwl_rxbuf *bf, u_int ix)
4484 {
4485 	const struct mwl_rxdesc *ds = bf->bf_desc;
4486 	uint32_t status = le32toh(ds->Status);
4487 
4488 	printf("R[%2u] (DS.V:%p DS.P:0x%jx) NEXT:%08x DATA:%08x RC:%02x%s\n"
4489 	       "      STAT:%02x LEN:%04x RSSI:%02x CHAN:%02x RATE:%02x QOS:%04x HT:%04x\n",
4490 	    ix, ds, (uintmax_t)bf->bf_daddr, le32toh(ds->pPhysNext),
4491 	    le32toh(ds->pPhysBuffData), ds->RxControl,
4492 	    ds->RxControl != EAGLE_RXD_CTRL_DRIVER_OWN ?
4493 	        "" : (status & EAGLE_RXD_STATUS_OK) ? " *" : " !",
4494 	    ds->Status, le16toh(ds->PktLen), ds->RSSI, ds->Channel,
4495 	    ds->Rate, le16toh(ds->QosCtrl), le16toh(ds->HtSig2));
4496 }
4497 
4498 static void
4499 mwl_printtxbuf(const struct mwl_txbuf *bf, u_int qnum, u_int ix)
4500 {
4501 	const struct mwl_txdesc *ds = bf->bf_desc;
4502 	uint32_t status = le32toh(ds->Status);
4503 
4504 	printf("Q%u[%3u]", qnum, ix);
4505 	printf(" (DS.V:%p DS.P:0x%jx)\n", ds, (uintmax_t)bf->bf_daddr);
4506 	printf("    NEXT:%08x DATA:%08x LEN:%04x STAT:%08x%s\n",
4507 	    le32toh(ds->pPhysNext),
4508 	    le32toh(ds->PktPtr), le16toh(ds->PktLen), status,
4509 	    status & EAGLE_TXD_STATUS_USED ?
4510 		"" : (status & 3) != 0 ? " *" : " !");
4511 	printf("    RATE:%02x PRI:%x QOS:%04x SAP:%08x FORMAT:%04x\n",
4512 	    ds->DataRate, ds->TxPriority, le16toh(ds->QosCtrl),
4513 	    le32toh(ds->SapPktInfo), le16toh(ds->Format));
4514 #if MWL_TXDESC > 1
4515 	printf("    MULTIFRAMES:%u LEN:%04x %04x %04x %04x %04x %04x\n"
4516 	    , le32toh(ds->multiframes)
4517 	    , le16toh(ds->PktLenArray[0]), le16toh(ds->PktLenArray[1])
4518 	    , le16toh(ds->PktLenArray[2]), le16toh(ds->PktLenArray[3])
4519 	    , le16toh(ds->PktLenArray[4]), le16toh(ds->PktLenArray[5])
4520 	);
4521 	printf("    DATA:%08x %08x %08x %08x %08x %08x\n"
4522 	    , le32toh(ds->PktPtrArray[0]), le32toh(ds->PktPtrArray[1])
4523 	    , le32toh(ds->PktPtrArray[2]), le32toh(ds->PktPtrArray[3])
4524 	    , le32toh(ds->PktPtrArray[4]), le32toh(ds->PktPtrArray[5])
4525 	);
4526 #endif
4527 #if 0
4528 { const uint8_t *cp = (const uint8_t *) ds;
4529   int i;
4530   for (i = 0; i < sizeof(struct mwl_txdesc); i++) {
4531 	printf("%02x ", cp[i]);
4532 	if (((i+1) % 16) == 0)
4533 		printf("\n");
4534   }
4535   printf("\n");
4536 }
4537 #endif
4538 }
4539 #endif /* MWL_DEBUG */
4540 
4541 #if 0
4542 static void
4543 mwl_txq_dump(struct mwl_txq *txq)
4544 {
4545 	struct mwl_txbuf *bf;
4546 	int i = 0;
4547 
4548 	MWL_TXQ_LOCK(txq);
4549 	STAILQ_FOREACH(bf, &txq->active, bf_list) {
4550 		struct mwl_txdesc *ds = bf->bf_desc;
4551 		MWL_TXDESC_SYNC(txq, ds,
4552 		    BUS_DMASYNC_POSTREAD | BUS_DMASYNC_POSTWRITE);
4553 #ifdef MWL_DEBUG
4554 		mwl_printtxbuf(bf, txq->qnum, i);
4555 #endif
4556 		i++;
4557 	}
4558 	MWL_TXQ_UNLOCK(txq);
4559 }
4560 #endif
4561 
4562 static void
4563 mwl_watchdog(void *arg)
4564 {
4565 	struct mwl_softc *sc = arg;
4566 
4567 	callout_reset(&sc->sc_watchdog, hz, mwl_watchdog, sc);
4568 	if (sc->sc_tx_timer == 0 || --sc->sc_tx_timer > 0)
4569 		return;
4570 
4571 	if (sc->sc_running && !sc->sc_invalid) {
4572 		if (mwl_hal_setkeepalive(sc->sc_mh))
4573 			device_printf(sc->sc_dev,
4574 			    "transmit timeout (firmware hung?)\n");
4575 		else
4576 			device_printf(sc->sc_dev,
4577 			    "transmit timeout\n");
4578 #if 0
4579 		mwl_reset(sc);
4580 mwl_txq_dump(&sc->sc_txq[0]);/*XXX*/
4581 #endif
4582 		counter_u64_add(sc->sc_ic.ic_oerrors, 1);
4583 		sc->sc_stats.mst_watchdog++;
4584 	}
4585 }
4586 
4587 #ifdef MWL_DIAGAPI
4588 /*
4589  * Diagnostic interface to the HAL.  This is used by various
4590  * tools to do things like retrieve register contents for
4591  * debugging.  The mechanism is intentionally opaque so that
4592  * it can change frequently w/o concern for compatibility.
4593  */
4594 static int
4595 mwl_ioctl_diag(struct mwl_softc *sc, struct mwl_diag *md)
4596 {
4597 	struct mwl_hal *mh = sc->sc_mh;
4598 	u_int id = md->md_id & MWL_DIAG_ID;
4599 	void *indata = NULL;
4600 	void *outdata = NULL;
4601 	u_int32_t insize = md->md_in_size;
4602 	u_int32_t outsize = md->md_out_size;
4603 	int error = 0;
4604 
4605 	if (md->md_id & MWL_DIAG_IN) {
4606 		/*
4607 		 * Copy in data.
4608 		 */
4609 		indata = malloc(insize, M_TEMP, M_NOWAIT);
4610 		if (indata == NULL) {
4611 			error = ENOMEM;
4612 			goto bad;
4613 		}
4614 		error = copyin(md->md_in_data, indata, insize);
4615 		if (error)
4616 			goto bad;
4617 	}
4618 	if (md->md_id & MWL_DIAG_DYN) {
4619 		/*
4620 		 * Allocate a buffer for the results (otherwise the HAL
4621 		 * returns a pointer to a buffer where we can read the
4622 		 * results).  Note that we depend on the HAL leaving this
4623 		 * pointer for us to use below in reclaiming the buffer;
4624 		 * may want to be more defensive.
4625 		 */
4626 		outdata = malloc(outsize, M_TEMP, M_NOWAIT);
4627 		if (outdata == NULL) {
4628 			error = ENOMEM;
4629 			goto bad;
4630 		}
4631 	}
4632 	if (mwl_hal_getdiagstate(mh, id, indata, insize, &outdata, &outsize)) {
4633 		if (outsize < md->md_out_size)
4634 			md->md_out_size = outsize;
4635 		if (outdata != NULL)
4636 			error = copyout(outdata, md->md_out_data,
4637 					md->md_out_size);
4638 	} else {
4639 		error = EINVAL;
4640 	}
4641 bad:
4642 	if ((md->md_id & MWL_DIAG_IN) && indata != NULL)
4643 		free(indata, M_TEMP);
4644 	if ((md->md_id & MWL_DIAG_DYN) && outdata != NULL)
4645 		free(outdata, M_TEMP);
4646 	return error;
4647 }
4648 
4649 static int
4650 mwl_ioctl_reset(struct mwl_softc *sc, struct mwl_diag *md)
4651 {
4652 	struct mwl_hal *mh = sc->sc_mh;
4653 	int error;
4654 
4655 	MWL_LOCK_ASSERT(sc);
4656 
4657 	if (md->md_id == 0 && mwl_hal_fwload(mh, NULL) != 0) {
4658 		device_printf(sc->sc_dev, "unable to load firmware\n");
4659 		return EIO;
4660 	}
4661 	if (mwl_hal_gethwspecs(mh, &sc->sc_hwspecs) != 0) {
4662 		device_printf(sc->sc_dev, "unable to fetch h/w specs\n");
4663 		return EIO;
4664 	}
4665 	error = mwl_setupdma(sc);
4666 	if (error != 0) {
4667 		/* NB: mwl_setupdma prints a msg */
4668 		return error;
4669 	}
4670 	/*
4671 	 * Reset tx/rx data structures; after reload we must
4672 	 * re-start the driver's notion of the next xmit/recv.
4673 	 */
4674 	mwl_draintxq(sc);		/* clear pending frames */
4675 	mwl_resettxq(sc);		/* rebuild tx q lists */
4676 	sc->sc_rxnext = NULL;		/* force rx to start at the list head */
4677 	return 0;
4678 }
4679 #endif /* MWL_DIAGAPI */
4680 
4681 static void
4682 mwl_parent(struct ieee80211com *ic)
4683 {
4684 	struct mwl_softc *sc = ic->ic_softc;
4685 	int startall = 0;
4686 
4687 	MWL_LOCK(sc);
4688 	if (ic->ic_nrunning > 0) {
4689 		if (sc->sc_running) {
4690 			/*
4691 			 * To avoid rescanning another access point,
4692 			 * do not call mwl_init() here.  Instead,
4693 			 * only reflect promisc mode settings.
4694 			 */
4695 			mwl_mode_init(sc);
4696 		} else {
4697 			/*
4698 			 * Beware of being called during attach/detach
4699 			 * to reset promiscuous mode.  In that case we
4700 			 * will still be marked UP but not RUNNING.
4701 			 * However trying to re-init the interface
4702 			 * is the wrong thing to do as we've already
4703 			 * torn down much of our state.  There's
4704 			 * probably a better way to deal with this.
4705 			 */
4706 			if (!sc->sc_invalid) {
4707 				mwl_init(sc);	/* XXX lose error */
4708 				startall = 1;
4709 			}
4710 		}
4711 	} else
4712 		mwl_stop(sc);
4713 	MWL_UNLOCK(sc);
4714 	if (startall)
4715 		ieee80211_start_all(ic);
4716 }
4717 
4718 static int
4719 mwl_ioctl(struct ieee80211com *ic, u_long cmd, void *data)
4720 {
4721 	struct mwl_softc *sc = ic->ic_softc;
4722 	struct ifreq *ifr = data;
4723 	int error = 0;
4724 
4725 	switch (cmd) {
4726 	case SIOCGMVSTATS:
4727 		mwl_hal_gethwstats(sc->sc_mh, &sc->sc_stats.hw_stats);
4728 #if 0
4729 		/* NB: embed these numbers to get a consistent view */
4730 		sc->sc_stats.mst_tx_packets =
4731 		    ifp->if_get_counter(ifp, IFCOUNTER_OPACKETS);
4732 		sc->sc_stats.mst_rx_packets =
4733 		    ifp->if_get_counter(ifp, IFCOUNTER_IPACKETS);
4734 #endif
4735 		/*
4736 		 * NB: Drop the softc lock in case of a page fault;
4737 		 * we'll accept any potential inconsisentcy in the
4738 		 * statistics.  The alternative is to copy the data
4739 		 * to a local structure.
4740 		 */
4741 		return (copyout(&sc->sc_stats, ifr_data_get_ptr(ifr),
4742 		    sizeof (sc->sc_stats)));
4743 #ifdef MWL_DIAGAPI
4744 	case SIOCGMVDIAG:
4745 		/* XXX check privs */
4746 		return mwl_ioctl_diag(sc, (struct mwl_diag *) ifr);
4747 	case SIOCGMVRESET:
4748 		/* XXX check privs */
4749 		MWL_LOCK(sc);
4750 		error = mwl_ioctl_reset(sc,(struct mwl_diag *) ifr);
4751 		MWL_UNLOCK(sc);
4752 		break;
4753 #endif /* MWL_DIAGAPI */
4754 	default:
4755 		error = ENOTTY;
4756 		break;
4757 	}
4758 	return (error);
4759 }
4760 
4761 #ifdef	MWL_DEBUG
4762 static int
4763 mwl_sysctl_debug(SYSCTL_HANDLER_ARGS)
4764 {
4765 	struct mwl_softc *sc = arg1;
4766 	int debug, error;
4767 
4768 	debug = sc->sc_debug | (mwl_hal_getdebug(sc->sc_mh) << 24);
4769 	error = sysctl_handle_int(oidp, &debug, 0, req);
4770 	if (error || !req->newptr)
4771 		return error;
4772 	mwl_hal_setdebug(sc->sc_mh, debug >> 24);
4773 	sc->sc_debug = debug & 0x00ffffff;
4774 	return 0;
4775 }
4776 #endif /* MWL_DEBUG */
4777 
4778 static void
4779 mwl_sysctlattach(struct mwl_softc *sc)
4780 {
4781 #ifdef	MWL_DEBUG
4782 	struct sysctl_ctx_list *ctx = device_get_sysctl_ctx(sc->sc_dev);
4783 	struct sysctl_oid *tree = device_get_sysctl_tree(sc->sc_dev);
4784 
4785 	sc->sc_debug = mwl_debug;
4786 	SYSCTL_ADD_PROC(ctx, SYSCTL_CHILDREN(tree), OID_AUTO,
4787 		"debug", CTLTYPE_INT | CTLFLAG_RW, sc, 0,
4788 		mwl_sysctl_debug, "I", "control debugging printfs");
4789 #endif
4790 }
4791 
4792 /*
4793  * Announce various information on device/driver attach.
4794  */
4795 static void
4796 mwl_announce(struct mwl_softc *sc)
4797 {
4798 
4799 	device_printf(sc->sc_dev, "Rev A%d hardware, v%d.%d.%d.%d firmware (regioncode %d)\n",
4800 		sc->sc_hwspecs.hwVersion,
4801 		(sc->sc_hwspecs.fwReleaseNumber>>24) & 0xff,
4802 		(sc->sc_hwspecs.fwReleaseNumber>>16) & 0xff,
4803 		(sc->sc_hwspecs.fwReleaseNumber>>8) & 0xff,
4804 		(sc->sc_hwspecs.fwReleaseNumber>>0) & 0xff,
4805 		sc->sc_hwspecs.regionCode);
4806 	sc->sc_fwrelease = sc->sc_hwspecs.fwReleaseNumber;
4807 
4808 	if (bootverbose) {
4809 		int i;
4810 		for (i = 0; i <= WME_AC_VO; i++) {
4811 			struct mwl_txq *txq = sc->sc_ac2q[i];
4812 			device_printf(sc->sc_dev, "Use hw queue %u for %s traffic\n",
4813 				txq->qnum, ieee80211_wme_acnames[i]);
4814 		}
4815 	}
4816 	if (bootverbose || mwl_rxdesc != MWL_RXDESC)
4817 		device_printf(sc->sc_dev, "using %u rx descriptors\n", mwl_rxdesc);
4818 	if (bootverbose || mwl_rxbuf != MWL_RXBUF)
4819 		device_printf(sc->sc_dev, "using %u rx buffers\n", mwl_rxbuf);
4820 	if (bootverbose || mwl_txbuf != MWL_TXBUF)
4821 		device_printf(sc->sc_dev, "using %u tx buffers\n", mwl_txbuf);
4822 	if (bootverbose && mwl_hal_ismbsscapable(sc->sc_mh))
4823 		device_printf(sc->sc_dev, "multi-bss support\n");
4824 #ifdef MWL_TX_NODROP
4825 	if (bootverbose)
4826 		device_printf(sc->sc_dev, "no tx drop\n");
4827 #endif
4828 }
4829