First pass at converting the net80211 infrastrcture from FreeBSD.
authorRui Paulo <rpaulo@FreeBSD.org>
Thu, 18 Feb 2010 14:42:11 +0000 (14:42 +0000)
committerRui Paulo <rpaulo@FreeBSD.org>
Thu, 18 Feb 2010 14:42:11 +0000 (14:42 +0000)
68 files changed:
sys/netproto/802_11/ieee80211_action.h [new file with mode: 0644]
sys/netproto/802_11/ieee80211_adhoc.h [new file with mode: 0644]
sys/netproto/802_11/ieee80211_ageq.h [new file with mode: 0644]
sys/netproto/802_11/ieee80211_crypto.h
sys/netproto/802_11/ieee80211_dfs.h [new file with mode: 0644]
sys/netproto/802_11/ieee80211_dragonfly.h
sys/netproto/802_11/ieee80211_hostap.h [new file with mode: 0644]
sys/netproto/802_11/ieee80211_ht.h [new file with mode: 0644]
sys/netproto/802_11/ieee80211_input.h [new file with mode: 0644]
sys/netproto/802_11/ieee80211_ioctl.h
sys/netproto/802_11/ieee80211_mesh.h [new file with mode: 0644]
sys/netproto/802_11/ieee80211_monitor.h [new file with mode: 0644]
sys/netproto/802_11/ieee80211_node.h
sys/netproto/802_11/ieee80211_phy.h [new file with mode: 0644]
sys/netproto/802_11/ieee80211_power.h [new file with mode: 0644]
sys/netproto/802_11/ieee80211_proto.h
sys/netproto/802_11/ieee80211_radiotap.h
sys/netproto/802_11/ieee80211_regdomain.h [new file with mode: 0644]
sys/netproto/802_11/ieee80211_rssadapt.h [new file with mode: 0644]
sys/netproto/802_11/ieee80211_scan.h [new file with mode: 0644]
sys/netproto/802_11/ieee80211_sta.h [new file with mode: 0644]
sys/netproto/802_11/ieee80211_superg.h [new file with mode: 0644]
sys/netproto/802_11/ieee80211_tdma.h [new file with mode: 0644]
sys/netproto/802_11/ieee80211_var.h
sys/netproto/802_11/ieee80211_wds.h [new file with mode: 0644]
sys/netproto/802_11/if_wavelan_ieee.h [deleted file]
sys/netproto/802_11/wlan/Makefile
sys/netproto/802_11/wlan/ieee80211.c
sys/netproto/802_11/wlan/ieee80211_action.c [new file with mode: 0644]
sys/netproto/802_11/wlan/ieee80211_adhoc.c [new file with mode: 0644]
sys/netproto/802_11/wlan/ieee80211_ageq.c [new file with mode: 0644]
sys/netproto/802_11/wlan/ieee80211_crypto.c
sys/netproto/802_11/wlan/ieee80211_crypto_none.c
sys/netproto/802_11/wlan/ieee80211_ddb.c [new file with mode: 0644]
sys/netproto/802_11/wlan/ieee80211_dfs.c [new file with mode: 0644]
sys/netproto/802_11/wlan/ieee80211_dragonfly.c
sys/netproto/802_11/wlan/ieee80211_hostap.c [new file with mode: 0644]
sys/netproto/802_11/wlan/ieee80211_ht.c [new file with mode: 0644]
sys/netproto/802_11/wlan/ieee80211_hwmp.c [new file with mode: 0644]
sys/netproto/802_11/wlan/ieee80211_input.c
sys/netproto/802_11/wlan/ieee80211_ioctl.c
sys/netproto/802_11/wlan/ieee80211_mesh.c [new file with mode: 0644]
sys/netproto/802_11/wlan/ieee80211_monitor.c [new file with mode: 0644]
sys/netproto/802_11/wlan/ieee80211_node.c
sys/netproto/802_11/wlan/ieee80211_output.c
sys/netproto/802_11/wlan/ieee80211_phy.c [new file with mode: 0644]
sys/netproto/802_11/wlan/ieee80211_power.c [new file with mode: 0644]
sys/netproto/802_11/wlan/ieee80211_proto.c
sys/netproto/802_11/wlan/ieee80211_radiotap.c [new file with mode: 0644]
sys/netproto/802_11/wlan/ieee80211_ratectl.c
sys/netproto/802_11/wlan/ieee80211_regdomain.c [new file with mode: 0644]
sys/netproto/802_11/wlan/ieee80211_rssadapt.c [new file with mode: 0644]
sys/netproto/802_11/wlan/ieee80211_scan.c [new file with mode: 0644]
sys/netproto/802_11/wlan/ieee80211_scan_sta.c [new file with mode: 0644]
sys/netproto/802_11/wlan/ieee80211_sta.c [new file with mode: 0644]
sys/netproto/802_11/wlan/ieee80211_superg.c [new file with mode: 0644]
sys/netproto/802_11/wlan/ieee80211_tdma.c [new file with mode: 0644]
sys/netproto/802_11/wlan/ieee80211_wds.c [new file with mode: 0644]
sys/netproto/802_11/wlan_acl/Makefile
sys/netproto/802_11/wlan_acl/ieee80211_acl.c
sys/netproto/802_11/wlan_ccmp/Makefile
sys/netproto/802_11/wlan_ccmp/ieee80211_crypto_ccmp.c
sys/netproto/802_11/wlan_tkip/Makefile
sys/netproto/802_11/wlan_tkip/ieee80211_crypto_tkip.c
sys/netproto/802_11/wlan_wep/Makefile
sys/netproto/802_11/wlan_wep/ieee80211_crypto_wep.c
sys/netproto/802_11/wlan_xauth/Makefile
sys/netproto/802_11/wlan_xauth/ieee80211_xauth.c

diff --git a/sys/netproto/802_11/ieee80211_action.h b/sys/netproto/802_11/ieee80211_action.h
new file mode 100644 (file)
index 0000000..484fe9a
--- /dev/null
@@ -0,0 +1,53 @@
+/*-
+ * Copyright (c) 2009 Sam Leffler, Errno Consulting
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
+ * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
+ * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
+ * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
+ * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
+ * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
+ * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
+ * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ *
+ * $FreeBSD: head/sys/net80211/ieee80211_action.h 195377 2009-07-05 17:59:19Z sam $
+ * $DragonFly$
+ */
+#ifndef _NET80211_IEEE80211_ACTION_H_
+#define _NET80211_IEEE80211_ACTION_H_
+
+/*
+ * 802.11 send/recv action frame support.
+ */
+
+struct ieee80211_node;
+struct ieee80211_frame;
+
+typedef int ieee80211_send_action_func(struct ieee80211_node *,
+    int, int, void *);
+int    ieee80211_send_action_register(int cat, int act,
+               ieee80211_send_action_func *f);
+void   ieee80211_send_action_unregister(int cat, int act);
+int    ieee80211_send_action(struct ieee80211_node *, int, int, void *);
+
+typedef int ieee80211_recv_action_func(struct ieee80211_node *,
+    const struct ieee80211_frame *, const uint8_t *, const uint8_t *);
+int    ieee80211_recv_action_register(int cat, int act,
+               ieee80211_recv_action_func *);
+void   ieee80211_recv_action_unregister(int cat, int act);
+int    ieee80211_recv_action(struct ieee80211_node *,
+               const struct ieee80211_frame *,
+               const uint8_t *, const uint8_t *);
+#endif /* _NET80211_IEEE80211_ACTION_H_ */
diff --git a/sys/netproto/802_11/ieee80211_adhoc.h b/sys/netproto/802_11/ieee80211_adhoc.h
new file mode 100644 (file)
index 0000000..2720ca0
--- /dev/null
@@ -0,0 +1,36 @@
+/*-
+ * Copyright (c) 2007-2008 Sam Leffler, Errno Consulting
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
+ * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
+ * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
+ * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
+ * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
+ * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
+ * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
+ * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ *
+ * $FreeBSD: head/sys/net80211/ieee80211_adhoc.h 178354 2008-04-20 20:35:46Z sam $
+ * $DragonFly$
+ */
+#ifndef _NET80211_IEEE80211_ADHOC_H_
+#define _NET80211_IEEE80211_ADHOC_H_
+
+/*
+ * Adhoc-mode (ibss+ahdemo) implementation definitions.
+ */
+void   ieee80211_adhoc_attach(struct ieee80211com *);
+void   ieee80211_adhoc_detach(struct ieee80211com *);
+#endif /* !_NET80211_IEEE80211_STA_H_ */
diff --git a/sys/netproto/802_11/ieee80211_ageq.h b/sys/netproto/802_11/ieee80211_ageq.h
new file mode 100644 (file)
index 0000000..3d95e90
--- /dev/null
@@ -0,0 +1,55 @@
+/*-
+ * Copyright (c) 2009 Sam Leffler, Errno Consulting
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
+ * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
+ * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
+ * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
+ * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
+ * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
+ * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
+ * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ *
+ * $FreeBSD: head/sys/net80211/ieee80211_ageq.h 195379 2009-07-05 18:17:37Z sam $
+ * $DragonFly$
+ */
+#ifndef _NET80211_IEEE80211_STAGEQ_H_
+#define _NET80211_IEEE80211_STAGEQ_H_
+
+struct ieee80211_node;
+struct mbuf;
+
+struct ieee80211_ageq {
+       ieee80211_ageq_lock_t   aq_lock;
+       int                     aq_len;         /* # items on queue */
+       int                     aq_maxlen;      /* max queue length */
+       int                     aq_drops;       /* frames dropped */
+       struct mbuf             *aq_head;       /* frames linked w/ m_nextpkt */
+       struct mbuf             *aq_tail;       /* last frame in queue */
+};
+
+void   ieee80211_ageq_init(struct ieee80211_ageq *, int maxlen,
+           const char *name);
+void   ieee80211_ageq_cleanup(struct ieee80211_ageq *);
+void   ieee80211_ageq_mfree(struct mbuf *);
+int    ieee80211_ageq_append(struct ieee80211_ageq *, struct mbuf *,
+           int age);
+void   ieee80211_ageq_drain(struct ieee80211_ageq *);
+void   ieee80211_ageq_drain_node(struct ieee80211_ageq *,
+           struct ieee80211_node *);
+struct mbuf *ieee80211_ageq_age(struct ieee80211_ageq *, int quanta);
+struct mbuf *ieee80211_ageq_remove(struct ieee80211_ageq *,
+           struct ieee80211_node *match);
+#endif /* _NET80211_IEEE80211_STAGEQ_H_ */
index f745b7f..727d2e1 100644 (file)
@@ -1,6 +1,6 @@
-/*
+/*-
  * Copyright (c) 2001 Atsushi Onoe
- * Copyright (c) 2002-2005 Sam Leffler, Errno Consulting
+ * Copyright (c) 2002-2008 Sam Leffler, Errno Consulting
  * All rights reserved.
  *
  * Redistribution and use in source and binary forms, with or without
  * 2. Redistributions in binary form must reproduce the above copyright
  *    notice, this list of conditions and the following disclaimer in the
  *    documentation and/or other materials provided with the distribution.
- * 3. The name of the author may not be used to endorse or promote products
- *    derived from this software without specific prior written permission.
- *
- * Alternatively, this software may be distributed under the terms of the
- * GNU General Public License ("GPL") version 2 as published by the Free
- * Software Foundation.
  *
  * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
  * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
@@ -29,8 +23,8 @@
  * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
  * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
  *
- * $FreeBSD: src/sys/net80211/ieee80211_crypto.h,v 1.9.2.1 2005/09/03 22:40:02 sam Exp $
- * $DragonFly: src/sys/netproto/802_11/ieee80211_crypto.h,v 1.4 2007/05/07 14:12:16 sephe Exp $
+ * $FreeBSD: head/sys/net80211/ieee80211_crypto.h 195812 2009-07-21 19:36:32Z sam $
+ * $DragonFly$
  */
 #ifndef _NET80211_IEEE80211_CRYPTO_H_
 #define _NET80211_IEEE80211_CRYPTO_H_
@@ -49,6 +43,15 @@ struct ieee80211_wepkey {
        uint8_t         wk_key[IEEE80211_KEYBUF_SIZE];
 };
 
+struct ieee80211_rsnparms {
+       uint8_t         rsn_mcastcipher;        /* mcast/group cipher */
+       uint8_t         rsn_mcastkeylen;        /* mcast key length */
+       uint8_t         rsn_ucastcipher;        /* selected unicast cipher */
+       uint8_t         rsn_ucastkeylen;        /* unicast key length */
+       uint8_t         rsn_keymgmt;            /* selected key mgmt algo */
+       uint16_t        rsn_caps;               /* capabilities */
+};
+
 struct ieee80211_cipher;
 
 /*
@@ -71,92 +74,93 @@ typedef uint16_t ieee80211_keyix;   /* h/w key index */
 
 struct ieee80211_key {
        uint8_t         wk_keylen;      /* key length in bytes */
-       uint8_t         wk_keyid;       /* key id */
+       uint8_t         wk_pad;
        uint16_t        wk_flags;
-#define        IEEE80211_KEY_XMIT      0x01    /* key used for xmit */
-#define        IEEE80211_KEY_RECV      0x02    /* key used for recv */
-#define        IEEE80211_KEY_GROUP     0x04    /* key used for WPA group operation */
-#define        IEEE80211_KEY_SWCRYPT   0x10    /* host-based encrypt/decrypt */
-#define        IEEE80211_KEY_SWMIC     0x20    /* host-based enmic/demic */
-#define IEEE80211_KEY_NOHDR    0x40    /* driver appends crypto header */
-#define IEEE80211_KEY_NOMIC    0x80    /* driver strips TKIP MIC */
+#define        IEEE80211_KEY_XMIT      0x0001  /* key used for xmit */
+#define        IEEE80211_KEY_RECV      0x0002  /* key used for recv */
+#define        IEEE80211_KEY_GROUP     0x0004  /* key used for WPA group operation */
+#define        IEEE80211_KEY_SWENCRYPT 0x0010  /* host-based encrypt */
+#define        IEEE80211_KEY_SWDECRYPT 0x0020  /* host-based decrypt */
+#define        IEEE80211_KEY_SWENMIC   0x0040  /* host-based enmic */
+#define        IEEE80211_KEY_SWDEMIC   0x0080  /* host-based demic */
+#define        IEEE80211_KEY_DEVKEY    0x0100  /* device key request completed */
+#define        IEEE80211_KEY_CIPHER0   0x1000  /* cipher-specific action 0 */
+#define        IEEE80211_KEY_CIPHER1   0x2000  /* cipher-specific action 1 */
        ieee80211_keyix wk_keyix;       /* h/w key index */
        ieee80211_keyix wk_rxkeyix;     /* optional h/w rx key index */
        uint8_t         wk_key[IEEE80211_KEYBUF_SIZE+IEEE80211_MICBUF_SIZE];
 #define        wk_txmic        wk_key+IEEE80211_KEYBUF_SIZE+0  /* XXX can't () right */
 #define        wk_rxmic        wk_key+IEEE80211_KEYBUF_SIZE+8  /* XXX can't () right */
-       uint64_t        wk_keyrsc;      /* key receive sequence counter */
+                                       /* key receive sequence counter */
+       uint64_t        wk_keyrsc[IEEE80211_TID_SIZE];
        uint64_t        wk_keytsc;      /* key transmit sequence counter */
        const struct ieee80211_cipher *wk_cipher;
        void            *wk_private;    /* private cipher state */
+       uint8_t         wk_macaddr[IEEE80211_ADDR_LEN];
 };
 #define        IEEE80211_KEY_COMMON            /* common flags passed in by apps */\
        (IEEE80211_KEY_XMIT | IEEE80211_KEY_RECV | IEEE80211_KEY_GROUP)
+#define        IEEE80211_KEY_DEVICE            /* flags owned by device driver */\
+       (IEEE80211_KEY_DEVKEY|IEEE80211_KEY_CIPHER0|IEEE80211_KEY_CIPHER1)
+
+#define        IEEE80211_KEY_SWCRYPT \
+       (IEEE80211_KEY_SWENCRYPT | IEEE80211_KEY_SWDECRYPT)
+#define        IEEE80211_KEY_SWMIC     (IEEE80211_KEY_SWENMIC | IEEE80211_KEY_SWDEMIC)
+
+#define        IEEE80211_KEY_BITS \
+       "\20\1XMIT\2RECV\3GROUP\4SWENCRYPT\5SWDECRYPT\6SWENMIC\7SWDEMIC" \
+       "\10DEVKEY\11CIPHER0\12CIPHER1"
+
+#define        IEEE80211_KEYIX_NONE    ((ieee80211_keyix) -1)
 
 /*
  * NB: these values are ordered carefully; there are lots of
- * of implications in any reordering.  In particular beware
- * that 4 is not used to avoid conflicting with IEEE80211_F_PRIVACY.
+ * of implications in any reordering.  Beware that 4 is used
+ * only to indicate h/w TKIP MIC support in driver capabilities;
+ * there is no separate cipher support (it's rolled into the
+ * TKIP cipher support).
  */
 #define        IEEE80211_CIPHER_WEP            0
 #define        IEEE80211_CIPHER_TKIP           1
 #define        IEEE80211_CIPHER_AES_OCB        2
 #define        IEEE80211_CIPHER_AES_CCM        3
+#define        IEEE80211_CIPHER_TKIPMIC        4       /* TKIP MIC capability */
 #define        IEEE80211_CIPHER_CKIP           5
 #define        IEEE80211_CIPHER_NONE           6       /* pseudo value */
 
 #define        IEEE80211_CIPHER_MAX            (IEEE80211_CIPHER_NONE+1)
 
-#define        IEEE80211_KEYIX_NONE    ((ieee80211_keyix) -1)
+/* capability bits in ic_cryptocaps/iv_cryptocaps */
+#define        IEEE80211_CRYPTO_WEP            (1<<IEEE80211_CIPHER_WEP)
+#define        IEEE80211_CRYPTO_TKIP           (1<<IEEE80211_CIPHER_TKIP)
+#define        IEEE80211_CRYPTO_AES_OCB        (1<<IEEE80211_CIPHER_AES_OCB)
+#define        IEEE80211_CRYPTO_AES_CCM        (1<<IEEE80211_CIPHER_AES_CCM)
+#define        IEEE80211_CRYPTO_TKIPMIC        (1<<IEEE80211_CIPHER_TKIPMIC)
+#define        IEEE80211_CRYPTO_CKIP           (1<<IEEE80211_CIPHER_CKIP)
+
+#define        IEEE80211_CRYPTO_BITS \
+       "\20\1WEP\2TKIP\3AES\4AES_CCM\5TKIPMIC\6CKIP"
 
 #if defined(__KERNEL__) || defined(_KERNEL)
 
 struct ieee80211com;
+struct ieee80211vap;
 struct ieee80211_node;
 struct mbuf;
 
-/*
- * Crypto state kept in each ieee80211com.  Some of this
- * can/should be shared when virtual AP's are supported.
- *
- * XXX save reference to ieee80211com to properly encapsulate state.
- * XXX split out crypto capabilities from ic_caps
- */
-struct ieee80211_crypto_state {
-       struct ieee80211_key    cs_nw_keys[IEEE80211_WEP_NKID];
-       ieee80211_keyix         cs_def_txkey;   /* default/group tx key index */
-       uint16_t                cs_max_keyix;   /* max h/w key index */
-
-       int                     (*cs_key_alloc)(struct ieee80211com *,
-                                       const struct ieee80211_key *,
-                                       ieee80211_keyix *, ieee80211_keyix *);
-       int                     (*cs_key_delete)(struct ieee80211com *, 
-                                       const struct ieee80211_key *);
-       int                     (*cs_key_set)(struct ieee80211com *,
-                                       const struct ieee80211_key *,
-                                       const uint8_t mac[IEEE80211_ADDR_LEN]);
-       void                    (*cs_key_update_begin)(struct ieee80211com *);
-       void                    (*cs_key_update_end)(struct ieee80211com *);
-};
+MALLOC_DECLARE(M_80211_CRYPTO);
 
 void   ieee80211_crypto_attach(struct ieee80211com *);
 void   ieee80211_crypto_detach(struct ieee80211com *);
-int    ieee80211_crypto_newkey(struct ieee80211com *,
+void   ieee80211_crypto_vattach(struct ieee80211vap *);
+void   ieee80211_crypto_vdetach(struct ieee80211vap *);
+int    ieee80211_crypto_newkey(struct ieee80211vap *,
                int cipher, int flags, struct ieee80211_key *);
-int    ieee80211_crypto_delkey(struct ieee80211com *,
+int    ieee80211_crypto_delkey(struct ieee80211vap *,
                struct ieee80211_key *);
-int    ieee80211_crypto_setkey(struct ieee80211com *,
-               struct ieee80211_key *, const uint8_t macaddr[IEEE80211_ADDR_LEN]);
-void   ieee80211_crypto_delglobalkeys(struct ieee80211com *);
-
-struct ieee80211_crypto_iv {
-       /*
-        * Keep this layout!
-        * Crypto modules will assume that ic_iv and ic_eiv are contiguous.
-        */
-       uint8_t ic_iv[4];
-       uint8_t ic_eiv[4];
-};
+int    ieee80211_crypto_setkey(struct ieee80211vap *, struct ieee80211_key *);
+void   ieee80211_crypto_delglobalkeys(struct ieee80211vap *);
+void   ieee80211_crypto_reload_keys(struct ieee80211com *);
 
 /*
  * Template for a supported cipher.  Ciphers register with the
@@ -170,7 +174,7 @@ struct ieee80211_cipher {
        u_int   ic_header;              /* size of privacy header (bytes) */
        u_int   ic_trailer;             /* size of privacy trailer (bytes) */
        u_int   ic_miclen;              /* size of mic trailer (bytes) */
-       void*   (*ic_attach)(struct ieee80211com *, struct ieee80211_key *);
+       void*   (*ic_attach)(struct ieee80211vap *, struct ieee80211_key *);
        void    (*ic_detach)(struct ieee80211_key *);
        int     (*ic_setkey)(struct ieee80211_key *);
        int     (*ic_encap)(struct ieee80211_key *, struct mbuf *,
@@ -178,42 +182,26 @@ struct ieee80211_cipher {
        int     (*ic_decap)(struct ieee80211_key *, struct mbuf *, int);
        int     (*ic_enmic)(struct ieee80211_key *, struct mbuf *, int);
        int     (*ic_demic)(struct ieee80211_key *, struct mbuf *, int);
-       int     (*ic_getiv)(struct ieee80211_key *,
-                       struct ieee80211_crypto_iv *, uint8_t);
-       int     (*ic_update)(struct ieee80211_key *,
-                       const struct ieee80211_crypto_iv *,
-                       const struct ieee80211_frame *);
 };
 extern const struct ieee80211_cipher ieee80211_cipher_none;
 
+#define        IEEE80211_KEY_UNDEFINED(k) \
+       ((k)->wk_cipher == &ieee80211_cipher_none)
+
 void   ieee80211_crypto_register(const struct ieee80211_cipher *);
 void   ieee80211_crypto_unregister(const struct ieee80211_cipher *);
 int    ieee80211_crypto_available(u_int cipher);
-const struct ieee80211_cipher *ieee80211_crypto_cipher(u_int cipher);
-
-void   ieee80211_crypto_resetkey(struct ieee80211com *,
-               struct ieee80211_key *, ieee80211_keyix);
-
-struct ieee80211_key *ieee80211_crypto_encap(struct ieee80211com *,
-               struct ieee80211_node *, struct mbuf *);
-struct ieee80211_key *ieee80211_crypto_decap(struct ieee80211com *,
-               struct ieee80211_node *, struct mbuf *, int);
-struct ieee80211_key *ieee80211_crypto_findkey(struct ieee80211com *,
-               struct ieee80211_node *, struct mbuf *);
-struct ieee80211_key *ieee80211_crypto_encap_withkey(struct ieee80211com *,
-               struct mbuf *, struct ieee80211_key *);
-
-struct ieee80211_key *ieee80211_crypto_update(struct ieee80211com *,
-               struct ieee80211_node *, const struct ieee80211_crypto_iv *,
-               const struct ieee80211_frame *);
-struct ieee80211_key *ieee80211_crypto_getiv(struct ieee80211com *,
-               struct ieee80211_crypto_iv *, struct ieee80211_key *);
+
+struct ieee80211_key *ieee80211_crypto_encap(struct ieee80211_node *,
+               struct mbuf *);
+struct ieee80211_key *ieee80211_crypto_decap(struct ieee80211_node *,
+               struct mbuf *, int);
 
 /*
  * Check and remove any MIC.
  */
 static __inline int
-ieee80211_crypto_demic(struct ieee80211com *ic, struct ieee80211_key *k,
+ieee80211_crypto_demic(struct ieee80211vap *vap, struct ieee80211_key *k,
        struct mbuf *m, int force)
 {
        const struct ieee80211_cipher *cip = k->wk_cipher;
@@ -224,21 +212,35 @@ ieee80211_crypto_demic(struct ieee80211com *ic, struct ieee80211_key *k,
  * Add any MIC.
  */
 static __inline int
-ieee80211_crypto_enmic(struct ieee80211com *ic,
+ieee80211_crypto_enmic(struct ieee80211vap *vap,
        struct ieee80211_key *k, struct mbuf *m, int force)
 {
        const struct ieee80211_cipher *cip = k->wk_cipher;
        return (cip->ic_miclen > 0 ? cip->ic_enmic(k, m, force) : 1);
 }
 
+/* 
+ * Reset key state to an unused state.  The crypto
+ * key allocation mechanism insures other state (e.g.
+ * key data) is properly setup before a key is used.
+ */
+static __inline void
+ieee80211_crypto_resetkey(struct ieee80211vap *vap,
+       struct ieee80211_key *k, ieee80211_keyix ix)
+{
+       k->wk_cipher = &ieee80211_cipher_none;
+       k->wk_private = k->wk_cipher->ic_attach(vap, k);
+       k->wk_keyix = k->wk_rxkeyix = ix;
+       k->wk_flags = IEEE80211_KEY_XMIT | IEEE80211_KEY_RECV;
+}
+
 /*
  * Crypt-related notification methods.
  */
-void   ieee80211_notify_replay_failure(struct ieee80211com *,
+void   ieee80211_notify_replay_failure(struct ieee80211vap *,
                const struct ieee80211_frame *, const struct ieee80211_key *,
-               uint64_t rsc);
-void   ieee80211_notify_michael_failure(struct ieee80211com *,
+               uint64_t rsc, int tid);
+void   ieee80211_notify_michael_failure(struct ieee80211vap *,
                const struct ieee80211_frame *, u_int keyix);
-
 #endif /* defined(__KERNEL__) || defined(_KERNEL) */
 #endif /* _NET80211_IEEE80211_CRYPTO_H_ */
diff --git a/sys/netproto/802_11/ieee80211_dfs.h b/sys/netproto/802_11/ieee80211_dfs.h
new file mode 100644 (file)
index 0000000..21601cc
--- /dev/null
@@ -0,0 +1,58 @@
+/*-
+ * Copyright (c) 2007-2008 Sam Leffler, Errno Consulting
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
+ * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
+ * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
+ * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
+ * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
+ * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
+ * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
+ * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ *
+ * $FreeBSD: head/sys/net80211/ieee80211_dfs.h 186107 2008-12-15 01:26:33Z sam $
+ * $DragonFly$
+ */
+#ifndef _NET80211_IEEE80211_DFS_H_
+#define _NET80211_IEEE80211_DFS_H_
+
+/*
+ * 802.11h/DFS definitions.
+ */
+
+struct ieee80211_dfs_state {
+       int             nol_event[IEEE80211_CHAN_MAX];
+       struct callout  nol_timer;              /* NOL list processing */
+       struct callout  cac_timer;              /* CAC timer */
+       struct timeval  lastevent;              /* time of last radar event */
+       int             cureps;                 /* current events/second */
+       const struct ieee80211_channel *lastchan;/* chan w/ last radar event */
+       struct ieee80211_channel *newchan;      /* chan selected next */
+};
+
+void   ieee80211_dfs_attach(struct ieee80211com *);
+void   ieee80211_dfs_detach(struct ieee80211com *);
+
+void   ieee80211_dfs_reset(struct ieee80211com *);
+
+void   ieee80211_dfs_cac_start(struct ieee80211vap *);
+void   ieee80211_dfs_cac_stop(struct ieee80211vap *);
+void   ieee80211_dfs_cac_clear(struct ieee80211com *,
+               const struct ieee80211_channel *);
+
+void   ieee80211_dfs_notify_radar(struct ieee80211com *,
+               struct ieee80211_channel *);
+struct ieee80211_channel *ieee80211_dfs_pickchannel(struct ieee80211com *);
+#endif /* _NET80211_IEEE80211_DFS_H_ */
index bc5c2fb..2e8355a 100644 (file)
@@ -1,5 +1,5 @@
-/*
- * Copyright (c) 2003-2005 Sam Leffler, Errno Consulting
+/*-
+ * Copyright (c) 2003-2008 Sam Leffler, Errno Consulting
  * All rights reserved.
  *
  * Redistribution and use in source and binary forms, with or without
@@ -10,8 +10,6 @@
  * 2. Redistributions in binary form must reproduce the above copyright
  *    notice, this list of conditions and the following disclaimer in the
  *    documentation and/or other materials provided with the distribution.
- * 3. The name of the author may not be used to endorse or promote products
- *    derived from this software without specific prior written permission.
  *
  * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
  * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
  * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
  * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
  *
- * $FreeBSD: src/sys/net80211/ieee80211_freebsd.h,v 1.5.2.1 2005/09/03 22:40:02 sam Exp $
- * $DragonFly: src/sys/netproto/802_11/ieee80211_dragonfly.h,v 1.4 2007/08/22 13:24:44 sephe Exp $
+ * $FreeBSD: head/sys/net80211/ieee80211_freebsd.h 195618 2009-07-11 15:02:45Z rpaulo $
+ * $DragonFly$
  */
 #ifndef _NET80211_IEEE80211_DRAGONFLY_H_
 #define _NET80211_IEEE80211_DRAGONFLY_H_
 
+#ifdef _KERNEL
+#include <sys/param.h>
+#include <sys/types.h>
+#include <sys/lock.h>
+#include <sys/mutex2.h>
+#include <sys/sysctl.h>
+#include <sys/taskqueue.h>
+
 /*
- * Per-node power-save queue definitions. 
+ * Common state locking definitions.
  */
-#define        IEEE80211_NODE_SAVEQ_INIT(_ni, _name) do {              \
-       (_ni)->ni_savedq.ifq_maxlen = IEEE80211_PS_MAX_QUEUE;   \
+typedef struct {
+       char            name[16];               /* e.g. "ath0_com_lock" */
+       struct lock     lock;
+} ieee80211_com_lock_t;
+#define        IEEE80211_LOCK_INIT(_ic, _name) do {                            \
+       ieee80211_com_lock_t *cl = &(_ic)->ic_comlock;                  \
+       ksnprintf(cl->name, sizeof(cl->name), "%s_com_lock", _name);    \
+       lockinit(&cl->lock, cl->name, 0, LK_CANRECURSE);                \
 } while (0)
-#define        IEEE80211_NODE_SAVEQ_DESTROY(_ni)       ((void)0)
-#define        IEEE80211_NODE_SAVEQ_QLEN(_ni)          IF_QLEN(&(_ni)->ni_savedq)
-#define        IEEE80211_NODE_SAVEQ_DEQUEUE(_ni, _m, _qlen) do {       \
-       IF_DEQUEUE(&(_ni)->ni_savedq, _m);                      \
-       (_qlen) = IEEE80211_NODE_SAVEQ_QLEN(_ni);               \
+#define        IEEE80211_LOCK_OBJ(_ic) (&(_ic)->ic_comlock.lock)
+#define        IEEE80211_LOCK_DESTROY(_ic) lockuninit(IEEE80211_LOCK_OBJ(_ic))
+#define        IEEE80211_LOCK(_ic) \
+       lockmgr(IEEE80211_LOCK_OBJ(_ic), LK_EXCLUSIVE)
+#define        IEEE80211_UNLOCK(_ic)      lockmgr(IEEE80211_LOCK_OBJ(_ic), LK_RELEASE)
+#define        IEEE80211_LOCK_ASSERT(_ic) \
+       KKASSERT(lockstatus(IEEE80211_LOCK_OBJ(_ic), curthread) == LK_EXCLUSIVE)
+
+/*
+ * Node locking definitions.
+ */
+typedef struct {
+       char            name[16];               /* e.g. "ath0_node_lock" */
+       struct lock     lock;
+} ieee80211_node_lock_t;
+#define        IEEE80211_NODE_LOCK_INIT(_nt, _name) do {                       \
+       ieee80211_node_lock_t *nl = &(_nt)->nt_nodelock;                \
+       ksnprintf(nl->name, sizeof(nl->name), "%s_node_lock", _name);   \
+       lockinit(&nl->lock, nl->name, 0, LK_CANRECURSE);                \
 } while (0)
-#define        IEEE80211_NODE_SAVEQ_DRAIN(_ni, _qlen) do {             \
-       (_qlen) = IEEE80211_NODE_SAVEQ_QLEN(_ni);               \
-       IF_DRAIN(&(_ni)->ni_savedq);                            \
+#define        IEEE80211_NODE_LOCK_OBJ(_nt)    (&(_nt)->nt_nodelock.lock)
+#define        IEEE80211_NODE_LOCK_DESTROY(_nt) \
+       lockuninit(IEEE80211_NODE_LOCK_OBJ(_nt))
+#define        IEEE80211_NODE_LOCK(_nt) \
+       lockmgr(IEEE80211_NODE_LOCK_OBJ(_nt), LK_EXCLUSIVE)
+#define        IEEE80211_NODE_IS_LOCKED(_nt) \
+       (lockstatus(IEEE80211_NODE_LOCK_OBJ(_nt), curthread) == LK_EXCLUSIVE)
+#define        IEEE80211_NODE_UNLOCK(_nt) \
+       lockmgr(IEEE80211_NODE_LOCK_OBJ(_nt), LK_RELEASE)
+#define        IEEE80211_NODE_LOCK_ASSERT(_nt) \
+       KKASSERT(lockstatus(IEEE80211_NODE_LOCK_OBJ(_nt), curthread) \
+           == LK_EXCLUSIVE)
+
+/*
+ * Node table iteration locking definitions; this protects the
+ * scan generation # used to iterate over the station table
+ * while grabbing+releasing the node lock.
+ */
+typedef struct {
+       char            name[16];               /* e.g. "ath0_scan_lock" */
+       struct lock     lock;
+} ieee80211_scan_lock_t;
+#define        IEEE80211_NODE_ITERATE_LOCK_INIT(_nt, _name) do {               \
+       ieee80211_scan_lock_t *sl = &(_nt)->nt_scanlock;                \
+       ksnprintf(sl->name, sizeof(sl->name), "%s_scan_lock", _name);   \
+       lockinit(&sl->lock, sl->name, 0, 0);                            \
 } while (0)
-/* XXX could be optimized */
-#define        _IEEE80211_NODE_SAVEQ_DEQUEUE_HEAD(_ni, _m) do {        \
-       IF_DEQUEUE(&(_ni)->ni_savedq, m);                       \
+#define        IEEE80211_NODE_ITERATE_LOCK_OBJ(_nt)    (&(_nt)->nt_scanlock.lock)
+#define        IEEE80211_NODE_ITERATE_LOCK_DESTROY(_nt) \
+       lockuninit(IEEE80211_NODE_ITERATE_LOCK_OBJ(_nt))
+#define        IEEE80211_NODE_ITERATE_LOCK(_nt) \
+       lockmgr(IEEE80211_NODE_ITERATE_LOCK_OBJ(_nt), LK_EXCLUSIVE)
+#define        IEEE80211_NODE_ITERATE_UNLOCK(_nt) \
+       lockmgr(IEEE80211_NODE_ITERATE_LOCK_OBJ(_nt), LK_RELEASE)
+
+/*
+ * Power-save queue definitions. 
+ */
+typedef struct lock ieee80211_psq_lock_t;
+#define        IEEE80211_PSQ_INIT(_psq, _name) \
+       lockinit(&(_psq)->psq_lock, _name, 0, 0)
+#define        IEEE80211_PSQ_DESTROY(_psq)     lockuninit(&(_psq)->psq_lock)
+#define        IEEE80211_PSQ_LOCK(_psq)        lockmgr(&(_psq)->psq_lock, LK_EXCLUSIVE)
+#define        IEEE80211_PSQ_UNLOCK(_psq)      lockmgr(&(_psq)->psq_lock, LK_RELEASE)
+
+#ifndef IF_PREPEND_LIST
+#define _IF_PREPEND_LIST(ifq, mhead, mtail, mcount) do {       \
+       (mtail)->m_nextpkt = (ifq)->ifq_head;                   \
+       if ((ifq)->ifq_tail == NULL)                            \
+               (ifq)->ifq_tail = (mtail);                      \
+       (ifq)->ifq_head = (mhead);                              \
+       (ifq)->ifq_len += (mcount);                             \
 } while (0)
-#define        _IEEE80211_NODE_SAVEQ_ENQUEUE(_ni, _m, _qlen, _age) do {\
-       (_m)->m_nextpkt = NULL;                                 \
-       if ((_ni)->ni_savedq.ifq_tail != NULL) {                \
-               _age -= M_AGE_GET((_ni)->ni_savedq.ifq_tail);   \
-               (_ni)->ni_savedq.ifq_tail->m_nextpkt = (_m);    \
-       } else {                                                \
-               (_ni)->ni_savedq.ifq_head = (_m);               \
-       }                                                       \
-       M_AGE_SET(_m, _age);                                    \
-       (_ni)->ni_savedq.ifq_tail = (_m);                       \
-       (_qlen) = ++(_ni)->ni_savedq.ifq_len;                   \
+#define IF_PREPEND_LIST(ifq, mhead, mtail, mcount) do {                \
+       IF_LOCK(ifq);                                           \
+       _IF_PREPEND_LIST(ifq, mhead, mtail, mcount);            \
+       IF_UNLOCK(ifq);                                         \
 } while (0)
+#endif /* IF_PREPEND_LIST */
+/*
+ * Age queue definitions.
+ */
+typedef struct lock ieee80211_ageq_lock_t;
+#define        IEEE80211_AGEQ_INIT(_aq, _name) \
+       lockinit(&(_aq)->aq_lock, _name, 0, 0)
+#define        IEEE80211_AGEQ_DESTROY(_aq)     lockuninit(&(_aq)->aq_lock)
+#define        IEEE80211_AGEQ_LOCK(_aq)        lockmgr(&(_aq)->aq_lock, LK_EXCLUSIVE)
+#define        IEEE80211_AGEQ_UNLOCK(_aq)      lockmgr(&(_aq)->aq_lock, LK_RELEASE)
+
+/*
+ * 802.1x MAC ACL database locking definitions.
+ */
+typedef struct lock acl_lock_t;
+#define        ACL_LOCK_INIT(_as, _name) \
+       lockinit(&(_as)->as_lock, _name, 0, 0)
+#define        ACL_LOCK_DESTROY(_as)           lockuninit(&(_as)->as_lock)
+#define        ACL_LOCK(_as)                   lockmgr(&(_as)->as_lock, LK_EXCLUSIVE)
+#define        ACL_UNLOCK(_as)                 lockmgr(&(_as)->as_lock, LK_RELEASE)
+#define        ACL_LOCK_ASSERT(_as) \
+       KKASSERT(lockstatus(&(_as)->as_lock, curthread) == LK_EXCLUSIVE)
 
 /*
  * Node reference counting definitions.
@@ -85,27 +172,69 @@ struct ieee80211_node;
 int    ieee80211_node_dectestref(struct ieee80211_node *ni);
 #define        ieee80211_node_refcnt(_ni)      (_ni)->ni_refcnt
 
-struct mbuf *ieee80211_getmgtframe(uint8_t **frm, int headroom, u_int pktlen);
+struct ifqueue;
+struct ieee80211vap;
+void   ieee80211_drain_ifq(struct ifqueue *);
+void   ieee80211_flush_ifq(struct ifqueue *, struct ieee80211vap *);
+
+void   ieee80211_vap_destroy(struct ieee80211vap *);
+
+#define        IFNET_IS_UP_RUNNING(_ifp) \
+       (((_ifp)->if_flags & IFF_UP) && \
+        ((_ifp)->if_drv_flags & IFF_DRV_RUNNING))
+
+#define        msecs_to_ticks(ms)      (((ms)*hz)/1000)
+#define        ticks_to_msecs(t)       (1000*(t) / hz)
+#define        ticks_to_secs(t)        ((t) / hz)
+#define time_after(a,b)        ((long)(b) - (long)(a) < 0)
+#define time_before(a,b)       time_after(b,a)
+#define time_after_eq(a,b)     ((long)(a) - (long)(b) >= 0)
+#define time_before_eq(a,b)    time_after_eq(b,a)
 
-/* M_PROTO1 unused */
+struct mbuf *ieee80211_getmgtframe(uint8_t **frm, int headroom, int pktlen);
+
+/* tx path usage */
+#define        M_ENCAP         M_PROTO1                /* 802.11 encap done */
+#define        M_EAPOL         M_PROTO3                /* PAE/EAPOL frame */
 #define        M_PWR_SAV       M_PROTO4                /* bypass PS handling */
 #define        M_MORE_DATA     M_PROTO5                /* more data frames to follow */
-/*
- * Encode WME access control bits in the PROTO flags.
- * This is safe since it's passed directly in to the
- * driver and there's no chance someone else will clobber
- * them on us.
- */
-#define        M_WME_AC_MASK   (M_PROTO2|M_PROTO3)
-/* XXX 5 is wrong if M_PROTO* are redefined */
-#define        M_WME_AC_SHIFT  5
+#define        M_FF            M_PROTO6                /* fast frame */
+#define        M_TXCB          M_PROTO7                /* do tx complete callback */
+#define        M_AMPDU_MPDU    M_PROTO8                /* ok for A-MPDU aggregation */
+#define        M_80211_TX \
+       (M_FRAG|M_FIRSTFRAG|M_LASTFRAG|M_ENCAP|M_EAPOL|M_PWR_SAV|\
+        M_MORE_DATA|M_FF|M_TXCB|M_AMPDU_MPDU)
+
+/* rx path usage */
+#define        M_AMPDU         M_PROTO1                /* A-MPDU subframe */
+#define        M_WEP           M_PROTO2                /* WEP done by hardware */
+#if 0
+#define        M_AMPDU_MPDU    M_PROTO8                /* A-MPDU re-order done */
+#endif
+#define        M_80211_RX      (M_AMPDU|M_WEP|M_AMPDU_MPDU)
+
+#define        IEEE80211_MBUF_TX_FLAG_BITS \
+       "\20\1M_EXT\2M_PKTHDR\3M_EOR\4M_RDONLY\5M_ENCAP\6M_WEP\7M_EAPOL" \
+       "\10M_PWR_SAV\11M_MORE_DATA\12M_BCAST\13M_MCAST\14M_FRAG\15M_FIRSTFRAG" \
+       "\16M_LASTFRAG\17M_SKIP_FIREWALL\20M_FREELIST\21M_VLANTAG\22M_PROMISC" \
+       "\23M_NOFREE\24M_FF\25M_TXCB\26M_AMPDU_MPDU\27M_FLOWID"
 
-#define M_IEEE80211    (M_PROTO2|M_PROTO3|M_PROTO4|M_PROTO5)
+#define        IEEE80211_MBUF_RX_FLAG_BITS \
+       "\20\1M_EXT\2M_PKTHDR\3M_EOR\4M_RDONLY\5M_AMPDU\6M_WEP\7M_PROTO3" \
+       "\10M_PROTO4\11M_PROTO5\12M_BCAST\13M_MCAST\14M_FRAG\15M_FIRSTFRAG" \
+       "\16M_LASTFRAG\17M_SKIP_FIREWALL\20M_FREELIST\21M_VLANTAG\22M_PROMISC" \
+       "\23M_NOFREE\24M_PROTO6\25M_PROTO7\26M_AMPDU_MPDU\27M_FLOWID"
 
+/*
+ * Store WME access control bits in the vlan tag.
+ * This is safe since it's done after the packet is classified
+ * (where we use any previous tag) and because it's passed
+ * directly in to the driver and there's no chance someone
+ * else will clobber them on us.
+ */
 #define        M_WME_SETAC(m, ac) \
-       ((m)->m_flags = ((m)->m_flags &~ M_WME_AC_MASK) | \
-               ((ac) << M_WME_AC_SHIFT))
-#define        M_WME_GETAC(m)  (((m)->m_flags >> M_WME_AC_SHIFT) & 0x3)
+       ((m)->m_pkthdr.ether_vlantag = (ac))
+#define        M_WME_GETAC(m)  ((m)->m_pkthdr.ether_vlantag)
 
 /*
  * Mbufs on the power save queue are tagged with an age and
@@ -116,17 +245,169 @@ struct mbuf *ieee80211_getmgtframe(uint8_t **frm, int headroom, u_int pktlen);
 #define        M_AGE_GET(m)            (m->m_pkthdr.csum_data)
 #define        M_AGE_SUB(m,adj)        (m->m_pkthdr.csum_data -= adj)
 
+/*
+ * Store the sequence number.
+ */
+#define        M_SEQNO_SET(m, seqno) \
+       ((m)->m_pkthdr.tso_segsz = (seqno))
+#define        M_SEQNO_GET(m)  ((m)->m_pkthdr.tso_segsz)
+
+#define        MTAG_ABI_NET80211       1132948340      /* net80211 ABI */
+
+struct ieee80211_cb {
+       void    (*func)(struct ieee80211_node *, void *, int status);
+       void    *arg;
+};
+#define        NET80211_TAG_CALLBACK   0       /* xmit complete callback */
+int    ieee80211_add_callback(struct mbuf *m,
+               void (*func)(struct ieee80211_node *, void *, int), void *arg);
+void   ieee80211_process_callback(struct ieee80211_node *, struct mbuf *, int);
+
 void   get_random_bytes(void *, size_t);
 
 struct ieee80211com;
 
 void   ieee80211_sysctl_attach(struct ieee80211com *);
 void   ieee80211_sysctl_detach(struct ieee80211com *);
+void   ieee80211_sysctl_vattach(struct ieee80211vap *);
+void   ieee80211_sysctl_vdetach(struct ieee80211vap *);
+
+SYSCTL_DECL(_net_wlan);
+int    ieee80211_sysctl_msecs_ticks(SYSCTL_HANDLER_ARGS);
 
 void   ieee80211_load_module(const char *);
-int    ieee80211_mbuf_append(struct mbuf *, int, const uint8_t *);
-struct mbuf *ieee80211_mbuf_clone(struct mbuf *, int);
-void   ieee80211_drain_mgtq(struct ifqueue *);
+
+/*
+ * A "policy module" is an adjunct module to net80211 that provides
+ * functionality that typically includes policy decisions.  This
+ * modularity enables extensibility and vendor-supplied functionality.
+ */
+#define        _IEEE80211_POLICY_MODULE(policy, name, version)                 \
+typedef void (*policy##_setup)(int);                                   \
+SET_DECLARE(policy##_set, policy##_setup);                             \
+static int                                                             \
+wlan_##name##_modevent(module_t mod, int type, void *unused)           \
+{                                                                      \
+       policy##_setup * const *iter, f;                                \
+       switch (type) {                                                 \
+       case MOD_LOAD:                                                  \
+               SET_FOREACH(iter, policy##_set) {                       \
+                       f = (void*) *iter;                              \
+                       f(type);                                        \
+               }                                                       \
+               return 0;                                               \
+       case MOD_UNLOAD:                                                \
+               if (nrefs) {                                            \
+                       kprintf("wlan_##name: still in use (%u dynamic refs)\n",\
+                               nrefs);                                 \
+                       return EBUSY;                                   \
+               }                                                       \
+               if (type == MOD_UNLOAD) {                               \
+                       SET_FOREACH(iter, policy##_set) {               \
+                               f = (void*) *iter;                      \
+                               f(type);                                \
+                       }                                               \
+               }                                                       \
+               return 0;                                               \
+       }                                                               \
+       return EINVAL;                                                  \
+}                                                                      \
+static moduledata_t name##_mod = {                                     \
+       "wlan_" #name,                                                  \
+       wlan_##name##_modevent,                                         \
+       0                                                               \
+};                                                                     \
+DECLARE_MODULE(wlan_##name, name##_mod, SI_SUB_DRIVERS, SI_ORDER_FIRST);\
+MODULE_VERSION(wlan_##name, version);                                  \
+MODULE_DEPEND(wlan_##name, wlan, 1, 1, 1)
+
+/*
+ * Crypto modules implement cipher support.
+ */
+#define        IEEE80211_CRYPTO_MODULE(name, version)                          \
+_IEEE80211_POLICY_MODULE(crypto, name, version);                       \
+static void                                                            \
+name##_modevent(int type)                                              \
+{                                                                      \
+       if (type == MOD_LOAD)                                           \
+               ieee80211_crypto_register(&name);                       \
+       else                                                            \
+               ieee80211_crypto_unregister(&name);                     \
+}                                                                      \
+TEXT_SET(crypto##_set, name##_modevent)
+
+/*
+ * Scanner modules provide scanning policy.
+ */
+#define        IEEE80211_SCANNER_MODULE(name, version)                         \
+       _IEEE80211_POLICY_MODULE(scanner, name, version)
+
+#define        IEEE80211_SCANNER_ALG(name, alg, v)                             \
+static void                                                            \
+name##_modevent(int type)                                              \
+{                                                                      \
+       if (type == MOD_LOAD)                                           \
+               ieee80211_scanner_register(alg, &v);                    \
+       else                                                            \
+               ieee80211_scanner_unregister(alg, &v);                  \
+}                                                                      \
+TEXT_SET(scanner_set, name##_modevent);                                        \
+
+/*
+ * ACL modules implement acl policy.
+ */
+#define        IEEE80211_ACL_MODULE(name, alg, version)                        \
+_IEEE80211_POLICY_MODULE(acl, name, version);                          \
+static void                                                            \
+alg##_modevent(int type)                                               \
+{                                                                      \
+       if (type == MOD_LOAD)                                           \
+               ieee80211_aclator_register(&alg);                       \
+       else                                                            \
+               ieee80211_aclator_unregister(&alg);                     \
+}                                                                      \
+TEXT_SET(acl_set, alg##_modevent);                                     \
+
+/*
+ * Authenticator modules handle 802.1x/WPA authentication.
+ */
+#define        IEEE80211_AUTH_MODULE(name, version)                            \
+       _IEEE80211_POLICY_MODULE(auth, name, version)
+
+#define        IEEE80211_AUTH_ALG(name, alg, v)                                \
+static void                                                            \
+name##_modevent(int type)                                              \
+{                                                                      \
+       if (type == MOD_LOAD)                                           \
+               ieee80211_authenticator_register(alg, &v);              \
+       else                                                            \
+               ieee80211_authenticator_unregister(alg);                \
+}                                                                      \
+TEXT_SET(auth_set, name##_modevent)
+
+/*
+ * Rate control modules provide tx rate control support.
+ */
+#define        IEEE80211_RATE_MODULE(alg, version)                             \
+_IEEE80211_POLICY_MODULE(rate, alg, version);                          \
+static void                                                            \
+alg##_modevent(int type)                                               \
+{                                                                      \
+       /* XXX nothing to do until the rate control framework arrives */\
+}                                                                      \
+TEXT_SET(rate##_set, alg##_modevent)
+
+struct ieee80211req;
+typedef int ieee80211_ioctl_getfunc(struct ieee80211vap *,
+    struct ieee80211req *);
+SET_DECLARE(ieee80211_ioctl_getset, ieee80211_ioctl_getfunc);
+#define        IEEE80211_IOCTL_GET(_name, _get) TEXT_SET(ieee80211_ioctl_getset, _get)
+
+typedef int ieee80211_ioctl_setfunc(struct ieee80211vap *,
+    struct ieee80211req *);
+SET_DECLARE(ieee80211_ioctl_setset, ieee80211_ioctl_setfunc);
+#define        IEEE80211_IOCTL_SET(_name, _set) TEXT_SET(ieee80211_ioctl_setset, _set)
+#endif /* _KERNEL */
 
 /* XXX this stuff belongs elsewhere */
 /*
@@ -158,6 +439,50 @@ struct ieee80211_michael_event {
        uint8_t         iev_keyix;      /* key id/index */
 };
 
+struct ieee80211_wds_event {
+       uint8_t         iev_addr[6];
+};
+
+struct ieee80211_csa_event {
+       uint32_t        iev_flags;      /* channel flags */
+       uint16_t        iev_freq;       /* setting in Mhz */
+       uint8_t         iev_ieee;       /* IEEE channel number */
+       uint8_t         iev_mode;       /* CSA mode */
+       uint8_t         iev_count;      /* CSA count */
+};
+
+struct ieee80211_cac_event {
+       uint32_t        iev_flags;      /* channel flags */
+       uint16_t        iev_freq;       /* setting in Mhz */
+       uint8_t         iev_ieee;       /* IEEE channel number */
+       /* XXX timestamp? */
+       uint8_t         iev_type;       /* IEEE80211_NOTIFY_CAC_* */
+};
+
+struct ieee80211_radar_event {
+       uint32_t        iev_flags;      /* channel flags */
+       uint16_t        iev_freq;       /* setting in Mhz */
+       uint8_t         iev_ieee;       /* IEEE channel number */
+       /* XXX timestamp? */
+};
+
+struct ieee80211_auth_event {
+       uint8_t         iev_addr[6];
+};
+
+struct ieee80211_deauth_event {
+       uint8_t         iev_addr[6];
+};
+
+struct ieee80211_country_event {
+       uint8_t         iev_addr[6];
+       uint8_t         iev_cc[2];      /* ISO country code */
+};
+
+struct ieee80211_radio_event {
+       uint8_t         iev_state;      /* 1 on, 0 off */
+};
+
 #define        RTM_IEEE80211_ASSOC     100     /* station associate (bss mode) */
 #define        RTM_IEEE80211_REASSOC   101     /* station re-associate (bss mode) */
 #define        RTM_IEEE80211_DISASSOC  102     /* station disassociate (bss mode) */
@@ -167,5 +492,46 @@ struct ieee80211_michael_event {
 #define        RTM_IEEE80211_REPLAY    106     /* sequence counter replay detected */
 #define        RTM_IEEE80211_MICHAEL   107     /* Michael MIC failure detected */
 #define        RTM_IEEE80211_REJOIN    108     /* station re-associate (ap mode) */
+#define        RTM_IEEE80211_WDS       109     /* WDS discovery (ap mode) */
+#define        RTM_IEEE80211_CSA       110     /* Channel Switch Announcement event */
+#define        RTM_IEEE80211_RADAR     111     /* radar event */
+#define        RTM_IEEE80211_CAC       112     /* Channel Availability Check event */
+#define        RTM_IEEE80211_DEAUTH    113     /* station deauthenticate */
+#define        RTM_IEEE80211_AUTH      114     /* station authenticate (ap mode) */
+#define        RTM_IEEE80211_COUNTRY   115     /* discovered country code (sta mode) */
+#define        RTM_IEEE80211_RADIO     116     /* RF kill switch state change */
 
+/*
+ * Structure prepended to raw packets sent through the bpf
+ * interface when set to DLT_IEEE802_11_RADIO.  This allows
+ * user applications to specify pretty much everything in
+ * an Atheros tx descriptor.  XXX need to generalize.
+ *
+ * XXX cannot be more than 14 bytes as it is copied to a sockaddr's
+ * XXX sa_data area.
+ */
+struct ieee80211_bpf_params {
+       uint8_t         ibp_vers;       /* version */
+#define        IEEE80211_BPF_VERSION   0
+       uint8_t         ibp_len;        /* header length in bytes */
+       uint8_t         ibp_flags;
+#define        IEEE80211_BPF_SHORTPRE  0x01    /* tx with short preamble */
+#define        IEEE80211_BPF_NOACK     0x02    /* tx with no ack */
+#define        IEEE80211_BPF_CRYPTO    0x04    /* tx with h/w encryption */
+#define        IEEE80211_BPF_FCS       0x10    /* frame incldues FCS */
+#define        IEEE80211_BPF_DATAPAD   0x20    /* frame includes data padding */
+#define        IEEE80211_BPF_RTS       0x40    /* tx with RTS/CTS */
+#define        IEEE80211_BPF_CTS       0x80    /* tx with CTS only */
+       uint8_t         ibp_pri;        /* WME/WMM AC+tx antenna */
+       uint8_t         ibp_try0;       /* series 1 try count */
+       uint8_t         ibp_rate0;      /* series 1 IEEE tx rate */
+       uint8_t         ibp_power;      /* tx power (device units) */
+       uint8_t         ibp_ctsrate;    /* IEEE tx rate for CTS */
+       uint8_t         ibp_try1;       /* series 2 try count */
+       uint8_t         ibp_rate1;      /* series 2 IEEE tx rate */
+       uint8_t         ibp_try2;       /* series 3 try count */
+       uint8_t         ibp_rate2;      /* series 3 IEEE tx rate */
+       uint8_t         ibp_try3;       /* series 4 try count */
+       uint8_t         ibp_rate3;      /* series 4 IEEE tx rate */
+};
 #endif /* _NET80211_IEEE80211_DRAGONFLY_H_ */
diff --git a/sys/netproto/802_11/ieee80211_hostap.h b/sys/netproto/802_11/ieee80211_hostap.h
new file mode 100644 (file)
index 0000000..a09c47b
--- /dev/null
@@ -0,0 +1,36 @@
+/*-
+ * Copyright (c) 2007-2008 Sam Leffler, Errno Consulting
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
+ * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
+ * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
+ * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
+ * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
+ * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
+ * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
+ * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ *
+ * $FreeBSD: head/sys/net80211/ieee80211_hostap.h 178354 2008-04-20 20:35:46Z sam $
+ * $DragonFly$
+ */
+#ifndef _NET80211_IEEE80211_HOSTAP_H_
+#define _NET80211_IEEE80211_HOSTAP_H_
+
+/*
+ * Hostap implementation definitions.
+ */
+void   ieee80211_hostap_attach(struct ieee80211com *);
+void   ieee80211_hostap_detach(struct ieee80211com *);
+#endif /* !_NET80211_IEEE80211_HOSTAP_H_ */
diff --git a/sys/netproto/802_11/ieee80211_ht.h b/sys/netproto/802_11/ieee80211_ht.h
new file mode 100644 (file)
index 0000000..a0f23b9
--- /dev/null
@@ -0,0 +1,203 @@
+/*-
+ * Copyright (c) 2007-2008 Sam Leffler, Errno Consulting
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
+ * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
+ * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
+ * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
+ * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
+ * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
+ * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
+ * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ *
+ * $FreeBSD: head/sys/net80211/ieee80211_ht.h 195377 2009-07-05 17:59:19Z sam $
+ * $DragonFly$
+ */
+#ifndef _NET80211_IEEE80211_HT_H_
+#define _NET80211_IEEE80211_HT_H_
+
+/*
+ * 802.11n protocol implementation definitions.
+ */
+
+#define        IEEE80211_AGGR_BAWMAX   64      /* max block ack window size */
+/* threshold for aging overlapping non-HT bss */
+#define        IEEE80211_NONHT_PRESENT_AGE     msecs_to_ticks(60*1000)
+
+struct ieee80211_tx_ampdu {
+       struct ieee80211_node *txa_ni;  /* back pointer */
+       u_short         txa_flags;
+#define        IEEE80211_AGGR_IMMEDIATE        0x0001  /* BA policy */
+#define        IEEE80211_AGGR_XCHGPEND         0x0002  /* ADDBA response pending */
+#define        IEEE80211_AGGR_RUNNING          0x0004  /* ADDBA response received */
+#define        IEEE80211_AGGR_SETUP            0x0008  /* deferred state setup */
+#define        IEEE80211_AGGR_NAK              0x0010  /* peer NAK'd ADDBA request */
+#define        IEEE80211_AGGR_BARPEND          0x0020  /* BAR response pending */
+       uint8_t         txa_ac;
+       uint8_t         txa_token;      /* dialog token */
+       int             txa_lastsample; /* ticks @ last traffic sample */
+       int             txa_pkts;       /* packets over last sample interval */
+       int             txa_avgpps;     /* filtered traffic over window */
+       int             txa_qbytes;     /* data queued (bytes) */
+       short           txa_qframes;    /* data queued (frames) */
+       ieee80211_seq   txa_start;      /* BA window left edge */
+       ieee80211_seq   txa_seqpending; /* new txa_start pending BAR response */
+       uint16_t        txa_wnd;        /* BA window size */
+       uint8_t         txa_attempts;   /* # ADDBA/BAR requests w/o a response*/
+       int             txa_nextrequest;/* soonest to make next request */
+       struct callout  txa_timer;
+       void            *txa_private;   /* driver-private storage */
+       uint64_t        txa_pad[4];
+};
+
+/* return non-zero if AMPDU tx for the TID is running */
+#define        IEEE80211_AMPDU_RUNNING(tap) \
+       (((tap)->txa_flags & IEEE80211_AGGR_RUNNING) != 0)
+
+/* return non-zero if AMPDU tx for the TID is running or started */
+#define        IEEE80211_AMPDU_REQUESTED(tap) \
+       (((tap)->txa_flags & \
+        (IEEE80211_AGGR_RUNNING|IEEE80211_AGGR_XCHGPEND|IEEE80211_AGGR_NAK)) != 0)
+
+#define        IEEE80211_AGGR_BITS \
+       "\20\1IMMEDIATE\2XCHGPEND\3RUNNING\4SETUP\5NAK"
+
+/*
+ * Traffic estimator support.  We estimate packets/sec for
+ * each AC that is setup for AMPDU or will potentially be
+ * setup for AMPDU.  The traffic rate can be used to decide
+ * when AMPDU should be setup (according to a threshold)
+ * and is available for drivers to do things like cache
+ * eviction when only a limited number of BA streams are
+ * available and more streams are requested than available.
+ */
+
+static __inline void
+ieee80211_txampdu_update_pps(struct ieee80211_tx_ampdu *tap)
+{
+       /* NB: scale factor of 2 was picked heuristically */
+       tap->txa_avgpps = ((tap->txa_avgpps << 2) -
+            tap->txa_avgpps + tap->txa_pkts) >> 2;
+}
+
+/*
+ * Count a packet towards the pps estimate.
+ */
+static __inline void
+ieee80211_txampdu_count_packet(struct ieee80211_tx_ampdu *tap)
+{
+       /* XXX bound loop/do more crude estimate? */
+       while (ticks - tap->txa_lastsample >= hz) {
+               ieee80211_txampdu_update_pps(tap);
+               /* reset to start new sample interval */
+               tap->txa_pkts = 0;
+               if (tap->txa_avgpps == 0) {
+                       tap->txa_lastsample = ticks;
+                       break;
+               }
+               tap->txa_lastsample += hz;
+       }
+       tap->txa_pkts++;
+}
+
+/*
+ * Get the current pps estimate.  If the average is out of
+ * date due to lack of traffic then we decay the estimate
+ * to account for the idle time.
+ */
+static __inline int
+ieee80211_txampdu_getpps(struct ieee80211_tx_ampdu *tap)
+{
+       /* XXX bound loop/do more crude estimate? */
+       while (ticks - tap->txa_lastsample >= hz) {
+               ieee80211_txampdu_update_pps(tap);
+               tap->txa_pkts = 0;
+               if (tap->txa_avgpps == 0) {
+                       tap->txa_lastsample = ticks;
+                       break;
+               }
+               tap->txa_lastsample += hz;
+       }
+       return tap->txa_avgpps;
+}
+
+struct ieee80211_rx_ampdu {
+       int             rxa_flags;
+       int             rxa_qbytes;     /* data queued (bytes) */
+       short           rxa_qframes;    /* data queued (frames) */
+       ieee80211_seq   rxa_seqstart;
+       ieee80211_seq   rxa_start;      /* start of current BA window */
+       uint16_t        rxa_wnd;        /* BA window size */
+       int             rxa_age;        /* age of oldest frame in window */
+       int             rxa_nframes;    /* frames since ADDBA */
+       struct mbuf *rxa_m[IEEE80211_AGGR_BAWMAX];
+       uint64_t        rxa_pad[4];
+};
+
+void   ieee80211_ht_attach(struct ieee80211com *);
+void   ieee80211_ht_detach(struct ieee80211com *);
+void   ieee80211_ht_vattach(struct ieee80211vap *);
+void   ieee80211_ht_vdetach(struct ieee80211vap *);
+
+void   ieee80211_ht_announce(struct ieee80211com *);
+
+struct ieee80211_mcs_rates {
+       uint16_t        ht20_rate_800ns;
+       uint16_t        ht20_rate_400ns;
+       uint16_t        ht40_rate_800ns;
+       uint16_t        ht40_rate_400ns;
+};
+extern const struct ieee80211_mcs_rates ieee80211_htrates[16];
+const struct ieee80211_htrateset *ieee80211_get_suphtrates(
+               struct ieee80211com *, const struct ieee80211_channel *);
+
+struct ieee80211_node;
+int    ieee80211_setup_htrates(struct ieee80211_node *,
+               const uint8_t *htcap, int flags);
+void   ieee80211_setup_basic_htrates(struct ieee80211_node *,
+               const uint8_t *htinfo);
+struct mbuf *ieee80211_decap_amsdu(struct ieee80211_node *, struct mbuf *);
+int    ieee80211_ampdu_reorder(struct ieee80211_node *, struct mbuf *);
+void   ieee80211_recv_bar(struct ieee80211_node *, struct mbuf *);
+void   ieee80211_ht_node_init(struct ieee80211_node *);
+void   ieee80211_ht_node_cleanup(struct ieee80211_node *);
+void   ieee80211_ht_node_age(struct ieee80211_node *);
+
+struct ieee80211_channel *ieee80211_ht_adjust_channel(struct ieee80211com *,
+               struct ieee80211_channel *, int);
+void   ieee80211_ht_wds_init(struct ieee80211_node *);
+void   ieee80211_ht_node_join(struct ieee80211_node *);
+void   ieee80211_ht_node_leave(struct ieee80211_node *);
+void   ieee80211_htprot_update(struct ieee80211com *, int protmode);
+void   ieee80211_ht_timeout(struct ieee80211com *);
+void   ieee80211_parse_htcap(struct ieee80211_node *, const uint8_t *);
+void   ieee80211_parse_htinfo(struct ieee80211_node *, const uint8_t *);
+void   ieee80211_ht_updateparams(struct ieee80211_node *, const uint8_t *,
+               const uint8_t *);
+void   ieee80211_ht_updatehtcap(struct ieee80211_node *, const uint8_t *);
+int    ieee80211_ampdu_request(struct ieee80211_node *,
+               struct ieee80211_tx_ampdu *);
+void   ieee80211_ampdu_stop(struct ieee80211_node *,
+               struct ieee80211_tx_ampdu *, int);
+int    ieee80211_send_bar(struct ieee80211_node *, struct ieee80211_tx_ampdu *,
+               ieee80211_seq);
+uint8_t        *ieee80211_add_htcap(uint8_t *, struct ieee80211_node *);
+uint8_t        *ieee80211_add_htcap_vendor(uint8_t *, struct ieee80211_node *);
+uint8_t        *ieee80211_add_htinfo(uint8_t *, struct ieee80211_node *);
+uint8_t        *ieee80211_add_htinfo_vendor(uint8_t *, struct ieee80211_node *);
+struct ieee80211_beacon_offsets;
+void   ieee80211_ht_update_beacon(struct ieee80211vap *,
+               struct ieee80211_beacon_offsets *);
+#endif /* _NET80211_IEEE80211_HT_H_ */
diff --git a/sys/netproto/802_11/ieee80211_input.h b/sys/netproto/802_11/ieee80211_input.h
new file mode 100644 (file)
index 0000000..011b404
--- /dev/null
@@ -0,0 +1,161 @@
+/*-
+ * Copyright (c) 2007-2009 Sam Leffler, Errno Consulting
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
+ * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
+ * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
+ * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
+ * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
+ * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
+ * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
+ * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ *
+ * $FreeBSD: head/sys/net80211/ieee80211_input.h 195757 2009-07-18 20:19:53Z sam $
+ * $DragonFly$
+ */
+#ifndef _NET80211_IEEE80211_INPUT_H_
+#define _NET80211_IEEE80211_INPUT_H_
+
+/* Verify the existence and length of __elem or get out. */
+#define IEEE80211_VERIFY_ELEMENT(__elem, __maxlen, _action) do {       \
+       if ((__elem) == NULL) {                                         \
+               IEEE80211_DISCARD(vap, IEEE80211_MSG_ELEMID,            \
+                   wh, NULL, "%s", "no " #__elem );                    \
+               vap->iv_stats.is_rx_elem_missing++;                     \
+               _action;                                                \
+       } else if ((__elem)[1] > (__maxlen)) {                          \
+               IEEE80211_DISCARD(vap, IEEE80211_MSG_ELEMID,            \
+                   wh, NULL, "bad " #__elem " len %d", (__elem)[1]);   \
+               vap->iv_stats.is_rx_elem_toobig++;                      \
+               _action;                                                \
+       }                                                               \
+} while (0)
+
+#define        IEEE80211_VERIFY_LENGTH(_len, _minlen, _action) do {            \
+       if ((_len) < (_minlen)) {                                       \
+               IEEE80211_DISCARD(vap, IEEE80211_MSG_ELEMID,            \
+                   wh, NULL, "ie too short, got %d, expected %d",      \
+                   (_len), (_minlen));                                 \
+               vap->iv_stats.is_rx_elem_toosmall++;                    \
+               _action;                                                \
+       }                                                               \
+} while (0)
+
+#ifdef IEEE80211_DEBUG
+void   ieee80211_ssid_mismatch(struct ieee80211vap *, const char *tag,
+       uint8_t mac[IEEE80211_ADDR_LEN], uint8_t *ssid);
+
+#define        IEEE80211_VERIFY_SSID(_ni, _ssid, _action) do {                 \
+       if ((_ssid)[1] != 0 &&                                          \
+           ((_ssid)[1] != (_ni)->ni_esslen ||                          \
+           memcmp((_ssid) + 2, (_ni)->ni_essid, (_ssid)[1]) != 0)) {   \
+               if (ieee80211_msg_input(vap))                           \
+                       ieee80211_ssid_mismatch(vap,                    \
+                           ieee80211_mgt_subtype_name[subtype >>       \
+                               IEEE80211_FC0_SUBTYPE_SHIFT],           \
+                               wh->i_addr2, _ssid);                    \
+               vap->iv_stats.is_rx_ssidmismatch++;                     \
+               _action;                                                \
+       }                                                               \
+} while (0)
+#else /* !IEEE80211_DEBUG */
+#define        IEEE80211_VERIFY_SSID(_ni, _ssid, _action) do {                 \
+       if ((_ssid)[1] != 0 &&                                          \
+           ((_ssid)[1] != (_ni)->ni_esslen ||                          \
+           memcmp((_ssid) + 2, (_ni)->ni_essid, (_ssid)[1]) != 0)) {   \
+               vap->iv_stats.is_rx_ssidmismatch++;                     \
+               _action;                                                \
+       }                                                               \
+} while (0)
+#endif /* !IEEE80211_DEBUG */
+
+/* unalligned little endian access */     
+#define LE_READ_2(p)                                   \
+       ((uint16_t)                                     \
+        ((((const uint8_t *)(p))[0]      ) |           \
+         (((const uint8_t *)(p))[1] <<  8)))
+#define LE_READ_4(p)                                   \
+       ((uint32_t)                                     \
+        ((((const uint8_t *)(p))[0]      ) |           \
+         (((const uint8_t *)(p))[1] <<  8) |           \
+         (((const uint8_t *)(p))[2] << 16) |           \
+         (((const uint8_t *)(p))[3] << 24)))
+
+static __inline int
+iswpaoui(const uint8_t *frm)
+{
+       return frm[1] > 3 && LE_READ_4(frm+2) == ((WPA_OUI_TYPE<<24)|WPA_OUI);
+}
+
+static __inline int
+iswmeoui(const uint8_t *frm)
+{
+       return frm[1] > 3 && LE_READ_4(frm+2) == ((WME_OUI_TYPE<<24)|WME_OUI);
+}
+
+static __inline int
+iswmeparam(const uint8_t *frm)
+{
+       return frm[1] > 5 && LE_READ_4(frm+2) == ((WME_OUI_TYPE<<24)|WME_OUI) &&
+               frm[6] == WME_PARAM_OUI_SUBTYPE;
+}
+
+static __inline int
+iswmeinfo(const uint8_t *frm)
+{
+       return frm[1] > 5 && LE_READ_4(frm+2) == ((WME_OUI_TYPE<<24)|WME_OUI) &&
+               frm[6] == WME_INFO_OUI_SUBTYPE;
+}
+
+static __inline int
+isatherosoui(const uint8_t *frm)
+{
+       return frm[1] > 3 && LE_READ_4(frm+2) == ((ATH_OUI_TYPE<<24)|ATH_OUI);
+}
+
+static __inline int
+istdmaoui(const uint8_t *frm)
+{
+       return frm[1] > 3 && LE_READ_4(frm+2) == ((TDMA_OUI_TYPE<<24)|TDMA_OUI);
+}
+
+static __inline int
+ishtcapoui(const uint8_t *frm)
+{
+       return frm[1] > 3 && LE_READ_4(frm+2) == ((BCM_OUI_HTCAP<<24)|BCM_OUI);
+}
+
+static __inline int
+ishtinfooui(const uint8_t *frm)
+{
+       return frm[1] > 3 && LE_READ_4(frm+2) == ((BCM_OUI_HTINFO<<24)|BCM_OUI);
+}
+
+void   ieee80211_deliver_data(struct ieee80211vap *,
+               struct ieee80211_node *, struct mbuf *);
+struct mbuf *ieee80211_defrag(struct ieee80211_node *,
+               struct mbuf *, int);
+struct mbuf *ieee80211_realign(struct ieee80211vap *, struct mbuf *, size_t);
+struct mbuf *ieee80211_decap(struct ieee80211vap *, struct mbuf *, int);
+struct mbuf *ieee80211_decap1(struct mbuf *, int *);
+int    ieee80211_setup_rates(struct ieee80211_node *ni,
+               const uint8_t *rates, const uint8_t *xrates, int flags);
+void ieee80211_send_error(struct ieee80211_node *,
+               const uint8_t mac[IEEE80211_ADDR_LEN], int subtype, int arg);
+int    ieee80211_alloc_challenge(struct ieee80211_node *);
+int    ieee80211_parse_beacon(struct ieee80211_node *, struct mbuf *,
+               struct ieee80211_scanparams *);
+int    ieee80211_parse_action(struct ieee80211_node *, struct mbuf *);
+#endif /* _NET80211_IEEE80211_INPUT_H_ */
index ce63d5b..d0c40b6 100644 (file)
@@ -1,6 +1,6 @@
-/*
+/*-
  * Copyright (c) 2001 Atsushi Onoe
- * Copyright (c) 2002-2005 Sam Leffler, Errno Consulting
+ * Copyright (c) 2002-2009 Sam Leffler, Errno Consulting
  * All rights reserved.
  *
  * Redistribution and use in source and binary forms, with or without
  * 2. Redistributions in binary form must reproduce the above copyright
  *    notice, this list of conditions and the following disclaimer in the
  *    documentation and/or other materials provided with the distribution.
- * 3. The name of the author may not be used to endorse or promote products
- *    derived from this software without specific prior written permission.
- *
- * Alternatively, this software may be distributed under the terms of the
- * GNU General Public License ("GPL") version 2 as published by the Free
- * Software Foundation.
  *
  * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
  * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
  * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
  * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
  *
- * $FreeBSD: src/sys/net80211/ieee80211_ioctl.h,v 1.10.2.7 2006/09/02 17:09:26 sam Exp $
- * $DragonFly: src/sys/netproto/802_11/ieee80211_ioctl.h,v 1.8 2008/01/19 07:34:13 sephe Exp $
+ * $FreeBSD: head/sys/net80211/ieee80211_ioctl.h 203556 2010-02-06 19:24:16Z rpaulo $
+ * $DragonFly$
  */
 #ifndef _NET80211_IEEE80211_IOCTL_H_
 #define _NET80211_IEEE80211_IOCTL_H_
 
-#include <sys/ioccom.h>
-
 /*
  * IEEE 802.11 ioctls.
  */
@@ -65,12 +57,15 @@ struct ieee80211_nodestats {
        uint32_t        ns_rx_defrag;           /* rx defragmentation failed */
        uint32_t        ns_rx_disassoc;         /* rx disassociation */
        uint32_t        ns_rx_deauth;           /* rx deauthentication */
+       uint32_t        ns_rx_action;           /* rx action */
        uint32_t        ns_rx_decryptcrc;       /* rx decrypt failed on crc */
        uint32_t        ns_rx_unauth;           /* rx on unauthorized port */
        uint32_t        ns_rx_unencrypted;      /* rx unecrypted w/ privacy */
+       uint32_t        ns_rx_drop;             /* rx discard other reason */
 
        uint32_t        ns_tx_data;             /* tx data frames */
        uint32_t        ns_tx_mgmt;             /* tx management frames */
+       uint32_t        ns_tx_ctrl;             /* tx control frames */
        uint32_t        ns_tx_ucast;            /* tx unicast frames */
        uint32_t        ns_tx_mcast;            /* tx multi/broadcast frames */
        uint64_t        ns_tx_bytes;            /* tx data count (bytes) */
@@ -90,6 +85,7 @@ struct ieee80211_nodestats {
        uint32_t        ns_tx_deauth_code;      /* last deauth reason */
        uint32_t        ns_tx_disassoc;         /* disassociations */
        uint32_t        ns_tx_disassoc_code;    /* last disassociation reason */
+       uint32_t        ns_spare[8];
 };
 
 /*
@@ -108,7 +104,7 @@ struct ieee80211_stats {
        uint32_t        is_rx_wepfail;          /* rx wep processing failed */
        uint32_t        is_rx_decap;            /* rx decapsulation failed */
        uint32_t        is_rx_mgtdiscard;       /* rx discard mgt frames */
-       uint32_t        is_rx_ctl;              /* rx discard ctrl frames */
+       uint32_t        is_rx_ctl;              /* rx ctrl frames */
        uint32_t        is_rx_beacon;           /* rx beacon frames */
        uint32_t        is_rx_rstoobig;         /* rx rate set truncated */
        uint32_t        is_rx_elem_missing;     /* rx required element missing*/
@@ -187,7 +183,67 @@ struct ieee80211_stats {
        uint32_t        is_rx_demicfail;        /* rx demic failed */
        uint32_t        is_rx_defrag;           /* rx defragmentation failed */
        uint32_t        is_rx_mgmt;             /* rx management frames */
-       uint32_t        is_spare[6];
+       uint32_t        is_rx_action;           /* rx action mgt frames */
+       uint32_t        is_amsdu_tooshort;      /* A-MSDU rx decap error */
+       uint32_t        is_amsdu_split;         /* A-MSDU rx split error */
+       uint32_t        is_amsdu_decap;         /* A-MSDU decap'd */
+       uint32_t        is_amsdu_encap;         /* A-MSDU encap'd for tx */
+       uint32_t        is_ampdu_bar_bad;       /* A-MPDU BAR out of window */
+       uint32_t        is_ampdu_bar_oow;       /* A-MPDU BAR before ADDBA */
+       uint32_t        is_ampdu_bar_move;      /* A-MPDU BAR moved window */
+       uint32_t        is_ampdu_bar_rx;        /* A-MPDU BAR frames handled */
+       uint32_t        is_ampdu_rx_flush;      /* A-MPDU frames flushed */
+       uint32_t        is_ampdu_rx_oor;        /* A-MPDU frames out-of-order */
+       uint32_t        is_ampdu_rx_copy;       /* A-MPDU frames copied down */
+       uint32_t        is_ampdu_rx_drop;       /* A-MPDU frames dropped */
+       uint32_t        is_tx_badstate;         /* tx discard state != RUN */
+       uint32_t        is_tx_notassoc;         /* tx failed, sta not assoc */
+       uint32_t        is_tx_classify;         /* tx classification failed */
+       uint32_t        is_dwds_mcast;          /* discard mcast over dwds */
+       uint32_t        is_dwds_qdrop;          /* dwds pending frame q full */
+       uint32_t        is_ht_assoc_nohtcap;    /* non-HT sta rejected */
+       uint32_t        is_ht_assoc_downgrade;  /* HT sta forced to legacy */
+       uint32_t        is_ht_assoc_norate;     /* HT assoc w/ rate mismatch */
+       uint32_t        is_ampdu_rx_age;        /* A-MPDU sent up 'cuz of age */
+       uint32_t        is_ampdu_rx_move;       /* A-MPDU MSDU moved window */
+       uint32_t        is_addba_reject;        /* ADDBA reject 'cuz disabled */
+       uint32_t        is_addba_norequest;     /* ADDBA response w/o ADDBA */
+       uint32_t        is_addba_badtoken;      /* ADDBA response w/ wrong
+                                                  dialogtoken */
+       uint32_t        is_addba_badpolicy;     /* ADDBA resp w/ wrong policy */
+       uint32_t        is_ampdu_stop;          /* A-MPDU stream stopped */
+       uint32_t        is_ampdu_stop_failed;   /* A-MPDU stream not running */
+       uint32_t        is_ampdu_rx_reorder;    /* A-MPDU held for rx reorder */
+       uint32_t        is_scan_bg;             /* background scans started */
+       uint8_t         is_rx_deauth_code;      /* last rx'd deauth reason */
+       uint8_t         is_rx_disassoc_code;    /* last rx'd disassoc reason */
+       uint8_t         is_rx_authfail_code;    /* last rx'd auth fail reason */
+       uint32_t        is_beacon_miss;         /* beacon miss notification */
+       uint32_t        is_rx_badstate;         /* rx discard state != RUN */
+       uint32_t        is_ff_flush;            /* ff's flush'd from stageq */
+       uint32_t        is_tx_ctl;              /* tx ctrl frames */
+       uint32_t        is_ampdu_rexmt;         /* A-MPDU frames rexmt ok */
+       uint32_t        is_ampdu_rexmt_fail;    /* A-MPDU frames rexmt fail */
+
+       uint32_t        is_mesh_wrongmesh;      /* dropped 'cuz not mesh sta*/
+       uint32_t        is_mesh_nolink;         /* dropped 'cuz link not estab*/
+       uint32_t        is_mesh_fwd_ttl;        /* mesh not fwd'd 'cuz ttl 0 */
+       uint32_t        is_mesh_fwd_nobuf;      /* mesh not fwd'd 'cuz no mbuf*/
+       uint32_t        is_mesh_fwd_tooshort;   /* mesh not fwd'd 'cuz no hdr */
+       uint32_t        is_mesh_fwd_disabled;   /* mesh not fwd'd 'cuz disabled */
+       uint32_t        is_mesh_fwd_nopath;     /* mesh not fwd'd 'cuz path unknown */
+
+       uint32_t        is_hwmp_wrongseq;       /* wrong hwmp seq no. */
+       uint32_t        is_hwmp_rootreqs;       /* root PREQs sent */
+       uint32_t        is_hwmp_rootrann;       /* root RANNs sent */
+
+       uint32_t        is_mesh_badae;          /* dropped 'cuz invalid AE */
+       uint32_t        is_mesh_rtaddfailed;    /* route add failed */
+       uint32_t        is_mesh_notproxy;       /* dropped 'cuz not proxying */
+       uint32_t        is_rx_badalign;         /* dropped 'cuz misaligned */
+       uint32_t        is_hwmp_proxy;          /* PREP for proxy route */
+       
+       uint32_t        is_spare[11];
 };
 
 /*
@@ -205,7 +261,7 @@ struct ieee80211_stats {
  * Otherwise a unicast/pairwise key is specified by the bssid
  * (on a station) or mac address (on an ap).  They key length
  * must include any MIC key data; otherwise it should be no
- more than IEEE80211_KEYBUF_SIZE.
more than IEEE80211_KEYBUF_SIZE.
  */
 struct ieee80211req_key {
        uint8_t         ik_type;        /* key/cipher type */
@@ -243,6 +299,7 @@ struct ieee80211req_mlme {
 #define        IEEE80211_MLME_DEAUTH           3       /* deauthenticate station */
 #define        IEEE80211_MLME_AUTHORIZE        4       /* authorize station */
 #define        IEEE80211_MLME_UNAUTHORIZE      5       /* unauthorize station */
+#define        IEEE80211_MLME_AUTH             6       /* authenticate station */
        uint8_t         im_ssid_len;    /* length of optional ssid */
        uint16_t        im_reason;      /* 802.11 reason code */
        uint8_t         im_macaddr[IEEE80211_ADDR_LEN];
@@ -260,20 +317,55 @@ enum {
        IEEE80211_MACCMD_DETACH         = 4,    /* detach ACL policy */
        IEEE80211_MACCMD_POLICY         = 5,    /* get ACL policy */
        IEEE80211_MACCMD_LIST           = 6,    /* get ACL database */
+       IEEE80211_MACCMD_POLICY_RADIUS  = 7,    /* set policy: RADIUS managed */
 };
 
 struct ieee80211req_maclist {
        uint8_t         ml_macaddr[IEEE80211_ADDR_LEN];
+} __packed;
+
+/*
+ * Mesh Routing Table Operations.
+ */
+enum {
+       IEEE80211_MESH_RTCMD_LIST   = 0, /* list HWMP routing table */
+       IEEE80211_MESH_RTCMD_FLUSH  = 1, /* flush HWMP routing table */
+       IEEE80211_MESH_RTCMD_ADD    = 2, /* add entry to the table */
+       IEEE80211_MESH_RTCMD_DELETE = 3, /* delete an entry from the table */
+};
+
+struct ieee80211req_mesh_route {
+       uint8_t         imr_flags;
+#define        IEEE80211_MESHRT_FLAGS_VALID    0x01
+#define        IEEE80211_MESHRT_FLAGS_PROXY    0x02
+       uint8_t         imr_dest[IEEE80211_ADDR_LEN];
+       uint8_t         imr_nexthop[IEEE80211_ADDR_LEN];
+       uint16_t        imr_nhops;
+       uint8_t         imr_pad;
+       uint32_t        imr_metric;
+       uint32_t        imr_lifetime;
+       uint32_t        imr_lastmseq;
 };
 
 /*
- * Set the active channel list.  Note this list is
- * intersected with the available channel list in
- * calculating the set of channels actually used in
- * scanning.
+ * HWMP root modes
+ */
+enum {
+       IEEE80211_HWMP_ROOTMODE_DISABLED        = 0,    /* disabled */
+       IEEE80211_HWMP_ROOTMODE_NORMAL          = 1,    /* normal PREPs */
+       IEEE80211_HWMP_ROOTMODE_PROACTIVE       = 2,    /* proactive PREPS */
+       IEEE80211_HWMP_ROOTMODE_RANN            = 3,    /* use RANN elemid */
+};
+
+
+/*
+ * Set the active channel list by IEEE channel #: each channel
+ * to be marked active is set in a bit vector.  Note this list is
+ * intersected with the available channel list in calculating
+ * the set of channels actually used in scanning.
  */
 struct ieee80211req_chanlist {
-       uint8_t         ic_channels[IEEE80211_CHAN_BYTES];
+       uint8_t         ic_channels[32];        /* NB: can be variable length */
 };
 
 /*
@@ -281,16 +373,26 @@ struct ieee80211req_chanlist {
  */
 struct ieee80211req_chaninfo {
        u_int   ic_nchans;
-       struct ieee80211_channel ic_chans[IEEE80211_CHAN_MAX];
+       struct ieee80211_channel ic_chans[1];   /* NB: variable length */
 };
+#define        IEEE80211_CHANINFO_SIZE(_nchan) \
+       (sizeof(struct ieee80211req_chaninfo) + \
+        (((_nchan)-1) * sizeof(struct ieee80211_channel)))
+#define        IEEE80211_CHANINFO_SPACE(_ci) \
+       IEEE80211_CHANINFO_SIZE((_ci)->ic_nchans)
 
 /*
  * Retrieve the WPA/RSN information element for an associated station.
  */
-struct ieee80211req_wpaie {
+struct ieee80211req_wpaie {    /* old version w/ only one ie */
        uint8_t         wpa_macaddr[IEEE80211_ADDR_LEN];
        uint8_t         wpa_ie[IEEE80211_MAX_OPT_IE];
 };
+struct ieee80211req_wpaie2 {
+       uint8_t         wpa_macaddr[IEEE80211_ADDR_LEN];
+       uint8_t         wpa_ie[IEEE80211_MAX_OPT_IE];
+       uint8_t         rsn_ie[IEEE80211_MAX_OPT_IE];
+};
 
 /*
  * Retrieve per-node statistics.
@@ -309,28 +411,37 @@ struct ieee80211req_sta_stats {
  * to retrieve other data like stats, unicast key, etc.
  */
 struct ieee80211req_sta_info {
-       uint16_t        isi_len;                /* length (mult of 4) */
+       uint16_t        isi_len;                /* total length (mult of 4) */
+       uint16_t        isi_ie_off;             /* offset to IE data */
+       uint16_t        isi_ie_len;             /* IE length */
        uint16_t        isi_freq;               /* MHz */
-       uint16_t        isi_flags;              /* channel flags */
-       uint16_t        isi_state;              /* state flags */
+       uint32_t        isi_flags;              /* channel flags */
+       uint32_t        isi_state;              /* state flags */
        uint8_t         isi_authmode;           /* authentication algorithm */
-       uint8_t         isi_rssi;               /* receive signal strength */
-       uint8_t         isi_capinfo;            /* deprecated */
+       int8_t          isi_rssi;               /* receive signal strength */
+       int8_t          isi_noise;              /* noise floor */
+       uint8_t         isi_capinfo;            /* capabilities */
        uint8_t         isi_erp;                /* ERP element */
        uint8_t         isi_macaddr[IEEE80211_ADDR_LEN];
        uint8_t         isi_nrates;
-                                       /* negotiated rates */
+                                               /* negotiated rates */
        uint8_t         isi_rates[IEEE80211_RATE_MAXSIZE];
-       uint8_t         isi_txrate;             /* index to isi_rates[] */
-       int8_t          isi_noise;              /* noise floor */
-       uint16_t        isi_ie_len;             /* IE length */
+       uint8_t         isi_txrate;             /* legacy/IEEE rate or MCS */
        uint16_t        isi_associd;            /* assoc response */
        uint16_t        isi_txpower;            /* current tx power */
        uint16_t        isi_vlan;               /* vlan tag */
-       uint16_t        isi_txseqs[17];         /* seq to be transmitted */
-       uint16_t        isi_rxseqs[17];         /* seq previous for qos frames*/
+       /* NB: [IEEE80211_NONQOS_TID] holds seq#'s for non-QoS stations */
+       uint16_t        isi_txseqs[IEEE80211_TID_SIZE];/* tx seq #/TID */
+       uint16_t        isi_rxseqs[IEEE80211_TID_SIZE];/* rx seq#/TID */
        uint16_t        isi_inact;              /* inactivity timer */
-       uint16_t        isi_capinfo2;           /* capabilities */
+       uint16_t        isi_txmbps;             /* current tx rate in .5 Mb/s */
+       uint16_t        isi_pad;
+       uint32_t        isi_jointime;           /* time of assoc/join */
+       struct ieee80211_mimo_info isi_mimo;    /* MIMO info for 11n sta's */
+       /* 11s info */
+       uint16_t        isi_peerid;
+       uint16_t        isi_localid;
+       uint8_t         isi_peerstate;
        /* XXX frag state? */
        /* variable length IE data */
 };
@@ -357,18 +468,111 @@ struct ieee80211req_sta_txpow {
 };
 
 /*
- * WME parameters are set and return using i_val and i_len.
- * i_val holds the value itself.  i_len specifies the AC
- * and, as appropriate, then high bit specifies whether the
- * operation is to be applied to the BSS or ourself.
+ * WME parameters manipulated with IEEE80211_IOC_WME_CWMIN
+ * through IEEE80211_IOC_WME_ACKPOLICY are set and return
+ * using i_val and i_len.  i_val holds the value itself.
+ * i_len specifies the AC and, as appropriate, then high bit
+ * specifies whether the operation is to be applied to the
+ * BSS or ourself.
  */
 #define        IEEE80211_WMEPARAM_SELF 0x0000          /* parameter applies to self */
 #define        IEEE80211_WMEPARAM_BSS  0x8000          /* parameter applies to BSS */
 #define        IEEE80211_WMEPARAM_VAL  0x7fff          /* parameter value */
 
-#if defined(__FreeBSD__) || defined(__DragonFly__)
 /*
- * FreeBSD-style ioctls.
+ * Application Information Elements can be appended to a variety
+ * of frames with the IEE80211_IOC_APPIE request.  This request
+ * piggybacks on a normal ieee80211req; the frame type is passed
+ * in i_val as the 802.11 FC0 bytes and the length of the IE data
+ * is passed in i_len.  The data is referenced in i_data.  If i_len
+ * is zero then any previously configured IE data is removed.  At
+ * most IEEE80211_MAX_APPIE data be appened.  Note that multiple
+ * IE's can be supplied; the data is treated opaquely.
+ */
+#define        IEEE80211_MAX_APPIE     1024            /* max app IE data */
+/*
+ * Hack: the WPA authenticator uses this mechanism to specify WPA
+ * ie's that are used instead of the ones normally constructed using
+ * the cipher state setup with separate ioctls.  This avoids issues
+ * like the authenticator ordering ie data differently than the
+ * net80211 layer and needing to keep separate state for WPA and RSN.
+ */
+#define        IEEE80211_APPIE_WPA \
+       (IEEE80211_FC0_TYPE_MGT | IEEE80211_FC0_SUBTYPE_BEACON | \
+        IEEE80211_FC0_SUBTYPE_PROBE_RESP)
+
+/*
+ * Station mode roaming parameters.  These are maintained
+ * per band/mode and control the roaming algorithm.
+ */
+struct ieee80211_roamparams_req {
+       struct ieee80211_roamparam params[IEEE80211_MODE_MAX];
+};
+
+/*
+ * Transmit parameters.  These can be used to set fixed transmit
+ * rate for each operating mode when operating as client or on a
+ * per-client basis according to the capabilities of the client
+ * (e.g. an 11b client associated to an 11g ap) when operating as
+ * an ap.
+ *
+ * MCS are distinguished from legacy rates by or'ing in 0x80.
+ */
+struct ieee80211_txparams_req {
+       struct ieee80211_txparam params[IEEE80211_MODE_MAX];
+};
+
+/*
+ * Set regulatory domain state with IEEE80211_IOC_REGDOMAIN.
+ * Note this is both the regulatory description and the channel
+ * list.  The get request for IEEE80211_IOC_REGDOMAIN returns
+ * only the regdomain info; the channel list is obtained
+ * separately with IEEE80211_IOC_CHANINFO.
+ */
+struct ieee80211_regdomain_req {
+       struct ieee80211_regdomain      rd;
+       struct ieee80211req_chaninfo    chaninfo;
+};
+#define        IEEE80211_REGDOMAIN_SIZE(_nchan) \
+       (sizeof(struct ieee80211_regdomain_req) + \
+        (((_nchan)-1) * sizeof(struct ieee80211_channel)))
+#define        IEEE80211_REGDOMAIN_SPACE(_req) \
+       IEEE80211_REGDOMAIN_SIZE((_req)->chaninfo.ic_nchans)
+
+/*
+ * Get driver capabilities.  Driver, hardware crypto, and
+ * HT/802.11n capabilities, and a table that describes what
+ * the radio can do.
+ */
+struct ieee80211_devcaps_req {
+       uint32_t        dc_drivercaps;          /* general driver caps */
+       uint32_t        dc_cryptocaps;          /* hardware crypto support */
+       uint32_t        dc_htcaps;              /* HT/802.11n support */
+       struct ieee80211req_chaninfo dc_chaninfo;
+};
+#define        IEEE80211_DEVCAPS_SIZE(_nchan) \
+       (sizeof(struct ieee80211_devcaps_req) + \
+        (((_nchan)-1) * sizeof(struct ieee80211_channel)))
+#define        IEEE80211_DEVCAPS_SPACE(_dc) \
+       IEEE80211_DEVCAPS_SIZE((_dc)->dc_chaninfo.ic_nchans)
+
+struct ieee80211_chanswitch_req {
+       struct ieee80211_channel csa_chan;      /* new channel */
+       int             csa_mode;               /* CSA mode */
+       int             csa_count;              /* beacon count to switch */
+};
+
+/*
+ * Get/set per-station vlan tag.
+ */
+struct ieee80211req_sta_vlan {
+       uint8_t         sv_macaddr[IEEE80211_ADDR_LEN];
+       uint16_t        sv_vlan;
+};
+
+#ifdef __DragonFly__
+/*
+ * DragonFlyBSD-style ioctls.
  */
 /* the first member must be matched with struct ifreq */
 struct ieee80211req {
@@ -380,6 +584,7 @@ struct ieee80211req {
 };
 #define        SIOCS80211               _IOW('i', 234, struct ieee80211req)
 #define        SIOCG80211              _IOWR('i', 235, struct ieee80211req)
+#define        SIOCG80211STATS         _IOWR('i', 236, struct ifreq)
 
 #define IEEE80211_IOC_SSID             1
 #define IEEE80211_IOC_NUMSSIDS         2
@@ -415,29 +620,24 @@ struct ieee80211req {
 #define        IEEE80211_IOC_WPAKEY            19
 #define        IEEE80211_IOC_DELKEY            20
 #define        IEEE80211_IOC_MLME              21
-#define        IEEE80211_IOC_OPTIE             22      /* optional info. element */
-#define        IEEE80211_IOC_SCAN_REQ          23
-#define        IEEE80211_IOC_SCAN_RESULTS      24
+/* 22 was IEEE80211_IOC_OPTIE, replaced by IEEE80211_IOC_APPIE */
+/* 23 was IEEE80211_IOC_SCAN_REQ */
+/* 24 was IEEE80211_IOC_SCAN_RESULTS */
 #define        IEEE80211_IOC_COUNTERMEASURES   25      /* WPA/TKIP countermeasures */
 #define        IEEE80211_IOC_WPA               26      /* WPA mode (0,1,2) */
 #define        IEEE80211_IOC_CHANLIST          27      /* channel list */
 #define        IEEE80211_IOC_WME               28      /* WME mode (on, off) */
 #define        IEEE80211_IOC_HIDESSID          29      /* hide SSID mode (on, off) */
 #define        IEEE80211_IOC_APBRIDGE          30      /* AP inter-sta bridging */
-#define        IEEE80211_IOC_MCASTCIPHER       31      /* multicast/default cipher */
-#define        IEEE80211_IOC_MCASTKEYLEN       32      /* multicast key length */
-#define        IEEE80211_IOC_UCASTCIPHERS      33      /* unicast cipher suites */
-#define        IEEE80211_IOC_UCASTCIPHER       34      /* unicast cipher */
-#define        IEEE80211_IOC_UCASTKEYLEN       35      /* unicast key length */
-#define        IEEE80211_IOC_DRIVER_CAPS       36      /* driver capabilities */
-#define        IEEE80211_IOC_KEYMGTALGS        37      /* key management algorithms */
-#define        IEEE80211_IOC_RSNCAPS           38      /* RSN capabilities */
+/* 31-35,37-38 were for WPA authenticator settings */
+/* 36 was IEEE80211_IOC_DRIVER_CAPS */
 #define        IEEE80211_IOC_WPAIE             39      /* WPA information element */
 #define        IEEE80211_IOC_STA_STATS         40      /* per-station statistics */
 #define        IEEE80211_IOC_MACCMD            41      /* MAC ACL operation */
 #define        IEEE80211_IOC_CHANINFO          42      /* channel info list */
 #define        IEEE80211_IOC_TXPOWMAX          43      /* max tx power for channel */
 #define        IEEE80211_IOC_STA_TXPOW         44      /* per-station tx power limit */
+/* 45 was IEEE80211_IOC_STA_INFO */
 #define        IEEE80211_IOC_WME_CWMIN         46      /* WME: ECWmin */
 #define        IEEE80211_IOC_WME_CWMAX         47      /* WME: ECWmax */
 #define        IEEE80211_IOC_WME_AIFS          48      /* WME: AIFSN */
@@ -449,36 +649,202 @@ struct ieee80211req {
 #define        IEEE80211_IOC_ADDMAC            54      /* add sta to MAC ACL table */
 #define        IEEE80211_IOC_DELMAC            55      /* del sta from MAC ACL table */
 #define        IEEE80211_IOC_PUREG             56      /* pure 11g (no 11b stations) */
-#define        IEEE80211_IOC_MCAST_RATE        72      /* tx rate for mcast frames */
+#define        IEEE80211_IOC_FF                57      /* ATH fast frames (on, off) */
+#define        IEEE80211_IOC_TURBOP            58      /* ATH turbo' (on, off) */
+#define        IEEE80211_IOC_BGSCAN            59      /* bg scanning (on, off) */
+#define        IEEE80211_IOC_BGSCAN_IDLE       60      /* bg scan idle threshold */
+#define        IEEE80211_IOC_BGSCAN_INTERVAL   61      /* bg scan interval */
+#define        IEEE80211_IOC_SCANVALID         65      /* scan cache valid threshold */
+/* 66-72 were IEEE80211_IOC_ROAM_* and IEEE80211_IOC_MCAST_RATE */
 #define        IEEE80211_IOC_FRAGTHRESHOLD     73      /* tx fragmentation threshold */
 #define        IEEE80211_IOC_BURST             75      /* packet bursting */
-#define IEEE80211_IOC_BMISSTHRESHOLD   77      /* beacon miss threshold */
-#define IEEE80211_IOC_STA_INFO         78      /* station/neighbor info */
-#define IEEE80211_IOC_RATECTL          255
+#define        IEEE80211_IOC_SCAN_RESULTS      76      /* get scan results */
+#define        IEEE80211_IOC_BMISSTHRESHOLD    77      /* beacon miss threshold */
+#define        IEEE80211_IOC_STA_INFO          78      /* station/neighbor info */
+#define        IEEE80211_IOC_WPAIE2            79      /* WPA+RSN info elements */
+#define        IEEE80211_IOC_CURCHAN           80      /* current channel */
+#define        IEEE80211_IOC_SHORTGI           81      /* 802.11n half GI */
+#define        IEEE80211_IOC_AMPDU             82      /* 802.11n A-MPDU (on, off) */
+#define        IEEE80211_IOC_AMPDU_LIMIT       83      /* A-MPDU length limit */
+#define        IEEE80211_IOC_AMPDU_DENSITY     84      /* A-MPDU density */
+#define        IEEE80211_IOC_AMSDU             85      /* 802.11n A-MSDU (on, off) */
+#define        IEEE80211_IOC_AMSDU_LIMIT       86      /* A-MSDU length limit */
+#define        IEEE80211_IOC_PUREN             87      /* pure 11n (no legacy sta's) */
+#define        IEEE80211_IOC_DOTH              88      /* 802.11h (on, off) */
+/* 89-91 were regulatory items */
+#define        IEEE80211_IOC_HTCOMPAT          92      /* support pre-D1.10 HT ie's */
+#define        IEEE80211_IOC_DWDS              93      /* DWDS/4-address handling */
+#define        IEEE80211_IOC_INACTIVITY        94      /* sta inactivity handling */
+#define        IEEE80211_IOC_APPIE             95      /* application IE's */
+#define        IEEE80211_IOC_WPS               96      /* WPS operation */
+#define        IEEE80211_IOC_TSN               97      /* TSN operation */
+#define        IEEE80211_IOC_DEVCAPS           98      /* driver+device capabilities */
+#define        IEEE80211_IOC_CHANSWITCH        99      /* start 11h channel switch */
+#define        IEEE80211_IOC_DFS               100     /* DFS (on, off) */
+#define        IEEE80211_IOC_DOTD              101     /* 802.11d (on, off) */
+#define IEEE80211_IOC_HTPROTMODE       102     /* HT protection (off, rts) */
+#define        IEEE80211_IOC_SCAN_REQ          103     /* scan w/ specified params */
+#define        IEEE80211_IOC_SCAN_CANCEL       104     /* cancel ongoing scan */
+#define        IEEE80211_IOC_HTCONF            105     /* HT config (off, HT20, HT40)*/
+#define        IEEE80211_IOC_REGDOMAIN         106     /* regulatory domain info */
+#define        IEEE80211_IOC_ROAM              107     /* roaming params en masse */
+#define        IEEE80211_IOC_TXPARAMS          108     /* tx parameters */
+#define        IEEE80211_IOC_STA_VLAN          109     /* per-station vlan tag */
+#define        IEEE80211_IOC_SMPS              110     /* MIMO power save */
+#define        IEEE80211_IOC_RIFS              111     /* RIFS config (on, off) */
+#define        IEEE80211_IOC_GREENFIELD        112     /* Greenfield (on, off) */
+#define        IEEE80211_IOC_STBC              113     /* STBC Tx/RX (on, off) */
+
+#define        IEEE80211_IOC_MESH_ID           170     /* mesh identifier */
+#define        IEEE80211_IOC_MESH_AP           171     /* accepting peerings */
+#define        IEEE80211_IOC_MESH_FWRD         172     /* forward frames */
+#define        IEEE80211_IOC_MESH_PROTO        173     /* mesh protocols */
+#define        IEEE80211_IOC_MESH_TTL          174     /* mesh TTL */
+#define        IEEE80211_IOC_MESH_RTCMD        175     /* mesh routing table commands*/
+#define        IEEE80211_IOC_MESH_PR_METRIC    176     /* mesh metric protocol */
+#define        IEEE80211_IOC_MESH_PR_PATH      177     /* mesh path protocol */
+#define        IEEE80211_IOC_MESH_PR_SIG       178     /* mesh sig protocol */
+#define        IEEE80211_IOC_MESH_PR_CC        179     /* mesh congestion protocol */
+#define        IEEE80211_IOC_MESH_PR_AUTH      180     /* mesh auth protocol */
+
+#define        IEEE80211_IOC_HWMP_ROOTMODE     190     /* HWMP root mode */
+#define        IEEE80211_IOC_HWMP_MAXHOPS      191     /* number of hops before drop */
+#define        IEEE80211_IOC_HWMP_TTL          192     /* HWMP TTL */
+
+#define        IEEE80211_IOC_TDMA_SLOT         201     /* TDMA: assigned slot */
+#define        IEEE80211_IOC_TDMA_SLOTCNT      202     /* TDMA: slots in bss */
+#define        IEEE80211_IOC_TDMA_SLOTLEN      203     /* TDMA: slot length (usecs) */
+#define        IEEE80211_IOC_TDMA_BINTERVAL    204     /* TDMA: beacon intvl (slots) */
+
+/*
+ * Parameters for controlling a scan requested with
+ * IEEE80211_IOC_SCAN_REQ.
+ *
+ * Active scans cause ProbeRequest frames to be issued for each
+ * specified ssid and, by default, a broadcast ProbeRequest frame.
+ * The set of ssid's is specified in the request.
+ *
+ * By default the scan will cause a BSS to be joined (in station/adhoc
+ * mode) or a channel to be selected for operation (hostap mode).
+ * To disable that specify IEEE80211_IOC_SCAN_NOPICK and if the
+ *
+ * If the station is currently associated to an AP then a scan request
+ * will cause the station to leave the current channel and potentially
+ * miss frames from the AP.  Alternatively the station may notify the
+ * AP that it is going into power save mode before it leaves the channel.
+ * This ensures frames for the station are buffered by the AP.  This is
+ * termed a ``bg scan'' and is requested with the IEEE80211_IOC_SCAN_BGSCAN
+ * flag.  Background scans may take longer than foreground scans and may
+ * be preempted by traffic.  If a station is not associated to an AP
+ * then a request for a background scan is automatically done in the
+ * foreground.
+ *
+ * The results of the scan request are cached by the system.  This
+ * information is aged out and/or invalidated based on events like not
+ * being able to associated to an AP.  To flush the current cache
+ * contents before doing a scan the IEEE80211_IOC_SCAN_FLUSH flag may
+ * be specified.
+ *
+ * By default the scan will be done until a suitable AP is located
+ * or a channel is found for use.  A scan can also be constrained
+ * to be done once (IEEE80211_IOC_SCAN_ONCE) or to last for no more
+ * than a specified duration.
+ */
+struct ieee80211_scan_req {
+       int             sr_flags;
+#define        IEEE80211_IOC_SCAN_NOPICK       0x00001 /* scan only, no selection */
+#define        IEEE80211_IOC_SCAN_ACTIVE       0x00002 /* active scan (probe req) */
+#define        IEEE80211_IOC_SCAN_PICK1ST      0x00004 /* ``hey sailor'' mode */
+#define        IEEE80211_IOC_SCAN_BGSCAN       0x00008 /* bg scan, exit ps at end */
+#define        IEEE80211_IOC_SCAN_ONCE         0x00010 /* do one complete pass */
+#define        IEEE80211_IOC_SCAN_NOBCAST      0x00020 /* don't send bcast probe req */
+#define        IEEE80211_IOC_SCAN_NOJOIN       0x00040 /* no auto-sequencing */
+#define        IEEE80211_IOC_SCAN_FLUSH        0x10000 /* flush scan cache first */
+#define        IEEE80211_IOC_SCAN_CHECK        0x20000 /* check scan cache first */
+       u_int           sr_duration;            /* duration (ms) */
+#define        IEEE80211_IOC_SCAN_DURATION_MIN 1
+#define        IEEE80211_IOC_SCAN_DURATION_MAX 0x7fffffff
+#define        IEEE80211_IOC_SCAN_FOREVER      IEEE80211_IOC_SCAN_DURATION_MAX
+       u_int           sr_mindwell;            /* min channel dwelltime (ms) */
+       u_int           sr_maxdwell;            /* max channel dwelltime (ms) */
+       int             sr_nssid;
+#define        IEEE80211_IOC_SCAN_MAX_SSID     3
+       struct {
+               int      len;                           /* length in bytes */
+               uint8_t ssid[IEEE80211_NWID_LEN];       /* ssid contents */
+       } sr_ssid[IEEE80211_IOC_SCAN_MAX_SSID];
+};
 
 /*
  * Scan result data returned for IEEE80211_IOC_SCAN_RESULTS.
+ * Each result is a fixed size structure followed by a variable
+ * length SSID and one or more variable length information elements.
+ * The size of each variable length item is found in the fixed
+ * size structure and the entire length of the record is specified
+ * in isr_len.  Result records are rounded to a multiple of 4 bytes.
  */
 struct ieee80211req_scan_result {
-       uint16_t        isr_len;                /* length (mult of 4) */
+       uint16_t        isr_len;                /* total length (mult of 4) */
+       uint16_t        isr_ie_off;             /* offset to SSID+IE data */
+       uint16_t        isr_ie_len;             /* IE length */
        uint16_t        isr_freq;               /* MHz */
        uint16_t        isr_flags;              /* channel flags */
-       uint8_t         isr_noise;
-       uint8_t         isr_rssi;
-       uint8_t         isr_intval;             /* beacon interval */
-       uint8_t         isr_capinfo;            /* capabilities (deprecated) */
+       int8_t          isr_noise;
+       int8_t          isr_rssi;
+       uint16_t        isr_intval;             /* beacon interval */
+       uint8_t         isr_capinfo;            /* capabilities */
        uint8_t         isr_erp;                /* ERP element */
        uint8_t         isr_bssid[IEEE80211_ADDR_LEN];
        uint8_t         isr_nrates;
        uint8_t         isr_rates[IEEE80211_RATE_MAXSIZE];
        uint8_t         isr_ssid_len;           /* SSID length */
-       uint8_t         isr_ie_len;             /* IE length */
-       uint16_t        isr_capinfo2;           /* capabilities */
-       uint8_t         isr_pad[3];
-       /* variable length SSID followed by IE data */
+       uint8_t         isr_meshid_len;         /* MESH ID length */
+       /* variable length SSID, followed by variable length MESH ID,
+         followed by IE data */
 };
 
-#define        SIOCG80211STATS         _IOWR('i', 236, struct ifreq)
-#endif /* __FreeBSD__ || __DragonFly__ */
+/*
+ * Virtual AP cloning parameters.  The parent device must
+ * be a vap-capable device.  All parameters specified with
+ * the clone request are fixed for the lifetime of the vap.
+ *
+ * There are two flavors of WDS vaps: legacy and dynamic.
+ * Legacy WDS operation implements a static binding between
+ * two stations encapsulating traffic in 4-address frames.
+ * Dynamic WDS vaps are created when a station associates to
+ * an AP and sends a 4-address frame.  If the AP vap is
+ * configured to support WDS then this will generate an
+ * event to user programs listening on the routing socket
+ * and a Dynamic WDS vap will be created to handle traffic
+ * to/from that station.  In both cases the bssid of the
+ * peer must be specified when creating the vap.
+ *
+ * By default a vap will inherit the mac address/bssid of
+ * the underlying device.  To request a unique address the
+ * IEEE80211_CLONE_BSSID flag should be supplied.  This is
+ * meaningless for WDS vaps as they share the bssid of an
+ * AP vap that must otherwise exist.  Note that some devices
+ * may not be able to support multiple addresses.
+ *
+ * Station mode vap's normally depend on the device to notice
+ * when the AP stops sending beacon frames.  If IEEE80211_CLONE_NOBEACONS
+ * is specified the net80211 layer will do this in s/w.  This
+ * is mostly useful when setting up a WDS repeater/extender where
+ * an AP vap is combined with a sta vap and the device isn't able
+ * to track beacon frames in hardware.
+ */
+struct ieee80211_clone_params {
+       char    icp_parent[IFNAMSIZ];           /* parent device */
+       uint16_t icp_opmode;                    /* operating mode */
+       uint16_t icp_flags;                     /* see below */
+       uint8_t icp_bssid[IEEE80211_ADDR_LEN];  /* for WDS links */
+       uint8_t icp_macaddr[IEEE80211_ADDR_LEN];/* local address */
+};
+#define        IEEE80211_CLONE_BSSID           0x0001  /* allocate unique mac/bssid */
+#define        IEEE80211_CLONE_NOBEACONS       0x0002  /* don't setup beacon timers */
+#define        IEEE80211_CLONE_WDSLEGACY       0x0004  /* legacy WDS processing */
+#define        IEEE80211_CLONE_MACADDR         0x0008  /* use specified mac addr */
+#define        IEEE80211_CLONE_TDMA            0x0010  /* operate in TDMA mode */
+#endif /* __DragonFly__ */
 
 #endif /* _NET80211_IEEE80211_IOCTL_H_ */
diff --git a/sys/netproto/802_11/ieee80211_mesh.h b/sys/netproto/802_11/ieee80211_mesh.h
new file mode 100644 (file)
index 0000000..2bcdbdb
--- /dev/null
@@ -0,0 +1,505 @@
+/*- 
+ * Copyright (c) 2009 The FreeBSD Foundation 
+ * All rights reserved. 
+ * 
+ * This software was developed by Rui Paulo under sponsorship from the
+ * FreeBSD Foundation. 
+ *  
+ * Redistribution and use in source and binary forms, with or without 
+ * modification, are permitted provided that the following conditions 
+ * are met: 
+ * 1. Redistributions of source code must retain the above copyright 
+ *    notice, this list of conditions and the following disclaimer. 
+ * 2. Redistributions in binary form must reproduce the above copyright 
+ *    notice, this list of conditions and the following disclaimer in the 
+ *    documentation and/or other materials provided with the distribution. 
+ * 
+ * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND 
+ * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE 
+ * ARE DISCLAIMED.  IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE 
+ * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL 
+ * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS 
+ * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) 
+ * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT 
+ * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY 
+ * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF 
+ * SUCH DAMAGE. 
+ * 
+ * $FreeBSD: head/sys/net80211/ieee80211_mesh.h 202178 2010-01-12 22:22:27Z rpaulo $
+ * $DragonFly$
+ */
+#ifndef _NET80211_IEEE80211_MESH_H_
+#define _NET80211_IEEE80211_MESH_H_
+
+#define        IEEE80211_MESH_DEFAULT_TTL      31
+
+/*
+ * NB: all structures are __packed  so sizeof works on arm, et. al.
+ */
+/*
+ * 802.11s Information Elements.
+*/
+/* Mesh Configuration */
+struct ieee80211_meshconf_ie {
+       uint8_t         conf_ie;        /* IEEE80211_ELEMID_MESHCONF */
+       uint8_t         conf_len;
+       uint8_t         conf_pselid;    /* Active Path Sel. Proto. ID */
+       uint8_t         conf_pmetid;    /* Active Metric Identifier */
+       uint8_t         conf_ccid;      /* Congestion Control Mode ID  */
+       uint8_t         conf_syncid;    /* Sync. Protocol ID */
+       uint8_t         conf_authid;    /* Auth. Protocol ID */
+       uint8_t         conf_form;      /* Formation Information */
+       uint16_t        conf_cap;
+} __packed;
+
+/* Hybrid Wireless Mesh Protocol */
+#define        IEEE80211_MESHCONF_PATH_HWMP            0x00
+/* Airtime Link Metric */
+#define        IEEE80211_MESHCONF_METRIC_AIRTIME       0x00
+/* Congestion Control */
+#define        IEEE80211_MESHCONF_CC_DISABLED          0x00
+#define        IEEE80211_MESHCONF_CC_SIG               0x01
+/* Neighbour Offset */
+#define        IEEE80211_MESHCONF_SYNC_NEIGHOFF        0x00
+#define        IEEE80211_MESHCONF_AUTH_DISABLED        0x00
+/* Simultaneous Authenticaction of Equals */
+#define        IEEE80211_MESHCONF_AUTH_SAE             0x01
+#define        IEEE80211_MESHCONF_FORM_MP              0x01 /* Connected to Portal */
+#define        IEEE80211_MESHCONF_FORM_NNEIGH_MASK     0x04 /* Number of Neighbours */
+#define        IEEE80211_MESHCONF_CAP_AP       0x01    /* Accepting Peers */
+#define        IEEE80211_MESHCONF_CAP_MCCAS    0x02    /* MCCA supported */
+#define        IEEE80211_MESHCONF_CAP_MCCAE    0x04    /* MCCA enabled */
+#define        IEEE80211_MESHCONF_CAP_FWRD     0x08    /* forwarding enabled */
+#define        IEEE80211_MESHCONF_CAP_BTR      0x10    /* Beacon Timing Report Enab */
+#define        IEEE80211_MESHCONF_CAP_TBTTA    0x20    /* TBTT Adj. Enabled */
+#define        IEEE80211_MESHCONF_CAP_TBTT     0x40    /* TBTT Adjusting  */
+#define        IEEE80211_MESHCONF_CAP_PSL      0x80    /* Power Save Level */
+
+/* Mesh Identifier */
+struct ieee80211_meshid_ie {
+       uint8_t         id_ie;          /* IEEE80211_ELEMID_MESHID */
+       uint8_t         id_len;
+} __packed;
+
+/* Link Metric Report */
+struct ieee80211_meshlmetric_ie {
+       uint8_t         lm_ie;  /* IEEE80211_ELEMID_MESHLINK */
+       uint8_t         lm_len;
+       uint32_t        lm_metric;
+#define        IEEE80211_MESHLMETRIC_INITIALVAL        0
+} __packed;
+
+/* Congestion Notification */
+struct ieee80211_meshcngst_ie {
+       uint8_t         cngst_ie;       /* IEEE80211_ELEMID_MESHCNGST */
+       uint8_t         cngst_len;
+       uint16_t        cngst_timer[4]; /* Expiration Timers: AC_BK,
+                                          AC_BE, AC_VI, AC_VO */
+} __packed;
+
+/* Peer Link Management */
+struct ieee80211_meshpeer_ie {
+       uint8_t         peer_ie;        /* IEEE80211_ELEMID_MESHPEER */
+       uint8_t         peer_len;
+       uint8_t         peer_proto[4];  /* Peer Management Protocol */
+       uint16_t        peer_llinkid;   /* Local Link ID */
+       uint16_t        peer_linkid;    /* Peer Link ID */
+       uint16_t        peer_rcode;
+} __packed;
+
+enum {
+       IEEE80211_MESH_PEER_LINK_OPEN           = 0,
+       IEEE80211_MESH_PEER_LINK_CONFIRM        = 1,
+       IEEE80211_MESH_PEER_LINK_CLOSE          = 2,
+       /* values 3-255 are reserved */
+};
+
+/* Mesh Peering Management Protocol */
+#define        IEEE80211_MESH_PEER_PROTO_OUI           0x00, 0x0f, 0xac
+#define        IEEE80211_MESH_PEER_PROTO_VALUE         0x2a
+#define        IEEE80211_MESH_PEER_PROTO       { IEEE80211_MESH_PEER_PROTO_OUI, \
+                                         IEEE80211_MESH_PEER_PROTO_VALUE }
+/* Abbreviated Handshake Protocol */
+#define        IEEE80211_MESH_PEER_PROTO_AH_OUI        0x00, 0x0f, 0xac
+#define        IEEE80211_MESH_PEER_PROTO_AH_VALUE      0x2b
+#define        IEEE80211_MESH_PEER_PROTO_AH    { IEEE80211_MESH_PEER_PROTO_AH_OUI, \
+                                         IEEE80211_MESH_PEER_PROTO_AH_VALUE }
+#ifdef notyet
+/* Mesh Channel Switch Annoucement */
+struct ieee80211_meshcsa_ie {
+       uint8_t         csa_ie;         /* IEEE80211_ELEMID_MESHCSA */
+       uint8_t         csa_len;
+       uint8_t         csa_mode;
+       uint8_t         csa_newclass;   /* New Regulatory Class */
+       uint8_t         csa_newchan;
+       uint8_t         csa_precvalue;  /* Precedence Value */
+       uint8_t         csa_count;
+} __packed;
+
+/* Mesh TIM */
+/* Equal to the non Mesh version */
+
+/* Mesh Awake Window */
+struct ieee80211_meshawakew_ie {
+       uint8_t         awakew_ie;              /* IEEE80211_ELEMID_MESHAWAKEW */
+       uint8_t         awakew_len;
+       uint8_t         awakew_windowlen;       /* in TUs */
+} __packed;
+
+/* Mesh Beacon Timing */
+struct ieee80211_meshbeacont_ie {
+       uint8_t         beacont_ie;             /* IEEE80211_ELEMID_MESHBEACONT */
+       uint8_t         beacont_len;
+       struct {
+               uint8_t         mp_aid;         /* Least Octet of AID */
+               uint16_t        mp_btime;       /* Beacon Time */
+               uint16_t        mp_bint;        /* Beacon Interval */
+       } __packed mp[1];                       /* NB: variable size */
+} __packed;
+#endif
+
+/* Portal (MP) Annoucement */
+struct ieee80211_meshpann_ie {
+       uint8_t         pann_ie;                /* IEEE80211_ELEMID_MESHPANN */
+       uint8_t         pann_len;
+       uint8_t         pann_flags;
+       uint8_t         pann_hopcount;
+       uint8_t         pann_ttl;
+       uint8_t         pann_addr[IEEE80211_ADDR_LEN];
+       uint8_t         pann_seq;               /* PANN Sequence Number */
+} __packed;
+
+/* Root (MP) Annoucement */
+struct ieee80211_meshrann_ie {
+       uint8_t         rann_ie;                /* IEEE80211_ELEMID_MESHRANN */
+       uint8_t         rann_len;
+       uint8_t         rann_flags;
+#define        IEEE80211_MESHRANN_FLAGS_PR     0x01    /* Portal Role */
+       uint8_t         rann_hopcount;
+       uint8_t         rann_ttl;
+       uint8_t         rann_addr[IEEE80211_ADDR_LEN];
+       uint32_t        rann_seq;               /* HWMP Sequence Number */
+       uint32_t        rann_metric;
+} __packed;
+
+/* Mesh Path Request */
+struct ieee80211_meshpreq_ie {
+       uint8_t         preq_ie;        /* IEEE80211_ELEMID_MESHPREQ */
+       uint8_t         preq_len;
+       uint8_t         preq_flags;
+#define        IEEE80211_MESHPREQ_FLAGS_PR     0x01    /* Portal Role */
+#define        IEEE80211_MESHPREQ_FLAGS_AM     0x02    /* 0 = ucast / 1 = bcast */
+#define        IEEE80211_MESHPREQ_FLAGS_PP     0x04    /* Proactive PREP */
+#define        IEEE80211_MESHPREQ_FLAGS_AE     0x40    /* Address Extension */
+       uint8_t         preq_hopcount;
+       uint8_t         preq_ttl;
+       uint32_t        preq_id;
+       uint8_t         preq_origaddr[IEEE80211_ADDR_LEN];
+       uint32_t        preq_origseq;   /* HWMP Sequence Number */
+       /* NB: may have Originator Proxied Address */
+       uint32_t        preq_lifetime;
+       uint32_t        preq_metric;
+       uint8_t         preq_tcount;    /* target count */
+       struct {
+               uint8_t         target_flags;
+#define        IEEE80211_MESHPREQ_TFLAGS_TO    0x01    /* Target Only */
+#define        IEEE80211_MESHPREQ_TFLAGS_RF    0x02    /* Reply and Forward */
+#define        IEEE80211_MESHPREQ_TFLAGS_USN   0x04    /* Unknown HWMP seq number */
+               uint8_t         target_addr[IEEE80211_ADDR_LEN];
+               uint32_t        target_seq;     /* HWMP Sequence Number */
+       } __packed preq_targets[1];             /* NB: variable size */
+} __packed;
+
+/* Mesh Path Reply */
+struct ieee80211_meshprep_ie {
+       uint8_t         prep_ie;        /* IEEE80211_ELEMID_MESHPREP */
+       uint8_t         prep_len;
+       uint8_t         prep_flags;
+       uint8_t         prep_hopcount;
+       uint8_t         prep_ttl;
+       uint8_t         prep_targetaddr[IEEE80211_ADDR_LEN];
+       uint32_t        prep_targetseq;
+       /* NB: May have Target Proxied Address */
+       uint32_t        prep_lifetime;
+       uint32_t        prep_metric;
+       uint8_t         prep_origaddr[IEEE80211_ADDR_LEN];
+       uint32_t        prep_origseq;   /* HWMP Sequence Number */
+} __packed;
+
+/* Mesh Path Error */
+struct ieee80211_meshperr_ie {
+       uint8_t         perr_ie;        /* IEEE80211_ELEMID_MESHPERR */
+       uint8_t         perr_len;
+       uint8_t         perr_ttl;
+       uint8_t         perr_ndests;    /* Number of Destinations */
+       struct {
+               uint8_t         dest_flags;
+#define        IEEE80211_MESHPERR_DFLAGS_USN   0x01
+#define        IEEE80211_MESHPERR_DFLAGS_RC    0x02
+               uint8_t         dest_addr[IEEE80211_ADDR_LEN];
+               uint32_t        dest_seq;       /* HWMP Sequence Number */
+               uint16_t        dest_rcode;
+       } __packed perr_dests[1];               /* NB: variable size */
+} __packed;
+
+#ifdef notyet
+/* Mesh Proxy Update */
+struct ieee80211_meshpu_ie {
+       uint8_t         pu_ie;          /* IEEE80211_ELEMID_MESHPU */
+       uint8_t         pu_len;
+       uint8_t         pu_flags;
+#define        IEEE80211_MESHPU_FLAGS_MASK             0x1
+#define        IEEE80211_MESHPU_FLAGS_DEL              0x0
+#define        IEEE80211_MESHPU_FLAGS_ADD              0x1
+       uint8_t         pu_seq;         /* PU Sequence Number */
+       uint8_t         pu_addr[IEEE80211_ADDR_LEN];
+       uint8_t         pu_naddr;       /* Number of Proxied Addresses */
+       /* NB: proxied address follows */
+} __packed;
+
+/* Mesh Proxy Update Confirmation */
+struct ieee80211_meshpuc_ie {
+       uint8_t         puc_ie;         /* IEEE80211_ELEMID_MESHPUC */
+       uint8_t         puc_len;
+       uint8_t         puc_flags;
+       uint8_t         puc_seq;        /* PU Sequence Number */
+       uint8_t         puc_daddr[IEEE80211_ADDR_LEN];
+} __packed;
+#endif
+
+/*
+ * 802.11s Action Frames
+ */
+#define        IEEE80211_ACTION_CAT_MESHPEERING        30      /* XXX Linux */
+#define        IEEE80211_ACTION_CAT_MESHLMETRIC        13
+#define        IEEE80211_ACTION_CAT_MESHPATH           32      /* XXX Linux */
+#define        IEEE80211_ACTION_CAT_INTERWORK          15
+#define        IEEE80211_ACTION_CAT_RESOURCE           16
+#define        IEEE80211_ACTION_CAT_PROXY              17
+
+/*
+ * Mesh Peering Action codes.
+ */
+enum {
+       IEEE80211_ACTION_MESHPEERING_OPEN       = 0,
+       IEEE80211_ACTION_MESHPEERING_CONFIRM    = 1,
+       IEEE80211_ACTION_MESHPEERING_CLOSE      = 2,
+       /* 3-255 reserved */
+};
+
+/*
+ * Mesh Path Selection Action code.
+ */
+enum {
+       IEEE80211_ACTION_MESHPATH_SEL   = 0,
+       /* 1-255 reserved */
+};
+
+/*
+ * Mesh Link Metric Action codes.
+ */
+enum {
+       IEEE80211_ACTION_MESHLMETRIC_REQ = 0,   /* Link Metric Request */
+       IEEE80211_ACTION_MESHLMETRIC_REP = 1,   /* Link Metric Report */
+       /* 2-255 reserved */
+};
+
+/*
+ * Mesh Portal Annoucement Action codes.
+ */
+enum {
+       IEEE80211_ACTION_MESHPANN       = 0,
+       /* 1-255 reserved */
+};
+
+/*
+ * Different mesh control structures based on the AE
+ * (Address Extension) bits.
+ */
+struct ieee80211_meshcntl {
+       uint8_t         mc_flags;       /* Address Extension 00 */
+       uint8_t         mc_ttl;         /* TTL */
+       uint8_t         mc_seq[4];      /* Sequence No. */
+       /* NB: more addresses may follow */
+} __packed;
+
+struct ieee80211_meshcntl_ae01 {
+       uint8_t         mc_flags;       /* Address Extension 01 */
+       uint8_t         mc_ttl;         /* TTL */
+       uint8_t         mc_seq[4];      /* Sequence No. */
+       uint8_t         mc_addr4[IEEE80211_ADDR_LEN];
+} __packed;
+
+struct ieee80211_meshcntl_ae10 {
+       uint8_t         mc_flags;       /* Address Extension 10 */
+       uint8_t         mc_ttl;         /* TTL */
+       uint8_t         mc_seq[4];      /* Sequence No. */
+       uint8_t         mc_addr4[IEEE80211_ADDR_LEN];
+       uint8_t         mc_addr5[IEEE80211_ADDR_LEN];
+} __packed;
+
+struct ieee80211_meshcntl_ae11 {
+       uint8_t         mc_flags;       /* Address Extension 11 */
+       uint8_t         mc_ttl;         /* TTL */
+       uint8_t         mc_seq[4];      /* Sequence No. */
+       uint8_t         mc_addr4[IEEE80211_ADDR_LEN];
+       uint8_t         mc_addr5[IEEE80211_ADDR_LEN];
+       uint8_t         mc_addr6[IEEE80211_ADDR_LEN];
+} __packed;
+
+#ifdef _KERNEL
+MALLOC_DECLARE(M_80211_MESH_RT);
+struct ieee80211_mesh_route {
+       TAILQ_ENTRY(ieee80211_mesh_route)       rt_next;
+       int                     rt_crtime;      /* creation time */
+       uint8_t                 rt_dest[IEEE80211_ADDR_LEN];
+       uint8_t                 rt_nexthop[IEEE80211_ADDR_LEN];
+       uint32_t                rt_metric;      /* path metric */
+       uint16_t                rt_nhops;       /* number of hops */
+       uint16_t                rt_flags;
+#define        IEEE80211_MESHRT_FLAGS_VALID    0x01    /* patch discovery complete */
+#define        IEEE80211_MESHRT_FLAGS_PROXY    0x02    /* proxy entry */
+       uint32_t                rt_lifetime;
+       uint32_t                rt_lastmseq;    /* last seq# seen dest */
+       void                    *rt_priv;       /* private data */
+};
+#define        IEEE80211_MESH_ROUTE_PRIV(rt, cast)     ((cast *)rt->rt_priv)
+
+#define        IEEE80211_MESH_PROTO_DSZ        12      /* description size */
+/*
+ * Mesh Path Selection Protocol.
+ */
+enum ieee80211_state;
+struct ieee80211_mesh_proto_path {
+       uint8_t         mpp_active;
+       char            mpp_descr[IEEE80211_MESH_PROTO_DSZ];
+       uint8_t         mpp_ie;
+       struct ieee80211_node *
+                       (*mpp_discover)(struct ieee80211vap *,
+                               const uint8_t [IEEE80211_ADDR_LEN],
+                               struct mbuf *);
+       void            (*mpp_peerdown)(struct ieee80211_node *);
+       void            (*mpp_vattach)(struct ieee80211vap *);
+       void            (*mpp_vdetach)(struct ieee80211vap *);
+       int             (*mpp_newstate)(struct ieee80211vap *,
+                           enum ieee80211_state, int);
+       const size_t    mpp_privlen;    /* size required in the routing table
+                                          for private data */
+       int             mpp_inact;      /* inact. timeout for invalid routes
+                                          (ticks) */
+};
+
+/*
+ * Mesh Link Metric Report Protocol.
+ */
+struct ieee80211_mesh_proto_metric {
+       uint8_t         mpm_active;
+       char            mpm_descr[IEEE80211_MESH_PROTO_DSZ];
+       uint8_t         mpm_ie;
+       uint32_t        (*mpm_metric)(struct ieee80211_node *);
+};
+
+#ifdef notyet
+/*
+ * Mesh Authentication Protocol.
+ */
+struct ieee80211_mesh_proto_auth {
+       uint8_t         mpa_ie[4];
+};
+
+struct ieee80211_mesh_proto_congestion {
+};
+
+struct ieee80211_mesh_proto_sync {
+};
+#endif
+
+typedef uint32_t ieee80211_mesh_seq;
+#define        IEEE80211_MESH_SEQ_LEQ(a, b)    ((int32_t)((a)-(b)) <= 0)
+#define        IEEE80211_MESH_SEQ_GEQ(a, b)    ((int32_t)((a)-(b)) >= 0)
+
+struct ieee80211_mesh_state {
+       int                             ms_idlen;
+       uint8_t                         ms_id[IEEE80211_MESHID_LEN];
+       ieee80211_mesh_seq              ms_seq; /* seq no for meshcntl */
+       uint16_t                        ms_neighbors;
+       uint8_t                         ms_ttl; /* mesh ttl set in packets */
+#define IEEE80211_MESHFLAGS_AP         0x01    /* accept peers */
+#define IEEE80211_MESHFLAGS_PORTAL     0x02    /* mesh portal role */
+#define IEEE80211_MESHFLAGS_FWD                0x04    /* forward packets */
+       uint8_t                         ms_flags;
+       struct lock                     ms_rt_lock;
+       struct callout                  ms_cleantimer;
+       TAILQ_HEAD(, ieee80211_mesh_route)  ms_routes;
+       struct ieee80211_mesh_proto_metric *ms_pmetric;
+       struct ieee80211_mesh_proto_path   *ms_ppath;
+};
+void           ieee80211_mesh_attach(struct ieee80211com *);
+void           ieee80211_mesh_detach(struct ieee80211com *);
+
+struct ieee80211_mesh_route *
+               ieee80211_mesh_rt_find(struct ieee80211vap *,
+                   const uint8_t [IEEE80211_ADDR_LEN]);
+struct ieee80211_mesh_route *
+                ieee80211_mesh_rt_add(struct ieee80211vap *,
+                   const uint8_t [IEEE80211_ADDR_LEN]);
+void           ieee80211_mesh_rt_del(struct ieee80211vap *,
+                   const uint8_t [IEEE80211_ADDR_LEN]);
+void           ieee80211_mesh_rt_flush(struct ieee80211vap *);
+void           ieee80211_mesh_rt_flush_peer(struct ieee80211vap *,
+                   const uint8_t [IEEE80211_ADDR_LEN]);
+void           ieee80211_mesh_proxy_check(struct ieee80211vap *,
+                   const uint8_t [IEEE80211_ADDR_LEN]);
+
+int            ieee80211_mesh_register_proto_path(const
+                   struct ieee80211_mesh_proto_path *);
+int            ieee80211_mesh_register_proto_metric(const
+                   struct ieee80211_mesh_proto_metric *);
+
+uint8_t *      ieee80211_add_meshid(uint8_t *, struct ieee80211vap *);
+uint8_t *      ieee80211_add_meshconf(uint8_t *, struct ieee80211vap *);
+uint8_t *      ieee80211_add_meshpeer(uint8_t *, uint8_t, uint16_t, uint16_t,
+                   uint16_t);
+uint8_t *      ieee80211_add_meshlmetric(uint8_t *, uint32_t);
+
+void           ieee80211_mesh_node_init(struct ieee80211vap *,
+                   struct ieee80211_node *);
+void           ieee80211_mesh_node_cleanup(struct ieee80211_node *);
+void           ieee80211_parse_meshid(struct ieee80211_node *,
+                   const uint8_t *);
+struct ieee80211_scanparams;
+void           ieee80211_mesh_init_neighbor(struct ieee80211_node *,
+                  const struct ieee80211_frame *,
+                  const struct ieee80211_scanparams *);
+void           ieee80211_mesh_update_beacon(struct ieee80211vap *,
+                   struct ieee80211_beacon_offsets *);
+
+/*
+ * Return non-zero if proxy operation is enabled.
+ */
+static __inline int
+ieee80211_mesh_isproxyena(struct ieee80211vap *vap)
+{
+       struct ieee80211_mesh_state *ms = vap->iv_mesh;
+       return (ms->ms_flags &
+           (IEEE80211_MESHFLAGS_AP | IEEE80211_MESHFLAGS_PORTAL)) != 0;
+}
+
+/*
+ * Process an outbound frame: if a path is known to the
+ * destination then return a reference to the next hop
+ * for immediate transmission.  Otherwise initiate path
+ * discovery and, if possible queue the packet to be
+ * sent when path discovery completes.
+ */
+static __inline struct ieee80211_node *
+ieee80211_mesh_discover(struct ieee80211vap *vap,
+    const uint8_t dest[IEEE80211_ADDR_LEN], struct mbuf *m)
+{
+       struct ieee80211_mesh_state *ms = vap->iv_mesh;
+       return ms->ms_ppath->mpp_discover(vap, dest, m);
+}
+
+#endif /* _KERNEL */
+#endif /* !_NET80211_IEEE80211_MESH_H_ */
diff --git a/sys/netproto/802_11/ieee80211_monitor.h b/sys/netproto/802_11/ieee80211_monitor.h
new file mode 100644 (file)
index 0000000..fe9a5d6
--- /dev/null
@@ -0,0 +1,36 @@
+/*-
+ * Copyright (c) 2007-2008 Sam Leffler, Errno Consulting
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
+ * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
+ * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
+ * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
+ * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
+ * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
+ * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
+ * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ *
+ * $FreeBSD: head/sys/net80211/ieee80211_monitor.h 178354 2008-04-20 20:35:46Z sam $
+ * $DragonFly$
+ */
+#ifndef _NET80211_IEEE80211_MONITOR_H_
+#define _NET80211_IEEE80211_MONITOR_H_
+
+/*
+ * Monitor implementation definitions.
+ */
+void   ieee80211_monitor_attach(struct ieee80211com *);
+void   ieee80211_monitor_detach(struct ieee80211com *);
+#endif /* !_NET80211_IEEE80211_MONITOR_H_ */
index 23d4c60..753adc4 100644 (file)
@@ -1,6 +1,6 @@
-/*
+/*-
  * Copyright (c) 2001 Atsushi Onoe
- * Copyright (c) 2002-2005 Sam Leffler, Errno Consulting
+ * Copyright (c) 2002-2009 Sam Leffler, Errno Consulting
  * All rights reserved.
  *
  * Redistribution and use in source and binary forms, with or without
  * 2. Redistributions in binary form must reproduce the above copyright
  *    notice, this list of conditions and the following disclaimer in the
  *    documentation and/or other materials provided with the distribution.
- * 3. The name of the author may not be used to endorse or promote products
- *    derived from this software without specific prior written permission.
- *
- * Alternatively, this software may be distributed under the terms of the
- * GNU General Public License ("GPL") version 2 as published by the Free
- * Software Foundation.
  *
  * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
  * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
  * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
  * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
  *
- * $FreeBSD: src/sys/net80211/ieee80211_node.h,v 1.17.2.5 2006/03/13 03:05:47 sam Exp $
- * $DragonFly: src/sys/netproto/802_11/ieee80211_node.h,v 1.5 2008/03/04 13:48:40 sephe Exp $
+ * $FreeBSD: head/sys/net80211/ieee80211_node.h 195618 2009-07-11 15:02:45Z rpaulo $
+ * $DragonFly$
  */
 #ifndef _NET80211_IEEE80211_NODE_H_
 #define _NET80211_IEEE80211_NODE_H_
 
 #include <netproto/802_11/ieee80211_ioctl.h>   /* for ieee80211_nodestats */
+#include <netproto/802_11/ieee80211_ht.h>      /* for aggregation state */
 
 /*
- * Each ieee80211com instance has a single timer that fires once a
- * second.  This is used to initiate various work depending on the
- * state of the instance: scanning (passive or active), ``transition''
- * (waiting for a response to a management frame when operating
- * as a station), and node inactivity processing (when operating
- * as an AP).  For inactivity processing each node has a timeout
- * set in it's ni_inact field that is decremented on each timeout
- * and the node is reclaimed when the counter goes to zero.  We
- * use different inactivity timeout values depending on whether
- * the node is associated and authorized (either by 802.1x or
- * open/shared key authentication) or associated but yet to be
- * authorized.  The latter timeout is shorter to more aggressively
+ * Each ieee80211com instance has a single timer that fires every
+ * IEEE80211_INACT_WAIT seconds to handle "inactivity processing".
+ * This is used to do node inactivity processing when operating
+ * as an AP, adhoc or mesh mode.  For inactivity processing each node
+ * has a timeout set in it's ni_inact field that is decremented
+ * on each timeout and the node is reclaimed when the counter goes
+ * to zero.  We use different inactivity timeout values depending
+ * on whether the node is associated and authorized (either by
+ * 802.1x or open/shared key authentication) or associated but yet
+ * to be authorized.  The latter timeout is shorter to more aggressively
  * reclaim nodes that leave part way through the 802.1x exchange.
  */
 #define        IEEE80211_INACT_WAIT    15              /* inactivity interval (secs) */
 #define        IEEE80211_INACT_PROBE   (30/IEEE80211_INACT_WAIT)       /* probe */
 #define        IEEE80211_INACT_SCAN    (300/IEEE80211_INACT_WAIT)      /* scanned */
 
-#define        IEEE80211_TRANS_WAIT    5               /* mgt frame tx timer (secs) */
+#define        IEEE80211_TRANS_WAIT    2               /* mgt frame tx timer (secs) */
+
+/* threshold for aging overlapping non-ERP bss */
+#define        IEEE80211_NONERP_PRESENT_AGE    msecs_to_ticks(60*1000)
 
-#define        IEEE80211_NODE_HASHSIZE 32
+#define        IEEE80211_NODE_HASHSIZE 32              /* NB: hash size must be pow2 */
 /* simple hash is enough for variation of macaddr */
-#define        IEEE80211_NODE_HASH(addr)       \
+#define        IEEE80211_NODE_HASH(ic, addr)   \
        (((const uint8_t *)(addr))[IEEE80211_ADDR_LEN - 1] % \
                IEEE80211_NODE_HASHSIZE)
 
-struct ieee80211_rsnparms {
-       uint8_t         rsn_mcastcipher;        /* mcast/group cipher */
-       uint8_t         rsn_mcastkeylen;        /* mcast key length */
-       uint8_t         rsn_ucastcipherset;     /* unicast cipher set */
-       uint8_t         rsn_ucastcipher;        /* selected unicast cipher */
-       uint8_t         rsn_ucastkeylen;        /* unicast key length */
-       uint8_t         rsn_keymgmtset;         /* key mangement algorithms */
-       uint8_t         rsn_keymgmt;            /* selected key mgmt algo */
-       uint16_t        rsn_caps;               /* capabilities */
-};
-
 struct ieee80211_node_table;
 struct ieee80211com;
+struct ieee80211vap;
+
+/*
+ * Information element ``blob''.  We use this structure
+ * to capture management frame payloads that need to be
+ * retained.  Information elements within the payload that
+ * we need to consult have references recorded.
+ */
+struct ieee80211_ies {
+       /* the following are either NULL or point within data */
+       uint8_t *wpa_ie;        /* captured WPA ie */
+       uint8_t *rsn_ie;        /* captured RSN ie */
+       uint8_t *wme_ie;        /* captured WME ie */
+       uint8_t *ath_ie;        /* captured Atheros ie */
+       uint8_t *htcap_ie;      /* captured HTCAP ie */
+       uint8_t *htinfo_ie;     /* captured HTINFO ie */
+       uint8_t *tdma_ie;       /* captured TDMA ie */
+       uint8_t *meshid_ie;     /* captured MESH ID ie */
+       uint8_t *spare[4];
+       /* NB: these must be the last members of this structure */
+       uint8_t *data;          /* frame data > 802.11 header */
+       int     len;            /* data size in bytes */
+};
+
+/*
+ * 802.11s (Mesh) Peer Link FSM state.
+ */
+enum ieee80211_mesh_mlstate {
+       IEEE80211_NODE_MESH_IDLE        = 0,
+       IEEE80211_NODE_MESH_OPENSNT     = 1,    /* open frame sent */
+       IEEE80211_NODE_MESH_OPENRCV     = 2,    /* open frame received */
+       IEEE80211_NODE_MESH_CONFIRMRCV  = 3,    /* confirm frame received */
+       IEEE80211_NODE_MESH_ESTABLISHED = 4,    /* link established */
+       IEEE80211_NODE_MESH_HOLDING     = 5,    /* link closing */
+};
+#define        IEEE80211_MESH_MLSTATE_BITS \
+       "\20\1IDLE\2OPENSNT\2OPENRCV\3CONFIRMRCV\4ESTABLISHED\5HOLDING"
 
 /*
  * Node specific information.  Note that drivers are expected
@@ -88,35 +110,62 @@ struct ieee80211com;
  * the ieee80211com structure.
  */
 struct ieee80211_node {
-       struct ieee80211com     *ni_ic;
-       struct ieee80211_node_table *ni_table;
-       TAILQ_ENTRY(ieee80211_node)     ni_list;
-       LIST_ENTRY(ieee80211_node)      ni_hash;
-       u_int                   ni_refcnt;
-       uint8_t                 ni_authmode;    /* authentication algorithm */
-       uint16_t                ni_flags;       /* special-purpose state */
-#define        IEEE80211_NODE_AUTH     0x0001          /* authorized for data */
-#define        IEEE80211_NODE_QOS      0x0002          /* QoS enabled */
-#define        IEEE80211_NODE_ERP      0x0004          /* ERP enabled */
+       struct ieee80211vap     *ni_vap;        /* associated vap */
+       struct ieee80211com     *ni_ic;         /* copy from vap to save deref*/
+       struct ieee80211_node_table *ni_table;  /* NB: may be NULL */
+       TAILQ_ENTRY(ieee80211_node) ni_list;    /* list of all nodes */
+       LIST_ENTRY(ieee80211_node) ni_hash;     /* hash collision list */
+       u_int                   ni_refcnt;      /* count of held references */
+       u_int                   ni_scangen;     /* gen# for timeout scan */
+       u_int                   ni_flags;
+#define        IEEE80211_NODE_AUTH     0x000001        /* authorized for data */
+#define        IEEE80211_NODE_QOS      0x000002        /* QoS enabled */
+#define        IEEE80211_NODE_ERP      0x000004        /* ERP enabled */
 /* NB: this must have the same value as IEEE80211_FC1_PWR_MGT */
-#define        IEEE80211_NODE_PWR_MGT  0x0010          /* power save mode enabled */
-#define        IEEE80211_NODE_AREF     0x0020          /* authentication ref held */
-       uint16_t                ni_associd;     /* assoc response */
-       uint16_t                ni_txpower;     /* current transmit power */
+#define        IEEE80211_NODE_PWR_MGT  0x000010        /* power save mode enabled */
+#define        IEEE80211_NODE_AREF     0x000020        /* authentication ref held */
+#define        IEEE80211_NODE_HT       0x000040        /* HT enabled */
+#define        IEEE80211_NODE_HTCOMPAT 0x000080        /* HT setup w/ vendor OUI's */
+#define        IEEE80211_NODE_WPS      0x000100        /* WPS association */
+#define        IEEE80211_NODE_TSN      0x000200        /* TSN association */
+#define        IEEE80211_NODE_AMPDU_RX 0x000400        /* AMPDU rx enabled */
+#define        IEEE80211_NODE_AMPDU_TX 0x000800        /* AMPDU tx enabled */
+#define        IEEE80211_NODE_MIMO_PS  0x001000        /* MIMO power save enabled */
+#define        IEEE80211_NODE_MIMO_RTS 0x002000        /* send RTS in MIMO PS */
+#define        IEEE80211_NODE_RIFS     0x004000        /* RIFS enabled */
+#define        IEEE80211_NODE_SGI20    0x008000        /* Short GI in HT20 enabled */
+#define        IEEE80211_NODE_SGI40    0x010000        /* Short GI in HT40 enabled */
+#define        IEEE80211_NODE_ASSOCID  0x020000        /* xmit requires associd */
+#define        IEEE80211_NODE_AMSDU_RX 0x040000        /* AMSDU rx enabled */
+#define        IEEE80211_NODE_AMSDU_TX 0x080000        /* AMSDU tx enabled */
+       uint16_t                ni_associd;     /* association ID */
        uint16_t                ni_vlan;        /* vlan tag */
+       uint16_t                ni_txpower;     /* current transmit power */
+       uint8_t                 ni_authmode;    /* authentication algorithm */
+       uint8_t                 ni_ath_flags;   /* Atheros feature flags */
+       /* NB: These must have the same values as IEEE80211_ATHC_* */
+#define IEEE80211_NODE_TURBOP  0x0001          /* Turbo prime enable */
+#define IEEE80211_NODE_COMP    0x0002          /* Compresssion enable */
+#define IEEE80211_NODE_FF      0x0004          /* Fast Frame capable */
+#define IEEE80211_NODE_XR      0x0008          /* Atheros WME enable */
+#define IEEE80211_NODE_AR      0x0010          /* AR capable */
+#define IEEE80211_NODE_BOOST   0x0080          /* Dynamic Turbo boosted */
+       uint16_t                ni_ath_defkeyix;/* Atheros def key index */
+       const struct ieee80211_txparam *ni_txparms;
+       uint32_t                ni_jointime;    /* time of join (secs) */
        uint32_t                *ni_challenge;  /* shared-key challenge */
-       uint8_t                 *ni_wpa_ie;     /* captured WPA/RSN ie */
-       uint8_t                 *ni_wme_ie;     /* captured WME ie */
-       uint16_t                ni_txseqs[17];  /* tx seq per-tid */
-       uint16_t                ni_rxseqs[17];  /* rx seq previous per-tid*/
+       struct ieee80211_ies    ni_ies;         /* captured ie's */
+                                               /* tx seq per-tid */
+       ieee80211_seq           ni_txseqs[IEEE80211_TID_SIZE];
+                                               /* rx seq previous per-tid*/
+       ieee80211_seq           ni_rxseqs[IEEE80211_TID_SIZE];
        uint32_t                ni_rxfragstamp; /* time stamp of last rx frag */
        struct mbuf             *ni_rxfrag[3];  /* rx frag reassembly */
-       struct ieee80211_rsnparms ni_rsn;       /* RSN/WPA parameters */
        struct ieee80211_key    ni_ucastkey;    /* unicast key */
 
        /* hardware */
-       uint32_t                ni_rstamp;      /* recv timestamp */
-       uint8_t                 ni_rssi;        /* recv ssi */
+       uint32_t                ni_avgrssi;     /* recv ssi state */
+       int8_t                  ni_noise;       /* noise floor */
 
        /* header */
        uint8_t                 ni_macaddr[IEEE80211_ADDR_LEN];
@@ -125,32 +174,71 @@ struct ieee80211_node {
        /* beacon, probe response */
        union {
                uint8_t         data[8];
-               uint64_t        tsf;
+               u_int64_t       tsf;
        } ni_tstamp;                            /* from last rcv'd beacon */
        uint16_t                ni_intval;      /* beacon interval */
        uint16_t                ni_capinfo;     /* capabilities */
        uint8_t                 ni_esslen;
        uint8_t                 ni_essid[IEEE80211_NWID_LEN];
        struct ieee80211_rateset ni_rates;      /* negotiated rate set */
-       struct ieee80211_channel *ni_chan;      /* XXX multiple uses */
+       struct ieee80211_channel *ni_chan;
        uint16_t                ni_fhdwell;     /* FH only */
        uint8_t                 ni_fhindex;     /* FH only */
-       uint8_t                 ni_erp;         /* ERP from beacon/probe resp */
+       uint16_t                ni_erp;         /* ERP from beacon/probe resp */
        uint16_t                ni_timoff;      /* byte offset to TIM ie */
        uint8_t                 ni_dtim_period; /* DTIM period */
        uint8_t                 ni_dtim_count;  /* DTIM count for last bcn */
 
+       /* 11s state */
+       uint8_t                 ni_meshidlen;
+       uint8_t                 ni_meshid[IEEE80211_MESHID_LEN];
+       enum ieee80211_mesh_mlstate ni_mlstate; /* peering management state */
+       uint16_t                ni_mllid;       /* link local ID */
+       uint16_t                ni_mlpid;       /* link peer ID */
+       struct callout          ni_mltimer;     /* link mesh timer */
+       uint8_t                 ni_mlrcnt;      /* link mesh retry counter */
+       uint8_t                 ni_mltval;      /* link mesh timer value */
+
+       /* 11n state */
+       uint16_t                ni_htcap;       /* HT capabilities */
+       uint8_t                 ni_htparam;     /* HT params */
+       uint8_t                 ni_htctlchan;   /* HT control channel */
+       uint8_t                 ni_ht2ndchan;   /* HT 2nd channel */
+       uint8_t                 ni_htopmode;    /* HT operating mode */
+       uint8_t                 ni_htstbc;      /* HT */
+       uint8_t                 ni_chw;         /* negotiated channel width */
+       struct ieee80211_htrateset ni_htrates;  /* negotiated ht rate set */
+       struct ieee80211_tx_ampdu ni_tx_ampdu[WME_NUM_AC];
+       struct ieee80211_rx_ampdu ni_rx_ampdu[WME_NUM_TID];
+
        /* others */
-       int                     ni_fails;       /* failure count to associate */
        short                   ni_inact;       /* inactivity mark count */
        short                   ni_inact_reload;/* inactivity reload value */
-       int                     ni_txrate;      /* index to ni_rates[] */
-       struct ifqueue          ni_savedq;      /* ps-poll queue */
+       int                     ni_txrate;      /* legacy rate/MCS */
+       struct ieee80211_psq    ni_psq;         /* power save queue */
        struct ieee80211_nodestats ni_stats;    /* per-node statistics */
-       void                    *ni_rate_data;
-       uint32_t                ni_pad[8];      /* future expansion */
+
+       struct ieee80211vap     *ni_wdsvap;     /* associated WDS vap */
+       uint64_t                ni_spare[4];
 };
 MALLOC_DECLARE(M_80211_NODE);
+MALLOC_DECLARE(M_80211_NODE_IE);
+
+#define        IEEE80211_NODE_ATH      (IEEE80211_NODE_FF | IEEE80211_NODE_TURBOP)
+#define        IEEE80211_NODE_AMPDU \
+       (IEEE80211_NODE_AMPDU_RX | IEEE80211_NODE_AMPDU_TX)
+#define        IEEE80211_NODE_AMSDU \
+       (IEEE80211_NODE_AMSDU_RX | IEEE80211_NODE_AMSDU_TX)
+#define        IEEE80211_NODE_HT_ALL \
+       (IEEE80211_NODE_HT | IEEE80211_NODE_HTCOMPAT | \
+        IEEE80211_NODE_AMPDU | IEEE80211_NODE_AMSDU | \
+        IEEE80211_NODE_MIMO_PS | IEEE80211_NODE_MIMO_RTS | \
+        IEEE80211_NODE_RIFS | IEEE80211_NODE_SGI20 | IEEE80211_NODE_SGI40)
+
+#define        IEEE80211_NODE_BITS \
+       "\20\1AUTH\2QOS\3ERP\5PWR_MGT\6AREF\7HT\10HTCOMPAT\11WPS\12TSN" \
+       "\13AMPDU_RX\14AMPDU_TX\15MIMO_PS\16MIMO_RTS\17RIFS\20SGI20\21SGI40" \
+       "\22ASSOCID"
 
 #define        IEEE80211_NODE_AID(ni)  IEEE80211_AID(ni->ni_associd)
 
@@ -158,6 +246,38 @@ MALLOC_DECLARE(M_80211_NODE);
 #define        IEEE80211_NODE_STAT_ADD(ni,stat,v)      (ni->ni_stats.ns_##stat += v)
 #define        IEEE80211_NODE_STAT_SET(ni,stat,v)      (ni->ni_stats.ns_##stat = v)
 
+/*
+ * Filtered rssi calculation support.  The receive rssi is maintained
+ * as an average over the last 10 frames received using a low pass filter
+ * (all frames for now, possibly need to be more selective).  Calculations
+ * are designed such that a good compiler can optimize them.  The avg
+ * rssi state should be initialized to IEEE80211_RSSI_DUMMY_MARKER and
+ * each sample incorporated with IEEE80211_RSSI_LPF.  Use IEEE80211_RSSI_GET
+ * to extract the current value.
+ *
+ * Note that we assume rssi data are in the range [-127..127] and we
+ * discard values <-20.  This is consistent with assumptions throughout
+ * net80211 that signal strength data are in .5 dBm units relative to
+ * the current noise floor (linear, not log).
+ */
+#define IEEE80211_RSSI_LPF_LEN         10
+#define        IEEE80211_RSSI_DUMMY_MARKER     127
+/* NB: pow2 to optimize out * and / */
+#define        IEEE80211_RSSI_EP_MULTIPLIER    (1<<7)
+#define IEEE80211_RSSI_IN(x)           ((x) * IEEE80211_RSSI_EP_MULTIPLIER)
+#define _IEEE80211_RSSI_LPF(x, y, len) \
+    (((x) != IEEE80211_RSSI_DUMMY_MARKER) ? (((x) * ((len) - 1) + (y)) / (len)) : (y))
+#define IEEE80211_RSSI_LPF(x, y) do {                                  \
+    if ((y) >= -20) {                                                  \
+       x = _IEEE80211_RSSI_LPF((x), IEEE80211_RSSI_IN((y)),            \
+               IEEE80211_RSSI_LPF_LEN);                                \
+    }                                                                  \
+} while (0)
+#define        IEEE80211_RSSI_EP_RND(x, mul) \
+       ((((x) % (mul)) >= ((mul)/2)) ? ((x) + ((mul) - 1)) / (mul) : (x)/(mul))
+#define        IEEE80211_RSSI_GET(x) \
+       IEEE80211_RSSI_EP_RND(x, IEEE80211_RSSI_EP_MULTIPLIER)
+
 static __inline struct ieee80211_node *
 ieee80211_ref_node(struct ieee80211_node *ni)
 {
@@ -177,6 +297,9 @@ struct ieee80211com;
 void   ieee80211_node_attach(struct ieee80211com *);
 void   ieee80211_node_lateattach(struct ieee80211com *);
 void   ieee80211_node_detach(struct ieee80211com *);
+void   ieee80211_node_vattach(struct ieee80211vap *);
+void   ieee80211_node_latevattach(struct ieee80211vap *);
+void   ieee80211_node_vdetach(struct ieee80211vap *);
 
 static __inline int
 ieee80211_node_is_authorized(const struct ieee80211_node *ni)
@@ -187,151 +310,147 @@ ieee80211_node_is_authorized(const struct ieee80211_node *ni)
 void   ieee80211_node_authorize(struct ieee80211_node *);
 void   ieee80211_node_unauthorize(struct ieee80211_node *);
 
-void   ieee80211_begin_scan(struct ieee80211com *, int);
-int    ieee80211_next_scan(struct ieee80211com *);
-void   ieee80211_set_scanchan(struct ieee80211com *,
+void   ieee80211_node_setuptxparms(struct ieee80211_node *);
+void   ieee80211_node_set_chan(struct ieee80211_node *,
                struct ieee80211_channel *);
-void   ieee80211_probe_curchan(struct ieee80211com *, int);
-void   ieee80211_create_ibss(struct ieee80211com*, struct ieee80211_channel *);
-void   ieee80211_reset_bss(struct ieee80211com *);
-void   ieee80211_cancel_scan(struct ieee80211com *);
-void   ieee80211_end_scan(struct ieee80211com *);
+void   ieee80211_create_ibss(struct ieee80211vap*, struct ieee80211_channel *);
+void   ieee80211_reset_bss(struct ieee80211vap *);
+void   ieee80211_sync_curchan(struct ieee80211com *);
+void   ieee80211_setupcurchan(struct ieee80211com *,
+           struct ieee80211_channel *);
+void   ieee80211_setcurchan(struct ieee80211com *, struct ieee80211_channel *);
 int    ieee80211_ibss_merge(struct ieee80211_node *);
-int    ieee80211_sta_join(struct ieee80211com *, struct ieee80211_node *);
-void   ieee80211_sta_leave(struct ieee80211com *, struct ieee80211_node *);
-void   ieee80211_update_shpreamble(struct ieee80211com *,
-               const struct ieee80211_node *);
+struct ieee80211_scan_entry;
+int    ieee80211_sta_join(struct ieee80211vap *, struct ieee80211_channel *,
+               const struct ieee80211_scan_entry *);
+void   ieee80211_sta_leave(struct ieee80211_node *);
+void   ieee80211_node_deauth(struct ieee80211_node *, int);
+
+int    ieee80211_ies_init(struct ieee80211_ies *, const uint8_t *, int);
+void   ieee80211_ies_cleanup(struct ieee80211_ies *);
+void   ieee80211_ies_expand(struct ieee80211_ies *);
+#define        ieee80211_ies_setie(_ies, _ie, _off) do {               \
+       (_ies)._ie = (_ies).data + (_off);                      \
+} while (0)
 
 /*
  * Table of ieee80211_node instances.  Each ieee80211com
- * has at least one for holding the scan candidates.
- * When operating as an access point or in ibss mode there
- * is a second table for associated stations or neighbors.
+ * has one that holds association stations (when operating
+ * as an ap) or neighbors (in ibss mode).
+ *
+ * XXX embed this in ieee80211com instead of indirect?
  */
 struct ieee80211_node_table {
        struct ieee80211com     *nt_ic;         /* back reference */
+       ieee80211_node_lock_t   nt_nodelock;    /* on node table */
        TAILQ_HEAD(, ieee80211_node) nt_node;   /* information of all nodes */
        LIST_HEAD(, ieee80211_node) nt_hash[IEEE80211_NODE_HASHSIZE];
-       const char              *nt_name;       /* for debugging */
-       int                     nt_inact_timer; /* inactivity timer */
-       int                     nt_inact_init;  /* initial node inact setting */
        struct ieee80211_node   **nt_keyixmap;  /* key ix -> node map */
        int                     nt_keyixmax;    /* keyixmap size */
-
-       void                    (*nt_timeout)(struct ieee80211_node_table *);
+       const char              *nt_name;       /* table name for debug msgs */
+       ieee80211_scan_lock_t   nt_scanlock;    /* on nt_scangen */
+       u_int                   nt_scangen;     /* gen# for iterators */
+       int                     nt_inact_init;  /* initial node inact setting */
 };
-void   ieee80211_node_table_reset(struct ieee80211_node_table *);
-
-struct ieee80211_node *ieee80211_alloc_node(
-               struct ieee80211_node_table *, const uint8_t *);
-struct ieee80211_node *ieee80211_tmp_node(struct ieee80211com *,
-               const uint8_t *macaddr);
-struct ieee80211_node *ieee80211_dup_bss(struct ieee80211_node_table *,
-               const uint8_t *);
+
+struct ieee80211_node *ieee80211_alloc_node(struct ieee80211_node_table *,
+               struct ieee80211vap *,
+               const uint8_t macaddr[IEEE80211_ADDR_LEN]);
+struct ieee80211_node *ieee80211_tmp_node(struct ieee80211vap *,
+               const uint8_t macaddr[IEEE80211_ADDR_LEN]);
+struct ieee80211_node *ieee80211_dup_bss(struct ieee80211vap *,
+               const uint8_t macaddr[IEEE80211_ADDR_LEN]);
+struct ieee80211_node *ieee80211_node_create_wds(struct ieee80211vap *,
+               const uint8_t bssid[IEEE80211_ADDR_LEN],
+               struct ieee80211_channel *);
 #ifdef IEEE80211_DEBUG_REFCNT
 void   ieee80211_free_node_debug(struct ieee80211_node *,
                const char *func, int line);
-struct ieee80211_node *ieee80211_find_node_debug(
-               struct ieee80211_node_table *, const uint8_t *,
+struct ieee80211_node *ieee80211_find_node_locked_debug(
+               struct ieee80211_node_table *,
+               const uint8_t macaddr[IEEE80211_ADDR_LEN],
                const char *func, int line);
-struct ieee80211_node * ieee80211_find_rxnode_debug(
-               struct ieee80211com *, const struct ieee80211_frame_min *,
+struct ieee80211_node *ieee80211_find_node_debug(struct ieee80211_node_table *,
+               const uint8_t macaddr[IEEE80211_ADDR_LEN],
+               const char *func, int line);
+struct ieee80211_node *ieee80211_find_vap_node_locked_debug(
+               struct ieee80211_node_table *,
+               const struct ieee80211vap *vap,
+               const uint8_t macaddr[IEEE80211_ADDR_LEN],
+               const char *func, int line);
+struct ieee80211_node *ieee80211_find_vap_node_debug(
+               struct ieee80211_node_table *,
+               const struct ieee80211vap *vap,
+               const uint8_t macaddr[IEEE80211_ADDR_LEN],
+               const char *func, int line);
+struct ieee80211_node * ieee80211_find_rxnode_debug(struct ieee80211com *,
+               const struct ieee80211_frame_min *,
                const char *func, int line);
 struct ieee80211_node * ieee80211_find_rxnode_withkey_debug(
                struct ieee80211com *,
                const struct ieee80211_frame_min *, uint16_t keyix,
                const char *func, int line);
-struct ieee80211_node *ieee80211_find_txnode_debug(
-               struct ieee80211com *, const uint8_t *,
-               const char *func, int line);
-struct ieee80211_node *ieee80211_find_node_with_channel_debug(
-               struct ieee80211_node_table *, const uint8_t *macaddr,
-               struct ieee80211_channel *, const char *func, int line);
-struct ieee80211_node *ieee80211_find_node_with_ssid_debug(
-               struct ieee80211_node_table *, const uint8_t *macaddr,
-               u_int ssidlen, const uint8_t *ssid,
+struct ieee80211_node *ieee80211_find_txnode_debug(struct ieee80211vap *,
+               const uint8_t *,
                const char *func, int line);
 #define        ieee80211_free_node(ni) \
        ieee80211_free_node_debug(ni, __func__, __LINE__)
+#define        ieee80211_find_node_locked(nt, mac) \
+       ieee80211_find_node_locked_debug(nt, mac, __func__, __LINE__)
 #define        ieee80211_find_node(nt, mac) \
        ieee80211_find_node_debug(nt, mac, __func__, __LINE__)
-#define        ieee80211_find_rxnode(nt, wh) \
-       ieee80211_find_rxnode_debug(nt, wh, __func__, __LINE__)
-#define        ieee80211_find_rxnode_withkey(nt, wh, keyix) \
-       ieee80211_find_rxnode_withkey_debug(nt, wh, keyix, __func__, __LINE__)
-#define        ieee80211_find_txnode(nt, mac) \
-       ieee80211_find_txnode_debug(nt, mac, __func__, __LINE__)
-#define        ieee80211_find_node_with_channel(nt, mac, c) \
-       ieee80211_find_node_with_channel_debug(nt, mac, c, __func__, __LINE__)
-#define        ieee80211_find_node_with_ssid(nt, mac, sl, ss) \
-       ieee80211_find_node_with_ssid_debug(nt, mac, sl, ss, __func__, __LINE__)
+#define        ieee80211_find_vap_node_locked(nt, vap, mac) \
+       ieee80211_find_vap_node_locked_debug(nt, vap, mac, __func__, __LINE__)
+#define        ieee80211_find_vap_node(nt, vap, mac) \
+       ieee80211_find_vap_node_debug(nt, vap, mac, __func__, __LINE__)
+#define        ieee80211_find_rxnode(ic, wh) \
+       ieee80211_find_rxnode_debug(ic, wh, __func__, __LINE__)
+#define        ieee80211_find_rxnode_withkey(ic, wh, keyix) \
+       ieee80211_find_rxnode_withkey_debug(ic, wh, keyix, __func__, __LINE__)
+#define        ieee80211_find_txnode(vap, mac) \
+       ieee80211_find_txnode_debug(vap, mac, __func__, __LINE__)
 #else
 void   ieee80211_free_node(struct ieee80211_node *);
-struct ieee80211_node *ieee80211_find_node(
-               struct ieee80211_node_table *, const uint8_t *);
-struct ieee80211_node * ieee80211_find_rxnode(
-               struct ieee80211com *, const struct ieee80211_frame_min *);
+struct ieee80211_node *ieee80211_find_node_locked(struct ieee80211_node_table *,
+               const uint8_t macaddr[IEEE80211_ADDR_LEN]);
+struct ieee80211_node *ieee80211_find_node(struct ieee80211_node_table *,
+               const uint8_t macaddr[IEEE80211_ADDR_LEN]);
+struct ieee80211_node *ieee80211_find_vap_node_locked(
+               struct ieee80211_node_table *, const struct ieee80211vap *,
+               const uint8_t macaddr[IEEE80211_ADDR_LEN]);
+struct ieee80211_node *ieee80211_find_vap_node(
+               struct ieee80211_node_table *, const struct ieee80211vap *,
+               const uint8_t macaddr[IEEE80211_ADDR_LEN]);
+struct ieee80211_node * ieee80211_find_rxnode(struct ieee80211com *,
+               const struct ieee80211_frame_min *);
 struct ieee80211_node * ieee80211_find_rxnode_withkey(struct ieee80211com *,
                const struct ieee80211_frame_min *, uint16_t keyix);
-struct ieee80211_node *ieee80211_find_txnode(
-               struct ieee80211com *, const uint8_t *);
-struct ieee80211_node *ieee80211_find_node_with_channel(
-               struct ieee80211_node_table *, const uint8_t *macaddr,
-               struct ieee80211_channel *);
-struct ieee80211_node *ieee80211_find_node_with_ssid(
-               struct ieee80211_node_table *, const uint8_t *macaddr,
-               u_int ssidlen, const uint8_t *ssid);
+struct ieee80211_node *ieee80211_find_txnode(struct ieee80211vap *,
+               const uint8_t macaddr[IEEE80211_ADDR_LEN]);
 #endif
 int    ieee80211_node_delucastkey(struct ieee80211_node *);
+void   ieee80211_node_timeout(void *arg);
 
 typedef void ieee80211_iter_func(void *, struct ieee80211_node *);
 void   ieee80211_iterate_nodes(struct ieee80211_node_table *,
                ieee80211_iter_func *, void *);
 
+void   ieee80211_notify_erp(struct ieee80211com *);
 void   ieee80211_dump_node(struct ieee80211_node_table *,
                struct ieee80211_node *);
 void   ieee80211_dump_nodes(struct ieee80211_node_table *);
 
-struct ieee80211_node *ieee80211_fakeup_adhoc_node(
-               struct ieee80211_node_table *, const uint8_t macaddr[]);
-void   ieee80211_node_join(struct ieee80211com *, struct ieee80211_node *,int);
-void   ieee80211_node_leave(struct ieee80211com *, struct ieee80211_node *);
-uint8_t ieee80211_getrssi(struct ieee80211com *ic);
-
-/*
- * Parameters supplied when adding/updating an entry in a
- * scan cache.  Pointer variables should be set to NULL
- * if no data is available.  Pointer references can be to
- * local data; any information that is saved will be copied.
- * All multi-byte values must be in host byte order.
- */
-struct ieee80211_scanparams {
-       uint16_t        capinfo;        /* 802.11 capabilities */
-       uint16_t        fhdwell;        /* FHSS dwell interval */
-       uint8_t         chan;           /* */
-       uint8_t         bchan;
-       uint8_t         fhindex;
-       uint8_t         erp;
-       uint16_t        bintval;
-       uint8_t         timoff;
-       uint8_t         *tim;
-       uint8_t         *tstamp;
-       uint8_t         *country;
-       uint8_t         *ssid;
-       uint8_t         *rates;
-       uint8_t         *xrates;
-       uint8_t         *wpa;
-       uint8_t         *wme;
-};
-
-void   ieee80211_add_scan(struct ieee80211com *,
-               const struct ieee80211_scanparams *,
-               const struct ieee80211_frame *,
-               int subtype, int rssi, int rstamp);
+struct ieee80211_node *ieee80211_fakeup_adhoc_node(struct ieee80211vap *,
+               const uint8_t macaddr[IEEE80211_ADDR_LEN]);
+struct ieee80211_scanparams;
 void   ieee80211_init_neighbor(struct ieee80211_node *,
                const struct ieee80211_frame *,
                const struct ieee80211_scanparams *);
-struct ieee80211_node *ieee80211_add_neighbor(struct ieee80211com *,
+struct ieee80211_node *ieee80211_add_neighbor(struct ieee80211vap *,
                const struct ieee80211_frame *,
                const struct ieee80211_scanparams *);
+void   ieee80211_node_join(struct ieee80211_node *,int);
+void   ieee80211_node_leave(struct ieee80211_node *);
+int8_t ieee80211_getrssi(struct ieee80211vap *);
+void   ieee80211_getsignal(struct ieee80211vap *, int8_t *, int8_t *);
 #endif /* _NET80211_IEEE80211_NODE_H_ */
diff --git a/sys/netproto/802_11/ieee80211_phy.h b/sys/netproto/802_11/ieee80211_phy.h
new file mode 100644 (file)
index 0000000..8ca0f1a
--- /dev/null
@@ -0,0 +1,156 @@
+/*-
+ * Copyright (c) 2007-2008 Sam Leffler, Errno Consulting
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
+ * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
+ * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
+ * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
+ * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
+ * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
+ * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
+ * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ *
+ * $FreeBSD: head/sys/net80211/ieee80211_phy.h 193072 2009-05-29 23:39:16Z sam $
+ * $DragonFly$
+ */
+
+#ifndef _NET80211_IEEE80211_PHY_H_
+#define _NET80211_IEEE80211_PHY_H_
+
+#ifdef _KERNEL
+/*
+ * IEEE 802.11 PHY-related definitions.
+ */
+
+/*
+ * Contention window (slots).
+ */
+#define IEEE80211_CW_MAX       1023    /* aCWmax */
+#define IEEE80211_CW_MIN_0     31      /* DS/CCK aCWmin, ERP aCWmin(0) */
+#define IEEE80211_CW_MIN_1     15      /* OFDM aCWmin, ERP aCWmin(1) */
+
+/*
+ * SIFS (microseconds).
+ */
+#define IEEE80211_DUR_SIFS     10      /* DS/CCK/ERP SIFS */
+#define IEEE80211_DUR_OFDM_SIFS        16      /* OFDM SIFS */
+
+/*
+ * Slot time (microseconds).
+ */
+#define IEEE80211_DUR_SLOT     20      /* DS/CCK slottime, ERP long slottime */
+#define IEEE80211_DUR_SHSLOT   9       /* ERP short slottime */
+#define IEEE80211_DUR_OFDM_SLOT        9       /* OFDM slottime */
+
+/*
+ * DIFS (microseconds).
+ */
+#define IEEE80211_DUR_DIFS(sifs, slot) ((sifs) + 2 * (slot))
+
+struct ieee80211_channel;
+
+struct ieee80211_rate_table {
+       int             rateCount;              /* NB: for proper padding */
+       uint8_t         rateCodeToIndex[256];   /* back mapping */
+       struct {
+               uint8_t         phy;            /* CCK/OFDM/TURBO */
+               uint32_t        rateKbps;       /* transfer rate in kbs */
+               uint8_t         shortPreamble;  /* mask for enabling short
+                                                * preamble in CCK rate code */
+               uint8_t         dot11Rate;      /* value for supported rates
+                                                * info element of MLME */
+               uint8_t         ctlRateIndex;   /* index of next lower basic
+                                                * rate; used for dur. calcs */
+               uint16_t        lpAckDuration;  /* long preamble ACK dur. */
+               uint16_t        spAckDuration;  /* short preamble ACK dur. */
+       } info[32];
+};
+
+const struct ieee80211_rate_table *ieee80211_get_ratetable(
+                       struct ieee80211_channel *);
+
+static __inline__ uint8_t
+ieee80211_ack_rate(const struct ieee80211_rate_table *rt, uint8_t rate)
+{
+       uint8_t cix = rt->info[rt->rateCodeToIndex[rate]].ctlRateIndex;
+       KASSERT(cix != (uint8_t)-1, ("rate %d has no info", rate));
+       return rt->info[cix].dot11Rate;
+}
+
+static __inline__ uint8_t
+ieee80211_ctl_rate(const struct ieee80211_rate_table *rt, uint8_t rate)
+{
+       uint8_t cix = rt->info[rt->rateCodeToIndex[rate]].ctlRateIndex;
+       KASSERT(cix != (uint8_t)-1, ("rate %d has no info", rate));
+       return rt->info[cix].dot11Rate;
+}
+
+static __inline__ enum ieee80211_phytype
+ieee80211_rate2phytype(const struct ieee80211_rate_table *rt, uint8_t rate)
+{
+       uint8_t rix = rt->rateCodeToIndex[rate];
+       KASSERT(rix != (uint8_t)-1, ("rate %d has no info", rate));
+       return rt->info[rix].phy;
+}
+
+static __inline__ int
+ieee80211_isratevalid(const struct ieee80211_rate_table *rt, uint8_t rate)
+{
+       return rt->rateCodeToIndex[rate] != (uint8_t)-1;
+}
+
+/*
+ * Calculate ACK field for
+ * o  non-fragment data frames
+ * o  management frames
+ * sent using rate, phy and short preamble setting.
+ */
+static __inline__ uint16_t
+ieee80211_ack_duration(const struct ieee80211_rate_table *rt,
+    uint8_t rate, int isShortPreamble)
+{
+       uint8_t rix = rt->rateCodeToIndex[rate];
+
+       KASSERT(rix != (uint8_t)-1, ("rate %d has no info", rate));
+       if (isShortPreamble) {
+               KASSERT(rt->info[rix].spAckDuration != 0,
+                       ("shpreamble ack dur is not computed!\n"));
+               return rt->info[rix].spAckDuration;
+       } else {
+               KASSERT(rt->info[rix].lpAckDuration != 0,
+                       ("lgpreamble ack dur is not computed!\n"));
+               return rt->info[rix].lpAckDuration;
+       }
+}
+
+/*
+ * Compute the time to transmit a frame of length frameLen bytes
+ * using the specified 802.11 rate code, phy, and short preamble
+ * setting.
+ *
+ * NB: SIFS is included.
+ */
+uint16_t       ieee80211_compute_duration(const struct ieee80211_rate_table *,
+                       uint32_t frameLen, uint16_t rate, int isShortPreamble);
+/*
+ * Convert PLCP signal/rate field to 802.11 rate code (.5Mbits/s)
+ */
+uint8_t                ieee80211_plcp2rate(uint8_t, enum ieee80211_phytype);
+/*
+ * Convert 802.11 rate code to PLCP signal.
+ */
+uint8_t                ieee80211_rate2plcp(int, enum ieee80211_phytype);
+#endif /* _KERNEL */
+#endif /* !_NET80211_IEEE80211_PHY_H_ */
diff --git a/sys/netproto/802_11/ieee80211_power.h b/sys/netproto/802_11/ieee80211_power.h
new file mode 100644 (file)
index 0000000..3478e08
--- /dev/null
@@ -0,0 +1,80 @@
+/*-
+ * Copyright (c) 2002-2008 Sam Leffler, Errno Consulting
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
+ * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
+ * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
+ * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
+ * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
+ * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
+ * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
+ * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ *
+ * $FreeBSD: head/sys/net80211/ieee80211_power.h 184288 2008-10-26 01:04:46Z sam $
+ * $DragonFly$
+ */
+#ifndef _NET80211_IEEE80211_POWER_H_
+#define _NET80211_IEEE80211_POWER_H_
+
+struct ieee80211com;
+struct ieee80211vap;
+struct ieee80211_node;
+struct mbuf;
+
+/*
+ * Power save packet queues.  There are two queues, one
+ * for frames coming from the net80211 layer and the other
+ * for frames that come from the driver. Frames from the
+ * driver are expected to have M_ENCAP marked to indicate
+ * they have already been encapsulated and are treated as
+ * higher priority: they are sent first when flushing the
+ * queue on a power save state change or in response to a
+ * ps-poll frame.
+ *
+ * Note that frames sent from the high priority queue are
+ * fed directly to the driver without going through
+ * ieee80211_start again; drivers that send up encap'd
+ * frames are required to handle them when they come back.
+ */
+struct ieee80211_psq {
+       ieee80211_psq_lock_t psq_lock;
+       int     psq_len;
+       int     psq_maxlen;
+       int     psq_drops;
+       struct ieee80211_psq_head {
+               struct mbuf *head;
+               struct mbuf *tail;
+               int len;
+       } psq_head[2];                  /* 2 priorities */
+};
+
+void   ieee80211_psq_init(struct ieee80211_psq *, const char *);
+void   ieee80211_psq_cleanup(struct ieee80211_psq *);
+
+void   ieee80211_power_attach(struct ieee80211com *);
+void   ieee80211_power_detach(struct ieee80211com *);
+void   ieee80211_power_vattach(struct ieee80211vap *);
+void   ieee80211_power_vdetach(struct ieee80211vap *);
+void   ieee80211_power_latevattach(struct ieee80211vap *);
+
+struct mbuf *ieee80211_node_psq_dequeue(struct ieee80211_node *ni, int *qlen);
+int    ieee80211_node_psq_drain(struct ieee80211_node *);
+int    ieee80211_node_psq_age(struct ieee80211_node *);
+int    ieee80211_pwrsave(struct ieee80211_node *, struct mbuf *);
+void   ieee80211_node_pwrsave(struct ieee80211_node *, int enable);
+void   ieee80211_sta_pwrsave(struct ieee80211vap *, int enable);
+
+void   ieee80211_power_poll(struct ieee80211com *);
+#endif /* _NET80211_IEEE80211_POWER_H_ */
index f2639dc..4d8aa43 100644 (file)
@@ -1,6 +1,6 @@
-/*
+/*-
  * Copyright (c) 2001 Atsushi Onoe
- * Copyright (c) 2002-2005 Sam Leffler, Errno Consulting
+ * Copyright (c) 2002-2009 Sam Leffler, Errno Consulting
  * All rights reserved.
  *
  * Redistribution and use in source and binary forms, with or without
  * 2. Redistributions in binary form must reproduce the above copyright
  *    notice, this list of conditions and the following disclaimer in the
  *    documentation and/or other materials provided with the distribution.
- * 3. The name of the author may not be used to endorse or promote products
- *    derived from this software without specific prior written permission.
- *
- * Alternatively, this software may be distributed under the terms of the
- * GNU General Public License ("GPL") version 2 as published by the Free
- * Software Foundation.
  *
  * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
  * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
@@ -29,8 +23,8 @@
  * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
  * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
  *
- * $FreeBSD: src/sys/net80211/ieee80211_proto.h,v 1.11.2.5 2006/02/12 19:00:39 sam Exp $
- * $DragonFly: src/sys/netproto/802_11/ieee80211_proto.h,v 1.13 2007/05/07 14:12:16 sephe Exp $
+ * $FreeBSD: head/sys/net80211/ieee80211_proto.h 199187 2009-11-11 15:00:56Z antoine $
+ * $DragonFly$
  */
 #ifndef _NET80211_IEEE80211_PROTO_H_
 #define _NET80211_IEEE80211_PROTO_H_
@@ -44,57 +38,86 @@ enum ieee80211_state {
        IEEE80211_S_SCAN        = 1,    /* scanning */
        IEEE80211_S_AUTH        = 2,    /* try to authenticate */
        IEEE80211_S_ASSOC       = 3,    /* try to assoc */
-       IEEE80211_S_RUN         = 4,    /* associated */
+       IEEE80211_S_CAC         = 4,    /* doing channel availability check */
+       IEEE80211_S_RUN         = 5,    /* operational (e.g. associated) */
+       IEEE80211_S_CSA         = 6,    /* channel switch announce pending */
+       IEEE80211_S_SLEEP       = 7,    /* power save */
 };
-#define        IEEE80211_S_MAX         (IEEE80211_S_RUN+1)
+#define        IEEE80211_S_MAX         (IEEE80211_S_SLEEP+1)
 
-#define        IEEE80211_SEND_MGMT(_ic,_ni,_type,_arg) \
-       ((*(_ic)->ic_send_mgmt)(_ic, _ni, _type, _arg))
+#define        IEEE80211_SEND_MGMT(_ni,_type,_arg) \
+       ((*(_ni)->ni_ic->ic_send_mgmt)(_ni, _type, _arg))
 
 extern const char *ieee80211_mgt_subtype_name[];
-extern const char *ieee80211_phymode_name[];
+extern const char *ieee80211_phymode_name[IEEE80211_MODE_MAX];
+extern const int ieee80211_opcap[IEEE80211_OPMODE_MAX];
 
 void   ieee80211_proto_attach(struct ieee80211com *);
 void   ieee80211_proto_detach(struct ieee80211com *);
+void   ieee80211_proto_vattach(struct ieee80211vap *);
+void   ieee80211_proto_vdetach(struct ieee80211vap *);
+
+void   ieee80211_syncifflag_locked(struct ieee80211com *, int flag);
+void   ieee80211_syncflag(struct ieee80211vap *, int flag);
+void   ieee80211_syncflag_ht(struct ieee80211vap *, int flag);
+void   ieee80211_syncflag_ext(struct ieee80211vap *, int flag);
 
-struct ieee80211_node;
-struct ieee80211_crypto_iv;
-int    ieee80211_input(struct ieee80211com *, struct mbuf *,
-               struct ieee80211_node *, int, uint32_t);
-int    ieee80211_input_withiv(struct ieee80211com *, struct mbuf *,
-               struct ieee80211_node *, int, uint32_t,
-               const struct ieee80211_crypto_iv *);
-int    ieee80211_setup_rates(struct ieee80211_node *ni,
-               const uint8_t *rates, const uint8_t *xrates,
-               int flags, int join);
-void   ieee80211_saveie(uint8_t **, const uint8_t *);
-void   ieee80211_recv_mgmt(struct ieee80211com *, struct mbuf *,
-               struct ieee80211_node *, int, int, uint32_t);
+#define        ieee80211_input(ni, m, rssi, nf) \
+       ((ni)->ni_vap->iv_input(ni, m, rssi, nf))
+int    ieee80211_input_all(struct ieee80211com *, struct mbuf *, int, int);
+struct ieee80211_bpf_params;
+int    ieee80211_mgmt_output(struct ieee80211_node *, struct mbuf *, int,
+               struct ieee80211_bpf_params *);
+int    ieee80211_raw_xmit(struct ieee80211_node *, struct mbuf *,
+               const struct ieee80211_bpf_params *);
+int    ieee80211_output(struct ifnet *, struct mbuf *,
+               struct sockaddr *, struct route *ro);
+void   ieee80211_send_setup(struct ieee80211_node *, struct mbuf *, int, int,
+        const uint8_t [IEEE80211_ADDR_LEN], const uint8_t [IEEE80211_ADDR_LEN],
+        const uint8_t [IEEE80211_ADDR_LEN]);
+void   ieee80211_start(struct ifnet *);
 int    ieee80211_send_nulldata(struct ieee80211_node *);
+int    ieee80211_classify(struct ieee80211_node *, struct mbuf *m);
+struct mbuf *ieee80211_mbuf_adjust(struct ieee80211vap *, int,
+               struct ieee80211_key *, struct mbuf *);
+struct mbuf *ieee80211_encap(struct ieee80211vap *, struct ieee80211_node *,
+               struct mbuf *);
+int    ieee80211_send_mgmt(struct ieee80211_node *, int, int);
+struct ieee80211_appie;
 int    ieee80211_send_probereq(struct ieee80211_node *ni,
                const uint8_t sa[IEEE80211_ADDR_LEN],
                const uint8_t da[IEEE80211_ADDR_LEN],
                const uint8_t bssid[IEEE80211_ADDR_LEN],
-               const uint8_t *ssid, size_t ssidlen,
-               const void *optie, size_t optielen);
-int    ieee80211_send_mgmt(struct ieee80211com *, struct ieee80211_node *,
-               int, int);
-int    ieee80211_classify(struct ieee80211com *, struct mbuf *,
-               struct ieee80211_node *);
-struct mbuf *ieee80211_encap(struct ieee80211com *, struct mbuf *,
-               struct ieee80211_node *);
-void   ieee80211_pwrsave(struct ieee80211com *, struct ieee80211_node *, 
-               struct mbuf *);
+               const uint8_t *ssid, size_t ssidlen);
+/*
+ * The formation of ProbeResponse frames requires guidance to
+ * deal with legacy clients.  When the client is identified as
+ * "legacy 11b" ieee80211_send_proberesp is passed this token.
+ */
+#define        IEEE80211_SEND_LEGACY_11B       0x1     /* legacy 11b client */
+#define        IEEE80211_SEND_LEGACY_11        0x2     /* other legacy client */
+#define        IEEE80211_SEND_LEGACY           0x3     /* any legacy client */
+struct mbuf *ieee80211_alloc_proberesp(struct ieee80211_node *, int);
+int    ieee80211_send_proberesp(struct ieee80211vap *,
+               const uint8_t da[IEEE80211_ADDR_LEN], int);
+struct mbuf *ieee80211_alloc_rts(struct ieee80211com *ic,
+               const uint8_t [IEEE80211_ADDR_LEN],
+               const uint8_t [IEEE80211_ADDR_LEN], uint16_t);
+struct mbuf *ieee80211_alloc_cts(struct ieee80211com *,
+               const uint8_t [IEEE80211_ADDR_LEN], uint16_t);
+
+uint8_t *ieee80211_add_rates(uint8_t *, const struct ieee80211_rateset *);
+uint8_t *ieee80211_add_xrates(uint8_t *, const struct ieee80211_rateset *);
+uint16_t ieee80211_getcapinfo(struct ieee80211vap *,
+               struct ieee80211_channel *);
 
 void   ieee80211_reset_erp(struct ieee80211com *);
-void   ieee80211_set_shortslottime(struct ieee80211com *, int);
-void   ieee80211_set_shortpreamble(struct ieee80211com *, int);
-int    ieee80211_iserp_rateset(struct ieee80211com *,
-               const struct ieee80211_rateset *);
-void   ieee80211_set_basicrates(struct ieee80211_rateset *,
-               enum ieee80211_phymode, int);
-int    ieee80211_copy_basicrates(struct ieee80211_rateset *,
-               const struct ieee80211_rateset *);
+void   ieee80211_set_shortslottime(struct ieee80211com *, int onoff);
+int    ieee80211_iserp_rateset(const struct ieee80211_rateset *);
+void   ieee80211_setbasicrates(struct ieee80211_rateset *,
+               enum ieee80211_phymode);
+void   ieee80211_addbasicrates(struct ieee80211_rateset *,
+               enum ieee80211_phymode);
 
 /*
  * Return the size of the 802.11 header for a management or data frame.
@@ -108,7 +131,7 @@ ieee80211_hdrsize(const void *data)
        /* NB: we don't handle control frames */
        KASSERT((wh->i_fc[0]&IEEE80211_FC0_TYPE_MASK) != IEEE80211_FC0_TYPE_CTL,
                ("%s: control frame", __func__));
-       if ((wh->i_fc[1] & IEEE80211_FC1_DIR_MASK) == IEEE80211_FC1_DIR_DSTODS)
+       if (IEEE80211_IS_DSTODS(wh))
                size += IEEE80211_ADDR_LEN;
        if (IEEE80211_QOS_HAS_SEQ(wh))
                size += sizeof(uint16_t);
@@ -116,7 +139,7 @@ ieee80211_hdrsize(const void *data)
 }
 
 /*
- * Return the size of the 802.11 header; handles any type of frame.
+ * Like ieee80211_hdrsize, but handles any type of frame.
  */
 static __inline int
 ieee80211_anyhdrsize(const void *data)
@@ -128,6 +151,8 @@ ieee80211_anyhdrsize(const void *data)
                case IEEE80211_FC0_SUBTYPE_CTS:
                case IEEE80211_FC0_SUBTYPE_ACK:
                        return sizeof(struct ieee80211_frame_ack);
+               case IEEE80211_FC0_SUBTYPE_BAR:
+                       return sizeof(struct ieee80211_frame_bar);
                }
                return sizeof(struct ieee80211_frame_min);
        } else
@@ -137,16 +162,16 @@ ieee80211_anyhdrsize(const void *data)
 /*
  * Template for an in-kernel authenticator.  Authenticators
  * register with the protocol code and are typically loaded
- * as separate modules as needed.
+ * as separate modules as needed.  One special authenticator
+ * is xauth; it intercepts requests so that protocols like
+ * WPA can be handled in user space.
  */
 struct ieee80211_authenticator {
        const char *ia_name;            /* printable name */
-       int     (*ia_attach)(struct ieee80211com *);
-       void    (*ia_detach)(struct ieee80211com *);
-       void    (*ia_node_join)(struct ieee80211com *,
-                               struct ieee80211_node *);
-       void    (*ia_node_leave)(struct ieee80211com *,
-                               struct ieee80211_node *);
+       int     (*ia_attach)(struct ieee80211vap *);
+       void    (*ia_detach)(struct ieee80211vap *);
+       void    (*ia_node_join)(struct ieee80211_node *);
+       void    (*ia_node_leave)(struct ieee80211_node *);
 };
 void   ieee80211_authenticator_register(int type,
                const struct ieee80211_authenticator *);
@@ -157,23 +182,23 @@ struct ieee80211req;
 /*
  * Template for an MAC ACL policy module.  Such modules
  * register with the protocol code and are passed the sender's
- * address of each received frame for validation.
+ * address of each received auth frame for validation.
  */
 struct ieee80211_aclator {
        const char *iac_name;           /* printable name */
-       int     (*iac_attach)(struct ieee80211com *);
-       void    (*iac_detach)(struct ieee80211com *);
-       int     (*iac_check)(struct ieee80211com *,
+       int     (*iac_attach)(struct ieee80211vap *);
+       void    (*iac_detach)(struct ieee80211vap *);
+       int     (*iac_check)(struct ieee80211vap *,
                        const uint8_t mac[IEEE80211_ADDR_LEN]);
-       int     (*iac_add)(struct ieee80211com *,
+       int     (*iac_add)(struct ieee80211vap *,
                        const uint8_t mac[IEEE80211_ADDR_LEN]);
-       int     (*iac_remove)(struct ieee80211com *,
+       int     (*iac_remove)(struct ieee80211vap *,
                        const uint8_t mac[IEEE80211_ADDR_LEN]);
-       int     (*iac_flush)(struct ieee80211com *);
-       int     (*iac_setpolicy)(struct ieee80211com *, int);
-       int     (*iac_getpolicy)(struct ieee80211com *);
-       int     (*iac_setioctl)(struct ieee80211com *, struct ieee80211req *);
-       int     (*iac_getioctl)(struct ieee80211com *, struct ieee80211req *);
+       int     (*iac_flush)(struct ieee80211vap *);
+       int     (*iac_setpolicy)(struct ieee80211vap *, int);
+       int     (*iac_getpolicy)(struct ieee80211vap *);
+       int     (*iac_setioctl)(struct ieee80211vap *, struct ieee80211req *);
+       int     (*iac_getioctl)(struct ieee80211vap *, struct ieee80211req *);
 };
 void   ieee80211_aclator_register(const struct ieee80211_aclator *);
 void   ieee80211_aclator_unregister(const struct ieee80211_aclator *);
@@ -181,10 +206,14 @@ const struct ieee80211_aclator *ieee80211_aclator_get(const char *name);
 
 /* flags for ieee80211_fix_rate() */
 #define        IEEE80211_F_DOSORT      0x00000001      /* sort rate list */
-#define        IEEE80211_F_DOFRATE     0x00000002      /* use fixed rate */
+#define        IEEE80211_F_DOFRATE     0x00000002      /* use fixed legacy rate */
 #define        IEEE80211_F_DONEGO      0x00000004      /* calc negotiated rate */
 #define        IEEE80211_F_DODEL       0x00000008      /* delete ignore rate */
-int    ieee80211_fix_rate(struct ieee80211_node *ni, int flags, int join);
+#define        IEEE80211_F_DOBRS       0x00000010      /* check basic rate set */
+#define        IEEE80211_F_JOIN        0x00000020      /* sta joining our bss */
+#define        IEEE80211_F_DOFMCS      0x00000040      /* use fixed HT rate */
+int    ieee80211_fix_rate(struct ieee80211_node *,
+               struct ieee80211_rateset *, int);
 
 /*
  * WME/WMM support.
@@ -221,17 +250,49 @@ struct ieee80211_wme_state {
        int     (*wme_update)(struct ieee80211com *);
 };
 
-void   ieee80211_wme_initparams(struct ieee80211com *);
-void   ieee80211_wme_updateparams(struct ieee80211com *);
+void   ieee80211_wme_initparams(struct ieee80211vap *);
+void   ieee80211_wme_updateparams(struct ieee80211vap *);
+void   ieee80211_wme_updateparams_locked(struct ieee80211vap *);
 
-#define        ieee80211_new_state(_ic, _nstate, _arg) \
-       (((_ic)->ic_newstate)((_ic), (_nstate), (_arg)))
-void   ieee80211_reset_state(struct ieee80211com *, enum ieee80211_state);
+/*
+ * Return the WME TID from a QoS frame.  If no TID
+ * is present return the index for the "non-QoS" entry.
+ */
+static __inline uint8_t
+ieee80211_gettid(const struct ieee80211_frame *wh)
+{
+       uint8_t tid;
+
+       if (IEEE80211_QOS_HAS_SEQ(wh)) {
+               if (IEEE80211_IS_DSTODS(wh))
+                       tid = ((const struct ieee80211_qosframe_addr4 *)wh)->
+                               i_qos[0];
+               else
+                       tid = ((const struct ieee80211_qosframe *)wh)->i_qos[0];
+               tid &= IEEE80211_QOS_TID;
+       } else
+               tid = IEEE80211_NONQOS_TID;
+       return tid;
+}
+
+void   ieee80211_waitfor_parent(struct ieee80211com *);
+void   ieee80211_start_locked(struct ieee80211vap *);
+void   ieee80211_init(void *);
+void   ieee80211_start_all(struct ieee80211com *);
+void   ieee80211_stop_locked(struct ieee80211vap *);
+void   ieee80211_stop(struct ieee80211vap *);
+void   ieee80211_stop_all(struct ieee80211com *);
+void   ieee80211_suspend_all(struct ieee80211com *);
+void   ieee80211_resume_all(struct ieee80211com *);
+void   ieee80211_dturbo_switch(struct ieee80211vap *, int newflags);
+void   ieee80211_swbmiss(void *arg);
 void   ieee80211_beacon_miss(struct ieee80211com *);
+int    ieee80211_new_state(struct ieee80211vap *, enum ieee80211_state, int);
 void   ieee80211_print_essid(const uint8_t *, int);
-void   ieee80211_print_rateset(const struct ieee80211_rateset *);
-void   ieee80211_dump_pkt(const uint8_t *, int, int, int);
+void   ieee80211_dump_pkt(struct ieee80211com *,
+               const uint8_t *, int, int, int);
 
+extern         const char *ieee80211_opmode_name[];
 extern const char *ieee80211_state_name[IEEE80211_S_MAX];
 extern const char *ieee80211_wme_acnames[];
 
@@ -241,36 +302,87 @@ extern    const char *ieee80211_wme_acnames[];
  * can update the frame later w/ minimal overhead.
  */
 struct ieee80211_beacon_offsets {
+       uint8_t         bo_flags[4];    /* update/state flags */
        uint16_t        *bo_caps;       /* capabilities */
+       uint8_t         *bo_cfp;        /* start of CFParms element */
        uint8_t         *bo_tim;        /* start of atim/dtim */
        uint8_t         *bo_wme;        /* start of WME parameters */
-       uint8_t         *bo_trailer;    /* start of fixed-size trailer */
+       uint8_t         *bo_tdma;       /* start of TDMA parameters */
+       uint8_t         *bo_tim_trailer;/* start of fixed-size trailer */
        uint16_t        bo_tim_len;     /* atim/dtim length in bytes */
-       uint16_t        bo_trailer_len; /* trailer length in bytes */
+       uint16_t        bo_tim_trailer_len;/* tim trailer length in bytes */
        uint8_t         *bo_erp;        /* start of ERP element */
-       void            *bo_pad[8];     /* future expansion */
+       uint8_t         *bo_htinfo;     /* start of HT info element */
+       uint8_t         *bo_ath;        /* start of ATH parameters */
+       uint8_t         *bo_appie;      /* start of AppIE element */
+       uint16_t        bo_appie_len;   /* AppIE length in bytes */
+       uint16_t        bo_csa_trailer_len;
+       uint8_t         *bo_csa;        /* start of CSA element */
+       uint8_t         *bo_meshconf;   /* start of MESHCONF element */
+       uint8_t         *bo_spare[3];
 };
-struct mbuf *ieee80211_beacon_alloc(struct ieee80211com *,
-               struct ieee80211_node *, struct ieee80211_beacon_offsets *);
-int    ieee80211_beacon_update(struct ieee80211com *,
-               struct ieee80211_node *, struct ieee80211_beacon_offsets *,
-               struct mbuf *, int broadcast);
+struct mbuf *ieee80211_beacon_alloc(struct ieee80211_node *,
+               struct ieee80211_beacon_offsets *);
 
-struct mbuf *ieee80211_probe_resp_alloc(struct ieee80211com *,
-               struct ieee80211_node *);
+/*
+ * Beacon frame updates are signaled through calls to iv_update_beacon
+ * with one of the IEEE80211_BEACON_* tokens defined below.  For devices
+ * that construct beacon frames on the host this can trigger a rebuild
+ * or defer the processing.  For devices that offload beacon frame
+ * handling this callback can be used to signal a rebuild.  The bo_flags
+ * array in the ieee80211_beacon_offsets structure is intended to record
+ * deferred processing requirements; ieee80211_beacon_update uses the
+ * state to optimize work.  Since this structure is owned by the driver
+ * and not visible to the 802.11 layer drivers must supply an iv_update_beacon
+ * callback that marks the flag bits and schedules (as necessary) an update.
+ */
+enum {
+       IEEE80211_BEACON_CAPS   = 0,    /* capabilities */
+       IEEE80211_BEACON_TIM    = 1,    /* DTIM/ATIM */
+       IEEE80211_BEACON_WME    = 2,
+       IEEE80211_BEACON_ERP    = 3,    /* Extended Rate Phy */
+       IEEE80211_BEACON_HTINFO = 4,    /* HT Information */
+       IEEE80211_BEACON_APPIE  = 5,    /* Application IE's */
+       IEEE80211_BEACON_CFP    = 6,    /* CFParms */
+       IEEE80211_BEACON_CSA    = 7,    /* Channel Switch Announcement */
+       IEEE80211_BEACON_TDMA   = 9,    /* TDMA Info */
+       IEEE80211_BEACON_ATH    = 10,   /* ATH parameters */
+       IEEE80211_BEACON_MESHCONF = 11, /* Mesh Configuration */
+};
+int    ieee80211_beacon_update(struct ieee80211_node *,
+               struct ieee80211_beacon_offsets *, struct mbuf *, int mcast);
 
-uint8_t                ieee80211_ack_rate(struct ieee80211_node *, uint8_t);
-uint16_t       ieee80211_txtime(struct ieee80211_node *, u_int, uint8_t,
-                                uint32_t);
+void   ieee80211_csa_startswitch(struct ieee80211com *,
+               struct ieee80211_channel *, int mode, int count);
+void   ieee80211_csa_completeswitch(struct ieee80211com *);
+void   ieee80211_csa_cancelswitch(struct ieee80211com *);
+void   ieee80211_cac_completeswitch(struct ieee80211vap *);
 
 /*
  * Notification methods called from the 802.11 state machine.
  * Note that while these are defined here, their implementation
  * is OS-specific.
  */
-void   ieee80211_notify_node_join(struct ieee80211com *,
-               struct ieee80211_node *, int newassoc);
-void   ieee80211_notify_node_leave(struct ieee80211com *,
-               struct ieee80211_node *);
-void   ieee80211_notify_scan_done(struct ieee80211com *);
+void   ieee80211_notify_node_join(struct ieee80211_node *, int newassoc);
+void   ieee80211_notify_node_leave(struct ieee80211_node *);
+void   ieee80211_notify_scan_done(struct ieee80211vap *);
+void   ieee80211_notify_wds_discover(struct ieee80211_node *);
+void   ieee80211_notify_csa(struct ieee80211com *,
+               const struct ieee80211_channel *, int mode, int count);
+void   ieee80211_notify_radar(struct ieee80211com *,
+               const struct ieee80211_channel *);
+enum ieee80211_notify_cac_event {
+       IEEE80211_NOTIFY_CAC_START  = 0, /* CAC timer started */
+       IEEE80211_NOTIFY_CAC_STOP   = 1, /* CAC intentionally stopped */
+       IEEE80211_NOTIFY_CAC_RADAR  = 2, /* CAC stopped due to radar detectio */
+       IEEE80211_NOTIFY_CAC_EXPIRE = 3, /* CAC expired w/o radar */
+};
+void   ieee80211_notify_cac(struct ieee80211com *,
+               const struct ieee80211_channel *,
+               enum ieee80211_notify_cac_event);
+void   ieee80211_notify_node_deauth(struct ieee80211_node *);
+void   ieee80211_notify_node_auth(struct ieee80211_node *);
+void   ieee80211_notify_country(struct ieee80211vap *, const uint8_t [],
+               const uint8_t cc[2]);
+void   ieee80211_notify_radio(struct ieee80211com *, int);
 #endif /* _NET80211_IEEE80211_PROTO_H_ */
index e8c0936..075a08c 100644 (file)
@@ -1,8 +1,8 @@
-/* $FreeBSD: src/sys/net80211/ieee80211_radiotap.h,v 1.5.2.1 2006/01/29 07:13:58 sam Exp $ */
-/* $NetBSD: ieee80211_radiotap.h,v 1.10 2005/01/04 00:34:58 dyoung Exp $ */
-/* $DragonFly: src/sys/netproto/802_11/ieee80211_radiotap.h,v 1.3 2006/12/25 14:42:36 sephe Exp $ */
+/* $DragonFly$ */
+/* $FreeBSD: head/sys/net80211/ieee80211_radiotap.h 174568 2007-12-13 01:23:40Z sam $ */
+/* $NetBSD: ieee80211_radiotap.h,v 1.16 2007/01/06 05:51:15 dyoung Exp $ */
 
-/*
+/*-
  * Copyright (c) 2003, 2004 David Young.  All rights reserved.
  *
  * Redistribution and use in source and binary forms, with or without
  * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY
  * OF SUCH DAMAGE.
  */
-#ifndef _NET_IF_IEEE80211RADIOTAP_H_
-#define _NET_IF_IEEE80211RADIOTAP_H_
+#ifndef _NET80211_IEEE80211_RADIOTAP_H_
+#define _NET80211_IEEE80211_RADIOTAP_H_
 
-/*
- * A generic radio capture format is desirable. It must be
+/* A generic radio capture format is desirable. It must be
  * rigidly defined (e.g., units for fields should be given),
  * and easily extensible.
  *
 #endif
 #endif /* defined(__KERNEL__) || defined(_KERNEL) */
 
-/*
- * XXX tcpdump/libpcap do not tolerate variable-length headers,
- * yet, so we pad every radiotap header to 64 bytes. Ugh.
- */
-#define IEEE80211_RADIOTAP_HDRLEN      64
+#define        IEEE80211_RADIOTAP_HDRLEN       64      /* XXX deprecated */
 
 /*
  * The radio capture header precedes the 802.11 header.
@@ -105,9 +100,10 @@ struct ieee80211_radiotap_header {
  *      For frequency-hopping radios, the hop set (first byte)
  *      and pattern (second byte).
  *
- * IEEE80211_RADIOTAP_RATE              uint8_t         500kb/s
+ * IEEE80211_RADIOTAP_RATE              uint8_t         500kb/s or index
  *
- *      Tx/Rx data rate
+ *      Tx/Rx data rate.  If bit 0x80 is set then it represents an
+ *     an MCS index and not an IEEE rate.
  *
  * IEEE80211_RADIOTAP_DBM_ANTSIGNAL     int8_t          decibels from
  *                                                      one milliwatt (dBm)
@@ -166,6 +162,17 @@ struct ieee80211_radiotap_header {
  *
  *      Unitless indication of the Rx/Tx antenna for this packet.
  *      The first antenna is antenna 0.
+ *
+ * IEEE80211_RADIOTAP_XCHANNEL          uint32_t        bitmap
+ *                                      uint16_t        MHz
+ *                                      uint8_t         channel number
+ *                                      int8_t          .5 dBm
+ *
+ *      Extended channel specification: flags (see below) followed by
+ *      frequency in MHz, the corresponding IEEE channel number, and
+ *      finally the maximum regulatory transmit power cap in .5 dBm
+ *      units.  This property supersedes IEEE80211_RADIOTAP_CHANNEL
+ *      and only one of the two should be present.
  */
 enum ieee80211_radiotap_type {
        IEEE80211_RADIOTAP_TSFT = 0,
@@ -182,19 +189,25 @@ enum ieee80211_radiotap_type {
        IEEE80211_RADIOTAP_ANTENNA = 11,
        IEEE80211_RADIOTAP_DB_ANTSIGNAL = 12,
        IEEE80211_RADIOTAP_DB_ANTNOISE = 13,
+       /* NB: gap for netbsd definitions */
+       IEEE80211_RADIOTAP_XCHANNEL = 18,
        IEEE80211_RADIOTAP_EXT = 31,
 };
 
 #ifndef _KERNEL
-/* Channel flags. */
-#define        IEEE80211_CHAN_TURBO    0x0010  /* Turbo channel */
-#define        IEEE80211_CHAN_CCK      0x0020  /* CCK channel */
-#define        IEEE80211_CHAN_OFDM     0x0040  /* OFDM channel */
-#define        IEEE80211_CHAN_2GHZ     0x0080  /* 2 GHz spectrum channel. */
-#define        IEEE80211_CHAN_5GHZ     0x0100  /* 5 GHz spectrum channel */
-#define        IEEE80211_CHAN_PASSIVE  0x0200  /* Only passive scan allowed */
-#define        IEEE80211_CHAN_DYN      0x0400  /* Dynamic CCK-OFDM channel */
-#define        IEEE80211_CHAN_GFSK     0x0800  /* GFSK channel (FHSS PHY) */
+/* channel attributes */
+#define        IEEE80211_CHAN_TURBO    0x00000010 /* Turbo channel */
+#define        IEEE80211_CHAN_CCK      0x00000020 /* CCK channel */
+#define        IEEE80211_CHAN_OFDM     0x00000040 /* OFDM channel */
+#define        IEEE80211_CHAN_2GHZ     0x00000080 /* 2 GHz spectrum channel. */
+#define        IEEE80211_CHAN_5GHZ     0x00000100 /* 5 GHz spectrum channel */
+#define        IEEE80211_CHAN_PASSIVE  0x00000200 /* Only passive scan allowed */
+#define        IEEE80211_CHAN_DYN      0x00000400 /* Dynamic CCK-OFDM channel */
+#define        IEEE80211_CHAN_GFSK     0x00000800 /* GFSK channel (FHSS PHY) */
+#define        IEEE80211_CHAN_GSM      0x00001000 /* 900 MHz spectrum channel */
+#define        IEEE80211_CHAN_STURBO   0x00002000 /* 11a static turbo channel only */
+#define        IEEE80211_CHAN_HALF     0x00004000 /* Half rate channel */
+#define        IEEE80211_CHAN_QUARTER  0x00008000 /* Quarter rate channel */
 #endif /* !_KERNEL */
 
 /* For IEEE80211_RADIOTAP_FLAGS */
@@ -217,5 +230,6 @@ enum ieee80211_radiotap_type {
                                                 * (to 32-bit boundary)
                                                 */
 #define        IEEE80211_RADIOTAP_F_BADFCS     0x40    /* does not pass FCS check */
+#define        IEEE80211_RADIOTAP_F_SHORTGI    0x80    /* HT short GI */
 
-#endif /* _NET_IF_IEEE80211RADIOTAP_H_ */
+#endif /* !_NET80211_IEEE80211_RADIOTAP_H_ */
diff --git a/sys/netproto/802_11/ieee80211_regdomain.h b/sys/netproto/802_11/ieee80211_regdomain.h
new file mode 100644 (file)
index 0000000..933b23e
--- /dev/null
@@ -0,0 +1,283 @@
+/*-
+ * Copyright (c) 2005-2008 Sam Leffler, Errno Consulting
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
+ * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
+ * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
+ * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
+ * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
+ * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
+ * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
+ * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ *
+ * $FreeBSD: head/sys/net80211/ieee80211_regdomain.h 187799 2009-01-27 23:09:55Z sam $
+ * $DragonFly$
+ */
+#ifndef _NET80211_IEEE80211_REGDOMAIN_H_
+#define _NET80211_IEEE80211_REGDOMAIN_H_
+
+/*
+ * 802.11 regulatory domain definitions.
+ */
+
+/*
+ * ISO 3166 Country/Region Codes
+ * http://ftp.ics.uci.edu/pub/ietf/http/related/iso3166.txt
+ */
+enum ISOCountryCode {
+       CTRY_AFGHANISTAN        = 4,
+       CTRY_ALBANIA            = 8,    /* Albania */
+       CTRY_ALGERIA            = 12,   /* Algeria */
+       CTRY_AMERICAN_SAMOA     = 16,
+       CTRY_ANDORRA            = 20,
+       CTRY_ANGOLA             = 24,
+       CTRY_ANGUILLA           = 660,
+       CTRY_ANTARTICA          = 10,
+       CTRY_ANTIGUA            = 28,   /* Antigua and Barbuda */
+       CTRY_ARGENTINA          = 32,   /* Argentina */
+       CTRY_ARMENIA            = 51,   /* Armenia */
+       CTRY_ARUBA              = 533,  /* Aruba */
+       CTRY_AUSTRALIA          = 36,   /* Australia */
+       CTRY_AUSTRIA            = 40,   /* Austria */
+       CTRY_AZERBAIJAN         = 31,   /* Azerbaijan */
+       CTRY_BAHAMAS            = 44,   /* Bahamas */
+       CTRY_BAHRAIN            = 48,   /* Bahrain */
+       CTRY_BANGLADESH         = 50,   /* Bangladesh */
+       CTRY_BARBADOS           = 52,
+       CTRY_BELARUS            = 112,  /* Belarus */
+       CTRY_BELGIUM            = 56,   /* Belgium */
+       CTRY_BELIZE             = 84,
+       CTRY_BENIN              = 204,
+       CTRY_BERMUDA            = 60,
+       CTRY_BHUTAN             = 64,
+       CTRY_BOLIVIA            = 68,   /* Bolivia */
+       CTRY_BOSNIA_AND_HERZEGOWINA = 70,
+       CTRY_BOTSWANA           = 72,
+       CTRY_BOUVET_ISLAND      = 74,
+       CTRY_BRAZIL             = 76,   /* Brazil */
+       CTRY_BRITISH_INDIAN_OCEAN_TERRITORY = 86,
+       CTRY_BRUNEI_DARUSSALAM  = 96,   /* Brunei Darussalam */
+       CTRY_BULGARIA           = 100,  /* Bulgaria */
+       CTRY_BURKINA_FASO       = 854,
+       CTRY_BURUNDI            = 108,
+       CTRY_CAMBODIA           = 116,
+       CTRY_CAMEROON           = 120,
+       CTRY_CANADA             = 124,  /* Canada */
+       CTRY_CAPE_VERDE         = 132,
+       CTRY_CAYMAN_ISLANDS     = 136,
+       CTRY_CENTRAL_AFRICAN_REPUBLIC = 140,
+       CTRY_CHAD               = 148,
+       CTRY_CHILE              = 152,  /* Chile */
+       CTRY_CHINA              = 156,  /* People's Republic of China */
+       CTRY_CHRISTMAS_ISLAND   = 162,
+       CTRY_COCOS_ISLANDS      = 166,
+       CTRY_COLOMBIA           = 170,  /* Colombia */
+       CTRY_COMOROS            = 174,
+       CTRY_CONGO              = 178,
+       CTRY_COOK_ISLANDS       = 184,
+       CTRY_COSTA_RICA         = 188,  /* Costa Rica */
+       CTRY_COTE_DIVOIRE       = 384,
+       CTRY_CROATIA            = 191,  /* Croatia (local name: Hrvatska) */
+       CTRY_CYPRUS             = 196,  /* Cyprus */
+       CTRY_CZECH              = 203,  /* Czech Republic */
+       CTRY_DENMARK            = 208,  /* Denmark */
+       CTRY_DJIBOUTI           = 262,
+       CTRY_DOMINICA           = 212,
+       CTRY_DOMINICAN_REPUBLIC = 214,  /* Dominican Republic */
+       CTRY_EAST_TIMOR         = 626,
+       CTRY_ECUADOR            = 218,  /* Ecuador */
+       CTRY_EGYPT              = 818,  /* Egypt */
+       CTRY_EL_SALVADOR        = 222,  /* El Salvador */
+       CTRY_EQUATORIAL_GUINEA  = 226,
+       CTRY_ERITREA            = 232,
+       CTRY_ESTONIA            = 233,  /* Estonia */
+       CTRY_ETHIOPIA           = 210,
+       CTRY_FALKLAND_ISLANDS   = 238,  /* (Malvinas) */
+       CTRY_FAEROE_ISLANDS     = 234,  /* Faeroe Islands */
+       CTRY_FIJI               = 242,
+       CTRY_FINLAND            = 246,  /* Finland */
+       CTRY_FRANCE             = 250,  /* France */
+       CTRY_FRANCE2            = 255,  /* France (Metropolitan) */
+       CTRY_FRENCH_GUIANA      = 254,
+       CTRY_FRENCH_POLYNESIA   = 258,
+       CTRY_FRENCH_SOUTHERN_TERRITORIES        = 260,
+       CTRY_GABON              = 266,
+       CTRY_GAMBIA             = 270,
+       CTRY_GEORGIA            = 268,  /* Georgia */
+       CTRY_GERMANY            = 276,  /* Germany */
+       CTRY_GHANA              = 288,
+       CTRY_GIBRALTAR          = 292,
+       CTRY_GREECE             = 300,  /* Greece */
+       CTRY_GREENLAND          = 304,
+       CTRY_GRENADA            = 308,
+       CTRY_GUADELOUPE         = 312,
+       CTRY_GUAM               = 316,
+       CTRY_GUATEMALA          = 320,  /* Guatemala */
+       CTRY_GUINEA             = 324,
+       CTRY_GUINEA_BISSAU      = 624,
+       CTRY_GUYANA             = 328,
+       /* XXX correct remainder */
+       CTRY_HAITI              = 332,
+       CTRY_HONDURAS           = 340,  /* Honduras */
+       CTRY_HONG_KONG          = 344,  /* Hong Kong S.A.R., P.R.C. */
+       CTRY_HUNGARY            = 348,  /* Hungary */
+       CTRY_ICELAND            = 352,  /* Iceland */
+       CTRY_INDIA              = 356,  /* India */
+       CTRY_INDONESIA          = 360,  /* Indonesia */
+       CTRY_IRAN               = 364,  /* Iran */
+       CTRY_IRAQ               = 368,  /* Iraq */
+       CTRY_IRELAND            = 372,  /* Ireland */
+       CTRY_ISRAEL             = 376,  /* Israel */
+       CTRY_ITALY              = 380,  /* Italy */
+       CTRY_JAMAICA            = 388,  /* Jamaica */
+       CTRY_JAPAN              = 392,  /* Japan */
+       CTRY_JORDAN             = 400,  /* Jordan */
+       CTRY_KAZAKHSTAN         = 398,  /* Kazakhstan */
+       CTRY_KENYA              = 404,  /* Kenya */
+       CTRY_KOREA_NORTH        = 408,  /* North Korea */
+       CTRY_KOREA_ROC          = 410,  /* South Korea */
+       CTRY_KOREA_ROC2         = 411,  /* South Korea */
+       CTRY_KUWAIT             = 414,  /* Kuwait */
+       CTRY_LATVIA             = 428,  /* Latvia */
+       CTRY_LEBANON            = 422,  /* Lebanon */
+       CTRY_LIBYA              = 434,  /* Libya */
+       CTRY_LIECHTENSTEIN      = 438,  /* Liechtenstein */
+       CTRY_LITHUANIA          = 440,  /* Lithuania */
+       CTRY_LUXEMBOURG         = 442,  /* Luxembourg */
+       CTRY_MACAU              = 446,  /* Macau */
+       CTRY_MACEDONIA          = 807,  /* the Former Yugoslav Republic of Macedonia */
+       CTRY_MALAYSIA           = 458,  /* Malaysia */
+       CTRY_MALTA              = 470,  /* Malta */
+       CTRY_MEXICO             = 484,  /* Mexico */
+       CTRY_MONACO             = 492,  /* Principality of Monaco */
+       CTRY_MOROCCO            = 504,  /* Morocco */
+       CTRY_NEPAL              = 524,  /* Nepal */
+       CTRY_NETHERLANDS        = 528,  /* Netherlands */
+       CTRY_NEW_ZEALAND        = 554,  /* New Zealand */
+       CTRY_NICARAGUA          = 558,  /* Nicaragua */
+       CTRY_NORWAY             = 578,  /* Norway */
+       CTRY_OMAN               = 512,  /* Oman */
+       CTRY_PAKISTAN           = 586,  /* Islamic Republic of Pakistan */
+       CTRY_PANAMA             = 591,  /* Panama */
+       CTRY_PARAGUAY           = 600,  /* Paraguay */
+       CTRY_PERU               = 604,  /* Peru */
+       CTRY_PHILIPPINES        = 608,  /* Republic of the Philippines */
+       CTRY_POLAND             = 616,  /* Poland */
+       CTRY_PORTUGAL           = 620,  /* Portugal */
+       CTRY_PUERTO_RICO        = 630,  /* Puerto Rico */
+       CTRY_QATAR              = 634,  /* Qatar */
+       CTRY_ROMANIA            = 642,  /* Romania */
+       CTRY_RUSSIA             = 643,  /* Russia */
+       CTRY_SAUDI_ARABIA       = 682,  /* Saudi Arabia */
+       CTRY_SINGAPORE          = 702,  /* Singapore */
+       CTRY_SLOVAKIA           = 703,  /* Slovak Republic */
+       CTRY_SLOVENIA           = 705,  /* Slovenia */
+       CTRY_SOUTH_AFRICA       = 710,  /* South Africa */
+       CTRY_SPAIN              = 724,  /* Spain */
+       CTRY_SRILANKA           = 144,  /* Sri Lanka */
+       CTRY_SWEDEN             = 752,  /* Sweden */
+       CTRY_SWITZERLAND        = 756,  /* Switzerland */
+       CTRY_SYRIA              = 760,  /* Syria */
+       CTRY_TAIWAN             = 158,  /* Taiwan */
+       CTRY_THAILAND           = 764,  /* Thailand */
+       CTRY_TRINIDAD_Y_TOBAGO  = 780,  /* Trinidad y Tobago */
+       CTRY_TUNISIA            = 788,  /* Tunisia */
+       CTRY_TURKEY             = 792,  /* Turkey */
+       CTRY_UAE                = 784,  /* U.A.E. */
+       CTRY_UKRAINE            = 804,  /* Ukraine */
+       CTRY_UNITED_KINGDOM     = 826,  /* United Kingdom */
+       CTRY_UNITED_STATES      = 840,  /* United States */
+       CTRY_URUGUAY            = 858,  /* Uruguay */
+       CTRY_UZBEKISTAN         = 860,  /* Uzbekistan */
+       CTRY_VENEZUELA          = 862,  /* Venezuela */
+       CTRY_VIET_NAM           = 704,  /* Viet Nam */
+       CTRY_YEMEN              = 887,  /* Yemen */
+       CTRY_ZIMBABWE           = 716,  /* Zimbabwe */
+
+       /* NB: from here down not listed in 3166; they come from Atheros */
+       CTRY_DEBUG              = 0x1ff, /* debug */
+       CTRY_DEFAULT            = 0,     /* default */
+
+       CTRY_UNITED_STATES_FCC49 = 842, /* United States (Public Safety)*/
+       CTRY_KOREA_ROC3         = 412,  /* South Korea */
+
+       CTRY_JAPAN1             = 393,  /* Japan (JP1) */
+       CTRY_JAPAN2             = 394,  /* Japan (JP0) */
+       CTRY_JAPAN3             = 395,  /* Japan (JP1-1) */
+       CTRY_JAPAN4             = 396,  /* Japan (JE1) */
+       CTRY_JAPAN5             = 397,  /* Japan (JE2) */
+       CTRY_JAPAN6             = 399,  /* Japan (JP6) */
+       CTRY_JAPAN7             = 4007, /* Japan (J7) */
+       CTRY_JAPAN8             = 4008, /* Japan (J8) */
+       CTRY_JAPAN9             = 4009, /* Japan (J9) */
+       CTRY_JAPAN10            = 4010, /* Japan (J10) */
+       CTRY_JAPAN11            = 4011, /* Japan (J11) */
+       CTRY_JAPAN12            = 4012, /* Japan (J12) */
+       CTRY_JAPAN13            = 4013, /* Japan (J13) */
+       CTRY_JAPAN14            = 4014, /* Japan (J14) */
+       CTRY_JAPAN15            = 4015, /* Japan (J15) */
+       CTRY_JAPAN16            = 4016, /* Japan (J16) */
+       CTRY_JAPAN17            = 4017, /* Japan (J17) */
+       CTRY_JAPAN18            = 4018, /* Japan (J18) */
+       CTRY_JAPAN19            = 4019, /* Japan (J19) */
+       CTRY_JAPAN20            = 4020, /* Japan (J20) */
+       CTRY_JAPAN21            = 4021, /* Japan (J21) */
+       CTRY_JAPAN22            = 4022, /* Japan (J22) */
+       CTRY_JAPAN23            = 4023, /* Japan (J23) */
+       CTRY_JAPAN24            = 4024, /* Japan (J24) */
+};
+
+enum RegdomainCode {
+       SKU_FCC                 = 0x10, /* FCC, aka United States */
+       SKU_CA                  = 0x20, /* North America, aka Canada */
+       SKU_ETSI                = 0x30, /* Europe */
+       SKU_ETSI2               = 0x32, /* Europe w/o HT40 in 5GHz */
+       SKU_ETSI3               = 0x33, /* Europe - channel 36 */
+       SKU_FCC3                = 0x3a, /* FCC w/5470 band, 11h, DFS */
+       SKU_JAPAN               = 0x40,
+       SKU_KOREA               = 0x45,
+       SKU_APAC                = 0x50, /* Asia Pacific */
+       SKU_APAC2               = 0x51, /* Asia Pacific w/ DFS on mid-band */
+       SKU_APAC3               = 0x5d, /* Asia Pacific w/o ISM band */
+       SKU_ROW                 = 0x81, /* China/Taiwan/Rest of World */
+       SKU_NONE                = 0xf0, /* "Region Free" */
+       SKU_DEBUG               = 0x1ff,
+
+       /* NB: from here down private */
+       SKU_SR9                 = 0x0298, /* Ubiquiti SR9 (900MHz/GSM) */
+       SKU_XR9                 = 0x0299, /* Ubiquiti XR9 (900MHz/GSM) */
+       SKU_GZ901               = 0x029a, /* Zcomax GZ-901 (900MHz/GSM) */
+};
+
+#if defined(__KERNEL__) || defined(_KERNEL)
+struct ieee80211com;
+void   ieee80211_regdomain_attach(struct ieee80211com *);
+void   ieee80211_regdomain_detach(struct ieee80211com *);
+struct ieee80211vap;
+void   ieee80211_regdomain_vattach(struct ieee80211vap *);
+void   ieee80211_regdomain_vdetach(struct ieee80211vap *);
+
+struct ieee80211_regdomain;
+int    ieee80211_init_channels(struct ieee80211com *,
+           const struct ieee80211_regdomain *, const uint8_t bands[]);
+struct ieee80211_channel;
+void   ieee80211_sort_channels(struct ieee80211_channel *chans, int nchans);
+struct ieee80211_appie;
+struct ieee80211_appie *ieee80211_alloc_countryie(struct ieee80211com *);
+struct ieee80211_regdomain_req;
+int    ieee80211_setregdomain(struct ieee80211vap *,
+           struct ieee80211_regdomain_req *);
+#endif /* defined(__KERNEL__) || defined(_KERNEL) */
+#endif /* _NET80211_IEEE80211_REGDOMAIN_H_ */
diff --git a/sys/netproto/802_11/ieee80211_rssadapt.h b/sys/netproto/802_11/ieee80211_rssadapt.h
new file mode 100644 (file)
index 0000000..7424cd0
--- /dev/null
@@ -0,0 +1,102 @@
+/* $DragonFly$ */
+/*     $FreeBSD: head/sys/net80211/ieee80211_rssadapt.h 178354 2008-04-20 20:35:46Z sam $      */
+/* $NetBSD: ieee80211_rssadapt.h,v 1.4 2005/02/26 22:45:09 perry Exp $ */
+/*-
+ * Copyright (c) 2003, 2004 David Young.  All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or
+ * without modification, are permitted provided that the following
+ * conditions are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above
+ *    copyright notice, this list of conditions and the following
+ *    disclaimer in the documentation and/or other materials provided
+ *    with the distribution.
+ * 3. The name of David Young may not be used to endorse or promote
+ *    products derived from this software without specific prior
+ *    written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY David Young ``AS IS'' AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO,
+ * THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A
+ * PARTICULAR PURPOSE ARE DISCLAIMED.  IN NO EVENT SHALL David
+ * Young BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
+ * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED
+ * TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
+ * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
+ * OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
+ * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY
+ * OF SUCH DAMAGE.
+ */
+#ifndef _NET80211_IEEE80211_RSSADAPT_H_
+#define _NET80211_IEEE80211_RSSADAPT_H_
+
+/* Data-rate adaptation loosely based on "Link Adaptation Strategy
+ * for IEEE 802.11 WLAN via Received Signal Strength Measurement"
+ * by Javier del Prado Pavon and Sunghyun Choi.
+ */
+
+/* Buckets for frames 0-128 bytes long, 129-1024, 1025-maximum. */
+#define        IEEE80211_RSSADAPT_BKTS         3
+#define IEEE80211_RSSADAPT_BKT0                128
+#define        IEEE80211_RSSADAPT_BKTPOWER     3       /* 2**_BKTPOWER */
+
+struct ieee80211_rssadapt {
+       struct ieee80211vap *vap;
+       int     interval;                       /* update interval (ticks) */
+};
+
+struct ieee80211_rssadapt_node {
+       struct ieee80211_rssadapt *ra_rs;       /* backpointer */
+       struct ieee80211_rateset ra_rates;      /* negotiated rates */
+       int     ra_rix;                         /* current rate index */
+       int     ra_ticks;                       /* time of last update */
+       int     ra_last_raise;                  /* time of last rate raise */
+       int     ra_raise_interval;              /* rate raise time threshold */
+
+       /* Tx failures in this update interval */
+       uint32_t                ra_nfail;
+       /* Tx successes in this update interval */
+       uint32_t                ra_nok;
+       /* exponential average packets/second */
+       uint32_t                ra_pktrate;
+       /* RSSI threshold for each Tx rate */
+       uint16_t                ra_rate_thresh[IEEE80211_RSSADAPT_BKTS]
+                                             [IEEE80211_RATE_SIZE];
+};
+
+void   ieee80211_rssadapt_init(struct ieee80211_rssadapt *,
+           struct ieee80211vap *, int);
+void   ieee80211_rssadapt_cleanup(struct ieee80211_rssadapt *);
+void   ieee80211_rssadapt_setinterval(struct ieee80211_rssadapt *, int);
+void   ieee80211_rssadapt_node_init(struct ieee80211_rssadapt *,
+           struct ieee80211_rssadapt_node *, struct ieee80211_node *);
+int    ieee80211_rssadapt_choose(struct ieee80211_node *,
+           struct ieee80211_rssadapt_node *, u_int);
+
+/* NB: these are public only for the inline below */
+void   ieee80211_rssadapt_raise_rate(struct ieee80211_rssadapt_node *,
+           int pktlen, int rssi);
+void   ieee80211_rssadapt_lower_rate(struct ieee80211_rssadapt_node *,
+           int pktlen, int rssi);
+
+#define        IEEE80211_RSSADAPT_SUCCESS      1
+#define        IEEE80211_RSSADAPT_FAILURE      0
+
+static __inline void
+ieee80211_rssadapt_tx_complete(struct ieee80211_rssadapt_node *ra,
+    int success, int pktlen, int rssi)
+{
+       if (success) {
+               ra->ra_nok++;
+               if ((ra->ra_rix + 1) < ra->ra_rates.rs_nrates &&
+                   (ticks - ra->ra_last_raise) >= ra->ra_raise_interval)
+                       ieee80211_rssadapt_raise_rate(ra, pktlen, rssi);
+       } else {
+               ra->ra_nfail++;
+               ieee80211_rssadapt_lower_rate(ra, pktlen, rssi);
+       }
+}
+#endif /* _NET80211_IEEE80211_RSSADAPT_H_ */
diff --git a/sys/netproto/802_11/ieee80211_scan.h b/sys/netproto/802_11/ieee80211_scan.h
new file mode 100644 (file)
index 0000000..495e577
--- /dev/null
@@ -0,0 +1,302 @@
+/*-
+ * Copyright (c) 2005-2009 Sam Leffler, Errno Consulting
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
+ * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
+ * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
+ * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
+ * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
+ * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
+ * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
+ * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ *
+ * $FreeBSD: head/sys/net80211/ieee80211_scan.h 195618 2009-07-11 15:02:45Z rpaulo $
+ * $DragonFly$
+ */
+#ifndef _NET80211_IEEE80211_SCAN_H_
+#define _NET80211_IEEE80211_SCAN_H_
+
+/*
+ * 802.11 scanning support.
+ *
+ * Scanning is the procedure by which a station locates a bss to join
+ * (infrastructure/ibss mode), or a channel to use (when operating as
+ * an ap or ibss master).  Scans are either "active" or "passive".  An
+ * active scan causes one or more probe request frames to be sent on
+ * visiting each channel.  A passive request causes each channel in the
+ * scan set to be visited but no frames to be transmitted; the station
+ * only listens for traffic.  Note that active scanning may still need
+ * to listen for traffic before sending probe request frames depending
+ * on regulatory constraints; the 802.11 layer handles this by generating
+ * a callback when scanning on a ``passive channel'' when the
+ * IEEE80211_FEXT_PROBECHAN flag is set.
+ *
+ * A scan operation involves constructing a set of channels to inspect
+ * (the scan set), visiting each channel and collecting information
+ * (e.g. what bss are present), and then analyzing the results to make
+ * decisions like which bss to join.  This process needs to be as fast
+ * as possible so we do things like intelligently construct scan sets
+ * and dwell on a channel only as long as necessary.  The scan code also
+ * maintains a cache of recent scan results and uses it to bypass scanning
+ * whenever possible.  The scan cache is also used to enable roaming
+ * between access points when operating in infrastructure mode.
+ *
+ * Scanning is handled with pluggable modules that implement "policy"
+ * per-operating mode.  The core scanning support provides an
+ * instrastructure to support these modules and exports a common api
+ * to the rest of the 802.11 layer.  Policy modules decide what
+ * channels to visit, what state to record to make decisions (e.g. ap
+ * mode scanning for auto channel selection keeps significantly less
+ * state than sta mode scanning for an ap to associate to), and selects
+ * the final station/channel to return as the result of a scan.
+ *
+ * Scanning is done synchronously when initially bringing a vap to an
+ * operational state and optionally in the background to maintain the
+ * scan cache for doing roaming and rogue ap monitoring.  Scanning is
+ * not tied to the 802.11 state machine that governs vaps though there
+ * is linkage to the IEEE80211_SCAN state.  Only one vap at a time may
+ * be scanning; this scheduling policy is handled in ieee80211_new_state
+ * and is invisible to the scanning code.
+*/
+#define        IEEE80211_SCAN_MAX      IEEE80211_CHAN_MAX
+
+struct ieee80211_scanner;                      /* scan policy state */
+
+struct ieee80211_scan_ssid {
+       int      len;                           /* length in bytes */
+       uint8_t ssid[IEEE80211_NWID_LEN];       /* ssid contents */
+};
+#define        IEEE80211_SCAN_MAX_SSID 1               /* max # ssid's to probe */
+
+/*
+ * Scan state visible to the 802.11 layer.  Scan parameters and
+ * results are stored in this data structure.  The ieee80211_scan_state
+ * structure is extended with space that is maintained private to
+ * the core scanning support.  We allocate one instance and link it
+ * to the ieee80211com structure; then share it between all associated
+ * vaps.  We could allocate multiple of these, e.g. to hold multiple
+ * scan results, but this is sufficient for current needs.
+ */
+struct ieee80211_scan_state {
+       struct ieee80211vap *ss_vap;
+       struct ieee80211com *ss_ic;
+       const struct ieee80211_scanner *ss_ops; /* policy hookup, see below */
+       void            *ss_priv;               /* scanner private state */
+       uint16_t        ss_flags;
+#define        IEEE80211_SCAN_NOPICK   0x0001          /* scan only, no selection */
+#define        IEEE80211_SCAN_ACTIVE   0x0002          /* active scan (probe req) */
+#define        IEEE80211_SCAN_PICK1ST  0x0004          /* ``hey sailor'' mode */
+#define        IEEE80211_SCAN_BGSCAN   0x0008          /* bg scan, exit ps at end */
+#define        IEEE80211_SCAN_ONCE     0x0010          /* do one complete pass */
+#define        IEEE80211_SCAN_NOBCAST  0x0020          /* no broadcast probe req */
+#define        IEEE80211_SCAN_NOJOIN   0x0040          /* no auto-sequencing */
+#define        IEEE80211_SCAN_GOTPICK  0x1000          /* got candidate, can stop */
+       uint8_t         ss_nssid;               /* # ssid's to probe/match */
+       struct ieee80211_scan_ssid ss_ssid[IEEE80211_SCAN_MAX_SSID];
+                                               /* ssid's to probe/match */
+                                               /* ordered channel set */
+       struct ieee80211_channel *ss_chans[IEEE80211_SCAN_MAX];
+       uint16_t        ss_next;                /* ix of next chan to scan */
+       uint16_t        ss_last;                /* ix+1 of last chan to scan */
+       unsigned long   ss_mindwell;            /* min dwell on channel */
+       unsigned long   ss_maxdwell;            /* max dwell on channel */
+};
+
+/*
+ * The upper 16 bits of the flags word is used to communicate
+ * information to the scanning code that is NOT recorded in
+ * ss_flags.  It might be better to split this stuff out into
+ * a separate variable to avoid confusion.
+ */
+#define        IEEE80211_SCAN_FLUSH    0x00010000      /* flush candidate table */
+#define        IEEE80211_SCAN_NOSSID   0x80000000      /* don't update ssid list */
+
+struct ieee80211com;
+void   ieee80211_scan_attach(struct ieee80211com *);
+void   ieee80211_scan_detach(struct ieee80211com *);
+void   ieee80211_scan_vattach(struct ieee80211vap *);
+void   ieee80211_scan_vdetach(struct ieee80211vap *);
+
+void   ieee80211_scan_dump_channels(const struct ieee80211_scan_state *);
+
+#define        IEEE80211_SCAN_FOREVER  0x7fffffff
+int    ieee80211_start_scan(struct ieee80211vap *, int flags,
+               u_int duration, u_int mindwell, u_int maxdwell,
+               u_int nssid, const struct ieee80211_scan_ssid ssids[]);
+int    ieee80211_check_scan(struct ieee80211vap *, int flags,
+               u_int duration, u_int mindwell, u_int maxdwell,
+               u_int nssid, const struct ieee80211_scan_ssid ssids[]);
+int    ieee80211_check_scan_current(struct ieee80211vap *);
+int    ieee80211_bg_scan(struct ieee80211vap *, int);
+void   ieee80211_cancel_scan(struct ieee80211vap *);
+void   ieee80211_cancel_anyscan(struct ieee80211vap *);
+void   ieee80211_scan_next(struct ieee80211vap *);
+void   ieee80211_scan_done(struct ieee80211vap *);
+void   ieee80211_probe_curchan(struct ieee80211vap *, int);
+struct ieee80211_channel *ieee80211_scan_pickchannel(struct ieee80211com *, int);
+
+struct ieee80211_scanparams;
+void   ieee80211_add_scan(struct ieee80211vap *,
+               const struct ieee80211_scanparams *,
+               const struct ieee80211_frame *,
+               int subtype, int rssi, int noise);
+void   ieee80211_scan_timeout(struct ieee80211com *);
+
+void   ieee80211_scan_assoc_success(struct ieee80211vap *,
+               const uint8_t mac[IEEE80211_ADDR_LEN]);
+enum {
+       IEEE80211_SCAN_FAIL_TIMEOUT     = 1,    /* no response to mgmt frame */
+       IEEE80211_SCAN_FAIL_STATUS      = 2     /* negative response to " " */
+};
+void   ieee80211_scan_assoc_fail(struct ieee80211vap *,
+               const uint8_t mac[IEEE80211_ADDR_LEN], int reason);
+void   ieee80211_scan_flush(struct ieee80211vap *);
+
+struct ieee80211_scan_entry;
+typedef void ieee80211_scan_iter_func(void *,
+               const struct ieee80211_scan_entry *);
+void   ieee80211_scan_iterate(struct ieee80211vap *,
+               ieee80211_scan_iter_func, void *);
+enum {
+       IEEE80211_BPARSE_BADIELEN       = 0x01, /* ie len past end of frame */
+       IEEE80211_BPARSE_RATES_INVALID  = 0x02, /* invalid RATES ie */
+       IEEE80211_BPARSE_XRATES_INVALID = 0x04, /* invalid XRATES ie */
+       IEEE80211_BPARSE_SSID_INVALID   = 0x08, /* invalid SSID ie */
+       IEEE80211_BPARSE_CHAN_INVALID   = 0x10, /* invalid FH/DSPARMS chan */
+       IEEE80211_BPARSE_OFFCHAN        = 0x20, /* DSPARMS chan != curchan */
+       IEEE80211_BPARSE_BINTVAL_INVALID= 0x40, /* invalid beacon interval */
+       IEEE80211_BPARSE_CSA_INVALID    = 0x80, /* invalid CSA ie */
+};
+
+/*
+ * Parameters supplied when adding/updating an entry in a
+ * scan cache.  Pointer variables should be set to NULL
+ * if no data is available.  Pointer references can be to
+ * local data; any information that is saved will be copied.
+ * All multi-byte values must be in host byte order.
+ */
+struct ieee80211_scanparams {
+       uint8_t         status;         /* bitmask of IEEE80211_BPARSE_* */
+       uint8_t         chan;           /* channel # from FH/DSPARMS */
+       uint8_t         bchan;          /* curchan's channel # */
+       uint8_t         fhindex;
+       uint16_t        fhdwell;        /* FHSS dwell interval */
+       uint16_t        capinfo;        /* 802.11 capabilities */
+       uint16_t        erp;            /* NB: 0x100 indicates ie present */
+       uint16_t        bintval;
+       uint8_t         timoff;
+       uint8_t         *ies;           /* all captured ies */
+       size_t          ies_len;        /* length of all captured ies */
+       uint8_t         *tim;
+       uint8_t         *tstamp;
+       uint8_t         *country;
+       uint8_t         *ssid;
+       uint8_t         *rates;
+       uint8_t         *xrates;
+       uint8_t         *doth;
+       uint8_t         *wpa;
+       uint8_t         *rsn;
+       uint8_t         *wme;
+       uint8_t         *htcap;
+       uint8_t         *htinfo;
+       uint8_t         *ath;
+       uint8_t         *tdma;
+       uint8_t         *csa;
+       uint8_t         *meshid;
+       uint8_t         *meshconf;
+       uint8_t         *spare[3];
+};
+
+/*
+ * Scan cache entry format used when exporting data from a policy
+ * module; this data may be represented some other way internally.
+ */
+struct ieee80211_scan_entry {
+       uint8_t         se_macaddr[IEEE80211_ADDR_LEN];
+       uint8_t         se_bssid[IEEE80211_ADDR_LEN];
+       /* XXX can point inside se_ies */
+       uint8_t         se_ssid[2+IEEE80211_NWID_LEN];
+       uint8_t         se_rates[2+IEEE80211_RATE_MAXSIZE];
+       uint8_t         se_xrates[2+IEEE80211_RATE_MAXSIZE];
+       union {
+               uint8_t         data[8];
+               u_int64_t       tsf;
+       } se_tstamp;                    /* from last rcv'd beacon */
+       uint16_t        se_intval;      /* beacon interval (host byte order) */
+       uint16_t        se_capinfo;     /* capabilities (host byte order) */
+       struct ieee80211_channel *se_chan;/* channel where sta found */
+       uint16_t        se_timoff;      /* byte offset to TIM ie */
+       uint16_t        se_fhdwell;     /* FH only (host byte order) */
+       uint8_t         se_fhindex;     /* FH only */
+       uint8_t         se_dtimperiod;  /* DTIM period */
+       uint16_t        se_erp;         /* ERP from beacon/probe resp */
+       int8_t          se_rssi;        /* avg'd recv ssi */
+       int8_t          se_noise;       /* noise floor */
+       uint8_t         se_cc[2];       /* captured country code */
+       uint8_t         se_meshid[2+IEEE80211_MESHID_LEN];
+       struct ieee80211_ies se_ies;    /* captured ie's */
+       u_int           se_age;         /* age of entry (0 on create) */
+};
+MALLOC_DECLARE(M_80211_SCAN);
+
+/*
+ * Template for an in-kernel scan policy module.
+ * Modules register with the scanning code and are
+ * typically loaded as needed.
+ */
+struct ieee80211_scanner {
+       const char *scan_name;          /* printable name */
+       int     (*scan_attach)(struct ieee80211_scan_state *);
+       int     (*scan_detach)(struct ieee80211_scan_state *);
+       int     (*scan_start)(struct ieee80211_scan_state *,
+                       struct ieee80211vap *);
+       int     (*scan_restart)(struct ieee80211_scan_state *,
+                       struct ieee80211vap *);
+       int     (*scan_cancel)(struct ieee80211_scan_state *,
+                       struct ieee80211vap *);
+       int     (*scan_end)(struct ieee80211_scan_state *,
+                       struct ieee80211vap *);
+       int     (*scan_flush)(struct ieee80211_scan_state *);
+       struct ieee80211_channel *(*scan_pickchan)(
+                       struct ieee80211_scan_state *, int);
+       /* add an entry to the cache */
+       int     (*scan_add)(struct ieee80211_scan_state *,
+                       const struct ieee80211_scanparams *,
+                       const struct ieee80211_frame *,
+                       int subtype, int rssi, int noise);
+       /* age and/or purge entries in the cache */
+       void    (*scan_age)(struct ieee80211_scan_state *);
+       /* note that association failed for an entry */
+       void    (*scan_assoc_fail)(struct ieee80211_scan_state *,
+                       const uint8_t macaddr[IEEE80211_ADDR_LEN],
+                       int reason);
+       /* note that association succeed for an entry */
+       void    (*scan_assoc_success)(struct ieee80211_scan_state *,
+                       const uint8_t macaddr[IEEE80211_ADDR_LEN]);
+       /* iterate over entries in the scan cache */
+       void    (*scan_iterate)(struct ieee80211_scan_state *,
+                       ieee80211_scan_iter_func *, void *);
+       void    (*scan_spare0)(void);
+       void    (*scan_spare1)(void);
+       void    (*scan_spare2)(void);
+       void    (*scan_spare4)(void);
+};
+void   ieee80211_scanner_register(enum ieee80211_opmode,
+               const struct ieee80211_scanner *);
+void   ieee80211_scanner_unregister(enum ieee80211_opmode,
+               const struct ieee80211_scanner *);
+void   ieee80211_scanner_unregister_all(const struct ieee80211_scanner *);
+const struct ieee80211_scanner *ieee80211_scanner_get(enum ieee80211_opmode);
+#endif /* _NET80211_IEEE80211_SCAN_H_ */
diff --git a/sys/netproto/802_11/ieee80211_sta.h b/sys/netproto/802_11/ieee80211_sta.h
new file mode 100644 (file)
index 0000000..9616b35
--- /dev/null
@@ -0,0 +1,37 @@
+/*-
+ * Copyright (c) 2007-2008 Sam Leffler, Errno Consulting
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
+ * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
+ * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
+ * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
+ * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
+ * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
+ * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
+ * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ *
+ * $FreeBSD: head/sys/net80211/ieee80211_sta.h 178354 2008-04-20 20:35:46Z sam $
+ * $DragonFly$
+ */
+#ifndef _NET80211_IEEE80211_STA_H_
+#define _NET80211_IEEE80211_STA_H_
+
+/*
+ * Station-mode implementation definitions.
+ */
+void   ieee80211_sta_attach(struct ieee80211com *);
+void   ieee80211_sta_detach(struct ieee80211com *);
+void   ieee80211_sta_vattach(struct ieee80211vap *);
+#endif /* !_NET80211_IEEE80211_STA_H_ */
diff --git a/sys/netproto/802_11/ieee80211_superg.h b/sys/netproto/802_11/ieee80211_superg.h
new file mode 100644 (file)
index 0000000..749a7ae
--- /dev/null
@@ -0,0 +1,130 @@
+/*-
+ * Copyright (c) 2009 Sam Leffler, Errno Consulting
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
+ * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
+ * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
+ * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
+ * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
+ * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
+ * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
+ * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ *
+ * $FreeBSD: head/sys/net80211/ieee80211_superg.h 191753 2009-05-02 20:16:55Z sam $
+ * $DragonFly$
+ */
+#ifndef _NET80211_IEEE80211_SUPERG_H_
+#define _NET80211_IEEE80211_SUPERG_H_
+
+/*
+ * Atheros' 802.11 SuperG protocol support.
+ */
+
+/*
+ * Atheros advanced capability information element.
+ */
+struct ieee80211_ath_ie {
+       uint8_t         ath_id;                 /* IEEE80211_ELEMID_VENDOR */
+       uint8_t         ath_len;                /* length in bytes */
+       uint8_t         ath_oui[3];             /* ATH_OUI */
+       uint8_t         ath_oui_type;           /* ATH_OUI_TYPE */
+       uint8_t         ath_oui_subtype;        /* ATH_OUI_SUBTYPE */
+       uint8_t         ath_version;            /* spec revision */
+       uint8_t         ath_capability;         /* capability info */
+#define        ATHEROS_CAP_TURBO_PRIME         0x01    /* dynamic turbo--aka Turbo' */
+#define        ATHEROS_CAP_COMPRESSION         0x02    /* data compression */
+#define        ATHEROS_CAP_FAST_FRAME          0x04    /* fast (jumbo) frames */
+#define        ATHEROS_CAP_XR                  0x08    /* Xtended Range support */
+#define        ATHEROS_CAP_AR                  0x10    /* Advanded Radar support */
+#define        ATHEROS_CAP_BURST               0x20    /* Bursting - not negotiated */
+#define        ATHEROS_CAP_WME                 0x40    /* CWMin tuning */
+#define        ATHEROS_CAP_BOOST               0x80    /* use turbo/!turbo mode */
+       uint8_t         ath_defkeyix[2];
+} __packed;
+
+#define        ATH_OUI_VERSION         0x00
+#define        ATH_OUI_SUBTYPE         0x01
+
+#ifdef _KERNEL
+struct ieee80211_stageq {
+       struct mbuf             *head;          /* frames linked w/ m_nextpkt */
+       struct mbuf             *tail;          /* last frame in queue */
+       int                     depth;          /* # items on head */
+};
+
+struct ieee80211_superg {
+       /* fast-frames staging q */
+       struct ieee80211_stageq ff_stageq[WME_NUM_AC];
+       int                     ff_stageqdepth; /* cumulative depth */
+};
+
+void   ieee80211_superg_attach(struct ieee80211com *);
+void   ieee80211_superg_detach(struct ieee80211com *);
+void   ieee80211_superg_vattach(struct ieee80211vap *);
+void   ieee80211_superg_vdetach(struct ieee80211vap *);
+
+uint8_t *ieee80211_add_ath(uint8_t *, uint8_t, ieee80211_keyix);
+uint8_t *ieee80211_add_athcaps(uint8_t *, const struct ieee80211_node *);
+void   ieee80211_parse_ath(struct ieee80211_node *, uint8_t *);
+int    ieee80211_parse_athparams(struct ieee80211_node *, uint8_t *,
+           const struct ieee80211_frame *);
+
+void   ieee80211_ff_node_init(struct ieee80211_node *);
+void   ieee80211_ff_node_cleanup(struct ieee80211_node *);
+
+struct mbuf *ieee80211_ff_check(struct ieee80211_node *, struct mbuf *);
+void   ieee80211_ff_age(struct ieee80211com *, struct ieee80211_stageq *,
+            int quanta);
+
+static __inline void
+ieee80211_ff_flush(struct ieee80211com *ic, int ac)
+{
+       struct ieee80211_superg *sg = ic->ic_superg;
+
+       if (sg != NULL && sg->ff_stageq[ac].depth)
+               ieee80211_ff_age(ic, &sg->ff_stageq[ac], 0x7fffffff);
+}
+
+static __inline void
+ieee80211_ff_age_all(struct ieee80211com *ic, int quanta)
+{
+       struct ieee80211_superg *sg = ic->ic_superg;
+
+       if (sg != NULL && sg->ff_stageqdepth) {
+               if (sg->ff_stageq[WME_AC_VO].depth)
+                       ieee80211_ff_age(ic, &sg->ff_stageq[WME_AC_VO], quanta);
+               if (sg->ff_stageq[WME_AC_VI].depth)
+                       ieee80211_ff_age(ic, &sg->ff_stageq[WME_AC_VI], quanta);
+               if (sg->ff_stageq[WME_AC_BE].depth)
+                       ieee80211_ff_age(ic, &sg->ff_stageq[WME_AC_BE], quanta);
+               if (sg->ff_stageq[WME_AC_BK].depth)
+                       ieee80211_ff_age(ic, &sg->ff_stageq[WME_AC_BK], quanta);
+       }
+}
+
+struct mbuf *ieee80211_ff_encap(struct ieee80211vap *, struct mbuf *,
+           int, struct ieee80211_key *);
+
+struct mbuf *ieee80211_ff_decap(struct ieee80211_node *, struct mbuf *);
+
+static __inline struct mbuf *
+ieee80211_decap_fastframe(struct ieee80211vap *vap, struct ieee80211_node *ni,
+    struct mbuf *m)
+{
+       return IEEE80211_ATH_CAP(vap, ni, IEEE80211_NODE_FF) ?
+           ieee80211_ff_decap(ni, m) : m;
+}
+#endif /* _KERNEL */
+#endif /* _NET80211_IEEE80211_SUPERG_H_ */
diff --git a/sys/netproto/802_11/ieee80211_tdma.h b/sys/netproto/802_11/ieee80211_tdma.h
new file mode 100644 (file)
index 0000000..1b8bec2
--- /dev/null
@@ -0,0 +1,103 @@
+/*-
+ * Copyright (c) 2007-2009 Sam Leffler, Errno Consulting
+ * Copyright (c) 2007-2009 Intel Corporation
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
+ * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
+ * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
+ * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
+ * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
+ * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
+ * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
+ * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ *
+ * $FreeBSD: head/sys/net80211/ieee80211_tdma.h 192468 2009-05-20 20:00:40Z sam $
+ * $DragonFly$
+ */
+#ifndef _NET80211_IEEE80211_TDMA_H_
+#define _NET80211_IEEE80211_TDMA_H_
+
+/*
+ * TDMA-mode implementation definitions.
+ */
+
+#define        TDMA_SUBTYPE_PARAM      0x01
+#define        TDMA_VERSION_V2         2
+#define        TDMA_VERSION            TDMA_VERSION_V2
+
+/* NB: we only support 2 right now but protocol handles up to 8 */
+#define        TDMA_MAXSLOTS           2       /* max slots/sta's */
+
+#define        TDMA_PARAM_LEN_V2       sizeof(struct ieee80211_tdma_param)
+
+/*
+ * TDMA information element.
+ */
+struct ieee80211_tdma_param {
+       u_int8_t        tdma_id;        /* IEEE80211_ELEMID_VENDOR */
+       u_int8_t        tdma_len;
+       u_int8_t        tdma_oui[3];    /* TDMA_OUI */
+       u_int8_t        tdma_type;      /* TDMA_OUI_TYPE */
+       u_int8_t        tdma_subtype;   /* TDMA_SUBTYPE_PARAM */
+       u_int8_t        tdma_version;   /* spec revision */
+       u_int8_t        tdma_slot;      /* station slot # [0..7] */
+       u_int8_t        tdma_slotcnt;   /* bss slot count [1..8] */
+       u_int16_t       tdma_slotlen;   /* bss slot len (100us) */
+       u_int8_t        tdma_bintval;   /* beacon interval (superframes) */
+       u_int8_t        tdma_inuse[1];  /* slot occupancy map */
+       u_int8_t        tdma_pad[2];
+       u_int8_t        tdma_tstamp[8]; /* timestamp from last beacon */
+} __packed;
+
+#ifdef _KERNEL
+/*
+ * Implementation state.
+ */
+struct ieee80211_tdma_state {
+       u_int   tdma_slotlen;           /* bss slot length (us) */
+       uint8_t tdma_version;           /* protocol version to use */
+       uint8_t tdma_slotcnt;           /* bss slot count */
+       uint8_t tdma_bintval;           /* beacon interval (slots) */
+       uint8_t tdma_slot;              /* station slot # */
+       uint8_t tdma_inuse[1];          /* mask of slots in use */
+       uint8_t tdma_active[1];         /* mask of active slots */
+       int     tdma_count;             /* active/inuse countdown */
+       void    *tdma_peer;             /* peer station cookie */
+       struct timeval tdma_lastprint;  /* time of last rate-limited printf */
+       int     tdma_fails;             /* fail count for rate-limiting */
+
+       /* parent method pointers */
+       int     (*tdma_newstate)(struct ieee80211vap *, enum ieee80211_state,
+                   int arg);
+       void    (*tdma_recv_mgmt)(struct ieee80211_node *,
+                   struct mbuf *, int, int, int);
+       void    (*tdma_opdetach)(struct ieee80211vap *);
+};
+#define        TDMA_UPDATE_SLOT        0x0001  /* tdma_slot changed */
+#define        TDMA_UPDATE_SLOTCNT     0x0002  /* tdma_slotcnt changed */
+#define        TDMA_UPDATE_SLOTLEN     0x0004  /* tdma_slotlen changed */
+#define        TDMA_UPDATE_BINTVAL     0x0008  /* tdma_bintval changed */
+
+void   ieee80211_tdma_vattach(struct ieee80211vap *);
+
+int    ieee80211_tdma_getslot(struct ieee80211vap *vap);
+void   ieee80211_parse_tdma(struct ieee80211_node *ni, const uint8_t *ie);
+uint8_t *ieee80211_add_tdma(uint8_t *frm, struct ieee80211vap *vap);
+struct ieee80211_beacon_offsets;
+void   ieee80211_tdma_update_beacon(struct ieee80211vap *vap,
+           struct ieee80211_beacon_offsets *bo);
+#endif /* _KERNEL */
+#endif /* !_NET80211_IEEE80211_TDMA_H_ */
index e88dfed..8f3fe28 100644 (file)
@@ -1,6 +1,6 @@
-/*
+/*-
  * Copyright (c) 2001 Atsushi Onoe
- * Copyright (c) 2002-2005 Sam Leffler, Errno Consulting
+ * Copyright (c) 2002-2009 Sam Leffler, Errno Consulting
  * All rights reserved.
  *
  * Redistribution and use in source and binary forms, with or without
  * 2. Redistributions in binary form must reproduce the above copyright
  *    notice, this list of conditions and the following disclaimer in the
  *    documentation and/or other materials provided with the distribution.
- * 3. The name of the author may not be used to endorse or promote products
- *    derived from this software without specific prior written permission.
- *
- * Alternatively, this software may be distributed under the terms of the
- * GNU General Public License ("GPL") version 2 as published by the Free
- * Software Foundation.
  *
  * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
  * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
  * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
  * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
  *
- * $FreeBSD: src/sys/net80211/ieee80211_var.h,v 1.22.2.11 2006/03/13 03:05:48 sam Exp $
- * $DragonFly: src/sys/netproto/802_11/ieee80211_var.h,v 1.19 2008/03/04 13:48:40 sephe Exp $
+ * $FreeBSD: head/sys/net80211/ieee80211_var.h 202612 2010-01-19 05:00:57Z thompsa $
+ * $DragonFly$
  */
 #ifndef _NET80211_IEEE80211_VAR_H_
 #define _NET80211_IEEE80211_VAR_H_
 
-#ifdef _KERNEL
-
 /*
  * Definitions for IEEE 802.11 drivers.
  */
-#define        IEEE80211_DEBUG
-#undef IEEE80211_DEBUG_REFCNT                  /* node refcnt stuff */
-
 /* NB: portability glue must go first */
-#ifdef __NetBSD__
+#if defined(__NetBSD__)
 #include <net80211/ieee80211_netbsd.h>
-#elif __FreeBSD__
+#elif defined(__FreeBSD__)
 #include <net80211/ieee80211_freebsd.h>
-#elif __linux__
+#elif defined(__linux__)
 #include <net80211/ieee80211_linux.h>
-#elif __DragonFly__
+#elif defined(__DragonFly__)
 #include <netproto/802_11/ieee80211_dragonfly.h>
 #else
 #error "No support for your operating system!"
 
 #include <netproto/802_11/_ieee80211.h>
 #include <netproto/802_11/ieee80211.h>
+#include <netproto/802_11/ieee80211_ageq.h>
 #include <netproto/802_11/ieee80211_crypto.h>
+#include <netproto/802_11/ieee80211_dfs.h>
 #include <netproto/802_11/ieee80211_ioctl.h>   /* for ieee80211_stats */
+#include <netproto/802_11/ieee80211_phy.h>
+#include <netproto/802_11/ieee80211_power.h>
 #include <netproto/802_11/ieee80211_node.h>
 #include <netproto/802_11/ieee80211_proto.h>
-#include <netproto/802_11/ieee80211_ratectl.h>
+#include <netproto/802_11/ieee80211_radiotap.h>
+#include <netproto/802_11/ieee80211_scan.h>
 
 #define        IEEE80211_TXPOWER_MAX   100     /* .5 dbM (XXX units?) */
 #define        IEEE80211_TXPOWER_MIN   0       /* kill radio */
 
 #define        IEEE80211_DTIM_DEFAULT  1       /* default DTIM period */
-
 #define        IEEE80211_BINTVAL_DEFAULT 100   /* default beacon interval (TU's) */
 
 #define        IEEE80211_BMISS_MAX     2       /* maximum consecutive bmiss allowed */
 #define        IEEE80211_HWBMISS_DEFAULT 7     /* h/w bmiss threshold (beacons) */
 
+#define        IEEE80211_BGSCAN_INTVAL_MIN     15      /* min bg scan intvl (secs) */
+#define        IEEE80211_BGSCAN_INTVAL_DEFAULT (5*60)  /* default bg scan intvl */
+
+#define        IEEE80211_BGSCAN_IDLE_MIN       100     /* min idle time (ms) */
+#define        IEEE80211_BGSCAN_IDLE_DEFAULT   250     /* default idle time (ms) */
+
+#define        IEEE80211_SCAN_VALID_MIN        10      /* min scan valid time (secs) */
+#define        IEEE80211_SCAN_VALID_DEFAULT    60      /* default scan valid time */
+
 #define        IEEE80211_PS_SLEEP      0x1     /* STA is in power saving mode */
 #define        IEEE80211_PS_MAX_QUEUE  50      /* maximum saved packets */
 
-#define        IEEE80211_FIXED_RATE_NONE       -1
-#define        IEEE80211_MCAST_RATE_DEFAULT    (2*1)   /* default mcast rate (1M) */
+#define        IEEE80211_FIXED_RATE_NONE       0xff
+#define        IEEE80211_TXMAX_DEFAULT         6       /* default ucast max retries */
 
 #define        IEEE80211_RTS_DEFAULT           IEEE80211_RTS_MAX
 #define        IEEE80211_FRAG_DEFAULT          IEEE80211_FRAG_MAX
 #define        IEEE80211_TU_TO_MS(x)   (((x) * 1024) / 1000)
 #define        IEEE80211_TU_TO_TICKS(x)(((x) * 1024 * hz) / (1000 * 1000))
 
-struct ieee80211_aclator;
-struct sysctl_ctx_list;
+/*
+ * 802.11 control state is split into a common portion that maps
+ * 1-1 to a physical device and one or more "Virtual AP's" (VAP)
+ * that are bound to an ieee80211com instance and share a single
+ * underlying device.  Each VAP has a corresponding OS device
+ * entity through which traffic flows and that applications use
+ * for issuing ioctls, etc.
+ */
+
+/*
+ * Data common to one or more virtual AP's.  State shared by
+ * the underlying device and the net80211 layer is exposed here;
+ * e.g. device-specific callbacks.
+ */
+struct ieee80211vap;
+typedef void (*ieee80211vap_attach)(struct ieee80211vap *);
+
+struct ieee80211_appie {
+       uint16_t                ie_len;         /* size of ie_data */
+       uint8_t                 ie_data[];      /* user-specified IE's */
+};
+
+struct ieee80211_tdma_param;
+struct ieee80211_rate_table;
+struct ieee80211_tx_ampdu;
+struct ieee80211_rx_ampdu;
+struct ieee80211_superg;
+struct ieee80211_frame;
 
 struct ieee80211com {
-       struct arpcom           ic_ac;
-#define ic_if  ic_ac.ac_if
-       SLIST_ENTRY(ieee80211com) ic_next;
        struct ifnet            *ic_ifp;        /* associated device */
-       struct ieee80211_stats  ic_stats;       /* statistics */
-       struct sysctl_ctx_list  *ic_sysctl;     /* dynamic sysctl context */
-       struct sysctl_oid       *ic_sysctl_oid; /* dynamic sysctl oid */
-       uint32_t                ic_debug;       /* debug msg flags */
-       int                     ic_vap;         /* virtual AP index */
+       ieee80211_com_lock_t    ic_comlock;     /* state update lock */
+       TAILQ_HEAD(, ieee80211vap) ic_vaps;     /* list of vap instances */
        int                     ic_headroom;    /* driver tx headroom needs */
+       enum ieee80211_phytype  ic_phytype;     /* XXX wrong for multi-mode */
+       enum ieee80211_opmode   ic_opmode;      /* operation mode */
+       struct ifmedia          ic_media;       /* interface media config */
+       struct callout          ic_inact;       /* inactivity processing */
+       struct taskqueue        *ic_tq;         /* deferred state thread */
+       struct task             ic_parent_task; /* deferred parent processing */
+       struct task             ic_promisc_task;/* deferred promisc update */
+       struct task             ic_mcast_task;  /* deferred mcast update */
+       struct task             ic_chan_task;   /* deferred channel change */
+       struct task             ic_bmiss_task;  /* deferred beacon miss hndlr */
 
-       int                     (*ic_reset)(struct ifnet *);
-       void                    (*ic_recv_mgmt)(struct ieee80211com *,
-                                   struct mbuf *, struct ieee80211_node *,
-                                   int, int, uint32_t);
-       int                     (*ic_send_mgmt)(struct ieee80211com *,
-                                   struct ieee80211_node *, int, int);
-       int                     (*ic_newstate)(struct ieee80211com *,
-                                   enum ieee80211_state, int);
-       void                    (*ic_newassoc)(struct ieee80211_node *, int);
-       void                    (*ic_updateslot)(struct ifnet *);
-       void                    (*ic_update_preamble)(struct ifnet *);
-       void                    (*ic_set_tim)(struct ieee80211_node *, int);
-       uint8_t                 ic_myaddr[IEEE80211_ADDR_LEN];
-       struct ieee80211_rateset ic_sup_rates[IEEE80211_MODE_MAX];
-       struct ieee80211_channel ic_channels[IEEE80211_CHAN_MAX+1];
-       uint8_t                 ic_chan_avail[IEEE80211_CHAN_BYTES];
-       uint8_t                 ic_chan_active[IEEE80211_CHAN_BYTES];
-       uint8_t                 ic_chan_scan[IEEE80211_CHAN_BYTES];
-       struct ieee80211_node_table ic_scan;    /* scan candidates */
-       struct ifqueue          ic_mgtq;
        uint32_t                ic_flags;       /* state flags */
        uint32_t                ic_flags_ext;   /* extended state flags */
+       uint32_t                ic_flags_ht;    /* HT state flags */
+       uint32_t                ic_flags_ven;   /* vendor state flags */
        uint32_t                ic_caps;        /* capabilities */
-       uint32_t                ic_caps_ext;    /* extended capabilities */
-       uint16_t                ic_modecaps;    /* set of mode capabilities */
-       uint16_t                ic_curmode;     /* current mode */
-       enum ieee80211_phytype  ic_phytype;     /* XXX wrong for multi-mode */
-       enum ieee80211_opmode   ic_opmode;      /* operation mode */
-       enum ieee80211_state    ic_state;       /* 802.11 state */
-       enum ieee80211_protmode ic_protmode;    /* 802.11g protection mode */
-       enum ieee80211_roamingmode ic_roaming;  /* roaming mode */
-       struct ieee80211_node_table ic_sta;     /* stations/neighbors */
-       uint32_t                *ic_aid_bitmap; /* association id map */
-       uint16_t                ic_max_aid;
-       uint16_t                ic_sta_assoc;   /* stations associated */
-       uint16_t                ic_ps_sta;      /* stations in power save */
-       uint16_t                ic_ps_pending;  /* ps sta's w/ pending frames */
-       uint8_t                 *ic_tim_bitmap; /* power-save stations w/ data*/
-       uint16_t                ic_tim_len;     /* ic_tim_bitmap size (bytes) */
-       uint8_t                 ic_dtim_period; /* DTIM period */
-       uint8_t                 ic_dtim_count;  /* DTIM count for last bcn */
-       struct ifmedia          ic_media;       /* interface media config */
-       struct bpf_if           *ic_rawbpf;     /* packet filter structure */
-       struct ieee80211_node   *ic_bss;        /* information for this node */
-       int                     ic_nbasicrates; /* number of BSS basic rates */
-       struct ieee80211_channel *ic_ibss_chan;
-       struct ieee80211_channel *ic_curchan;   /* current channel */
-       int                     ic_fixed_rate;  /* index to ic_sup_rates[] */
-       int                     ic_mcast_rate;  /* rate for mcast frames */
-       uint16_t                ic_rtsthreshold;
-       uint16_t                ic_fragthreshold;
-       uint8_t                 ic_bmissthreshold;
-       uint8_t                 ic_bmiss_count; /* current beacon miss count */
-       int                     ic_bmiss_max;   /* max bmiss before scan */
-       uint16_t                ic_swbmiss_count;/* beacons in last period */
-       uint16_t                ic_swbmiss_period;/* s/w bmiss period */
-       struct callout          ic_swbmiss;     /* s/w beacon miss timer */
-       struct ieee80211_node   *(*ic_node_alloc)(struct ieee80211_node_table*);
-       void                    (*ic_node_free)(struct ieee80211_node *);
-       void                    (*ic_node_cleanup)(struct ieee80211_node *);
-       uint8_t                 (*ic_node_getrssi)(const struct ieee80211_node*);
-       uint16_t                ic_lintval;     /* listen interval */
+       uint32_t                ic_htcaps;      /* HT capabilities */
+       uint32_t                ic_cryptocaps;  /* crypto capabilities */
+       uint8_t                 ic_modecaps[2]; /* set of mode capabilities */
+       uint8_t                 ic_promisc;     /* vap's needing promisc mode */
+       uint8_t                 ic_allmulti;    /* vap's needing all multicast*/
+       uint8_t                 ic_nrunning;    /* vap's marked running */
+       uint8_t                 ic_curmode;     /* current mode */
        uint16_t                ic_bintval;     /* beacon interval */
+       uint16_t                ic_lintval;     /* listen interval */
        uint16_t                ic_holdover;    /* PM hold over duration */
-       uint16_t                ic_txmin;       /* min tx retry count */
-       uint16_t                ic_txmax;       /* max tx retry count */
-       uint16_t                ic_txlifetime;  /* tx lifetime */
        uint16_t                ic_txpowlimit;  /* global tx power limit */
-       uint16_t                ic_pad0;        /* was ic_bmisstimeout */
-       uint16_t                ic_nonerpsta;   /* # non-ERP stations */
-       uint16_t                ic_longslotsta; /* # long slot time stations */
-       int                     ic_mgt_timer;   /* mgmt timeout */
-       int                     ic_inact_timer; /* inactivity timer wait */
-       int                     ic_des_esslen;
-       uint8_t                 ic_des_essid[IEEE80211_NWID_LEN];
-       struct ieee80211_channel *ic_des_chan;  /* desired channel */
-       uint8_t                 ic_des_bssid[IEEE80211_ADDR_LEN];
-       void                    *ic_opt_ie;     /* user-specified IE's */
-       uint16_t                ic_opt_ie_len;  /* length of ni_opt_ie */
-       /*
-        * Inactivity timer settings for nodes.
-        */
-       int                     ic_inact_init;  /* initial setting */
-       int                     ic_inact_auth;  /* auth but not assoc setting */
-       int                     ic_inact_run;   /* authorized setting */
-       int                     ic_inact_probe; /* inactive probe time */
+       struct ieee80211_rateset ic_sup_rates[IEEE80211_MODE_MAX];
 
        /*
-        * WME/WMM state.
+        * Channel state:
+        *
+        * ic_channels is the set of available channels for the device;
+        *    it is setup by the driver
+        * ic_nchans is the number of valid entries in ic_channels
+        * ic_chan_avail is a bit vector of these channels used to check
+        *    whether a channel is available w/o searching the channel table.
+        * ic_chan_active is a (potentially) constrained subset of
+        *    ic_chan_avail that reflects any mode setting or user-specified
+        *    limit on the set of channels to use/scan
+        * ic_curchan is the current channel the device is set to; it may
+        *    be different from ic_bsschan when we are off-channel scanning
+        *    or otherwise doing background work
+        * ic_bsschan is the channel selected for operation; it may
+        *    be undefined (IEEE80211_CHAN_ANYC)
+        * ic_prevchan is a cached ``previous channel'' used to optimize
+        *    lookups when switching back+forth between two channels
+        *    (e.g. for dynamic turbo)
         */
-       struct ieee80211_wme_state ic_wme;
+       int                     ic_nchans;      /* # entries in ic_channels */
+       struct ieee80211_channel ic_channels[IEEE80211_CHAN_MAX];
+       uint8_t                 ic_chan_avail[IEEE80211_CHAN_BYTES];
+       uint8_t                 ic_chan_active[IEEE80211_CHAN_BYTES];
+       uint8_t                 ic_chan_scan[IEEE80211_CHAN_BYTES];
+       struct ieee80211_channel *ic_curchan;   /* current channel */
+       const struct ieee80211_rate_table *ic_rt; /* table for ic_curchan */
+       struct ieee80211_channel *ic_bsschan;   /* bss channel */
+       struct ieee80211_channel *ic_prevchan;  /* previous channel */
+       struct ieee80211_regdomain ic_regdomain;/* regulatory data */
+       struct ieee80211_appie  *ic_countryie;  /* calculated country ie */
+       struct ieee80211_channel *ic_countryie_chan;
+
+       /* 802.11h/DFS state */
+       struct ieee80211_channel *ic_csa_newchan;/* channel for doing CSA */
+       short                   ic_csa_mode;    /* mode for doing CSA */
+       short                   ic_csa_count;   /* count for doing CSA */
+       struct ieee80211_dfs_state ic_dfs;      /* DFS state */
+
+       struct ieee80211_scan_state *ic_scan;   /* scan state */
+       int                     ic_lastdata;    /* time of last data frame */
+       int                     ic_lastscan;    /* time last scan completed */
+
+       /* NB: this is the union of all vap stations/neighbors */
+       int                     ic_max_keyix;   /* max h/w key index */
+       struct ieee80211_node_table ic_sta;     /* stations/neighbors */
+       struct ieee80211_ageq   ic_stageq;      /* frame staging queue */
+       uint32_t                ic_hash_key;    /* random key for mac hash */
 
-       /*
-        * Cipher state/configuration.
-        */
-       struct ieee80211_crypto_state ic_crypto;
-#define        ic_nw_keys      ic_crypto.cs_nw_keys    /* XXX compatibility */
-#define        ic_def_txkey    ic_crypto.cs_def_txkey  /* XXX compatibility */
+       /* XXX multi-bss: split out common/vap parts */
+       struct ieee80211_wme_state ic_wme;      /* WME/WMM state */
 
-       /*
-        * 802.1x glue.  When an authenticator attaches it
-        * fills in this section.  We assume that when ic_ec
-        * is setup that the methods are safe to call.
-        */
-       const struct ieee80211_authenticator *ic_auth;
-       struct eapolcom         *ic_ec; 
+       /* XXX multi-bss: can per-vap be done/make sense? */
+       enum ieee80211_protmode ic_protmode;    /* 802.11g protection mode */
+       uint16_t                ic_nonerpsta;   /* # non-ERP stations */
+       uint16_t                ic_longslotsta; /* # long slot time stations */
+       uint16_t                ic_sta_assoc;   /* stations associated */
+       uint16_t                ic_ht_sta_assoc;/* HT stations associated */
+       uint16_t                ic_ht40_sta_assoc;/* HT40 stations associated */
+       uint8_t                 ic_curhtprotmode;/* HTINFO bss state */
+       enum ieee80211_protmode ic_htprotmode;  /* HT protection mode */
+       int                     ic_lastnonerp;  /* last time non-ERP sta noted*/
+       int                     ic_lastnonht;   /* last time non-HT sta noted */
+
+       /* optional state for Atheros SuperG protocol extensions */
+       struct ieee80211_superg *ic_superg;
+
+       /* radiotap handling */
+       struct ieee80211_radiotap_header *ic_th;/* tx radiotap headers */
+       void                    *ic_txchan;     /* channel state in ic_th */
+       struct ieee80211_radiotap_header *ic_rh;/* rx radiotap headers */
+       void                    *ic_rxchan;     /* channel state in ic_rh */
+       int                     ic_montaps;     /* active monitor mode taps */
+
+       /* virtual ap create/delete */
+       struct ieee80211vap*    (*ic_vap_create)(struct ieee80211com *,
+                                   const char name[IFNAMSIZ], int unit,
+                                   int opmode, int flags,
+                                   const uint8_t bssid[IEEE80211_ADDR_LEN],
+                                   const uint8_t macaddr[IEEE80211_ADDR_LEN]);
+       void                    (*ic_vap_delete)(struct ieee80211vap *);
+       /* operating mode attachment */
+       ieee80211vap_attach     ic_vattach[IEEE80211_OPMODE_MAX];
+       /* return hardware/radio capabilities */
+       void                    (*ic_getradiocaps)(struct ieee80211com *,
+                                   int, int *, struct ieee80211_channel []);
+       /* check and/or prepare regdomain state change */
+       int                     (*ic_setregdomain)(struct ieee80211com *,
+                                   struct ieee80211_regdomain *,
+                                   int, struct ieee80211_channel []);
+       /* send/recv 802.11 management frame */
+       int                     (*ic_send_mgmt)(struct ieee80211_node *,
+                                    int, int);
+       /* send raw 802.11 frame */
+       int                     (*ic_raw_xmit)(struct ieee80211_node *,
+                                   struct mbuf *,
+                                   const struct ieee80211_bpf_params *);
+       /* update device state for 802.11 slot time change */
+       void                    (*ic_updateslot)(struct ifnet *);
+       /* handle multicast state changes */
+       void                    (*ic_update_mcast)(struct ifnet *);
+       /* handle promiscuous mode changes */
+       void                    (*ic_update_promisc)(struct ifnet *);
+       /* new station association callback/notification */
+       void                    (*ic_newassoc)(struct ieee80211_node *, int);
+       /* TDMA update notification */
+       void                    (*ic_tdma_update)(struct ieee80211_node *,
+                                   const struct ieee80211_tdma_param *, int);
+       /* node state management */
+       struct ieee80211_node*  (*ic_node_alloc)(struct ieee80211vap *,
+                                   const uint8_t [IEEE80211_ADDR_LEN]);
+       void                    (*ic_node_free)(struct ieee80211_node *);
+       void                    (*ic_node_cleanup)(struct ieee80211_node *);
+       void                    (*ic_node_age)(struct ieee80211_node *);
+       void                    (*ic_node_drain)(struct ieee80211_node *);
+       int8_t                  (*ic_node_getrssi)(const struct ieee80211_node*);
+       void                    (*ic_node_getsignal)(const struct ieee80211_node*,
+                                   int8_t *, int8_t *);
+       void                    (*ic_node_getmimoinfo)(
+                                   const struct ieee80211_node*,
+                                   struct ieee80211_mimo_info *);
+       /* scanning support */
+       void                    (*ic_scan_start)(struct ieee80211com *);
+       void                    (*ic_scan_end)(struct ieee80211com *);
+       void                    (*ic_set_channel)(struct ieee80211com *);
+       void                    (*ic_scan_curchan)(struct ieee80211_scan_state *,
+                                   unsigned long);
+       void                    (*ic_scan_mindwell)(struct ieee80211_scan_state *);
 
        /*
-        * Access control glue.  When a control agent attaches
-        * it fills in this section.  We assume that when ic_ac
-        * is setup that the methods are safe to call.
+        * 802.11n ADDBA support.  A simple/generic implementation
+        * of A-MPDU tx aggregation is provided; the driver may
+        * override these methods to provide their own support.
+        * A-MPDU rx re-ordering happens automatically if the
+        * driver passes out-of-order frames to ieee80211_input
+        * from an assocated HT station.
         */
-       const struct ieee80211_aclator *ic_acl;
-       void                    *ic_as;
+       int                     (*ic_recv_action)(struct ieee80211_node *,
+                                   const struct ieee80211_frame *,
+                                   const uint8_t *frm, const uint8_t *efrm);
+       int                     (*ic_send_action)(struct ieee80211_node *,
+                                   int category, int action, void *);
+       /* check if A-MPDU should be enabled this station+ac */
+       int                     (*ic_ampdu_enable)(struct ieee80211_node *,
+                                   struct ieee80211_tx_ampdu *);
+       /* start/stop doing A-MPDU tx aggregation for a station */
+       int                     (*ic_addba_request)(struct ieee80211_node *,
+                                   struct ieee80211_tx_ampdu *,
+                                   int dialogtoken, int baparamset,
+                                   int batimeout);
+       int                     (*ic_addba_response)(struct ieee80211_node *,
+                                   struct ieee80211_tx_ampdu *,
+                                   int status, int baparamset, int batimeout);
+       void                    (*ic_addba_stop)(struct ieee80211_node *,
+                                   struct ieee80211_tx_ampdu *);
+       /* BAR response received */
+       void                    (*ic_bar_response)(struct ieee80211_node *,
+                                   struct ieee80211_tx_ampdu *, int status);
+       /* start/stop doing A-MPDU rx processing for a station */
+       int                     (*ic_ampdu_rx_start)(struct ieee80211_node *,
+                                   struct ieee80211_rx_ampdu *, int baparamset,
+                                   int batimeout, int baseqctl);
+       void                    (*ic_ampdu_rx_stop)(struct ieee80211_node *,
+                                   struct ieee80211_rx_ampdu *);
+       uint64_t                ic_spare[8];
+};
 
-       /*
-        * Rate control state/configuration.
-        */
-       struct ieee80211_ratectl_state ic_ratectl;
-       uint32_t                ic_pad[56];     /* future expansion */
+struct ieee80211_aclator;
+struct ieee80211_tdma_state;
+struct ieee80211_mesh_state;
+struct ieee80211_hwmp_state;
+
+struct ieee80211vap {
+       struct ifmedia          iv_media;       /* interface media config */
+       struct ifnet            *iv_ifp;        /* associated device */
+       struct bpf_if           *iv_rawbpf;     /* packet filter structure */
+       struct sysctl_ctx_list  *iv_sysctl;     /* dynamic sysctl context */
+       struct sysctl_oid       *iv_oid;        /* net.wlan.X sysctl oid */
+
+       TAILQ_ENTRY(ieee80211vap) iv_next;      /* list of vap instances */
+       struct ieee80211com     *iv_ic;         /* back ptr to common state */
+       uint32_t                iv_debug;       /* debug msg flags */
+       struct ieee80211_stats  iv_stats;       /* statistics */
+
+       uint8_t                 iv_myaddr[IEEE80211_ADDR_LEN];
+       uint32_t                iv_flags;       /* state flags */
+       uint32_t                iv_flags_ext;   /* extended state flags */
+       uint32_t                iv_flags_ht;    /* HT state flags */
+       uint32_t                iv_flags_ven;   /* vendor state flags */
+       uint32_t                iv_caps;        /* capabilities */
+       uint32_t                iv_htcaps;      /* HT capabilities */
+       enum ieee80211_opmode   iv_opmode;      /* operation mode */
+       enum ieee80211_state    iv_state;       /* state machine state */
+       enum ieee80211_state    iv_nstate;      /* pending state */
+       int                     iv_nstate_arg;  /* pending state arg */
+       struct task             iv_nstate_task; /* deferred state processing */
+       struct task             iv_swbmiss_task;/* deferred iv_bmiss call */
+       struct callout          iv_mgtsend;     /* mgmt frame response timer */
+                                               /* inactivity timer settings */
+       int                     iv_inact_init;  /* setting for new station */
+       int                     iv_inact_auth;  /* auth but not assoc setting */
+       int                     iv_inact_run;   /* authorized setting */
+       int                     iv_inact_probe; /* inactive probe time */
+
+       int                     iv_des_nssid;   /* # desired ssids */
+       struct ieee80211_scan_ssid iv_des_ssid[1];/* desired ssid table */
+       uint8_t                 iv_des_bssid[IEEE80211_ADDR_LEN];
+       struct ieee80211_channel *iv_des_chan;  /* desired channel */
+       uint16_t                iv_des_mode;    /* desired mode */
+       int                     iv_nicknamelen; /* XXX junk */
+       uint8_t                 iv_nickname[IEEE80211_NWID_LEN];
+       u_int                   iv_bgscanidle;  /* bg scan idle threshold */
+       u_int                   iv_bgscanintvl; /* bg scan min interval */
+       u_int                   iv_scanvalid;   /* scan cache valid threshold */
+       u_int                   iv_scanreq_duration;
+       u_int                   iv_scanreq_mindwell;
+       u_int                   iv_scanreq_maxdwell;
+       uint16_t                iv_scanreq_flags;/* held scan request params */
+       uint8_t                 iv_scanreq_nssid;
+       struct ieee80211_scan_ssid iv_scanreq_ssid[IEEE80211_SCAN_MAX_SSID];
+       /* sta-mode roaming state */
+       enum ieee80211_roamingmode iv_roaming;  /* roaming mode */
+       struct ieee80211_roamparam iv_roamparms[IEEE80211_MODE_MAX];
+
+       uint8_t                 iv_bmissthreshold;
+       uint8_t                 iv_bmiss_count; /* current beacon miss count */
+       int                     iv_bmiss_max;   /* max bmiss before scan */
+       uint16_t                iv_swbmiss_count;/* beacons in last period */
+       uint16_t                iv_swbmiss_period;/* s/w bmiss period */
+       struct callout          iv_swbmiss;     /* s/w beacon miss timer */
+
+       int                     iv_ampdu_rxmax; /* A-MPDU rx limit (bytes) */
+       int                     iv_ampdu_density;/* A-MPDU density */
+       int                     iv_ampdu_limit; /* A-MPDU tx limit (bytes) */
+       int                     iv_amsdu_limit; /* A-MSDU tx limit (bytes) */
+       u_int                   iv_ampdu_mintraffic[WME_NUM_AC];
+
+       uint32_t                *iv_aid_bitmap; /* association id map */
+       uint16_t                iv_max_aid;
+       uint16_t                iv_sta_assoc;   /* stations associated */
+       uint16_t                iv_ps_sta;      /* stations in power save */
+       uint16_t                iv_ps_pending;  /* ps sta's w/ pending frames */
+       uint16_t                iv_txseq;       /* mcast xmit seq# space */
+       uint16_t                iv_tim_len;     /* ic_tim_bitmap size (bytes) */
+       uint8_t                 *iv_tim_bitmap; /* power-save stations w/ data*/
+       uint8_t                 iv_dtim_period; /* DTIM period */
+       uint8_t                 iv_dtim_count;  /* DTIM count from last bcn */
+                                               /* set/unset aid pwrsav state */
+       int                     iv_csa_count;   /* count for doing CSA */
+
+       struct ieee80211_node   *iv_bss;        /* information for this node */
+       struct ieee80211_txparam iv_txparms[IEEE80211_MODE_MAX];
+       uint16_t                iv_rtsthreshold;
+       uint16_t                iv_fragthreshold;
+       int                     iv_inact_timer; /* inactivity timer wait */
+       /* application-specified IE's to attach to mgt frames */
+       struct ieee80211_appie  *iv_appie_beacon;
+       struct ieee80211_appie  *iv_appie_probereq;
+       struct ieee80211_appie  *iv_appie_proberesp;
+       struct ieee80211_appie  *iv_appie_assocreq;
+       struct ieee80211_appie  *iv_appie_assocresp;
+       struct ieee80211_appie  *iv_appie_wpa;
+       uint8_t                 *iv_wpa_ie;
+       uint8_t                 *iv_rsn_ie;
+       uint16_t                iv_max_keyix;   /* max h/w key index */
+       ieee80211_keyix         iv_def_txkey;   /* default/group tx key index */
+       struct ieee80211_key    iv_nw_keys[IEEE80211_WEP_NKID];
+       int                     (*iv_key_alloc)(struct ieee80211vap *,
+                                   struct ieee80211_key *,
+                                   ieee80211_keyix *, ieee80211_keyix *);
+       int                     (*iv_key_delete)(struct ieee80211vap *, 
+                                   const struct ieee80211_key *);
+       int                     (*iv_key_set)(struct ieee80211vap *,
+                                   const struct ieee80211_key *,
+                                   const uint8_t mac[IEEE80211_ADDR_LEN]);
+       void                    (*iv_key_update_begin)(struct ieee80211vap *);
+       void                    (*iv_key_update_end)(struct ieee80211vap *);
+
+       const struct ieee80211_authenticator *iv_auth; /* authenticator glue */
+       void                    *iv_ec;         /* private auth state */
+
+       const struct ieee80211_aclator *iv_acl; /* acl glue */
+       void                    *iv_as;         /* private aclator state */
+
+       struct ieee80211_tdma_state *iv_tdma;   /* tdma state */
+       struct ieee80211_mesh_state *iv_mesh;   /* MBSS state */
+       struct ieee80211_hwmp_state *iv_hwmp;   /* HWMP state */
+
+       /* operate-mode detach hook */
+       void                    (*iv_opdetach)(struct ieee80211vap *);
+       /* receive processing */
+       int                     (*iv_input)(struct ieee80211_node *,
+                                   struct mbuf *, int, int);
+       void                    (*iv_recv_mgmt)(struct ieee80211_node *,
+                                   struct mbuf *, int, int, int);
+       void                    (*iv_recv_ctl)(struct ieee80211_node *,
+                                   struct mbuf *, int);
+       void                    (*iv_deliver_data)(struct ieee80211vap *,
+                                   struct ieee80211_node *, struct mbuf *);
+#if 0
+       /* send processing */
+       int                     (*iv_send_mgmt)(struct ieee80211_node *,
+                                    int, int);
+#endif
+       /* beacon miss processing */
+       void                    (*iv_bmiss)(struct ieee80211vap *);
+       /* reset device state after 802.11 parameter/state change */
+       int                     (*iv_reset)(struct ieee80211vap *, u_long);
+       /* [schedule] beacon frame update */
+       void                    (*iv_update_beacon)(struct ieee80211vap *, int);
+       /* power save handling */
+       void                    (*iv_update_ps)(struct ieee80211vap *, int);
+       int                     (*iv_set_tim)(struct ieee80211_node *, int);
+       /* state machine processing */
+       int                     (*iv_newstate)(struct ieee80211vap *,
+                                   enum ieee80211_state, int);
+       /* 802.3 output method for raw frame xmit */
+       int                     (*iv_output)(struct ifnet *, struct mbuf *,
+                                   struct sockaddr *, struct route *);
+       uint64_t                iv_spare[8];
 };
+MALLOC_DECLARE(M_80211_VAP);
 
 #define        IEEE80211_ADDR_EQ(a1,a2)        (memcmp(a1,a2,IEEE80211_ADDR_LEN) == 0)
 #define        IEEE80211_ADDR_COPY(dst,src)    memcpy(dst,src,IEEE80211_ADDR_LEN)
 
-/* ic_flags */
-/* NB: bits 0x4c available */
-#define        IEEE80211_F_FF          0x00000001      /* CONF: ATH FF enabled */
-#define        IEEE80211_F_TURBOP      0x00000002      /* CONF: ATH Turbo enabled*/
-#define        IEEE80211_F_BURST       0x00000004      /* CONF: bursting enabled */
+/* ic_flags/iv_flags */
+#define        IEEE80211_F_TURBOP      0x00000001      /* CONF: ATH Turbo enabled*/
+#define        IEEE80211_F_COMP        0x00000002      /* CONF: ATH comp enabled */
+#define        IEEE80211_F_FF          0x00000004      /* CONF: ATH FF enabled */
+#define        IEEE80211_F_BURST       0x00000008      /* CONF: bursting enabled */
 /* NB: this is intentionally setup to be IEEE80211_CAPINFO_PRIVACY */
 #define        IEEE80211_F_PRIVACY     0x00000010      /* CONF: privacy enabled */
 #define        IEEE80211_F_PUREG       0x00000020      /* CONF: 11g w/o 11b sta's */
@@ -251,7 +502,7 @@ struct ieee80211com {
 #define        IEEE80211_F_DATAPAD     0x00080000      /* CONF: do alignment pad */
 #define        IEEE80211_F_USEPROT     0x00100000      /* STATUS: protection enabled */
 #define        IEEE80211_F_USEBARKER   0x00200000      /* STATUS: use barker preamble*/
-#define        IEEE80211_F_TIMUPDATE   0x00400000      /* STATUS: update beacon tim */
+#define        IEEE80211_F_CSAPENDING  0x00400000      /* STATUS: chan switch pending*/
 #define        IEEE80211_F_WPA1        0x00800000      /* CONF: WPA enabled */
 #define        IEEE80211_F_WPA2        0x01000000      /* CONF: WPA2 enabled */
 #define        IEEE80211_F_WPA         0x01800000      /* CONF: WPA/WPA2 enabled */
@@ -259,22 +510,80 @@ struct ieee80211com {
 #define        IEEE80211_F_COUNTERM    0x04000000      /* CONF: TKIP countermeasures */
 #define        IEEE80211_F_HIDESSID    0x08000000      /* CONF: hide SSID in beacon */
 #define        IEEE80211_F_NOBRIDGE    0x10000000      /* CONF: dis. internal bridge */
-#define        IEEE80211_F_WMEUPDATE   0x20000000      /* STATUS: update beacon wme */
-
-/* ic_flags_ext */
-#define        IEEE80211_FEXT_WDS      0x00000001      /* CONF: 4 addr allowed */
+#define        IEEE80211_F_PCF         0x20000000      /* CONF: PCF enabled */
+#define        IEEE80211_F_DOTH        0x40000000      /* CONF: 11h enabled */
+#define        IEEE80211_F_DWDS        0x80000000      /* CONF: Dynamic WDS enabled */
+
+#define        IEEE80211_F_BITS \
+       "\20\1TURBOP\2COMP\3FF\4BURST\5PRIVACY\6PUREG\10SCAN\11ASCAN\12SIBSS" \
+       "\13SHSLOT\14PMGTON\15DESBSSID\16WME\17BGSCAN\20SWRETRY\21TXPOW_FIXED" \
+       "\22IBSSON\23SHPREAMBLE\24DATAPAD\25USEPROT\26USERBARKER\27CSAPENDING" \
+       "\30WPA1\31WPA2\32DROPUNENC\33COUNTERM\34HIDESSID\35NOBRIDG\36PCF" \
+       "\37DOTH\40DWDS"
+
+/* Atheros protocol-specific flags */
+#define        IEEE80211_F_ATHEROS \
+       (IEEE80211_F_FF | IEEE80211_F_COMP | IEEE80211_F_TURBOP)
+/* Check if an Atheros capability was negotiated for use */
+#define        IEEE80211_ATH_CAP(vap, ni, bit) \
+       ((vap)->iv_flags & (ni)->ni_ath_flags & (bit))
+
+/* ic_flags_ext/iv_flags_ext */
+#define        IEEE80211_FEXT_INACT     0x00000002     /* CONF: sta inact handling */
+#define        IEEE80211_FEXT_SCANWAIT  0x00000004     /* STATUS: awaiting scan */
 /* 0x00000006 reserved */
-#define        IEEE80211_FEXT_BGSCAN   0x00000008      /* STATUS: enable full bgscan completion */
-#define        IEEE80211_FEXT_ERPUPDATE 0x00000200     /* STATUS: update ERP element */
-#define        IEEE80211_FEXT_SWBMISS  0x00000400      /* CONF: do bmiss in s/w */
+#define        IEEE80211_FEXT_BGSCAN    0x00000008     /* STATUS: complete bgscan */
+#define        IEEE80211_FEXT_WPS       0x00000010     /* CONF: WPS enabled */
+#define        IEEE80211_FEXT_TSN       0x00000020     /* CONF: TSN enabled */
+#define        IEEE80211_FEXT_SCANREQ   0x00000040     /* STATUS: scan req params */
+#define        IEEE80211_FEXT_RESUME    0x00000080     /* STATUS: start on resume */
+#define        IEEE80211_FEXT_4ADDR     0x00000100     /* CONF: apply 4-addr encap */
+#define        IEEE80211_FEXT_NONERP_PR 0x00000200     /* STATUS: non-ERP sta present*/
+#define        IEEE80211_FEXT_SWBMISS   0x00000400     /* CONF: do bmiss in s/w */
+#define        IEEE80211_FEXT_DFS       0x00000800     /* CONF: DFS enabled */
+#define        IEEE80211_FEXT_DOTD      0x00001000     /* CONF: 11d enabled */
+#define        IEEE80211_FEXT_STATEWAIT 0x00002000     /* STATUS: awaiting state chg */
+#define        IEEE80211_FEXT_REINIT    0x00004000     /* STATUS: INIT state first */
+#define        IEEE80211_FEXT_BPF       0x00008000     /* STATUS: BPF tap present */
+/* NB: immutable: should be set only when creating a vap */
+#define        IEEE80211_FEXT_WDSLEGACY 0x00010000     /* CONF: legacy WDS operation */
 #define        IEEE80211_FEXT_PROBECHAN 0x00020000     /* CONF: probe passive channel*/
-
-/* ic_caps */
-#define        IEEE80211_C_WEP         0x00000001      /* CAPABILITY: WEP available */
-#define        IEEE80211_C_TKIP        0x00000002      /* CAPABILITY: TKIP available */
-#define        IEEE80211_C_AES         0x00000004      /* CAPABILITY: AES OCB avail */
-#define        IEEE80211_C_AES_CCM     0x00000008      /* CAPABILITY: AES CCM avail */
-#define        IEEE80211_C_CKIP        0x00000020      /* CAPABILITY: CKIP available */
+#define        IEEE80211_FEXT_UNIQMAC   0x00040000     /* CONF: user or computed mac */
+
+#define        IEEE80211_FEXT_BITS \
+       "\20\2INACT\3SCANWAIT\4BGSCAN\5WPS\6TSN\7SCANREQ\10RESUME" \
+       "\0114ADDR\12NONEPR_PR\13SWBMISS\14DFS\15DOTD\16STATEWAIT\17REINIT" \
+       "\20BPF\21WDSLEGACY\22PROBECHAN\23UNIQMAC"
+
+/* ic_flags_ht/iv_flags_ht */
+#define        IEEE80211_FHT_NONHT_PR   0x00000001     /* STATUS: non-HT sta present */
+#define        IEEE80211_FHT_GF         0x00040000     /* CONF: Greenfield enabled */
+#define        IEEE80211_FHT_HT         0x00080000     /* CONF: HT supported */
+#define        IEEE80211_FHT_AMPDU_TX   0x00100000     /* CONF: A-MPDU tx supported */
+#define        IEEE80211_FHT_AMPDU_RX   0x00200000     /* CONF: A-MPDU rx supported */
+#define        IEEE80211_FHT_AMSDU_TX   0x00400000     /* CONF: A-MSDU tx supported */
+#define        IEEE80211_FHT_AMSDU_RX   0x00800000     /* CONF: A-MSDU rx supported */
+#define        IEEE80211_FHT_USEHT40    0x01000000     /* CONF: 20/40 use enabled */
+#define        IEEE80211_FHT_PUREN      0x02000000     /* CONF: 11n w/o legacy sta's */
+#define        IEEE80211_FHT_SHORTGI20  0x04000000     /* CONF: short GI in HT20 */
+#define        IEEE80211_FHT_SHORTGI40  0x08000000     /* CONF: short GI in HT40 */
+#define        IEEE80211_FHT_HTCOMPAT   0x10000000     /* CONF: HT vendor OUI's */
+#define        IEEE80211_FHT_RIFS       0x20000000     /* CONF: RIFS enabled */
+#define        IEEE80211_FHT_STBC_TX    0x40000000     /* CONF: STBC tx enabled */
+#define        IEEE80211_FHT_STBC_RX    0x80000000     /* CONF: STBC rx enabled */
+
+#define        IEEE80211_FHT_BITS \
+       "\20\1NONHT_PR" \
+       "\23GF\24HT\25AMDPU_TX\26AMPDU_TX" \
+       "\27AMSDU_TX\30AMSDU_RX\31USEHT40\32PUREN\33SHORTGI20\34SHORTGI40" \
+       "\35HTCOMPAT\36RIFS\37STBC_TX\40STBC_RX"
+
+#define        IEEE80211_FVEN_BITS     "\20"
+
+/* ic_caps/iv_caps: device driver capabilities */
+/* 0x2e available */
+#define        IEEE80211_C_STA         0x00000001      /* CAPABILITY: STA available */
+#define        IEEE80211_C_8023ENCAP   0x00000002      /* CAPABILITY: 802.3 encap */
 #define        IEEE80211_C_FF          0x00000040      /* CAPABILITY: ATH FF avail */
 #define        IEEE80211_C_TURBOP      0x00000080      /* CAPABILITY: ATH Turbo avail*/
 #define        IEEE80211_C_IBSS        0x00000100      /* CAPABILITY: IBSS available */
@@ -286,7 +595,9 @@ struct ieee80211com {
 #define        IEEE80211_C_SHSLOT      0x00004000      /* CAPABILITY: short slottime */
 #define        IEEE80211_C_SHPREAMBLE  0x00008000      /* CAPABILITY: short preamble */
 #define        IEEE80211_C_MONITOR     0x00010000      /* CAPABILITY: monitor mode */
-#define        IEEE80211_C_TKIPMIC     0x00020000      /* CAPABILITY: TKIP MIC avail */
+#define        IEEE80211_C_DFS         0x00020000      /* CAPABILITY: DFS/radar avail*/
+#define        IEEE80211_C_MBSS        0x00040000      /* CAPABILITY: MBSS available */
+/* 0x7c0000 available */
 #define        IEEE80211_C_WPA1        0x00800000      /* CAPABILITY: WPA1 avail */
 #define        IEEE80211_C_WPA2        0x01000000      /* CAPABILITY: WPA2 avail */
 #define        IEEE80211_C_WPA         0x01800000      /* CAPABILITY: WPA1+WPA2 avail*/
@@ -296,63 +607,129 @@ struct ieee80211com {
 /* 0x10000000 reserved */
 #define        IEEE80211_C_BGSCAN      0x20000000      /* CAPABILITY: bg scanning */
 #define        IEEE80211_C_TXFRAG      0x40000000      /* CAPABILITY: tx fragments */
+#define        IEEE80211_C_TDMA        0x80000000      /* CAPABILITY: TDMA avail */
 /* XXX protection/barker? */
 
-#define        IEEE80211_C_CRYPTO      0x0000002f      /* CAPABILITY: crypto alg's */
-
-/* ic_caps_ext */
-#define IEEE80211_CEXT_PBCC    0x00000001      /* CAPABILITY: PBCC modulation */
-#define IEEE80211_CEXT_CRYPTO_HDR 0x00000002   /* CAPABILITY:
-                                                * driver appends crypto header
-                                                */
-#define IEEE80211_CEXT_STRIP_MIC 0x00000004    /* CAPABILITY:
-                                                * driver strips TKIP MIC
-                                                */
-#define IEEE80211_CEXT_AUTOSCAN        0x00000008      /* CAPABILITY:
-                                                * auto channel scanning
-                                                */
-
-void   ieee80211_ifattach(struct ieee80211com *);
+#define        IEEE80211_C_OPMODE \
+       (IEEE80211_C_STA | IEEE80211_C_IBSS | IEEE80211_C_HOSTAP | \
+        IEEE80211_C_AHDEMO | IEEE80211_C_MONITOR | IEEE80211_C_WDS | \
+        IEEE80211_C_TDMA | IEEE80211_C_MBSS)
+
+#define        IEEE80211_C_BITS \
+       "\20\1STA\002803ENCAP\7FF\10TURBOP\11IBSS\12PMGT" \
+       "\13HOSTAP\14AHDEMO\15SWRETRY\16TXPMGT\17SHSLOT\20SHPREAMBLE" \
+       "\21MONITOR\22DFS\23MBSS\30WPA1\31WPA2\32BURST\33WME\34WDS\36BGSCAN" \
+       "\37TXFRAG\40TDMA"
+
+/*
+ * ic_htcaps/iv_htcaps: HT-specific device/driver capabilities
+ *
+ * NB: the low 16-bits are the 802.11 definitions, the upper
+ *     16-bits are used to define s/w/driver capabilities.
+ */
+#define        IEEE80211_HTC_AMPDU     0x00010000      /* CAPABILITY: A-MPDU tx */
+#define        IEEE80211_HTC_AMSDU     0x00020000      /* CAPABILITY: A-MSDU tx */
+/* NB: HT40 is implied by IEEE80211_HTCAP_CHWIDTH40 */
+#define        IEEE80211_HTC_HT        0x00040000      /* CAPABILITY: HT operation */
+#define        IEEE80211_HTC_SMPS      0x00080000      /* CAPABILITY: MIMO power save*/
+#define        IEEE80211_HTC_RIFS      0x00100000      /* CAPABILITY: RIFS support */
+
+#define        IEEE80211_C_HTCAP_BITS \
+       "\20\1LDPC\2CHWIDTH40\5GREENFIELD\6SHORTGI20\7SHORTGI40\10TXSTBC" \
+       "\21AMPDU\22AMSDU\23HT\24SMPS\25RIFS"
+
+void   ieee80211_ifattach(struct ieee80211com *,
+               const uint8_t macaddr[IEEE80211_ADDR_LEN]);
 void   ieee80211_ifdetach(struct ieee80211com *);
-void   ieee80211_announce(struct ieee80211com *);
-void   ieee80211_media_init(struct ieee80211com *,
+int    ieee80211_vap_setup(struct ieee80211com *, struct ieee80211vap *,
+               const char name[IFNAMSIZ], int unit, int opmode, int flags,
+               const uint8_t bssid[IEEE80211_ADDR_LEN],
+               const uint8_t macaddr[IEEE80211_ADDR_LEN]);
+int    ieee80211_vap_attach(struct ieee80211vap *,
                ifm_change_cb_t, ifm_stat_cb_t);
+void   ieee80211_vap_detach(struct ieee80211vap *);
+const struct ieee80211_rateset *ieee80211_get_suprates(struct ieee80211com *ic,
+               const struct ieee80211_channel *);
+void   ieee80211_announce(struct ieee80211com *);
+void   ieee80211_announce_channels(struct ieee80211com *);
+void   ieee80211_drain(struct ieee80211com *);
+void   ieee80211_media_init(struct ieee80211com *);
 struct ieee80211com *ieee80211_find_vap(const uint8_t mac[IEEE80211_ADDR_LEN]);
 int    ieee80211_media_change(struct ifnet *);
 void   ieee80211_media_status(struct ifnet *, struct ifmediareq *);
-int    ieee80211_ioctl(struct ieee80211com *, u_long, caddr_t, struct ucred *);
-int    ieee80211_cfgget(struct ieee80211com *, u_long, caddr_t, struct ucred *);
-int    ieee80211_cfgset(struct ieee80211com *, u_long, caddr_t);
-void   ieee80211_watchdog(struct ieee80211com *);
+int    ieee80211_ioctl(struct ifnet *, u_long, caddr_t);
 int    ieee80211_rate2media(struct ieee80211com *, int,
                enum ieee80211_phymode);
 int    ieee80211_media2rate(int);
-uint8_t        ieee80211_plcp2rate(uint8_t, int);
-u_int  ieee80211_mhz2ieee(u_int, u_int);
-u_int  ieee80211_chan2ieee(struct ieee80211com *,
+int    ieee80211_mhz2ieee(u_int, u_int);
+int    ieee80211_chan2ieee(struct ieee80211com *,
                const struct ieee80211_channel *);
 u_int  ieee80211_ieee2mhz(u_int, u_int);
+struct ieee80211_channel *ieee80211_find_channel(struct ieee80211com *,
+               int freq, int flags);
+struct ieee80211_channel *ieee80211_find_channel_byieee(struct ieee80211com *,
+               int ieee, int flags);
 int    ieee80211_setmode(struct ieee80211com *, enum ieee80211_phymode);
-enum ieee80211_phymode ieee80211_chan2mode(struct ieee80211com *,
-               struct ieee80211_channel *);
-enum ieee80211_modtype ieee80211_rate2modtype(uint8_t);
+enum ieee80211_phymode ieee80211_chan2mode(const struct ieee80211_channel *);
+uint32_t ieee80211_mac_hash(const struct ieee80211com *,
+               const uint8_t addr[IEEE80211_ADDR_LEN]);
+
+void   ieee80211_radiotap_attach(struct ieee80211com *,
+           struct ieee80211_radiotap_header *th, int tlen,
+               uint32_t tx_radiotap,
+           struct ieee80211_radiotap_header *rh, int rlen,
+               uint32_t rx_radiotap);
+void   ieee80211_radiotap_detach(struct ieee80211com *);
+void   ieee80211_radiotap_vattach(struct ieee80211vap *);
+void   ieee80211_radiotap_vdetach(struct ieee80211vap *);
+void   ieee80211_radiotap_chan_change(struct ieee80211com *);
+void   ieee80211_radiotap_tx(struct ieee80211vap *, struct mbuf *);
+void   ieee80211_radiotap_rx(struct ieee80211vap *, struct mbuf *);
+void   ieee80211_radiotap_rx_all(struct ieee80211com *, struct mbuf *);
+
+static __inline int
+ieee80211_radiotap_active(const struct ieee80211com *ic)
+{
+       return (ic->ic_flags_ext & IEEE80211_FEXT_BPF) != 0;
+}
+
+static __inline int
+ieee80211_radiotap_active_vap(const struct ieee80211vap *vap)
+{
+       return (vap->iv_flags_ext & IEEE80211_FEXT_BPF) ||
+           vap->iv_ic->ic_montaps != 0;
+}
+
+/*
+ * Enqueue a task on the state thread.
+ */
+static __inline void
+ieee80211_runtask(struct ieee80211com *ic, struct task *task)
+{
+       taskqueue_enqueue(ic->ic_tq, task);
+}
 
-uint8_t *ieee80211_add_ssid(uint8_t *, const uint8_t *, u_int);
-uint8_t *ieee80211_add_xrates(uint8_t *, const struct ieee80211_rateset *);
-uint8_t *ieee80211_add_rates(uint8_t *, const struct ieee80211_rateset *);
+/*
+ * Wait for a queued task to complete.
+ */
+static __inline void
+ieee80211_draintask(struct ieee80211com *ic, struct task *task)
+{
+       taskqueue_drain(ic->ic_tq, task);
+}
 
 /* 
  * Key update synchronization methods.  XXX should not be visible.
  */
 static __inline void
-ieee80211_key_update_begin(struct ieee80211com *ic)
+ieee80211_key_update_begin(struct ieee80211vap *vap)
 {
-       ic->ic_crypto.cs_key_update_begin(ic);
+       vap->iv_key_update_begin(vap);
 }
 static __inline void
-ieee80211_key_update_end(struct ieee80211com *ic)
+ieee80211_key_update_end(struct ieee80211vap *vap)
 {
-       ic->ic_crypto.cs_key_update_end(ic);
+       vap->iv_key_update_end(vap);
 }
 
 /*
@@ -385,8 +762,39 @@ ieee80211_anyhdrspace(struct ieee80211com *ic, const void *data)
        return size;
 }
 
-#endif /* _KERNEL */
+/*
+ * Notify a vap that beacon state has been updated.
+ */
+static __inline void
+ieee80211_beacon_notify(struct ieee80211vap *vap, int what)
+{
+       if (vap->iv_state == IEEE80211_S_RUN)
+               vap->iv_update_beacon(vap, what);
+}
 
+/*
+ * Calculate HT channel promotion flags for a channel.
+ * XXX belongs in ieee80211_ht.h but needs IEEE80211_FHT_*
+ */
+static __inline int
+ieee80211_htchanflags(const struct ieee80211_channel *c)
+{
+       return IEEE80211_IS_CHAN_HT40(c) ?
+           IEEE80211_FHT_HT | IEEE80211_FHT_USEHT40 :
+           IEEE80211_IS_CHAN_HT(c) ?  IEEE80211_FHT_HT : 0;
+}
+
+/*
+ * Debugging facilities compiled in when IEEE80211_DEBUG is defined.
+ *
+ * The intent is that any problem in the net80211 layer can be
+ * diagnosed by inspecting the statistics (dumped by the wlanstats
+ * program) and/or the msgs generated by net80211.  Messages are
+ * broken into functional classes and can be controlled with the
+ * wlandebug program.  Certain of these msg groups are for facilities
+ * that are no longer part of net80211 (e.g. IEEE80211_MSG_DOT1XSM).
+ */
+#define        IEEE80211_MSG_11N       0x80000000      /* 11n mode debug */
 #define        IEEE80211_MSG_DEBUG     0x40000000      /* IFF_DEBUG equivalent */
 #define        IEEE80211_MSG_DUMPPKTS  0x20000000      /* IFF_LINK2 equivalant */
 #define        IEEE80211_MSG_CRYPTO    0x10000000      /* crypto work */
@@ -400,11 +808,11 @@ ieee80211_anyhdrspace(struct ieee80211com *ic, const void *data)
 #define        IEEE80211_MSG_OUTPUT    0x00100000      /* output handling */
 #define        IEEE80211_MSG_STATE     0x00080000      /* state machine */
 #define        IEEE80211_MSG_POWER     0x00040000      /* power save handling */
-#define        IEEE80211_MSG_DOT1X     0x00020000      /* 802.1x authenticator */
+#define        IEEE80211_MSG_HWMP      0x00020000      /* hybrid mesh protocol */
 #define        IEEE80211_MSG_DOT1XSM   0x00010000      /* 802.1x state machine */
 #define        IEEE80211_MSG_RADIUS    0x00008000      /* 802.1x radius client */
 #define        IEEE80211_MSG_RADDUMP   0x00004000      /* dump 802.1x radius packets */
-#define        IEEE80211_MSG_RADKEYS   0x00002000      /* dump 802.1x keys */
+#define        IEEE80211_MSG_MESH      0x00002000      /* mesh networking */
 #define        IEEE80211_MSG_WPA       0x00001000      /* WPA/RSN protocol */
 #define        IEEE80211_MSG_ACL       0x00000800      /* ACL handling */
 #define        IEEE80211_MSG_WME       0x00000400      /* WME protocol */
@@ -412,67 +820,97 @@ ieee80211_anyhdrspace(struct ieee80211com *ic, const void *data)
 #define        IEEE80211_MSG_DOTH      0x00000100      /* 802.11h support */
 #define        IEEE80211_MSG_INACT     0x00000080      /* inactivity handling */
 #define        IEEE80211_MSG_ROAM      0x00000040      /* sta-mode roaming */
+#define        IEEE80211_MSG_RATECTL   0x00000020      /* tx rate control */
+#define        IEEE80211_MSG_ACTION    0x00000010      /* action frame handling */
+#define        IEEE80211_MSG_WDS       0x00000008      /* WDS handling */
+#define        IEEE80211_MSG_IOCTL     0x00000004      /* ioctl handling */
+#define        IEEE80211_MSG_TDMA      0x00000002      /* TDMA handling */
 
 #define        IEEE80211_MSG_ANY       0xffffffff      /* anything */
 
-#ifdef _KERNEL
+#define        IEEE80211_MSG_BITS \
+       "\20\2TDMA\3IOCTL\4WDS\5ACTION\6RATECTL\7ROAM\10INACT\11DOTH\12SUPERG" \
+       "\13WME\14ACL\15WPA\16RADKEYS\17RADDUMP\20RADIUS\21DOT1XSM\22HWMP" \
+       "\23POWER\24STATE\25OUTPUT\26SCAN\27AUTH\30ASSOC\31NODE\32ELEMID" \
+       "\33XRATE\34INPUT\35CRYPTO\36DUPMPKTS\37DEBUG\04011N"
 
 #ifdef IEEE80211_DEBUG
-#define        ieee80211_msg(_ic, _m)  ((_ic)->ic_debug & (_m))
-#define        IEEE80211_DPRINTF(_ic, _m, _fmt, ...) do {                      \
-       if (ieee80211_msg(_ic, _m))                                     \
-               ieee80211_note(_ic, _fmt, __VA_ARGS__);                 \
+#define        ieee80211_msg(_vap, _m) ((_vap)->iv_debug & (_m))
+#define        IEEE80211_DPRINTF(_vap, _m, _fmt, ...) do {                     \
+       if (ieee80211_msg(_vap, _m))                                    \
+               ieee80211_note(_vap, _fmt, __VA_ARGS__);                \
 } while (0)
-#define IEEE80211_PRINT_NODERATES(_ic, _ni, _m) do {                   \
-       if (ieee80211_msg(_ic, _m | IEEE80211_MSG_XRATE)) {             \
-               ieee80211_note(_ic, "%s: [%6D] rate set: ", __func__,   \
-                              _ni->ni_macaddr, ":");                   \
-               ieee80211_print_rateset(&_ni->ni_rates);                \
-               kprintf("\n");                                          \
-       }                                                               \
+#define        IEEE80211_NOTE(_vap, _m, _ni, _fmt, ...) do {                   \
+       if (ieee80211_msg(_vap, _m))                                    \
+               ieee80211_note_mac(_vap, (_ni)->ni_macaddr, _fmt, __VA_ARGS__);\
 } while (0)
-#define        IEEE80211_NOTE(_ic, _m, _ni, _fmt, ...) do {                    \
-       if (ieee80211_msg(_ic, _m))                                     \
-               ieee80211_note_mac(_ic, (_ni)->ni_macaddr, _fmt, __VA_ARGS__);\
+#define        IEEE80211_NOTE_MAC(_vap, _m, _mac, _fmt, ...) do {              \
+       if (ieee80211_msg(_vap, _m))                                    \
+               ieee80211_note_mac(_vap, _mac, _fmt, __VA_ARGS__);      \
 } while (0)
-#define        IEEE80211_NOTE_MAC(_ic, _m, _mac, _fmt, ...) do {               \
-       if (ieee80211_msg(_ic, _m))                                     \
-               ieee80211_note_mac(_ic, _mac, _fmt, __VA_ARGS__);       \
+#define        IEEE80211_NOTE_FRAME(_vap, _m, _wh, _fmt, ...) do {             \
+       if (ieee80211_msg(_vap, _m))                                    \
+               ieee80211_note_frame(_vap, _wh, _fmt, __VA_ARGS__);     \
 } while (0)
-#define        IEEE80211_NOTE_FRAME(_ic, _m, _wh, _fmt, ...) do {              \
-       if (ieee80211_msg(_ic, _m))                                     \
-               ieee80211_note_frame(_ic, _wh, _fmt, __VA_ARGS__);      \
+void   ieee80211_note(struct ieee80211vap *, const char *, ...);
+void   ieee80211_note_mac(struct ieee80211vap *,
+               const uint8_t mac[IEEE80211_ADDR_LEN], const char *, ...);
+void   ieee80211_note_frame(struct ieee80211vap *,
+               const struct ieee80211_frame *, const char *, ...);
+#define        ieee80211_msg_debug(_vap) \
+       ((_vap)->iv_debug & IEEE80211_MSG_DEBUG)
+#define        ieee80211_msg_dumppkts(_vap) \
+       ((_vap)->iv_debug & IEEE80211_MSG_DUMPPKTS)
+#define        ieee80211_msg_input(_vap) \
+       ((_vap)->iv_debug & IEEE80211_MSG_INPUT)
+#define        ieee80211_msg_radius(_vap) \
+       ((_vap)->iv_debug & IEEE80211_MSG_RADIUS)
+#define        ieee80211_msg_dumpradius(_vap) \
+       ((_vap)->iv_debug & IEEE80211_MSG_RADDUMP)
+#define        ieee80211_msg_dumpradkeys(_vap) \
+       ((_vap)->iv_debug & IEEE80211_MSG_RADKEYS)
+#define        ieee80211_msg_scan(_vap) \
+       ((_vap)->iv_debug & IEEE80211_MSG_SCAN)
+#define        ieee80211_msg_assoc(_vap) \
+       ((_vap)->iv_debug & IEEE80211_MSG_ASSOC)
+
+/*
+ * Emit a debug message about discarding a frame or information
+ * element.  One format is for extracting the mac address from
+ * the frame header; the other is for when a header is not
+ * available or otherwise appropriate.
+ */
+#define        IEEE80211_DISCARD(_vap, _m, _wh, _type, _fmt, ...) do {         \
+       if ((_vap)->iv_debug & (_m))                                    \
+               ieee80211_discard_frame(_vap, _wh, _type, _fmt, __VA_ARGS__);\
+} while (0)
+#define        IEEE80211_DISCARD_IE(_vap, _m, _wh, _type, _fmt, ...) do {      \
+       if ((_vap)->iv_debug & (_m))                                    \
+               ieee80211_discard_ie(_vap, _wh, _type, _fmt, __VA_ARGS__);\
 } while (0)
-void   ieee80211_note(struct ieee80211com *ic, const char *fmt, ...);
-void   ieee80211_note_mac(struct ieee80211com *ic,
-               const uint8_t mac[IEEE80211_ADDR_LEN], const char *fmt, ...);
-void   ieee80211_note_frame(struct ieee80211com *ic,
-               const struct ieee80211_frame *wh, const char *fmt, ...);
-#define        ieee80211_msg_debug(_ic) \
-       ((_ic)->ic_debug & IEEE80211_MSG_DEBUG)
-#define        ieee80211_msg_dumppkts(_ic) \
-       ((_ic)->ic_debug & IEEE80211_MSG_DUMPPKTS)
-#define        ieee80211_msg_input(_ic) \
-       ((_ic)->ic_debug & IEEE80211_MSG_INPUT)
-#define        ieee80211_msg_radius(_ic) \
-       ((_ic)->ic_debug & IEEE80211_MSG_RADIUS)
-#define        ieee80211_msg_dumpradius(_ic) \
-       ((_ic)->ic_debug & IEEE80211_MSG_RADDUMP)
-#define        ieee80211_msg_dumpradkeys(_ic) \
-       ((_ic)->ic_debug & IEEE80211_MSG_RADKEYS)
-#define        ieee80211_msg_scan(_ic) \
-       ((_ic)->ic_debug & IEEE80211_MSG_SCAN)
-#define        ieee80211_msg_assoc(_ic) \
-       ((_ic)->ic_debug & IEEE80211_MSG_ASSOC)
+#define        IEEE80211_DISCARD_MAC(_vap, _m, _mac, _type, _fmt, ...) do {    \
+       if ((_vap)->iv_debug & (_m))                                    \
+               ieee80211_discard_mac(_vap, _mac, _type, _fmt, __VA_ARGS__);\
+} while (0)
+
+void ieee80211_discard_frame(struct ieee80211vap *,
+       const struct ieee80211_frame *, const char *type, const char *fmt, ...);
+void ieee80211_discard_ie(struct ieee80211vap *,
+       const struct ieee80211_frame *, const char *type, const char *fmt, ...);
+void ieee80211_discard_mac(struct ieee80211vap *,
+       const uint8_t mac[IEEE80211_ADDR_LEN], const char *type,
+       const char *fmt, ...);
 #else
-#define        IEEE80211_DPRINTF(_ic, _m, _fmt, ...)
-#define IEEE80211_PRINT_NODERATES(_ic, _ni, _m)
-#define        IEEE80211_NOTE_FRAME(_ic, _m, _wh, _fmt, ...)
-#define        IEEE80211_NOTE_MAC(_ic, _m, _mac, _fmt, ...)
-#define        ieee80211_msg_dumppkts(_ic)     0
-#define        ieee80211_msg(_ic, _m)          0
+#define        IEEE80211_DPRINTF(_vap, _m, _fmt, ...)
+#define        IEEE80211_NOTE(_vap, _m, _ni, _fmt, ...)
+#define        IEEE80211_NOTE_FRAME(_vap, _m, _wh, _fmt, ...)
+#define        IEEE80211_NOTE_MAC(_vap, _m, _mac, _fmt, ...)
+#define        ieee80211_msg_dumppkts(_vap)    0
+#define        ieee80211_msg(_vap, _m)         0
+
+#define        IEEE80211_DISCARD(_vap, _m, _wh, _type, _fmt, ...)
+#define        IEEE80211_DISCARD_IE(_vap, _m, _wh, _type, _fmt, ...)
+#define        IEEE80211_DISCARD_MAC(_vap, _m, _mac, _type, _fmt, ...)
 #endif
 
-#endif /* _KERNEL */
-
 #endif /* _NET80211_IEEE80211_VAR_H_ */
diff --git a/sys/netproto/802_11/ieee80211_wds.h b/sys/netproto/802_11/ieee80211_wds.h
new file mode 100644 (file)
index 0000000..dc53b94
--- /dev/null
@@ -0,0 +1,40 @@
+/*-
+ * Copyright (c) 2007-2008 Sam Leffler, Errno Consulting
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
+ * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
+ * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
+ * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
+ * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
+ * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
+ * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
+ * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ *
+ * $FreeBSD: head/sys/net80211/ieee80211_wds.h 178354 2008-04-20 20:35:46Z sam $
+ * $DragonFly$
+ */
+#ifndef _NET80211_IEEE80211_WDS_H_
+#define _NET80211_IEEE80211_WDS_H_
+
+/*
+ * WDS implementation definitions.
+ */
+void   ieee80211_wds_attach(struct ieee80211com *);
+void   ieee80211_wds_detach(struct ieee80211com *);
+
+void   ieee80211_dwds_mcast(struct ieee80211vap *, struct mbuf *);
+void   ieee80211_dwds_discover(struct ieee80211_node *, struct mbuf *);
+int    ieee80211_node_wdsq_age(struct ieee80211_node *);
+#endif /* !_NET80211_IEEE80211_WDS_H_ */
diff --git a/sys/netproto/802_11/if_wavelan_ieee.h b/sys/netproto/802_11/if_wavelan_ieee.h
deleted file mode 100644 (file)
index d941271..0000000
+++ /dev/null
@@ -1,750 +0,0 @@
-/*
- * Copyright (c) 1997, 1998, 1999
- *     Bill Paul <wpaul@ctr.columbia.edu>.  All rights reserved.
- *
- * Redistribution and use in source and binary forms, with or without
- * modification, are permitted provided that the following conditions
- * are met:
- * 1. Redistributions of source code must retain the above copyright
- *    notice, this list of conditions and the following disclaimer.
- * 2. Redistributions in binary form must reproduce the above copyright
- *    notice, this list of conditions and the following disclaimer in the
- *    documentation and/or other materials provided with the distribution.
- * 3. All advertising materials mentioning features or use of this software
- *    must display the following acknowledgement:
- *     This product includes software developed by Bill Paul.
- * 4. Neither the name of the author nor the names of any co-contributors
- *    may be used to endorse or promote products derived from this software
- *    without specific prior written permission.
- *
- * THIS SOFTWARE IS PROVIDED BY Bill Paul AND CONTRIBUTORS ``AS IS'' AND
- * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
- * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
- * ARE DISCLAIMED.  IN NO EVENT SHALL Bill Paul OR THE VOICES IN HIS HEAD
- * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
- * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
- * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
- * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
- * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
- * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
- * THE POSSIBILITY OF SUCH DAMAGE.
- *
- * $FreeBSD: src/sys/dev/wi/if_wavelan_ieee.h,v 1.18 2003/06/27 00:49:04 sam Exp $
- * $DragonFly: src/sys/netproto/802_11/if_wavelan_ieee.h,v 1.1 2004/07/26 16:30:17 joerg Exp $
- */
-
-#ifndef _NETPROTO_802_11_IF_WAVELAN_IEEE_H 
-#define        _NETPROTO_802_11_IF_WAVELAN_IEEE_H 
-
-#include <sys/ioccom.h>
-
-/*
- * This header defines a simple command interface to the FreeBSD
- * WaveLAN/IEEE driver (wi) driver, which is used to set certain
- * device-specific parameters which can't be easily managed through
- * ifconfig(8). No, sysctl(2) is not the answer. I said a _simple_
- * interface, didn't I.
- */
-
-#ifndef SIOCSWAVELAN
-#define        SIOCSWAVELAN    SIOCSIFGENERIC
-#endif
-
-#ifndef SIOCGWAVELAN
-#define        SIOCGWAVELAN    SIOCGIFGENERIC
-#endif
-
-/*
- * Technically I don't think there's a limit to a record
- * length. The largest record is the one that contains the CIS
- * data, which is 240 words long, so 256 should be a safe
- * value.
- */
-#define        WI_MAX_DATALEN  512
-
-struct wi_req {
-       uint16_t        wi_len;
-       uint16_t        wi_type;
-       uint16_t        wi_val[WI_MAX_DATALEN];
-};
-
-/*
- * Private LTV records (interpreted only by the driver). This is
- * a minor kludge to allow reading the interface statistics from
- * the driver.
- */
-#define        WI_RID_IFACE_STATS      0x0100
-#define        WI_RID_MGMT_XMIT        0x0200
-#define        WI_RID_ZERO_CACHE       0x0300
-#define        WI_RID_READ_CACHE       0x0400
-#define        WI_RID_FWDOWNLOAD       0x0500
-#define        WI_RID_MONITOR_MODE     0x0600
-#define        WI_RID_MIF              0x0700
-#define        WI_RID_SCAN_APS         0x0800
-#define        WI_RID_READ_APS         0x0900
-
-struct wi_80211_hdr {
-       uint16_t                frame_ctl;
-       uint16_t                dur_id;
-       uint8_t                 addr1[6];
-       uint8_t                 addr2[6];
-       uint8_t                 addr3[6];
-       uint16_t                seq_ctl;
-       uint8_t                 addr4[6];
-};
-
-#define        WI_FCTL_VERS            0x0002
-#define        WI_FCTL_FTYPE           0x000C
-#define        WI_FCTL_STYPE           0x00F0
-#define        WI_FCTL_TODS            0x0100
-#define        WI_FCTL_FROMDS          0x0200
-#define        WI_FCTL_MOREFRAGS       0x0400
-#define        WI_FCTL_RETRY           0x0800
-#define        WI_FCTL_PM              0x1000
-#define        WI_FCTL_MOREDATA        0x2000
-#define        WI_FCTL_WEP             0x4000
-#define        WI_FCTL_ORDER           0x8000
-
-#define        WI_FTYPE_MGMT           0x0000
-#define        WI_FTYPE_CTL            0x0004
-#define        WI_FTYPE_DATA           0x0008
-
-#define        WI_STYPE_MGMT_ASREQ     0x0000  /* association request */
-#define        WI_STYPE_MGMT_ASRESP    0x0010  /* association response */
-#define        WI_STYPE_MGMT_REASREQ   0x0020  /* reassociation request */
-#define        WI_STYPE_MGMT_REASRESP  0x0030  /* reassociation response */
-#define        WI_STYPE_MGMT_PROBEREQ  0x0040  /* probe request */
-#define        WI_STYPE_MGMT_PROBERESP 0x0050  /* probe response */
-#define        WI_STYPE_MGMT_BEACON    0x0080  /* beacon */
-#define        WI_STYPE_MGMT_ATIM      0x0090  /* announcement traffic ind msg */
-#define        WI_STYPE_MGMT_DISAS     0x00A0  /* disassociation */
-#define        WI_STYPE_MGMT_AUTH      0x00B0  /* authentication */
-#define        WI_STYPE_MGMT_DEAUTH    0x00C0  /* deauthentication */
-
-#define        WI_STYPE_CTL_PSPOLL     0x00A0
-#define        WI_STYPE_CTL_RTS        0x00B0
-#define        WI_STYPE_CTL_CTS        0x00C0
-#define        WI_STYPE_CTL_ACK        0x00D0
-#define        WI_STYPE_CTL_CFEND      0x00E0
-#define        WI_STYPE_CTL_CFENDACK   0x00F0
-
-struct wi_mgmt_hdr {
-       uint16_t                frame_ctl;
-       uint16_t                duration;
-       uint8_t                 dst_addr[6];
-       uint8_t                 src_addr[6];
-       uint8_t                 bssid[6];
-       uint16_t                seq_ctl;
-};
-
-/* 
- * Lucent/wavelan IEEE signal strength cache
- *
- * driver keeps cache of last
- * MAXWICACHE packets to arrive including signal strength info.
- * daemons may read this via ioctl
- *
- * Each entry in the wi_sigcache has a unique macsrc.
- */
-struct wi_sigcache {
-       char    macsrc[6];      /* unique MAC address for entry */
-       int     ipsrc;          /* ip address associated with packet */
-       int     signal;         /* signal strength of the packet */
-       int     noise;          /* noise value */
-       int     quality;        /* quality of the packet */
-};
-
-/*
- * Firmware downloading API.  We support downloading into RAM and into
- * flash.  We copy the entire .hex file for both the primary and secondary
- * firmware into the kernel, which is minorly gross, but matches the
- * format of the compiled in firmware.
- */
-struct wi_fwdownload {
-       int     type;           /* What type of download. */
-#define        WI_FW_RAM       1
-#define        WI_FW_FLASH     2
-       size_t  pri_len;        /* Primary firmware length */
-       size_t  sec_len;        /* Secondary firmware length */
-       caddr_t pri_data;       /* Pointer (user) to primary data */
-       caddr_t sec_data;       /* Pointer (user) to secondary data */
-};
-
-struct wi_counters {
-       uint32_t                wi_tx_unicast_frames;
-       uint32_t                wi_tx_multicast_frames;
-       uint32_t                wi_tx_fragments;
-       uint32_t                wi_tx_unicast_octets;
-       uint32_t                wi_tx_multicast_octets;
-       uint32_t                wi_tx_deferred_xmits;
-       uint32_t                wi_tx_single_retries;
-       uint32_t                wi_tx_multi_retries;
-       uint32_t                wi_tx_retry_limit;
-       uint32_t                wi_tx_discards;
-       uint32_t                wi_rx_unicast_frames;
-       uint32_t                wi_rx_multicast_frames;
-       uint32_t                wi_rx_fragments;
-       uint32_t                wi_rx_unicast_octets;
-       uint32_t                wi_rx_multicast_octets;
-       uint32_t                wi_rx_fcs_errors;
-       uint32_t                wi_rx_discards_nobuf;
-       uint32_t                wi_tx_discards_wrong_sa;
-       uint32_t                wi_rx_WEP_cant_decrypt;
-       uint32_t                wi_rx_msg_in_msg_frags;
-       uint32_t                wi_rx_msg_in_bad_msg_frags;
-};
-
-/*
- * Network parameters, static configuration entities.
- */
-#define        WI_RID_PORTTYPE         0xFC00 /* Connection control characteristics */
-#define        WI_RID_MAC_NODE         0xFC01 /* MAC address of this station */
-#define        WI_RID_DESIRED_SSID     0xFC02 /* Service Set ID for connection */
-#define        WI_RID_OWN_CHNL         0xFC03 /* Comm channel for BSS creation */
-#define        WI_RID_OWN_SSID         0xFC04 /* IBSS creation ID */
-#define        WI_RID_OWN_ATIM_WIN     0xFC05 /* ATIM window time for IBSS creation */
-#define        WI_RID_SYSTEM_SCALE     0xFC06 /* scale that specifies AP density */
-#define        WI_RID_MAX_DATALEN      0xFC07 /* Max len of MAC frame body data */
-#define        WI_RID_MAC_WDS          0xFC08 /* MAC addr of corresponding WDS node */
-#define        WI_RID_PM_ENABLED       0xFC09 /* ESS power management enable */
-#define        WI_RID_PM_EPS           0xFC0A /* PM EPS/PS mode */
-#define        WI_RID_MCAST_RX         0xFC0B /* ESS PM mcast reception */
-#define        WI_RID_MAX_SLEEP        0xFC0C /* max sleep time for ESS PM */
-#define        WI_RID_HOLDOVER         0xFC0D /* holdover time for ESS PM */
-#define        WI_RID_NODENAME         0xFC0E /* ID name of this node for diag */
-#define        WI_RID_DTIM_PERIOD      0xFC10 /* beacon interval between DTIMs */
-#define        WI_RID_WDS_ADDR1        0xFC11 /* port 1 MAC of WDS link node */
-#define        WI_RID_WDS_ADDR2        0xFC12 /* port 1 MAC of WDS link node */
-#define        WI_RID_WDS_ADDR3        0xFC13 /* port 1 MAC of WDS link node */
-#define        WI_RID_WDS_ADDR4        0xFC14 /* port 1 MAC of WDS link node */
-#define        WI_RID_WDS_ADDR5        0xFC15 /* port 1 MAC of WDS link node */
-#define        WI_RID_WDS_ADDR6        0xFC16 /* port 1 MAC of WDS link node */
-#define        WI_RID_MCAST_PM_BUF     0xFC17 /* PM buffering of mcast */
-#define        WI_RID_ENCRYPTION       0xFC20 /* enable/disable WEP */
-#define        WI_RID_AUTHTYPE         0xFC21 /* specify authentication type */
-#define        WI_RID_P2_TX_CRYPT_KEY  0xFC23
-#define        WI_RID_P2_CRYPT_KEY0    0xFC24
-#define        WI_RID_P2_CRYPT_KEY1    0xFC25
-#define        WI_RID_MICROWAVE_OVEN   0xFC25
-#define        WI_RID_P2_CRYPT_KEY2    0xFC26
-#define        WI_RID_P2_CRYPT_KEY3    0xFC27
-#define        WI_RID_P2_ENCRYPTION    0xFC28
-#define                PRIVACY_INVOKED         0x01
-#define                EXCLUDE_UNENCRYPTED     0x02
-#define                HOST_ENCRYPT            0x10
-#define                IV_EVERY_FRAME          0x00    /* IV = Initialization Vector */
-#define                IV_EVERY10_FRAME        0x20    /* every 10 frame IV reuse */
-#define                IV_EVERY50_FRAME        0x40    /* every 50 frame IV reuse */
-#define                IV_EVERY100_FRAME       0x60    /* every 100 frame IV reuse */
-#define                HOST_DECRYPT            0x80
-#define        WI_RID_WEP_MAPTABLE     0xFC29
-#define        WI_RID_CNFAUTHMODE      0xFC2A
-#define        WI_RID_ROAMING_MODE     0xFC2D
-#define        WI_RID_OWN_BEACON_INT   0xFC33 /* beacon xmit time for BSS creation */
-#define        WI_RID_CNF_DBM_ADJUST   0xFC46
-#define        WI_RID_DBM_ADJUST       0xFC46 /* RSSI - WI_RID_DBM_ADJUST ~ dBm */
-#define        WI_RID_BASIC_RATE       0xFCB3
-#define        WI_RID_SUPPORT_RATE     0xFCB4
-
-/*
- * Network parameters, dynamic configuration entities
- */
-#define        WI_RID_MCAST_LIST       0xFC80 /* list of multicast addrs */
-#define        WI_RID_CREATE_IBSS      0xFC81 /* create IBSS */
-#define        WI_RID_FRAG_THRESH      0xFC82 /* frag len, unicast msg xmit */
-#define        WI_RID_RTS_THRESH       0xFC83 /* frame len for RTS/CTS handshake */
-#define        WI_RID_TX_RATE          0xFC84 /* data rate for message xmit
-                                       * 0 == Fixed 1mbps
-                                       * 1 == Fixed 2mbps
-                                       * 2 == auto fallback
-                                       */
-#define        WI_RID_PROMISC          0xFC85 /* enable promisc mode */
-#define        WI_RID_FRAG_THRESH0     0xFC90
-#define        WI_RID_FRAG_THRESH1     0xFC91
-#define        WI_RID_FRAG_THRESH2     0xFC92
-#define        WI_RID_FRAG_THRESH3     0xFC93
-#define        WI_RID_FRAG_THRESH4     0xFC94
-#define        WI_RID_FRAG_THRESH5     0xFC95
-#define        WI_RID_FRAG_THRESH6     0xFC96
-#define        WI_RID_RTS_THRESH0      0xFC97
-#define        WI_RID_RTS_THRESH1      0xFC98
-#define        WI_RID_RTS_THRESH2      0xFC99