1/*
2 * Marvell Wireless LAN device driver: CFG80211
3 *
4 * Copyright (C) 2011-2014, Marvell International Ltd.
5 *
6 * This software file (the "File") is distributed by Marvell International
7 * Ltd. under the terms of the GNU General Public License Version 2, June 1991
8 * (the "License").  You may use, redistribute and/or modify this File in
9 * accordance with the terms and conditions of the License, a copy of which
10 * is available by writing to the Free Software Foundation, Inc.,
11 * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA or on the
12 * worldwide web at http://www.gnu.org/licenses/old-licenses/gpl-2.0.txt.
13 *
14 * THE FILE IS DISTRIBUTED AS-IS, WITHOUT WARRANTY OF ANY KIND, AND THE
15 * IMPLIED WARRANTIES OF MERCHANTABILITY OR FITNESS FOR A PARTICULAR PURPOSE
16 * ARE EXPRESSLY DISCLAIMED.  The License provides additional details about
17 * this warranty disclaimer.
18 */
19
20#include "cfg80211.h"
21#include "main.h"
22
23static char *reg_alpha2;
24module_param(reg_alpha2, charp, 0);
25
26static const struct ieee80211_iface_limit mwifiex_ap_sta_limits[] = {
27	{
28		.max = 2, .types = BIT(NL80211_IFTYPE_STATION) |
29				   BIT(NL80211_IFTYPE_P2P_GO) |
30				   BIT(NL80211_IFTYPE_P2P_CLIENT),
31	},
32	{
33		.max = 1, .types = BIT(NL80211_IFTYPE_AP),
34	},
35};
36
37static const struct ieee80211_iface_combination mwifiex_iface_comb_ap_sta = {
38	.limits = mwifiex_ap_sta_limits,
39	.num_different_channels = 1,
40	.n_limits = ARRAY_SIZE(mwifiex_ap_sta_limits),
41	.max_interfaces = MWIFIEX_MAX_BSS_NUM,
42	.beacon_int_infra_match = true,
43};
44
45/*
46 * This function maps the nl802.11 channel type into driver channel type.
47 *
48 * The mapping is as follows -
49 *      NL80211_CHAN_NO_HT     -> IEEE80211_HT_PARAM_CHA_SEC_NONE
50 *      NL80211_CHAN_HT20      -> IEEE80211_HT_PARAM_CHA_SEC_NONE
51 *      NL80211_CHAN_HT40PLUS  -> IEEE80211_HT_PARAM_CHA_SEC_ABOVE
52 *      NL80211_CHAN_HT40MINUS -> IEEE80211_HT_PARAM_CHA_SEC_BELOW
53 *      Others                 -> IEEE80211_HT_PARAM_CHA_SEC_NONE
54 */
55u8 mwifiex_chan_type_to_sec_chan_offset(enum nl80211_channel_type chan_type)
56{
57	switch (chan_type) {
58	case NL80211_CHAN_NO_HT:
59	case NL80211_CHAN_HT20:
60		return IEEE80211_HT_PARAM_CHA_SEC_NONE;
61	case NL80211_CHAN_HT40PLUS:
62		return IEEE80211_HT_PARAM_CHA_SEC_ABOVE;
63	case NL80211_CHAN_HT40MINUS:
64		return IEEE80211_HT_PARAM_CHA_SEC_BELOW;
65	default:
66		return IEEE80211_HT_PARAM_CHA_SEC_NONE;
67	}
68}
69
70/*
71 * This function checks whether WEP is set.
72 */
73static int
74mwifiex_is_alg_wep(u32 cipher)
75{
76	switch (cipher) {
77	case WLAN_CIPHER_SUITE_WEP40:
78	case WLAN_CIPHER_SUITE_WEP104:
79		return 1;
80	default:
81		break;
82	}
83
84	return 0;
85}
86
87/*
88 * This function retrieves the private structure from kernel wiphy structure.
89 */
90static void *mwifiex_cfg80211_get_adapter(struct wiphy *wiphy)
91{
92	return (void *) (*(unsigned long *) wiphy_priv(wiphy));
93}
94
95/*
96 * CFG802.11 operation handler to delete a network key.
97 */
98static int
99mwifiex_cfg80211_del_key(struct wiphy *wiphy, struct net_device *netdev,
100			 u8 key_index, bool pairwise, const u8 *mac_addr)
101{
102	struct mwifiex_private *priv = mwifiex_netdev_get_priv(netdev);
103	const u8 bc_mac[] = {0xff, 0xff, 0xff, 0xff, 0xff, 0xff};
104	const u8 *peer_mac = pairwise ? mac_addr : bc_mac;
105
106	if (mwifiex_set_encode(priv, NULL, NULL, 0, key_index, peer_mac, 1)) {
107		wiphy_err(wiphy, "deleting the crypto keys\n");
108		return -EFAULT;
109	}
110
111	wiphy_dbg(wiphy, "info: crypto keys deleted\n");
112	return 0;
113}
114
115/*
116 * This function forms an skb for management frame.
117 */
118static int
119mwifiex_form_mgmt_frame(struct sk_buff *skb, const u8 *buf, size_t len)
120{
121	u8 addr[ETH_ALEN] = {0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF};
122	u16 pkt_len;
123	u32 tx_control = 0, pkt_type = PKT_TYPE_MGMT;
124
125	pkt_len = len + ETH_ALEN;
126
127	skb_reserve(skb, MWIFIEX_MIN_DATA_HEADER_LEN +
128		    MWIFIEX_MGMT_FRAME_HEADER_SIZE + sizeof(pkt_len));
129	memcpy(skb_push(skb, sizeof(pkt_len)), &pkt_len, sizeof(pkt_len));
130
131	memcpy(skb_push(skb, sizeof(tx_control)),
132	       &tx_control, sizeof(tx_control));
133
134	memcpy(skb_push(skb, sizeof(pkt_type)), &pkt_type, sizeof(pkt_type));
135
136	/* Add packet data and address4 */
137	memcpy(skb_put(skb, sizeof(struct ieee80211_hdr_3addr)), buf,
138	       sizeof(struct ieee80211_hdr_3addr));
139	memcpy(skb_put(skb, ETH_ALEN), addr, ETH_ALEN);
140	memcpy(skb_put(skb, len - sizeof(struct ieee80211_hdr_3addr)),
141	       buf + sizeof(struct ieee80211_hdr_3addr),
142	       len - sizeof(struct ieee80211_hdr_3addr));
143
144	skb->priority = LOW_PRIO_TID;
145	__net_timestamp(skb);
146
147	return 0;
148}
149
150/*
151 * CFG802.11 operation handler to transmit a management frame.
152 */
153static int
154mwifiex_cfg80211_mgmt_tx(struct wiphy *wiphy, struct wireless_dev *wdev,
155			 struct cfg80211_mgmt_tx_params *params, u64 *cookie)
156{
157	const u8 *buf = params->buf;
158	size_t len = params->len;
159	struct sk_buff *skb;
160	u16 pkt_len;
161	const struct ieee80211_mgmt *mgmt;
162	struct mwifiex_txinfo *tx_info;
163	struct mwifiex_private *priv = mwifiex_netdev_get_priv(wdev->netdev);
164
165	if (!buf || !len) {
166		wiphy_err(wiphy, "invalid buffer and length\n");
167		return -EFAULT;
168	}
169
170	mgmt = (const struct ieee80211_mgmt *)buf;
171	if (GET_BSS_ROLE(priv) != MWIFIEX_BSS_ROLE_STA &&
172	    ieee80211_is_probe_resp(mgmt->frame_control)) {
173		/* Since we support offload probe resp, we need to skip probe
174		 * resp in AP or GO mode */
175		wiphy_dbg(wiphy,
176			  "info: skip to send probe resp in AP or GO mode\n");
177		return 0;
178	}
179
180	pkt_len = len + ETH_ALEN;
181	skb = dev_alloc_skb(MWIFIEX_MIN_DATA_HEADER_LEN +
182			    MWIFIEX_MGMT_FRAME_HEADER_SIZE +
183			    pkt_len + sizeof(pkt_len));
184
185	if (!skb) {
186		wiphy_err(wiphy, "allocate skb failed for management frame\n");
187		return -ENOMEM;
188	}
189
190	tx_info = MWIFIEX_SKB_TXCB(skb);
191	memset(tx_info, 0, sizeof(*tx_info));
192	tx_info->bss_num = priv->bss_num;
193	tx_info->bss_type = priv->bss_type;
194	tx_info->pkt_len = pkt_len;
195
196	mwifiex_form_mgmt_frame(skb, buf, len);
197	*cookie = prandom_u32() | 1;
198
199	if (ieee80211_is_action(mgmt->frame_control))
200		skb = mwifiex_clone_skb_for_tx_status(priv,
201						      skb,
202				MWIFIEX_BUF_FLAG_ACTION_TX_STATUS, cookie);
203	else
204		cfg80211_mgmt_tx_status(wdev, *cookie, buf, len, true,
205					GFP_ATOMIC);
206
207	mwifiex_queue_tx_pkt(priv, skb);
208
209	wiphy_dbg(wiphy, "info: management frame transmitted\n");
210	return 0;
211}
212
213/*
214 * CFG802.11 operation handler to register a mgmt frame.
215 */
216static void
217mwifiex_cfg80211_mgmt_frame_register(struct wiphy *wiphy,
218				     struct wireless_dev *wdev,
219				     u16 frame_type, bool reg)
220{
221	struct mwifiex_private *priv = mwifiex_netdev_get_priv(wdev->netdev);
222	u32 mask;
223
224	if (reg)
225		mask = priv->mgmt_frame_mask | BIT(frame_type >> 4);
226	else
227		mask = priv->mgmt_frame_mask & ~BIT(frame_type >> 4);
228
229	if (mask != priv->mgmt_frame_mask) {
230		priv->mgmt_frame_mask = mask;
231		mwifiex_send_cmd(priv, HostCmd_CMD_MGMT_FRAME_REG,
232				 HostCmd_ACT_GEN_SET, 0,
233				 &priv->mgmt_frame_mask, false);
234		wiphy_dbg(wiphy, "info: mgmt frame registered\n");
235	}
236}
237
238/*
239 * CFG802.11 operation handler to remain on channel.
240 */
241static int
242mwifiex_cfg80211_remain_on_channel(struct wiphy *wiphy,
243				   struct wireless_dev *wdev,
244				   struct ieee80211_channel *chan,
245				   unsigned int duration, u64 *cookie)
246{
247	struct mwifiex_private *priv = mwifiex_netdev_get_priv(wdev->netdev);
248	int ret;
249
250	if (!chan || !cookie) {
251		wiphy_err(wiphy, "Invalid parameter for ROC\n");
252		return -EINVAL;
253	}
254
255	if (priv->roc_cfg.cookie) {
256		wiphy_dbg(wiphy, "info: ongoing ROC, cookie = 0x%llx\n",
257			  priv->roc_cfg.cookie);
258		return -EBUSY;
259	}
260
261	ret = mwifiex_remain_on_chan_cfg(priv, HostCmd_ACT_GEN_SET, chan,
262					 duration);
263
264	if (!ret) {
265		*cookie = prandom_u32() | 1;
266		priv->roc_cfg.cookie = *cookie;
267		priv->roc_cfg.chan = *chan;
268
269		cfg80211_ready_on_channel(wdev, *cookie, chan,
270					  duration, GFP_ATOMIC);
271
272		wiphy_dbg(wiphy, "info: ROC, cookie = 0x%llx\n", *cookie);
273	}
274
275	return ret;
276}
277
278/*
279 * CFG802.11 operation handler to cancel remain on channel.
280 */
281static int
282mwifiex_cfg80211_cancel_remain_on_channel(struct wiphy *wiphy,
283					  struct wireless_dev *wdev, u64 cookie)
284{
285	struct mwifiex_private *priv = mwifiex_netdev_get_priv(wdev->netdev);
286	int ret;
287
288	if (cookie != priv->roc_cfg.cookie)
289		return -ENOENT;
290
291	ret = mwifiex_remain_on_chan_cfg(priv, HostCmd_ACT_GEN_REMOVE,
292					 &priv->roc_cfg.chan, 0);
293
294	if (!ret) {
295		cfg80211_remain_on_channel_expired(wdev, cookie,
296						   &priv->roc_cfg.chan,
297						   GFP_ATOMIC);
298
299		memset(&priv->roc_cfg, 0, sizeof(struct mwifiex_roc_cfg));
300
301		wiphy_dbg(wiphy, "info: cancel ROC, cookie = 0x%llx\n", cookie);
302	}
303
304	return ret;
305}
306
307/*
308 * CFG802.11 operation handler to set Tx power.
309 */
310static int
311mwifiex_cfg80211_set_tx_power(struct wiphy *wiphy,
312			      struct wireless_dev *wdev,
313			      enum nl80211_tx_power_setting type,
314			      int mbm)
315{
316	struct mwifiex_adapter *adapter = mwifiex_cfg80211_get_adapter(wiphy);
317	struct mwifiex_private *priv;
318	struct mwifiex_power_cfg power_cfg;
319	int dbm = MBM_TO_DBM(mbm);
320
321	if (type == NL80211_TX_POWER_FIXED) {
322		power_cfg.is_power_auto = 0;
323		power_cfg.power_level = dbm;
324	} else {
325		power_cfg.is_power_auto = 1;
326	}
327
328	priv = mwifiex_get_priv(adapter, MWIFIEX_BSS_ROLE_ANY);
329
330	return mwifiex_set_tx_power(priv, &power_cfg);
331}
332
333/*
334 * CFG802.11 operation handler to set Power Save option.
335 *
336 * The timeout value, if provided, is currently ignored.
337 */
338static int
339mwifiex_cfg80211_set_power_mgmt(struct wiphy *wiphy,
340				struct net_device *dev,
341				bool enabled, int timeout)
342{
343	struct mwifiex_private *priv = mwifiex_netdev_get_priv(dev);
344	u32 ps_mode;
345
346	if (timeout)
347		wiphy_dbg(wiphy,
348			  "info: ignore timeout value for IEEE Power Save\n");
349
350	ps_mode = enabled;
351
352	return mwifiex_drv_set_power(priv, &ps_mode);
353}
354
355/*
356 * CFG802.11 operation handler to set the default network key.
357 */
358static int
359mwifiex_cfg80211_set_default_key(struct wiphy *wiphy, struct net_device *netdev,
360				 u8 key_index, bool unicast,
361				 bool multicast)
362{
363	struct mwifiex_private *priv = mwifiex_netdev_get_priv(netdev);
364
365	/* Return if WEP key not configured */
366	if (!priv->sec_info.wep_enabled)
367		return 0;
368
369	if (priv->bss_type == MWIFIEX_BSS_TYPE_UAP) {
370		priv->wep_key_curr_index = key_index;
371	} else if (mwifiex_set_encode(priv, NULL, NULL, 0, key_index,
372				      NULL, 0)) {
373		wiphy_err(wiphy, "set default Tx key index\n");
374		return -EFAULT;
375	}
376
377	return 0;
378}
379
380/*
381 * CFG802.11 operation handler to add a network key.
382 */
383static int
384mwifiex_cfg80211_add_key(struct wiphy *wiphy, struct net_device *netdev,
385			 u8 key_index, bool pairwise, const u8 *mac_addr,
386			 struct key_params *params)
387{
388	struct mwifiex_private *priv = mwifiex_netdev_get_priv(netdev);
389	struct mwifiex_wep_key *wep_key;
390	const u8 bc_mac[] = {0xff, 0xff, 0xff, 0xff, 0xff, 0xff};
391	const u8 *peer_mac = pairwise ? mac_addr : bc_mac;
392
393	if (GET_BSS_ROLE(priv) == MWIFIEX_BSS_ROLE_UAP &&
394	    (params->cipher == WLAN_CIPHER_SUITE_WEP40 ||
395	     params->cipher == WLAN_CIPHER_SUITE_WEP104)) {
396		if (params->key && params->key_len) {
397			wep_key = &priv->wep_key[key_index];
398			memset(wep_key, 0, sizeof(struct mwifiex_wep_key));
399			memcpy(wep_key->key_material, params->key,
400			       params->key_len);
401			wep_key->key_index = key_index;
402			wep_key->key_length = params->key_len;
403			priv->sec_info.wep_enabled = 1;
404		}
405		return 0;
406	}
407
408	if (mwifiex_set_encode(priv, params, params->key, params->key_len,
409			       key_index, peer_mac, 0)) {
410		wiphy_err(wiphy, "crypto keys added\n");
411		return -EFAULT;
412	}
413
414	return 0;
415}
416
417/*
418 * This function sends domain information to the firmware.
419 *
420 * The following information are passed to the firmware -
421 *      - Country codes
422 *      - Sub bands (first channel, number of channels, maximum Tx power)
423 */
424static int mwifiex_send_domain_info_cmd_fw(struct wiphy *wiphy)
425{
426	u8 no_of_triplet = 0;
427	struct ieee80211_country_ie_triplet *t;
428	u8 no_of_parsed_chan = 0;
429	u8 first_chan = 0, next_chan = 0, max_pwr = 0;
430	u8 i, flag = 0;
431	enum ieee80211_band band;
432	struct ieee80211_supported_band *sband;
433	struct ieee80211_channel *ch;
434	struct mwifiex_adapter *adapter = mwifiex_cfg80211_get_adapter(wiphy);
435	struct mwifiex_private *priv;
436	struct mwifiex_802_11d_domain_reg *domain_info = &adapter->domain_reg;
437
438	/* Set country code */
439	domain_info->country_code[0] = adapter->country_code[0];
440	domain_info->country_code[1] = adapter->country_code[1];
441	domain_info->country_code[2] = ' ';
442
443	band = mwifiex_band_to_radio_type(adapter->config_bands);
444	if (!wiphy->bands[band]) {
445		wiphy_err(wiphy, "11D: setting domain info in FW\n");
446		return -1;
447	}
448
449	sband = wiphy->bands[band];
450
451	for (i = 0; i < sband->n_channels ; i++) {
452		ch = &sband->channels[i];
453		if (ch->flags & IEEE80211_CHAN_DISABLED)
454			continue;
455
456		if (!flag) {
457			flag = 1;
458			first_chan = (u32) ch->hw_value;
459			next_chan = first_chan;
460			max_pwr = ch->max_power;
461			no_of_parsed_chan = 1;
462			continue;
463		}
464
465		if (ch->hw_value == next_chan + 1 &&
466		    ch->max_power == max_pwr) {
467			next_chan++;
468			no_of_parsed_chan++;
469		} else {
470			t = &domain_info->triplet[no_of_triplet];
471			t->chans.first_channel = first_chan;
472			t->chans.num_channels = no_of_parsed_chan;
473			t->chans.max_power = max_pwr;
474			no_of_triplet++;
475			first_chan = (u32) ch->hw_value;
476			next_chan = first_chan;
477			max_pwr = ch->max_power;
478			no_of_parsed_chan = 1;
479		}
480	}
481
482	if (flag) {
483		t = &domain_info->triplet[no_of_triplet];
484		t->chans.first_channel = first_chan;
485		t->chans.num_channels = no_of_parsed_chan;
486		t->chans.max_power = max_pwr;
487		no_of_triplet++;
488	}
489
490	domain_info->no_of_triplet = no_of_triplet;
491
492	priv = mwifiex_get_priv(adapter, MWIFIEX_BSS_ROLE_ANY);
493
494	if (mwifiex_send_cmd(priv, HostCmd_CMD_802_11D_DOMAIN_INFO,
495			     HostCmd_ACT_GEN_SET, 0, NULL, false)) {
496		wiphy_err(wiphy, "11D: setting domain info in FW\n");
497		return -1;
498	}
499
500	return 0;
501}
502
503/*
504 * CFG802.11 regulatory domain callback function.
505 *
506 * This function is called when the regulatory domain is changed due to the
507 * following reasons -
508 *      - Set by driver
509 *      - Set by system core
510 *      - Set by user
511 *      - Set bt Country IE
512 */
513static void mwifiex_reg_notifier(struct wiphy *wiphy,
514				 struct regulatory_request *request)
515{
516	struct mwifiex_adapter *adapter = mwifiex_cfg80211_get_adapter(wiphy);
517	struct mwifiex_private *priv = mwifiex_get_priv(adapter,
518							MWIFIEX_BSS_ROLE_ANY);
519
520	wiphy_dbg(wiphy, "info: cfg80211 regulatory domain callback for %c%c\n",
521		  request->alpha2[0], request->alpha2[1]);
522
523	switch (request->initiator) {
524	case NL80211_REGDOM_SET_BY_DRIVER:
525	case NL80211_REGDOM_SET_BY_CORE:
526	case NL80211_REGDOM_SET_BY_USER:
527	case NL80211_REGDOM_SET_BY_COUNTRY_IE:
528		break;
529	default:
530		wiphy_err(wiphy, "unknown regdom initiator: %d\n",
531			  request->initiator);
532		return;
533	}
534
535	/* Don't send world or same regdom info to firmware */
536	if (strncmp(request->alpha2, "00", 2) &&
537	    strncmp(request->alpha2, adapter->country_code,
538		    sizeof(request->alpha2))) {
539		memcpy(adapter->country_code, request->alpha2,
540		       sizeof(request->alpha2));
541		mwifiex_send_domain_info_cmd_fw(wiphy);
542		mwifiex_dnld_txpwr_table(priv);
543	}
544}
545
546/*
547 * This function sets the fragmentation threshold.
548 *
549 * The fragmentation threshold value must lie between MWIFIEX_FRAG_MIN_VALUE
550 * and MWIFIEX_FRAG_MAX_VALUE.
551 */
552static int
553mwifiex_set_frag(struct mwifiex_private *priv, u32 frag_thr)
554{
555	if (frag_thr < MWIFIEX_FRAG_MIN_VALUE ||
556	    frag_thr > MWIFIEX_FRAG_MAX_VALUE)
557		frag_thr = MWIFIEX_FRAG_MAX_VALUE;
558
559	return mwifiex_send_cmd(priv, HostCmd_CMD_802_11_SNMP_MIB,
560				HostCmd_ACT_GEN_SET, FRAG_THRESH_I,
561				&frag_thr, true);
562}
563
564/*
565 * This function sets the RTS threshold.
566
567 * The rts value must lie between MWIFIEX_RTS_MIN_VALUE
568 * and MWIFIEX_RTS_MAX_VALUE.
569 */
570static int
571mwifiex_set_rts(struct mwifiex_private *priv, u32 rts_thr)
572{
573	if (rts_thr < MWIFIEX_RTS_MIN_VALUE || rts_thr > MWIFIEX_RTS_MAX_VALUE)
574		rts_thr = MWIFIEX_RTS_MAX_VALUE;
575
576	return mwifiex_send_cmd(priv, HostCmd_CMD_802_11_SNMP_MIB,
577				HostCmd_ACT_GEN_SET, RTS_THRESH_I,
578				&rts_thr, true);
579}
580
581/*
582 * CFG802.11 operation handler to set wiphy parameters.
583 *
584 * This function can be used to set the RTS threshold and the
585 * Fragmentation threshold of the driver.
586 */
587static int
588mwifiex_cfg80211_set_wiphy_params(struct wiphy *wiphy, u32 changed)
589{
590	struct mwifiex_adapter *adapter = mwifiex_cfg80211_get_adapter(wiphy);
591	struct mwifiex_private *priv;
592	struct mwifiex_uap_bss_param *bss_cfg;
593	int ret;
594
595	priv = mwifiex_get_priv(adapter, MWIFIEX_BSS_ROLE_ANY);
596
597	switch (priv->bss_role) {
598	case MWIFIEX_BSS_ROLE_UAP:
599		if (priv->bss_started) {
600			dev_err(adapter->dev,
601				"cannot change wiphy params when bss started");
602			return -EINVAL;
603		}
604
605		bss_cfg = kzalloc(sizeof(*bss_cfg), GFP_KERNEL);
606		if (!bss_cfg)
607			return -ENOMEM;
608
609		mwifiex_set_sys_config_invalid_data(bss_cfg);
610
611		if (changed & WIPHY_PARAM_RTS_THRESHOLD)
612			bss_cfg->rts_threshold = wiphy->rts_threshold;
613		if (changed & WIPHY_PARAM_FRAG_THRESHOLD)
614			bss_cfg->frag_threshold = wiphy->frag_threshold;
615		if (changed & WIPHY_PARAM_RETRY_LONG)
616			bss_cfg->retry_limit = wiphy->retry_long;
617
618		ret = mwifiex_send_cmd(priv, HostCmd_CMD_UAP_SYS_CONFIG,
619				       HostCmd_ACT_GEN_SET,
620				       UAP_BSS_PARAMS_I, bss_cfg,
621				       false);
622
623		kfree(bss_cfg);
624		if (ret) {
625			wiphy_err(wiphy, "Failed to set wiphy phy params\n");
626			return ret;
627		}
628		break;
629
630		case MWIFIEX_BSS_ROLE_STA:
631		if (priv->media_connected) {
632			dev_err(adapter->dev,
633				"cannot change wiphy params when connected");
634			return -EINVAL;
635		}
636		if (changed & WIPHY_PARAM_RTS_THRESHOLD) {
637			ret = mwifiex_set_rts(priv,
638					      wiphy->rts_threshold);
639			if (ret)
640				return ret;
641		}
642		if (changed & WIPHY_PARAM_FRAG_THRESHOLD) {
643			ret = mwifiex_set_frag(priv,
644					       wiphy->frag_threshold);
645			if (ret)
646				return ret;
647		}
648		break;
649	}
650
651	return 0;
652}
653
654static int
655mwifiex_cfg80211_deinit_p2p(struct mwifiex_private *priv)
656{
657	u16 mode = P2P_MODE_DISABLE;
658
659	if (mwifiex_send_cmd(priv, HostCmd_CMD_P2P_MODE_CFG,
660			     HostCmd_ACT_GEN_SET, 0, &mode, true))
661		return -1;
662
663	return 0;
664}
665
666/*
667 * This function initializes the functionalities for P2P client.
668 * The P2P client initialization sequence is:
669 * disable -> device -> client
670 */
671static int
672mwifiex_cfg80211_init_p2p_client(struct mwifiex_private *priv)
673{
674	u16 mode;
675
676	if (mwifiex_cfg80211_deinit_p2p(priv))
677		return -1;
678
679	mode = P2P_MODE_DEVICE;
680	if (mwifiex_send_cmd(priv, HostCmd_CMD_P2P_MODE_CFG,
681			     HostCmd_ACT_GEN_SET, 0, &mode, true))
682		return -1;
683
684	mode = P2P_MODE_CLIENT;
685	if (mwifiex_send_cmd(priv, HostCmd_CMD_P2P_MODE_CFG,
686			     HostCmd_ACT_GEN_SET, 0, &mode, true))
687		return -1;
688
689	return 0;
690}
691
692/*
693 * This function initializes the functionalities for P2P GO.
694 * The P2P GO initialization sequence is:
695 * disable -> device -> GO
696 */
697static int
698mwifiex_cfg80211_init_p2p_go(struct mwifiex_private *priv)
699{
700	u16 mode;
701
702	if (mwifiex_cfg80211_deinit_p2p(priv))
703		return -1;
704
705	mode = P2P_MODE_DEVICE;
706	if (mwifiex_send_cmd(priv, HostCmd_CMD_P2P_MODE_CFG,
707			     HostCmd_ACT_GEN_SET, 0, &mode, true))
708		return -1;
709
710	mode = P2P_MODE_GO;
711	if (mwifiex_send_cmd(priv, HostCmd_CMD_P2P_MODE_CFG,
712			     HostCmd_ACT_GEN_SET, 0, &mode, true))
713		return -1;
714
715	return 0;
716}
717
718static int mwifiex_deinit_priv_params(struct mwifiex_private *priv)
719{
720	struct mwifiex_adapter *adapter = priv->adapter;
721	unsigned long flags;
722
723	priv->mgmt_frame_mask = 0;
724	if (mwifiex_send_cmd(priv, HostCmd_CMD_MGMT_FRAME_REG,
725			     HostCmd_ACT_GEN_SET, 0,
726			     &priv->mgmt_frame_mask, false)) {
727		dev_warn(priv->adapter->dev,
728			 "could not unregister mgmt frame rx\n");
729		return -1;
730	}
731
732	mwifiex_deauthenticate(priv, NULL);
733
734	spin_lock_irqsave(&adapter->main_proc_lock, flags);
735	adapter->main_locked = true;
736	if (adapter->mwifiex_processing) {
737		spin_unlock_irqrestore(&adapter->main_proc_lock, flags);
738		flush_workqueue(adapter->workqueue);
739	} else {
740		spin_unlock_irqrestore(&adapter->main_proc_lock, flags);
741	}
742
743	spin_lock_irqsave(&adapter->rx_proc_lock, flags);
744	adapter->rx_locked = true;
745	if (adapter->rx_processing) {
746		spin_unlock_irqrestore(&adapter->rx_proc_lock, flags);
747		flush_workqueue(adapter->rx_workqueue);
748	} else {
749	spin_unlock_irqrestore(&adapter->rx_proc_lock, flags);
750	}
751
752	mwifiex_free_priv(priv);
753	priv->wdev.iftype = NL80211_IFTYPE_UNSPECIFIED;
754	priv->bss_mode = NL80211_IFTYPE_UNSPECIFIED;
755	priv->sec_info.authentication_mode = NL80211_AUTHTYPE_OPEN_SYSTEM;
756
757	return 0;
758}
759
760static int
761mwifiex_init_new_priv_params(struct mwifiex_private *priv,
762			     struct net_device *dev,
763			     enum nl80211_iftype type)
764{
765	struct mwifiex_adapter *adapter = priv->adapter;
766	unsigned long flags;
767
768	mwifiex_init_priv(priv);
769
770	priv->bss_mode = type;
771	priv->wdev.iftype = type;
772
773	mwifiex_init_priv_params(priv, priv->netdev);
774	priv->bss_started = 0;
775
776	switch (type) {
777	case NL80211_IFTYPE_STATION:
778	case NL80211_IFTYPE_ADHOC:
779		priv->bss_role =  MWIFIEX_BSS_ROLE_STA;
780		priv->bss_type = MWIFIEX_BSS_TYPE_STA;
781		break;
782	case NL80211_IFTYPE_P2P_CLIENT:
783	case NL80211_IFTYPE_P2P_GO:
784		priv->bss_role =  MWIFIEX_BSS_ROLE_STA;
785		priv->bss_type = MWIFIEX_BSS_TYPE_P2P;
786		break;
787	case NL80211_IFTYPE_AP:
788		priv->bss_type = MWIFIEX_BSS_TYPE_UAP;
789		priv->bss_role = MWIFIEX_BSS_ROLE_UAP;
790		break;
791	default:
792		dev_err(priv->adapter->dev,
793			"%s: changing to %d not supported\n",
794			dev->name, type);
795		return -EOPNOTSUPP;
796	}
797
798	spin_lock_irqsave(&adapter->main_proc_lock, flags);
799	adapter->main_locked = false;
800	spin_unlock_irqrestore(&adapter->main_proc_lock, flags);
801
802	spin_lock_irqsave(&adapter->rx_proc_lock, flags);
803	adapter->rx_locked = false;
804	spin_unlock_irqrestore(&adapter->rx_proc_lock, flags);
805
806	return 0;
807}
808
809static int
810mwifiex_change_vif_to_p2p(struct net_device *dev,
811			  enum nl80211_iftype curr_iftype,
812			  enum nl80211_iftype type, u32 *flags,
813			  struct vif_params *params)
814{
815	struct mwifiex_private *priv;
816	struct mwifiex_adapter *adapter;
817
818	priv = mwifiex_netdev_get_priv(dev);
819
820	if (!priv)
821		return -1;
822
823	adapter = priv->adapter;
824
825	if (adapter->curr_iface_comb.p2p_intf ==
826	    adapter->iface_limit.p2p_intf) {
827		dev_err(adapter->dev,
828			"cannot create multiple P2P ifaces\n");
829		return -1;
830	}
831
832	dev_dbg(priv->adapter->dev, "%s: changing role to p2p\n", dev->name);
833
834	if (mwifiex_deinit_priv_params(priv))
835		return -1;
836	if (mwifiex_init_new_priv_params(priv, dev, type))
837		return -1;
838
839	switch (type) {
840	case NL80211_IFTYPE_P2P_CLIENT:
841		if (mwifiex_cfg80211_init_p2p_client(priv))
842			return -EFAULT;
843		break;
844	case NL80211_IFTYPE_P2P_GO:
845		if (mwifiex_cfg80211_init_p2p_go(priv))
846			return -EFAULT;
847		break;
848	default:
849		dev_err(priv->adapter->dev,
850			"%s: changing to %d not supported\n",
851			dev->name, type);
852		return -EOPNOTSUPP;
853	}
854
855	if (mwifiex_send_cmd(priv, HostCmd_CMD_SET_BSS_MODE,
856			     HostCmd_ACT_GEN_SET, 0, NULL, true))
857		return -1;
858
859	if (mwifiex_sta_init_cmd(priv, false, false))
860		return -1;
861
862	switch (curr_iftype) {
863	case NL80211_IFTYPE_STATION:
864	case NL80211_IFTYPE_ADHOC:
865		adapter->curr_iface_comb.sta_intf--;
866		break;
867	case NL80211_IFTYPE_AP:
868		adapter->curr_iface_comb.uap_intf--;
869		break;
870	default:
871		break;
872	}
873
874	adapter->curr_iface_comb.p2p_intf++;
875	dev->ieee80211_ptr->iftype = type;
876
877	return 0;
878}
879
880static int
881mwifiex_change_vif_to_sta_adhoc(struct net_device *dev,
882				enum nl80211_iftype curr_iftype,
883				enum nl80211_iftype type, u32 *flags,
884				struct vif_params *params)
885{
886	struct mwifiex_private *priv;
887	struct mwifiex_adapter *adapter;
888
889	priv = mwifiex_netdev_get_priv(dev);
890
891	if (!priv)
892		return -1;
893
894	adapter = priv->adapter;
895
896	if ((curr_iftype != NL80211_IFTYPE_P2P_CLIENT &&
897	     curr_iftype != NL80211_IFTYPE_P2P_GO) &&
898	    (adapter->curr_iface_comb.sta_intf ==
899	     adapter->iface_limit.sta_intf)) {
900		dev_err(adapter->dev,
901			"cannot create multiple station/adhoc ifaces\n");
902		return -1;
903	}
904
905	if (type == NL80211_IFTYPE_STATION)
906		dev_notice(adapter->dev,
907			   "%s: changing role to station\n", dev->name);
908	else
909		dev_notice(adapter->dev,
910			   "%s: changing role to adhoc\n", dev->name);
911
912	if (mwifiex_deinit_priv_params(priv))
913		return -1;
914	if (mwifiex_init_new_priv_params(priv, dev, type))
915		return -1;
916	if (mwifiex_send_cmd(priv, HostCmd_CMD_SET_BSS_MODE,
917			     HostCmd_ACT_GEN_SET, 0, NULL, true))
918		return -1;
919	if (mwifiex_sta_init_cmd(priv, false, false))
920		return -1;
921
922	switch (curr_iftype) {
923	case NL80211_IFTYPE_P2P_CLIENT:
924	case NL80211_IFTYPE_P2P_GO:
925		adapter->curr_iface_comb.p2p_intf--;
926		break;
927	case NL80211_IFTYPE_AP:
928		adapter->curr_iface_comb.uap_intf--;
929		break;
930	default:
931		break;
932	}
933
934	adapter->curr_iface_comb.sta_intf++;
935	dev->ieee80211_ptr->iftype = type;
936	return 0;
937}
938
939static int
940mwifiex_change_vif_to_ap(struct net_device *dev,
941			 enum nl80211_iftype curr_iftype,
942			 enum nl80211_iftype type, u32 *flags,
943			 struct vif_params *params)
944{
945	struct mwifiex_private *priv;
946	struct mwifiex_adapter *adapter;
947
948	priv = mwifiex_netdev_get_priv(dev);
949
950	if (!priv)
951		return -1;
952
953	adapter = priv->adapter;
954
955	if (adapter->curr_iface_comb.uap_intf ==
956	    adapter->iface_limit.uap_intf) {
957		dev_err(adapter->dev,
958			"cannot create multiple AP ifaces\n");
959		return -1;
960	}
961
962	dev_notice(adapter->dev, "%s: changing role to AP\n", dev->name);
963
964	if (mwifiex_deinit_priv_params(priv))
965		return -1;
966	if (mwifiex_init_new_priv_params(priv, dev, type))
967		return -1;
968	if (mwifiex_send_cmd(priv, HostCmd_CMD_SET_BSS_MODE,
969			     HostCmd_ACT_GEN_SET, 0, NULL, true))
970		return -1;
971	if (mwifiex_sta_init_cmd(priv, false, false))
972		return -1;
973
974	switch (curr_iftype) {
975	case NL80211_IFTYPE_P2P_CLIENT:
976	case NL80211_IFTYPE_P2P_GO:
977		adapter->curr_iface_comb.p2p_intf--;
978		break;
979	case NL80211_IFTYPE_STATION:
980	case NL80211_IFTYPE_ADHOC:
981		adapter->curr_iface_comb.sta_intf--;
982		break;
983	default:
984		break;
985	}
986
987	adapter->curr_iface_comb.uap_intf++;
988	dev->ieee80211_ptr->iftype = type;
989	return 0;
990}
991/*
992 * CFG802.11 operation handler to change interface type.
993 */
994static int
995mwifiex_cfg80211_change_virtual_intf(struct wiphy *wiphy,
996				     struct net_device *dev,
997				     enum nl80211_iftype type, u32 *flags,
998				     struct vif_params *params)
999{
1000	struct mwifiex_private *priv = mwifiex_netdev_get_priv(dev);
1001	enum nl80211_iftype curr_iftype = dev->ieee80211_ptr->iftype;
1002
1003	switch (curr_iftype) {
1004	case NL80211_IFTYPE_ADHOC:
1005		switch (type) {
1006		case NL80211_IFTYPE_STATION:
1007			priv->bss_mode = type;
1008			priv->sec_info.authentication_mode =
1009						   NL80211_AUTHTYPE_OPEN_SYSTEM;
1010			dev->ieee80211_ptr->iftype = type;
1011			mwifiex_deauthenticate(priv, NULL);
1012			return mwifiex_send_cmd(priv, HostCmd_CMD_SET_BSS_MODE,
1013						HostCmd_ACT_GEN_SET, 0, NULL,
1014						true);
1015		case NL80211_IFTYPE_P2P_CLIENT:
1016		case NL80211_IFTYPE_P2P_GO:
1017			return mwifiex_change_vif_to_p2p(dev, curr_iftype,
1018							 type, flags, params);
1019		case NL80211_IFTYPE_AP:
1020			return mwifiex_change_vif_to_ap(dev, curr_iftype, type,
1021							flags, params);
1022		case NL80211_IFTYPE_UNSPECIFIED:
1023			wiphy_warn(wiphy, "%s: kept type as IBSS\n", dev->name);
1024		case NL80211_IFTYPE_ADHOC:	/* This shouldn't happen */
1025			return 0;
1026		default:
1027			wiphy_err(wiphy, "%s: changing to %d not supported\n",
1028				  dev->name, type);
1029			return -EOPNOTSUPP;
1030		}
1031		break;
1032	case NL80211_IFTYPE_STATION:
1033		switch (type) {
1034		case NL80211_IFTYPE_ADHOC:
1035			priv->bss_mode = type;
1036			priv->sec_info.authentication_mode =
1037						   NL80211_AUTHTYPE_OPEN_SYSTEM;
1038			dev->ieee80211_ptr->iftype = type;
1039			mwifiex_deauthenticate(priv, NULL);
1040			return mwifiex_send_cmd(priv, HostCmd_CMD_SET_BSS_MODE,
1041						HostCmd_ACT_GEN_SET, 0, NULL,
1042						true);
1043		case NL80211_IFTYPE_P2P_CLIENT:
1044		case NL80211_IFTYPE_P2P_GO:
1045			return mwifiex_change_vif_to_p2p(dev, curr_iftype,
1046							 type, flags, params);
1047		case NL80211_IFTYPE_AP:
1048			return mwifiex_change_vif_to_ap(dev, curr_iftype, type,
1049							flags, params);
1050		case NL80211_IFTYPE_UNSPECIFIED:
1051			wiphy_warn(wiphy, "%s: kept type as STA\n", dev->name);
1052		case NL80211_IFTYPE_STATION:	/* This shouldn't happen */
1053			return 0;
1054		default:
1055			wiphy_err(wiphy, "%s: changing to %d not supported\n",
1056				  dev->name, type);
1057			return -EOPNOTSUPP;
1058		}
1059		break;
1060	case NL80211_IFTYPE_AP:
1061		switch (type) {
1062		case NL80211_IFTYPE_ADHOC:
1063		case NL80211_IFTYPE_STATION:
1064			return mwifiex_change_vif_to_sta_adhoc(dev, curr_iftype,
1065							       type, flags,
1066							       params);
1067			break;
1068		case NL80211_IFTYPE_P2P_CLIENT:
1069		case NL80211_IFTYPE_P2P_GO:
1070			return mwifiex_change_vif_to_p2p(dev, curr_iftype,
1071							 type, flags, params);
1072		case NL80211_IFTYPE_UNSPECIFIED:
1073			wiphy_warn(wiphy, "%s: kept type as AP\n", dev->name);
1074		case NL80211_IFTYPE_AP:		/* This shouldn't happen */
1075			return 0;
1076		default:
1077			wiphy_err(wiphy, "%s: changing to %d not supported\n",
1078				  dev->name, type);
1079			return -EOPNOTSUPP;
1080		}
1081		break;
1082	case NL80211_IFTYPE_P2P_CLIENT:
1083	case NL80211_IFTYPE_P2P_GO:
1084		switch (type) {
1085		case NL80211_IFTYPE_STATION:
1086			if (mwifiex_cfg80211_init_p2p_client(priv))
1087				return -EFAULT;
1088			dev->ieee80211_ptr->iftype = type;
1089			break;
1090		case NL80211_IFTYPE_ADHOC:
1091			if (mwifiex_cfg80211_deinit_p2p(priv))
1092				return -EFAULT;
1093			return mwifiex_change_vif_to_sta_adhoc(dev, curr_iftype,
1094							       type, flags,
1095							       params);
1096			break;
1097		case NL80211_IFTYPE_AP:
1098			if (mwifiex_cfg80211_deinit_p2p(priv))
1099				return -EFAULT;
1100			return mwifiex_change_vif_to_ap(dev, curr_iftype, type,
1101							flags, params);
1102		case NL80211_IFTYPE_UNSPECIFIED:
1103			wiphy_warn(wiphy, "%s: kept type as P2P\n", dev->name);
1104		case NL80211_IFTYPE_P2P_CLIENT:
1105		case NL80211_IFTYPE_P2P_GO:
1106			return 0;
1107		default:
1108			wiphy_err(wiphy, "%s: changing to %d not supported\n",
1109				  dev->name, type);
1110			return -EOPNOTSUPP;
1111		}
1112		break;
1113	default:
1114		wiphy_err(wiphy, "%s: unknown iftype: %d\n",
1115			  dev->name, dev->ieee80211_ptr->iftype);
1116		return -EOPNOTSUPP;
1117	}
1118
1119
1120	return 0;
1121}
1122
1123static void
1124mwifiex_parse_htinfo(struct mwifiex_private *priv, u8 tx_htinfo,
1125		     struct rate_info *rate)
1126{
1127	struct mwifiex_adapter *adapter = priv->adapter;
1128
1129	if (adapter->is_hw_11ac_capable) {
1130		/* bit[1-0]: 00=LG 01=HT 10=VHT */
1131		if (tx_htinfo & BIT(0)) {
1132			/* HT */
1133			rate->mcs = priv->tx_rate;
1134			rate->flags |= RATE_INFO_FLAGS_MCS;
1135		}
1136		if (tx_htinfo & BIT(1)) {
1137			/* VHT */
1138			rate->mcs = priv->tx_rate & 0x0F;
1139			rate->flags |= RATE_INFO_FLAGS_VHT_MCS;
1140		}
1141
1142		if (tx_htinfo & (BIT(1) | BIT(0))) {
1143			/* HT or VHT */
1144			switch (tx_htinfo & (BIT(3) | BIT(2))) {
1145			case 0:
1146				rate->bw = RATE_INFO_BW_20;
1147				break;
1148			case (BIT(2)):
1149				rate->bw = RATE_INFO_BW_40;
1150				break;
1151			case (BIT(3)):
1152				rate->bw = RATE_INFO_BW_80;
1153				break;
1154			case (BIT(3) | BIT(2)):
1155				rate->bw = RATE_INFO_BW_160;
1156				break;
1157			}
1158
1159			if (tx_htinfo & BIT(4))
1160				rate->flags |= RATE_INFO_FLAGS_SHORT_GI;
1161
1162			if ((priv->tx_rate >> 4) == 1)
1163				rate->nss = 2;
1164			else
1165				rate->nss = 1;
1166		}
1167	} else {
1168		/*
1169		 * Bit 0 in tx_htinfo indicates that current Tx rate
1170		 * is 11n rate. Valid MCS index values for us are 0 to 15.
1171		 */
1172		if ((tx_htinfo & BIT(0)) && (priv->tx_rate < 16)) {
1173			rate->mcs = priv->tx_rate;
1174			rate->flags |= RATE_INFO_FLAGS_MCS;
1175			rate->bw = RATE_INFO_BW_20;
1176			if (tx_htinfo & BIT(1))
1177				rate->bw = RATE_INFO_BW_40;
1178			if (tx_htinfo & BIT(2))
1179				rate->flags |= RATE_INFO_FLAGS_SHORT_GI;
1180		}
1181	}
1182}
1183
1184/*
1185 * This function dumps the station information on a buffer.
1186 *
1187 * The following information are shown -
1188 *      - Total bytes transmitted
1189 *      - Total bytes received
1190 *      - Total packets transmitted
1191 *      - Total packets received
1192 *      - Signal quality level
1193 *      - Transmission rate
1194 */
1195static int
1196mwifiex_dump_station_info(struct mwifiex_private *priv,
1197			  struct station_info *sinfo)
1198{
1199	u32 rate;
1200
1201	sinfo->filled = BIT(NL80211_STA_INFO_RX_BYTES) | BIT(NL80211_STA_INFO_TX_BYTES) |
1202			BIT(NL80211_STA_INFO_RX_PACKETS) | BIT(NL80211_STA_INFO_TX_PACKETS) |
1203			BIT(NL80211_STA_INFO_TX_BITRATE) |
1204			BIT(NL80211_STA_INFO_SIGNAL) | BIT(NL80211_STA_INFO_SIGNAL_AVG);
1205
1206	/* Get signal information from the firmware */
1207	if (mwifiex_send_cmd(priv, HostCmd_CMD_RSSI_INFO,
1208			     HostCmd_ACT_GEN_GET, 0, NULL, true)) {
1209		dev_err(priv->adapter->dev, "failed to get signal information\n");
1210		return -EFAULT;
1211	}
1212
1213	if (mwifiex_drv_get_data_rate(priv, &rate)) {
1214		dev_err(priv->adapter->dev, "getting data rate\n");
1215		return -EFAULT;
1216	}
1217
1218	/* Get DTIM period information from firmware */
1219	mwifiex_send_cmd(priv, HostCmd_CMD_802_11_SNMP_MIB,
1220			 HostCmd_ACT_GEN_GET, DTIM_PERIOD_I,
1221			 &priv->dtim_period, true);
1222
1223	mwifiex_parse_htinfo(priv, priv->tx_htinfo, &sinfo->txrate);
1224
1225	sinfo->signal_avg = priv->bcn_rssi_avg;
1226	sinfo->rx_bytes = priv->stats.rx_bytes;
1227	sinfo->tx_bytes = priv->stats.tx_bytes;
1228	sinfo->rx_packets = priv->stats.rx_packets;
1229	sinfo->tx_packets = priv->stats.tx_packets;
1230	sinfo->signal = priv->bcn_rssi_avg;
1231	/* bit rate is in 500 kb/s units. Convert it to 100kb/s units */
1232	sinfo->txrate.legacy = rate * 5;
1233
1234	if (priv->bss_mode == NL80211_IFTYPE_STATION) {
1235		sinfo->filled |= BIT(NL80211_STA_INFO_BSS_PARAM);
1236		sinfo->bss_param.flags = 0;
1237		if (priv->curr_bss_params.bss_descriptor.cap_info_bitmap &
1238						WLAN_CAPABILITY_SHORT_PREAMBLE)
1239			sinfo->bss_param.flags |=
1240					BSS_PARAM_FLAGS_SHORT_PREAMBLE;
1241		if (priv->curr_bss_params.bss_descriptor.cap_info_bitmap &
1242						WLAN_CAPABILITY_SHORT_SLOT_TIME)
1243			sinfo->bss_param.flags |=
1244					BSS_PARAM_FLAGS_SHORT_SLOT_TIME;
1245		sinfo->bss_param.dtim_period = priv->dtim_period;
1246		sinfo->bss_param.beacon_interval =
1247			priv->curr_bss_params.bss_descriptor.beacon_period;
1248	}
1249
1250	return 0;
1251}
1252
1253/*
1254 * CFG802.11 operation handler to get station information.
1255 *
1256 * This function only works in connected mode, and dumps the
1257 * requested station information, if available.
1258 */
1259static int
1260mwifiex_cfg80211_get_station(struct wiphy *wiphy, struct net_device *dev,
1261			     const u8 *mac, struct station_info *sinfo)
1262{
1263	struct mwifiex_private *priv = mwifiex_netdev_get_priv(dev);
1264
1265	if (!priv->media_connected)
1266		return -ENOENT;
1267	if (memcmp(mac, priv->cfg_bssid, ETH_ALEN))
1268		return -ENOENT;
1269
1270	return mwifiex_dump_station_info(priv, sinfo);
1271}
1272
1273/*
1274 * CFG802.11 operation handler to dump station information.
1275 */
1276static int
1277mwifiex_cfg80211_dump_station(struct wiphy *wiphy, struct net_device *dev,
1278			      int idx, u8 *mac, struct station_info *sinfo)
1279{
1280	struct mwifiex_private *priv = mwifiex_netdev_get_priv(dev);
1281
1282	if (!priv->media_connected || idx)
1283		return -ENOENT;
1284
1285	memcpy(mac, priv->cfg_bssid, ETH_ALEN);
1286
1287	return mwifiex_dump_station_info(priv, sinfo);
1288}
1289
1290static int
1291mwifiex_cfg80211_dump_survey(struct wiphy *wiphy, struct net_device *dev,
1292			     int idx, struct survey_info *survey)
1293{
1294	struct mwifiex_private *priv = mwifiex_netdev_get_priv(dev);
1295	struct mwifiex_chan_stats *pchan_stats = priv->adapter->chan_stats;
1296	enum ieee80211_band band;
1297
1298	dev_dbg(priv->adapter->dev, "dump_survey idx=%d\n", idx);
1299
1300	memset(survey, 0, sizeof(struct survey_info));
1301
1302	if ((GET_BSS_ROLE(priv) == MWIFIEX_BSS_ROLE_STA) &&
1303	    priv->media_connected && idx == 0) {
1304			u8 curr_bss_band = priv->curr_bss_params.band;
1305			u32 chan = priv->curr_bss_params.bss_descriptor.channel;
1306
1307			band = mwifiex_band_to_radio_type(curr_bss_band);
1308			survey->channel = ieee80211_get_channel(wiphy,
1309				ieee80211_channel_to_frequency(chan, band));
1310
1311			if (priv->bcn_nf_last) {
1312				survey->filled = SURVEY_INFO_NOISE_DBM;
1313				survey->noise = priv->bcn_nf_last;
1314			}
1315			return 0;
1316	}
1317
1318	if (idx >= priv->adapter->num_in_chan_stats)
1319		return -ENOENT;
1320
1321	if (!pchan_stats[idx].cca_scan_dur)
1322		return 0;
1323
1324	band = pchan_stats[idx].bandcfg;
1325	survey->channel = ieee80211_get_channel(wiphy,
1326	    ieee80211_channel_to_frequency(pchan_stats[idx].chan_num, band));
1327	survey->filled = SURVEY_INFO_NOISE_DBM |
1328			 SURVEY_INFO_TIME |
1329			 SURVEY_INFO_TIME_BUSY;
1330	survey->noise = pchan_stats[idx].noise;
1331	survey->time = pchan_stats[idx].cca_scan_dur;
1332	survey->time_busy = pchan_stats[idx].cca_busy_dur;
1333
1334	return 0;
1335}
1336
1337/* Supported rates to be advertised to the cfg80211 */
1338static struct ieee80211_rate mwifiex_rates[] = {
1339	{.bitrate = 10, .hw_value = 2, },
1340	{.bitrate = 20, .hw_value = 4, },
1341	{.bitrate = 55, .hw_value = 11, },
1342	{.bitrate = 110, .hw_value = 22, },
1343	{.bitrate = 60, .hw_value = 12, },
1344	{.bitrate = 90, .hw_value = 18, },
1345	{.bitrate = 120, .hw_value = 24, },
1346	{.bitrate = 180, .hw_value = 36, },
1347	{.bitrate = 240, .hw_value = 48, },
1348	{.bitrate = 360, .hw_value = 72, },
1349	{.bitrate = 480, .hw_value = 96, },
1350	{.bitrate = 540, .hw_value = 108, },
1351};
1352
1353/* Channel definitions to be advertised to cfg80211 */
1354static struct ieee80211_channel mwifiex_channels_2ghz[] = {
1355	{.center_freq = 2412, .hw_value = 1, },
1356	{.center_freq = 2417, .hw_value = 2, },
1357	{.center_freq = 2422, .hw_value = 3, },
1358	{.center_freq = 2427, .hw_value = 4, },
1359	{.center_freq = 2432, .hw_value = 5, },
1360	{.center_freq = 2437, .hw_value = 6, },
1361	{.center_freq = 2442, .hw_value = 7, },
1362	{.center_freq = 2447, .hw_value = 8, },
1363	{.center_freq = 2452, .hw_value = 9, },
1364	{.center_freq = 2457, .hw_value = 10, },
1365	{.center_freq = 2462, .hw_value = 11, },
1366	{.center_freq = 2467, .hw_value = 12, },
1367	{.center_freq = 2472, .hw_value = 13, },
1368	{.center_freq = 2484, .hw_value = 14, },
1369};
1370
1371static struct ieee80211_supported_band mwifiex_band_2ghz = {
1372	.channels = mwifiex_channels_2ghz,
1373	.n_channels = ARRAY_SIZE(mwifiex_channels_2ghz),
1374	.bitrates = mwifiex_rates,
1375	.n_bitrates = ARRAY_SIZE(mwifiex_rates),
1376};
1377
1378static struct ieee80211_channel mwifiex_channels_5ghz[] = {
1379	{.center_freq = 5040, .hw_value = 8, },
1380	{.center_freq = 5060, .hw_value = 12, },
1381	{.center_freq = 5080, .hw_value = 16, },
1382	{.center_freq = 5170, .hw_value = 34, },
1383	{.center_freq = 5190, .hw_value = 38, },
1384	{.center_freq = 5210, .hw_value = 42, },
1385	{.center_freq = 5230, .hw_value = 46, },
1386	{.center_freq = 5180, .hw_value = 36, },
1387	{.center_freq = 5200, .hw_value = 40, },
1388	{.center_freq = 5220, .hw_value = 44, },
1389	{.center_freq = 5240, .hw_value = 48, },
1390	{.center_freq = 5260, .hw_value = 52, },
1391	{.center_freq = 5280, .hw_value = 56, },
1392	{.center_freq = 5300, .hw_value = 60, },
1393	{.center_freq = 5320, .hw_value = 64, },
1394	{.center_freq = 5500, .hw_value = 100, },
1395	{.center_freq = 5520, .hw_value = 104, },
1396	{.center_freq = 5540, .hw_value = 108, },
1397	{.center_freq = 5560, .hw_value = 112, },
1398	{.center_freq = 5580, .hw_value = 116, },
1399	{.center_freq = 5600, .hw_value = 120, },
1400	{.center_freq = 5620, .hw_value = 124, },
1401	{.center_freq = 5640, .hw_value = 128, },
1402	{.center_freq = 5660, .hw_value = 132, },
1403	{.center_freq = 5680, .hw_value = 136, },
1404	{.center_freq = 5700, .hw_value = 140, },
1405	{.center_freq = 5745, .hw_value = 149, },
1406	{.center_freq = 5765, .hw_value = 153, },
1407	{.center_freq = 5785, .hw_value = 157, },
1408	{.center_freq = 5805, .hw_value = 161, },
1409	{.center_freq = 5825, .hw_value = 165, },
1410};
1411
1412static struct ieee80211_supported_band mwifiex_band_5ghz = {
1413	.channels = mwifiex_channels_5ghz,
1414	.n_channels = ARRAY_SIZE(mwifiex_channels_5ghz),
1415	.bitrates = mwifiex_rates + 4,
1416	.n_bitrates = ARRAY_SIZE(mwifiex_rates) - 4,
1417};
1418
1419
1420/* Supported crypto cipher suits to be advertised to cfg80211 */
1421static const u32 mwifiex_cipher_suites[] = {
1422	WLAN_CIPHER_SUITE_WEP40,
1423	WLAN_CIPHER_SUITE_WEP104,
1424	WLAN_CIPHER_SUITE_TKIP,
1425	WLAN_CIPHER_SUITE_CCMP,
1426	WLAN_CIPHER_SUITE_AES_CMAC,
1427};
1428
1429/* Supported mgmt frame types to be advertised to cfg80211 */
1430static const struct ieee80211_txrx_stypes
1431mwifiex_mgmt_stypes[NUM_NL80211_IFTYPES] = {
1432	[NL80211_IFTYPE_STATION] = {
1433		.tx = BIT(IEEE80211_STYPE_ACTION >> 4) |
1434		      BIT(IEEE80211_STYPE_PROBE_RESP >> 4),
1435		.rx = BIT(IEEE80211_STYPE_ACTION >> 4) |
1436		      BIT(IEEE80211_STYPE_PROBE_REQ >> 4),
1437	},
1438	[NL80211_IFTYPE_AP] = {
1439		.tx = BIT(IEEE80211_STYPE_ACTION >> 4) |
1440		      BIT(IEEE80211_STYPE_PROBE_RESP >> 4),
1441		.rx = BIT(IEEE80211_STYPE_ACTION >> 4) |
1442		      BIT(IEEE80211_STYPE_PROBE_REQ >> 4),
1443	},
1444	[NL80211_IFTYPE_P2P_CLIENT] = {
1445		.tx = BIT(IEEE80211_STYPE_ACTION >> 4) |
1446		      BIT(IEEE80211_STYPE_PROBE_RESP >> 4),
1447		.rx = BIT(IEEE80211_STYPE_ACTION >> 4) |
1448		      BIT(IEEE80211_STYPE_PROBE_REQ >> 4),
1449	},
1450	[NL80211_IFTYPE_P2P_GO] = {
1451		.tx = BIT(IEEE80211_STYPE_ACTION >> 4) |
1452		      BIT(IEEE80211_STYPE_PROBE_RESP >> 4),
1453		.rx = BIT(IEEE80211_STYPE_ACTION >> 4) |
1454		      BIT(IEEE80211_STYPE_PROBE_REQ >> 4),
1455	},
1456};
1457
1458/*
1459 * CFG802.11 operation handler for setting bit rates.
1460 *
1461 * Function configures data rates to firmware using bitrate mask
1462 * provided by cfg80211.
1463 */
1464static int mwifiex_cfg80211_set_bitrate_mask(struct wiphy *wiphy,
1465				struct net_device *dev,
1466				const u8 *peer,
1467				const struct cfg80211_bitrate_mask *mask)
1468{
1469	struct mwifiex_private *priv = mwifiex_netdev_get_priv(dev);
1470	u16 bitmap_rates[MAX_BITMAP_RATES_SIZE];
1471	enum ieee80211_band band;
1472	struct mwifiex_adapter *adapter = priv->adapter;
1473
1474	if (!priv->media_connected) {
1475		dev_err(adapter->dev,
1476			"Can not set Tx data rate in disconnected state\n");
1477		return -EINVAL;
1478	}
1479
1480	band = mwifiex_band_to_radio_type(priv->curr_bss_params.band);
1481
1482	memset(bitmap_rates, 0, sizeof(bitmap_rates));
1483
1484	/* Fill HR/DSSS rates. */
1485	if (band == IEEE80211_BAND_2GHZ)
1486		bitmap_rates[0] = mask->control[band].legacy & 0x000f;
1487
1488	/* Fill OFDM rates */
1489	if (band == IEEE80211_BAND_2GHZ)
1490		bitmap_rates[1] = (mask->control[band].legacy & 0x0ff0) >> 4;
1491	else
1492		bitmap_rates[1] = mask->control[band].legacy;
1493
1494	/* Fill HT MCS rates */
1495	bitmap_rates[2] = mask->control[band].ht_mcs[0];
1496	if (adapter->hw_dev_mcs_support == HT_STREAM_2X2)
1497		bitmap_rates[2] |= mask->control[band].ht_mcs[1] << 8;
1498
1499       /* Fill VHT MCS rates */
1500	if (adapter->fw_api_ver == MWIFIEX_FW_V15) {
1501		bitmap_rates[10] = mask->control[band].vht_mcs[0];
1502		if (adapter->hw_dev_mcs_support == HT_STREAM_2X2)
1503			bitmap_rates[11] = mask->control[band].vht_mcs[1];
1504	}
1505
1506	return mwifiex_send_cmd(priv, HostCmd_CMD_TX_RATE_CFG,
1507				HostCmd_ACT_GEN_SET, 0, bitmap_rates, true);
1508}
1509
1510/*
1511 * CFG802.11 operation handler for connection quality monitoring.
1512 *
1513 * This function subscribes/unsubscribes HIGH_RSSI and LOW_RSSI
1514 * events to FW.
1515 */
1516static int mwifiex_cfg80211_set_cqm_rssi_config(struct wiphy *wiphy,
1517						struct net_device *dev,
1518						s32 rssi_thold, u32 rssi_hyst)
1519{
1520	struct mwifiex_private *priv = mwifiex_netdev_get_priv(dev);
1521	struct mwifiex_ds_misc_subsc_evt subsc_evt;
1522
1523	priv->cqm_rssi_thold = rssi_thold;
1524	priv->cqm_rssi_hyst = rssi_hyst;
1525
1526	memset(&subsc_evt, 0x00, sizeof(struct mwifiex_ds_misc_subsc_evt));
1527	subsc_evt.events = BITMASK_BCN_RSSI_LOW | BITMASK_BCN_RSSI_HIGH;
1528
1529	/* Subscribe/unsubscribe low and high rssi events */
1530	if (rssi_thold && rssi_hyst) {
1531		subsc_evt.action = HostCmd_ACT_BITWISE_SET;
1532		subsc_evt.bcn_l_rssi_cfg.abs_value = abs(rssi_thold);
1533		subsc_evt.bcn_h_rssi_cfg.abs_value = abs(rssi_thold);
1534		subsc_evt.bcn_l_rssi_cfg.evt_freq = 1;
1535		subsc_evt.bcn_h_rssi_cfg.evt_freq = 1;
1536		return mwifiex_send_cmd(priv,
1537					HostCmd_CMD_802_11_SUBSCRIBE_EVENT,
1538					0, 0, &subsc_evt, true);
1539	} else {
1540		subsc_evt.action = HostCmd_ACT_BITWISE_CLR;
1541		return mwifiex_send_cmd(priv,
1542					HostCmd_CMD_802_11_SUBSCRIBE_EVENT,
1543					0, 0, &subsc_evt, true);
1544	}
1545
1546	return 0;
1547}
1548
1549/* cfg80211 operation handler for change_beacon.
1550 * Function retrieves and sets modified management IEs to FW.
1551 */
1552static int mwifiex_cfg80211_change_beacon(struct wiphy *wiphy,
1553					  struct net_device *dev,
1554					  struct cfg80211_beacon_data *data)
1555{
1556	struct mwifiex_private *priv = mwifiex_netdev_get_priv(dev);
1557
1558	if (GET_BSS_ROLE(priv) != MWIFIEX_BSS_ROLE_UAP) {
1559		wiphy_err(wiphy, "%s: bss_type mismatched\n", __func__);
1560		return -EINVAL;
1561	}
1562
1563	if (!priv->bss_started) {
1564		wiphy_err(wiphy, "%s: bss not started\n", __func__);
1565		return -EINVAL;
1566	}
1567
1568	if (mwifiex_set_mgmt_ies(priv, data)) {
1569		wiphy_err(wiphy, "%s: setting mgmt ies failed\n", __func__);
1570		return -EFAULT;
1571	}
1572
1573	return 0;
1574}
1575
1576/* cfg80211 operation handler for del_station.
1577 * Function deauthenticates station which value is provided in mac parameter.
1578 * If mac is NULL/broadcast, all stations in associated station list are
1579 * deauthenticated. If bss is not started or there are no stations in
1580 * associated stations list, no action is taken.
1581 */
1582static int
1583mwifiex_cfg80211_del_station(struct wiphy *wiphy, struct net_device *dev,
1584			     struct station_del_parameters *params)
1585{
1586	struct mwifiex_private *priv = mwifiex_netdev_get_priv(dev);
1587	struct mwifiex_sta_node *sta_node;
1588	u8 deauth_mac[ETH_ALEN];
1589	unsigned long flags;
1590
1591	if (list_empty(&priv->sta_list) || !priv->bss_started)
1592		return 0;
1593
1594	if (!params->mac || is_broadcast_ether_addr(params->mac))
1595		return 0;
1596
1597	wiphy_dbg(wiphy, "%s: mac address %pM\n", __func__, params->mac);
1598
1599	eth_zero_addr(deauth_mac);
1600
1601	spin_lock_irqsave(&priv->sta_list_spinlock, flags);
1602	sta_node = mwifiex_get_sta_entry(priv, params->mac);
1603	if (sta_node)
1604		ether_addr_copy(deauth_mac, params->mac);
1605	spin_unlock_irqrestore(&priv->sta_list_spinlock, flags);
1606
1607	if (is_valid_ether_addr(deauth_mac)) {
1608		if (mwifiex_send_cmd(priv, HostCmd_CMD_UAP_STA_DEAUTH,
1609				     HostCmd_ACT_GEN_SET, 0,
1610				     deauth_mac, true))
1611			return -1;
1612	}
1613
1614	return 0;
1615}
1616
1617static int
1618mwifiex_cfg80211_set_antenna(struct wiphy *wiphy, u32 tx_ant, u32 rx_ant)
1619{
1620	struct mwifiex_adapter *adapter = mwifiex_cfg80211_get_adapter(wiphy);
1621	struct mwifiex_private *priv = mwifiex_get_priv(adapter,
1622							MWIFIEX_BSS_ROLE_ANY);
1623	struct mwifiex_ds_ant_cfg ant_cfg;
1624
1625	if (!tx_ant || !rx_ant)
1626		return -EOPNOTSUPP;
1627
1628	if (adapter->hw_dev_mcs_support != HT_STREAM_2X2) {
1629		/* Not a MIMO chip. User should provide specific antenna number
1630		 * for Tx/Rx path or enable all antennas for diversity
1631		 */
1632		if (tx_ant != rx_ant)
1633			return -EOPNOTSUPP;
1634
1635		if ((tx_ant & (tx_ant - 1)) &&
1636		    (tx_ant != BIT(adapter->number_of_antenna) - 1))
1637			return -EOPNOTSUPP;
1638
1639		if ((tx_ant == BIT(adapter->number_of_antenna) - 1) &&
1640		    (priv->adapter->number_of_antenna > 1)) {
1641			tx_ant = RF_ANTENNA_AUTO;
1642			rx_ant = RF_ANTENNA_AUTO;
1643		}
1644	} else {
1645		struct ieee80211_sta_ht_cap *ht_info;
1646		int rx_mcs_supp;
1647		enum ieee80211_band band;
1648
1649		if ((tx_ant == 0x1 && rx_ant == 0x1)) {
1650			adapter->user_dev_mcs_support = HT_STREAM_1X1;
1651			if (adapter->is_hw_11ac_capable)
1652				adapter->usr_dot_11ac_mcs_support =
1653						MWIFIEX_11AC_MCS_MAP_1X1;
1654		} else {
1655			adapter->user_dev_mcs_support = HT_STREAM_2X2;
1656			if (adapter->is_hw_11ac_capable)
1657				adapter->usr_dot_11ac_mcs_support =
1658						MWIFIEX_11AC_MCS_MAP_2X2;
1659		}
1660
1661		for (band = 0; band < IEEE80211_NUM_BANDS; band++) {
1662			if (!adapter->wiphy->bands[band])
1663				continue;
1664
1665			ht_info = &adapter->wiphy->bands[band]->ht_cap;
1666			rx_mcs_supp =
1667				GET_RXMCSSUPP(adapter->user_dev_mcs_support);
1668			memset(&ht_info->mcs, 0, adapter->number_of_antenna);
1669			memset(&ht_info->mcs, 0xff, rx_mcs_supp);
1670		}
1671	}
1672
1673	ant_cfg.tx_ant = tx_ant;
1674	ant_cfg.rx_ant = rx_ant;
1675
1676	return mwifiex_send_cmd(priv, HostCmd_CMD_RF_ANTENNA,
1677				HostCmd_ACT_GEN_SET, 0, &ant_cfg, true);
1678}
1679
1680/* cfg80211 operation handler for stop ap.
1681 * Function stops BSS running at uAP interface.
1682 */
1683static int mwifiex_cfg80211_stop_ap(struct wiphy *wiphy, struct net_device *dev)
1684{
1685	struct mwifiex_private *priv = mwifiex_netdev_get_priv(dev);
1686
1687	mwifiex_abort_cac(priv);
1688
1689	if (mwifiex_del_mgmt_ies(priv))
1690		wiphy_err(wiphy, "Failed to delete mgmt IEs!\n");
1691
1692	priv->ap_11n_enabled = 0;
1693	memset(&priv->bss_cfg, 0, sizeof(priv->bss_cfg));
1694
1695	if (mwifiex_send_cmd(priv, HostCmd_CMD_UAP_BSS_STOP,
1696			     HostCmd_ACT_GEN_SET, 0, NULL, true)) {
1697		wiphy_err(wiphy, "Failed to stop the BSS\n");
1698		return -1;
1699	}
1700
1701	return 0;
1702}
1703
1704/* cfg80211 operation handler for start_ap.
1705 * Function sets beacon period, DTIM period, SSID and security into
1706 * AP config structure.
1707 * AP is configured with these settings and BSS is started.
1708 */
1709static int mwifiex_cfg80211_start_ap(struct wiphy *wiphy,
1710				     struct net_device *dev,
1711				     struct cfg80211_ap_settings *params)
1712{
1713	struct mwifiex_uap_bss_param *bss_cfg;
1714	struct mwifiex_private *priv = mwifiex_netdev_get_priv(dev);
1715
1716	if (GET_BSS_ROLE(priv) != MWIFIEX_BSS_ROLE_UAP)
1717		return -1;
1718
1719	bss_cfg = kzalloc(sizeof(struct mwifiex_uap_bss_param), GFP_KERNEL);
1720	if (!bss_cfg)
1721		return -ENOMEM;
1722
1723	mwifiex_set_sys_config_invalid_data(bss_cfg);
1724
1725	if (params->beacon_interval)
1726		bss_cfg->beacon_period = params->beacon_interval;
1727	if (params->dtim_period)
1728		bss_cfg->dtim_period = params->dtim_period;
1729
1730	if (params->ssid && params->ssid_len) {
1731		memcpy(bss_cfg->ssid.ssid, params->ssid, params->ssid_len);
1732		bss_cfg->ssid.ssid_len = params->ssid_len;
1733	}
1734	if (params->inactivity_timeout > 0) {
1735		/* sta_ao_timer/ps_sta_ao_timer is in unit of 100ms */
1736		bss_cfg->sta_ao_timer = 10 * params->inactivity_timeout;
1737		bss_cfg->ps_sta_ao_timer = 10 * params->inactivity_timeout;
1738	}
1739
1740	switch (params->hidden_ssid) {
1741	case NL80211_HIDDEN_SSID_NOT_IN_USE:
1742		bss_cfg->bcast_ssid_ctl = 1;
1743		break;
1744	case NL80211_HIDDEN_SSID_ZERO_LEN:
1745		bss_cfg->bcast_ssid_ctl = 0;
1746		break;
1747	case NL80211_HIDDEN_SSID_ZERO_CONTENTS:
1748		/* firmware doesn't support this type of hidden SSID */
1749	default:
1750		kfree(bss_cfg);
1751		return -EINVAL;
1752	}
1753
1754	mwifiex_uap_set_channel(bss_cfg, params->chandef);
1755	mwifiex_set_uap_rates(bss_cfg, params);
1756
1757	if (mwifiex_set_secure_params(priv, bss_cfg, params)) {
1758		kfree(bss_cfg);
1759		wiphy_err(wiphy, "Failed to parse secuirty parameters!\n");
1760		return -1;
1761	}
1762
1763	mwifiex_set_ht_params(priv, bss_cfg, params);
1764
1765	if (priv->adapter->is_hw_11ac_capable) {
1766		mwifiex_set_vht_params(priv, bss_cfg, params);
1767		mwifiex_set_vht_width(priv, params->chandef.width,
1768				      priv->ap_11ac_enabled);
1769	}
1770
1771	if (priv->ap_11ac_enabled)
1772		mwifiex_set_11ac_ba_params(priv);
1773	else
1774		mwifiex_set_ba_params(priv);
1775
1776	mwifiex_set_wmm_params(priv, bss_cfg, params);
1777
1778	if (mwifiex_is_11h_active(priv) &&
1779	    !cfg80211_chandef_dfs_required(wiphy, &params->chandef,
1780					   priv->bss_mode)) {
1781		dev_dbg(priv->adapter->dev, "Disable 11h extensions in FW\n");
1782		if (mwifiex_11h_activate(priv, false)) {
1783			dev_err(priv->adapter->dev,
1784				"Failed to disable 11h extensions!!");
1785			return -1;
1786		}
1787		priv->state_11h.is_11h_active = true;
1788	}
1789
1790	if (mwifiex_config_start_uap(priv, bss_cfg)) {
1791		wiphy_err(wiphy, "Failed to start AP\n");
1792		kfree(bss_cfg);
1793		return -1;
1794	}
1795
1796	if (mwifiex_set_mgmt_ies(priv, &params->beacon))
1797		return -1;
1798
1799	memcpy(&priv->bss_cfg, bss_cfg, sizeof(priv->bss_cfg));
1800	kfree(bss_cfg);
1801	return 0;
1802}
1803
1804/*
1805 * CFG802.11 operation handler for disconnection request.
1806 *
1807 * This function does not work when there is already a disconnection
1808 * procedure going on.
1809 */
1810static int
1811mwifiex_cfg80211_disconnect(struct wiphy *wiphy, struct net_device *dev,
1812			    u16 reason_code)
1813{
1814	struct mwifiex_private *priv = mwifiex_netdev_get_priv(dev);
1815
1816	if (mwifiex_deauthenticate(priv, NULL))
1817		return -EFAULT;
1818
1819	wiphy_dbg(wiphy, "info: successfully disconnected from %pM:"
1820		" reason code %d\n", priv->cfg_bssid, reason_code);
1821
1822	eth_zero_addr(priv->cfg_bssid);
1823	priv->hs2_enabled = false;
1824
1825	return 0;
1826}
1827
1828/*
1829 * This function informs the CFG802.11 subsystem of a new IBSS.
1830 *
1831 * The following information are sent to the CFG802.11 subsystem
1832 * to register the new IBSS. If we do not register the new IBSS,
1833 * a kernel panic will result.
1834 *      - SSID
1835 *      - SSID length
1836 *      - BSSID
1837 *      - Channel
1838 */
1839static int mwifiex_cfg80211_inform_ibss_bss(struct mwifiex_private *priv)
1840{
1841	struct ieee80211_channel *chan;
1842	struct mwifiex_bss_info bss_info;
1843	struct cfg80211_bss *bss;
1844	int ie_len;
1845	u8 ie_buf[IEEE80211_MAX_SSID_LEN + sizeof(struct ieee_types_header)];
1846	enum ieee80211_band band;
1847
1848	if (mwifiex_get_bss_info(priv, &bss_info))
1849		return -1;
1850
1851	ie_buf[0] = WLAN_EID_SSID;
1852	ie_buf[1] = bss_info.ssid.ssid_len;
1853
1854	memcpy(&ie_buf[sizeof(struct ieee_types_header)],
1855	       &bss_info.ssid.ssid, bss_info.ssid.ssid_len);
1856	ie_len = ie_buf[1] + sizeof(struct ieee_types_header);
1857
1858	band = mwifiex_band_to_radio_type(priv->curr_bss_params.band);
1859	chan = __ieee80211_get_channel(priv->wdev.wiphy,
1860			ieee80211_channel_to_frequency(bss_info.bss_chan,
1861						       band));
1862
1863	bss = cfg80211_inform_bss(priv->wdev.wiphy, chan,
1864				  CFG80211_BSS_FTYPE_UNKNOWN,
1865				  bss_info.bssid, 0, WLAN_CAPABILITY_IBSS,
1866				  0, ie_buf, ie_len, 0, GFP_KERNEL);
1867	cfg80211_put_bss(priv->wdev.wiphy, bss);
1868	memcpy(priv->cfg_bssid, bss_info.bssid, ETH_ALEN);
1869
1870	return 0;
1871}
1872
1873/*
1874 * This function connects with a BSS.
1875 *
1876 * This function handles both Infra and Ad-Hoc modes. It also performs
1877 * validity checking on the provided parameters, disconnects from the
1878 * current BSS (if any), sets up the association/scan parameters,
1879 * including security settings, and performs specific SSID scan before
1880 * trying to connect.
1881 *
1882 * For Infra mode, the function returns failure if the specified SSID
1883 * is not found in scan table. However, for Ad-Hoc mode, it can create
1884 * the IBSS if it does not exist. On successful completion in either case,
1885 * the function notifies the CFG802.11 subsystem of the new BSS connection.
1886 */
1887static int
1888mwifiex_cfg80211_assoc(struct mwifiex_private *priv, size_t ssid_len,
1889		       const u8 *ssid, const u8 *bssid, int mode,
1890		       struct ieee80211_channel *channel,
1891		       struct cfg80211_connect_params *sme, bool privacy)
1892{
1893	struct cfg80211_ssid req_ssid;
1894	int ret, auth_type = 0;
1895	struct cfg80211_bss *bss = NULL;
1896	u8 is_scanning_required = 0;
1897
1898	memset(&req_ssid, 0, sizeof(struct cfg80211_ssid));
1899
1900	req_ssid.ssid_len = ssid_len;
1901	if (ssid_len > IEEE80211_MAX_SSID_LEN) {
1902		dev_err(priv->adapter->dev, "invalid SSID - aborting\n");
1903		return -EINVAL;
1904	}
1905
1906	memcpy(req_ssid.ssid, ssid, ssid_len);
1907	if (!req_ssid.ssid_len || req_ssid.ssid[0] < 0x20) {
1908		dev_err(priv->adapter->dev, "invalid SSID - aborting\n");
1909		return -EINVAL;
1910	}
1911
1912	/* As this is new association, clear locally stored
1913	 * keys and security related flags */
1914	priv->sec_info.wpa_enabled = false;
1915	priv->sec_info.wpa2_enabled = false;
1916	priv->wep_key_curr_index = 0;
1917	priv->sec_info.encryption_mode = 0;
1918	priv->sec_info.is_authtype_auto = 0;
1919	ret = mwifiex_set_encode(priv, NULL, NULL, 0, 0, NULL, 1);
1920
1921	if (mode == NL80211_IFTYPE_ADHOC) {
1922		/* "privacy" is set only for ad-hoc mode */
1923		if (privacy) {
1924			/*
1925			 * Keep WLAN_CIPHER_SUITE_WEP104 for now so that
1926			 * the firmware can find a matching network from the
1927			 * scan. The cfg80211 does not give us the encryption
1928			 * mode at this stage so just setting it to WEP here.
1929			 */
1930			priv->sec_info.encryption_mode =
1931					WLAN_CIPHER_SUITE_WEP104;
1932			priv->sec_info.authentication_mode =
1933					NL80211_AUTHTYPE_OPEN_SYSTEM;
1934		}
1935
1936		goto done;
1937	}
1938
1939	/* Now handle infra mode. "sme" is valid for infra mode only */
1940	if (sme->auth_type == NL80211_AUTHTYPE_AUTOMATIC) {
1941		auth_type = NL80211_AUTHTYPE_OPEN_SYSTEM;
1942		priv->sec_info.is_authtype_auto = 1;
1943	} else {
1944		auth_type = sme->auth_type;
1945	}
1946
1947	if (sme->crypto.n_ciphers_pairwise) {
1948		priv->sec_info.encryption_mode =
1949						sme->crypto.ciphers_pairwise[0];
1950		priv->sec_info.authentication_mode = auth_type;
1951	}
1952
1953	if (sme->crypto.cipher_group) {
1954		priv->sec_info.encryption_mode = sme->crypto.cipher_group;
1955		priv->sec_info.authentication_mode = auth_type;
1956	}
1957	if (sme->ie)
1958		ret = mwifiex_set_gen_ie(priv, sme->ie, sme->ie_len);
1959
1960	if (sme->key) {
1961		if (mwifiex_is_alg_wep(priv->sec_info.encryption_mode)) {
1962			dev_dbg(priv->adapter->dev,
1963				"info: setting wep encryption"
1964				" with key len %d\n", sme->key_len);
1965			priv->wep_key_curr_index = sme->key_idx;
1966			ret = mwifiex_set_encode(priv, NULL, sme->key,
1967						 sme->key_len, sme->key_idx,
1968						 NULL, 0);
1969		}
1970	}
1971done:
1972	/*
1973	 * Scan entries are valid for some time (15 sec). So we can save one
1974	 * active scan time if we just try cfg80211_get_bss first. If it fails
1975	 * then request scan and cfg80211_get_bss() again for final output.
1976	 */
1977	while (1) {
1978		if (is_scanning_required) {
1979			/* Do specific SSID scanning */
1980			if (mwifiex_request_scan(priv, &req_ssid)) {
1981				dev_err(priv->adapter->dev, "scan error\n");
1982				return -EFAULT;
1983			}
1984		}
1985
1986		/* Find the BSS we want using available scan results */
1987		if (mode == NL80211_IFTYPE_ADHOC)
1988			bss = cfg80211_get_bss(priv->wdev.wiphy, channel,
1989					       bssid, ssid, ssid_len,
1990					       IEEE80211_BSS_TYPE_IBSS,
1991					       IEEE80211_PRIVACY_ANY);
1992		else
1993			bss = cfg80211_get_bss(priv->wdev.wiphy, channel,
1994					       bssid, ssid, ssid_len,
1995					       IEEE80211_BSS_TYPE_ESS,
1996					       IEEE80211_PRIVACY_ANY);
1997
1998		if (!bss) {
1999			if (is_scanning_required) {
2000				dev_warn(priv->adapter->dev,
2001					 "assoc: requested bss not found in scan results\n");
2002				break;
2003			}
2004			is_scanning_required = 1;
2005		} else {
2006			dev_dbg(priv->adapter->dev,
2007				"info: trying to associate to '%s' bssid %pM\n",
2008				(char *) req_ssid.ssid, bss->bssid);
2009			memcpy(&priv->cfg_bssid, bss->bssid, ETH_ALEN);
2010			break;
2011		}
2012	}
2013
2014	ret = mwifiex_bss_start(priv, bss, &req_ssid);
2015	if (ret)
2016		return ret;
2017
2018	if (mode == NL80211_IFTYPE_ADHOC) {
2019		/* Inform the BSS information to kernel, otherwise
2020		 * kernel will give a panic after successful assoc */
2021		if (mwifiex_cfg80211_inform_ibss_bss(priv))
2022			return -EFAULT;
2023	}
2024
2025	return ret;
2026}
2027
2028/*
2029 * CFG802.11 operation handler for association request.
2030 *
2031 * This function does not work when the current mode is set to Ad-Hoc, or
2032 * when there is already an association procedure going on. The given BSS
2033 * information is used to associate.
2034 */
2035static int
2036mwifiex_cfg80211_connect(struct wiphy *wiphy, struct net_device *dev,
2037			 struct cfg80211_connect_params *sme)
2038{
2039	struct mwifiex_private *priv = mwifiex_netdev_get_priv(dev);
2040	struct mwifiex_adapter *adapter = priv->adapter;
2041	int ret;
2042
2043	if (GET_BSS_ROLE(priv) != MWIFIEX_BSS_ROLE_STA) {
2044		wiphy_err(wiphy,
2045			  "%s: reject infra assoc request in non-STA role\n",
2046			  dev->name);
2047		return -EINVAL;
2048	}
2049
2050	if (priv->wdev.current_bss) {
2051		wiphy_warn(wiphy, "%s: already connected\n", dev->name);
2052		return -EALREADY;
2053	}
2054
2055	if (adapter->surprise_removed || adapter->is_cmd_timedout) {
2056		wiphy_err(wiphy,
2057			  "%s: Ignore connection. Card removed or FW in bad state\n",
2058			  dev->name);
2059		return -EFAULT;
2060	}
2061
2062	wiphy_dbg(wiphy, "info: Trying to associate to %s and bssid %pM\n",
2063		  (char *) sme->ssid, sme->bssid);
2064
2065	ret = mwifiex_cfg80211_assoc(priv, sme->ssid_len, sme->ssid, sme->bssid,
2066				     priv->bss_mode, sme->channel, sme, 0);
2067	if (!ret) {
2068		cfg80211_connect_result(priv->netdev, priv->cfg_bssid, NULL, 0,
2069					NULL, 0, WLAN_STATUS_SUCCESS,
2070					GFP_KERNEL);
2071		dev_dbg(priv->adapter->dev,
2072			"info: associated to bssid %pM successfully\n",
2073			priv->cfg_bssid);
2074		if (ISSUPP_TDLS_ENABLED(priv->adapter->fw_cap_info) &&
2075		    priv->adapter->auto_tdls &&
2076		    priv->bss_type == MWIFIEX_BSS_TYPE_STA)
2077			mwifiex_setup_auto_tdls_timer(priv);
2078	} else {
2079		dev_dbg(priv->adapter->dev,
2080			"info: association to bssid %pM failed\n",
2081			priv->cfg_bssid);
2082		eth_zero_addr(priv->cfg_bssid);
2083
2084		if (ret > 0)
2085			cfg80211_connect_result(priv->netdev, priv->cfg_bssid,
2086						NULL, 0, NULL, 0, ret,
2087						GFP_KERNEL);
2088		else
2089			cfg80211_connect_result(priv->netdev, priv->cfg_bssid,
2090						NULL, 0, NULL, 0,
2091						WLAN_STATUS_UNSPECIFIED_FAILURE,
2092						GFP_KERNEL);
2093	}
2094
2095	return 0;
2096}
2097
2098/*
2099 * This function sets following parameters for ibss network.
2100 *  -  channel
2101 *  -  start band
2102 *  -  11n flag
2103 *  -  secondary channel offset
2104 */
2105static int mwifiex_set_ibss_params(struct mwifiex_private *priv,
2106				   struct cfg80211_ibss_params *params)
2107{
2108	struct wiphy *wiphy = priv->wdev.wiphy;
2109	struct mwifiex_adapter *adapter = priv->adapter;
2110	int index = 0, i;
2111	u8 config_bands = 0;
2112
2113	if (params->chandef.chan->band == IEEE80211_BAND_2GHZ) {
2114		if (!params->basic_rates) {
2115			config_bands = BAND_B | BAND_G;
2116		} else {
2117			for (i = 0; i < mwifiex_band_2ghz.n_bitrates; i++) {
2118				/*
2119				 * Rates below 6 Mbps in the table are CCK
2120				 * rates; 802.11b and from 6 they are OFDM;
2121				 * 802.11G
2122				 */
2123				if (mwifiex_rates[i].bitrate == 60) {
2124					index = 1 << i;
2125					break;
2126				}
2127			}
2128
2129			if (params->basic_rates < index) {
2130				config_bands = BAND_B;
2131			} else {
2132				config_bands = BAND_G;
2133				if (params->basic_rates % index)
2134					config_bands |= BAND_B;
2135			}
2136		}
2137
2138		if (cfg80211_get_chandef_type(&params->chandef) !=
2139						NL80211_CHAN_NO_HT)
2140			config_bands |= BAND_G | BAND_GN;
2141	} else {
2142		if (cfg80211_get_chandef_type(&params->chandef) ==
2143						NL80211_CHAN_NO_HT)
2144			config_bands = BAND_A;
2145		else
2146			config_bands = BAND_AN | BAND_A;
2147	}
2148
2149	if (!((config_bands | adapter->fw_bands) & ~adapter->fw_bands)) {
2150		adapter->config_bands = config_bands;
2151		adapter->adhoc_start_band = config_bands;
2152
2153		if ((config_bands & BAND_GN) || (config_bands & BAND_AN))
2154			adapter->adhoc_11n_enabled = true;
2155		else
2156			adapter->adhoc_11n_enabled = false;
2157	}
2158
2159	adapter->sec_chan_offset =
2160		mwifiex_chan_type_to_sec_chan_offset(
2161			cfg80211_get_chandef_type(&params->chandef));
2162	priv->adhoc_channel = ieee80211_frequency_to_channel(
2163				params->chandef.chan->center_freq);
2164
2165	wiphy_dbg(wiphy, "info: set ibss band %d, chan %d, chan offset %d\n",
2166		  config_bands, priv->adhoc_channel, adapter->sec_chan_offset);
2167
2168	return 0;
2169}
2170
2171/*
2172 * CFG802.11 operation handler to join an IBSS.
2173 *
2174 * This function does not work in any mode other than Ad-Hoc, or if
2175 * a join operation is already in progress.
2176 */
2177static int
2178mwifiex_cfg80211_join_ibss(struct wiphy *wiphy, struct net_device *dev,
2179			   struct cfg80211_ibss_params *params)
2180{
2181	struct mwifiex_private *priv = mwifiex_netdev_get_priv(dev);
2182	int ret = 0;
2183
2184	if (priv->bss_mode != NL80211_IFTYPE_ADHOC) {
2185		wiphy_err(wiphy, "request to join ibss received "
2186				"when station is not in ibss mode\n");
2187		goto done;
2188	}
2189
2190	wiphy_dbg(wiphy, "info: trying to join to %s and bssid %pM\n",
2191		  (char *) params->ssid, params->bssid);
2192
2193	mwifiex_set_ibss_params(priv, params);
2194
2195	ret = mwifiex_cfg80211_assoc(priv, params->ssid_len, params->ssid,
2196				     params->bssid, priv->bss_mode,
2197				     params->chandef.chan, NULL,
2198				     params->privacy);
2199done:
2200	if (!ret) {
2201		cfg80211_ibss_joined(priv->netdev, priv->cfg_bssid,
2202				     params->chandef.chan, GFP_KERNEL);
2203		dev_dbg(priv->adapter->dev,
2204			"info: joined/created adhoc network with bssid"
2205			" %pM successfully\n", priv->cfg_bssid);
2206	} else {
2207		dev_dbg(priv->adapter->dev,
2208			"info: failed creating/joining adhoc network\n");
2209	}
2210
2211	return ret;
2212}
2213
2214/*
2215 * CFG802.11 operation handler to leave an IBSS.
2216 *
2217 * This function does not work if a leave operation is
2218 * already in progress.
2219 */
2220static int
2221mwifiex_cfg80211_leave_ibss(struct wiphy *wiphy, struct net_device *dev)
2222{
2223	struct mwifiex_private *priv = mwifiex_netdev_get_priv(dev);
2224
2225	wiphy_dbg(wiphy, "info: disconnecting from essid %pM\n",
2226		  priv->cfg_bssid);
2227	if (mwifiex_deauthenticate(priv, NULL))
2228		return -EFAULT;
2229
2230	eth_zero_addr(priv->cfg_bssid);
2231
2232	return 0;
2233}
2234
2235/*
2236 * CFG802.11 operation handler for scan request.
2237 *
2238 * This function issues a scan request to the firmware based upon
2239 * the user specified scan configuration. On successfull completion,
2240 * it also informs the results.
2241 */
2242static int
2243mwifiex_cfg80211_scan(struct wiphy *wiphy,
2244		      struct cfg80211_scan_request *request)
2245{
2246	struct net_device *dev = request->wdev->netdev;
2247	struct mwifiex_private *priv = mwifiex_netdev_get_priv(dev);
2248	int i, offset, ret;
2249	struct ieee80211_channel *chan;
2250	struct ieee_types_header *ie;
2251	struct mwifiex_user_scan_cfg *user_scan_cfg;
2252
2253	wiphy_dbg(wiphy, "info: received scan request on %s\n", dev->name);
2254
2255	/* Block scan request if scan operation or scan cleanup when interface
2256	 * is disabled is in process
2257	 */
2258	if (priv->scan_request || priv->scan_aborting) {
2259		dev_err(priv->adapter->dev, "cmd: Scan already in process..\n");
2260		return -EBUSY;
2261	}
2262
2263	user_scan_cfg = kzalloc(sizeof(*user_scan_cfg), GFP_KERNEL);
2264	if (!user_scan_cfg)
2265		return -ENOMEM;
2266
2267	priv->scan_request = request;
2268
2269	user_scan_cfg->num_ssids = request->n_ssids;
2270	user_scan_cfg->ssid_list = request->ssids;
2271
2272	if (request->ie && request->ie_len) {
2273		offset = 0;
2274		for (i = 0; i < MWIFIEX_MAX_VSIE_NUM; i++) {
2275			if (priv->vs_ie[i].mask != MWIFIEX_VSIE_MASK_CLEAR)
2276				continue;
2277			priv->vs_ie[i].mask = MWIFIEX_VSIE_MASK_SCAN;
2278			ie = (struct ieee_types_header *)(request->ie + offset);
2279			memcpy(&priv->vs_ie[i].ie, ie, sizeof(*ie) + ie->len);
2280			offset += sizeof(*ie) + ie->len;
2281
2282			if (offset >= request->ie_len)
2283				break;
2284		}
2285	}
2286
2287	for (i = 0; i < min_t(u32, request->n_channels,
2288			      MWIFIEX_USER_SCAN_CHAN_MAX); i++) {
2289		chan = request->channels[i];
2290		user_scan_cfg->chan_list[i].chan_number = chan->hw_value;
2291		user_scan_cfg->chan_list[i].radio_type = chan->band;
2292
2293		if ((chan->flags & IEEE80211_CHAN_NO_IR) || !request->n_ssids)
2294			user_scan_cfg->chan_list[i].scan_type =
2295						MWIFIEX_SCAN_TYPE_PASSIVE;
2296		else
2297			user_scan_cfg->chan_list[i].scan_type =
2298						MWIFIEX_SCAN_TYPE_ACTIVE;
2299
2300		user_scan_cfg->chan_list[i].scan_time = 0;
2301	}
2302
2303	if (priv->adapter->scan_chan_gap_enabled &&
2304	    mwifiex_is_any_intf_active(priv))
2305		user_scan_cfg->scan_chan_gap =
2306					      priv->adapter->scan_chan_gap_time;
2307
2308	ret = mwifiex_scan_networks(priv, user_scan_cfg);
2309	kfree(user_scan_cfg);
2310	if (ret) {
2311		dev_err(priv->adapter->dev, "scan failed: %d\n", ret);
2312		priv->scan_aborting = false;
2313		priv->scan_request = NULL;
2314		return ret;
2315	}
2316
2317	if (request->ie && request->ie_len) {
2318		for (i = 0; i < MWIFIEX_MAX_VSIE_NUM; i++) {
2319			if (priv->vs_ie[i].mask == MWIFIEX_VSIE_MASK_SCAN) {
2320				priv->vs_ie[i].mask = MWIFIEX_VSIE_MASK_CLEAR;
2321				memset(&priv->vs_ie[i].ie, 0,
2322				       MWIFIEX_MAX_VSIE_LEN);
2323			}
2324		}
2325	}
2326	return 0;
2327}
2328
2329static void mwifiex_setup_vht_caps(struct ieee80211_sta_vht_cap *vht_info,
2330				   struct mwifiex_private *priv)
2331{
2332	struct mwifiex_adapter *adapter = priv->adapter;
2333
2334	vht_info->vht_supported = true;
2335
2336	vht_info->cap = adapter->hw_dot_11ac_dev_cap;
2337	/* Update MCS support for VHT */
2338	vht_info->vht_mcs.rx_mcs_map = cpu_to_le16(
2339				adapter->hw_dot_11ac_mcs_support & 0xFFFF);
2340	vht_info->vht_mcs.rx_highest = 0;
2341	vht_info->vht_mcs.tx_mcs_map = cpu_to_le16(
2342				adapter->hw_dot_11ac_mcs_support >> 16);
2343	vht_info->vht_mcs.tx_highest = 0;
2344}
2345
2346/*
2347 * This function sets up the CFG802.11 specific HT capability fields
2348 * with default values.
2349 *
2350 * The following default values are set -
2351 *      - HT Supported = True
2352 *      - Maximum AMPDU length factor = IEEE80211_HT_MAX_AMPDU_64K
2353 *      - Minimum AMPDU spacing = IEEE80211_HT_MPDU_DENSITY_NONE
2354 *      - HT Capabilities supported by firmware
2355 *      - MCS information, Rx mask = 0xff
2356 *      - MCD information, Tx parameters = IEEE80211_HT_MCS_TX_DEFINED (0x01)
2357 */
2358static void
2359mwifiex_setup_ht_caps(struct ieee80211_sta_ht_cap *ht_info,
2360		      struct mwifiex_private *priv)
2361{
2362	int rx_mcs_supp;
2363	struct ieee80211_mcs_info mcs_set;
2364	u8 *mcs = (u8 *)&mcs_set;
2365	struct mwifiex_adapter *adapter = priv->adapter;
2366
2367	ht_info->ht_supported = true;
2368	ht_info->ampdu_factor = IEEE80211_HT_MAX_AMPDU_64K;
2369	ht_info->ampdu_density = IEEE80211_HT_MPDU_DENSITY_NONE;
2370
2371	memset(&ht_info->mcs, 0, sizeof(ht_info->mcs));
2372
2373	/* Fill HT capability information */
2374	if (ISSUPP_CHANWIDTH40(adapter->hw_dot_11n_dev_cap))
2375		ht_info->cap |= IEEE80211_HT_CAP_SUP_WIDTH_20_40;
2376	else
2377		ht_info->cap &= ~IEEE80211_HT_CAP_SUP_WIDTH_20_40;
2378
2379	if (ISSUPP_SHORTGI20(adapter->hw_dot_11n_dev_cap))
2380		ht_info->cap |= IEEE80211_HT_CAP_SGI_20;
2381	else
2382		ht_info->cap &= ~IEEE80211_HT_CAP_SGI_20;
2383
2384	if (ISSUPP_SHORTGI40(adapter->hw_dot_11n_dev_cap))
2385		ht_info->cap |= IEEE80211_HT_CAP_SGI_40;
2386	else
2387		ht_info->cap &= ~IEEE80211_HT_CAP_SGI_40;
2388
2389	if (adapter->user_dev_mcs_support == HT_STREAM_2X2)
2390		ht_info->cap |= 3 << IEEE80211_HT_CAP_RX_STBC_SHIFT;
2391	else
2392		ht_info->cap |= 1 << IEEE80211_HT_CAP_RX_STBC_SHIFT;
2393
2394	if (ISSUPP_TXSTBC(adapter->hw_dot_11n_dev_cap))
2395		ht_info->cap |= IEEE80211_HT_CAP_TX_STBC;
2396	else
2397		ht_info->cap &= ~IEEE80211_HT_CAP_TX_STBC;
2398
2399	if (ISSUPP_GREENFIELD(adapter->hw_dot_11n_dev_cap))
2400		ht_info->cap |= IEEE80211_HT_CAP_GRN_FLD;
2401	else
2402		ht_info->cap &= ~IEEE80211_HT_CAP_GRN_FLD;
2403
2404	if (ISENABLED_40MHZ_INTOLERANT(adapter->hw_dot_11n_dev_cap))
2405		ht_info->cap |= IEEE80211_HT_CAP_40MHZ_INTOLERANT;
2406	else
2407		ht_info->cap &= ~IEEE80211_HT_CAP_40MHZ_INTOLERANT;
2408
2409	if (ISSUPP_RXLDPC(adapter->hw_dot_11n_dev_cap))
2410		ht_info->cap |= IEEE80211_HT_CAP_LDPC_CODING;
2411	else
2412		ht_info->cap &= ~IEEE80211_HT_CAP_LDPC_CODING;
2413
2414	ht_info->cap &= ~IEEE80211_HT_CAP_MAX_AMSDU;
2415	ht_info->cap |= IEEE80211_HT_CAP_SM_PS;
2416
2417	rx_mcs_supp = GET_RXMCSSUPP(adapter->user_dev_mcs_support);
2418	/* Set MCS for 1x1/2x2 */
2419	memset(mcs, 0xff, rx_mcs_supp);
2420	/* Clear all the other values */
2421	memset(&mcs[rx_mcs_supp], 0,
2422	       sizeof(struct ieee80211_mcs_info) - rx_mcs_supp);
2423	if (priv->bss_mode == NL80211_IFTYPE_STATION ||
2424	    ISSUPP_CHANWIDTH40(adapter->hw_dot_11n_dev_cap))
2425		/* Set MCS32 for infra mode or ad-hoc mode with 40MHz support */
2426		SETHT_MCS32(mcs_set.rx_mask);
2427
2428	memcpy((u8 *) &ht_info->mcs, mcs, sizeof(struct ieee80211_mcs_info));
2429
2430	ht_info->mcs.tx_params = IEEE80211_HT_MCS_TX_DEFINED;
2431}
2432
2433/*
2434 *  create a new virtual interface with the given name and name assign type
2435 */
2436struct wireless_dev *mwifiex_add_virtual_intf(struct wiphy *wiphy,
2437					      const char *name,
2438					      unsigned char name_assign_type,
2439					      enum nl80211_iftype type,
2440					      u32 *flags,
2441					      struct vif_params *params)
2442{
2443	struct mwifiex_adapter *adapter = mwifiex_cfg80211_get_adapter(wiphy);
2444	struct mwifiex_private *priv;
2445	struct net_device *dev;
2446	void *mdev_priv;
2447
2448	if (!adapter)
2449		return ERR_PTR(-EFAULT);
2450
2451	switch (type) {
2452	case NL80211_IFTYPE_UNSPECIFIED:
2453	case NL80211_IFTYPE_STATION:
2454	case NL80211_IFTYPE_ADHOC:
2455		if (adapter->curr_iface_comb.sta_intf ==
2456		    adapter->iface_limit.sta_intf) {
2457			wiphy_err(wiphy,
2458				  "cannot create multiple sta/adhoc ifaces\n");
2459			return ERR_PTR(-EINVAL);
2460		}
2461
2462		priv = mwifiex_get_unused_priv(adapter);
2463		if (!priv) {
2464			wiphy_err(wiphy,
2465				  "could not get free private struct\n");
2466			return ERR_PTR(-EFAULT);
2467		}
2468
2469		priv->wdev.wiphy = wiphy;
2470		priv->wdev.iftype = NL80211_IFTYPE_STATION;
2471
2472		if (type == NL80211_IFTYPE_UNSPECIFIED)
2473			priv->bss_mode = NL80211_IFTYPE_STATION;
2474		else
2475			priv->bss_mode = type;
2476
2477		priv->bss_type = MWIFIEX_BSS_TYPE_STA;
2478		priv->frame_type = MWIFIEX_DATA_FRAME_TYPE_ETH_II;
2479		priv->bss_priority = 0;
2480		priv->bss_role = MWIFIEX_BSS_ROLE_STA;
2481		priv->bss_num = 0;
2482
2483		break;
2484	case NL80211_IFTYPE_AP:
2485		if (adapter->curr_iface_comb.uap_intf ==
2486		    adapter->iface_limit.uap_intf) {
2487			wiphy_err(wiphy,
2488				  "cannot create multiple AP ifaces\n");
2489			return ERR_PTR(-EINVAL);
2490		}
2491
2492		priv = mwifiex_get_unused_priv(adapter);
2493		if (!priv) {
2494			wiphy_err(wiphy,
2495				  "could not get free private struct\n");
2496			return ERR_PTR(-EFAULT);
2497		}
2498
2499		priv->wdev.wiphy = wiphy;
2500		priv->wdev.iftype = NL80211_IFTYPE_AP;
2501
2502		priv->bss_type = MWIFIEX_BSS_TYPE_UAP;
2503		priv->frame_type = MWIFIEX_DATA_FRAME_TYPE_ETH_II;
2504		priv->bss_priority = 0;
2505		priv->bss_role = MWIFIEX_BSS_ROLE_UAP;
2506		priv->bss_started = 0;
2507		priv->bss_num = 0;
2508		priv->bss_mode = type;
2509
2510		break;
2511	case NL80211_IFTYPE_P2P_CLIENT:
2512		if (adapter->curr_iface_comb.p2p_intf ==
2513		    adapter->iface_limit.p2p_intf) {
2514			wiphy_err(wiphy,
2515				  "cannot create multiple P2P ifaces\n");
2516			return ERR_PTR(-EINVAL);
2517		}
2518
2519		priv = mwifiex_get_unused_priv(adapter);
2520		if (!priv) {
2521			wiphy_err(wiphy,
2522				  "could not get free private struct\n");
2523			return ERR_PTR(-EFAULT);
2524		}
2525
2526		priv->wdev.wiphy = wiphy;
2527		/* At start-up, wpa_supplicant tries to change the interface
2528		 * to NL80211_IFTYPE_STATION if it is not managed mode.
2529		 */
2530		priv->wdev.iftype = NL80211_IFTYPE_P2P_CLIENT;
2531		priv->bss_mode = NL80211_IFTYPE_P2P_CLIENT;
2532
2533		/* Setting bss_type to P2P tells firmware that this interface
2534		 * is receiving P2P peers found during find phase and doing
2535		 * action frame handshake.
2536		 */
2537		priv->bss_type = MWIFIEX_BSS_TYPE_P2P;
2538
2539		priv->frame_type = MWIFIEX_DATA_FRAME_TYPE_ETH_II;
2540		priv->bss_priority = MWIFIEX_BSS_ROLE_STA;
2541		priv->bss_role = MWIFIEX_BSS_ROLE_STA;
2542		priv->bss_started = 0;
2543		priv->bss_num = 0;
2544
2545		if (mwifiex_cfg80211_init_p2p_client(priv)) {
2546			memset(&priv->wdev, 0, sizeof(priv->wdev));
2547			priv->wdev.iftype = NL80211_IFTYPE_UNSPECIFIED;
2548			return ERR_PTR(-EFAULT);
2549		}
2550
2551		break;
2552	default:
2553		wiphy_err(wiphy, "type not supported\n");
2554		return ERR_PTR(-EINVAL);
2555	}
2556
2557	dev = alloc_netdev_mqs(sizeof(struct mwifiex_private *), name,
2558			       name_assign_type, ether_setup,
2559			       IEEE80211_NUM_ACS, 1);
2560	if (!dev) {
2561		wiphy_err(wiphy, "no memory available for netdevice\n");
2562		memset(&priv->wdev, 0, sizeof(priv->wdev));
2563		priv->wdev.iftype = NL80211_IFTYPE_UNSPECIFIED;
2564		priv->bss_mode = NL80211_IFTYPE_UNSPECIFIED;
2565		return ERR_PTR(-ENOMEM);
2566	}
2567
2568	mwifiex_init_priv_params(priv, dev);
2569	priv->netdev = dev;
2570
2571	mwifiex_setup_ht_caps(&wiphy->bands[IEEE80211_BAND_2GHZ]->ht_cap, priv);
2572	if (adapter->is_hw_11ac_capable)
2573		mwifiex_setup_vht_caps(
2574			&wiphy->bands[IEEE80211_BAND_2GHZ]->vht_cap, priv);
2575
2576	if (adapter->config_bands & BAND_A)
2577		mwifiex_setup_ht_caps(
2578			&wiphy->bands[IEEE80211_BAND_5GHZ]->ht_cap, priv);
2579
2580	if ((adapter->config_bands & BAND_A) && adapter->is_hw_11ac_capable)
2581		mwifiex_setup_vht_caps(
2582			&wiphy->bands[IEEE80211_BAND_5GHZ]->vht_cap, priv);
2583
2584	dev_net_set(dev, wiphy_net(wiphy));
2585	dev->ieee80211_ptr = &priv->wdev;
2586	dev->ieee80211_ptr->iftype = priv->bss_mode;
2587	memcpy(dev->dev_addr, wiphy->perm_addr, ETH_ALEN);
2588	SET_NETDEV_DEV(dev, wiphy_dev(wiphy));
2589
2590	dev->flags |= IFF_BROADCAST | IFF_MULTICAST;
2591	dev->watchdog_timeo = MWIFIEX_DEFAULT_WATCHDOG_TIMEOUT;
2592	dev->hard_header_len += MWIFIEX_MIN_DATA_HEADER_LEN;
2593	dev->ethtool_ops = &mwifiex_ethtool_ops;
2594
2595	mdev_priv = netdev_priv(dev);
2596	*((unsigned long *) mdev_priv) = (unsigned long) priv;
2597
2598	SET_NETDEV_DEV(dev, adapter->dev);
2599
2600	/* Register network device */
2601	if (register_netdevice(dev)) {
2602		wiphy_err(wiphy, "cannot register virtual network device\n");
2603		free_netdev(dev);
2604		priv->bss_mode = NL80211_IFTYPE_UNSPECIFIED;
2605		priv->netdev = NULL;
2606		memset(&priv->wdev, 0, sizeof(priv->wdev));
2607		priv->wdev.iftype = NL80211_IFTYPE_UNSPECIFIED;
2608		return ERR_PTR(-EFAULT);
2609	}
2610
2611	priv->dfs_cac_workqueue = alloc_workqueue("MWIFIEX_DFS_CAC%s",
2612						  WQ_HIGHPRI |
2613						  WQ_MEM_RECLAIM |
2614						  WQ_UNBOUND, 1, name);
2615	if (!priv->dfs_cac_workqueue) {
2616		wiphy_err(wiphy, "cannot register virtual network device\n");
2617		free_netdev(dev);
2618		priv->bss_mode = NL80211_IFTYPE_UNSPECIFIED;
2619		priv->netdev = NULL;
2620		memset(&priv->wdev, 0, sizeof(priv->wdev));
2621		priv->wdev.iftype = NL80211_IFTYPE_UNSPECIFIED;
2622		return ERR_PTR(-ENOMEM);
2623	}
2624
2625	INIT_DELAYED_WORK(&priv->dfs_cac_work, mwifiex_dfs_cac_work_queue);
2626
2627	priv->dfs_chan_sw_workqueue = alloc_workqueue("MWIFIEX_DFS_CHSW%s",
2628						      WQ_HIGHPRI | WQ_UNBOUND |
2629						      WQ_MEM_RECLAIM, 1, name);
2630	if (!priv->dfs_chan_sw_workqueue) {
2631		wiphy_err(wiphy, "cannot register virtual network device\n");
2632		free_netdev(dev);
2633		priv->bss_mode = NL80211_IFTYPE_UNSPECIFIED;
2634		priv->netdev = NULL;
2635		memset(&priv->wdev, 0, sizeof(priv->wdev));
2636		priv->wdev.iftype = NL80211_IFTYPE_UNSPECIFIED;
2637		return ERR_PTR(-ENOMEM);
2638	}
2639
2640	INIT_DELAYED_WORK(&priv->dfs_chan_sw_work,
2641			  mwifiex_dfs_chan_sw_work_queue);
2642
2643	sema_init(&priv->async_sem, 1);
2644
2645	dev_dbg(adapter->dev, "info: %s: Marvell 802.11 Adapter\n", dev->name);
2646
2647#ifdef CONFIG_DEBUG_FS
2648	mwifiex_dev_debugfs_init(priv);
2649#endif
2650
2651	switch (type) {
2652	case NL80211_IFTYPE_UNSPECIFIED:
2653	case NL80211_IFTYPE_STATION:
2654	case NL80211_IFTYPE_ADHOC:
2655		adapter->curr_iface_comb.sta_intf++;
2656		break;
2657	case NL80211_IFTYPE_AP:
2658		adapter->curr_iface_comb.uap_intf++;
2659		break;
2660	case NL80211_IFTYPE_P2P_CLIENT:
2661		adapter->curr_iface_comb.p2p_intf++;
2662		break;
2663	default:
2664		wiphy_err(wiphy, "type not supported\n");
2665		return ERR_PTR(-EINVAL);
2666	}
2667
2668	return &priv->wdev;
2669}
2670EXPORT_SYMBOL_GPL(mwifiex_add_virtual_intf);
2671
2672/*
2673 * del_virtual_intf: remove the virtual interface determined by dev
2674 */
2675int mwifiex_del_virtual_intf(struct wiphy *wiphy, struct wireless_dev *wdev)
2676{
2677	struct mwifiex_private *priv = mwifiex_netdev_get_priv(wdev->netdev);
2678	struct mwifiex_adapter *adapter = priv->adapter;
2679
2680#ifdef CONFIG_DEBUG_FS
2681	mwifiex_dev_debugfs_remove(priv);
2682#endif
2683
2684	mwifiex_stop_net_dev_queue(priv->netdev, adapter);
2685
2686	if (netif_carrier_ok(priv->netdev))
2687		netif_carrier_off(priv->netdev);
2688
2689	if (wdev->netdev->reg_state == NETREG_REGISTERED)
2690		unregister_netdevice(wdev->netdev);
2691
2692	if (priv->dfs_cac_workqueue) {
2693		flush_workqueue(priv->dfs_cac_workqueue);
2694		destroy_workqueue(priv->dfs_cac_workqueue);
2695		priv->dfs_cac_workqueue = NULL;
2696	}
2697
2698	if (priv->dfs_chan_sw_workqueue) {
2699		flush_workqueue(priv->dfs_chan_sw_workqueue);
2700		destroy_workqueue(priv->dfs_chan_sw_workqueue);
2701		priv->dfs_chan_sw_workqueue = NULL;
2702	}
2703	/* Clear the priv in adapter */
2704	priv->netdev->ieee80211_ptr = NULL;
2705	priv->netdev = NULL;
2706	priv->wdev.iftype = NL80211_IFTYPE_UNSPECIFIED;
2707
2708	priv->media_connected = false;
2709
2710	switch (priv->bss_mode) {
2711	case NL80211_IFTYPE_UNSPECIFIED:
2712	case NL80211_IFTYPE_STATION:
2713	case NL80211_IFTYPE_ADHOC:
2714		adapter->curr_iface_comb.sta_intf++;
2715		break;
2716	case NL80211_IFTYPE_AP:
2717		adapter->curr_iface_comb.uap_intf++;
2718		break;
2719	case NL80211_IFTYPE_P2P_CLIENT:
2720	case NL80211_IFTYPE_P2P_GO:
2721		adapter->curr_iface_comb.p2p_intf++;
2722		break;
2723	default:
2724		dev_err(adapter->dev, "del_virtual_intf: type not supported\n");
2725		break;
2726	}
2727
2728	priv->bss_mode = NL80211_IFTYPE_UNSPECIFIED;
2729
2730	if (GET_BSS_ROLE(priv) == MWIFIEX_BSS_ROLE_STA ||
2731	    GET_BSS_ROLE(priv) == MWIFIEX_BSS_ROLE_UAP)
2732		kfree(priv->hist_data);
2733
2734	return 0;
2735}
2736EXPORT_SYMBOL_GPL(mwifiex_del_virtual_intf);
2737
2738static bool
2739mwifiex_is_pattern_supported(struct cfg80211_pkt_pattern *pat, s8 *byte_seq,
2740			     u8 max_byte_seq)
2741{
2742	int j, k, valid_byte_cnt = 0;
2743	bool dont_care_byte = false;
2744
2745	for (j = 0; j < DIV_ROUND_UP(pat->pattern_len, 8); j++) {
2746		for (k = 0; k < 8; k++) {
2747			if (pat->mask[j] & 1 << k) {
2748				memcpy(byte_seq + valid_byte_cnt,
2749				       &pat->pattern[j * 8 + k], 1);
2750				valid_byte_cnt++;
2751				if (dont_care_byte)
2752					return false;
2753			} else {
2754				if (valid_byte_cnt)
2755					dont_care_byte = true;
2756			}
2757
2758			if (valid_byte_cnt > max_byte_seq)
2759				return false;
2760		}
2761	}
2762
2763	byte_seq[max_byte_seq] = valid_byte_cnt;
2764
2765	return true;
2766}
2767
2768#ifdef CONFIG_PM
2769static void mwifiex_set_auto_arp_mef_entry(struct mwifiex_private *priv,
2770					   struct mwifiex_mef_entry *mef_entry)
2771{
2772	int i, filt_num = 0, num_ipv4 = 0;
2773	struct in_device *in_dev;
2774	struct in_ifaddr *ifa;
2775	__be32 ips[MWIFIEX_MAX_SUPPORTED_IPADDR];
2776	struct mwifiex_adapter *adapter = priv->adapter;
2777
2778	mef_entry->mode = MEF_MODE_HOST_SLEEP;
2779	mef_entry->action = MEF_ACTION_AUTO_ARP;
2780
2781	/* Enable ARP offload feature */
2782	memset(ips, 0, sizeof(ips));
2783	for (i = 0; i < MWIFIEX_MAX_BSS_NUM; i++) {
2784		if (adapter->priv[i]->netdev) {
2785			in_dev = __in_dev_get_rtnl(adapter->priv[i]->netdev);
2786			if (!in_dev)
2787				continue;
2788			ifa = in_dev->ifa_list;
2789			if (!ifa || !ifa->ifa_local)
2790				continue;
2791			ips[i] = ifa->ifa_local;
2792			num_ipv4++;
2793		}
2794	}
2795
2796	for (i = 0; i < num_ipv4; i++) {
2797		if (!ips[i])
2798			continue;
2799		mef_entry->filter[filt_num].repeat = 1;
2800		memcpy(mef_entry->filter[filt_num].byte_seq,
2801		       (u8 *)&ips[i], sizeof(ips[i]));
2802		mef_entry->filter[filt_num].
2803			byte_seq[MWIFIEX_MEF_MAX_BYTESEQ] =
2804			sizeof(ips[i]);
2805		mef_entry->filter[filt_num].offset = 46;
2806		mef_entry->filter[filt_num].filt_type = TYPE_EQ;
2807		if (filt_num) {
2808			mef_entry->filter[filt_num].filt_action =
2809				TYPE_OR;
2810		}
2811		filt_num++;
2812	}
2813
2814	mef_entry->filter[filt_num].repeat = 1;
2815	mef_entry->filter[filt_num].byte_seq[0] = 0x08;
2816	mef_entry->filter[filt_num].byte_seq[1] = 0x06;
2817	mef_entry->filter[filt_num].byte_seq[MWIFIEX_MEF_MAX_BYTESEQ] = 2;
2818	mef_entry->filter[filt_num].offset = 20;
2819	mef_entry->filter[filt_num].filt_type = TYPE_EQ;
2820	mef_entry->filter[filt_num].filt_action = TYPE_AND;
2821}
2822
2823static int mwifiex_set_wowlan_mef_entry(struct mwifiex_private *priv,
2824					struct mwifiex_ds_mef_cfg *mef_cfg,
2825					struct mwifiex_mef_entry *mef_entry,
2826					struct cfg80211_wowlan *wowlan)
2827{
2828	int i, filt_num = 0, ret = 0;
2829	bool first_pat = true;
2830	u8 byte_seq[MWIFIEX_MEF_MAX_BYTESEQ + 1];
2831	const u8 ipv4_mc_mac[] = {0x33, 0x33};
2832	const u8 ipv6_mc_mac[] = {0x01, 0x00, 0x5e};
2833
2834	mef_entry->mode = MEF_MODE_HOST_SLEEP;
2835	mef_entry->action = MEF_ACTION_ALLOW_AND_WAKEUP_HOST;
2836
2837	for (i = 0; i < wowlan->n_patterns; i++) {
2838		memset(byte_seq, 0, sizeof(byte_seq));
2839		if (!mwifiex_is_pattern_supported(&wowlan->patterns[i],
2840					byte_seq,
2841					MWIFIEX_MEF_MAX_BYTESEQ)) {
2842			dev_err(priv->adapter->dev, "Pattern not supported\n");
2843			kfree(mef_entry);
2844			return -EOPNOTSUPP;
2845		}
2846
2847		if (!wowlan->patterns[i].pkt_offset) {
2848			if (!(byte_seq[0] & 0x01) &&
2849			    (byte_seq[MWIFIEX_MEF_MAX_BYTESEQ] == 1)) {
2850				mef_cfg->criteria |= MWIFIEX_CRITERIA_UNICAST;
2851				continue;
2852			} else if (is_broadcast_ether_addr(byte_seq)) {
2853				mef_cfg->criteria |= MWIFIEX_CRITERIA_BROADCAST;
2854				continue;
2855			} else if ((!memcmp(byte_seq, ipv4_mc_mac, 2) &&
2856				    (byte_seq[MWIFIEX_MEF_MAX_BYTESEQ] == 2)) ||
2857				   (!memcmp(byte_seq, ipv6_mc_mac, 3) &&
2858				    (byte_seq[MWIFIEX_MEF_MAX_BYTESEQ] == 3))) {
2859				mef_cfg->criteria |= MWIFIEX_CRITERIA_MULTICAST;
2860				continue;
2861			}
2862		}
2863		mef_entry->filter[filt_num].repeat = 1;
2864		mef_entry->filter[filt_num].offset =
2865			wowlan->patterns[i].pkt_offset;
2866		memcpy(mef_entry->filter[filt_num].byte_seq, byte_seq,
2867				sizeof(byte_seq));
2868		mef_entry->filter[filt_num].filt_type = TYPE_EQ;
2869
2870		if (first_pat)
2871			first_pat = false;
2872		else
2873			mef_entry->filter[filt_num].filt_action = TYPE_AND;
2874
2875		filt_num++;
2876	}
2877
2878	if (wowlan->magic_pkt) {
2879		mef_cfg->criteria |= MWIFIEX_CRITERIA_UNICAST;
2880		mef_entry->filter[filt_num].repeat = 16;
2881		memcpy(mef_entry->filter[filt_num].byte_seq, priv->curr_addr,
2882				ETH_ALEN);
2883		mef_entry->filter[filt_num].byte_seq[MWIFIEX_MEF_MAX_BYTESEQ] =
2884			ETH_ALEN;
2885		mef_entry->filter[filt_num].offset = 28;
2886		mef_entry->filter[filt_num].filt_type = TYPE_EQ;
2887		if (filt_num)
2888			mef_entry->filter[filt_num].filt_action = TYPE_OR;
2889
2890		filt_num++;
2891		mef_entry->filter[filt_num].repeat = 16;
2892		memcpy(mef_entry->filter[filt_num].byte_seq, priv->curr_addr,
2893				ETH_ALEN);
2894		mef_entry->filter[filt_num].byte_seq[MWIFIEX_MEF_MAX_BYTESEQ] =
2895			ETH_ALEN;
2896		mef_entry->filter[filt_num].offset = 56;
2897		mef_entry->filter[filt_num].filt_type = TYPE_EQ;
2898		mef_entry->filter[filt_num].filt_action = TYPE_OR;
2899	}
2900	return ret;
2901}
2902
2903static int mwifiex_set_mef_filter(struct mwifiex_private *priv,
2904				  struct cfg80211_wowlan *wowlan)
2905{
2906	int ret = 0, num_entries = 1;
2907	struct mwifiex_ds_mef_cfg mef_cfg;
2908	struct mwifiex_mef_entry *mef_entry;
2909
2910	if (wowlan->n_patterns || wowlan->magic_pkt)
2911		num_entries++;
2912
2913	mef_entry = kcalloc(num_entries, sizeof(*mef_entry), GFP_KERNEL);
2914	if (!mef_entry)
2915		return -ENOMEM;
2916
2917	memset(&mef_cfg, 0, sizeof(mef_cfg));
2918	mef_cfg.criteria |= MWIFIEX_CRITERIA_BROADCAST |
2919		MWIFIEX_CRITERIA_UNICAST;
2920	mef_cfg.num_entries = num_entries;
2921	mef_cfg.mef_entry = mef_entry;
2922
2923	mwifiex_set_auto_arp_mef_entry(priv, &mef_entry[0]);
2924
2925	if (wowlan->n_patterns || wowlan->magic_pkt)
2926		ret = mwifiex_set_wowlan_mef_entry(priv, &mef_cfg,
2927						   &mef_entry[1], wowlan);
2928
2929	if (!mef_cfg.criteria)
2930		mef_cfg.criteria = MWIFIEX_CRITERIA_BROADCAST |
2931			MWIFIEX_CRITERIA_UNICAST |
2932			MWIFIEX_CRITERIA_MULTICAST;
2933
2934	ret = mwifiex_send_cmd(priv, HostCmd_CMD_MEF_CFG,
2935			HostCmd_ACT_GEN_SET, 0,
2936			&mef_cfg, true);
2937	kfree(mef_entry);
2938	return ret;
2939}
2940
2941static int mwifiex_cfg80211_suspend(struct wiphy *wiphy,
2942				    struct cfg80211_wowlan *wowlan)
2943{
2944	struct mwifiex_adapter *adapter = mwifiex_cfg80211_get_adapter(wiphy);
2945	struct mwifiex_ds_hs_cfg hs_cfg;
2946	int i, ret = 0;
2947	struct mwifiex_private *priv;
2948
2949	for (i = 0; i < adapter->priv_num; i++) {
2950		priv = adapter->priv[i];
2951		mwifiex_abort_cac(priv);
2952	}
2953
2954	mwifiex_cancel_all_pending_cmd(adapter);
2955
2956	if (!wowlan) {
2957		dev_warn(adapter->dev, "None of the WOWLAN triggers enabled\n");
2958		return 0;
2959	}
2960
2961	priv = mwifiex_get_priv(adapter, MWIFIEX_BSS_ROLE_STA);
2962
2963	if (!priv->media_connected) {
2964		dev_warn(adapter->dev,
2965			 "Can not configure WOWLAN in disconnected state\n");
2966		return 0;
2967	}
2968
2969	ret = mwifiex_set_mef_filter(priv, wowlan);
2970	if (ret) {
2971		dev_err(adapter->dev, "Failed to set MEF filter\n");
2972		return ret;
2973	}
2974
2975	if (wowlan->disconnect) {
2976		memset(&hs_cfg, 0, sizeof(hs_cfg));
2977		hs_cfg.is_invoke_hostcmd = false;
2978		hs_cfg.conditions = HS_CFG_COND_MAC_EVENT;
2979		hs_cfg.gpio = HS_CFG_GPIO_DEF;
2980		hs_cfg.gap = HS_CFG_GAP_DEF;
2981		ret = mwifiex_set_hs_params(priv, HostCmd_ACT_GEN_SET,
2982					    MWIFIEX_SYNC_CMD, &hs_cfg);
2983		if (ret) {
2984			dev_err(adapter->dev, "Failed to set HS params\n");
2985			return ret;
2986		}
2987	}
2988
2989	return ret;
2990}
2991
2992static int mwifiex_cfg80211_resume(struct wiphy *wiphy)
2993{
2994	return 0;
2995}
2996
2997static void mwifiex_cfg80211_set_wakeup(struct wiphy *wiphy,
2998				       bool enabled)
2999{
3000	struct mwifiex_adapter *adapter = mwifiex_cfg80211_get_adapter(wiphy);
3001
3002	device_set_wakeup_enable(adapter->dev, enabled);
3003}
3004#endif
3005
3006static int mwifiex_get_coalesce_pkt_type(u8 *byte_seq)
3007{
3008	const u8 ipv4_mc_mac[] = {0x33, 0x33};
3009	const u8 ipv6_mc_mac[] = {0x01, 0x00, 0x5e};
3010	const u8 bc_mac[] = {0xff, 0xff, 0xff, 0xff};
3011
3012	if ((byte_seq[0] & 0x01) &&
3013	    (byte_seq[MWIFIEX_COALESCE_MAX_BYTESEQ] == 1))
3014		return PACKET_TYPE_UNICAST;
3015	else if (!memcmp(byte_seq, bc_mac, 4))
3016		return PACKET_TYPE_BROADCAST;
3017	else if ((!memcmp(byte_seq, ipv4_mc_mac, 2) &&
3018		  byte_seq[MWIFIEX_COALESCE_MAX_BYTESEQ] == 2) ||
3019		 (!memcmp(byte_seq, ipv6_mc_mac, 3) &&
3020		  byte_seq[MWIFIEX_COALESCE_MAX_BYTESEQ] == 3))
3021		return PACKET_TYPE_MULTICAST;
3022
3023	return 0;
3024}
3025
3026static int
3027mwifiex_fill_coalesce_rule_info(struct mwifiex_private *priv,
3028				struct cfg80211_coalesce_rules *crule,
3029				struct mwifiex_coalesce_rule *mrule)
3030{
3031	u8 byte_seq[MWIFIEX_COALESCE_MAX_BYTESEQ + 1];
3032	struct filt_field_param *param;
3033	int i;
3034
3035	mrule->max_coalescing_delay = crule->delay;
3036
3037	param = mrule->params;
3038
3039	for (i = 0; i < crule->n_patterns; i++) {
3040		memset(byte_seq, 0, sizeof(byte_seq));
3041		if (!mwifiex_is_pattern_supported(&crule->patterns[i],
3042						  byte_seq,
3043						MWIFIEX_COALESCE_MAX_BYTESEQ)) {
3044			dev_err(priv->adapter->dev, "Pattern not supported\n");
3045			return -EOPNOTSUPP;
3046		}
3047
3048		if (!crule->patterns[i].pkt_offset) {
3049			u8 pkt_type;
3050
3051			pkt_type = mwifiex_get_coalesce_pkt_type(byte_seq);
3052			if (pkt_type && mrule->pkt_type) {
3053				dev_err(priv->adapter->dev,
3054					"Multiple packet types not allowed\n");
3055				return -EOPNOTSUPP;
3056			} else if (pkt_type) {
3057				mrule->pkt_type = pkt_type;
3058				continue;
3059			}
3060		}
3061
3062		if (crule->condition == NL80211_COALESCE_CONDITION_MATCH)
3063			param->operation = RECV_FILTER_MATCH_TYPE_EQ;
3064		else
3065			param->operation = RECV_FILTER_MATCH_TYPE_NE;
3066
3067		param->operand_len = byte_seq[MWIFIEX_COALESCE_MAX_BYTESEQ];
3068		memcpy(param->operand_byte_stream, byte_seq,
3069		       param->operand_len);
3070		param->offset = crule->patterns[i].pkt_offset;
3071		param++;
3072
3073		mrule->num_of_fields++;
3074	}
3075
3076	if (!mrule->pkt_type) {
3077		dev_err(priv->adapter->dev,
3078			"Packet type can not be determined\n");
3079		return -EOPNOTSUPP;
3080	}
3081
3082	return 0;
3083}
3084
3085static int mwifiex_cfg80211_set_coalesce(struct wiphy *wiphy,
3086					 struct cfg80211_coalesce *coalesce)
3087{
3088	struct mwifiex_adapter *adapter = mwifiex_cfg80211_get_adapter(wiphy);
3089	int i, ret;
3090	struct mwifiex_ds_coalesce_cfg coalesce_cfg;
3091	struct mwifiex_private *priv =
3092			mwifiex_get_priv(adapter, MWIFIEX_BSS_ROLE_STA);
3093
3094	memset(&coalesce_cfg, 0, sizeof(coalesce_cfg));
3095	if (!coalesce) {
3096		dev_dbg(adapter->dev,
3097			"Disable coalesce and reset all previous rules\n");
3098		return mwifiex_send_cmd(priv, HostCmd_CMD_COALESCE_CFG,
3099					HostCmd_ACT_GEN_SET, 0,
3100					&coalesce_cfg, true);
3101	}
3102
3103	coalesce_cfg.num_of_rules = coalesce->n_rules;
3104	for (i = 0; i < coalesce->n_rules; i++) {
3105		ret = mwifiex_fill_coalesce_rule_info(priv, &coalesce->rules[i],
3106						      &coalesce_cfg.rule[i]);
3107		if (ret) {
3108			dev_err(priv->adapter->dev,
3109				"Recheck the patterns provided for rule %d\n",
3110				i + 1);
3111			return ret;
3112		}
3113	}
3114
3115	return mwifiex_send_cmd(priv, HostCmd_CMD_COALESCE_CFG,
3116				HostCmd_ACT_GEN_SET, 0, &coalesce_cfg, true);
3117}
3118
3119/* cfg80211 ops handler for tdls_mgmt.
3120 * Function prepares TDLS action frame packets and forwards them to FW
3121 */
3122static int
3123mwifiex_cfg80211_tdls_mgmt(struct wiphy *wiphy, struct net_device *dev,
3124			   const u8 *peer, u8 action_code, u8 dialog_token,
3125			   u16 status_code, u32 peer_capability,
3126			   bool initiator, const u8 *extra_ies,
3127			   size_t extra_ies_len)
3128{
3129	struct mwifiex_private *priv = mwifiex_netdev_get_priv(dev);
3130	int ret;
3131
3132	if (!(wiphy->flags & WIPHY_FLAG_SUPPORTS_TDLS))
3133		return -ENOTSUPP;
3134
3135	/* make sure we are in station mode and connected */
3136	if (!(priv->bss_type == MWIFIEX_BSS_TYPE_STA && priv->media_connected))
3137		return -ENOTSUPP;
3138
3139	switch (action_code) {
3140	case WLAN_TDLS_SETUP_REQUEST:
3141		dev_dbg(priv->adapter->dev,
3142			"Send TDLS Setup Request to %pM status_code=%d\n", peer,
3143			 status_code);
3144		mwifiex_add_auto_tdls_peer(priv, peer);
3145		ret = mwifiex_send_tdls_data_frame(priv, peer, action_code,
3146						   dialog_token, status_code,
3147						   extra_ies, extra_ies_len);
3148		break;
3149	case WLAN_TDLS_SETUP_RESPONSE:
3150		mwifiex_add_auto_tdls_peer(priv, peer);
3151		dev_dbg(priv->adapter->dev,
3152			"Send TDLS Setup Response to %pM status_code=%d\n",
3153			peer, status_code);
3154		ret = mwifiex_send_tdls_data_frame(priv, peer, action_code,
3155						   dialog_token, status_code,
3156						   extra_ies, extra_ies_len);
3157		break;
3158	case WLAN_TDLS_SETUP_CONFIRM:
3159		dev_dbg(priv->adapter->dev,
3160			"Send TDLS Confirm to %pM status_code=%d\n", peer,
3161			status_code);
3162		ret = mwifiex_send_tdls_data_frame(priv, peer, action_code,
3163						   dialog_token, status_code,
3164						   extra_ies, extra_ies_len);
3165		break;
3166	case WLAN_TDLS_TEARDOWN:
3167		dev_dbg(priv->adapter->dev, "Send TDLS Tear down to %pM\n",
3168			peer);
3169		ret = mwifiex_send_tdls_data_frame(priv, peer, action_code,
3170						   dialog_token, status_code,
3171						   extra_ies, extra_ies_len);
3172		break;
3173	case WLAN_TDLS_DISCOVERY_REQUEST:
3174		dev_dbg(priv->adapter->dev,
3175			"Send TDLS Discovery Request to %pM\n", peer);
3176		ret = mwifiex_send_tdls_data_frame(priv, peer, action_code,
3177						   dialog_token, status_code,
3178						   extra_ies, extra_ies_len);
3179		break;
3180	case WLAN_PUB_ACTION_TDLS_DISCOVER_RES:
3181		dev_dbg(priv->adapter->dev,
3182			"Send TDLS Discovery Response to %pM\n", peer);
3183		ret = mwifiex_send_tdls_action_frame(priv, peer, action_code,
3184						   dialog_token, status_code,
3185						   extra_ies, extra_ies_len);
3186		break;
3187	default:
3188		dev_warn(priv->adapter->dev,
3189			 "Unknown TDLS mgmt/action frame %pM\n", peer);
3190		ret = -EINVAL;
3191		break;
3192	}
3193
3194	return ret;
3195}
3196
3197static int
3198mwifiex_cfg80211_tdls_oper(struct wiphy *wiphy, struct net_device *dev,
3199			   const u8 *peer, enum nl80211_tdls_operation action)
3200{
3201	struct mwifiex_private *priv = mwifiex_netdev_get_priv(dev);
3202
3203	if (!(wiphy->flags & WIPHY_FLAG_SUPPORTS_TDLS) ||
3204	    !(wiphy->flags & WIPHY_FLAG_TDLS_EXTERNAL_SETUP))
3205		return -ENOTSUPP;
3206
3207	/* make sure we are in station mode and connected */
3208	if (!(priv->bss_type == MWIFIEX_BSS_TYPE_STA && priv->media_connected))
3209		return -ENOTSUPP;
3210
3211	dev_dbg(priv->adapter->dev,
3212		"TDLS peer=%pM, oper=%d\n", peer, action);
3213
3214	switch (action) {
3215	case NL80211_TDLS_ENABLE_LINK:
3216		action = MWIFIEX_TDLS_ENABLE_LINK;
3217		break;
3218	case NL80211_TDLS_DISABLE_LINK:
3219		action = MWIFIEX_TDLS_DISABLE_LINK;
3220		break;
3221	case NL80211_TDLS_TEARDOWN:
3222		/* shouldn't happen!*/
3223		dev_warn(priv->adapter->dev,
3224			 "tdls_oper: teardown from driver not supported\n");
3225		return -EINVAL;
3226	case NL80211_TDLS_SETUP:
3227		/* shouldn't happen!*/
3228		dev_warn(priv->adapter->dev,
3229			 "tdls_oper: setup from driver not supported\n");
3230		return -EINVAL;
3231	case NL80211_TDLS_DISCOVERY_REQ:
3232		/* shouldn't happen!*/
3233		dev_warn(priv->adapter->dev,
3234			 "tdls_oper: discovery from driver not supported\n");
3235		return -EINVAL;
3236	default:
3237		dev_err(priv->adapter->dev,
3238			"tdls_oper: operation not supported\n");
3239		return -ENOTSUPP;
3240	}
3241
3242	return mwifiex_tdls_oper(priv, peer, action);
3243}
3244
3245static int
3246mwifiex_cfg80211_add_station(struct wiphy *wiphy, struct net_device *dev,
3247			     const u8 *mac, struct station_parameters *params)
3248{
3249	struct mwifiex_private *priv = mwifiex_netdev_get_priv(dev);
3250
3251	if (!(params->sta_flags_set & BIT(NL80211_STA_FLAG_TDLS_PEER)))
3252		return -ENOTSUPP;
3253
3254	/* make sure we are in station mode and connected */
3255	if ((priv->bss_type != MWIFIEX_BSS_TYPE_STA) || !priv->media_connected)
3256		return -ENOTSUPP;
3257
3258	return mwifiex_tdls_oper(priv, mac, MWIFIEX_TDLS_CREATE_LINK);
3259}
3260
3261static int
3262mwifiex_cfg80211_channel_switch(struct wiphy *wiphy, struct net_device *dev,
3263				struct cfg80211_csa_settings *params)
3264{
3265	struct ieee_types_header *chsw_ie;
3266	struct ieee80211_channel_sw_ie *channel_sw;
3267	int chsw_msec;
3268	struct mwifiex_private *priv = mwifiex_netdev_get_priv(dev);
3269
3270	if (priv->adapter->scan_processing) {
3271		dev_err(priv->adapter->dev,
3272			"radar detection: scan in process...\n");
3273		return -EBUSY;
3274	}
3275
3276	if (priv->wdev.cac_started)
3277		return -EBUSY;
3278
3279	if (cfg80211_chandef_identical(&params->chandef,
3280				       &priv->dfs_chandef))
3281		return -EINVAL;
3282
3283	chsw_ie = (void *)cfg80211_find_ie(WLAN_EID_CHANNEL_SWITCH,
3284					   params->beacon_csa.tail,
3285					   params->beacon_csa.tail_len);
3286	if (!chsw_ie) {
3287		dev_err(priv->adapter->dev,
3288			"Could not parse channel switch announcement IE\n");
3289		return -EINVAL;
3290	}
3291
3292	channel_sw = (void *)(chsw_ie + 1);
3293	if (channel_sw->mode) {
3294		if (netif_carrier_ok(priv->netdev))
3295			netif_carrier_off(priv->netdev);
3296		mwifiex_stop_net_dev_queue(priv->netdev, priv->adapter);
3297	}
3298
3299	if (mwifiex_del_mgmt_ies(priv))
3300		wiphy_err(wiphy, "Failed to delete mgmt IEs!\n");
3301
3302	if (mwifiex_set_mgmt_ies(priv, &params->beacon_csa)) {
3303		wiphy_err(wiphy, "%s: setting mgmt ies failed\n", __func__);
3304		return -EFAULT;
3305	}
3306
3307	memcpy(&priv->dfs_chandef, &params->chandef, sizeof(priv->dfs_chandef));
3308	memcpy(&priv->beacon_after, &params->beacon_after,
3309	       sizeof(priv->beacon_after));
3310
3311	chsw_msec = max(channel_sw->count * priv->bss_cfg.beacon_period, 100);
3312	queue_delayed_work(priv->dfs_chan_sw_workqueue, &priv->dfs_chan_sw_work,
3313			   msecs_to_jiffies(chsw_msec));
3314	return 0;
3315}
3316
3317static int
3318mwifiex_cfg80211_start_radar_detection(struct wiphy *wiphy,
3319				       struct net_device *dev,
3320				       struct cfg80211_chan_def *chandef,
3321				       u32 cac_time_ms)
3322{
3323	struct mwifiex_private *priv = mwifiex_netdev_get_priv(dev);
3324	struct mwifiex_radar_params radar_params;
3325
3326	if (priv->adapter->scan_processing) {
3327		dev_err(priv->adapter->dev,
3328			"radar detection: scan already in process...\n");
3329		return -EBUSY;
3330	}
3331
3332	if (!mwifiex_is_11h_active(priv)) {
3333		dev_dbg(priv->adapter->dev, "Enable 11h extensions in FW\n");
3334		if (mwifiex_11h_activate(priv, true)) {
3335			dev_err(priv->adapter->dev,
3336				"Failed to activate 11h extensions!!");
3337			return -1;
3338		}
3339		priv->state_11h.is_11h_active = true;
3340	}
3341
3342	memset(&radar_params, 0, sizeof(struct mwifiex_radar_params));
3343	radar_params.chandef = chandef;
3344	radar_params.cac_time_ms = cac_time_ms;
3345
3346	memcpy(&priv->dfs_chandef, chandef, sizeof(priv->dfs_chandef));
3347
3348	if (mwifiex_send_cmd(priv, HostCmd_CMD_CHAN_REPORT_REQUEST,
3349			     HostCmd_ACT_GEN_SET, 0, &radar_params, true))
3350		return -1;
3351
3352	queue_delayed_work(priv->dfs_cac_workqueue, &priv->dfs_cac_work,
3353			   msecs_to_jiffies(cac_time_ms));
3354	return 0;
3355}
3356
3357static int
3358mwifiex_cfg80211_change_station(struct wiphy *wiphy, struct net_device *dev,
3359				const u8 *mac,
3360				struct station_parameters *params)
3361{
3362	int ret;
3363	struct mwifiex_private *priv = mwifiex_netdev_get_priv(dev);
3364
3365	/* we support change_station handler only for TDLS peers*/
3366	if (!(params->sta_flags_set & BIT(NL80211_STA_FLAG_TDLS_PEER)))
3367		return -ENOTSUPP;
3368
3369	/* make sure we are in station mode and connected */
3370	if ((priv->bss_type != MWIFIEX_BSS_TYPE_STA) || !priv->media_connected)
3371		return -ENOTSUPP;
3372
3373	priv->sta_params = params;
3374
3375	ret = mwifiex_tdls_oper(priv, mac, MWIFIEX_TDLS_CONFIG_LINK);
3376	priv->sta_params = NULL;
3377
3378	return ret;
3379}
3380
3381/* station cfg80211 operations */
3382static struct cfg80211_ops mwifiex_cfg80211_ops = {
3383	.add_virtual_intf = mwifiex_add_virtual_intf,
3384	.del_virtual_intf = mwifiex_del_virtual_intf,
3385	.change_virtual_intf = mwifiex_cfg80211_change_virtual_intf,
3386	.scan = mwifiex_cfg80211_scan,
3387	.connect = mwifiex_cfg80211_connect,
3388	.disconnect = mwifiex_cfg80211_disconnect,
3389	.get_station = mwifiex_cfg80211_get_station,
3390	.dump_station = mwifiex_cfg80211_dump_station,
3391	.dump_survey = mwifiex_cfg80211_dump_survey,
3392	.set_wiphy_params = mwifiex_cfg80211_set_wiphy_params,
3393	.join_ibss = mwifiex_cfg80211_join_ibss,
3394	.leave_ibss = mwifiex_cfg80211_leave_ibss,
3395	.add_key = mwifiex_cfg80211_add_key,
3396	.del_key = mwifiex_cfg80211_del_key,
3397	.mgmt_tx = mwifiex_cfg80211_mgmt_tx,
3398	.mgmt_frame_register = mwifiex_cfg80211_mgmt_frame_register,
3399	.remain_on_channel = mwifiex_cfg80211_remain_on_channel,
3400	.cancel_remain_on_channel = mwifiex_cfg80211_cancel_remain_on_channel,
3401	.set_default_key = mwifiex_cfg80211_set_default_key,
3402	.set_power_mgmt = mwifiex_cfg80211_set_power_mgmt,
3403	.set_tx_power = mwifiex_cfg80211_set_tx_power,
3404	.set_bitrate_mask = mwifiex_cfg80211_set_bitrate_mask,
3405	.start_ap = mwifiex_cfg80211_start_ap,
3406	.stop_ap = mwifiex_cfg80211_stop_ap,
3407	.change_beacon = mwifiex_cfg80211_change_beacon,
3408	.set_cqm_rssi_config = mwifiex_cfg80211_set_cqm_rssi_config,
3409	.set_antenna = mwifiex_cfg80211_set_antenna,
3410	.del_station = mwifiex_cfg80211_del_station,
3411#ifdef CONFIG_PM
3412	.suspend = mwifiex_cfg80211_suspend,
3413	.resume = mwifiex_cfg80211_resume,
3414	.set_wakeup = mwifiex_cfg80211_set_wakeup,
3415#endif
3416	.set_coalesce = mwifiex_cfg80211_set_coalesce,
3417	.tdls_mgmt = mwifiex_cfg80211_tdls_mgmt,
3418	.tdls_oper = mwifiex_cfg80211_tdls_oper,
3419	.add_station = mwifiex_cfg80211_add_station,
3420	.change_station = mwifiex_cfg80211_change_station,
3421	.start_radar_detection = mwifiex_cfg80211_start_radar_detection,
3422	.channel_switch = mwifiex_cfg80211_channel_switch,
3423};
3424
3425#ifdef CONFIG_PM
3426static const struct wiphy_wowlan_support mwifiex_wowlan_support = {
3427	.flags = WIPHY_WOWLAN_MAGIC_PKT | WIPHY_WOWLAN_DISCONNECT,
3428	.n_patterns = MWIFIEX_MEF_MAX_FILTERS,
3429	.pattern_min_len = 1,
3430	.pattern_max_len = MWIFIEX_MAX_PATTERN_LEN,
3431	.max_pkt_offset = MWIFIEX_MAX_OFFSET_LEN,
3432};
3433#endif
3434
3435static bool mwifiex_is_valid_alpha2(const char *alpha2)
3436{
3437	if (!alpha2 || strlen(alpha2) != 2)
3438		return false;
3439
3440	if (isalpha(alpha2[0]) && isalpha(alpha2[1]))
3441		return true;
3442
3443	return false;
3444}
3445
3446static const struct wiphy_coalesce_support mwifiex_coalesce_support = {
3447	.n_rules = MWIFIEX_COALESCE_MAX_RULES,
3448	.max_delay = MWIFIEX_MAX_COALESCING_DELAY,
3449	.n_patterns = MWIFIEX_COALESCE_MAX_FILTERS,
3450	.pattern_min_len = 1,
3451	.pattern_max_len = MWIFIEX_MAX_PATTERN_LEN,
3452	.max_pkt_offset = MWIFIEX_MAX_OFFSET_LEN,
3453};
3454
3455int mwifiex_init_channel_scan_gap(struct mwifiex_adapter *adapter)
3456{
3457	u32 n_channels_bg, n_channels_a = 0;
3458
3459	n_channels_bg = mwifiex_band_2ghz.n_channels;
3460
3461	if (adapter->config_bands & BAND_A)
3462		n_channels_a = mwifiex_band_5ghz.n_channels;
3463
3464	adapter->num_in_chan_stats = max_t(u32, n_channels_bg, n_channels_a);
3465	adapter->chan_stats = vmalloc(sizeof(*adapter->chan_stats) *
3466				      adapter->num_in_chan_stats);
3467
3468	if (!adapter->chan_stats)
3469		return -ENOMEM;
3470
3471	return 0;
3472}
3473
3474/*
3475 * This function registers the device with CFG802.11 subsystem.
3476 *
3477 * The function creates the wireless device/wiphy, populates it with
3478 * default parameters and handler function pointers, and finally
3479 * registers the device.
3480 */
3481
3482int mwifiex_register_cfg80211(struct mwifiex_adapter *adapter)
3483{
3484	int ret;
3485	void *wdev_priv;
3486	struct wiphy *wiphy;
3487	struct mwifiex_private *priv = adapter->priv[MWIFIEX_BSS_TYPE_STA];
3488	u8 *country_code;
3489	u32 thr, retry;
3490
3491	/* create a new wiphy for use with cfg80211 */
3492	wiphy = wiphy_new(&mwifiex_cfg80211_ops,
3493			  sizeof(struct mwifiex_adapter *));
3494	if (!wiphy) {
3495		dev_err(adapter->dev, "%s: creating new wiphy\n", __func__);
3496		return -ENOMEM;
3497	}
3498	wiphy->max_scan_ssids = MWIFIEX_MAX_SSID_LIST_LENGTH;
3499	wiphy->max_scan_ie_len = MWIFIEX_MAX_VSIE_LEN;
3500	wiphy->mgmt_stypes = mwifiex_mgmt_stypes;
3501	wiphy->max_remain_on_channel_duration = 5000;
3502	wiphy->interface_modes = BIT(NL80211_IFTYPE_STATION) |
3503				 BIT(NL80211_IFTYPE_ADHOC) |
3504				 BIT(NL80211_IFTYPE_P2P_CLIENT) |
3505				 BIT(NL80211_IFTYPE_P2P_GO) |
3506				 BIT(NL80211_IFTYPE_AP);
3507
3508	wiphy->bands[IEEE80211_BAND_2GHZ] = &mwifiex_band_2ghz;
3509	if (adapter->config_bands & BAND_A)
3510		wiphy->bands[IEEE80211_BAND_5GHZ] = &mwifiex_band_5ghz;
3511	else
3512		wiphy->bands[IEEE80211_BAND_5GHZ] = NULL;
3513
3514	wiphy->iface_combinations = &mwifiex_iface_comb_ap_sta;
3515	wiphy->n_iface_combinations = 1;
3516
3517	/* Initialize cipher suits */
3518	wiphy->cipher_suites = mwifiex_cipher_suites;
3519	wiphy->n_cipher_suites = ARRAY_SIZE(mwifiex_cipher_suites);
3520
3521	ether_addr_copy(wiphy->perm_addr, adapter->perm_addr);
3522	wiphy->signal_type = CFG80211_SIGNAL_TYPE_MBM;
3523	wiphy->flags |= WIPHY_FLAG_HAVE_AP_SME |
3524			WIPHY_FLAG_AP_PROBE_RESP_OFFLOAD |
3525			WIPHY_FLAG_AP_UAPSD |
3526			WIPHY_FLAG_HAS_REMAIN_ON_CHANNEL |
3527			WIPHY_FLAG_HAS_CHANNEL_SWITCH;
3528
3529	if (ISSUPP_TDLS_ENABLED(adapter->fw_cap_info))
3530		wiphy->flags |= WIPHY_FLAG_SUPPORTS_TDLS |
3531				WIPHY_FLAG_TDLS_EXTERNAL_SETUP;
3532
3533#ifdef CONFIG_PM
3534	wiphy->wowlan = &mwifiex_wowlan_support;
3535#endif
3536
3537	wiphy->coalesce = &mwifiex_coalesce_support;
3538
3539	wiphy->probe_resp_offload = NL80211_PROBE_RESP_OFFLOAD_SUPPORT_WPS |
3540				    NL80211_PROBE_RESP_OFFLOAD_SUPPORT_WPS2 |
3541				    NL80211_PROBE_RESP_OFFLOAD_SUPPORT_P2P;
3542
3543	wiphy->available_antennas_tx = BIT(adapter->number_of_antenna) - 1;
3544	wiphy->available_antennas_rx = BIT(adapter->number_of_antenna) - 1;
3545
3546	wiphy->features |= NL80211_FEATURE_HT_IBSS |
3547			   NL80211_FEATURE_INACTIVITY_TIMER |
3548			   NL80211_FEATURE_NEED_OBSS_SCAN;
3549
3550	if (adapter->fw_api_ver == MWIFIEX_FW_V15)
3551		wiphy->features |= NL80211_FEATURE_SK_TX_STATUS;
3552
3553	/* Reserve space for mwifiex specific private data for BSS */
3554	wiphy->bss_priv_size = sizeof(struct mwifiex_bss_priv);
3555
3556	wiphy->reg_notifier = mwifiex_reg_notifier;
3557
3558	/* Set struct mwifiex_adapter pointer in wiphy_priv */
3559	wdev_priv = wiphy_priv(wiphy);
3560	*(unsigned long *)wdev_priv = (unsigned long)adapter;
3561
3562	set_wiphy_dev(wiphy, priv->adapter->dev);
3563
3564	ret = wiphy_register(wiphy);
3565	if (ret < 0) {
3566		dev_err(adapter->dev,
3567			"%s: wiphy_register failed: %d\n", __func__, ret);
3568		wiphy_free(wiphy);
3569		return ret;
3570	}
3571
3572	if (reg_alpha2 && mwifiex_is_valid_alpha2(reg_alpha2)) {
3573		wiphy_info(wiphy, "driver hint alpha2: %2.2s\n", reg_alpha2);
3574		regulatory_hint(wiphy, reg_alpha2);
3575	} else {
3576		country_code = mwifiex_11d_code_2_region(adapter->region_code);
3577		if (country_code)
3578			wiphy_info(wiphy, "ignoring F/W country code %2.2s\n",
3579				   country_code);
3580	}
3581
3582	mwifiex_send_cmd(priv, HostCmd_CMD_802_11_SNMP_MIB,
3583			 HostCmd_ACT_GEN_GET, FRAG_THRESH_I, &thr, true);
3584	wiphy->frag_threshold = thr;
3585	mwifiex_send_cmd(priv, HostCmd_CMD_802_11_SNMP_MIB,
3586			 HostCmd_ACT_GEN_GET, RTS_THRESH_I, &thr, true);
3587	wiphy->rts_threshold = thr;
3588	mwifiex_send_cmd(priv, HostCmd_CMD_802_11_SNMP_MIB,
3589			 HostCmd_ACT_GEN_GET, SHORT_RETRY_LIM_I, &retry, true);
3590	wiphy->retry_short = (u8) retry;
3591	mwifiex_send_cmd(priv, HostCmd_CMD_802_11_SNMP_MIB,
3592			 HostCmd_ACT_GEN_GET, LONG_RETRY_LIM_I, &retry, true);
3593	wiphy->retry_long = (u8) retry;
3594
3595	adapter->wiphy = wiphy;
3596	return ret;
3597}
3598