]> git.karo-electronics.de Git - karo-tx-linux.git/blob - drivers/net/wireless/ath/ath6kl/cfg80211.c
Merge branch 'release' of git://git.kernel.org/pub/scm/linux/kernel/git/lenb/linux
[karo-tx-linux.git] / drivers / net / wireless / ath / ath6kl / cfg80211.c
1 /*
2  * Copyright (c) 2004-2011 Atheros Communications Inc.
3  * Copyright (c) 2011-2012 Qualcomm Atheros, Inc.
4  *
5  * Permission to use, copy, modify, and/or distribute this software for any
6  * purpose with or without fee is hereby granted, provided that the above
7  * copyright notice and this permission notice appear in all copies.
8  *
9  * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
10  * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
11  * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
12  * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
13  * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
14  * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
15  * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
16  */
17
18 #define pr_fmt(fmt) KBUILD_MODNAME ": " fmt
19
20 #include <linux/moduleparam.h>
21 #include <linux/inetdevice.h>
22 #include <linux/export.h>
23
24 #include "core.h"
25 #include "cfg80211.h"
26 #include "debug.h"
27 #include "hif-ops.h"
28 #include "testmode.h"
29
30 #define RATETAB_ENT(_rate, _rateid, _flags) {   \
31         .bitrate    = (_rate),                  \
32         .flags      = (_flags),                 \
33         .hw_value   = (_rateid),                \
34 }
35
36 #define CHAN2G(_channel, _freq, _flags) {   \
37         .band           = IEEE80211_BAND_2GHZ,  \
38         .hw_value       = (_channel),           \
39         .center_freq    = (_freq),              \
40         .flags          = (_flags),             \
41         .max_antenna_gain   = 0,                \
42         .max_power      = 30,                   \
43 }
44
45 #define CHAN5G(_channel, _flags) {                  \
46         .band           = IEEE80211_BAND_5GHZ,      \
47         .hw_value       = (_channel),               \
48         .center_freq    = 5000 + (5 * (_channel)),  \
49         .flags          = (_flags),                 \
50         .max_antenna_gain   = 0,                    \
51         .max_power      = 30,                       \
52 }
53
54 #define DEFAULT_BG_SCAN_PERIOD 60
55
56 struct ath6kl_cfg80211_match_probe_ssid {
57         struct cfg80211_ssid ssid;
58         u8 flag;
59 };
60
61 static struct ieee80211_rate ath6kl_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 ath6kl_a_rates     (ath6kl_rates + 4)
77 #define ath6kl_a_rates_size    8
78 #define ath6kl_g_rates     (ath6kl_rates + 0)
79 #define ath6kl_g_rates_size    12
80
81 #define ath6kl_g_htcap IEEE80211_HT_CAP_SGI_20
82 #define ath6kl_a_htcap (IEEE80211_HT_CAP_SUP_WIDTH_20_40 | \
83                         IEEE80211_HT_CAP_SGI_20          | \
84                         IEEE80211_HT_CAP_SGI_40)
85
86 static struct ieee80211_channel ath6kl_2ghz_channels[] = {
87         CHAN2G(1, 2412, 0),
88         CHAN2G(2, 2417, 0),
89         CHAN2G(3, 2422, 0),
90         CHAN2G(4, 2427, 0),
91         CHAN2G(5, 2432, 0),
92         CHAN2G(6, 2437, 0),
93         CHAN2G(7, 2442, 0),
94         CHAN2G(8, 2447, 0),
95         CHAN2G(9, 2452, 0),
96         CHAN2G(10, 2457, 0),
97         CHAN2G(11, 2462, 0),
98         CHAN2G(12, 2467, 0),
99         CHAN2G(13, 2472, 0),
100         CHAN2G(14, 2484, 0),
101 };
102
103 static struct ieee80211_channel ath6kl_5ghz_a_channels[] = {
104         CHAN5G(34, 0), CHAN5G(36, 0),
105         CHAN5G(38, 0), CHAN5G(40, 0),
106         CHAN5G(42, 0), CHAN5G(44, 0),
107         CHAN5G(46, 0), CHAN5G(48, 0),
108         CHAN5G(52, 0), CHAN5G(56, 0),
109         CHAN5G(60, 0), CHAN5G(64, 0),
110         CHAN5G(100, 0), CHAN5G(104, 0),
111         CHAN5G(108, 0), CHAN5G(112, 0),
112         CHAN5G(116, 0), CHAN5G(120, 0),
113         CHAN5G(124, 0), CHAN5G(128, 0),
114         CHAN5G(132, 0), CHAN5G(136, 0),
115         CHAN5G(140, 0), CHAN5G(149, 0),
116         CHAN5G(153, 0), CHAN5G(157, 0),
117         CHAN5G(161, 0), CHAN5G(165, 0),
118         CHAN5G(184, 0), CHAN5G(188, 0),
119         CHAN5G(192, 0), CHAN5G(196, 0),
120         CHAN5G(200, 0), CHAN5G(204, 0),
121         CHAN5G(208, 0), CHAN5G(212, 0),
122         CHAN5G(216, 0),
123 };
124
125 static struct ieee80211_supported_band ath6kl_band_2ghz = {
126         .n_channels = ARRAY_SIZE(ath6kl_2ghz_channels),
127         .channels = ath6kl_2ghz_channels,
128         .n_bitrates = ath6kl_g_rates_size,
129         .bitrates = ath6kl_g_rates,
130         .ht_cap.cap = ath6kl_g_htcap,
131         .ht_cap.ht_supported = true,
132 };
133
134 static struct ieee80211_supported_band ath6kl_band_5ghz = {
135         .n_channels = ARRAY_SIZE(ath6kl_5ghz_a_channels),
136         .channels = ath6kl_5ghz_a_channels,
137         .n_bitrates = ath6kl_a_rates_size,
138         .bitrates = ath6kl_a_rates,
139         .ht_cap.cap = ath6kl_a_htcap,
140         .ht_cap.ht_supported = true,
141 };
142
143 #define CCKM_KRK_CIPHER_SUITE 0x004096ff /* use for KRK */
144
145 /* returns true if scheduled scan was stopped */
146 static bool __ath6kl_cfg80211_sscan_stop(struct ath6kl_vif *vif)
147 {
148         struct ath6kl *ar = vif->ar;
149
150         if (!test_and_clear_bit(SCHED_SCANNING, &vif->flags))
151                 return false;
152
153         del_timer_sync(&vif->sched_scan_timer);
154
155         if (ar->state == ATH6KL_STATE_RECOVERY)
156                 return true;
157
158         ath6kl_wmi_enable_sched_scan_cmd(ar->wmi, vif->fw_vif_idx, false);
159
160         return true;
161 }
162
163 static void ath6kl_cfg80211_sscan_disable(struct ath6kl_vif *vif)
164 {
165         struct ath6kl *ar = vif->ar;
166         bool stopped;
167
168         stopped = __ath6kl_cfg80211_sscan_stop(vif);
169
170         if (!stopped)
171                 return;
172
173         cfg80211_sched_scan_stopped(ar->wiphy);
174 }
175
176 static int ath6kl_set_wpa_version(struct ath6kl_vif *vif,
177                                   enum nl80211_wpa_versions wpa_version)
178 {
179         ath6kl_dbg(ATH6KL_DBG_WLAN_CFG, "%s: %u\n", __func__, wpa_version);
180
181         if (!wpa_version) {
182                 vif->auth_mode = NONE_AUTH;
183         } else if (wpa_version & NL80211_WPA_VERSION_2) {
184                 vif->auth_mode = WPA2_AUTH;
185         } else if (wpa_version & NL80211_WPA_VERSION_1) {
186                 vif->auth_mode = WPA_AUTH;
187         } else {
188                 ath6kl_err("%s: %u not supported\n", __func__, wpa_version);
189                 return -ENOTSUPP;
190         }
191
192         return 0;
193 }
194
195 static int ath6kl_set_auth_type(struct ath6kl_vif *vif,
196                                 enum nl80211_auth_type auth_type)
197 {
198         ath6kl_dbg(ATH6KL_DBG_WLAN_CFG, "%s: 0x%x\n", __func__, auth_type);
199
200         switch (auth_type) {
201         case NL80211_AUTHTYPE_OPEN_SYSTEM:
202                 vif->dot11_auth_mode = OPEN_AUTH;
203                 break;
204         case NL80211_AUTHTYPE_SHARED_KEY:
205                 vif->dot11_auth_mode = SHARED_AUTH;
206                 break;
207         case NL80211_AUTHTYPE_NETWORK_EAP:
208                 vif->dot11_auth_mode = LEAP_AUTH;
209                 break;
210
211         case NL80211_AUTHTYPE_AUTOMATIC:
212                 vif->dot11_auth_mode = OPEN_AUTH | SHARED_AUTH;
213                 break;
214
215         default:
216                 ath6kl_err("%s: 0x%x not supported\n", __func__, auth_type);
217                 return -ENOTSUPP;
218         }
219
220         return 0;
221 }
222
223 static int ath6kl_set_cipher(struct ath6kl_vif *vif, u32 cipher, bool ucast)
224 {
225         u8 *ar_cipher = ucast ? &vif->prwise_crypto : &vif->grp_crypto;
226         u8 *ar_cipher_len = ucast ? &vif->prwise_crypto_len :
227                 &vif->grp_crypto_len;
228
229         ath6kl_dbg(ATH6KL_DBG_WLAN_CFG, "%s: cipher 0x%x, ucast %u\n",
230                    __func__, cipher, ucast);
231
232         switch (cipher) {
233         case 0:
234                 /* our own hack to use value 0 as no crypto used */
235                 *ar_cipher = NONE_CRYPT;
236                 *ar_cipher_len = 0;
237                 break;
238         case WLAN_CIPHER_SUITE_WEP40:
239                 *ar_cipher = WEP_CRYPT;
240                 *ar_cipher_len = 5;
241                 break;
242         case WLAN_CIPHER_SUITE_WEP104:
243                 *ar_cipher = WEP_CRYPT;
244                 *ar_cipher_len = 13;
245                 break;
246         case WLAN_CIPHER_SUITE_TKIP:
247                 *ar_cipher = TKIP_CRYPT;
248                 *ar_cipher_len = 0;
249                 break;
250         case WLAN_CIPHER_SUITE_CCMP:
251                 *ar_cipher = AES_CRYPT;
252                 *ar_cipher_len = 0;
253                 break;
254         case WLAN_CIPHER_SUITE_SMS4:
255                 *ar_cipher = WAPI_CRYPT;
256                 *ar_cipher_len = 0;
257                 break;
258         default:
259                 ath6kl_err("cipher 0x%x not supported\n", cipher);
260                 return -ENOTSUPP;
261         }
262
263         return 0;
264 }
265
266 static void ath6kl_set_key_mgmt(struct ath6kl_vif *vif, u32 key_mgmt)
267 {
268         ath6kl_dbg(ATH6KL_DBG_WLAN_CFG, "%s: 0x%x\n", __func__, key_mgmt);
269
270         if (key_mgmt == WLAN_AKM_SUITE_PSK) {
271                 if (vif->auth_mode == WPA_AUTH)
272                         vif->auth_mode = WPA_PSK_AUTH;
273                 else if (vif->auth_mode == WPA2_AUTH)
274                         vif->auth_mode = WPA2_PSK_AUTH;
275         } else if (key_mgmt == 0x00409600) {
276                 if (vif->auth_mode == WPA_AUTH)
277                         vif->auth_mode = WPA_AUTH_CCKM;
278                 else if (vif->auth_mode == WPA2_AUTH)
279                         vif->auth_mode = WPA2_AUTH_CCKM;
280         } else if (key_mgmt != WLAN_AKM_SUITE_8021X) {
281                 vif->auth_mode = NONE_AUTH;
282         }
283 }
284
285 static bool ath6kl_cfg80211_ready(struct ath6kl_vif *vif)
286 {
287         struct ath6kl *ar = vif->ar;
288
289         if (!test_bit(WMI_READY, &ar->flag)) {
290                 ath6kl_err("wmi is not ready\n");
291                 return false;
292         }
293
294         if (!test_bit(WLAN_ENABLED, &vif->flags)) {
295                 ath6kl_err("wlan disabled\n");
296                 return false;
297         }
298
299         return true;
300 }
301
302 static bool ath6kl_is_wpa_ie(const u8 *pos)
303 {
304         return pos[0] == WLAN_EID_VENDOR_SPECIFIC && pos[1] >= 4 &&
305                 pos[2] == 0x00 && pos[3] == 0x50 &&
306                 pos[4] == 0xf2 && pos[5] == 0x01;
307 }
308
309 static bool ath6kl_is_rsn_ie(const u8 *pos)
310 {
311         return pos[0] == WLAN_EID_RSN;
312 }
313
314 static bool ath6kl_is_wps_ie(const u8 *pos)
315 {
316         return (pos[0] == WLAN_EID_VENDOR_SPECIFIC &&
317                 pos[1] >= 4 &&
318                 pos[2] == 0x00 && pos[3] == 0x50 && pos[4] == 0xf2 &&
319                 pos[5] == 0x04);
320 }
321
322 static int ath6kl_set_assoc_req_ies(struct ath6kl_vif *vif, const u8 *ies,
323                                     size_t ies_len)
324 {
325         struct ath6kl *ar = vif->ar;
326         const u8 *pos;
327         u8 *buf = NULL;
328         size_t len = 0;
329         int ret;
330
331         /*
332          * Clear previously set flag
333          */
334
335         ar->connect_ctrl_flags &= ~CONNECT_WPS_FLAG;
336
337         /*
338          * Filter out RSN/WPA IE(s)
339          */
340
341         if (ies && ies_len) {
342                 buf = kmalloc(ies_len, GFP_KERNEL);
343                 if (buf == NULL)
344                         return -ENOMEM;
345                 pos = ies;
346
347                 while (pos + 1 < ies + ies_len) {
348                         if (pos + 2 + pos[1] > ies + ies_len)
349                                 break;
350                         if (!(ath6kl_is_wpa_ie(pos) || ath6kl_is_rsn_ie(pos))) {
351                                 memcpy(buf + len, pos, 2 + pos[1]);
352                                 len += 2 + pos[1];
353                         }
354
355                         if (ath6kl_is_wps_ie(pos))
356                                 ar->connect_ctrl_flags |= CONNECT_WPS_FLAG;
357
358                         pos += 2 + pos[1];
359                 }
360         }
361
362         ret = ath6kl_wmi_set_appie_cmd(ar->wmi, vif->fw_vif_idx,
363                                        WMI_FRAME_ASSOC_REQ, buf, len);
364         kfree(buf);
365         return ret;
366 }
367
368 static int ath6kl_nliftype_to_drv_iftype(enum nl80211_iftype type, u8 *nw_type)
369 {
370         switch (type) {
371         case NL80211_IFTYPE_STATION:
372         case NL80211_IFTYPE_P2P_CLIENT:
373                 *nw_type = INFRA_NETWORK;
374                 break;
375         case NL80211_IFTYPE_ADHOC:
376                 *nw_type = ADHOC_NETWORK;
377                 break;
378         case NL80211_IFTYPE_AP:
379         case NL80211_IFTYPE_P2P_GO:
380                 *nw_type = AP_NETWORK;
381                 break;
382         default:
383                 ath6kl_err("invalid interface type %u\n", type);
384                 return -ENOTSUPP;
385         }
386
387         return 0;
388 }
389
390 static bool ath6kl_is_valid_iftype(struct ath6kl *ar, enum nl80211_iftype type,
391                                    u8 *if_idx, u8 *nw_type)
392 {
393         int i;
394
395         if (ath6kl_nliftype_to_drv_iftype(type, nw_type))
396                 return false;
397
398         if (ar->ibss_if_active || ((type == NL80211_IFTYPE_ADHOC) &&
399                                    ar->num_vif))
400                 return false;
401
402         if (type == NL80211_IFTYPE_STATION ||
403             type == NL80211_IFTYPE_AP || type == NL80211_IFTYPE_ADHOC) {
404                 for (i = 0; i < ar->vif_max; i++) {
405                         if ((ar->avail_idx_map) & BIT(i)) {
406                                 *if_idx = i;
407                                 return true;
408                         }
409                 }
410         }
411
412         if (type == NL80211_IFTYPE_P2P_CLIENT ||
413             type == NL80211_IFTYPE_P2P_GO) {
414                 for (i = ar->max_norm_iface; i < ar->vif_max; i++) {
415                         if ((ar->avail_idx_map) & BIT(i)) {
416                                 *if_idx = i;
417                                 return true;
418                         }
419                 }
420         }
421
422         return false;
423 }
424
425 static bool ath6kl_is_tx_pending(struct ath6kl *ar)
426 {
427         return ar->tx_pending[ath6kl_wmi_get_control_ep(ar->wmi)] == 0;
428 }
429
430 static void ath6kl_cfg80211_sta_bmiss_enhance(struct ath6kl_vif *vif,
431                                               bool enable)
432 {
433         int err;
434
435         if (WARN_ON(!test_bit(WMI_READY, &vif->ar->flag)))
436                 return;
437
438         if (vif->nw_type != INFRA_NETWORK)
439                 return;
440
441         if (!test_bit(ATH6KL_FW_CAPABILITY_BMISS_ENHANCE,
442                       vif->ar->fw_capabilities))
443                 return;
444
445         ath6kl_dbg(ATH6KL_DBG_WLAN_CFG, "%s fw bmiss enhance\n",
446                    enable ? "enable" : "disable");
447
448         err = ath6kl_wmi_sta_bmiss_enhance_cmd(vif->ar->wmi,
449                                                vif->fw_vif_idx, enable);
450         if (err)
451                 ath6kl_err("failed to %s enhanced bmiss detection: %d\n",
452                            enable ? "enable" : "disable", err);
453 }
454
455 static int ath6kl_cfg80211_connect(struct wiphy *wiphy, struct net_device *dev,
456                                    struct cfg80211_connect_params *sme)
457 {
458         struct ath6kl *ar = ath6kl_priv(dev);
459         struct ath6kl_vif *vif = netdev_priv(dev);
460         int status;
461         u8 nw_subtype = (ar->p2p) ? SUBTYPE_P2PDEV : SUBTYPE_NONE;
462         u16 interval;
463
464         ath6kl_cfg80211_sscan_disable(vif);
465
466         vif->sme_state = SME_CONNECTING;
467
468         if (!ath6kl_cfg80211_ready(vif))
469                 return -EIO;
470
471         if (test_bit(DESTROY_IN_PROGRESS, &ar->flag)) {
472                 ath6kl_err("destroy in progress\n");
473                 return -EBUSY;
474         }
475
476         if (test_bit(SKIP_SCAN, &ar->flag) &&
477             ((sme->channel && sme->channel->center_freq == 0) ||
478              (sme->bssid && is_zero_ether_addr(sme->bssid)))) {
479                 ath6kl_err("SkipScan: channel or bssid invalid\n");
480                 return -EINVAL;
481         }
482
483         if (down_interruptible(&ar->sem)) {
484                 ath6kl_err("busy, couldn't get access\n");
485                 return -ERESTARTSYS;
486         }
487
488         if (test_bit(DESTROY_IN_PROGRESS, &ar->flag)) {
489                 ath6kl_err("busy, destroy in progress\n");
490                 up(&ar->sem);
491                 return -EBUSY;
492         }
493
494         if (ar->tx_pending[ath6kl_wmi_get_control_ep(ar->wmi)]) {
495                 /*
496                  * sleep until the command queue drains
497                  */
498                 wait_event_interruptible_timeout(ar->event_wq,
499                                                  ath6kl_is_tx_pending(ar),
500                                                  WMI_TIMEOUT);
501                 if (signal_pending(current)) {
502                         ath6kl_err("cmd queue drain timeout\n");
503                         up(&ar->sem);
504                         return -EINTR;
505                 }
506         }
507
508         status = ath6kl_set_assoc_req_ies(vif, sme->ie, sme->ie_len);
509         if (status) {
510                 up(&ar->sem);
511                 return status;
512         }
513
514         if (sme->ie == NULL || sme->ie_len == 0)
515                 ar->connect_ctrl_flags &= ~CONNECT_WPS_FLAG;
516
517         if (test_bit(CONNECTED, &vif->flags) &&
518             vif->ssid_len == sme->ssid_len &&
519             !memcmp(vif->ssid, sme->ssid, vif->ssid_len)) {
520                 vif->reconnect_flag = true;
521                 status = ath6kl_wmi_reconnect_cmd(ar->wmi, vif->fw_vif_idx,
522                                                   vif->req_bssid,
523                                                   vif->ch_hint);
524
525                 up(&ar->sem);
526                 if (status) {
527                         ath6kl_err("wmi_reconnect_cmd failed\n");
528                         return -EIO;
529                 }
530                 return 0;
531         } else if (vif->ssid_len == sme->ssid_len &&
532                    !memcmp(vif->ssid, sme->ssid, vif->ssid_len)) {
533                 ath6kl_disconnect(vif);
534         }
535
536         memset(vif->ssid, 0, sizeof(vif->ssid));
537         vif->ssid_len = sme->ssid_len;
538         memcpy(vif->ssid, sme->ssid, sme->ssid_len);
539
540         if (sme->channel)
541                 vif->ch_hint = sme->channel->center_freq;
542
543         memset(vif->req_bssid, 0, sizeof(vif->req_bssid));
544         if (sme->bssid && !is_broadcast_ether_addr(sme->bssid))
545                 memcpy(vif->req_bssid, sme->bssid, sizeof(vif->req_bssid));
546
547         ath6kl_set_wpa_version(vif, sme->crypto.wpa_versions);
548
549         status = ath6kl_set_auth_type(vif, sme->auth_type);
550         if (status) {
551                 up(&ar->sem);
552                 return status;
553         }
554
555         if (sme->crypto.n_ciphers_pairwise)
556                 ath6kl_set_cipher(vif, sme->crypto.ciphers_pairwise[0], true);
557         else
558                 ath6kl_set_cipher(vif, 0, true);
559
560         ath6kl_set_cipher(vif, sme->crypto.cipher_group, false);
561
562         if (sme->crypto.n_akm_suites)
563                 ath6kl_set_key_mgmt(vif, sme->crypto.akm_suites[0]);
564
565         if ((sme->key_len) &&
566             (vif->auth_mode == NONE_AUTH) &&
567             (vif->prwise_crypto == WEP_CRYPT)) {
568                 struct ath6kl_key *key = NULL;
569
570                 if (sme->key_idx > WMI_MAX_KEY_INDEX) {
571                         ath6kl_err("key index %d out of bounds\n",
572                                    sme->key_idx);
573                         up(&ar->sem);
574                         return -ENOENT;
575                 }
576
577                 key = &vif->keys[sme->key_idx];
578                 key->key_len = sme->key_len;
579                 memcpy(key->key, sme->key, key->key_len);
580                 key->cipher = vif->prwise_crypto;
581                 vif->def_txkey_index = sme->key_idx;
582
583                 ath6kl_wmi_addkey_cmd(ar->wmi, vif->fw_vif_idx, sme->key_idx,
584                                       vif->prwise_crypto,
585                                       GROUP_USAGE | TX_USAGE,
586                                       key->key_len,
587                                       NULL, 0,
588                                       key->key, KEY_OP_INIT_VAL, NULL,
589                                       NO_SYNC_WMIFLAG);
590         }
591
592         if (!ar->usr_bss_filter) {
593                 clear_bit(CLEAR_BSSFILTER_ON_BEACON, &vif->flags);
594                 if (ath6kl_wmi_bssfilter_cmd(ar->wmi, vif->fw_vif_idx,
595                                              ALL_BSS_FILTER, 0) != 0) {
596                         ath6kl_err("couldn't set bss filtering\n");
597                         up(&ar->sem);
598                         return -EIO;
599                 }
600         }
601
602         vif->nw_type = vif->next_mode;
603
604         /* enable enhanced bmiss detection if applicable */
605         ath6kl_cfg80211_sta_bmiss_enhance(vif, true);
606
607         if (vif->wdev.iftype == NL80211_IFTYPE_P2P_CLIENT)
608                 nw_subtype = SUBTYPE_P2PCLIENT;
609
610         ath6kl_dbg(ATH6KL_DBG_WLAN_CFG,
611                    "%s: connect called with authmode %d dot11 auth %d"
612                    " PW crypto %d PW crypto len %d GRP crypto %d"
613                    " GRP crypto len %d channel hint %u\n",
614                    __func__,
615                    vif->auth_mode, vif->dot11_auth_mode, vif->prwise_crypto,
616                    vif->prwise_crypto_len, vif->grp_crypto,
617                    vif->grp_crypto_len, vif->ch_hint);
618
619         vif->reconnect_flag = 0;
620
621         if (vif->nw_type == INFRA_NETWORK) {
622                 interval = max_t(u16, vif->listen_intvl_t,
623                                  ATH6KL_MAX_WOW_LISTEN_INTL);
624                 status = ath6kl_wmi_listeninterval_cmd(ar->wmi, vif->fw_vif_idx,
625                                                        interval,
626                                                        0);
627                 if (status) {
628                         ath6kl_err("couldn't set listen intervel\n");
629                         up(&ar->sem);
630                         return status;
631                 }
632         }
633
634         status = ath6kl_wmi_connect_cmd(ar->wmi, vif->fw_vif_idx, vif->nw_type,
635                                         vif->dot11_auth_mode, vif->auth_mode,
636                                         vif->prwise_crypto,
637                                         vif->prwise_crypto_len,
638                                         vif->grp_crypto, vif->grp_crypto_len,
639                                         vif->ssid_len, vif->ssid,
640                                         vif->req_bssid, vif->ch_hint,
641                                         ar->connect_ctrl_flags, nw_subtype);
642
643         if (sme->bg_scan_period == 0) {
644                 /* disable background scan if period is 0 */
645                 sme->bg_scan_period = 0xffff;
646         } else if (sme->bg_scan_period == -1) {
647                 /* configure default value if not specified */
648                 sme->bg_scan_period = DEFAULT_BG_SCAN_PERIOD;
649         }
650
651         ath6kl_wmi_scanparams_cmd(ar->wmi, vif->fw_vif_idx, 0, 0,
652                                   sme->bg_scan_period, 0, 0, 0, 3, 0, 0, 0);
653
654         up(&ar->sem);
655
656         if (status == -EINVAL) {
657                 memset(vif->ssid, 0, sizeof(vif->ssid));
658                 vif->ssid_len = 0;
659                 ath6kl_err("invalid request\n");
660                 return -ENOENT;
661         } else if (status) {
662                 ath6kl_err("ath6kl_wmi_connect_cmd failed\n");
663                 return -EIO;
664         }
665
666         if ((!(ar->connect_ctrl_flags & CONNECT_DO_WPA_OFFLOAD)) &&
667             ((vif->auth_mode == WPA_PSK_AUTH) ||
668              (vif->auth_mode == WPA2_PSK_AUTH))) {
669                 mod_timer(&vif->disconnect_timer,
670                           jiffies + msecs_to_jiffies(DISCON_TIMER_INTVAL));
671         }
672
673         ar->connect_ctrl_flags &= ~CONNECT_DO_WPA_OFFLOAD;
674         set_bit(CONNECT_PEND, &vif->flags);
675
676         return 0;
677 }
678
679 static struct cfg80211_bss *
680 ath6kl_add_bss_if_needed(struct ath6kl_vif *vif,
681                          enum network_type nw_type,
682                          const u8 *bssid,
683                          struct ieee80211_channel *chan,
684                          const u8 *beacon_ie,
685                          size_t beacon_ie_len)
686 {
687         struct ath6kl *ar = vif->ar;
688         struct cfg80211_bss *bss;
689         u16 cap_mask, cap_val;
690         u8 *ie;
691
692         if (nw_type & ADHOC_NETWORK) {
693                 cap_mask = WLAN_CAPABILITY_IBSS;
694                 cap_val = WLAN_CAPABILITY_IBSS;
695         } else {
696                 cap_mask = WLAN_CAPABILITY_ESS;
697                 cap_val = WLAN_CAPABILITY_ESS;
698         }
699
700         bss = cfg80211_get_bss(ar->wiphy, chan, bssid,
701                                vif->ssid, vif->ssid_len,
702                                cap_mask, cap_val);
703         if (bss == NULL) {
704                 /*
705                  * Since cfg80211 may not yet know about the BSS,
706                  * generate a partial entry until the first BSS info
707                  * event becomes available.
708                  *
709                  * Prepend SSID element since it is not included in the Beacon
710                  * IEs from the target.
711                  */
712                 ie = kmalloc(2 + vif->ssid_len + beacon_ie_len, GFP_KERNEL);
713                 if (ie == NULL)
714                         return NULL;
715                 ie[0] = WLAN_EID_SSID;
716                 ie[1] = vif->ssid_len;
717                 memcpy(ie + 2, vif->ssid, vif->ssid_len);
718                 memcpy(ie + 2 + vif->ssid_len, beacon_ie, beacon_ie_len);
719                 bss = cfg80211_inform_bss(ar->wiphy, chan,
720                                           bssid, 0, cap_val, 100,
721                                           ie, 2 + vif->ssid_len + beacon_ie_len,
722                                           0, GFP_KERNEL);
723                 if (bss)
724                         ath6kl_dbg(ATH6KL_DBG_WLAN_CFG,
725                                    "added bss %pM to cfg80211\n", bssid);
726                 kfree(ie);
727         } else {
728                 ath6kl_dbg(ATH6KL_DBG_WLAN_CFG, "cfg80211 already has a bss\n");
729         }
730
731         return bss;
732 }
733
734 void ath6kl_cfg80211_connect_event(struct ath6kl_vif *vif, u16 channel,
735                                    u8 *bssid, u16 listen_intvl,
736                                    u16 beacon_intvl,
737                                    enum network_type nw_type,
738                                    u8 beacon_ie_len, u8 assoc_req_len,
739                                    u8 assoc_resp_len, u8 *assoc_info)
740 {
741         struct ieee80211_channel *chan;
742         struct ath6kl *ar = vif->ar;
743         struct cfg80211_bss *bss;
744
745         /* capinfo + listen interval */
746         u8 assoc_req_ie_offset = sizeof(u16) + sizeof(u16);
747
748         /* capinfo + status code +  associd */
749         u8 assoc_resp_ie_offset = sizeof(u16) + sizeof(u16) + sizeof(u16);
750
751         u8 *assoc_req_ie = assoc_info + beacon_ie_len + assoc_req_ie_offset;
752         u8 *assoc_resp_ie = assoc_info + beacon_ie_len + assoc_req_len +
753             assoc_resp_ie_offset;
754
755         assoc_req_len -= assoc_req_ie_offset;
756         assoc_resp_len -= assoc_resp_ie_offset;
757
758         /*
759          * Store Beacon interval here; DTIM period will be available only once
760          * a Beacon frame from the AP is seen.
761          */
762         vif->assoc_bss_beacon_int = beacon_intvl;
763         clear_bit(DTIM_PERIOD_AVAIL, &vif->flags);
764
765         if (nw_type & ADHOC_NETWORK) {
766                 if (vif->wdev.iftype != NL80211_IFTYPE_ADHOC) {
767                         ath6kl_dbg(ATH6KL_DBG_WLAN_CFG,
768                                    "%s: ath6k not in ibss mode\n", __func__);
769                         return;
770                 }
771         }
772
773         if (nw_type & INFRA_NETWORK) {
774                 if (vif->wdev.iftype != NL80211_IFTYPE_STATION &&
775                     vif->wdev.iftype != NL80211_IFTYPE_P2P_CLIENT) {
776                         ath6kl_dbg(ATH6KL_DBG_WLAN_CFG,
777                                    "%s: ath6k not in station mode\n", __func__);
778                         return;
779                 }
780         }
781
782         chan = ieee80211_get_channel(ar->wiphy, (int) channel);
783
784         bss = ath6kl_add_bss_if_needed(vif, nw_type, bssid, chan,
785                                        assoc_info, beacon_ie_len);
786         if (!bss) {
787                 ath6kl_err("could not add cfg80211 bss entry\n");
788                 return;
789         }
790
791         if (nw_type & ADHOC_NETWORK) {
792                 ath6kl_dbg(ATH6KL_DBG_WLAN_CFG, "ad-hoc %s selected\n",
793                            nw_type & ADHOC_CREATOR ? "creator" : "joiner");
794                 cfg80211_ibss_joined(vif->ndev, bssid, chan, GFP_KERNEL);
795                 cfg80211_put_bss(ar->wiphy, bss);
796                 return;
797         }
798
799         if (vif->sme_state == SME_CONNECTING) {
800                 /* inform connect result to cfg80211 */
801                 vif->sme_state = SME_CONNECTED;
802                 cfg80211_connect_result(vif->ndev, bssid,
803                                         assoc_req_ie, assoc_req_len,
804                                         assoc_resp_ie, assoc_resp_len,
805                                         WLAN_STATUS_SUCCESS, GFP_KERNEL);
806                 cfg80211_put_bss(ar->wiphy, bss);
807         } else if (vif->sme_state == SME_CONNECTED) {
808                 /* inform roam event to cfg80211 */
809                 cfg80211_roamed_bss(vif->ndev, bss, assoc_req_ie, assoc_req_len,
810                                     assoc_resp_ie, assoc_resp_len, GFP_KERNEL);
811         }
812 }
813
814 static int ath6kl_cfg80211_disconnect(struct wiphy *wiphy,
815                                       struct net_device *dev, u16 reason_code)
816 {
817         struct ath6kl *ar = ath6kl_priv(dev);
818         struct ath6kl_vif *vif = netdev_priv(dev);
819
820         ath6kl_dbg(ATH6KL_DBG_WLAN_CFG, "%s: reason=%u\n", __func__,
821                    reason_code);
822
823         ath6kl_cfg80211_sscan_disable(vif);
824
825         if (!ath6kl_cfg80211_ready(vif))
826                 return -EIO;
827
828         if (test_bit(DESTROY_IN_PROGRESS, &ar->flag)) {
829                 ath6kl_err("busy, destroy in progress\n");
830                 return -EBUSY;
831         }
832
833         if (down_interruptible(&ar->sem)) {
834                 ath6kl_err("busy, couldn't get access\n");
835                 return -ERESTARTSYS;
836         }
837
838         vif->reconnect_flag = 0;
839         ath6kl_disconnect(vif);
840         memset(vif->ssid, 0, sizeof(vif->ssid));
841         vif->ssid_len = 0;
842
843         if (!test_bit(SKIP_SCAN, &ar->flag))
844                 memset(vif->req_bssid, 0, sizeof(vif->req_bssid));
845
846         up(&ar->sem);
847
848         vif->sme_state = SME_DISCONNECTED;
849
850         return 0;
851 }
852
853 void ath6kl_cfg80211_disconnect_event(struct ath6kl_vif *vif, u8 reason,
854                                       u8 *bssid, u8 assoc_resp_len,
855                                       u8 *assoc_info, u16 proto_reason)
856 {
857         struct ath6kl *ar = vif->ar;
858
859         if (vif->scan_req) {
860                 cfg80211_scan_done(vif->scan_req, true);
861                 vif->scan_req = NULL;
862         }
863
864         if (vif->nw_type & ADHOC_NETWORK) {
865                 if (vif->wdev.iftype != NL80211_IFTYPE_ADHOC)
866                         ath6kl_dbg(ATH6KL_DBG_WLAN_CFG,
867                                    "%s: ath6k not in ibss mode\n", __func__);
868                 return;
869         }
870
871         if (vif->nw_type & INFRA_NETWORK) {
872                 if (vif->wdev.iftype != NL80211_IFTYPE_STATION &&
873                     vif->wdev.iftype != NL80211_IFTYPE_P2P_CLIENT) {
874                         ath6kl_dbg(ATH6KL_DBG_WLAN_CFG,
875                                    "%s: ath6k not in station mode\n", __func__);
876                         return;
877                 }
878         }
879
880         clear_bit(CONNECT_PEND, &vif->flags);
881
882         if (vif->sme_state == SME_CONNECTING) {
883                 cfg80211_connect_result(vif->ndev,
884                                         bssid, NULL, 0,
885                                         NULL, 0,
886                                         WLAN_STATUS_UNSPECIFIED_FAILURE,
887                                         GFP_KERNEL);
888         } else if (vif->sme_state == SME_CONNECTED) {
889                 cfg80211_disconnected(vif->ndev, proto_reason,
890                                       NULL, 0, GFP_KERNEL);
891         }
892
893         vif->sme_state = SME_DISCONNECTED;
894
895         /*
896          * Send a disconnect command to target when a disconnect event is
897          * received with reason code other than 3 (DISCONNECT_CMD - disconnect
898          * request from host) to make the firmware stop trying to connect even
899          * after giving disconnect event. There will be one more disconnect
900          * event for this disconnect command with reason code DISCONNECT_CMD
901          * which won't be notified to cfg80211.
902          */
903         if (reason != DISCONNECT_CMD)
904                 ath6kl_wmi_disconnect_cmd(ar->wmi, vif->fw_vif_idx);
905 }
906
907 static int ath6kl_set_probed_ssids(struct ath6kl *ar,
908                                    struct ath6kl_vif *vif,
909                                    struct cfg80211_ssid *ssids, int n_ssids,
910                                    struct cfg80211_match_set *match_set,
911                                    int n_match_ssid)
912 {
913         u8 i, j, index_to_add, ssid_found = false;
914         struct ath6kl_cfg80211_match_probe_ssid ssid_list[MAX_PROBED_SSIDS];
915
916         memset(ssid_list, 0, sizeof(ssid_list));
917
918         if (n_ssids > MAX_PROBED_SSIDS ||
919             n_match_ssid > MAX_PROBED_SSIDS)
920                 return -EINVAL;
921
922         for (i = 0; i < n_ssids; i++) {
923                 memcpy(ssid_list[i].ssid.ssid,
924                        ssids[i].ssid,
925                        ssids[i].ssid_len);
926                 ssid_list[i].ssid.ssid_len = ssids[i].ssid_len;
927
928                 if (ssids[i].ssid_len)
929                         ssid_list[i].flag = SPECIFIC_SSID_FLAG;
930                 else
931                         ssid_list[i].flag = ANY_SSID_FLAG;
932
933                 if (n_match_ssid == 0)
934                         ssid_list[i].flag |= MATCH_SSID_FLAG;
935         }
936
937         index_to_add = i;
938
939         for (i = 0; i < n_match_ssid; i++) {
940                 ssid_found = false;
941
942                 for (j = 0; j < n_ssids; j++) {
943                         if ((match_set[i].ssid.ssid_len ==
944                              ssid_list[j].ssid.ssid_len) &&
945                             (!memcmp(ssid_list[j].ssid.ssid,
946                                      match_set[i].ssid.ssid,
947                                      match_set[i].ssid.ssid_len))) {
948                                 ssid_list[j].flag |= MATCH_SSID_FLAG;
949                                 ssid_found = true;
950                                 break;
951                         }
952                 }
953
954                 if (ssid_found)
955                         continue;
956
957                 if (index_to_add >= MAX_PROBED_SSIDS)
958                         continue;
959
960                 ssid_list[index_to_add].ssid.ssid_len =
961                         match_set[i].ssid.ssid_len;
962                 memcpy(ssid_list[index_to_add].ssid.ssid,
963                        match_set[i].ssid.ssid,
964                        match_set[i].ssid.ssid_len);
965                 ssid_list[index_to_add].flag |= MATCH_SSID_FLAG;
966                 index_to_add++;
967         }
968
969         for (i = 0; i < index_to_add; i++) {
970                 ath6kl_wmi_probedssid_cmd(ar->wmi, vif->fw_vif_idx, i,
971                                           ssid_list[i].flag,
972                                           ssid_list[i].ssid.ssid_len,
973                                           ssid_list[i].ssid.ssid);
974         }
975
976         /* Make sure no old entries are left behind */
977         for (i = index_to_add; i < MAX_PROBED_SSIDS; i++) {
978                 ath6kl_wmi_probedssid_cmd(ar->wmi, vif->fw_vif_idx, i,
979                                           DISABLE_SSID_FLAG, 0, NULL);
980         }
981
982         return 0;
983 }
984
985 static int ath6kl_cfg80211_scan(struct wiphy *wiphy,
986                                 struct cfg80211_scan_request *request)
987 {
988         struct ath6kl_vif *vif = ath6kl_vif_from_wdev(request->wdev);
989         struct ath6kl *ar = ath6kl_priv(vif->ndev);
990         s8 n_channels = 0;
991         u16 *channels = NULL;
992         int ret = 0;
993         u32 force_fg_scan = 0;
994
995         if (!ath6kl_cfg80211_ready(vif))
996                 return -EIO;
997
998         ath6kl_cfg80211_sscan_disable(vif);
999
1000         if (!ar->usr_bss_filter) {
1001                 clear_bit(CLEAR_BSSFILTER_ON_BEACON, &vif->flags);
1002                 ret = ath6kl_wmi_bssfilter_cmd(ar->wmi, vif->fw_vif_idx,
1003                                                ALL_BSS_FILTER, 0);
1004                 if (ret) {
1005                         ath6kl_err("couldn't set bss filtering\n");
1006                         return ret;
1007                 }
1008         }
1009
1010         ret = ath6kl_set_probed_ssids(ar, vif, request->ssids,
1011                                       request->n_ssids, NULL, 0);
1012         if (ret < 0)
1013                 return ret;
1014
1015         /* this also clears IE in fw if it's not set */
1016         ret = ath6kl_wmi_set_appie_cmd(ar->wmi, vif->fw_vif_idx,
1017                                        WMI_FRAME_PROBE_REQ,
1018                                        request->ie, request->ie_len);
1019         if (ret) {
1020                 ath6kl_err("failed to set Probe Request appie for scan\n");
1021                 return ret;
1022         }
1023
1024         /*
1025          * Scan only the requested channels if the request specifies a set of
1026          * channels. If the list is longer than the target supports, do not
1027          * configure the list and instead, scan all available channels.
1028          */
1029         if (request->n_channels > 0 &&
1030             request->n_channels <= WMI_MAX_CHANNELS) {
1031                 u8 i;
1032
1033                 n_channels = request->n_channels;
1034
1035                 channels = kzalloc(n_channels * sizeof(u16), GFP_KERNEL);
1036                 if (channels == NULL) {
1037                         ath6kl_warn("failed to set scan channels, scan all channels");
1038                         n_channels = 0;
1039                 }
1040
1041                 for (i = 0; i < n_channels; i++)
1042                         channels[i] = request->channels[i]->center_freq;
1043         }
1044
1045         if (test_bit(CONNECTED, &vif->flags))
1046                 force_fg_scan = 1;
1047
1048         vif->scan_req = request;
1049
1050         ret = ath6kl_wmi_beginscan_cmd(ar->wmi, vif->fw_vif_idx,
1051                                        WMI_LONG_SCAN, force_fg_scan,
1052                                        false, 0,
1053                                        ATH6KL_FG_SCAN_INTERVAL,
1054                                        n_channels, channels,
1055                                        request->no_cck,
1056                                        request->rates);
1057         if (ret) {
1058                 ath6kl_err("failed to start scan: %d\n", ret);
1059                 vif->scan_req = NULL;
1060         }
1061
1062         kfree(channels);
1063
1064         return ret;
1065 }
1066
1067 void ath6kl_cfg80211_scan_complete_event(struct ath6kl_vif *vif, bool aborted)
1068 {
1069         struct ath6kl *ar = vif->ar;
1070         int i;
1071
1072         ath6kl_dbg(ATH6KL_DBG_WLAN_CFG, "%s: status%s\n", __func__,
1073                    aborted ? " aborted" : "");
1074
1075         if (!vif->scan_req)
1076                 return;
1077
1078         if (aborted)
1079                 goto out;
1080
1081         if (vif->scan_req->n_ssids && vif->scan_req->ssids[0].ssid_len) {
1082                 for (i = 0; i < vif->scan_req->n_ssids; i++) {
1083                         ath6kl_wmi_probedssid_cmd(ar->wmi, vif->fw_vif_idx,
1084                                                   i + 1, DISABLE_SSID_FLAG,
1085                                                   0, NULL);
1086                 }
1087         }
1088
1089 out:
1090         cfg80211_scan_done(vif->scan_req, aborted);
1091         vif->scan_req = NULL;
1092 }
1093
1094 void ath6kl_cfg80211_ch_switch_notify(struct ath6kl_vif *vif, int freq,
1095                                       enum wmi_phy_mode mode)
1096 {
1097         struct cfg80211_chan_def chandef;
1098
1099         ath6kl_dbg(ATH6KL_DBG_WLAN_CFG,
1100                    "channel switch notify nw_type %d freq %d mode %d\n",
1101                    vif->nw_type, freq, mode);
1102
1103         cfg80211_chandef_create(&chandef,
1104                                 ieee80211_get_channel(vif->ar->wiphy, freq),
1105                                 (mode == WMI_11G_HT20) ?
1106                                         NL80211_CHAN_HT20 : NL80211_CHAN_NO_HT);
1107
1108         mutex_lock(&vif->wdev.mtx);
1109         cfg80211_ch_switch_notify(vif->ndev, &chandef);
1110         mutex_unlock(&vif->wdev.mtx);
1111 }
1112
1113 static int ath6kl_cfg80211_add_key(struct wiphy *wiphy, struct net_device *ndev,
1114                                    u8 key_index, bool pairwise,
1115                                    const u8 *mac_addr,
1116                                    struct key_params *params)
1117 {
1118         struct ath6kl *ar = ath6kl_priv(ndev);
1119         struct ath6kl_vif *vif = netdev_priv(ndev);
1120         struct ath6kl_key *key = NULL;
1121         int seq_len;
1122         u8 key_usage;
1123         u8 key_type;
1124
1125         if (!ath6kl_cfg80211_ready(vif))
1126                 return -EIO;
1127
1128         if (params->cipher == CCKM_KRK_CIPHER_SUITE) {
1129                 if (params->key_len != WMI_KRK_LEN)
1130                         return -EINVAL;
1131                 return ath6kl_wmi_add_krk_cmd(ar->wmi, vif->fw_vif_idx,
1132                                               params->key);
1133         }
1134
1135         if (key_index > WMI_MAX_KEY_INDEX) {
1136                 ath6kl_dbg(ATH6KL_DBG_WLAN_CFG,
1137                            "%s: key index %d out of bounds\n", __func__,
1138                            key_index);
1139                 return -ENOENT;
1140         }
1141
1142         key = &vif->keys[key_index];
1143         memset(key, 0, sizeof(struct ath6kl_key));
1144
1145         if (pairwise)
1146                 key_usage = PAIRWISE_USAGE;
1147         else
1148                 key_usage = GROUP_USAGE;
1149
1150         seq_len = params->seq_len;
1151         if (params->cipher == WLAN_CIPHER_SUITE_SMS4 &&
1152             seq_len > ATH6KL_KEY_SEQ_LEN) {
1153                 /* Only first half of the WPI PN is configured */
1154                 seq_len = ATH6KL_KEY_SEQ_LEN;
1155         }
1156         if (params->key_len > WLAN_MAX_KEY_LEN ||
1157             seq_len > sizeof(key->seq))
1158                 return -EINVAL;
1159
1160         key->key_len = params->key_len;
1161         memcpy(key->key, params->key, key->key_len);
1162         key->seq_len = seq_len;
1163         memcpy(key->seq, params->seq, key->seq_len);
1164         key->cipher = params->cipher;
1165
1166         switch (key->cipher) {
1167         case WLAN_CIPHER_SUITE_WEP40:
1168         case WLAN_CIPHER_SUITE_WEP104:
1169                 key_type = WEP_CRYPT;
1170                 break;
1171
1172         case WLAN_CIPHER_SUITE_TKIP:
1173                 key_type = TKIP_CRYPT;
1174                 break;
1175
1176         case WLAN_CIPHER_SUITE_CCMP:
1177                 key_type = AES_CRYPT;
1178                 break;
1179         case WLAN_CIPHER_SUITE_SMS4:
1180                 key_type = WAPI_CRYPT;
1181                 break;
1182
1183         default:
1184                 return -ENOTSUPP;
1185         }
1186
1187         if (((vif->auth_mode == WPA_PSK_AUTH) ||
1188              (vif->auth_mode == WPA2_PSK_AUTH)) &&
1189             (key_usage & GROUP_USAGE))
1190                 del_timer(&vif->disconnect_timer);
1191
1192         ath6kl_dbg(ATH6KL_DBG_WLAN_CFG,
1193                    "%s: index %d, key_len %d, key_type 0x%x, key_usage 0x%x, seq_len %d\n",
1194                    __func__, key_index, key->key_len, key_type,
1195                    key_usage, key->seq_len);
1196
1197         if (vif->nw_type == AP_NETWORK && !pairwise &&
1198             (key_type == TKIP_CRYPT || key_type == AES_CRYPT ||
1199              key_type == WAPI_CRYPT)) {
1200                 ar->ap_mode_bkey.valid = true;
1201                 ar->ap_mode_bkey.key_index = key_index;
1202                 ar->ap_mode_bkey.key_type = key_type;
1203                 ar->ap_mode_bkey.key_len = key->key_len;
1204                 memcpy(ar->ap_mode_bkey.key, key->key, key->key_len);
1205                 if (!test_bit(CONNECTED, &vif->flags)) {
1206                         ath6kl_dbg(ATH6KL_DBG_WLAN_CFG,
1207                                    "Delay initial group key configuration until AP mode has been started\n");
1208                         /*
1209                          * The key will be set in ath6kl_connect_ap_mode() once
1210                          * the connected event is received from the target.
1211                          */
1212                         return 0;
1213                 }
1214         }
1215
1216         if (vif->next_mode == AP_NETWORK && key_type == WEP_CRYPT &&
1217             !test_bit(CONNECTED, &vif->flags)) {
1218                 /*
1219                  * Store the key locally so that it can be re-configured after
1220                  * the AP mode has properly started
1221                  * (ath6kl_install_statioc_wep_keys).
1222                  */
1223                 ath6kl_dbg(ATH6KL_DBG_WLAN_CFG,
1224                            "Delay WEP key configuration until AP mode has been started\n");
1225                 vif->wep_key_list[key_index].key_len = key->key_len;
1226                 memcpy(vif->wep_key_list[key_index].key, key->key,
1227                        key->key_len);
1228                 return 0;
1229         }
1230
1231         return ath6kl_wmi_addkey_cmd(ar->wmi, vif->fw_vif_idx, key_index,
1232                                      key_type, key_usage, key->key_len,
1233                                      key->seq, key->seq_len, key->key,
1234                                      KEY_OP_INIT_VAL,
1235                                      (u8 *) mac_addr, SYNC_BOTH_WMIFLAG);
1236 }
1237
1238 static int ath6kl_cfg80211_del_key(struct wiphy *wiphy, struct net_device *ndev,
1239                                    u8 key_index, bool pairwise,
1240                                    const u8 *mac_addr)
1241 {
1242         struct ath6kl *ar = ath6kl_priv(ndev);
1243         struct ath6kl_vif *vif = netdev_priv(ndev);
1244
1245         ath6kl_dbg(ATH6KL_DBG_WLAN_CFG, "%s: index %d\n", __func__, key_index);
1246
1247         if (!ath6kl_cfg80211_ready(vif))
1248                 return -EIO;
1249
1250         if (key_index > WMI_MAX_KEY_INDEX) {
1251                 ath6kl_dbg(ATH6KL_DBG_WLAN_CFG,
1252                            "%s: key index %d out of bounds\n", __func__,
1253                            key_index);
1254                 return -ENOENT;
1255         }
1256
1257         if (!vif->keys[key_index].key_len) {
1258                 ath6kl_dbg(ATH6KL_DBG_WLAN_CFG,
1259                            "%s: index %d is empty\n", __func__, key_index);
1260                 return 0;
1261         }
1262
1263         vif->keys[key_index].key_len = 0;
1264
1265         return ath6kl_wmi_deletekey_cmd(ar->wmi, vif->fw_vif_idx, key_index);
1266 }
1267
1268 static int ath6kl_cfg80211_get_key(struct wiphy *wiphy, struct net_device *ndev,
1269                                    u8 key_index, bool pairwise,
1270                                    const u8 *mac_addr, void *cookie,
1271                                    void (*callback) (void *cookie,
1272                                                      struct key_params *))
1273 {
1274         struct ath6kl_vif *vif = netdev_priv(ndev);
1275         struct ath6kl_key *key = NULL;
1276         struct key_params params;
1277
1278         ath6kl_dbg(ATH6KL_DBG_WLAN_CFG, "%s: index %d\n", __func__, key_index);
1279
1280         if (!ath6kl_cfg80211_ready(vif))
1281                 return -EIO;
1282
1283         if (key_index > WMI_MAX_KEY_INDEX) {
1284                 ath6kl_dbg(ATH6KL_DBG_WLAN_CFG,
1285                            "%s: key index %d out of bounds\n", __func__,
1286                            key_index);
1287                 return -ENOENT;
1288         }
1289
1290         key = &vif->keys[key_index];
1291         memset(&params, 0, sizeof(params));
1292         params.cipher = key->cipher;
1293         params.key_len = key->key_len;
1294         params.seq_len = key->seq_len;
1295         params.seq = key->seq;
1296         params.key = key->key;
1297
1298         callback(cookie, &params);
1299
1300         return key->key_len ? 0 : -ENOENT;
1301 }
1302
1303 static int ath6kl_cfg80211_set_default_key(struct wiphy *wiphy,
1304                                            struct net_device *ndev,
1305                                            u8 key_index, bool unicast,
1306                                            bool multicast)
1307 {
1308         struct ath6kl *ar = ath6kl_priv(ndev);
1309         struct ath6kl_vif *vif = netdev_priv(ndev);
1310         struct ath6kl_key *key = NULL;
1311         u8 key_usage;
1312         enum crypto_type key_type = NONE_CRYPT;
1313
1314         ath6kl_dbg(ATH6KL_DBG_WLAN_CFG, "%s: index %d\n", __func__, key_index);
1315
1316         if (!ath6kl_cfg80211_ready(vif))
1317                 return -EIO;
1318
1319         if (key_index > WMI_MAX_KEY_INDEX) {
1320                 ath6kl_dbg(ATH6KL_DBG_WLAN_CFG,
1321                            "%s: key index %d out of bounds\n",
1322                            __func__, key_index);
1323                 return -ENOENT;
1324         }
1325
1326         if (!vif->keys[key_index].key_len) {
1327                 ath6kl_dbg(ATH6KL_DBG_WLAN_CFG, "%s: invalid key index %d\n",
1328                            __func__, key_index);
1329                 return -EINVAL;
1330         }
1331
1332         vif->def_txkey_index = key_index;
1333         key = &vif->keys[vif->def_txkey_index];
1334         key_usage = GROUP_USAGE;
1335         if (vif->prwise_crypto == WEP_CRYPT)
1336                 key_usage |= TX_USAGE;
1337         if (unicast)
1338                 key_type = vif->prwise_crypto;
1339         if (multicast)
1340                 key_type = vif->grp_crypto;
1341
1342         if (vif->next_mode == AP_NETWORK && !test_bit(CONNECTED, &vif->flags))
1343                 return 0; /* Delay until AP mode has been started */
1344
1345         return ath6kl_wmi_addkey_cmd(ar->wmi, vif->fw_vif_idx,
1346                                      vif->def_txkey_index,
1347                                      key_type, key_usage,
1348                                      key->key_len, key->seq, key->seq_len,
1349                                      key->key,
1350                                      KEY_OP_INIT_VAL, NULL,
1351                                      SYNC_BOTH_WMIFLAG);
1352 }
1353
1354 void ath6kl_cfg80211_tkip_micerr_event(struct ath6kl_vif *vif, u8 keyid,
1355                                        bool ismcast)
1356 {
1357         ath6kl_dbg(ATH6KL_DBG_WLAN_CFG,
1358                    "%s: keyid %d, ismcast %d\n", __func__, keyid, ismcast);
1359
1360         cfg80211_michael_mic_failure(vif->ndev, vif->bssid,
1361                                      (ismcast ? NL80211_KEYTYPE_GROUP :
1362                                       NL80211_KEYTYPE_PAIRWISE), keyid, NULL,
1363                                      GFP_KERNEL);
1364 }
1365
1366 static int ath6kl_cfg80211_set_wiphy_params(struct wiphy *wiphy, u32 changed)
1367 {
1368         struct ath6kl *ar = (struct ath6kl *)wiphy_priv(wiphy);
1369         struct ath6kl_vif *vif;
1370         int ret;
1371
1372         ath6kl_dbg(ATH6KL_DBG_WLAN_CFG, "%s: changed 0x%x\n", __func__,
1373                    changed);
1374
1375         vif = ath6kl_vif_first(ar);
1376         if (!vif)
1377                 return -EIO;
1378
1379         if (!ath6kl_cfg80211_ready(vif))
1380                 return -EIO;
1381
1382         if (changed & WIPHY_PARAM_RTS_THRESHOLD) {
1383                 ret = ath6kl_wmi_set_rts_cmd(ar->wmi, wiphy->rts_threshold);
1384                 if (ret != 0) {
1385                         ath6kl_err("ath6kl_wmi_set_rts_cmd failed\n");
1386                         return -EIO;
1387                 }
1388         }
1389
1390         return 0;
1391 }
1392
1393 static int ath6kl_cfg80211_set_txpower(struct wiphy *wiphy,
1394                                        struct wireless_dev *wdev,
1395                                        enum nl80211_tx_power_setting type,
1396                                        int mbm)
1397 {
1398         struct ath6kl *ar = (struct ath6kl *)wiphy_priv(wiphy);
1399         struct ath6kl_vif *vif;
1400         int dbm = MBM_TO_DBM(mbm);
1401
1402         ath6kl_dbg(ATH6KL_DBG_WLAN_CFG, "%s: type 0x%x, dbm %d\n", __func__,
1403                    type, dbm);
1404
1405         vif = ath6kl_vif_first(ar);
1406         if (!vif)
1407                 return -EIO;
1408
1409         if (!ath6kl_cfg80211_ready(vif))
1410                 return -EIO;
1411
1412         switch (type) {
1413         case NL80211_TX_POWER_AUTOMATIC:
1414                 return 0;
1415         case NL80211_TX_POWER_LIMITED:
1416                 ar->tx_pwr = dbm;
1417                 break;
1418         default:
1419                 ath6kl_dbg(ATH6KL_DBG_WLAN_CFG, "%s: type 0x%x not supported\n",
1420                            __func__, type);
1421                 return -EOPNOTSUPP;
1422         }
1423
1424         ath6kl_wmi_set_tx_pwr_cmd(ar->wmi, vif->fw_vif_idx, dbm);
1425
1426         return 0;
1427 }
1428
1429 static int ath6kl_cfg80211_get_txpower(struct wiphy *wiphy,
1430                                        struct wireless_dev *wdev,
1431                                        int *dbm)
1432 {
1433         struct ath6kl *ar = (struct ath6kl *)wiphy_priv(wiphy);
1434         struct ath6kl_vif *vif;
1435
1436         vif = ath6kl_vif_first(ar);
1437         if (!vif)
1438                 return -EIO;
1439
1440         if (!ath6kl_cfg80211_ready(vif))
1441                 return -EIO;
1442
1443         if (test_bit(CONNECTED, &vif->flags)) {
1444                 ar->tx_pwr = 0;
1445
1446                 if (ath6kl_wmi_get_tx_pwr_cmd(ar->wmi, vif->fw_vif_idx) != 0) {
1447                         ath6kl_err("ath6kl_wmi_get_tx_pwr_cmd failed\n");
1448                         return -EIO;
1449                 }
1450
1451                 wait_event_interruptible_timeout(ar->event_wq, ar->tx_pwr != 0,
1452                                                  5 * HZ);
1453
1454                 if (signal_pending(current)) {
1455                         ath6kl_err("target did not respond\n");
1456                         return -EINTR;
1457                 }
1458         }
1459
1460         *dbm = ar->tx_pwr;
1461         return 0;
1462 }
1463
1464 static int ath6kl_cfg80211_set_power_mgmt(struct wiphy *wiphy,
1465                                           struct net_device *dev,
1466                                           bool pmgmt, int timeout)
1467 {
1468         struct ath6kl *ar = ath6kl_priv(dev);
1469         struct wmi_power_mode_cmd mode;
1470         struct ath6kl_vif *vif = netdev_priv(dev);
1471
1472         ath6kl_dbg(ATH6KL_DBG_WLAN_CFG, "%s: pmgmt %d, timeout %d\n",
1473                    __func__, pmgmt, timeout);
1474
1475         if (!ath6kl_cfg80211_ready(vif))
1476                 return -EIO;
1477
1478         if (pmgmt) {
1479                 ath6kl_dbg(ATH6KL_DBG_WLAN_CFG, "%s: rec power\n", __func__);
1480                 mode.pwr_mode = REC_POWER;
1481         } else {
1482                 ath6kl_dbg(ATH6KL_DBG_WLAN_CFG, "%s: max perf\n", __func__);
1483                 mode.pwr_mode = MAX_PERF_POWER;
1484         }
1485
1486         if (ath6kl_wmi_powermode_cmd(ar->wmi, vif->fw_vif_idx,
1487                                      mode.pwr_mode) != 0) {
1488                 ath6kl_err("wmi_powermode_cmd failed\n");
1489                 return -EIO;
1490         }
1491
1492         return 0;
1493 }
1494
1495 static struct wireless_dev *ath6kl_cfg80211_add_iface(struct wiphy *wiphy,
1496                                                       const char *name,
1497                                                       enum nl80211_iftype type,
1498                                                       u32 *flags,
1499                                                       struct vif_params *params)
1500 {
1501         struct ath6kl *ar = wiphy_priv(wiphy);
1502         struct wireless_dev *wdev;
1503         u8 if_idx, nw_type;
1504
1505         if (ar->num_vif == ar->vif_max) {
1506                 ath6kl_err("Reached maximum number of supported vif\n");
1507                 return ERR_PTR(-EINVAL);
1508         }
1509
1510         if (!ath6kl_is_valid_iftype(ar, type, &if_idx, &nw_type)) {
1511                 ath6kl_err("Not a supported interface type\n");
1512                 return ERR_PTR(-EINVAL);
1513         }
1514
1515         wdev = ath6kl_interface_add(ar, name, type, if_idx, nw_type);
1516         if (!wdev)
1517                 return ERR_PTR(-ENOMEM);
1518
1519         ar->num_vif++;
1520
1521         return wdev;
1522 }
1523
1524 static int ath6kl_cfg80211_del_iface(struct wiphy *wiphy,
1525                                      struct wireless_dev *wdev)
1526 {
1527         struct ath6kl *ar = wiphy_priv(wiphy);
1528         struct ath6kl_vif *vif = netdev_priv(wdev->netdev);
1529
1530         spin_lock_bh(&ar->list_lock);
1531         list_del(&vif->list);
1532         spin_unlock_bh(&ar->list_lock);
1533
1534         ath6kl_cfg80211_vif_stop(vif, test_bit(WMI_READY, &ar->flag));
1535
1536         rtnl_lock();
1537         ath6kl_cfg80211_vif_cleanup(vif);
1538         rtnl_unlock();
1539
1540         return 0;
1541 }
1542
1543 static int ath6kl_cfg80211_change_iface(struct wiphy *wiphy,
1544                                         struct net_device *ndev,
1545                                         enum nl80211_iftype type, u32 *flags,
1546                                         struct vif_params *params)
1547 {
1548         struct ath6kl_vif *vif = netdev_priv(ndev);
1549         int i;
1550
1551         ath6kl_dbg(ATH6KL_DBG_WLAN_CFG, "%s: type %u\n", __func__, type);
1552
1553         /*
1554          * Don't bring up p2p on an interface which is not initialized
1555          * for p2p operation where fw does not have capability to switch
1556          * dynamically between non-p2p and p2p type interface.
1557          */
1558         if (!test_bit(ATH6KL_FW_CAPABILITY_STA_P2PDEV_DUPLEX,
1559                       vif->ar->fw_capabilities) &&
1560             (type == NL80211_IFTYPE_P2P_CLIENT ||
1561              type == NL80211_IFTYPE_P2P_GO)) {
1562                 if (vif->ar->vif_max == 1) {
1563                         if (vif->fw_vif_idx != 0)
1564                                 return -EINVAL;
1565                         else
1566                                 goto set_iface_type;
1567                 }
1568
1569                 for (i = vif->ar->max_norm_iface; i < vif->ar->vif_max; i++) {
1570                         if (i == vif->fw_vif_idx)
1571                                 break;
1572                 }
1573
1574                 if (i == vif->ar->vif_max) {
1575                         ath6kl_err("Invalid interface to bring up P2P\n");
1576                         return -EINVAL;
1577                 }
1578         }
1579
1580         /* need to clean up enhanced bmiss detection fw state */
1581         ath6kl_cfg80211_sta_bmiss_enhance(vif, false);
1582
1583 set_iface_type:
1584         switch (type) {
1585         case NL80211_IFTYPE_STATION:
1586         case NL80211_IFTYPE_P2P_CLIENT:
1587                 vif->next_mode = INFRA_NETWORK;
1588                 break;
1589         case NL80211_IFTYPE_ADHOC:
1590                 vif->next_mode = ADHOC_NETWORK;
1591                 break;
1592         case NL80211_IFTYPE_AP:
1593         case NL80211_IFTYPE_P2P_GO:
1594                 vif->next_mode = AP_NETWORK;
1595                 break;
1596         default:
1597                 ath6kl_err("invalid interface type %u\n", type);
1598                 return -EOPNOTSUPP;
1599         }
1600
1601         vif->wdev.iftype = type;
1602
1603         return 0;
1604 }
1605
1606 static int ath6kl_cfg80211_join_ibss(struct wiphy *wiphy,
1607                                      struct net_device *dev,
1608                                      struct cfg80211_ibss_params *ibss_param)
1609 {
1610         struct ath6kl *ar = ath6kl_priv(dev);
1611         struct ath6kl_vif *vif = netdev_priv(dev);
1612         int status;
1613
1614         if (!ath6kl_cfg80211_ready(vif))
1615                 return -EIO;
1616
1617         vif->ssid_len = ibss_param->ssid_len;
1618         memcpy(vif->ssid, ibss_param->ssid, vif->ssid_len);
1619
1620         if (ibss_param->chandef.chan)
1621                 vif->ch_hint = ibss_param->chandef.chan->center_freq;
1622
1623         if (ibss_param->channel_fixed) {
1624                 /*
1625                  * TODO: channel_fixed: The channel should be fixed, do not
1626                  * search for IBSSs to join on other channels. Target
1627                  * firmware does not support this feature, needs to be
1628                  * updated.
1629                  */
1630                 return -EOPNOTSUPP;
1631         }
1632
1633         memset(vif->req_bssid, 0, sizeof(vif->req_bssid));
1634         if (ibss_param->bssid && !is_broadcast_ether_addr(ibss_param->bssid))
1635                 memcpy(vif->req_bssid, ibss_param->bssid,
1636                        sizeof(vif->req_bssid));
1637
1638         ath6kl_set_wpa_version(vif, 0);
1639
1640         status = ath6kl_set_auth_type(vif, NL80211_AUTHTYPE_OPEN_SYSTEM);
1641         if (status)
1642                 return status;
1643
1644         if (ibss_param->privacy) {
1645                 ath6kl_set_cipher(vif, WLAN_CIPHER_SUITE_WEP40, true);
1646                 ath6kl_set_cipher(vif, WLAN_CIPHER_SUITE_WEP40, false);
1647         } else {
1648                 ath6kl_set_cipher(vif, 0, true);
1649                 ath6kl_set_cipher(vif, 0, false);
1650         }
1651
1652         vif->nw_type = vif->next_mode;
1653
1654         ath6kl_dbg(ATH6KL_DBG_WLAN_CFG,
1655                    "%s: connect called with authmode %d dot11 auth %d"
1656                    " PW crypto %d PW crypto len %d GRP crypto %d"
1657                    " GRP crypto len %d channel hint %u\n",
1658                    __func__,
1659                    vif->auth_mode, vif->dot11_auth_mode, vif->prwise_crypto,
1660                    vif->prwise_crypto_len, vif->grp_crypto,
1661                    vif->grp_crypto_len, vif->ch_hint);
1662
1663         status = ath6kl_wmi_connect_cmd(ar->wmi, vif->fw_vif_idx, vif->nw_type,
1664                                         vif->dot11_auth_mode, vif->auth_mode,
1665                                         vif->prwise_crypto,
1666                                         vif->prwise_crypto_len,
1667                                         vif->grp_crypto, vif->grp_crypto_len,
1668                                         vif->ssid_len, vif->ssid,
1669                                         vif->req_bssid, vif->ch_hint,
1670                                         ar->connect_ctrl_flags, SUBTYPE_NONE);
1671         set_bit(CONNECT_PEND, &vif->flags);
1672
1673         return 0;
1674 }
1675
1676 static int ath6kl_cfg80211_leave_ibss(struct wiphy *wiphy,
1677                                       struct net_device *dev)
1678 {
1679         struct ath6kl_vif *vif = netdev_priv(dev);
1680
1681         if (!ath6kl_cfg80211_ready(vif))
1682                 return -EIO;
1683
1684         ath6kl_disconnect(vif);
1685         memset(vif->ssid, 0, sizeof(vif->ssid));
1686         vif->ssid_len = 0;
1687
1688         return 0;
1689 }
1690
1691 static const u32 cipher_suites[] = {
1692         WLAN_CIPHER_SUITE_WEP40,
1693         WLAN_CIPHER_SUITE_WEP104,
1694         WLAN_CIPHER_SUITE_TKIP,
1695         WLAN_CIPHER_SUITE_CCMP,
1696         CCKM_KRK_CIPHER_SUITE,
1697         WLAN_CIPHER_SUITE_SMS4,
1698 };
1699
1700 static bool is_rate_legacy(s32 rate)
1701 {
1702         static const s32 legacy[] = { 1000, 2000, 5500, 11000,
1703                 6000, 9000, 12000, 18000, 24000,
1704                 36000, 48000, 54000
1705         };
1706         u8 i;
1707
1708         for (i = 0; i < ARRAY_SIZE(legacy); i++)
1709                 if (rate == legacy[i])
1710                         return true;
1711
1712         return false;
1713 }
1714
1715 static bool is_rate_ht20(s32 rate, u8 *mcs, bool *sgi)
1716 {
1717         static const s32 ht20[] = { 6500, 13000, 19500, 26000, 39000,
1718                 52000, 58500, 65000, 72200
1719         };
1720         u8 i;
1721
1722         for (i = 0; i < ARRAY_SIZE(ht20); i++) {
1723                 if (rate == ht20[i]) {
1724                         if (i == ARRAY_SIZE(ht20) - 1)
1725                                 /* last rate uses sgi */
1726                                 *sgi = true;
1727                         else
1728                                 *sgi = false;
1729
1730                         *mcs = i;
1731                         return true;
1732                 }
1733         }
1734         return false;
1735 }
1736
1737 static bool is_rate_ht40(s32 rate, u8 *mcs, bool *sgi)
1738 {
1739         static const s32 ht40[] = { 13500, 27000, 40500, 54000,
1740                 81000, 108000, 121500, 135000,
1741                 150000
1742         };
1743         u8 i;
1744
1745         for (i = 0; i < ARRAY_SIZE(ht40); i++) {
1746                 if (rate == ht40[i]) {
1747                         if (i == ARRAY_SIZE(ht40) - 1)
1748                                 /* last rate uses sgi */
1749                                 *sgi = true;
1750                         else
1751                                 *sgi = false;
1752
1753                         *mcs = i;
1754                         return true;
1755                 }
1756         }
1757
1758         return false;
1759 }
1760
1761 static int ath6kl_get_station(struct wiphy *wiphy, struct net_device *dev,
1762                               const u8 *mac, struct station_info *sinfo)
1763 {
1764         struct ath6kl *ar = ath6kl_priv(dev);
1765         struct ath6kl_vif *vif = netdev_priv(dev);
1766         long left;
1767         bool sgi;
1768         s32 rate;
1769         int ret;
1770         u8 mcs;
1771
1772         if (memcmp(mac, vif->bssid, ETH_ALEN) != 0)
1773                 return -ENOENT;
1774
1775         if (down_interruptible(&ar->sem))
1776                 return -EBUSY;
1777
1778         set_bit(STATS_UPDATE_PEND, &vif->flags);
1779
1780         ret = ath6kl_wmi_get_stats_cmd(ar->wmi, vif->fw_vif_idx);
1781
1782         if (ret != 0) {
1783                 up(&ar->sem);
1784                 return -EIO;
1785         }
1786
1787         left = wait_event_interruptible_timeout(ar->event_wq,
1788                                                 !test_bit(STATS_UPDATE_PEND,
1789                                                           &vif->flags),
1790                                                 WMI_TIMEOUT);
1791
1792         up(&ar->sem);
1793
1794         if (left == 0)
1795                 return -ETIMEDOUT;
1796         else if (left < 0)
1797                 return left;
1798
1799         if (vif->target_stats.rx_byte) {
1800                 sinfo->rx_bytes = vif->target_stats.rx_byte;
1801                 sinfo->filled |= STATION_INFO_RX_BYTES64;
1802                 sinfo->rx_packets = vif->target_stats.rx_pkt;
1803                 sinfo->filled |= STATION_INFO_RX_PACKETS;
1804         }
1805
1806         if (vif->target_stats.tx_byte) {
1807                 sinfo->tx_bytes = vif->target_stats.tx_byte;
1808                 sinfo->filled |= STATION_INFO_TX_BYTES64;
1809                 sinfo->tx_packets = vif->target_stats.tx_pkt;
1810                 sinfo->filled |= STATION_INFO_TX_PACKETS;
1811         }
1812
1813         sinfo->signal = vif->target_stats.cs_rssi;
1814         sinfo->filled |= STATION_INFO_SIGNAL;
1815
1816         rate = vif->target_stats.tx_ucast_rate;
1817
1818         if (is_rate_legacy(rate)) {
1819                 sinfo->txrate.legacy = rate / 100;
1820         } else if (is_rate_ht20(rate, &mcs, &sgi)) {
1821                 if (sgi) {
1822                         sinfo->txrate.flags |= RATE_INFO_FLAGS_SHORT_GI;
1823                         sinfo->txrate.mcs = mcs - 1;
1824                 } else {
1825                         sinfo->txrate.mcs = mcs;
1826                 }
1827
1828                 sinfo->txrate.flags |= RATE_INFO_FLAGS_MCS;
1829         } else if (is_rate_ht40(rate, &mcs, &sgi)) {
1830                 if (sgi) {
1831                         sinfo->txrate.flags |= RATE_INFO_FLAGS_SHORT_GI;
1832                         sinfo->txrate.mcs = mcs - 1;
1833                 } else {
1834                         sinfo->txrate.mcs = mcs;
1835                 }
1836
1837                 sinfo->txrate.flags |= RATE_INFO_FLAGS_40_MHZ_WIDTH;
1838                 sinfo->txrate.flags |= RATE_INFO_FLAGS_MCS;
1839         } else {
1840                 ath6kl_dbg(ATH6KL_DBG_WLAN_CFG,
1841                            "invalid rate from stats: %d\n", rate);
1842                 ath6kl_debug_war(ar, ATH6KL_WAR_INVALID_RATE);
1843                 return 0;
1844         }
1845
1846         sinfo->filled |= STATION_INFO_TX_BITRATE;
1847
1848         if (test_bit(CONNECTED, &vif->flags) &&
1849             test_bit(DTIM_PERIOD_AVAIL, &vif->flags) &&
1850             vif->nw_type == INFRA_NETWORK) {
1851                 sinfo->filled |= STATION_INFO_BSS_PARAM;
1852                 sinfo->bss_param.flags = 0;
1853                 sinfo->bss_param.dtim_period = vif->assoc_bss_dtim_period;
1854                 sinfo->bss_param.beacon_interval = vif->assoc_bss_beacon_int;
1855         }
1856
1857         return 0;
1858 }
1859
1860 static int ath6kl_set_pmksa(struct wiphy *wiphy, struct net_device *netdev,
1861                             struct cfg80211_pmksa *pmksa)
1862 {
1863         struct ath6kl *ar = ath6kl_priv(netdev);
1864         struct ath6kl_vif *vif = netdev_priv(netdev);
1865
1866         return ath6kl_wmi_setpmkid_cmd(ar->wmi, vif->fw_vif_idx, pmksa->bssid,
1867                                        pmksa->pmkid, true);
1868 }
1869
1870 static int ath6kl_del_pmksa(struct wiphy *wiphy, struct net_device *netdev,
1871                             struct cfg80211_pmksa *pmksa)
1872 {
1873         struct ath6kl *ar = ath6kl_priv(netdev);
1874         struct ath6kl_vif *vif = netdev_priv(netdev);
1875
1876         return ath6kl_wmi_setpmkid_cmd(ar->wmi, vif->fw_vif_idx, pmksa->bssid,
1877                                        pmksa->pmkid, false);
1878 }
1879
1880 static int ath6kl_flush_pmksa(struct wiphy *wiphy, struct net_device *netdev)
1881 {
1882         struct ath6kl *ar = ath6kl_priv(netdev);
1883         struct ath6kl_vif *vif = netdev_priv(netdev);
1884
1885         if (test_bit(CONNECTED, &vif->flags))
1886                 return ath6kl_wmi_setpmkid_cmd(ar->wmi, vif->fw_vif_idx,
1887                                                vif->bssid, NULL, false);
1888         return 0;
1889 }
1890
1891 static int ath6kl_wow_usr(struct ath6kl *ar, struct ath6kl_vif *vif,
1892                           struct cfg80211_wowlan *wow, u32 *filter)
1893 {
1894         int ret, pos;
1895         u8 mask[WOW_PATTERN_SIZE];
1896         u16 i;
1897
1898         /* Configure the patterns that we received from the user. */
1899         for (i = 0; i < wow->n_patterns; i++) {
1900                 /*
1901                  * Convert given nl80211 specific mask value to equivalent
1902                  * driver specific mask value and send it to the chip along
1903                  * with patterns. For example, If the mask value defined in
1904                  * struct cfg80211_wowlan is 0xA (equivalent binary is 1010),
1905                  * then equivalent driver specific mask value is
1906                  * "0xFF 0x00 0xFF 0x00".
1907                  */
1908                 memset(&mask, 0, sizeof(mask));
1909                 for (pos = 0; pos < wow->patterns[i].pattern_len; pos++) {
1910                         if (wow->patterns[i].mask[pos / 8] & (0x1 << (pos % 8)))
1911                                 mask[pos] = 0xFF;
1912                 }
1913                 /*
1914                  * Note: Pattern's offset is not passed as part of wowlan
1915                  * parameter from CFG layer. So it's always passed as ZERO
1916                  * to the firmware. It means, given WOW patterns are always
1917                  * matched from the first byte of received pkt in the firmware.
1918                  */
1919                 ret = ath6kl_wmi_add_wow_pattern_cmd(ar->wmi,
1920                                 vif->fw_vif_idx, WOW_LIST_ID,
1921                                 wow->patterns[i].pattern_len,
1922                                 0 /* pattern offset */,
1923                                 wow->patterns[i].pattern, mask);
1924                 if (ret)
1925                         return ret;
1926         }
1927
1928         if (wow->disconnect)
1929                 *filter |= WOW_FILTER_OPTION_NWK_DISASSOC;
1930
1931         if (wow->magic_pkt)
1932                 *filter |= WOW_FILTER_OPTION_MAGIC_PACKET;
1933
1934         if (wow->gtk_rekey_failure)
1935                 *filter |= WOW_FILTER_OPTION_GTK_ERROR;
1936
1937         if (wow->eap_identity_req)
1938                 *filter |= WOW_FILTER_OPTION_EAP_REQ;
1939
1940         if (wow->four_way_handshake)
1941                 *filter |= WOW_FILTER_OPTION_8021X_4WAYHS;
1942
1943         return 0;
1944 }
1945
1946 static int ath6kl_wow_ap(struct ath6kl *ar, struct ath6kl_vif *vif)
1947 {
1948         static const u8 unicst_pattern[] = { 0x00, 0x00, 0x00,
1949                 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
1950                 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
1951                 0x00, 0x08 };
1952         static const u8 unicst_mask[] = { 0x01, 0x00, 0x00,
1953                 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
1954                 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
1955                 0x00, 0x7f };
1956         u8 unicst_offset = 0;
1957         static const u8 arp_pattern[] = { 0x08, 0x06 };
1958         static const u8 arp_mask[] = { 0xff, 0xff };
1959         u8 arp_offset = 20;
1960         static const u8 discvr_pattern[] = { 0xe0, 0x00, 0x00, 0xf8 };
1961         static const u8 discvr_mask[] = { 0xf0, 0x00, 0x00, 0xf8 };
1962         u8 discvr_offset = 38;
1963         static const u8 dhcp_pattern[] = { 0xff, 0xff, 0xff, 0xff,
1964                 0xff, 0xff, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
1965                 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x08, 0x00,
1966                 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
1967                 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
1968                 0x00, 0x00, 0x00, 0x00, 0x00, 0x43 /* port 67 */ };
1969         static const u8 dhcp_mask[] = { 0xff, 0xff, 0xff, 0xff,
1970                 0xff, 0xff, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
1971                 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xff, 0xff,
1972                 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
1973                 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
1974                 0x00, 0x00, 0x00, 0x00, 0xff, 0xff /* port 67 */ };
1975         u8 dhcp_offset = 0;
1976         int ret;
1977
1978         /* Setup unicast IP, EAPOL-like and ARP pkt pattern */
1979         ret = ath6kl_wmi_add_wow_pattern_cmd(ar->wmi,
1980                         vif->fw_vif_idx, WOW_LIST_ID,
1981                         sizeof(unicst_pattern), unicst_offset,
1982                         unicst_pattern, unicst_mask);
1983         if (ret) {
1984                 ath6kl_err("failed to add WOW unicast IP pattern\n");
1985                 return ret;
1986         }
1987
1988         /* Setup all ARP pkt pattern */
1989         ret = ath6kl_wmi_add_wow_pattern_cmd(ar->wmi,
1990                         vif->fw_vif_idx, WOW_LIST_ID,
1991                         sizeof(arp_pattern), arp_offset,
1992                         arp_pattern, arp_mask);
1993         if (ret) {
1994                 ath6kl_err("failed to add WOW ARP pattern\n");
1995                 return ret;
1996         }
1997
1998         /*
1999          * Setup multicast pattern for mDNS 224.0.0.251,
2000          * SSDP 239.255.255.250 and LLMNR  224.0.0.252
2001          */
2002         ret = ath6kl_wmi_add_wow_pattern_cmd(ar->wmi,
2003                         vif->fw_vif_idx, WOW_LIST_ID,
2004                         sizeof(discvr_pattern), discvr_offset,
2005                         discvr_pattern, discvr_mask);
2006         if (ret) {
2007                 ath6kl_err("failed to add WOW mDNS/SSDP/LLMNR pattern\n");
2008                 return ret;
2009         }
2010
2011         /* Setup all DHCP broadcast pkt pattern */
2012         ret = ath6kl_wmi_add_wow_pattern_cmd(ar->wmi,
2013                         vif->fw_vif_idx, WOW_LIST_ID,
2014                         sizeof(dhcp_pattern), dhcp_offset,
2015                         dhcp_pattern, dhcp_mask);
2016         if (ret) {
2017                 ath6kl_err("failed to add WOW DHCP broadcast pattern\n");
2018                 return ret;
2019         }
2020
2021         return 0;
2022 }
2023
2024 static int ath6kl_wow_sta(struct ath6kl *ar, struct ath6kl_vif *vif)
2025 {
2026         struct net_device *ndev = vif->ndev;
2027         static const u8 discvr_pattern[] = { 0xe0, 0x00, 0x00, 0xf8 };
2028         static const u8 discvr_mask[] = { 0xf0, 0x00, 0x00, 0xf8 };
2029         u8 discvr_offset = 38;
2030         u8 mac_mask[ETH_ALEN];
2031         int ret;
2032
2033         /* Setup unicast pkt pattern */
2034         memset(mac_mask, 0xff, ETH_ALEN);
2035         ret = ath6kl_wmi_add_wow_pattern_cmd(ar->wmi,
2036                                 vif->fw_vif_idx, WOW_LIST_ID,
2037                                 ETH_ALEN, 0, ndev->dev_addr,
2038                                 mac_mask);
2039         if (ret) {
2040                 ath6kl_err("failed to add WOW unicast pattern\n");
2041                 return ret;
2042         }
2043
2044         /*
2045          * Setup multicast pattern for mDNS 224.0.0.251,
2046          * SSDP 239.255.255.250 and LLMNR 224.0.0.252
2047          */
2048         if ((ndev->flags & IFF_ALLMULTI) ||
2049             (ndev->flags & IFF_MULTICAST && netdev_mc_count(ndev) > 0)) {
2050                 ret = ath6kl_wmi_add_wow_pattern_cmd(ar->wmi,
2051                                 vif->fw_vif_idx, WOW_LIST_ID,
2052                                 sizeof(discvr_pattern), discvr_offset,
2053                                 discvr_pattern, discvr_mask);
2054                 if (ret) {
2055                         ath6kl_err("failed to add WOW mDNS/SSDP/LLMNR pattern\n");
2056                         return ret;
2057                 }
2058         }
2059
2060         return 0;
2061 }
2062
2063 static int is_hsleep_mode_procsed(struct ath6kl_vif *vif)
2064 {
2065         return test_bit(HOST_SLEEP_MODE_CMD_PROCESSED, &vif->flags);
2066 }
2067
2068 static bool is_ctrl_ep_empty(struct ath6kl *ar)
2069 {
2070         return !ar->tx_pending[ar->ctrl_ep];
2071 }
2072
2073 static int ath6kl_cfg80211_host_sleep(struct ath6kl *ar, struct ath6kl_vif *vif)
2074 {
2075         int ret, left;
2076
2077         clear_bit(HOST_SLEEP_MODE_CMD_PROCESSED, &vif->flags);
2078
2079         ret = ath6kl_wmi_set_host_sleep_mode_cmd(ar->wmi, vif->fw_vif_idx,
2080                                                  ATH6KL_HOST_MODE_ASLEEP);
2081         if (ret)
2082                 return ret;
2083
2084         left = wait_event_interruptible_timeout(ar->event_wq,
2085                                                 is_hsleep_mode_procsed(vif),
2086                                                 WMI_TIMEOUT);
2087         if (left == 0) {
2088                 ath6kl_warn("timeout, didn't get host sleep cmd processed event\n");
2089                 ret = -ETIMEDOUT;
2090         } else if (left < 0) {
2091                 ath6kl_warn("error while waiting for host sleep cmd processed event %d\n",
2092                             left);
2093                 ret = left;
2094         }
2095
2096         if (ar->tx_pending[ar->ctrl_ep]) {
2097                 left = wait_event_interruptible_timeout(ar->event_wq,
2098                                                         is_ctrl_ep_empty(ar),
2099                                                         WMI_TIMEOUT);
2100                 if (left == 0) {
2101                         ath6kl_warn("clear wmi ctrl data timeout\n");
2102                         ret = -ETIMEDOUT;
2103                 } else if (left < 0) {
2104                         ath6kl_warn("clear wmi ctrl data failed: %d\n", left);
2105                         ret = left;
2106                 }
2107         }
2108
2109         return ret;
2110 }
2111
2112 static int ath6kl_wow_suspend_vif(struct ath6kl_vif *vif,
2113                                   struct cfg80211_wowlan *wow, u32 *filter)
2114 {
2115         struct ath6kl *ar = vif->ar;
2116         struct in_device *in_dev;
2117         struct in_ifaddr *ifa;
2118         int ret;
2119         u16 i, bmiss_time;
2120         __be32 ips[MAX_IP_ADDRS];
2121         u8 index = 0;
2122
2123         if (!test_bit(NETDEV_MCAST_ALL_ON, &vif->flags) &&
2124             test_bit(ATH6KL_FW_CAPABILITY_WOW_MULTICAST_FILTER,
2125                      ar->fw_capabilities)) {
2126                 ret = ath6kl_wmi_mcast_filter_cmd(vif->ar->wmi,
2127                                                 vif->fw_vif_idx, false);
2128                 if (ret)
2129                         return ret;
2130         }
2131
2132         /* Clear existing WOW patterns */
2133         for (i = 0; i < WOW_MAX_FILTERS_PER_LIST; i++)
2134                 ath6kl_wmi_del_wow_pattern_cmd(ar->wmi, vif->fw_vif_idx,
2135                                                WOW_LIST_ID, i);
2136
2137         /*
2138          * Skip the default WOW pattern configuration
2139          * if the driver receives any WOW patterns from
2140          * the user.
2141          */
2142         if (wow)
2143                 ret = ath6kl_wow_usr(ar, vif, wow, filter);
2144         else if (vif->nw_type == AP_NETWORK)
2145                 ret = ath6kl_wow_ap(ar, vif);
2146         else
2147                 ret = ath6kl_wow_sta(ar, vif);
2148
2149         if (ret)
2150                 return ret;
2151
2152         netif_stop_queue(vif->ndev);
2153
2154         if (vif->nw_type != AP_NETWORK) {
2155                 ret = ath6kl_wmi_listeninterval_cmd(ar->wmi, vif->fw_vif_idx,
2156                                                     ATH6KL_MAX_WOW_LISTEN_INTL,
2157                                                     0);
2158                 if (ret)
2159                         return ret;
2160
2161                 /* Set listen interval x 15 times as bmiss time */
2162                 bmiss_time = ATH6KL_MAX_WOW_LISTEN_INTL * 15;
2163                 if (bmiss_time > ATH6KL_MAX_BMISS_TIME)
2164                         bmiss_time = ATH6KL_MAX_BMISS_TIME;
2165
2166                 ret = ath6kl_wmi_bmisstime_cmd(ar->wmi, vif->fw_vif_idx,
2167                                                bmiss_time, 0);
2168                 if (ret)
2169                         return ret;
2170
2171                 ret = ath6kl_wmi_scanparams_cmd(ar->wmi, vif->fw_vif_idx,
2172                                                 0xFFFF, 0, 0xFFFF, 0, 0, 0,
2173                                                 0, 0, 0, 0);
2174                 if (ret)
2175                         return ret;
2176         }
2177
2178         /* Setup own IP addr for ARP agent. */
2179         in_dev = __in_dev_get_rtnl(vif->ndev);
2180         if (!in_dev)
2181                 return 0;
2182
2183         ifa = in_dev->ifa_list;
2184         memset(&ips, 0, sizeof(ips));
2185
2186         /* Configure IP addr only if IP address count < MAX_IP_ADDRS */
2187         while (index < MAX_IP_ADDRS && ifa) {
2188                 ips[index] = ifa->ifa_local;
2189                 ifa = ifa->ifa_next;
2190                 index++;
2191         }
2192
2193         if (ifa) {
2194                 ath6kl_err("total IP addr count is exceeding fw limit\n");
2195                 return -EINVAL;
2196         }
2197
2198         ret = ath6kl_wmi_set_ip_cmd(ar->wmi, vif->fw_vif_idx, ips[0], ips[1]);
2199         if (ret) {
2200                 ath6kl_err("fail to setup ip for arp agent\n");
2201                 return ret;
2202         }
2203
2204         return ret;
2205 }
2206
2207 static int ath6kl_wow_suspend(struct ath6kl *ar, struct cfg80211_wowlan *wow)
2208 {
2209         struct ath6kl_vif *first_vif, *vif;
2210         int ret = 0;
2211         u32 filter = 0;
2212         bool connected = false;
2213
2214         /* enter / leave wow suspend on first vif always */
2215         first_vif = ath6kl_vif_first(ar);
2216         if (WARN_ON(unlikely(!first_vif)) ||
2217             !ath6kl_cfg80211_ready(first_vif))
2218                 return -EIO;
2219
2220         if (wow && (wow->n_patterns > WOW_MAX_FILTERS_PER_LIST))
2221                 return -EINVAL;
2222
2223         /* install filters for each connected vif */
2224         spin_lock_bh(&ar->list_lock);
2225         list_for_each_entry(vif, &ar->vif_list, list) {
2226                 if (!test_bit(CONNECTED, &vif->flags) ||
2227                     !ath6kl_cfg80211_ready(vif))
2228                         continue;
2229                 connected = true;
2230
2231                 ret = ath6kl_wow_suspend_vif(vif, wow, &filter);
2232                 if (ret)
2233                         break;
2234         }
2235         spin_unlock_bh(&ar->list_lock);
2236
2237         if (!connected)
2238                 return -ENOTCONN;
2239         else if (ret)
2240                 return ret;
2241
2242         ar->state = ATH6KL_STATE_SUSPENDING;
2243
2244         ret = ath6kl_wmi_set_wow_mode_cmd(ar->wmi, first_vif->fw_vif_idx,
2245                                           ATH6KL_WOW_MODE_ENABLE,
2246                                           filter,
2247                                           WOW_HOST_REQ_DELAY);
2248         if (ret)
2249                 return ret;
2250
2251         return ath6kl_cfg80211_host_sleep(ar, first_vif);
2252 }
2253
2254 static int ath6kl_wow_resume_vif(struct ath6kl_vif *vif)
2255 {
2256         struct ath6kl *ar = vif->ar;
2257         int ret;
2258
2259         if (vif->nw_type != AP_NETWORK) {
2260                 ret = ath6kl_wmi_scanparams_cmd(ar->wmi, vif->fw_vif_idx,
2261                                                 0, 0, 0, 0, 0, 0, 3, 0, 0, 0);
2262                 if (ret)
2263                         return ret;
2264
2265                 ret = ath6kl_wmi_listeninterval_cmd(ar->wmi, vif->fw_vif_idx,
2266                                                     vif->listen_intvl_t, 0);
2267                 if (ret)
2268                         return ret;
2269
2270                 ret = ath6kl_wmi_bmisstime_cmd(ar->wmi, vif->fw_vif_idx,
2271                                                vif->bmiss_time_t, 0);
2272                 if (ret)
2273                         return ret;
2274         }
2275
2276         if (!test_bit(NETDEV_MCAST_ALL_OFF, &vif->flags) &&
2277             test_bit(ATH6KL_FW_CAPABILITY_WOW_MULTICAST_FILTER,
2278                      ar->fw_capabilities)) {
2279                 ret = ath6kl_wmi_mcast_filter_cmd(vif->ar->wmi,
2280                                                   vif->fw_vif_idx, true);
2281                 if (ret)
2282                         return ret;
2283         }
2284
2285         netif_wake_queue(vif->ndev);
2286
2287         return 0;
2288 }
2289
2290 static int ath6kl_wow_resume(struct ath6kl *ar)
2291 {
2292         struct ath6kl_vif *vif;
2293         int ret;
2294
2295         vif = ath6kl_vif_first(ar);
2296         if (WARN_ON(unlikely(!vif)) ||
2297             !ath6kl_cfg80211_ready(vif))
2298                 return -EIO;
2299
2300         ar->state = ATH6KL_STATE_RESUMING;
2301
2302         ret = ath6kl_wmi_set_host_sleep_mode_cmd(ar->wmi, vif->fw_vif_idx,
2303                                                  ATH6KL_HOST_MODE_AWAKE);
2304         if (ret) {
2305                 ath6kl_warn("Failed to configure host sleep mode for wow resume: %d\n",
2306                             ret);
2307                 goto cleanup;
2308         }
2309
2310         spin_lock_bh(&ar->list_lock);
2311         list_for_each_entry(vif, &ar->vif_list, list) {
2312                 if (!test_bit(CONNECTED, &vif->flags) ||
2313                     !ath6kl_cfg80211_ready(vif))
2314                         continue;
2315                 ret = ath6kl_wow_resume_vif(vif);
2316                 if (ret)
2317                         break;
2318         }
2319         spin_unlock_bh(&ar->list_lock);
2320
2321         if (ret)
2322                 goto cleanup;
2323
2324         ar->state = ATH6KL_STATE_ON;
2325         return 0;
2326
2327 cleanup:
2328         ar->state = ATH6KL_STATE_WOW;
2329         return ret;
2330 }
2331
2332 static int ath6kl_cfg80211_deepsleep_suspend(struct ath6kl *ar)
2333 {
2334         struct ath6kl_vif *vif;
2335         int ret;
2336
2337         vif = ath6kl_vif_first(ar);
2338         if (!vif)
2339                 return -EIO;
2340
2341         if (!test_bit(WMI_READY, &ar->flag)) {
2342                 ath6kl_err("deepsleep failed as wmi is not ready\n");
2343                 return -EIO;
2344         }
2345
2346         ath6kl_cfg80211_stop_all(ar);
2347
2348         /* Save the current power mode before enabling power save */
2349         ar->wmi->saved_pwr_mode = ar->wmi->pwr_mode;
2350
2351         ret = ath6kl_wmi_powermode_cmd(ar->wmi, 0, REC_POWER);
2352         if (ret)
2353                 return ret;
2354
2355         /* Disable WOW mode */
2356         ret = ath6kl_wmi_set_wow_mode_cmd(ar->wmi, vif->fw_vif_idx,
2357                                           ATH6KL_WOW_MODE_DISABLE,
2358                                           0, 0);
2359         if (ret)
2360                 return ret;
2361
2362         /* Flush all non control pkts in TX path */
2363         ath6kl_tx_data_cleanup(ar);
2364
2365         ret = ath6kl_cfg80211_host_sleep(ar, vif);
2366         if (ret)
2367                 return ret;
2368
2369         return 0;
2370 }
2371
2372 static int ath6kl_cfg80211_deepsleep_resume(struct ath6kl *ar)
2373 {
2374         struct ath6kl_vif *vif;
2375         int ret;
2376
2377         vif = ath6kl_vif_first(ar);
2378
2379         if (!vif)
2380                 return -EIO;
2381
2382         if (ar->wmi->pwr_mode != ar->wmi->saved_pwr_mode) {
2383                 ret = ath6kl_wmi_powermode_cmd(ar->wmi, 0,
2384                                                ar->wmi->saved_pwr_mode);
2385                 if (ret)
2386                         return ret;
2387         }
2388
2389         ret = ath6kl_wmi_set_host_sleep_mode_cmd(ar->wmi, vif->fw_vif_idx,
2390                                                  ATH6KL_HOST_MODE_AWAKE);
2391         if (ret)
2392                 return ret;
2393
2394         ar->state = ATH6KL_STATE_ON;
2395
2396         /* Reset scan parameter to default values */
2397         ret = ath6kl_wmi_scanparams_cmd(ar->wmi, vif->fw_vif_idx,
2398                                         0, 0, 0, 0, 0, 0, 3, 0, 0, 0);
2399         if (ret)
2400                 return ret;
2401
2402         return 0;
2403 }
2404
2405 int ath6kl_cfg80211_suspend(struct ath6kl *ar,
2406                             enum ath6kl_cfg_suspend_mode mode,
2407                             struct cfg80211_wowlan *wow)
2408 {
2409         struct ath6kl_vif *vif;
2410         enum ath6kl_state prev_state;
2411         int ret;
2412
2413         switch (mode) {
2414         case ATH6KL_CFG_SUSPEND_WOW:
2415
2416                 ath6kl_dbg(ATH6KL_DBG_SUSPEND, "wow mode suspend\n");
2417
2418                 /* Flush all non control pkts in TX path */
2419                 ath6kl_tx_data_cleanup(ar);
2420
2421                 prev_state = ar->state;
2422
2423                 ret = ath6kl_wow_suspend(ar, wow);
2424                 if (ret) {
2425                         ar->state = prev_state;
2426                         return ret;
2427                 }
2428
2429                 ar->state = ATH6KL_STATE_WOW;
2430                 break;
2431
2432         case ATH6KL_CFG_SUSPEND_DEEPSLEEP:
2433
2434                 ath6kl_dbg(ATH6KL_DBG_SUSPEND, "deep sleep suspend\n");
2435
2436                 ret = ath6kl_cfg80211_deepsleep_suspend(ar);
2437                 if (ret) {
2438                         ath6kl_err("deepsleep suspend failed: %d\n", ret);
2439                         return ret;
2440                 }
2441
2442                 ar->state = ATH6KL_STATE_DEEPSLEEP;
2443
2444                 break;
2445
2446         case ATH6KL_CFG_SUSPEND_CUTPOWER:
2447
2448                 ath6kl_cfg80211_stop_all(ar);
2449
2450                 if (ar->state == ATH6KL_STATE_OFF) {
2451                         ath6kl_dbg(ATH6KL_DBG_SUSPEND,
2452                                    "suspend hw off, no action for cutpower\n");
2453                         break;
2454                 }
2455
2456                 ath6kl_dbg(ATH6KL_DBG_SUSPEND, "suspend cutting power\n");
2457
2458                 ret = ath6kl_init_hw_stop(ar);
2459                 if (ret) {
2460                         ath6kl_warn("failed to stop hw during suspend: %d\n",
2461                                     ret);
2462                 }
2463
2464                 ar->state = ATH6KL_STATE_CUTPOWER;
2465
2466                 break;
2467
2468         default:
2469                 break;
2470         }
2471
2472         list_for_each_entry(vif, &ar->vif_list, list)
2473                 ath6kl_cfg80211_scan_complete_event(vif, true);
2474
2475         return 0;
2476 }
2477 EXPORT_SYMBOL(ath6kl_cfg80211_suspend);
2478
2479 int ath6kl_cfg80211_resume(struct ath6kl *ar)
2480 {
2481         int ret;
2482
2483         switch (ar->state) {
2484         case  ATH6KL_STATE_WOW:
2485                 ath6kl_dbg(ATH6KL_DBG_SUSPEND, "wow mode resume\n");
2486
2487                 ret = ath6kl_wow_resume(ar);
2488                 if (ret) {
2489                         ath6kl_warn("wow mode resume failed: %d\n", ret);
2490                         return ret;
2491                 }
2492
2493                 break;
2494
2495         case ATH6KL_STATE_DEEPSLEEP:
2496                 ath6kl_dbg(ATH6KL_DBG_SUSPEND, "deep sleep resume\n");
2497
2498                 ret = ath6kl_cfg80211_deepsleep_resume(ar);
2499                 if (ret) {
2500                         ath6kl_warn("deep sleep resume failed: %d\n", ret);
2501                         return ret;
2502                 }
2503                 break;
2504
2505         case ATH6KL_STATE_CUTPOWER:
2506                 ath6kl_dbg(ATH6KL_DBG_SUSPEND, "resume restoring power\n");
2507
2508                 ret = ath6kl_init_hw_start(ar);
2509                 if (ret) {
2510                         ath6kl_warn("Failed to boot hw in resume: %d\n", ret);
2511                         return ret;
2512                 }
2513                 break;
2514
2515         default:
2516                 break;
2517         }
2518
2519         return 0;
2520 }
2521 EXPORT_SYMBOL(ath6kl_cfg80211_resume);
2522
2523 #ifdef CONFIG_PM
2524
2525 /* hif layer decides what suspend mode to use */
2526 static int __ath6kl_cfg80211_suspend(struct wiphy *wiphy,
2527                                  struct cfg80211_wowlan *wow)
2528 {
2529         struct ath6kl *ar = wiphy_priv(wiphy);
2530
2531         ath6kl_recovery_suspend(ar);
2532
2533         return ath6kl_hif_suspend(ar, wow);
2534 }
2535
2536 static int __ath6kl_cfg80211_resume(struct wiphy *wiphy)
2537 {
2538         struct ath6kl *ar = wiphy_priv(wiphy);
2539         int err;
2540
2541         err = ath6kl_hif_resume(ar);
2542         if (err)
2543                 return err;
2544
2545         ath6kl_recovery_resume(ar);
2546
2547         return 0;
2548 }
2549
2550 /*
2551  * FIXME: WOW suspend mode is selected if the host sdio controller supports
2552  * both sdio irq wake up and keep power. The target pulls sdio data line to
2553  * wake up the host when WOW pattern matches. This causes sdio irq handler
2554  * is being called in the host side which internally hits ath6kl's RX path.
2555  *
2556  * Since sdio interrupt is not disabled, RX path executes even before
2557  * the host executes the actual resume operation from PM module.
2558  *
2559  * In the current scenario, WOW resume should happen before start processing
2560  * any data from the target. So It's required to perform WOW resume in RX path.
2561  * Ideally we should perform WOW resume only in the actual platform
2562  * resume path. This area needs bit rework to avoid WOW resume in RX path.
2563  *
2564  * ath6kl_check_wow_status() is called from ath6kl_rx().
2565  */
2566 void ath6kl_check_wow_status(struct ath6kl *ar)
2567 {
2568         if (ar->state == ATH6KL_STATE_SUSPENDING)
2569                 return;
2570
2571         if (ar->state == ATH6KL_STATE_WOW)
2572                 ath6kl_cfg80211_resume(ar);
2573 }
2574
2575 #else
2576
2577 void ath6kl_check_wow_status(struct ath6kl *ar)
2578 {
2579 }
2580 #endif
2581
2582 static int ath6kl_set_htcap(struct ath6kl_vif *vif, enum ieee80211_band band,
2583                             bool ht_enable)
2584 {
2585         struct ath6kl_htcap *htcap = &vif->htcap[band];
2586
2587         if (htcap->ht_enable == ht_enable)
2588                 return 0;
2589
2590         if (ht_enable) {
2591                 /* Set default ht capabilities */
2592                 htcap->ht_enable = true;
2593                 htcap->cap_info = (band == IEEE80211_BAND_2GHZ) ?
2594                                    ath6kl_g_htcap : ath6kl_a_htcap;
2595                 htcap->ampdu_factor = IEEE80211_HT_MAX_AMPDU_16K;
2596         } else /* Disable ht */
2597                 memset(htcap, 0, sizeof(*htcap));
2598
2599         return ath6kl_wmi_set_htcap_cmd(vif->ar->wmi, vif->fw_vif_idx,
2600                                         band, htcap);
2601 }
2602
2603 static int ath6kl_restore_htcap(struct ath6kl_vif *vif)
2604 {
2605         struct wiphy *wiphy = vif->ar->wiphy;
2606         int band, ret = 0;
2607
2608         for (band = 0; band < IEEE80211_NUM_BANDS; band++) {
2609                 if (!wiphy->bands[band])
2610                         continue;
2611
2612                 ret = ath6kl_set_htcap(vif, band,
2613                                 wiphy->bands[band]->ht_cap.ht_supported);
2614                 if (ret)
2615                         return ret;
2616         }
2617
2618         return ret;
2619 }
2620
2621 static bool ath6kl_is_p2p_ie(const u8 *pos)
2622 {
2623         return pos[0] == WLAN_EID_VENDOR_SPECIFIC && pos[1] >= 4 &&
2624                 pos[2] == 0x50 && pos[3] == 0x6f &&
2625                 pos[4] == 0x9a && pos[5] == 0x09;
2626 }
2627
2628 static int ath6kl_set_ap_probe_resp_ies(struct ath6kl_vif *vif,
2629                                         const u8 *ies, size_t ies_len)
2630 {
2631         struct ath6kl *ar = vif->ar;
2632         const u8 *pos;
2633         u8 *buf = NULL;
2634         size_t len = 0;
2635         int ret;
2636
2637         /*
2638          * Filter out P2P IE(s) since they will be included depending on
2639          * the Probe Request frame in ath6kl_send_go_probe_resp().
2640          */
2641
2642         if (ies && ies_len) {
2643                 buf = kmalloc(ies_len, GFP_KERNEL);
2644                 if (buf == NULL)
2645                         return -ENOMEM;
2646                 pos = ies;
2647                 while (pos + 1 < ies + ies_len) {
2648                         if (pos + 2 + pos[1] > ies + ies_len)
2649                                 break;
2650                         if (!ath6kl_is_p2p_ie(pos)) {
2651                                 memcpy(buf + len, pos, 2 + pos[1]);
2652                                 len += 2 + pos[1];
2653                         }
2654                         pos += 2 + pos[1];
2655                 }
2656         }
2657
2658         ret = ath6kl_wmi_set_appie_cmd(ar->wmi, vif->fw_vif_idx,
2659                                        WMI_FRAME_PROBE_RESP, buf, len);
2660         kfree(buf);
2661         return ret;
2662 }
2663
2664 static int ath6kl_set_ies(struct ath6kl_vif *vif,
2665                           struct cfg80211_beacon_data *info)
2666 {
2667         struct ath6kl *ar = vif->ar;
2668         int res;
2669
2670         /* this also clears IE in fw if it's not set */
2671         res = ath6kl_wmi_set_appie_cmd(ar->wmi, vif->fw_vif_idx,
2672                                        WMI_FRAME_BEACON,
2673                                        info->beacon_ies,
2674                                        info->beacon_ies_len);
2675         if (res)
2676                 return res;
2677
2678         /* this also clears IE in fw if it's not set */
2679         res = ath6kl_set_ap_probe_resp_ies(vif, info->proberesp_ies,
2680                                            info->proberesp_ies_len);
2681         if (res)
2682                 return res;
2683
2684         /* this also clears IE in fw if it's not set */
2685         res = ath6kl_wmi_set_appie_cmd(ar->wmi, vif->fw_vif_idx,
2686                                        WMI_FRAME_ASSOC_RESP,
2687                                        info->assocresp_ies,
2688                                        info->assocresp_ies_len);
2689         if (res)
2690                 return res;
2691
2692         return 0;
2693 }
2694
2695 static int ath6kl_get_rsn_capab(struct cfg80211_beacon_data *beacon,
2696                                 u8 *rsn_capab)
2697 {
2698         const u8 *rsn_ie;
2699         size_t rsn_ie_len;
2700         u16 cnt;
2701
2702         if (!beacon->tail)
2703                 return -EINVAL;
2704
2705         rsn_ie = cfg80211_find_ie(WLAN_EID_RSN, beacon->tail, beacon->tail_len);
2706         if (!rsn_ie)
2707                 return -EINVAL;
2708
2709         rsn_ie_len = *(rsn_ie + 1);
2710         /* skip element id and length */
2711         rsn_ie += 2;
2712
2713         /* skip version */
2714         if (rsn_ie_len < 2)
2715                 return -EINVAL;
2716         rsn_ie +=  2;
2717         rsn_ie_len -= 2;
2718
2719         /* skip group cipher suite */
2720         if (rsn_ie_len < 4)
2721                 return 0;
2722         rsn_ie +=  4;
2723         rsn_ie_len -= 4;
2724
2725         /* skip pairwise cipher suite */
2726         if (rsn_ie_len < 2)
2727                 return 0;
2728         cnt = get_unaligned_le16(rsn_ie);
2729         rsn_ie += (2 + cnt * 4);
2730         rsn_ie_len -= (2 + cnt * 4);
2731
2732         /* skip akm suite */
2733         if (rsn_ie_len < 2)
2734                 return 0;
2735         cnt = get_unaligned_le16(rsn_ie);
2736         rsn_ie += (2 + cnt * 4);
2737         rsn_ie_len -= (2 + cnt * 4);
2738
2739         if (rsn_ie_len < 2)
2740                 return 0;
2741
2742         memcpy(rsn_capab, rsn_ie, 2);
2743
2744         return 0;
2745 }
2746
2747 static int ath6kl_start_ap(struct wiphy *wiphy, struct net_device *dev,
2748                            struct cfg80211_ap_settings *info)
2749 {
2750         struct ath6kl *ar = ath6kl_priv(dev);
2751         struct ath6kl_vif *vif = netdev_priv(dev);
2752         struct ieee80211_mgmt *mgmt;
2753         bool hidden = false;
2754         u8 *ies;
2755         int ies_len;
2756         struct wmi_connect_cmd p;
2757         int res;
2758         int i, ret;
2759         u16 rsn_capab = 0;
2760         int inactivity_timeout = 0;
2761
2762         ath6kl_dbg(ATH6KL_DBG_WLAN_CFG, "%s:\n", __func__);
2763
2764         if (!ath6kl_cfg80211_ready(vif))
2765                 return -EIO;
2766
2767         if (vif->next_mode != AP_NETWORK)
2768                 return -EOPNOTSUPP;
2769
2770         res = ath6kl_set_ies(vif, &info->beacon);
2771
2772         ar->ap_mode_bkey.valid = false;
2773
2774         ret = ath6kl_wmi_ap_set_beacon_intvl_cmd(ar->wmi, vif->fw_vif_idx,
2775                                                  info->beacon_interval);
2776
2777         if (ret)
2778                 ath6kl_warn("Failed to set beacon interval: %d\n", ret);
2779
2780         ret = ath6kl_wmi_ap_set_dtim_cmd(ar->wmi, vif->fw_vif_idx,
2781                                          info->dtim_period);
2782
2783         /* ignore error, just print a warning and continue normally */
2784         if (ret)
2785                 ath6kl_warn("Failed to set dtim_period in beacon: %d\n", ret);
2786
2787         if (info->beacon.head == NULL)
2788                 return -EINVAL;
2789         mgmt = (struct ieee80211_mgmt *) info->beacon.head;
2790         ies = mgmt->u.beacon.variable;
2791         if (ies > info->beacon.head + info->beacon.head_len)
2792                 return -EINVAL;
2793         ies_len = info->beacon.head + info->beacon.head_len - ies;
2794
2795         if (info->ssid == NULL)
2796                 return -EINVAL;
2797         memcpy(vif->ssid, info->ssid, info->ssid_len);
2798         vif->ssid_len = info->ssid_len;
2799         if (info->hidden_ssid != NL80211_HIDDEN_SSID_NOT_IN_USE)
2800                 hidden = true;
2801
2802         res = ath6kl_wmi_ap_hidden_ssid(ar->wmi, vif->fw_vif_idx, hidden);
2803         if (res)
2804                 return res;
2805
2806         ret = ath6kl_set_auth_type(vif, info->auth_type);
2807         if (ret)
2808                 return ret;
2809
2810         memset(&p, 0, sizeof(p));
2811
2812         for (i = 0; i < info->crypto.n_akm_suites; i++) {
2813                 switch (info->crypto.akm_suites[i]) {
2814                 case WLAN_AKM_SUITE_8021X:
2815                         if (info->crypto.wpa_versions & NL80211_WPA_VERSION_1)
2816                                 p.auth_mode |= WPA_AUTH;
2817                         if (info->crypto.wpa_versions & NL80211_WPA_VERSION_2)
2818                                 p.auth_mode |= WPA2_AUTH;
2819                         break;
2820                 case WLAN_AKM_SUITE_PSK:
2821                         if (info->crypto.wpa_versions & NL80211_WPA_VERSION_1)
2822                                 p.auth_mode |= WPA_PSK_AUTH;
2823                         if (info->crypto.wpa_versions & NL80211_WPA_VERSION_2)
2824                                 p.auth_mode |= WPA2_PSK_AUTH;
2825                         break;
2826                 }
2827         }
2828         if (p.auth_mode == 0)
2829                 p.auth_mode = NONE_AUTH;
2830         vif->auth_mode = p.auth_mode;
2831
2832         for (i = 0; i < info->crypto.n_ciphers_pairwise; i++) {
2833                 switch (info->crypto.ciphers_pairwise[i]) {
2834                 case WLAN_CIPHER_SUITE_WEP40:
2835                 case WLAN_CIPHER_SUITE_WEP104:
2836                         p.prwise_crypto_type |= WEP_CRYPT;
2837                         break;
2838                 case WLAN_CIPHER_SUITE_TKIP:
2839                         p.prwise_crypto_type |= TKIP_CRYPT;
2840                         break;
2841                 case WLAN_CIPHER_SUITE_CCMP:
2842                         p.prwise_crypto_type |= AES_CRYPT;
2843                         break;
2844                 case WLAN_CIPHER_SUITE_SMS4:
2845                         p.prwise_crypto_type |= WAPI_CRYPT;
2846                         break;
2847                 }
2848         }
2849         if (p.prwise_crypto_type == 0) {
2850                 p.prwise_crypto_type = NONE_CRYPT;
2851                 ath6kl_set_cipher(vif, 0, true);
2852         } else if (info->crypto.n_ciphers_pairwise == 1) {
2853                 ath6kl_set_cipher(vif, info->crypto.ciphers_pairwise[0], true);
2854         }
2855
2856         switch (info->crypto.cipher_group) {
2857         case WLAN_CIPHER_SUITE_WEP40:
2858         case WLAN_CIPHER_SUITE_WEP104:
2859                 p.grp_crypto_type = WEP_CRYPT;
2860                 break;
2861         case WLAN_CIPHER_SUITE_TKIP:
2862                 p.grp_crypto_type = TKIP_CRYPT;
2863                 break;
2864         case WLAN_CIPHER_SUITE_CCMP:
2865                 p.grp_crypto_type = AES_CRYPT;
2866                 break;
2867         case WLAN_CIPHER_SUITE_SMS4:
2868                 p.grp_crypto_type = WAPI_CRYPT;
2869                 break;
2870         default:
2871                 p.grp_crypto_type = NONE_CRYPT;
2872                 break;
2873         }
2874         ath6kl_set_cipher(vif, info->crypto.cipher_group, false);
2875
2876         p.nw_type = AP_NETWORK;
2877         vif->nw_type = vif->next_mode;
2878
2879         p.ssid_len = vif->ssid_len;
2880         memcpy(p.ssid, vif->ssid, vif->ssid_len);
2881         p.dot11_auth_mode = vif->dot11_auth_mode;
2882         p.ch = cpu_to_le16(info->chandef.chan->center_freq);
2883
2884         /* Enable uAPSD support by default */
2885         res = ath6kl_wmi_ap_set_apsd(ar->wmi, vif->fw_vif_idx, true);
2886         if (res < 0)
2887                 return res;
2888
2889         if (vif->wdev.iftype == NL80211_IFTYPE_P2P_GO) {
2890                 p.nw_subtype = SUBTYPE_P2PGO;
2891         } else {
2892                 /*
2893                  * Due to firmware limitation, it is not possible to
2894                  * do P2P mgmt operations in AP mode
2895                  */
2896                 p.nw_subtype = SUBTYPE_NONE;
2897         }
2898
2899         if (info->inactivity_timeout) {
2900                 inactivity_timeout = info->inactivity_timeout;
2901
2902                 if (test_bit(ATH6KL_FW_CAPABILITY_AP_INACTIVITY_MINS,
2903                              ar->fw_capabilities))
2904                         inactivity_timeout = DIV_ROUND_UP(inactivity_timeout,
2905                                                           60);
2906
2907                 res = ath6kl_wmi_set_inact_period(ar->wmi, vif->fw_vif_idx,
2908                                                   inactivity_timeout);
2909                 if (res < 0)
2910                         return res;
2911         }
2912
2913         if (ath6kl_set_htcap(vif, info->chandef.chan->band,
2914                              cfg80211_get_chandef_type(&info->chandef)
2915                                         != NL80211_CHAN_NO_HT))
2916                 return -EIO;
2917
2918         /*
2919          * Get the PTKSA replay counter in the RSN IE. Supplicant
2920          * will use the RSN IE in M3 message and firmware has to
2921          * advertise the same in beacon/probe response. Send
2922          * the complete RSN IE capability field to firmware
2923          */
2924         if (!ath6kl_get_rsn_capab(&info->beacon, (u8 *) &rsn_capab) &&
2925             test_bit(ATH6KL_FW_CAPABILITY_RSN_CAP_OVERRIDE,
2926                      ar->fw_capabilities)) {
2927                 res = ath6kl_wmi_set_ie_cmd(ar->wmi, vif->fw_vif_idx,
2928                                             WLAN_EID_RSN, WMI_RSN_IE_CAPB,
2929                                             (const u8 *) &rsn_capab,
2930                                             sizeof(rsn_capab));
2931                 vif->rsn_capab = rsn_capab;
2932                 if (res < 0)
2933                         return res;
2934         }
2935
2936         memcpy(&vif->profile, &p, sizeof(p));
2937         res = ath6kl_wmi_ap_profile_commit(ar->wmi, vif->fw_vif_idx, &p);
2938         if (res < 0)
2939                 return res;
2940
2941         return 0;
2942 }
2943
2944 static int ath6kl_change_beacon(struct wiphy *wiphy, struct net_device *dev,
2945                                 struct cfg80211_beacon_data *beacon)
2946 {
2947         struct ath6kl_vif *vif = netdev_priv(dev);
2948
2949         if (!ath6kl_cfg80211_ready(vif))
2950                 return -EIO;
2951
2952         if (vif->next_mode != AP_NETWORK)
2953                 return -EOPNOTSUPP;
2954
2955         return ath6kl_set_ies(vif, beacon);
2956 }
2957
2958 static int ath6kl_stop_ap(struct wiphy *wiphy, struct net_device *dev)
2959 {
2960         struct ath6kl *ar = ath6kl_priv(dev);
2961         struct ath6kl_vif *vif = netdev_priv(dev);
2962
2963         if (vif->nw_type != AP_NETWORK)
2964                 return -EOPNOTSUPP;
2965         if (!test_bit(CONNECTED, &vif->flags))
2966                 return -ENOTCONN;
2967
2968         ath6kl_wmi_disconnect_cmd(ar->wmi, vif->fw_vif_idx);
2969         clear_bit(CONNECTED, &vif->flags);
2970
2971         /* Restore ht setting in firmware */
2972         return ath6kl_restore_htcap(vif);
2973 }
2974
2975 static const u8 bcast_addr[ETH_ALEN] = { 0xff, 0xff, 0xff, 0xff, 0xff, 0xff };
2976
2977 static int ath6kl_del_station(struct wiphy *wiphy, struct net_device *dev,
2978                               const u8 *mac)
2979 {
2980         struct ath6kl *ar = ath6kl_priv(dev);
2981         struct ath6kl_vif *vif = netdev_priv(dev);
2982         const u8 *addr = mac ? mac : bcast_addr;
2983
2984         return ath6kl_wmi_ap_set_mlme(ar->wmi, vif->fw_vif_idx, WMI_AP_DEAUTH,
2985                                       addr, WLAN_REASON_PREV_AUTH_NOT_VALID);
2986 }
2987
2988 static int ath6kl_change_station(struct wiphy *wiphy, struct net_device *dev,
2989                                  const u8 *mac,
2990                                  struct station_parameters *params)
2991 {
2992         struct ath6kl *ar = ath6kl_priv(dev);
2993         struct ath6kl_vif *vif = netdev_priv(dev);
2994         int err;
2995
2996         if (vif->nw_type != AP_NETWORK)
2997                 return -EOPNOTSUPP;
2998
2999         err = cfg80211_check_station_change(wiphy, params,
3000                                             CFG80211_STA_AP_MLME_CLIENT);
3001         if (err)
3002                 return err;
3003
3004         if (params->sta_flags_set & BIT(NL80211_STA_FLAG_AUTHORIZED))
3005                 return ath6kl_wmi_ap_set_mlme(ar->wmi, vif->fw_vif_idx,
3006                                               WMI_AP_MLME_AUTHORIZE, mac, 0);
3007         return ath6kl_wmi_ap_set_mlme(ar->wmi, vif->fw_vif_idx,
3008                                       WMI_AP_MLME_UNAUTHORIZE, mac, 0);
3009 }
3010
3011 static int ath6kl_remain_on_channel(struct wiphy *wiphy,
3012                                     struct wireless_dev *wdev,
3013                                     struct ieee80211_channel *chan,
3014                                     unsigned int duration,
3015                                     u64 *cookie)
3016 {
3017         struct ath6kl_vif *vif = ath6kl_vif_from_wdev(wdev);
3018         struct ath6kl *ar = ath6kl_priv(vif->ndev);
3019         u32 id;
3020
3021         /* TODO: if already pending or ongoing remain-on-channel,
3022          * return -EBUSY */
3023         id = ++vif->last_roc_id;
3024         if (id == 0) {
3025                 /* Do not use 0 as the cookie value */
3026                 id = ++vif->last_roc_id;
3027         }
3028         *cookie = id;
3029
3030         return ath6kl_wmi_remain_on_chnl_cmd(ar->wmi, vif->fw_vif_idx,
3031                                              chan->center_freq, duration);
3032 }
3033
3034 static int ath6kl_cancel_remain_on_channel(struct wiphy *wiphy,
3035                                            struct wireless_dev *wdev,
3036                                            u64 cookie)
3037 {
3038         struct ath6kl_vif *vif = ath6kl_vif_from_wdev(wdev);
3039         struct ath6kl *ar = ath6kl_priv(vif->ndev);
3040
3041         if (cookie != vif->last_roc_id)
3042                 return -ENOENT;
3043         vif->last_cancel_roc_id = cookie;
3044
3045         return ath6kl_wmi_cancel_remain_on_chnl_cmd(ar->wmi, vif->fw_vif_idx);
3046 }
3047
3048 static int ath6kl_send_go_probe_resp(struct ath6kl_vif *vif,
3049                                      const u8 *buf, size_t len,
3050                                      unsigned int freq)
3051 {
3052         struct ath6kl *ar = vif->ar;
3053         const u8 *pos;
3054         u8 *p2p;
3055         int p2p_len;
3056         int ret;
3057         const struct ieee80211_mgmt *mgmt;
3058
3059         mgmt = (const struct ieee80211_mgmt *) buf;
3060
3061         /* Include P2P IE(s) from the frame generated in user space. */
3062
3063         p2p = kmalloc(len, GFP_KERNEL);
3064         if (p2p == NULL)
3065                 return -ENOMEM;
3066         p2p_len = 0;
3067
3068         pos = mgmt->u.probe_resp.variable;
3069         while (pos + 1 < buf + len) {
3070                 if (pos + 2 + pos[1] > buf + len)
3071                         break;
3072                 if (ath6kl_is_p2p_ie(pos)) {
3073                         memcpy(p2p + p2p_len, pos, 2 + pos[1]);
3074                         p2p_len += 2 + pos[1];
3075                 }
3076                 pos += 2 + pos[1];
3077         }
3078
3079         ret = ath6kl_wmi_send_probe_response_cmd(ar->wmi, vif->fw_vif_idx, freq,
3080                                                  mgmt->da, p2p, p2p_len);
3081         kfree(p2p);
3082         return ret;
3083 }
3084
3085 static bool ath6kl_mgmt_powersave_ap(struct ath6kl_vif *vif,
3086                                      u32 id,
3087                                      u32 freq,
3088                                      u32 wait,
3089                                      const u8 *buf,
3090                                      size_t len,
3091                                      bool *more_data,
3092                                      bool no_cck)
3093 {
3094         struct ieee80211_mgmt *mgmt;
3095         struct ath6kl_sta *conn;
3096         bool is_psq_empty = false;
3097         struct ath6kl_mgmt_buff *mgmt_buf;
3098         size_t mgmt_buf_size;
3099         struct ath6kl *ar = vif->ar;
3100
3101         mgmt = (struct ieee80211_mgmt *) buf;
3102         if (is_multicast_ether_addr(mgmt->da))
3103                 return false;
3104
3105         conn = ath6kl_find_sta(vif, mgmt->da);
3106         if (!conn)
3107                 return false;
3108
3109         if (conn->sta_flags & STA_PS_SLEEP) {
3110                 if (!(conn->sta_flags & STA_PS_POLLED)) {
3111                         /* Queue the frames if the STA is sleeping */
3112                         mgmt_buf_size = len + sizeof(struct ath6kl_mgmt_buff);
3113                         mgmt_buf = kmalloc(mgmt_buf_size, GFP_KERNEL);
3114                         if (!mgmt_buf)
3115                                 return false;
3116
3117                         INIT_LIST_HEAD(&mgmt_buf->list);
3118                         mgmt_buf->id = id;
3119                         mgmt_buf->freq = freq;
3120                         mgmt_buf->wait = wait;
3121                         mgmt_buf->len = len;
3122                         mgmt_buf->no_cck = no_cck;
3123                         memcpy(mgmt_buf->buf, buf, len);
3124                         spin_lock_bh(&conn->psq_lock);
3125                         is_psq_empty = skb_queue_empty(&conn->psq) &&
3126                                         (conn->mgmt_psq_len == 0);
3127                         list_add_tail(&mgmt_buf->list, &conn->mgmt_psq);
3128                         conn->mgmt_psq_len++;
3129                         spin_unlock_bh(&conn->psq_lock);
3130
3131                         /*
3132                          * If this is the first pkt getting queued
3133                          * for this STA, update the PVB for this
3134                          * STA.
3135                          */
3136                         if (is_psq_empty)
3137                                 ath6kl_wmi_set_pvb_cmd(ar->wmi, vif->fw_vif_idx,
3138                                                        conn->aid, 1);
3139                         return true;
3140                 }
3141
3142                 /*
3143                  * This tx is because of a PsPoll.
3144                  * Determine if MoreData bit has to be set.
3145                  */
3146                 spin_lock_bh(&conn->psq_lock);
3147                 if (!skb_queue_empty(&conn->psq) || (conn->mgmt_psq_len != 0))
3148                         *more_data = true;
3149                 spin_unlock_bh(&conn->psq_lock);
3150         }
3151
3152         return false;
3153 }
3154
3155 /* Check if SSID length is greater than DIRECT- */
3156 static bool ath6kl_is_p2p_go_ssid(const u8 *buf, size_t len)
3157 {
3158         const struct ieee80211_mgmt *mgmt;
3159         mgmt = (const struct ieee80211_mgmt *) buf;
3160
3161         /* variable[1] contains the SSID tag length */
3162         if (buf + len >= &mgmt->u.probe_resp.variable[1] &&
3163             (mgmt->u.probe_resp.variable[1] > P2P_WILDCARD_SSID_LEN)) {
3164                 return true;
3165         }
3166
3167         return false;
3168 }
3169
3170 static int ath6kl_mgmt_tx(struct wiphy *wiphy, struct wireless_dev *wdev,
3171                           struct cfg80211_mgmt_tx_params *params, u64 *cookie)
3172 {
3173         struct ath6kl_vif *vif = ath6kl_vif_from_wdev(wdev);
3174         struct ath6kl *ar = ath6kl_priv(vif->ndev);
3175         struct ieee80211_channel *chan = params->chan;
3176         const u8 *buf = params->buf;
3177         size_t len = params->len;
3178         unsigned int wait = params->wait;
3179         bool no_cck = params->no_cck;
3180         u32 id, freq;
3181         const struct ieee80211_mgmt *mgmt;
3182         bool more_data, queued;
3183
3184         /* default to the current channel, but use the one specified as argument
3185          * if any
3186          */
3187         freq = vif->ch_hint;
3188         if (chan)
3189                 freq = chan->center_freq;
3190
3191         /* never send freq zero to the firmware */
3192         if (WARN_ON(freq == 0))
3193                 return -EINVAL;
3194
3195         mgmt = (const struct ieee80211_mgmt *) buf;
3196         if (vif->nw_type == AP_NETWORK && test_bit(CONNECTED, &vif->flags) &&
3197             ieee80211_is_probe_resp(mgmt->frame_control) &&
3198             ath6kl_is_p2p_go_ssid(buf, len)) {
3199                 /*
3200                  * Send Probe Response frame in GO mode using a separate WMI
3201                  * command to allow the target to fill in the generic IEs.
3202                  */
3203                 *cookie = 0; /* TX status not supported */
3204                 return ath6kl_send_go_probe_resp(vif, buf, len, freq);
3205         }
3206
3207         id = vif->send_action_id++;
3208         if (id == 0) {
3209                 /*
3210                  * 0 is a reserved value in the WMI command and shall not be
3211                  * used for the command.
3212                  */
3213                 id = vif->send_action_id++;
3214         }
3215
3216         *cookie = id;
3217
3218         /* AP mode Power saving processing */
3219         if (vif->nw_type == AP_NETWORK) {
3220                 queued = ath6kl_mgmt_powersave_ap(vif, id, freq, wait, buf, len,
3221                                                   &more_data, no_cck);
3222                 if (queued)
3223                         return 0;
3224         }
3225
3226         return ath6kl_wmi_send_mgmt_cmd(ar->wmi, vif->fw_vif_idx, id, freq,
3227                                         wait, buf, len, no_cck);
3228 }
3229
3230 static void ath6kl_mgmt_frame_register(struct wiphy *wiphy,
3231                                        struct wireless_dev *wdev,
3232                                        u16 frame_type, bool reg)
3233 {
3234         struct ath6kl_vif *vif = ath6kl_vif_from_wdev(wdev);
3235
3236         ath6kl_dbg(ATH6KL_DBG_WLAN_CFG, "%s: frame_type=0x%x reg=%d\n",
3237                    __func__, frame_type, reg);
3238         if (frame_type == IEEE80211_STYPE_PROBE_REQ) {
3239                 /*
3240                  * Note: This notification callback is not allowed to sleep, so
3241                  * we cannot send WMI_PROBE_REQ_REPORT_CMD here. Instead, we
3242                  * hardcode target to report Probe Request frames all the time.
3243                  */
3244                 vif->probe_req_report = reg;
3245         }
3246 }
3247
3248 static int ath6kl_cfg80211_sscan_start(struct wiphy *wiphy,
3249                         struct net_device *dev,
3250                         struct cfg80211_sched_scan_request *request)
3251 {
3252         struct ath6kl *ar = ath6kl_priv(dev);
3253         struct ath6kl_vif *vif = netdev_priv(dev);
3254         u16 interval;
3255         int ret, rssi_thold;
3256         int n_match_sets = request->n_match_sets;
3257
3258         /*
3259          * If there's a matchset w/o an SSID, then assume it's just for
3260          * the RSSI (nothing else is currently supported) and ignore it.
3261          * The device only supports a global RSSI filter that we set below.
3262          */
3263         if (n_match_sets == 1 && !request->match_sets[0].ssid.ssid_len)
3264                 n_match_sets = 0;
3265
3266         if (ar->state != ATH6KL_STATE_ON)
3267                 return -EIO;
3268
3269         if (vif->sme_state != SME_DISCONNECTED)
3270                 return -EBUSY;
3271
3272         ath6kl_cfg80211_scan_complete_event(vif, true);
3273
3274         ret = ath6kl_set_probed_ssids(ar, vif, request->ssids,
3275                                       request->n_ssids,
3276                                       request->match_sets,
3277                                       n_match_sets);
3278         if (ret < 0)
3279                 return ret;
3280
3281         if (!n_match_sets) {
3282                 ret = ath6kl_wmi_bssfilter_cmd(ar->wmi, vif->fw_vif_idx,
3283                                                ALL_BSS_FILTER, 0);
3284                 if (ret < 0)
3285                         return ret;
3286         } else {
3287                  ret = ath6kl_wmi_bssfilter_cmd(ar->wmi, vif->fw_vif_idx,
3288                                                 MATCHED_SSID_FILTER, 0);
3289                 if (ret < 0)
3290                         return ret;
3291         }
3292
3293         if (test_bit(ATH6KL_FW_CAPABILITY_RSSI_SCAN_THOLD,
3294                      ar->fw_capabilities)) {
3295                 if (request->min_rssi_thold <= NL80211_SCAN_RSSI_THOLD_OFF)
3296                         rssi_thold = 0;
3297                 else if (request->min_rssi_thold < -127)
3298                         rssi_thold = -127;
3299                 else
3300                         rssi_thold = request->min_rssi_thold;
3301
3302                 ret = ath6kl_wmi_set_rssi_filter_cmd(ar->wmi, vif->fw_vif_idx,
3303                                                      rssi_thold);
3304                 if (ret) {
3305                         ath6kl_err("failed to set RSSI threshold for scan\n");
3306                         return ret;
3307                 }
3308         }
3309
3310         /* fw uses seconds, also make sure that it's >0 */
3311         interval = max_t(u16, 1, request->interval / 1000);
3312
3313         ath6kl_wmi_scanparams_cmd(ar->wmi, vif->fw_vif_idx,
3314                                   interval, interval,
3315                                   vif->bg_scan_period, 0, 0, 0, 3, 0, 0, 0);
3316
3317         /* this also clears IE in fw if it's not set */
3318         ret = ath6kl_wmi_set_appie_cmd(ar->wmi, vif->fw_vif_idx,
3319                                        WMI_FRAME_PROBE_REQ,
3320                                        request->ie, request->ie_len);
3321         if (ret) {
3322                 ath6kl_warn("Failed to set probe request IE for scheduled scan: %d\n",
3323                             ret);
3324                 return ret;
3325         }
3326
3327         ret = ath6kl_wmi_enable_sched_scan_cmd(ar->wmi, vif->fw_vif_idx, true);
3328         if (ret)
3329                 return ret;
3330
3331         set_bit(SCHED_SCANNING, &vif->flags);
3332
3333         return 0;
3334 }
3335
3336 static int ath6kl_cfg80211_sscan_stop(struct wiphy *wiphy,
3337                                       struct net_device *dev)
3338 {
3339         struct ath6kl_vif *vif = netdev_priv(dev);
3340         bool stopped;
3341
3342         stopped = __ath6kl_cfg80211_sscan_stop(vif);
3343
3344         if (!stopped)
3345                 return -EIO;
3346
3347         return 0;
3348 }
3349
3350 static int ath6kl_cfg80211_set_bitrate(struct wiphy *wiphy,
3351                                        struct net_device *dev,
3352                                        const u8 *addr,
3353                                        const struct cfg80211_bitrate_mask *mask)
3354 {
3355         struct ath6kl *ar = ath6kl_priv(dev);
3356         struct ath6kl_vif *vif = netdev_priv(dev);
3357
3358         return ath6kl_wmi_set_bitrate_mask(ar->wmi, vif->fw_vif_idx,
3359                                            mask);
3360 }
3361
3362 static int ath6kl_cfg80211_set_txe_config(struct wiphy *wiphy,
3363                                           struct net_device *dev,
3364                                           u32 rate, u32 pkts, u32 intvl)
3365 {
3366         struct ath6kl *ar = ath6kl_priv(dev);
3367         struct ath6kl_vif *vif = netdev_priv(dev);
3368
3369         if (vif->nw_type != INFRA_NETWORK ||
3370             !test_bit(ATH6KL_FW_CAPABILITY_TX_ERR_NOTIFY, ar->fw_capabilities))
3371                 return -EOPNOTSUPP;
3372
3373         if (vif->sme_state != SME_CONNECTED)
3374                 return -ENOTCONN;
3375
3376         /* save this since the firmware won't report the interval */
3377         vif->txe_intvl = intvl;
3378
3379         return ath6kl_wmi_set_txe_notify(ar->wmi, vif->fw_vif_idx,
3380                                          rate, pkts, intvl);
3381 }
3382
3383 static const struct ieee80211_txrx_stypes
3384 ath6kl_mgmt_stypes[NUM_NL80211_IFTYPES] = {
3385         [NL80211_IFTYPE_STATION] = {
3386                 .tx = BIT(IEEE80211_STYPE_ACTION >> 4) |
3387                 BIT(IEEE80211_STYPE_PROBE_RESP >> 4),
3388                 .rx = BIT(IEEE80211_STYPE_ACTION >> 4) |
3389                 BIT(IEEE80211_STYPE_PROBE_REQ >> 4)
3390         },
3391         [NL80211_IFTYPE_AP] = {
3392                 .tx = BIT(IEEE80211_STYPE_ACTION >> 4) |
3393                 BIT(IEEE80211_STYPE_PROBE_RESP >> 4),
3394                 .rx = BIT(IEEE80211_STYPE_ACTION >> 4) |
3395                 BIT(IEEE80211_STYPE_PROBE_REQ >> 4)
3396         },
3397         [NL80211_IFTYPE_P2P_CLIENT] = {
3398                 .tx = BIT(IEEE80211_STYPE_ACTION >> 4) |
3399                 BIT(IEEE80211_STYPE_PROBE_RESP >> 4),
3400                 .rx = BIT(IEEE80211_STYPE_ACTION >> 4) |
3401                 BIT(IEEE80211_STYPE_PROBE_REQ >> 4)
3402         },
3403         [NL80211_IFTYPE_P2P_GO] = {
3404                 .tx = BIT(IEEE80211_STYPE_ACTION >> 4) |
3405                 BIT(IEEE80211_STYPE_PROBE_RESP >> 4),
3406                 .rx = BIT(IEEE80211_STYPE_ACTION >> 4) |
3407                 BIT(IEEE80211_STYPE_PROBE_REQ >> 4)
3408         },
3409 };
3410
3411 static struct cfg80211_ops ath6kl_cfg80211_ops = {
3412         .add_virtual_intf = ath6kl_cfg80211_add_iface,
3413         .del_virtual_intf = ath6kl_cfg80211_del_iface,
3414         .change_virtual_intf = ath6kl_cfg80211_change_iface,
3415         .scan = ath6kl_cfg80211_scan,
3416         .connect = ath6kl_cfg80211_connect,
3417         .disconnect = ath6kl_cfg80211_disconnect,
3418         .add_key = ath6kl_cfg80211_add_key,
3419         .get_key = ath6kl_cfg80211_get_key,
3420         .del_key = ath6kl_cfg80211_del_key,
3421         .set_default_key = ath6kl_cfg80211_set_default_key,
3422         .set_wiphy_params = ath6kl_cfg80211_set_wiphy_params,
3423         .set_tx_power = ath6kl_cfg80211_set_txpower,
3424         .get_tx_power = ath6kl_cfg80211_get_txpower,
3425         .set_power_mgmt = ath6kl_cfg80211_set_power_mgmt,
3426         .join_ibss = ath6kl_cfg80211_join_ibss,
3427         .leave_ibss = ath6kl_cfg80211_leave_ibss,
3428         .get_station = ath6kl_get_station,
3429         .set_pmksa = ath6kl_set_pmksa,
3430         .del_pmksa = ath6kl_del_pmksa,
3431         .flush_pmksa = ath6kl_flush_pmksa,
3432         CFG80211_TESTMODE_CMD(ath6kl_tm_cmd)
3433 #ifdef CONFIG_PM
3434         .suspend = __ath6kl_cfg80211_suspend,
3435         .resume = __ath6kl_cfg80211_resume,
3436 #endif
3437         .start_ap = ath6kl_start_ap,
3438         .change_beacon = ath6kl_change_beacon,
3439         .stop_ap = ath6kl_stop_ap,
3440         .del_station = ath6kl_del_station,
3441         .change_station = ath6kl_change_station,
3442         .remain_on_channel = ath6kl_remain_on_channel,
3443         .cancel_remain_on_channel = ath6kl_cancel_remain_on_channel,
3444         .mgmt_tx = ath6kl_mgmt_tx,
3445         .mgmt_frame_register = ath6kl_mgmt_frame_register,
3446         .sched_scan_start = ath6kl_cfg80211_sscan_start,
3447         .sched_scan_stop = ath6kl_cfg80211_sscan_stop,
3448         .set_bitrate_mask = ath6kl_cfg80211_set_bitrate,
3449         .set_cqm_txe_config = ath6kl_cfg80211_set_txe_config,
3450 };
3451
3452 void ath6kl_cfg80211_stop(struct ath6kl_vif *vif)
3453 {
3454         ath6kl_cfg80211_sscan_disable(vif);
3455
3456         switch (vif->sme_state) {
3457         case SME_DISCONNECTED:
3458                 break;
3459         case SME_CONNECTING:
3460                 cfg80211_connect_result(vif->ndev, vif->bssid, NULL, 0,
3461                                         NULL, 0,
3462                                         WLAN_STATUS_UNSPECIFIED_FAILURE,
3463                                         GFP_KERNEL);
3464                 break;
3465         case SME_CONNECTED:
3466                 cfg80211_disconnected(vif->ndev, 0, NULL, 0, GFP_KERNEL);
3467                 break;
3468         }
3469
3470         if (vif->ar->state != ATH6KL_STATE_RECOVERY &&
3471             (test_bit(CONNECTED, &vif->flags) ||
3472             test_bit(CONNECT_PEND, &vif->flags)))
3473                 ath6kl_wmi_disconnect_cmd(vif->ar->wmi, vif->fw_vif_idx);
3474
3475         vif->sme_state = SME_DISCONNECTED;
3476         clear_bit(CONNECTED, &vif->flags);
3477         clear_bit(CONNECT_PEND, &vif->flags);
3478
3479         /* Stop netdev queues, needed during recovery */
3480         netif_stop_queue(vif->ndev);
3481         netif_carrier_off(vif->ndev);
3482
3483         /* disable scanning */
3484         if (vif->ar->state != ATH6KL_STATE_RECOVERY &&
3485             ath6kl_wmi_scanparams_cmd(vif->ar->wmi, vif->fw_vif_idx, 0xFFFF,
3486                                       0, 0, 0, 0, 0, 0, 0, 0, 0) != 0)
3487                 ath6kl_warn("failed to disable scan during stop\n");
3488
3489         ath6kl_cfg80211_scan_complete_event(vif, true);
3490 }
3491
3492 void ath6kl_cfg80211_stop_all(struct ath6kl *ar)
3493 {
3494         struct ath6kl_vif *vif;
3495
3496         vif = ath6kl_vif_first(ar);
3497         if (!vif && ar->state != ATH6KL_STATE_RECOVERY) {
3498                 /* save the current power mode before enabling power save */
3499                 ar->wmi->saved_pwr_mode = ar->wmi->pwr_mode;
3500
3501                 if (ath6kl_wmi_powermode_cmd(ar->wmi, 0, REC_POWER) != 0)
3502                         ath6kl_warn("ath6kl_deep_sleep_enable: wmi_powermode_cmd failed\n");
3503                 return;
3504         }
3505
3506         /*
3507          * FIXME: we should take ar->list_lock to protect changes in the
3508          * vif_list, but that's not trivial to do as ath6kl_cfg80211_stop()
3509          * sleeps.
3510          */
3511         list_for_each_entry(vif, &ar->vif_list, list)
3512                 ath6kl_cfg80211_stop(vif);
3513 }
3514
3515 static void ath6kl_cfg80211_reg_notify(struct wiphy *wiphy,
3516                                        struct regulatory_request *request)
3517 {
3518         struct ath6kl *ar = wiphy_priv(wiphy);
3519         u32 rates[IEEE80211_NUM_BANDS];
3520         int ret, i;
3521
3522         ath6kl_dbg(ATH6KL_DBG_WLAN_CFG,
3523                    "cfg reg_notify %c%c%s%s initiator %d hint_type %d\n",
3524                    request->alpha2[0], request->alpha2[1],
3525                    request->intersect ? " intersect" : "",
3526                    request->processed ? " processed" : "",
3527                    request->initiator, request->user_reg_hint_type);
3528
3529         if (request->user_reg_hint_type != NL80211_USER_REG_HINT_CELL_BASE)
3530                 return;
3531
3532         ret = ath6kl_wmi_set_regdomain_cmd(ar->wmi, request->alpha2);
3533         if (ret) {
3534                 ath6kl_err("failed to set regdomain: %d\n", ret);
3535                 return;
3536         }
3537
3538         /*
3539          * Firmware will apply the regdomain change only after a scan is
3540          * issued and it will send a WMI_REGDOMAIN_EVENTID when it has been
3541          * changed.
3542          */
3543
3544         for (i = 0; i < IEEE80211_NUM_BANDS; i++)
3545                 if (wiphy->bands[i])
3546                         rates[i] = (1 << wiphy->bands[i]->n_bitrates) - 1;
3547
3548
3549         ret = ath6kl_wmi_beginscan_cmd(ar->wmi, 0, WMI_LONG_SCAN, false,
3550                                        false, 0, ATH6KL_FG_SCAN_INTERVAL,
3551                                        0, NULL, false, rates);
3552         if (ret) {
3553                 ath6kl_err("failed to start scan for a regdomain change: %d\n",
3554                            ret);
3555                 return;
3556         }
3557 }
3558
3559 static int ath6kl_cfg80211_vif_init(struct ath6kl_vif *vif)
3560 {
3561         vif->aggr_cntxt = aggr_init(vif);
3562         if (!vif->aggr_cntxt) {
3563                 ath6kl_err("failed to initialize aggr\n");
3564                 return -ENOMEM;
3565         }
3566
3567         setup_timer(&vif->disconnect_timer, disconnect_timer_handler,
3568                     (unsigned long) vif->ndev);
3569         setup_timer(&vif->sched_scan_timer, ath6kl_wmi_sscan_timer,
3570                     (unsigned long) vif);
3571
3572         set_bit(WMM_ENABLED, &vif->flags);
3573         spin_lock_init(&vif->if_lock);
3574
3575         INIT_LIST_HEAD(&vif->mc_filter);
3576
3577         return 0;
3578 }
3579
3580 void ath6kl_cfg80211_vif_stop(struct ath6kl_vif *vif, bool wmi_ready)
3581 {
3582         static u8 bcast_mac[] = {0xff, 0xff, 0xff, 0xff, 0xff, 0xff};
3583         bool discon_issued;
3584
3585         netif_stop_queue(vif->ndev);
3586
3587         clear_bit(WLAN_ENABLED, &vif->flags);
3588
3589         if (wmi_ready) {
3590                 discon_issued = test_bit(CONNECTED, &vif->flags) ||
3591                                 test_bit(CONNECT_PEND, &vif->flags);
3592                 ath6kl_disconnect(vif);
3593                 del_timer(&vif->disconnect_timer);
3594
3595                 if (discon_issued)
3596                         ath6kl_disconnect_event(vif, DISCONNECT_CMD,
3597                                                 (vif->nw_type & AP_NETWORK) ?
3598                                                 bcast_mac : vif->bssid,
3599                                                 0, NULL, 0);
3600         }
3601
3602         if (vif->scan_req) {
3603                 cfg80211_scan_done(vif->scan_req, true);
3604                 vif->scan_req = NULL;
3605         }
3606
3607         /* need to clean up enhanced bmiss detection fw state */
3608         ath6kl_cfg80211_sta_bmiss_enhance(vif, false);
3609 }
3610
3611 void ath6kl_cfg80211_vif_cleanup(struct ath6kl_vif *vif)
3612 {
3613         struct ath6kl *ar = vif->ar;
3614         struct ath6kl_mc_filter *mc_filter, *tmp;
3615
3616         aggr_module_destroy(vif->aggr_cntxt);
3617
3618         ar->avail_idx_map |= BIT(vif->fw_vif_idx);
3619
3620         if (vif->nw_type == ADHOC_NETWORK)
3621                 ar->ibss_if_active = false;
3622
3623         list_for_each_entry_safe(mc_filter, tmp, &vif->mc_filter, list) {
3624                 list_del(&mc_filter->list);
3625                 kfree(mc_filter);
3626         }
3627
3628         unregister_netdevice(vif->ndev);
3629
3630         ar->num_vif--;
3631 }
3632
3633 struct wireless_dev *ath6kl_interface_add(struct ath6kl *ar, const char *name,
3634                                           enum nl80211_iftype type,
3635                                           u8 fw_vif_idx, u8 nw_type)
3636 {
3637         struct net_device *ndev;
3638         struct ath6kl_vif *vif;
3639
3640         ndev = alloc_netdev(sizeof(*vif), name, NET_NAME_UNKNOWN, ether_setup);
3641         if (!ndev)
3642                 return NULL;
3643
3644         vif = netdev_priv(ndev);
3645         ndev->ieee80211_ptr = &vif->wdev;
3646         vif->wdev.wiphy = ar->wiphy;
3647         vif->ar = ar;
3648         vif->ndev = ndev;
3649         SET_NETDEV_DEV(ndev, wiphy_dev(vif->wdev.wiphy));
3650         vif->wdev.netdev = ndev;
3651         vif->wdev.iftype = type;
3652         vif->fw_vif_idx = fw_vif_idx;
3653         vif->nw_type = nw_type;
3654         vif->next_mode = nw_type;
3655         vif->listen_intvl_t = ATH6KL_DEFAULT_LISTEN_INTVAL;
3656         vif->bmiss_time_t = ATH6KL_DEFAULT_BMISS_TIME;
3657         vif->bg_scan_period = 0;
3658         vif->htcap[IEEE80211_BAND_2GHZ].ht_enable = true;
3659         vif->htcap[IEEE80211_BAND_5GHZ].ht_enable = true;
3660
3661         memcpy(ndev->dev_addr, ar->mac_addr, ETH_ALEN);
3662         if (fw_vif_idx != 0) {
3663                 ndev->dev_addr[0] = (ndev->dev_addr[0] ^ (1 << fw_vif_idx)) |
3664                                      0x2;
3665                 if (test_bit(ATH6KL_FW_CAPABILITY_CUSTOM_MAC_ADDR,
3666                              ar->fw_capabilities))
3667                         ndev->dev_addr[4] ^= 0x80;
3668         }
3669
3670         init_netdev(ndev);
3671
3672         ath6kl_init_control_info(vif);
3673
3674         if (ath6kl_cfg80211_vif_init(vif))
3675                 goto err;
3676
3677         if (register_netdevice(ndev))
3678                 goto err;
3679
3680         ar->avail_idx_map &= ~BIT(fw_vif_idx);
3681         vif->sme_state = SME_DISCONNECTED;
3682         set_bit(WLAN_ENABLED, &vif->flags);
3683         ar->wlan_pwr_state = WLAN_POWER_STATE_ON;
3684
3685         if (type == NL80211_IFTYPE_ADHOC)
3686                 ar->ibss_if_active = true;
3687
3688         spin_lock_bh(&ar->list_lock);
3689         list_add_tail(&vif->list, &ar->vif_list);
3690         spin_unlock_bh(&ar->list_lock);
3691
3692         return &vif->wdev;
3693
3694 err:
3695         aggr_module_destroy(vif->aggr_cntxt);
3696         free_netdev(ndev);
3697         return NULL;
3698 }
3699
3700 #ifdef CONFIG_PM
3701 static const struct wiphy_wowlan_support ath6kl_wowlan_support = {
3702         .flags = WIPHY_WOWLAN_MAGIC_PKT |
3703                  WIPHY_WOWLAN_DISCONNECT |
3704                  WIPHY_WOWLAN_GTK_REKEY_FAILURE  |
3705                  WIPHY_WOWLAN_SUPPORTS_GTK_REKEY |
3706                  WIPHY_WOWLAN_EAP_IDENTITY_REQ   |
3707                  WIPHY_WOWLAN_4WAY_HANDSHAKE,
3708         .n_patterns = WOW_MAX_FILTERS_PER_LIST,
3709         .pattern_min_len = 1,
3710         .pattern_max_len = WOW_PATTERN_SIZE,
3711 };
3712 #endif
3713
3714 int ath6kl_cfg80211_init(struct ath6kl *ar)
3715 {
3716         struct wiphy *wiphy = ar->wiphy;
3717         bool band_2gig = false, band_5gig = false, ht = false;
3718         int ret;
3719
3720         wiphy->mgmt_stypes = ath6kl_mgmt_stypes;
3721
3722         wiphy->max_remain_on_channel_duration = 5000;
3723
3724         /* set device pointer for wiphy */
3725         set_wiphy_dev(wiphy, ar->dev);
3726
3727         wiphy->interface_modes = BIT(NL80211_IFTYPE_STATION) |
3728                                  BIT(NL80211_IFTYPE_ADHOC) |
3729                                  BIT(NL80211_IFTYPE_AP);
3730         if (ar->p2p) {
3731                 wiphy->interface_modes |= BIT(NL80211_IFTYPE_P2P_GO) |
3732                                           BIT(NL80211_IFTYPE_P2P_CLIENT);
3733         }
3734
3735         if (config_enabled(CONFIG_ATH6KL_REGDOMAIN) &&
3736             test_bit(ATH6KL_FW_CAPABILITY_REGDOMAIN, ar->fw_capabilities)) {
3737                 wiphy->reg_notifier = ath6kl_cfg80211_reg_notify;
3738                 ar->wiphy->features |= NL80211_FEATURE_CELL_BASE_REG_HINTS;
3739         }
3740
3741         /* max num of ssids that can be probed during scanning */
3742         wiphy->max_scan_ssids = MAX_PROBED_SSIDS;
3743
3744         /* max num of ssids that can be matched after scan */
3745         if (test_bit(ATH6KL_FW_CAPABILITY_SCHED_SCAN_MATCH_LIST,
3746                      ar->fw_capabilities))
3747                 wiphy->max_match_sets = MAX_PROBED_SSIDS;
3748
3749         wiphy->max_scan_ie_len = 1000; /* FIX: what is correct limit? */
3750         switch (ar->hw.cap) {
3751         case WMI_11AN_CAP:
3752                 ht = true;
3753         case WMI_11A_CAP:
3754                 band_5gig = true;
3755                 break;
3756         case WMI_11GN_CAP:
3757                 ht = true;
3758         case WMI_11G_CAP:
3759                 band_2gig = true;
3760                 break;
3761         case WMI_11AGN_CAP:
3762                 ht = true;
3763         case WMI_11AG_CAP:
3764                 band_2gig = true;
3765                 band_5gig = true;
3766                 break;
3767         default:
3768                 ath6kl_err("invalid phy capability!\n");
3769                 return -EINVAL;
3770         }
3771
3772         /*
3773          * Even if the fw has HT support, advertise HT cap only when
3774          * the firmware has support to override RSN capability, otherwise
3775          * 4-way handshake would fail.
3776          */
3777         if (!(ht &&
3778               test_bit(ATH6KL_FW_CAPABILITY_RSN_CAP_OVERRIDE,
3779                        ar->fw_capabilities))) {
3780                 ath6kl_band_2ghz.ht_cap.cap = 0;
3781                 ath6kl_band_2ghz.ht_cap.ht_supported = false;
3782                 ath6kl_band_5ghz.ht_cap.cap = 0;
3783                 ath6kl_band_5ghz.ht_cap.ht_supported = false;
3784         }
3785
3786         if (test_bit(ATH6KL_FW_CAPABILITY_64BIT_RATES,
3787                      ar->fw_capabilities)) {
3788                 ath6kl_band_2ghz.ht_cap.mcs.rx_mask[0] = 0xff;
3789                 ath6kl_band_5ghz.ht_cap.mcs.rx_mask[0] = 0xff;
3790                 ath6kl_band_2ghz.ht_cap.mcs.rx_mask[1] = 0xff;
3791                 ath6kl_band_5ghz.ht_cap.mcs.rx_mask[1] = 0xff;
3792         } else {
3793                 ath6kl_band_2ghz.ht_cap.mcs.rx_mask[0] = 0xff;
3794                 ath6kl_band_5ghz.ht_cap.mcs.rx_mask[0] = 0xff;
3795         }
3796
3797         if (band_2gig)
3798                 wiphy->bands[IEEE80211_BAND_2GHZ] = &ath6kl_band_2ghz;
3799         if (band_5gig)
3800                 wiphy->bands[IEEE80211_BAND_5GHZ] = &ath6kl_band_5ghz;
3801
3802         wiphy->signal_type = CFG80211_SIGNAL_TYPE_MBM;
3803
3804         wiphy->cipher_suites = cipher_suites;
3805         wiphy->n_cipher_suites = ARRAY_SIZE(cipher_suites);
3806
3807 #ifdef CONFIG_PM
3808         wiphy->wowlan = &ath6kl_wowlan_support;
3809 #endif
3810
3811         wiphy->max_sched_scan_ssids = MAX_PROBED_SSIDS;
3812
3813         ar->wiphy->flags |= WIPHY_FLAG_SUPPORTS_FW_ROAM |
3814                             WIPHY_FLAG_HAVE_AP_SME |
3815                             WIPHY_FLAG_HAS_REMAIN_ON_CHANNEL |
3816                             WIPHY_FLAG_AP_PROBE_RESP_OFFLOAD;
3817
3818         if (test_bit(ATH6KL_FW_CAPABILITY_SCHED_SCAN_V2, ar->fw_capabilities))
3819                 ar->wiphy->flags |= WIPHY_FLAG_SUPPORTS_SCHED_SCAN;
3820
3821         if (test_bit(ATH6KL_FW_CAPABILITY_INACTIVITY_TIMEOUT,
3822                      ar->fw_capabilities))
3823                 ar->wiphy->features |= NL80211_FEATURE_INACTIVITY_TIMER;
3824
3825         ar->wiphy->probe_resp_offload =
3826                 NL80211_PROBE_RESP_OFFLOAD_SUPPORT_WPS |
3827                 NL80211_PROBE_RESP_OFFLOAD_SUPPORT_WPS2 |
3828                 NL80211_PROBE_RESP_OFFLOAD_SUPPORT_P2P;
3829
3830         ret = wiphy_register(wiphy);
3831         if (ret < 0) {
3832                 ath6kl_err("couldn't register wiphy device\n");
3833                 return ret;
3834         }
3835
3836         ar->wiphy_registered = true;
3837
3838         return 0;
3839 }
3840
3841 void ath6kl_cfg80211_cleanup(struct ath6kl *ar)
3842 {
3843         wiphy_unregister(ar->wiphy);
3844
3845         ar->wiphy_registered = false;
3846 }
3847
3848 struct ath6kl *ath6kl_cfg80211_create(void)
3849 {
3850         struct ath6kl *ar;
3851         struct wiphy *wiphy;
3852
3853         /* create a new wiphy for use with cfg80211 */
3854         wiphy = wiphy_new(&ath6kl_cfg80211_ops, sizeof(struct ath6kl));
3855
3856         if (!wiphy) {
3857                 ath6kl_err("couldn't allocate wiphy device\n");
3858                 return NULL;
3859         }
3860
3861         ar = wiphy_priv(wiphy);
3862         ar->wiphy = wiphy;
3863
3864         return ar;
3865 }
3866
3867 /* Note: ar variable must not be accessed after calling this! */
3868 void ath6kl_cfg80211_destroy(struct ath6kl *ar)
3869 {
3870         int i;
3871
3872         for (i = 0; i < AP_MAX_NUM_STA; i++)
3873                 kfree(ar->sta_list[i].aggr_conn);
3874
3875         wiphy_free(ar->wiphy);
3876 }
3877