2 * Copyright (c) 2010 The FreeBSD Foundation
5 * This software was developed by Shteryana Sotirova Shopova under
6 * sponsorship from the FreeBSD Foundation.
8 * Redistribution and use in source and binary forms, with or without
9 * modification, are permitted provided that the following conditions
11 * 1. Redistributions of source code must retain the above copyright
12 * notice, this list of conditions and the following disclaimer.
13 * 2. Redistributions in binary form must reproduce the above copyright
14 * notice, this list of conditions and the following disclaimer in the
15 * documentation and/or other materials provided with the distribution.
17 * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND
18 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
19 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
20 * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE
21 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
22 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
23 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
24 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
25 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
26 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
32 #include <sys/ioctl.h>
33 #include <sys/param.h>
34 #include <sys/module.h>
35 #include <sys/linker.h>
36 #include <sys/socket.h>
37 #include <sys/sysctl.h>
40 #include <net/if_dl.h>
41 #include <net/if_media.h>
42 #include <net/if_mib.h>
43 #include <net/if_types.h>
44 #include <net80211/ieee80211.h>
45 #include <net80211/ieee80211_ioctl.h>
46 #include <net80211/ieee80211_regdomain.h>
56 #include <bsnmp/snmpmod.h>
57 #include <bsnmp/snmp_mibII.h>
59 #include "wlan_tree.h"
60 #include "wlan_snmp.h"
64 static int wlan_ioctl(char *, uint16_t, int *, void *, size_t *, int);
65 static int wlan_kmod_load(const char *);
66 static uint32_t wlan_drivercaps_to_snmp(uint32_t);
67 static uint32_t wlan_cryptocaps_to_snmp(uint32_t);
68 static uint32_t wlan_htcaps_to_snmp(uint32_t);
69 static uint32_t wlan_peerstate_to_snmp(uint32_t);
70 static uint32_t wlan_peercaps_to_snmp(uint32_t );
71 static uint32_t wlan_channel_flags_to_snmp_phy(uint32_t);
72 static uint32_t wlan_regdomain_to_snmp(int);
73 static uint32_t wlan_snmp_to_scan_flags(int);
74 static int wlan_config_snmp2ioctl(int);
75 static int wlan_snmp_to_regdomain(enum WlanRegDomainCode);
76 static int wlan_config_get_country(struct wlan_iface *);
77 static int wlan_config_set_country(struct wlan_iface *, char *, int);
78 static int wlan_config_get_dchannel(struct wlan_iface *wif);
79 static int wlan_config_set_dchannel(struct wlan_iface *wif, uint32_t);
80 static int wlan_config_get_bssid(struct wlan_iface *);
81 static int wlan_config_set_bssid(struct wlan_iface *, uint8_t *);
82 static void wlan_config_set_snmp_intval(struct wlan_iface *, int, int);
83 static int wlan_config_snmp2value(int, int, int *);
84 static int wlan_config_check(struct wlan_iface *, int);
85 static int wlan_config_get_intval(struct wlan_iface *, int);
86 static int wlan_config_set_intval(struct wlan_iface *, int, int);
87 static int wlan_add_new_scan_result(struct wlan_iface *,
88 const struct ieee80211req_scan_result *, uint8_t *);
89 static int wlan_add_mac_macinfo(struct wlan_iface *,
90 const struct ieee80211req_maclist *);
91 static struct wlan_peer *wlan_add_peerinfo(const struct ieee80211req_sta_info *);
96 if ((sock = socket(PF_INET, SOCK_DGRAM, 0)) < 0) {
97 syslog(LOG_ERR, "cannot open socket : %s", strerror(errno));
104 * Load the needed modules in kernel if not already there.
113 static const char *wmod_names[] = {
121 wlan_kmod_load(const char *modname)
124 struct module_stat mstat;
126 mstat.version = sizeof(struct module_stat);
127 for (fileid = kldnext(0); fileid > 0; fileid = kldnext(fileid)) {
128 for (modid = kldfirstmod(fileid); modid > 0;
129 modid = modfnext(modid)) {
130 if (modstat(modid, &mstat) < 0)
132 if (strcmp(modname, mstat.name) == 0)
137 /* Not present - load it. */
138 if (kldload(modname) < 0) {
139 syslog(LOG_ERR, "failed to load %s kernel module - %s", modname,
148 wlan_kmodules_load(void)
150 if (wlan_kmod_load(wmod_names[WLAN_KMOD]) < 0)
153 if (wlan_kmod_load(wmod_names[WLAN_KMOD_ACL]) > 0)
154 syslog(LOG_NOTICE, "SNMP wlan loaded %s module",
155 wmod_names[WLAN_KMOD_ACL]);
157 if (wlan_kmod_load(wmod_names[WLAN_KMOD_WEP]) > 0)
158 syslog(LOG_NOTICE, "SNMP wlan loaded %s module",
159 wmod_names[WLAN_KMOD_WEP]);
166 wlan_ioctl(char *wif_name, uint16_t req_type, int *val, void *arg,
167 size_t *argsize, int set)
169 struct ieee80211req ireq;
171 memset(&ireq, 0, sizeof(struct ieee80211req));
172 strlcpy(ireq.i_name, wif_name, IFNAMSIZ);
174 ireq.i_type = req_type;
176 ireq.i_len = *argsize;
179 if (ioctl(sock, set ? SIOCS80211 : SIOCG80211, &ireq) < 0) {
180 syslog(LOG_ERR, "iface %s - %s param: ioctl(%d) "
181 "failed: %s", wif_name, set ? "set" : "get",
182 req_type, strerror(errno));
186 *argsize = ireq.i_len;
193 wlan_check_media(char *ifname)
195 struct ifmediareq ifmr;
197 memset(&ifmr, 0, sizeof(struct ifmediareq));
198 strlcpy(ifmr.ifm_name, ifname, sizeof(ifmr.ifm_name));
200 if (ioctl(sock, SIOCGIFMEDIA, &ifmr) < 0 || ifmr.ifm_count == 0)
201 return (0); /* Interface doesn't support SIOCGIFMEDIA. */
203 if ((ifmr.ifm_status & IFM_AVALID) == 0)
206 return (IFM_TYPE(ifmr.ifm_active));
210 wlan_get_opmode(struct wlan_iface *wif)
212 struct ifmediareq ifmr;
214 memset(&ifmr, 0, sizeof(struct ifmediareq));
215 strlcpy(ifmr.ifm_name, wif->wname, sizeof(ifmr.ifm_name));
217 if (ioctl(sock, SIOCGIFMEDIA, &ifmr) < 0) {
220 wif->mode = WlanIfaceOperatingModeType_station;
224 if (ifmr.ifm_current & IFM_IEEE80211_ADHOC) {
225 if (ifmr.ifm_current & IFM_FLAG0)
226 wif->mode = WlanIfaceOperatingModeType_adhocDemo;
228 wif->mode = WlanIfaceOperatingModeType_ibss;
229 } else if (ifmr.ifm_current & IFM_IEEE80211_HOSTAP)
230 wif->mode = WlanIfaceOperatingModeType_hostAp;
231 else if (ifmr.ifm_current & IFM_IEEE80211_MONITOR)
232 wif->mode = WlanIfaceOperatingModeType_monitor;
233 else if (ifmr.ifm_current & IFM_IEEE80211_MBSS)
234 wif->mode = WlanIfaceOperatingModeType_meshPoint;
235 else if (ifmr.ifm_current & IFM_IEEE80211_WDS)
236 wif->mode = WlanIfaceOperatingModeType_wds;
242 wlan_config_state(struct wlan_iface *wif, uint8_t set)
247 memset(&ifr, 0, sizeof(ifr));
248 strcpy(ifr.ifr_name, wif->wname);
250 if (ioctl(sock, SIOCGIFFLAGS, (caddr_t) &ifr) < 0) {
251 syslog(LOG_ERR, "set %s status: ioctl(SIOCGIFFLAGS) "
252 "failed: %s", wif->wname, strerror(errno));
257 if ((ifr.ifr_flags & IFF_UP) != 0)
258 wif->state = wlanIfaceState_up;
260 wif->state = wlanIfaceState_down;
264 flags = (ifr.ifr_flags & 0xffff) | (ifr.ifr_flagshigh << 16);
266 if (wif->state == wlanIfaceState_up)
271 ifr.ifr_flags = flags & 0xffff;
272 ifr.ifr_flagshigh = flags >> 16;
273 if (ioctl(sock, SIOCSIFFLAGS, (caddr_t) &ifr) < 0) {
274 syslog(LOG_ERR, "set %s %s: ioctl(SIOCSIFFLAGS) failed: %s",
275 wif->wname, wif->state == wlanIfaceState_up?"up":"down",
284 wlan_get_local_addr(struct wlan_iface *wif)
287 char ifname[IFNAMSIZ];
288 struct ifaddrs *ifap, *ifa;
289 struct sockaddr_dl sdl;
291 if (getifaddrs(&ifap) != 0) {
292 syslog(LOG_ERR, "wlan get mac: getifaddrs() failed - %s",
297 for (ifa = ifap; ifa != NULL; ifa = ifa->ifa_next) {
298 if (ifa->ifa_addr->sa_family != AF_LINK)
300 memcpy(&sdl, ifa->ifa_addr, sizeof(struct sockaddr_dl));
301 if (sdl.sdl_alen > IEEE80211_ADDR_LEN)
303 if ((len = sdl.sdl_nlen) >= IFNAMSIZ)
305 memcpy(ifname, sdl.sdl_data, len);
307 if (strcmp(wif->wname, ifname) == 0)
316 wlan_get_parent(struct wlan_iface *wif __unused)
318 /* XXX: There's no way to fetch this from the kernel. */
323 #define IEEE80211_C_STA 0x00000001 /* CAPABILITY: STA available */
324 #define IEEE80211_C_8023ENCAP 0x00000002 /* CAPABILITY: 802.3 encap */
325 #define IEEE80211_C_FF 0x00000040 /* CAPABILITY: ATH FF avail */
326 #define IEEE80211_C_TURBOP 0x00000080 /* CAPABILITY: ATH Turbo avail*/
327 #define IEEE80211_C_IBSS 0x00000100 /* CAPABILITY: IBSS available */
328 #define IEEE80211_C_PMGT 0x00000200 /* CAPABILITY: Power mgmt */
329 #define IEEE80211_C_HOSTAP 0x00000400 /* CAPABILITY: HOSTAP avail */
330 #define IEEE80211_C_AHDEMO 0x00000800 /* CAPABILITY: Old Adhoc Demo */
331 #define IEEE80211_C_SWRETRY 0x00001000 /* CAPABILITY: sw tx retry */
332 #define IEEE80211_C_TXPMGT 0x00002000 /* CAPABILITY: tx power mgmt */
333 #define IEEE80211_C_SHSLOT 0x00004000 /* CAPABILITY: short slottime */
334 #define IEEE80211_C_SHPREAMBLE 0x00008000 /* CAPABILITY: short preamble */
335 #define IEEE80211_C_MONITOR 0x00010000 /* CAPABILITY: monitor mode */
336 #define IEEE80211_C_DFS 0x00020000 /* CAPABILITY: DFS/radar avail*/
337 #define IEEE80211_C_MBSS 0x00040000 /* CAPABILITY: MBSS available */
338 /* 0x7c0000 available */
339 #define IEEE80211_C_WPA1 0x00800000 /* CAPABILITY: WPA1 avail */
340 #define IEEE80211_C_WPA2 0x01000000 /* CAPABILITY: WPA2 avail */
341 #define IEEE80211_C_WPA 0x01800000 /* CAPABILITY: WPA1+WPA2 avail*/
342 #define IEEE80211_C_BURST 0x02000000 /* CAPABILITY: frame bursting */
343 #define IEEE80211_C_WME 0x04000000 /* CAPABILITY: WME avail */
344 #define IEEE80211_C_WDS 0x08000000 /* CAPABILITY: 4-addr support */
345 /* 0x10000000 reserved */
346 #define IEEE80211_C_BGSCAN 0x20000000 /* CAPABILITY: bg scanning */
347 #define IEEE80211_C_TXFRAG 0x40000000 /* CAPABILITY: tx fragments */
348 #define IEEE80211_C_TDMA 0x80000000 /* CAPABILITY: TDMA avail */
351 wlan_drivercaps_to_snmp(uint32_t dcaps)
355 if ((dcaps & IEEE80211_C_STA) != 0)
356 scaps |= (0x1 << WlanDriverCaps_station);
357 if ((dcaps & IEEE80211_C_8023ENCAP) != 0)
358 scaps |= (0x1 << WlanDriverCaps_ieee8023encap);
359 if ((dcaps & IEEE80211_C_FF) != 0)
360 scaps |= (0x1 << WlanDriverCaps_athFastFrames);
361 if ((dcaps & IEEE80211_C_TURBOP) != 0)
362 scaps |= (0x1 << WlanDriverCaps_athTurbo);
363 if ((dcaps & IEEE80211_C_IBSS) != 0)
364 scaps |= (0x1 << WlanDriverCaps_ibss);
365 if ((dcaps & IEEE80211_C_PMGT) != 0)
366 scaps |= (0x1 << WlanDriverCaps_pmgt);
367 if ((dcaps & IEEE80211_C_HOSTAP) != 0)
368 scaps |= (0x1 << WlanDriverCaps_hostAp);
369 if ((dcaps & IEEE80211_C_AHDEMO) != 0)
370 scaps |= (0x1 << WlanDriverCaps_ahDemo);
371 if ((dcaps & IEEE80211_C_SWRETRY) != 0)
372 scaps |= (0x1 << WlanDriverCaps_swRetry);
373 if ((dcaps & IEEE80211_C_TXPMGT) != 0)
374 scaps |= (0x1 << WlanDriverCaps_txPmgt);
375 if ((dcaps & IEEE80211_C_SHSLOT) != 0)
376 scaps |= (0x1 << WlanDriverCaps_shortSlot);
377 if ((dcaps & IEEE80211_C_SHPREAMBLE) != 0)
378 scaps |= (0x1 << WlanDriverCaps_shortPreamble);
379 if ((dcaps & IEEE80211_C_MONITOR) != 0)
380 scaps |= (0x1 << WlanDriverCaps_monitor);
381 if ((dcaps & IEEE80211_C_DFS) != 0)
382 scaps |= (0x1 << WlanDriverCaps_dfs);
383 if ((dcaps & IEEE80211_C_MBSS) != 0)
384 scaps |= (0x1 << WlanDriverCaps_mbss);
385 if ((dcaps & IEEE80211_C_WPA1) != 0)
386 scaps |= (0x1 << WlanDriverCaps_wpa1);
387 if ((dcaps & IEEE80211_C_WPA2) != 0)
388 scaps |= (0x1 << WlanDriverCaps_wpa2);
389 if ((dcaps & IEEE80211_C_BURST) != 0)
390 scaps |= (0x1 << WlanDriverCaps_burst);
391 if ((dcaps & IEEE80211_C_WME) != 0)
392 scaps |= (0x1 << WlanDriverCaps_wme);
393 if ((dcaps & IEEE80211_C_WDS) != 0)
394 scaps |= (0x1 << WlanDriverCaps_wds);
395 if ((dcaps & IEEE80211_C_BGSCAN) != 0)
396 scaps |= (0x1 << WlanDriverCaps_bgScan);
397 if ((dcaps & IEEE80211_C_TXFRAG) != 0)
398 scaps |= (0x1 << WlanDriverCaps_txFrag);
399 if ((dcaps & IEEE80211_C_TDMA) != 0)
400 scaps |= (0x1 << WlanDriverCaps_tdma);
406 wlan_cryptocaps_to_snmp(uint32_t ccaps)
411 if ((ccaps & IEEE80211_CRYPTO_WEP) != 0)
412 scaps |= (0x1 << wlanCryptoCaps_wep);
413 if ((ccaps & IEEE80211_CRYPTO_TKIP) != 0)
414 scaps |= (0x1 << wlanCryptoCaps_tkip);
415 if ((ccaps & IEEE80211_CRYPTO_AES_OCB) != 0)
416 scaps |= (0x1 << wlanCryptoCaps_aes);
417 if ((ccaps & IEEE80211_CRYPTO_AES_CCM) != 0)
418 scaps |= (0x1 << wlanCryptoCaps_aesCcm);
419 if ((ccaps & IEEE80211_CRYPTO_TKIPMIC) != 0)
420 scaps |= (0x1 << wlanCryptoCaps_tkipMic);
421 if ((ccaps & IEEE80211_CRYPTO_CKIP) != 0)
422 scaps |= (0x1 << wlanCryptoCaps_ckip);
429 #define IEEE80211_HTC_AMPDU 0x00010000 /* CAPABILITY: A-MPDU tx */
430 #define IEEE80211_HTC_AMSDU 0x00020000 /* CAPABILITY: A-MSDU tx */
431 /* NB: HT40 is implied by IEEE80211_HTCAP_CHWIDTH40 */
432 #define IEEE80211_HTC_HT 0x00040000 /* CAPABILITY: HT operation */
433 #define IEEE80211_HTC_SMPS 0x00080000 /* CAPABILITY: MIMO power save*/
434 #define IEEE80211_HTC_RIFS 0x00100000 /* CAPABILITY: RIFS support */
437 wlan_htcaps_to_snmp(uint32_t hcaps)
441 if ((hcaps & IEEE80211_HTCAP_LDPC) != 0)
442 scaps |= (0x1 << WlanHTCaps_ldpc);
443 if ((hcaps & IEEE80211_HTCAP_CHWIDTH40) != 0)
444 scaps |= (0x1 << WlanHTCaps_chwidth40);
445 if ((hcaps & IEEE80211_HTCAP_GREENFIELD) != 0)
446 scaps |= (0x1 << WlanHTCaps_greenField);
447 if ((hcaps & IEEE80211_HTCAP_SHORTGI20) != 0)
448 scaps |= (0x1 << WlanHTCaps_shortGi20);
449 if ((hcaps & IEEE80211_HTCAP_SHORTGI40) != 0)
450 scaps |= (0x1 << WlanHTCaps_shortGi40);
451 if ((hcaps & IEEE80211_HTCAP_TXSTBC) != 0)
452 scaps |= (0x1 << WlanHTCaps_txStbc);
453 if ((hcaps & IEEE80211_HTCAP_DELBA) != 0)
454 scaps |= (0x1 << WlanHTCaps_delba);
455 if ((hcaps & IEEE80211_HTCAP_MAXAMSDU_7935) != 0)
456 scaps |= (0x1 << WlanHTCaps_amsdu7935);
457 if ((hcaps & IEEE80211_HTCAP_DSSSCCK40) != 0)
458 scaps |= (0x1 << WlanHTCaps_dssscck40);
459 if ((hcaps & IEEE80211_HTCAP_PSMP) != 0)
460 scaps |= (0x1 << WlanHTCaps_psmp);
461 if ((hcaps & IEEE80211_HTCAP_40INTOLERANT) != 0)
462 scaps |= (0x1 << WlanHTCaps_fortyMHzIntolerant);
463 if ((hcaps & IEEE80211_HTCAP_LSIGTXOPPROT) != 0)
464 scaps |= (0x1 << WlanHTCaps_lsigTxOpProt);
465 if ((hcaps & IEEE80211_HTC_AMPDU) != 0)
466 scaps |= (0x1 << WlanHTCaps_htcAmpdu);
467 if ((hcaps & IEEE80211_HTC_AMSDU) != 0)
468 scaps |= (0x1 << WlanHTCaps_htcAmsdu);
469 if ((hcaps & IEEE80211_HTC_HT) != 0)
470 scaps |= (0x1 << WlanHTCaps_htcHt);
471 if ((hcaps & IEEE80211_HTC_SMPS) != 0)
472 scaps |= (0x1 << WlanHTCaps_htcSmps);
473 if ((hcaps & IEEE80211_HTC_RIFS) != 0)
474 scaps |= (0x1 << WlanHTCaps_htcRifs);
480 #define WLAN_SET_TDMA_OPMODE(w) do { \
481 if ((w)->mode == WlanIfaceOperatingModeType_adhocDemo && \
482 ((w)->drivercaps & WlanDriverCaps_tdma) != 0) \
483 (w)->mode = WlanIfaceOperatingModeType_tdma; \
486 wlan_get_driver_caps(struct wlan_iface *wif)
490 struct ieee80211_devcaps_req dc;
492 memset(&dc, 0, sizeof(struct ieee80211_devcaps_req));
493 argsize = sizeof(struct ieee80211_devcaps_req);
495 if (wlan_ioctl(wif->wname, IEEE80211_IOC_DEVCAPS, &val, &dc,
499 wif->drivercaps = wlan_drivercaps_to_snmp(dc.dc_drivercaps);
500 wif->cryptocaps = wlan_cryptocaps_to_snmp(dc.dc_cryptocaps);
501 wif->htcaps = wlan_htcaps_to_snmp(dc.dc_htcaps);
503 WLAN_SET_TDMA_OPMODE(wif);
505 argsize = dc.dc_chaninfo.ic_nchans * sizeof(struct ieee80211_channel);
506 wif->chanlist = (struct ieee80211_channel *)malloc(argsize);
507 if (wif->chanlist == NULL)
510 memcpy(wif->chanlist, dc.dc_chaninfo.ic_chans, argsize);
511 wif->nchannels = dc.dc_chaninfo.ic_nchans;
517 wlan_channel_state_to_snmp(uint8_t cstate)
521 if ((cstate & IEEE80211_CHANSTATE_RADAR) != 0)
522 cs |= (0x1 << WlanIfaceChannelStateType_radar);
523 if ((cstate & IEEE80211_CHANSTATE_CACDONE) != 0)
524 cs |= (0x1 << WlanIfaceChannelStateType_cacDone);
525 if ((cstate & IEEE80211_CHANSTATE_CWINT) != 0)
526 cs |= (0x1 << WlanIfaceChannelStateType_interferenceDetected);
527 if ((cstate & IEEE80211_CHANSTATE_NORADAR) != 0)
528 cs |= (0x1 << WlanIfaceChannelStateType_radarClear);
534 wlan_channel_flags_to_snmp(uint32_t cflags)
538 if ((cflags & IEEE80211_CHAN_TURBO) != 0)
539 cf |= (0x1 << WlanIfaceChannelFlagsType_turbo);
540 if ((cflags & IEEE80211_CHAN_CCK) != 0)
541 cf |= (0x1 << WlanIfaceChannelFlagsType_cck);
542 if ((cflags & IEEE80211_CHAN_OFDM) != 0)
543 cf |= (0x1 << WlanIfaceChannelFlagsType_ofdm);
544 if ((cflags & IEEE80211_CHAN_2GHZ) != 0)
545 cf |= (0x1 << WlanIfaceChannelFlagsType_spectrum2Ghz);
546 if ((cflags & IEEE80211_CHAN_5GHZ) != 0)
547 cf |= (0x1 << WlanIfaceChannelFlagsType_spectrum5Ghz);
548 if ((cflags & IEEE80211_CHAN_PASSIVE) != 0)
549 cf |= (0x1 << WlanIfaceChannelFlagsType_passiveScan);
550 if ((cflags & IEEE80211_CHAN_DYN) != 0)
551 cf |= (0x1 << WlanIfaceChannelFlagsType_dynamicCckOfdm);
552 if ((cflags & IEEE80211_CHAN_GFSK) != 0)
553 cf |= (0x1 << WlanIfaceChannelFlagsType_gfsk);
554 if ((cflags & IEEE80211_CHAN_GSM) != 0)
555 cf |= (0x1 << WlanIfaceChannelFlagsType_spectrum900Mhz);
556 if ((cflags & IEEE80211_CHAN_STURBO) != 0)
557 cf |= (0x1 << WlanIfaceChannelFlagsType_dot11aStaticTurbo);
558 if ((cflags & IEEE80211_CHAN_HALF) != 0)
559 cf |= (0x1 << WlanIfaceChannelFlagsType_halfRate);
560 if ((cflags & IEEE80211_CHAN_QUARTER) != 0)
561 cf |= (0x1 << WlanIfaceChannelFlagsType_quarterRate);
562 if ((cflags & IEEE80211_CHAN_HT20) != 0)
563 cf |= (0x1 << WlanIfaceChannelFlagsType_ht20);
564 if ((cflags & IEEE80211_CHAN_HT40U) != 0)
565 cf |= (0x1 << WlanIfaceChannelFlagsType_ht40u);
566 if ((cflags & IEEE80211_CHAN_HT40D) != 0)
567 cf |= (0x1 << WlanIfaceChannelFlagsType_ht40d);
568 if ((cflags & IEEE80211_CHAN_DFS) != 0)
569 cf |= (0x1 << WlanIfaceChannelFlagsType_dfs);
570 if ((cflags & IEEE80211_CHAN_4MSXMIT) != 0)
571 cf |= (0x1 << WlanIfaceChannelFlagsType_xmit4ms);
572 if ((cflags & IEEE80211_CHAN_NOADHOC) != 0)
573 cf |= (0x1 << WlanIfaceChannelFlagsType_noAdhoc);
574 if ((cflags & IEEE80211_CHAN_NOHOSTAP) != 0)
575 cf |= (0x1 << WlanIfaceChannelFlagsType_noHostAp);
576 if ((cflags & IEEE80211_CHAN_11D) != 0)
577 cf |= (0x1 << WlanIfaceChannelFlagsType_dot11d);
583 #define WLAN_SNMP_MAX_CHANS 256
585 wlan_get_channel_list(struct wlan_iface *wif)
590 struct ieee80211req_chaninfo *chaninfo;
591 struct ieee80211req_chanlist active;
592 const struct ieee80211_channel *c;
594 argsize = sizeof(struct ieee80211req_chaninfo) +
595 sizeof(struct ieee80211_channel) * WLAN_SNMP_MAX_CHANS;
596 chaninfo = (struct ieee80211req_chaninfo *)malloc(argsize);
597 if (chaninfo == NULL)
600 if (wlan_ioctl(wif->wname, IEEE80211_IOC_CHANINFO, &val, chaninfo,
604 argsize = sizeof(active);
605 if (wlan_ioctl(wif->wname, IEEE80211_IOC_CHANLIST, &val, &active,
609 for (i = 0, nchans = 0; i < chaninfo->ic_nchans; i++) {
610 c = &chaninfo->ic_chans[i];
611 if (!isset(active.ic_channels, c->ic_ieee))
615 wif->chanlist = (struct ieee80211_channel *)reallocf(wif->chanlist,
616 nchans * sizeof(*c));
617 if (wif->chanlist == NULL)
619 wif->nchannels = nchans;
620 for (i = 0, nchans = 0; i < chaninfo->ic_nchans; i++) {
621 c = &chaninfo->ic_chans[i];
622 if (!isset(active.ic_channels, c->ic_ieee))
624 memcpy(wif->chanlist + nchans, c, sizeof (*c));
636 static enum WlanIfPhyMode
637 wlan_channel_flags_to_snmp_phy(uint32_t cflags)
640 if ((cflags & IEEE80211_CHAN_A) != 0)
641 return (WlanIfPhyMode_dot11a);
642 if ((cflags & IEEE80211_CHAN_B) != 0)
643 return (WlanIfPhyMode_dot11b);
644 if ((cflags & IEEE80211_CHAN_G) != 0 ||
645 (cflags & IEEE80211_CHAN_PUREG) != 0)
646 return (WlanIfPhyMode_dot11g);
647 if ((cflags & IEEE80211_CHAN_FHSS) != 0)
648 return (WlanIfPhyMode_fh);
649 if ((cflags & IEEE80211_CHAN_TURBO) != 0 &&
650 (cflags & IEEE80211_CHAN_A) != 0)
651 return (WlanIfPhyMode_turboA);
652 if ((cflags & IEEE80211_CHAN_TURBO) != 0 &&
653 (cflags & IEEE80211_CHAN_G) != 0)
654 return (WlanIfPhyMode_turboG);
655 if ((cflags & IEEE80211_CHAN_STURBO) != 0)
656 return (WlanIfPhyMode_sturboA);
657 if ((cflags & IEEE80211_CHAN_HALF) != 0)
658 return (WlanIfPhyMode_ofdmHalf);
659 if ((cflags & IEEE80211_CHAN_QUARTER) != 0)
660 return (WlanIfPhyMode_ofdmQuarter);
662 return (WlanIfPhyMode_auto);
666 wlan_get_roam_params(struct wlan_iface *wif)
671 argsize = sizeof(struct ieee80211_roamparams_req);
672 if (wlan_ioctl(wif->wname, IEEE80211_IOC_ROAM, &val,
673 &wif->roamparams, &argsize, 0) < 0)
680 wlan_get_tx_params(struct wlan_iface *wif)
686 * XXX: Reset IEEE80211_RATE_MCS bit on IEEE80211_MODE_11NA
687 * and IEEE80211_MODE_11NG modes.
689 argsize = sizeof(struct ieee80211_txparams_req);
690 if (wlan_ioctl(wif->wname, IEEE80211_IOC_TXPARAMS, &val,
691 &wif->txparams, &argsize, 0) < 0)
698 wlan_set_tx_params(struct wlan_iface *wif, int32_t pmode __unused)
704 * XXX: Set IEEE80211_RATE_MCS bit on IEEE80211_MODE_11NA
705 * and IEEE80211_MODE_11NG modes.
707 argsize = sizeof(struct ieee80211_txparams_req);
708 if (wlan_ioctl(wif->wname, IEEE80211_IOC_TXPARAMS, &val,
709 &wif->txparams, &argsize, 1) < 0)
716 wlan_clone_create(struct wlan_iface *wif)
719 struct ieee80211_clone_params wcp;
720 static const uint8_t zerobssid[IEEE80211_ADDR_LEN];
722 memset(&wcp, 0, sizeof(wcp));
723 memset(&ifr, 0, sizeof(ifr));
726 if (wif == NULL || wif->pname[0] == '\0' || wif->mode > WLAN_IFMODE_MAX)
727 return (SNMP_ERR_INCONS_VALUE);
729 if (wif->mode == WlanIfaceOperatingModeType_wds &&
730 memcmp(wif->dbssid, zerobssid, IEEE80211_ADDR_LEN) == 0)
731 return (SNMP_ERR_INCONS_VALUE);
733 strlcpy(wcp.icp_parent, wif->pname, IFNAMSIZ);
734 if ((wif->flags & WlanIfaceFlagsType_uniqueBssid) != 0)
735 wcp.icp_flags |= IEEE80211_CLONE_BSSID;
736 if ((wif->flags & WlanIfaceFlagsType_noBeacons) != 0)
737 wcp.icp_flags |= IEEE80211_CLONE_NOBEACONS;
738 if (wif->mode == WlanIfaceOperatingModeType_wds &&
739 (wif->flags & WlanIfaceFlagsType_wdsLegacy) != 0)
740 wcp.icp_flags |= IEEE80211_CLONE_WDSLEGACY;
743 case WlanIfaceOperatingModeType_ibss:
744 wcp.icp_opmode = IEEE80211_M_IBSS;
746 case WlanIfaceOperatingModeType_station:
747 wcp.icp_opmode = IEEE80211_M_STA;
749 case WlanIfaceOperatingModeType_wds:
750 wcp.icp_opmode = IEEE80211_M_WDS;
752 case WlanIfaceOperatingModeType_adhocDemo:
753 wcp.icp_opmode = IEEE80211_M_AHDEMO;
755 case WlanIfaceOperatingModeType_hostAp:
756 wcp.icp_opmode = IEEE80211_M_HOSTAP;
758 case WlanIfaceOperatingModeType_monitor:
759 wcp.icp_opmode = IEEE80211_M_MONITOR;
761 case WlanIfaceOperatingModeType_meshPoint:
762 wcp.icp_opmode = IEEE80211_M_MBSS;
764 case WlanIfaceOperatingModeType_tdma:
765 wcp.icp_opmode = IEEE80211_M_AHDEMO;
766 wcp.icp_flags |= IEEE80211_CLONE_TDMA;
770 memcpy(wcp.icp_bssid, wif->dbssid, IEEE80211_ADDR_LEN);
771 if (memcmp(wif->dlmac, zerobssid, IEEE80211_ADDR_LEN) != 0) {
772 memcpy(wcp.icp_macaddr, wif->dlmac, IEEE80211_ADDR_LEN);
773 wcp.icp_flags |= IEEE80211_CLONE_MACADDR;
776 strlcpy(ifr.ifr_name, wif->wname, IFNAMSIZ);
777 ifr.ifr_data = (caddr_t) &wcp;
779 if (ioctl(sock, SIOCIFCREATE2, (caddr_t) &ifr) < 0) {
780 syslog(LOG_ERR, "wlan clone create: ioctl(SIOCIFCREATE2) "
781 "failed: %s", strerror(errno));
782 return (SNMP_ERR_GENERR);
785 return (SNMP_ERR_NOERROR);
789 wlan_clone_destroy(struct wlan_iface *wif)
794 return (SNMP_ERR_INCONS_VALUE);
796 memset(&ifr, 0, sizeof(ifr));
797 strcpy(ifr.ifr_name, wif->wname);
799 if (ioctl(sock, SIOCIFDESTROY, &ifr) < 0) {
800 syslog(LOG_ERR, "wlan clone destroy: ioctl(SIOCIFDESTROY) "
801 "failed: %s", strerror(errno));
802 return (SNMP_ERR_GENERR);
805 return (SNMP_ERR_NOERROR);
809 wlan_config_snmp2ioctl(int which)
814 case LEAF_wlanIfacePacketBurst:
815 op = IEEE80211_IOC_BURST;
817 case LEAF_wlanIfaceCountryCode:
818 op = IEEE80211_IOC_REGDOMAIN;
820 case LEAF_wlanIfaceRegDomain:
821 op = IEEE80211_IOC_REGDOMAIN;
823 case LEAF_wlanIfaceDesiredSsid:
824 op = IEEE80211_IOC_SSID;
826 case LEAF_wlanIfaceDesiredChannel:
827 op = IEEE80211_IOC_CURCHAN;
829 case LEAF_wlanIfaceDynamicFreqSelection:
830 op = IEEE80211_IOC_DFS;
832 case LEAF_wlanIfaceFastFrames:
833 op = IEEE80211_IOC_FF;
835 case LEAF_wlanIfaceDturbo:
836 op = IEEE80211_IOC_TURBOP;
838 case LEAF_wlanIfaceTxPower:
839 op = IEEE80211_IOC_TXPOWER;
841 case LEAF_wlanIfaceFragmentThreshold:
842 op = IEEE80211_IOC_FRAGTHRESHOLD;
844 case LEAF_wlanIfaceRTSThreshold:
845 op = IEEE80211_IOC_RTSTHRESHOLD;
847 case LEAF_wlanIfaceWlanPrivacySubscribe:
848 op = IEEE80211_IOC_WPS;
850 case LEAF_wlanIfaceBgScan:
851 op = IEEE80211_IOC_BGSCAN;
853 case LEAF_wlanIfaceBgScanIdle:
854 op = IEEE80211_IOC_BGSCAN_IDLE;
856 case LEAF_wlanIfaceBgScanInterval:
857 op = IEEE80211_IOC_BGSCAN_INTERVAL;
859 case LEAF_wlanIfaceBeaconMissedThreshold:
860 op = IEEE80211_IOC_BMISSTHRESHOLD;
862 case LEAF_wlanIfaceDesiredBssid:
863 op = IEEE80211_IOC_BSSID;
865 case LEAF_wlanIfaceRoamingMode:
866 op = IEEE80211_IOC_ROAMING;
868 case LEAF_wlanIfaceDot11d:
869 op = IEEE80211_IOC_DOTD;
871 case LEAF_wlanIfaceDot11h:
872 op = IEEE80211_IOC_DOTH;
874 case LEAF_wlanIfaceDynamicWds:
875 op = IEEE80211_IOC_DWDS;
877 case LEAF_wlanIfacePowerSave:
878 op = IEEE80211_IOC_POWERSAVE;
880 case LEAF_wlanIfaceApBridge:
881 op = IEEE80211_IOC_APBRIDGE;
883 case LEAF_wlanIfaceBeaconInterval:
884 op = IEEE80211_IOC_BEACON_INTERVAL;
886 case LEAF_wlanIfaceDtimPeriod:
887 op = IEEE80211_IOC_DTIM_PERIOD;
889 case LEAF_wlanIfaceHideSsid:
890 op = IEEE80211_IOC_HIDESSID;
892 case LEAF_wlanIfaceInactivityProccess:
893 op = IEEE80211_IOC_INACTIVITY;
895 case LEAF_wlanIfaceDot11gProtMode:
896 op = IEEE80211_IOC_PROTMODE;
898 case LEAF_wlanIfaceDot11gPureMode:
899 op = IEEE80211_IOC_PUREG;
901 case LEAF_wlanIfaceDot11nPureMode:
902 op = IEEE80211_IOC_PUREN;
904 case LEAF_wlanIfaceDot11nAmpdu:
905 op = IEEE80211_IOC_AMPDU;
907 case LEAF_wlanIfaceDot11nAmpduDensity:
908 op = IEEE80211_IOC_AMPDU_DENSITY;
910 case LEAF_wlanIfaceDot11nAmpduLimit:
911 op = IEEE80211_IOC_AMPDU_LIMIT;
913 case LEAF_wlanIfaceDot11nAmsdu:
914 op = IEEE80211_IOC_AMSDU;
916 case LEAF_wlanIfaceDot11nAmsduLimit:
917 op = IEEE80211_IOC_AMSDU_LIMIT;
919 case LEAF_wlanIfaceDot11nHighThroughput:
920 op = IEEE80211_IOC_HTCONF;
922 case LEAF_wlanIfaceDot11nHTCompatible:
923 op = IEEE80211_IOC_HTCOMPAT;
925 case LEAF_wlanIfaceDot11nHTProtMode:
926 op = IEEE80211_IOC_HTPROTMODE;
928 case LEAF_wlanIfaceDot11nRIFS:
929 op = IEEE80211_IOC_RIFS;
931 case LEAF_wlanIfaceDot11nShortGI:
932 op = IEEE80211_IOC_SHORTGI;
934 case LEAF_wlanIfaceDot11nSMPSMode:
935 op = IEEE80211_IOC_SMPS;
937 case LEAF_wlanIfaceTdmaSlot:
938 op = IEEE80211_IOC_TDMA_SLOT;
940 case LEAF_wlanIfaceTdmaSlotCount:
941 op = IEEE80211_IOC_TDMA_SLOTCNT;
943 case LEAF_wlanIfaceTdmaSlotLength:
944 op = IEEE80211_IOC_TDMA_SLOTLEN;
946 case LEAF_wlanIfaceTdmaBeaconInterval:
947 op = IEEE80211_IOC_TDMA_BINTERVAL;
956 static enum WlanRegDomainCode
957 wlan_regdomain_to_snmp(int which)
959 enum WlanRegDomainCode reg_domain;
963 reg_domain = WlanRegDomainCode_fcc;
966 reg_domain = WlanRegDomainCode_ca;
969 reg_domain = WlanRegDomainCode_etsi;
972 reg_domain = WlanRegDomainCode_etsi2;
975 reg_domain = WlanRegDomainCode_etsi3;
978 reg_domain = WlanRegDomainCode_fcc3;
981 reg_domain = WlanRegDomainCode_japan;
984 reg_domain = WlanRegDomainCode_korea;
987 reg_domain = WlanRegDomainCode_apac;
990 reg_domain = WlanRegDomainCode_apac2;
993 reg_domain = WlanRegDomainCode_apac3;
996 reg_domain = WlanRegDomainCode_row;
999 reg_domain = WlanRegDomainCode_none;
1002 reg_domain = WlanRegDomainCode_debug;
1005 reg_domain = WlanRegDomainCode_sr9;
1008 reg_domain = WlanRegDomainCode_xr9;
1011 reg_domain = WlanRegDomainCode_gz901;
1014 reg_domain = WlanRegDomainCode_none;
1017 syslog(LOG_ERR, "unknown regdomain (0x%x) ", which);
1018 reg_domain = WlanRegDomainCode_none;
1022 return (reg_domain);
1026 wlan_snmp_to_regdomain(enum WlanRegDomainCode regdomain)
1030 switch (regdomain) {
1031 case WlanRegDomainCode_fcc:
1034 case WlanRegDomainCode_ca:
1037 case WlanRegDomainCode_etsi:
1040 case WlanRegDomainCode_etsi2:
1043 case WlanRegDomainCode_etsi3:
1046 case WlanRegDomainCode_fcc3:
1049 case WlanRegDomainCode_japan:
1052 case WlanRegDomainCode_korea:
1055 case WlanRegDomainCode_apac:
1058 case WlanRegDomainCode_apac2:
1061 case WlanRegDomainCode_apac3:
1064 case WlanRegDomainCode_row:
1067 case WlanRegDomainCode_none:
1070 case WlanRegDomainCode_debug:
1073 case WlanRegDomainCode_sr9:
1076 case WlanRegDomainCode_xr9:
1079 case WlanRegDomainCode_gz901:
1083 syslog(LOG_ERR, "unknown snmp regdomain (0x%x) ", regdomain);
1092 wlan_config_get_country(struct wlan_iface *wif)
1096 struct ieee80211_regdomain regdomain;
1098 memset(®domain, 0, sizeof(regdomain));
1099 argsize = sizeof(regdomain);
1101 if (wlan_ioctl(wif->wname, IEEE80211_IOC_REGDOMAIN, &val, ®domain,
1105 wif->reg_domain = wlan_regdomain_to_snmp(regdomain.regdomain);
1106 wif->country_code[0] = regdomain.isocc[0];
1107 wif->country_code[1] = regdomain.isocc[1];
1108 wif->country_code[2] = regdomain.location;
1114 wlan_config_set_country(struct wlan_iface *wif, char *ccode, int rdomain)
1116 int val = 0, txpowermax;
1119 struct ieee80211_regdomain_req *regdomain;
1121 if (wlan_get_channel_list(wif) < 0)
1124 if (wif->nchannels == 0) {
1125 syslog(LOG_ERR, "iface %s - set regdomain failed", wif->wname);
1129 if (wlan_ioctl(wif->wname, IEEE80211_IOC_TXPOWMAX, &txpowermax, 0,
1133 regdomain = malloc(IEEE80211_REGDOMAIN_SIZE(wif->nchannels));
1134 if (regdomain == NULL)
1136 memset(regdomain, 0, IEEE80211_REGDOMAIN_SIZE(wif->nchannels));
1137 argsize = IEEE80211_REGDOMAIN_SIZE(wif->nchannels);
1139 /* XXX: recheck with how this is done by ifconfig(8) */
1140 regdomain->rd.regdomain = wlan_snmp_to_regdomain(rdomain);
1141 regdomain->rd.isocc[0] = ccode[0];
1142 regdomain->rd.isocc[1] = ccode[1];
1143 regdomain->rd.location = ccode[2];
1145 /* XXX: fill the channel list properly */
1146 regdomain->chaninfo.ic_nchans = wif->nchannels;
1147 memcpy(regdomain->chaninfo.ic_chans, wif->chanlist,
1148 wif->nchannels * sizeof(struct ieee80211_channel));
1149 for (i = 0; i < wif->nchannels; i++)
1150 regdomain->chaninfo.ic_chans[i].ic_maxregpower = txpowermax;
1152 wif->state = wlanIfaceState_down;
1153 if (wlan_config_state(wif, 1) < 0 ||
1154 wlan_ioctl(wif->wname, IEEE80211_IOC_REGDOMAIN, &val, regdomain,
1160 wif->state = wlanIfaceState_up;
1161 (void)wlan_config_state(wif, 1);
1162 wif->reg_domain = wlan_regdomain_to_snmp(regdomain->rd.regdomain);
1163 wif->country_code[0] = regdomain->rd.isocc[0];
1164 wif->country_code[1] = regdomain->rd.isocc[1];
1165 wif->country_code[2] = regdomain->rd.location;
1172 wlan_config_get_dssid(struct wlan_iface *wif)
1175 size_t argsize = IEEE80211_NWID_LEN + 1;
1176 char ssid[IEEE80211_NWID_LEN + 1];
1178 memset(ssid, 0, IEEE80211_NWID_LEN + 1);
1180 if (wlan_ioctl(wif->wname,
1181 (wif->mode == WlanIfaceOperatingModeType_meshPoint) ?
1182 IEEE80211_IOC_MESH_ID : IEEE80211_IOC_SSID, &val, ssid,
1186 if (argsize > IEEE80211_NWID_LEN)
1187 argsize = IEEE80211_NWID_LEN;
1188 memcpy(wif->desired_ssid, ssid, argsize);
1189 wif->desired_ssid[argsize] = '\0';
1195 wlan_config_set_dssid(struct wlan_iface *wif, char *ssid, int slen)
1198 size_t argsize = slen;
1200 if (wlan_ioctl(wif->wname,
1201 (wif->mode == WlanIfaceOperatingModeType_meshPoint) ?
1202 IEEE80211_IOC_MESH_ID : IEEE80211_IOC_SSID, &val, ssid,
1206 if (argsize > IEEE80211_NWID_LEN)
1207 argsize = IEEE80211_NWID_LEN;
1208 memcpy(wif->desired_ssid, ssid, argsize);
1209 wif->desired_ssid[argsize] = '\0';
1215 wlan_config_get_dchannel(struct wlan_iface *wif)
1219 size_t argsize = sizeof(struct ieee80211_channel);
1220 struct ieee80211_channel chan;
1222 if (wlan_get_channel_list(wif) < 0)
1225 memset(&chan, 0, sizeof(chan));
1226 if (wlan_ioctl(wif->wname, IEEE80211_IOC_CURCHAN, &val, &chan,
1230 for (i = 0; i < wif->nchannels; i++)
1231 if (chan.ic_ieee == wif->chanlist[i].ic_ieee &&
1232 chan.ic_flags == wif->chanlist[i].ic_flags) {
1233 wif->desired_channel = i + 1;
1241 wlan_config_set_dchannel(struct wlan_iface *wif, uint32_t dchannel)
1244 size_t argsize = sizeof(struct ieee80211_channel);
1245 struct ieee80211_channel chan;
1247 if (wlan_get_channel_list(wif) < 0)
1250 if (dchannel > wif->nchannels)
1253 memcpy(&chan, wif->chanlist + dchannel - 1, sizeof(chan));
1254 if (wlan_ioctl(wif->wname, IEEE80211_IOC_CURCHAN, &val, &chan,
1258 wif->desired_channel = dchannel;
1264 wlan_config_get_bssid(struct wlan_iface *wif)
1267 size_t argsize = IEEE80211_ADDR_LEN;
1268 char bssid[IEEE80211_ADDR_LEN];
1270 memset(bssid, 0, IEEE80211_ADDR_LEN);
1272 if (wlan_ioctl(wif->wname, IEEE80211_IOC_BSSID, &val, bssid,
1273 &argsize, 0) < 0 || argsize != IEEE80211_ADDR_LEN)
1276 memcpy(wif->desired_bssid, bssid, IEEE80211_ADDR_LEN);
1282 wlan_config_set_bssid(struct wlan_iface *wif, uint8_t *bssid)
1285 size_t argsize = IEEE80211_ADDR_LEN;
1287 if (wlan_ioctl(wif->wname, IEEE80211_IOC_BSSID, &val, bssid,
1288 &argsize, 1) < 0 || argsize != IEEE80211_ADDR_LEN)
1291 memcpy(wif->desired_bssid, bssid, IEEE80211_ADDR_LEN);
1297 * Convert the value returned by the kernel to the appropriate SNMP
1298 * representation and set the corresponding interface member accordingly.
1301 wlan_config_set_snmp_intval(struct wlan_iface *wif, int op, int val)
1304 case IEEE80211_IOC_BURST:
1306 wif->packet_burst = TruthValue_false;
1308 wif->packet_burst = TruthValue_true;
1310 case IEEE80211_IOC_DFS:
1312 wif->dyn_frequency = TruthValue_false;
1314 wif->dyn_frequency = TruthValue_true;
1316 case IEEE80211_IOC_FF:
1318 wif->fast_frames = TruthValue_false;
1320 wif->fast_frames = TruthValue_true;
1322 case IEEE80211_IOC_TURBOP:
1324 wif->dturbo = TruthValue_false;
1326 wif->dturbo = TruthValue_true;
1328 case IEEE80211_IOC_TXPOWER:
1329 wif->tx_power = val / 2;
1331 case IEEE80211_IOC_FRAGTHRESHOLD:
1332 wif->frag_threshold = val;
1334 case IEEE80211_IOC_RTSTHRESHOLD:
1335 wif->rts_threshold = val;
1337 case IEEE80211_IOC_WPS:
1339 wif->priv_subscribe = TruthValue_false;
1341 wif->priv_subscribe = TruthValue_true;
1343 case IEEE80211_IOC_BGSCAN:
1345 wif->bg_scan = TruthValue_false;
1347 wif->bg_scan = TruthValue_true;
1349 case IEEE80211_IOC_BGSCAN_IDLE:
1350 wif->bg_scan_idle = val;
1352 case IEEE80211_IOC_BGSCAN_INTERVAL:
1353 wif->bg_scan_interval = val;
1355 case IEEE80211_IOC_BMISSTHRESHOLD:
1356 wif->beacons_missed = val;
1358 case IEEE80211_IOC_ROAMING:
1360 case IEEE80211_ROAMING_DEVICE:
1361 wif->roam_mode = wlanIfaceRoamingMode_device;
1363 case IEEE80211_ROAMING_MANUAL:
1364 wif->roam_mode = wlanIfaceRoamingMode_manual;
1366 case IEEE80211_ROAMING_AUTO:
1369 wif->roam_mode = wlanIfaceRoamingMode_auto;
1373 case IEEE80211_IOC_DOTD:
1375 wif->dot11d = TruthValue_false;
1377 wif->dot11d = TruthValue_true;
1379 case IEEE80211_IOC_DOTH:
1381 wif->dot11h = TruthValue_false;
1383 wif->dot11h = TruthValue_true;
1385 case IEEE80211_IOC_DWDS:
1387 wif->dynamic_wds = TruthValue_false;
1389 wif->dynamic_wds = TruthValue_true;
1391 case IEEE80211_IOC_POWERSAVE:
1393 wif->power_save = TruthValue_false;
1395 wif->power_save = TruthValue_true;
1397 case IEEE80211_IOC_APBRIDGE:
1399 wif->ap_bridge = TruthValue_false;
1401 wif->ap_bridge = TruthValue_true;
1403 case IEEE80211_IOC_BEACON_INTERVAL:
1404 wif->beacon_interval = val;
1406 case IEEE80211_IOC_DTIM_PERIOD:
1407 wif->dtim_period = val;
1409 case IEEE80211_IOC_HIDESSID:
1411 wif->hide_ssid = TruthValue_false;
1413 wif->hide_ssid = TruthValue_true;
1415 case IEEE80211_IOC_INACTIVITY:
1417 wif->inact_process = TruthValue_false;
1419 wif->inact_process = TruthValue_true;
1421 case IEEE80211_IOC_PROTMODE:
1423 case IEEE80211_PROTMODE_CTS:
1424 wif->do11g_protect = wlanIfaceDot11gProtMode_cts;
1426 case IEEE80211_PROTMODE_RTSCTS:
1427 wif->do11g_protect = wlanIfaceDot11gProtMode_rtscts;
1429 case IEEE80211_PROTMODE_OFF:
1432 wif->do11g_protect = wlanIfaceDot11gProtMode_off;
1436 case IEEE80211_IOC_PUREG:
1438 wif->dot11g_pure = TruthValue_false;
1440 wif->dot11g_pure = TruthValue_true;
1442 case IEEE80211_IOC_PUREN:
1444 wif->dot11n_pure = TruthValue_false;
1446 wif->dot11n_pure = TruthValue_true;
1448 case IEEE80211_IOC_AMPDU:
1451 wif->ampdu = WlanIfaceDot11nPduType_disabled;
1454 wif->ampdu = WlanIfaceDot11nPduType_txOnly;
1457 wif->ampdu = WlanIfaceDot11nPduType_rxOnly;
1462 wif->ampdu = WlanIfaceDot11nPduType_txAndRx;
1466 case IEEE80211_IOC_AMPDU_DENSITY:
1468 case IEEE80211_HTCAP_MPDUDENSITY_025:
1469 wif->ampdu_density = 25;
1471 case IEEE80211_HTCAP_MPDUDENSITY_05:
1472 wif->ampdu_density = 50;
1474 case IEEE80211_HTCAP_MPDUDENSITY_1:
1475 wif->ampdu_density = 100;
1477 case IEEE80211_HTCAP_MPDUDENSITY_2:
1478 wif->ampdu_density = 200;
1480 case IEEE80211_HTCAP_MPDUDENSITY_4:
1481 wif->ampdu_density = 400;
1483 case IEEE80211_HTCAP_MPDUDENSITY_8:
1484 wif->ampdu_density = 800;
1486 case IEEE80211_HTCAP_MPDUDENSITY_16:
1487 wif->ampdu_density = 1600;
1489 case IEEE80211_HTCAP_MPDUDENSITY_NA:
1491 wif->ampdu_density = 0;
1495 case IEEE80211_IOC_AMPDU_LIMIT:
1497 case IEEE80211_HTCAP_MAXRXAMPDU_8K:
1498 wif->ampdu_limit = 8192;
1500 case IEEE80211_HTCAP_MAXRXAMPDU_16K:
1501 wif->ampdu_limit = 16384;
1503 case IEEE80211_HTCAP_MAXRXAMPDU_32K:
1504 wif->ampdu_limit = 32768;
1506 case IEEE80211_HTCAP_MAXRXAMPDU_64K:
1508 wif->ampdu_limit = 65536;
1512 case IEEE80211_IOC_AMSDU:
1515 wif->amsdu = WlanIfaceDot11nPduType_disabled;
1518 wif->amsdu = WlanIfaceDot11nPduType_txOnly;
1521 wif->amsdu = WlanIfaceDot11nPduType_txAndRx;
1526 wif->amsdu = WlanIfaceDot11nPduType_rxOnly;
1530 case IEEE80211_IOC_AMSDU_LIMIT:
1531 wif->amsdu_limit = val;
1533 case IEEE80211_IOC_HTCONF:
1534 if (val == 0) /* XXX */
1535 wif->ht_enabled = TruthValue_false;
1537 wif->ht_enabled = TruthValue_true;
1539 case IEEE80211_IOC_HTCOMPAT:
1541 wif->ht_compatible = TruthValue_false;
1543 wif->ht_compatible = TruthValue_true;
1545 case IEEE80211_IOC_HTPROTMODE:
1546 if (val == IEEE80211_PROTMODE_RTSCTS)
1547 wif->ht_prot_mode = wlanIfaceDot11nHTProtMode_rts;
1549 wif->ht_prot_mode = wlanIfaceDot11nHTProtMode_off;
1551 case IEEE80211_IOC_RIFS:
1553 wif->rifs = TruthValue_false;
1555 wif->rifs = TruthValue_true;
1557 case IEEE80211_IOC_SHORTGI:
1559 wif->short_gi = TruthValue_false;
1561 wif->short_gi = TruthValue_true;
1563 case IEEE80211_IOC_SMPS:
1565 case IEEE80211_HTCAP_SMPS_DYNAMIC:
1566 wif->smps_mode = wlanIfaceDot11nSMPSMode_dynamic;
1568 case IEEE80211_HTCAP_SMPS_ENA:
1569 wif->smps_mode = wlanIfaceDot11nSMPSMode_static;
1571 case IEEE80211_HTCAP_SMPS_OFF:
1574 wif->smps_mode = wlanIfaceDot11nSMPSMode_disabled;
1578 case IEEE80211_IOC_TDMA_SLOT:
1579 wif->tdma_slot = val;
1581 case IEEE80211_IOC_TDMA_SLOTCNT:
1582 wif->tdma_slot_count = val;
1584 case IEEE80211_IOC_TDMA_SLOTLEN:
1585 wif->tdma_slot_length = val;
1587 case IEEE80211_IOC_TDMA_BINTERVAL:
1588 wif->tdma_binterval = val;
1596 * Convert an SNMP value to the kernel equivalent and also do sanity check
1597 * for each specific type.
1600 wlan_config_snmp2value(int which, int sval, int *value)
1605 case IEEE80211_IOC_BURST:
1606 case IEEE80211_IOC_DFS:
1607 case IEEE80211_IOC_FF:
1608 case IEEE80211_IOC_TURBOP:
1609 case IEEE80211_IOC_WPS:
1610 case IEEE80211_IOC_BGSCAN:
1611 case IEEE80211_IOC_DOTD:
1612 case IEEE80211_IOC_DOTH:
1613 case IEEE80211_IOC_DWDS:
1614 case IEEE80211_IOC_POWERSAVE:
1615 case IEEE80211_IOC_APBRIDGE:
1616 case IEEE80211_IOC_HIDESSID:
1617 case IEEE80211_IOC_INACTIVITY:
1618 case IEEE80211_IOC_PUREG:
1619 case IEEE80211_IOC_PUREN:
1620 case IEEE80211_IOC_HTCONF:
1621 case IEEE80211_IOC_HTCOMPAT:
1622 case IEEE80211_IOC_RIFS:
1623 if (sval == TruthValue_true)
1625 else if (sval != TruthValue_false)
1626 return (SNMP_ERR_INCONS_VALUE);
1628 case IEEE80211_IOC_REGDOMAIN:
1630 case IEEE80211_IOC_SSID:
1632 case IEEE80211_IOC_CURCHAN:
1634 case IEEE80211_IOC_TXPOWER:
1637 case IEEE80211_IOC_FRAGTHRESHOLD:
1638 if (sval < IEEE80211_FRAG_MIN || sval > IEEE80211_FRAG_MAX)
1639 return (SNMP_ERR_INCONS_VALUE);
1642 case IEEE80211_IOC_RTSTHRESHOLD:
1643 if (sval < IEEE80211_RTS_MIN || sval > IEEE80211_RTS_MAX)
1644 return (SNMP_ERR_INCONS_VALUE);
1647 case IEEE80211_IOC_BGSCAN_IDLE:
1648 if (sval < WLAN_BGSCAN_IDLE_MIN)
1649 return (SNMP_ERR_INCONS_VALUE);
1652 case IEEE80211_IOC_BGSCAN_INTERVAL:
1653 if (sval < WLAN_SCAN_VALID_MIN)
1654 return (SNMP_ERR_INCONS_VALUE);
1657 case IEEE80211_IOC_BMISSTHRESHOLD:
1658 if (sval < IEEE80211_HWBMISS_MIN || sval > IEEE80211_HWBMISS_MAX)
1659 return (SNMP_ERR_INCONS_VALUE);
1662 case IEEE80211_IOC_BSSID:
1664 case IEEE80211_IOC_ROAMING:
1666 case wlanIfaceRoamingMode_device:
1667 *value = IEEE80211_ROAMING_DEVICE;
1669 case wlanIfaceRoamingMode_manual:
1670 *value = IEEE80211_ROAMING_MANUAL;
1672 case wlanIfaceRoamingMode_auto:
1673 *value = IEEE80211_ROAMING_AUTO;
1676 return (SNMP_ERR_INCONS_VALUE);
1679 case IEEE80211_IOC_BEACON_INTERVAL:
1680 if (sval < IEEE80211_BINTVAL_MIN || sval > IEEE80211_BINTVAL_MAX)
1681 return (SNMP_ERR_INCONS_VALUE);
1684 case IEEE80211_IOC_DTIM_PERIOD:
1685 if (sval < IEEE80211_DTIM_MIN || sval > IEEE80211_DTIM_MAX)
1686 return (SNMP_ERR_INCONS_VALUE);
1689 case IEEE80211_IOC_PROTMODE:
1691 case wlanIfaceDot11gProtMode_cts:
1692 *value = IEEE80211_PROTMODE_CTS;
1694 case wlanIfaceDot11gProtMode_rtscts:
1695 *value = IEEE80211_PROTMODE_RTSCTS;
1697 case wlanIfaceDot11gProtMode_off:
1698 *value = IEEE80211_PROTMODE_OFF;
1701 return (SNMP_ERR_INCONS_VALUE);
1704 case IEEE80211_IOC_AMPDU:
1706 case WlanIfaceDot11nPduType_disabled:
1708 case WlanIfaceDot11nPduType_txOnly:
1711 case WlanIfaceDot11nPduType_rxOnly:
1714 case WlanIfaceDot11nPduType_txAndRx:
1718 return (SNMP_ERR_INCONS_VALUE);
1721 case IEEE80211_IOC_AMPDU_DENSITY:
1724 *value = IEEE80211_HTCAP_MPDUDENSITY_NA;
1727 *value = IEEE80211_HTCAP_MPDUDENSITY_025;
1730 *value = IEEE80211_HTCAP_MPDUDENSITY_05;
1733 *value = IEEE80211_HTCAP_MPDUDENSITY_1;
1736 *value = IEEE80211_HTCAP_MPDUDENSITY_2;
1739 *value = IEEE80211_HTCAP_MPDUDENSITY_4;
1742 *value = IEEE80211_HTCAP_MPDUDENSITY_8;
1745 *value = IEEE80211_HTCAP_MPDUDENSITY_16;
1748 return (SNMP_ERR_INCONS_VALUE);
1751 case IEEE80211_IOC_AMPDU_LIMIT:
1754 *value = IEEE80211_HTCAP_MAXRXAMPDU_8K;
1757 *value = IEEE80211_HTCAP_MAXRXAMPDU_16K;
1760 *value = IEEE80211_HTCAP_MAXRXAMPDU_32K;
1763 *value = IEEE80211_HTCAP_MAXRXAMPDU_64K;
1766 return (SNMP_ERR_INCONS_VALUE);
1769 case IEEE80211_IOC_AMSDU:
1771 case WlanIfaceDot11nPduType_disabled:
1773 case WlanIfaceDot11nPduType_txOnly:
1776 case WlanIfaceDot11nPduType_rxOnly:
1779 case WlanIfaceDot11nPduType_txAndRx:
1783 return (SNMP_ERR_INCONS_VALUE);
1786 case IEEE80211_IOC_AMSDU_LIMIT:
1787 if (sval == 3839 || sval == 0)
1788 *value = IEEE80211_HTCAP_MAXAMSDU_3839;
1789 else if (sval == 7935)
1790 *value = IEEE80211_HTCAP_MAXAMSDU_7935;
1792 return (SNMP_ERR_INCONS_VALUE);
1794 case IEEE80211_IOC_HTPROTMODE:
1796 case wlanIfaceDot11nHTProtMode_rts:
1797 *value = IEEE80211_PROTMODE_RTSCTS;
1799 case wlanIfaceDot11nHTProtMode_off:
1802 return (SNMP_ERR_INCONS_VALUE);
1805 case IEEE80211_IOC_SHORTGI:
1806 if (sval == TruthValue_true)
1807 *value = IEEE80211_HTCAP_SHORTGI20 |
1808 IEEE80211_HTCAP_SHORTGI40;
1809 else if (sval != TruthValue_false)
1810 return (SNMP_ERR_INCONS_VALUE);
1812 case IEEE80211_IOC_SMPS:
1814 case wlanIfaceDot11nSMPSMode_disabled:
1815 *value = IEEE80211_HTCAP_SMPS_OFF;
1817 case wlanIfaceDot11nSMPSMode_static:
1818 *value = IEEE80211_HTCAP_SMPS_ENA;
1820 case wlanIfaceDot11nSMPSMode_dynamic:
1821 *value = IEEE80211_HTCAP_SMPS_DYNAMIC;
1824 return (SNMP_ERR_INCONS_VALUE);
1827 case IEEE80211_IOC_TDMA_SLOT:
1828 if (sval < 0 || sval > WLAN_TDMA_MAXSLOTS) /* XXX */
1829 return (SNMP_ERR_INCONS_VALUE);
1832 case IEEE80211_IOC_TDMA_SLOTCNT:
1833 if (sval < 0 || sval > WLAN_TDMA_MAXSLOTS) /* XXX */
1834 return (SNMP_ERR_INCONS_VALUE);
1837 case IEEE80211_IOC_TDMA_SLOTLEN:
1838 if (sval < 2*100 || sval > 0xfffff) /* XXX */
1839 return (SNMP_ERR_INCONS_VALUE);
1842 case IEEE80211_IOC_TDMA_BINTERVAL:
1843 if (sval < 1) /* XXX */
1844 return (SNMP_ERR_INCONS_VALUE);
1848 return (SNMP_ERR_INCONS_VALUE);
1851 return (SNMP_ERR_NOERROR);
1855 * Sanity checks for the wlanIfaceConfigTable.
1858 wlan_config_check(struct wlan_iface *wif, int op)
1861 case IEEE80211_IOC_BURST:
1862 if ((wif->drivercaps & (0x1 << WlanDriverCaps_burst)) == 0) {
1863 wif->packet_burst = TruthValue_false;
1867 case IEEE80211_IOC_DFS:
1868 if ((wif->drivercaps & (0x1 << WlanDriverCaps_dfs)) == 0) {
1869 wif->dyn_frequency = TruthValue_false;
1873 case IEEE80211_IOC_FF:
1874 if ((wif->drivercaps & (0x1 << WlanDriverCaps_athFastFrames))
1876 wif->fast_frames = TruthValue_false;
1880 case IEEE80211_IOC_TURBOP:
1881 if ((wif->drivercaps & (0x1 << WlanDriverCaps_athTurbo)) == 0) {
1882 wif->dturbo = TruthValue_false;
1886 case IEEE80211_IOC_TXPOWER:
1887 if ((wif->drivercaps & (0x1 << WlanDriverCaps_txPmgt)) == 0) {
1892 case IEEE80211_IOC_FRAGTHRESHOLD:
1893 if ((wif->drivercaps & (0x1 << WlanDriverCaps_txFrag)) == 0) {
1894 wif->frag_threshold = IEEE80211_FRAG_MAX;
1898 case IEEE80211_IOC_DWDS:
1899 if ((wif->drivercaps & (0x1 << WlanDriverCaps_wds)) == 0) {
1900 wif->dynamic_wds = TruthValue_false;
1904 case IEEE80211_IOC_POWERSAVE:
1905 if ((wif->drivercaps & (0x1 << WlanDriverCaps_pmgt)) == 0) {
1906 wif->power_save = TruthValue_false;
1910 case IEEE80211_IOC_BEACON_INTERVAL:
1911 if (wif->mode != WlanIfaceOperatingModeType_hostAp &&
1912 wif->mode != WlanIfaceOperatingModeType_meshPoint &&
1913 wif->mode != WlanIfaceOperatingModeType_ibss) {
1914 wif->beacon_interval = 100; /* XXX */
1918 case IEEE80211_IOC_DTIM_PERIOD:
1919 if (wif->mode != WlanIfaceOperatingModeType_hostAp &&
1920 wif->mode != WlanIfaceOperatingModeType_meshPoint &&
1921 wif->mode != WlanIfaceOperatingModeType_ibss) {
1922 wif->dtim_period = 1; /* XXX */
1926 case IEEE80211_IOC_PUREN:
1927 if ((wif->htcaps & (0x1 << WlanHTCaps_htcHt)) == 0) {
1928 wif->dot11n_pure = TruthValue_false;
1932 case IEEE80211_IOC_AMPDU:
1933 if ((wif->htcaps & (0x1 << WlanHTCaps_htcAmpdu)) == 0) {
1934 wif->ampdu = WlanIfaceDot11nPduType_disabled;
1938 case IEEE80211_IOC_AMSDU:
1939 if ((wif->htcaps & (0x1 << WlanHTCaps_htcAmsdu)) == 0) {
1940 wif->amsdu = WlanIfaceDot11nPduType_disabled;
1944 case IEEE80211_IOC_RIFS:
1945 if ((wif->htcaps & (0x1 << WlanHTCaps_htcRifs)) == 0) {
1946 wif->rifs = TruthValue_false;
1950 case IEEE80211_IOC_SHORTGI:
1951 if ((wif->htcaps & (0x1 << WlanHTCaps_shortGi20 |
1952 0x1 << WlanHTCaps_shortGi40)) == 0) {
1953 wif->short_gi = TruthValue_false;
1957 case IEEE80211_IOC_SMPS:
1958 if ((wif->htcaps & (0x1 << WlanHTCaps_htcSmps)) == 0) {
1959 wif->smps_mode = wlanIfaceDot11nSMPSMode_disabled;
1963 case IEEE80211_IOC_TDMA_SLOT:
1964 if ((wif->drivercaps & (0x1 << WlanDriverCaps_tdma)) == 0) {
1969 case IEEE80211_IOC_TDMA_SLOTCNT:
1970 if ((wif->drivercaps & (0x1 << WlanDriverCaps_tdma)) == 0) {
1971 wif->tdma_slot_count = 0;
1975 case IEEE80211_IOC_TDMA_SLOTLEN:
1976 if ((wif->drivercaps & (0x1 << WlanDriverCaps_tdma)) == 0) {
1977 wif->tdma_slot_length = 0;
1981 case IEEE80211_IOC_TDMA_BINTERVAL:
1982 if ((wif->drivercaps & (0x1 << WlanDriverCaps_tdma)) == 0) {
1983 wif->tdma_binterval = 0;
1995 wlan_config_get_intval(struct wlan_iface *wif, int op)
2000 if (wlan_config_check(wif, op) < 0)
2002 if (wlan_ioctl(wif->wname, op, &val, NULL, &argsize, 0) < 0)
2004 wlan_config_set_snmp_intval(wif, op, val);
2010 wlan_config_set_intval(struct wlan_iface *wif, int op, int sval)
2015 if (wlan_config_check(wif, op) < 0)
2017 if (wlan_config_snmp2value(op, sval, &val) != SNMP_ERR_NOERROR)
2019 if (wlan_ioctl(wif->wname, op, &val, NULL, &argsize, 1) < 0)
2021 wlan_config_set_snmp_intval(wif, op, val);
2027 wlan_config_get_ioctl(struct wlan_iface *wif, int which)
2032 case LEAF_wlanIfaceCountryCode:
2034 case LEAF_wlanIfaceRegDomain:
2035 return (wlan_config_get_country(wif));
2036 case LEAF_wlanIfaceDesiredSsid:
2037 return (wlan_config_get_dssid(wif));
2038 case LEAF_wlanIfaceDesiredChannel:
2039 return (wlan_config_get_dchannel(wif));
2040 case LEAF_wlanIfaceDesiredBssid:
2041 return (wlan_config_get_bssid(wif));
2043 op = wlan_config_snmp2ioctl(which);
2044 return (wlan_config_get_intval(wif, op));
2051 wlan_config_set_ioctl(struct wlan_iface *wif, int which, int val,
2052 char *strval, int len)
2057 case LEAF_wlanIfaceCountryCode:
2058 return (wlan_config_set_country(wif, strval,
2060 case LEAF_wlanIfaceRegDomain:
2061 return (wlan_config_set_country(wif, wif->country_code,
2063 case LEAF_wlanIfaceDesiredSsid:
2064 return (wlan_config_set_dssid(wif, strval, len));
2065 case LEAF_wlanIfaceDesiredChannel:
2066 return (wlan_config_set_dchannel(wif, val));
2067 case LEAF_wlanIfaceDesiredBssid:
2068 return (wlan_config_set_bssid(wif, strval));
2070 op = wlan_config_snmp2ioctl(which);
2071 return (wlan_config_set_intval(wif, op, val));
2078 wlan_snmp_to_scan_flags(int flags)
2082 if ((flags & (0x1 << WlanScanFlagsType_noSelection)) != 0)
2083 sr_flags |= IEEE80211_IOC_SCAN_NOPICK;
2084 if ((flags & (0x1 << WlanScanFlagsType_activeScan)) != 0)
2085 sr_flags |= IEEE80211_IOC_SCAN_ACTIVE;
2086 if ((flags & (0x1 << WlanScanFlagsType_pickFirst)) != 0)
2087 sr_flags |= IEEE80211_IOC_SCAN_PICK1ST;
2088 if ((flags & (0x1 << WlanScanFlagsType_backgroundScan)) != 0)
2089 sr_flags |= IEEE80211_IOC_SCAN_BGSCAN;
2090 if ((flags & (0x1 << WlanScanFlagsType_once)) != 0)
2091 sr_flags |= IEEE80211_IOC_SCAN_ONCE;
2092 if ((flags & (0x1 << WlanScanFlagsType_noBroadcast)) != 0)
2093 sr_flags |= IEEE80211_IOC_SCAN_NOBCAST;
2094 if ((flags & (0x1 << WlanScanFlagsType_noAutoSequencing)) != 0)
2095 sr_flags |= IEEE80211_IOC_SCAN_NOJOIN;
2096 if ((flags & (0x1 << WlanScanFlagsType_flushCashe)) != 0)
2097 sr_flags |= IEEE80211_IOC_SCAN_FLUSH;
2098 if ((flags & (0x1 << WlanScanFlagsType_chechCashe)) != 0)
2099 sr_flags |= IEEE80211_IOC_SCAN_CHECK;
2105 wlan_set_scan_config(struct wlan_iface *wif)
2109 struct ieee80211_scan_req sr;
2112 memset(&sr, 0, sizeof(sr));
2113 argsize = sizeof(struct ieee80211_scan_req);
2114 sr.sr_flags = wlan_snmp_to_scan_flags(wif->scan_flags);
2115 sr.sr_flags |= IEEE80211_IOC_SCAN_BGSCAN;
2116 sr.sr_duration = wif->scan_duration;
2117 sr.sr_mindwell = wif->scan_mindwell;
2118 sr.sr_maxdwell = wif->scan_maxdwell;
2121 if (wlan_ioctl(wif->wname, IEEE80211_IOC_SCAN_REQ,
2122 &val, &sr, &argsize, 1) < 0)
2125 wif->scan_status = wlanScanConfigStatus_running;
2130 wlan_peercaps_to_snmp(uint32_t pcaps)
2134 if ((pcaps & IEEE80211_CAPINFO_ESS) != 0)
2135 scaps |= (0x1 << WlanPeerCapabilityFlags_ess);
2136 if ((pcaps & IEEE80211_CAPINFO_IBSS) != 0)
2137 scaps |= (0x1 << WlanPeerCapabilityFlags_ibss);
2138 if ((pcaps & IEEE80211_CAPINFO_CF_POLLABLE) != 0)
2139 scaps |= (0x1 << WlanPeerCapabilityFlags_cfPollable);
2140 if ((pcaps & IEEE80211_CAPINFO_CF_POLLREQ) != 0)
2141 scaps |= (0x1 << WlanPeerCapabilityFlags_cfPollRequest);
2142 if ((pcaps & IEEE80211_CAPINFO_PRIVACY) != 0)
2143 scaps |= (0x1 << WlanPeerCapabilityFlags_privacy);
2144 if ((pcaps & IEEE80211_CAPINFO_SHORT_PREAMBLE) != 0)
2145 scaps |= (0x1 << WlanPeerCapabilityFlags_shortPreamble);
2146 if ((pcaps & IEEE80211_CAPINFO_PBCC) != 0)
2147 scaps |= (0x1 << WlanPeerCapabilityFlags_pbcc);
2148 if ((pcaps & IEEE80211_CAPINFO_CHNL_AGILITY) != 0)
2149 scaps |= (0x1 << WlanPeerCapabilityFlags_channelAgility);
2150 if ((pcaps & IEEE80211_CAPINFO_SHORT_SLOTTIME) != 0)
2151 scaps |= (0x1 << WlanPeerCapabilityFlags_shortSlotTime);
2152 if ((pcaps & IEEE80211_CAPINFO_RSN) != 0)
2153 scaps |= (0x1 << WlanPeerCapabilityFlags_rsn);
2154 if ((pcaps & IEEE80211_CAPINFO_DSSSOFDM) != 0)
2155 scaps |= (0x1 << WlanPeerCapabilityFlags_dsssofdm);
2161 wlan_add_new_scan_result(struct wlan_iface *wif,
2162 const struct ieee80211req_scan_result *isr, uint8_t *ssid)
2164 struct wlan_scan_result *sr;
2166 if ((sr = wlan_scan_new_result(ssid, isr->isr_bssid)) == NULL)
2169 sr->opchannel = wlan_channel_flags_to_snmp_phy(isr->isr_flags);
2170 sr->rssi = isr->isr_rssi;
2171 sr->frequency = isr->isr_freq;
2172 sr->noise = isr->isr_noise;
2173 sr->bintval = isr->isr_intval;
2174 sr->capinfo = wlan_peercaps_to_snmp(isr->isr_capinfo);
2176 if (wlan_scan_add_result(wif, sr) < 0) {
2177 wlan_scan_free_result(sr);
2185 wlan_get_scan_results(struct wlan_iface *wif)
2187 int ssidlen, val = 0;
2188 uint8_t buf[24 * 1024];
2190 const uint8_t *cp, *idp;
2191 uint8_t ssid[IEEE80211_NWID_LEN + 1];
2192 struct ieee80211req_scan_result isr;
2194 argsize = sizeof(buf);
2195 if (wlan_ioctl(wif->wname, IEEE80211_IOC_SCAN_RESULTS, &val, &buf,
2199 if (argsize < sizeof(struct ieee80211req_scan_result))
2204 memcpy(&isr, cp, sizeof(struct ieee80211req_scan_result));
2205 memset(ssid, 0, IEEE80211_NWID_LEN + 1);
2207 if (isr.isr_meshid_len) {
2208 idp = cp + isr.isr_ie_off + isr.isr_ssid_len;
2209 ssidlen = isr.isr_meshid_len;
2211 idp = cp + isr.isr_ie_off;
2212 ssidlen = isr.isr_ssid_len;
2214 if (ssidlen > IEEE80211_NWID_LEN)
2215 ssidlen = IEEE80211_NWID_LEN;
2216 memcpy(ssid, idp, ssidlen);
2217 ssid[IEEE80211_NWID_LEN] = '\0';
2218 (void)wlan_add_new_scan_result(wif, &isr, ssid);
2220 argsize -= isr.isr_len;
2221 } while (argsize >= sizeof(struct ieee80211req_scan_result));
2227 wlan_get_stats(struct wlan_iface *wif)
2231 memset(&ifr, 0, sizeof(struct ifreq));
2232 strlcpy(ifr.ifr_name, wif->wname, IFNAMSIZ);
2234 ifr.ifr_data = (caddr_t) &wif->stats;
2236 if (ioctl(sock, SIOCG80211STATS, &ifr) < 0) {
2237 syslog(LOG_ERR, "iface %s - ioctl(SIOCG80211STATS) failed: %s",
2238 wif->wname, strerror(errno));
2246 wlan_get_wepmode(struct wlan_iface *wif)
2251 if (wlan_ioctl(wif->wname, IEEE80211_IOC_WEP, &val, NULL,
2252 &argsize, 0) < 0 || val == IEEE80211_WEP_NOSUP) {
2253 wif->wepsupported = 0; /* XXX */
2254 wif->wepmode = wlanWepMode_off;
2259 wif->wepsupported = 1;
2262 case IEEE80211_WEP_ON:
2263 wif->wepmode = wlanWepMode_on;
2265 case IEEE80211_WEP_MIXED:
2266 wif->wepmode = wlanWepMode_mixed;
2268 case IEEE80211_WEP_OFF:
2271 wif->wepmode = wlanWepMode_off;
2279 wlan_set_wepmode(struct wlan_iface *wif)
2284 if (!wif->wepsupported)
2287 switch (wif->wepmode) {
2288 case wlanWepMode_off:
2289 val = IEEE80211_WEP_OFF;
2291 case wlanWepMode_on:
2292 val = IEEE80211_WEP_ON;
2294 case wlanWepMode_mixed:
2295 val = IEEE80211_WEP_MIXED;
2301 if (wlan_ioctl(wif->wname, IEEE80211_IOC_WEP, &val, NULL,
2309 wlan_get_weptxkey(struct wlan_iface *wif)
2314 if (!wif->wepsupported)
2317 if (wlan_ioctl(wif->wname, IEEE80211_IOC_WEPTXKEY, &val, NULL,
2321 if (val == IEEE80211_KEYIX_NONE)
2324 wif->weptxkey = val + 1;
2330 wlan_set_weptxkey(struct wlan_iface *wif)
2335 if (!wif->wepsupported)
2338 if (wif->weptxkey >= IEEE80211_WEP_NKID)
2341 if (wif->weptxkey == 0)
2342 val = IEEE80211_KEYIX_NONE;
2344 val = wif->weptxkey - 1;
2345 if (wlan_ioctl(wif->wname, IEEE80211_IOC_WEPTXKEY, &val, NULL,
2353 wlan_get_wepkeys(struct wlan_iface *wif __unused)
2355 /* XXX: should they be visible via SNMP */
2360 wlan_set_wepkeys(struct wlan_iface *wif __unused)
2362 /* XXX: should they be configurable via SNMP */
2367 wlan_get_mac_policy(struct wlan_iface *wif)
2369 int val = IEEE80211_MACCMD_POLICY;
2371 struct ieee80211req ireq;
2373 memset(&ireq, 0, sizeof(struct ieee80211req));
2374 strlcpy(ireq.i_name, wif->wname, IFNAMSIZ);
2375 ireq.i_type = IEEE80211_IOC_MACCMD;
2376 ireq.i_val = IEEE80211_MACCMD_POLICY;
2378 if (ioctl(sock, SIOCG80211, &ireq) < 0) {
2379 if (errno != EINVAL) {
2380 syslog(LOG_ERR, "iface %s - get param: ioctl(%d) "
2381 "failed: %s", wif->wname, ireq.i_type,
2383 wif->macsupported = 0;
2386 wif->macsupported = 1;
2387 wif->mac_policy = wlanMACAccessControlPolicy_open;
2393 wif->macsupported = 1;
2396 case IEEE80211_MACCMD_POLICY_ALLOW:
2397 wif->mac_policy = wlanMACAccessControlPolicy_allow;
2399 case IEEE80211_MACCMD_POLICY_DENY:
2400 wif->mac_policy = wlanMACAccessControlPolicy_deny;
2402 case IEEE80211_MACCMD_POLICY_RADIUS:
2403 wif->mac_policy = wlanMACAccessControlPolicy_radius;
2405 case IEEE80211_MACCMD_POLICY_OPEN:
2408 wif->mac_policy = wlanMACAccessControlPolicy_open;
2413 val = IEEE80211_MACCMD_LIST;
2414 if (wlan_ioctl(wif->wname, IEEE80211_IOC_MACCMD, &val, NULL,
2418 wif->mac_nacls = argsize / sizeof(struct ieee80211req_maclist *);
2423 wlan_set_mac_policy(struct wlan_iface *wif)
2428 if (!wif->macsupported)
2431 switch (wif->mac_policy) {
2432 case wlanMACAccessControlPolicy_allow:
2433 val = IEEE80211_MACCMD_POLICY_ALLOW;
2435 case wlanMACAccessControlPolicy_deny:
2436 val = IEEE80211_MACCMD_POLICY_DENY;
2438 case wlanMACAccessControlPolicy_radius:
2439 val = IEEE80211_MACCMD_POLICY_RADIUS;
2441 case wlanMACAccessControlPolicy_open:
2442 val = IEEE80211_MACCMD_POLICY_OPEN;
2448 if (wlan_ioctl(wif->wname, IEEE80211_IOC_MACCMD, &val, NULL,
2456 wlan_flush_mac_mac(struct wlan_iface *wif)
2458 int val = IEEE80211_MACCMD_FLUSH;
2461 if (wlan_ioctl(wif->wname, IEEE80211_IOC_MACCMD, &val, NULL,
2469 wlan_add_mac_macinfo(struct wlan_iface *wif,
2470 const struct ieee80211req_maclist *ml)
2472 struct wlan_mac_mac *mmac;
2474 if ((mmac = wlan_mac_new_mac(ml->ml_macaddr)) == NULL)
2477 mmac->mac_status = RowStatus_active;
2478 if (wlan_mac_add_mac(wif, mmac) < 0) {
2479 wlan_mac_free_mac(mmac);
2487 wlan_get_mac_acl_macs(struct wlan_iface *wif)
2489 int i, nacls, val = IEEE80211_MACCMD_LIST;
2492 struct ieee80211req ireq;
2493 const struct ieee80211req_maclist *acllist;
2495 if (wif->mac_policy == wlanMACAccessControlPolicy_radius) {
2500 memset(&ireq, 0, sizeof(struct ieee80211req));
2501 strlcpy(ireq.i_name, wif->wname, IFNAMSIZ);
2502 ireq.i_type = IEEE80211_IOC_MACCMD;
2503 ireq.i_val = IEEE80211_MACCMD_LIST;
2506 if (ioctl(sock, SIOCG80211, &ireq) < 0) {
2507 if (errno != EINVAL) {
2508 syslog(LOG_ERR, "iface %s - get param: ioctl(%d) "
2509 "failed: %s", wif->wname, ireq.i_type,
2511 wif->macsupported = 0;
2521 if ((data = (uint8_t *)malloc(argsize)) == NULL)
2524 if (wlan_ioctl(wif->wname, IEEE80211_IOC_MACCMD, &val, data,
2528 nacls = argsize / sizeof(*acllist);
2529 acllist = (struct ieee80211req_maclist *) data;
2530 for (i = 0; i < nacls; i++)
2531 (void)wlan_add_mac_macinfo(wif, acllist + i);
2533 wif->mac_nacls = nacls;
2538 wlan_add_mac_acl_mac(struct wlan_iface *wif, struct wlan_mac_mac *mmac)
2541 size_t argsize = IEEE80211_ADDR_LEN;
2542 struct ieee80211req_mlme mlme;
2544 if (wlan_ioctl(wif->wname, IEEE80211_IOC_ADDMAC, &val,
2545 mmac->mac, &argsize, 1) < 0)
2548 mmac->mac_status = RowStatus_active;
2550 /* If policy is deny, try to kick the station just in case. */
2551 if (wif->mac_policy != wlanMACAccessControlPolicy_deny)
2554 memset(&mlme, 0, sizeof(mlme));
2555 mlme.im_op = IEEE80211_MLME_DEAUTH;
2556 mlme.im_reason = IEEE80211_REASON_AUTH_EXPIRE;
2557 memcpy(mlme.im_macaddr, mmac->mac, IEEE80211_ADDR_LEN);
2558 argsize = sizeof(struct ieee80211req_mlme);
2560 if (wlan_ioctl(wif->wname, IEEE80211_IOC_MLME, &val, &mlme,
2561 &argsize, 1) < 0 && errno != ENOENT)
2568 wlan_del_mac_acl_mac(struct wlan_iface *wif, struct wlan_mac_mac *mmac)
2571 size_t argsize = IEEE80211_ADDR_LEN;
2572 struct ieee80211req_mlme mlme;
2574 if (wlan_ioctl(wif->wname, IEEE80211_IOC_DELMAC, &val,
2575 mmac->mac, &argsize, 1) < 0)
2578 mmac->mac_status = RowStatus_active;
2580 /* If policy is allow, try to kick the station just in case. */
2581 if (wif->mac_policy != wlanMACAccessControlPolicy_allow)
2584 memset(&mlme, 0, sizeof(mlme));
2585 mlme.im_op = IEEE80211_MLME_DEAUTH;
2586 mlme.im_reason = IEEE80211_REASON_AUTH_EXPIRE;
2587 memcpy(mlme.im_macaddr, mmac->mac, IEEE80211_ADDR_LEN);
2588 argsize = sizeof(struct ieee80211req_mlme);
2590 if (wlan_ioctl(wif->wname, IEEE80211_IOC_MLME, &val, &mlme,
2591 &argsize, 1) < 0 && errno != ENOENT)
2598 wlan_peer_set_vlan(struct wlan_iface *wif, struct wlan_peer *wip, int vlan)
2602 struct ieee80211req_sta_vlan vreq;
2604 memcpy(vreq.sv_macaddr, wip->pmac, IEEE80211_ADDR_LEN);
2605 vreq.sv_vlan = vlan;
2606 argsize = sizeof(struct ieee80211req_sta_vlan);
2608 if (wlan_ioctl(wif->wname, IEEE80211_IOC_STA_VLAN,
2609 &val, &vreq, &argsize, 1) < 0)
2618 #ifndef IEEE80211_NODE_AUTH
2619 #define IEEE80211_NODE_AUTH 0x000001 /* authorized for data */
2620 #define IEEE80211_NODE_QOS 0x000002 /* QoS enabled */
2621 #define IEEE80211_NODE_ERP 0x000004 /* ERP enabled */
2622 #define IEEE80211_NODE_PWR_MGT 0x000010 /* power save mode enabled */
2623 #define IEEE80211_NODE_AREF 0x000020 /* authentication ref held */
2624 #define IEEE80211_NODE_HT 0x000040 /* HT enabled */
2625 #define IEEE80211_NODE_HTCOMPAT 0x000080 /* HT setup w/ vendor OUI's */
2626 #define IEEE80211_NODE_WPS 0x000100 /* WPS association */
2627 #define IEEE80211_NODE_TSN 0x000200 /* TSN association */
2628 #define IEEE80211_NODE_AMPDU_RX 0x000400 /* AMPDU rx enabled */
2629 #define IEEE80211_NODE_AMPDU_TX 0x000800 /* AMPDU tx enabled */
2630 #define IEEE80211_NODE_MIMO_PS 0x001000 /* MIMO power save enabled */
2631 #define IEEE80211_NODE_MIMO_RTS 0x002000 /* send RTS in MIMO PS */
2632 #define IEEE80211_NODE_RIFS 0x004000 /* RIFS enabled */
2633 #define IEEE80211_NODE_SGI20 0x008000 /* Short GI in HT20 enabled */
2634 #define IEEE80211_NODE_SGI40 0x010000 /* Short GI in HT40 enabled */
2635 #define IEEE80211_NODE_ASSOCID 0x020000 /* xmit requires associd */
2636 #define IEEE80211_NODE_AMSDU_RX 0x040000 /* AMSDU rx enabled */
2637 #define IEEE80211_NODE_AMSDU_TX 0x080000 /* AMSDU tx enabled */
2641 wlan_peerstate_to_snmp(uint32_t pstate)
2643 uint32_t sstate = 0;
2645 if ((pstate & IEEE80211_NODE_AUTH) != 0)
2646 sstate |= (0x1 << WlanIfacePeerFlagsType_authorizedForData);
2647 if ((pstate & IEEE80211_NODE_QOS) != 0)
2648 sstate |= (0x1 << WlanIfacePeerFlagsType_qosEnabled);
2649 if ((pstate & IEEE80211_NODE_ERP) != 0)
2650 sstate |= (0x1 << WlanIfacePeerFlagsType_erpEnabled);
2651 if ((pstate & IEEE80211_NODE_PWR_MGT) != 0)
2652 sstate |= (0x1 << WlanIfacePeerFlagsType_powerSaveMode);
2653 if ((pstate & IEEE80211_NODE_AREF) != 0)
2654 sstate |= (0x1 << WlanIfacePeerFlagsType_authRefHeld);
2655 if ((pstate & IEEE80211_NODE_HT) != 0)
2656 sstate |= (0x1 << WlanIfacePeerFlagsType_htEnabled);
2657 if ((pstate & IEEE80211_NODE_HTCOMPAT) != 0)
2658 sstate |= (0x1 << WlanIfacePeerFlagsType_htCompat);
2659 if ((pstate & IEEE80211_NODE_WPS) != 0)
2660 sstate |= (0x1 << WlanIfacePeerFlagsType_wpsAssoc);
2661 if ((pstate & IEEE80211_NODE_TSN) != 0)
2662 sstate |= (0x1 << WlanIfacePeerFlagsType_tsnAssoc);
2663 if ((pstate & IEEE80211_NODE_AMPDU_RX) != 0)
2664 sstate |= (0x1 << WlanIfacePeerFlagsType_ampduRx);
2665 if ((pstate & IEEE80211_NODE_AMPDU_TX) != 0)
2666 sstate |= (0x1 << WlanIfacePeerFlagsType_ampduTx);
2667 if ((pstate & IEEE80211_NODE_MIMO_PS) != 0)
2668 sstate |= (0x1 << WlanIfacePeerFlagsType_mimoPowerSave);
2669 if ((pstate & IEEE80211_NODE_MIMO_RTS) != 0)
2670 sstate |= (0x1 << WlanIfacePeerFlagsType_sendRts);
2671 if ((pstate & IEEE80211_NODE_RIFS) != 0)
2672 sstate |= (0x1 << WlanIfacePeerFlagsType_rifs);
2673 if ((pstate & IEEE80211_NODE_SGI20) != 0)
2674 sstate |= (0x1 << WlanIfacePeerFlagsType_shortGiHT20);
2675 if ((pstate & IEEE80211_NODE_SGI40) != 0)
2676 sstate |= (0x1 << WlanIfacePeerFlagsType_shortGiHT40);
2677 if ((pstate & IEEE80211_NODE_AMSDU_RX) != 0)
2678 sstate |= (0x1 << WlanIfacePeerFlagsType_amsduRx);
2679 if ((pstate & IEEE80211_NODE_AMSDU_TX) != 0)
2680 sstate |= (0x1 << WlanIfacePeerFlagsType_amsduTx);
2685 static struct wlan_peer *
2686 wlan_add_peerinfo(const struct ieee80211req_sta_info *si)
2688 struct wlan_peer *wip;
2690 if ((wip = wlan_new_peer(si->isi_macaddr))== NULL)
2693 wip->associd = IEEE80211_AID(si->isi_associd);
2694 wip->vlan = si->isi_vlan;
2695 wip->frequency = si->isi_freq;
2696 wip->fflags = si->isi_flags;
2697 wip->txrate = si->isi_txrate;
2698 wip->rssi = si->isi_rssi;
2699 wip->idle = si->isi_inact;
2700 wip->txseqs = si->isi_txseqs[0]; /* XXX */
2701 wip->rxseqs = si->isi_rxseqs[0]; /* XXX */
2702 wip->txpower = si->isi_txpower;
2703 wip->capinfo = wlan_peercaps_to_snmp(si->isi_capinfo);
2704 wip->state = wlan_peerstate_to_snmp(si->isi_state);
2705 wip->local_id = si->isi_localid;
2706 wip->peer_id = si->isi_peerid;
2712 wlan_get_peerinfo(struct wlan_iface *wif)
2715 struct ieee80211req_sta_req req;
2716 uint8_t buf[24 * 1024];
2721 struct ieee80211req_sta_info si;
2722 struct wlan_peer *wip;
2724 /* Get all stations - broadcast address */
2725 (void) memset(u.req.is_u.macaddr, 0xff, IEEE80211_ADDR_LEN);
2728 if (wlan_ioctl(wif->wname, IEEE80211_IOC_STA_INFO,
2729 & val, &u, &len, 0) < 0)
2732 if (len < sizeof(struct ieee80211req_sta_info))
2735 cp = (const uint8_t *) u.req.info;
2737 memcpy(&si, cp, sizeof(struct ieee80211req_sta_info));
2738 if ((wip = wlan_add_peerinfo(&si)) != NULL &&
2739 wlan_add_peer(wif, wip) < 0)
2740 wlan_free_peer(wip);
2741 cp += si.isi_len, len -= si.isi_len;
2742 } while (len >= sizeof(struct ieee80211req_sta_info));
2747 /************************************************************************
2748 * Wireless MESH & HWMP sysctl config.
2750 const char wlan_sysctl_name[] = "net.wlan.";
2752 static const char *wlan_sysctl[] = {
2753 "mesh.retrytimeout",
2754 "mesh.holdingtimeout",
2755 "mesh.confirmtimeout",
2758 "hwmp.replyforward",
2759 "hwmp.pathlifetime",
2767 wlan_do_sysctl(struct wlan_config *cfg, enum wlan_syscl which, int set)
2774 vlen = sizeof(sval);
2776 case WLAN_MESH_RETRY_TO:
2777 sval = cfg->mesh_retryto;
2779 case WLAN_MESH_HOLDING_TO:
2780 sval = cfg->mesh_holdingto;
2782 case WLAN_MESH_CONFIRM_TO:
2783 sval = cfg->mesh_confirmto;
2785 case WLAN_MESH_MAX_RETRIES:
2786 sval = cfg->mesh_maxretries;
2788 case WLAN_HWMP_TARGET_ONLY:
2789 sval = cfg->hwmp_targetonly;
2791 case WLAN_HWMP_REPLY_FORWARD:
2792 sval = cfg->hwmp_replyforward;
2794 case WLAN_HWMP_PATH_LIFETIME:
2795 sval = cfg->hwmp_pathlifetime;
2797 case WLAN_HWMP_ROOT_TO:
2798 sval = cfg->hwmp_roottimeout;
2800 case WLAN_HWMP_ROOT_INT:
2801 sval = cfg->hwmp_rootint;
2803 case WLAN_HWMP_RANN_INT:
2804 sval = cfg->hwmp_rannint;
2806 case WLAN_HWMP_INACTIVITY_TO:
2807 sval = cfg->hwmp_inact;
2813 if (which >= WLAN_SYSCTL_MAX)
2818 strlcpy(mib_name, wlan_sysctl_name, sizeof(mib_name));
2819 strlcat(mib_name, wlan_sysctl[which], sizeof(mib_name));
2822 if (sysctlbyname(mib_name, &val, &len, (set? &sval : NULL), vlen) < 0) {
2823 syslog(LOG_ERR, "sysctl(%s) failed - %s", mib_name,
2829 case WLAN_MESH_RETRY_TO:
2830 cfg->mesh_retryto = val;
2832 case WLAN_MESH_HOLDING_TO:
2833 cfg->mesh_holdingto = val;
2835 case WLAN_MESH_CONFIRM_TO:
2836 cfg->mesh_confirmto = val;
2838 case WLAN_MESH_MAX_RETRIES:
2839 cfg->mesh_maxretries = val;
2841 case WLAN_HWMP_TARGET_ONLY:
2842 cfg->hwmp_targetonly = val;
2844 case WLAN_HWMP_REPLY_FORWARD:
2845 cfg->hwmp_replyforward = val;
2847 case WLAN_HWMP_PATH_LIFETIME:
2848 cfg->hwmp_pathlifetime = val;
2850 case WLAN_HWMP_ROOT_TO:
2851 cfg->hwmp_roottimeout = val;
2853 case WLAN_HWMP_ROOT_INT:
2854 cfg->hwmp_rootint = val;
2856 case WLAN_HWMP_RANN_INT:
2857 cfg->hwmp_rannint = val;
2859 case WLAN_HWMP_INACTIVITY_TO:
2860 cfg->hwmp_inact = val;
2871 wlan_mesh_config_get(struct wlan_iface *wif, int which)
2875 uint8_t data[32], *pd = NULL;
2878 case LEAF_wlanMeshTTL:
2879 op = IEEE80211_IOC_MESH_TTL;
2881 case LEAF_wlanMeshPeeringEnabled:
2882 op = IEEE80211_IOC_MESH_AP;
2884 case LEAF_wlanMeshForwardingEnabled:
2885 op = IEEE80211_IOC_MESH_FWRD;
2887 case LEAF_wlanMeshMetric:
2888 op = IEEE80211_IOC_MESH_PR_METRIC;
2890 argsize = sizeof(data);
2892 case LEAF_wlanMeshPath:
2893 op = IEEE80211_IOC_MESH_PR_PATH;
2895 argsize = sizeof(data);
2897 case LEAF_wlanMeshRoutesFlush:
2903 if (wlan_ioctl(wif->wname, op, &val, pd, &argsize, 0) < 0)
2907 case LEAF_wlanMeshTTL:
2908 wif->mesh_ttl = val;
2910 case LEAF_wlanMeshPeeringEnabled:
2912 wif->mesh_peering = wlanMeshPeeringEnabled_true;
2914 wif->mesh_peering = wlanMeshPeeringEnabled_false;
2916 case LEAF_wlanMeshForwardingEnabled:
2918 wif->mesh_forwarding = wlanMeshForwardingEnabled_true;
2920 wif->mesh_forwarding = wlanMeshForwardingEnabled_false;
2922 case LEAF_wlanMeshMetric:
2923 data[argsize] = '\0';
2924 if (strcmp(data, "AIRTIME") == 0)
2925 wif->mesh_metric = wlanMeshMetric_airtime;
2927 wif->mesh_metric = wlanMeshMetric_unknown;
2929 case LEAF_wlanMeshPath:
2930 data[argsize] = '\0';
2931 if (strcmp(data, "HWMP") == 0)
2932 wif->mesh_path = wlanMeshPath_hwmp;
2934 wif->mesh_path = wlanMeshPath_unknown;
2941 wlan_mesh_config_set(struct wlan_iface *wif, int which)
2945 uint8_t data[32], *pd = NULL;
2948 case LEAF_wlanMeshTTL:
2949 op = IEEE80211_IOC_MESH_TTL;
2950 val = wif->mesh_ttl;
2952 case LEAF_wlanMeshPeeringEnabled:
2953 op = IEEE80211_IOC_MESH_AP;
2954 if (wif->mesh_peering == wlanMeshPeeringEnabled_true)
2957 case LEAF_wlanMeshForwardingEnabled:
2958 if (wif->mesh_forwarding == wlanMeshForwardingEnabled_true)
2960 op = IEEE80211_IOC_MESH_FWRD;
2962 case LEAF_wlanMeshMetric:
2963 op = IEEE80211_IOC_MESH_PR_METRIC;
2964 if (wif->mesh_metric == wlanMeshMetric_airtime)
2965 strcpy(data, "AIRTIME");
2969 argsize = sizeof(data);
2971 case LEAF_wlanMeshPath:
2972 op = IEEE80211_IOC_MESH_PR_PATH;
2973 if (wif->mesh_path == wlanMeshPath_hwmp)
2974 strcpy(data, "HWMP");
2978 argsize = sizeof(data);
2984 if (wlan_ioctl(wif->wname, op, &val, pd, &argsize, 1) < 0)
2991 wlan_mesh_flush_routes(struct wlan_iface *wif)
2993 int val = IEEE80211_MESH_RTCMD_FLUSH;
2996 if (wlan_ioctl(wif->wname, IEEE80211_IOC_MESH_RTCMD, &val, NULL,
3004 wlan_mesh_add_route(struct wlan_iface *wif, struct wlan_mesh_route *wmr)
3006 int val = IEEE80211_MESH_RTCMD_ADD;
3007 size_t argsize = IEEE80211_ADDR_LEN;
3009 if (wlan_ioctl(wif->wname, IEEE80211_IOC_MESH_RTCMD, &val,
3010 wmr->imroute.imr_dest, &argsize, 1) < 0)
3013 wmr->mroute_status = RowStatus_active;
3019 wlan_mesh_del_route(struct wlan_iface *wif, struct wlan_mesh_route *wmr)
3021 int val = IEEE80211_MESH_RTCMD_DELETE;
3022 size_t argsize = IEEE80211_ADDR_LEN;
3024 if (wlan_ioctl(wif->wname, IEEE80211_IOC_MESH_RTCMD, &val,
3025 wmr->imroute.imr_dest, &argsize, 1) < 0)
3028 wmr->mroute_status = RowStatus_destroy;
3034 wlan_mesh_get_routelist(struct wlan_iface *wif)
3036 int i, nroutes, val = IEEE80211_MESH_RTCMD_LIST;
3038 struct ieee80211req_mesh_route routes[128];
3039 struct ieee80211req_mesh_route *rt;
3040 struct wlan_mesh_route *wmr;
3042 argsize = sizeof(routes);
3043 if (wlan_ioctl(wif->wname, IEEE80211_IOC_MESH_RTCMD, &val, routes,
3044 &argsize, 0) < 0) /* XXX: ENOMEM? */
3047 nroutes = argsize / sizeof(*rt);
3048 for (i = 0; i < nroutes; i++) {
3050 if ((wmr = wlan_mesh_new_route(rt->imr_dest)) == NULL)
3052 memcpy(&wmr->imroute, rt, sizeof(*rt));
3053 wmr->mroute_status = RowStatus_active;
3054 if (wlan_mesh_add_rtentry(wif, wmr) < 0)
3055 wlan_mesh_free_route(wmr);
3062 wlan_hwmp_config_get(struct wlan_iface *wif, int which)
3068 case LEAF_wlanHWMPRootMode:
3069 op = IEEE80211_IOC_HWMP_ROOTMODE;
3071 case LEAF_wlanHWMPMaxHops:
3072 op = IEEE80211_IOC_HWMP_MAXHOPS;
3078 if (wlan_ioctl(wif->wname, op, &val, NULL, &argsize, 0) < 0)
3082 case LEAF_wlanHWMPRootMode:
3084 case IEEE80211_HWMP_ROOTMODE_NORMAL:
3085 wif->hwmp_root_mode = wlanHWMPRootMode_normal;
3087 case IEEE80211_HWMP_ROOTMODE_PROACTIVE:
3088 wif->hwmp_root_mode = wlanHWMPRootMode_proactive;
3090 case IEEE80211_HWMP_ROOTMODE_RANN:
3091 wif->hwmp_root_mode = wlanHWMPRootMode_rann;
3093 case IEEE80211_HWMP_ROOTMODE_DISABLED:
3095 wif->hwmp_root_mode = wlanHWMPRootMode_disabled;
3099 case LEAF_wlanHWMPMaxHops:
3100 wif->hwmp_max_hops = val;
3108 wlan_hwmp_config_set(struct wlan_iface *wif, int which)
3114 case LEAF_wlanHWMPRootMode:
3115 op = IEEE80211_IOC_HWMP_ROOTMODE;
3116 switch (wif->hwmp_root_mode) {
3117 case wlanHWMPRootMode_disabled:
3118 val = IEEE80211_HWMP_ROOTMODE_DISABLED;
3120 case wlanHWMPRootMode_normal:
3121 val = IEEE80211_HWMP_ROOTMODE_NORMAL;
3123 case wlanHWMPRootMode_proactive:
3124 val = IEEE80211_HWMP_ROOTMODE_PROACTIVE;
3126 case wlanHWMPRootMode_rann:
3127 val = IEEE80211_HWMP_ROOTMODE_RANN;
3133 case LEAF_wlanHWMPMaxHops:
3134 op = IEEE80211_IOC_HWMP_MAXHOPS;
3135 val = wif->hwmp_max_hops;
3141 if (wlan_ioctl(wif->wname, op, &val, NULL, &argsize, 1) < 0)