xref: /freebsd/usr.sbin/wlanstat/wlanstat.c (revision 89eee8ee2ce57b7884defb8f9af016cd28ef1562)
1*89eee8eeSLi-Wen Hsu /*-
2*89eee8eeSLi-Wen Hsu  * Copyright (c) 2002-2007 Sam Leffler, Errno Consulting
3*89eee8eeSLi-Wen Hsu  * All rights reserved.
4*89eee8eeSLi-Wen Hsu  *
5*89eee8eeSLi-Wen Hsu  * Redistribution and use in source and binary forms, with or without
6*89eee8eeSLi-Wen Hsu  * modification, are permitted provided that the following conditions
7*89eee8eeSLi-Wen Hsu  * are met:
8*89eee8eeSLi-Wen Hsu  * 1. Redistributions of source code must retain the above copyright
9*89eee8eeSLi-Wen Hsu  *    notice, this list of conditions and the following disclaimer,
10*89eee8eeSLi-Wen Hsu  *    without modification.
11*89eee8eeSLi-Wen Hsu  * 2. Redistributions in binary form must reproduce at minimum a disclaimer
12*89eee8eeSLi-Wen Hsu  *    similar to the "NO WARRANTY" disclaimer below ("Disclaimer") and any
13*89eee8eeSLi-Wen Hsu  *    redistribution must be conditioned upon including a substantially
14*89eee8eeSLi-Wen Hsu  *    similar Disclaimer requirement for further binary redistribution.
15*89eee8eeSLi-Wen Hsu  *
16*89eee8eeSLi-Wen Hsu  * NO WARRANTY
17*89eee8eeSLi-Wen Hsu  * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
18*89eee8eeSLi-Wen Hsu  * ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
19*89eee8eeSLi-Wen Hsu  * LIMITED TO, THE IMPLIED WARRANTIES OF NONINFRINGEMENT, MERCHANTIBILITY
20*89eee8eeSLi-Wen Hsu  * AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL
21*89eee8eeSLi-Wen Hsu  * THE COPYRIGHT HOLDERS OR CONTRIBUTORS BE LIABLE FOR SPECIAL, EXEMPLARY,
22*89eee8eeSLi-Wen Hsu  * OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
23*89eee8eeSLi-Wen Hsu  * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
24*89eee8eeSLi-Wen Hsu  * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER
25*89eee8eeSLi-Wen Hsu  * IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
26*89eee8eeSLi-Wen Hsu  * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
27*89eee8eeSLi-Wen Hsu  * THE POSSIBILITY OF SUCH DAMAGES.
28*89eee8eeSLi-Wen Hsu  */
29*89eee8eeSLi-Wen Hsu 
30*89eee8eeSLi-Wen Hsu /*
31*89eee8eeSLi-Wen Hsu  * net80211 statistics class.
32*89eee8eeSLi-Wen Hsu  */
33*89eee8eeSLi-Wen Hsu 
34*89eee8eeSLi-Wen Hsu #include <sys/param.h>
35*89eee8eeSLi-Wen Hsu #include <sys/file.h>
36*89eee8eeSLi-Wen Hsu #include <sys/sockio.h>
37*89eee8eeSLi-Wen Hsu #include <sys/socket.h>
38*89eee8eeSLi-Wen Hsu 
39*89eee8eeSLi-Wen Hsu #include <net/if.h>
40*89eee8eeSLi-Wen Hsu #include <net/if_dl.h>
41*89eee8eeSLi-Wen Hsu #include <net/if_media.h>
42*89eee8eeSLi-Wen Hsu #include <net/if_var.h>
43*89eee8eeSLi-Wen Hsu #include <net/ethernet.h>
44*89eee8eeSLi-Wen Hsu 
45*89eee8eeSLi-Wen Hsu #include <err.h>
46*89eee8eeSLi-Wen Hsu #include <ifaddrs.h>
47*89eee8eeSLi-Wen Hsu #include <signal.h>
48*89eee8eeSLi-Wen Hsu #include <stdio.h>
49*89eee8eeSLi-Wen Hsu #include <stdlib.h>
50*89eee8eeSLi-Wen Hsu #include <string.h>
51*89eee8eeSLi-Wen Hsu #include <unistd.h>
52*89eee8eeSLi-Wen Hsu 
53*89eee8eeSLi-Wen Hsu #include "../../sys/net80211/ieee80211_ioctl.h"
54*89eee8eeSLi-Wen Hsu 
55*89eee8eeSLi-Wen Hsu #include "wlanstat.h"
56*89eee8eeSLi-Wen Hsu 
57*89eee8eeSLi-Wen Hsu #ifndef IEEE80211_ADDR_COPY
58*89eee8eeSLi-Wen Hsu #define	IEEE80211_ADDR_COPY(dst, src)	memcpy(dst, src, IEEE80211_ADDR_LEN)
59*89eee8eeSLi-Wen Hsu #define	IEEE80211_ADDR_EQ(a1,a2)	(memcmp(a1,a2,IEEE80211_ADDR_LEN) == 0)
60*89eee8eeSLi-Wen Hsu #endif
61*89eee8eeSLi-Wen Hsu 
62*89eee8eeSLi-Wen Hsu #define	AFTER(prev)	((prev)+1)
63*89eee8eeSLi-Wen Hsu 
64*89eee8eeSLi-Wen Hsu static const struct fmt wlanstat[] = {
65*89eee8eeSLi-Wen Hsu #define	S_RX_BADVERSION		0
66*89eee8eeSLi-Wen Hsu 	{ 5,  "rx_badversion",	"bvers",	"rx frame with bad version" },
67*89eee8eeSLi-Wen Hsu #define	S_RX_TOOSHORT		AFTER(S_RX_BADVERSION)
68*89eee8eeSLi-Wen Hsu 	{ 5,  "rx_tooshort",	"2short",	"rx frame too short" },
69*89eee8eeSLi-Wen Hsu #define	S_RX_WRONGBSS		AFTER(S_RX_TOOSHORT)
70*89eee8eeSLi-Wen Hsu 	{ 5,  "rx_wrongbss",	"wrbss",	"rx from wrong bssid" },
71*89eee8eeSLi-Wen Hsu #define	S_RX_DUP		AFTER(S_RX_WRONGBSS)
72*89eee8eeSLi-Wen Hsu 	{ 5,  "rx_dup",		"rxdup",	"rx discard 'cuz dup" },
73*89eee8eeSLi-Wen Hsu #define	S_RX_WRONGDIR		AFTER(S_RX_DUP)
74*89eee8eeSLi-Wen Hsu 	{ 5,  "rx_wrongdir",	"wrdir",	"rx w/ wrong direction" },
75*89eee8eeSLi-Wen Hsu #define	S_RX_MCASTECHO		AFTER(S_RX_WRONGDIR)
76*89eee8eeSLi-Wen Hsu 	{ 5,  "rx_mcastecho",	"mecho",	"rx discard 'cuz mcast echo" },
77*89eee8eeSLi-Wen Hsu #define	S_RX_NOTASSOC		AFTER(S_RX_MCASTECHO)
78*89eee8eeSLi-Wen Hsu 	{ 6,  "rx_notassoc",	"!assoc",	"rx discard 'cuz sta !assoc" },
79*89eee8eeSLi-Wen Hsu #define	S_RX_NOPRIVACY		AFTER(S_RX_NOTASSOC)
80*89eee8eeSLi-Wen Hsu 	{ 6,  "rx_noprivacy",	"nopriv",	"rx w/ wep but privacy off" },
81*89eee8eeSLi-Wen Hsu #define	S_RX_UNENCRYPTED	AFTER(S_RX_NOPRIVACY)
82*89eee8eeSLi-Wen Hsu 	{ 6,  "rx_unencrypted",	"unencr",	"rx w/o wep and privacy on" },
83*89eee8eeSLi-Wen Hsu #define	S_RX_WEPFAIL		AFTER(S_RX_UNENCRYPTED)
84*89eee8eeSLi-Wen Hsu 	{ 7,  "rx_wepfail",	"wepfail",	"rx wep processing failed" },
85*89eee8eeSLi-Wen Hsu #define	S_RX_DECAP		AFTER(S_RX_WEPFAIL)
86*89eee8eeSLi-Wen Hsu 	{ 5,  "rx_decap",	"decap",	"rx decapsulation failed" },
87*89eee8eeSLi-Wen Hsu #define	S_RX_MGTDISCARD		AFTER(S_RX_DECAP)
88*89eee8eeSLi-Wen Hsu 	{ 8,  "rx_mgtdiscard",	"mgtdiscard",	"rx discard mgt frames" },
89*89eee8eeSLi-Wen Hsu #define	S_RX_CTL		AFTER(S_RX_MGTDISCARD)
90*89eee8eeSLi-Wen Hsu 	{ 5,  "rx_ctl",		"ctl",		"rx ctrl frames" },
91*89eee8eeSLi-Wen Hsu #define	S_RX_BEACON		AFTER(S_RX_CTL)
92*89eee8eeSLi-Wen Hsu 	{ 6,  "rx_beacon",	"beacon",	"rx beacon frames" },
93*89eee8eeSLi-Wen Hsu #define	S_RX_RSTOOBIG		AFTER(S_RX_BEACON)
94*89eee8eeSLi-Wen Hsu 	{ 6,  "rx_rstoobig",	"rs2big",	"rx rate set truncated" },
95*89eee8eeSLi-Wen Hsu #define	S_RX_ELEM_MISSING	AFTER(S_RX_RSTOOBIG)
96*89eee8eeSLi-Wen Hsu 	{ 6,  "rx_elem_missing","iemiss",	"rx required element missing" },
97*89eee8eeSLi-Wen Hsu #define	S_RX_ELEM_TOOBIG	AFTER(S_RX_ELEM_MISSING)
98*89eee8eeSLi-Wen Hsu 	{ 6,  "rx_elem_toobig",	"ie2big",	"rx element too big" },
99*89eee8eeSLi-Wen Hsu #define	S_RX_ELEM_TOOSMALL	AFTER(S_RX_ELEM_TOOBIG)
100*89eee8eeSLi-Wen Hsu 	{ 7,  "rx_elem_toosmall","ie2small","rx element too small" },
101*89eee8eeSLi-Wen Hsu #define	S_RX_ELEM_UNKNOWN 	AFTER(S_RX_ELEM_TOOSMALL)
102*89eee8eeSLi-Wen Hsu 	{ 5,  "rx_elem_unknown","ieunk",	"rx element unknown" },
103*89eee8eeSLi-Wen Hsu #define	S_RX_BADCHAN		AFTER(S_RX_ELEM_UNKNOWN)
104*89eee8eeSLi-Wen Hsu 	{ 6,  "rx_badchan",	"badchan",	"rx frame w/ invalid chan" },
105*89eee8eeSLi-Wen Hsu #define	S_RX_CHANMISMATCH	AFTER(S_RX_BADCHAN)
106*89eee8eeSLi-Wen Hsu 	{ 5,  "rx_chanmismatch","chanmismatch",	"rx frame chan mismatch" },
107*89eee8eeSLi-Wen Hsu #define	S_RX_NODEALLOC		AFTER(S_RX_CHANMISMATCH)
108*89eee8eeSLi-Wen Hsu 	{ 5,  "rx_nodealloc",	"nodealloc",	"nodes allocated (rx)" },
109*89eee8eeSLi-Wen Hsu #define	S_RX_SSIDMISMATCH	AFTER(S_RX_NODEALLOC)
110*89eee8eeSLi-Wen Hsu 	{ 5,  "rx_ssidmismatch","ssidmismatch",	"rx frame ssid mismatch" },
111*89eee8eeSLi-Wen Hsu #define	S_RX_AUTH_UNSUPPORTED	AFTER(S_RX_SSIDMISMATCH)
112*89eee8eeSLi-Wen Hsu 	{ 5,  "rx_auth_unsupported","auth_unsupported",
113*89eee8eeSLi-Wen Hsu 		"rx w/ unsupported auth alg" },
114*89eee8eeSLi-Wen Hsu #define	S_RX_AUTH_FAIL		AFTER(S_RX_AUTH_UNSUPPORTED)
115*89eee8eeSLi-Wen Hsu 	{ 5,  "rx_auth_fail",	"auth_fail",	"rx sta auth failure" },
116*89eee8eeSLi-Wen Hsu #define	S_RX_AUTH_FAIL_CODE	AFTER(S_RX_AUTH_FAIL)
117*89eee8eeSLi-Wen Hsu 	{ 5,  "rx_auth_fail_code","auth_fail_code",
118*89eee8eeSLi-Wen Hsu 		"last rx auth failure reason" },
119*89eee8eeSLi-Wen Hsu #define	S_RX_AUTH_COUNTERMEASURES	AFTER(S_RX_AUTH_FAIL_CODE)
120*89eee8eeSLi-Wen Hsu 	{ 5,  "rx_auth_countermeasures",	"auth_countermeasures",
121*89eee8eeSLi-Wen Hsu 		"rx sta auth failure 'cuz of TKIP countermeasures" },
122*89eee8eeSLi-Wen Hsu #define	S_RX_ASSOC_BSS		AFTER(S_RX_AUTH_COUNTERMEASURES)
123*89eee8eeSLi-Wen Hsu 	{ 5,  "rx_assoc_bss",	"assoc_bss",	"rx assoc from wrong bssid" },
124*89eee8eeSLi-Wen Hsu #define	S_RX_ASSOC_NOTAUTH	AFTER(S_RX_ASSOC_BSS)
125*89eee8eeSLi-Wen Hsu 	{ 5,  "rx_assoc_notauth","assoc_notauth",	"rx assoc w/o auth" },
126*89eee8eeSLi-Wen Hsu #define	S_RX_ASSOC_CAPMISMATCH	AFTER(S_RX_ASSOC_NOTAUTH)
127*89eee8eeSLi-Wen Hsu 	{ 5,  "rx_assoc_capmismatch","assoc_capmismatch",
128*89eee8eeSLi-Wen Hsu 		"rx assoc w/ cap mismatch" },
129*89eee8eeSLi-Wen Hsu #define	S_RX_ASSOC_NORATE	AFTER(S_RX_ASSOC_CAPMISMATCH)
130*89eee8eeSLi-Wen Hsu 	{ 5,  "rx_assoc_norate","assoc_norate",	"rx assoc w/ no rate match" },
131*89eee8eeSLi-Wen Hsu #define	S_RX_ASSOC_BADWPAIE	AFTER(S_RX_ASSOC_NORATE)
132*89eee8eeSLi-Wen Hsu 	{ 5,  "rx_assoc_badwpaie","assoc_badwpaie",
133*89eee8eeSLi-Wen Hsu 		"rx assoc w/ bad WPA IE" },
134*89eee8eeSLi-Wen Hsu #define	S_RX_DEAUTH		AFTER(S_RX_ASSOC_BADWPAIE)
135*89eee8eeSLi-Wen Hsu 	{ 5,  "rx_deauth",	"deauth",	"rx deauthentication" },
136*89eee8eeSLi-Wen Hsu #define	S_RX_DEAUTH_CODE	AFTER(S_RX_DEAUTH)
137*89eee8eeSLi-Wen Hsu 	{ 5,  "rx_deauth_code","deauth_code",	"last rx deauth reason" },
138*89eee8eeSLi-Wen Hsu #define	S_RX_DISASSOC		AFTER(S_RX_DEAUTH_CODE)
139*89eee8eeSLi-Wen Hsu 	{ 5,  "rx_disassoc",	"disassoc",	"rx disassociation" },
140*89eee8eeSLi-Wen Hsu #define	S_RX_DISASSOC_CODE	AFTER(S_RX_DISASSOC)
141*89eee8eeSLi-Wen Hsu 	{ 5,  "rx_disassoc_code","disassoc_code",
142*89eee8eeSLi-Wen Hsu 		"last rx disassoc reason" },
143*89eee8eeSLi-Wen Hsu #define	S_BMISS			AFTER(S_RX_DISASSOC_CODE)
144*89eee8eeSLi-Wen Hsu 	{ 5,  "bmiss",		"bmiss",	"beacon miss events handled" },
145*89eee8eeSLi-Wen Hsu #define	S_RX_BADSUBTYPE		AFTER(S_BMISS)
146*89eee8eeSLi-Wen Hsu 	{ 5,  "rx_badsubtype",	"badsubtype",	"rx frame w/ unknown subtype" },
147*89eee8eeSLi-Wen Hsu #define	S_RX_NOBUF		AFTER(S_RX_BADSUBTYPE)
148*89eee8eeSLi-Wen Hsu 	{ 5,  "rx_nobuf",	"nobuf",	"rx failed for lack of mbuf" },
149*89eee8eeSLi-Wen Hsu #define	S_RX_DECRYPTCRC		AFTER(S_RX_NOBUF)
150*89eee8eeSLi-Wen Hsu 	{ 5,  "rx_decryptcrc",	"decryptcrc",	"rx decrypt failed on crc" },
151*89eee8eeSLi-Wen Hsu #define	S_RX_AHDEMO_MGT		AFTER(S_RX_DECRYPTCRC)
152*89eee8eeSLi-Wen Hsu 	{ 5,  "rx_ahdemo_mgt",	"ahdemo_mgt",
153*89eee8eeSLi-Wen Hsu 		"rx discard mgmt frame received in ahdoc demo mode" },
154*89eee8eeSLi-Wen Hsu #define	S_RX_BAD_AUTH		AFTER(S_RX_AHDEMO_MGT)
155*89eee8eeSLi-Wen Hsu 	{ 5,  "rx_bad_auth",	"bad_auth",	"rx bad authentication request" },
156*89eee8eeSLi-Wen Hsu #define	S_RX_UNAUTH		AFTER(S_RX_BAD_AUTH)
157*89eee8eeSLi-Wen Hsu 	{ 5,  "rx_unauth",	"unauth",
158*89eee8eeSLi-Wen Hsu 		"rx discard 'cuz port unauthorized" },
159*89eee8eeSLi-Wen Hsu #define	S_RX_BADKEYID		AFTER(S_RX_UNAUTH)
160*89eee8eeSLi-Wen Hsu 	{ 5,  "rx_badkeyid",	"rxkid",	"rx w/ incorrect keyid" },
161*89eee8eeSLi-Wen Hsu #define	S_RX_CCMPREPLAY		AFTER(S_RX_BADKEYID)
162*89eee8eeSLi-Wen Hsu 	{ 5,  "rx_ccmpreplay",	"ccmpreplay",	"rx seq# violation (CCMP)" },
163*89eee8eeSLi-Wen Hsu #define	S_RX_CCMPFORMAT		AFTER(S_RX_CCMPREPLAY)
164*89eee8eeSLi-Wen Hsu 	{ 5,  "rx_ccmpformat",	"ccmpformat",	"rx format bad (CCMP)" },
165*89eee8eeSLi-Wen Hsu #define	S_RX_CCMPMIC		AFTER(S_RX_CCMPFORMAT)
166*89eee8eeSLi-Wen Hsu 	{ 5,  "rx_ccmpmic",	"ccmpmic",	"rx MIC check failed (CCMP)" },
167*89eee8eeSLi-Wen Hsu #define	S_RX_TKIPREPLAY		AFTER(S_RX_CCMPMIC)
168*89eee8eeSLi-Wen Hsu 	{ 5,  "rx_tkipreplay",	"tkipreplay",	"rx seq# violation (TKIP)" },
169*89eee8eeSLi-Wen Hsu #define	S_RX_TKIPFORMAT		AFTER(S_RX_TKIPREPLAY)
170*89eee8eeSLi-Wen Hsu 	{ 5,  "rx_tkipformat",	"tkipformat",	"rx format bad (TKIP)" },
171*89eee8eeSLi-Wen Hsu #define	S_RX_TKIPMIC		AFTER(S_RX_TKIPFORMAT)
172*89eee8eeSLi-Wen Hsu 	{ 5,  "rx_tkipmic",	"tkipmic",	"rx MIC check failed (TKIP)" },
173*89eee8eeSLi-Wen Hsu #define	S_RX_TKIPICV		AFTER(S_RX_TKIPMIC)
174*89eee8eeSLi-Wen Hsu 	{ 5,  "rx_tkipicv",	"tkipicv",	"rx ICV check failed (TKIP)" },
175*89eee8eeSLi-Wen Hsu #define	S_RX_BADCIPHER		AFTER(S_RX_TKIPICV)
176*89eee8eeSLi-Wen Hsu 	{ 5,  "rx_badcipher",	"badcipher",	"rx failed 'cuz bad cipher/key type" },
177*89eee8eeSLi-Wen Hsu #define	S_RX_NOCIPHERCTX	AFTER(S_RX_BADCIPHER)
178*89eee8eeSLi-Wen Hsu 	{ 5,  "rx_nocipherctx",	"nocipherctx",	"rx failed 'cuz key/cipher ctx not setup" },
179*89eee8eeSLi-Wen Hsu #define	S_RX_ACL		AFTER(S_RX_NOCIPHERCTX)
180*89eee8eeSLi-Wen Hsu 	{ 5,  "rx_acl",		"acl",		"rx discard 'cuz acl policy" },
181*89eee8eeSLi-Wen Hsu #define	S_TX_NOBUF		AFTER(S_RX_ACL)
182*89eee8eeSLi-Wen Hsu 	{ 5,  "tx_nobuf",	"nobuf",	"tx failed for lack of mbuf" },
183*89eee8eeSLi-Wen Hsu #define	S_TX_NONODE		AFTER(S_TX_NOBUF)
184*89eee8eeSLi-Wen Hsu 	{ 5,  "tx_nonode",	"nonode",	"tx failed for no node" },
185*89eee8eeSLi-Wen Hsu #define	S_TX_UNKNOWNMGT		AFTER(S_TX_NONODE)
186*89eee8eeSLi-Wen Hsu 	{ 5,  "tx_unknownmgt",	"unknownmgt",	"tx of unknown mgt frame" },
187*89eee8eeSLi-Wen Hsu #define	S_TX_BADCIPHER		AFTER(S_TX_UNKNOWNMGT)
188*89eee8eeSLi-Wen Hsu 	{ 5,  "tx_badcipher",	"badcipher",	"tx failed 'cuz bad ciper/key type" },
189*89eee8eeSLi-Wen Hsu #define	S_TX_NODEFKEY		AFTER(S_TX_BADCIPHER)
190*89eee8eeSLi-Wen Hsu 	{ 5,  "tx_nodefkey",	"nodefkey",	"tx failed 'cuz no defkey" },
191*89eee8eeSLi-Wen Hsu #define	S_TX_NOHEADROOM		AFTER(S_TX_NODEFKEY)
192*89eee8eeSLi-Wen Hsu 	{ 5,  "tx_noheadroom",	"noheadroom",	"tx failed 'cuz no space for crypto hdrs" },
193*89eee8eeSLi-Wen Hsu #define	S_TX_FRAGFRAMES		AFTER(S_TX_NOHEADROOM)
194*89eee8eeSLi-Wen Hsu 	{ 5,  "tx_fragframes",	"fragframes",	"tx frames fragmented" },
195*89eee8eeSLi-Wen Hsu #define	S_TX_FRAGS		AFTER(S_TX_FRAGFRAMES)
196*89eee8eeSLi-Wen Hsu 	{ 5,  "tx_frags",	"frags",		"tx frags generated" },
197*89eee8eeSLi-Wen Hsu #define	S_SCAN_ACTIVE		AFTER(S_TX_FRAGS)
198*89eee8eeSLi-Wen Hsu 	{ 5,  "scan_active",	"ascan",	"active scans started" },
199*89eee8eeSLi-Wen Hsu #define	S_SCAN_PASSIVE		AFTER(S_SCAN_ACTIVE)
200*89eee8eeSLi-Wen Hsu 	{ 5,  "scan_passive",	"pscan",	"passive scans started" },
201*89eee8eeSLi-Wen Hsu #define	S_SCAN_BG		AFTER(S_SCAN_PASSIVE)
202*89eee8eeSLi-Wen Hsu 	{ 5,  "scan_bg",	"bgscn",	"background scans started" },
203*89eee8eeSLi-Wen Hsu #define	S_NODE_TIMEOUT		AFTER(S_SCAN_BG)
204*89eee8eeSLi-Wen Hsu 	{ 5,  "node_timeout",	"node_timeout",	"nodes timed out for inactivity" },
205*89eee8eeSLi-Wen Hsu #define	S_CRYPTO_NOMEM		AFTER(S_NODE_TIMEOUT)
206*89eee8eeSLi-Wen Hsu 	{ 5,  "crypto_nomem",	"crypto_nomem",	"cipher context malloc failed" },
207*89eee8eeSLi-Wen Hsu #define	S_CRYPTO_TKIP		AFTER(S_CRYPTO_NOMEM)
208*89eee8eeSLi-Wen Hsu 	{ 5,  "crypto_tkip",	"crypto_tkip",	"tkip crypto done in s/w" },
209*89eee8eeSLi-Wen Hsu #define	S_CRYPTO_TKIPENMIC	AFTER(S_CRYPTO_TKIP)
210*89eee8eeSLi-Wen Hsu 	{ 5,  "crypto_tkipenmic","crypto_tkipenmic",	"tkip tx MIC done in s/w" },
211*89eee8eeSLi-Wen Hsu #define	S_CRYPTO_TKIPDEMIC	AFTER(S_CRYPTO_TKIPENMIC)
212*89eee8eeSLi-Wen Hsu 	{ 5,  "crypto_tkipdemic","crypto_tkipdemic",	"tkip rx MIC done in s/w" },
213*89eee8eeSLi-Wen Hsu #define	S_CRYPTO_TKIPCM		AFTER(S_CRYPTO_TKIPDEMIC)
214*89eee8eeSLi-Wen Hsu 	{ 5,  "crypto_tkipcm",	"crypto_tkipcm",	"tkip dropped frames 'cuz of countermeasures" },
215*89eee8eeSLi-Wen Hsu #define	S_CRYPTO_CCMP		AFTER(S_CRYPTO_TKIPCM)
216*89eee8eeSLi-Wen Hsu 	{ 5,  "crypto_ccmp",	"crypto_ccmp",	"ccmp crypto done in s/w" },
217*89eee8eeSLi-Wen Hsu #define	S_CRYPTO_WEP		AFTER(S_CRYPTO_CCMP)
218*89eee8eeSLi-Wen Hsu 	{ 5,  "crypto_wep",	"crypto_wep",	"wep crypto done in s/w" },
219*89eee8eeSLi-Wen Hsu #define	S_CRYPTO_SETKEY_CIPHER	AFTER(S_CRYPTO_WEP)
220*89eee8eeSLi-Wen Hsu 	{ 5,  "crypto_setkey_cipher",	"crypto_setkey_cipher","setkey failed 'cuz cipher rejected data" },
221*89eee8eeSLi-Wen Hsu #define	S_CRYPTO_SETKEY_NOKEY	AFTER(S_CRYPTO_SETKEY_CIPHER)
222*89eee8eeSLi-Wen Hsu 	{ 5,  "crypto_setkey_nokey",	"crypto_setkey_nokey","setkey failed 'cuz no key index" },
223*89eee8eeSLi-Wen Hsu #define	S_CRYPTO_DELKEY		AFTER(S_CRYPTO_SETKEY_NOKEY)
224*89eee8eeSLi-Wen Hsu 	{ 5,  "crypto_delkey",	"crypto_delkey",	"driver key delete failed" },
225*89eee8eeSLi-Wen Hsu #define	S_CRYPTO_BADCIPHER	AFTER(S_CRYPTO_DELKEY)
226*89eee8eeSLi-Wen Hsu 	{ 5,  "crypto_badcipher","crypto_badcipher",	"setkey failed 'cuz unknown cipher" },
227*89eee8eeSLi-Wen Hsu #define	S_CRYPTO_NOCIPHER	AFTER(S_CRYPTO_BADCIPHER)
228*89eee8eeSLi-Wen Hsu 	{ 5,  "crypto_nocipher","crypto_nocipher",	"setkey failed 'cuz cipher module unavailable" },
229*89eee8eeSLi-Wen Hsu #define	S_CRYPTO_ATTACHFAIL	AFTER(S_CRYPTO_NOCIPHER)
230*89eee8eeSLi-Wen Hsu 	{ 5,  "crypto_attachfail","crypto_attachfail",	"setkey failed 'cuz cipher attach failed" },
231*89eee8eeSLi-Wen Hsu #define	S_CRYPTO_SWFALLBACK	AFTER(S_CRYPTO_ATTACHFAIL)
232*89eee8eeSLi-Wen Hsu 	{ 5,  "crypto_swfallback","crypto_swfallback",	"crypto fell back to s/w implementation" },
233*89eee8eeSLi-Wen Hsu #define	S_CRYPTO_KEYFAIL	AFTER(S_CRYPTO_SWFALLBACK)
234*89eee8eeSLi-Wen Hsu 	{ 5,  "crypto_keyfail",	"crypto_keyfail",	"setkey failed 'cuz driver key alloc failed" },
235*89eee8eeSLi-Wen Hsu #define	S_CRYPTO_ENMICFAIL	AFTER(S_CRYPTO_KEYFAIL)
236*89eee8eeSLi-Wen Hsu 	{ 5,  "crypto_enmicfail","crypto_enmicfail",	"enmic failed (may be mbuf exhaustion)" },
237*89eee8eeSLi-Wen Hsu #define	S_IBSS_CAPMISMATCH	AFTER(S_CRYPTO_ENMICFAIL)
238*89eee8eeSLi-Wen Hsu 	{ 5,  "ibss_capmismatch","ibss_capmismatch",	"ibss merge faied 'cuz capabilities mismatch" },
239*89eee8eeSLi-Wen Hsu #define	S_IBSS_NORATE		AFTER(S_IBSS_CAPMISMATCH)
240*89eee8eeSLi-Wen Hsu 	{ 5,  "ibss_norate",	"ibss_norate",	"ibss merge faied 'cuz rate set mismatch" },
241*89eee8eeSLi-Wen Hsu #define	S_PS_UNASSOC		AFTER(S_IBSS_NORATE)
242*89eee8eeSLi-Wen Hsu 	{ 5,  "ps_unassoc",	"ps_unassoc",	"ps-poll received for unassociated station" },
243*89eee8eeSLi-Wen Hsu #define	S_PS_BADAID		AFTER(S_PS_UNASSOC)
244*89eee8eeSLi-Wen Hsu 	{ 5,  "ps_badaid",	"ps_badaid",	"ps-poll received with invalid association id" },
245*89eee8eeSLi-Wen Hsu #define	S_PS_QEMPTY		AFTER(S_PS_BADAID)
246*89eee8eeSLi-Wen Hsu 	{ 5,  "ps_qempty",	"ps_qempty",	"ps-poll received with nothing to send" },
247*89eee8eeSLi-Wen Hsu #define	S_FF_BADHDR		AFTER(S_PS_QEMPTY)
248*89eee8eeSLi-Wen Hsu 	{ 5,  "ff_badhdr",	"ff_badhdr",	"fast frame rx'd w/ bad hdr" },
249*89eee8eeSLi-Wen Hsu #define	S_FF_TOOSHORT		AFTER(S_FF_BADHDR)
250*89eee8eeSLi-Wen Hsu 	{ 5,  "ff_tooshort",	"ff_tooshort",	"fast frame rx decap error" },
251*89eee8eeSLi-Wen Hsu #define	S_FF_SPLIT		AFTER(S_FF_TOOSHORT)
252*89eee8eeSLi-Wen Hsu 	{ 5,  "ff_split",	"ff_split",	"fast frame rx split error" },
253*89eee8eeSLi-Wen Hsu #define	S_FF_DECAP		AFTER(S_FF_SPLIT)
254*89eee8eeSLi-Wen Hsu 	{ 5,  "ff_decap",	"ff_decap",	"fast frames decap'd" },
255*89eee8eeSLi-Wen Hsu #define	S_FF_ENCAP		AFTER(S_FF_DECAP)
256*89eee8eeSLi-Wen Hsu 	{ 5,  "ff_encap",	"ff_encap",	"fast frames encap'd for tx" },
257*89eee8eeSLi-Wen Hsu #define	S_FF_ENCAPFAIL		AFTER(S_FF_ENCAP)
258*89eee8eeSLi-Wen Hsu 	{ 5,  "ff_encapfail",	"ff_encapfail",	"fast frames encap failed" },
259*89eee8eeSLi-Wen Hsu #define	S_RX_BADBINTVAL		AFTER(S_FF_ENCAPFAIL)
260*89eee8eeSLi-Wen Hsu 	{ 5,  "rx_badbintval",	"rx_badbintval","rx frame with bogus beacon interval" },
261*89eee8eeSLi-Wen Hsu #define	S_RX_MGMT		AFTER(S_RX_BADBINTVAL)
262*89eee8eeSLi-Wen Hsu 	{ 8,  "rx_mgmt",	"mgmt",		"rx management frames" },
263*89eee8eeSLi-Wen Hsu #define	S_RX_DEMICFAIL		AFTER(S_RX_MGMT)
264*89eee8eeSLi-Wen Hsu 	{ 5,  "rx_demicfail",	"rx_demicfail",	"rx demic failed" },
265*89eee8eeSLi-Wen Hsu #define	S_RX_DEFRAG		AFTER(S_RX_DEMICFAIL)
266*89eee8eeSLi-Wen Hsu 	{ 5,  "rx_defrag",	"rx_defrag",	"rx defragmentation failed" },
267*89eee8eeSLi-Wen Hsu #define	S_RX_ACTION		AFTER(S_RX_DEFRAG)
268*89eee8eeSLi-Wen Hsu 	{ 5,  "rx_action",	"rx_action",	"rx action frames" },
269*89eee8eeSLi-Wen Hsu #define	S_AMSDU_TOOSHORT	AFTER(S_RX_ACTION)
270*89eee8eeSLi-Wen Hsu 	{ 8,  "amsdu_tooshort",	"tooshort","A-MSDU rx decap error" },
271*89eee8eeSLi-Wen Hsu #define	S_AMSDU_SPLIT		AFTER(S_AMSDU_TOOSHORT)
272*89eee8eeSLi-Wen Hsu 	{ 8,  "amsdu_split",	"split",	"A-MSDU rx failed on frame split" },
273*89eee8eeSLi-Wen Hsu #define	S_AMSDU_DECAP		AFTER(S_AMSDU_SPLIT)
274*89eee8eeSLi-Wen Hsu 	{ 8,  "amsdu_decap",	"decap",	"A-MSDU frames received" },
275*89eee8eeSLi-Wen Hsu #define	S_AMSDU_ENCAP		AFTER(S_AMSDU_DECAP)
276*89eee8eeSLi-Wen Hsu 	{ 8,  "amsdu_encap",	"encap",	"A-MSDU frames transmitted" },
277*89eee8eeSLi-Wen Hsu #define	S_AMSDU_RX_MORE		AFTER(S_AMSDU_ENCAP)
278*89eee8eeSLi-Wen Hsu 	{ 13,  "rx_amsdu_more",	"rx_amsdu_more",	"A-MSDU HW intermediary decap'ed received" },
279*89eee8eeSLi-Wen Hsu #define	S_AMSDU_RX_MORE_END		AFTER(S_AMSDU_RX_MORE)
280*89eee8eeSLi-Wen Hsu 	{ 17,  "rx_amsdu_more_end",	"rx_amsdu_more_end",	"A-MSDU HW end decap'ed received" },
281*89eee8eeSLi-Wen Hsu #define	S_AMPDU_REORDER		AFTER(S_AMSDU_RX_MORE_END)
282*89eee8eeSLi-Wen Hsu 	{ 8,  "ampdu_reorder",	"reorder","A-MPDU frames held in reorder q" },
283*89eee8eeSLi-Wen Hsu #define	S_AMPDU_FLUSH		AFTER(S_AMPDU_REORDER)
284*89eee8eeSLi-Wen Hsu 	{ 8,  "ampdu_flush",	"flush",	"A-MPDU frames sent up from reorder q" },
285*89eee8eeSLi-Wen Hsu #define	S_AMPDU_BARBAD		AFTER(S_AMPDU_FLUSH)
286*89eee8eeSLi-Wen Hsu 	{ 6,  "ampdu_barbad",	"barbad",	"A-MPDU BAR rx before ADDBA exchange (or disabled with net.link.ieee80211)" },
287*89eee8eeSLi-Wen Hsu #define	S_AMPDU_BAROOW		AFTER(S_AMPDU_BARBAD)
288*89eee8eeSLi-Wen Hsu 	{ 6,  "ampdu_baroow",	"baroow",	"A-MPDU BAR rx out of BA window" },
289*89eee8eeSLi-Wen Hsu #define	S_AMPDU_BARMOVE		AFTER(S_AMPDU_BAROOW)
290*89eee8eeSLi-Wen Hsu 	{ 8,  "ampdu_barmove",	"barmove","A-MPDU BAR rx moved BA window" },
291*89eee8eeSLi-Wen Hsu #define	S_AMPDU_BAR		AFTER(S_AMPDU_BARMOVE)
292*89eee8eeSLi-Wen Hsu 	{ 8,  "ampdu_bar",	"rxbar",	"A-MPDU BAR rx successful" },
293*89eee8eeSLi-Wen Hsu #define	S_AMPDU_MOVE		AFTER(S_AMPDU_BAR)
294*89eee8eeSLi-Wen Hsu 	{ 5,  "ampdu_move",	"move",	"A-MPDU frame moved BA window" },
295*89eee8eeSLi-Wen Hsu #define	S_AMPDU_OOR		AFTER(S_AMPDU_MOVE)
296*89eee8eeSLi-Wen Hsu 	{ 8,  "ampdu_oor",	"oorx",	"A-MPDU frames rx out-of-order" },
297*89eee8eeSLi-Wen Hsu #define	S_AMPDU_COPY		AFTER(S_AMPDU_OOR)
298*89eee8eeSLi-Wen Hsu 	{ 8,  "ampdu_copy",	"copy",	"A-MPDU rx window slots copied" },
299*89eee8eeSLi-Wen Hsu #define	S_AMPDU_DROP		AFTER(S_AMPDU_COPY)
300*89eee8eeSLi-Wen Hsu 	{ 5,  "ampdu_drop",	"drop",	"A-MPDU frames discarded for out of range seqno" },
301*89eee8eeSLi-Wen Hsu #define	S_AMPDU_AGE		AFTER(S_AMPDU_DROP)
302*89eee8eeSLi-Wen Hsu 	{ 5,  "ampdu_age",	"age",	"A-MPDU frames sent up due to old age" },
303*89eee8eeSLi-Wen Hsu #define	S_AMPDU_STOP		AFTER(S_AMPDU_AGE)
304*89eee8eeSLi-Wen Hsu 	{ 5,  "ampdu_stop",	"stop",	"A-MPDU streams stopped" },
305*89eee8eeSLi-Wen Hsu #define	S_AMPDU_STOP_FAILED	AFTER(S_AMPDU_STOP)
306*89eee8eeSLi-Wen Hsu 	{ 5,  "ampdu_stop_failed","!stop",	"A-MPDU stop requests failed 'cuz stream not running" },
307*89eee8eeSLi-Wen Hsu #define	S_ADDBA_REJECT		AFTER(S_AMPDU_STOP_FAILED)
308*89eee8eeSLi-Wen Hsu 	{ 5,  "addba_reject",	"reject",	"ADDBA requests rejected 'cuz A-MPDU rx is disabled" },
309*89eee8eeSLi-Wen Hsu #define	S_ADDBA_NOREQUEST	AFTER(S_ADDBA_REJECT)
310*89eee8eeSLi-Wen Hsu 	{ 5,  "addba_norequest","norequest","ADDBA response frames discarded because no ADDBA request was pending" },
311*89eee8eeSLi-Wen Hsu #define	S_ADDBA_BADTOKEN	AFTER(S_ADDBA_NOREQUEST)
312*89eee8eeSLi-Wen Hsu 	{ 5,  "addba_badtoken",	"badtoken","ADDBA response frames discarded 'cuz rx'd dialog token is wrong" },
313*89eee8eeSLi-Wen Hsu #define	S_TX_BADSTATE		AFTER(S_ADDBA_BADTOKEN)
314*89eee8eeSLi-Wen Hsu 	{ 4,  "tx_badstate",	"badstate",	"tx failed 'cuz vap not in RUN state" },
315*89eee8eeSLi-Wen Hsu #define	S_TX_NOTASSOC		AFTER(S_TX_BADSTATE)
316*89eee8eeSLi-Wen Hsu 	{ 4,  "tx_notassoc",	"notassoc",	"tx failed 'cuz dest sta not associated" },
317*89eee8eeSLi-Wen Hsu #define	S_TX_CLASSIFY		AFTER(S_TX_NOTASSOC)
318*89eee8eeSLi-Wen Hsu 	{ 4,  "tx_classify",	"classify",	"tx packet classification failed" },
319*89eee8eeSLi-Wen Hsu #define	S_DWDS_MCAST		AFTER(S_TX_CLASSIFY)
320*89eee8eeSLi-Wen Hsu 	{ 8,  "dwds_mcast",	"dwds_mcast",	"mcast frame transmitted on dwds vap discarded" },
321*89eee8eeSLi-Wen Hsu #define	S_DWDS_QDROP		AFTER(S_DWDS_MCAST)
322*89eee8eeSLi-Wen Hsu 	{ 8,  "dwds_qdrop",	"dwds_qdrop",	"4-address frame discarded because dwds pending queue is full" },
323*89eee8eeSLi-Wen Hsu #define	S_HT_ASSOC_NOHTCAP	AFTER(S_DWDS_QDROP)
324*89eee8eeSLi-Wen Hsu 	{ 4,  "ht_nohtcap",	"ht_nohtcap",	"non-HT station rejected in HT-only BSS" },
325*89eee8eeSLi-Wen Hsu #define	S_HT_ASSOC_DOWNGRADE	AFTER(S_HT_ASSOC_NOHTCAP)
326*89eee8eeSLi-Wen Hsu 	{ 4,  "ht_downgrade",	"ht_downgrade",	"HT station downgraded to legacy operation" },
327*89eee8eeSLi-Wen Hsu #define	S_HT_ASSOC_NORATE	AFTER(S_HT_ASSOC_DOWNGRADE)
328*89eee8eeSLi-Wen Hsu 	{ 4,  "ht_norate",	"ht_norate",	"HT station rejected because of HT rate set" },
329*89eee8eeSLi-Wen Hsu #define	S_MESH_WRONGMESH	AFTER(S_HT_ASSOC_NORATE)
330*89eee8eeSLi-Wen Hsu 	{ 4,  "mesh_wrong",	"mesh_wrong",	"frame discarded because sender not a mesh sta" },
331*89eee8eeSLi-Wen Hsu #define	S_MESH_NOLINK		AFTER(S_MESH_WRONGMESH)
332*89eee8eeSLi-Wen Hsu 	{ 4,  "mesh_nolink",	"mesh_nolink",	"frame discarded because link not established" },
333*89eee8eeSLi-Wen Hsu #define	S_MESH_FWD_TTL		AFTER(S_MESH_NOLINK)
334*89eee8eeSLi-Wen Hsu 	{ 4,  "mesh_fwd_ttl",	"mesh_fwd_ttl",	"frame not forwarded because TTL zero" },
335*89eee8eeSLi-Wen Hsu #define	S_MESH_FWD_NOBUF	AFTER(S_MESH_FWD_TTL)
336*89eee8eeSLi-Wen Hsu 	{ 4,  "mesh_fwd_nobuf",	"mesh_fwd_nobuf",	"frame not forwarded because mbuf could not be allocated" },
337*89eee8eeSLi-Wen Hsu #define	S_MESH_FWD_TOOSHORT	AFTER(S_MESH_FWD_NOBUF)
338*89eee8eeSLi-Wen Hsu 	{ 4,  "mesh_fwd_tooshort",	"mesh_fwd_tooshort",	"frame not forwarded because too short to have 802.11 header" },
339*89eee8eeSLi-Wen Hsu #define	S_MESH_FWD_DISABLED	AFTER(S_MESH_FWD_TOOSHORT)
340*89eee8eeSLi-Wen Hsu 	{ 4,  "mesh_fwd_disabled",	"mesh_fwd_disabled",	"frame not forwarded because administratively disabled" },
341*89eee8eeSLi-Wen Hsu #define	S_MESH_FWD_NOPATH	AFTER(S_MESH_FWD_DISABLED)
342*89eee8eeSLi-Wen Hsu 	{ 4,  "mesh_fwd_nopath",	"mesh_fwd_nopath",	"frame not forwarded because no path found to destination" },
343*89eee8eeSLi-Wen Hsu #define	S_HWMP_WRONGSEQ		AFTER(S_MESH_FWD_NOPATH)
344*89eee8eeSLi-Wen Hsu 	{ 4,  "hwmp_wrongseq",	"hwmp_wrongseq",	"frame discarded because mesh sequence number is invalid" },
345*89eee8eeSLi-Wen Hsu #define	S_HWMP_ROOTREQS		AFTER(S_HWMP_WRONGSEQ)
346*89eee8eeSLi-Wen Hsu 	{ 4,  "hwmp_rootreqs",	"hwmp_rootreqs",	"root PREQ frames sent" },
347*89eee8eeSLi-Wen Hsu #define	S_HWMP_ROOTANN		AFTER(S_HWMP_ROOTREQS)
348*89eee8eeSLi-Wen Hsu 	{ 4,  "hwmp_rootann",	"hwmp_rootann",	"root RANN frames received" },
349*89eee8eeSLi-Wen Hsu #define	S_MESH_BADAE		AFTER(S_HWMP_ROOTANN)
350*89eee8eeSLi-Wen Hsu 	{ 4,  "mesh_badae",	"mesh_badae",	"frame discarded for bad AddressExtension (AE)" },
351*89eee8eeSLi-Wen Hsu #define	S_MESH_RTADDFAILED	AFTER(S_MESH_BADAE)
352*89eee8eeSLi-Wen Hsu 	{ 4,  "mesh_rtadd",	"mesh_rtadd",	"mesh route add failed" },
353*89eee8eeSLi-Wen Hsu #define	S_MESH_NOTPROXY		AFTER(S_MESH_RTADDFAILED)
354*89eee8eeSLi-Wen Hsu 	{ 8,  "mesh_notproxy",	"mesh_notproxy","frame discarded because station not acting as a proxy" },
355*89eee8eeSLi-Wen Hsu #define	S_RX_BADALIGN		AFTER(S_MESH_NOTPROXY)
356*89eee8eeSLi-Wen Hsu 	{ 4,  "rx_badalign",	"rx_badalign","frame discarded because payload re-alignment failed" },
357*89eee8eeSLi-Wen Hsu #define	S_INPUT			AFTER(S_RX_BADALIGN)
358*89eee8eeSLi-Wen Hsu 	{ 8,	"input",	"input",	"total data frames received" },
359*89eee8eeSLi-Wen Hsu #define	S_RX_UCAST		AFTER(S_INPUT)
360*89eee8eeSLi-Wen Hsu 	{ 8,	"rx_ucast",	"rx_ucast",	"unicast data frames received" },
361*89eee8eeSLi-Wen Hsu #define	S_RX_MCAST		AFTER(S_RX_UCAST)
362*89eee8eeSLi-Wen Hsu 	{ 8,	"rx_mcast",	"rx_mcast",	"multicast data frames received" },
363*89eee8eeSLi-Wen Hsu #define	S_OUTPUT		AFTER(S_RX_MCAST)
364*89eee8eeSLi-Wen Hsu 	{ 8,	"output",	"output",	"total data frames transmit" },
365*89eee8eeSLi-Wen Hsu #define	S_TX_UCAST		AFTER(S_OUTPUT)
366*89eee8eeSLi-Wen Hsu 	{ 8,	"tx_ucast",	"tx_ucast",	"unicast data frames sent" },
367*89eee8eeSLi-Wen Hsu #define	S_TX_MCAST		AFTER(S_TX_UCAST)
368*89eee8eeSLi-Wen Hsu 	{ 8,	"tx_mcast",	"tx_mcast",	"multicast data frames sent" },
369*89eee8eeSLi-Wen Hsu #define	S_RATE			AFTER(S_TX_MCAST)
370*89eee8eeSLi-Wen Hsu 	{ 7,	"rate",		"rate",		"current transmit rate" },
371*89eee8eeSLi-Wen Hsu #define	S_RSSI			AFTER(S_RATE)
372*89eee8eeSLi-Wen Hsu 	{ 6,	"rssi",		"rssi",		"current rssi" },
373*89eee8eeSLi-Wen Hsu #define	S_NOISE			AFTER(S_RSSI)
374*89eee8eeSLi-Wen Hsu 	{ 5,	"noise",	"noise",	"current noise floor (dBm)" },
375*89eee8eeSLi-Wen Hsu #define	S_SIGNAL		AFTER(S_NOISE)
376*89eee8eeSLi-Wen Hsu 	{ 6,	"signal",	"sig",		"current signal (dBm)" },
377*89eee8eeSLi-Wen Hsu #define	S_BEACON_BAD		AFTER(S_SIGNAL)
378*89eee8eeSLi-Wen Hsu 	{ 9,	"beacon_bad",	"beaconbad",	"bad beacons received" },
379*89eee8eeSLi-Wen Hsu #define	S_AMPDU_BARTX		AFTER(S_BEACON_BAD)
380*89eee8eeSLi-Wen Hsu 	{ 5,	"ampdu_bartx",	"bartx",	"BAR frames sent" },
381*89eee8eeSLi-Wen Hsu #define	S_AMPDU_BARTX_FAIL	AFTER(S_AMPDU_BARTX)
382*89eee8eeSLi-Wen Hsu 	{ 9,	"ampdu_bartxfail",	"bartx_fail",	"BAR frames failed to send" },
383*89eee8eeSLi-Wen Hsu #define	S_AMPDU_BARTX_RETRY	AFTER(S_AMPDU_BARTX_FAIL)
384*89eee8eeSLi-Wen Hsu 	{ 10,	"ampdu_bartxretry",	"bartx_retry",	"BAR frames retried" },
385*89eee8eeSLi-Wen Hsu #define	S_CRYPTO_GCMP		AFTER(S_AMPDU_BARTX_RETRY)
386*89eee8eeSLi-Wen Hsu 	{ 11,	 "crypto_gcmp",	"crypto_gcmp",	"gcmp crypto done in s/w" },
387*89eee8eeSLi-Wen Hsu #define	S_RX_GCMPREPLAY		AFTER(S_CRYPTO_GCMP)
388*89eee8eeSLi-Wen Hsu 	{ 10,	"rx_gcmpreplay",	"gcmpreplay",	"rx seq# violation (GCMP)" },
389*89eee8eeSLi-Wen Hsu #define	S_RX_GCMPFORMAT		AFTER(S_RX_GCMPREPLAY)
390*89eee8eeSLi-Wen Hsu 	{ 10,	 "rx_gcmpformat",	"gcmpformat",	"rx format bad (GCMP)" },
391*89eee8eeSLi-Wen Hsu #define	S_RX_GCMPMIC		AFTER(S_RX_GCMPFORMAT)
392*89eee8eeSLi-Wen Hsu 	{ 7,	"rx_gcmpmic",	"gcmpmic",	"rx MIC check failed (GCMP)" },
393*89eee8eeSLi-Wen Hsu #define	S_RX_GCMPNOMEM		AFTER(S_RX_GCMPMIC)
394*89eee8eeSLi-Wen Hsu 	{ 9,	"gcmp_nomem",	"gcmpnomem",	"No memory available (GCMP)" },
395*89eee8eeSLi-Wen Hsu #define	S_RX_GCMPNOSPC		AFTER(S_RX_GCMPNOMEM)
396*89eee8eeSLi-Wen Hsu 	{ 9,	"gcmp_nospc",	"gcmpnospc",	"No mbuf space available (GCMP)" },
397*89eee8eeSLi-Wen Hsu #define	S_CRYPTO_SWCIPHERFAIL	AFTER(S_RX_GCMPNOSPC)
398*89eee8eeSLi-Wen Hsu 	{ 12,	"crypto_swcipherfail",	"swcipherfail",	"No matching software cipher support" },
399*89eee8eeSLi-Wen Hsu };
400*89eee8eeSLi-Wen Hsu 
401*89eee8eeSLi-Wen Hsu struct wlanstatfoo_p {
402*89eee8eeSLi-Wen Hsu 	struct wlanstatfoo base;
403*89eee8eeSLi-Wen Hsu 	int s;
404*89eee8eeSLi-Wen Hsu 	int opmode;
405*89eee8eeSLi-Wen Hsu 	uint8_t mac[IEEE80211_ADDR_LEN];
406*89eee8eeSLi-Wen Hsu 	struct ifreq ifr;
407*89eee8eeSLi-Wen Hsu 	struct ieee80211_stats cur;
408*89eee8eeSLi-Wen Hsu 	struct ieee80211_stats total;
409*89eee8eeSLi-Wen Hsu 	struct ieee80211req ireq;
410*89eee8eeSLi-Wen Hsu 	union {
411*89eee8eeSLi-Wen Hsu 		struct ieee80211req_sta_req info;
412*89eee8eeSLi-Wen Hsu 		char buf[1024];
413*89eee8eeSLi-Wen Hsu 	} u_info;
414*89eee8eeSLi-Wen Hsu 	struct ieee80211req_sta_stats ncur;
415*89eee8eeSLi-Wen Hsu 	struct ieee80211req_sta_stats ntotal;
416*89eee8eeSLi-Wen Hsu };
417*89eee8eeSLi-Wen Hsu 
418*89eee8eeSLi-Wen Hsu static void
wlan_setifname(struct wlanstatfoo * wf0,const char * ifname)419*89eee8eeSLi-Wen Hsu wlan_setifname(struct wlanstatfoo *wf0, const char *ifname)
420*89eee8eeSLi-Wen Hsu {
421*89eee8eeSLi-Wen Hsu 	struct wlanstatfoo_p *wf = (struct wlanstatfoo_p *) wf0;
422*89eee8eeSLi-Wen Hsu 
423*89eee8eeSLi-Wen Hsu 	strncpy(wf->ifr.ifr_name, ifname, sizeof (wf->ifr.ifr_name));
424*89eee8eeSLi-Wen Hsu 	strncpy(wf->ireq.i_name, ifname, sizeof (wf->ireq.i_name));
425*89eee8eeSLi-Wen Hsu }
426*89eee8eeSLi-Wen Hsu 
427*89eee8eeSLi-Wen Hsu static const char *
wlan_getifname(struct wlanstatfoo * wf0)428*89eee8eeSLi-Wen Hsu wlan_getifname(struct wlanstatfoo *wf0)
429*89eee8eeSLi-Wen Hsu {
430*89eee8eeSLi-Wen Hsu 	struct wlanstatfoo_p *wf = (struct wlanstatfoo_p *) wf0;
431*89eee8eeSLi-Wen Hsu 
432*89eee8eeSLi-Wen Hsu 	return wf->ifr.ifr_name;
433*89eee8eeSLi-Wen Hsu }
434*89eee8eeSLi-Wen Hsu 
435*89eee8eeSLi-Wen Hsu static int
wlan_getopmode(struct wlanstatfoo * wf0)436*89eee8eeSLi-Wen Hsu wlan_getopmode(struct wlanstatfoo *wf0)
437*89eee8eeSLi-Wen Hsu {
438*89eee8eeSLi-Wen Hsu 	struct wlanstatfoo_p *wf = (struct wlanstatfoo_p *) wf0;
439*89eee8eeSLi-Wen Hsu 
440*89eee8eeSLi-Wen Hsu 	if (wf->opmode == -1) {
441*89eee8eeSLi-Wen Hsu 		struct ifmediareq ifmr;
442*89eee8eeSLi-Wen Hsu 
443*89eee8eeSLi-Wen Hsu 		memset(&ifmr, 0, sizeof(ifmr));
444*89eee8eeSLi-Wen Hsu 		strlcpy(ifmr.ifm_name, wf->ifr.ifr_name, sizeof(ifmr.ifm_name));
445*89eee8eeSLi-Wen Hsu 		if (ioctl(wf->s, SIOCGIFMEDIA, &ifmr) < 0)
446*89eee8eeSLi-Wen Hsu 			err(1, "%s (SIOCGIFMEDIA)", wf->ifr.ifr_name);
447*89eee8eeSLi-Wen Hsu 		if (ifmr.ifm_current & IFM_IEEE80211_ADHOC) {
448*89eee8eeSLi-Wen Hsu 			if (ifmr.ifm_current & IFM_FLAG0)
449*89eee8eeSLi-Wen Hsu 				wf->opmode = IEEE80211_M_AHDEMO;
450*89eee8eeSLi-Wen Hsu 			else
451*89eee8eeSLi-Wen Hsu 				wf->opmode = IEEE80211_M_IBSS;
452*89eee8eeSLi-Wen Hsu 		} else if (ifmr.ifm_current & IFM_IEEE80211_HOSTAP)
453*89eee8eeSLi-Wen Hsu 			wf->opmode = IEEE80211_M_HOSTAP;
454*89eee8eeSLi-Wen Hsu 		else if (ifmr.ifm_current & IFM_IEEE80211_MONITOR)
455*89eee8eeSLi-Wen Hsu 			wf->opmode = IEEE80211_M_MONITOR;
456*89eee8eeSLi-Wen Hsu 		else
457*89eee8eeSLi-Wen Hsu 			wf->opmode = IEEE80211_M_STA;
458*89eee8eeSLi-Wen Hsu 	}
459*89eee8eeSLi-Wen Hsu 	return wf->opmode;
460*89eee8eeSLi-Wen Hsu }
461*89eee8eeSLi-Wen Hsu 
462*89eee8eeSLi-Wen Hsu static void
getlladdr(struct wlanstatfoo_p * wf)463*89eee8eeSLi-Wen Hsu getlladdr(struct wlanstatfoo_p *wf)
464*89eee8eeSLi-Wen Hsu {
465*89eee8eeSLi-Wen Hsu 	const struct sockaddr_dl *sdl;
466*89eee8eeSLi-Wen Hsu 	struct ifaddrs *ifp, *p;
467*89eee8eeSLi-Wen Hsu 
468*89eee8eeSLi-Wen Hsu 	if (getifaddrs(&ifp) != 0)
469*89eee8eeSLi-Wen Hsu 		err(1, "getifaddrs");
470*89eee8eeSLi-Wen Hsu 	for (p = ifp; p != NULL; p = p->ifa_next)
471*89eee8eeSLi-Wen Hsu 		if (strcmp(p->ifa_name, wf->ifr.ifr_name) == 0 &&
472*89eee8eeSLi-Wen Hsu 		    p->ifa_addr->sa_family == AF_LINK)
473*89eee8eeSLi-Wen Hsu 			break;
474*89eee8eeSLi-Wen Hsu 	if (p == NULL)
475*89eee8eeSLi-Wen Hsu 		errx(1, "did not find link layer address for interface %s",
476*89eee8eeSLi-Wen Hsu 			wf->ifr.ifr_name);
477*89eee8eeSLi-Wen Hsu 	sdl = (const struct sockaddr_dl *)(const void *)p->ifa_addr;
478*89eee8eeSLi-Wen Hsu 	IEEE80211_ADDR_COPY(wf->mac, sdl->sdl_data + sdl->sdl_nlen);
479*89eee8eeSLi-Wen Hsu 	freeifaddrs(ifp);
480*89eee8eeSLi-Wen Hsu }
481*89eee8eeSLi-Wen Hsu 
482*89eee8eeSLi-Wen Hsu static int
getbssid(struct wlanstatfoo_p * wf)483*89eee8eeSLi-Wen Hsu getbssid(struct wlanstatfoo_p *wf)
484*89eee8eeSLi-Wen Hsu {
485*89eee8eeSLi-Wen Hsu 	wf->ireq.i_type = IEEE80211_IOC_BSSID;
486*89eee8eeSLi-Wen Hsu 	wf->ireq.i_data = wf->mac;
487*89eee8eeSLi-Wen Hsu 	wf->ireq.i_len = IEEE80211_ADDR_LEN;
488*89eee8eeSLi-Wen Hsu 	return ioctl(wf->s, SIOCG80211, &wf->ireq);
489*89eee8eeSLi-Wen Hsu }
490*89eee8eeSLi-Wen Hsu 
491*89eee8eeSLi-Wen Hsu static void
wlan_setstamac(struct wlanstatfoo * wf0,const uint8_t * mac)492*89eee8eeSLi-Wen Hsu wlan_setstamac(struct wlanstatfoo *wf0, const uint8_t *mac)
493*89eee8eeSLi-Wen Hsu {
494*89eee8eeSLi-Wen Hsu 	static const uint8_t zeromac[IEEE80211_ADDR_LEN];
495*89eee8eeSLi-Wen Hsu 	struct wlanstatfoo_p *wf = (struct wlanstatfoo_p *) wf0;
496*89eee8eeSLi-Wen Hsu 
497*89eee8eeSLi-Wen Hsu 	if (mac == NULL) {
498*89eee8eeSLi-Wen Hsu 		switch (wlan_getopmode(wf0)) {
499*89eee8eeSLi-Wen Hsu 		case IEEE80211_M_HOSTAP:
500*89eee8eeSLi-Wen Hsu 		case IEEE80211_M_MONITOR:
501*89eee8eeSLi-Wen Hsu 			getlladdr(wf);
502*89eee8eeSLi-Wen Hsu 			break;
503*89eee8eeSLi-Wen Hsu 		case IEEE80211_M_IBSS:
504*89eee8eeSLi-Wen Hsu 		case IEEE80211_M_AHDEMO:
505*89eee8eeSLi-Wen Hsu 			/*
506*89eee8eeSLi-Wen Hsu 			 * NB: this may not work in which case the
507*89eee8eeSLi-Wen Hsu 			 * mac must be specified on the command line
508*89eee8eeSLi-Wen Hsu 			 */
509*89eee8eeSLi-Wen Hsu 			if (getbssid(wf) < 0 ||
510*89eee8eeSLi-Wen Hsu 			    IEEE80211_ADDR_EQ(wf->mac, zeromac))
511*89eee8eeSLi-Wen Hsu 				getlladdr(wf);
512*89eee8eeSLi-Wen Hsu 			break;
513*89eee8eeSLi-Wen Hsu 		case IEEE80211_M_STA:
514*89eee8eeSLi-Wen Hsu 			if (getbssid(wf) < 0)
515*89eee8eeSLi-Wen Hsu 				err(1, "%s (IEEE80211_IOC_BSSID)",
516*89eee8eeSLi-Wen Hsu 				    wf->ireq.i_name);
517*89eee8eeSLi-Wen Hsu 			break;
518*89eee8eeSLi-Wen Hsu 		}
519*89eee8eeSLi-Wen Hsu 	} else
520*89eee8eeSLi-Wen Hsu 		IEEE80211_ADDR_COPY(wf->mac, mac);
521*89eee8eeSLi-Wen Hsu }
522*89eee8eeSLi-Wen Hsu 
523*89eee8eeSLi-Wen Hsu /* XXX only fetch what's needed to do reports */
524*89eee8eeSLi-Wen Hsu static void
wlan_collect(struct wlanstatfoo_p * wf,struct ieee80211_stats * stats,struct ieee80211req_sta_stats * nstats)525*89eee8eeSLi-Wen Hsu wlan_collect(struct wlanstatfoo_p *wf,
526*89eee8eeSLi-Wen Hsu 	struct ieee80211_stats *stats, struct ieee80211req_sta_stats *nstats)
527*89eee8eeSLi-Wen Hsu {
528*89eee8eeSLi-Wen Hsu 
529*89eee8eeSLi-Wen Hsu 	IEEE80211_ADDR_COPY(wf->u_info.info.is_u.macaddr, wf->mac);
530*89eee8eeSLi-Wen Hsu 	wf->ireq.i_type = IEEE80211_IOC_STA_INFO;
531*89eee8eeSLi-Wen Hsu 	wf->ireq.i_data = (caddr_t) &wf->u_info;
532*89eee8eeSLi-Wen Hsu 	wf->ireq.i_len = sizeof(wf->u_info);
533*89eee8eeSLi-Wen Hsu 	if (ioctl(wf->s, SIOCG80211, &wf->ireq) < 0) {
534*89eee8eeSLi-Wen Hsu 		warn("%s:%s (IEEE80211_IOC_STA_INFO)", wf->ireq.i_name,
535*89eee8eeSLi-Wen Hsu 		    ether_ntoa((const struct ether_addr*) wf->mac));
536*89eee8eeSLi-Wen Hsu 	}
537*89eee8eeSLi-Wen Hsu 
538*89eee8eeSLi-Wen Hsu 	IEEE80211_ADDR_COPY(nstats->is_u.macaddr, wf->mac);
539*89eee8eeSLi-Wen Hsu 	wf->ireq.i_type = IEEE80211_IOC_STA_STATS;
540*89eee8eeSLi-Wen Hsu 	wf->ireq.i_data = (caddr_t) nstats;
541*89eee8eeSLi-Wen Hsu 	wf->ireq.i_len = sizeof(*nstats);
542*89eee8eeSLi-Wen Hsu 	if (ioctl(wf->s, SIOCG80211, &wf->ireq) < 0)
543*89eee8eeSLi-Wen Hsu 		warn("%s:%s (IEEE80211_IOC_STA_STATS)", wf->ireq.i_name,
544*89eee8eeSLi-Wen Hsu 		    ether_ntoa((const struct ether_addr*) wf->mac));
545*89eee8eeSLi-Wen Hsu 
546*89eee8eeSLi-Wen Hsu 	wf->ifr.ifr_data = (caddr_t) stats;
547*89eee8eeSLi-Wen Hsu 	if (ioctl(wf->s, SIOCG80211STATS, &wf->ifr) < 0)
548*89eee8eeSLi-Wen Hsu 		err(1, "%s (SIOCG80211STATS)", wf->ifr.ifr_name);
549*89eee8eeSLi-Wen Hsu }
550*89eee8eeSLi-Wen Hsu 
551*89eee8eeSLi-Wen Hsu static void
wlan_collect_cur(struct bsdstat * sf)552*89eee8eeSLi-Wen Hsu wlan_collect_cur(struct bsdstat *sf)
553*89eee8eeSLi-Wen Hsu {
554*89eee8eeSLi-Wen Hsu 	struct wlanstatfoo_p *wf = (struct wlanstatfoo_p *) sf;
555*89eee8eeSLi-Wen Hsu 
556*89eee8eeSLi-Wen Hsu 	wlan_collect(wf, &wf->cur, &wf->ncur);
557*89eee8eeSLi-Wen Hsu }
558*89eee8eeSLi-Wen Hsu 
559*89eee8eeSLi-Wen Hsu static void
wlan_collect_tot(struct bsdstat * sf)560*89eee8eeSLi-Wen Hsu wlan_collect_tot(struct bsdstat *sf)
561*89eee8eeSLi-Wen Hsu {
562*89eee8eeSLi-Wen Hsu 	struct wlanstatfoo_p *wf = (struct wlanstatfoo_p *) sf;
563*89eee8eeSLi-Wen Hsu 
564*89eee8eeSLi-Wen Hsu 	wlan_collect(wf, &wf->total, &wf->ntotal);
565*89eee8eeSLi-Wen Hsu }
566*89eee8eeSLi-Wen Hsu 
567*89eee8eeSLi-Wen Hsu static void
wlan_update_tot(struct bsdstat * sf)568*89eee8eeSLi-Wen Hsu wlan_update_tot(struct bsdstat *sf)
569*89eee8eeSLi-Wen Hsu {
570*89eee8eeSLi-Wen Hsu 	struct wlanstatfoo_p *wf = (struct wlanstatfoo_p *) sf;
571*89eee8eeSLi-Wen Hsu 
572*89eee8eeSLi-Wen Hsu 	wf->total = wf->cur;
573*89eee8eeSLi-Wen Hsu 	wf->ntotal = wf->ncur;
574*89eee8eeSLi-Wen Hsu }
575*89eee8eeSLi-Wen Hsu 
576*89eee8eeSLi-Wen Hsu static void
setreason(char b[],size_t bs,unsigned int v)577*89eee8eeSLi-Wen Hsu setreason(char b[], size_t bs, unsigned int v)
578*89eee8eeSLi-Wen Hsu {
579*89eee8eeSLi-Wen Hsu     static const char *reasons[] = {
580*89eee8eeSLi-Wen Hsu 	[IEEE80211_REASON_UNSPECIFIED]		= "unspecified",
581*89eee8eeSLi-Wen Hsu 	[IEEE80211_REASON_AUTH_EXPIRE]		= "auth expire",
582*89eee8eeSLi-Wen Hsu 	[IEEE80211_REASON_AUTH_LEAVE]		= "auth leave",
583*89eee8eeSLi-Wen Hsu 	[IEEE80211_REASON_ASSOC_EXPIRE]		= "assoc expire",
584*89eee8eeSLi-Wen Hsu 	[IEEE80211_REASON_ASSOC_TOOMANY]	= "assoc toomany",
585*89eee8eeSLi-Wen Hsu 	[IEEE80211_REASON_NOT_AUTHED]		= "not authed",
586*89eee8eeSLi-Wen Hsu 	[IEEE80211_REASON_NOT_ASSOCED]		= "not assoced",
587*89eee8eeSLi-Wen Hsu 	[IEEE80211_REASON_ASSOC_LEAVE]		= "assoc leave",
588*89eee8eeSLi-Wen Hsu 	[IEEE80211_REASON_ASSOC_NOT_AUTHED]	= "assoc not authed",
589*89eee8eeSLi-Wen Hsu 	[IEEE80211_REASON_DISASSOC_PWRCAP_BAD]	= "disassoc pwrcap bad",
590*89eee8eeSLi-Wen Hsu 	[IEEE80211_REASON_DISASSOC_SUPCHAN_BAD]	= "disassoc supchan bad",
591*89eee8eeSLi-Wen Hsu 	[IEEE80211_REASON_IE_INVALID]		= "ie invalid",
592*89eee8eeSLi-Wen Hsu 	[IEEE80211_REASON_MIC_FAILURE]		= "mic failure",
593*89eee8eeSLi-Wen Hsu 	[IEEE80211_REASON_4WAY_HANDSHAKE_TIMEOUT]= "4-way handshake timeout",
594*89eee8eeSLi-Wen Hsu 	[IEEE80211_REASON_GROUP_KEY_UPDATE_TIMEOUT] = "group key update timeout",
595*89eee8eeSLi-Wen Hsu 	[IEEE80211_REASON_IE_IN_4WAY_DIFFERS]	= "ie in 4-way differs",
596*89eee8eeSLi-Wen Hsu 	[IEEE80211_REASON_GROUP_CIPHER_INVALID]	= "group cipher invalid",
597*89eee8eeSLi-Wen Hsu 	[IEEE80211_REASON_PAIRWISE_CIPHER_INVALID]= "pairwise cipher invalid",
598*89eee8eeSLi-Wen Hsu 	[IEEE80211_REASON_AKMP_INVALID]		= "akmp invalid",
599*89eee8eeSLi-Wen Hsu 	[IEEE80211_REASON_UNSUPP_RSN_IE_VERSION]= "unsupported rsn ie version",
600*89eee8eeSLi-Wen Hsu 	[IEEE80211_REASON_INVALID_RSN_IE_CAP]	= "invalid rsn ie cap",
601*89eee8eeSLi-Wen Hsu 	[IEEE80211_REASON_802_1X_AUTH_FAILED]	= "802.1x auth failed",
602*89eee8eeSLi-Wen Hsu 	[IEEE80211_REASON_CIPHER_SUITE_REJECTED]= "cipher suite rejected",
603*89eee8eeSLi-Wen Hsu     };
604*89eee8eeSLi-Wen Hsu     if (v < nitems(reasons) && reasons[v] != NULL)
605*89eee8eeSLi-Wen Hsu 	    snprintf(b, bs, "%s (%u)", reasons[v], v);
606*89eee8eeSLi-Wen Hsu     else
607*89eee8eeSLi-Wen Hsu 	    snprintf(b, bs, "%u", v);
608*89eee8eeSLi-Wen Hsu }
609*89eee8eeSLi-Wen Hsu 
610*89eee8eeSLi-Wen Hsu static void
setstatus(char b[],size_t bs,unsigned int v)611*89eee8eeSLi-Wen Hsu setstatus(char b[], size_t bs, unsigned int v)
612*89eee8eeSLi-Wen Hsu {
613*89eee8eeSLi-Wen Hsu     static const char *status[] = {
614*89eee8eeSLi-Wen Hsu 	[IEEE80211_STATUS_SUCCESS]		= "success",
615*89eee8eeSLi-Wen Hsu 	[IEEE80211_STATUS_UNSPECIFIED]		= "unspecified",
616*89eee8eeSLi-Wen Hsu 	[IEEE80211_STATUS_CAPINFO]		= "capinfo",
617*89eee8eeSLi-Wen Hsu 	[IEEE80211_STATUS_NOT_ASSOCED]		= "not assoced",
618*89eee8eeSLi-Wen Hsu 	[IEEE80211_STATUS_OTHER]		= "other",
619*89eee8eeSLi-Wen Hsu 	[IEEE80211_STATUS_ALG]			= "algorithm",
620*89eee8eeSLi-Wen Hsu 	[IEEE80211_STATUS_SEQUENCE]		= "sequence",
621*89eee8eeSLi-Wen Hsu 	[IEEE80211_STATUS_CHALLENGE]		= "challenge",
622*89eee8eeSLi-Wen Hsu 	[IEEE80211_STATUS_TIMEOUT]		= "timeout",
623*89eee8eeSLi-Wen Hsu 	[IEEE80211_STATUS_TOOMANY]		= "toomany",
624*89eee8eeSLi-Wen Hsu 	[IEEE80211_STATUS_BASIC_RATE]		= "basic rate",
625*89eee8eeSLi-Wen Hsu 	[IEEE80211_STATUS_SP_REQUIRED]		= "sp required",
626*89eee8eeSLi-Wen Hsu 	[IEEE80211_STATUS_PBCC_REQUIRED]	= "pbcc required",
627*89eee8eeSLi-Wen Hsu 	[IEEE80211_STATUS_CA_REQUIRED]		= "ca required",
628*89eee8eeSLi-Wen Hsu 	[IEEE80211_STATUS_SPECMGMT_REQUIRED]	= "specmgmt required",
629*89eee8eeSLi-Wen Hsu 	[IEEE80211_STATUS_PWRCAP_REQUIRED]	= "pwrcap required",
630*89eee8eeSLi-Wen Hsu 	[IEEE80211_STATUS_SUPCHAN_REQUIRED]	= "supchan required",
631*89eee8eeSLi-Wen Hsu 	[IEEE80211_STATUS_SHORTSLOT_REQUIRED]	= "shortslot required",
632*89eee8eeSLi-Wen Hsu 	[IEEE80211_STATUS_DSSSOFDM_REQUIRED]	= "dsssofdm required",
633*89eee8eeSLi-Wen Hsu 	[IEEE80211_STATUS_INVALID_IE]		= "invalid ie",
634*89eee8eeSLi-Wen Hsu 	[IEEE80211_STATUS_GROUP_CIPHER_INVALID]	= "group cipher invalid",
635*89eee8eeSLi-Wen Hsu 	[IEEE80211_STATUS_PAIRWISE_CIPHER_INVALID]= "pairwise cipher invalid",
636*89eee8eeSLi-Wen Hsu 	[IEEE80211_STATUS_AKMP_INVALID]		= "akmp invalid",
637*89eee8eeSLi-Wen Hsu 	[IEEE80211_STATUS_UNSUPP_RSN_IE_VERSION]= "unsupported rsn ie version",
638*89eee8eeSLi-Wen Hsu 	[IEEE80211_STATUS_INVALID_RSN_IE_CAP]	= "invalid rsn ie cap",
639*89eee8eeSLi-Wen Hsu 	[IEEE80211_STATUS_CIPHER_SUITE_REJECTED]= "cipher suite rejected",
640*89eee8eeSLi-Wen Hsu     };
641*89eee8eeSLi-Wen Hsu     if (v < nitems(status) && status[v] != NULL)
642*89eee8eeSLi-Wen Hsu 	    snprintf(b, bs, "%s (%u)", status[v], v);
643*89eee8eeSLi-Wen Hsu     else
644*89eee8eeSLi-Wen Hsu 	    snprintf(b, bs, "%u", v);
645*89eee8eeSLi-Wen Hsu }
646*89eee8eeSLi-Wen Hsu 
647*89eee8eeSLi-Wen Hsu static int
wlan_getinfo(struct wlanstatfoo_p * wf,int s,char b[],size_t bs)648*89eee8eeSLi-Wen Hsu wlan_getinfo(struct wlanstatfoo_p *wf, int s, char b[], size_t bs)
649*89eee8eeSLi-Wen Hsu {
650*89eee8eeSLi-Wen Hsu 	const struct ieee80211req_sta_info *si = &wf->u_info.info.info[0];
651*89eee8eeSLi-Wen Hsu 
652*89eee8eeSLi-Wen Hsu 	switch (s) {
653*89eee8eeSLi-Wen Hsu 	case S_RATE:
654*89eee8eeSLi-Wen Hsu 		snprintf(b, bs, "%.1fM", (float) si->isi_txmbps/2.0);
655*89eee8eeSLi-Wen Hsu 		return 1;
656*89eee8eeSLi-Wen Hsu 	case S_RSSI:
657*89eee8eeSLi-Wen Hsu 		snprintf(b, bs, "%.1f", (float) si->isi_rssi/2.0);
658*89eee8eeSLi-Wen Hsu 		return 1;
659*89eee8eeSLi-Wen Hsu 	case S_NOISE:
660*89eee8eeSLi-Wen Hsu 		snprintf(b, bs, "%d", si->isi_noise);
661*89eee8eeSLi-Wen Hsu 		return 1;
662*89eee8eeSLi-Wen Hsu 	case S_SIGNAL:
663*89eee8eeSLi-Wen Hsu 		snprintf(b, bs, "%.1f", (float) si->isi_rssi/2.0
664*89eee8eeSLi-Wen Hsu 		    + (float) si->isi_noise);
665*89eee8eeSLi-Wen Hsu 		return 1;
666*89eee8eeSLi-Wen Hsu 	case S_RX_AUTH_FAIL_CODE:
667*89eee8eeSLi-Wen Hsu 		if (wf->cur.is_rx_authfail_code == 0)
668*89eee8eeSLi-Wen Hsu 			break;
669*89eee8eeSLi-Wen Hsu 		setstatus(b, bs, wf->cur.is_rx_authfail_code);
670*89eee8eeSLi-Wen Hsu 		return 1;
671*89eee8eeSLi-Wen Hsu 	case S_RX_DEAUTH_CODE:
672*89eee8eeSLi-Wen Hsu 		if (wf->cur.is_rx_deauth_code == 0)
673*89eee8eeSLi-Wen Hsu 			break;
674*89eee8eeSLi-Wen Hsu 		setreason(b, bs, wf->cur.is_rx_deauth_code);
675*89eee8eeSLi-Wen Hsu 		return 1;
676*89eee8eeSLi-Wen Hsu 	case S_RX_DISASSOC_CODE:
677*89eee8eeSLi-Wen Hsu 		if (wf->cur.is_rx_disassoc_code == 0)
678*89eee8eeSLi-Wen Hsu 			break;
679*89eee8eeSLi-Wen Hsu 		setreason(b, bs, wf->cur.is_rx_disassoc_code);
680*89eee8eeSLi-Wen Hsu 		return 1;
681*89eee8eeSLi-Wen Hsu 	}
682*89eee8eeSLi-Wen Hsu 	b[0] = '\0';
683*89eee8eeSLi-Wen Hsu 	return 0;
684*89eee8eeSLi-Wen Hsu }
685*89eee8eeSLi-Wen Hsu 
686*89eee8eeSLi-Wen Hsu static int
wlan_get_curstat(struct bsdstat * sf,int s,char b[],size_t bs)687*89eee8eeSLi-Wen Hsu wlan_get_curstat(struct bsdstat *sf, int s, char b[], size_t bs)
688*89eee8eeSLi-Wen Hsu {
689*89eee8eeSLi-Wen Hsu 	struct wlanstatfoo_p *wf = (struct wlanstatfoo_p *) sf;
690*89eee8eeSLi-Wen Hsu #define	STAT(x) \
691*89eee8eeSLi-Wen Hsu 	snprintf(b, bs, "%u", wf->cur.is_##x - wf->total.is_##x); return 1
692*89eee8eeSLi-Wen Hsu #define	NSTAT(x) \
693*89eee8eeSLi-Wen Hsu 	snprintf(b, bs, "%u", \
694*89eee8eeSLi-Wen Hsu 	    wf->ncur.is_stats.ns_##x - wf->ntotal.is_stats.ns_##x); \
695*89eee8eeSLi-Wen Hsu 	    return 1
696*89eee8eeSLi-Wen Hsu 
697*89eee8eeSLi-Wen Hsu 	switch (s) {
698*89eee8eeSLi-Wen Hsu 	case S_RX_BADVERSION:	STAT(rx_badversion);
699*89eee8eeSLi-Wen Hsu 	case S_RX_TOOSHORT:	STAT(rx_tooshort);
700*89eee8eeSLi-Wen Hsu 	case S_RX_WRONGBSS:	STAT(rx_wrongbss);
701*89eee8eeSLi-Wen Hsu 	case S_RX_DUP:		STAT(rx_dup);
702*89eee8eeSLi-Wen Hsu 	case S_RX_WRONGDIR:	STAT(rx_wrongdir);
703*89eee8eeSLi-Wen Hsu 	case S_RX_MCASTECHO:	STAT(rx_mcastecho);
704*89eee8eeSLi-Wen Hsu 	case S_RX_NOTASSOC:	STAT(rx_notassoc);
705*89eee8eeSLi-Wen Hsu 	case S_RX_NOPRIVACY:	STAT(rx_noprivacy);
706*89eee8eeSLi-Wen Hsu 	case S_RX_UNENCRYPTED:	STAT(rx_unencrypted);
707*89eee8eeSLi-Wen Hsu 	case S_RX_WEPFAIL:	STAT(rx_wepfail);
708*89eee8eeSLi-Wen Hsu 	case S_RX_DECAP:	STAT(rx_decap);
709*89eee8eeSLi-Wen Hsu 	case S_RX_MGTDISCARD:	STAT(rx_mgtdiscard);
710*89eee8eeSLi-Wen Hsu 	case S_RX_CTL:		STAT(rx_ctl);
711*89eee8eeSLi-Wen Hsu 	case S_RX_BEACON:	STAT(rx_beacon);
712*89eee8eeSLi-Wen Hsu 	case S_RX_RSTOOBIG:	STAT(rx_rstoobig);
713*89eee8eeSLi-Wen Hsu 	case S_RX_ELEM_MISSING:	STAT(rx_elem_missing);
714*89eee8eeSLi-Wen Hsu 	case S_RX_ELEM_TOOBIG:	STAT(rx_elem_toobig);
715*89eee8eeSLi-Wen Hsu 	case S_RX_ELEM_TOOSMALL:	STAT(rx_elem_toosmall);
716*89eee8eeSLi-Wen Hsu 	case S_RX_ELEM_UNKNOWN:	STAT(rx_elem_unknown);
717*89eee8eeSLi-Wen Hsu 	case S_RX_BADCHAN:	STAT(rx_badchan);
718*89eee8eeSLi-Wen Hsu 	case S_RX_CHANMISMATCH:	STAT(rx_chanmismatch);
719*89eee8eeSLi-Wen Hsu 	case S_RX_NODEALLOC:	STAT(rx_nodealloc);
720*89eee8eeSLi-Wen Hsu 	case S_RX_SSIDMISMATCH:	STAT(rx_ssidmismatch);
721*89eee8eeSLi-Wen Hsu 	case S_RX_AUTH_UNSUPPORTED:	STAT(rx_auth_unsupported);
722*89eee8eeSLi-Wen Hsu 	case S_RX_AUTH_FAIL:	STAT(rx_auth_fail);
723*89eee8eeSLi-Wen Hsu 	case S_RX_AUTH_COUNTERMEASURES:	STAT(rx_auth_countermeasures);
724*89eee8eeSLi-Wen Hsu 	case S_RX_ASSOC_BSS:	STAT(rx_assoc_bss);
725*89eee8eeSLi-Wen Hsu 	case S_RX_ASSOC_NOTAUTH:	STAT(rx_assoc_notauth);
726*89eee8eeSLi-Wen Hsu 	case S_RX_ASSOC_CAPMISMATCH:	STAT(rx_assoc_capmismatch);
727*89eee8eeSLi-Wen Hsu 	case S_RX_ASSOC_NORATE:	STAT(rx_assoc_norate);
728*89eee8eeSLi-Wen Hsu 	case S_RX_ASSOC_BADWPAIE:	STAT(rx_assoc_badwpaie);
729*89eee8eeSLi-Wen Hsu 	case S_RX_DEAUTH:	STAT(rx_deauth);
730*89eee8eeSLi-Wen Hsu 	case S_RX_DISASSOC:	STAT(rx_disassoc);
731*89eee8eeSLi-Wen Hsu 	case S_BMISS:		STAT(beacon_miss);
732*89eee8eeSLi-Wen Hsu 	case S_RX_BADSUBTYPE:	STAT(rx_badsubtype);
733*89eee8eeSLi-Wen Hsu 	case S_RX_NOBUF:	STAT(rx_nobuf);
734*89eee8eeSLi-Wen Hsu 	case S_RX_DECRYPTCRC:	STAT(rx_decryptcrc);
735*89eee8eeSLi-Wen Hsu 	case S_RX_AHDEMO_MGT:	STAT(rx_ahdemo_mgt);
736*89eee8eeSLi-Wen Hsu 	case S_RX_BAD_AUTH:	STAT(rx_bad_auth);
737*89eee8eeSLi-Wen Hsu 	case S_RX_UNAUTH:	STAT(rx_unauth);
738*89eee8eeSLi-Wen Hsu 	case S_RX_BADKEYID:	STAT(rx_badkeyid);
739*89eee8eeSLi-Wen Hsu 	case S_RX_CCMPREPLAY:	STAT(rx_ccmpreplay);
740*89eee8eeSLi-Wen Hsu 	case S_RX_CCMPFORMAT:	STAT(rx_ccmpformat);
741*89eee8eeSLi-Wen Hsu 	case S_RX_CCMPMIC:	STAT(rx_ccmpmic);
742*89eee8eeSLi-Wen Hsu 	case S_RX_TKIPREPLAY:	STAT(rx_tkipreplay);
743*89eee8eeSLi-Wen Hsu 	case S_RX_TKIPFORMAT:	STAT(rx_tkipformat);
744*89eee8eeSLi-Wen Hsu 	case S_RX_TKIPMIC:	STAT(rx_tkipmic);
745*89eee8eeSLi-Wen Hsu 	case S_RX_TKIPICV:	STAT(rx_tkipicv);
746*89eee8eeSLi-Wen Hsu 	case S_RX_BADCIPHER:	STAT(rx_badcipher);
747*89eee8eeSLi-Wen Hsu 	case S_RX_NOCIPHERCTX:	STAT(rx_nocipherctx);
748*89eee8eeSLi-Wen Hsu 	case S_RX_ACL:		STAT(rx_acl);
749*89eee8eeSLi-Wen Hsu 	case S_TX_NOBUF:	STAT(tx_nobuf);
750*89eee8eeSLi-Wen Hsu 	case S_TX_NONODE:	STAT(tx_nonode);
751*89eee8eeSLi-Wen Hsu 	case S_TX_UNKNOWNMGT:	STAT(tx_unknownmgt);
752*89eee8eeSLi-Wen Hsu 	case S_TX_BADCIPHER:	STAT(tx_badcipher);
753*89eee8eeSLi-Wen Hsu 	case S_TX_NODEFKEY:	STAT(tx_nodefkey);
754*89eee8eeSLi-Wen Hsu 	case S_TX_NOHEADROOM:	STAT(tx_noheadroom);
755*89eee8eeSLi-Wen Hsu 	case S_TX_FRAGFRAMES:	STAT(tx_fragframes);
756*89eee8eeSLi-Wen Hsu 	case S_TX_FRAGS:	STAT(tx_frags);
757*89eee8eeSLi-Wen Hsu 	case S_SCAN_ACTIVE:	STAT(scan_active);
758*89eee8eeSLi-Wen Hsu 	case S_SCAN_PASSIVE:	STAT(scan_passive);
759*89eee8eeSLi-Wen Hsu 	case S_SCAN_BG:		STAT(scan_bg);
760*89eee8eeSLi-Wen Hsu 	case S_NODE_TIMEOUT:	STAT(node_timeout);
761*89eee8eeSLi-Wen Hsu 	case S_CRYPTO_NOMEM:	STAT(crypto_nomem);
762*89eee8eeSLi-Wen Hsu 	case S_CRYPTO_TKIP:	STAT(crypto_tkip);
763*89eee8eeSLi-Wen Hsu 	case S_CRYPTO_TKIPENMIC:	STAT(crypto_tkipenmic);
764*89eee8eeSLi-Wen Hsu 	case S_CRYPTO_TKIPDEMIC:	STAT(crypto_tkipdemic);
765*89eee8eeSLi-Wen Hsu 	case S_CRYPTO_TKIPCM:	STAT(crypto_tkipcm);
766*89eee8eeSLi-Wen Hsu 	case S_CRYPTO_CCMP:	STAT(crypto_ccmp);
767*89eee8eeSLi-Wen Hsu 	case S_CRYPTO_WEP:	STAT(crypto_wep);
768*89eee8eeSLi-Wen Hsu 	case S_CRYPTO_SETKEY_CIPHER:	STAT(crypto_setkey_cipher);
769*89eee8eeSLi-Wen Hsu 	case S_CRYPTO_SETKEY_NOKEY:	STAT(crypto_setkey_nokey);
770*89eee8eeSLi-Wen Hsu 	case S_CRYPTO_DELKEY:	STAT(crypto_delkey);
771*89eee8eeSLi-Wen Hsu 	case S_CRYPTO_BADCIPHER:	STAT(crypto_badcipher);
772*89eee8eeSLi-Wen Hsu 	case S_CRYPTO_NOCIPHER:	STAT(crypto_nocipher);
773*89eee8eeSLi-Wen Hsu 	case S_CRYPTO_ATTACHFAIL:	STAT(crypto_attachfail);
774*89eee8eeSLi-Wen Hsu 	case S_CRYPTO_SWFALLBACK:	STAT(crypto_swfallback);
775*89eee8eeSLi-Wen Hsu 	case S_CRYPTO_KEYFAIL:	STAT(crypto_keyfail);
776*89eee8eeSLi-Wen Hsu 	case S_CRYPTO_ENMICFAIL:	STAT(crypto_enmicfail);
777*89eee8eeSLi-Wen Hsu 	case S_IBSS_CAPMISMATCH:	STAT(ibss_capmismatch);
778*89eee8eeSLi-Wen Hsu 	case S_IBSS_NORATE:	STAT(ibss_norate);
779*89eee8eeSLi-Wen Hsu 	case S_PS_UNASSOC:	STAT(ps_unassoc);
780*89eee8eeSLi-Wen Hsu 	case S_PS_BADAID:	STAT(ps_badaid);
781*89eee8eeSLi-Wen Hsu 	case S_PS_QEMPTY:	STAT(ps_qempty);
782*89eee8eeSLi-Wen Hsu 	case S_FF_BADHDR:	STAT(ff_badhdr);
783*89eee8eeSLi-Wen Hsu 	case S_FF_TOOSHORT:	STAT(ff_tooshort);
784*89eee8eeSLi-Wen Hsu 	case S_FF_SPLIT:	STAT(ff_split);
785*89eee8eeSLi-Wen Hsu 	case S_FF_DECAP:	STAT(ff_decap);
786*89eee8eeSLi-Wen Hsu 	case S_FF_ENCAP:	STAT(ff_encap);
787*89eee8eeSLi-Wen Hsu 	case S_FF_ENCAPFAIL:	STAT(ff_encapfail);
788*89eee8eeSLi-Wen Hsu 	case S_RX_BADBINTVAL:	STAT(rx_badbintval);
789*89eee8eeSLi-Wen Hsu 	case S_RX_MGMT:		STAT(rx_mgmt);
790*89eee8eeSLi-Wen Hsu 	case S_RX_DEMICFAIL:	STAT(rx_demicfail);
791*89eee8eeSLi-Wen Hsu 	case S_RX_DEFRAG:	STAT(rx_defrag);
792*89eee8eeSLi-Wen Hsu 	case S_RX_ACTION:	STAT(rx_action);
793*89eee8eeSLi-Wen Hsu 	case S_AMSDU_TOOSHORT:	STAT(amsdu_tooshort);
794*89eee8eeSLi-Wen Hsu 	case S_AMSDU_SPLIT:	STAT(amsdu_split);
795*89eee8eeSLi-Wen Hsu 	case S_AMSDU_DECAP:	STAT(amsdu_decap);
796*89eee8eeSLi-Wen Hsu 	case S_AMSDU_ENCAP:	STAT(amsdu_encap);
797*89eee8eeSLi-Wen Hsu 	case S_AMSDU_RX_MORE:	NSTAT(rx_amsdu_more);
798*89eee8eeSLi-Wen Hsu 	case S_AMSDU_RX_MORE_END:	NSTAT(rx_amsdu_more_end);
799*89eee8eeSLi-Wen Hsu 	case S_AMPDU_REORDER:	STAT(ampdu_rx_reorder);
800*89eee8eeSLi-Wen Hsu 	case S_AMPDU_FLUSH:	STAT(ampdu_rx_flush);
801*89eee8eeSLi-Wen Hsu 	case S_AMPDU_BARBAD:	STAT(ampdu_bar_bad);
802*89eee8eeSLi-Wen Hsu 	case S_AMPDU_BAROOW:	STAT(ampdu_bar_oow);
803*89eee8eeSLi-Wen Hsu 	case S_AMPDU_BARMOVE:	STAT(ampdu_bar_move);
804*89eee8eeSLi-Wen Hsu 	case S_AMPDU_BAR:	STAT(ampdu_bar_rx);
805*89eee8eeSLi-Wen Hsu 	case S_AMPDU_MOVE:	STAT(ampdu_rx_move);
806*89eee8eeSLi-Wen Hsu 	case S_AMPDU_OOR:	STAT(ampdu_rx_oor);
807*89eee8eeSLi-Wen Hsu 	case S_AMPDU_COPY:	STAT(ampdu_rx_copy);
808*89eee8eeSLi-Wen Hsu 	case S_AMPDU_DROP:	STAT(ampdu_rx_drop);
809*89eee8eeSLi-Wen Hsu 	case S_AMPDU_AGE:	STAT(ampdu_rx_age);
810*89eee8eeSLi-Wen Hsu 	case S_AMPDU_STOP:	STAT(ampdu_stop);
811*89eee8eeSLi-Wen Hsu 	case S_AMPDU_STOP_FAILED:STAT(ampdu_stop_failed);
812*89eee8eeSLi-Wen Hsu 	case S_ADDBA_REJECT:	STAT(addba_reject);
813*89eee8eeSLi-Wen Hsu 	case S_ADDBA_NOREQUEST:	STAT(addba_norequest);
814*89eee8eeSLi-Wen Hsu 	case S_ADDBA_BADTOKEN:	STAT(addba_badtoken);
815*89eee8eeSLi-Wen Hsu 	case S_TX_BADSTATE:	STAT(tx_badstate);
816*89eee8eeSLi-Wen Hsu 	case S_TX_NOTASSOC:	STAT(tx_notassoc);
817*89eee8eeSLi-Wen Hsu 	case S_TX_CLASSIFY:	STAT(tx_classify);
818*89eee8eeSLi-Wen Hsu 	case S_DWDS_MCAST:	STAT(dwds_mcast);
819*89eee8eeSLi-Wen Hsu 	case S_DWDS_QDROP:	STAT(dwds_qdrop);
820*89eee8eeSLi-Wen Hsu 	case S_HT_ASSOC_NOHTCAP:STAT(ht_assoc_nohtcap);
821*89eee8eeSLi-Wen Hsu 	case S_HT_ASSOC_DOWNGRADE:STAT(ht_assoc_downgrade);
822*89eee8eeSLi-Wen Hsu 	case S_HT_ASSOC_NORATE:	STAT(ht_assoc_norate);
823*89eee8eeSLi-Wen Hsu 	case S_MESH_WRONGMESH:	STAT(mesh_wrongmesh);
824*89eee8eeSLi-Wen Hsu 	case S_MESH_NOLINK:	STAT(mesh_nolink);
825*89eee8eeSLi-Wen Hsu 	case S_MESH_FWD_TTL:	STAT(mesh_fwd_ttl);
826*89eee8eeSLi-Wen Hsu 	case S_MESH_FWD_NOBUF:	STAT(mesh_fwd_nobuf);
827*89eee8eeSLi-Wen Hsu 	case S_MESH_FWD_TOOSHORT: STAT(mesh_fwd_tooshort);
828*89eee8eeSLi-Wen Hsu 	case S_MESH_FWD_DISABLED: STAT(mesh_fwd_disabled);
829*89eee8eeSLi-Wen Hsu 	case S_MESH_FWD_NOPATH:	STAT(mesh_fwd_nopath);
830*89eee8eeSLi-Wen Hsu 	case S_HWMP_WRONGSEQ:	STAT(hwmp_wrongseq);
831*89eee8eeSLi-Wen Hsu 	case S_HWMP_ROOTREQS:	STAT(hwmp_rootreqs);
832*89eee8eeSLi-Wen Hsu 	case S_HWMP_ROOTANN:	STAT(hwmp_rootrann);
833*89eee8eeSLi-Wen Hsu 	case S_MESH_BADAE:	STAT(mesh_badae);
834*89eee8eeSLi-Wen Hsu 	case S_MESH_RTADDFAILED:STAT(mesh_rtaddfailed);
835*89eee8eeSLi-Wen Hsu 	case S_MESH_NOTPROXY:	STAT(mesh_notproxy);
836*89eee8eeSLi-Wen Hsu 	case S_RX_BADALIGN:	STAT(rx_badalign);
837*89eee8eeSLi-Wen Hsu 	case S_INPUT:		NSTAT(rx_data);
838*89eee8eeSLi-Wen Hsu 	case S_OUTPUT:		NSTAT(tx_data);
839*89eee8eeSLi-Wen Hsu 	case S_RX_UCAST:	NSTAT(rx_ucast);
840*89eee8eeSLi-Wen Hsu 	case S_RX_MCAST:	NSTAT(rx_mcast);
841*89eee8eeSLi-Wen Hsu 	case S_TX_UCAST:	NSTAT(tx_ucast);
842*89eee8eeSLi-Wen Hsu 	case S_TX_MCAST:	NSTAT(tx_mcast);
843*89eee8eeSLi-Wen Hsu 	case S_BEACON_BAD:	STAT(beacon_bad);
844*89eee8eeSLi-Wen Hsu 	case S_AMPDU_BARTX:	STAT(ampdu_bar_tx);
845*89eee8eeSLi-Wen Hsu 	case S_AMPDU_BARTX_RETRY:	STAT(ampdu_bar_tx_retry);
846*89eee8eeSLi-Wen Hsu 	case S_AMPDU_BARTX_FAIL:	STAT(ampdu_bar_tx_fail);
847*89eee8eeSLi-Wen Hsu 	case S_CRYPTO_GCMP:	STAT(crypto_gcmp);
848*89eee8eeSLi-Wen Hsu 	case S_RX_GCMPREPLAY:	STAT(rx_gcmpreplay);
849*89eee8eeSLi-Wen Hsu 	case S_RX_GCMPFORMAT:	STAT(rx_gcmpformat);
850*89eee8eeSLi-Wen Hsu 	case S_RX_GCMPMIC:	STAT(rx_gcmpmic);
851*89eee8eeSLi-Wen Hsu 	case S_RX_GCMPNOMEM:	STAT(crypto_gcmp_nomem);
852*89eee8eeSLi-Wen Hsu 	case S_RX_GCMPNOSPC:	STAT(crypto_gcmp_nospc);
853*89eee8eeSLi-Wen Hsu 	case S_CRYPTO_SWCIPHERFAIL:	STAT(crypto_swcipherfail);
854*89eee8eeSLi-Wen Hsu 	}
855*89eee8eeSLi-Wen Hsu 	return wlan_getinfo(wf, s, b, bs);
856*89eee8eeSLi-Wen Hsu #undef NSTAT
857*89eee8eeSLi-Wen Hsu #undef STAT
858*89eee8eeSLi-Wen Hsu }
859*89eee8eeSLi-Wen Hsu 
860*89eee8eeSLi-Wen Hsu static int
wlan_get_totstat(struct bsdstat * sf,int s,char b[],size_t bs)861*89eee8eeSLi-Wen Hsu wlan_get_totstat(struct bsdstat *sf, int s, char b[], size_t bs)
862*89eee8eeSLi-Wen Hsu {
863*89eee8eeSLi-Wen Hsu 	struct wlanstatfoo_p *wf = (struct wlanstatfoo_p *) sf;
864*89eee8eeSLi-Wen Hsu #define	STAT(x) \
865*89eee8eeSLi-Wen Hsu 	snprintf(b, bs, "%u", wf->total.is_##x); return 1
866*89eee8eeSLi-Wen Hsu #define	NSTAT(x) \
867*89eee8eeSLi-Wen Hsu 	snprintf(b, bs, "%u", wf->ntotal.is_stats.ns_##x); return 1
868*89eee8eeSLi-Wen Hsu 
869*89eee8eeSLi-Wen Hsu 	switch (s) {
870*89eee8eeSLi-Wen Hsu 	case S_RX_BADVERSION:	STAT(rx_badversion);
871*89eee8eeSLi-Wen Hsu 	case S_RX_TOOSHORT:	STAT(rx_tooshort);
872*89eee8eeSLi-Wen Hsu 	case S_RX_WRONGBSS:	STAT(rx_wrongbss);
873*89eee8eeSLi-Wen Hsu 	case S_RX_DUP:	STAT(rx_dup);
874*89eee8eeSLi-Wen Hsu 	case S_RX_WRONGDIR:	STAT(rx_wrongdir);
875*89eee8eeSLi-Wen Hsu 	case S_RX_MCASTECHO:	STAT(rx_mcastecho);
876*89eee8eeSLi-Wen Hsu 	case S_RX_NOTASSOC:	STAT(rx_notassoc);
877*89eee8eeSLi-Wen Hsu 	case S_RX_NOPRIVACY:	STAT(rx_noprivacy);
878*89eee8eeSLi-Wen Hsu 	case S_RX_UNENCRYPTED:	STAT(rx_unencrypted);
879*89eee8eeSLi-Wen Hsu 	case S_RX_WEPFAIL:	STAT(rx_wepfail);
880*89eee8eeSLi-Wen Hsu 	case S_RX_DECAP:	STAT(rx_decap);
881*89eee8eeSLi-Wen Hsu 	case S_RX_MGTDISCARD:	STAT(rx_mgtdiscard);
882*89eee8eeSLi-Wen Hsu 	case S_RX_CTL:		STAT(rx_ctl);
883*89eee8eeSLi-Wen Hsu 	case S_RX_BEACON:	STAT(rx_beacon);
884*89eee8eeSLi-Wen Hsu 	case S_RX_RSTOOBIG:	STAT(rx_rstoobig);
885*89eee8eeSLi-Wen Hsu 	case S_RX_ELEM_MISSING:	STAT(rx_elem_missing);
886*89eee8eeSLi-Wen Hsu 	case S_RX_ELEM_TOOBIG:	STAT(rx_elem_toobig);
887*89eee8eeSLi-Wen Hsu 	case S_RX_ELEM_TOOSMALL:	STAT(rx_elem_toosmall);
888*89eee8eeSLi-Wen Hsu 	case S_RX_ELEM_UNKNOWN:	STAT(rx_elem_unknown);
889*89eee8eeSLi-Wen Hsu 	case S_RX_BADCHAN:	STAT(rx_badchan);
890*89eee8eeSLi-Wen Hsu 	case S_RX_CHANMISMATCH:	STAT(rx_chanmismatch);
891*89eee8eeSLi-Wen Hsu 	case S_RX_NODEALLOC:	STAT(rx_nodealloc);
892*89eee8eeSLi-Wen Hsu 	case S_RX_SSIDMISMATCH:	STAT(rx_ssidmismatch);
893*89eee8eeSLi-Wen Hsu 	case S_RX_AUTH_UNSUPPORTED:	STAT(rx_auth_unsupported);
894*89eee8eeSLi-Wen Hsu 	case S_RX_AUTH_FAIL:	STAT(rx_auth_fail);
895*89eee8eeSLi-Wen Hsu 	case S_RX_AUTH_COUNTERMEASURES:	STAT(rx_auth_countermeasures);
896*89eee8eeSLi-Wen Hsu 	case S_RX_ASSOC_BSS:	STAT(rx_assoc_bss);
897*89eee8eeSLi-Wen Hsu 	case S_RX_ASSOC_NOTAUTH:	STAT(rx_assoc_notauth);
898*89eee8eeSLi-Wen Hsu 	case S_RX_ASSOC_CAPMISMATCH:	STAT(rx_assoc_capmismatch);
899*89eee8eeSLi-Wen Hsu 	case S_RX_ASSOC_NORATE:	STAT(rx_assoc_norate);
900*89eee8eeSLi-Wen Hsu 	case S_RX_ASSOC_BADWPAIE:	STAT(rx_assoc_badwpaie);
901*89eee8eeSLi-Wen Hsu 	case S_RX_DEAUTH:	STAT(rx_deauth);
902*89eee8eeSLi-Wen Hsu 	case S_RX_DISASSOC:	STAT(rx_disassoc);
903*89eee8eeSLi-Wen Hsu 	case S_BMISS:		STAT(beacon_miss);
904*89eee8eeSLi-Wen Hsu 	case S_RX_BADSUBTYPE:	STAT(rx_badsubtype);
905*89eee8eeSLi-Wen Hsu 	case S_RX_NOBUF:	STAT(rx_nobuf);
906*89eee8eeSLi-Wen Hsu 	case S_RX_DECRYPTCRC:	STAT(rx_decryptcrc);
907*89eee8eeSLi-Wen Hsu 	case S_RX_AHDEMO_MGT:	STAT(rx_ahdemo_mgt);
908*89eee8eeSLi-Wen Hsu 	case S_RX_BAD_AUTH:	STAT(rx_bad_auth);
909*89eee8eeSLi-Wen Hsu 	case S_RX_UNAUTH:	STAT(rx_unauth);
910*89eee8eeSLi-Wen Hsu 	case S_RX_BADKEYID:	STAT(rx_badkeyid);
911*89eee8eeSLi-Wen Hsu 	case S_RX_CCMPREPLAY:	STAT(rx_ccmpreplay);
912*89eee8eeSLi-Wen Hsu 	case S_RX_CCMPFORMAT:	STAT(rx_ccmpformat);
913*89eee8eeSLi-Wen Hsu 	case S_RX_CCMPMIC:	STAT(rx_ccmpmic);
914*89eee8eeSLi-Wen Hsu 	case S_RX_TKIPREPLAY:	STAT(rx_tkipreplay);
915*89eee8eeSLi-Wen Hsu 	case S_RX_TKIPFORMAT:	STAT(rx_tkipformat);
916*89eee8eeSLi-Wen Hsu 	case S_RX_TKIPMIC:	STAT(rx_tkipmic);
917*89eee8eeSLi-Wen Hsu 	case S_RX_TKIPICV:	STAT(rx_tkipicv);
918*89eee8eeSLi-Wen Hsu 	case S_RX_BADCIPHER:	STAT(rx_badcipher);
919*89eee8eeSLi-Wen Hsu 	case S_RX_NOCIPHERCTX:	STAT(rx_nocipherctx);
920*89eee8eeSLi-Wen Hsu 	case S_RX_ACL:		STAT(rx_acl);
921*89eee8eeSLi-Wen Hsu 	case S_TX_NOBUF:	STAT(tx_nobuf);
922*89eee8eeSLi-Wen Hsu 	case S_TX_NONODE:	STAT(tx_nonode);
923*89eee8eeSLi-Wen Hsu 	case S_TX_UNKNOWNMGT:	STAT(tx_unknownmgt);
924*89eee8eeSLi-Wen Hsu 	case S_TX_BADCIPHER:	STAT(tx_badcipher);
925*89eee8eeSLi-Wen Hsu 	case S_TX_NODEFKEY:	STAT(tx_nodefkey);
926*89eee8eeSLi-Wen Hsu 	case S_TX_NOHEADROOM:	STAT(tx_noheadroom);
927*89eee8eeSLi-Wen Hsu 	case S_TX_FRAGFRAMES:	STAT(tx_fragframes);
928*89eee8eeSLi-Wen Hsu 	case S_TX_FRAGS:	STAT(tx_frags);
929*89eee8eeSLi-Wen Hsu 	case S_SCAN_ACTIVE:	STAT(scan_active);
930*89eee8eeSLi-Wen Hsu 	case S_SCAN_PASSIVE:	STAT(scan_passive);
931*89eee8eeSLi-Wen Hsu 	case S_SCAN_BG:		STAT(scan_bg);
932*89eee8eeSLi-Wen Hsu 	case S_NODE_TIMEOUT:	STAT(node_timeout);
933*89eee8eeSLi-Wen Hsu 	case S_CRYPTO_NOMEM:	STAT(crypto_nomem);
934*89eee8eeSLi-Wen Hsu 	case S_CRYPTO_TKIP:	STAT(crypto_tkip);
935*89eee8eeSLi-Wen Hsu 	case S_CRYPTO_TKIPENMIC:	STAT(crypto_tkipenmic);
936*89eee8eeSLi-Wen Hsu 	case S_CRYPTO_TKIPDEMIC:	STAT(crypto_tkipdemic);
937*89eee8eeSLi-Wen Hsu 	case S_CRYPTO_TKIPCM:	STAT(crypto_tkipcm);
938*89eee8eeSLi-Wen Hsu 	case S_CRYPTO_CCMP:	STAT(crypto_ccmp);
939*89eee8eeSLi-Wen Hsu 	case S_CRYPTO_WEP:	STAT(crypto_wep);
940*89eee8eeSLi-Wen Hsu 	case S_CRYPTO_SETKEY_CIPHER:	STAT(crypto_setkey_cipher);
941*89eee8eeSLi-Wen Hsu 	case S_CRYPTO_SETKEY_NOKEY:	STAT(crypto_setkey_nokey);
942*89eee8eeSLi-Wen Hsu 	case S_CRYPTO_DELKEY:	STAT(crypto_delkey);
943*89eee8eeSLi-Wen Hsu 	case S_CRYPTO_BADCIPHER:	STAT(crypto_badcipher);
944*89eee8eeSLi-Wen Hsu 	case S_CRYPTO_NOCIPHER:	STAT(crypto_nocipher);
945*89eee8eeSLi-Wen Hsu 	case S_CRYPTO_ATTACHFAIL:	STAT(crypto_attachfail);
946*89eee8eeSLi-Wen Hsu 	case S_CRYPTO_SWFALLBACK:	STAT(crypto_swfallback);
947*89eee8eeSLi-Wen Hsu 	case S_CRYPTO_KEYFAIL:	STAT(crypto_keyfail);
948*89eee8eeSLi-Wen Hsu 	case S_CRYPTO_ENMICFAIL:	STAT(crypto_enmicfail);
949*89eee8eeSLi-Wen Hsu 	case S_IBSS_CAPMISMATCH:	STAT(ibss_capmismatch);
950*89eee8eeSLi-Wen Hsu 	case S_IBSS_NORATE:	STAT(ibss_norate);
951*89eee8eeSLi-Wen Hsu 	case S_PS_UNASSOC:	STAT(ps_unassoc);
952*89eee8eeSLi-Wen Hsu 	case S_PS_BADAID:	STAT(ps_badaid);
953*89eee8eeSLi-Wen Hsu 	case S_PS_QEMPTY:	STAT(ps_qempty);
954*89eee8eeSLi-Wen Hsu 	case S_FF_BADHDR:	STAT(ff_badhdr);
955*89eee8eeSLi-Wen Hsu 	case S_FF_TOOSHORT:	STAT(ff_tooshort);
956*89eee8eeSLi-Wen Hsu 	case S_FF_SPLIT:	STAT(ff_split);
957*89eee8eeSLi-Wen Hsu 	case S_FF_DECAP:	STAT(ff_decap);
958*89eee8eeSLi-Wen Hsu 	case S_FF_ENCAP:	STAT(ff_encap);
959*89eee8eeSLi-Wen Hsu 	case S_FF_ENCAPFAIL:	STAT(ff_encapfail);
960*89eee8eeSLi-Wen Hsu 	case S_RX_BADBINTVAL:	STAT(rx_badbintval);
961*89eee8eeSLi-Wen Hsu 	case S_RX_MGMT:		STAT(rx_mgmt);
962*89eee8eeSLi-Wen Hsu 	case S_RX_DEMICFAIL:	STAT(rx_demicfail);
963*89eee8eeSLi-Wen Hsu 	case S_RX_DEFRAG:	STAT(rx_defrag);
964*89eee8eeSLi-Wen Hsu 	case S_RX_ACTION:	STAT(rx_action);
965*89eee8eeSLi-Wen Hsu 	case S_AMSDU_TOOSHORT:	STAT(amsdu_tooshort);
966*89eee8eeSLi-Wen Hsu 	case S_AMSDU_SPLIT:	STAT(amsdu_split);
967*89eee8eeSLi-Wen Hsu 	case S_AMSDU_DECAP:	STAT(amsdu_decap);
968*89eee8eeSLi-Wen Hsu 	case S_AMSDU_ENCAP:	STAT(amsdu_encap);
969*89eee8eeSLi-Wen Hsu 	case S_AMSDU_RX_MORE:	NSTAT(rx_amsdu_more);
970*89eee8eeSLi-Wen Hsu 	case S_AMSDU_RX_MORE_END:	NSTAT(rx_amsdu_more_end);
971*89eee8eeSLi-Wen Hsu 	case S_AMPDU_REORDER:	STAT(ampdu_rx_reorder);
972*89eee8eeSLi-Wen Hsu 	case S_AMPDU_FLUSH:	STAT(ampdu_rx_flush);
973*89eee8eeSLi-Wen Hsu 	case S_AMPDU_BARBAD:	STAT(ampdu_bar_bad);
974*89eee8eeSLi-Wen Hsu 	case S_AMPDU_BAROOW:	STAT(ampdu_bar_oow);
975*89eee8eeSLi-Wen Hsu 	case S_AMPDU_BARMOVE:	STAT(ampdu_bar_move);
976*89eee8eeSLi-Wen Hsu 	case S_AMPDU_BAR:	STAT(ampdu_bar_rx);
977*89eee8eeSLi-Wen Hsu 	case S_AMPDU_MOVE:	STAT(ampdu_rx_move);
978*89eee8eeSLi-Wen Hsu 	case S_AMPDU_OOR:	STAT(ampdu_rx_oor);
979*89eee8eeSLi-Wen Hsu 	case S_AMPDU_COPY:	STAT(ampdu_rx_copy);
980*89eee8eeSLi-Wen Hsu 	case S_AMPDU_DROP:	STAT(ampdu_rx_drop);
981*89eee8eeSLi-Wen Hsu 	case S_AMPDU_AGE:	STAT(ampdu_rx_age);
982*89eee8eeSLi-Wen Hsu 	case S_AMPDU_STOP:	STAT(ampdu_stop);
983*89eee8eeSLi-Wen Hsu 	case S_AMPDU_STOP_FAILED:STAT(ampdu_stop_failed);
984*89eee8eeSLi-Wen Hsu 	case S_ADDBA_REJECT:	STAT(addba_reject);
985*89eee8eeSLi-Wen Hsu 	case S_ADDBA_NOREQUEST:	STAT(addba_norequest);
986*89eee8eeSLi-Wen Hsu 	case S_ADDBA_BADTOKEN:	STAT(addba_badtoken);
987*89eee8eeSLi-Wen Hsu 	case S_TX_BADSTATE:	STAT(tx_badstate);
988*89eee8eeSLi-Wen Hsu 	case S_TX_NOTASSOC:	STAT(tx_notassoc);
989*89eee8eeSLi-Wen Hsu 	case S_TX_CLASSIFY:	STAT(tx_classify);
990*89eee8eeSLi-Wen Hsu 	case S_DWDS_MCAST:	STAT(dwds_mcast);
991*89eee8eeSLi-Wen Hsu 	case S_DWDS_QDROP:	STAT(dwds_qdrop);
992*89eee8eeSLi-Wen Hsu 	case S_HT_ASSOC_NOHTCAP:STAT(ht_assoc_nohtcap);
993*89eee8eeSLi-Wen Hsu 	case S_HT_ASSOC_DOWNGRADE:STAT(ht_assoc_downgrade);
994*89eee8eeSLi-Wen Hsu 	case S_HT_ASSOC_NORATE:	STAT(ht_assoc_norate);
995*89eee8eeSLi-Wen Hsu 	case S_MESH_WRONGMESH:	STAT(mesh_wrongmesh);
996*89eee8eeSLi-Wen Hsu 	case S_MESH_NOLINK:	STAT(mesh_nolink);
997*89eee8eeSLi-Wen Hsu 	case S_MESH_FWD_TTL:	STAT(mesh_fwd_ttl);
998*89eee8eeSLi-Wen Hsu 	case S_MESH_FWD_NOBUF:	STAT(mesh_fwd_nobuf);
999*89eee8eeSLi-Wen Hsu 	case S_MESH_FWD_TOOSHORT: STAT(mesh_fwd_tooshort);
1000*89eee8eeSLi-Wen Hsu 	case S_MESH_FWD_DISABLED: STAT(mesh_fwd_disabled);
1001*89eee8eeSLi-Wen Hsu 	case S_MESH_FWD_NOPATH:	STAT(mesh_fwd_nopath);
1002*89eee8eeSLi-Wen Hsu 	case S_HWMP_WRONGSEQ:	STAT(hwmp_wrongseq);
1003*89eee8eeSLi-Wen Hsu 	case S_HWMP_ROOTREQS:	STAT(hwmp_rootreqs);
1004*89eee8eeSLi-Wen Hsu 	case S_HWMP_ROOTANN:	STAT(hwmp_rootrann);
1005*89eee8eeSLi-Wen Hsu 	case S_MESH_BADAE:	STAT(mesh_badae);
1006*89eee8eeSLi-Wen Hsu 	case S_MESH_RTADDFAILED:STAT(mesh_rtaddfailed);
1007*89eee8eeSLi-Wen Hsu 	case S_MESH_NOTPROXY:	STAT(mesh_notproxy);
1008*89eee8eeSLi-Wen Hsu 	case S_RX_BADALIGN:	STAT(rx_badalign);
1009*89eee8eeSLi-Wen Hsu 	case S_INPUT:		NSTAT(rx_data);
1010*89eee8eeSLi-Wen Hsu 	case S_OUTPUT:		NSTAT(tx_data);
1011*89eee8eeSLi-Wen Hsu 	case S_RX_UCAST:	NSTAT(rx_ucast);
1012*89eee8eeSLi-Wen Hsu 	case S_RX_MCAST:	NSTAT(rx_mcast);
1013*89eee8eeSLi-Wen Hsu 	case S_TX_UCAST:	NSTAT(tx_ucast);
1014*89eee8eeSLi-Wen Hsu 	case S_TX_MCAST:	NSTAT(tx_mcast);
1015*89eee8eeSLi-Wen Hsu 	case S_BEACON_BAD:	STAT(beacon_bad);
1016*89eee8eeSLi-Wen Hsu 	case S_AMPDU_BARTX:	STAT(ampdu_bar_tx);
1017*89eee8eeSLi-Wen Hsu 	case S_AMPDU_BARTX_RETRY:	STAT(ampdu_bar_tx_retry);
1018*89eee8eeSLi-Wen Hsu 	case S_AMPDU_BARTX_FAIL:	STAT(ampdu_bar_tx_fail);
1019*89eee8eeSLi-Wen Hsu 	case S_CRYPTO_GCMP:	STAT(crypto_gcmp);
1020*89eee8eeSLi-Wen Hsu 	case S_RX_GCMPREPLAY:	STAT(rx_gcmpreplay);
1021*89eee8eeSLi-Wen Hsu 	case S_RX_GCMPFORMAT:	STAT(rx_gcmpformat);
1022*89eee8eeSLi-Wen Hsu 	case S_RX_GCMPMIC:	STAT(rx_gcmpmic);
1023*89eee8eeSLi-Wen Hsu 	case S_RX_GCMPNOMEM:	STAT(crypto_gcmp_nomem);
1024*89eee8eeSLi-Wen Hsu 	case S_RX_GCMPNOSPC:	STAT(crypto_gcmp_nospc);
1025*89eee8eeSLi-Wen Hsu 	case S_CRYPTO_SWCIPHERFAIL:	STAT(crypto_swcipherfail);
1026*89eee8eeSLi-Wen Hsu 	}
1027*89eee8eeSLi-Wen Hsu 	return wlan_getinfo(wf, s, b, bs);
1028*89eee8eeSLi-Wen Hsu #undef NSTAT
1029*89eee8eeSLi-Wen Hsu #undef STAT
1030*89eee8eeSLi-Wen Hsu }
1031*89eee8eeSLi-Wen Hsu 
BSDSTAT_DEFINE_BOUNCE(wlanstatfoo)1032*89eee8eeSLi-Wen Hsu BSDSTAT_DEFINE_BOUNCE(wlanstatfoo)
1033*89eee8eeSLi-Wen Hsu 
1034*89eee8eeSLi-Wen Hsu struct wlanstatfoo *
1035*89eee8eeSLi-Wen Hsu wlanstat_new(const char *ifname, const char *fmtstring)
1036*89eee8eeSLi-Wen Hsu {
1037*89eee8eeSLi-Wen Hsu 	struct wlanstatfoo_p *wf;
1038*89eee8eeSLi-Wen Hsu 
1039*89eee8eeSLi-Wen Hsu 	wf = calloc(1, sizeof(struct wlanstatfoo_p));
1040*89eee8eeSLi-Wen Hsu 	if (wf != NULL) {
1041*89eee8eeSLi-Wen Hsu 		bsdstat_init(&wf->base.base, "wlanstat", wlanstat,
1042*89eee8eeSLi-Wen Hsu 		    nitems(wlanstat));
1043*89eee8eeSLi-Wen Hsu 		/* override base methods */
1044*89eee8eeSLi-Wen Hsu 		wf->base.base.collect_cur = wlan_collect_cur;
1045*89eee8eeSLi-Wen Hsu 		wf->base.base.collect_tot = wlan_collect_tot;
1046*89eee8eeSLi-Wen Hsu 		wf->base.base.get_curstat = wlan_get_curstat;
1047*89eee8eeSLi-Wen Hsu 		wf->base.base.get_totstat = wlan_get_totstat;
1048*89eee8eeSLi-Wen Hsu 		wf->base.base.update_tot = wlan_update_tot;
1049*89eee8eeSLi-Wen Hsu 
1050*89eee8eeSLi-Wen Hsu 		/* setup bounce functions for public methods */
1051*89eee8eeSLi-Wen Hsu 		BSDSTAT_BOUNCE(wf, wlanstatfoo);
1052*89eee8eeSLi-Wen Hsu 
1053*89eee8eeSLi-Wen Hsu 		/* setup our public methods */
1054*89eee8eeSLi-Wen Hsu 		wf->base.setifname = wlan_setifname;
1055*89eee8eeSLi-Wen Hsu 		wf->base.getifname = wlan_getifname;
1056*89eee8eeSLi-Wen Hsu 		wf->base.getopmode = wlan_getopmode;
1057*89eee8eeSLi-Wen Hsu 		wf->base.setstamac = wlan_setstamac;
1058*89eee8eeSLi-Wen Hsu 		wf->opmode = -1;
1059*89eee8eeSLi-Wen Hsu 
1060*89eee8eeSLi-Wen Hsu 		wf->s = socket(AF_INET, SOCK_DGRAM, 0);
1061*89eee8eeSLi-Wen Hsu 		if (wf->s < 0)
1062*89eee8eeSLi-Wen Hsu 			err(1, "socket");
1063*89eee8eeSLi-Wen Hsu 
1064*89eee8eeSLi-Wen Hsu 		wlan_setifname(&wf->base, ifname);
1065*89eee8eeSLi-Wen Hsu 		wf->base.setfmt(&wf->base, fmtstring);
1066*89eee8eeSLi-Wen Hsu 	}
1067*89eee8eeSLi-Wen Hsu 	return &wf->base;
1068*89eee8eeSLi-Wen Hsu }
1069