1 /*
2  * Copyright (c) 2010 Broadcom Corporation
3  *
4  * Permission to use, copy, modify, and/or distribute this software for any
5  * purpose with or without fee is hereby granted, provided that the above
6  * copyright notice and this permission notice appear in all copies.
7  *
8  * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
9  * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
10  * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY
11  * SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
12  * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION
13  * OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN
14  * CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
15  */
16 
17 /* Toplevel file. Relies on dhd_linux.c to send commands to the dongle. */
18 
19 #include <linux/kernel.h>
20 #include <linux/etherdevice.h>
21 #include <linux/module.h>
22 #include <linux/vmalloc.h>
23 #include <net/cfg80211.h>
24 #include <net/netlink.h>
25 
26 #include <brcmu_utils.h>
27 #include <defs.h>
28 #include <brcmu_wifi.h>
29 #include "core.h"
30 #include "debug.h"
31 #include "tracepoint.h"
32 #include "fwil_types.h"
33 #include "p2p.h"
34 #include "btcoex.h"
35 #include "pno.h"
36 #include "cfg80211.h"
37 #include "feature.h"
38 #include "fwil.h"
39 #include "proto.h"
40 #include "vendor.h"
41 #include "bus.h"
42 #include "common.h"
43 
44 #define BRCMF_SCAN_IE_LEN_MAX		2048
45 
46 #define WPA_OUI				"\x00\x50\xF2"	/* WPA OUI */
47 #define WPA_OUI_TYPE			1
48 #define RSN_OUI				"\x00\x0F\xAC"	/* RSN OUI */
49 #define	WME_OUI_TYPE			2
50 #define WPS_OUI_TYPE			4
51 
52 #define VS_IE_FIXED_HDR_LEN		6
53 #define WPA_IE_VERSION_LEN		2
54 #define WPA_IE_MIN_OUI_LEN		4
55 #define WPA_IE_SUITE_COUNT_LEN		2
56 
57 #define WPA_CIPHER_NONE			0	/* None */
58 #define WPA_CIPHER_WEP_40		1	/* WEP (40-bit) */
59 #define WPA_CIPHER_TKIP			2	/* TKIP: default for WPA */
60 #define WPA_CIPHER_AES_CCM		4	/* AES (CCM) */
61 #define WPA_CIPHER_WEP_104		5	/* WEP (104-bit) */
62 
63 #define RSN_AKM_NONE			0	/* None (IBSS) */
64 #define RSN_AKM_UNSPECIFIED		1	/* Over 802.1x */
65 #define RSN_AKM_PSK			2	/* Pre-shared Key */
66 #define RSN_AKM_SHA256_1X		5	/* SHA256, 802.1X */
67 #define RSN_AKM_SHA256_PSK		6	/* SHA256, Pre-shared Key */
68 #define RSN_CAP_LEN			2	/* Length of RSN capabilities */
69 #define RSN_CAP_PTK_REPLAY_CNTR_MASK	(BIT(2) | BIT(3))
70 #define RSN_CAP_MFPR_MASK		BIT(6)
71 #define RSN_CAP_MFPC_MASK		BIT(7)
72 #define RSN_PMKID_COUNT_LEN		2
73 
74 #define VNDR_IE_CMD_LEN			4	/* length of the set command
75 						 * string :"add", "del" (+ NUL)
76 						 */
77 #define VNDR_IE_COUNT_OFFSET		4
78 #define VNDR_IE_PKTFLAG_OFFSET		8
79 #define VNDR_IE_VSIE_OFFSET		12
80 #define VNDR_IE_HDR_SIZE		12
81 #define VNDR_IE_PARSE_LIMIT		5
82 
83 #define	DOT11_MGMT_HDR_LEN		24	/* d11 management header len */
84 #define	DOT11_BCN_PRB_FIXED_LEN		12	/* beacon/probe fixed length */
85 
86 #define BRCMF_SCAN_JOIN_ACTIVE_DWELL_TIME_MS	320
87 #define BRCMF_SCAN_JOIN_PASSIVE_DWELL_TIME_MS	400
88 #define BRCMF_SCAN_JOIN_PROBE_INTERVAL_MS	20
89 
90 #define BRCMF_SCAN_CHANNEL_TIME		40
91 #define BRCMF_SCAN_UNASSOC_TIME		40
92 #define BRCMF_SCAN_PASSIVE_TIME		120
93 
94 #define BRCMF_ND_INFO_TIMEOUT		msecs_to_jiffies(2000)
95 
96 #define BRCMF_ASSOC_PARAMS_FIXED_SIZE \
97 	(sizeof(struct brcmf_assoc_params_le) - sizeof(u16))
98 
99 static bool check_vif_up(struct brcmf_cfg80211_vif *vif)
100 {
101 	if (!test_bit(BRCMF_VIF_STATUS_READY, &vif->sme_state)) {
102 		brcmf_dbg(INFO, "device is not ready : status (%lu)\n",
103 			  vif->sme_state);
104 		return false;
105 	}
106 	return true;
107 }
108 
109 #define RATE_TO_BASE100KBPS(rate)   (((rate) * 10) / 2)
110 #define RATETAB_ENT(_rateid, _flags) \
111 	{                                                               \
112 		.bitrate        = RATE_TO_BASE100KBPS(_rateid),     \
113 		.hw_value       = (_rateid),                            \
114 		.flags          = (_flags),                             \
115 	}
116 
117 static struct ieee80211_rate __wl_rates[] = {
118 	RATETAB_ENT(BRCM_RATE_1M, 0),
119 	RATETAB_ENT(BRCM_RATE_2M, IEEE80211_RATE_SHORT_PREAMBLE),
120 	RATETAB_ENT(BRCM_RATE_5M5, IEEE80211_RATE_SHORT_PREAMBLE),
121 	RATETAB_ENT(BRCM_RATE_11M, IEEE80211_RATE_SHORT_PREAMBLE),
122 	RATETAB_ENT(BRCM_RATE_6M, 0),
123 	RATETAB_ENT(BRCM_RATE_9M, 0),
124 	RATETAB_ENT(BRCM_RATE_12M, 0),
125 	RATETAB_ENT(BRCM_RATE_18M, 0),
126 	RATETAB_ENT(BRCM_RATE_24M, 0),
127 	RATETAB_ENT(BRCM_RATE_36M, 0),
128 	RATETAB_ENT(BRCM_RATE_48M, 0),
129 	RATETAB_ENT(BRCM_RATE_54M, 0),
130 };
131 
132 #define wl_g_rates		(__wl_rates + 0)
133 #define wl_g_rates_size		ARRAY_SIZE(__wl_rates)
134 #define wl_a_rates		(__wl_rates + 4)
135 #define wl_a_rates_size		(wl_g_rates_size - 4)
136 
137 #define CHAN2G(_channel, _freq) {				\
138 	.band			= NL80211_BAND_2GHZ,		\
139 	.center_freq		= (_freq),			\
140 	.hw_value		= (_channel),			\
141 	.flags			= IEEE80211_CHAN_DISABLED,	\
142 	.max_antenna_gain	= 0,				\
143 	.max_power		= 30,				\
144 }
145 
146 #define CHAN5G(_channel) {					\
147 	.band			= NL80211_BAND_5GHZ,		\
148 	.center_freq		= 5000 + (5 * (_channel)),	\
149 	.hw_value		= (_channel),			\
150 	.flags			= IEEE80211_CHAN_DISABLED,	\
151 	.max_antenna_gain	= 0,				\
152 	.max_power		= 30,				\
153 }
154 
155 static struct ieee80211_channel __wl_2ghz_channels[] = {
156 	CHAN2G(1, 2412), CHAN2G(2, 2417), CHAN2G(3, 2422), CHAN2G(4, 2427),
157 	CHAN2G(5, 2432), CHAN2G(6, 2437), CHAN2G(7, 2442), CHAN2G(8, 2447),
158 	CHAN2G(9, 2452), CHAN2G(10, 2457), CHAN2G(11, 2462), CHAN2G(12, 2467),
159 	CHAN2G(13, 2472), CHAN2G(14, 2484)
160 };
161 
162 static struct ieee80211_channel __wl_5ghz_channels[] = {
163 	CHAN5G(34), CHAN5G(36), CHAN5G(38), CHAN5G(40), CHAN5G(42),
164 	CHAN5G(44), CHAN5G(46), CHAN5G(48), CHAN5G(52), CHAN5G(56),
165 	CHAN5G(60), CHAN5G(64), CHAN5G(100), CHAN5G(104), CHAN5G(108),
166 	CHAN5G(112), CHAN5G(116), CHAN5G(120), CHAN5G(124), CHAN5G(128),
167 	CHAN5G(132), CHAN5G(136), CHAN5G(140), CHAN5G(144), CHAN5G(149),
168 	CHAN5G(153), CHAN5G(157), CHAN5G(161), CHAN5G(165)
169 };
170 
171 /* Band templates duplicated per wiphy. The channel info
172  * above is added to the band during setup.
173  */
174 static const struct ieee80211_supported_band __wl_band_2ghz = {
175 	.band = NL80211_BAND_2GHZ,
176 	.bitrates = wl_g_rates,
177 	.n_bitrates = wl_g_rates_size,
178 };
179 
180 static const struct ieee80211_supported_band __wl_band_5ghz = {
181 	.band = NL80211_BAND_5GHZ,
182 	.bitrates = wl_a_rates,
183 	.n_bitrates = wl_a_rates_size,
184 };
185 
186 /* This is to override regulatory domains defined in cfg80211 module (reg.c)
187  * By default world regulatory domain defined in reg.c puts the flags
188  * NL80211_RRF_NO_IR for 5GHz channels (for * 36..48 and 149..165).
189  * With respect to these flags, wpa_supplicant doesn't * start p2p
190  * operations on 5GHz channels. All the changes in world regulatory
191  * domain are to be done here.
192  */
193 static const struct ieee80211_regdomain brcmf_regdom = {
194 	.n_reg_rules = 4,
195 	.alpha2 =  "99",
196 	.reg_rules = {
197 		/* IEEE 802.11b/g, channels 1..11 */
198 		REG_RULE(2412-10, 2472+10, 40, 6, 20, 0),
199 		/* If any */
200 		/* IEEE 802.11 channel 14 - Only JP enables
201 		 * this and for 802.11b only
202 		 */
203 		REG_RULE(2484-10, 2484+10, 20, 6, 20, 0),
204 		/* IEEE 802.11a, channel 36..64 */
205 		REG_RULE(5150-10, 5350+10, 80, 6, 20, 0),
206 		/* IEEE 802.11a, channel 100..165 */
207 		REG_RULE(5470-10, 5850+10, 80, 6, 20, 0), }
208 };
209 
210 /* Note: brcmf_cipher_suites is an array of int defining which cipher suites
211  * are supported. A pointer to this array and the number of entries is passed
212  * on to upper layers. AES_CMAC defines whether or not the driver supports MFP.
213  * So the cipher suite AES_CMAC has to be the last one in the array, and when
214  * device does not support MFP then the number of suites will be decreased by 1
215  */
216 static const u32 brcmf_cipher_suites[] = {
217 	WLAN_CIPHER_SUITE_WEP40,
218 	WLAN_CIPHER_SUITE_WEP104,
219 	WLAN_CIPHER_SUITE_TKIP,
220 	WLAN_CIPHER_SUITE_CCMP,
221 	/* Keep as last entry: */
222 	WLAN_CIPHER_SUITE_AES_CMAC
223 };
224 
225 /* Vendor specific ie. id = 221, oui and type defines exact ie */
226 struct brcmf_vs_tlv {
227 	u8 id;
228 	u8 len;
229 	u8 oui[3];
230 	u8 oui_type;
231 };
232 
233 struct parsed_vndr_ie_info {
234 	u8 *ie_ptr;
235 	u32 ie_len;	/* total length including id & length field */
236 	struct brcmf_vs_tlv vndrie;
237 };
238 
239 struct parsed_vndr_ies {
240 	u32 count;
241 	struct parsed_vndr_ie_info ie_info[VNDR_IE_PARSE_LIMIT];
242 };
243 
244 static u8 nl80211_band_to_fwil(enum nl80211_band band)
245 {
246 	switch (band) {
247 	case NL80211_BAND_2GHZ:
248 		return WLC_BAND_2G;
249 	case NL80211_BAND_5GHZ:
250 		return WLC_BAND_5G;
251 	default:
252 		WARN_ON(1);
253 		break;
254 	}
255 	return 0;
256 }
257 
258 static u16 chandef_to_chanspec(struct brcmu_d11inf *d11inf,
259 			       struct cfg80211_chan_def *ch)
260 {
261 	struct brcmu_chan ch_inf;
262 	s32 primary_offset;
263 
264 	brcmf_dbg(TRACE, "chandef: control %d center %d width %d\n",
265 		  ch->chan->center_freq, ch->center_freq1, ch->width);
266 	ch_inf.chnum = ieee80211_frequency_to_channel(ch->center_freq1);
267 	primary_offset = ch->chan->center_freq - ch->center_freq1;
268 	switch (ch->width) {
269 	case NL80211_CHAN_WIDTH_20:
270 	case NL80211_CHAN_WIDTH_20_NOHT:
271 		ch_inf.bw = BRCMU_CHAN_BW_20;
272 		WARN_ON(primary_offset != 0);
273 		break;
274 	case NL80211_CHAN_WIDTH_40:
275 		ch_inf.bw = BRCMU_CHAN_BW_40;
276 		if (primary_offset > 0)
277 			ch_inf.sb = BRCMU_CHAN_SB_U;
278 		else
279 			ch_inf.sb = BRCMU_CHAN_SB_L;
280 		break;
281 	case NL80211_CHAN_WIDTH_80:
282 		ch_inf.bw = BRCMU_CHAN_BW_80;
283 		if (primary_offset == -30)
284 			ch_inf.sb = BRCMU_CHAN_SB_LL;
285 		else if (primary_offset == -10)
286 			ch_inf.sb = BRCMU_CHAN_SB_LU;
287 		else if (primary_offset == 10)
288 			ch_inf.sb = BRCMU_CHAN_SB_UL;
289 		else
290 			ch_inf.sb = BRCMU_CHAN_SB_UU;
291 		break;
292 	case NL80211_CHAN_WIDTH_80P80:
293 	case NL80211_CHAN_WIDTH_160:
294 	case NL80211_CHAN_WIDTH_5:
295 	case NL80211_CHAN_WIDTH_10:
296 	default:
297 		WARN_ON_ONCE(1);
298 	}
299 	switch (ch->chan->band) {
300 	case NL80211_BAND_2GHZ:
301 		ch_inf.band = BRCMU_CHAN_BAND_2G;
302 		break;
303 	case NL80211_BAND_5GHZ:
304 		ch_inf.band = BRCMU_CHAN_BAND_5G;
305 		break;
306 	case NL80211_BAND_60GHZ:
307 	default:
308 		WARN_ON_ONCE(1);
309 	}
310 	d11inf->encchspec(&ch_inf);
311 
312 	return ch_inf.chspec;
313 }
314 
315 u16 channel_to_chanspec(struct brcmu_d11inf *d11inf,
316 			struct ieee80211_channel *ch)
317 {
318 	struct brcmu_chan ch_inf;
319 
320 	ch_inf.chnum = ieee80211_frequency_to_channel(ch->center_freq);
321 	ch_inf.bw = BRCMU_CHAN_BW_20;
322 	d11inf->encchspec(&ch_inf);
323 
324 	return ch_inf.chspec;
325 }
326 
327 /* Traverse a string of 1-byte tag/1-byte length/variable-length value
328  * triples, returning a pointer to the substring whose first element
329  * matches tag
330  */
331 const struct brcmf_tlv *
332 brcmf_parse_tlvs(const void *buf, int buflen, uint key)
333 {
334 	const struct brcmf_tlv *elt = buf;
335 	int totlen = buflen;
336 
337 	/* find tagged parameter */
338 	while (totlen >= TLV_HDR_LEN) {
339 		int len = elt->len;
340 
341 		/* validate remaining totlen */
342 		if ((elt->id == key) && (totlen >= (len + TLV_HDR_LEN)))
343 			return elt;
344 
345 		elt = (struct brcmf_tlv *)((u8 *)elt + (len + TLV_HDR_LEN));
346 		totlen -= (len + TLV_HDR_LEN);
347 	}
348 
349 	return NULL;
350 }
351 
352 /* Is any of the tlvs the expected entry? If
353  * not update the tlvs buffer pointer/length.
354  */
355 static bool
356 brcmf_tlv_has_ie(const u8 *ie, const u8 **tlvs, u32 *tlvs_len,
357 		 const u8 *oui, u32 oui_len, u8 type)
358 {
359 	/* If the contents match the OUI and the type */
360 	if (ie[TLV_LEN_OFF] >= oui_len + 1 &&
361 	    !memcmp(&ie[TLV_BODY_OFF], oui, oui_len) &&
362 	    type == ie[TLV_BODY_OFF + oui_len]) {
363 		return true;
364 	}
365 
366 	if (tlvs == NULL)
367 		return false;
368 	/* point to the next ie */
369 	ie += ie[TLV_LEN_OFF] + TLV_HDR_LEN;
370 	/* calculate the length of the rest of the buffer */
371 	*tlvs_len -= (int)(ie - *tlvs);
372 	/* update the pointer to the start of the buffer */
373 	*tlvs = ie;
374 
375 	return false;
376 }
377 
378 static struct brcmf_vs_tlv *
379 brcmf_find_wpaie(const u8 *parse, u32 len)
380 {
381 	const struct brcmf_tlv *ie;
382 
383 	while ((ie = brcmf_parse_tlvs(parse, len, WLAN_EID_VENDOR_SPECIFIC))) {
384 		if (brcmf_tlv_has_ie((const u8 *)ie, &parse, &len,
385 				     WPA_OUI, TLV_OUI_LEN, WPA_OUI_TYPE))
386 			return (struct brcmf_vs_tlv *)ie;
387 	}
388 	return NULL;
389 }
390 
391 static struct brcmf_vs_tlv *
392 brcmf_find_wpsie(const u8 *parse, u32 len)
393 {
394 	const struct brcmf_tlv *ie;
395 
396 	while ((ie = brcmf_parse_tlvs(parse, len, WLAN_EID_VENDOR_SPECIFIC))) {
397 		if (brcmf_tlv_has_ie((u8 *)ie, &parse, &len,
398 				     WPA_OUI, TLV_OUI_LEN, WPS_OUI_TYPE))
399 			return (struct brcmf_vs_tlv *)ie;
400 	}
401 	return NULL;
402 }
403 
404 static int brcmf_vif_change_validate(struct brcmf_cfg80211_info *cfg,
405 				     struct brcmf_cfg80211_vif *vif,
406 				     enum nl80211_iftype new_type)
407 {
408 	struct brcmf_cfg80211_vif *pos;
409 	bool check_combos = false;
410 	int ret = 0;
411 	struct iface_combination_params params = {
412 		.num_different_channels = 1,
413 	};
414 
415 	list_for_each_entry(pos, &cfg->vif_list, list)
416 		if (pos == vif) {
417 			params.iftype_num[new_type]++;
418 		} else {
419 			/* concurrent interfaces so need check combinations */
420 			check_combos = true;
421 			params.iftype_num[pos->wdev.iftype]++;
422 		}
423 
424 	if (check_combos)
425 		ret = cfg80211_check_combinations(cfg->wiphy, &params);
426 
427 	return ret;
428 }
429 
430 static int brcmf_vif_add_validate(struct brcmf_cfg80211_info *cfg,
431 				  enum nl80211_iftype new_type)
432 {
433 	struct brcmf_cfg80211_vif *pos;
434 	struct iface_combination_params params = {
435 		.num_different_channels = 1,
436 	};
437 
438 	list_for_each_entry(pos, &cfg->vif_list, list)
439 		params.iftype_num[pos->wdev.iftype]++;
440 
441 	params.iftype_num[new_type]++;
442 	return cfg80211_check_combinations(cfg->wiphy, &params);
443 }
444 
445 static void convert_key_from_CPU(struct brcmf_wsec_key *key,
446 				 struct brcmf_wsec_key_le *key_le)
447 {
448 	key_le->index = cpu_to_le32(key->index);
449 	key_le->len = cpu_to_le32(key->len);
450 	key_le->algo = cpu_to_le32(key->algo);
451 	key_le->flags = cpu_to_le32(key->flags);
452 	key_le->rxiv.hi = cpu_to_le32(key->rxiv.hi);
453 	key_le->rxiv.lo = cpu_to_le16(key->rxiv.lo);
454 	key_le->iv_initialized = cpu_to_le32(key->iv_initialized);
455 	memcpy(key_le->data, key->data, sizeof(key->data));
456 	memcpy(key_le->ea, key->ea, sizeof(key->ea));
457 }
458 
459 static int
460 send_key_to_dongle(struct brcmf_if *ifp, struct brcmf_wsec_key *key)
461 {
462 	int err;
463 	struct brcmf_wsec_key_le key_le;
464 
465 	convert_key_from_CPU(key, &key_le);
466 
467 	brcmf_netdev_wait_pend8021x(ifp);
468 
469 	err = brcmf_fil_bsscfg_data_set(ifp, "wsec_key", &key_le,
470 					sizeof(key_le));
471 
472 	if (err)
473 		brcmf_err("wsec_key error (%d)\n", err);
474 	return err;
475 }
476 
477 static s32
478 brcmf_configure_arp_nd_offload(struct brcmf_if *ifp, bool enable)
479 {
480 	s32 err;
481 	u32 mode;
482 
483 	if (enable)
484 		mode = BRCMF_ARP_OL_AGENT | BRCMF_ARP_OL_PEER_AUTO_REPLY;
485 	else
486 		mode = 0;
487 
488 	/* Try to set and enable ARP offload feature, this may fail, then it  */
489 	/* is simply not supported and err 0 will be returned                 */
490 	err = brcmf_fil_iovar_int_set(ifp, "arp_ol", mode);
491 	if (err) {
492 		brcmf_dbg(TRACE, "failed to set ARP offload mode to 0x%x, err = %d\n",
493 			  mode, err);
494 		err = 0;
495 	} else {
496 		err = brcmf_fil_iovar_int_set(ifp, "arpoe", enable);
497 		if (err) {
498 			brcmf_dbg(TRACE, "failed to configure (%d) ARP offload err = %d\n",
499 				  enable, err);
500 			err = 0;
501 		} else
502 			brcmf_dbg(TRACE, "successfully configured (%d) ARP offload to 0x%x\n",
503 				  enable, mode);
504 	}
505 
506 	err = brcmf_fil_iovar_int_set(ifp, "ndoe", enable);
507 	if (err) {
508 		brcmf_dbg(TRACE, "failed to configure (%d) ND offload err = %d\n",
509 			  enable, err);
510 		err = 0;
511 	} else
512 		brcmf_dbg(TRACE, "successfully configured (%d) ND offload to 0x%x\n",
513 			  enable, mode);
514 
515 	return err;
516 }
517 
518 static void
519 brcmf_cfg80211_update_proto_addr_mode(struct wireless_dev *wdev)
520 {
521 	struct brcmf_cfg80211_vif *vif;
522 	struct brcmf_if *ifp;
523 
524 	vif = container_of(wdev, struct brcmf_cfg80211_vif, wdev);
525 	ifp = vif->ifp;
526 
527 	if ((wdev->iftype == NL80211_IFTYPE_ADHOC) ||
528 	    (wdev->iftype == NL80211_IFTYPE_AP) ||
529 	    (wdev->iftype == NL80211_IFTYPE_P2P_GO))
530 		brcmf_proto_configure_addr_mode(ifp->drvr, ifp->ifidx,
531 						ADDR_DIRECT);
532 	else
533 		brcmf_proto_configure_addr_mode(ifp->drvr, ifp->ifidx,
534 						ADDR_INDIRECT);
535 }
536 
537 static int brcmf_get_first_free_bsscfgidx(struct brcmf_pub *drvr)
538 {
539 	int bsscfgidx;
540 
541 	for (bsscfgidx = 0; bsscfgidx < BRCMF_MAX_IFS; bsscfgidx++) {
542 		/* bsscfgidx 1 is reserved for legacy P2P */
543 		if (bsscfgidx == 1)
544 			continue;
545 		if (!drvr->iflist[bsscfgidx])
546 			return bsscfgidx;
547 	}
548 
549 	return -ENOMEM;
550 }
551 
552 static int brcmf_cfg80211_request_ap_if(struct brcmf_if *ifp)
553 {
554 	struct brcmf_mbss_ssid_le mbss_ssid_le;
555 	int bsscfgidx;
556 	int err;
557 
558 	memset(&mbss_ssid_le, 0, sizeof(mbss_ssid_le));
559 	bsscfgidx = brcmf_get_first_free_bsscfgidx(ifp->drvr);
560 	if (bsscfgidx < 0)
561 		return bsscfgidx;
562 
563 	mbss_ssid_le.bsscfgidx = cpu_to_le32(bsscfgidx);
564 	mbss_ssid_le.SSID_len = cpu_to_le32(5);
565 	sprintf(mbss_ssid_le.SSID, "ssid%d" , bsscfgidx);
566 
567 	err = brcmf_fil_bsscfg_data_set(ifp, "bsscfg:ssid", &mbss_ssid_le,
568 					sizeof(mbss_ssid_le));
569 	if (err < 0)
570 		brcmf_err("setting ssid failed %d\n", err);
571 
572 	return err;
573 }
574 
575 /**
576  * brcmf_ap_add_vif() - create a new AP virtual interface for multiple BSS
577  *
578  * @wiphy: wiphy device of new interface.
579  * @name: name of the new interface.
580  * @flags: not used.
581  * @params: contains mac address for AP device.
582  */
583 static
584 struct wireless_dev *brcmf_ap_add_vif(struct wiphy *wiphy, const char *name,
585 				      u32 *flags, struct vif_params *params)
586 {
587 	struct brcmf_cfg80211_info *cfg = wiphy_to_cfg(wiphy);
588 	struct brcmf_if *ifp = netdev_priv(cfg_to_ndev(cfg));
589 	struct brcmf_cfg80211_vif *vif;
590 	int err;
591 
592 	if (brcmf_cfg80211_vif_event_armed(cfg))
593 		return ERR_PTR(-EBUSY);
594 
595 	brcmf_dbg(INFO, "Adding vif \"%s\"\n", name);
596 
597 	vif = brcmf_alloc_vif(cfg, NL80211_IFTYPE_AP);
598 	if (IS_ERR(vif))
599 		return (struct wireless_dev *)vif;
600 
601 	brcmf_cfg80211_arm_vif_event(cfg, vif);
602 
603 	err = brcmf_cfg80211_request_ap_if(ifp);
604 	if (err) {
605 		brcmf_cfg80211_arm_vif_event(cfg, NULL);
606 		goto fail;
607 	}
608 
609 	/* wait for firmware event */
610 	err = brcmf_cfg80211_wait_vif_event(cfg, BRCMF_E_IF_ADD,
611 					    BRCMF_VIF_EVENT_TIMEOUT);
612 	brcmf_cfg80211_arm_vif_event(cfg, NULL);
613 	if (!err) {
614 		brcmf_err("timeout occurred\n");
615 		err = -EIO;
616 		goto fail;
617 	}
618 
619 	/* interface created in firmware */
620 	ifp = vif->ifp;
621 	if (!ifp) {
622 		brcmf_err("no if pointer provided\n");
623 		err = -ENOENT;
624 		goto fail;
625 	}
626 
627 	strncpy(ifp->ndev->name, name, sizeof(ifp->ndev->name) - 1);
628 	err = brcmf_net_attach(ifp, true);
629 	if (err) {
630 		brcmf_err("Registering netdevice failed\n");
631 		goto fail;
632 	}
633 
634 	return &ifp->vif->wdev;
635 
636 fail:
637 	brcmf_free_vif(vif);
638 	return ERR_PTR(err);
639 }
640 
641 static bool brcmf_is_apmode(struct brcmf_cfg80211_vif *vif)
642 {
643 	enum nl80211_iftype iftype;
644 
645 	iftype = vif->wdev.iftype;
646 	return iftype == NL80211_IFTYPE_AP || iftype == NL80211_IFTYPE_P2P_GO;
647 }
648 
649 static bool brcmf_is_ibssmode(struct brcmf_cfg80211_vif *vif)
650 {
651 	return vif->wdev.iftype == NL80211_IFTYPE_ADHOC;
652 }
653 
654 static struct wireless_dev *brcmf_cfg80211_add_iface(struct wiphy *wiphy,
655 						     const char *name,
656 						     unsigned char name_assign_type,
657 						     enum nl80211_iftype type,
658 						     u32 *flags,
659 						     struct vif_params *params)
660 {
661 	struct wireless_dev *wdev;
662 	int err;
663 
664 	brcmf_dbg(TRACE, "enter: %s type %d\n", name, type);
665 	err = brcmf_vif_add_validate(wiphy_to_cfg(wiphy), type);
666 	if (err) {
667 		brcmf_err("iface validation failed: err=%d\n", err);
668 		return ERR_PTR(err);
669 	}
670 	switch (type) {
671 	case NL80211_IFTYPE_ADHOC:
672 	case NL80211_IFTYPE_STATION:
673 	case NL80211_IFTYPE_AP_VLAN:
674 	case NL80211_IFTYPE_WDS:
675 	case NL80211_IFTYPE_MONITOR:
676 	case NL80211_IFTYPE_MESH_POINT:
677 		return ERR_PTR(-EOPNOTSUPP);
678 	case NL80211_IFTYPE_AP:
679 		wdev = brcmf_ap_add_vif(wiphy, name, flags, params);
680 		break;
681 	case NL80211_IFTYPE_P2P_CLIENT:
682 	case NL80211_IFTYPE_P2P_GO:
683 	case NL80211_IFTYPE_P2P_DEVICE:
684 		wdev = brcmf_p2p_add_vif(wiphy, name, name_assign_type, type, flags, params);
685 		break;
686 	case NL80211_IFTYPE_UNSPECIFIED:
687 	default:
688 		return ERR_PTR(-EINVAL);
689 	}
690 
691 	if (IS_ERR(wdev))
692 		brcmf_err("add iface %s type %d failed: err=%d\n",
693 			  name, type, (int)PTR_ERR(wdev));
694 	else
695 		brcmf_cfg80211_update_proto_addr_mode(wdev);
696 
697 	return wdev;
698 }
699 
700 static void brcmf_scan_config_mpc(struct brcmf_if *ifp, int mpc)
701 {
702 	if (brcmf_feat_is_quirk_enabled(ifp, BRCMF_FEAT_QUIRK_NEED_MPC))
703 		brcmf_set_mpc(ifp, mpc);
704 }
705 
706 void brcmf_set_mpc(struct brcmf_if *ifp, int mpc)
707 {
708 	s32 err = 0;
709 
710 	if (check_vif_up(ifp->vif)) {
711 		err = brcmf_fil_iovar_int_set(ifp, "mpc", mpc);
712 		if (err) {
713 			brcmf_err("fail to set mpc\n");
714 			return;
715 		}
716 		brcmf_dbg(INFO, "MPC : %d\n", mpc);
717 	}
718 }
719 
720 s32 brcmf_notify_escan_complete(struct brcmf_cfg80211_info *cfg,
721 				struct brcmf_if *ifp, bool aborted,
722 				bool fw_abort)
723 {
724 	struct brcmf_scan_params_le params_le;
725 	struct cfg80211_scan_request *scan_request;
726 	s32 err = 0;
727 
728 	brcmf_dbg(SCAN, "Enter\n");
729 
730 	/* clear scan request, because the FW abort can cause a second call */
731 	/* to this functon and might cause a double cfg80211_scan_done      */
732 	scan_request = cfg->scan_request;
733 	cfg->scan_request = NULL;
734 
735 	if (timer_pending(&cfg->escan_timeout))
736 		del_timer_sync(&cfg->escan_timeout);
737 
738 	if (fw_abort) {
739 		/* Do a scan abort to stop the driver's scan engine */
740 		brcmf_dbg(SCAN, "ABORT scan in firmware\n");
741 		memset(&params_le, 0, sizeof(params_le));
742 		eth_broadcast_addr(params_le.bssid);
743 		params_le.bss_type = DOT11_BSSTYPE_ANY;
744 		params_le.scan_type = 0;
745 		params_le.channel_num = cpu_to_le32(1);
746 		params_le.nprobes = cpu_to_le32(1);
747 		params_le.active_time = cpu_to_le32(-1);
748 		params_le.passive_time = cpu_to_le32(-1);
749 		params_le.home_time = cpu_to_le32(-1);
750 		/* Scan is aborted by setting channel_list[0] to -1 */
751 		params_le.channel_list[0] = cpu_to_le16(-1);
752 		/* E-Scan (or anyother type) can be aborted by SCAN */
753 		err = brcmf_fil_cmd_data_set(ifp, BRCMF_C_SCAN,
754 					     &params_le, sizeof(params_le));
755 		if (err)
756 			brcmf_err("Scan abort  failed\n");
757 	}
758 
759 	brcmf_scan_config_mpc(ifp, 1);
760 
761 	/*
762 	 * e-scan can be initiated internally
763 	 * which takes precedence.
764 	 */
765 	if (cfg->internal_escan) {
766 		brcmf_dbg(SCAN, "scheduled scan completed\n");
767 		cfg->internal_escan = false;
768 		if (!aborted)
769 			cfg80211_sched_scan_results(cfg_to_wiphy(cfg));
770 	} else if (scan_request) {
771 		struct cfg80211_scan_info info = {
772 			.aborted = aborted,
773 		};
774 
775 		brcmf_dbg(SCAN, "ESCAN Completed scan: %s\n",
776 			  aborted ? "Aborted" : "Done");
777 		cfg80211_scan_done(scan_request, &info);
778 	}
779 	if (!test_and_clear_bit(BRCMF_SCAN_STATUS_BUSY, &cfg->scan_status))
780 		brcmf_dbg(SCAN, "Scan complete, probably P2P scan\n");
781 
782 	return err;
783 }
784 
785 static int brcmf_cfg80211_del_ap_iface(struct wiphy *wiphy,
786 				       struct wireless_dev *wdev)
787 {
788 	struct brcmf_cfg80211_info *cfg = wiphy_priv(wiphy);
789 	struct net_device *ndev = wdev->netdev;
790 	struct brcmf_if *ifp = netdev_priv(ndev);
791 	int ret;
792 	int err;
793 
794 	brcmf_cfg80211_arm_vif_event(cfg, ifp->vif);
795 
796 	err = brcmf_fil_bsscfg_data_set(ifp, "interface_remove", NULL, 0);
797 	if (err) {
798 		brcmf_err("interface_remove failed %d\n", err);
799 		goto err_unarm;
800 	}
801 
802 	/* wait for firmware event */
803 	ret = brcmf_cfg80211_wait_vif_event(cfg, BRCMF_E_IF_DEL,
804 					    BRCMF_VIF_EVENT_TIMEOUT);
805 	if (!ret) {
806 		brcmf_err("timeout occurred\n");
807 		err = -EIO;
808 		goto err_unarm;
809 	}
810 
811 	brcmf_remove_interface(ifp, true);
812 
813 err_unarm:
814 	brcmf_cfg80211_arm_vif_event(cfg, NULL);
815 	return err;
816 }
817 
818 static
819 int brcmf_cfg80211_del_iface(struct wiphy *wiphy, struct wireless_dev *wdev)
820 {
821 	struct brcmf_cfg80211_info *cfg = wiphy_priv(wiphy);
822 	struct net_device *ndev = wdev->netdev;
823 
824 	if (ndev && ndev == cfg_to_ndev(cfg))
825 		return -ENOTSUPP;
826 
827 	/* vif event pending in firmware */
828 	if (brcmf_cfg80211_vif_event_armed(cfg))
829 		return -EBUSY;
830 
831 	if (ndev) {
832 		if (test_bit(BRCMF_SCAN_STATUS_BUSY, &cfg->scan_status) &&
833 		    cfg->escan_info.ifp == netdev_priv(ndev))
834 			brcmf_notify_escan_complete(cfg, netdev_priv(ndev),
835 						    true, true);
836 
837 		brcmf_fil_iovar_int_set(netdev_priv(ndev), "mpc", 1);
838 	}
839 
840 	switch (wdev->iftype) {
841 	case NL80211_IFTYPE_ADHOC:
842 	case NL80211_IFTYPE_STATION:
843 	case NL80211_IFTYPE_AP_VLAN:
844 	case NL80211_IFTYPE_WDS:
845 	case NL80211_IFTYPE_MONITOR:
846 	case NL80211_IFTYPE_MESH_POINT:
847 		return -EOPNOTSUPP;
848 	case NL80211_IFTYPE_AP:
849 		return brcmf_cfg80211_del_ap_iface(wiphy, wdev);
850 	case NL80211_IFTYPE_P2P_CLIENT:
851 	case NL80211_IFTYPE_P2P_GO:
852 	case NL80211_IFTYPE_P2P_DEVICE:
853 		return brcmf_p2p_del_vif(wiphy, wdev);
854 	case NL80211_IFTYPE_UNSPECIFIED:
855 	default:
856 		return -EINVAL;
857 	}
858 	return -EOPNOTSUPP;
859 }
860 
861 static s32
862 brcmf_cfg80211_change_iface(struct wiphy *wiphy, struct net_device *ndev,
863 			 enum nl80211_iftype type, u32 *flags,
864 			 struct vif_params *params)
865 {
866 	struct brcmf_cfg80211_info *cfg = wiphy_priv(wiphy);
867 	struct brcmf_if *ifp = netdev_priv(ndev);
868 	struct brcmf_cfg80211_vif *vif = ifp->vif;
869 	s32 infra = 0;
870 	s32 ap = 0;
871 	s32 err = 0;
872 
873 	brcmf_dbg(TRACE, "Enter, bsscfgidx=%d, type=%d\n", ifp->bsscfgidx,
874 		  type);
875 
876 	/* WAR: There are a number of p2p interface related problems which
877 	 * need to be handled initially (before doing the validate).
878 	 * wpa_supplicant tends to do iface changes on p2p device/client/go
879 	 * which are not always possible/allowed. However we need to return
880 	 * OK otherwise the wpa_supplicant wont start. The situation differs
881 	 * on configuration and setup (p2pon=1 module param). The first check
882 	 * is to see if the request is a change to station for p2p iface.
883 	 */
884 	if ((type == NL80211_IFTYPE_STATION) &&
885 	    ((vif->wdev.iftype == NL80211_IFTYPE_P2P_CLIENT) ||
886 	     (vif->wdev.iftype == NL80211_IFTYPE_P2P_GO) ||
887 	     (vif->wdev.iftype == NL80211_IFTYPE_P2P_DEVICE))) {
888 		brcmf_dbg(TRACE, "Ignoring cmd for p2p if\n");
889 		/* Now depending on whether module param p2pon=1 was used the
890 		 * response needs to be either 0 or EOPNOTSUPP. The reason is
891 		 * that if p2pon=1 is used, but a newer supplicant is used then
892 		 * we should return an error, as this combination wont work.
893 		 * In other situations 0 is returned and supplicant will start
894 		 * normally. It will give a trace in cfg80211, but it is the
895 		 * only way to get it working. Unfortunately this will result
896 		 * in situation where we wont support new supplicant in
897 		 * combination with module param p2pon=1, but that is the way
898 		 * it is. If the user tries this then unloading of driver might
899 		 * fail/lock.
900 		 */
901 		if (cfg->p2p.p2pdev_dynamically)
902 			return -EOPNOTSUPP;
903 		else
904 			return 0;
905 	}
906 	err = brcmf_vif_change_validate(wiphy_to_cfg(wiphy), vif, type);
907 	if (err) {
908 		brcmf_err("iface validation failed: err=%d\n", err);
909 		return err;
910 	}
911 	switch (type) {
912 	case NL80211_IFTYPE_MONITOR:
913 	case NL80211_IFTYPE_WDS:
914 		brcmf_err("type (%d) : currently we do not support this type\n",
915 			  type);
916 		return -EOPNOTSUPP;
917 	case NL80211_IFTYPE_ADHOC:
918 		infra = 0;
919 		break;
920 	case NL80211_IFTYPE_STATION:
921 		infra = 1;
922 		break;
923 	case NL80211_IFTYPE_AP:
924 	case NL80211_IFTYPE_P2P_GO:
925 		ap = 1;
926 		break;
927 	default:
928 		err = -EINVAL;
929 		goto done;
930 	}
931 
932 	if (ap) {
933 		if (type == NL80211_IFTYPE_P2P_GO) {
934 			brcmf_dbg(INFO, "IF Type = P2P GO\n");
935 			err = brcmf_p2p_ifchange(cfg, BRCMF_FIL_P2P_IF_GO);
936 		}
937 		if (!err) {
938 			brcmf_dbg(INFO, "IF Type = AP\n");
939 		}
940 	} else {
941 		err = brcmf_fil_cmd_int_set(ifp, BRCMF_C_SET_INFRA, infra);
942 		if (err) {
943 			brcmf_err("WLC_SET_INFRA error (%d)\n", err);
944 			err = -EAGAIN;
945 			goto done;
946 		}
947 		brcmf_dbg(INFO, "IF Type = %s\n", brcmf_is_ibssmode(vif) ?
948 			  "Adhoc" : "Infra");
949 	}
950 	ndev->ieee80211_ptr->iftype = type;
951 
952 	brcmf_cfg80211_update_proto_addr_mode(&vif->wdev);
953 
954 done:
955 	brcmf_dbg(TRACE, "Exit\n");
956 
957 	return err;
958 }
959 
960 static void brcmf_escan_prep(struct brcmf_cfg80211_info *cfg,
961 			     struct brcmf_scan_params_le *params_le,
962 			     struct cfg80211_scan_request *request)
963 {
964 	u32 n_ssids;
965 	u32 n_channels;
966 	s32 i;
967 	s32 offset;
968 	u16 chanspec;
969 	char *ptr;
970 	struct brcmf_ssid_le ssid_le;
971 
972 	eth_broadcast_addr(params_le->bssid);
973 	params_le->bss_type = DOT11_BSSTYPE_ANY;
974 	params_le->scan_type = 0;
975 	params_le->channel_num = 0;
976 	params_le->nprobes = cpu_to_le32(-1);
977 	params_le->active_time = cpu_to_le32(-1);
978 	params_le->passive_time = cpu_to_le32(-1);
979 	params_le->home_time = cpu_to_le32(-1);
980 	memset(&params_le->ssid_le, 0, sizeof(params_le->ssid_le));
981 
982 	/* if request is null exit so it will be all channel broadcast scan */
983 	if (!request)
984 		return;
985 
986 	n_ssids = request->n_ssids;
987 	n_channels = request->n_channels;
988 	/* Copy channel array if applicable */
989 	brcmf_dbg(SCAN, "### List of channelspecs to scan ### %d\n",
990 		  n_channels);
991 	if (n_channels > 0) {
992 		for (i = 0; i < n_channels; i++) {
993 			chanspec = channel_to_chanspec(&cfg->d11inf,
994 						       request->channels[i]);
995 			brcmf_dbg(SCAN, "Chan : %d, Channel spec: %x\n",
996 				  request->channels[i]->hw_value, chanspec);
997 			params_le->channel_list[i] = cpu_to_le16(chanspec);
998 		}
999 	} else {
1000 		brcmf_dbg(SCAN, "Scanning all channels\n");
1001 	}
1002 	/* Copy ssid array if applicable */
1003 	brcmf_dbg(SCAN, "### List of SSIDs to scan ### %d\n", n_ssids);
1004 	if (n_ssids > 0) {
1005 		offset = offsetof(struct brcmf_scan_params_le, channel_list) +
1006 				n_channels * sizeof(u16);
1007 		offset = roundup(offset, sizeof(u32));
1008 		ptr = (char *)params_le + offset;
1009 		for (i = 0; i < n_ssids; i++) {
1010 			memset(&ssid_le, 0, sizeof(ssid_le));
1011 			ssid_le.SSID_len =
1012 					cpu_to_le32(request->ssids[i].ssid_len);
1013 			memcpy(ssid_le.SSID, request->ssids[i].ssid,
1014 			       request->ssids[i].ssid_len);
1015 			if (!ssid_le.SSID_len)
1016 				brcmf_dbg(SCAN, "%d: Broadcast scan\n", i);
1017 			else
1018 				brcmf_dbg(SCAN, "%d: scan for  %s size =%d\n",
1019 					  i, ssid_le.SSID, ssid_le.SSID_len);
1020 			memcpy(ptr, &ssid_le, sizeof(ssid_le));
1021 			ptr += sizeof(ssid_le);
1022 		}
1023 	} else {
1024 		brcmf_dbg(SCAN, "Broadcast scan %p\n", request->ssids);
1025 		if ((request->ssids) && request->ssids->ssid_len) {
1026 			brcmf_dbg(SCAN, "SSID %s len=%d\n",
1027 				  params_le->ssid_le.SSID,
1028 				  request->ssids->ssid_len);
1029 			params_le->ssid_le.SSID_len =
1030 				cpu_to_le32(request->ssids->ssid_len);
1031 			memcpy(&params_le->ssid_le.SSID, request->ssids->ssid,
1032 				request->ssids->ssid_len);
1033 		}
1034 	}
1035 	/* Adding mask to channel numbers */
1036 	params_le->channel_num =
1037 		cpu_to_le32((n_ssids << BRCMF_SCAN_PARAMS_NSSID_SHIFT) |
1038 			(n_channels & BRCMF_SCAN_PARAMS_COUNT_MASK));
1039 }
1040 
1041 static s32
1042 brcmf_run_escan(struct brcmf_cfg80211_info *cfg, struct brcmf_if *ifp,
1043 		struct cfg80211_scan_request *request)
1044 {
1045 	s32 params_size = BRCMF_SCAN_PARAMS_FIXED_SIZE +
1046 			  offsetof(struct brcmf_escan_params_le, params_le);
1047 	struct brcmf_escan_params_le *params;
1048 	s32 err = 0;
1049 
1050 	brcmf_dbg(SCAN, "E-SCAN START\n");
1051 
1052 	if (request != NULL) {
1053 		/* Allocate space for populating ssids in struct */
1054 		params_size += sizeof(u32) * ((request->n_channels + 1) / 2);
1055 
1056 		/* Allocate space for populating ssids in struct */
1057 		params_size += sizeof(struct brcmf_ssid_le) * request->n_ssids;
1058 	}
1059 
1060 	params = kzalloc(params_size, GFP_KERNEL);
1061 	if (!params) {
1062 		err = -ENOMEM;
1063 		goto exit;
1064 	}
1065 	BUG_ON(params_size + sizeof("escan") >= BRCMF_DCMD_MEDLEN);
1066 	brcmf_escan_prep(cfg, &params->params_le, request);
1067 	params->version = cpu_to_le32(BRCMF_ESCAN_REQ_VERSION);
1068 	params->action = cpu_to_le16(WL_ESCAN_ACTION_START);
1069 	params->sync_id = cpu_to_le16(0x1234);
1070 
1071 	err = brcmf_fil_iovar_data_set(ifp, "escan", params, params_size);
1072 	if (err) {
1073 		if (err == -EBUSY)
1074 			brcmf_dbg(INFO, "system busy : escan canceled\n");
1075 		else
1076 			brcmf_err("error (%d)\n", err);
1077 	}
1078 
1079 	kfree(params);
1080 exit:
1081 	return err;
1082 }
1083 
1084 static s32
1085 brcmf_do_escan(struct brcmf_if *ifp, struct cfg80211_scan_request *request)
1086 {
1087 	struct brcmf_cfg80211_info *cfg = ifp->drvr->config;
1088 	s32 err;
1089 	u32 passive_scan;
1090 	struct brcmf_scan_results *results;
1091 	struct escan_info *escan = &cfg->escan_info;
1092 
1093 	brcmf_dbg(SCAN, "Enter\n");
1094 	escan->ifp = ifp;
1095 	escan->wiphy = cfg->wiphy;
1096 	escan->escan_state = WL_ESCAN_STATE_SCANNING;
1097 	passive_scan = cfg->active_scan ? 0 : 1;
1098 	err = brcmf_fil_cmd_int_set(ifp, BRCMF_C_SET_PASSIVE_SCAN,
1099 				    passive_scan);
1100 	if (err) {
1101 		brcmf_err("error (%d)\n", err);
1102 		return err;
1103 	}
1104 	brcmf_scan_config_mpc(ifp, 0);
1105 	results = (struct brcmf_scan_results *)cfg->escan_info.escan_buf;
1106 	results->version = 0;
1107 	results->count = 0;
1108 	results->buflen = WL_ESCAN_RESULTS_FIXED_SIZE;
1109 
1110 	err = escan->run(cfg, ifp, request);
1111 	if (err)
1112 		brcmf_scan_config_mpc(ifp, 1);
1113 	return err;
1114 }
1115 
1116 static s32
1117 brcmf_cfg80211_escan(struct wiphy *wiphy, struct brcmf_cfg80211_vif *vif,
1118 		     struct cfg80211_scan_request *request,
1119 		     struct cfg80211_ssid *this_ssid)
1120 {
1121 	struct brcmf_if *ifp = vif->ifp;
1122 	struct brcmf_cfg80211_info *cfg = wiphy_to_cfg(wiphy);
1123 	struct cfg80211_ssid *ssids;
1124 	u32 passive_scan;
1125 	bool escan_req;
1126 	bool spec_scan;
1127 	s32 err;
1128 	struct brcmf_ssid_le ssid_le;
1129 	u32 SSID_len;
1130 
1131 	brcmf_dbg(SCAN, "START ESCAN\n");
1132 
1133 	if (test_bit(BRCMF_SCAN_STATUS_BUSY, &cfg->scan_status)) {
1134 		brcmf_err("Scanning already: status (%lu)\n", cfg->scan_status);
1135 		return -EAGAIN;
1136 	}
1137 	if (test_bit(BRCMF_SCAN_STATUS_ABORT, &cfg->scan_status)) {
1138 		brcmf_err("Scanning being aborted: status (%lu)\n",
1139 			  cfg->scan_status);
1140 		return -EAGAIN;
1141 	}
1142 	if (test_bit(BRCMF_SCAN_STATUS_SUPPRESS, &cfg->scan_status)) {
1143 		brcmf_err("Scanning suppressed: status (%lu)\n",
1144 			  cfg->scan_status);
1145 		return -EAGAIN;
1146 	}
1147 	if (test_bit(BRCMF_VIF_STATUS_CONNECTING, &ifp->vif->sme_state)) {
1148 		brcmf_err("Connecting: status (%lu)\n", ifp->vif->sme_state);
1149 		return -EAGAIN;
1150 	}
1151 
1152 	/* If scan req comes for p2p0, send it over primary I/F */
1153 	if (vif == cfg->p2p.bss_idx[P2PAPI_BSSCFG_DEVICE].vif)
1154 		vif = cfg->p2p.bss_idx[P2PAPI_BSSCFG_PRIMARY].vif;
1155 
1156 	escan_req = false;
1157 	if (request) {
1158 		/* scan bss */
1159 		ssids = request->ssids;
1160 		escan_req = true;
1161 	} else {
1162 		/* scan in ibss */
1163 		/* we don't do escan in ibss */
1164 		ssids = this_ssid;
1165 	}
1166 
1167 	cfg->scan_request = request;
1168 	set_bit(BRCMF_SCAN_STATUS_BUSY, &cfg->scan_status);
1169 	if (escan_req) {
1170 		cfg->escan_info.run = brcmf_run_escan;
1171 		err = brcmf_p2p_scan_prep(wiphy, request, vif);
1172 		if (err)
1173 			goto scan_out;
1174 
1175 		err = brcmf_do_escan(vif->ifp, request);
1176 		if (err)
1177 			goto scan_out;
1178 	} else {
1179 		brcmf_dbg(SCAN, "ssid \"%s\", ssid_len (%d)\n",
1180 			  ssids->ssid, ssids->ssid_len);
1181 		memset(&ssid_le, 0, sizeof(ssid_le));
1182 		SSID_len = min_t(u8, sizeof(ssid_le.SSID), ssids->ssid_len);
1183 		ssid_le.SSID_len = cpu_to_le32(0);
1184 		spec_scan = false;
1185 		if (SSID_len) {
1186 			memcpy(ssid_le.SSID, ssids->ssid, SSID_len);
1187 			ssid_le.SSID_len = cpu_to_le32(SSID_len);
1188 			spec_scan = true;
1189 		} else
1190 			brcmf_dbg(SCAN, "Broadcast scan\n");
1191 
1192 		passive_scan = cfg->active_scan ? 0 : 1;
1193 		err = brcmf_fil_cmd_int_set(ifp, BRCMF_C_SET_PASSIVE_SCAN,
1194 					    passive_scan);
1195 		if (err) {
1196 			brcmf_err("WLC_SET_PASSIVE_SCAN error (%d)\n", err);
1197 			goto scan_out;
1198 		}
1199 		brcmf_scan_config_mpc(ifp, 0);
1200 		err = brcmf_fil_cmd_data_set(ifp, BRCMF_C_SCAN, &ssid_le,
1201 					     sizeof(ssid_le));
1202 		if (err) {
1203 			if (err == -EBUSY)
1204 				brcmf_dbg(INFO, "BUSY: scan for \"%s\" canceled\n",
1205 					  ssid_le.SSID);
1206 			else
1207 				brcmf_err("WLC_SCAN error (%d)\n", err);
1208 
1209 			brcmf_scan_config_mpc(ifp, 1);
1210 			goto scan_out;
1211 		}
1212 	}
1213 
1214 	/* Arm scan timeout timer */
1215 	mod_timer(&cfg->escan_timeout, jiffies +
1216 			BRCMF_ESCAN_TIMER_INTERVAL_MS * HZ / 1000);
1217 
1218 	return 0;
1219 
1220 scan_out:
1221 	clear_bit(BRCMF_SCAN_STATUS_BUSY, &cfg->scan_status);
1222 	cfg->scan_request = NULL;
1223 	return err;
1224 }
1225 
1226 static s32
1227 brcmf_cfg80211_scan(struct wiphy *wiphy, struct cfg80211_scan_request *request)
1228 {
1229 	struct brcmf_cfg80211_vif *vif;
1230 	s32 err = 0;
1231 
1232 	brcmf_dbg(TRACE, "Enter\n");
1233 	vif = container_of(request->wdev, struct brcmf_cfg80211_vif, wdev);
1234 	if (!check_vif_up(vif))
1235 		return -EIO;
1236 
1237 	err = brcmf_cfg80211_escan(wiphy, vif, request, NULL);
1238 
1239 	if (err)
1240 		brcmf_err("scan error (%d)\n", err);
1241 
1242 	brcmf_dbg(TRACE, "Exit\n");
1243 	return err;
1244 }
1245 
1246 static s32 brcmf_set_rts(struct net_device *ndev, u32 rts_threshold)
1247 {
1248 	s32 err = 0;
1249 
1250 	err = brcmf_fil_iovar_int_set(netdev_priv(ndev), "rtsthresh",
1251 				      rts_threshold);
1252 	if (err)
1253 		brcmf_err("Error (%d)\n", err);
1254 
1255 	return err;
1256 }
1257 
1258 static s32 brcmf_set_frag(struct net_device *ndev, u32 frag_threshold)
1259 {
1260 	s32 err = 0;
1261 
1262 	err = brcmf_fil_iovar_int_set(netdev_priv(ndev), "fragthresh",
1263 				      frag_threshold);
1264 	if (err)
1265 		brcmf_err("Error (%d)\n", err);
1266 
1267 	return err;
1268 }
1269 
1270 static s32 brcmf_set_retry(struct net_device *ndev, u32 retry, bool l)
1271 {
1272 	s32 err = 0;
1273 	u32 cmd = (l ? BRCMF_C_SET_LRL : BRCMF_C_SET_SRL);
1274 
1275 	err = brcmf_fil_cmd_int_set(netdev_priv(ndev), cmd, retry);
1276 	if (err) {
1277 		brcmf_err("cmd (%d) , error (%d)\n", cmd, err);
1278 		return err;
1279 	}
1280 	return err;
1281 }
1282 
1283 static s32 brcmf_cfg80211_set_wiphy_params(struct wiphy *wiphy, u32 changed)
1284 {
1285 	struct brcmf_cfg80211_info *cfg = wiphy_to_cfg(wiphy);
1286 	struct net_device *ndev = cfg_to_ndev(cfg);
1287 	struct brcmf_if *ifp = netdev_priv(ndev);
1288 	s32 err = 0;
1289 
1290 	brcmf_dbg(TRACE, "Enter\n");
1291 	if (!check_vif_up(ifp->vif))
1292 		return -EIO;
1293 
1294 	if (changed & WIPHY_PARAM_RTS_THRESHOLD &&
1295 	    (cfg->conf->rts_threshold != wiphy->rts_threshold)) {
1296 		cfg->conf->rts_threshold = wiphy->rts_threshold;
1297 		err = brcmf_set_rts(ndev, cfg->conf->rts_threshold);
1298 		if (!err)
1299 			goto done;
1300 	}
1301 	if (changed & WIPHY_PARAM_FRAG_THRESHOLD &&
1302 	    (cfg->conf->frag_threshold != wiphy->frag_threshold)) {
1303 		cfg->conf->frag_threshold = wiphy->frag_threshold;
1304 		err = brcmf_set_frag(ndev, cfg->conf->frag_threshold);
1305 		if (!err)
1306 			goto done;
1307 	}
1308 	if (changed & WIPHY_PARAM_RETRY_LONG
1309 	    && (cfg->conf->retry_long != wiphy->retry_long)) {
1310 		cfg->conf->retry_long = wiphy->retry_long;
1311 		err = brcmf_set_retry(ndev, cfg->conf->retry_long, true);
1312 		if (!err)
1313 			goto done;
1314 	}
1315 	if (changed & WIPHY_PARAM_RETRY_SHORT
1316 	    && (cfg->conf->retry_short != wiphy->retry_short)) {
1317 		cfg->conf->retry_short = wiphy->retry_short;
1318 		err = brcmf_set_retry(ndev, cfg->conf->retry_short, false);
1319 		if (!err)
1320 			goto done;
1321 	}
1322 
1323 done:
1324 	brcmf_dbg(TRACE, "Exit\n");
1325 	return err;
1326 }
1327 
1328 static void brcmf_init_prof(struct brcmf_cfg80211_profile *prof)
1329 {
1330 	memset(prof, 0, sizeof(*prof));
1331 }
1332 
1333 static u16 brcmf_map_fw_linkdown_reason(const struct brcmf_event_msg *e)
1334 {
1335 	u16 reason;
1336 
1337 	switch (e->event_code) {
1338 	case BRCMF_E_DEAUTH:
1339 	case BRCMF_E_DEAUTH_IND:
1340 	case BRCMF_E_DISASSOC_IND:
1341 		reason = e->reason;
1342 		break;
1343 	case BRCMF_E_LINK:
1344 	default:
1345 		reason = 0;
1346 		break;
1347 	}
1348 	return reason;
1349 }
1350 
1351 static void brcmf_link_down(struct brcmf_cfg80211_vif *vif, u16 reason)
1352 {
1353 	struct brcmf_cfg80211_info *cfg = wiphy_to_cfg(vif->wdev.wiphy);
1354 	s32 err = 0;
1355 
1356 	brcmf_dbg(TRACE, "Enter\n");
1357 
1358 	if (test_and_clear_bit(BRCMF_VIF_STATUS_CONNECTED, &vif->sme_state)) {
1359 		brcmf_dbg(INFO, "Call WLC_DISASSOC to stop excess roaming\n ");
1360 		err = brcmf_fil_cmd_data_set(vif->ifp,
1361 					     BRCMF_C_DISASSOC, NULL, 0);
1362 		if (err) {
1363 			brcmf_err("WLC_DISASSOC failed (%d)\n", err);
1364 		}
1365 		if ((vif->wdev.iftype == NL80211_IFTYPE_STATION) ||
1366 		    (vif->wdev.iftype == NL80211_IFTYPE_P2P_CLIENT))
1367 			cfg80211_disconnected(vif->wdev.netdev, reason, NULL, 0,
1368 					      true, GFP_KERNEL);
1369 	}
1370 	clear_bit(BRCMF_VIF_STATUS_CONNECTING, &vif->sme_state);
1371 	clear_bit(BRCMF_SCAN_STATUS_SUPPRESS, &cfg->scan_status);
1372 	brcmf_btcoex_set_mode(vif, BRCMF_BTCOEX_ENABLED, 0);
1373 	brcmf_dbg(TRACE, "Exit\n");
1374 }
1375 
1376 static s32
1377 brcmf_cfg80211_join_ibss(struct wiphy *wiphy, struct net_device *ndev,
1378 		      struct cfg80211_ibss_params *params)
1379 {
1380 	struct brcmf_cfg80211_info *cfg = wiphy_to_cfg(wiphy);
1381 	struct brcmf_if *ifp = netdev_priv(ndev);
1382 	struct brcmf_cfg80211_profile *profile = &ifp->vif->profile;
1383 	struct brcmf_join_params join_params;
1384 	size_t join_params_size = 0;
1385 	s32 err = 0;
1386 	s32 wsec = 0;
1387 	s32 bcnprd;
1388 	u16 chanspec;
1389 	u32 ssid_len;
1390 
1391 	brcmf_dbg(TRACE, "Enter\n");
1392 	if (!check_vif_up(ifp->vif))
1393 		return -EIO;
1394 
1395 	if (params->ssid)
1396 		brcmf_dbg(CONN, "SSID: %s\n", params->ssid);
1397 	else {
1398 		brcmf_dbg(CONN, "SSID: NULL, Not supported\n");
1399 		return -EOPNOTSUPP;
1400 	}
1401 
1402 	set_bit(BRCMF_VIF_STATUS_CONNECTING, &ifp->vif->sme_state);
1403 
1404 	if (params->bssid)
1405 		brcmf_dbg(CONN, "BSSID: %pM\n", params->bssid);
1406 	else
1407 		brcmf_dbg(CONN, "No BSSID specified\n");
1408 
1409 	if (params->chandef.chan)
1410 		brcmf_dbg(CONN, "channel: %d\n",
1411 			  params->chandef.chan->center_freq);
1412 	else
1413 		brcmf_dbg(CONN, "no channel specified\n");
1414 
1415 	if (params->channel_fixed)
1416 		brcmf_dbg(CONN, "fixed channel required\n");
1417 	else
1418 		brcmf_dbg(CONN, "no fixed channel required\n");
1419 
1420 	if (params->ie && params->ie_len)
1421 		brcmf_dbg(CONN, "ie len: %d\n", params->ie_len);
1422 	else
1423 		brcmf_dbg(CONN, "no ie specified\n");
1424 
1425 	if (params->beacon_interval)
1426 		brcmf_dbg(CONN, "beacon interval: %d\n",
1427 			  params->beacon_interval);
1428 	else
1429 		brcmf_dbg(CONN, "no beacon interval specified\n");
1430 
1431 	if (params->basic_rates)
1432 		brcmf_dbg(CONN, "basic rates: %08X\n", params->basic_rates);
1433 	else
1434 		brcmf_dbg(CONN, "no basic rates specified\n");
1435 
1436 	if (params->privacy)
1437 		brcmf_dbg(CONN, "privacy required\n");
1438 	else
1439 		brcmf_dbg(CONN, "no privacy required\n");
1440 
1441 	/* Configure Privacy for starter */
1442 	if (params->privacy)
1443 		wsec |= WEP_ENABLED;
1444 
1445 	err = brcmf_fil_iovar_int_set(ifp, "wsec", wsec);
1446 	if (err) {
1447 		brcmf_err("wsec failed (%d)\n", err);
1448 		goto done;
1449 	}
1450 
1451 	/* Configure Beacon Interval for starter */
1452 	if (params->beacon_interval)
1453 		bcnprd = params->beacon_interval;
1454 	else
1455 		bcnprd = 100;
1456 
1457 	err = brcmf_fil_cmd_int_set(ifp, BRCMF_C_SET_BCNPRD, bcnprd);
1458 	if (err) {
1459 		brcmf_err("WLC_SET_BCNPRD failed (%d)\n", err);
1460 		goto done;
1461 	}
1462 
1463 	/* Configure required join parameter */
1464 	memset(&join_params, 0, sizeof(struct brcmf_join_params));
1465 
1466 	/* SSID */
1467 	ssid_len = min_t(u32, params->ssid_len, IEEE80211_MAX_SSID_LEN);
1468 	memcpy(join_params.ssid_le.SSID, params->ssid, ssid_len);
1469 	join_params.ssid_le.SSID_len = cpu_to_le32(ssid_len);
1470 	join_params_size = sizeof(join_params.ssid_le);
1471 
1472 	/* BSSID */
1473 	if (params->bssid) {
1474 		memcpy(join_params.params_le.bssid, params->bssid, ETH_ALEN);
1475 		join_params_size += BRCMF_ASSOC_PARAMS_FIXED_SIZE;
1476 		memcpy(profile->bssid, params->bssid, ETH_ALEN);
1477 	} else {
1478 		eth_broadcast_addr(join_params.params_le.bssid);
1479 		eth_zero_addr(profile->bssid);
1480 	}
1481 
1482 	/* Channel */
1483 	if (params->chandef.chan) {
1484 		u32 target_channel;
1485 
1486 		cfg->channel =
1487 			ieee80211_frequency_to_channel(
1488 				params->chandef.chan->center_freq);
1489 		if (params->channel_fixed) {
1490 			/* adding chanspec */
1491 			chanspec = chandef_to_chanspec(&cfg->d11inf,
1492 						       &params->chandef);
1493 			join_params.params_le.chanspec_list[0] =
1494 				cpu_to_le16(chanspec);
1495 			join_params.params_le.chanspec_num = cpu_to_le32(1);
1496 			join_params_size += sizeof(join_params.params_le);
1497 		}
1498 
1499 		/* set channel for starter */
1500 		target_channel = cfg->channel;
1501 		err = brcmf_fil_cmd_int_set(ifp, BRCMF_C_SET_CHANNEL,
1502 					    target_channel);
1503 		if (err) {
1504 			brcmf_err("WLC_SET_CHANNEL failed (%d)\n", err);
1505 			goto done;
1506 		}
1507 	} else
1508 		cfg->channel = 0;
1509 
1510 	cfg->ibss_starter = false;
1511 
1512 
1513 	err = brcmf_fil_cmd_data_set(ifp, BRCMF_C_SET_SSID,
1514 				     &join_params, join_params_size);
1515 	if (err) {
1516 		brcmf_err("WLC_SET_SSID failed (%d)\n", err);
1517 		goto done;
1518 	}
1519 
1520 done:
1521 	if (err)
1522 		clear_bit(BRCMF_VIF_STATUS_CONNECTING, &ifp->vif->sme_state);
1523 	brcmf_dbg(TRACE, "Exit\n");
1524 	return err;
1525 }
1526 
1527 static s32
1528 brcmf_cfg80211_leave_ibss(struct wiphy *wiphy, struct net_device *ndev)
1529 {
1530 	struct brcmf_if *ifp = netdev_priv(ndev);
1531 
1532 	brcmf_dbg(TRACE, "Enter\n");
1533 	if (!check_vif_up(ifp->vif)) {
1534 		/* When driver is being unloaded, it can end up here. If an
1535 		 * error is returned then later on a debug trace in the wireless
1536 		 * core module will be printed. To avoid this 0 is returned.
1537 		 */
1538 		return 0;
1539 	}
1540 
1541 	brcmf_link_down(ifp->vif, WLAN_REASON_DEAUTH_LEAVING);
1542 	brcmf_net_setcarrier(ifp, false);
1543 
1544 	brcmf_dbg(TRACE, "Exit\n");
1545 
1546 	return 0;
1547 }
1548 
1549 static s32 brcmf_set_wpa_version(struct net_device *ndev,
1550 				 struct cfg80211_connect_params *sme)
1551 {
1552 	struct brcmf_cfg80211_profile *profile = ndev_to_prof(ndev);
1553 	struct brcmf_cfg80211_security *sec;
1554 	s32 val = 0;
1555 	s32 err = 0;
1556 
1557 	if (sme->crypto.wpa_versions & NL80211_WPA_VERSION_1)
1558 		val = WPA_AUTH_PSK | WPA_AUTH_UNSPECIFIED;
1559 	else if (sme->crypto.wpa_versions & NL80211_WPA_VERSION_2)
1560 		val = WPA2_AUTH_PSK | WPA2_AUTH_UNSPECIFIED;
1561 	else
1562 		val = WPA_AUTH_DISABLED;
1563 	brcmf_dbg(CONN, "setting wpa_auth to 0x%0x\n", val);
1564 	err = brcmf_fil_bsscfg_int_set(netdev_priv(ndev), "wpa_auth", val);
1565 	if (err) {
1566 		brcmf_err("set wpa_auth failed (%d)\n", err);
1567 		return err;
1568 	}
1569 	sec = &profile->sec;
1570 	sec->wpa_versions = sme->crypto.wpa_versions;
1571 	return err;
1572 }
1573 
1574 static s32 brcmf_set_auth_type(struct net_device *ndev,
1575 			       struct cfg80211_connect_params *sme)
1576 {
1577 	struct brcmf_cfg80211_profile *profile = ndev_to_prof(ndev);
1578 	struct brcmf_cfg80211_security *sec;
1579 	s32 val = 0;
1580 	s32 err = 0;
1581 
1582 	switch (sme->auth_type) {
1583 	case NL80211_AUTHTYPE_OPEN_SYSTEM:
1584 		val = 0;
1585 		brcmf_dbg(CONN, "open system\n");
1586 		break;
1587 	case NL80211_AUTHTYPE_SHARED_KEY:
1588 		val = 1;
1589 		brcmf_dbg(CONN, "shared key\n");
1590 		break;
1591 	default:
1592 		val = 2;
1593 		brcmf_dbg(CONN, "automatic, auth type (%d)\n", sme->auth_type);
1594 		break;
1595 	}
1596 
1597 	err = brcmf_fil_bsscfg_int_set(netdev_priv(ndev), "auth", val);
1598 	if (err) {
1599 		brcmf_err("set auth failed (%d)\n", err);
1600 		return err;
1601 	}
1602 	sec = &profile->sec;
1603 	sec->auth_type = sme->auth_type;
1604 	return err;
1605 }
1606 
1607 static s32
1608 brcmf_set_wsec_mode(struct net_device *ndev,
1609 		    struct cfg80211_connect_params *sme)
1610 {
1611 	struct brcmf_cfg80211_profile *profile = ndev_to_prof(ndev);
1612 	struct brcmf_cfg80211_security *sec;
1613 	s32 pval = 0;
1614 	s32 gval = 0;
1615 	s32 wsec;
1616 	s32 err = 0;
1617 
1618 	if (sme->crypto.n_ciphers_pairwise) {
1619 		switch (sme->crypto.ciphers_pairwise[0]) {
1620 		case WLAN_CIPHER_SUITE_WEP40:
1621 		case WLAN_CIPHER_SUITE_WEP104:
1622 			pval = WEP_ENABLED;
1623 			break;
1624 		case WLAN_CIPHER_SUITE_TKIP:
1625 			pval = TKIP_ENABLED;
1626 			break;
1627 		case WLAN_CIPHER_SUITE_CCMP:
1628 			pval = AES_ENABLED;
1629 			break;
1630 		case WLAN_CIPHER_SUITE_AES_CMAC:
1631 			pval = AES_ENABLED;
1632 			break;
1633 		default:
1634 			brcmf_err("invalid cipher pairwise (%d)\n",
1635 				  sme->crypto.ciphers_pairwise[0]);
1636 			return -EINVAL;
1637 		}
1638 	}
1639 	if (sme->crypto.cipher_group) {
1640 		switch (sme->crypto.cipher_group) {
1641 		case WLAN_CIPHER_SUITE_WEP40:
1642 		case WLAN_CIPHER_SUITE_WEP104:
1643 			gval = WEP_ENABLED;
1644 			break;
1645 		case WLAN_CIPHER_SUITE_TKIP:
1646 			gval = TKIP_ENABLED;
1647 			break;
1648 		case WLAN_CIPHER_SUITE_CCMP:
1649 			gval = AES_ENABLED;
1650 			break;
1651 		case WLAN_CIPHER_SUITE_AES_CMAC:
1652 			gval = AES_ENABLED;
1653 			break;
1654 		default:
1655 			brcmf_err("invalid cipher group (%d)\n",
1656 				  sme->crypto.cipher_group);
1657 			return -EINVAL;
1658 		}
1659 	}
1660 
1661 	brcmf_dbg(CONN, "pval (%d) gval (%d)\n", pval, gval);
1662 	/* In case of privacy, but no security and WPS then simulate */
1663 	/* setting AES. WPS-2.0 allows no security                   */
1664 	if (brcmf_find_wpsie(sme->ie, sme->ie_len) && !pval && !gval &&
1665 	    sme->privacy)
1666 		pval = AES_ENABLED;
1667 
1668 	wsec = pval | gval;
1669 	err = brcmf_fil_bsscfg_int_set(netdev_priv(ndev), "wsec", wsec);
1670 	if (err) {
1671 		brcmf_err("error (%d)\n", err);
1672 		return err;
1673 	}
1674 
1675 	sec = &profile->sec;
1676 	sec->cipher_pairwise = sme->crypto.ciphers_pairwise[0];
1677 	sec->cipher_group = sme->crypto.cipher_group;
1678 
1679 	return err;
1680 }
1681 
1682 static s32
1683 brcmf_set_key_mgmt(struct net_device *ndev, struct cfg80211_connect_params *sme)
1684 {
1685 	struct brcmf_if *ifp = netdev_priv(ndev);
1686 	s32 val;
1687 	s32 err;
1688 	const struct brcmf_tlv *rsn_ie;
1689 	const u8 *ie;
1690 	u32 ie_len;
1691 	u32 offset;
1692 	u16 rsn_cap;
1693 	u32 mfp;
1694 	u16 count;
1695 
1696 	if (!sme->crypto.n_akm_suites)
1697 		return 0;
1698 
1699 	err = brcmf_fil_bsscfg_int_get(netdev_priv(ndev), "wpa_auth", &val);
1700 	if (err) {
1701 		brcmf_err("could not get wpa_auth (%d)\n", err);
1702 		return err;
1703 	}
1704 	if (val & (WPA_AUTH_PSK | WPA_AUTH_UNSPECIFIED)) {
1705 		switch (sme->crypto.akm_suites[0]) {
1706 		case WLAN_AKM_SUITE_8021X:
1707 			val = WPA_AUTH_UNSPECIFIED;
1708 			break;
1709 		case WLAN_AKM_SUITE_PSK:
1710 			val = WPA_AUTH_PSK;
1711 			break;
1712 		default:
1713 			brcmf_err("invalid cipher group (%d)\n",
1714 				  sme->crypto.cipher_group);
1715 			return -EINVAL;
1716 		}
1717 	} else if (val & (WPA2_AUTH_PSK | WPA2_AUTH_UNSPECIFIED)) {
1718 		switch (sme->crypto.akm_suites[0]) {
1719 		case WLAN_AKM_SUITE_8021X:
1720 			val = WPA2_AUTH_UNSPECIFIED;
1721 			break;
1722 		case WLAN_AKM_SUITE_8021X_SHA256:
1723 			val = WPA2_AUTH_1X_SHA256;
1724 			break;
1725 		case WLAN_AKM_SUITE_PSK_SHA256:
1726 			val = WPA2_AUTH_PSK_SHA256;
1727 			break;
1728 		case WLAN_AKM_SUITE_PSK:
1729 			val = WPA2_AUTH_PSK;
1730 			break;
1731 		default:
1732 			brcmf_err("invalid cipher group (%d)\n",
1733 				  sme->crypto.cipher_group);
1734 			return -EINVAL;
1735 		}
1736 	}
1737 
1738 	if (!brcmf_feat_is_enabled(ifp, BRCMF_FEAT_MFP))
1739 		goto skip_mfp_config;
1740 	/* The MFP mode (1 or 2) needs to be determined, parse IEs. The
1741 	 * IE will not be verified, just a quick search for MFP config
1742 	 */
1743 	rsn_ie = brcmf_parse_tlvs((const u8 *)sme->ie, sme->ie_len,
1744 				  WLAN_EID_RSN);
1745 	if (!rsn_ie)
1746 		goto skip_mfp_config;
1747 	ie = (const u8 *)rsn_ie;
1748 	ie_len = rsn_ie->len + TLV_HDR_LEN;
1749 	/* Skip unicast suite */
1750 	offset = TLV_HDR_LEN + WPA_IE_VERSION_LEN + WPA_IE_MIN_OUI_LEN;
1751 	if (offset + WPA_IE_SUITE_COUNT_LEN >= ie_len)
1752 		goto skip_mfp_config;
1753 	/* Skip multicast suite */
1754 	count = ie[offset] + (ie[offset + 1] << 8);
1755 	offset += WPA_IE_SUITE_COUNT_LEN + (count * WPA_IE_MIN_OUI_LEN);
1756 	if (offset + WPA_IE_SUITE_COUNT_LEN >= ie_len)
1757 		goto skip_mfp_config;
1758 	/* Skip auth key management suite(s) */
1759 	count = ie[offset] + (ie[offset + 1] << 8);
1760 	offset += WPA_IE_SUITE_COUNT_LEN + (count * WPA_IE_MIN_OUI_LEN);
1761 	if (offset + WPA_IE_SUITE_COUNT_LEN > ie_len)
1762 		goto skip_mfp_config;
1763 	/* Ready to read capabilities */
1764 	mfp = BRCMF_MFP_NONE;
1765 	rsn_cap = ie[offset] + (ie[offset + 1] << 8);
1766 	if (rsn_cap & RSN_CAP_MFPR_MASK)
1767 		mfp = BRCMF_MFP_REQUIRED;
1768 	else if (rsn_cap & RSN_CAP_MFPC_MASK)
1769 		mfp = BRCMF_MFP_CAPABLE;
1770 	brcmf_fil_bsscfg_int_set(netdev_priv(ndev), "mfp", mfp);
1771 
1772 skip_mfp_config:
1773 	brcmf_dbg(CONN, "setting wpa_auth to %d\n", val);
1774 	err = brcmf_fil_bsscfg_int_set(netdev_priv(ndev), "wpa_auth", val);
1775 	if (err) {
1776 		brcmf_err("could not set wpa_auth (%d)\n", err);
1777 		return err;
1778 	}
1779 
1780 	return err;
1781 }
1782 
1783 static s32
1784 brcmf_set_sharedkey(struct net_device *ndev,
1785 		    struct cfg80211_connect_params *sme)
1786 {
1787 	struct brcmf_cfg80211_profile *profile = ndev_to_prof(ndev);
1788 	struct brcmf_cfg80211_security *sec;
1789 	struct brcmf_wsec_key key;
1790 	s32 val;
1791 	s32 err = 0;
1792 
1793 	brcmf_dbg(CONN, "key len (%d)\n", sme->key_len);
1794 
1795 	if (sme->key_len == 0)
1796 		return 0;
1797 
1798 	sec = &profile->sec;
1799 	brcmf_dbg(CONN, "wpa_versions 0x%x cipher_pairwise 0x%x\n",
1800 		  sec->wpa_versions, sec->cipher_pairwise);
1801 
1802 	if (sec->wpa_versions & (NL80211_WPA_VERSION_1 | NL80211_WPA_VERSION_2))
1803 		return 0;
1804 
1805 	if (!(sec->cipher_pairwise &
1806 	    (WLAN_CIPHER_SUITE_WEP40 | WLAN_CIPHER_SUITE_WEP104)))
1807 		return 0;
1808 
1809 	memset(&key, 0, sizeof(key));
1810 	key.len = (u32) sme->key_len;
1811 	key.index = (u32) sme->key_idx;
1812 	if (key.len > sizeof(key.data)) {
1813 		brcmf_err("Too long key length (%u)\n", key.len);
1814 		return -EINVAL;
1815 	}
1816 	memcpy(key.data, sme->key, key.len);
1817 	key.flags = BRCMF_PRIMARY_KEY;
1818 	switch (sec->cipher_pairwise) {
1819 	case WLAN_CIPHER_SUITE_WEP40:
1820 		key.algo = CRYPTO_ALGO_WEP1;
1821 		break;
1822 	case WLAN_CIPHER_SUITE_WEP104:
1823 		key.algo = CRYPTO_ALGO_WEP128;
1824 		break;
1825 	default:
1826 		brcmf_err("Invalid algorithm (%d)\n",
1827 			  sme->crypto.ciphers_pairwise[0]);
1828 		return -EINVAL;
1829 	}
1830 	/* Set the new key/index */
1831 	brcmf_dbg(CONN, "key length (%d) key index (%d) algo (%d)\n",
1832 		  key.len, key.index, key.algo);
1833 	brcmf_dbg(CONN, "key \"%s\"\n", key.data);
1834 	err = send_key_to_dongle(netdev_priv(ndev), &key);
1835 	if (err)
1836 		return err;
1837 
1838 	if (sec->auth_type == NL80211_AUTHTYPE_SHARED_KEY) {
1839 		brcmf_dbg(CONN, "set auth_type to shared key\n");
1840 		val = WL_AUTH_SHARED_KEY;	/* shared key */
1841 		err = brcmf_fil_bsscfg_int_set(netdev_priv(ndev), "auth", val);
1842 		if (err)
1843 			brcmf_err("set auth failed (%d)\n", err);
1844 	}
1845 	return err;
1846 }
1847 
1848 static
1849 enum nl80211_auth_type brcmf_war_auth_type(struct brcmf_if *ifp,
1850 					   enum nl80211_auth_type type)
1851 {
1852 	if (type == NL80211_AUTHTYPE_AUTOMATIC &&
1853 	    brcmf_feat_is_quirk_enabled(ifp, BRCMF_FEAT_QUIRK_AUTO_AUTH)) {
1854 		brcmf_dbg(CONN, "WAR: use OPEN instead of AUTO\n");
1855 		type = NL80211_AUTHTYPE_OPEN_SYSTEM;
1856 	}
1857 	return type;
1858 }
1859 
1860 static void brcmf_set_join_pref(struct brcmf_if *ifp,
1861 				struct cfg80211_bss_selection *bss_select)
1862 {
1863 	struct brcmf_join_pref_params join_pref_params[2];
1864 	enum nl80211_band band;
1865 	int err, i = 0;
1866 
1867 	join_pref_params[i].len = 2;
1868 	join_pref_params[i].rssi_gain = 0;
1869 
1870 	if (bss_select->behaviour != NL80211_BSS_SELECT_ATTR_BAND_PREF)
1871 		brcmf_fil_cmd_int_set(ifp, BRCMF_C_SET_ASSOC_PREFER, WLC_BAND_AUTO);
1872 
1873 	switch (bss_select->behaviour) {
1874 	case __NL80211_BSS_SELECT_ATTR_INVALID:
1875 		brcmf_c_set_joinpref_default(ifp);
1876 		return;
1877 	case NL80211_BSS_SELECT_ATTR_BAND_PREF:
1878 		join_pref_params[i].type = BRCMF_JOIN_PREF_BAND;
1879 		band = bss_select->param.band_pref;
1880 		join_pref_params[i].band = nl80211_band_to_fwil(band);
1881 		i++;
1882 		break;
1883 	case NL80211_BSS_SELECT_ATTR_RSSI_ADJUST:
1884 		join_pref_params[i].type = BRCMF_JOIN_PREF_RSSI_DELTA;
1885 		band = bss_select->param.adjust.band;
1886 		join_pref_params[i].band = nl80211_band_to_fwil(band);
1887 		join_pref_params[i].rssi_gain = bss_select->param.adjust.delta;
1888 		i++;
1889 		break;
1890 	case NL80211_BSS_SELECT_ATTR_RSSI:
1891 	default:
1892 		break;
1893 	}
1894 	join_pref_params[i].type = BRCMF_JOIN_PREF_RSSI;
1895 	join_pref_params[i].len = 2;
1896 	join_pref_params[i].rssi_gain = 0;
1897 	join_pref_params[i].band = 0;
1898 	err = brcmf_fil_iovar_data_set(ifp, "join_pref", join_pref_params,
1899 				       sizeof(join_pref_params));
1900 	if (err)
1901 		brcmf_err("Set join_pref error (%d)\n", err);
1902 }
1903 
1904 static s32
1905 brcmf_cfg80211_connect(struct wiphy *wiphy, struct net_device *ndev,
1906 		       struct cfg80211_connect_params *sme)
1907 {
1908 	struct brcmf_cfg80211_info *cfg = wiphy_to_cfg(wiphy);
1909 	struct brcmf_if *ifp = netdev_priv(ndev);
1910 	struct ieee80211_channel *chan = sme->channel;
1911 	struct brcmf_join_params join_params;
1912 	size_t join_params_size;
1913 	const struct brcmf_tlv *rsn_ie;
1914 	const struct brcmf_vs_tlv *wpa_ie;
1915 	const void *ie;
1916 	u32 ie_len;
1917 	struct brcmf_ext_join_params_le *ext_join_params;
1918 	u16 chanspec;
1919 	s32 err = 0;
1920 	u32 ssid_len;
1921 
1922 	brcmf_dbg(TRACE, "Enter\n");
1923 	if (!check_vif_up(ifp->vif))
1924 		return -EIO;
1925 
1926 	if (!sme->ssid) {
1927 		brcmf_err("Invalid ssid\n");
1928 		return -EOPNOTSUPP;
1929 	}
1930 
1931 	if (ifp->vif == cfg->p2p.bss_idx[P2PAPI_BSSCFG_PRIMARY].vif) {
1932 		/* A normal (non P2P) connection request setup. */
1933 		ie = NULL;
1934 		ie_len = 0;
1935 		/* find the WPA_IE */
1936 		wpa_ie = brcmf_find_wpaie((u8 *)sme->ie, sme->ie_len);
1937 		if (wpa_ie) {
1938 			ie = wpa_ie;
1939 			ie_len = wpa_ie->len + TLV_HDR_LEN;
1940 		} else {
1941 			/* find the RSN_IE */
1942 			rsn_ie = brcmf_parse_tlvs((const u8 *)sme->ie,
1943 						  sme->ie_len,
1944 						  WLAN_EID_RSN);
1945 			if (rsn_ie) {
1946 				ie = rsn_ie;
1947 				ie_len = rsn_ie->len + TLV_HDR_LEN;
1948 			}
1949 		}
1950 		brcmf_fil_iovar_data_set(ifp, "wpaie", ie, ie_len);
1951 	}
1952 
1953 	err = brcmf_vif_set_mgmt_ie(ifp->vif, BRCMF_VNDR_IE_ASSOCREQ_FLAG,
1954 				    sme->ie, sme->ie_len);
1955 	if (err)
1956 		brcmf_err("Set Assoc REQ IE Failed\n");
1957 	else
1958 		brcmf_dbg(TRACE, "Applied Vndr IEs for Assoc request\n");
1959 
1960 	set_bit(BRCMF_VIF_STATUS_CONNECTING, &ifp->vif->sme_state);
1961 
1962 	if (chan) {
1963 		cfg->channel =
1964 			ieee80211_frequency_to_channel(chan->center_freq);
1965 		chanspec = channel_to_chanspec(&cfg->d11inf, chan);
1966 		brcmf_dbg(CONN, "channel=%d, center_req=%d, chanspec=0x%04x\n",
1967 			  cfg->channel, chan->center_freq, chanspec);
1968 	} else {
1969 		cfg->channel = 0;
1970 		chanspec = 0;
1971 	}
1972 
1973 	brcmf_dbg(INFO, "ie (%p), ie_len (%zd)\n", sme->ie, sme->ie_len);
1974 
1975 	err = brcmf_set_wpa_version(ndev, sme);
1976 	if (err) {
1977 		brcmf_err("wl_set_wpa_version failed (%d)\n", err);
1978 		goto done;
1979 	}
1980 
1981 	sme->auth_type = brcmf_war_auth_type(ifp, sme->auth_type);
1982 	err = brcmf_set_auth_type(ndev, sme);
1983 	if (err) {
1984 		brcmf_err("wl_set_auth_type failed (%d)\n", err);
1985 		goto done;
1986 	}
1987 
1988 	err = brcmf_set_wsec_mode(ndev, sme);
1989 	if (err) {
1990 		brcmf_err("wl_set_set_cipher failed (%d)\n", err);
1991 		goto done;
1992 	}
1993 
1994 	err = brcmf_set_key_mgmt(ndev, sme);
1995 	if (err) {
1996 		brcmf_err("wl_set_key_mgmt failed (%d)\n", err);
1997 		goto done;
1998 	}
1999 
2000 	err = brcmf_set_sharedkey(ndev, sme);
2001 	if (err) {
2002 		brcmf_err("brcmf_set_sharedkey failed (%d)\n", err);
2003 		goto done;
2004 	}
2005 
2006 	/* Join with specific BSSID and cached SSID
2007 	 * If SSID is zero join based on BSSID only
2008 	 */
2009 	join_params_size = offsetof(struct brcmf_ext_join_params_le, assoc_le) +
2010 		offsetof(struct brcmf_assoc_params_le, chanspec_list);
2011 	if (cfg->channel)
2012 		join_params_size += sizeof(u16);
2013 	ext_join_params = kzalloc(join_params_size, GFP_KERNEL);
2014 	if (ext_join_params == NULL) {
2015 		err = -ENOMEM;
2016 		goto done;
2017 	}
2018 	ssid_len = min_t(u32, sme->ssid_len, IEEE80211_MAX_SSID_LEN);
2019 	ext_join_params->ssid_le.SSID_len = cpu_to_le32(ssid_len);
2020 	memcpy(&ext_join_params->ssid_le.SSID, sme->ssid, ssid_len);
2021 	if (ssid_len < IEEE80211_MAX_SSID_LEN)
2022 		brcmf_dbg(CONN, "SSID \"%s\", len (%d)\n",
2023 			  ext_join_params->ssid_le.SSID, ssid_len);
2024 
2025 	/* Set up join scan parameters */
2026 	ext_join_params->scan_le.scan_type = -1;
2027 	ext_join_params->scan_le.home_time = cpu_to_le32(-1);
2028 
2029 	if (sme->bssid)
2030 		memcpy(&ext_join_params->assoc_le.bssid, sme->bssid, ETH_ALEN);
2031 	else
2032 		eth_broadcast_addr(ext_join_params->assoc_le.bssid);
2033 
2034 	if (cfg->channel) {
2035 		ext_join_params->assoc_le.chanspec_num = cpu_to_le32(1);
2036 
2037 		ext_join_params->assoc_le.chanspec_list[0] =
2038 			cpu_to_le16(chanspec);
2039 		/* Increase dwell time to receive probe response or detect
2040 		 * beacon from target AP at a noisy air only during connect
2041 		 * command.
2042 		 */
2043 		ext_join_params->scan_le.active_time =
2044 			cpu_to_le32(BRCMF_SCAN_JOIN_ACTIVE_DWELL_TIME_MS);
2045 		ext_join_params->scan_le.passive_time =
2046 			cpu_to_le32(BRCMF_SCAN_JOIN_PASSIVE_DWELL_TIME_MS);
2047 		/* To sync with presence period of VSDB GO send probe request
2048 		 * more frequently. Probe request will be stopped when it gets
2049 		 * probe response from target AP/GO.
2050 		 */
2051 		ext_join_params->scan_le.nprobes =
2052 			cpu_to_le32(BRCMF_SCAN_JOIN_ACTIVE_DWELL_TIME_MS /
2053 				    BRCMF_SCAN_JOIN_PROBE_INTERVAL_MS);
2054 	} else {
2055 		ext_join_params->scan_le.active_time = cpu_to_le32(-1);
2056 		ext_join_params->scan_le.passive_time = cpu_to_le32(-1);
2057 		ext_join_params->scan_le.nprobes = cpu_to_le32(-1);
2058 	}
2059 
2060 	brcmf_set_join_pref(ifp, &sme->bss_select);
2061 
2062 	err  = brcmf_fil_bsscfg_data_set(ifp, "join", ext_join_params,
2063 					 join_params_size);
2064 	kfree(ext_join_params);
2065 	if (!err)
2066 		/* This is it. join command worked, we are done */
2067 		goto done;
2068 
2069 	/* join command failed, fallback to set ssid */
2070 	memset(&join_params, 0, sizeof(join_params));
2071 	join_params_size = sizeof(join_params.ssid_le);
2072 
2073 	memcpy(&join_params.ssid_le.SSID, sme->ssid, ssid_len);
2074 	join_params.ssid_le.SSID_len = cpu_to_le32(ssid_len);
2075 
2076 	if (sme->bssid)
2077 		memcpy(join_params.params_le.bssid, sme->bssid, ETH_ALEN);
2078 	else
2079 		eth_broadcast_addr(join_params.params_le.bssid);
2080 
2081 	if (cfg->channel) {
2082 		join_params.params_le.chanspec_list[0] = cpu_to_le16(chanspec);
2083 		join_params.params_le.chanspec_num = cpu_to_le32(1);
2084 		join_params_size += sizeof(join_params.params_le);
2085 	}
2086 	err = brcmf_fil_cmd_data_set(ifp, BRCMF_C_SET_SSID,
2087 				     &join_params, join_params_size);
2088 	if (err)
2089 		brcmf_err("BRCMF_C_SET_SSID failed (%d)\n", err);
2090 
2091 done:
2092 	if (err)
2093 		clear_bit(BRCMF_VIF_STATUS_CONNECTING, &ifp->vif->sme_state);
2094 	brcmf_dbg(TRACE, "Exit\n");
2095 	return err;
2096 }
2097 
2098 static s32
2099 brcmf_cfg80211_disconnect(struct wiphy *wiphy, struct net_device *ndev,
2100 		       u16 reason_code)
2101 {
2102 	struct brcmf_if *ifp = netdev_priv(ndev);
2103 	struct brcmf_cfg80211_profile *profile = &ifp->vif->profile;
2104 	struct brcmf_scb_val_le scbval;
2105 	s32 err = 0;
2106 
2107 	brcmf_dbg(TRACE, "Enter. Reason code = %d\n", reason_code);
2108 	if (!check_vif_up(ifp->vif))
2109 		return -EIO;
2110 
2111 	clear_bit(BRCMF_VIF_STATUS_CONNECTED, &ifp->vif->sme_state);
2112 	clear_bit(BRCMF_VIF_STATUS_CONNECTING, &ifp->vif->sme_state);
2113 	cfg80211_disconnected(ndev, reason_code, NULL, 0, true, GFP_KERNEL);
2114 
2115 	memcpy(&scbval.ea, &profile->bssid, ETH_ALEN);
2116 	scbval.val = cpu_to_le32(reason_code);
2117 	err = brcmf_fil_cmd_data_set(ifp, BRCMF_C_DISASSOC,
2118 				     &scbval, sizeof(scbval));
2119 	if (err)
2120 		brcmf_err("error (%d)\n", err);
2121 
2122 	brcmf_dbg(TRACE, "Exit\n");
2123 	return err;
2124 }
2125 
2126 static s32
2127 brcmf_cfg80211_set_tx_power(struct wiphy *wiphy, struct wireless_dev *wdev,
2128 			    enum nl80211_tx_power_setting type, s32 mbm)
2129 {
2130 	struct brcmf_cfg80211_info *cfg = wiphy_to_cfg(wiphy);
2131 	struct net_device *ndev = cfg_to_ndev(cfg);
2132 	struct brcmf_if *ifp = netdev_priv(ndev);
2133 	s32 err;
2134 	s32 disable;
2135 	u32 qdbm = 127;
2136 
2137 	brcmf_dbg(TRACE, "Enter %d %d\n", type, mbm);
2138 	if (!check_vif_up(ifp->vif))
2139 		return -EIO;
2140 
2141 	switch (type) {
2142 	case NL80211_TX_POWER_AUTOMATIC:
2143 		break;
2144 	case NL80211_TX_POWER_LIMITED:
2145 	case NL80211_TX_POWER_FIXED:
2146 		if (mbm < 0) {
2147 			brcmf_err("TX_POWER_FIXED - dbm is negative\n");
2148 			err = -EINVAL;
2149 			goto done;
2150 		}
2151 		qdbm =  MBM_TO_DBM(4 * mbm);
2152 		if (qdbm > 127)
2153 			qdbm = 127;
2154 		qdbm |= WL_TXPWR_OVERRIDE;
2155 		break;
2156 	default:
2157 		brcmf_err("Unsupported type %d\n", type);
2158 		err = -EINVAL;
2159 		goto done;
2160 	}
2161 	/* Make sure radio is off or on as far as software is concerned */
2162 	disable = WL_RADIO_SW_DISABLE << 16;
2163 	err = brcmf_fil_cmd_int_set(ifp, BRCMF_C_SET_RADIO, disable);
2164 	if (err)
2165 		brcmf_err("WLC_SET_RADIO error (%d)\n", err);
2166 
2167 	err = brcmf_fil_iovar_int_set(ifp, "qtxpower", qdbm);
2168 	if (err)
2169 		brcmf_err("qtxpower error (%d)\n", err);
2170 
2171 done:
2172 	brcmf_dbg(TRACE, "Exit %d (qdbm)\n", qdbm & ~WL_TXPWR_OVERRIDE);
2173 	return err;
2174 }
2175 
2176 static s32
2177 brcmf_cfg80211_get_tx_power(struct wiphy *wiphy, struct wireless_dev *wdev,
2178 			    s32 *dbm)
2179 {
2180 	struct brcmf_cfg80211_info *cfg = wiphy_to_cfg(wiphy);
2181 	struct net_device *ndev = cfg_to_ndev(cfg);
2182 	struct brcmf_if *ifp = netdev_priv(ndev);
2183 	s32 qdbm = 0;
2184 	s32 err;
2185 
2186 	brcmf_dbg(TRACE, "Enter\n");
2187 	if (!check_vif_up(ifp->vif))
2188 		return -EIO;
2189 
2190 	err = brcmf_fil_iovar_int_get(ifp, "qtxpower", &qdbm);
2191 	if (err) {
2192 		brcmf_err("error (%d)\n", err);
2193 		goto done;
2194 	}
2195 	*dbm = (qdbm & ~WL_TXPWR_OVERRIDE) / 4;
2196 
2197 done:
2198 	brcmf_dbg(TRACE, "Exit (0x%x %d)\n", qdbm, *dbm);
2199 	return err;
2200 }
2201 
2202 static s32
2203 brcmf_cfg80211_config_default_key(struct wiphy *wiphy, struct net_device *ndev,
2204 				  u8 key_idx, bool unicast, bool multicast)
2205 {
2206 	struct brcmf_if *ifp = netdev_priv(ndev);
2207 	u32 index;
2208 	u32 wsec;
2209 	s32 err = 0;
2210 
2211 	brcmf_dbg(TRACE, "Enter\n");
2212 	brcmf_dbg(CONN, "key index (%d)\n", key_idx);
2213 	if (!check_vif_up(ifp->vif))
2214 		return -EIO;
2215 
2216 	err = brcmf_fil_bsscfg_int_get(ifp, "wsec", &wsec);
2217 	if (err) {
2218 		brcmf_err("WLC_GET_WSEC error (%d)\n", err);
2219 		goto done;
2220 	}
2221 
2222 	if (wsec & WEP_ENABLED) {
2223 		/* Just select a new current key */
2224 		index = key_idx;
2225 		err = brcmf_fil_cmd_int_set(ifp,
2226 					    BRCMF_C_SET_KEY_PRIMARY, index);
2227 		if (err)
2228 			brcmf_err("error (%d)\n", err);
2229 	}
2230 done:
2231 	brcmf_dbg(TRACE, "Exit\n");
2232 	return err;
2233 }
2234 
2235 static s32
2236 brcmf_cfg80211_del_key(struct wiphy *wiphy, struct net_device *ndev,
2237 		       u8 key_idx, bool pairwise, const u8 *mac_addr)
2238 {
2239 	struct brcmf_if *ifp = netdev_priv(ndev);
2240 	struct brcmf_wsec_key *key;
2241 	s32 err;
2242 
2243 	brcmf_dbg(TRACE, "Enter\n");
2244 	brcmf_dbg(CONN, "key index (%d)\n", key_idx);
2245 
2246 	if (!check_vif_up(ifp->vif))
2247 		return -EIO;
2248 
2249 	if (key_idx >= BRCMF_MAX_DEFAULT_KEYS) {
2250 		/* we ignore this key index in this case */
2251 		return -EINVAL;
2252 	}
2253 
2254 	key = &ifp->vif->profile.key[key_idx];
2255 
2256 	if (key->algo == CRYPTO_ALGO_OFF) {
2257 		brcmf_dbg(CONN, "Ignore clearing of (never configured) key\n");
2258 		return -EINVAL;
2259 	}
2260 
2261 	memset(key, 0, sizeof(*key));
2262 	key->index = (u32)key_idx;
2263 	key->flags = BRCMF_PRIMARY_KEY;
2264 
2265 	/* Clear the key/index */
2266 	err = send_key_to_dongle(ifp, key);
2267 
2268 	brcmf_dbg(TRACE, "Exit\n");
2269 	return err;
2270 }
2271 
2272 static s32
2273 brcmf_cfg80211_add_key(struct wiphy *wiphy, struct net_device *ndev,
2274 		       u8 key_idx, bool pairwise, const u8 *mac_addr,
2275 		       struct key_params *params)
2276 {
2277 	struct brcmf_if *ifp = netdev_priv(ndev);
2278 	struct brcmf_wsec_key *key;
2279 	s32 val;
2280 	s32 wsec;
2281 	s32 err;
2282 	u8 keybuf[8];
2283 	bool ext_key;
2284 
2285 	brcmf_dbg(TRACE, "Enter\n");
2286 	brcmf_dbg(CONN, "key index (%d)\n", key_idx);
2287 	if (!check_vif_up(ifp->vif))
2288 		return -EIO;
2289 
2290 	if (key_idx >= BRCMF_MAX_DEFAULT_KEYS) {
2291 		/* we ignore this key index in this case */
2292 		brcmf_err("invalid key index (%d)\n", key_idx);
2293 		return -EINVAL;
2294 	}
2295 
2296 	if (params->key_len == 0)
2297 		return brcmf_cfg80211_del_key(wiphy, ndev, key_idx, pairwise,
2298 					      mac_addr);
2299 
2300 	if (params->key_len > sizeof(key->data)) {
2301 		brcmf_err("Too long key length (%u)\n", params->key_len);
2302 		return -EINVAL;
2303 	}
2304 
2305 	ext_key = false;
2306 	if (mac_addr && (params->cipher != WLAN_CIPHER_SUITE_WEP40) &&
2307 	    (params->cipher != WLAN_CIPHER_SUITE_WEP104)) {
2308 		brcmf_dbg(TRACE, "Ext key, mac %pM", mac_addr);
2309 		ext_key = true;
2310 	}
2311 
2312 	key = &ifp->vif->profile.key[key_idx];
2313 	memset(key, 0, sizeof(*key));
2314 	if ((ext_key) && (!is_multicast_ether_addr(mac_addr)))
2315 		memcpy((char *)&key->ea, (void *)mac_addr, ETH_ALEN);
2316 	key->len = params->key_len;
2317 	key->index = key_idx;
2318 	memcpy(key->data, params->key, key->len);
2319 	if (!ext_key)
2320 		key->flags = BRCMF_PRIMARY_KEY;
2321 
2322 	switch (params->cipher) {
2323 	case WLAN_CIPHER_SUITE_WEP40:
2324 		key->algo = CRYPTO_ALGO_WEP1;
2325 		val = WEP_ENABLED;
2326 		brcmf_dbg(CONN, "WLAN_CIPHER_SUITE_WEP40\n");
2327 		break;
2328 	case WLAN_CIPHER_SUITE_WEP104:
2329 		key->algo = CRYPTO_ALGO_WEP128;
2330 		val = WEP_ENABLED;
2331 		brcmf_dbg(CONN, "WLAN_CIPHER_SUITE_WEP104\n");
2332 		break;
2333 	case WLAN_CIPHER_SUITE_TKIP:
2334 		if (!brcmf_is_apmode(ifp->vif)) {
2335 			brcmf_dbg(CONN, "Swapping RX/TX MIC key\n");
2336 			memcpy(keybuf, &key->data[24], sizeof(keybuf));
2337 			memcpy(&key->data[24], &key->data[16], sizeof(keybuf));
2338 			memcpy(&key->data[16], keybuf, sizeof(keybuf));
2339 		}
2340 		key->algo = CRYPTO_ALGO_TKIP;
2341 		val = TKIP_ENABLED;
2342 		brcmf_dbg(CONN, "WLAN_CIPHER_SUITE_TKIP\n");
2343 		break;
2344 	case WLAN_CIPHER_SUITE_AES_CMAC:
2345 		key->algo = CRYPTO_ALGO_AES_CCM;
2346 		val = AES_ENABLED;
2347 		brcmf_dbg(CONN, "WLAN_CIPHER_SUITE_AES_CMAC\n");
2348 		break;
2349 	case WLAN_CIPHER_SUITE_CCMP:
2350 		key->algo = CRYPTO_ALGO_AES_CCM;
2351 		val = AES_ENABLED;
2352 		brcmf_dbg(CONN, "WLAN_CIPHER_SUITE_CCMP\n");
2353 		break;
2354 	default:
2355 		brcmf_err("Invalid cipher (0x%x)\n", params->cipher);
2356 		err = -EINVAL;
2357 		goto done;
2358 	}
2359 
2360 	err = send_key_to_dongle(ifp, key);
2361 	if (ext_key || err)
2362 		goto done;
2363 
2364 	err = brcmf_fil_bsscfg_int_get(ifp, "wsec", &wsec);
2365 	if (err) {
2366 		brcmf_err("get wsec error (%d)\n", err);
2367 		goto done;
2368 	}
2369 	wsec |= val;
2370 	err = brcmf_fil_bsscfg_int_set(ifp, "wsec", wsec);
2371 	if (err) {
2372 		brcmf_err("set wsec error (%d)\n", err);
2373 		goto done;
2374 	}
2375 
2376 done:
2377 	brcmf_dbg(TRACE, "Exit\n");
2378 	return err;
2379 }
2380 
2381 static s32
2382 brcmf_cfg80211_get_key(struct wiphy *wiphy, struct net_device *ndev, u8 key_idx,
2383 		       bool pairwise, const u8 *mac_addr, void *cookie,
2384 		       void (*callback)(void *cookie,
2385 					struct key_params *params))
2386 {
2387 	struct key_params params;
2388 	struct brcmf_if *ifp = netdev_priv(ndev);
2389 	struct brcmf_cfg80211_profile *profile = &ifp->vif->profile;
2390 	struct brcmf_cfg80211_security *sec;
2391 	s32 wsec;
2392 	s32 err = 0;
2393 
2394 	brcmf_dbg(TRACE, "Enter\n");
2395 	brcmf_dbg(CONN, "key index (%d)\n", key_idx);
2396 	if (!check_vif_up(ifp->vif))
2397 		return -EIO;
2398 
2399 	memset(&params, 0, sizeof(params));
2400 
2401 	err = brcmf_fil_bsscfg_int_get(ifp, "wsec", &wsec);
2402 	if (err) {
2403 		brcmf_err("WLC_GET_WSEC error (%d)\n", err);
2404 		/* Ignore this error, may happen during DISASSOC */
2405 		err = -EAGAIN;
2406 		goto done;
2407 	}
2408 	if (wsec & WEP_ENABLED) {
2409 		sec = &profile->sec;
2410 		if (sec->cipher_pairwise & WLAN_CIPHER_SUITE_WEP40) {
2411 			params.cipher = WLAN_CIPHER_SUITE_WEP40;
2412 			brcmf_dbg(CONN, "WLAN_CIPHER_SUITE_WEP40\n");
2413 		} else if (sec->cipher_pairwise & WLAN_CIPHER_SUITE_WEP104) {
2414 			params.cipher = WLAN_CIPHER_SUITE_WEP104;
2415 			brcmf_dbg(CONN, "WLAN_CIPHER_SUITE_WEP104\n");
2416 		}
2417 	} else if (wsec & TKIP_ENABLED) {
2418 		params.cipher = WLAN_CIPHER_SUITE_TKIP;
2419 		brcmf_dbg(CONN, "WLAN_CIPHER_SUITE_TKIP\n");
2420 	} else if (wsec & AES_ENABLED) {
2421 		params.cipher = WLAN_CIPHER_SUITE_AES_CMAC;
2422 		brcmf_dbg(CONN, "WLAN_CIPHER_SUITE_AES_CMAC\n");
2423 	} else  {
2424 		brcmf_err("Invalid algo (0x%x)\n", wsec);
2425 		err = -EINVAL;
2426 		goto done;
2427 	}
2428 	callback(cookie, &params);
2429 
2430 done:
2431 	brcmf_dbg(TRACE, "Exit\n");
2432 	return err;
2433 }
2434 
2435 static s32
2436 brcmf_cfg80211_config_default_mgmt_key(struct wiphy *wiphy,
2437 				       struct net_device *ndev, u8 key_idx)
2438 {
2439 	struct brcmf_if *ifp = netdev_priv(ndev);
2440 
2441 	brcmf_dbg(TRACE, "Enter key_idx %d\n", key_idx);
2442 
2443 	if (brcmf_feat_is_enabled(ifp, BRCMF_FEAT_MFP))
2444 		return 0;
2445 
2446 	brcmf_dbg(INFO, "Not supported\n");
2447 
2448 	return -EOPNOTSUPP;
2449 }
2450 
2451 static void
2452 brcmf_cfg80211_reconfigure_wep(struct brcmf_if *ifp)
2453 {
2454 	s32 err;
2455 	u8 key_idx;
2456 	struct brcmf_wsec_key *key;
2457 	s32 wsec;
2458 
2459 	for (key_idx = 0; key_idx < BRCMF_MAX_DEFAULT_KEYS; key_idx++) {
2460 		key = &ifp->vif->profile.key[key_idx];
2461 		if ((key->algo == CRYPTO_ALGO_WEP1) ||
2462 		    (key->algo == CRYPTO_ALGO_WEP128))
2463 			break;
2464 	}
2465 	if (key_idx == BRCMF_MAX_DEFAULT_KEYS)
2466 		return;
2467 
2468 	err = send_key_to_dongle(ifp, key);
2469 	if (err) {
2470 		brcmf_err("Setting WEP key failed (%d)\n", err);
2471 		return;
2472 	}
2473 	err = brcmf_fil_bsscfg_int_get(ifp, "wsec", &wsec);
2474 	if (err) {
2475 		brcmf_err("get wsec error (%d)\n", err);
2476 		return;
2477 	}
2478 	wsec |= WEP_ENABLED;
2479 	err = brcmf_fil_bsscfg_int_set(ifp, "wsec", wsec);
2480 	if (err)
2481 		brcmf_err("set wsec error (%d)\n", err);
2482 }
2483 
2484 static void brcmf_convert_sta_flags(u32 fw_sta_flags, struct station_info *si)
2485 {
2486 	struct nl80211_sta_flag_update *sfu;
2487 
2488 	brcmf_dbg(TRACE, "flags %08x\n", fw_sta_flags);
2489 	si->filled |= BIT(NL80211_STA_INFO_STA_FLAGS);
2490 	sfu = &si->sta_flags;
2491 	sfu->mask = BIT(NL80211_STA_FLAG_WME) |
2492 		    BIT(NL80211_STA_FLAG_AUTHENTICATED) |
2493 		    BIT(NL80211_STA_FLAG_ASSOCIATED) |
2494 		    BIT(NL80211_STA_FLAG_AUTHORIZED);
2495 	if (fw_sta_flags & BRCMF_STA_WME)
2496 		sfu->set |= BIT(NL80211_STA_FLAG_WME);
2497 	if (fw_sta_flags & BRCMF_STA_AUTHE)
2498 		sfu->set |= BIT(NL80211_STA_FLAG_AUTHENTICATED);
2499 	if (fw_sta_flags & BRCMF_STA_ASSOC)
2500 		sfu->set |= BIT(NL80211_STA_FLAG_ASSOCIATED);
2501 	if (fw_sta_flags & BRCMF_STA_AUTHO)
2502 		sfu->set |= BIT(NL80211_STA_FLAG_AUTHORIZED);
2503 }
2504 
2505 static void brcmf_fill_bss_param(struct brcmf_if *ifp, struct station_info *si)
2506 {
2507 	struct {
2508 		__le32 len;
2509 		struct brcmf_bss_info_le bss_le;
2510 	} *buf;
2511 	u16 capability;
2512 	int err;
2513 
2514 	buf = kzalloc(WL_BSS_INFO_MAX, GFP_KERNEL);
2515 	if (!buf)
2516 		return;
2517 
2518 	buf->len = cpu_to_le32(WL_BSS_INFO_MAX);
2519 	err = brcmf_fil_cmd_data_get(ifp, BRCMF_C_GET_BSS_INFO, buf,
2520 				     WL_BSS_INFO_MAX);
2521 	if (err) {
2522 		brcmf_err("Failed to get bss info (%d)\n", err);
2523 		goto out_kfree;
2524 	}
2525 	si->filled |= BIT(NL80211_STA_INFO_BSS_PARAM);
2526 	si->bss_param.beacon_interval = le16_to_cpu(buf->bss_le.beacon_period);
2527 	si->bss_param.dtim_period = buf->bss_le.dtim_period;
2528 	capability = le16_to_cpu(buf->bss_le.capability);
2529 	if (capability & IEEE80211_HT_STBC_PARAM_DUAL_CTS_PROT)
2530 		si->bss_param.flags |= BSS_PARAM_FLAGS_CTS_PROT;
2531 	if (capability & WLAN_CAPABILITY_SHORT_PREAMBLE)
2532 		si->bss_param.flags |= BSS_PARAM_FLAGS_SHORT_PREAMBLE;
2533 	if (capability & WLAN_CAPABILITY_SHORT_SLOT_TIME)
2534 		si->bss_param.flags |= BSS_PARAM_FLAGS_SHORT_SLOT_TIME;
2535 
2536 out_kfree:
2537 	kfree(buf);
2538 }
2539 
2540 static s32
2541 brcmf_cfg80211_get_station_ibss(struct brcmf_if *ifp,
2542 				struct station_info *sinfo)
2543 {
2544 	struct brcmf_scb_val_le scbval;
2545 	struct brcmf_pktcnt_le pktcnt;
2546 	s32 err;
2547 	u32 rate;
2548 	u32 rssi;
2549 
2550 	/* Get the current tx rate */
2551 	err = brcmf_fil_cmd_int_get(ifp, BRCMF_C_GET_RATE, &rate);
2552 	if (err < 0) {
2553 		brcmf_err("BRCMF_C_GET_RATE error (%d)\n", err);
2554 		return err;
2555 	}
2556 	sinfo->filled |= BIT(NL80211_STA_INFO_TX_BITRATE);
2557 	sinfo->txrate.legacy = rate * 5;
2558 
2559 	memset(&scbval, 0, sizeof(scbval));
2560 	err = brcmf_fil_cmd_data_get(ifp, BRCMF_C_GET_RSSI, &scbval,
2561 				     sizeof(scbval));
2562 	if (err) {
2563 		brcmf_err("BRCMF_C_GET_RSSI error (%d)\n", err);
2564 		return err;
2565 	}
2566 	rssi = le32_to_cpu(scbval.val);
2567 	sinfo->filled |= BIT(NL80211_STA_INFO_SIGNAL);
2568 	sinfo->signal = rssi;
2569 
2570 	err = brcmf_fil_cmd_data_get(ifp, BRCMF_C_GET_GET_PKTCNTS, &pktcnt,
2571 				     sizeof(pktcnt));
2572 	if (err) {
2573 		brcmf_err("BRCMF_C_GET_GET_PKTCNTS error (%d)\n", err);
2574 		return err;
2575 	}
2576 	sinfo->filled |= BIT(NL80211_STA_INFO_RX_PACKETS) |
2577 			 BIT(NL80211_STA_INFO_RX_DROP_MISC) |
2578 			 BIT(NL80211_STA_INFO_TX_PACKETS) |
2579 			 BIT(NL80211_STA_INFO_TX_FAILED);
2580 	sinfo->rx_packets = le32_to_cpu(pktcnt.rx_good_pkt);
2581 	sinfo->rx_dropped_misc = le32_to_cpu(pktcnt.rx_bad_pkt);
2582 	sinfo->tx_packets = le32_to_cpu(pktcnt.tx_good_pkt);
2583 	sinfo->tx_failed  = le32_to_cpu(pktcnt.tx_bad_pkt);
2584 
2585 	return 0;
2586 }
2587 
2588 static s32
2589 brcmf_cfg80211_get_station(struct wiphy *wiphy, struct net_device *ndev,
2590 			   const u8 *mac, struct station_info *sinfo)
2591 {
2592 	struct brcmf_if *ifp = netdev_priv(ndev);
2593 	struct brcmf_scb_val_le scb_val;
2594 	s32 err = 0;
2595 	struct brcmf_sta_info_le sta_info_le;
2596 	u32 sta_flags;
2597 	u32 is_tdls_peer;
2598 	s32 total_rssi;
2599 	s32 count_rssi;
2600 	int rssi;
2601 	u32 i;
2602 
2603 	brcmf_dbg(TRACE, "Enter, MAC %pM\n", mac);
2604 	if (!check_vif_up(ifp->vif))
2605 		return -EIO;
2606 
2607 	if (brcmf_is_ibssmode(ifp->vif))
2608 		return brcmf_cfg80211_get_station_ibss(ifp, sinfo);
2609 
2610 	memset(&sta_info_le, 0, sizeof(sta_info_le));
2611 	memcpy(&sta_info_le, mac, ETH_ALEN);
2612 	err = brcmf_fil_iovar_data_get(ifp, "tdls_sta_info",
2613 				       &sta_info_le,
2614 				       sizeof(sta_info_le));
2615 	is_tdls_peer = !err;
2616 	if (err) {
2617 		err = brcmf_fil_iovar_data_get(ifp, "sta_info",
2618 					       &sta_info_le,
2619 					       sizeof(sta_info_le));
2620 		if (err < 0) {
2621 			brcmf_err("GET STA INFO failed, %d\n", err);
2622 			goto done;
2623 		}
2624 	}
2625 	brcmf_dbg(TRACE, "version %d\n", le16_to_cpu(sta_info_le.ver));
2626 	sinfo->filled = BIT(NL80211_STA_INFO_INACTIVE_TIME);
2627 	sinfo->inactive_time = le32_to_cpu(sta_info_le.idle) * 1000;
2628 	sta_flags = le32_to_cpu(sta_info_le.flags);
2629 	brcmf_convert_sta_flags(sta_flags, sinfo);
2630 	sinfo->sta_flags.mask |= BIT(NL80211_STA_FLAG_TDLS_PEER);
2631 	if (is_tdls_peer)
2632 		sinfo->sta_flags.set |= BIT(NL80211_STA_FLAG_TDLS_PEER);
2633 	else
2634 		sinfo->sta_flags.set &= ~BIT(NL80211_STA_FLAG_TDLS_PEER);
2635 	if (sta_flags & BRCMF_STA_ASSOC) {
2636 		sinfo->filled |= BIT(NL80211_STA_INFO_CONNECTED_TIME);
2637 		sinfo->connected_time = le32_to_cpu(sta_info_le.in);
2638 		brcmf_fill_bss_param(ifp, sinfo);
2639 	}
2640 	if (sta_flags & BRCMF_STA_SCBSTATS) {
2641 		sinfo->filled |= BIT(NL80211_STA_INFO_TX_FAILED);
2642 		sinfo->tx_failed = le32_to_cpu(sta_info_le.tx_failures);
2643 		sinfo->filled |= BIT(NL80211_STA_INFO_TX_PACKETS);
2644 		sinfo->tx_packets = le32_to_cpu(sta_info_le.tx_pkts);
2645 		sinfo->tx_packets += le32_to_cpu(sta_info_le.tx_mcast_pkts);
2646 		sinfo->filled |= BIT(NL80211_STA_INFO_RX_PACKETS);
2647 		sinfo->rx_packets = le32_to_cpu(sta_info_le.rx_ucast_pkts);
2648 		sinfo->rx_packets += le32_to_cpu(sta_info_le.rx_mcast_pkts);
2649 		if (sinfo->tx_packets) {
2650 			sinfo->filled |= BIT(NL80211_STA_INFO_TX_BITRATE);
2651 			sinfo->txrate.legacy =
2652 				le32_to_cpu(sta_info_le.tx_rate) / 100;
2653 		}
2654 		if (sinfo->rx_packets) {
2655 			sinfo->filled |= BIT(NL80211_STA_INFO_RX_BITRATE);
2656 			sinfo->rxrate.legacy =
2657 				le32_to_cpu(sta_info_le.rx_rate) / 100;
2658 		}
2659 		if (le16_to_cpu(sta_info_le.ver) >= 4) {
2660 			sinfo->filled |= BIT(NL80211_STA_INFO_TX_BYTES);
2661 			sinfo->tx_bytes = le64_to_cpu(sta_info_le.tx_tot_bytes);
2662 			sinfo->filled |= BIT(NL80211_STA_INFO_RX_BYTES);
2663 			sinfo->rx_bytes = le64_to_cpu(sta_info_le.rx_tot_bytes);
2664 		}
2665 		total_rssi = 0;
2666 		count_rssi = 0;
2667 		for (i = 0; i < BRCMF_ANT_MAX; i++) {
2668 			if (sta_info_le.rssi[i]) {
2669 				sinfo->chain_signal_avg[count_rssi] =
2670 					sta_info_le.rssi[i];
2671 				sinfo->chain_signal[count_rssi] =
2672 					sta_info_le.rssi[i];
2673 				total_rssi += sta_info_le.rssi[i];
2674 				count_rssi++;
2675 			}
2676 		}
2677 		if (count_rssi) {
2678 			sinfo->filled |= BIT(NL80211_STA_INFO_CHAIN_SIGNAL);
2679 			sinfo->chains = count_rssi;
2680 
2681 			sinfo->filled |= BIT(NL80211_STA_INFO_SIGNAL);
2682 			total_rssi /= count_rssi;
2683 			sinfo->signal = total_rssi;
2684 		} else if (test_bit(BRCMF_VIF_STATUS_CONNECTED,
2685 			&ifp->vif->sme_state)) {
2686 			memset(&scb_val, 0, sizeof(scb_val));
2687 			err = brcmf_fil_cmd_data_get(ifp, BRCMF_C_GET_RSSI,
2688 						     &scb_val, sizeof(scb_val));
2689 			if (err) {
2690 				brcmf_err("Could not get rssi (%d)\n", err);
2691 				goto done;
2692 			} else {
2693 				rssi = le32_to_cpu(scb_val.val);
2694 				sinfo->filled |= BIT(NL80211_STA_INFO_SIGNAL);
2695 				sinfo->signal = rssi;
2696 				brcmf_dbg(CONN, "RSSI %d dBm\n", rssi);
2697 			}
2698 		}
2699 	}
2700 done:
2701 	brcmf_dbg(TRACE, "Exit\n");
2702 	return err;
2703 }
2704 
2705 static int
2706 brcmf_cfg80211_dump_station(struct wiphy *wiphy, struct net_device *ndev,
2707 			    int idx, u8 *mac, struct station_info *sinfo)
2708 {
2709 	struct brcmf_cfg80211_info *cfg = wiphy_to_cfg(wiphy);
2710 	struct brcmf_if *ifp = netdev_priv(ndev);
2711 	s32 err;
2712 
2713 	brcmf_dbg(TRACE, "Enter, idx %d\n", idx);
2714 
2715 	if (idx == 0) {
2716 		cfg->assoclist.count = cpu_to_le32(BRCMF_MAX_ASSOCLIST);
2717 		err = brcmf_fil_cmd_data_get(ifp, BRCMF_C_GET_ASSOCLIST,
2718 					     &cfg->assoclist,
2719 					     sizeof(cfg->assoclist));
2720 		if (err) {
2721 			brcmf_err("BRCMF_C_GET_ASSOCLIST unsupported, err=%d\n",
2722 				  err);
2723 			cfg->assoclist.count = 0;
2724 			return -EOPNOTSUPP;
2725 		}
2726 	}
2727 	if (idx < le32_to_cpu(cfg->assoclist.count)) {
2728 		memcpy(mac, cfg->assoclist.mac[idx], ETH_ALEN);
2729 		return brcmf_cfg80211_get_station(wiphy, ndev, mac, sinfo);
2730 	}
2731 	return -ENOENT;
2732 }
2733 
2734 static s32
2735 brcmf_cfg80211_set_power_mgmt(struct wiphy *wiphy, struct net_device *ndev,
2736 			   bool enabled, s32 timeout)
2737 {
2738 	s32 pm;
2739 	s32 err = 0;
2740 	struct brcmf_cfg80211_info *cfg = wiphy_to_cfg(wiphy);
2741 	struct brcmf_if *ifp = netdev_priv(ndev);
2742 
2743 	brcmf_dbg(TRACE, "Enter\n");
2744 
2745 	/*
2746 	 * Powersave enable/disable request is coming from the
2747 	 * cfg80211 even before the interface is up. In that
2748 	 * scenario, driver will be storing the power save
2749 	 * preference in cfg struct to apply this to
2750 	 * FW later while initializing the dongle
2751 	 */
2752 	cfg->pwr_save = enabled;
2753 	if (!check_vif_up(ifp->vif)) {
2754 
2755 		brcmf_dbg(INFO, "Device is not ready, storing the value in cfg_info struct\n");
2756 		goto done;
2757 	}
2758 
2759 	pm = enabled ? PM_FAST : PM_OFF;
2760 	/* Do not enable the power save after assoc if it is a p2p interface */
2761 	if (ifp->vif->wdev.iftype == NL80211_IFTYPE_P2P_CLIENT) {
2762 		brcmf_dbg(INFO, "Do not enable power save for P2P clients\n");
2763 		pm = PM_OFF;
2764 	}
2765 	brcmf_dbg(INFO, "power save %s\n", (pm ? "enabled" : "disabled"));
2766 
2767 	err = brcmf_fil_cmd_int_set(ifp, BRCMF_C_SET_PM, pm);
2768 	if (err) {
2769 		if (err == -ENODEV)
2770 			brcmf_err("net_device is not ready yet\n");
2771 		else
2772 			brcmf_err("error (%d)\n", err);
2773 	}
2774 done:
2775 	brcmf_dbg(TRACE, "Exit\n");
2776 	return err;
2777 }
2778 
2779 static s32 brcmf_inform_single_bss(struct brcmf_cfg80211_info *cfg,
2780 				   struct brcmf_bss_info_le *bi)
2781 {
2782 	struct wiphy *wiphy = cfg_to_wiphy(cfg);
2783 	struct ieee80211_channel *notify_channel;
2784 	struct cfg80211_bss *bss;
2785 	struct ieee80211_supported_band *band;
2786 	struct brcmu_chan ch;
2787 	u16 channel;
2788 	u32 freq;
2789 	u16 notify_capability;
2790 	u16 notify_interval;
2791 	u8 *notify_ie;
2792 	size_t notify_ielen;
2793 	s32 notify_signal;
2794 
2795 	if (le32_to_cpu(bi->length) > WL_BSS_INFO_MAX) {
2796 		brcmf_err("Bss info is larger than buffer. Discarding\n");
2797 		return 0;
2798 	}
2799 
2800 	if (!bi->ctl_ch) {
2801 		ch.chspec = le16_to_cpu(bi->chanspec);
2802 		cfg->d11inf.decchspec(&ch);
2803 		bi->ctl_ch = ch.control_ch_num;
2804 	}
2805 	channel = bi->ctl_ch;
2806 
2807 	if (channel <= CH_MAX_2G_CHANNEL)
2808 		band = wiphy->bands[NL80211_BAND_2GHZ];
2809 	else
2810 		band = wiphy->bands[NL80211_BAND_5GHZ];
2811 
2812 	freq = ieee80211_channel_to_frequency(channel, band->band);
2813 	notify_channel = ieee80211_get_channel(wiphy, freq);
2814 
2815 	notify_capability = le16_to_cpu(bi->capability);
2816 	notify_interval = le16_to_cpu(bi->beacon_period);
2817 	notify_ie = (u8 *)bi + le16_to_cpu(bi->ie_offset);
2818 	notify_ielen = le32_to_cpu(bi->ie_length);
2819 	notify_signal = (s16)le16_to_cpu(bi->RSSI) * 100;
2820 
2821 	brcmf_dbg(CONN, "bssid: %pM\n", bi->BSSID);
2822 	brcmf_dbg(CONN, "Channel: %d(%d)\n", channel, freq);
2823 	brcmf_dbg(CONN, "Capability: %X\n", notify_capability);
2824 	brcmf_dbg(CONN, "Beacon interval: %d\n", notify_interval);
2825 	brcmf_dbg(CONN, "Signal: %d\n", notify_signal);
2826 
2827 	bss = cfg80211_inform_bss(wiphy, notify_channel,
2828 				  CFG80211_BSS_FTYPE_UNKNOWN,
2829 				  (const u8 *)bi->BSSID,
2830 				  0, notify_capability,
2831 				  notify_interval, notify_ie,
2832 				  notify_ielen, notify_signal,
2833 				  GFP_KERNEL);
2834 
2835 	if (!bss)
2836 		return -ENOMEM;
2837 
2838 	cfg80211_put_bss(wiphy, bss);
2839 
2840 	return 0;
2841 }
2842 
2843 static struct brcmf_bss_info_le *
2844 next_bss_le(struct brcmf_scan_results *list, struct brcmf_bss_info_le *bss)
2845 {
2846 	if (bss == NULL)
2847 		return list->bss_info_le;
2848 	return (struct brcmf_bss_info_le *)((unsigned long)bss +
2849 					    le32_to_cpu(bss->length));
2850 }
2851 
2852 static s32 brcmf_inform_bss(struct brcmf_cfg80211_info *cfg)
2853 {
2854 	struct brcmf_scan_results *bss_list;
2855 	struct brcmf_bss_info_le *bi = NULL;	/* must be initialized */
2856 	s32 err = 0;
2857 	int i;
2858 
2859 	bss_list = (struct brcmf_scan_results *)cfg->escan_info.escan_buf;
2860 	if (bss_list->count != 0 &&
2861 	    bss_list->version != BRCMF_BSS_INFO_VERSION) {
2862 		brcmf_err("Version %d != WL_BSS_INFO_VERSION\n",
2863 			  bss_list->version);
2864 		return -EOPNOTSUPP;
2865 	}
2866 	brcmf_dbg(SCAN, "scanned AP count (%d)\n", bss_list->count);
2867 	for (i = 0; i < bss_list->count; i++) {
2868 		bi = next_bss_le(bss_list, bi);
2869 		err = brcmf_inform_single_bss(cfg, bi);
2870 		if (err)
2871 			break;
2872 	}
2873 	return err;
2874 }
2875 
2876 static s32 brcmf_inform_ibss(struct brcmf_cfg80211_info *cfg,
2877 			     struct net_device *ndev, const u8 *bssid)
2878 {
2879 	struct wiphy *wiphy = cfg_to_wiphy(cfg);
2880 	struct ieee80211_channel *notify_channel;
2881 	struct brcmf_bss_info_le *bi = NULL;
2882 	struct ieee80211_supported_band *band;
2883 	struct cfg80211_bss *bss;
2884 	struct brcmu_chan ch;
2885 	u8 *buf = NULL;
2886 	s32 err = 0;
2887 	u32 freq;
2888 	u16 notify_capability;
2889 	u16 notify_interval;
2890 	u8 *notify_ie;
2891 	size_t notify_ielen;
2892 	s32 notify_signal;
2893 
2894 	brcmf_dbg(TRACE, "Enter\n");
2895 
2896 	buf = kzalloc(WL_BSS_INFO_MAX, GFP_KERNEL);
2897 	if (buf == NULL) {
2898 		err = -ENOMEM;
2899 		goto CleanUp;
2900 	}
2901 
2902 	*(__le32 *)buf = cpu_to_le32(WL_BSS_INFO_MAX);
2903 
2904 	err = brcmf_fil_cmd_data_get(netdev_priv(ndev), BRCMF_C_GET_BSS_INFO,
2905 				     buf, WL_BSS_INFO_MAX);
2906 	if (err) {
2907 		brcmf_err("WLC_GET_BSS_INFO failed: %d\n", err);
2908 		goto CleanUp;
2909 	}
2910 
2911 	bi = (struct brcmf_bss_info_le *)(buf + 4);
2912 
2913 	ch.chspec = le16_to_cpu(bi->chanspec);
2914 	cfg->d11inf.decchspec(&ch);
2915 
2916 	if (ch.band == BRCMU_CHAN_BAND_2G)
2917 		band = wiphy->bands[NL80211_BAND_2GHZ];
2918 	else
2919 		band = wiphy->bands[NL80211_BAND_5GHZ];
2920 
2921 	freq = ieee80211_channel_to_frequency(ch.control_ch_num, band->band);
2922 	cfg->channel = freq;
2923 	notify_channel = ieee80211_get_channel(wiphy, freq);
2924 
2925 	notify_capability = le16_to_cpu(bi->capability);
2926 	notify_interval = le16_to_cpu(bi->beacon_period);
2927 	notify_ie = (u8 *)bi + le16_to_cpu(bi->ie_offset);
2928 	notify_ielen = le32_to_cpu(bi->ie_length);
2929 	notify_signal = (s16)le16_to_cpu(bi->RSSI) * 100;
2930 
2931 	brcmf_dbg(CONN, "channel: %d(%d)\n", ch.control_ch_num, freq);
2932 	brcmf_dbg(CONN, "capability: %X\n", notify_capability);
2933 	brcmf_dbg(CONN, "beacon interval: %d\n", notify_interval);
2934 	brcmf_dbg(CONN, "signal: %d\n", notify_signal);
2935 
2936 	bss = cfg80211_inform_bss(wiphy, notify_channel,
2937 				  CFG80211_BSS_FTYPE_UNKNOWN, bssid, 0,
2938 				  notify_capability, notify_interval,
2939 				  notify_ie, notify_ielen, notify_signal,
2940 				  GFP_KERNEL);
2941 
2942 	if (!bss) {
2943 		err = -ENOMEM;
2944 		goto CleanUp;
2945 	}
2946 
2947 	cfg80211_put_bss(wiphy, bss);
2948 
2949 CleanUp:
2950 
2951 	kfree(buf);
2952 
2953 	brcmf_dbg(TRACE, "Exit\n");
2954 
2955 	return err;
2956 }
2957 
2958 static s32 brcmf_update_bss_info(struct brcmf_cfg80211_info *cfg,
2959 				 struct brcmf_if *ifp)
2960 {
2961 	struct brcmf_bss_info_le *bi;
2962 	const struct brcmf_tlv *tim;
2963 	u16 beacon_interval;
2964 	u8 dtim_period;
2965 	size_t ie_len;
2966 	u8 *ie;
2967 	s32 err = 0;
2968 
2969 	brcmf_dbg(TRACE, "Enter\n");
2970 	if (brcmf_is_ibssmode(ifp->vif))
2971 		return err;
2972 
2973 	*(__le32 *)cfg->extra_buf = cpu_to_le32(WL_EXTRA_BUF_MAX);
2974 	err = brcmf_fil_cmd_data_get(ifp, BRCMF_C_GET_BSS_INFO,
2975 				     cfg->extra_buf, WL_EXTRA_BUF_MAX);
2976 	if (err) {
2977 		brcmf_err("Could not get bss info %d\n", err);
2978 		goto update_bss_info_out;
2979 	}
2980 
2981 	bi = (struct brcmf_bss_info_le *)(cfg->extra_buf + 4);
2982 	err = brcmf_inform_single_bss(cfg, bi);
2983 	if (err)
2984 		goto update_bss_info_out;
2985 
2986 	ie = ((u8 *)bi) + le16_to_cpu(bi->ie_offset);
2987 	ie_len = le32_to_cpu(bi->ie_length);
2988 	beacon_interval = le16_to_cpu(bi->beacon_period);
2989 
2990 	tim = brcmf_parse_tlvs(ie, ie_len, WLAN_EID_TIM);
2991 	if (tim)
2992 		dtim_period = tim->data[1];
2993 	else {
2994 		/*
2995 		* active scan was done so we could not get dtim
2996 		* information out of probe response.
2997 		* so we speficially query dtim information to dongle.
2998 		*/
2999 		u32 var;
3000 		err = brcmf_fil_iovar_int_get(ifp, "dtim_assoc", &var);
3001 		if (err) {
3002 			brcmf_err("wl dtim_assoc failed (%d)\n", err);
3003 			goto update_bss_info_out;
3004 		}
3005 		dtim_period = (u8)var;
3006 	}
3007 
3008 update_bss_info_out:
3009 	brcmf_dbg(TRACE, "Exit");
3010 	return err;
3011 }
3012 
3013 void brcmf_abort_scanning(struct brcmf_cfg80211_info *cfg)
3014 {
3015 	struct escan_info *escan = &cfg->escan_info;
3016 
3017 	set_bit(BRCMF_SCAN_STATUS_ABORT, &cfg->scan_status);
3018 	if (cfg->internal_escan || cfg->scan_request) {
3019 		escan->escan_state = WL_ESCAN_STATE_IDLE;
3020 		brcmf_notify_escan_complete(cfg, escan->ifp, true, true);
3021 	}
3022 	clear_bit(BRCMF_SCAN_STATUS_BUSY, &cfg->scan_status);
3023 	clear_bit(BRCMF_SCAN_STATUS_ABORT, &cfg->scan_status);
3024 }
3025 
3026 static void brcmf_cfg80211_escan_timeout_worker(struct work_struct *work)
3027 {
3028 	struct brcmf_cfg80211_info *cfg =
3029 			container_of(work, struct brcmf_cfg80211_info,
3030 				     escan_timeout_work);
3031 
3032 	brcmf_inform_bss(cfg);
3033 	brcmf_notify_escan_complete(cfg, cfg->escan_info.ifp, true, true);
3034 }
3035 
3036 static void brcmf_escan_timeout(unsigned long data)
3037 {
3038 	struct brcmf_cfg80211_info *cfg =
3039 			(struct brcmf_cfg80211_info *)data;
3040 
3041 	if (cfg->internal_escan || cfg->scan_request) {
3042 		brcmf_err("timer expired\n");
3043 		schedule_work(&cfg->escan_timeout_work);
3044 	}
3045 }
3046 
3047 static s32
3048 brcmf_compare_update_same_bss(struct brcmf_cfg80211_info *cfg,
3049 			      struct brcmf_bss_info_le *bss,
3050 			      struct brcmf_bss_info_le *bss_info_le)
3051 {
3052 	struct brcmu_chan ch_bss, ch_bss_info_le;
3053 
3054 	ch_bss.chspec = le16_to_cpu(bss->chanspec);
3055 	cfg->d11inf.decchspec(&ch_bss);
3056 	ch_bss_info_le.chspec = le16_to_cpu(bss_info_le->chanspec);
3057 	cfg->d11inf.decchspec(&ch_bss_info_le);
3058 
3059 	if (!memcmp(&bss_info_le->BSSID, &bss->BSSID, ETH_ALEN) &&
3060 		ch_bss.band == ch_bss_info_le.band &&
3061 		bss_info_le->SSID_len == bss->SSID_len &&
3062 		!memcmp(bss_info_le->SSID, bss->SSID, bss_info_le->SSID_len)) {
3063 		if ((bss->flags & BRCMF_BSS_RSSI_ON_CHANNEL) ==
3064 			(bss_info_le->flags & BRCMF_BSS_RSSI_ON_CHANNEL)) {
3065 			s16 bss_rssi = le16_to_cpu(bss->RSSI);
3066 			s16 bss_info_rssi = le16_to_cpu(bss_info_le->RSSI);
3067 
3068 			/* preserve max RSSI if the measurements are
3069 			* both on-channel or both off-channel
3070 			*/
3071 			if (bss_info_rssi > bss_rssi)
3072 				bss->RSSI = bss_info_le->RSSI;
3073 		} else if ((bss->flags & BRCMF_BSS_RSSI_ON_CHANNEL) &&
3074 			(bss_info_le->flags & BRCMF_BSS_RSSI_ON_CHANNEL) == 0) {
3075 			/* preserve the on-channel rssi measurement
3076 			* if the new measurement is off channel
3077 			*/
3078 			bss->RSSI = bss_info_le->RSSI;
3079 			bss->flags |= BRCMF_BSS_RSSI_ON_CHANNEL;
3080 		}
3081 		return 1;
3082 	}
3083 	return 0;
3084 }
3085 
3086 static s32
3087 brcmf_cfg80211_escan_handler(struct brcmf_if *ifp,
3088 			     const struct brcmf_event_msg *e, void *data)
3089 {
3090 	struct brcmf_cfg80211_info *cfg = ifp->drvr->config;
3091 	s32 status;
3092 	struct brcmf_escan_result_le *escan_result_le;
3093 	struct brcmf_bss_info_le *bss_info_le;
3094 	struct brcmf_bss_info_le *bss = NULL;
3095 	u32 bi_length;
3096 	struct brcmf_scan_results *list;
3097 	u32 i;
3098 	bool aborted;
3099 
3100 	status = e->status;
3101 
3102 	if (!test_bit(BRCMF_SCAN_STATUS_BUSY, &cfg->scan_status)) {
3103 		brcmf_err("scan not ready, bsscfgidx=%d\n", ifp->bsscfgidx);
3104 		return -EPERM;
3105 	}
3106 
3107 	if (status == BRCMF_E_STATUS_PARTIAL) {
3108 		brcmf_dbg(SCAN, "ESCAN Partial result\n");
3109 		escan_result_le = (struct brcmf_escan_result_le *) data;
3110 		if (!escan_result_le) {
3111 			brcmf_err("Invalid escan result (NULL pointer)\n");
3112 			goto exit;
3113 		}
3114 		if (le16_to_cpu(escan_result_le->bss_count) != 1) {
3115 			brcmf_err("Invalid bss_count %d: ignoring\n",
3116 				  escan_result_le->bss_count);
3117 			goto exit;
3118 		}
3119 		bss_info_le = &escan_result_le->bss_info_le;
3120 
3121 		if (brcmf_p2p_scan_finding_common_channel(cfg, bss_info_le))
3122 			goto exit;
3123 
3124 		if (!cfg->internal_escan && !cfg->scan_request) {
3125 			brcmf_dbg(SCAN, "result without cfg80211 request\n");
3126 			goto exit;
3127 		}
3128 
3129 		bi_length = le32_to_cpu(bss_info_le->length);
3130 		if (bi_length != (le32_to_cpu(escan_result_le->buflen) -
3131 					WL_ESCAN_RESULTS_FIXED_SIZE)) {
3132 			brcmf_err("Invalid bss_info length %d: ignoring\n",
3133 				  bi_length);
3134 			goto exit;
3135 		}
3136 
3137 		if (!(cfg_to_wiphy(cfg)->interface_modes &
3138 					BIT(NL80211_IFTYPE_ADHOC))) {
3139 			if (le16_to_cpu(bss_info_le->capability) &
3140 						WLAN_CAPABILITY_IBSS) {
3141 				brcmf_err("Ignoring IBSS result\n");
3142 				goto exit;
3143 			}
3144 		}
3145 
3146 		list = (struct brcmf_scan_results *)
3147 				cfg->escan_info.escan_buf;
3148 		if (bi_length > BRCMF_ESCAN_BUF_SIZE - list->buflen) {
3149 			brcmf_err("Buffer is too small: ignoring\n");
3150 			goto exit;
3151 		}
3152 
3153 		for (i = 0; i < list->count; i++) {
3154 			bss = bss ? (struct brcmf_bss_info_le *)
3155 				((unsigned char *)bss +
3156 				le32_to_cpu(bss->length)) : list->bss_info_le;
3157 			if (brcmf_compare_update_same_bss(cfg, bss,
3158 							  bss_info_le))
3159 				goto exit;
3160 		}
3161 		memcpy(&cfg->escan_info.escan_buf[list->buflen], bss_info_le,
3162 		       bi_length);
3163 		list->version = le32_to_cpu(bss_info_le->version);
3164 		list->buflen += bi_length;
3165 		list->count++;
3166 	} else {
3167 		cfg->escan_info.escan_state = WL_ESCAN_STATE_IDLE;
3168 		if (brcmf_p2p_scan_finding_common_channel(cfg, NULL))
3169 			goto exit;
3170 		if (cfg->internal_escan || cfg->scan_request) {
3171 			brcmf_inform_bss(cfg);
3172 			aborted = status != BRCMF_E_STATUS_SUCCESS;
3173 			brcmf_notify_escan_complete(cfg, ifp, aborted, false);
3174 		} else
3175 			brcmf_dbg(SCAN, "Ignored scan complete result 0x%x\n",
3176 				  status);
3177 	}
3178 exit:
3179 	return 0;
3180 }
3181 
3182 static void brcmf_init_escan(struct brcmf_cfg80211_info *cfg)
3183 {
3184 	brcmf_fweh_register(cfg->pub, BRCMF_E_ESCAN_RESULT,
3185 			    brcmf_cfg80211_escan_handler);
3186 	cfg->escan_info.escan_state = WL_ESCAN_STATE_IDLE;
3187 	/* Init scan_timeout timer */
3188 	init_timer(&cfg->escan_timeout);
3189 	cfg->escan_timeout.data = (unsigned long) cfg;
3190 	cfg->escan_timeout.function = brcmf_escan_timeout;
3191 	INIT_WORK(&cfg->escan_timeout_work,
3192 		  brcmf_cfg80211_escan_timeout_worker);
3193 }
3194 
3195 static struct cfg80211_scan_request *
3196 brcmf_alloc_internal_escan_request(struct wiphy *wiphy, u32 n_netinfo) {
3197 	struct cfg80211_scan_request *req;
3198 	size_t req_size;
3199 
3200 	req_size = sizeof(*req) +
3201 		   n_netinfo * sizeof(req->channels[0]) +
3202 		   n_netinfo * sizeof(*req->ssids);
3203 
3204 	req = kzalloc(req_size, GFP_KERNEL);
3205 	if (req) {
3206 		req->wiphy = wiphy;
3207 		req->ssids = (void *)(&req->channels[0]) +
3208 			     n_netinfo * sizeof(req->channels[0]);
3209 	}
3210 	return req;
3211 }
3212 
3213 static int brcmf_internal_escan_add_info(struct cfg80211_scan_request *req,
3214 					 u8 *ssid, u8 ssid_len, u8 channel)
3215 {
3216 	struct ieee80211_channel *chan;
3217 	enum nl80211_band band;
3218 	int freq;
3219 
3220 	if (channel <= CH_MAX_2G_CHANNEL)
3221 		band = NL80211_BAND_2GHZ;
3222 	else
3223 		band = NL80211_BAND_5GHZ;
3224 
3225 	freq = ieee80211_channel_to_frequency(channel, band);
3226 	if (!freq)
3227 		return -EINVAL;
3228 
3229 	chan = ieee80211_get_channel(req->wiphy, freq);
3230 	if (!chan)
3231 		return -EINVAL;
3232 
3233 	req->channels[req->n_channels++] = chan;
3234 	memcpy(req->ssids[req->n_ssids].ssid, ssid, ssid_len);
3235 	req->ssids[req->n_ssids++].ssid_len = ssid_len;
3236 
3237 	return 0;
3238 }
3239 
3240 static int brcmf_start_internal_escan(struct brcmf_if *ifp,
3241 				      struct cfg80211_scan_request *request)
3242 {
3243 	struct brcmf_cfg80211_info *cfg = ifp->drvr->config;
3244 	int err;
3245 
3246 	if (test_bit(BRCMF_SCAN_STATUS_BUSY, &cfg->scan_status)) {
3247 		/* Abort any on-going scan */
3248 		brcmf_abort_scanning(cfg);
3249 	}
3250 
3251 	set_bit(BRCMF_SCAN_STATUS_BUSY, &cfg->scan_status);
3252 	cfg->escan_info.run = brcmf_run_escan;
3253 	err = brcmf_do_escan(ifp, request);
3254 	if (err) {
3255 		clear_bit(BRCMF_SCAN_STATUS_BUSY, &cfg->scan_status);
3256 		return err;
3257 	}
3258 	cfg->internal_escan = true;
3259 	return 0;
3260 }
3261 
3262 static struct brcmf_pno_net_info_le *
3263 brcmf_get_netinfo_array(struct brcmf_pno_scanresults_le *pfn_v1)
3264 {
3265 	struct brcmf_pno_scanresults_v2_le *pfn_v2;
3266 	struct brcmf_pno_net_info_le *netinfo;
3267 
3268 	switch (pfn_v1->version) {
3269 	default:
3270 		WARN_ON(1);
3271 		/* fall-thru */
3272 	case cpu_to_le32(1):
3273 		netinfo = (struct brcmf_pno_net_info_le *)(pfn_v1 + 1);
3274 		break;
3275 	case cpu_to_le32(2):
3276 		pfn_v2 = (struct brcmf_pno_scanresults_v2_le *)pfn_v1;
3277 		netinfo = (struct brcmf_pno_net_info_le *)(pfn_v2 + 1);
3278 		break;
3279 	}
3280 
3281 	return netinfo;
3282 }
3283 
3284 /* PFN result doesn't have all the info which are required by the supplicant
3285  * (For e.g IEs) Do a target Escan so that sched scan results are reported
3286  * via wl_inform_single_bss in the required format. Escan does require the
3287  * scan request in the form of cfg80211_scan_request. For timebeing, create
3288  * cfg80211_scan_request one out of the received PNO event.
3289  */
3290 static s32
3291 brcmf_notify_sched_scan_results(struct brcmf_if *ifp,
3292 				const struct brcmf_event_msg *e, void *data)
3293 {
3294 	struct brcmf_cfg80211_info *cfg = ifp->drvr->config;
3295 	struct brcmf_pno_net_info_le *netinfo, *netinfo_start;
3296 	struct cfg80211_scan_request *request = NULL;
3297 	struct wiphy *wiphy = cfg_to_wiphy(cfg);
3298 	int i, err = 0;
3299 	struct brcmf_pno_scanresults_le *pfn_result;
3300 	u32 result_count;
3301 	u32 status;
3302 
3303 	brcmf_dbg(SCAN, "Enter\n");
3304 
3305 	if (e->datalen < (sizeof(*pfn_result) + sizeof(*netinfo))) {
3306 		brcmf_dbg(SCAN, "Event data to small. Ignore\n");
3307 		return 0;
3308 	}
3309 
3310 	if (e->event_code == BRCMF_E_PFN_NET_LOST) {
3311 		brcmf_dbg(SCAN, "PFN NET LOST event. Do Nothing\n");
3312 		return 0;
3313 	}
3314 
3315 	pfn_result = (struct brcmf_pno_scanresults_le *)data;
3316 	result_count = le32_to_cpu(pfn_result->count);
3317 	status = le32_to_cpu(pfn_result->status);
3318 
3319 	/* PFN event is limited to fit 512 bytes so we may get
3320 	 * multiple NET_FOUND events. For now place a warning here.
3321 	 */
3322 	WARN_ON(status != BRCMF_PNO_SCAN_COMPLETE);
3323 	brcmf_dbg(SCAN, "PFN NET FOUND event. count: %d\n", result_count);
3324 	if (!result_count) {
3325 		brcmf_err("FALSE PNO Event. (pfn_count == 0)\n");
3326 		goto out_err;
3327 	}
3328 	request = brcmf_alloc_internal_escan_request(wiphy,
3329 						     result_count);
3330 	if (!request) {
3331 		err = -ENOMEM;
3332 		goto out_err;
3333 	}
3334 
3335 	data += sizeof(struct brcmf_pno_scanresults_le);
3336 	netinfo_start = brcmf_get_netinfo_array(pfn_result);
3337 
3338 	for (i = 0; i < result_count; i++) {
3339 		netinfo = &netinfo_start[i];
3340 		if (!netinfo) {
3341 			brcmf_err("Invalid netinfo ptr. index: %d\n",
3342 				  i);
3343 			err = -EINVAL;
3344 			goto out_err;
3345 		}
3346 
3347 		brcmf_dbg(SCAN, "SSID:%.32s Channel:%d\n",
3348 			  netinfo->SSID, netinfo->channel);
3349 		err = brcmf_internal_escan_add_info(request,
3350 						    netinfo->SSID,
3351 						    netinfo->SSID_len,
3352 						    netinfo->channel);
3353 		if (err)
3354 			goto out_err;
3355 	}
3356 
3357 	err = brcmf_start_internal_escan(ifp, request);
3358 	if (!err)
3359 		goto free_req;
3360 
3361 out_err:
3362 	cfg80211_sched_scan_stopped(wiphy);
3363 free_req:
3364 	kfree(request);
3365 	return err;
3366 }
3367 
3368 static int
3369 brcmf_cfg80211_sched_scan_start(struct wiphy *wiphy,
3370 				struct net_device *ndev,
3371 				struct cfg80211_sched_scan_request *req)
3372 {
3373 	struct brcmf_if *ifp = netdev_priv(ndev);
3374 	struct brcmf_cfg80211_info *cfg = wiphy_priv(wiphy);
3375 
3376 	brcmf_dbg(SCAN, "Enter n_match_sets:%d n_ssids:%d\n",
3377 		  req->n_match_sets, req->n_ssids);
3378 
3379 	if (test_bit(BRCMF_SCAN_STATUS_SUPPRESS, &cfg->scan_status)) {
3380 		brcmf_err("Scanning suppressed: status (%lu)\n",
3381 			  cfg->scan_status);
3382 		return -EAGAIN;
3383 	}
3384 
3385 	if (req->n_match_sets <= 0) {
3386 		brcmf_dbg(SCAN, "invalid number of matchsets specified: %d\n",
3387 			  req->n_match_sets);
3388 		return -EINVAL;
3389 	}
3390 
3391 	return brcmf_pno_start_sched_scan(ifp, req);
3392 }
3393 
3394 static int brcmf_cfg80211_sched_scan_stop(struct wiphy *wiphy,
3395 					  struct net_device *ndev)
3396 {
3397 	struct brcmf_cfg80211_info *cfg = wiphy_to_cfg(wiphy);
3398 	struct brcmf_if *ifp = netdev_priv(ndev);
3399 
3400 	brcmf_dbg(SCAN, "enter\n");
3401 	brcmf_pno_clean(ifp);
3402 	if (cfg->internal_escan)
3403 		brcmf_notify_escan_complete(cfg, ifp, true, true);
3404 	return 0;
3405 }
3406 
3407 static __always_inline void brcmf_delay(u32 ms)
3408 {
3409 	if (ms < 1000 / HZ) {
3410 		cond_resched();
3411 		mdelay(ms);
3412 	} else {
3413 		msleep(ms);
3414 	}
3415 }
3416 
3417 static s32 brcmf_config_wowl_pattern(struct brcmf_if *ifp, u8 cmd[4],
3418 				     u8 *pattern, u32 patternsize, u8 *mask,
3419 				     u32 packet_offset)
3420 {
3421 	struct brcmf_fil_wowl_pattern_le *filter;
3422 	u32 masksize;
3423 	u32 patternoffset;
3424 	u8 *buf;
3425 	u32 bufsize;
3426 	s32 ret;
3427 
3428 	masksize = (patternsize + 7) / 8;
3429 	patternoffset = sizeof(*filter) - sizeof(filter->cmd) + masksize;
3430 
3431 	bufsize = sizeof(*filter) + patternsize + masksize;
3432 	buf = kzalloc(bufsize, GFP_KERNEL);
3433 	if (!buf)
3434 		return -ENOMEM;
3435 	filter = (struct brcmf_fil_wowl_pattern_le *)buf;
3436 
3437 	memcpy(filter->cmd, cmd, 4);
3438 	filter->masksize = cpu_to_le32(masksize);
3439 	filter->offset = cpu_to_le32(packet_offset);
3440 	filter->patternoffset = cpu_to_le32(patternoffset);
3441 	filter->patternsize = cpu_to_le32(patternsize);
3442 	filter->type = cpu_to_le32(BRCMF_WOWL_PATTERN_TYPE_BITMAP);
3443 
3444 	if ((mask) && (masksize))
3445 		memcpy(buf + sizeof(*filter), mask, masksize);
3446 	if ((pattern) && (patternsize))
3447 		memcpy(buf + sizeof(*filter) + masksize, pattern, patternsize);
3448 
3449 	ret = brcmf_fil_iovar_data_set(ifp, "wowl_pattern", buf, bufsize);
3450 
3451 	kfree(buf);
3452 	return ret;
3453 }
3454 
3455 static s32
3456 brcmf_wowl_nd_results(struct brcmf_if *ifp, const struct brcmf_event_msg *e,
3457 		      void *data)
3458 {
3459 	struct brcmf_cfg80211_info *cfg = ifp->drvr->config;
3460 	struct brcmf_pno_scanresults_le *pfn_result;
3461 	struct brcmf_pno_net_info_le *netinfo;
3462 
3463 	brcmf_dbg(SCAN, "Enter\n");
3464 
3465 	if (e->datalen < (sizeof(*pfn_result) + sizeof(*netinfo))) {
3466 		brcmf_dbg(SCAN, "Event data to small. Ignore\n");
3467 		return 0;
3468 	}
3469 
3470 	pfn_result = (struct brcmf_pno_scanresults_le *)data;
3471 
3472 	if (e->event_code == BRCMF_E_PFN_NET_LOST) {
3473 		brcmf_dbg(SCAN, "PFN NET LOST event. Ignore\n");
3474 		return 0;
3475 	}
3476 
3477 	if (le32_to_cpu(pfn_result->count) < 1) {
3478 		brcmf_err("Invalid result count, expected 1 (%d)\n",
3479 			  le32_to_cpu(pfn_result->count));
3480 		return -EINVAL;
3481 	}
3482 
3483 	data += sizeof(struct brcmf_pno_scanresults_le);
3484 	netinfo = (struct brcmf_pno_net_info_le *)data;
3485 	memcpy(cfg->wowl.nd->ssid.ssid, netinfo->SSID, netinfo->SSID_len);
3486 	cfg->wowl.nd->ssid.ssid_len = netinfo->SSID_len;
3487 	cfg->wowl.nd->n_channels = 1;
3488 	cfg->wowl.nd->channels[0] =
3489 		ieee80211_channel_to_frequency(netinfo->channel,
3490 			netinfo->channel <= CH_MAX_2G_CHANNEL ?
3491 					NL80211_BAND_2GHZ : NL80211_BAND_5GHZ);
3492 	cfg->wowl.nd_info->n_matches = 1;
3493 	cfg->wowl.nd_info->matches[0] = cfg->wowl.nd;
3494 
3495 	/* Inform (the resume task) that the net detect information was recvd */
3496 	cfg->wowl.nd_data_completed = true;
3497 	wake_up(&cfg->wowl.nd_data_wait);
3498 
3499 	return 0;
3500 }
3501 
3502 #ifdef CONFIG_PM
3503 
3504 static void brcmf_report_wowl_wakeind(struct wiphy *wiphy, struct brcmf_if *ifp)
3505 {
3506 	struct brcmf_cfg80211_info *cfg = wiphy_to_cfg(wiphy);
3507 	struct brcmf_wowl_wakeind_le wake_ind_le;
3508 	struct cfg80211_wowlan_wakeup wakeup_data;
3509 	struct cfg80211_wowlan_wakeup *wakeup;
3510 	u32 wakeind;
3511 	s32 err;
3512 	int timeout;
3513 
3514 	err = brcmf_fil_iovar_data_get(ifp, "wowl_wakeind", &wake_ind_le,
3515 				       sizeof(wake_ind_le));
3516 	if (err) {
3517 		brcmf_err("Get wowl_wakeind failed, err = %d\n", err);
3518 		return;
3519 	}
3520 
3521 	wakeind = le32_to_cpu(wake_ind_le.ucode_wakeind);
3522 	if (wakeind & (BRCMF_WOWL_MAGIC | BRCMF_WOWL_DIS | BRCMF_WOWL_BCN |
3523 		       BRCMF_WOWL_RETR | BRCMF_WOWL_NET |
3524 		       BRCMF_WOWL_PFN_FOUND)) {
3525 		wakeup = &wakeup_data;
3526 		memset(&wakeup_data, 0, sizeof(wakeup_data));
3527 		wakeup_data.pattern_idx = -1;
3528 
3529 		if (wakeind & BRCMF_WOWL_MAGIC) {
3530 			brcmf_dbg(INFO, "WOWL Wake indicator: BRCMF_WOWL_MAGIC\n");
3531 			wakeup_data.magic_pkt = true;
3532 		}
3533 		if (wakeind & BRCMF_WOWL_DIS) {
3534 			brcmf_dbg(INFO, "WOWL Wake indicator: BRCMF_WOWL_DIS\n");
3535 			wakeup_data.disconnect = true;
3536 		}
3537 		if (wakeind & BRCMF_WOWL_BCN) {
3538 			brcmf_dbg(INFO, "WOWL Wake indicator: BRCMF_WOWL_BCN\n");
3539 			wakeup_data.disconnect = true;
3540 		}
3541 		if (wakeind & BRCMF_WOWL_RETR) {
3542 			brcmf_dbg(INFO, "WOWL Wake indicator: BRCMF_WOWL_RETR\n");
3543 			wakeup_data.disconnect = true;
3544 		}
3545 		if (wakeind & BRCMF_WOWL_NET) {
3546 			brcmf_dbg(INFO, "WOWL Wake indicator: BRCMF_WOWL_NET\n");
3547 			/* For now always map to pattern 0, no API to get
3548 			 * correct information available at the moment.
3549 			 */
3550 			wakeup_data.pattern_idx = 0;
3551 		}
3552 		if (wakeind & BRCMF_WOWL_PFN_FOUND) {
3553 			brcmf_dbg(INFO, "WOWL Wake indicator: BRCMF_WOWL_PFN_FOUND\n");
3554 			timeout = wait_event_timeout(cfg->wowl.nd_data_wait,
3555 				cfg->wowl.nd_data_completed,
3556 				BRCMF_ND_INFO_TIMEOUT);
3557 			if (!timeout)
3558 				brcmf_err("No result for wowl net detect\n");
3559 			else
3560 				wakeup_data.net_detect = cfg->wowl.nd_info;
3561 		}
3562 		if (wakeind & BRCMF_WOWL_GTK_FAILURE) {
3563 			brcmf_dbg(INFO, "WOWL Wake indicator: BRCMF_WOWL_GTK_FAILURE\n");
3564 			wakeup_data.gtk_rekey_failure = true;
3565 		}
3566 	} else {
3567 		wakeup = NULL;
3568 	}
3569 	cfg80211_report_wowlan_wakeup(&ifp->vif->wdev, wakeup, GFP_KERNEL);
3570 }
3571 
3572 #else
3573 
3574 static void brcmf_report_wowl_wakeind(struct wiphy *wiphy, struct brcmf_if *ifp)
3575 {
3576 }
3577 
3578 #endif /* CONFIG_PM */
3579 
3580 static s32 brcmf_cfg80211_resume(struct wiphy *wiphy)
3581 {
3582 	struct brcmf_cfg80211_info *cfg = wiphy_to_cfg(wiphy);
3583 	struct net_device *ndev = cfg_to_ndev(cfg);
3584 	struct brcmf_if *ifp = netdev_priv(ndev);
3585 
3586 	brcmf_dbg(TRACE, "Enter\n");
3587 
3588 	if (cfg->wowl.active) {
3589 		brcmf_report_wowl_wakeind(wiphy, ifp);
3590 		brcmf_fil_iovar_int_set(ifp, "wowl_clear", 0);
3591 		brcmf_config_wowl_pattern(ifp, "clr", NULL, 0, NULL, 0);
3592 		if (!brcmf_feat_is_enabled(ifp, BRCMF_FEAT_WOWL_ARP_ND))
3593 			brcmf_configure_arp_nd_offload(ifp, true);
3594 		brcmf_fil_cmd_int_set(ifp, BRCMF_C_SET_PM,
3595 				      cfg->wowl.pre_pmmode);
3596 		cfg->wowl.active = false;
3597 		if (cfg->wowl.nd_enabled) {
3598 			brcmf_cfg80211_sched_scan_stop(cfg->wiphy, ifp->ndev);
3599 			brcmf_fweh_unregister(cfg->pub, BRCMF_E_PFN_NET_FOUND);
3600 			brcmf_fweh_register(cfg->pub, BRCMF_E_PFN_NET_FOUND,
3601 					    brcmf_notify_sched_scan_results);
3602 			cfg->wowl.nd_enabled = false;
3603 		}
3604 	}
3605 	return 0;
3606 }
3607 
3608 static void brcmf_configure_wowl(struct brcmf_cfg80211_info *cfg,
3609 				 struct brcmf_if *ifp,
3610 				 struct cfg80211_wowlan *wowl)
3611 {
3612 	u32 wowl_config;
3613 	struct brcmf_wowl_wakeind_le wowl_wakeind;
3614 	u32 i;
3615 
3616 	brcmf_dbg(TRACE, "Suspend, wowl config.\n");
3617 
3618 	if (!brcmf_feat_is_enabled(ifp, BRCMF_FEAT_WOWL_ARP_ND))
3619 		brcmf_configure_arp_nd_offload(ifp, false);
3620 	brcmf_fil_cmd_int_get(ifp, BRCMF_C_GET_PM, &cfg->wowl.pre_pmmode);
3621 	brcmf_fil_cmd_int_set(ifp, BRCMF_C_SET_PM, PM_MAX);
3622 
3623 	wowl_config = 0;
3624 	if (wowl->disconnect)
3625 		wowl_config = BRCMF_WOWL_DIS | BRCMF_WOWL_BCN | BRCMF_WOWL_RETR;
3626 	if (wowl->magic_pkt)
3627 		wowl_config |= BRCMF_WOWL_MAGIC;
3628 	if ((wowl->patterns) && (wowl->n_patterns)) {
3629 		wowl_config |= BRCMF_WOWL_NET;
3630 		for (i = 0; i < wowl->n_patterns; i++) {
3631 			brcmf_config_wowl_pattern(ifp, "add",
3632 				(u8 *)wowl->patterns[i].pattern,
3633 				wowl->patterns[i].pattern_len,
3634 				(u8 *)wowl->patterns[i].mask,
3635 				wowl->patterns[i].pkt_offset);
3636 		}
3637 	}
3638 	if (wowl->nd_config) {
3639 		brcmf_cfg80211_sched_scan_start(cfg->wiphy, ifp->ndev,
3640 						wowl->nd_config);
3641 		wowl_config |= BRCMF_WOWL_PFN_FOUND;
3642 
3643 		cfg->wowl.nd_data_completed = false;
3644 		cfg->wowl.nd_enabled = true;
3645 		/* Now reroute the event for PFN to the wowl function. */
3646 		brcmf_fweh_unregister(cfg->pub, BRCMF_E_PFN_NET_FOUND);
3647 		brcmf_fweh_register(cfg->pub, BRCMF_E_PFN_NET_FOUND,
3648 				    brcmf_wowl_nd_results);
3649 	}
3650 	if (wowl->gtk_rekey_failure)
3651 		wowl_config |= BRCMF_WOWL_GTK_FAILURE;
3652 	if (!test_bit(BRCMF_VIF_STATUS_CONNECTED, &ifp->vif->sme_state))
3653 		wowl_config |= BRCMF_WOWL_UNASSOC;
3654 
3655 	memcpy(&wowl_wakeind, "clear", 6);
3656 	brcmf_fil_iovar_data_set(ifp, "wowl_wakeind", &wowl_wakeind,
3657 				 sizeof(wowl_wakeind));
3658 	brcmf_fil_iovar_int_set(ifp, "wowl", wowl_config);
3659 	brcmf_fil_iovar_int_set(ifp, "wowl_activate", 1);
3660 	brcmf_bus_wowl_config(cfg->pub->bus_if, true);
3661 	cfg->wowl.active = true;
3662 }
3663 
3664 static s32 brcmf_cfg80211_suspend(struct wiphy *wiphy,
3665 				  struct cfg80211_wowlan *wowl)
3666 {
3667 	struct brcmf_cfg80211_info *cfg = wiphy_to_cfg(wiphy);
3668 	struct net_device *ndev = cfg_to_ndev(cfg);
3669 	struct brcmf_if *ifp = netdev_priv(ndev);
3670 	struct brcmf_cfg80211_vif *vif;
3671 
3672 	brcmf_dbg(TRACE, "Enter\n");
3673 
3674 	/* if the primary net_device is not READY there is nothing
3675 	 * we can do but pray resume goes smoothly.
3676 	 */
3677 	if (!check_vif_up(ifp->vif))
3678 		goto exit;
3679 
3680 	/* Stop scheduled scan */
3681 	if (brcmf_feat_is_enabled(ifp, BRCMF_FEAT_PNO))
3682 		brcmf_cfg80211_sched_scan_stop(wiphy, ndev);
3683 
3684 	/* end any scanning */
3685 	if (test_bit(BRCMF_SCAN_STATUS_BUSY, &cfg->scan_status))
3686 		brcmf_abort_scanning(cfg);
3687 
3688 	if (wowl == NULL) {
3689 		brcmf_bus_wowl_config(cfg->pub->bus_if, false);
3690 		list_for_each_entry(vif, &cfg->vif_list, list) {
3691 			if (!test_bit(BRCMF_VIF_STATUS_READY, &vif->sme_state))
3692 				continue;
3693 			/* While going to suspend if associated with AP
3694 			 * disassociate from AP to save power while system is
3695 			 * in suspended state
3696 			 */
3697 			brcmf_link_down(vif, WLAN_REASON_UNSPECIFIED);
3698 			/* Make sure WPA_Supplicant receives all the event
3699 			 * generated due to DISASSOC call to the fw to keep
3700 			 * the state fw and WPA_Supplicant state consistent
3701 			 */
3702 			brcmf_delay(500);
3703 		}
3704 		/* Configure MPC */
3705 		brcmf_set_mpc(ifp, 1);
3706 
3707 	} else {
3708 		/* Configure WOWL paramaters */
3709 		brcmf_configure_wowl(cfg, ifp, wowl);
3710 	}
3711 
3712 exit:
3713 	brcmf_dbg(TRACE, "Exit\n");
3714 	/* clear any scanning activity */
3715 	cfg->scan_status = 0;
3716 	return 0;
3717 }
3718 
3719 static __used s32
3720 brcmf_update_pmklist(struct brcmf_cfg80211_info *cfg, struct brcmf_if *ifp)
3721 {
3722 	struct brcmf_pmk_list_le *pmk_list;
3723 	int i;
3724 	u32 npmk;
3725 	s32 err;
3726 
3727 	pmk_list = &cfg->pmk_list;
3728 	npmk = le32_to_cpu(pmk_list->npmk);
3729 
3730 	brcmf_dbg(CONN, "No of elements %d\n", npmk);
3731 	for (i = 0; i < npmk; i++)
3732 		brcmf_dbg(CONN, "PMK[%d]: %pM\n", i, &pmk_list->pmk[i].bssid);
3733 
3734 	err = brcmf_fil_iovar_data_set(ifp, "pmkid_info", pmk_list,
3735 				       sizeof(*pmk_list));
3736 
3737 	return err;
3738 }
3739 
3740 static s32
3741 brcmf_cfg80211_set_pmksa(struct wiphy *wiphy, struct net_device *ndev,
3742 			 struct cfg80211_pmksa *pmksa)
3743 {
3744 	struct brcmf_cfg80211_info *cfg = wiphy_to_cfg(wiphy);
3745 	struct brcmf_if *ifp = netdev_priv(ndev);
3746 	struct brcmf_pmksa *pmk = &cfg->pmk_list.pmk[0];
3747 	s32 err;
3748 	u32 npmk, i;
3749 
3750 	brcmf_dbg(TRACE, "Enter\n");
3751 	if (!check_vif_up(ifp->vif))
3752 		return -EIO;
3753 
3754 	npmk = le32_to_cpu(cfg->pmk_list.npmk);
3755 	for (i = 0; i < npmk; i++)
3756 		if (!memcmp(pmksa->bssid, pmk[i].bssid, ETH_ALEN))
3757 			break;
3758 	if (i < BRCMF_MAXPMKID) {
3759 		memcpy(pmk[i].bssid, pmksa->bssid, ETH_ALEN);
3760 		memcpy(pmk[i].pmkid, pmksa->pmkid, WLAN_PMKID_LEN);
3761 		if (i == npmk) {
3762 			npmk++;
3763 			cfg->pmk_list.npmk = cpu_to_le32(npmk);
3764 		}
3765 	} else {
3766 		brcmf_err("Too many PMKSA entries cached %d\n", npmk);
3767 		return -EINVAL;
3768 	}
3769 
3770 	brcmf_dbg(CONN, "set_pmksa - PMK bssid: %pM =\n", pmk[npmk].bssid);
3771 	for (i = 0; i < WLAN_PMKID_LEN; i += 4)
3772 		brcmf_dbg(CONN, "%02x %02x %02x %02x\n", pmk[npmk].pmkid[i],
3773 			  pmk[npmk].pmkid[i + 1], pmk[npmk].pmkid[i + 2],
3774 			  pmk[npmk].pmkid[i + 3]);
3775 
3776 	err = brcmf_update_pmklist(cfg, ifp);
3777 
3778 	brcmf_dbg(TRACE, "Exit\n");
3779 	return err;
3780 }
3781 
3782 static s32
3783 brcmf_cfg80211_del_pmksa(struct wiphy *wiphy, struct net_device *ndev,
3784 			 struct cfg80211_pmksa *pmksa)
3785 {
3786 	struct brcmf_cfg80211_info *cfg = wiphy_to_cfg(wiphy);
3787 	struct brcmf_if *ifp = netdev_priv(ndev);
3788 	struct brcmf_pmksa *pmk = &cfg->pmk_list.pmk[0];
3789 	s32 err;
3790 	u32 npmk, i;
3791 
3792 	brcmf_dbg(TRACE, "Enter\n");
3793 	if (!check_vif_up(ifp->vif))
3794 		return -EIO;
3795 
3796 	brcmf_dbg(CONN, "del_pmksa - PMK bssid = %pM\n", pmksa->bssid);
3797 
3798 	npmk = le32_to_cpu(cfg->pmk_list.npmk);
3799 	for (i = 0; i < npmk; i++)
3800 		if (!memcmp(pmksa->bssid, pmk[i].bssid, ETH_ALEN))
3801 			break;
3802 
3803 	if ((npmk > 0) && (i < npmk)) {
3804 		for (; i < (npmk - 1); i++) {
3805 			memcpy(&pmk[i].bssid, &pmk[i + 1].bssid, ETH_ALEN);
3806 			memcpy(&pmk[i].pmkid, &pmk[i + 1].pmkid,
3807 			       WLAN_PMKID_LEN);
3808 		}
3809 		memset(&pmk[i], 0, sizeof(*pmk));
3810 		cfg->pmk_list.npmk = cpu_to_le32(npmk - 1);
3811 	} else {
3812 		brcmf_err("Cache entry not found\n");
3813 		return -EINVAL;
3814 	}
3815 
3816 	err = brcmf_update_pmklist(cfg, ifp);
3817 
3818 	brcmf_dbg(TRACE, "Exit\n");
3819 	return err;
3820 
3821 }
3822 
3823 static s32
3824 brcmf_cfg80211_flush_pmksa(struct wiphy *wiphy, struct net_device *ndev)
3825 {
3826 	struct brcmf_cfg80211_info *cfg = wiphy_to_cfg(wiphy);
3827 	struct brcmf_if *ifp = netdev_priv(ndev);
3828 	s32 err;
3829 
3830 	brcmf_dbg(TRACE, "Enter\n");
3831 	if (!check_vif_up(ifp->vif))
3832 		return -EIO;
3833 
3834 	memset(&cfg->pmk_list, 0, sizeof(cfg->pmk_list));
3835 	err = brcmf_update_pmklist(cfg, ifp);
3836 
3837 	brcmf_dbg(TRACE, "Exit\n");
3838 	return err;
3839 
3840 }
3841 
3842 static s32 brcmf_configure_opensecurity(struct brcmf_if *ifp)
3843 {
3844 	s32 err;
3845 
3846 	/* set auth */
3847 	err = brcmf_fil_bsscfg_int_set(ifp, "auth", 0);
3848 	if (err < 0) {
3849 		brcmf_err("auth error %d\n", err);
3850 		return err;
3851 	}
3852 	/* set wsec */
3853 	err = brcmf_fil_bsscfg_int_set(ifp, "wsec", 0);
3854 	if (err < 0) {
3855 		brcmf_err("wsec error %d\n", err);
3856 		return err;
3857 	}
3858 	/* set upper-layer auth */
3859 	err = brcmf_fil_bsscfg_int_set(ifp, "wpa_auth", WPA_AUTH_NONE);
3860 	if (err < 0) {
3861 		brcmf_err("wpa_auth error %d\n", err);
3862 		return err;
3863 	}
3864 
3865 	return 0;
3866 }
3867 
3868 static bool brcmf_valid_wpa_oui(u8 *oui, bool is_rsn_ie)
3869 {
3870 	if (is_rsn_ie)
3871 		return (memcmp(oui, RSN_OUI, TLV_OUI_LEN) == 0);
3872 
3873 	return (memcmp(oui, WPA_OUI, TLV_OUI_LEN) == 0);
3874 }
3875 
3876 static s32
3877 brcmf_configure_wpaie(struct brcmf_if *ifp,
3878 		      const struct brcmf_vs_tlv *wpa_ie,
3879 		      bool is_rsn_ie)
3880 {
3881 	u32 auth = 0; /* d11 open authentication */
3882 	u16 count;
3883 	s32 err = 0;
3884 	s32 len;
3885 	u32 i;
3886 	u32 wsec;
3887 	u32 pval = 0;
3888 	u32 gval = 0;
3889 	u32 wpa_auth = 0;
3890 	u32 offset;
3891 	u8 *data;
3892 	u16 rsn_cap;
3893 	u32 wme_bss_disable;
3894 	u32 mfp;
3895 
3896 	brcmf_dbg(TRACE, "Enter\n");
3897 	if (wpa_ie == NULL)
3898 		goto exit;
3899 
3900 	len = wpa_ie->len + TLV_HDR_LEN;
3901 	data = (u8 *)wpa_ie;
3902 	offset = TLV_HDR_LEN;
3903 	if (!is_rsn_ie)
3904 		offset += VS_IE_FIXED_HDR_LEN;
3905 	else
3906 		offset += WPA_IE_VERSION_LEN;
3907 
3908 	/* check for multicast cipher suite */
3909 	if (offset + WPA_IE_MIN_OUI_LEN > len) {
3910 		err = -EINVAL;
3911 		brcmf_err("no multicast cipher suite\n");
3912 		goto exit;
3913 	}
3914 
3915 	if (!brcmf_valid_wpa_oui(&data[offset], is_rsn_ie)) {
3916 		err = -EINVAL;
3917 		brcmf_err("ivalid OUI\n");
3918 		goto exit;
3919 	}
3920 	offset += TLV_OUI_LEN;
3921 
3922 	/* pick up multicast cipher */
3923 	switch (data[offset]) {
3924 	case WPA_CIPHER_NONE:
3925 		gval = 0;
3926 		break;
3927 	case WPA_CIPHER_WEP_40:
3928 	case WPA_CIPHER_WEP_104:
3929 		gval = WEP_ENABLED;
3930 		break;
3931 	case WPA_CIPHER_TKIP:
3932 		gval = TKIP_ENABLED;
3933 		break;
3934 	case WPA_CIPHER_AES_CCM:
3935 		gval = AES_ENABLED;
3936 		break;
3937 	default:
3938 		err = -EINVAL;
3939 		brcmf_err("Invalid multi cast cipher info\n");
3940 		goto exit;
3941 	}
3942 
3943 	offset++;
3944 	/* walk thru unicast cipher list and pick up what we recognize */
3945 	count = data[offset] + (data[offset + 1] << 8);
3946 	offset += WPA_IE_SUITE_COUNT_LEN;
3947 	/* Check for unicast suite(s) */
3948 	if (offset + (WPA_IE_MIN_OUI_LEN * count) > len) {
3949 		err = -EINVAL;
3950 		brcmf_err("no unicast cipher suite\n");
3951 		goto exit;
3952 	}
3953 	for (i = 0; i < count; i++) {
3954 		if (!brcmf_valid_wpa_oui(&data[offset], is_rsn_ie)) {
3955 			err = -EINVAL;
3956 			brcmf_err("ivalid OUI\n");
3957 			goto exit;
3958 		}
3959 		offset += TLV_OUI_LEN;
3960 		switch (data[offset]) {
3961 		case WPA_CIPHER_NONE:
3962 			break;
3963 		case WPA_CIPHER_WEP_40:
3964 		case WPA_CIPHER_WEP_104:
3965 			pval |= WEP_ENABLED;
3966 			break;
3967 		case WPA_CIPHER_TKIP:
3968 			pval |= TKIP_ENABLED;
3969 			break;
3970 		case WPA_CIPHER_AES_CCM:
3971 			pval |= AES_ENABLED;
3972 			break;
3973 		default:
3974 			brcmf_err("Ivalid unicast security info\n");
3975 		}
3976 		offset++;
3977 	}
3978 	/* walk thru auth management suite list and pick up what we recognize */
3979 	count = data[offset] + (data[offset + 1] << 8);
3980 	offset += WPA_IE_SUITE_COUNT_LEN;
3981 	/* Check for auth key management suite(s) */
3982 	if (offset + (WPA_IE_MIN_OUI_LEN * count) > len) {
3983 		err = -EINVAL;
3984 		brcmf_err("no auth key mgmt suite\n");
3985 		goto exit;
3986 	}
3987 	for (i = 0; i < count; i++) {
3988 		if (!brcmf_valid_wpa_oui(&data[offset], is_rsn_ie)) {
3989 			err = -EINVAL;
3990 			brcmf_err("ivalid OUI\n");
3991 			goto exit;
3992 		}
3993 		offset += TLV_OUI_LEN;
3994 		switch (data[offset]) {
3995 		case RSN_AKM_NONE:
3996 			brcmf_dbg(TRACE, "RSN_AKM_NONE\n");
3997 			wpa_auth |= WPA_AUTH_NONE;
3998 			break;
3999 		case RSN_AKM_UNSPECIFIED:
4000 			brcmf_dbg(TRACE, "RSN_AKM_UNSPECIFIED\n");
4001 			is_rsn_ie ? (wpa_auth |= WPA2_AUTH_UNSPECIFIED) :
4002 				    (wpa_auth |= WPA_AUTH_UNSPECIFIED);
4003 			break;
4004 		case RSN_AKM_PSK:
4005 			brcmf_dbg(TRACE, "RSN_AKM_PSK\n");
4006 			is_rsn_ie ? (wpa_auth |= WPA2_AUTH_PSK) :
4007 				    (wpa_auth |= WPA_AUTH_PSK);
4008 			break;
4009 		case RSN_AKM_SHA256_PSK:
4010 			brcmf_dbg(TRACE, "RSN_AKM_MFP_PSK\n");
4011 			wpa_auth |= WPA2_AUTH_PSK_SHA256;
4012 			break;
4013 		case RSN_AKM_SHA256_1X:
4014 			brcmf_dbg(TRACE, "RSN_AKM_MFP_1X\n");
4015 			wpa_auth |= WPA2_AUTH_1X_SHA256;
4016 			break;
4017 		default:
4018 			brcmf_err("Ivalid key mgmt info\n");
4019 		}
4020 		offset++;
4021 	}
4022 
4023 	mfp = BRCMF_MFP_NONE;
4024 	if (is_rsn_ie) {
4025 		wme_bss_disable = 1;
4026 		if ((offset + RSN_CAP_LEN) <= len) {
4027 			rsn_cap = data[offset] + (data[offset + 1] << 8);
4028 			if (rsn_cap & RSN_CAP_PTK_REPLAY_CNTR_MASK)
4029 				wme_bss_disable = 0;
4030 			if (rsn_cap & RSN_CAP_MFPR_MASK) {
4031 				brcmf_dbg(TRACE, "MFP Required\n");
4032 				mfp = BRCMF_MFP_REQUIRED;
4033 				/* Firmware only supports mfp required in
4034 				 * combination with WPA2_AUTH_PSK_SHA256 or
4035 				 * WPA2_AUTH_1X_SHA256.
4036 				 */
4037 				if (!(wpa_auth & (WPA2_AUTH_PSK_SHA256 |
4038 						  WPA2_AUTH_1X_SHA256))) {
4039 					err = -EINVAL;
4040 					goto exit;
4041 				}
4042 				/* Firmware has requirement that WPA2_AUTH_PSK/
4043 				 * WPA2_AUTH_UNSPECIFIED be set, if SHA256 OUI
4044 				 * is to be included in the rsn ie.
4045 				 */
4046 				if (wpa_auth & WPA2_AUTH_PSK_SHA256)
4047 					wpa_auth |= WPA2_AUTH_PSK;
4048 				else if (wpa_auth & WPA2_AUTH_1X_SHA256)
4049 					wpa_auth |= WPA2_AUTH_UNSPECIFIED;
4050 			} else if (rsn_cap & RSN_CAP_MFPC_MASK) {
4051 				brcmf_dbg(TRACE, "MFP Capable\n");
4052 				mfp = BRCMF_MFP_CAPABLE;
4053 			}
4054 		}
4055 		offset += RSN_CAP_LEN;
4056 		/* set wme_bss_disable to sync RSN Capabilities */
4057 		err = brcmf_fil_bsscfg_int_set(ifp, "wme_bss_disable",
4058 					       wme_bss_disable);
4059 		if (err < 0) {
4060 			brcmf_err("wme_bss_disable error %d\n", err);
4061 			goto exit;
4062 		}
4063 
4064 		/* Skip PMKID cnt as it is know to be 0 for AP. */
4065 		offset += RSN_PMKID_COUNT_LEN;
4066 
4067 		/* See if there is BIP wpa suite left for MFP */
4068 		if (brcmf_feat_is_enabled(ifp, BRCMF_FEAT_MFP) &&
4069 		    ((offset + WPA_IE_MIN_OUI_LEN) <= len)) {
4070 			err = brcmf_fil_bsscfg_data_set(ifp, "bip",
4071 							&data[offset],
4072 							WPA_IE_MIN_OUI_LEN);
4073 			if (err < 0) {
4074 				brcmf_err("bip error %d\n", err);
4075 				goto exit;
4076 			}
4077 		}
4078 	}
4079 	/* FOR WPS , set SES_OW_ENABLED */
4080 	wsec = (pval | gval | SES_OW_ENABLED);
4081 
4082 	/* set auth */
4083 	err = brcmf_fil_bsscfg_int_set(ifp, "auth", auth);
4084 	if (err < 0) {
4085 		brcmf_err("auth error %d\n", err);
4086 		goto exit;
4087 	}
4088 	/* set wsec */
4089 	err = brcmf_fil_bsscfg_int_set(ifp, "wsec", wsec);
4090 	if (err < 0) {
4091 		brcmf_err("wsec error %d\n", err);
4092 		goto exit;
4093 	}
4094 	/* Configure MFP, this needs to go after wsec otherwise the wsec command
4095 	 * will overwrite the values set by MFP
4096 	 */
4097 	if (brcmf_feat_is_enabled(ifp, BRCMF_FEAT_MFP)) {
4098 		err = brcmf_fil_bsscfg_int_set(ifp, "mfp", mfp);
4099 		if (err < 0) {
4100 			brcmf_err("mfp error %d\n", err);
4101 			goto exit;
4102 		}
4103 	}
4104 	/* set upper-layer auth */
4105 	err = brcmf_fil_bsscfg_int_set(ifp, "wpa_auth", wpa_auth);
4106 	if (err < 0) {
4107 		brcmf_err("wpa_auth error %d\n", err);
4108 		goto exit;
4109 	}
4110 
4111 exit:
4112 	return err;
4113 }
4114 
4115 static s32
4116 brcmf_parse_vndr_ies(const u8 *vndr_ie_buf, u32 vndr_ie_len,
4117 		     struct parsed_vndr_ies *vndr_ies)
4118 {
4119 	struct brcmf_vs_tlv *vndrie;
4120 	struct brcmf_tlv *ie;
4121 	struct parsed_vndr_ie_info *parsed_info;
4122 	s32 remaining_len;
4123 
4124 	remaining_len = (s32)vndr_ie_len;
4125 	memset(vndr_ies, 0, sizeof(*vndr_ies));
4126 
4127 	ie = (struct brcmf_tlv *)vndr_ie_buf;
4128 	while (ie) {
4129 		if (ie->id != WLAN_EID_VENDOR_SPECIFIC)
4130 			goto next;
4131 		vndrie = (struct brcmf_vs_tlv *)ie;
4132 		/* len should be bigger than OUI length + one */
4133 		if (vndrie->len < (VS_IE_FIXED_HDR_LEN - TLV_HDR_LEN + 1)) {
4134 			brcmf_err("invalid vndr ie. length is too small %d\n",
4135 				  vndrie->len);
4136 			goto next;
4137 		}
4138 		/* if wpa or wme ie, do not add ie */
4139 		if (!memcmp(vndrie->oui, (u8 *)WPA_OUI, TLV_OUI_LEN) &&
4140 		    ((vndrie->oui_type == WPA_OUI_TYPE) ||
4141 		    (vndrie->oui_type == WME_OUI_TYPE))) {
4142 			brcmf_dbg(TRACE, "Found WPA/WME oui. Do not add it\n");
4143 			goto next;
4144 		}
4145 
4146 		parsed_info = &vndr_ies->ie_info[vndr_ies->count];
4147 
4148 		/* save vndr ie information */
4149 		parsed_info->ie_ptr = (char *)vndrie;
4150 		parsed_info->ie_len = vndrie->len + TLV_HDR_LEN;
4151 		memcpy(&parsed_info->vndrie, vndrie, sizeof(*vndrie));
4152 
4153 		vndr_ies->count++;
4154 
4155 		brcmf_dbg(TRACE, "** OUI %02x %02x %02x, type 0x%02x\n",
4156 			  parsed_info->vndrie.oui[0],
4157 			  parsed_info->vndrie.oui[1],
4158 			  parsed_info->vndrie.oui[2],
4159 			  parsed_info->vndrie.oui_type);
4160 
4161 		if (vndr_ies->count >= VNDR_IE_PARSE_LIMIT)
4162 			break;
4163 next:
4164 		remaining_len -= (ie->len + TLV_HDR_LEN);
4165 		if (remaining_len <= TLV_HDR_LEN)
4166 			ie = NULL;
4167 		else
4168 			ie = (struct brcmf_tlv *)(((u8 *)ie) + ie->len +
4169 				TLV_HDR_LEN);
4170 	}
4171 	return 0;
4172 }
4173 
4174 static u32
4175 brcmf_vndr_ie(u8 *iebuf, s32 pktflag, u8 *ie_ptr, u32 ie_len, s8 *add_del_cmd)
4176 {
4177 
4178 	strncpy(iebuf, add_del_cmd, VNDR_IE_CMD_LEN - 1);
4179 	iebuf[VNDR_IE_CMD_LEN - 1] = '\0';
4180 
4181 	put_unaligned_le32(1, &iebuf[VNDR_IE_COUNT_OFFSET]);
4182 
4183 	put_unaligned_le32(pktflag, &iebuf[VNDR_IE_PKTFLAG_OFFSET]);
4184 
4185 	memcpy(&iebuf[VNDR_IE_VSIE_OFFSET], ie_ptr, ie_len);
4186 
4187 	return ie_len + VNDR_IE_HDR_SIZE;
4188 }
4189 
4190 s32 brcmf_vif_set_mgmt_ie(struct brcmf_cfg80211_vif *vif, s32 pktflag,
4191 			  const u8 *vndr_ie_buf, u32 vndr_ie_len)
4192 {
4193 	struct brcmf_if *ifp;
4194 	struct vif_saved_ie *saved_ie;
4195 	s32 err = 0;
4196 	u8  *iovar_ie_buf;
4197 	u8  *curr_ie_buf;
4198 	u8  *mgmt_ie_buf = NULL;
4199 	int mgmt_ie_buf_len;
4200 	u32 *mgmt_ie_len;
4201 	u32 del_add_ie_buf_len = 0;
4202 	u32 total_ie_buf_len = 0;
4203 	u32 parsed_ie_buf_len = 0;
4204 	struct parsed_vndr_ies old_vndr_ies;
4205 	struct parsed_vndr_ies new_vndr_ies;
4206 	struct parsed_vndr_ie_info *vndrie_info;
4207 	s32 i;
4208 	u8 *ptr;
4209 	int remained_buf_len;
4210 
4211 	if (!vif)
4212 		return -ENODEV;
4213 	ifp = vif->ifp;
4214 	saved_ie = &vif->saved_ie;
4215 
4216 	brcmf_dbg(TRACE, "bsscfgidx %d, pktflag : 0x%02X\n", ifp->bsscfgidx,
4217 		  pktflag);
4218 	iovar_ie_buf = kzalloc(WL_EXTRA_BUF_MAX, GFP_KERNEL);
4219 	if (!iovar_ie_buf)
4220 		return -ENOMEM;
4221 	curr_ie_buf = iovar_ie_buf;
4222 	switch (pktflag) {
4223 	case BRCMF_VNDR_IE_PRBREQ_FLAG:
4224 		mgmt_ie_buf = saved_ie->probe_req_ie;
4225 		mgmt_ie_len = &saved_ie->probe_req_ie_len;
4226 		mgmt_ie_buf_len = sizeof(saved_ie->probe_req_ie);
4227 		break;
4228 	case BRCMF_VNDR_IE_PRBRSP_FLAG:
4229 		mgmt_ie_buf = saved_ie->probe_res_ie;
4230 		mgmt_ie_len = &saved_ie->probe_res_ie_len;
4231 		mgmt_ie_buf_len = sizeof(saved_ie->probe_res_ie);
4232 		break;
4233 	case BRCMF_VNDR_IE_BEACON_FLAG:
4234 		mgmt_ie_buf = saved_ie->beacon_ie;
4235 		mgmt_ie_len = &saved_ie->beacon_ie_len;
4236 		mgmt_ie_buf_len = sizeof(saved_ie->beacon_ie);
4237 		break;
4238 	case BRCMF_VNDR_IE_ASSOCREQ_FLAG:
4239 		mgmt_ie_buf = saved_ie->assoc_req_ie;
4240 		mgmt_ie_len = &saved_ie->assoc_req_ie_len;
4241 		mgmt_ie_buf_len = sizeof(saved_ie->assoc_req_ie);
4242 		break;
4243 	default:
4244 		err = -EPERM;
4245 		brcmf_err("not suitable type\n");
4246 		goto exit;
4247 	}
4248 
4249 	if (vndr_ie_len > mgmt_ie_buf_len) {
4250 		err = -ENOMEM;
4251 		brcmf_err("extra IE size too big\n");
4252 		goto exit;
4253 	}
4254 
4255 	/* parse and save new vndr_ie in curr_ie_buff before comparing it */
4256 	if (vndr_ie_buf && vndr_ie_len && curr_ie_buf) {
4257 		ptr = curr_ie_buf;
4258 		brcmf_parse_vndr_ies(vndr_ie_buf, vndr_ie_len, &new_vndr_ies);
4259 		for (i = 0; i < new_vndr_ies.count; i++) {
4260 			vndrie_info = &new_vndr_ies.ie_info[i];
4261 			memcpy(ptr + parsed_ie_buf_len, vndrie_info->ie_ptr,
4262 			       vndrie_info->ie_len);
4263 			parsed_ie_buf_len += vndrie_info->ie_len;
4264 		}
4265 	}
4266 
4267 	if (mgmt_ie_buf && *mgmt_ie_len) {
4268 		if (parsed_ie_buf_len && (parsed_ie_buf_len == *mgmt_ie_len) &&
4269 		    (memcmp(mgmt_ie_buf, curr_ie_buf,
4270 			    parsed_ie_buf_len) == 0)) {
4271 			brcmf_dbg(TRACE, "Previous mgmt IE equals to current IE\n");
4272 			goto exit;
4273 		}
4274 
4275 		/* parse old vndr_ie */
4276 		brcmf_parse_vndr_ies(mgmt_ie_buf, *mgmt_ie_len, &old_vndr_ies);
4277 
4278 		/* make a command to delete old ie */
4279 		for (i = 0; i < old_vndr_ies.count; i++) {
4280 			vndrie_info = &old_vndr_ies.ie_info[i];
4281 
4282 			brcmf_dbg(TRACE, "DEL ID : %d, Len: %d , OUI:%02x:%02x:%02x\n",
4283 				  vndrie_info->vndrie.id,
4284 				  vndrie_info->vndrie.len,
4285 				  vndrie_info->vndrie.oui[0],
4286 				  vndrie_info->vndrie.oui[1],
4287 				  vndrie_info->vndrie.oui[2]);
4288 
4289 			del_add_ie_buf_len = brcmf_vndr_ie(curr_ie_buf, pktflag,
4290 							   vndrie_info->ie_ptr,
4291 							   vndrie_info->ie_len,
4292 							   "del");
4293 			curr_ie_buf += del_add_ie_buf_len;
4294 			total_ie_buf_len += del_add_ie_buf_len;
4295 		}
4296 	}
4297 
4298 	*mgmt_ie_len = 0;
4299 	/* Add if there is any extra IE */
4300 	if (mgmt_ie_buf && parsed_ie_buf_len) {
4301 		ptr = mgmt_ie_buf;
4302 
4303 		remained_buf_len = mgmt_ie_buf_len;
4304 
4305 		/* make a command to add new ie */
4306 		for (i = 0; i < new_vndr_ies.count; i++) {
4307 			vndrie_info = &new_vndr_ies.ie_info[i];
4308 
4309 			/* verify remained buf size before copy data */
4310 			if (remained_buf_len < (vndrie_info->vndrie.len +
4311 							VNDR_IE_VSIE_OFFSET)) {
4312 				brcmf_err("no space in mgmt_ie_buf: len left %d",
4313 					  remained_buf_len);
4314 				break;
4315 			}
4316 			remained_buf_len -= (vndrie_info->ie_len +
4317 					     VNDR_IE_VSIE_OFFSET);
4318 
4319 			brcmf_dbg(TRACE, "ADDED ID : %d, Len: %d, OUI:%02x:%02x:%02x\n",
4320 				  vndrie_info->vndrie.id,
4321 				  vndrie_info->vndrie.len,
4322 				  vndrie_info->vndrie.oui[0],
4323 				  vndrie_info->vndrie.oui[1],
4324 				  vndrie_info->vndrie.oui[2]);
4325 
4326 			del_add_ie_buf_len = brcmf_vndr_ie(curr_ie_buf, pktflag,
4327 							   vndrie_info->ie_ptr,
4328 							   vndrie_info->ie_len,
4329 							   "add");
4330 
4331 			/* save the parsed IE in wl struct */
4332 			memcpy(ptr + (*mgmt_ie_len), vndrie_info->ie_ptr,
4333 			       vndrie_info->ie_len);
4334 			*mgmt_ie_len += vndrie_info->ie_len;
4335 
4336 			curr_ie_buf += del_add_ie_buf_len;
4337 			total_ie_buf_len += del_add_ie_buf_len;
4338 		}
4339 	}
4340 	if (total_ie_buf_len) {
4341 		err  = brcmf_fil_bsscfg_data_set(ifp, "vndr_ie", iovar_ie_buf,
4342 						 total_ie_buf_len);
4343 		if (err)
4344 			brcmf_err("vndr ie set error : %d\n", err);
4345 	}
4346 
4347 exit:
4348 	kfree(iovar_ie_buf);
4349 	return err;
4350 }
4351 
4352 s32 brcmf_vif_clear_mgmt_ies(struct brcmf_cfg80211_vif *vif)
4353 {
4354 	s32 pktflags[] = {
4355 		BRCMF_VNDR_IE_PRBREQ_FLAG,
4356 		BRCMF_VNDR_IE_PRBRSP_FLAG,
4357 		BRCMF_VNDR_IE_BEACON_FLAG
4358 	};
4359 	int i;
4360 
4361 	for (i = 0; i < ARRAY_SIZE(pktflags); i++)
4362 		brcmf_vif_set_mgmt_ie(vif, pktflags[i], NULL, 0);
4363 
4364 	memset(&vif->saved_ie, 0, sizeof(vif->saved_ie));
4365 	return 0;
4366 }
4367 
4368 static s32
4369 brcmf_config_ap_mgmt_ie(struct brcmf_cfg80211_vif *vif,
4370 			struct cfg80211_beacon_data *beacon)
4371 {
4372 	s32 err;
4373 
4374 	/* Set Beacon IEs to FW */
4375 	err = brcmf_vif_set_mgmt_ie(vif, BRCMF_VNDR_IE_BEACON_FLAG,
4376 				    beacon->tail, beacon->tail_len);
4377 	if (err) {
4378 		brcmf_err("Set Beacon IE Failed\n");
4379 		return err;
4380 	}
4381 	brcmf_dbg(TRACE, "Applied Vndr IEs for Beacon\n");
4382 
4383 	/* Set Probe Response IEs to FW */
4384 	err = brcmf_vif_set_mgmt_ie(vif, BRCMF_VNDR_IE_PRBRSP_FLAG,
4385 				    beacon->proberesp_ies,
4386 				    beacon->proberesp_ies_len);
4387 	if (err)
4388 		brcmf_err("Set Probe Resp IE Failed\n");
4389 	else
4390 		brcmf_dbg(TRACE, "Applied Vndr IEs for Probe Resp\n");
4391 
4392 	return err;
4393 }
4394 
4395 static s32
4396 brcmf_cfg80211_start_ap(struct wiphy *wiphy, struct net_device *ndev,
4397 			struct cfg80211_ap_settings *settings)
4398 {
4399 	s32 ie_offset;
4400 	struct brcmf_cfg80211_info *cfg = wiphy_to_cfg(wiphy);
4401 	struct brcmf_if *ifp = netdev_priv(ndev);
4402 	const struct brcmf_tlv *ssid_ie;
4403 	const struct brcmf_tlv *country_ie;
4404 	struct brcmf_ssid_le ssid_le;
4405 	s32 err = -EPERM;
4406 	const struct brcmf_tlv *rsn_ie;
4407 	const struct brcmf_vs_tlv *wpa_ie;
4408 	struct brcmf_join_params join_params;
4409 	enum nl80211_iftype dev_role;
4410 	struct brcmf_fil_bss_enable_le bss_enable;
4411 	u16 chanspec = chandef_to_chanspec(&cfg->d11inf, &settings->chandef);
4412 	bool mbss;
4413 	int is_11d;
4414 	bool supports_11d;
4415 
4416 	brcmf_dbg(TRACE, "ctrlchn=%d, center=%d, bw=%d, beacon_interval=%d, dtim_period=%d,\n",
4417 		  settings->chandef.chan->hw_value,
4418 		  settings->chandef.center_freq1, settings->chandef.width,
4419 		  settings->beacon_interval, settings->dtim_period);
4420 	brcmf_dbg(TRACE, "ssid=%s(%zu), auth_type=%d, inactivity_timeout=%d\n",
4421 		  settings->ssid, settings->ssid_len, settings->auth_type,
4422 		  settings->inactivity_timeout);
4423 	dev_role = ifp->vif->wdev.iftype;
4424 	mbss = ifp->vif->mbss;
4425 
4426 	/* store current 11d setting */
4427 	if (brcmf_fil_cmd_int_get(ifp, BRCMF_C_GET_REGULATORY,
4428 				  &ifp->vif->is_11d)) {
4429 		is_11d = supports_11d = false;
4430 	} else {
4431 		country_ie = brcmf_parse_tlvs((u8 *)settings->beacon.tail,
4432 					      settings->beacon.tail_len,
4433 					      WLAN_EID_COUNTRY);
4434 		is_11d = country_ie ? 1 : 0;
4435 		supports_11d = true;
4436 	}
4437 
4438 	memset(&ssid_le, 0, sizeof(ssid_le));
4439 	if (settings->ssid == NULL || settings->ssid_len == 0) {
4440 		ie_offset = DOT11_MGMT_HDR_LEN + DOT11_BCN_PRB_FIXED_LEN;
4441 		ssid_ie = brcmf_parse_tlvs(
4442 				(u8 *)&settings->beacon.head[ie_offset],
4443 				settings->beacon.head_len - ie_offset,
4444 				WLAN_EID_SSID);
4445 		if (!ssid_ie || ssid_ie->len > IEEE80211_MAX_SSID_LEN)
4446 			return -EINVAL;
4447 
4448 		memcpy(ssid_le.SSID, ssid_ie->data, ssid_ie->len);
4449 		ssid_le.SSID_len = cpu_to_le32(ssid_ie->len);
4450 		brcmf_dbg(TRACE, "SSID is (%s) in Head\n", ssid_le.SSID);
4451 	} else {
4452 		memcpy(ssid_le.SSID, settings->ssid, settings->ssid_len);
4453 		ssid_le.SSID_len = cpu_to_le32((u32)settings->ssid_len);
4454 	}
4455 
4456 	if (!mbss) {
4457 		brcmf_set_mpc(ifp, 0);
4458 		brcmf_configure_arp_nd_offload(ifp, false);
4459 	}
4460 
4461 	/* find the RSN_IE */
4462 	rsn_ie = brcmf_parse_tlvs((u8 *)settings->beacon.tail,
4463 				  settings->beacon.tail_len, WLAN_EID_RSN);
4464 
4465 	/* find the WPA_IE */
4466 	wpa_ie = brcmf_find_wpaie((u8 *)settings->beacon.tail,
4467 				  settings->beacon.tail_len);
4468 
4469 	if ((wpa_ie != NULL || rsn_ie != NULL)) {
4470 		brcmf_dbg(TRACE, "WPA(2) IE is found\n");
4471 		if (wpa_ie != NULL) {
4472 			/* WPA IE */
4473 			err = brcmf_configure_wpaie(ifp, wpa_ie, false);
4474 			if (err < 0)
4475 				goto exit;
4476 		} else {
4477 			struct brcmf_vs_tlv *tmp_ie;
4478 
4479 			tmp_ie = (struct brcmf_vs_tlv *)rsn_ie;
4480 
4481 			/* RSN IE */
4482 			err = brcmf_configure_wpaie(ifp, tmp_ie, true);
4483 			if (err < 0)
4484 				goto exit;
4485 		}
4486 	} else {
4487 		brcmf_dbg(TRACE, "No WPA(2) IEs found\n");
4488 		brcmf_configure_opensecurity(ifp);
4489 	}
4490 
4491 	/* Parameters shared by all radio interfaces */
4492 	if (!mbss) {
4493 		if ((supports_11d) && (is_11d != ifp->vif->is_11d)) {
4494 			err = brcmf_fil_cmd_int_set(ifp, BRCMF_C_SET_REGULATORY,
4495 						    is_11d);
4496 			if (err < 0) {
4497 				brcmf_err("Regulatory Set Error, %d\n", err);
4498 				goto exit;
4499 			}
4500 		}
4501 		if (settings->beacon_interval) {
4502 			err = brcmf_fil_cmd_int_set(ifp, BRCMF_C_SET_BCNPRD,
4503 						    settings->beacon_interval);
4504 			if (err < 0) {
4505 				brcmf_err("Beacon Interval Set Error, %d\n",
4506 					  err);
4507 				goto exit;
4508 			}
4509 		}
4510 		if (settings->dtim_period) {
4511 			err = brcmf_fil_cmd_int_set(ifp, BRCMF_C_SET_DTIMPRD,
4512 						    settings->dtim_period);
4513 			if (err < 0) {
4514 				brcmf_err("DTIM Interval Set Error, %d\n", err);
4515 				goto exit;
4516 			}
4517 		}
4518 
4519 		if ((dev_role == NL80211_IFTYPE_AP) &&
4520 		    ((ifp->ifidx == 0) ||
4521 		     !brcmf_feat_is_enabled(ifp, BRCMF_FEAT_RSDB))) {
4522 			err = brcmf_fil_cmd_int_set(ifp, BRCMF_C_DOWN, 1);
4523 			if (err < 0) {
4524 				brcmf_err("BRCMF_C_DOWN error %d\n", err);
4525 				goto exit;
4526 			}
4527 			brcmf_fil_iovar_int_set(ifp, "apsta", 0);
4528 		}
4529 
4530 		err = brcmf_fil_cmd_int_set(ifp, BRCMF_C_SET_INFRA, 1);
4531 		if (err < 0) {
4532 			brcmf_err("SET INFRA error %d\n", err);
4533 			goto exit;
4534 		}
4535 	} else if (WARN_ON(supports_11d && (is_11d != ifp->vif->is_11d))) {
4536 		/* Multiple-BSS should use same 11d configuration */
4537 		err = -EINVAL;
4538 		goto exit;
4539 	}
4540 
4541 	/* Interface specific setup */
4542 	if (dev_role == NL80211_IFTYPE_AP) {
4543 		if ((brcmf_feat_is_enabled(ifp, BRCMF_FEAT_MBSS)) && (!mbss))
4544 			brcmf_fil_iovar_int_set(ifp, "mbss", 1);
4545 
4546 		err = brcmf_fil_cmd_int_set(ifp, BRCMF_C_SET_AP, 1);
4547 		if (err < 0) {
4548 			brcmf_err("setting AP mode failed %d\n", err);
4549 			goto exit;
4550 		}
4551 		if (!mbss) {
4552 			/* Firmware 10.x requires setting channel after enabling
4553 			 * AP and before bringing interface up.
4554 			 */
4555 			err = brcmf_fil_iovar_int_set(ifp, "chanspec", chanspec);
4556 			if (err < 0) {
4557 				brcmf_err("Set Channel failed: chspec=%d, %d\n",
4558 					  chanspec, err);
4559 				goto exit;
4560 			}
4561 		}
4562 		err = brcmf_fil_cmd_int_set(ifp, BRCMF_C_UP, 1);
4563 		if (err < 0) {
4564 			brcmf_err("BRCMF_C_UP error (%d)\n", err);
4565 			goto exit;
4566 		}
4567 		/* On DOWN the firmware removes the WEP keys, reconfigure
4568 		 * them if they were set.
4569 		 */
4570 		brcmf_cfg80211_reconfigure_wep(ifp);
4571 
4572 		memset(&join_params, 0, sizeof(join_params));
4573 		/* join parameters starts with ssid */
4574 		memcpy(&join_params.ssid_le, &ssid_le, sizeof(ssid_le));
4575 		/* create softap */
4576 		err = brcmf_fil_cmd_data_set(ifp, BRCMF_C_SET_SSID,
4577 					     &join_params, sizeof(join_params));
4578 		if (err < 0) {
4579 			brcmf_err("SET SSID error (%d)\n", err);
4580 			goto exit;
4581 		}
4582 
4583 		if (settings->hidden_ssid) {
4584 			err = brcmf_fil_iovar_int_set(ifp, "closednet", 1);
4585 			if (err) {
4586 				brcmf_err("closednet error (%d)\n", err);
4587 				goto exit;
4588 			}
4589 		}
4590 
4591 		brcmf_dbg(TRACE, "AP mode configuration complete\n");
4592 	} else if (dev_role == NL80211_IFTYPE_P2P_GO) {
4593 		err = brcmf_fil_iovar_int_set(ifp, "chanspec", chanspec);
4594 		if (err < 0) {
4595 			brcmf_err("Set Channel failed: chspec=%d, %d\n",
4596 				  chanspec, err);
4597 			goto exit;
4598 		}
4599 		err = brcmf_fil_bsscfg_data_set(ifp, "ssid", &ssid_le,
4600 						sizeof(ssid_le));
4601 		if (err < 0) {
4602 			brcmf_err("setting ssid failed %d\n", err);
4603 			goto exit;
4604 		}
4605 		bss_enable.bsscfgidx = cpu_to_le32(ifp->bsscfgidx);
4606 		bss_enable.enable = cpu_to_le32(1);
4607 		err = brcmf_fil_iovar_data_set(ifp, "bss", &bss_enable,
4608 					       sizeof(bss_enable));
4609 		if (err < 0) {
4610 			brcmf_err("bss_enable config failed %d\n", err);
4611 			goto exit;
4612 		}
4613 
4614 		brcmf_dbg(TRACE, "GO mode configuration complete\n");
4615 	} else {
4616 		WARN_ON(1);
4617 	}
4618 
4619 	brcmf_config_ap_mgmt_ie(ifp->vif, &settings->beacon);
4620 	set_bit(BRCMF_VIF_STATUS_AP_CREATED, &ifp->vif->sme_state);
4621 	brcmf_net_setcarrier(ifp, true);
4622 
4623 exit:
4624 	if ((err) && (!mbss)) {
4625 		brcmf_set_mpc(ifp, 1);
4626 		brcmf_configure_arp_nd_offload(ifp, true);
4627 	}
4628 	return err;
4629 }
4630 
4631 static int brcmf_cfg80211_stop_ap(struct wiphy *wiphy, struct net_device *ndev)
4632 {
4633 	struct brcmf_if *ifp = netdev_priv(ndev);
4634 	s32 err;
4635 	struct brcmf_fil_bss_enable_le bss_enable;
4636 	struct brcmf_join_params join_params;
4637 
4638 	brcmf_dbg(TRACE, "Enter\n");
4639 
4640 	if (ifp->vif->wdev.iftype == NL80211_IFTYPE_AP) {
4641 		/* Due to most likely deauths outstanding we sleep */
4642 		/* first to make sure they get processed by fw. */
4643 		msleep(400);
4644 
4645 		if (ifp->vif->mbss) {
4646 			err = brcmf_fil_cmd_int_set(ifp, BRCMF_C_DOWN, 1);
4647 			return err;
4648 		}
4649 
4650 		/* First BSS doesn't get a full reset */
4651 		if (ifp->bsscfgidx == 0)
4652 			brcmf_fil_iovar_int_set(ifp, "closednet", 0);
4653 
4654 		memset(&join_params, 0, sizeof(join_params));
4655 		err = brcmf_fil_cmd_data_set(ifp, BRCMF_C_SET_SSID,
4656 					     &join_params, sizeof(join_params));
4657 		if (err < 0)
4658 			brcmf_err("SET SSID error (%d)\n", err);
4659 		err = brcmf_fil_cmd_int_set(ifp, BRCMF_C_DOWN, 1);
4660 		if (err < 0)
4661 			brcmf_err("BRCMF_C_DOWN error %d\n", err);
4662 		err = brcmf_fil_cmd_int_set(ifp, BRCMF_C_SET_AP, 0);
4663 		if (err < 0)
4664 			brcmf_err("setting AP mode failed %d\n", err);
4665 		err = brcmf_fil_cmd_int_set(ifp, BRCMF_C_SET_INFRA, 0);
4666 		if (err < 0)
4667 			brcmf_err("setting INFRA mode failed %d\n", err);
4668 		if (brcmf_feat_is_enabled(ifp, BRCMF_FEAT_MBSS))
4669 			brcmf_fil_iovar_int_set(ifp, "mbss", 0);
4670 		brcmf_fil_cmd_int_set(ifp, BRCMF_C_SET_REGULATORY,
4671 				      ifp->vif->is_11d);
4672 		/* Bring device back up so it can be used again */
4673 		err = brcmf_fil_cmd_int_set(ifp, BRCMF_C_UP, 1);
4674 		if (err < 0)
4675 			brcmf_err("BRCMF_C_UP error %d\n", err);
4676 
4677 		brcmf_vif_clear_mgmt_ies(ifp->vif);
4678 	} else {
4679 		bss_enable.bsscfgidx = cpu_to_le32(ifp->bsscfgidx);
4680 		bss_enable.enable = cpu_to_le32(0);
4681 		err = brcmf_fil_iovar_data_set(ifp, "bss", &bss_enable,
4682 					       sizeof(bss_enable));
4683 		if (err < 0)
4684 			brcmf_err("bss_enable config failed %d\n", err);
4685 	}
4686 	brcmf_set_mpc(ifp, 1);
4687 	brcmf_configure_arp_nd_offload(ifp, true);
4688 	clear_bit(BRCMF_VIF_STATUS_AP_CREATED, &ifp->vif->sme_state);
4689 	brcmf_net_setcarrier(ifp, false);
4690 
4691 	return err;
4692 }
4693 
4694 static s32
4695 brcmf_cfg80211_change_beacon(struct wiphy *wiphy, struct net_device *ndev,
4696 			     struct cfg80211_beacon_data *info)
4697 {
4698 	struct brcmf_if *ifp = netdev_priv(ndev);
4699 	s32 err;
4700 
4701 	brcmf_dbg(TRACE, "Enter\n");
4702 
4703 	err = brcmf_config_ap_mgmt_ie(ifp->vif, info);
4704 
4705 	return err;
4706 }
4707 
4708 static int
4709 brcmf_cfg80211_del_station(struct wiphy *wiphy, struct net_device *ndev,
4710 			   struct station_del_parameters *params)
4711 {
4712 	struct brcmf_cfg80211_info *cfg = wiphy_to_cfg(wiphy);
4713 	struct brcmf_scb_val_le scbval;
4714 	struct brcmf_if *ifp = netdev_priv(ndev);
4715 	s32 err;
4716 
4717 	if (!params->mac)
4718 		return -EFAULT;
4719 
4720 	brcmf_dbg(TRACE, "Enter %pM\n", params->mac);
4721 
4722 	if (ifp->vif == cfg->p2p.bss_idx[P2PAPI_BSSCFG_DEVICE].vif)
4723 		ifp = cfg->p2p.bss_idx[P2PAPI_BSSCFG_PRIMARY].vif->ifp;
4724 	if (!check_vif_up(ifp->vif))
4725 		return -EIO;
4726 
4727 	memcpy(&scbval.ea, params->mac, ETH_ALEN);
4728 	scbval.val = cpu_to_le32(params->reason_code);
4729 	err = brcmf_fil_cmd_data_set(ifp, BRCMF_C_SCB_DEAUTHENTICATE_FOR_REASON,
4730 				     &scbval, sizeof(scbval));
4731 	if (err)
4732 		brcmf_err("SCB_DEAUTHENTICATE_FOR_REASON failed %d\n", err);
4733 
4734 	brcmf_dbg(TRACE, "Exit\n");
4735 	return err;
4736 }
4737 
4738 static int
4739 brcmf_cfg80211_change_station(struct wiphy *wiphy, struct net_device *ndev,
4740 			      const u8 *mac, struct station_parameters *params)
4741 {
4742 	struct brcmf_if *ifp = netdev_priv(ndev);
4743 	s32 err;
4744 
4745 	brcmf_dbg(TRACE, "Enter, MAC %pM, mask 0x%04x set 0x%04x\n", mac,
4746 		  params->sta_flags_mask, params->sta_flags_set);
4747 
4748 	/* Ignore all 00 MAC */
4749 	if (is_zero_ether_addr(mac))
4750 		return 0;
4751 
4752 	if (!(params->sta_flags_mask & BIT(NL80211_STA_FLAG_AUTHORIZED)))
4753 		return 0;
4754 
4755 	if (params->sta_flags_set & BIT(NL80211_STA_FLAG_AUTHORIZED))
4756 		err = brcmf_fil_cmd_data_set(ifp, BRCMF_C_SET_SCB_AUTHORIZE,
4757 					     (void *)mac, ETH_ALEN);
4758 	else
4759 		err = brcmf_fil_cmd_data_set(ifp, BRCMF_C_SET_SCB_DEAUTHORIZE,
4760 					     (void *)mac, ETH_ALEN);
4761 	if (err < 0)
4762 		brcmf_err("Setting SCB (de-)authorize failed, %d\n", err);
4763 
4764 	return err;
4765 }
4766 
4767 static void
4768 brcmf_cfg80211_mgmt_frame_register(struct wiphy *wiphy,
4769 				   struct wireless_dev *wdev,
4770 				   u16 frame_type, bool reg)
4771 {
4772 	struct brcmf_cfg80211_vif *vif;
4773 	u16 mgmt_type;
4774 
4775 	brcmf_dbg(TRACE, "Enter, frame_type %04x, reg=%d\n", frame_type, reg);
4776 
4777 	mgmt_type = (frame_type & IEEE80211_FCTL_STYPE) >> 4;
4778 	vif = container_of(wdev, struct brcmf_cfg80211_vif, wdev);
4779 	if (reg)
4780 		vif->mgmt_rx_reg |= BIT(mgmt_type);
4781 	else
4782 		vif->mgmt_rx_reg &= ~BIT(mgmt_type);
4783 }
4784 
4785 
4786 static int
4787 brcmf_cfg80211_mgmt_tx(struct wiphy *wiphy, struct wireless_dev *wdev,
4788 		       struct cfg80211_mgmt_tx_params *params, u64 *cookie)
4789 {
4790 	struct brcmf_cfg80211_info *cfg = wiphy_to_cfg(wiphy);
4791 	struct ieee80211_channel *chan = params->chan;
4792 	const u8 *buf = params->buf;
4793 	size_t len = params->len;
4794 	const struct ieee80211_mgmt *mgmt;
4795 	struct brcmf_cfg80211_vif *vif;
4796 	s32 err = 0;
4797 	s32 ie_offset;
4798 	s32 ie_len;
4799 	struct brcmf_fil_action_frame_le *action_frame;
4800 	struct brcmf_fil_af_params_le *af_params;
4801 	bool ack;
4802 	s32 chan_nr;
4803 	u32 freq;
4804 
4805 	brcmf_dbg(TRACE, "Enter\n");
4806 
4807 	*cookie = 0;
4808 
4809 	mgmt = (const struct ieee80211_mgmt *)buf;
4810 
4811 	if (!ieee80211_is_mgmt(mgmt->frame_control)) {
4812 		brcmf_err("Driver only allows MGMT packet type\n");
4813 		return -EPERM;
4814 	}
4815 
4816 	vif = container_of(wdev, struct brcmf_cfg80211_vif, wdev);
4817 
4818 	if (ieee80211_is_probe_resp(mgmt->frame_control)) {
4819 		/* Right now the only reason to get a probe response */
4820 		/* is for p2p listen response or for p2p GO from     */
4821 		/* wpa_supplicant. Unfortunately the probe is send   */
4822 		/* on primary ndev, while dongle wants it on the p2p */
4823 		/* vif. Since this is only reason for a probe        */
4824 		/* response to be sent, the vif is taken from cfg.   */
4825 		/* If ever desired to send proberesp for non p2p     */
4826 		/* response then data should be checked for          */
4827 		/* "DIRECT-". Note in future supplicant will take    */
4828 		/* dedicated p2p wdev to do this and then this 'hack'*/
4829 		/* is not needed anymore.                            */
4830 		ie_offset =  DOT11_MGMT_HDR_LEN +
4831 			     DOT11_BCN_PRB_FIXED_LEN;
4832 		ie_len = len - ie_offset;
4833 		if (vif == cfg->p2p.bss_idx[P2PAPI_BSSCFG_PRIMARY].vif)
4834 			vif = cfg->p2p.bss_idx[P2PAPI_BSSCFG_DEVICE].vif;
4835 		err = brcmf_vif_set_mgmt_ie(vif,
4836 					    BRCMF_VNDR_IE_PRBRSP_FLAG,
4837 					    &buf[ie_offset],
4838 					    ie_len);
4839 		cfg80211_mgmt_tx_status(wdev, *cookie, buf, len, true,
4840 					GFP_KERNEL);
4841 	} else if (ieee80211_is_action(mgmt->frame_control)) {
4842 		af_params = kzalloc(sizeof(*af_params), GFP_KERNEL);
4843 		if (af_params == NULL) {
4844 			brcmf_err("unable to allocate frame\n");
4845 			err = -ENOMEM;
4846 			goto exit;
4847 		}
4848 		action_frame = &af_params->action_frame;
4849 		/* Add the packet Id */
4850 		action_frame->packet_id = cpu_to_le32(*cookie);
4851 		/* Add BSSID */
4852 		memcpy(&action_frame->da[0], &mgmt->da[0], ETH_ALEN);
4853 		memcpy(&af_params->bssid[0], &mgmt->bssid[0], ETH_ALEN);
4854 		/* Add the length exepted for 802.11 header  */
4855 		action_frame->len = cpu_to_le16(len - DOT11_MGMT_HDR_LEN);
4856 		/* Add the channel. Use the one specified as parameter if any or
4857 		 * the current one (got from the firmware) otherwise
4858 		 */
4859 		if (chan)
4860 			freq = chan->center_freq;
4861 		else
4862 			brcmf_fil_cmd_int_get(vif->ifp, BRCMF_C_GET_CHANNEL,
4863 					      &freq);
4864 		chan_nr = ieee80211_frequency_to_channel(freq);
4865 		af_params->channel = cpu_to_le32(chan_nr);
4866 
4867 		memcpy(action_frame->data, &buf[DOT11_MGMT_HDR_LEN],
4868 		       le16_to_cpu(action_frame->len));
4869 
4870 		brcmf_dbg(TRACE, "Action frame, cookie=%lld, len=%d, freq=%d\n",
4871 			  *cookie, le16_to_cpu(action_frame->len), freq);
4872 
4873 		ack = brcmf_p2p_send_action_frame(cfg, cfg_to_ndev(cfg),
4874 						  af_params);
4875 
4876 		cfg80211_mgmt_tx_status(wdev, *cookie, buf, len, ack,
4877 					GFP_KERNEL);
4878 		kfree(af_params);
4879 	} else {
4880 		brcmf_dbg(TRACE, "Unhandled, fc=%04x!!\n", mgmt->frame_control);
4881 		brcmf_dbg_hex_dump(true, buf, len, "payload, len=%Zu\n", len);
4882 	}
4883 
4884 exit:
4885 	return err;
4886 }
4887 
4888 
4889 static int
4890 brcmf_cfg80211_cancel_remain_on_channel(struct wiphy *wiphy,
4891 					struct wireless_dev *wdev,
4892 					u64 cookie)
4893 {
4894 	struct brcmf_cfg80211_info *cfg = wiphy_to_cfg(wiphy);
4895 	struct brcmf_cfg80211_vif *vif;
4896 	int err = 0;
4897 
4898 	brcmf_dbg(TRACE, "Enter p2p listen cancel\n");
4899 
4900 	vif = cfg->p2p.bss_idx[P2PAPI_BSSCFG_DEVICE].vif;
4901 	if (vif == NULL) {
4902 		brcmf_err("No p2p device available for probe response\n");
4903 		err = -ENODEV;
4904 		goto exit;
4905 	}
4906 	brcmf_p2p_cancel_remain_on_channel(vif->ifp);
4907 exit:
4908 	return err;
4909 }
4910 
4911 static int brcmf_cfg80211_get_channel(struct wiphy *wiphy,
4912 				      struct wireless_dev *wdev,
4913 				      struct cfg80211_chan_def *chandef)
4914 {
4915 	struct brcmf_cfg80211_info *cfg = wiphy_to_cfg(wiphy);
4916 	struct net_device *ndev = wdev->netdev;
4917 	struct brcmf_if *ifp;
4918 	struct brcmu_chan ch;
4919 	enum nl80211_band band = 0;
4920 	enum nl80211_chan_width width = 0;
4921 	u32 chanspec;
4922 	int freq, err;
4923 
4924 	if (!ndev)
4925 		return -ENODEV;
4926 	ifp = netdev_priv(ndev);
4927 
4928 	err = brcmf_fil_iovar_int_get(ifp, "chanspec", &chanspec);
4929 	if (err) {
4930 		brcmf_err("chanspec failed (%d)\n", err);
4931 		return err;
4932 	}
4933 
4934 	ch.chspec = chanspec;
4935 	cfg->d11inf.decchspec(&ch);
4936 
4937 	switch (ch.band) {
4938 	case BRCMU_CHAN_BAND_2G:
4939 		band = NL80211_BAND_2GHZ;
4940 		break;
4941 	case BRCMU_CHAN_BAND_5G:
4942 		band = NL80211_BAND_5GHZ;
4943 		break;
4944 	}
4945 
4946 	switch (ch.bw) {
4947 	case BRCMU_CHAN_BW_80:
4948 		width = NL80211_CHAN_WIDTH_80;
4949 		break;
4950 	case BRCMU_CHAN_BW_40:
4951 		width = NL80211_CHAN_WIDTH_40;
4952 		break;
4953 	case BRCMU_CHAN_BW_20:
4954 		width = NL80211_CHAN_WIDTH_20;
4955 		break;
4956 	case BRCMU_CHAN_BW_80P80:
4957 		width = NL80211_CHAN_WIDTH_80P80;
4958 		break;
4959 	case BRCMU_CHAN_BW_160:
4960 		width = NL80211_CHAN_WIDTH_160;
4961 		break;
4962 	}
4963 
4964 	freq = ieee80211_channel_to_frequency(ch.control_ch_num, band);
4965 	chandef->chan = ieee80211_get_channel(wiphy, freq);
4966 	chandef->width = width;
4967 	chandef->center_freq1 = ieee80211_channel_to_frequency(ch.chnum, band);
4968 	chandef->center_freq2 = 0;
4969 
4970 	return 0;
4971 }
4972 
4973 static int brcmf_cfg80211_crit_proto_start(struct wiphy *wiphy,
4974 					   struct wireless_dev *wdev,
4975 					   enum nl80211_crit_proto_id proto,
4976 					   u16 duration)
4977 {
4978 	struct brcmf_cfg80211_info *cfg = wiphy_to_cfg(wiphy);
4979 	struct brcmf_cfg80211_vif *vif;
4980 
4981 	vif = container_of(wdev, struct brcmf_cfg80211_vif, wdev);
4982 
4983 	/* only DHCP support for now */
4984 	if (proto != NL80211_CRIT_PROTO_DHCP)
4985 		return -EINVAL;
4986 
4987 	/* suppress and abort scanning */
4988 	set_bit(BRCMF_SCAN_STATUS_SUPPRESS, &cfg->scan_status);
4989 	brcmf_abort_scanning(cfg);
4990 
4991 	return brcmf_btcoex_set_mode(vif, BRCMF_BTCOEX_DISABLED, duration);
4992 }
4993 
4994 static void brcmf_cfg80211_crit_proto_stop(struct wiphy *wiphy,
4995 					   struct wireless_dev *wdev)
4996 {
4997 	struct brcmf_cfg80211_info *cfg = wiphy_to_cfg(wiphy);
4998 	struct brcmf_cfg80211_vif *vif;
4999 
5000 	vif = container_of(wdev, struct brcmf_cfg80211_vif, wdev);
5001 
5002 	brcmf_btcoex_set_mode(vif, BRCMF_BTCOEX_ENABLED, 0);
5003 	clear_bit(BRCMF_SCAN_STATUS_SUPPRESS, &cfg->scan_status);
5004 }
5005 
5006 static s32
5007 brcmf_notify_tdls_peer_event(struct brcmf_if *ifp,
5008 			     const struct brcmf_event_msg *e, void *data)
5009 {
5010 	switch (e->reason) {
5011 	case BRCMF_E_REASON_TDLS_PEER_DISCOVERED:
5012 		brcmf_dbg(TRACE, "TDLS Peer Discovered\n");
5013 		break;
5014 	case BRCMF_E_REASON_TDLS_PEER_CONNECTED:
5015 		brcmf_dbg(TRACE, "TDLS Peer Connected\n");
5016 		brcmf_proto_add_tdls_peer(ifp->drvr, ifp->ifidx, (u8 *)e->addr);
5017 		break;
5018 	case BRCMF_E_REASON_TDLS_PEER_DISCONNECTED:
5019 		brcmf_dbg(TRACE, "TDLS Peer Disconnected\n");
5020 		brcmf_proto_delete_peer(ifp->drvr, ifp->ifidx, (u8 *)e->addr);
5021 		break;
5022 	}
5023 
5024 	return 0;
5025 }
5026 
5027 static int brcmf_convert_nl80211_tdls_oper(enum nl80211_tdls_operation oper)
5028 {
5029 	int ret;
5030 
5031 	switch (oper) {
5032 	case NL80211_TDLS_DISCOVERY_REQ:
5033 		ret = BRCMF_TDLS_MANUAL_EP_DISCOVERY;
5034 		break;
5035 	case NL80211_TDLS_SETUP:
5036 		ret = BRCMF_TDLS_MANUAL_EP_CREATE;
5037 		break;
5038 	case NL80211_TDLS_TEARDOWN:
5039 		ret = BRCMF_TDLS_MANUAL_EP_DELETE;
5040 		break;
5041 	default:
5042 		brcmf_err("unsupported operation: %d\n", oper);
5043 		ret = -EOPNOTSUPP;
5044 	}
5045 	return ret;
5046 }
5047 
5048 static int brcmf_cfg80211_tdls_oper(struct wiphy *wiphy,
5049 				    struct net_device *ndev, const u8 *peer,
5050 				    enum nl80211_tdls_operation oper)
5051 {
5052 	struct brcmf_if *ifp;
5053 	struct brcmf_tdls_iovar_le info;
5054 	int ret = 0;
5055 
5056 	ret = brcmf_convert_nl80211_tdls_oper(oper);
5057 	if (ret < 0)
5058 		return ret;
5059 
5060 	ifp = netdev_priv(ndev);
5061 	memset(&info, 0, sizeof(info));
5062 	info.mode = (u8)ret;
5063 	if (peer)
5064 		memcpy(info.ea, peer, ETH_ALEN);
5065 
5066 	ret = brcmf_fil_iovar_data_set(ifp, "tdls_endpoint",
5067 				       &info, sizeof(info));
5068 	if (ret < 0)
5069 		brcmf_err("tdls_endpoint iovar failed: ret=%d\n", ret);
5070 
5071 	return ret;
5072 }
5073 
5074 #ifdef CONFIG_PM
5075 static int
5076 brcmf_cfg80211_set_rekey_data(struct wiphy *wiphy, struct net_device *ndev,
5077 			      struct cfg80211_gtk_rekey_data *gtk)
5078 {
5079 	struct brcmf_if *ifp = netdev_priv(ndev);
5080 	struct brcmf_gtk_keyinfo_le gtk_le;
5081 	int ret;
5082 
5083 	brcmf_dbg(TRACE, "Enter, bssidx=%d\n", ifp->bsscfgidx);
5084 
5085 	memcpy(gtk_le.kck, gtk->kck, sizeof(gtk_le.kck));
5086 	memcpy(gtk_le.kek, gtk->kek, sizeof(gtk_le.kek));
5087 	memcpy(gtk_le.replay_counter, gtk->replay_ctr,
5088 	       sizeof(gtk_le.replay_counter));
5089 
5090 	ret = brcmf_fil_iovar_data_set(ifp, "gtk_key_info", &gtk_le,
5091 				       sizeof(gtk_le));
5092 	if (ret < 0)
5093 		brcmf_err("gtk_key_info iovar failed: ret=%d\n", ret);
5094 
5095 	return ret;
5096 }
5097 #endif
5098 
5099 static struct cfg80211_ops brcmf_cfg80211_ops = {
5100 	.add_virtual_intf = brcmf_cfg80211_add_iface,
5101 	.del_virtual_intf = brcmf_cfg80211_del_iface,
5102 	.change_virtual_intf = brcmf_cfg80211_change_iface,
5103 	.scan = brcmf_cfg80211_scan,
5104 	.set_wiphy_params = brcmf_cfg80211_set_wiphy_params,
5105 	.join_ibss = brcmf_cfg80211_join_ibss,
5106 	.leave_ibss = brcmf_cfg80211_leave_ibss,
5107 	.get_station = brcmf_cfg80211_get_station,
5108 	.dump_station = brcmf_cfg80211_dump_station,
5109 	.set_tx_power = brcmf_cfg80211_set_tx_power,
5110 	.get_tx_power = brcmf_cfg80211_get_tx_power,
5111 	.add_key = brcmf_cfg80211_add_key,
5112 	.del_key = brcmf_cfg80211_del_key,
5113 	.get_key = brcmf_cfg80211_get_key,
5114 	.set_default_key = brcmf_cfg80211_config_default_key,
5115 	.set_default_mgmt_key = brcmf_cfg80211_config_default_mgmt_key,
5116 	.set_power_mgmt = brcmf_cfg80211_set_power_mgmt,
5117 	.connect = brcmf_cfg80211_connect,
5118 	.disconnect = brcmf_cfg80211_disconnect,
5119 	.suspend = brcmf_cfg80211_suspend,
5120 	.resume = brcmf_cfg80211_resume,
5121 	.set_pmksa = brcmf_cfg80211_set_pmksa,
5122 	.del_pmksa = brcmf_cfg80211_del_pmksa,
5123 	.flush_pmksa = brcmf_cfg80211_flush_pmksa,
5124 	.start_ap = brcmf_cfg80211_start_ap,
5125 	.stop_ap = brcmf_cfg80211_stop_ap,
5126 	.change_beacon = brcmf_cfg80211_change_beacon,
5127 	.del_station = brcmf_cfg80211_del_station,
5128 	.change_station = brcmf_cfg80211_change_station,
5129 	.sched_scan_start = brcmf_cfg80211_sched_scan_start,
5130 	.sched_scan_stop = brcmf_cfg80211_sched_scan_stop,
5131 	.mgmt_frame_register = brcmf_cfg80211_mgmt_frame_register,
5132 	.mgmt_tx = brcmf_cfg80211_mgmt_tx,
5133 	.remain_on_channel = brcmf_p2p_remain_on_channel,
5134 	.cancel_remain_on_channel = brcmf_cfg80211_cancel_remain_on_channel,
5135 	.get_channel = brcmf_cfg80211_get_channel,
5136 	.start_p2p_device = brcmf_p2p_start_device,
5137 	.stop_p2p_device = brcmf_p2p_stop_device,
5138 	.crit_proto_start = brcmf_cfg80211_crit_proto_start,
5139 	.crit_proto_stop = brcmf_cfg80211_crit_proto_stop,
5140 	.tdls_oper = brcmf_cfg80211_tdls_oper,
5141 };
5142 
5143 struct brcmf_cfg80211_vif *brcmf_alloc_vif(struct brcmf_cfg80211_info *cfg,
5144 					   enum nl80211_iftype type)
5145 {
5146 	struct brcmf_cfg80211_vif *vif_walk;
5147 	struct brcmf_cfg80211_vif *vif;
5148 	bool mbss;
5149 
5150 	brcmf_dbg(TRACE, "allocating virtual interface (size=%zu)\n",
5151 		  sizeof(*vif));
5152 	vif = kzalloc(sizeof(*vif), GFP_KERNEL);
5153 	if (!vif)
5154 		return ERR_PTR(-ENOMEM);
5155 
5156 	vif->wdev.wiphy = cfg->wiphy;
5157 	vif->wdev.iftype = type;
5158 
5159 	brcmf_init_prof(&vif->profile);
5160 
5161 	if (type == NL80211_IFTYPE_AP) {
5162 		mbss = false;
5163 		list_for_each_entry(vif_walk, &cfg->vif_list, list) {
5164 			if (vif_walk->wdev.iftype == NL80211_IFTYPE_AP) {
5165 				mbss = true;
5166 				break;
5167 			}
5168 		}
5169 		vif->mbss = mbss;
5170 	}
5171 
5172 	list_add_tail(&vif->list, &cfg->vif_list);
5173 	return vif;
5174 }
5175 
5176 void brcmf_free_vif(struct brcmf_cfg80211_vif *vif)
5177 {
5178 	list_del(&vif->list);
5179 	kfree(vif);
5180 }
5181 
5182 void brcmf_cfg80211_free_netdev(struct net_device *ndev)
5183 {
5184 	struct brcmf_cfg80211_vif *vif;
5185 	struct brcmf_if *ifp;
5186 
5187 	ifp = netdev_priv(ndev);
5188 	vif = ifp->vif;
5189 
5190 	if (vif)
5191 		brcmf_free_vif(vif);
5192 	free_netdev(ndev);
5193 }
5194 
5195 static bool brcmf_is_linkup(const struct brcmf_event_msg *e)
5196 {
5197 	u32 event = e->event_code;
5198 	u32 status = e->status;
5199 
5200 	if (event == BRCMF_E_SET_SSID && status == BRCMF_E_STATUS_SUCCESS) {
5201 		brcmf_dbg(CONN, "Processing set ssid\n");
5202 		return true;
5203 	}
5204 
5205 	return false;
5206 }
5207 
5208 static bool brcmf_is_linkdown(const struct brcmf_event_msg *e)
5209 {
5210 	u32 event = e->event_code;
5211 	u16 flags = e->flags;
5212 
5213 	if ((event == BRCMF_E_DEAUTH) || (event == BRCMF_E_DEAUTH_IND) ||
5214 	    (event == BRCMF_E_DISASSOC_IND) ||
5215 	    ((event == BRCMF_E_LINK) && (!(flags & BRCMF_EVENT_MSG_LINK)))) {
5216 		brcmf_dbg(CONN, "Processing link down\n");
5217 		return true;
5218 	}
5219 	return false;
5220 }
5221 
5222 static bool brcmf_is_nonetwork(struct brcmf_cfg80211_info *cfg,
5223 			       const struct brcmf_event_msg *e)
5224 {
5225 	u32 event = e->event_code;
5226 	u32 status = e->status;
5227 
5228 	if (event == BRCMF_E_LINK && status == BRCMF_E_STATUS_NO_NETWORKS) {
5229 		brcmf_dbg(CONN, "Processing Link %s & no network found\n",
5230 			  e->flags & BRCMF_EVENT_MSG_LINK ? "up" : "down");
5231 		return true;
5232 	}
5233 
5234 	if (event == BRCMF_E_SET_SSID && status != BRCMF_E_STATUS_SUCCESS) {
5235 		brcmf_dbg(CONN, "Processing connecting & no network found\n");
5236 		return true;
5237 	}
5238 
5239 	return false;
5240 }
5241 
5242 static void brcmf_clear_assoc_ies(struct brcmf_cfg80211_info *cfg)
5243 {
5244 	struct brcmf_cfg80211_connect_info *conn_info = cfg_to_conn(cfg);
5245 
5246 	kfree(conn_info->req_ie);
5247 	conn_info->req_ie = NULL;
5248 	conn_info->req_ie_len = 0;
5249 	kfree(conn_info->resp_ie);
5250 	conn_info->resp_ie = NULL;
5251 	conn_info->resp_ie_len = 0;
5252 }
5253 
5254 static s32 brcmf_get_assoc_ies(struct brcmf_cfg80211_info *cfg,
5255 			       struct brcmf_if *ifp)
5256 {
5257 	struct brcmf_cfg80211_assoc_ielen_le *assoc_info;
5258 	struct brcmf_cfg80211_connect_info *conn_info = cfg_to_conn(cfg);
5259 	u32 req_len;
5260 	u32 resp_len;
5261 	s32 err = 0;
5262 
5263 	brcmf_clear_assoc_ies(cfg);
5264 
5265 	err = brcmf_fil_iovar_data_get(ifp, "assoc_info",
5266 				       cfg->extra_buf, WL_ASSOC_INFO_MAX);
5267 	if (err) {
5268 		brcmf_err("could not get assoc info (%d)\n", err);
5269 		return err;
5270 	}
5271 	assoc_info =
5272 		(struct brcmf_cfg80211_assoc_ielen_le *)cfg->extra_buf;
5273 	req_len = le32_to_cpu(assoc_info->req_len);
5274 	resp_len = le32_to_cpu(assoc_info->resp_len);
5275 	if (req_len) {
5276 		err = brcmf_fil_iovar_data_get(ifp, "assoc_req_ies",
5277 					       cfg->extra_buf,
5278 					       WL_ASSOC_INFO_MAX);
5279 		if (err) {
5280 			brcmf_err("could not get assoc req (%d)\n", err);
5281 			return err;
5282 		}
5283 		conn_info->req_ie_len = req_len;
5284 		conn_info->req_ie =
5285 		    kmemdup(cfg->extra_buf, conn_info->req_ie_len,
5286 			    GFP_KERNEL);
5287 	} else {
5288 		conn_info->req_ie_len = 0;
5289 		conn_info->req_ie = NULL;
5290 	}
5291 	if (resp_len) {
5292 		err = brcmf_fil_iovar_data_get(ifp, "assoc_resp_ies",
5293 					       cfg->extra_buf,
5294 					       WL_ASSOC_INFO_MAX);
5295 		if (err) {
5296 			brcmf_err("could not get assoc resp (%d)\n", err);
5297 			return err;
5298 		}
5299 		conn_info->resp_ie_len = resp_len;
5300 		conn_info->resp_ie =
5301 		    kmemdup(cfg->extra_buf, conn_info->resp_ie_len,
5302 			    GFP_KERNEL);
5303 	} else {
5304 		conn_info->resp_ie_len = 0;
5305 		conn_info->resp_ie = NULL;
5306 	}
5307 	brcmf_dbg(CONN, "req len (%d) resp len (%d)\n",
5308 		  conn_info->req_ie_len, conn_info->resp_ie_len);
5309 
5310 	return err;
5311 }
5312 
5313 static s32
5314 brcmf_bss_roaming_done(struct brcmf_cfg80211_info *cfg,
5315 		       struct net_device *ndev,
5316 		       const struct brcmf_event_msg *e)
5317 {
5318 	struct brcmf_if *ifp = netdev_priv(ndev);
5319 	struct brcmf_cfg80211_profile *profile = &ifp->vif->profile;
5320 	struct brcmf_cfg80211_connect_info *conn_info = cfg_to_conn(cfg);
5321 	struct wiphy *wiphy = cfg_to_wiphy(cfg);
5322 	struct ieee80211_channel *notify_channel = NULL;
5323 	struct ieee80211_supported_band *band;
5324 	struct brcmf_bss_info_le *bi;
5325 	struct brcmu_chan ch;
5326 	u32 freq;
5327 	s32 err = 0;
5328 	u8 *buf;
5329 
5330 	brcmf_dbg(TRACE, "Enter\n");
5331 
5332 	brcmf_get_assoc_ies(cfg, ifp);
5333 	memcpy(profile->bssid, e->addr, ETH_ALEN);
5334 	brcmf_update_bss_info(cfg, ifp);
5335 
5336 	buf = kzalloc(WL_BSS_INFO_MAX, GFP_KERNEL);
5337 	if (buf == NULL) {
5338 		err = -ENOMEM;
5339 		goto done;
5340 	}
5341 
5342 	/* data sent to dongle has to be little endian */
5343 	*(__le32 *)buf = cpu_to_le32(WL_BSS_INFO_MAX);
5344 	err = brcmf_fil_cmd_data_get(ifp, BRCMF_C_GET_BSS_INFO,
5345 				     buf, WL_BSS_INFO_MAX);
5346 
5347 	if (err)
5348 		goto done;
5349 
5350 	bi = (struct brcmf_bss_info_le *)(buf + 4);
5351 	ch.chspec = le16_to_cpu(bi->chanspec);
5352 	cfg->d11inf.decchspec(&ch);
5353 
5354 	if (ch.band == BRCMU_CHAN_BAND_2G)
5355 		band = wiphy->bands[NL80211_BAND_2GHZ];
5356 	else
5357 		band = wiphy->bands[NL80211_BAND_5GHZ];
5358 
5359 	freq = ieee80211_channel_to_frequency(ch.control_ch_num, band->band);
5360 	notify_channel = ieee80211_get_channel(wiphy, freq);
5361 
5362 done:
5363 	kfree(buf);
5364 	cfg80211_roamed(ndev, notify_channel, (u8 *)profile->bssid,
5365 			conn_info->req_ie, conn_info->req_ie_len,
5366 			conn_info->resp_ie, conn_info->resp_ie_len, GFP_KERNEL);
5367 	brcmf_dbg(CONN, "Report roaming result\n");
5368 
5369 	set_bit(BRCMF_VIF_STATUS_CONNECTED, &ifp->vif->sme_state);
5370 	brcmf_dbg(TRACE, "Exit\n");
5371 	return err;
5372 }
5373 
5374 static s32
5375 brcmf_bss_connect_done(struct brcmf_cfg80211_info *cfg,
5376 		       struct net_device *ndev, const struct brcmf_event_msg *e,
5377 		       bool completed)
5378 {
5379 	struct brcmf_if *ifp = netdev_priv(ndev);
5380 	struct brcmf_cfg80211_profile *profile = &ifp->vif->profile;
5381 	struct brcmf_cfg80211_connect_info *conn_info = cfg_to_conn(cfg);
5382 
5383 	brcmf_dbg(TRACE, "Enter\n");
5384 
5385 	if (test_and_clear_bit(BRCMF_VIF_STATUS_CONNECTING,
5386 			       &ifp->vif->sme_state)) {
5387 		if (completed) {
5388 			brcmf_get_assoc_ies(cfg, ifp);
5389 			memcpy(profile->bssid, e->addr, ETH_ALEN);
5390 			brcmf_update_bss_info(cfg, ifp);
5391 			set_bit(BRCMF_VIF_STATUS_CONNECTED,
5392 				&ifp->vif->sme_state);
5393 		}
5394 		cfg80211_connect_result(ndev,
5395 					(u8 *)profile->bssid,
5396 					conn_info->req_ie,
5397 					conn_info->req_ie_len,
5398 					conn_info->resp_ie,
5399 					conn_info->resp_ie_len,
5400 					completed ? WLAN_STATUS_SUCCESS :
5401 						    WLAN_STATUS_AUTH_TIMEOUT,
5402 					GFP_KERNEL);
5403 		brcmf_dbg(CONN, "Report connect result - connection %s\n",
5404 			  completed ? "succeeded" : "failed");
5405 	}
5406 	brcmf_dbg(TRACE, "Exit\n");
5407 	return 0;
5408 }
5409 
5410 static s32
5411 brcmf_notify_connect_status_ap(struct brcmf_cfg80211_info *cfg,
5412 			       struct net_device *ndev,
5413 			       const struct brcmf_event_msg *e, void *data)
5414 {
5415 	static int generation;
5416 	u32 event = e->event_code;
5417 	u32 reason = e->reason;
5418 	struct station_info sinfo;
5419 
5420 	brcmf_dbg(CONN, "event %s (%u), reason %d\n",
5421 		  brcmf_fweh_event_name(event), event, reason);
5422 	if (event == BRCMF_E_LINK && reason == BRCMF_E_REASON_LINK_BSSCFG_DIS &&
5423 	    ndev != cfg_to_ndev(cfg)) {
5424 		brcmf_dbg(CONN, "AP mode link down\n");
5425 		complete(&cfg->vif_disabled);
5426 		return 0;
5427 	}
5428 
5429 	if (((event == BRCMF_E_ASSOC_IND) || (event == BRCMF_E_REASSOC_IND)) &&
5430 	    (reason == BRCMF_E_STATUS_SUCCESS)) {
5431 		memset(&sinfo, 0, sizeof(sinfo));
5432 		if (!data) {
5433 			brcmf_err("No IEs present in ASSOC/REASSOC_IND");
5434 			return -EINVAL;
5435 		}
5436 		sinfo.assoc_req_ies = data;
5437 		sinfo.assoc_req_ies_len = e->datalen;
5438 		generation++;
5439 		sinfo.generation = generation;
5440 		cfg80211_new_sta(ndev, e->addr, &sinfo, GFP_KERNEL);
5441 	} else if ((event == BRCMF_E_DISASSOC_IND) ||
5442 		   (event == BRCMF_E_DEAUTH_IND) ||
5443 		   (event == BRCMF_E_DEAUTH)) {
5444 		cfg80211_del_sta(ndev, e->addr, GFP_KERNEL);
5445 	}
5446 	return 0;
5447 }
5448 
5449 static s32
5450 brcmf_notify_connect_status(struct brcmf_if *ifp,
5451 			    const struct brcmf_event_msg *e, void *data)
5452 {
5453 	struct brcmf_cfg80211_info *cfg = ifp->drvr->config;
5454 	struct net_device *ndev = ifp->ndev;
5455 	struct brcmf_cfg80211_profile *profile = &ifp->vif->profile;
5456 	struct ieee80211_channel *chan;
5457 	s32 err = 0;
5458 
5459 	if ((e->event_code == BRCMF_E_DEAUTH) ||
5460 	    (e->event_code == BRCMF_E_DEAUTH_IND) ||
5461 	    (e->event_code == BRCMF_E_DISASSOC_IND) ||
5462 	    ((e->event_code == BRCMF_E_LINK) && (!e->flags))) {
5463 		brcmf_proto_delete_peer(ifp->drvr, ifp->ifidx, (u8 *)e->addr);
5464 	}
5465 
5466 	if (brcmf_is_apmode(ifp->vif)) {
5467 		err = brcmf_notify_connect_status_ap(cfg, ndev, e, data);
5468 	} else if (brcmf_is_linkup(e)) {
5469 		brcmf_dbg(CONN, "Linkup\n");
5470 		if (brcmf_is_ibssmode(ifp->vif)) {
5471 			brcmf_inform_ibss(cfg, ndev, e->addr);
5472 			chan = ieee80211_get_channel(cfg->wiphy, cfg->channel);
5473 			memcpy(profile->bssid, e->addr, ETH_ALEN);
5474 			cfg80211_ibss_joined(ndev, e->addr, chan, GFP_KERNEL);
5475 			clear_bit(BRCMF_VIF_STATUS_CONNECTING,
5476 				  &ifp->vif->sme_state);
5477 			set_bit(BRCMF_VIF_STATUS_CONNECTED,
5478 				&ifp->vif->sme_state);
5479 		} else
5480 			brcmf_bss_connect_done(cfg, ndev, e, true);
5481 		brcmf_net_setcarrier(ifp, true);
5482 	} else if (brcmf_is_linkdown(e)) {
5483 		brcmf_dbg(CONN, "Linkdown\n");
5484 		if (!brcmf_is_ibssmode(ifp->vif)) {
5485 			brcmf_bss_connect_done(cfg, ndev, e, false);
5486 			brcmf_link_down(ifp->vif,
5487 					brcmf_map_fw_linkdown_reason(e));
5488 			brcmf_init_prof(ndev_to_prof(ndev));
5489 			if (ndev != cfg_to_ndev(cfg))
5490 				complete(&cfg->vif_disabled);
5491 			brcmf_net_setcarrier(ifp, false);
5492 		}
5493 	} else if (brcmf_is_nonetwork(cfg, e)) {
5494 		if (brcmf_is_ibssmode(ifp->vif))
5495 			clear_bit(BRCMF_VIF_STATUS_CONNECTING,
5496 				  &ifp->vif->sme_state);
5497 		else
5498 			brcmf_bss_connect_done(cfg, ndev, e, false);
5499 	}
5500 
5501 	return err;
5502 }
5503 
5504 static s32
5505 brcmf_notify_roaming_status(struct brcmf_if *ifp,
5506 			    const struct brcmf_event_msg *e, void *data)
5507 {
5508 	struct brcmf_cfg80211_info *cfg = ifp->drvr->config;
5509 	u32 event = e->event_code;
5510 	u32 status = e->status;
5511 
5512 	if (event == BRCMF_E_ROAM && status == BRCMF_E_STATUS_SUCCESS) {
5513 		if (test_bit(BRCMF_VIF_STATUS_CONNECTED, &ifp->vif->sme_state))
5514 			brcmf_bss_roaming_done(cfg, ifp->ndev, e);
5515 		else
5516 			brcmf_bss_connect_done(cfg, ifp->ndev, e, true);
5517 	}
5518 
5519 	return 0;
5520 }
5521 
5522 static s32
5523 brcmf_notify_mic_status(struct brcmf_if *ifp,
5524 			const struct brcmf_event_msg *e, void *data)
5525 {
5526 	u16 flags = e->flags;
5527 	enum nl80211_key_type key_type;
5528 
5529 	if (flags & BRCMF_EVENT_MSG_GROUP)
5530 		key_type = NL80211_KEYTYPE_GROUP;
5531 	else
5532 		key_type = NL80211_KEYTYPE_PAIRWISE;
5533 
5534 	cfg80211_michael_mic_failure(ifp->ndev, (u8 *)&e->addr, key_type, -1,
5535 				     NULL, GFP_KERNEL);
5536 
5537 	return 0;
5538 }
5539 
5540 static s32 brcmf_notify_vif_event(struct brcmf_if *ifp,
5541 				  const struct brcmf_event_msg *e, void *data)
5542 {
5543 	struct brcmf_cfg80211_info *cfg = ifp->drvr->config;
5544 	struct brcmf_if_event *ifevent = (struct brcmf_if_event *)data;
5545 	struct brcmf_cfg80211_vif_event *event = &cfg->vif_event;
5546 	struct brcmf_cfg80211_vif *vif;
5547 
5548 	brcmf_dbg(TRACE, "Enter: action %u flags %u ifidx %u bsscfgidx %u\n",
5549 		  ifevent->action, ifevent->flags, ifevent->ifidx,
5550 		  ifevent->bsscfgidx);
5551 
5552 	spin_lock(&event->vif_event_lock);
5553 	event->action = ifevent->action;
5554 	vif = event->vif;
5555 
5556 	switch (ifevent->action) {
5557 	case BRCMF_E_IF_ADD:
5558 		/* waiting process may have timed out */
5559 		if (!cfg->vif_event.vif) {
5560 			spin_unlock(&event->vif_event_lock);
5561 			return -EBADF;
5562 		}
5563 
5564 		ifp->vif = vif;
5565 		vif->ifp = ifp;
5566 		if (ifp->ndev) {
5567 			vif->wdev.netdev = ifp->ndev;
5568 			ifp->ndev->ieee80211_ptr = &vif->wdev;
5569 			SET_NETDEV_DEV(ifp->ndev, wiphy_dev(cfg->wiphy));
5570 		}
5571 		spin_unlock(&event->vif_event_lock);
5572 		wake_up(&event->vif_wq);
5573 		return 0;
5574 
5575 	case BRCMF_E_IF_DEL:
5576 		spin_unlock(&event->vif_event_lock);
5577 		/* event may not be upon user request */
5578 		if (brcmf_cfg80211_vif_event_armed(cfg))
5579 			wake_up(&event->vif_wq);
5580 		return 0;
5581 
5582 	case BRCMF_E_IF_CHANGE:
5583 		spin_unlock(&event->vif_event_lock);
5584 		wake_up(&event->vif_wq);
5585 		return 0;
5586 
5587 	default:
5588 		spin_unlock(&event->vif_event_lock);
5589 		break;
5590 	}
5591 	return -EINVAL;
5592 }
5593 
5594 static void brcmf_init_conf(struct brcmf_cfg80211_conf *conf)
5595 {
5596 	conf->frag_threshold = (u32)-1;
5597 	conf->rts_threshold = (u32)-1;
5598 	conf->retry_short = (u32)-1;
5599 	conf->retry_long = (u32)-1;
5600 }
5601 
5602 static void brcmf_register_event_handlers(struct brcmf_cfg80211_info *cfg)
5603 {
5604 	brcmf_fweh_register(cfg->pub, BRCMF_E_LINK,
5605 			    brcmf_notify_connect_status);
5606 	brcmf_fweh_register(cfg->pub, BRCMF_E_DEAUTH_IND,
5607 			    brcmf_notify_connect_status);
5608 	brcmf_fweh_register(cfg->pub, BRCMF_E_DEAUTH,
5609 			    brcmf_notify_connect_status);
5610 	brcmf_fweh_register(cfg->pub, BRCMF_E_DISASSOC_IND,
5611 			    brcmf_notify_connect_status);
5612 	brcmf_fweh_register(cfg->pub, BRCMF_E_ASSOC_IND,
5613 			    brcmf_notify_connect_status);
5614 	brcmf_fweh_register(cfg->pub, BRCMF_E_REASSOC_IND,
5615 			    brcmf_notify_connect_status);
5616 	brcmf_fweh_register(cfg->pub, BRCMF_E_ROAM,
5617 			    brcmf_notify_roaming_status);
5618 	brcmf_fweh_register(cfg->pub, BRCMF_E_MIC_ERROR,
5619 			    brcmf_notify_mic_status);
5620 	brcmf_fweh_register(cfg->pub, BRCMF_E_SET_SSID,
5621 			    brcmf_notify_connect_status);
5622 	brcmf_fweh_register(cfg->pub, BRCMF_E_PFN_NET_FOUND,
5623 			    brcmf_notify_sched_scan_results);
5624 	brcmf_fweh_register(cfg->pub, BRCMF_E_IF,
5625 			    brcmf_notify_vif_event);
5626 	brcmf_fweh_register(cfg->pub, BRCMF_E_P2P_PROBEREQ_MSG,
5627 			    brcmf_p2p_notify_rx_mgmt_p2p_probereq);
5628 	brcmf_fweh_register(cfg->pub, BRCMF_E_P2P_DISC_LISTEN_COMPLETE,
5629 			    brcmf_p2p_notify_listen_complete);
5630 	brcmf_fweh_register(cfg->pub, BRCMF_E_ACTION_FRAME_RX,
5631 			    brcmf_p2p_notify_action_frame_rx);
5632 	brcmf_fweh_register(cfg->pub, BRCMF_E_ACTION_FRAME_COMPLETE,
5633 			    brcmf_p2p_notify_action_tx_complete);
5634 	brcmf_fweh_register(cfg->pub, BRCMF_E_ACTION_FRAME_OFF_CHAN_COMPLETE,
5635 			    brcmf_p2p_notify_action_tx_complete);
5636 }
5637 
5638 static void brcmf_deinit_priv_mem(struct brcmf_cfg80211_info *cfg)
5639 {
5640 	kfree(cfg->conf);
5641 	cfg->conf = NULL;
5642 	kfree(cfg->extra_buf);
5643 	cfg->extra_buf = NULL;
5644 	kfree(cfg->wowl.nd);
5645 	cfg->wowl.nd = NULL;
5646 	kfree(cfg->wowl.nd_info);
5647 	cfg->wowl.nd_info = NULL;
5648 	kfree(cfg->escan_info.escan_buf);
5649 	cfg->escan_info.escan_buf = NULL;
5650 }
5651 
5652 static s32 brcmf_init_priv_mem(struct brcmf_cfg80211_info *cfg)
5653 {
5654 	cfg->conf = kzalloc(sizeof(*cfg->conf), GFP_KERNEL);
5655 	if (!cfg->conf)
5656 		goto init_priv_mem_out;
5657 	cfg->extra_buf = kzalloc(WL_EXTRA_BUF_MAX, GFP_KERNEL);
5658 	if (!cfg->extra_buf)
5659 		goto init_priv_mem_out;
5660 	cfg->wowl.nd = kzalloc(sizeof(*cfg->wowl.nd) + sizeof(u32), GFP_KERNEL);
5661 	if (!cfg->wowl.nd)
5662 		goto init_priv_mem_out;
5663 	cfg->wowl.nd_info = kzalloc(sizeof(*cfg->wowl.nd_info) +
5664 				    sizeof(struct cfg80211_wowlan_nd_match *),
5665 				    GFP_KERNEL);
5666 	if (!cfg->wowl.nd_info)
5667 		goto init_priv_mem_out;
5668 	cfg->escan_info.escan_buf = kzalloc(BRCMF_ESCAN_BUF_SIZE, GFP_KERNEL);
5669 	if (!cfg->escan_info.escan_buf)
5670 		goto init_priv_mem_out;
5671 
5672 	return 0;
5673 
5674 init_priv_mem_out:
5675 	brcmf_deinit_priv_mem(cfg);
5676 
5677 	return -ENOMEM;
5678 }
5679 
5680 static s32 wl_init_priv(struct brcmf_cfg80211_info *cfg)
5681 {
5682 	s32 err = 0;
5683 
5684 	cfg->scan_request = NULL;
5685 	cfg->pwr_save = true;
5686 	cfg->active_scan = true;	/* we do active scan per default */
5687 	cfg->dongle_up = false;		/* dongle is not up yet */
5688 	err = brcmf_init_priv_mem(cfg);
5689 	if (err)
5690 		return err;
5691 	brcmf_register_event_handlers(cfg);
5692 	mutex_init(&cfg->usr_sync);
5693 	brcmf_init_escan(cfg);
5694 	brcmf_init_conf(cfg->conf);
5695 	init_completion(&cfg->vif_disabled);
5696 	return err;
5697 }
5698 
5699 static void wl_deinit_priv(struct brcmf_cfg80211_info *cfg)
5700 {
5701 	cfg->dongle_up = false;	/* dongle down */
5702 	brcmf_abort_scanning(cfg);
5703 	brcmf_deinit_priv_mem(cfg);
5704 }
5705 
5706 static void init_vif_event(struct brcmf_cfg80211_vif_event *event)
5707 {
5708 	init_waitqueue_head(&event->vif_wq);
5709 	spin_lock_init(&event->vif_event_lock);
5710 }
5711 
5712 static s32 brcmf_dongle_roam(struct brcmf_if *ifp)
5713 {
5714 	s32 err;
5715 	u32 bcn_timeout;
5716 	__le32 roamtrigger[2];
5717 	__le32 roam_delta[2];
5718 
5719 	/* Configure beacon timeout value based upon roaming setting */
5720 	if (ifp->drvr->settings->roamoff)
5721 		bcn_timeout = BRCMF_DEFAULT_BCN_TIMEOUT_ROAM_OFF;
5722 	else
5723 		bcn_timeout = BRCMF_DEFAULT_BCN_TIMEOUT_ROAM_ON;
5724 	err = brcmf_fil_iovar_int_set(ifp, "bcn_timeout", bcn_timeout);
5725 	if (err) {
5726 		brcmf_err("bcn_timeout error (%d)\n", err);
5727 		goto roam_setup_done;
5728 	}
5729 
5730 	/* Enable/Disable built-in roaming to allow supplicant to take care of
5731 	 * roaming.
5732 	 */
5733 	brcmf_dbg(INFO, "Internal Roaming = %s\n",
5734 		  ifp->drvr->settings->roamoff ? "Off" : "On");
5735 	err = brcmf_fil_iovar_int_set(ifp, "roam_off",
5736 				      ifp->drvr->settings->roamoff);
5737 	if (err) {
5738 		brcmf_err("roam_off error (%d)\n", err);
5739 		goto roam_setup_done;
5740 	}
5741 
5742 	roamtrigger[0] = cpu_to_le32(WL_ROAM_TRIGGER_LEVEL);
5743 	roamtrigger[1] = cpu_to_le32(BRCM_BAND_ALL);
5744 	err = brcmf_fil_cmd_data_set(ifp, BRCMF_C_SET_ROAM_TRIGGER,
5745 				     (void *)roamtrigger, sizeof(roamtrigger));
5746 	if (err) {
5747 		brcmf_err("WLC_SET_ROAM_TRIGGER error (%d)\n", err);
5748 		goto roam_setup_done;
5749 	}
5750 
5751 	roam_delta[0] = cpu_to_le32(WL_ROAM_DELTA);
5752 	roam_delta[1] = cpu_to_le32(BRCM_BAND_ALL);
5753 	err = brcmf_fil_cmd_data_set(ifp, BRCMF_C_SET_ROAM_DELTA,
5754 				     (void *)roam_delta, sizeof(roam_delta));
5755 	if (err) {
5756 		brcmf_err("WLC_SET_ROAM_DELTA error (%d)\n", err);
5757 		goto roam_setup_done;
5758 	}
5759 
5760 roam_setup_done:
5761 	return err;
5762 }
5763 
5764 static s32
5765 brcmf_dongle_scantime(struct brcmf_if *ifp)
5766 {
5767 	s32 err = 0;
5768 
5769 	err = brcmf_fil_cmd_int_set(ifp, BRCMF_C_SET_SCAN_CHANNEL_TIME,
5770 				    BRCMF_SCAN_CHANNEL_TIME);
5771 	if (err) {
5772 		brcmf_err("Scan assoc time error (%d)\n", err);
5773 		goto dongle_scantime_out;
5774 	}
5775 	err = brcmf_fil_cmd_int_set(ifp, BRCMF_C_SET_SCAN_UNASSOC_TIME,
5776 				    BRCMF_SCAN_UNASSOC_TIME);
5777 	if (err) {
5778 		brcmf_err("Scan unassoc time error (%d)\n", err);
5779 		goto dongle_scantime_out;
5780 	}
5781 
5782 	err = brcmf_fil_cmd_int_set(ifp, BRCMF_C_SET_SCAN_PASSIVE_TIME,
5783 				    BRCMF_SCAN_PASSIVE_TIME);
5784 	if (err) {
5785 		brcmf_err("Scan passive time error (%d)\n", err);
5786 		goto dongle_scantime_out;
5787 	}
5788 
5789 dongle_scantime_out:
5790 	return err;
5791 }
5792 
5793 static void brcmf_update_bw40_channel_flag(struct ieee80211_channel *channel,
5794 					   struct brcmu_chan *ch)
5795 {
5796 	u32 ht40_flag;
5797 
5798 	ht40_flag = channel->flags & IEEE80211_CHAN_NO_HT40;
5799 	if (ch->sb == BRCMU_CHAN_SB_U) {
5800 		if (ht40_flag == IEEE80211_CHAN_NO_HT40)
5801 			channel->flags &= ~IEEE80211_CHAN_NO_HT40;
5802 		channel->flags |= IEEE80211_CHAN_NO_HT40PLUS;
5803 	} else {
5804 		/* It should be one of
5805 		 * IEEE80211_CHAN_NO_HT40 or
5806 		 * IEEE80211_CHAN_NO_HT40PLUS
5807 		 */
5808 		channel->flags &= ~IEEE80211_CHAN_NO_HT40;
5809 		if (ht40_flag == IEEE80211_CHAN_NO_HT40)
5810 			channel->flags |= IEEE80211_CHAN_NO_HT40MINUS;
5811 	}
5812 }
5813 
5814 static int brcmf_construct_chaninfo(struct brcmf_cfg80211_info *cfg,
5815 				    u32 bw_cap[])
5816 {
5817 	struct brcmf_if *ifp = netdev_priv(cfg_to_ndev(cfg));
5818 	struct ieee80211_supported_band *band;
5819 	struct ieee80211_channel *channel;
5820 	struct wiphy *wiphy;
5821 	struct brcmf_chanspec_list *list;
5822 	struct brcmu_chan ch;
5823 	int err;
5824 	u8 *pbuf;
5825 	u32 i, j;
5826 	u32 total;
5827 	u32 chaninfo;
5828 	u32 index;
5829 
5830 	pbuf = kzalloc(BRCMF_DCMD_MEDLEN, GFP_KERNEL);
5831 
5832 	if (pbuf == NULL)
5833 		return -ENOMEM;
5834 
5835 	list = (struct brcmf_chanspec_list *)pbuf;
5836 
5837 	err = brcmf_fil_iovar_data_get(ifp, "chanspecs", pbuf,
5838 				       BRCMF_DCMD_MEDLEN);
5839 	if (err) {
5840 		brcmf_err("get chanspecs error (%d)\n", err);
5841 		goto fail_pbuf;
5842 	}
5843 
5844 	wiphy = cfg_to_wiphy(cfg);
5845 	band = wiphy->bands[NL80211_BAND_2GHZ];
5846 	if (band)
5847 		for (i = 0; i < band->n_channels; i++)
5848 			band->channels[i].flags = IEEE80211_CHAN_DISABLED;
5849 	band = wiphy->bands[NL80211_BAND_5GHZ];
5850 	if (band)
5851 		for (i = 0; i < band->n_channels; i++)
5852 			band->channels[i].flags = IEEE80211_CHAN_DISABLED;
5853 
5854 	total = le32_to_cpu(list->count);
5855 	for (i = 0; i < total; i++) {
5856 		ch.chspec = (u16)le32_to_cpu(list->element[i]);
5857 		cfg->d11inf.decchspec(&ch);
5858 
5859 		if (ch.band == BRCMU_CHAN_BAND_2G) {
5860 			band = wiphy->bands[NL80211_BAND_2GHZ];
5861 		} else if (ch.band == BRCMU_CHAN_BAND_5G) {
5862 			band = wiphy->bands[NL80211_BAND_5GHZ];
5863 		} else {
5864 			brcmf_err("Invalid channel Spec. 0x%x.\n", ch.chspec);
5865 			continue;
5866 		}
5867 		if (!band)
5868 			continue;
5869 		if (!(bw_cap[band->band] & WLC_BW_40MHZ_BIT) &&
5870 		    ch.bw == BRCMU_CHAN_BW_40)
5871 			continue;
5872 		if (!(bw_cap[band->band] & WLC_BW_80MHZ_BIT) &&
5873 		    ch.bw == BRCMU_CHAN_BW_80)
5874 			continue;
5875 
5876 		channel = band->channels;
5877 		index = band->n_channels;
5878 		for (j = 0; j < band->n_channels; j++) {
5879 			if (channel[j].hw_value == ch.control_ch_num) {
5880 				index = j;
5881 				break;
5882 			}
5883 		}
5884 		channel[index].center_freq =
5885 			ieee80211_channel_to_frequency(ch.control_ch_num,
5886 						       band->band);
5887 		channel[index].hw_value = ch.control_ch_num;
5888 
5889 		/* assuming the chanspecs order is HT20,
5890 		 * HT40 upper, HT40 lower, and VHT80.
5891 		 */
5892 		if (ch.bw == BRCMU_CHAN_BW_80) {
5893 			channel[index].flags &= ~IEEE80211_CHAN_NO_80MHZ;
5894 		} else if (ch.bw == BRCMU_CHAN_BW_40) {
5895 			brcmf_update_bw40_channel_flag(&channel[index], &ch);
5896 		} else {
5897 			/* enable the channel and disable other bandwidths
5898 			 * for now as mentioned order assure they are enabled
5899 			 * for subsequent chanspecs.
5900 			 */
5901 			channel[index].flags = IEEE80211_CHAN_NO_HT40 |
5902 					       IEEE80211_CHAN_NO_80MHZ;
5903 			ch.bw = BRCMU_CHAN_BW_20;
5904 			cfg->d11inf.encchspec(&ch);
5905 			chaninfo = ch.chspec;
5906 			err = brcmf_fil_bsscfg_int_get(ifp, "per_chan_info",
5907 						       &chaninfo);
5908 			if (!err) {
5909 				if (chaninfo & WL_CHAN_RADAR)
5910 					channel[index].flags |=
5911 						(IEEE80211_CHAN_RADAR |
5912 						 IEEE80211_CHAN_NO_IR);
5913 				if (chaninfo & WL_CHAN_PASSIVE)
5914 					channel[index].flags |=
5915 						IEEE80211_CHAN_NO_IR;
5916 			}
5917 		}
5918 	}
5919 
5920 fail_pbuf:
5921 	kfree(pbuf);
5922 	return err;
5923 }
5924 
5925 static int brcmf_enable_bw40_2g(struct brcmf_cfg80211_info *cfg)
5926 {
5927 	struct brcmf_if *ifp = netdev_priv(cfg_to_ndev(cfg));
5928 	struct ieee80211_supported_band *band;
5929 	struct brcmf_fil_bwcap_le band_bwcap;
5930 	struct brcmf_chanspec_list *list;
5931 	u8 *pbuf;
5932 	u32 val;
5933 	int err;
5934 	struct brcmu_chan ch;
5935 	u32 num_chan;
5936 	int i, j;
5937 
5938 	/* verify support for bw_cap command */
5939 	val = WLC_BAND_5G;
5940 	err = brcmf_fil_iovar_int_get(ifp, "bw_cap", &val);
5941 
5942 	if (!err) {
5943 		/* only set 2G bandwidth using bw_cap command */
5944 		band_bwcap.band = cpu_to_le32(WLC_BAND_2G);
5945 		band_bwcap.bw_cap = cpu_to_le32(WLC_BW_CAP_40MHZ);
5946 		err = brcmf_fil_iovar_data_set(ifp, "bw_cap", &band_bwcap,
5947 					       sizeof(band_bwcap));
5948 	} else {
5949 		brcmf_dbg(INFO, "fallback to mimo_bw_cap\n");
5950 		val = WLC_N_BW_40ALL;
5951 		err = brcmf_fil_iovar_int_set(ifp, "mimo_bw_cap", val);
5952 	}
5953 
5954 	if (!err) {
5955 		/* update channel info in 2G band */
5956 		pbuf = kzalloc(BRCMF_DCMD_MEDLEN, GFP_KERNEL);
5957 
5958 		if (pbuf == NULL)
5959 			return -ENOMEM;
5960 
5961 		ch.band = BRCMU_CHAN_BAND_2G;
5962 		ch.bw = BRCMU_CHAN_BW_40;
5963 		ch.sb = BRCMU_CHAN_SB_NONE;
5964 		ch.chnum = 0;
5965 		cfg->d11inf.encchspec(&ch);
5966 
5967 		/* pass encoded chanspec in query */
5968 		*(__le16 *)pbuf = cpu_to_le16(ch.chspec);
5969 
5970 		err = brcmf_fil_iovar_data_get(ifp, "chanspecs", pbuf,
5971 					       BRCMF_DCMD_MEDLEN);
5972 		if (err) {
5973 			brcmf_err("get chanspecs error (%d)\n", err);
5974 			kfree(pbuf);
5975 			return err;
5976 		}
5977 
5978 		band = cfg_to_wiphy(cfg)->bands[NL80211_BAND_2GHZ];
5979 		list = (struct brcmf_chanspec_list *)pbuf;
5980 		num_chan = le32_to_cpu(list->count);
5981 		for (i = 0; i < num_chan; i++) {
5982 			ch.chspec = (u16)le32_to_cpu(list->element[i]);
5983 			cfg->d11inf.decchspec(&ch);
5984 			if (WARN_ON(ch.band != BRCMU_CHAN_BAND_2G))
5985 				continue;
5986 			if (WARN_ON(ch.bw != BRCMU_CHAN_BW_40))
5987 				continue;
5988 			for (j = 0; j < band->n_channels; j++) {
5989 				if (band->channels[j].hw_value == ch.control_ch_num)
5990 					break;
5991 			}
5992 			if (WARN_ON(j == band->n_channels))
5993 				continue;
5994 
5995 			brcmf_update_bw40_channel_flag(&band->channels[j], &ch);
5996 		}
5997 		kfree(pbuf);
5998 	}
5999 	return err;
6000 }
6001 
6002 static void brcmf_get_bwcap(struct brcmf_if *ifp, u32 bw_cap[])
6003 {
6004 	u32 band, mimo_bwcap;
6005 	int err;
6006 
6007 	band = WLC_BAND_2G;
6008 	err = brcmf_fil_iovar_int_get(ifp, "bw_cap", &band);
6009 	if (!err) {
6010 		bw_cap[NL80211_BAND_2GHZ] = band;
6011 		band = WLC_BAND_5G;
6012 		err = brcmf_fil_iovar_int_get(ifp, "bw_cap", &band);
6013 		if (!err) {
6014 			bw_cap[NL80211_BAND_5GHZ] = band;
6015 			return;
6016 		}
6017 		WARN_ON(1);
6018 		return;
6019 	}
6020 	brcmf_dbg(INFO, "fallback to mimo_bw_cap info\n");
6021 	mimo_bwcap = 0;
6022 	err = brcmf_fil_iovar_int_get(ifp, "mimo_bw_cap", &mimo_bwcap);
6023 	if (err)
6024 		/* assume 20MHz if firmware does not give a clue */
6025 		mimo_bwcap = WLC_N_BW_20ALL;
6026 
6027 	switch (mimo_bwcap) {
6028 	case WLC_N_BW_40ALL:
6029 		bw_cap[NL80211_BAND_2GHZ] |= WLC_BW_40MHZ_BIT;
6030 		/* fall-thru */
6031 	case WLC_N_BW_20IN2G_40IN5G:
6032 		bw_cap[NL80211_BAND_5GHZ] |= WLC_BW_40MHZ_BIT;
6033 		/* fall-thru */
6034 	case WLC_N_BW_20ALL:
6035 		bw_cap[NL80211_BAND_2GHZ] |= WLC_BW_20MHZ_BIT;
6036 		bw_cap[NL80211_BAND_5GHZ] |= WLC_BW_20MHZ_BIT;
6037 		break;
6038 	default:
6039 		brcmf_err("invalid mimo_bw_cap value\n");
6040 	}
6041 }
6042 
6043 static void brcmf_update_ht_cap(struct ieee80211_supported_band *band,
6044 				u32 bw_cap[2], u32 nchain)
6045 {
6046 	band->ht_cap.ht_supported = true;
6047 	if (bw_cap[band->band] & WLC_BW_40MHZ_BIT) {
6048 		band->ht_cap.cap |= IEEE80211_HT_CAP_SGI_40;
6049 		band->ht_cap.cap |= IEEE80211_HT_CAP_SUP_WIDTH_20_40;
6050 	}
6051 	band->ht_cap.cap |= IEEE80211_HT_CAP_SGI_20;
6052 	band->ht_cap.cap |= IEEE80211_HT_CAP_DSSSCCK40;
6053 	band->ht_cap.ampdu_factor = IEEE80211_HT_MAX_AMPDU_64K;
6054 	band->ht_cap.ampdu_density = IEEE80211_HT_MPDU_DENSITY_16;
6055 	memset(band->ht_cap.mcs.rx_mask, 0xff, nchain);
6056 	band->ht_cap.mcs.tx_params = IEEE80211_HT_MCS_TX_DEFINED;
6057 }
6058 
6059 static __le16 brcmf_get_mcs_map(u32 nchain, enum ieee80211_vht_mcs_support supp)
6060 {
6061 	u16 mcs_map;
6062 	int i;
6063 
6064 	for (i = 0, mcs_map = 0xFFFF; i < nchain; i++)
6065 		mcs_map = (mcs_map << 2) | supp;
6066 
6067 	return cpu_to_le16(mcs_map);
6068 }
6069 
6070 static void brcmf_update_vht_cap(struct ieee80211_supported_band *band,
6071 				 u32 bw_cap[2], u32 nchain, u32 txstreams,
6072 				 u32 txbf_bfe_cap, u32 txbf_bfr_cap)
6073 {
6074 	__le16 mcs_map;
6075 
6076 	/* not allowed in 2.4G band */
6077 	if (band->band == NL80211_BAND_2GHZ)
6078 		return;
6079 
6080 	band->vht_cap.vht_supported = true;
6081 	/* 80MHz is mandatory */
6082 	band->vht_cap.cap |= IEEE80211_VHT_CAP_SHORT_GI_80;
6083 	if (bw_cap[band->band] & WLC_BW_160MHZ_BIT) {
6084 		band->vht_cap.cap |= IEEE80211_VHT_CAP_SUPP_CHAN_WIDTH_160MHZ;
6085 		band->vht_cap.cap |= IEEE80211_VHT_CAP_SHORT_GI_160;
6086 	}
6087 	/* all support 256-QAM */
6088 	mcs_map = brcmf_get_mcs_map(nchain, IEEE80211_VHT_MCS_SUPPORT_0_9);
6089 	band->vht_cap.vht_mcs.rx_mcs_map = mcs_map;
6090 	band->vht_cap.vht_mcs.tx_mcs_map = mcs_map;
6091 
6092 	/* Beamforming support information */
6093 	if (txbf_bfe_cap & BRCMF_TXBF_SU_BFE_CAP)
6094 		band->vht_cap.cap |= IEEE80211_VHT_CAP_SU_BEAMFORMEE_CAPABLE;
6095 	if (txbf_bfe_cap & BRCMF_TXBF_MU_BFE_CAP)
6096 		band->vht_cap.cap |= IEEE80211_VHT_CAP_MU_BEAMFORMEE_CAPABLE;
6097 	if (txbf_bfr_cap & BRCMF_TXBF_SU_BFR_CAP)
6098 		band->vht_cap.cap |= IEEE80211_VHT_CAP_SU_BEAMFORMER_CAPABLE;
6099 	if (txbf_bfr_cap & BRCMF_TXBF_MU_BFR_CAP)
6100 		band->vht_cap.cap |= IEEE80211_VHT_CAP_MU_BEAMFORMER_CAPABLE;
6101 
6102 	if ((txbf_bfe_cap || txbf_bfr_cap) && (txstreams > 1)) {
6103 		band->vht_cap.cap |=
6104 			(2 << IEEE80211_VHT_CAP_BEAMFORMEE_STS_SHIFT);
6105 		band->vht_cap.cap |= ((txstreams - 1) <<
6106 				IEEE80211_VHT_CAP_SOUNDING_DIMENSIONS_SHIFT);
6107 		band->vht_cap.cap |=
6108 			IEEE80211_VHT_CAP_VHT_LINK_ADAPTATION_VHT_MRQ_MFB;
6109 	}
6110 }
6111 
6112 static int brcmf_setup_wiphybands(struct wiphy *wiphy)
6113 {
6114 	struct brcmf_cfg80211_info *cfg = wiphy_priv(wiphy);
6115 	struct brcmf_if *ifp = netdev_priv(cfg_to_ndev(cfg));
6116 	u32 nmode = 0;
6117 	u32 vhtmode = 0;
6118 	u32 bw_cap[2] = { WLC_BW_20MHZ_BIT, WLC_BW_20MHZ_BIT };
6119 	u32 rxchain;
6120 	u32 nchain;
6121 	int err;
6122 	s32 i;
6123 	struct ieee80211_supported_band *band;
6124 	u32 txstreams = 0;
6125 	u32 txbf_bfe_cap = 0;
6126 	u32 txbf_bfr_cap = 0;
6127 
6128 	(void)brcmf_fil_iovar_int_get(ifp, "vhtmode", &vhtmode);
6129 	err = brcmf_fil_iovar_int_get(ifp, "nmode", &nmode);
6130 	if (err) {
6131 		brcmf_err("nmode error (%d)\n", err);
6132 	} else {
6133 		brcmf_get_bwcap(ifp, bw_cap);
6134 	}
6135 	brcmf_dbg(INFO, "nmode=%d, vhtmode=%d, bw_cap=(%d, %d)\n",
6136 		  nmode, vhtmode, bw_cap[NL80211_BAND_2GHZ],
6137 		  bw_cap[NL80211_BAND_5GHZ]);
6138 
6139 	err = brcmf_fil_iovar_int_get(ifp, "rxchain", &rxchain);
6140 	if (err) {
6141 		brcmf_err("rxchain error (%d)\n", err);
6142 		nchain = 1;
6143 	} else {
6144 		for (nchain = 0; rxchain; nchain++)
6145 			rxchain = rxchain & (rxchain - 1);
6146 	}
6147 	brcmf_dbg(INFO, "nchain=%d\n", nchain);
6148 
6149 	err = brcmf_construct_chaninfo(cfg, bw_cap);
6150 	if (err) {
6151 		brcmf_err("brcmf_construct_chaninfo failed (%d)\n", err);
6152 		return err;
6153 	}
6154 
6155 	if (vhtmode) {
6156 		(void)brcmf_fil_iovar_int_get(ifp, "txstreams", &txstreams);
6157 		(void)brcmf_fil_iovar_int_get(ifp, "txbf_bfe_cap",
6158 					      &txbf_bfe_cap);
6159 		(void)brcmf_fil_iovar_int_get(ifp, "txbf_bfr_cap",
6160 					      &txbf_bfr_cap);
6161 	}
6162 
6163 	wiphy = cfg_to_wiphy(cfg);
6164 	for (i = 0; i < ARRAY_SIZE(wiphy->bands); i++) {
6165 		band = wiphy->bands[i];
6166 		if (band == NULL)
6167 			continue;
6168 
6169 		if (nmode)
6170 			brcmf_update_ht_cap(band, bw_cap, nchain);
6171 		if (vhtmode)
6172 			brcmf_update_vht_cap(band, bw_cap, nchain, txstreams,
6173 					     txbf_bfe_cap, txbf_bfr_cap);
6174 	}
6175 
6176 	return 0;
6177 }
6178 
6179 static const struct ieee80211_txrx_stypes
6180 brcmf_txrx_stypes[NUM_NL80211_IFTYPES] = {
6181 	[NL80211_IFTYPE_STATION] = {
6182 		.tx = 0xffff,
6183 		.rx = BIT(IEEE80211_STYPE_ACTION >> 4) |
6184 		      BIT(IEEE80211_STYPE_PROBE_REQ >> 4)
6185 	},
6186 	[NL80211_IFTYPE_P2P_CLIENT] = {
6187 		.tx = 0xffff,
6188 		.rx = BIT(IEEE80211_STYPE_ACTION >> 4) |
6189 		      BIT(IEEE80211_STYPE_PROBE_REQ >> 4)
6190 	},
6191 	[NL80211_IFTYPE_P2P_GO] = {
6192 		.tx = 0xffff,
6193 		.rx = BIT(IEEE80211_STYPE_ASSOC_REQ >> 4) |
6194 		      BIT(IEEE80211_STYPE_REASSOC_REQ >> 4) |
6195 		      BIT(IEEE80211_STYPE_PROBE_REQ >> 4) |
6196 		      BIT(IEEE80211_STYPE_DISASSOC >> 4) |
6197 		      BIT(IEEE80211_STYPE_AUTH >> 4) |
6198 		      BIT(IEEE80211_STYPE_DEAUTH >> 4) |
6199 		      BIT(IEEE80211_STYPE_ACTION >> 4)
6200 	},
6201 	[NL80211_IFTYPE_P2P_DEVICE] = {
6202 		.tx = 0xffff,
6203 		.rx = BIT(IEEE80211_STYPE_ACTION >> 4) |
6204 		      BIT(IEEE80211_STYPE_PROBE_REQ >> 4)
6205 	}
6206 };
6207 
6208 /**
6209  * brcmf_setup_ifmodes() - determine interface modes and combinations.
6210  *
6211  * @wiphy: wiphy object.
6212  * @ifp: interface object needed for feat module api.
6213  *
6214  * The interface modes and combinations are determined dynamically here
6215  * based on firmware functionality.
6216  *
6217  * no p2p and no mbss:
6218  *
6219  *	#STA <= 1, #AP <= 1, channels = 1, 2 total
6220  *
6221  * no p2p and mbss:
6222  *
6223  *	#STA <= 1, #AP <= 1, channels = 1, 2 total
6224  *	#AP <= 4, matching BI, channels = 1, 4 total
6225  *
6226  * p2p, no mchan, and mbss:
6227  *
6228  *	#STA <= 1, #P2P-DEV <= 1, #{P2P-CL, P2P-GO} <= 1, channels = 1, 3 total
6229  *	#STA <= 1, #P2P-DEV <= 1, #AP <= 1, #P2P-CL <= 1, channels = 1, 4 total
6230  *	#AP <= 4, matching BI, channels = 1, 4 total
6231  *
6232  * p2p, mchan, and mbss:
6233  *
6234  *	#STA <= 1, #P2P-DEV <= 1, #{P2P-CL, P2P-GO} <= 1, channels = 2, 3 total
6235  *	#STA <= 1, #P2P-DEV <= 1, #AP <= 1, #P2P-CL <= 1, channels = 1, 4 total
6236  *	#AP <= 4, matching BI, channels = 1, 4 total
6237  */
6238 static int brcmf_setup_ifmodes(struct wiphy *wiphy, struct brcmf_if *ifp)
6239 {
6240 	struct ieee80211_iface_combination *combo = NULL;
6241 	struct ieee80211_iface_limit *c0_limits = NULL;
6242 	struct ieee80211_iface_limit *p2p_limits = NULL;
6243 	struct ieee80211_iface_limit *mbss_limits = NULL;
6244 	bool mbss, p2p;
6245 	int i, c, n_combos;
6246 
6247 	mbss = brcmf_feat_is_enabled(ifp, BRCMF_FEAT_MBSS);
6248 	p2p = brcmf_feat_is_enabled(ifp, BRCMF_FEAT_P2P);
6249 
6250 	n_combos = 1 + !!p2p + !!mbss;
6251 	combo = kcalloc(n_combos, sizeof(*combo), GFP_KERNEL);
6252 	if (!combo)
6253 		goto err;
6254 
6255 	wiphy->interface_modes = BIT(NL80211_IFTYPE_STATION) |
6256 				 BIT(NL80211_IFTYPE_ADHOC) |
6257 				 BIT(NL80211_IFTYPE_AP);
6258 
6259 	c = 0;
6260 	i = 0;
6261 	c0_limits = kcalloc(p2p ? 3 : 2, sizeof(*c0_limits), GFP_KERNEL);
6262 	if (!c0_limits)
6263 		goto err;
6264 	c0_limits[i].max = 1;
6265 	c0_limits[i++].types = BIT(NL80211_IFTYPE_STATION);
6266 	if (p2p) {
6267 		if (brcmf_feat_is_enabled(ifp, BRCMF_FEAT_MCHAN))
6268 			combo[c].num_different_channels = 2;
6269 		wiphy->interface_modes |= BIT(NL80211_IFTYPE_P2P_CLIENT) |
6270 					  BIT(NL80211_IFTYPE_P2P_GO) |
6271 					  BIT(NL80211_IFTYPE_P2P_DEVICE);
6272 		c0_limits[i].max = 1;
6273 		c0_limits[i++].types = BIT(NL80211_IFTYPE_P2P_DEVICE);
6274 		c0_limits[i].max = 1;
6275 		c0_limits[i++].types = BIT(NL80211_IFTYPE_P2P_CLIENT) |
6276 				       BIT(NL80211_IFTYPE_P2P_GO);
6277 	} else {
6278 		c0_limits[i].max = 1;
6279 		c0_limits[i++].types = BIT(NL80211_IFTYPE_AP);
6280 	}
6281 	combo[c].num_different_channels = 1;
6282 	combo[c].max_interfaces = i;
6283 	combo[c].n_limits = i;
6284 	combo[c].limits = c0_limits;
6285 
6286 	if (p2p) {
6287 		c++;
6288 		i = 0;
6289 		p2p_limits = kcalloc(4, sizeof(*p2p_limits), GFP_KERNEL);
6290 		if (!p2p_limits)
6291 			goto err;
6292 		p2p_limits[i].max = 1;
6293 		p2p_limits[i++].types = BIT(NL80211_IFTYPE_STATION);
6294 		p2p_limits[i].max = 1;
6295 		p2p_limits[i++].types = BIT(NL80211_IFTYPE_AP);
6296 		p2p_limits[i].max = 1;
6297 		p2p_limits[i++].types = BIT(NL80211_IFTYPE_P2P_CLIENT);
6298 		p2p_limits[i].max = 1;
6299 		p2p_limits[i++].types = BIT(NL80211_IFTYPE_P2P_DEVICE);
6300 		combo[c].num_different_channels = 1;
6301 		combo[c].max_interfaces = i;
6302 		combo[c].n_limits = i;
6303 		combo[c].limits = p2p_limits;
6304 	}
6305 
6306 	if (mbss) {
6307 		c++;
6308 		i = 0;
6309 		mbss_limits = kcalloc(1, sizeof(*mbss_limits), GFP_KERNEL);
6310 		if (!mbss_limits)
6311 			goto err;
6312 		mbss_limits[i].max = 4;
6313 		mbss_limits[i++].types = BIT(NL80211_IFTYPE_AP);
6314 		combo[c].beacon_int_infra_match = true;
6315 		combo[c].num_different_channels = 1;
6316 		combo[c].max_interfaces = 4;
6317 		combo[c].n_limits = i;
6318 		combo[c].limits = mbss_limits;
6319 	}
6320 
6321 	wiphy->n_iface_combinations = n_combos;
6322 	wiphy->iface_combinations = combo;
6323 	return 0;
6324 
6325 err:
6326 	kfree(c0_limits);
6327 	kfree(p2p_limits);
6328 	kfree(mbss_limits);
6329 	kfree(combo);
6330 	return -ENOMEM;
6331 }
6332 
6333 static void brcmf_wiphy_pno_params(struct wiphy *wiphy)
6334 {
6335 	/* scheduled scan settings */
6336 	wiphy->max_sched_scan_ssids = BRCMF_PNO_MAX_PFN_COUNT;
6337 	wiphy->max_match_sets = BRCMF_PNO_MAX_PFN_COUNT;
6338 	wiphy->max_sched_scan_ie_len = BRCMF_SCAN_IE_LEN_MAX;
6339 	wiphy->max_sched_scan_plan_interval = BRCMF_PNO_SCHED_SCAN_MAX_PERIOD;
6340 	wiphy->flags |= WIPHY_FLAG_SUPPORTS_SCHED_SCAN;
6341 }
6342 
6343 #ifdef CONFIG_PM
6344 static struct wiphy_wowlan_support brcmf_wowlan_support = {
6345 	.flags = WIPHY_WOWLAN_MAGIC_PKT | WIPHY_WOWLAN_DISCONNECT,
6346 	.n_patterns = BRCMF_WOWL_MAXPATTERNS,
6347 	.pattern_max_len = BRCMF_WOWL_MAXPATTERNSIZE,
6348 	.pattern_min_len = 1,
6349 	.max_pkt_offset = 1500,
6350 };
6351 #endif
6352 
6353 static void brcmf_wiphy_wowl_params(struct wiphy *wiphy, struct brcmf_if *ifp)
6354 {
6355 #ifdef CONFIG_PM
6356 	struct brcmf_cfg80211_info *cfg = wiphy_to_cfg(wiphy);
6357 
6358 	if (brcmf_feat_is_enabled(ifp, BRCMF_FEAT_PNO)) {
6359 		if (brcmf_feat_is_enabled(ifp, BRCMF_FEAT_WOWL_ND)) {
6360 			brcmf_wowlan_support.flags |= WIPHY_WOWLAN_NET_DETECT;
6361 			init_waitqueue_head(&cfg->wowl.nd_data_wait);
6362 		}
6363 	}
6364 	if (brcmf_feat_is_enabled(ifp, BRCMF_FEAT_WOWL_GTK)) {
6365 		brcmf_wowlan_support.flags |= WIPHY_WOWLAN_SUPPORTS_GTK_REKEY;
6366 		brcmf_wowlan_support.flags |= WIPHY_WOWLAN_GTK_REKEY_FAILURE;
6367 	}
6368 
6369 	wiphy->wowlan = &brcmf_wowlan_support;
6370 #endif
6371 }
6372 
6373 static int brcmf_setup_wiphy(struct wiphy *wiphy, struct brcmf_if *ifp)
6374 {
6375 	struct brcmf_pub *drvr = ifp->drvr;
6376 	const struct ieee80211_iface_combination *combo;
6377 	struct ieee80211_supported_band *band;
6378 	u16 max_interfaces = 0;
6379 	__le32 bandlist[3];
6380 	u32 n_bands;
6381 	int err, i;
6382 
6383 	wiphy->max_scan_ssids = WL_NUM_SCAN_MAX;
6384 	wiphy->max_scan_ie_len = BRCMF_SCAN_IE_LEN_MAX;
6385 	wiphy->max_num_pmkids = BRCMF_MAXPMKID;
6386 
6387 	err = brcmf_setup_ifmodes(wiphy, ifp);
6388 	if (err)
6389 		return err;
6390 
6391 	for (i = 0, combo = wiphy->iface_combinations;
6392 	     i < wiphy->n_iface_combinations; i++, combo++) {
6393 		max_interfaces = max(max_interfaces, combo->max_interfaces);
6394 	}
6395 
6396 	for (i = 0; i < max_interfaces && i < ARRAY_SIZE(drvr->addresses);
6397 	     i++) {
6398 		u8 *addr = drvr->addresses[i].addr;
6399 
6400 		memcpy(addr, drvr->mac, ETH_ALEN);
6401 		if (i) {
6402 			addr[0] |= BIT(1);
6403 			addr[ETH_ALEN - 1] ^= i;
6404 		}
6405 	}
6406 	wiphy->addresses = drvr->addresses;
6407 	wiphy->n_addresses = i;
6408 
6409 	wiphy->signal_type = CFG80211_SIGNAL_TYPE_MBM;
6410 	wiphy->cipher_suites = brcmf_cipher_suites;
6411 	wiphy->n_cipher_suites = ARRAY_SIZE(brcmf_cipher_suites);
6412 	if (!brcmf_feat_is_enabled(ifp, BRCMF_FEAT_MFP))
6413 		wiphy->n_cipher_suites--;
6414 	wiphy->bss_select_support = BIT(NL80211_BSS_SELECT_ATTR_RSSI) |
6415 				    BIT(NL80211_BSS_SELECT_ATTR_BAND_PREF) |
6416 				    BIT(NL80211_BSS_SELECT_ATTR_RSSI_ADJUST);
6417 
6418 	wiphy->flags |= WIPHY_FLAG_PS_ON_BY_DEFAULT |
6419 			WIPHY_FLAG_OFFCHAN_TX |
6420 			WIPHY_FLAG_HAS_REMAIN_ON_CHANNEL;
6421 	if (brcmf_feat_is_enabled(ifp, BRCMF_FEAT_TDLS))
6422 		wiphy->flags |= WIPHY_FLAG_SUPPORTS_TDLS;
6423 	if (!ifp->drvr->settings->roamoff)
6424 		wiphy->flags |= WIPHY_FLAG_SUPPORTS_FW_ROAM;
6425 	wiphy->mgmt_stypes = brcmf_txrx_stypes;
6426 	wiphy->max_remain_on_channel_duration = 5000;
6427 	if (brcmf_feat_is_enabled(ifp, BRCMF_FEAT_PNO))
6428 		brcmf_wiphy_pno_params(wiphy);
6429 
6430 	/* vendor commands/events support */
6431 	wiphy->vendor_commands = brcmf_vendor_cmds;
6432 	wiphy->n_vendor_commands = BRCMF_VNDR_CMDS_LAST - 1;
6433 
6434 	if (brcmf_feat_is_enabled(ifp, BRCMF_FEAT_WOWL))
6435 		brcmf_wiphy_wowl_params(wiphy, ifp);
6436 	err = brcmf_fil_cmd_data_get(ifp, BRCMF_C_GET_BANDLIST, &bandlist,
6437 				     sizeof(bandlist));
6438 	if (err) {
6439 		brcmf_err("could not obtain band info: err=%d\n", err);
6440 		return err;
6441 	}
6442 	/* first entry in bandlist is number of bands */
6443 	n_bands = le32_to_cpu(bandlist[0]);
6444 	for (i = 1; i <= n_bands && i < ARRAY_SIZE(bandlist); i++) {
6445 		if (bandlist[i] == cpu_to_le32(WLC_BAND_2G)) {
6446 			band = kmemdup(&__wl_band_2ghz, sizeof(__wl_band_2ghz),
6447 				       GFP_KERNEL);
6448 			if (!band)
6449 				return -ENOMEM;
6450 
6451 			band->channels = kmemdup(&__wl_2ghz_channels,
6452 						 sizeof(__wl_2ghz_channels),
6453 						 GFP_KERNEL);
6454 			if (!band->channels) {
6455 				kfree(band);
6456 				return -ENOMEM;
6457 			}
6458 
6459 			band->n_channels = ARRAY_SIZE(__wl_2ghz_channels);
6460 			wiphy->bands[NL80211_BAND_2GHZ] = band;
6461 		}
6462 		if (bandlist[i] == cpu_to_le32(WLC_BAND_5G)) {
6463 			band = kmemdup(&__wl_band_5ghz, sizeof(__wl_band_5ghz),
6464 				       GFP_KERNEL);
6465 			if (!band)
6466 				return -ENOMEM;
6467 
6468 			band->channels = kmemdup(&__wl_5ghz_channels,
6469 						 sizeof(__wl_5ghz_channels),
6470 						 GFP_KERNEL);
6471 			if (!band->channels) {
6472 				kfree(band);
6473 				return -ENOMEM;
6474 			}
6475 
6476 			band->n_channels = ARRAY_SIZE(__wl_5ghz_channels);
6477 			wiphy->bands[NL80211_BAND_5GHZ] = band;
6478 		}
6479 	}
6480 	err = brcmf_setup_wiphybands(wiphy);
6481 	return err;
6482 }
6483 
6484 static s32 brcmf_config_dongle(struct brcmf_cfg80211_info *cfg)
6485 {
6486 	struct net_device *ndev;
6487 	struct wireless_dev *wdev;
6488 	struct brcmf_if *ifp;
6489 	s32 power_mode;
6490 	s32 err = 0;
6491 
6492 	if (cfg->dongle_up)
6493 		return err;
6494 
6495 	ndev = cfg_to_ndev(cfg);
6496 	wdev = ndev->ieee80211_ptr;
6497 	ifp = netdev_priv(ndev);
6498 
6499 	/* make sure RF is ready for work */
6500 	brcmf_fil_cmd_int_set(ifp, BRCMF_C_UP, 0);
6501 
6502 	brcmf_dongle_scantime(ifp);
6503 
6504 	power_mode = cfg->pwr_save ? PM_FAST : PM_OFF;
6505 	err = brcmf_fil_cmd_int_set(ifp, BRCMF_C_SET_PM, power_mode);
6506 	if (err)
6507 		goto default_conf_out;
6508 	brcmf_dbg(INFO, "power save set to %s\n",
6509 		  (power_mode ? "enabled" : "disabled"));
6510 
6511 	err = brcmf_dongle_roam(ifp);
6512 	if (err)
6513 		goto default_conf_out;
6514 	err = brcmf_cfg80211_change_iface(wdev->wiphy, ndev, wdev->iftype,
6515 					  NULL, NULL);
6516 	if (err)
6517 		goto default_conf_out;
6518 
6519 	brcmf_configure_arp_nd_offload(ifp, true);
6520 
6521 	cfg->dongle_up = true;
6522 default_conf_out:
6523 
6524 	return err;
6525 
6526 }
6527 
6528 static s32 __brcmf_cfg80211_up(struct brcmf_if *ifp)
6529 {
6530 	set_bit(BRCMF_VIF_STATUS_READY, &ifp->vif->sme_state);
6531 
6532 	return brcmf_config_dongle(ifp->drvr->config);
6533 }
6534 
6535 static s32 __brcmf_cfg80211_down(struct brcmf_if *ifp)
6536 {
6537 	struct brcmf_cfg80211_info *cfg = ifp->drvr->config;
6538 
6539 	/*
6540 	 * While going down, if associated with AP disassociate
6541 	 * from AP to save power
6542 	 */
6543 	if (check_vif_up(ifp->vif)) {
6544 		brcmf_link_down(ifp->vif, WLAN_REASON_UNSPECIFIED);
6545 
6546 		/* Make sure WPA_Supplicant receives all the event
6547 		   generated due to DISASSOC call to the fw to keep
6548 		   the state fw and WPA_Supplicant state consistent
6549 		 */
6550 		brcmf_delay(500);
6551 	}
6552 
6553 	brcmf_abort_scanning(cfg);
6554 	clear_bit(BRCMF_VIF_STATUS_READY, &ifp->vif->sme_state);
6555 
6556 	return 0;
6557 }
6558 
6559 s32 brcmf_cfg80211_up(struct net_device *ndev)
6560 {
6561 	struct brcmf_if *ifp = netdev_priv(ndev);
6562 	struct brcmf_cfg80211_info *cfg = ifp->drvr->config;
6563 	s32 err = 0;
6564 
6565 	mutex_lock(&cfg->usr_sync);
6566 	err = __brcmf_cfg80211_up(ifp);
6567 	mutex_unlock(&cfg->usr_sync);
6568 
6569 	return err;
6570 }
6571 
6572 s32 brcmf_cfg80211_down(struct net_device *ndev)
6573 {
6574 	struct brcmf_if *ifp = netdev_priv(ndev);
6575 	struct brcmf_cfg80211_info *cfg = ifp->drvr->config;
6576 	s32 err = 0;
6577 
6578 	mutex_lock(&cfg->usr_sync);
6579 	err = __brcmf_cfg80211_down(ifp);
6580 	mutex_unlock(&cfg->usr_sync);
6581 
6582 	return err;
6583 }
6584 
6585 enum nl80211_iftype brcmf_cfg80211_get_iftype(struct brcmf_if *ifp)
6586 {
6587 	struct wireless_dev *wdev = &ifp->vif->wdev;
6588 
6589 	return wdev->iftype;
6590 }
6591 
6592 bool brcmf_get_vif_state_any(struct brcmf_cfg80211_info *cfg,
6593 			     unsigned long state)
6594 {
6595 	struct brcmf_cfg80211_vif *vif;
6596 
6597 	list_for_each_entry(vif, &cfg->vif_list, list) {
6598 		if (test_bit(state, &vif->sme_state))
6599 			return true;
6600 	}
6601 	return false;
6602 }
6603 
6604 static inline bool vif_event_equals(struct brcmf_cfg80211_vif_event *event,
6605 				    u8 action)
6606 {
6607 	u8 evt_action;
6608 
6609 	spin_lock(&event->vif_event_lock);
6610 	evt_action = event->action;
6611 	spin_unlock(&event->vif_event_lock);
6612 	return evt_action == action;
6613 }
6614 
6615 void brcmf_cfg80211_arm_vif_event(struct brcmf_cfg80211_info *cfg,
6616 				  struct brcmf_cfg80211_vif *vif)
6617 {
6618 	struct brcmf_cfg80211_vif_event *event = &cfg->vif_event;
6619 
6620 	spin_lock(&event->vif_event_lock);
6621 	event->vif = vif;
6622 	event->action = 0;
6623 	spin_unlock(&event->vif_event_lock);
6624 }
6625 
6626 bool brcmf_cfg80211_vif_event_armed(struct brcmf_cfg80211_info *cfg)
6627 {
6628 	struct brcmf_cfg80211_vif_event *event = &cfg->vif_event;
6629 	bool armed;
6630 
6631 	spin_lock(&event->vif_event_lock);
6632 	armed = event->vif != NULL;
6633 	spin_unlock(&event->vif_event_lock);
6634 
6635 	return armed;
6636 }
6637 
6638 int brcmf_cfg80211_wait_vif_event(struct brcmf_cfg80211_info *cfg,
6639 				  u8 action, ulong timeout)
6640 {
6641 	struct brcmf_cfg80211_vif_event *event = &cfg->vif_event;
6642 
6643 	return wait_event_timeout(event->vif_wq,
6644 				  vif_event_equals(event, action), timeout);
6645 }
6646 
6647 static s32 brcmf_translate_country_code(struct brcmf_pub *drvr, char alpha2[2],
6648 					struct brcmf_fil_country_le *ccreq)
6649 {
6650 	struct brcmfmac_pd_cc *country_codes;
6651 	struct brcmfmac_pd_cc_entry *cc;
6652 	s32 found_index;
6653 	int i;
6654 
6655 	country_codes = drvr->settings->country_codes;
6656 	if (!country_codes) {
6657 		brcmf_dbg(TRACE, "No country codes configured for device\n");
6658 		return -EINVAL;
6659 	}
6660 
6661 	if ((alpha2[0] == ccreq->country_abbrev[0]) &&
6662 	    (alpha2[1] == ccreq->country_abbrev[1])) {
6663 		brcmf_dbg(TRACE, "Country code already set\n");
6664 		return -EAGAIN;
6665 	}
6666 
6667 	found_index = -1;
6668 	for (i = 0; i < country_codes->table_size; i++) {
6669 		cc = &country_codes->table[i];
6670 		if ((cc->iso3166[0] == '\0') && (found_index == -1))
6671 			found_index = i;
6672 		if ((cc->iso3166[0] == alpha2[0]) &&
6673 		    (cc->iso3166[1] == alpha2[1])) {
6674 			found_index = i;
6675 			break;
6676 		}
6677 	}
6678 	if (found_index == -1) {
6679 		brcmf_dbg(TRACE, "No country code match found\n");
6680 		return -EINVAL;
6681 	}
6682 	memset(ccreq, 0, sizeof(*ccreq));
6683 	ccreq->rev = cpu_to_le32(country_codes->table[found_index].rev);
6684 	memcpy(ccreq->ccode, country_codes->table[found_index].cc,
6685 	       BRCMF_COUNTRY_BUF_SZ);
6686 	ccreq->country_abbrev[0] = alpha2[0];
6687 	ccreq->country_abbrev[1] = alpha2[1];
6688 	ccreq->country_abbrev[2] = 0;
6689 
6690 	return 0;
6691 }
6692 
6693 static void brcmf_cfg80211_reg_notifier(struct wiphy *wiphy,
6694 					struct regulatory_request *req)
6695 {
6696 	struct brcmf_cfg80211_info *cfg = wiphy_priv(wiphy);
6697 	struct brcmf_if *ifp = netdev_priv(cfg_to_ndev(cfg));
6698 	struct brcmf_fil_country_le ccreq;
6699 	s32 err;
6700 	int i;
6701 
6702 	/* ignore non-ISO3166 country codes */
6703 	for (i = 0; i < sizeof(req->alpha2); i++)
6704 		if (req->alpha2[i] < 'A' || req->alpha2[i] > 'Z') {
6705 			brcmf_err("not a ISO3166 code (0x%02x 0x%02x)\n",
6706 				  req->alpha2[0], req->alpha2[1]);
6707 			return;
6708 		}
6709 
6710 	brcmf_dbg(TRACE, "Enter: initiator=%d, alpha=%c%c\n", req->initiator,
6711 		  req->alpha2[0], req->alpha2[1]);
6712 
6713 	err = brcmf_fil_iovar_data_get(ifp, "country", &ccreq, sizeof(ccreq));
6714 	if (err) {
6715 		brcmf_err("Country code iovar returned err = %d\n", err);
6716 		return;
6717 	}
6718 
6719 	err = brcmf_translate_country_code(ifp->drvr, req->alpha2, &ccreq);
6720 	if (err)
6721 		return;
6722 
6723 	err = brcmf_fil_iovar_data_set(ifp, "country", &ccreq, sizeof(ccreq));
6724 	if (err) {
6725 		brcmf_err("Firmware rejected country setting\n");
6726 		return;
6727 	}
6728 	brcmf_setup_wiphybands(wiphy);
6729 }
6730 
6731 static void brcmf_free_wiphy(struct wiphy *wiphy)
6732 {
6733 	int i;
6734 
6735 	if (!wiphy)
6736 		return;
6737 
6738 	if (wiphy->iface_combinations) {
6739 		for (i = 0; i < wiphy->n_iface_combinations; i++)
6740 			kfree(wiphy->iface_combinations[i].limits);
6741 	}
6742 	kfree(wiphy->iface_combinations);
6743 	if (wiphy->bands[NL80211_BAND_2GHZ]) {
6744 		kfree(wiphy->bands[NL80211_BAND_2GHZ]->channels);
6745 		kfree(wiphy->bands[NL80211_BAND_2GHZ]);
6746 	}
6747 	if (wiphy->bands[NL80211_BAND_5GHZ]) {
6748 		kfree(wiphy->bands[NL80211_BAND_5GHZ]->channels);
6749 		kfree(wiphy->bands[NL80211_BAND_5GHZ]);
6750 	}
6751 	wiphy_free(wiphy);
6752 }
6753 
6754 struct brcmf_cfg80211_info *brcmf_cfg80211_attach(struct brcmf_pub *drvr,
6755 						  struct device *busdev,
6756 						  bool p2pdev_forced)
6757 {
6758 	struct net_device *ndev = brcmf_get_ifp(drvr, 0)->ndev;
6759 	struct brcmf_cfg80211_info *cfg;
6760 	struct wiphy *wiphy;
6761 	struct cfg80211_ops *ops;
6762 	struct brcmf_cfg80211_vif *vif;
6763 	struct brcmf_if *ifp;
6764 	s32 err = 0;
6765 	s32 io_type;
6766 	u16 *cap = NULL;
6767 
6768 	if (!ndev) {
6769 		brcmf_err("ndev is invalid\n");
6770 		return NULL;
6771 	}
6772 
6773 	ops = kmemdup(&brcmf_cfg80211_ops, sizeof(*ops), GFP_KERNEL);
6774 	if (!ops)
6775 		return NULL;
6776 
6777 	ifp = netdev_priv(ndev);
6778 #ifdef CONFIG_PM
6779 	if (brcmf_feat_is_enabled(ifp, BRCMF_FEAT_WOWL_GTK))
6780 		ops->set_rekey_data = brcmf_cfg80211_set_rekey_data;
6781 #endif
6782 	wiphy = wiphy_new(ops, sizeof(struct brcmf_cfg80211_info));
6783 	if (!wiphy) {
6784 		brcmf_err("Could not allocate wiphy device\n");
6785 		return NULL;
6786 	}
6787 	memcpy(wiphy->perm_addr, drvr->mac, ETH_ALEN);
6788 	set_wiphy_dev(wiphy, busdev);
6789 
6790 	cfg = wiphy_priv(wiphy);
6791 	cfg->wiphy = wiphy;
6792 	cfg->ops = ops;
6793 	cfg->pub = drvr;
6794 	init_vif_event(&cfg->vif_event);
6795 	INIT_LIST_HEAD(&cfg->vif_list);
6796 
6797 	vif = brcmf_alloc_vif(cfg, NL80211_IFTYPE_STATION);
6798 	if (IS_ERR(vif))
6799 		goto wiphy_out;
6800 
6801 	vif->ifp = ifp;
6802 	vif->wdev.netdev = ndev;
6803 	ndev->ieee80211_ptr = &vif->wdev;
6804 	SET_NETDEV_DEV(ndev, wiphy_dev(cfg->wiphy));
6805 
6806 	err = wl_init_priv(cfg);
6807 	if (err) {
6808 		brcmf_err("Failed to init iwm_priv (%d)\n", err);
6809 		brcmf_free_vif(vif);
6810 		goto wiphy_out;
6811 	}
6812 	ifp->vif = vif;
6813 
6814 	/* determine d11 io type before wiphy setup */
6815 	err = brcmf_fil_cmd_int_get(ifp, BRCMF_C_GET_VERSION, &io_type);
6816 	if (err) {
6817 		brcmf_err("Failed to get D11 version (%d)\n", err);
6818 		goto priv_out;
6819 	}
6820 	cfg->d11inf.io_type = (u8)io_type;
6821 	brcmu_d11_attach(&cfg->d11inf);
6822 
6823 	err = brcmf_setup_wiphy(wiphy, ifp);
6824 	if (err < 0)
6825 		goto priv_out;
6826 
6827 	brcmf_dbg(INFO, "Registering custom regulatory\n");
6828 	wiphy->reg_notifier = brcmf_cfg80211_reg_notifier;
6829 	wiphy->regulatory_flags |= REGULATORY_CUSTOM_REG;
6830 	wiphy_apply_custom_regulatory(wiphy, &brcmf_regdom);
6831 
6832 	/* firmware defaults to 40MHz disabled in 2G band. We signal
6833 	 * cfg80211 here that we do and have it decide we can enable
6834 	 * it. But first check if device does support 2G operation.
6835 	 */
6836 	if (wiphy->bands[NL80211_BAND_2GHZ]) {
6837 		cap = &wiphy->bands[NL80211_BAND_2GHZ]->ht_cap.cap;
6838 		*cap |= IEEE80211_HT_CAP_SUP_WIDTH_20_40;
6839 	}
6840 	err = wiphy_register(wiphy);
6841 	if (err < 0) {
6842 		brcmf_err("Could not register wiphy device (%d)\n", err);
6843 		goto priv_out;
6844 	}
6845 
6846 	/* If cfg80211 didn't disable 40MHz HT CAP in wiphy_register(),
6847 	 * setup 40MHz in 2GHz band and enable OBSS scanning.
6848 	 */
6849 	if (cap && (*cap & IEEE80211_HT_CAP_SUP_WIDTH_20_40)) {
6850 		err = brcmf_enable_bw40_2g(cfg);
6851 		if (!err)
6852 			err = brcmf_fil_iovar_int_set(ifp, "obss_coex",
6853 						      BRCMF_OBSS_COEX_AUTO);
6854 		else
6855 			*cap &= ~IEEE80211_HT_CAP_SUP_WIDTH_20_40;
6856 	}
6857 	/* p2p might require that "if-events" get processed by fweh. So
6858 	 * activate the already registered event handlers now and activate
6859 	 * the rest when initialization has completed. drvr->config needs to
6860 	 * be assigned before activating events.
6861 	 */
6862 	drvr->config = cfg;
6863 	err = brcmf_fweh_activate_events(ifp);
6864 	if (err) {
6865 		brcmf_err("FWEH activation failed (%d)\n", err);
6866 		goto wiphy_unreg_out;
6867 	}
6868 
6869 	err = brcmf_p2p_attach(cfg, p2pdev_forced);
6870 	if (err) {
6871 		brcmf_err("P2P initialisation failed (%d)\n", err);
6872 		goto wiphy_unreg_out;
6873 	}
6874 	err = brcmf_btcoex_attach(cfg);
6875 	if (err) {
6876 		brcmf_err("BT-coex initialisation failed (%d)\n", err);
6877 		brcmf_p2p_detach(&cfg->p2p);
6878 		goto wiphy_unreg_out;
6879 	}
6880 
6881 	if (brcmf_feat_is_enabled(ifp, BRCMF_FEAT_TDLS)) {
6882 		err = brcmf_fil_iovar_int_set(ifp, "tdls_enable", 1);
6883 		if (err) {
6884 			brcmf_dbg(INFO, "TDLS not enabled (%d)\n", err);
6885 			wiphy->flags &= ~WIPHY_FLAG_SUPPORTS_TDLS;
6886 		} else {
6887 			brcmf_fweh_register(cfg->pub, BRCMF_E_TDLS_PEER_EVENT,
6888 					    brcmf_notify_tdls_peer_event);
6889 		}
6890 	}
6891 
6892 	/* (re-) activate FWEH event handling */
6893 	err = brcmf_fweh_activate_events(ifp);
6894 	if (err) {
6895 		brcmf_err("FWEH activation failed (%d)\n", err);
6896 		goto detach;
6897 	}
6898 
6899 	/* Fill in some of the advertised nl80211 supported features */
6900 	if (brcmf_feat_is_enabled(ifp, BRCMF_FEAT_SCAN_RANDOM_MAC)) {
6901 		wiphy->features |= NL80211_FEATURE_SCHED_SCAN_RANDOM_MAC_ADDR;
6902 #ifdef CONFIG_PM
6903 		if (wiphy->wowlan &&
6904 		    wiphy->wowlan->flags & WIPHY_WOWLAN_NET_DETECT)
6905 			wiphy->features |= NL80211_FEATURE_ND_RANDOM_MAC_ADDR;
6906 #endif
6907 	}
6908 
6909 	return cfg;
6910 
6911 detach:
6912 	brcmf_btcoex_detach(cfg);
6913 	brcmf_p2p_detach(&cfg->p2p);
6914 wiphy_unreg_out:
6915 	wiphy_unregister(cfg->wiphy);
6916 priv_out:
6917 	wl_deinit_priv(cfg);
6918 	brcmf_free_vif(vif);
6919 	ifp->vif = NULL;
6920 wiphy_out:
6921 	brcmf_free_wiphy(wiphy);
6922 	kfree(ops);
6923 	return NULL;
6924 }
6925 
6926 void brcmf_cfg80211_detach(struct brcmf_cfg80211_info *cfg)
6927 {
6928 	if (!cfg)
6929 		return;
6930 
6931 	brcmf_btcoex_detach(cfg);
6932 	wiphy_unregister(cfg->wiphy);
6933 	kfree(cfg->ops);
6934 	wl_deinit_priv(cfg);
6935 	brcmf_free_wiphy(cfg->wiphy);
6936 }
6937