1 //------------------------------------------------------------------------------
2 // <copyright file="wlan_recv_beacon.c" company="Atheros">
3 // Copyright (c) 2004-2010 Atheros Corporation. All rights reserved.
6 // Permission to use, copy, modify, and/or distribute this software for any
7 // purpose with or without fee is hereby granted, provided that the above
8 // copyright notice and this permission notice appear in all copies.
10 // THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
11 // WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
12 // MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
13 // ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
14 // WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
15 // ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
16 // OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
19 //------------------------------------------------------------------------------
20 //==============================================================================
21 // IEEE 802.11 input handling.
23 // Author(s): ="Atheros"
24 //==============================================================================
30 #include <ieee80211.h>
33 #define IEEE80211_VERIFY_LENGTH(_len, _minlen) do { \
34 if ((_len) < (_minlen)) { \
39 #define IEEE80211_VERIFY_ELEMENT(__elem, __maxlen) do { \
40 if ((__elem) == NULL) { \
43 if ((__elem)[1] > (__maxlen)) { \
49 /* unaligned little endian access */
50 #define LE_READ_2(p) \
52 ((((u8 *)(p))[0] ) | (((u8 *)(p))[1] << 8)))
54 #define LE_READ_4(p) \
56 ((((u8 *)(p))[0] ) | (((u8 *)(p))[1] << 8) | \
57 (((u8 *)(p))[2] << 16) | (((u8 *)(p))[3] << 24)))
61 iswpaoui(const u8 *frm)
63 return frm[1] > 3 && LE_READ_4(frm+2) == ((WPA_OUI_TYPE<<24)|WPA_OUI);
67 iswmmoui(const u8 *frm)
69 return frm[1] > 3 && LE_READ_4(frm+2) == ((WMM_OUI_TYPE<<24)|WMM_OUI);
72 /* unused functions for now */
75 iswmmparam(const u8 *frm)
77 return frm[1] > 5 && frm[6] == WMM_PARAM_OUI_SUBTYPE;
81 iswmminfo(const u8 *frm)
83 return frm[1] > 5 && frm[6] == WMM_INFO_OUI_SUBTYPE;
88 isatherosoui(const u8 *frm)
90 return frm[1] > 3 && LE_READ_4(frm+2) == ((ATH_OUI_TYPE<<24)|ATH_OUI);
94 iswscoui(const u8 *frm)
96 return frm[1] > 3 && LE_READ_4(frm+2) == ((0x04<<24)|WPA_OUI);
100 wlan_parse_beacon(u8 *buf, int framelen, struct ieee80211_common_ie *cie)
103 u8 elemid_ssid = false;
106 efrm = (u8 *) (frm + framelen);
109 * beacon/probe response frame format
111 * [2] beacon interval
112 * [2] capability information
114 * [tlv] supported rates
115 * [tlv] country information
116 * [tlv] parameter set (FH/DS)
117 * [tlv] erp information
118 * [tlv] extended supported rates
121 * [tlv] Atheros Advanced Capabilities
123 IEEE80211_VERIFY_LENGTH(efrm - frm, 12);
124 A_MEMZERO(cie, sizeof(*cie));
126 cie->ie_tstamp = frm; frm += 8;
127 cie->ie_beaconInt = A_LE2CPU16(*(u16 *)frm); frm += 2;
128 cie->ie_capInfo = A_LE2CPU16(*(u16 *)frm); frm += 2;
133 case IEEE80211_ELEMID_SSID:
139 case IEEE80211_ELEMID_RATES:
142 case IEEE80211_ELEMID_COUNTRY:
143 cie->ie_country = frm;
145 case IEEE80211_ELEMID_FHPARMS:
147 case IEEE80211_ELEMID_DSPARMS:
148 cie->ie_chan = frm[2];
150 case IEEE80211_ELEMID_TIM:
153 case IEEE80211_ELEMID_IBSSPARMS:
155 case IEEE80211_ELEMID_XRATES:
156 cie->ie_xrates = frm;
158 case IEEE80211_ELEMID_ERP:
160 //A_PRINTF("Discarding ERP Element - Bad Len\n");
163 cie->ie_erp = frm[2];
165 case IEEE80211_ELEMID_RSN:
168 case IEEE80211_ELEMID_HTCAP_ANA:
171 case IEEE80211_ELEMID_HTINFO_ANA:
175 case IEEE80211_ELEMID_WAPI:
179 case IEEE80211_ELEMID_VENDOR:
182 } else if (iswmmoui(frm)) {
184 } else if (isatherosoui(frm)) {
186 } else if(iswscoui(frm)) {
195 IEEE80211_VERIFY_ELEMENT(cie->ie_rates, IEEE80211_RATE_MAXSIZE);
196 IEEE80211_VERIFY_ELEMENT(cie->ie_ssid, IEEE80211_NWID_LEN);