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