Merge branch 'tty-linus' of git://git.kernel.org/pub/scm/linux/kernel/git/gregkh...
[pandora-kernel.git] / drivers / staging / ath6kl / os / linux / cfg80211.c
1 //------------------------------------------------------------------------------
2 // Copyright (c) 2004-2010 Atheros Communications Inc.
3 // All rights reserved.
4 //
5 // 
6 //
7 // Permission to use, copy, modify, and/or distribute this software for any
8 // purpose with or without fee is hereby granted, provided that the above
9 // copyright notice and this permission notice appear in all copies.
10 //
11 // THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
12 // WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
13 // MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
14 // ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
15 // WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
16 // ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
17 // OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
18 //
19 //
20 //
21 // Author(s): ="Atheros"
22 //------------------------------------------------------------------------------
23
24 #include <linux/wireless.h>
25 #include <linux/ieee80211.h>
26 #include <net/cfg80211.h>
27
28 #include "ar6000_drv.h"
29
30
31 extern A_WAITQUEUE_HEAD arEvent;
32 extern unsigned int wmitimeout;
33 extern int reconnect_flag;
34
35
36 #define RATETAB_ENT(_rate, _rateid, _flags) {   \
37     .bitrate    = (_rate),                  \
38     .flags      = (_flags),                 \
39     .hw_value   = (_rateid),                \
40 }
41
42 #define CHAN2G(_channel, _freq, _flags) {   \
43     .band           = IEEE80211_BAND_2GHZ,  \
44     .hw_value       = (_channel),           \
45     .center_freq    = (_freq),              \
46     .flags          = (_flags),             \
47     .max_antenna_gain   = 0,                \
48     .max_power      = 30,                   \
49 }
50
51 #define CHAN5G(_channel, _flags) {              \
52     .band           = IEEE80211_BAND_5GHZ,      \
53     .hw_value       = (_channel),               \
54     .center_freq    = 5000 + (5 * (_channel)),  \
55     .flags          = (_flags),                 \
56     .max_antenna_gain   = 0,                    \
57     .max_power      = 30,                       \
58 }
59
60 static struct
61 ieee80211_rate ar6k_rates[] = {
62     RATETAB_ENT(10,  0x1,   0),
63     RATETAB_ENT(20,  0x2,   0),
64     RATETAB_ENT(55,  0x4,   0),
65     RATETAB_ENT(110, 0x8,   0),
66     RATETAB_ENT(60,  0x10,  0),
67     RATETAB_ENT(90,  0x20,  0),
68     RATETAB_ENT(120, 0x40,  0),
69     RATETAB_ENT(180, 0x80,  0),
70     RATETAB_ENT(240, 0x100, 0),
71     RATETAB_ENT(360, 0x200, 0),
72     RATETAB_ENT(480, 0x400, 0),
73     RATETAB_ENT(540, 0x800, 0),
74 };
75
76 #define ar6k_a_rates     (ar6k_rates + 4)
77 #define ar6k_a_rates_size    8
78 #define ar6k_g_rates     (ar6k_rates + 0)
79 #define ar6k_g_rates_size    12
80
81 static struct
82 ieee80211_channel ar6k_2ghz_channels[] = {
83     CHAN2G(1, 2412, 0),
84     CHAN2G(2, 2417, 0),
85     CHAN2G(3, 2422, 0),
86     CHAN2G(4, 2427, 0),
87     CHAN2G(5, 2432, 0),
88     CHAN2G(6, 2437, 0),
89     CHAN2G(7, 2442, 0),
90     CHAN2G(8, 2447, 0),
91     CHAN2G(9, 2452, 0),
92     CHAN2G(10, 2457, 0),
93     CHAN2G(11, 2462, 0),
94     CHAN2G(12, 2467, 0),
95     CHAN2G(13, 2472, 0),
96     CHAN2G(14, 2484, 0),
97 };
98
99 static struct
100 ieee80211_channel ar6k_5ghz_a_channels[] = {
101     CHAN5G(34, 0),      CHAN5G(36, 0),
102     CHAN5G(38, 0),      CHAN5G(40, 0),
103     CHAN5G(42, 0),      CHAN5G(44, 0),
104     CHAN5G(46, 0),      CHAN5G(48, 0),
105     CHAN5G(52, 0),      CHAN5G(56, 0),
106     CHAN5G(60, 0),      CHAN5G(64, 0),
107     CHAN5G(100, 0),     CHAN5G(104, 0),
108     CHAN5G(108, 0),     CHAN5G(112, 0),
109     CHAN5G(116, 0),     CHAN5G(120, 0),
110     CHAN5G(124, 0),     CHAN5G(128, 0),
111     CHAN5G(132, 0),     CHAN5G(136, 0),
112     CHAN5G(140, 0),     CHAN5G(149, 0),
113     CHAN5G(153, 0),     CHAN5G(157, 0),
114     CHAN5G(161, 0),     CHAN5G(165, 0),
115     CHAN5G(184, 0),     CHAN5G(188, 0),
116     CHAN5G(192, 0),     CHAN5G(196, 0),
117     CHAN5G(200, 0),     CHAN5G(204, 0),
118     CHAN5G(208, 0),     CHAN5G(212, 0),
119     CHAN5G(216, 0),
120 };
121
122 static struct
123 ieee80211_supported_band ar6k_band_2ghz = {
124     .n_channels = ARRAY_SIZE(ar6k_2ghz_channels),
125     .channels = ar6k_2ghz_channels,
126     .n_bitrates = ar6k_g_rates_size,
127     .bitrates = ar6k_g_rates,
128 };
129
130 static struct
131 ieee80211_supported_band ar6k_band_5ghz = {
132     .n_channels = ARRAY_SIZE(ar6k_5ghz_a_channels),
133     .channels = ar6k_5ghz_a_channels,
134     .n_bitrates = ar6k_a_rates_size,
135     .bitrates = ar6k_a_rates,
136 };
137
138 static int
139 ar6k_set_wpa_version(struct ar6_softc *ar, enum nl80211_wpa_versions wpa_version)
140 {
141
142     AR_DEBUG_PRINTF(ATH_DEBUG_INFO, ("%s: %u\n", __func__, wpa_version));
143
144     if (!wpa_version) {
145         ar->arAuthMode = NONE_AUTH;
146     } else if (wpa_version & NL80211_WPA_VERSION_1) {
147         ar->arAuthMode = WPA_AUTH;
148     } else if (wpa_version & NL80211_WPA_VERSION_2) {
149         ar->arAuthMode = WPA2_AUTH;
150     } else {
151         AR_DEBUG_PRINTF(ATH_DEBUG_ERR,
152                         ("%s: %u not spported\n", __func__, wpa_version));
153         return -ENOTSUPP;
154     }
155
156     return 0;
157 }
158
159 static int
160 ar6k_set_auth_type(struct ar6_softc *ar, enum nl80211_auth_type auth_type)
161 {
162
163     AR_DEBUG_PRINTF(ATH_DEBUG_INFO, ("%s: 0x%x\n", __func__, auth_type));
164
165     switch (auth_type) {
166     case NL80211_AUTHTYPE_OPEN_SYSTEM:
167         ar->arDot11AuthMode = OPEN_AUTH;
168         break;
169     case NL80211_AUTHTYPE_SHARED_KEY:
170         ar->arDot11AuthMode = SHARED_AUTH;
171         break;
172     case NL80211_AUTHTYPE_NETWORK_EAP:
173         ar->arDot11AuthMode = LEAP_AUTH;
174         break;
175
176     case NL80211_AUTHTYPE_AUTOMATIC:
177         ar->arDot11AuthMode = OPEN_AUTH;
178         ar->arAutoAuthStage = AUTH_OPEN_IN_PROGRESS;
179         break;
180
181     default:
182         ar->arDot11AuthMode = OPEN_AUTH;
183         AR_DEBUG_PRINTF(ATH_DEBUG_INFO,
184                         ("%s: 0x%x not spported\n", __func__, auth_type));
185         return -ENOTSUPP;
186     }
187
188     return 0;
189 }
190
191 static int
192 ar6k_set_cipher(struct ar6_softc *ar, u32 cipher, bool ucast)
193 {
194     u8 *ar_cipher = ucast ? &ar->arPairwiseCrypto :
195                                 &ar->arGroupCrypto;
196     u8 *ar_cipher_len = ucast ? &ar->arPairwiseCryptoLen :
197                                     &ar->arGroupCryptoLen;
198
199     AR_DEBUG_PRINTF(ATH_DEBUG_INFO,
200                     ("%s: cipher 0x%x, ucast %u\n", __func__, cipher, ucast));
201
202     switch (cipher) {
203     case 0:
204     case IW_AUTH_CIPHER_NONE:
205         *ar_cipher = NONE_CRYPT;
206         *ar_cipher_len = 0;
207         break;
208     case WLAN_CIPHER_SUITE_WEP40:
209         *ar_cipher = WEP_CRYPT;
210         *ar_cipher_len = 5;
211         break;
212     case WLAN_CIPHER_SUITE_WEP104:
213         *ar_cipher = WEP_CRYPT;
214         *ar_cipher_len = 13;
215         break;
216     case WLAN_CIPHER_SUITE_TKIP:
217         *ar_cipher = TKIP_CRYPT;
218         *ar_cipher_len = 0;
219         break;
220     case WLAN_CIPHER_SUITE_CCMP:
221         *ar_cipher = AES_CRYPT;
222         *ar_cipher_len = 0;
223         break;
224     default:
225         AR_DEBUG_PRINTF(ATH_DEBUG_ERR,
226                         ("%s: cipher 0x%x not supported\n", __func__, cipher));
227         return -ENOTSUPP;
228     }
229
230     return 0;
231 }
232
233 static void
234 ar6k_set_key_mgmt(struct ar6_softc *ar, u32 key_mgmt)
235 {
236     AR_DEBUG_PRINTF(ATH_DEBUG_INFO, ("%s: 0x%x\n", __func__, key_mgmt));
237
238     if (WLAN_AKM_SUITE_PSK == key_mgmt) {
239         if (WPA_AUTH == ar->arAuthMode) {
240             ar->arAuthMode = WPA_PSK_AUTH;
241         } else if (WPA2_AUTH == ar->arAuthMode) {
242             ar->arAuthMode = WPA2_PSK_AUTH;
243         }
244     } else if (WLAN_AKM_SUITE_8021X != key_mgmt) {
245         ar->arAuthMode = NONE_AUTH;
246     }
247 }
248
249 static int
250 ar6k_cfg80211_connect(struct wiphy *wiphy, struct net_device *dev,
251                       struct cfg80211_connect_params *sme)
252 {
253     struct ar6_softc *ar = ar6k_priv(dev);
254     int status;
255
256     AR_DEBUG_PRINTF(ATH_DEBUG_INFO, ("%s: \n", __func__));
257     ar->smeState = SME_CONNECTING;
258
259     if(ar->arWmiReady == false) {
260         AR_DEBUG_PRINTF(ATH_DEBUG_ERR, ("%s: Wmi not ready yet\n", __func__));
261         return -EIO;
262     }
263
264     if(ar->arWlanState == WLAN_DISABLED) {
265         AR_DEBUG_PRINTF(ATH_DEBUG_ERR, ("%s: Wlan disabled\n", __func__));
266         return -EIO;
267     }
268
269     if(ar->bIsDestroyProgress) {
270         AR_DEBUG_PRINTF(ATH_DEBUG_ERR, ("%s: destroy in progress\n", __func__));
271         return -EBUSY;
272     }
273
274     if(!sme->ssid_len || IEEE80211_MAX_SSID_LEN < sme->ssid_len) {
275         AR_DEBUG_PRINTF(ATH_DEBUG_ERR, ("%s: ssid invalid\n", __func__));
276         return -EINVAL;
277     }
278
279     if(ar->arSkipScan == true &&
280        ((sme->channel && sme->channel->center_freq == 0) ||
281         (sme->bssid && !sme->bssid[0] && !sme->bssid[1] && !sme->bssid[2] &&
282          !sme->bssid[3] && !sme->bssid[4] && !sme->bssid[5])))
283     {
284         AR_DEBUG_PRINTF(ATH_DEBUG_ERR, ("%s:SkipScan: channel or bssid invalid\n", __func__));
285         return -EINVAL;
286     }
287
288     if(down_interruptible(&ar->arSem)) {
289         AR_DEBUG_PRINTF(ATH_DEBUG_ERR, ("%s: busy, couldn't get access\n", __func__));
290         return -ERESTARTSYS;
291     }
292
293     if(ar->bIsDestroyProgress) {
294         AR_DEBUG_PRINTF(ATH_DEBUG_ERR, ("%s: busy, destroy in progress\n", __func__));
295         up(&ar->arSem);
296         return -EBUSY;
297     }
298
299     if(ar->arTxPending[wmi_get_control_ep(ar->arWmi)]) {
300         /*
301         * sleep until the command queue drains
302         */
303         wait_event_interruptible_timeout(arEvent,
304         ar->arTxPending[wmi_get_control_ep(ar->arWmi)] == 0, wmitimeout * HZ);
305         if (signal_pending(current)) {
306             AR_DEBUG_PRINTF(ATH_DEBUG_ERR, ("%s: cmd queue drain timeout\n", __func__));
307             up(&ar->arSem);
308             return -EINTR;
309         }
310     }
311
312     if(ar->arConnected == true &&
313        ar->arSsidLen == sme->ssid_len &&
314        !memcmp(ar->arSsid, sme->ssid, ar->arSsidLen)) {
315         reconnect_flag = true;
316         status = wmi_reconnect_cmd(ar->arWmi,
317                                    ar->arReqBssid,
318                                    ar->arChannelHint);
319
320         up(&ar->arSem);
321         if (status) {
322             AR_DEBUG_PRINTF(ATH_DEBUG_ERR, ("%s: wmi_reconnect_cmd failed\n", __func__));
323             return -EIO;
324         }
325         return 0;
326     } else if(ar->arSsidLen == sme->ssid_len &&
327               !memcmp(ar->arSsid, sme->ssid, ar->arSsidLen)) {
328             ar6000_disconnect(ar);
329     }
330
331     A_MEMZERO(ar->arSsid, sizeof(ar->arSsid));
332     ar->arSsidLen = sme->ssid_len;
333     memcpy(ar->arSsid, sme->ssid, sme->ssid_len);
334
335     if(sme->channel){
336         ar->arChannelHint = sme->channel->center_freq;
337     }
338
339     A_MEMZERO(ar->arReqBssid, sizeof(ar->arReqBssid));
340     if(sme->bssid){
341         if(memcmp(&sme->bssid, bcast_mac, AR6000_ETH_ADDR_LEN)) {
342             memcpy(ar->arReqBssid, sme->bssid, sizeof(ar->arReqBssid));
343         }
344     }
345
346     ar6k_set_wpa_version(ar, sme->crypto.wpa_versions);
347     ar6k_set_auth_type(ar, sme->auth_type);
348
349     if(sme->crypto.n_ciphers_pairwise) {
350         ar6k_set_cipher(ar, sme->crypto.ciphers_pairwise[0], true);
351     } else {
352         ar6k_set_cipher(ar, IW_AUTH_CIPHER_NONE, true);
353     }
354     ar6k_set_cipher(ar, sme->crypto.cipher_group, false);
355
356     if(sme->crypto.n_akm_suites) {
357         ar6k_set_key_mgmt(ar, sme->crypto.akm_suites[0]);
358     }
359
360     if((sme->key_len) &&
361        (NONE_AUTH == ar->arAuthMode) &&
362         (WEP_CRYPT == ar->arPairwiseCrypto)) {
363         struct ar_key *key = NULL;
364
365         if(sme->key_idx < WMI_MIN_KEY_INDEX || sme->key_idx > WMI_MAX_KEY_INDEX) {
366             AR_DEBUG_PRINTF(ATH_DEBUG_ERR,
367                             ("%s: key index %d out of bounds\n", __func__, sme->key_idx));
368             up(&ar->arSem);
369             return -ENOENT;
370         }
371
372         key = &ar->keys[sme->key_idx];
373         key->key_len = sme->key_len;
374         memcpy(key->key, sme->key, key->key_len);
375         key->cipher = ar->arPairwiseCrypto;
376         ar->arDefTxKeyIndex = sme->key_idx;
377
378         wmi_addKey_cmd(ar->arWmi, sme->key_idx,
379                     ar->arPairwiseCrypto,
380                     GROUP_USAGE | TX_USAGE,
381                     key->key_len,
382                     NULL,
383                     key->key, KEY_OP_INIT_VAL, NULL,
384                     NO_SYNC_WMIFLAG);
385     }
386
387     if (!ar->arUserBssFilter) {
388         if (wmi_bssfilter_cmd(ar->arWmi, ALL_BSS_FILTER, 0) != 0) {
389             AR_DEBUG_PRINTF(ATH_DEBUG_ERR, ("%s: Couldn't set bss filtering\n", __func__));
390             up(&ar->arSem);
391             return -EIO;
392         }
393     }
394
395     ar->arNetworkType = ar->arNextMode;
396
397     AR_DEBUG_PRINTF(ATH_DEBUG_INFO, ("%s: Connect called with authmode %d dot11 auth %d"\
398                     " PW crypto %d PW crypto Len %d GRP crypto %d"\
399                     " GRP crypto Len %d channel hint %u\n",
400                     __func__, ar->arAuthMode, ar->arDot11AuthMode,
401                     ar->arPairwiseCrypto, ar->arPairwiseCryptoLen,
402                     ar->arGroupCrypto, ar->arGroupCryptoLen, ar->arChannelHint));
403
404     reconnect_flag = 0;
405     status = wmi_connect_cmd(ar->arWmi, ar->arNetworkType,
406                             ar->arDot11AuthMode, ar->arAuthMode,
407                             ar->arPairwiseCrypto, ar->arPairwiseCryptoLen,
408                             ar->arGroupCrypto,ar->arGroupCryptoLen,
409                             ar->arSsidLen, ar->arSsid,
410                             ar->arReqBssid, ar->arChannelHint,
411                             ar->arConnectCtrlFlags);
412
413     up(&ar->arSem);
414
415     if (A_EINVAL == status) {
416         A_MEMZERO(ar->arSsid, sizeof(ar->arSsid));
417         ar->arSsidLen = 0;
418         AR_DEBUG_PRINTF(ATH_DEBUG_ERR, ("%s: Invalid request\n", __func__));
419         return -ENOENT;
420     } else if (status) {
421         AR_DEBUG_PRINTF(ATH_DEBUG_ERR, ("%s: wmi_connect_cmd failed\n", __func__));
422         return -EIO;
423     }
424
425     if ((!(ar->arConnectCtrlFlags & CONNECT_DO_WPA_OFFLOAD)) &&
426         ((WPA_PSK_AUTH == ar->arAuthMode) || (WPA2_PSK_AUTH == ar->arAuthMode)))
427     {
428         A_TIMEOUT_MS(&ar->disconnect_timer, A_DISCONNECT_TIMER_INTERVAL, 0);
429     }
430
431     ar->arConnectCtrlFlags &= ~CONNECT_DO_WPA_OFFLOAD;
432     ar->arConnectPending = true;
433
434     return 0;
435 }
436
437 void
438 ar6k_cfg80211_connect_event(struct ar6_softc *ar, u16 channel,
439                 u8 *bssid, u16 listenInterval,
440                 u16 beaconInterval,NETWORK_TYPE networkType,
441                 u8 beaconIeLen, u8 assocReqLen,
442                 u8 assocRespLen, u8 *assocInfo)
443 {
444     u16 size = 0;
445     u16 capability = 0;
446     struct cfg80211_bss *bss = NULL;
447     struct ieee80211_mgmt *mgmt = NULL;
448     struct ieee80211_channel *ibss_channel = NULL;
449     s32 signal = 50 * 100;
450     u8 ie_buf_len = 0;
451     unsigned char ie_buf[256];
452     unsigned char *ptr_ie_buf = ie_buf;
453     unsigned char *ieeemgmtbuf = NULL;
454     u8 source_mac[ATH_MAC_LEN];
455
456     u8 assocReqIeOffset = sizeof(u16)  +  /* capinfo*/
457                                sizeof(u16);    /* listen interval */
458     u8 assocRespIeOffset = sizeof(u16) +  /* capinfo*/
459                                 sizeof(u16) +  /* status Code */
460                                 sizeof(u16);   /* associd */
461     u8 *assocReqIe = assocInfo + beaconIeLen + assocReqIeOffset;
462     u8 *assocRespIe = assocInfo + beaconIeLen + assocReqLen + assocRespIeOffset;
463
464     AR_DEBUG_PRINTF(ATH_DEBUG_INFO, ("%s: \n", __func__));
465
466     assocReqLen -= assocReqIeOffset;
467     assocRespLen -= assocRespIeOffset;
468
469     ar->arAutoAuthStage = AUTH_IDLE;
470
471     if((ADHOC_NETWORK & networkType)) {
472         if(NL80211_IFTYPE_ADHOC != ar->wdev->iftype) {
473             AR_DEBUG_PRINTF(ATH_DEBUG_INFO,
474                             ("%s: ath6k not in ibss mode\n", __func__));
475             return;
476         }
477     }
478
479     if((INFRA_NETWORK & networkType)) {
480         if(NL80211_IFTYPE_STATION != ar->wdev->iftype) {
481             AR_DEBUG_PRINTF(ATH_DEBUG_INFO,
482                             ("%s: ath6k not in station mode\n", __func__));
483             return;
484         }
485     }
486
487     /* Before informing the join/connect event, make sure that
488      * bss entry is present in scan list, if it not present
489      * construct and insert into scan list, otherwise that
490      * event will be dropped on the way by cfg80211, due to
491      * this keys will not be plumbed in case of WEP and
492      * application will not be aware of join/connect status. */
493     bss = cfg80211_get_bss(ar->wdev->wiphy, NULL, bssid,
494                            ar->wdev->ssid, ar->wdev->ssid_len,
495                            ((ADHOC_NETWORK & networkType) ? WLAN_CAPABILITY_IBSS : WLAN_CAPABILITY_ESS),
496                            ((ADHOC_NETWORK & networkType) ? WLAN_CAPABILITY_IBSS : WLAN_CAPABILITY_ESS));
497
498     /*
499      * Earlier we were updating the cfg about bss by making a beacon frame
500      * only if the entry for bss is not there. This can have some issue if
501      * ROAM event is generated and a heavy traffic is ongoing. The ROAM
502      * event is handled through a work queue and by the time it really gets
503      * handled, BSS would have been aged out. So it is better to update the
504      * cfg about BSS irrespective of its entry being present right now or
505      * not.
506      */
507
508     if (ADHOC_NETWORK & networkType) {
509             /* construct 802.11 mgmt beacon */
510             if(ptr_ie_buf) {
511                     *ptr_ie_buf++ = WLAN_EID_SSID;
512                     *ptr_ie_buf++ = ar->arSsidLen;
513                     memcpy(ptr_ie_buf, ar->arSsid, ar->arSsidLen);
514                     ptr_ie_buf +=ar->arSsidLen;
515
516                     *ptr_ie_buf++ = WLAN_EID_IBSS_PARAMS;
517                     *ptr_ie_buf++ = 2; /* length */
518                     *ptr_ie_buf++ = 0; /* ATIM window */
519                     *ptr_ie_buf++ = 0; /* ATIM window */
520
521                     /* TODO: update ibss params and include supported rates,
522                      * DS param set, extened support rates, wmm. */
523
524                     ie_buf_len = ptr_ie_buf - ie_buf;
525             }
526
527             capability |= IEEE80211_CAPINFO_IBSS;
528             if(WEP_CRYPT == ar->arPairwiseCrypto) {
529                     capability |= IEEE80211_CAPINFO_PRIVACY;
530             }
531             memcpy(source_mac, ar->arNetDev->dev_addr, ATH_MAC_LEN);
532             ptr_ie_buf = ie_buf;
533     } else {
534             capability = *(u16 *)(&assocInfo[beaconIeLen]);
535             memcpy(source_mac, bssid, ATH_MAC_LEN);
536             ptr_ie_buf = assocReqIe;
537             ie_buf_len = assocReqLen;
538     }
539
540     size = offsetof(struct ieee80211_mgmt, u)
541             + sizeof(mgmt->u.beacon)
542             + ie_buf_len;
543
544     ieeemgmtbuf = A_MALLOC_NOWAIT(size);
545     if(!ieeemgmtbuf) {
546             AR_DEBUG_PRINTF(ATH_DEBUG_ERR,
547                             ("%s: ieeeMgmtbuf alloc error\n", __func__));
548             cfg80211_put_bss(bss);
549             return;
550     }
551
552     A_MEMZERO(ieeemgmtbuf, size);
553     mgmt = (struct ieee80211_mgmt *)ieeemgmtbuf;
554     mgmt->frame_control = (IEEE80211_FTYPE_MGMT | IEEE80211_STYPE_BEACON);
555     memcpy(mgmt->da, bcast_mac, ATH_MAC_LEN);
556     memcpy(mgmt->sa, source_mac, ATH_MAC_LEN);
557     memcpy(mgmt->bssid, bssid, ATH_MAC_LEN);
558     mgmt->u.beacon.beacon_int = beaconInterval;
559     mgmt->u.beacon.capab_info = capability;
560     memcpy(mgmt->u.beacon.variable, ptr_ie_buf, ie_buf_len);
561
562     ibss_channel = ieee80211_get_channel(ar->wdev->wiphy, (int)channel);
563
564     AR_DEBUG_PRINTF(ATH_DEBUG_INFO,
565                     ("%s: inform bss with bssid %pM channel %d beaconInterval %d "
566                      "capability 0x%x\n", __func__, mgmt->bssid,
567                      ibss_channel->hw_value, beaconInterval, capability));
568
569     bss = cfg80211_inform_bss_frame(ar->wdev->wiphy,
570                                     ibss_channel, mgmt,
571                                     le16_to_cpu(size),
572                                     signal, GFP_KERNEL);
573     kfree(ieeemgmtbuf);
574     cfg80211_put_bss(bss);
575
576     if((ADHOC_NETWORK & networkType)) {
577         cfg80211_ibss_joined(ar->arNetDev, bssid, GFP_KERNEL);
578         return;
579     }
580
581     if (false == ar->arConnected) {
582         /* inform connect result to cfg80211 */
583         ar->smeState = SME_DISCONNECTED;
584         cfg80211_connect_result(ar->arNetDev, bssid,
585                                 assocReqIe, assocReqLen,
586                                 assocRespIe, assocRespLen,
587                                 WLAN_STATUS_SUCCESS, GFP_KERNEL);
588     } else {
589         /* inform roam event to cfg80211 */
590         cfg80211_roamed(ar->arNetDev, ibss_channel, bssid,
591                         assocReqIe, assocReqLen,
592                         assocRespIe, assocRespLen,
593                         GFP_KERNEL);
594     }
595 }
596
597 static int
598 ar6k_cfg80211_disconnect(struct wiphy *wiphy, struct net_device *dev,
599                         u16 reason_code)
600 {
601     struct ar6_softc *ar = (struct ar6_softc *)ar6k_priv(dev);
602
603     AR_DEBUG_PRINTF(ATH_DEBUG_INFO, ("%s: reason=%u\n", __func__, reason_code));
604
605     if(ar->arWmiReady == false) {
606         AR_DEBUG_PRINTF(ATH_DEBUG_ERR, ("%s: Wmi not ready\n", __func__));
607         return -EIO;
608     }
609
610     if(ar->arWlanState == WLAN_DISABLED) {
611         AR_DEBUG_PRINTF(ATH_DEBUG_ERR, ("%s: Wlan disabled\n", __func__));
612         return -EIO;
613     }
614
615     if(ar->bIsDestroyProgress) {
616         AR_DEBUG_PRINTF(ATH_DEBUG_ERR, ("%s: busy, destroy in progress\n", __func__));
617         return -EBUSY;
618     }
619
620     if(down_interruptible(&ar->arSem)) {
621         AR_DEBUG_PRINTF(ATH_DEBUG_ERR, ("%s: busy, couldn't get access\n", __func__));
622         return -ERESTARTSYS;
623     }
624
625     reconnect_flag = 0;
626     ar6000_disconnect(ar);
627     A_MEMZERO(ar->arSsid, sizeof(ar->arSsid));
628     ar->arSsidLen = 0;
629
630     if (ar->arSkipScan == false) {
631         A_MEMZERO(ar->arReqBssid, sizeof(ar->arReqBssid));
632     }
633
634     up(&ar->arSem);
635
636     return 0;
637 }
638
639 void
640 ar6k_cfg80211_disconnect_event(struct ar6_softc *ar, u8 reason,
641                                u8 *bssid, u8 assocRespLen,
642                                u8 *assocInfo, u16 protocolReasonStatus)
643 {
644
645     u16 status;
646
647     AR_DEBUG_PRINTF(ATH_DEBUG_INFO, ("%s: reason=%u\n", __func__, reason));
648
649     if (ar->scan_request) {
650         cfg80211_scan_done(ar->scan_request, true);
651         ar->scan_request = NULL;
652     }
653     if((ADHOC_NETWORK & ar->arNetworkType)) {
654         if(NL80211_IFTYPE_ADHOC != ar->wdev->iftype) {
655             AR_DEBUG_PRINTF(ATH_DEBUG_INFO,
656                             ("%s: ath6k not in ibss mode\n", __func__));
657             return;
658         }
659         A_MEMZERO(bssid, ETH_ALEN);
660         cfg80211_ibss_joined(ar->arNetDev, bssid, GFP_KERNEL);
661         return;
662     }
663
664     if((INFRA_NETWORK & ar->arNetworkType)) {
665         if(NL80211_IFTYPE_STATION != ar->wdev->iftype) {
666             AR_DEBUG_PRINTF(ATH_DEBUG_INFO,
667                             ("%s: ath6k not in station mode\n", __func__));
668             return;
669         }
670     }
671
672     if(true == ar->arConnectPending) {
673         if(NO_NETWORK_AVAIL == reason) {
674             /* connect cmd failed */
675             wmi_disconnect_cmd(ar->arWmi);
676         } else if (reason == DISCONNECT_CMD) {
677                 if (ar->arAutoAuthStage) {
678                         /*
679                          * If the current auth algorithm is open try shared
680                          * and make autoAuthStage idle. We do not make it
681                          * leap for now being.
682                          */
683                         if (ar->arDot11AuthMode == OPEN_AUTH) {
684                                 struct ar_key *key = NULL;
685                                 key = &ar->keys[ar->arDefTxKeyIndex];
686                                 if (down_interruptible(&ar->arSem)) {
687                                         AR_DEBUG_PRINTF(ATH_DEBUG_ERR, ("%s: busy, couldn't get access\n", __func__));
688                                         return;
689                                 }
690
691
692                                 ar->arDot11AuthMode = SHARED_AUTH;
693                                 ar->arAutoAuthStage = AUTH_IDLE;
694
695                                 wmi_addKey_cmd(ar->arWmi, ar->arDefTxKeyIndex,
696                                                 ar->arPairwiseCrypto,
697                                                 GROUP_USAGE | TX_USAGE,
698                                                 key->key_len,
699                                                 NULL,
700                                                 key->key, KEY_OP_INIT_VAL, NULL,
701                                                 NO_SYNC_WMIFLAG);
702
703                                 status = wmi_connect_cmd(ar->arWmi,
704                                                          ar->arNetworkType,
705                                                          ar->arDot11AuthMode,
706                                                          ar->arAuthMode,
707                                                          ar->arPairwiseCrypto,
708                                                          ar->arPairwiseCryptoLen,
709                                                          ar->arGroupCrypto,
710                                                          ar->arGroupCryptoLen,
711                                                          ar->arSsidLen,
712                                                          ar->arSsid,
713                                                          ar->arReqBssid,
714                                                          ar->arChannelHint,
715                                                          ar->arConnectCtrlFlags);
716                                 up(&ar->arSem);
717
718                         } else if (ar->arDot11AuthMode == SHARED_AUTH) {
719                                 /* should not reach here */
720                         }
721                 } else {
722                         ar->arConnectPending = false;
723                         if (ar->smeState == SME_CONNECTING) {
724                                 cfg80211_connect_result(ar->arNetDev, bssid,
725                                                         NULL, 0,
726                                                         NULL, 0,
727                                                         WLAN_STATUS_UNSPECIFIED_FAILURE,
728                                                         GFP_KERNEL);
729                         } else {
730                                 cfg80211_disconnected(ar->arNetDev,
731                                                       reason,
732                                                       NULL, 0,
733                                                       GFP_KERNEL);
734                         }
735                         ar->smeState = SME_DISCONNECTED;
736                 }
737         }
738     } else {
739             if (reason != DISCONNECT_CMD)
740                     wmi_disconnect_cmd(ar->arWmi);
741     }
742 }
743
744 void
745 ar6k_cfg80211_scan_node(void *arg, bss_t *ni)
746 {
747     struct wiphy *wiphy = (struct wiphy *)arg;
748     u16 size;
749     unsigned char *ieeemgmtbuf = NULL;
750     struct ieee80211_mgmt *mgmt;
751     struct ieee80211_channel *channel;
752     struct ieee80211_supported_band *band;
753     struct ieee80211_common_ie  *cie;
754     s32 signal;
755     int freq;
756
757     cie = &ni->ni_cie;
758
759 #define CHAN_IS_11A(x)  (!((x >= 2412) && (x <= 2484)))
760     if(CHAN_IS_11A(cie->ie_chan)) {
761         /* 11a */
762         band = wiphy->bands[IEEE80211_BAND_5GHZ];
763     } else if((cie->ie_erp) || (cie->ie_xrates)) {
764         /* 11g */
765         band = wiphy->bands[IEEE80211_BAND_2GHZ];
766     } else {
767         /* 11b */
768         band = wiphy->bands[IEEE80211_BAND_2GHZ];
769     }
770
771     size = ni->ni_framelen + offsetof(struct ieee80211_mgmt, u);
772     ieeemgmtbuf = A_MALLOC_NOWAIT(size);
773     if(!ieeemgmtbuf)
774     {
775         AR_DEBUG_PRINTF(ATH_DEBUG_ERR, ("%s: ieeeMgmtbuf alloc error\n", __func__));
776         return;
777     }
778
779     /* Note:
780        TODO: Update target to include 802.11 mac header while sending bss info.
781        Target removes 802.11 mac header while sending the bss info to host,
782        cfg80211 needs it, for time being just filling the da, sa and bssid fields alone.
783     */
784     mgmt = (struct ieee80211_mgmt *)ieeemgmtbuf;
785     memcpy(mgmt->da, bcast_mac, ATH_MAC_LEN);
786     memcpy(mgmt->sa, ni->ni_macaddr, ATH_MAC_LEN);
787     memcpy(mgmt->bssid, ni->ni_macaddr, ATH_MAC_LEN);
788     memcpy(ieeemgmtbuf + offsetof(struct ieee80211_mgmt, u),
789              ni->ni_buf, ni->ni_framelen);
790
791     freq    = cie->ie_chan;
792     channel = ieee80211_get_channel(wiphy, freq);
793     signal  = ni->ni_snr * 100;
794
795         AR_DEBUG_PRINTF(ATH_DEBUG_INFO,
796                 ("%s: bssid %pM channel %d freq %d size %d\n", __func__,
797                         mgmt->bssid, channel->hw_value, freq, size));
798     cfg80211_inform_bss_frame(wiphy, channel, mgmt,
799                               le16_to_cpu(size),
800                               signal, GFP_KERNEL);
801
802     kfree (ieeemgmtbuf);
803 }
804
805 static int
806 ar6k_cfg80211_scan(struct wiphy *wiphy, struct net_device *ndev,
807                    struct cfg80211_scan_request *request)
808 {
809     struct ar6_softc *ar = (struct ar6_softc *)ar6k_priv(ndev);
810     int ret = 0;
811     u32 forceFgScan = 0;
812
813     AR_DEBUG_PRINTF(ATH_DEBUG_INFO, ("%s: \n", __func__));
814
815     if(ar->arWmiReady == false) {
816         AR_DEBUG_PRINTF(ATH_DEBUG_ERR, ("%s: Wmi not ready\n", __func__));
817         return -EIO;
818     }
819
820     if(ar->arWlanState == WLAN_DISABLED) {
821         AR_DEBUG_PRINTF(ATH_DEBUG_ERR, ("%s: Wlan disabled\n", __func__));
822         return -EIO;
823     }
824
825     if (!ar->arUserBssFilter) {
826         if (wmi_bssfilter_cmd(ar->arWmi,
827                              (ar->arConnected ? ALL_BUT_BSS_FILTER : ALL_BSS_FILTER),
828                              0) != 0) {
829             AR_DEBUG_PRINTF(ATH_DEBUG_ERR, ("%s: Couldn't set bss filtering\n", __func__));
830             return -EIO;
831         }
832     }
833
834     if(request->n_ssids &&
835        request->ssids[0].ssid_len) {
836         u8 i;
837
838         if(request->n_ssids > (MAX_PROBED_SSID_INDEX - 1)) {
839             request->n_ssids = MAX_PROBED_SSID_INDEX - 1;
840         }
841
842         for (i = 0; i < request->n_ssids; i++) {
843             wmi_probedSsid_cmd(ar->arWmi, i+1, SPECIFIC_SSID_FLAG,
844                                request->ssids[i].ssid_len,
845                                request->ssids[i].ssid);
846         }
847     }
848
849     if(ar->arConnected) {
850         forceFgScan = 1;
851     }
852
853     if(wmi_startscan_cmd(ar->arWmi, WMI_LONG_SCAN, forceFgScan, false, \
854                          0, 0, 0, NULL) != 0) {
855         AR_DEBUG_PRINTF(ATH_DEBUG_ERR, ("%s: wmi_startscan_cmd failed\n", __func__));
856         ret = -EIO;
857     }
858
859     ar->scan_request = request;
860
861     return ret;
862 }
863
864 void
865 ar6k_cfg80211_scanComplete_event(struct ar6_softc *ar, int status)
866 {
867
868     AR_DEBUG_PRINTF(ATH_DEBUG_INFO, ("%s: status %d\n", __func__, status));
869
870     if(ar->scan_request)
871     {
872         /* Translate data to cfg80211 mgmt format */
873         if (ar->arWmi)
874                 wmi_iterate_nodes(ar->arWmi, ar6k_cfg80211_scan_node, ar->wdev->wiphy);
875
876         cfg80211_scan_done(ar->scan_request,
877             ((status & A_ECANCELED) || (status & A_EBUSY)) ? true : false);
878
879         if(ar->scan_request->n_ssids &&
880            ar->scan_request->ssids[0].ssid_len) {
881             u8 i;
882
883             for (i = 0; i < ar->scan_request->n_ssids; i++) {
884                 wmi_probedSsid_cmd(ar->arWmi, i+1, DISABLE_SSID_FLAG,
885                                    0, NULL);
886             }
887         }
888         ar->scan_request = NULL;
889     }
890 }
891
892 static int
893 ar6k_cfg80211_add_key(struct wiphy *wiphy, struct net_device *ndev,
894                       u8 key_index, bool pairwise, const u8 *mac_addr,
895                       struct key_params *params)
896 {
897     struct ar6_softc *ar = (struct ar6_softc *)ar6k_priv(ndev);
898     struct ar_key *key = NULL;
899     u8 key_usage;
900     u8 key_type;
901     int status = 0;
902
903     AR_DEBUG_PRINTF(ATH_DEBUG_INFO, ("%s:\n", __func__));
904
905     if(ar->arWmiReady == false) {
906         AR_DEBUG_PRINTF(ATH_DEBUG_ERR, ("%s: Wmi not ready\n", __func__));
907         return -EIO;
908     }
909
910     if(ar->arWlanState == WLAN_DISABLED) {
911         AR_DEBUG_PRINTF(ATH_DEBUG_ERR, ("%s: Wlan disabled\n", __func__));
912         return -EIO;
913     }
914
915     if(key_index < WMI_MIN_KEY_INDEX || key_index > WMI_MAX_KEY_INDEX) {
916         AR_DEBUG_PRINTF(ATH_DEBUG_INFO,
917                         ("%s: key index %d out of bounds\n", __func__, key_index));
918         return -ENOENT;
919     }
920
921     key = &ar->keys[key_index];
922     A_MEMZERO(key, sizeof(struct ar_key));
923
924     if(!mac_addr || is_broadcast_ether_addr(mac_addr)) {
925         key_usage = GROUP_USAGE;
926     } else {
927         key_usage = PAIRWISE_USAGE;
928     }
929
930     if(params) {
931         if(params->key_len > WLAN_MAX_KEY_LEN ||
932             params->seq_len > IW_ENCODE_SEQ_MAX_SIZE)
933             return -EINVAL;
934
935         key->key_len = params->key_len;
936         memcpy(key->key, params->key, key->key_len);
937         key->seq_len = params->seq_len;
938         memcpy(key->seq, params->seq, key->seq_len);
939         key->cipher = params->cipher;
940     }
941
942     switch (key->cipher) {
943     case WLAN_CIPHER_SUITE_WEP40:
944     case WLAN_CIPHER_SUITE_WEP104:
945         key_type = WEP_CRYPT;
946         break;
947
948     case WLAN_CIPHER_SUITE_TKIP:
949         key_type = TKIP_CRYPT;
950         break;
951
952     case WLAN_CIPHER_SUITE_CCMP:
953         key_type = AES_CRYPT;
954         break;
955
956     default:
957         return -ENOTSUPP;
958     }
959
960     if (((WPA_PSK_AUTH == ar->arAuthMode) || (WPA2_PSK_AUTH == ar->arAuthMode)) &&
961         (GROUP_USAGE & key_usage))
962     {
963         A_UNTIMEOUT(&ar->disconnect_timer);
964     }
965
966     AR_DEBUG_PRINTF(ATH_DEBUG_INFO,
967                     ("%s: index %d, key_len %d, key_type 0x%x,"\
968                     " key_usage 0x%x, seq_len %d\n",
969                     __func__, key_index, key->key_len, key_type,
970                     key_usage, key->seq_len));
971
972     ar->arDefTxKeyIndex = key_index;
973     status = wmi_addKey_cmd(ar->arWmi, ar->arDefTxKeyIndex, key_type, key_usage,
974                     key->key_len, key->seq, key->key, KEY_OP_INIT_VAL,
975                     (u8 *)mac_addr, SYNC_BOTH_WMIFLAG);
976
977
978     if (status) {
979         return -EIO;
980     }
981
982     return 0;
983 }
984
985 static int
986 ar6k_cfg80211_del_key(struct wiphy *wiphy, struct net_device *ndev,
987                       u8 key_index, bool pairwise, const u8 *mac_addr)
988 {
989     struct ar6_softc *ar = (struct ar6_softc *)ar6k_priv(ndev);
990
991     AR_DEBUG_PRINTF(ATH_DEBUG_INFO, ("%s: index %d\n", __func__, key_index));
992
993     if(ar->arWmiReady == false) {
994         AR_DEBUG_PRINTF(ATH_DEBUG_ERR, ("%s: Wmi not ready\n", __func__));
995         return -EIO;
996     }
997
998     if(ar->arWlanState == WLAN_DISABLED) {
999         AR_DEBUG_PRINTF(ATH_DEBUG_ERR, ("%s: Wlan disabled\n", __func__));
1000         return -EIO;
1001     }
1002
1003     if(key_index < WMI_MIN_KEY_INDEX || key_index > WMI_MAX_KEY_INDEX) {
1004         AR_DEBUG_PRINTF(ATH_DEBUG_INFO,
1005                         ("%s: key index %d out of bounds\n", __func__, key_index));
1006         return -ENOENT;
1007     }
1008
1009     if(!ar->keys[key_index].key_len) {
1010         AR_DEBUG_PRINTF(ATH_DEBUG_INFO, ("%s: index %d is empty\n", __func__, key_index));
1011         return 0;
1012     }
1013
1014     ar->keys[key_index].key_len = 0;
1015
1016     return wmi_deleteKey_cmd(ar->arWmi, key_index);
1017 }
1018
1019
1020 static int
1021 ar6k_cfg80211_get_key(struct wiphy *wiphy, struct net_device *ndev,
1022                       u8 key_index, bool pairwise, const u8 *mac_addr,
1023                       void *cookie,
1024                       void (*callback)(void *cookie, struct key_params*))
1025 {
1026     struct ar6_softc *ar = (struct ar6_softc *)ar6k_priv(ndev);
1027     struct ar_key *key = NULL;
1028     struct key_params params;
1029
1030     AR_DEBUG_PRINTF(ATH_DEBUG_INFO, ("%s: index %d\n", __func__, key_index));
1031
1032     if(ar->arWmiReady == false) {
1033         AR_DEBUG_PRINTF(ATH_DEBUG_ERR, ("%s: Wmi not ready\n", __func__));
1034         return -EIO;
1035     }
1036
1037     if(ar->arWlanState == WLAN_DISABLED) {
1038         AR_DEBUG_PRINTF(ATH_DEBUG_ERR, ("%s: Wlan disabled\n", __func__));
1039         return -EIO;
1040     }
1041
1042     if(key_index < WMI_MIN_KEY_INDEX || key_index > WMI_MAX_KEY_INDEX) {
1043         AR_DEBUG_PRINTF(ATH_DEBUG_INFO,
1044                         ("%s: key index %d out of bounds\n", __func__, key_index));
1045         return -ENOENT;
1046     }
1047
1048     key = &ar->keys[key_index];
1049     A_MEMZERO(&params, sizeof(params));
1050     params.cipher = key->cipher;
1051     params.key_len = key->key_len;
1052     params.seq_len = key->seq_len;
1053     params.seq = key->seq;
1054     params.key = key->key;
1055
1056     callback(cookie, &params);
1057
1058     return key->key_len ? 0 : -ENOENT;
1059 }
1060
1061
1062 static int
1063 ar6k_cfg80211_set_default_key(struct wiphy *wiphy, struct net_device *ndev,
1064                               u8 key_index, bool unicast, bool multicast)
1065 {
1066     struct ar6_softc *ar = (struct ar6_softc *)ar6k_priv(ndev);
1067     struct ar_key *key = NULL;
1068     int status = 0;
1069     u8 key_usage;
1070
1071     AR_DEBUG_PRINTF(ATH_DEBUG_INFO, ("%s: index %d\n", __func__, key_index));
1072
1073     if(ar->arWmiReady == false) {
1074         AR_DEBUG_PRINTF(ATH_DEBUG_ERR, ("%s: Wmi not ready\n", __func__));
1075         return -EIO;
1076     }
1077
1078     if(ar->arWlanState == WLAN_DISABLED) {
1079         AR_DEBUG_PRINTF(ATH_DEBUG_ERR, ("%s: Wlan disabled\n", __func__));
1080         return -EIO;
1081     }
1082
1083     if(key_index < WMI_MIN_KEY_INDEX || key_index > WMI_MAX_KEY_INDEX) {
1084         AR_DEBUG_PRINTF(ATH_DEBUG_INFO,
1085                         ("%s: key index %d out of bounds\n",
1086                         __func__, key_index));
1087         return -ENOENT;
1088     }
1089
1090     if(!ar->keys[key_index].key_len) {
1091         AR_DEBUG_PRINTF(ATH_DEBUG_INFO, ("%s: invalid key index %d\n",
1092                         __func__, key_index));
1093         return -EINVAL;
1094     }
1095
1096     ar->arDefTxKeyIndex = key_index;
1097     key = &ar->keys[ar->arDefTxKeyIndex];
1098     key_usage = GROUP_USAGE;
1099     if (WEP_CRYPT == ar->arPairwiseCrypto) {
1100         key_usage |= TX_USAGE;
1101     }
1102
1103     status = wmi_addKey_cmd(ar->arWmi, ar->arDefTxKeyIndex,
1104                             ar->arPairwiseCrypto, key_usage,
1105                             key->key_len, key->seq, key->key, KEY_OP_INIT_VAL,
1106                             NULL, SYNC_BOTH_WMIFLAG);
1107     if (status) {
1108         return -EIO;
1109     }
1110
1111     return 0;
1112 }
1113
1114 static int
1115 ar6k_cfg80211_set_default_mgmt_key(struct wiphy *wiphy, struct net_device *ndev,
1116                                    u8 key_index)
1117 {
1118     struct ar6_softc *ar = (struct ar6_softc *)ar6k_priv(ndev);
1119
1120     AR_DEBUG_PRINTF(ATH_DEBUG_INFO, ("%s: index %d\n", __func__, key_index));
1121
1122     if(ar->arWmiReady == false) {
1123         AR_DEBUG_PRINTF(ATH_DEBUG_ERR, ("%s: Wmi not ready\n", __func__));
1124         return -EIO;
1125     }
1126
1127     if(ar->arWlanState == WLAN_DISABLED) {
1128         AR_DEBUG_PRINTF(ATH_DEBUG_ERR, ("%s: Wlan disabled\n", __func__));
1129         return -EIO;
1130     }
1131
1132     AR_DEBUG_PRINTF(ATH_DEBUG_INFO, ("%s: not supported\n", __func__));
1133     return -ENOTSUPP;
1134 }
1135
1136 void
1137 ar6k_cfg80211_tkip_micerr_event(struct ar6_softc *ar, u8 keyid, bool ismcast)
1138 {
1139     AR_DEBUG_PRINTF(ATH_DEBUG_INFO,
1140                     ("%s: keyid %d, ismcast %d\n", __func__, keyid, ismcast));
1141
1142     cfg80211_michael_mic_failure(ar->arNetDev, ar->arBssid,
1143                                  (ismcast ? NL80211_KEYTYPE_GROUP : NL80211_KEYTYPE_PAIRWISE),
1144                                  keyid, NULL, GFP_KERNEL);
1145 }
1146
1147 static int
1148 ar6k_cfg80211_set_wiphy_params(struct wiphy *wiphy, u32 changed)
1149 {
1150     struct ar6_softc *ar = (struct ar6_softc *)wiphy_priv(wiphy);
1151
1152     AR_DEBUG_PRINTF(ATH_DEBUG_INFO, ("%s: changed 0x%x\n", __func__, changed));
1153
1154     if(ar->arWmiReady == false) {
1155         AR_DEBUG_PRINTF(ATH_DEBUG_ERR, ("%s: Wmi not ready\n", __func__));
1156         return -EIO;
1157     }
1158
1159     if(ar->arWlanState == WLAN_DISABLED) {
1160         AR_DEBUG_PRINTF(ATH_DEBUG_ERR, ("%s: Wlan disabled\n", __func__));
1161         return -EIO;
1162     }
1163
1164     if (changed & WIPHY_PARAM_RTS_THRESHOLD) {
1165         if (wmi_set_rts_cmd(ar->arWmi,wiphy->rts_threshold) != 0){
1166             AR_DEBUG_PRINTF(ATH_DEBUG_ERR, ("%s: wmi_set_rts_cmd failed\n", __func__));
1167             return -EIO;
1168         }
1169     }
1170
1171     return 0;
1172 }
1173
1174 static int
1175 ar6k_cfg80211_set_bitrate_mask(struct wiphy *wiphy, struct net_device *dev,
1176                                const u8 *peer,
1177                                const struct cfg80211_bitrate_mask *mask)
1178 {
1179     AR_DEBUG_PRINTF(ATH_DEBUG_ERR, ("Setting rates: Not supported\n"));
1180     return -EIO;
1181 }
1182
1183 /* The type nl80211_tx_power_setting replaces the following data type from 2.6.36 onwards */
1184 static int
1185 ar6k_cfg80211_set_txpower(struct wiphy *wiphy, enum nl80211_tx_power_setting type, int dbm)
1186 {
1187     struct ar6_softc *ar = (struct ar6_softc *)wiphy_priv(wiphy);
1188     u8 ar_dbm;
1189
1190     AR_DEBUG_PRINTF(ATH_DEBUG_INFO, ("%s: type 0x%x, dbm %d\n", __func__, type, dbm));
1191
1192     if(ar->arWmiReady == false) {
1193         AR_DEBUG_PRINTF(ATH_DEBUG_ERR, ("%s: Wmi not ready\n", __func__));
1194         return -EIO;
1195     }
1196
1197     if(ar->arWlanState == WLAN_DISABLED) {
1198         AR_DEBUG_PRINTF(ATH_DEBUG_ERR, ("%s: Wlan disabled\n", __func__));
1199         return -EIO;
1200     }
1201
1202     ar->arTxPwrSet = false;
1203     switch(type) {
1204     case NL80211_TX_POWER_AUTOMATIC:
1205         return 0;
1206     case NL80211_TX_POWER_LIMITED:
1207         ar->arTxPwr = ar_dbm = dbm;
1208         ar->arTxPwrSet = true;
1209         break;
1210     default:
1211         AR_DEBUG_PRINTF(ATH_DEBUG_INFO, ("%s: type 0x%x not supported\n", __func__, type));
1212         return -EOPNOTSUPP;
1213     }
1214
1215     wmi_set_txPwr_cmd(ar->arWmi, ar_dbm);
1216
1217     return 0;
1218 }
1219
1220 static int
1221 ar6k_cfg80211_get_txpower(struct wiphy *wiphy, int *dbm)
1222 {
1223     struct ar6_softc *ar = (struct ar6_softc *)wiphy_priv(wiphy);
1224
1225     AR_DEBUG_PRINTF(ATH_DEBUG_INFO, ("%s: \n", __func__));
1226
1227     if(ar->arWmiReady == false) {
1228         AR_DEBUG_PRINTF(ATH_DEBUG_ERR, ("%s: Wmi not ready\n", __func__));
1229         return -EIO;
1230     }
1231
1232     if(ar->arWlanState == WLAN_DISABLED) {
1233         AR_DEBUG_PRINTF(ATH_DEBUG_ERR, ("%s: Wlan disabled\n", __func__));
1234         return -EIO;
1235     }
1236
1237     if((ar->arConnected == true)) {
1238         ar->arTxPwr = 0;
1239
1240         if(wmi_get_txPwr_cmd(ar->arWmi) != 0) {
1241             AR_DEBUG_PRINTF(ATH_DEBUG_ERR, ("%s: wmi_get_txPwr_cmd failed\n", __func__));
1242             return -EIO;
1243         }
1244
1245         wait_event_interruptible_timeout(arEvent, ar->arTxPwr != 0, 5 * HZ);
1246
1247         if(signal_pending(current)) {
1248             AR_DEBUG_PRINTF(ATH_DEBUG_ERR, ("%s: Target did not respond\n", __func__));
1249             return -EINTR;
1250         }
1251     }
1252
1253     *dbm = ar->arTxPwr;
1254     return 0;
1255 }
1256
1257 static int
1258 ar6k_cfg80211_set_power_mgmt(struct wiphy *wiphy,
1259                              struct net_device *dev,
1260                              bool pmgmt, int timeout)
1261 {
1262     struct ar6_softc *ar = ar6k_priv(dev);
1263     WMI_POWER_MODE_CMD pwrMode;
1264
1265     AR_DEBUG_PRINTF(ATH_DEBUG_INFO, ("%s: pmgmt %d, timeout %d\n", __func__, pmgmt, timeout));
1266
1267     if(ar->arWmiReady == false) {
1268         AR_DEBUG_PRINTF(ATH_DEBUG_ERR, ("%s: Wmi not ready\n", __func__));
1269         return -EIO;
1270     }
1271
1272     if(ar->arWlanState == WLAN_DISABLED) {
1273         AR_DEBUG_PRINTF(ATH_DEBUG_ERR, ("%s: Wlan disabled\n", __func__));
1274         return -EIO;
1275     }
1276
1277     if(pmgmt) {
1278         AR_DEBUG_PRINTF(ATH_DEBUG_INFO, ("%s: Max Perf\n", __func__));
1279         pwrMode.powerMode = REC_POWER;
1280     } else {
1281         AR_DEBUG_PRINTF(ATH_DEBUG_INFO, ("%s: Rec Power\n", __func__));
1282         pwrMode.powerMode = MAX_PERF_POWER;
1283     }
1284
1285     if(wmi_powermode_cmd(ar->arWmi, pwrMode.powerMode) != 0) {
1286         AR_DEBUG_PRINTF(ATH_DEBUG_ERR, ("%s: wmi_powermode_cmd failed\n", __func__));
1287         return -EIO;
1288     }
1289
1290     return 0;
1291 }
1292
1293 static struct net_device *
1294 ar6k_cfg80211_add_virtual_intf(struct wiphy *wiphy, char *name,
1295                                             enum nl80211_iftype type, u32 *flags,
1296                                             struct vif_params *params)
1297 {
1298
1299     AR_DEBUG_PRINTF(ATH_DEBUG_INFO, ("%s: not supported\n", __func__));
1300
1301     /* Multiple virtual interface is not supported.
1302      * The default interface supports STA and IBSS type
1303      */
1304     return ERR_PTR(-EOPNOTSUPP);
1305 }
1306
1307 static int
1308 ar6k_cfg80211_del_virtual_intf(struct wiphy *wiphy, struct net_device *dev)
1309 {
1310
1311     AR_DEBUG_PRINTF(ATH_DEBUG_INFO, ("%s: not supported\n", __func__));
1312
1313     /* Multiple virtual interface is not supported.
1314      * The default interface supports STA and IBSS type
1315      */
1316     return -EOPNOTSUPP;
1317 }
1318
1319 static int
1320 ar6k_cfg80211_change_iface(struct wiphy *wiphy, struct net_device *ndev,
1321                            enum nl80211_iftype type, u32 *flags,
1322                            struct vif_params *params)
1323 {
1324     struct ar6_softc *ar = ar6k_priv(ndev);
1325     struct wireless_dev *wdev = ar->wdev;
1326
1327     AR_DEBUG_PRINTF(ATH_DEBUG_INFO, ("%s: type %u\n", __func__, type));
1328
1329     if(ar->arWmiReady == false) {
1330         AR_DEBUG_PRINTF(ATH_DEBUG_ERR, ("%s: Wmi not ready\n", __func__));
1331         return -EIO;
1332     }
1333
1334     if(ar->arWlanState == WLAN_DISABLED) {
1335         AR_DEBUG_PRINTF(ATH_DEBUG_ERR, ("%s: Wlan disabled\n", __func__));
1336         return -EIO;
1337     }
1338
1339     switch (type) {
1340     case NL80211_IFTYPE_STATION:
1341         ar->arNextMode = INFRA_NETWORK;
1342         break;
1343     case NL80211_IFTYPE_ADHOC:
1344         ar->arNextMode = ADHOC_NETWORK;
1345         break;
1346     default:
1347         AR_DEBUG_PRINTF(ATH_DEBUG_ERR, ("%s: type %u\n", __func__, type));
1348         return -EOPNOTSUPP;
1349     }
1350
1351     wdev->iftype = type;
1352
1353     return 0;
1354 }
1355
1356 static int
1357 ar6k_cfg80211_join_ibss(struct wiphy *wiphy, struct net_device *dev,
1358                         struct cfg80211_ibss_params *ibss_param)
1359 {
1360     struct ar6_softc *ar = ar6k_priv(dev);
1361     int status;
1362
1363     AR_DEBUG_PRINTF(ATH_DEBUG_INFO, ("%s: \n", __func__));
1364
1365     if(ar->arWmiReady == false) {
1366         AR_DEBUG_PRINTF(ATH_DEBUG_ERR, ("%s: Wmi not ready\n", __func__));
1367         return -EIO;
1368     }
1369
1370     if(ar->arWlanState == WLAN_DISABLED) {
1371         AR_DEBUG_PRINTF(ATH_DEBUG_ERR, ("%s: Wlan disabled\n", __func__));
1372         return -EIO;
1373     }
1374
1375     if(!ibss_param->ssid_len || IEEE80211_MAX_SSID_LEN < ibss_param->ssid_len) {
1376         AR_DEBUG_PRINTF(ATH_DEBUG_ERR, ("%s: ssid invalid\n", __func__));
1377         return -EINVAL;
1378     }
1379
1380     ar->arSsidLen = ibss_param->ssid_len;
1381     memcpy(ar->arSsid, ibss_param->ssid, ar->arSsidLen);
1382
1383     if(ibss_param->channel) {
1384         ar->arChannelHint = ibss_param->channel->center_freq;
1385     }
1386
1387     if(ibss_param->channel_fixed) {
1388         /* TODO: channel_fixed: The channel should be fixed, do not search for
1389          * IBSSs to join on other channels. Target firmware does not support this
1390          * feature, needs to be updated.*/
1391     }
1392
1393     A_MEMZERO(ar->arReqBssid, sizeof(ar->arReqBssid));
1394     if(ibss_param->bssid) {
1395         if(memcmp(&ibss_param->bssid, bcast_mac, AR6000_ETH_ADDR_LEN)) {
1396             memcpy(ar->arReqBssid, ibss_param->bssid, sizeof(ar->arReqBssid));
1397         }
1398     }
1399
1400     ar6k_set_wpa_version(ar, 0);
1401     ar6k_set_auth_type(ar, NL80211_AUTHTYPE_OPEN_SYSTEM);
1402
1403     if(ibss_param->privacy) {
1404         ar6k_set_cipher(ar, WLAN_CIPHER_SUITE_WEP40, true);
1405         ar6k_set_cipher(ar, WLAN_CIPHER_SUITE_WEP40, false);
1406     } else {
1407         ar6k_set_cipher(ar, IW_AUTH_CIPHER_NONE, true);
1408         ar6k_set_cipher(ar, IW_AUTH_CIPHER_NONE, false);
1409     }
1410
1411     ar->arNetworkType = ar->arNextMode;
1412
1413     AR_DEBUG_PRINTF(ATH_DEBUG_INFO, ("%s: Connect called with authmode %d dot11 auth %d"\
1414                     " PW crypto %d PW crypto Len %d GRP crypto %d"\
1415                     " GRP crypto Len %d channel hint %u\n",
1416                     __func__, ar->arAuthMode, ar->arDot11AuthMode,
1417                     ar->arPairwiseCrypto, ar->arPairwiseCryptoLen,
1418                     ar->arGroupCrypto, ar->arGroupCryptoLen, ar->arChannelHint));
1419
1420     status = wmi_connect_cmd(ar->arWmi, ar->arNetworkType,
1421                             ar->arDot11AuthMode, ar->arAuthMode,
1422                             ar->arPairwiseCrypto, ar->arPairwiseCryptoLen,
1423                             ar->arGroupCrypto,ar->arGroupCryptoLen,
1424                             ar->arSsidLen, ar->arSsid,
1425                             ar->arReqBssid, ar->arChannelHint,
1426                             ar->arConnectCtrlFlags);
1427     ar->arConnectPending = true;
1428
1429     return 0;
1430 }
1431
1432 static int
1433 ar6k_cfg80211_leave_ibss(struct wiphy *wiphy, struct net_device *dev)
1434 {
1435     struct ar6_softc *ar = (struct ar6_softc *)ar6k_priv(dev);
1436
1437     AR_DEBUG_PRINTF(ATH_DEBUG_INFO, ("%s: \n", __func__));
1438
1439     if(ar->arWmiReady == false) {
1440         AR_DEBUG_PRINTF(ATH_DEBUG_ERR, ("%s: Wmi not ready\n", __func__));
1441         return -EIO;
1442     }
1443
1444     if(ar->arWlanState == WLAN_DISABLED) {
1445         AR_DEBUG_PRINTF(ATH_DEBUG_ERR, ("%s: Wlan disabled\n", __func__));
1446         return -EIO;
1447     }
1448
1449     ar6000_disconnect(ar);
1450     A_MEMZERO(ar->arSsid, sizeof(ar->arSsid));
1451     ar->arSsidLen = 0;
1452
1453     return 0;
1454 }
1455
1456
1457 static const
1458 u32 cipher_suites[] = {
1459     WLAN_CIPHER_SUITE_WEP40,
1460     WLAN_CIPHER_SUITE_WEP104,
1461     WLAN_CIPHER_SUITE_TKIP,
1462     WLAN_CIPHER_SUITE_CCMP,
1463 };
1464
1465 bool is_rate_legacy(s32 rate)
1466 {
1467         static const s32 legacy[] = { 1000, 2000, 5500, 11000,
1468                                       6000, 9000, 12000, 18000, 24000,
1469                                       36000, 48000, 54000 };
1470         u8 i;
1471
1472         for (i = 0; i < ARRAY_SIZE(legacy); i++) {
1473                 if (rate == legacy[i])
1474                         return true;
1475         }
1476
1477         return false;
1478 }
1479
1480 bool is_rate_ht20(s32 rate, u8 *mcs, bool *sgi)
1481 {
1482         static const s32 ht20[] = { 6500, 13000, 19500, 26000, 39000,
1483                                     52000, 58500, 65000, 72200 };
1484         u8 i;
1485
1486         for (i = 0; i < ARRAY_SIZE(ht20); i++) {
1487                 if (rate == ht20[i]) {
1488                         if (i == ARRAY_SIZE(ht20) - 1)
1489                                 /* last rate uses sgi */
1490                                 *sgi = true;
1491                         else
1492                                 *sgi = false;
1493
1494                         *mcs = i;
1495                         return true;
1496                 }
1497         }
1498         return false;
1499 }
1500
1501 bool is_rate_ht40(s32 rate, u8 *mcs, bool *sgi)
1502 {
1503         static const s32 ht40[] = { 13500, 27000, 40500, 54000,
1504                                     81000, 108000, 121500, 135000,
1505                                     150000 };
1506         u8 i;
1507
1508         for (i = 0; i < ARRAY_SIZE(ht40); i++) {
1509                 if (rate == ht40[i]) {
1510                         if (i == ARRAY_SIZE(ht40) - 1)
1511                                 /* last rate uses sgi */
1512                                 *sgi = true;
1513                         else
1514                                 *sgi = false;
1515
1516                         *mcs = i;
1517                         return true;
1518                 }
1519         }
1520
1521         return false;
1522 }
1523
1524 static int ar6k_get_station(struct wiphy *wiphy, struct net_device *dev,
1525                             u8 *mac, struct station_info *sinfo)
1526 {
1527         struct ar6_softc *ar = ar6k_priv(dev);
1528         long left;
1529         bool sgi;
1530         s32 rate;
1531         int ret;
1532         u8 mcs;
1533
1534         if (memcmp(mac, ar->arBssid, ETH_ALEN) != 0)
1535                 return -ENOENT;
1536
1537         if (down_interruptible(&ar->arSem))
1538                 return -EBUSY;
1539
1540         ar->statsUpdatePending = true;
1541
1542         ret = wmi_get_stats_cmd(ar->arWmi);
1543
1544         if (ret != 0) {
1545                 up(&ar->arSem);
1546                 return -EIO;
1547         }
1548
1549         left = wait_event_interruptible_timeout(arEvent,
1550                                                 ar->statsUpdatePending == false,
1551                                                 wmitimeout * HZ);
1552
1553         up(&ar->arSem);
1554
1555         if (left == 0)
1556                 return -ETIMEDOUT;
1557         else if (left < 0)
1558                 return left;
1559
1560         if (ar->arTargetStats.rx_bytes) {
1561                 sinfo->rx_bytes = ar->arTargetStats.rx_bytes;
1562                 sinfo->filled |= STATION_INFO_RX_BYTES;
1563                 sinfo->rx_packets = ar->arTargetStats.rx_packets;
1564                 sinfo->filled |= STATION_INFO_RX_PACKETS;
1565         }
1566
1567         if (ar->arTargetStats.tx_bytes) {
1568                 sinfo->tx_bytes = ar->arTargetStats.tx_bytes;
1569                 sinfo->filled |= STATION_INFO_TX_BYTES;
1570                 sinfo->tx_packets = ar->arTargetStats.tx_packets;
1571                 sinfo->filled |= STATION_INFO_TX_PACKETS;
1572         }
1573
1574         sinfo->signal = ar->arTargetStats.cs_rssi;
1575         sinfo->filled |= STATION_INFO_SIGNAL;
1576
1577         rate = ar->arTargetStats.tx_unicast_rate;
1578
1579         if (is_rate_legacy(rate)) {
1580                 sinfo->txrate.legacy = rate / 100;
1581         } else if (is_rate_ht20(rate, &mcs, &sgi)) {
1582                 if (sgi) {
1583                         sinfo->txrate.flags |= RATE_INFO_FLAGS_SHORT_GI;
1584                         sinfo->txrate.mcs = mcs - 1;
1585                 } else {
1586                         sinfo->txrate.mcs = mcs;
1587                 }
1588
1589                 sinfo->txrate.flags |= RATE_INFO_FLAGS_MCS;
1590         } else if (is_rate_ht40(rate, &mcs, &sgi)) {
1591                 if (sgi) {
1592                         sinfo->txrate.flags |= RATE_INFO_FLAGS_SHORT_GI;
1593                         sinfo->txrate.mcs = mcs - 1;
1594                 } else {
1595                         sinfo->txrate.mcs = mcs;
1596                 }
1597
1598                 sinfo->txrate.flags |= RATE_INFO_FLAGS_40_MHZ_WIDTH;
1599                 sinfo->txrate.flags |= RATE_INFO_FLAGS_MCS;
1600         } else {
1601                 WARN(1, "invalid rate: %d", rate);
1602                 return 0;
1603         }
1604
1605         sinfo->filled |= STATION_INFO_TX_BITRATE;
1606
1607         return 0;
1608 }
1609
1610 static struct
1611 cfg80211_ops ar6k_cfg80211_ops = {
1612     .change_virtual_intf = ar6k_cfg80211_change_iface,
1613     .add_virtual_intf = ar6k_cfg80211_add_virtual_intf,
1614     .del_virtual_intf = ar6k_cfg80211_del_virtual_intf,
1615     .scan = ar6k_cfg80211_scan,
1616     .connect = ar6k_cfg80211_connect,
1617     .disconnect = ar6k_cfg80211_disconnect,
1618     .add_key = ar6k_cfg80211_add_key,
1619     .get_key = ar6k_cfg80211_get_key,
1620     .del_key = ar6k_cfg80211_del_key,
1621     .set_default_key = ar6k_cfg80211_set_default_key,
1622     .set_default_mgmt_key = ar6k_cfg80211_set_default_mgmt_key,
1623     .set_wiphy_params = ar6k_cfg80211_set_wiphy_params,
1624     .set_bitrate_mask = ar6k_cfg80211_set_bitrate_mask,
1625     .set_tx_power = ar6k_cfg80211_set_txpower,
1626     .get_tx_power = ar6k_cfg80211_get_txpower,
1627     .set_power_mgmt = ar6k_cfg80211_set_power_mgmt,
1628     .join_ibss = ar6k_cfg80211_join_ibss,
1629     .leave_ibss = ar6k_cfg80211_leave_ibss,
1630     .get_station = ar6k_get_station,
1631 };
1632
1633 struct wireless_dev *
1634 ar6k_cfg80211_init(struct device *dev)
1635 {
1636     int ret = 0;
1637     struct wireless_dev *wdev;
1638
1639     AR_DEBUG_PRINTF(ATH_DEBUG_INFO, ("%s: \n", __func__));
1640
1641     wdev = kzalloc(sizeof(struct wireless_dev), GFP_KERNEL);
1642     if(!wdev) {
1643         AR_DEBUG_PRINTF(ATH_DEBUG_ERR,
1644                         ("%s: Couldn't allocate wireless device\n", __func__));
1645         return ERR_PTR(-ENOMEM);
1646     }
1647
1648     /* create a new wiphy for use with cfg80211 */
1649     wdev->wiphy = wiphy_new(&ar6k_cfg80211_ops, sizeof(struct ar6_softc));
1650     if(!wdev->wiphy) {
1651         AR_DEBUG_PRINTF(ATH_DEBUG_ERR,
1652                         ("%s: Couldn't allocate wiphy device\n", __func__));
1653         kfree(wdev);
1654         return ERR_PTR(-ENOMEM);
1655     }
1656
1657     /* set device pointer for wiphy */
1658     set_wiphy_dev(wdev->wiphy, dev);
1659
1660     wdev->wiphy->interface_modes = BIT(NL80211_IFTYPE_STATION) |
1661                                    BIT(NL80211_IFTYPE_ADHOC);
1662     /* max num of ssids that can be probed during scanning */
1663     wdev->wiphy->max_scan_ssids = MAX_PROBED_SSID_INDEX;
1664     wdev->wiphy->bands[IEEE80211_BAND_2GHZ] = &ar6k_band_2ghz;
1665     wdev->wiphy->bands[IEEE80211_BAND_5GHZ] = &ar6k_band_5ghz;
1666     wdev->wiphy->signal_type = CFG80211_SIGNAL_TYPE_MBM;
1667
1668     wdev->wiphy->cipher_suites = cipher_suites;
1669     wdev->wiphy->n_cipher_suites = ARRAY_SIZE(cipher_suites);
1670
1671     ret = wiphy_register(wdev->wiphy);
1672     if(ret < 0) {
1673         AR_DEBUG_PRINTF(ATH_DEBUG_ERR,
1674                         ("%s: Couldn't register wiphy device\n", __func__));
1675         wiphy_free(wdev->wiphy);
1676         return ERR_PTR(ret);
1677     }
1678
1679     return wdev;
1680 }
1681
1682 void
1683 ar6k_cfg80211_deinit(struct ar6_softc *ar)
1684 {
1685     struct wireless_dev *wdev = ar->wdev;
1686
1687     AR_DEBUG_PRINTF(ATH_DEBUG_INFO, ("%s: \n", __func__));
1688
1689     if(ar->scan_request) {
1690         cfg80211_scan_done(ar->scan_request, true);
1691         ar->scan_request = NULL;
1692     }
1693
1694     if(!wdev)
1695         return;
1696
1697     wiphy_unregister(wdev->wiphy);
1698     wiphy_free(wdev->wiphy);
1699     kfree(wdev);
1700 }
1701
1702
1703
1704
1705
1706
1707