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