1 /*
2  * Copyright (c) 2012-2021 The Linux Foundation. All rights reserved.
3  * Copyright (c) 2021-2024 Qualcomm Innovation Center, Inc. All rights reserved.
4  *
5  * Permission to use, copy, modify, and/or distribute this software for
6  * any purpose with or without fee is hereby granted, provided that the
7  * above copyright notice and this permission notice appear in all
8  * copies.
9  *
10  * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL
11  * WARRANTIES WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED
12  * WARRANTIES OF MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE
13  * AUTHOR BE LIABLE FOR ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL
14  * DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR
15  * PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER
16  * TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR
17  * PERFORMANCE OF THIS SOFTWARE.
18  */
19 
20 /**
21  *  DOC: wlan_hdd_assoc.c
22  *
23  *  WLAN Host Device Driver implementation
24  *
25  */
26 
27 #include "wlan_hdd_includes.h"
28 #include <ani_global.h>
29 #include "dot11f.h"
30 #include "wlan_hdd_power.h"
31 #include "wlan_hdd_trace.h"
32 #include <linux/ieee80211.h>
33 #include <linux/wireless.h>
34 #include <linux/etherdevice.h>
35 #include <net/cfg80211.h>
36 #include "wlan_hdd_cfg80211.h"
37 #include "csr_inside_api.h"
38 #include "wlan_hdd_p2p.h"
39 #include "wlan_hdd_tdls.h"
40 #include "sme_api.h"
41 #include "wlan_hdd_hostapd.h"
42 #include <wlan_hdd_green_ap.h>
43 #include <wlan_hdd_ipa.h>
44 #include "wlan_hdd_lpass.h"
45 #include <wlan_logging_sock_svc.h>
46 #include <cds_sched.h>
47 #include "wlan_policy_mgr_api.h"
48 #include <cds_utils.h>
49 #include "sme_power_save_api.h"
50 #include "wlan_hdd_napi.h"
51 #include <cdp_txrx_cmn.h>
52 #include <cdp_txrx_flow_ctrl_legacy.h>
53 #include <cdp_txrx_peer_ops.h>
54 #include <cdp_txrx_misc.h>
55 #include <cdp_txrx_ctrl.h>
56 #include "ol_txrx.h"
57 #include <wlan_logging_sock_svc.h>
58 #include <wlan_hdd_object_manager.h>
59 #include <cdp_txrx_handle.h>
60 #include "wlan_pmo_ucfg_api.h"
61 #include "wlan_hdd_tsf.h"
62 #include "wlan_utility.h"
63 #include "wlan_p2p_ucfg_api.h"
64 #include "wlan_ipa_ucfg_api.h"
65 #include "wlan_hdd_stats.h"
66 #include "wlan_hdd_scan.h"
67 #include "wlan_crypto_global_api.h"
68 #include "wlan_hdd_bcn_recv.h"
69 #include "wlan_mlme_twt_ucfg_api.h"
70 
71 #include <wlan_cfg80211_crypto.h>
72 #include <wlan_crypto_global_api.h>
73 #include "wlan_dlm_ucfg_api.h"
74 #include "wlan_hdd_sta_info.h"
75 #include "wlan_hdd_ftm_time_sync.h"
76 #include "wlan_cm_roam_api.h"
77 
78 #include <ol_defines.h>
79 #include "wlan_pkt_capture_ucfg_api.h"
80 #include "wlan_if_mgr_ucfg_api.h"
81 #include "wlan_if_mgr_public_struct.h"
82 #include "wlan_cm_public_struct.h"
83 #include "osif_cm_util.h"
84 #include "wlan_hdd_cm_api.h"
85 #include "cm_utf.h"
86 
87 #include "wlan_hdd_bootup_marker.h"
88 #include "wlan_roam_debug.h"
89 
90 #include "wlan_hdd_twt.h"
91 #include "wlan_cm_roam_ucfg_api.h"
92 #include "wlan_hdd_son.h"
93 #include "wlan_dp_ucfg_api.h"
94 #include "wlan_cm_ucfg_api.h"
95 
96 /* These are needed to recognize WPA and RSN suite types */
97 #define HDD_WPA_OUI_SIZE 4
98 #define HDD_RSN_OUI_SIZE 4
99 uint8_t ccp_wpa_oui00[HDD_WPA_OUI_SIZE] = { 0x00, 0x50, 0xf2, 0x00 };
100 uint8_t ccp_wpa_oui01[HDD_WPA_OUI_SIZE] = { 0x00, 0x50, 0xf2, 0x01 };
101 uint8_t ccp_wpa_oui02[HDD_WPA_OUI_SIZE] = { 0x00, 0x50, 0xf2, 0x02 };
102 uint8_t ccp_wpa_oui03[HDD_WPA_OUI_SIZE] = { 0x00, 0x50, 0xf2, 0x03 };
103 uint8_t ccp_wpa_oui04[HDD_WPA_OUI_SIZE] = { 0x00, 0x50, 0xf2, 0x04 };
104 uint8_t ccp_wpa_oui05[HDD_WPA_OUI_SIZE] = { 0x00, 0x50, 0xf2, 0x05 };
105 
106 #ifdef FEATURE_WLAN_ESE
107 /* CCKM */
108 uint8_t ccp_wpa_oui06[HDD_WPA_OUI_SIZE] = { 0x00, 0x40, 0x96, 0x00 };
109 /* CCKM */
110 uint8_t ccp_rsn_oui06[HDD_RSN_OUI_SIZE] = { 0x00, 0x40, 0x96, 0x00 };
111 #endif /* FEATURE_WLAN_ESE */
112 
113 /* group cipher */
114 uint8_t ccp_rsn_oui00[HDD_RSN_OUI_SIZE] = { 0x00, 0x0F, 0xAC, 0x00 };
115 
116 /* WEP-40 or RSN */
117 uint8_t ccp_rsn_oui01[HDD_RSN_OUI_SIZE] = { 0x00, 0x0F, 0xAC, 0x01 };
118 
119 /* TKIP or RSN-PSK */
120 uint8_t ccp_rsn_oui02[HDD_RSN_OUI_SIZE] = { 0x00, 0x0F, 0xAC, 0x02 };
121 
122 /* Reserved */
123 uint8_t ccp_rsn_oui03[HDD_RSN_OUI_SIZE] = { 0x00, 0x0F, 0xAC, 0x03 };
124 
125 /* AES-CCMP */
126 uint8_t ccp_rsn_oui04[HDD_RSN_OUI_SIZE] = { 0x00, 0x0F, 0xAC, 0x04 };
127 
128 /* WEP-104 */
129 uint8_t ccp_rsn_oui05[HDD_RSN_OUI_SIZE] = { 0x00, 0x0F, 0xAC, 0x05 };
130 
131 /* RSN-PSK-SHA256 */
132 uint8_t ccp_rsn_oui07[HDD_RSN_OUI_SIZE] = { 0x00, 0x0F, 0xAC, 0x06 };
133 
134 /* RSN-8021X-SHA256 */
135 uint8_t ccp_rsn_oui08[HDD_RSN_OUI_SIZE] = { 0x00, 0x0F, 0xAC, 0x05 };
136 
137 /* AES-GCMP-128 */
138 uint8_t ccp_rsn_oui09[HDD_RSN_OUI_SIZE] = { 0x00, 0x0F, 0xAC, 0x08 };
139 
140 /* AES-GCMP-256 */
141 uint8_t ccp_rsn_oui0a[HDD_RSN_OUI_SIZE] = { 0x00, 0x0F, 0xAC, 0x09 };
142 #ifdef WLAN_FEATURE_FILS_SK
143 uint8_t ccp_rsn_oui_0e[HDD_RSN_OUI_SIZE] = {0x00, 0x0F, 0xAC, 0x0E};
144 uint8_t ccp_rsn_oui_0f[HDD_RSN_OUI_SIZE] = {0x00, 0x0F, 0xAC, 0x0F};
145 uint8_t ccp_rsn_oui_10[HDD_RSN_OUI_SIZE] = {0x00, 0x0F, 0xAC, 0x10};
146 uint8_t ccp_rsn_oui_11[HDD_RSN_OUI_SIZE] = {0x00, 0x0F, 0xAC, 0x11};
147 #endif
148 uint8_t ccp_rsn_oui_12[HDD_RSN_OUI_SIZE] = {0x50, 0x6F, 0x9A, 0x02};
149 uint8_t ccp_rsn_oui_0b[HDD_RSN_OUI_SIZE] = {0x00, 0x0F, 0xAC, 0x0B};
150 uint8_t ccp_rsn_oui_0c[HDD_RSN_OUI_SIZE] = {0x00, 0x0F, 0xAC, 0x0C};
151 /* FT-SUITE-B AKM */
152 uint8_t ccp_rsn_oui_0d[HDD_RSN_OUI_SIZE] = {0x00, 0x0F, 0xAC, 0x0D};
153 
154 /* OWE https://tools.ietf.org/html/rfc8110 */
155 uint8_t ccp_rsn_oui_18[HDD_RSN_OUI_SIZE] = {0x00, 0x0F, 0xAC, 0x12};
156 
157 #ifdef WLAN_FEATURE_SAE
158 /* SAE AKM */
159 uint8_t ccp_rsn_oui_80[HDD_RSN_OUI_SIZE] = {0x00, 0x0F, 0xAC, 0x08};
160 /* FT SAE AKM */
161 uint8_t ccp_rsn_oui_90[HDD_RSN_OUI_SIZE] = {0x00, 0x0F, 0xAC, 0x09};
162 #endif
163 static const
164 u8 ccp_rsn_oui_13[HDD_RSN_OUI_SIZE] = {0x50, 0x6F, 0x9A, 0x01};
165 
166 #ifdef FEATURE_WLAN_WAPI
167 #define HDD_WAPI_OUI_SIZE 4
168 /* WPI-SMS4 */
169 uint8_t ccp_wapi_oui01[HDD_WAPI_OUI_SIZE] = { 0x00, 0x14, 0x72, 0x01 };
170 /* WAI-PSK */
171 uint8_t ccp_wapi_oui02[HDD_WAPI_OUI_SIZE] = { 0x00, 0x14, 0x72, 0x02 };
172 #endif  /* FEATURE_WLAN_WAPI */
173 
174 /* Offset where the EID-Len-IE, start. */
175 #define ASSOC_RSP_IES_OFFSET 6  /* Capability(2) + AID(2) + Status Code(2) */
176 #define ASSOC_REQ_IES_OFFSET 4  /* Capability(2) + LI(2) */
177 
178 /*
179  * beacon_filter_table - table of IEs used for beacon filtering
180  */
181 static const int beacon_filter_table[] = {
182 	WLAN_ELEMID_DSPARMS,
183 	WLAN_ELEMID_ERP,
184 	WLAN_ELEMID_EDCAPARMS,
185 	WLAN_ELEMID_QOS_CAPABILITY,
186 	WLAN_ELEMID_HTINFO_ANA,
187 	WLAN_ELEMID_OP_MODE_NOTIFY,
188 	WLAN_ELEMID_VHTOP,
189 	WLAN_ELEMID_QUIET_CHANNEL,
190 	WLAN_ELEMID_TWT,
191 #ifdef WLAN_FEATURE_11AX_BSS_COLOR
192 	/*
193 	 * EID: 221 vendor IE is being used temporarily by 11AX
194 	 * bss-color-change IE till it gets any fixed number. This
195 	 * vendor EID needs to be replaced with bss-color-change IE
196 	 * number.
197 	 */
198 	WLAN_ELEMID_VENDOR,
199 #endif
200 };
201 
202 /*
203  * beacon_filter_extn_table - table of extn IEs used for beacon filtering
204  */
205 static const int beacon_filter_extn_table[] = {
206 	WLAN_EXTN_ELEMID_HEOP,
207 	WLAN_EXTN_ELEMID_UORA,
208 	WLAN_EXTN_ELEMID_MUEDCA,
209 #ifdef WLAN_FEATURE_11BE
210 	WLAN_EXTN_ELEMID_EHTOP,
211 #endif
212 };
213 
214 /* HE operation BIT positins */
215 #if defined(WLAN_FEATURE_11AX)
216 #define HE_OPERATION_DFLT_PE_DURATION_POS 0
217 #define HE_OPERATION_TWT_REQUIRED_POS 3
218 #define HE_OPERATION_RTS_THRESHOLD_POS 4
219 #define HE_OPERATION_VHT_OPER_POS 14
220 #define HE_OPERATION_CO_LOCATED_BSS_POS 15
221 #define HE_OPERATION_ER_SU_DISABLE_POS 16
222 #define HE_OPERATION_OPER_INFO_6G_POS 17
223 #define HE_OPERATION_RESERVED_POS 18
224 #define HE_OPERATION_BSS_COLOR_POS 24
225 #define HE_OPERATION_PARTIAL_BSS_COLOR_POS 30
226 #define HE_OPERATION_BSS_COL_DISABLED_POS 31
227 #endif
228 
229 /* EHT operation BIT positins */
230 #if defined(WLAN_FEATURE_11BE)
231 #define EHT_OPER_BASIC_RX_NSS_MCS_0_TO_7_POS 0
232 #define EHT_OPER_BASIC_TX_NSS_MCS_0_TO_7_POS 4
233 #define EHT_OPER_BASIC_RX_NSS_MCS_8_AND_9_POS 8
234 #define EHT_OPER_BASIC_TX_NSS_MCS_8_AND_9_POS 12
235 #define EHT_OPER_BASIC_RX_NSS_MCS_10_AND_11_POS 16
236 #define EHT_OPER_BASIC_TX_NSS_MCS_10_AND_11_POS 20
237 #define EHT_OPER_BASIC_RX_NSS_MCS_12_AND_13_POS 24
238 #define EHT_OPER_BASIC_TX_NSS_MCS_12_AND_13_POS 28
239 #endif
240 
241 #if defined(WLAN_FEATURE_SAE) && \
242 		(defined(CFG80211_EXTERNAL_AUTH_SUPPORT) || \
243 		LINUX_VERSION_CODE >= KERNEL_VERSION(4, 17, 0))
244 #if defined (CFG80211_SAE_AUTH_TA_ADDR_SUPPORT)
245 /**
246  * wlan_hdd_sae_copy_ta_addr() - Send TA address to supplicant
247  * @params: pointer to external auth params
248  * @link_info: Link info pointer in HDD adapter
249  *
250  * This API is used to copy TA address info in supplicant structure.
251  *
252  * Return: None
253  */
254 static inline
wlan_hdd_sae_copy_ta_addr(struct cfg80211_external_auth_params * params,struct wlan_hdd_link_info * link_info)255 void wlan_hdd_sae_copy_ta_addr(struct cfg80211_external_auth_params *params,
256 			       struct wlan_hdd_link_info *link_info)
257 {
258 	struct qdf_mac_addr ta = QDF_MAC_ADDR_ZERO_INIT;
259 	QDF_STATUS status = QDF_STATUS_SUCCESS;
260 	uint8_t *link_addr;
261 
262 	status = ucfg_cm_get_sae_auth_ta(link_info->adapter->hdd_ctx->pdev,
263 					 link_info->vdev_id,
264 					 &ta);
265 	if (QDF_IS_STATUS_SUCCESS(status))
266 		qdf_ether_addr_copy(params->tx_addr, ta.bytes);
267 	else if (wlan_vdev_mlme_is_mlo_vdev(link_info->vdev)) {
268 		link_addr = wlan_vdev_mlme_get_linkaddr(link_info->vdev);
269 		qdf_ether_addr_copy(params->tx_addr, link_addr);
270 	}
271 
272 	hdd_debug("status:%d ta:" QDF_MAC_ADDR_FMT, status,
273 		  QDF_MAC_ADDR_REF(params->tx_addr));
274 
275 }
276 #else
277 static inline
wlan_hdd_sae_copy_ta_addr(struct cfg80211_external_auth_params * params,struct wlan_hdd_link_info * link_info)278 void wlan_hdd_sae_copy_ta_addr(struct cfg80211_external_auth_params *params,
279 			       struct wlan_hdd_link_info *link_info)
280 {
281 }
282 #endif
283 
284 #if defined(WLAN_FEATURE_11BE_MLO) && defined(WLAN_EXTERNAL_AUTH_MLO_SUPPORT)
285 /**
286  * wlan_hdd_sae_update_mld_addr() - Send mld address to supplicant
287  * @params: pointer to external auth params
288  * @link_info: Link info pointer in HDD adapter
289  *
290  * This API is used to copy MLD address info in supplicant structure.
291  *
292  * Return: QDF_STATUS
293  */
294 static inline QDF_STATUS
wlan_hdd_sae_update_mld_addr(struct cfg80211_external_auth_params * params,struct wlan_hdd_link_info * link_info)295 wlan_hdd_sae_update_mld_addr(struct cfg80211_external_auth_params *params,
296 			     struct wlan_hdd_link_info *link_info)
297 {
298 	struct qdf_mac_addr mld_addr;
299 	struct qdf_mac_addr *mld_roaming_addr;
300 	QDF_STATUS status = QDF_STATUS_SUCCESS;
301 	struct wlan_objmgr_vdev *vdev;
302 
303 	if (!link_info->vdev)
304 		return QDF_STATUS_E_INVAL;
305 
306 	vdev = link_info->vdev;
307 	wlan_objmgr_vdev_get_ref(vdev, WLAN_HDD_ID_OBJ_MGR);
308 
309 	if (!ucfg_cm_is_sae_auth_addr_conversion_required(vdev))
310 		goto end;
311 
312 	if (ucfg_cm_is_vdev_roaming(vdev)) {
313 		/*
314 		 * while roaming, peer is not created yet till authentication
315 		 * So retrieving the MLD address which is cached from the
316 		 * scan entry.
317 		 */
318 		mld_roaming_addr = ucfg_cm_roaming_get_peer_mld_addr(vdev);
319 		if (!mld_roaming_addr) {
320 			status = QDF_STATUS_E_INVAL;
321 			goto end;
322 		}
323 		mld_addr = *mld_roaming_addr;
324 	} else {
325 		status = wlan_vdev_get_bss_peer_mld_mac(vdev, &mld_addr);
326 		if (QDF_IS_STATUS_ERROR(status)) {
327 			status = QDF_STATUS_E_INVAL;
328 			goto end;
329 		}
330 	}
331 
332 	qdf_mem_copy(params->mld_addr, mld_addr.bytes, QDF_MAC_ADDR_SIZE);
333 	hdd_debug("Sending MLD:" QDF_MAC_ADDR_FMT" to userspace",
334 		  QDF_MAC_ADDR_REF(mld_addr.bytes));
335 
336 end:
337 	wlan_objmgr_vdev_release_ref(vdev, WLAN_HDD_ID_OBJ_MGR);
338 	return status;
339 }
340 #else
341 static inline QDF_STATUS
wlan_hdd_sae_update_mld_addr(struct cfg80211_external_auth_params * params,struct wlan_hdd_link_info * link_info)342 wlan_hdd_sae_update_mld_addr(struct cfg80211_external_auth_params *params,
343 			     struct wlan_hdd_link_info *link_info)
344 {
345 	return QDF_STATUS_SUCCESS;
346 }
347 #endif
348 
349 /**
350  * wlan_hdd_get_keymgmt_for_sae_akm() - Get the keymgmt OUI
351  * corresponding to the SAE AKM type
352  * @akm: AKM type
353  *
354  * This API is used to get the keymgmt OUI for the SAE AKM type.
355  * Return: keymgmt OUI
356  */
357 static uint32_t
wlan_hdd_get_keymgmt_for_sae_akm(uint32_t akm)358 wlan_hdd_get_keymgmt_for_sae_akm(uint32_t akm)
359 {
360 	if (akm == WLAN_AKM_SAE)
361 		return WLAN_AKM_SUITE_SAE;
362 	else if (akm == WLAN_AKM_FT_SAE)
363 		return WLAN_AKM_SUITE_FT_OVER_SAE;
364 	else if (akm == WLAN_AKM_SAE_EXT_KEY)
365 		return WLAN_AKM_SUITE_SAE_EXT_KEY;
366 	else if (akm == WLAN_AKM_FT_SAE_EXT_KEY)
367 		return WLAN_AKM_SUITE_FT_SAE_EXT_KEY;
368 	/**
369 	 * Legacy FW doesn't support SAE-EXK-KEY or
370 	 * Cross-SAE_AKM roaming. In such cases, send
371 	 * SAE for both SAE and FT-SAE AKMs. The supplicant
372 	 * has backward compatibility to handle this case.
373 	 */
374 	else
375 		return WLAN_AKM_SUITE_SAE;
376 }
377 
378 /**
379  * wlan_hdd_sae_callback() - Sends SAE info to supplicant
380  * @link_info: Link info pointer in HDD adapter
381  * @roam_info: pointer to roam info
382  *
383  * This API is used to send required SAE info to trigger SAE in supplicant.
384  *
385  * Return: None
386  */
wlan_hdd_sae_callback(struct wlan_hdd_link_info * link_info,struct csr_roam_info * roam_info)387 static void wlan_hdd_sae_callback(struct wlan_hdd_link_info *link_info,
388 				  struct csr_roam_info *roam_info)
389 {
390 	struct hdd_adapter *adapter = link_info->adapter;
391 	struct hdd_context *hdd_ctx = adapter->hdd_ctx;
392 	int flags;
393 	struct sir_sae_info *sae_info = roam_info->sae_info;
394 	struct cfg80211_external_auth_params params = {0};
395 	QDF_STATUS status;
396 
397 	if (wlan_hdd_validate_context(hdd_ctx))
398 		return;
399 
400 	if (!sae_info) {
401 		hdd_err("SAE info in NULL");
402 		return;
403 	}
404 
405 	flags = cds_get_gfp_flags();
406 
407 	params.key_mgmt_suite =
408 		wlan_hdd_get_keymgmt_for_sae_akm(sae_info->akm);
409 
410 	params.action = NL80211_EXTERNAL_AUTH_START;
411 	qdf_ether_addr_copy(params.bssid, sae_info->peer_mac_addr.bytes);
412 	wlan_hdd_sae_copy_ta_addr(&params, link_info);
413 	status = wlan_hdd_sae_update_mld_addr(&params, link_info);
414 	if (QDF_IS_STATUS_ERROR(status))
415 		return;
416 
417 	qdf_mem_copy(params.ssid.ssid, sae_info->ssid.ssId,
418 		     sae_info->ssid.length);
419 	params.ssid.ssid_len = sae_info->ssid.length;
420 	cfg80211_external_auth_request(adapter->dev, &params, flags);
421 	hdd_debug("SAE: sent cmd");
422 }
423 #else
wlan_hdd_sae_callback(struct wlan_hdd_link_info * link_info,struct csr_roam_info * roam_info)424 static inline void wlan_hdd_sae_callback(struct wlan_hdd_link_info *link_info,
425 					 struct csr_roam_info *roam_info)
426 { }
427 #endif
428 
429 /**
430  * hdd_start_powersave_timer_on_associated() - Start auto powersave timer
431  *  after associated
432  *  @link_info: Link info pointer in HDD adapter
433  *
434  * This function will start auto powersave timer for STA/P2P Client.
435  *
436  * Return: none
437  */
438 static void
hdd_start_powersave_timer_on_associated(struct wlan_hdd_link_info * link_info)439 hdd_start_powersave_timer_on_associated(struct wlan_hdd_link_info *link_info)
440 {
441 	uint32_t timeout;
442 	uint32_t auto_bmps_timer_val;
443 	struct hdd_adapter *adapter = link_info->adapter;
444 	struct hdd_context *hdd_ctx = WLAN_HDD_GET_CTX(adapter);
445 
446 	if (adapter->device_mode != QDF_STA_MODE &&
447 	    adapter->device_mode != QDF_P2P_CLIENT_MODE)
448 		return;
449 
450 	ucfg_mlme_get_auto_bmps_timer_value(hdd_ctx->psoc,
451 					    &auto_bmps_timer_val);
452 	timeout = hdd_cm_is_vdev_roaming(link_info) ?
453 		AUTO_PS_ENTRY_TIMER_DEFAULT_VALUE :
454 		(auto_bmps_timer_val * 1000);
455 	sme_ps_enable_auto_ps_timer(hdd_ctx->mac_handle,
456 				    link_info->vdev_id,
457 				    timeout);
458 }
459 
hdd_conn_set_authenticated(struct wlan_hdd_link_info * link_info,uint8_t auth_state)460 void hdd_conn_set_authenticated(struct wlan_hdd_link_info *link_info,
461 				uint8_t auth_state)
462 {
463 	struct hdd_station_ctx *sta_ctx;
464 	struct wlan_objmgr_vdev *vdev;
465 	char *auth_time;
466 	uint32_t time_buffer_size;
467 
468 	sta_ctx = WLAN_HDD_GET_STATION_CTX_PTR(link_info);
469 	/* save the new connection state */
470 	hdd_debug("Authenticated state Changed from oldState:%d to State:%d",
471 		  sta_ctx->conn_info.is_authenticated, auth_state);
472 	sta_ctx->conn_info.is_authenticated = auth_state;
473 
474 	vdev = hdd_objmgr_get_vdev_by_user(link_info, WLAN_DP_ID);
475 	if (vdev) {
476 		ucfg_dp_conn_info_set_peer_authenticate(vdev, auth_state);
477 		hdd_objmgr_put_vdev_by_user(vdev, WLAN_DP_ID);
478 	}
479 
480 	auth_time = sta_ctx->conn_info.auth_time;
481 	time_buffer_size = sizeof(sta_ctx->conn_info.auth_time);
482 
483 	if (auth_state)
484 		qdf_get_time_of_the_day_in_hr_min_sec_usec(auth_time,
485 							   time_buffer_size);
486 	else
487 		qdf_mem_zero(auth_time, time_buffer_size);
488 	if (auth_state &&
489 	    (sta_ctx->conn_info.ptk_installed ||
490 	     sta_ctx->conn_info.uc_encrypt_type == eCSR_ENCRYPT_TYPE_NONE))
491 		hdd_start_powersave_timer_on_associated(link_info);
492 }
493 
hdd_conn_set_connection_state(struct hdd_adapter * adapter,eConnectionState conn_state)494 void hdd_conn_set_connection_state(struct hdd_adapter *adapter,
495 				   eConnectionState conn_state)
496 {
497 	struct hdd_station_ctx *hdd_sta_ctx =
498 		WLAN_HDD_GET_STATION_CTX_PTR(adapter->deflink);
499 
500 	/* save the new connection state */
501 	if (conn_state == hdd_sta_ctx->conn_info.conn_state)
502 		return;
503 
504 	hdd_nofl_debug("connection state changed %d --> %d for dev %s (vdev %d)",
505 		       hdd_sta_ctx->conn_info.conn_state, conn_state,
506 		       adapter->dev->name, adapter->deflink->vdev_id);
507 
508 	hdd_sta_ctx->conn_info.conn_state = conn_state;
509 }
510 
hdd_conn_get_connected_band(struct wlan_hdd_link_info * link_info)511 enum band_info hdd_conn_get_connected_band(struct wlan_hdd_link_info *link_info)
512 {
513 	struct hdd_station_ctx *sta_ctx;
514 	uint32_t sta_freq = 0;
515 
516 	sta_ctx = WLAN_HDD_GET_STATION_CTX_PTR(link_info);
517 	if (hdd_cm_is_vdev_associated(link_info))
518 		sta_freq = sta_ctx->conn_info.chan_freq;
519 
520 	if (wlan_reg_is_24ghz_ch_freq(sta_freq))
521 		return BAND_2G;
522 	else if (wlan_reg_is_5ghz_ch_freq(sta_freq) ||
523 		 wlan_reg_is_6ghz_chan_freq(sta_freq))
524 		return BAND_5G;
525 	else   /* If station is not connected return as BAND_ALL */
526 		return BAND_ALL;
527 }
528 
529 /**
530  * hdd_conn_get_connected_cipher_algo() - get current connection cipher type
531  * @link_info: Link info pointer in HDD adapter.
532  * @sta_ctx: pointer to global HDD Station context
533  * @pConnectedCipherAlgo: pointer to connected cipher algo
534  *
535  * Return: false if any errors encountered, true otherwise
536  */
537 static inline bool
hdd_conn_get_connected_cipher_algo(struct wlan_hdd_link_info * link_info,struct hdd_station_ctx * sta_ctx,eCsrEncryptionType * pConnectedCipherAlgo)538 hdd_conn_get_connected_cipher_algo(struct wlan_hdd_link_info *link_info,
539 				   struct hdd_station_ctx *sta_ctx,
540 				   eCsrEncryptionType *pConnectedCipherAlgo)
541 {
542 	bool connected;
543 
544 	connected = hdd_cm_is_vdev_associated(link_info);
545 	if (pConnectedCipherAlgo)
546 		*pConnectedCipherAlgo = sta_ctx->conn_info.uc_encrypt_type;
547 
548 	return connected;
549 }
550 
551 struct wlan_hdd_link_info *
hdd_get_sta_connection_in_progress(struct hdd_context * hdd_ctx)552 hdd_get_sta_connection_in_progress(struct hdd_context *hdd_ctx)
553 {
554 	struct hdd_adapter *adapter = NULL, *next_adapter = NULL;
555 	wlan_net_dev_ref_dbgid dbgid =
556 				NET_DEV_HOLD_GET_STA_CONNECTION_IN_PROGRESS;
557 	struct wlan_hdd_link_info *link_info;
558 
559 	if (!hdd_ctx) {
560 		hdd_err("HDD context is NULL");
561 		return NULL;
562 	}
563 
564 	hdd_for_each_adapter_dev_held_safe(hdd_ctx, adapter, next_adapter,
565 					   dbgid) {
566 		if ((QDF_STA_MODE == adapter->device_mode) ||
567 		    (QDF_P2P_CLIENT_MODE == adapter->device_mode) ||
568 		    (QDF_P2P_DEVICE_MODE == adapter->device_mode)) {
569 			hdd_adapter_for_each_active_link_info(adapter,
570 							      link_info) {
571 				if (!hdd_cm_is_connecting(link_info))
572 					continue;
573 
574 				hdd_debug("vdev_id %d: Connection is in progress",
575 					  link_info->vdev_id);
576 				hdd_adapter_dev_put_debug(adapter, dbgid);
577 				if (next_adapter)
578 					hdd_adapter_dev_put_debug(next_adapter,
579 								  dbgid);
580 				return link_info;
581 			}
582 		}
583 		hdd_adapter_dev_put_debug(adapter, dbgid);
584 	}
585 	return NULL;
586 }
587 
hdd_abort_ongoing_sta_connection(struct hdd_context * hdd_ctx)588 void hdd_abort_ongoing_sta_connection(struct hdd_context *hdd_ctx)
589 {
590 	struct wlan_hdd_link_info *link_info;
591 
592 	link_info = hdd_get_sta_connection_in_progress(hdd_ctx);
593 	if (link_info &&
594 	    !wlan_vdev_mlme_is_mlo_link_switch_in_progress(link_info->vdev))
595 		wlan_hdd_cm_issue_disconnect(link_info,
596 					     REASON_UNSPEC_FAILURE, false);
597 }
598 
hdd_abort_ongoing_sta_sae_connection(struct hdd_context * hdd_ctx)599 void hdd_abort_ongoing_sta_sae_connection(struct hdd_context *hdd_ctx)
600 {
601 	struct wlan_hdd_link_info *link_info;
602 	struct wlan_objmgr_vdev *vdev;
603 	int32_t key_mgmt;
604 
605 	link_info = hdd_get_sta_connection_in_progress(hdd_ctx);
606 	if (!link_info ||
607 	    wlan_vdev_mlme_is_mlo_link_switch_in_progress(link_info->vdev))
608 		return;
609 
610 	vdev = hdd_objmgr_get_vdev_by_user(link_info->adapter->deflink,
611 					   WLAN_OSIF_ID);
612 	if (!vdev)
613 		return;
614 
615 	key_mgmt = wlan_crypto_get_param(vdev, WLAN_CRYPTO_PARAM_KEY_MGMT);
616 	hdd_objmgr_put_vdev_by_user(vdev, WLAN_OSIF_ID);
617 
618 	if (key_mgmt < 0) {
619 		hdd_debug_rl("Invalid key_mgmt: %d", key_mgmt);
620 		return;
621 	}
622 
623 	if (QDF_HAS_PARAM(key_mgmt, WLAN_CRYPTO_KEY_MGMT_SAE) ||
624 	    QDF_HAS_PARAM(key_mgmt, WLAN_CRYPTO_KEY_MGMT_FT_SAE) ||
625 	    QDF_HAS_PARAM(key_mgmt, WLAN_CRYPTO_KEY_MGMT_SAE_EXT_KEY) ||
626 	    QDF_HAS_PARAM(key_mgmt, WLAN_CRYPTO_KEY_MGMT_FT_SAE_EXT_KEY))
627 		wlan_hdd_cm_issue_disconnect(link_info->adapter->deflink,
628 					     REASON_DISASSOC_NETWORK_LEAVING,
629 					     false);
630 }
631 
hdd_get_first_connected_sta_vdev_id(struct hdd_context * hdd_ctx,uint32_t * vdev_id)632 QDF_STATUS hdd_get_first_connected_sta_vdev_id(struct hdd_context *hdd_ctx,
633 					       uint32_t *vdev_id)
634 {
635 	struct hdd_adapter *adapter = NULL, *next_adapter = NULL;
636 	wlan_net_dev_ref_dbgid dbgid = NET_DEV_HOLD_IS_ANY_STA_CONNECTED;
637 	struct wlan_hdd_link_info *link_info;
638 
639 	if (!hdd_ctx) {
640 		hdd_err("HDD context is NULL");
641 		return QDF_STATUS_E_INVAL;
642 	}
643 
644 	hdd_for_each_adapter_dev_held_safe(hdd_ctx, adapter, next_adapter,
645 					   dbgid) {
646 		if (adapter->device_mode == QDF_STA_MODE ||
647 		    adapter->device_mode == QDF_P2P_CLIENT_MODE) {
648 			hdd_adapter_for_each_active_link_info(adapter,
649 							      link_info) {
650 				if (!hdd_cm_is_vdev_connected(link_info))
651 					continue;
652 
653 				*vdev_id = link_info->vdev_id;
654 				hdd_adapter_dev_put_debug(adapter, dbgid);
655 				if (next_adapter)
656 					hdd_adapter_dev_put_debug(next_adapter,
657 								  dbgid);
658 				return QDF_STATUS_SUCCESS;
659 			}
660 		}
661 		hdd_adapter_dev_put_debug(adapter, dbgid);
662 	}
663 	return QDF_STATUS_E_FAILURE;
664 }
665 
hdd_is_any_sta_connected(struct hdd_context * hdd_ctx)666 bool hdd_is_any_sta_connected(struct hdd_context *hdd_ctx)
667 {
668 	QDF_STATUS status;
669 	uint32_t vdev_id;
670 
671 	status = hdd_get_first_connected_sta_vdev_id(hdd_ctx, &vdev_id);
672 	return QDF_IS_STATUS_ERROR(status) ? false : true;
673 }
674 
675 /**
676  * hdd_remove_beacon_filter() - remove beacon filter
677  * @adapter: Pointer to the hdd adapter
678  *
679  * Return: 0 on success and errno on failure
680  */
hdd_remove_beacon_filter(struct hdd_adapter * adapter)681 int hdd_remove_beacon_filter(struct hdd_adapter *adapter)
682 {
683 	QDF_STATUS status;
684 	struct hdd_context *hdd_ctx = WLAN_HDD_GET_CTX(adapter);
685 
686 	status = sme_remove_beacon_filter(hdd_ctx->mac_handle,
687 					  adapter->deflink->vdev_id);
688 	if (!QDF_IS_STATUS_SUCCESS(status)) {
689 		hdd_err("sme_remove_beacon_filter() failed");
690 		return -EFAULT;
691 	}
692 
693 	return 0;
694 }
695 
hdd_add_beacon_filter(struct hdd_adapter * adapter)696 int hdd_add_beacon_filter(struct hdd_adapter *adapter)
697 {
698 	int i;
699 	uint32_t ie_map[SIR_BCN_FLT_MAX_ELEMS_IE_LIST] = {0};
700 	QDF_STATUS status;
701 	struct hdd_context *hdd_ctx = WLAN_HDD_GET_CTX(adapter);
702 
703 	for (i = 0; i < ARRAY_SIZE(beacon_filter_table); i++)
704 		qdf_set_bit(beacon_filter_table[i],
705 			    (unsigned long *)ie_map);
706 
707 	for (i = 0; i < ARRAY_SIZE(beacon_filter_extn_table); i++)
708 		qdf_set_bit(beacon_filter_extn_table[i] + WLAN_ELEMID_EXTN_ELEM,
709 			    (unsigned long *)ie_map);
710 
711 	status = sme_add_beacon_filter(hdd_ctx->mac_handle,
712 				       adapter->deflink->vdev_id, ie_map);
713 	if (!QDF_IS_STATUS_SUCCESS(status)) {
714 		hdd_err("sme_add_beacon_filter() failed");
715 		return -EFAULT;
716 	}
717 	return 0;
718 }
719 
hdd_copy_ht_caps(struct ieee80211_ht_cap * hdd_ht_cap,tDot11fIEHTCaps * roam_ht_cap)720 void hdd_copy_ht_caps(struct ieee80211_ht_cap *hdd_ht_cap,
721 		      tDot11fIEHTCaps *roam_ht_cap)
722 
723 {
724 	uint32_t i, temp_ht_cap;
725 
726 	qdf_mem_zero(hdd_ht_cap, sizeof(struct ieee80211_ht_cap));
727 
728 	if (roam_ht_cap->advCodingCap)
729 		hdd_ht_cap->cap_info |= IEEE80211_HT_CAP_LDPC_CODING;
730 	if (roam_ht_cap->supportedChannelWidthSet)
731 		hdd_ht_cap->cap_info |= IEEE80211_HT_CAP_SUP_WIDTH_20_40;
732 	temp_ht_cap = roam_ht_cap->mimoPowerSave &
733 	    (IEEE80211_HT_CAP_SM_PS >> IEEE80211_HT_CAP_SM_PS_SHIFT);
734 	if (temp_ht_cap)
735 		hdd_ht_cap->cap_info |=
736 			temp_ht_cap << IEEE80211_HT_CAP_SM_PS_SHIFT;
737 	if (roam_ht_cap->greenField)
738 		hdd_ht_cap->cap_info |= IEEE80211_HT_CAP_GRN_FLD;
739 	if (roam_ht_cap->shortGI20MHz)
740 		hdd_ht_cap->cap_info |= IEEE80211_HT_CAP_SGI_20;
741 	if (roam_ht_cap->shortGI40MHz)
742 		hdd_ht_cap->cap_info |= IEEE80211_HT_CAP_SGI_40;
743 	if (roam_ht_cap->txSTBC)
744 		hdd_ht_cap->cap_info |= IEEE80211_HT_CAP_TX_STBC;
745 	temp_ht_cap = roam_ht_cap->rxSTBC & (IEEE80211_HT_CAP_RX_STBC >>
746 	    IEEE80211_HT_CAP_RX_STBC_SHIFT);
747 	if (temp_ht_cap)
748 		hdd_ht_cap->cap_info |=
749 			temp_ht_cap << IEEE80211_HT_CAP_RX_STBC_SHIFT;
750 	if (roam_ht_cap->delayedBA)
751 		hdd_ht_cap->cap_info |= IEEE80211_HT_CAP_DELAY_BA;
752 	if (roam_ht_cap->maximalAMSDUsize)
753 		hdd_ht_cap->cap_info |= IEEE80211_HT_CAP_MAX_AMSDU;
754 	if (roam_ht_cap->dsssCckMode40MHz)
755 		hdd_ht_cap->cap_info |= IEEE80211_HT_CAP_DSSSCCK40;
756 	if (roam_ht_cap->psmp)
757 		hdd_ht_cap->cap_info |= IEEE80211_HT_CAP_RESERVED;
758 	if (roam_ht_cap->stbcControlFrame)
759 		hdd_ht_cap->cap_info |= IEEE80211_HT_CAP_40MHZ_INTOLERANT;
760 	if (roam_ht_cap->lsigTXOPProtection)
761 		hdd_ht_cap->cap_info |= IEEE80211_HT_CAP_LSIG_TXOP_PROT;
762 
763 	/* 802.11n HT capability AMPDU settings (for ampdu_params_info) */
764 	if (roam_ht_cap->maxRxAMPDUFactor)
765 		hdd_ht_cap->ampdu_params_info |=
766 			IEEE80211_HT_AMPDU_PARM_FACTOR;
767 	temp_ht_cap = roam_ht_cap->mpduDensity &
768 	    (IEEE80211_HT_AMPDU_PARM_DENSITY >>
769 	     IEEE80211_HT_AMPDU_PARM_DENSITY_SHIFT);
770 	if (temp_ht_cap)
771 		hdd_ht_cap->ampdu_params_info |=
772 		temp_ht_cap << IEEE80211_HT_AMPDU_PARM_DENSITY_SHIFT;
773 
774 	/* 802.11n HT extended capabilities masks */
775 	if (roam_ht_cap->pco)
776 		hdd_ht_cap->extended_ht_cap_info |=
777 			IEEE80211_HT_EXT_CAP_PCO;
778 	temp_ht_cap = roam_ht_cap->transitionTime &
779 	    (IEEE80211_HT_EXT_CAP_PCO_TIME >>
780 	    IEEE80211_HT_EXT_CAP_PCO_TIME_SHIFT);
781 	if (temp_ht_cap)
782 		hdd_ht_cap->extended_ht_cap_info |=
783 			temp_ht_cap << IEEE80211_HT_EXT_CAP_PCO_TIME_SHIFT;
784 	temp_ht_cap = roam_ht_cap->mcsFeedback &
785 	    (IEEE80211_HT_EXT_CAP_MCS_FB >> IEEE80211_HT_EXT_CAP_MCS_FB_SHIFT);
786 	if (temp_ht_cap)
787 		hdd_ht_cap->extended_ht_cap_info |=
788 			temp_ht_cap << IEEE80211_HT_EXT_CAP_MCS_FB_SHIFT;
789 
790 	/* tx_bf_cap_info capabilities */
791 	if (roam_ht_cap->txBF)
792 		hdd_ht_cap->tx_BF_cap_info |= TX_BF_CAP_INFO_TX_BF;
793 	if (roam_ht_cap->rxStaggeredSounding)
794 		hdd_ht_cap->tx_BF_cap_info |=
795 			TX_BF_CAP_INFO_RX_STAG_RED_SOUNDING;
796 	if (roam_ht_cap->txStaggeredSounding)
797 		hdd_ht_cap->tx_BF_cap_info |=
798 			TX_BF_CAP_INFO_TX_STAG_RED_SOUNDING;
799 	if (roam_ht_cap->rxZLF)
800 		hdd_ht_cap->tx_BF_cap_info |= TX_BF_CAP_INFO_RX_ZFL;
801 	if (roam_ht_cap->txZLF)
802 		hdd_ht_cap->tx_BF_cap_info |= TX_BF_CAP_INFO_TX_ZFL;
803 	if (roam_ht_cap->implicitTxBF)
804 		hdd_ht_cap->tx_BF_cap_info |= TX_BF_CAP_INFO_IMP_TX_BF;
805 	temp_ht_cap = roam_ht_cap->calibration &
806 	    (TX_BF_CAP_INFO_CALIBRATION >> TX_BF_CAP_INFO_CALIBRATION_SHIFT);
807 	if (temp_ht_cap)
808 		hdd_ht_cap->tx_BF_cap_info |=
809 			temp_ht_cap << TX_BF_CAP_INFO_CALIBRATION_SHIFT;
810 	if (roam_ht_cap->explicitCSITxBF)
811 		hdd_ht_cap->tx_BF_cap_info |= TX_BF_CAP_INFO_EXP_CSIT_BF;
812 	if (roam_ht_cap->explicitUncompressedSteeringMatrix)
813 		hdd_ht_cap->tx_BF_cap_info |=
814 			TX_BF_CAP_INFO_EXP_UNCOMP_STEER_MAT;
815 	temp_ht_cap = roam_ht_cap->explicitBFCSIFeedback &
816 	    (TX_BF_CAP_INFO_EXP_BF_CSI_FB >>
817 	     TX_BF_CAP_INFO_EXP_BF_CSI_FB_SHIFT);
818 	if (temp_ht_cap)
819 		hdd_ht_cap->tx_BF_cap_info |=
820 			temp_ht_cap << TX_BF_CAP_INFO_EXP_BF_CSI_FB_SHIFT;
821 	temp_ht_cap =
822 	    roam_ht_cap->explicitUncompressedSteeringMatrixFeedback &
823 	    (TX_BF_CAP_INFO_EXP_UNCMP_STEER_MAT >>
824 	     TX_BF_CAP_INFO_EXP_UNCMP_STEER_MAT_SHIFT);
825 	if (temp_ht_cap)
826 		hdd_ht_cap->tx_BF_cap_info |=
827 			temp_ht_cap <<
828 			TX_BF_CAP_INFO_EXP_UNCMP_STEER_MAT_SHIFT;
829 	temp_ht_cap =
830 	    roam_ht_cap->explicitCompressedSteeringMatrixFeedback &
831 	    (TX_BF_CAP_INFO_EXP_CMP_STEER_MAT_FB >>
832 	     TX_BF_CAP_INFO_EXP_CMP_STEER_MAT_FB_SHIFT);
833 	if (temp_ht_cap)
834 		hdd_ht_cap->tx_BF_cap_info |=
835 			temp_ht_cap <<
836 				TX_BF_CAP_INFO_EXP_CMP_STEER_MAT_FB_SHIFT;
837 	temp_ht_cap = roam_ht_cap->csiNumBFAntennae &
838 	    (TX_BF_CAP_INFO_CSI_NUM_BF_ANT >>
839 	     TX_BF_CAP_INFO_CSI_NUM_BF_ANT_SHIFT);
840 	if (temp_ht_cap)
841 		hdd_ht_cap->tx_BF_cap_info |=
842 			temp_ht_cap << TX_BF_CAP_INFO_CSI_NUM_BF_ANT_SHIFT;
843 	temp_ht_cap = roam_ht_cap->uncompressedSteeringMatrixBFAntennae &
844 	    (TX_BF_CAP_INFO_UNCOMP_STEER_MAT_BF_ANT >>
845 	     TX_BF_CAP_INFO_UNCOMP_STEER_MAT_BF_ANT_SHIFT);
846 	if (temp_ht_cap)
847 		hdd_ht_cap->tx_BF_cap_info |=
848 			temp_ht_cap <<
849 				TX_BF_CAP_INFO_UNCOMP_STEER_MAT_BF_ANT_SHIFT;
850 	temp_ht_cap = roam_ht_cap->compressedSteeringMatrixBFAntennae &
851 	    (TX_BF_CAP_INFO_COMP_STEER_MAT_BF_ANT >>
852 	     TX_BF_CAP_INFO_COMP_STEER_MAT_BF_ANT_SHIFT);
853 	if (temp_ht_cap)
854 		hdd_ht_cap->tx_BF_cap_info |=
855 			temp_ht_cap <<
856 				TX_BF_CAP_INFO_COMP_STEER_MAT_BF_ANT_SHIFT;
857 
858 	/* antenna selection */
859 	if (roam_ht_cap->antennaSelection)
860 		hdd_ht_cap->antenna_selection_info |= ANTENNA_SEL_INFO;
861 	if (roam_ht_cap->explicitCSIFeedbackTx)
862 		hdd_ht_cap->antenna_selection_info |=
863 			ANTENNA_SEL_INFO_EXP_CSI_FB_TX;
864 	if (roam_ht_cap->antennaIndicesFeedbackTx)
865 		hdd_ht_cap->antenna_selection_info |=
866 			ANTENNA_SEL_INFO_ANT_ID_FB_TX;
867 	if (roam_ht_cap->explicitCSIFeedback)
868 		hdd_ht_cap->antenna_selection_info |=
869 			ANTENNA_SEL_INFO_EXP_CSI_FB;
870 	if (roam_ht_cap->antennaIndicesFeedback)
871 		hdd_ht_cap->antenna_selection_info |=
872 			ANTENNA_SEL_INFO_ANT_ID_FB;
873 	if (roam_ht_cap->rxAS)
874 		hdd_ht_cap->antenna_selection_info |=
875 			ANTENNA_SEL_INFO_RX_AS;
876 	if (roam_ht_cap->txSoundingPPDUs)
877 		hdd_ht_cap->antenna_selection_info |=
878 			ANTENNA_SEL_INFO_TX_SOUNDING_PPDU;
879 
880 	/* mcs data rate */
881 	for (i = 0; i < IEEE80211_HT_MCS_MASK_LEN; ++i)
882 		hdd_ht_cap->mcs.rx_mask[i] =
883 			roam_ht_cap->supportedMCSSet[i];
884 	hdd_ht_cap->mcs.rx_highest =
885 			((short) (roam_ht_cap->supportedMCSSet[11]) << 8) |
886 			((short) (roam_ht_cap->supportedMCSSet[10]));
887 	hdd_ht_cap->mcs.tx_params =
888 			roam_ht_cap->supportedMCSSet[12];
889 }
890 
891 #define VHT_CAP_MAX_MPDU_LENGTH_MASK 0x00000003
892 #define VHT_CAP_SUPP_CHAN_WIDTH_MASK_SHIFT 2
893 #define VHT_CAP_RXSTBC_MASK_SHIFT 8
894 #define VHT_CAP_BEAMFORMEE_STS_SHIFT 13
895 #define VHT_CAP_BEAMFORMEE_STS_MASK \
896 	(0x0000e000 >> VHT_CAP_BEAMFORMEE_STS_SHIFT)
897 #define VHT_CAP_SOUNDING_DIMENSIONS_SHIFT 16
898 #define VHT_CAP_SOUNDING_DIMENSIONS_MASK \
899 	(0x00070000 >> VHT_CAP_SOUNDING_DIMENSIONS_SHIFT)
900 #define VHT_CAP_MAX_A_MPDU_LENGTH_EXPONENT_MASK_SHIFT 23
901 #define VHT_CAP_MAX_A_MPDU_LENGTH_EXPONENT_MASK \
902 	(0x03800000 >> VHT_CAP_MAX_A_MPDU_LENGTH_EXPONENT_MASK_SHIFT)
903 #define VHT_CAP_VHT_LINK_ADAPTATION_VHT_MRQ_MFB_SHIFT 26
904 
hdd_copy_vht_caps(struct ieee80211_vht_cap * hdd_vht_cap,tDot11fIEVHTCaps * roam_vht_cap)905 void hdd_copy_vht_caps(struct ieee80211_vht_cap *hdd_vht_cap,
906 		       tDot11fIEVHTCaps *roam_vht_cap)
907 {
908 	uint32_t temp_vht_cap;
909 
910 	qdf_mem_zero(hdd_vht_cap, sizeof(struct ieee80211_vht_cap));
911 
912 	temp_vht_cap = roam_vht_cap->maxMPDULen & VHT_CAP_MAX_MPDU_LENGTH_MASK;
913 	hdd_vht_cap->vht_cap_info |= temp_vht_cap;
914 	temp_vht_cap = roam_vht_cap->supportedChannelWidthSet &
915 		(IEEE80211_VHT_CAP_SUPP_CHAN_WIDTH_MASK >>
916 			VHT_CAP_SUPP_CHAN_WIDTH_MASK_SHIFT);
917 	if (temp_vht_cap) {
918 		if (roam_vht_cap->supportedChannelWidthSet &
919 		    (IEEE80211_VHT_CAP_SUPP_CHAN_WIDTH_160MHZ >>
920 			VHT_CAP_SUPP_CHAN_WIDTH_MASK_SHIFT))
921 			hdd_vht_cap->vht_cap_info |=
922 				temp_vht_cap <<
923 				IEEE80211_VHT_CAP_SUPP_CHAN_WIDTH_160MHZ;
924 		if (roam_vht_cap->supportedChannelWidthSet &
925 		    (IEEE80211_VHT_CAP_SUPP_CHAN_WIDTH_160_80PLUS80MHZ >>
926 			VHT_CAP_SUPP_CHAN_WIDTH_MASK_SHIFT))
927 			hdd_vht_cap->vht_cap_info |=
928 			temp_vht_cap <<
929 			IEEE80211_VHT_CAP_SUPP_CHAN_WIDTH_160_80PLUS80MHZ;
930 	}
931 	if (roam_vht_cap->ldpcCodingCap)
932 		hdd_vht_cap->vht_cap_info |= IEEE80211_VHT_CAP_RXLDPC;
933 	if (roam_vht_cap->shortGI80MHz)
934 		hdd_vht_cap->vht_cap_info |= IEEE80211_VHT_CAP_SHORT_GI_80;
935 	if (roam_vht_cap->shortGI160and80plus80MHz)
936 		hdd_vht_cap->vht_cap_info |= IEEE80211_VHT_CAP_SHORT_GI_160;
937 	if (roam_vht_cap->txSTBC)
938 		hdd_vht_cap->vht_cap_info |= IEEE80211_VHT_CAP_TXSTBC;
939 	temp_vht_cap = roam_vht_cap->rxSTBC & (IEEE80211_VHT_CAP_RXSTBC_MASK >>
940 		VHT_CAP_RXSTBC_MASK_SHIFT);
941 	if (temp_vht_cap)
942 		hdd_vht_cap->vht_cap_info |=
943 			temp_vht_cap << VHT_CAP_RXSTBC_MASK_SHIFT;
944 	if (roam_vht_cap->suBeamFormerCap)
945 		hdd_vht_cap->vht_cap_info |=
946 			IEEE80211_VHT_CAP_SU_BEAMFORMER_CAPABLE;
947 	if (roam_vht_cap->suBeamformeeCap)
948 		hdd_vht_cap->vht_cap_info |=
949 			IEEE80211_VHT_CAP_SU_BEAMFORMEE_CAPABLE;
950 	temp_vht_cap = roam_vht_cap->csnofBeamformerAntSup &
951 			(VHT_CAP_BEAMFORMEE_STS_MASK);
952 	if (temp_vht_cap)
953 		hdd_vht_cap->vht_cap_info |=
954 			temp_vht_cap << VHT_CAP_BEAMFORMEE_STS_SHIFT;
955 	temp_vht_cap = roam_vht_cap->numSoundingDim &
956 			(VHT_CAP_SOUNDING_DIMENSIONS_MASK);
957 	if (temp_vht_cap)
958 		hdd_vht_cap->vht_cap_info |=
959 			temp_vht_cap << VHT_CAP_SOUNDING_DIMENSIONS_SHIFT;
960 	if (roam_vht_cap->muBeamformerCap)
961 		hdd_vht_cap->vht_cap_info |=
962 			IEEE80211_VHT_CAP_MU_BEAMFORMER_CAPABLE;
963 	if (roam_vht_cap->muBeamformeeCap)
964 		hdd_vht_cap->vht_cap_info |=
965 			IEEE80211_VHT_CAP_MU_BEAMFORMEE_CAPABLE;
966 	if (roam_vht_cap->vhtTXOPPS)
967 		hdd_vht_cap->vht_cap_info |=
968 			IEEE80211_VHT_CAP_VHT_TXOP_PS;
969 	if (roam_vht_cap->htcVHTCap)
970 		hdd_vht_cap->vht_cap_info |=
971 			IEEE80211_VHT_CAP_HTC_VHT;
972 	temp_vht_cap = roam_vht_cap->maxAMPDULenExp &
973 			(VHT_CAP_MAX_A_MPDU_LENGTH_EXPONENT_MASK);
974 	if (temp_vht_cap)
975 		hdd_vht_cap->vht_cap_info |=
976 			temp_vht_cap <<
977 			VHT_CAP_MAX_A_MPDU_LENGTH_EXPONENT_MASK_SHIFT;
978 	temp_vht_cap = roam_vht_cap->vhtLinkAdaptCap &
979 		(IEEE80211_VHT_CAP_VHT_LINK_ADAPTATION_VHT_MRQ_MFB >>
980 		 VHT_CAP_VHT_LINK_ADAPTATION_VHT_MRQ_MFB_SHIFT);
981 	if (temp_vht_cap)
982 		hdd_vht_cap->vht_cap_info |= temp_vht_cap <<
983 			VHT_CAP_VHT_LINK_ADAPTATION_VHT_MRQ_MFB_SHIFT;
984 	if (roam_vht_cap->rxAntPattern)
985 		hdd_vht_cap->vht_cap_info |=
986 			IEEE80211_VHT_CAP_RX_ANTENNA_PATTERN;
987 	if (roam_vht_cap->txAntPattern)
988 		hdd_vht_cap->vht_cap_info |=
989 			IEEE80211_VHT_CAP_TX_ANTENNA_PATTERN;
990 	hdd_vht_cap->supp_mcs.rx_mcs_map = roam_vht_cap->rxMCSMap;
991 	hdd_vht_cap->supp_mcs.rx_highest =
992 		((uint16_t)roam_vht_cap->rxHighSupDataRate);
993 	hdd_vht_cap->supp_mcs.tx_mcs_map = roam_vht_cap->txMCSMap;
994 	hdd_vht_cap->supp_mcs.tx_highest =
995 		((uint16_t)roam_vht_cap->txSupDataRate);
996 }
997 
998 /* ht param */
999 #define HT_PARAM_CONTROLLED_ACCESS_ONLY 0x10
1000 #define HT_PARAM_SERVICE_INT_GRAN 0xe0
1001 #define HT_PARAM_SERVICE_INT_GRAN_SHIFT 5
1002 
1003 /* operatinon mode */
1004 #define HT_OP_MODE_TX_BURST_LIMIT 0x0008
1005 
1006 /* stbc_param */
1007 #define HT_STBC_PARAM_MCS 0x007f
1008 
hdd_copy_ht_operation(struct hdd_station_ctx * hdd_sta_ctx,tDot11fIEHTInfo * ht_ops)1009 void hdd_copy_ht_operation(struct hdd_station_ctx *hdd_sta_ctx,
1010 			   tDot11fIEHTInfo *ht_ops)
1011 {
1012 	struct ieee80211_ht_operation *hdd_ht_ops =
1013 		&hdd_sta_ctx->conn_info.ht_operation;
1014 	uint32_t i, temp_ht_ops;
1015 
1016 	qdf_mem_zero(hdd_ht_ops, sizeof(struct ieee80211_ht_operation));
1017 
1018 	hdd_ht_ops->primary_chan = ht_ops->primaryChannel;
1019 
1020 	/* HT_PARAMS */
1021 	temp_ht_ops = ht_ops->secondaryChannelOffset &
1022 		IEEE80211_HT_PARAM_CHA_SEC_OFFSET;
1023 	if (temp_ht_ops)
1024 		hdd_ht_ops->ht_param |= temp_ht_ops;
1025 	else
1026 		hdd_ht_ops->ht_param = IEEE80211_HT_PARAM_CHA_SEC_NONE;
1027 	if (ht_ops->recommendedTxWidthSet)
1028 		hdd_ht_ops->ht_param |= IEEE80211_HT_PARAM_CHAN_WIDTH_ANY;
1029 	if (ht_ops->rifsMode)
1030 		hdd_ht_ops->ht_param |= IEEE80211_HT_PARAM_RIFS_MODE;
1031 	if (ht_ops->controlledAccessOnly)
1032 		hdd_ht_ops->ht_param |= HT_PARAM_CONTROLLED_ACCESS_ONLY;
1033 	temp_ht_ops = ht_ops->serviceIntervalGranularity &
1034 		(HT_PARAM_SERVICE_INT_GRAN >> HT_PARAM_SERVICE_INT_GRAN_SHIFT);
1035 	if (temp_ht_ops)
1036 		hdd_ht_ops->ht_param |= temp_ht_ops <<
1037 			HT_PARAM_SERVICE_INT_GRAN_SHIFT;
1038 
1039 	/* operation mode */
1040 	temp_ht_ops = ht_ops->opMode &
1041 			IEEE80211_HT_OP_MODE_PROTECTION;
1042 	switch (temp_ht_ops) {
1043 	case IEEE80211_HT_OP_MODE_PROTECTION_NONMEMBER:
1044 		hdd_ht_ops->operation_mode |=
1045 			IEEE80211_HT_OP_MODE_PROTECTION_NONMEMBER;
1046 		break;
1047 	case IEEE80211_HT_OP_MODE_PROTECTION_20MHZ:
1048 		hdd_ht_ops->operation_mode |=
1049 			IEEE80211_HT_OP_MODE_PROTECTION_20MHZ;
1050 		break;
1051 	case IEEE80211_HT_OP_MODE_PROTECTION_NONHT_MIXED:
1052 		hdd_ht_ops->operation_mode |=
1053 			IEEE80211_HT_OP_MODE_PROTECTION_NONHT_MIXED;
1054 		break;
1055 	case IEEE80211_HT_OP_MODE_PROTECTION_NONE:
1056 	default:
1057 		hdd_ht_ops->operation_mode |=
1058 			IEEE80211_HT_OP_MODE_PROTECTION_NONE;
1059 	}
1060 	if (ht_ops->nonGFDevicesPresent)
1061 		hdd_ht_ops->operation_mode |=
1062 			IEEE80211_HT_OP_MODE_NON_GF_STA_PRSNT;
1063 	if (ht_ops->transmitBurstLimit)
1064 		hdd_ht_ops->operation_mode |=
1065 			HT_OP_MODE_TX_BURST_LIMIT;
1066 	if (ht_ops->obssNonHTStaPresent)
1067 		hdd_ht_ops->operation_mode |=
1068 			IEEE80211_HT_OP_MODE_NON_HT_STA_PRSNT;
1069 
1070 	if (ht_ops->chan_center_freq_seg2)
1071 		hdd_ht_ops->operation_mode |=
1072 			(ht_ops->chan_center_freq_seg2 << IEEE80211_HT_OP_MODE_CCFS2_SHIFT);
1073 	/* stbc_param */
1074 	temp_ht_ops = ht_ops->basicSTBCMCS &
1075 			HT_STBC_PARAM_MCS;
1076 	if (temp_ht_ops)
1077 		hdd_ht_ops->stbc_param |= temp_ht_ops;
1078 	if (ht_ops->dualCTSProtection)
1079 		hdd_ht_ops->stbc_param |=
1080 			IEEE80211_HT_STBC_PARAM_DUAL_CTS_PROT;
1081 	if (ht_ops->secondaryBeacon)
1082 		hdd_ht_ops->stbc_param |=
1083 			IEEE80211_HT_STBC_PARAM_STBC_BEACON;
1084 	if (ht_ops->lsigTXOPProtectionFullSupport)
1085 		hdd_ht_ops->stbc_param |=
1086 			IEEE80211_HT_STBC_PARAM_LSIG_TXOP_FULLPROT;
1087 	if (ht_ops->pcoActive)
1088 		hdd_ht_ops->stbc_param |=
1089 			IEEE80211_HT_STBC_PARAM_PCO_ACTIVE;
1090 	if (ht_ops->pcoPhase)
1091 		hdd_ht_ops->stbc_param |=
1092 			IEEE80211_HT_STBC_PARAM_PCO_PHASE;
1093 
1094 	/* basic MCs set */
1095 	for (i = 0; i < 16; ++i)
1096 		hdd_ht_ops->basic_set[i] =
1097 			ht_ops->basicMCSSet[i];
1098 }
1099 
1100 #if LINUX_VERSION_CODE >= KERNEL_VERSION(4, 12, 0)
hdd_copy_vht_center_freq(struct ieee80211_vht_operation * ieee_ops,tDot11fIEVHTOperation * roam_ops)1101 static void hdd_copy_vht_center_freq(struct ieee80211_vht_operation *ieee_ops,
1102 				     tDot11fIEVHTOperation *roam_ops)
1103 {
1104 	ieee_ops->center_freq_seg0_idx = roam_ops->chan_center_freq_seg0;
1105 	ieee_ops->center_freq_seg1_idx = roam_ops->chan_center_freq_seg1;
1106 }
1107 #else
hdd_copy_vht_center_freq(struct ieee80211_vht_operation * ieee_ops,tDot11fIEVHTOperation * roam_ops)1108 static void hdd_copy_vht_center_freq(struct ieee80211_vht_operation *ieee_ops,
1109 				     tDot11fIEVHTOperation *roam_ops)
1110 {
1111 	ieee_ops->center_freq_seg1_idx = roam_ops->chan_center_freq_seg0;
1112 	ieee_ops->center_freq_seg2_idx = roam_ops->chan_center_freq_seg1;
1113 }
1114 #endif /* KERNEL_VERSION(4, 12, 0) */
1115 
hdd_copy_vht_operation(struct hdd_station_ctx * hdd_sta_ctx,tDot11fIEVHTOperation * vht_ops)1116 void hdd_copy_vht_operation(struct hdd_station_ctx *hdd_sta_ctx,
1117 			    tDot11fIEVHTOperation *vht_ops)
1118 {
1119 	struct ieee80211_vht_operation *hdd_vht_ops =
1120 		&hdd_sta_ctx->conn_info.vht_operation;
1121 
1122 	qdf_mem_zero(hdd_vht_ops, sizeof(struct ieee80211_vht_operation));
1123 
1124 	hdd_vht_ops->chan_width = vht_ops->chanWidth;
1125 	hdd_copy_vht_center_freq(hdd_vht_ops, vht_ops);
1126 	hdd_vht_ops->basic_mcs_set = vht_ops->basicMCSSet;
1127 }
1128 
1129 #if (LINUX_VERSION_CODE >= KERNEL_VERSION(6, 5, 0)) && \
1130 	defined(WLAN_FEATURE_11BE)
hdd_copy_eht_operation(struct hdd_station_ctx * hdd_sta_ctx,tDot11fIEeht_op * eht_ops)1131 void hdd_copy_eht_operation(struct hdd_station_ctx *hdd_sta_ctx,
1132 			    tDot11fIEeht_op *eht_ops)
1133 {
1134 	struct ieee80211_eht_operation *hdd_eht_ops =
1135 		&hdd_sta_ctx->conn_info.eht_operation;
1136 	struct ieee80211_eht_mcs_nss_supp_20mhz_only  mcs_param;
1137 	uint32_t filled = 0, len = 0;
1138 
1139 	qdf_mem_zero(hdd_eht_ops, sizeof(struct ieee80211_eht_operation));
1140 
1141 	if (!eht_ops->eht_op_information_present)
1142 		return;
1143 
1144 	/* Min length if op_info_present */
1145 	len += 3;
1146 
1147 	hdd_eht_ops->params |= IEEE80211_EHT_OPER_INFO_PRESENT;
1148 
1149 	if (eht_ops->eht_default_pe_duration)
1150 		hdd_eht_ops->params |=
1151 			IEEE80211_EHT_OPER_EHT_DEF_PE_DURATION;
1152 	if (eht_ops->group_addr_bu_indication_limit)
1153 		hdd_eht_ops->params |=
1154 			IEEE80211_EHT_OPER_GROUP_ADDRESSED_BU_IND_LIMIT;
1155 	if (eht_ops->group_addr_bu_indication_exponent)
1156 		hdd_eht_ops->params |=
1157 			IEEE80211_EHT_OPER_GROUP_ADDRESSED_BU_IND_EXP_MASK;
1158 
1159 	mcs_param.rx_tx_mcs7_max_nss =
1160 		eht_ops->basic_rx_max_nss_for_mcs_0_to_7 <<
1161 					EHT_OPER_BASIC_RX_NSS_MCS_0_TO_7_POS;
1162 	mcs_param.rx_tx_mcs7_max_nss |=
1163 		eht_ops->basic_tx_max_nss_for_mcs_0_to_7 <<
1164 					EHT_OPER_BASIC_TX_NSS_MCS_0_TO_7_POS;
1165 	mcs_param.rx_tx_mcs9_max_nss =
1166 		eht_ops->basic_rx_max_nss_for_mcs_8_and_9 <<
1167 					EHT_OPER_BASIC_RX_NSS_MCS_8_AND_9_POS;
1168 	mcs_param.rx_tx_mcs9_max_nss |=
1169 		eht_ops->basic_tx_max_nss_for_mcs_8_and_9 <<
1170 					EHT_OPER_BASIC_TX_NSS_MCS_8_AND_9_POS;
1171 	mcs_param.rx_tx_mcs11_max_nss =
1172 		eht_ops->basic_rx_max_nss_for_mcs_10_and_11 <<
1173 					EHT_OPER_BASIC_RX_NSS_MCS_10_AND_11_POS;
1174 	mcs_param.rx_tx_mcs11_max_nss |=
1175 		eht_ops->basic_tx_max_nss_for_mcs_10_and_11 <<
1176 					EHT_OPER_BASIC_TX_NSS_MCS_10_AND_11_POS;
1177 	mcs_param.rx_tx_mcs13_max_nss =
1178 		eht_ops->basic_rx_max_nss_for_mcs_12_and_13 <<
1179 					EHT_OPER_BASIC_RX_NSS_MCS_12_AND_13_POS;
1180 	mcs_param.rx_tx_mcs13_max_nss |=
1181 		eht_ops->basic_tx_max_nss_for_mcs_12_and_13 <<
1182 					EHT_OPER_BASIC_TX_NSS_MCS_12_AND_13_POS;
1183 
1184 	hdd_eht_ops->basic_mcs_nss = mcs_param;
1185 	hdd_eht_ops->optional[filled++] = eht_ops->channel_width;
1186 	hdd_eht_ops->optional[filled++] = eht_ops->ccfs0;
1187 	hdd_eht_ops->optional[filled++] = eht_ops->ccfs1;
1188 
1189 	if (eht_ops->disabled_sub_chan_bitmap_present) {
1190 		hdd_eht_ops->params |=
1191 			IEEE80211_EHT_OPER_DISABLED_SUBCHANNEL_BITMAP_PRESENT;
1192 		len += 2;
1193 		hdd_eht_ops->optional[filled++] =
1194 				eht_ops->disabled_sub_chan_bitmap[0][0];
1195 		hdd_eht_ops->optional[filled++] =
1196 				eht_ops->disabled_sub_chan_bitmap[0][1];
1197 	}
1198 	hdd_sta_ctx->conn_info.eht_oper_len =
1199 				sizeof(struct ieee80211_eht_operation) + len;
1200 }
1201 #elif (LINUX_VERSION_CODE >= KERNEL_VERSION(6, 0, 0)) && \
1202 	defined(WLAN_FEATURE_11BE)
hdd_copy_eht_operation(struct hdd_station_ctx * hdd_sta_ctx,tDot11fIEeht_op * eht_ops)1203 void hdd_copy_eht_operation(struct hdd_station_ctx *hdd_sta_ctx,
1204 			    tDot11fIEeht_op *eht_ops)
1205 {
1206 	struct ieee80211_eht_operation *hdd_eht_ops =
1207 		&hdd_sta_ctx->conn_info.eht_operation;
1208 	uint32_t mcs_param = 0, filled = 0, len = 0;
1209 
1210 	qdf_mem_zero(hdd_eht_ops, sizeof(struct ieee80211_eht_operation));
1211 
1212 	if (!eht_ops->eht_op_information_present)
1213 		return;
1214 
1215 	/* Min length if op_info_present */
1216 	len += 3;
1217 
1218 	hdd_eht_ops->params |= IEEE80211_EHT_OPER_INFO_PRESENT;
1219 
1220 	if (eht_ops->eht_default_pe_duration)
1221 		hdd_eht_ops->params |=
1222 			IEEE80211_EHT_OPER_EHT_DEF_PE_DURATION;
1223 	if (eht_ops->group_addr_bu_indication_limit)
1224 		hdd_eht_ops->params |=
1225 			IEEE80211_EHT_OPER_GROUP_ADDRESSED_BU_IND_LIMIT;
1226 	if (eht_ops->group_addr_bu_indication_exponent)
1227 		hdd_eht_ops->params |=
1228 			IEEE80211_EHT_OPER_GROUP_ADDRESSED_BU_IND_EXP_MASK;
1229 
1230 	mcs_param |= eht_ops->basic_rx_max_nss_for_mcs_0_to_7 <<
1231 				EHT_OPER_BASIC_RX_NSS_MCS_0_TO_7_POS;
1232 	mcs_param |= eht_ops->basic_tx_max_nss_for_mcs_0_to_7 <<
1233 				EHT_OPER_BASIC_TX_NSS_MCS_0_TO_7_POS;
1234 	mcs_param |= eht_ops->basic_rx_max_nss_for_mcs_8_and_9 <<
1235 				EHT_OPER_BASIC_RX_NSS_MCS_8_AND_9_POS;
1236 	mcs_param |= eht_ops->basic_tx_max_nss_for_mcs_8_and_9 <<
1237 				EHT_OPER_BASIC_TX_NSS_MCS_8_AND_9_POS;
1238 	mcs_param |= eht_ops->basic_rx_max_nss_for_mcs_10_and_11 <<
1239 				EHT_OPER_BASIC_RX_NSS_MCS_10_AND_11_POS;
1240 	mcs_param |= eht_ops->basic_tx_max_nss_for_mcs_10_and_11 <<
1241 				EHT_OPER_BASIC_TX_NSS_MCS_10_AND_11_POS;
1242 	mcs_param |= eht_ops->basic_rx_max_nss_for_mcs_12_and_13 <<
1243 				EHT_OPER_BASIC_RX_NSS_MCS_12_AND_13_POS;
1244 	mcs_param |= eht_ops->basic_tx_max_nss_for_mcs_12_and_13 <<
1245 				EHT_OPER_BASIC_TX_NSS_MCS_12_AND_13_POS;
1246 
1247 	hdd_eht_ops->basic_mcs_nss = mcs_param;
1248 	hdd_eht_ops->optional[filled++] = eht_ops->channel_width;
1249 	hdd_eht_ops->optional[filled++] = eht_ops->ccfs0;
1250 	hdd_eht_ops->optional[filled++] = eht_ops->ccfs1;
1251 
1252 	if (eht_ops->disabled_sub_chan_bitmap_present) {
1253 		hdd_eht_ops->params |=
1254 			IEEE80211_EHT_OPER_DISABLED_SUBCHANNEL_BITMAP_PRESENT;
1255 		len += 2;
1256 		hdd_eht_ops->optional[filled++] =
1257 				eht_ops->disabled_sub_chan_bitmap[0][0];
1258 		hdd_eht_ops->optional[filled++] =
1259 				eht_ops->disabled_sub_chan_bitmap[0][1];
1260 	}
1261 	hdd_sta_ctx->conn_info.eht_oper_len =
1262 				sizeof(struct ieee80211_eht_operation) + len;
1263 }
1264 #elif (LINUX_VERSION_CODE >= KERNEL_VERSION(5, 18, 0)) && \
1265 	defined(WLAN_FEATURE_11BE)
hdd_copy_eht_operation(struct hdd_station_ctx * hdd_sta_ctx,tDot11fIEeht_op * eht_ops)1266 void hdd_copy_eht_operation(struct hdd_station_ctx *hdd_sta_ctx,
1267 			    tDot11fIEeht_op *eht_ops)
1268 {
1269 	struct ieee80211_eht_operation *hdd_eht_ops =
1270 		&hdd_sta_ctx->conn_info.eht_operation;
1271 	uint32_t filled = 0, len = 0;
1272 
1273 	qdf_mem_zero(hdd_eht_ops, sizeof(struct ieee80211_eht_operation));
1274 
1275 	if (!eht_ops->eht_op_information_present)
1276 		return;
1277 
1278 	hdd_eht_ops->chan_width = eht_ops->channel_width;
1279 	hdd_eht_ops->ccfs = eht_ops->ccfs0;
1280 	hdd_eht_ops->present_bm = eht_ops->disabled_sub_chan_bitmap_present;
1281 
1282 	if (eht_ops->disabled_sub_chan_bitmap_present) {
1283 		hdd_eht_ops->disable_subchannel_bitmap[filled++] =
1284 				eht_ops->disabled_sub_chan_bitmap[0][0];
1285 		hdd_eht_ops->disable_subchannel_bitmap[filled++] =
1286 				eht_ops->disabled_sub_chan_bitmap[0][1];
1287 		len += 2;
1288 	}
1289 	hdd_sta_ctx->conn_info.eht_oper_len =
1290 				sizeof(struct ieee80211_eht_operation) + len;
1291 }
1292 #endif
1293 
1294 #if (LINUX_VERSION_CODE >= KERNEL_VERSION(4, 19, 0)) && \
1295      defined(WLAN_FEATURE_11AX)
hdd_copy_he_operation(struct hdd_station_ctx * hdd_sta_ctx,tDot11fIEhe_op * he_operation)1296 void hdd_copy_he_operation(struct hdd_station_ctx *hdd_sta_ctx,
1297 			   tDot11fIEhe_op *he_operation)
1298 {
1299 	struct ieee80211_he_operation *hdd_he_operation;
1300 	uint32_t he_oper_params = 0;
1301 	uint32_t len = 0, filled = 0;
1302 	uint8_t he_oper_6g_params = 0;
1303 	uint32_t he_oper_len;
1304 
1305 	if (!he_operation->present)
1306 		return;
1307 	if (he_operation->vht_oper_present)
1308 		len += 3;
1309 	if (he_operation->co_located_bss)
1310 		len += 1;
1311 	if (he_operation->oper_info_6g_present)
1312 		len += 5;
1313 
1314 	he_oper_len = sizeof(struct ieee80211_he_operation) + len;
1315 
1316 	hdd_he_operation = qdf_mem_malloc(he_oper_len);
1317 	if (!hdd_he_operation)
1318 		return;
1319 
1320 	/* Fill he_oper_params */
1321 	he_oper_params |= he_operation->default_pe <<
1322 					HE_OPERATION_DFLT_PE_DURATION_POS;
1323 	he_oper_params |= he_operation->twt_required <<
1324 					HE_OPERATION_TWT_REQUIRED_POS;
1325 	he_oper_params |= he_operation->txop_rts_threshold <<
1326 					HE_OPERATION_RTS_THRESHOLD_POS;
1327 	he_oper_params |= he_operation->vht_oper_present <<
1328 					HE_OPERATION_VHT_OPER_POS;
1329 	he_oper_params |= he_operation->co_located_bss <<
1330 					HE_OPERATION_CO_LOCATED_BSS_POS;
1331 	he_oper_params |= he_operation->er_su_disable <<
1332 					HE_OPERATION_ER_SU_DISABLE_POS;
1333 	he_oper_params |= he_operation->oper_info_6g_present <<
1334 					HE_OPERATION_OPER_INFO_6G_POS;
1335 	he_oper_params |= he_operation->reserved2 <<
1336 					HE_OPERATION_RESERVED_POS;
1337 	he_oper_params |= he_operation->bss_color <<
1338 					HE_OPERATION_BSS_COLOR_POS;
1339 	he_oper_params |= he_operation->partial_bss_col <<
1340 					HE_OPERATION_PARTIAL_BSS_COLOR_POS;
1341 	he_oper_params |= he_operation->bss_col_disabled <<
1342 					HE_OPERATION_BSS_COL_DISABLED_POS;
1343 
1344 	hdd_he_operation->he_oper_params = he_oper_params;
1345 
1346 	/* Fill he_mcs_nss set */
1347 	qdf_mem_copy(&hdd_he_operation->he_mcs_nss_set,
1348 		     he_operation->basic_mcs_nss,
1349 		     sizeof(hdd_he_operation->he_mcs_nss_set));
1350 
1351 	/* Fill he_params_optional fields */
1352 
1353 	if (he_operation->vht_oper_present) {
1354 		hdd_he_operation->optional[filled++] =
1355 			he_operation->vht_oper.info.chan_width;
1356 		hdd_he_operation->optional[filled++] =
1357 			he_operation->vht_oper.info.center_freq_seg0;
1358 		hdd_he_operation->optional[filled++] =
1359 			he_operation->vht_oper.info.center_freq_seg1;
1360 	}
1361 	if (he_operation->co_located_bss)
1362 		hdd_he_operation->optional[filled++] =
1363 				he_operation->maxbssid_ind.info.data;
1364 
1365 	if (he_operation->oper_info_6g_present) {
1366 		hdd_he_operation->optional[filled++] =
1367 			he_operation->oper_info_6g.info.primary_ch;
1368 		he_oper_6g_params |=
1369 			he_operation->oper_info_6g.info.ch_width << 0;
1370 		he_oper_6g_params |=
1371 			he_operation->oper_info_6g.info.dup_bcon << 2;
1372 		he_oper_6g_params |=
1373 			he_operation->oper_info_6g.info.reserved << 3;
1374 
1375 		hdd_he_operation->optional[filled++] = he_oper_6g_params;
1376 		hdd_he_operation->optional[filled++] =
1377 			he_operation->oper_info_6g.info.center_freq_seg0;
1378 		hdd_he_operation->optional[filled++] =
1379 			he_operation->oper_info_6g.info.center_freq_seg1;
1380 		hdd_he_operation->optional[filled] =
1381 				he_operation->oper_info_6g.info.min_rate;
1382 	}
1383 
1384 	if (hdd_sta_ctx->cache_conn_info.he_operation) {
1385 		qdf_mem_free(hdd_sta_ctx->cache_conn_info.he_operation);
1386 		hdd_sta_ctx->cache_conn_info.he_operation = NULL;
1387 	}
1388 
1389 	hdd_sta_ctx->cache_conn_info.he_oper_len = he_oper_len;
1390 
1391 	hdd_sta_ctx->cache_conn_info.he_operation = hdd_he_operation;
1392 }
1393 #endif
1394 
hdd_is_roam_sync_in_progress(struct hdd_context * hdd_ctx,uint8_t vdev_id)1395 bool hdd_is_roam_sync_in_progress(struct hdd_context *hdd_ctx, uint8_t vdev_id)
1396 {
1397 	return wlan_cm_is_roam_sync_in_progress(hdd_ctx->psoc, vdev_id);
1398 }
1399 
hdd_conn_remove_connect_info(struct hdd_station_ctx * sta_ctx)1400 void hdd_conn_remove_connect_info(struct hdd_station_ctx *sta_ctx)
1401 {
1402 	/* Remove bssid and peer_macaddr */
1403 	qdf_mem_zero(&sta_ctx->conn_info.bssid, QDF_MAC_ADDR_SIZE);
1404 	qdf_mem_zero(&sta_ctx->conn_info.peer_macaddr[0],
1405 		     QDF_MAC_ADDR_SIZE);
1406 
1407 	/* Clear all security settings */
1408 	sta_ctx->conn_info.auth_type = eCSR_AUTH_TYPE_OPEN_SYSTEM;
1409 	sta_ctx->conn_info.uc_encrypt_type = eCSR_ENCRYPT_TYPE_NONE;
1410 
1411 	sta_ctx->conn_info.proxy_arp_service = 0;
1412 
1413 	qdf_mem_zero(&sta_ctx->conn_info.ssid, sizeof(tCsrSSIDInfo));
1414 
1415 	/*
1416 	 * Reset the ptk, gtk status flags to avoid using current connection
1417 	 * status in further connections.
1418 	 */
1419 	sta_ctx->conn_info.gtk_installed = false;
1420 	sta_ctx->conn_info.ptk_installed = false;
1421 }
1422 
hdd_clear_roam_profile_ie(struct hdd_adapter * adapter)1423 void hdd_clear_roam_profile_ie(struct hdd_adapter *adapter)
1424 {
1425 	hdd_enter();
1426 
1427 #ifdef FEATURE_WLAN_WAPI
1428 	adapter->wapi_info.wapi_auth_mode = WAPI_AUTH_MODE_OPEN;
1429 	adapter->wapi_info.wapi_mode = false;
1430 #endif
1431 
1432 	hdd_exit();
1433 }
1434 
1435 #if defined(QCA_LL_LEGACY_TX_FLOW_CONTROL) || defined(QCA_LL_TX_FLOW_CONTROL_V2)
hdd_set_unpause_queue(void * soc,uint8_t vdev_id)1436 static inline void hdd_set_unpause_queue(void *soc, uint8_t vdev_id)
1437 {
1438 	cdp_fc_vdev_unpause(soc, vdev_id,
1439 			    OL_TXQ_PAUSE_REASON_PEER_UNAUTHORIZED, 0);
1440 }
1441 #else
hdd_set_unpause_queue(void * soc,uint8_t vdev_id)1442 static inline void hdd_set_unpause_queue(void *soc, uint8_t vdev_id)
1443 {
1444 }
1445 #endif
1446 
1447 #ifdef FEATURE_WDS
1448 /**
1449  * hdd_config_wds_repeater_mode() - configures vdev for wds repeater mode
1450  * @link_info: Link info pointer in HDD adapter
1451  * @peer_addr: peer mac address
1452  *
1453  * Configure dp vdev to detect and drop multicast echo packets and enable
1454  * 4 address frame format in fw.
1455  *
1456  * Return: None
1457  */
hdd_config_wds_repeater_mode(struct wlan_hdd_link_info * link_info,uint8_t * peer_addr)1458 static void hdd_config_wds_repeater_mode(struct wlan_hdd_link_info *link_info,
1459 					 uint8_t *peer_addr)
1460 {
1461 	cdp_config_param_type vdev_param;
1462 	ol_txrx_soc_handle soc = cds_get_context(QDF_MODULE_ID_SOC);
1463 
1464 	vdev_param.cdp_vdev_param_mec = true;
1465 	if (cdp_txrx_set_vdev_param(soc, link_info->vdev_id,
1466 				    CDP_ENABLE_MEC, vdev_param))
1467 		hdd_debug("Failed to set MEC param on DP vdev");
1468 
1469 	hdd_nofl_info("Turn on 4 address for peer: " QDF_MAC_ADDR_FMT,
1470 		      QDF_MAC_ADDR_REF(peer_addr));
1471 	if (sme_set_peer_param(peer_addr, WMI_HOST_PEER_USE_4ADDR, true,
1472 			       link_info->vdev_id))
1473 		hdd_err("Failed to enable WDS on vdev");
1474 }
1475 #else
1476 static inline void
hdd_config_wds_repeater_mode(struct wlan_hdd_link_info * link_info,uint8_t * peer_addr)1477 hdd_config_wds_repeater_mode(struct wlan_hdd_link_info *link_info,
1478 			     uint8_t *peer_addr)
1479 {
1480 }
1481 #endif
1482 
hdd_change_peer_state(struct wlan_hdd_link_info * link_info,uint8_t * peer_mac,enum ol_txrx_peer_state sta_state)1483 QDF_STATUS hdd_change_peer_state(struct wlan_hdd_link_info *link_info,
1484 				 uint8_t *peer_mac,
1485 				 enum ol_txrx_peer_state sta_state)
1486 {
1487 	QDF_STATUS err;
1488 	struct hdd_adapter *adapter = link_info->adapter;
1489 	struct hdd_context *hdd_ctx = WLAN_HDD_GET_CTX(adapter);
1490 	void *soc = cds_get_context(QDF_MODULE_ID_SOC);
1491 
1492 	err = cdp_peer_state_update(soc, peer_mac, sta_state);
1493 	if (err != QDF_STATUS_SUCCESS) {
1494 		hdd_err("peer state update failed");
1495 		return QDF_STATUS_E_FAULT;
1496 	}
1497 
1498 	if (hdd_is_roam_sync_in_progress(hdd_ctx, link_info->vdev_id)) {
1499 		if (adapter->device_mode == QDF_STA_MODE &&
1500 		    (wlan_mlme_get_wds_mode(hdd_ctx->psoc) ==
1501 		    WLAN_WDS_MODE_REPEATER))
1502 			hdd_config_wds_repeater_mode(link_info, peer_mac);
1503 
1504 		hdd_son_deliver_peer_authorize_event(link_info, peer_mac);
1505 		return QDF_STATUS_SUCCESS;
1506 	}
1507 
1508 	if (sta_state == OL_TXRX_PEER_STATE_AUTH) {
1509 		/* Reset scan reject params on successful set key */
1510 		hdd_debug("Reset scan reject params");
1511 		hdd_init_scan_reject_params(hdd_ctx);
1512 
1513 		err = sme_set_peer_authorized(peer_mac, link_info->vdev_id);
1514 		if (err != QDF_STATUS_SUCCESS) {
1515 			hdd_err("Failed to set the peer state to authorized");
1516 			return QDF_STATUS_E_FAULT;
1517 		}
1518 
1519 		if (adapter->device_mode == QDF_STA_MODE ||
1520 		    adapter->device_mode == QDF_P2P_CLIENT_MODE) {
1521 			hdd_set_unpause_queue(soc, link_info->vdev_id);
1522 		}
1523 
1524 		if (adapter->device_mode == QDF_STA_MODE &&
1525 		    (wlan_mlme_get_wds_mode(hdd_ctx->psoc) ==
1526 		    WLAN_WDS_MODE_REPEATER))
1527 			hdd_config_wds_repeater_mode(link_info, peer_mac);
1528 
1529 		hdd_son_deliver_peer_authorize_event(link_info, peer_mac);
1530 	}
1531 	return QDF_STATUS_SUCCESS;
1532 }
1533 
hdd_update_dp_vdev_flags(void * cbk_data,uint8_t vdev_id,uint32_t vdev_param,bool is_link_up)1534 QDF_STATUS hdd_update_dp_vdev_flags(void *cbk_data,
1535 				    uint8_t vdev_id,
1536 				    uint32_t vdev_param,
1537 				    bool is_link_up)
1538 {
1539 	QDF_STATUS status = QDF_STATUS_SUCCESS;
1540 	void *soc = cds_get_context(QDF_MODULE_ID_SOC);
1541 	struct hdd_context *hdd_ctx;
1542 	struct wlan_objmgr_psoc **psoc;
1543 	cdp_config_param_type val;
1544 
1545 	if (!cbk_data)
1546 		return status;
1547 
1548 	psoc = cbk_data;
1549 
1550 	hdd_ctx = cds_get_context(QDF_MODULE_ID_HDD);
1551 	if (!hdd_ctx)
1552 		return QDF_STATUS_E_INVAL;
1553 
1554 	if (!hdd_ctx->tdls_nap_active)
1555 		return status;
1556 
1557 	if (vdev_id == WLAN_INVALID_VDEV_ID) {
1558 		status = QDF_STATUS_E_FAILURE;
1559 		return status;
1560 	}
1561 
1562 	val.cdp_vdev_param_tdls_flags = is_link_up;
1563 	cdp_txrx_set_vdev_param(soc, vdev_id, vdev_param, val);
1564 
1565 	return status;
1566 }
1567 
hdd_roam_register_sta(struct wlan_hdd_link_info * link_info,struct qdf_mac_addr * bssid,bool is_auth_required)1568 QDF_STATUS hdd_roam_register_sta(struct wlan_hdd_link_info *link_info,
1569 				 struct qdf_mac_addr *bssid,
1570 				 bool is_auth_required)
1571 {
1572 	QDF_STATUS qdf_status = QDF_STATUS_E_FAILURE;
1573 	struct ol_txrx_desc_type txrx_desc = {0};
1574 	void *soc = cds_get_context(QDF_MODULE_ID_SOC);
1575 	enum phy_ch_width ch_width;
1576 	enum wlan_phymode phymode;
1577 	struct wlan_objmgr_vdev *vdev;
1578 	struct hdd_adapter *adapter = link_info->adapter;
1579 
1580 	/* Get the Station ID from the one saved during the association */
1581 	if (!QDF_IS_ADDR_BROADCAST(bssid->bytes))
1582 		WLAN_ADDR_COPY(txrx_desc.peer_addr.bytes,
1583 			       bssid->bytes);
1584 	else
1585 		WLAN_ADDR_COPY(txrx_desc.peer_addr.bytes,
1586 			       adapter->mac_addr.bytes);
1587 
1588 	/* set the QoS field appropriately */
1589 	if (hdd_wmm_is_active(adapter))
1590 		txrx_desc.is_qos_enabled = 1;
1591 	else
1592 		txrx_desc.is_qos_enabled = 0;
1593 
1594 #ifdef FEATURE_WLAN_WAPI
1595 	hdd_debug("WAPI STA Registered: %d",
1596 		   adapter->wapi_info.is_wapi_sta);
1597 	if (adapter->wapi_info.is_wapi_sta)
1598 		txrx_desc.is_wapi_supported = 1;
1599 	else
1600 		txrx_desc.is_wapi_supported = 0;
1601 #endif /* FEATURE_WLAN_WAPI */
1602 
1603 	vdev = hdd_objmgr_get_vdev_by_user(link_info, WLAN_DP_ID);
1604 	if (!vdev)
1605 		return QDF_STATUS_E_INVAL;
1606 
1607 	qdf_status = ucfg_dp_sta_register_txrx_ops(vdev);
1608 	hdd_objmgr_put_vdev_by_user(vdev, WLAN_DP_ID);
1609 	if (!QDF_IS_STATUS_SUCCESS(qdf_status)) {
1610 		hdd_err("DP tx/rx ops register failed Status: %d", qdf_status);
1611 		return qdf_status;
1612 	}
1613 
1614 	if (adapter->device_mode == QDF_NDI_MODE) {
1615 		phymode = ucfg_mlme_get_vdev_phy_mode(
1616 						adapter->hdd_ctx->psoc,
1617 						link_info->vdev_id);
1618 		ch_width = ucfg_mlme_get_ch_width_from_phymode(phymode);
1619 	} else {
1620 		ch_width = ucfg_mlme_get_peer_ch_width(adapter->hdd_ctx->psoc,
1621 						txrx_desc.peer_addr.bytes);
1622 	}
1623 	txrx_desc.bw = hdd_convert_ch_width_to_cdp_peer_bw(ch_width);
1624 	qdf_status = cdp_peer_register(soc, OL_TXRX_PDEV_ID, &txrx_desc);
1625 	if (!QDF_IS_STATUS_SUCCESS(qdf_status)) {
1626 		hdd_err("cdp_peer_register() failed Status: %d [0x%08X]",
1627 			 qdf_status, qdf_status);
1628 		return qdf_status;
1629 	}
1630 
1631 	hdd_cm_set_peer_authenticate(link_info, &txrx_desc.peer_addr,
1632 				     is_auth_required);
1633 
1634 	return qdf_status;
1635 }
1636 
1637 /**
1638  * hdd_change_sta_state_authenticated()-
1639  * This function changes STA state to authenticated
1640  * @link_info: Link info pointer in HDD adapter
1641  * @roaminfo: pointer to the RoamInfo structure.
1642  *
1643  * This is called from hdd_RoamSetKeyCompleteHandler
1644  * in context to eCSR_ROAM_SET_KEY_COMPLETE event from fw.
1645  *
1646  * Return: 0 on success and errno on failure
1647  */
1648 static int
hdd_change_sta_state_authenticated(struct wlan_hdd_link_info * link_info,struct csr_roam_info * roaminfo)1649 hdd_change_sta_state_authenticated(struct wlan_hdd_link_info *link_info,
1650 				   struct csr_roam_info *roaminfo)
1651 {
1652 	uint8_t *mac_addr;
1653 	struct hdd_station_ctx *sta_ctx;
1654 	struct hdd_adapter *adapter = link_info->adapter;
1655 	struct hdd_context *hdd_ctx;
1656 	QDF_STATUS status;
1657 	bool alt_pipe;
1658 
1659 	sta_ctx = WLAN_HDD_GET_STATION_CTX_PTR(link_info);
1660 
1661 	mac_addr = sta_ctx->conn_info.bssid.bytes;
1662 
1663 	if (ucfg_ipa_is_enabled() && !sta_ctx->conn_info.is_authenticated &&
1664 	    adapter->device_mode == QDF_STA_MODE &&
1665 	    sta_ctx->conn_info.auth_type != eCSR_AUTH_TYPE_NONE &&
1666 	    sta_ctx->conn_info.auth_type != eCSR_AUTH_TYPE_OPEN_SYSTEM &&
1667 	    sta_ctx->conn_info.auth_type != eCSR_AUTH_TYPE_SHARED_KEY) {
1668 
1669 		hdd_ctx = WLAN_HDD_GET_CTX(adapter);
1670 		status = hdd_ipa_get_tx_pipe(hdd_ctx, link_info, &alt_pipe);
1671 		if (!QDF_IS_STATUS_SUCCESS(status)) {
1672 			hdd_debug("Failed to get alternate pipe for vdev %d",
1673 				  link_info->vdev_id);
1674 			alt_pipe = false;
1675 		}
1676 
1677 		ucfg_ipa_wlan_evt(adapter->hdd_ctx->pdev, adapter->dev,
1678 				  adapter->device_mode,
1679 				  link_info->vdev_id,
1680 				  WLAN_IPA_STA_CONNECT, mac_addr,
1681 				  alt_pipe);
1682 	}
1683 
1684 	hdd_cm_set_peer_authenticate(link_info,
1685 				     &sta_ctx->conn_info.bssid, false);
1686 
1687 	return 0;
1688 }
1689 
1690 /**
1691  * hdd_change_peer_state_after_set_key() - change the peer state on set key
1692  *                                         complete
1693  * @link_info: Link info pointer in HDD adapter
1694  * @roaminfo: pointer to roam info
1695  * @roam_result: roam result
1696  *
1697  * Peer state will be OL_TXRX_PEER_STATE_CONN until set key is complete.
1698  * This function checks for the successful set key completion and update
1699  * the peer state to OL_TXRX_PEER_STATE_AUTH.
1700  *
1701  * Return: None
1702  */
1703 static void
hdd_change_peer_state_after_set_key(struct wlan_hdd_link_info * link_info,struct csr_roam_info * roaminfo,eCsrRoamResult roam_result)1704 hdd_change_peer_state_after_set_key(struct wlan_hdd_link_info *link_info,
1705 				    struct csr_roam_info *roaminfo,
1706 				    eCsrRoamResult roam_result)
1707 {
1708 	struct hdd_station_ctx *hdd_sta_ctx;
1709 	eCsrEncryptionType encr_type;
1710 	struct hdd_adapter *adapter = link_info->adapter;
1711 
1712 	hdd_sta_ctx = WLAN_HDD_GET_STATION_CTX_PTR(link_info);
1713 	encr_type = hdd_sta_ctx->conn_info.uc_encrypt_type;
1714 
1715 	if (eCSR_ROAM_RESULT_AUTHENTICATED == roam_result) {
1716 		hdd_sta_ctx->conn_info.gtk_installed = true;
1717 		/*
1718 		 * PTK exchange happens in preauthentication itself if key_mgmt
1719 		 * is FT-PSK, ptk_installed was false as there is no set PTK
1720 		 * after roaming. STA TL state moves to authenticated only if
1721 		 * ptk_installed is true. So, make ptk_installed to true in
1722 		 * case of 11R roaming.
1723 		 */
1724 		if (sme_neighbor_roam_is11r_assoc(adapter->hdd_ctx->mac_handle,
1725 						  link_info->vdev_id))
1726 			hdd_sta_ctx->conn_info.ptk_installed = true;
1727 	} else {
1728 		hdd_sta_ctx->conn_info.ptk_installed = true;
1729 	}
1730 
1731 	/* In WPA case move STA to authenticated when ptk is installed. Earlier
1732 	 * in WEP case STA was moved to AUTHENTICATED prior to setting the
1733 	 * unicast key and it was resulting in sending few un-encrypted packet.
1734 	 * Now in WEP case STA state will be moved to AUTHENTICATED after we
1735 	 * set the unicast and broadcast key.
1736 	 */
1737 	if ((encr_type == eCSR_ENCRYPT_TYPE_WEP40) ||
1738 	    (encr_type == eCSR_ENCRYPT_TYPE_WEP104) ||
1739 	    (encr_type == eCSR_ENCRYPT_TYPE_WEP40_STATICKEY) ||
1740 	    (encr_type == eCSR_ENCRYPT_TYPE_WEP104_STATICKEY)) {
1741 		if (hdd_sta_ctx->conn_info.gtk_installed &&
1742 		    hdd_sta_ctx->conn_info.ptk_installed)
1743 			hdd_change_sta_state_authenticated(link_info, roaminfo);
1744 	} else if (hdd_sta_ctx->conn_info.ptk_installed) {
1745 		hdd_change_sta_state_authenticated(link_info, roaminfo);
1746 	}
1747 
1748 	if (hdd_sta_ctx->conn_info.gtk_installed &&
1749 		hdd_sta_ctx->conn_info.ptk_installed) {
1750 		hdd_sta_ctx->conn_info.gtk_installed = false;
1751 		hdd_sta_ctx->conn_info.ptk_installed = false;
1752 	}
1753 }
1754 
1755 /**
1756  * hdd_roam_set_key_complete_handler() - Update the security parameters
1757  * @link_info: Link info pointer in HDD adapter
1758  * @roam_info: pointer to roam info
1759  * @roam_status: roam status
1760  * @roam_result: roam result
1761  *
1762  * Return: QDF_STATUS enumeration
1763  */
1764 static QDF_STATUS
hdd_roam_set_key_complete_handler(struct wlan_hdd_link_info * link_info,struct csr_roam_info * roam_info,eRoamCmdStatus roam_status,eCsrRoamResult roam_result)1765 hdd_roam_set_key_complete_handler(struct wlan_hdd_link_info *link_info,
1766 				  struct csr_roam_info *roam_info,
1767 				  eRoamCmdStatus roam_status,
1768 				  eCsrRoamResult roam_result)
1769 {
1770 	eCsrEncryptionType algorithm;
1771 	bool connected;
1772 	struct hdd_station_ctx *sta_ctx;
1773 	struct hdd_context *hdd_ctx = WLAN_HDD_GET_CTX(link_info->adapter);
1774 
1775 	hdd_enter();
1776 
1777 	if (!roam_info) {
1778 		hdd_err("roam_info is NULL");
1779 		return QDF_STATUS_E_FAILURE;
1780 	}
1781 
1782 	if (!hdd_ctx || !hdd_ctx->psoc) {
1783 		hdd_err("hdd_ctx or psoc is NULL");
1784 		return QDF_STATUS_E_FAILURE;
1785 	}
1786 
1787 	sta_ctx = WLAN_HDD_GET_STATION_CTX_PTR(link_info);
1788 	/*
1789 	 * if (WPA), tell TL to go to 'authenticated' after the keys are set.
1790 	 * then go to 'authenticated'.  For all other authentication types
1791 	 * (those that do not require upper layer authentication) we can put TL
1792 	 * directly into 'authenticated' state.
1793 	 */
1794 	hdd_debug("Set Key completion roam_status =%d roam_result=%d "
1795 		  QDF_MAC_ADDR_FMT, roam_status, roam_result,
1796 		  QDF_MAC_ADDR_REF(roam_info->peerMac.bytes));
1797 
1798 	sta_ctx = WLAN_HDD_GET_STATION_CTX_PTR(link_info);
1799 	connected = hdd_conn_get_connected_cipher_algo(link_info, sta_ctx,
1800 						       &algorithm);
1801 	if (connected) {
1802 		hdd_change_peer_state_after_set_key(link_info,
1803 						    roam_info, roam_result);
1804 	}
1805 
1806 	policy_mgr_restart_opportunistic_timer(hdd_ctx->psoc, false);
1807 
1808 	hdd_exit();
1809 	return QDF_STATUS_SUCCESS;
1810 }
1811 
hdd_save_peer(struct hdd_station_ctx * sta_ctx,struct qdf_mac_addr * peer_mac_addr)1812 bool hdd_save_peer(struct hdd_station_ctx *sta_ctx,
1813 		   struct qdf_mac_addr *peer_mac_addr)
1814 {
1815 	int idx;
1816 	struct qdf_mac_addr *mac_addr;
1817 
1818 	for (idx = 0; idx < MAX_PEERS; idx++) {
1819 		mac_addr = &sta_ctx->conn_info.peer_macaddr[idx];
1820 		if (qdf_is_macaddr_zero(mac_addr)) {
1821 			hdd_debug("adding peer: "QDF_MAC_ADDR_FMT" at idx: %d",
1822 				  QDF_MAC_ADDR_REF(peer_mac_addr->bytes), idx);
1823 			qdf_copy_macaddr(mac_addr, peer_mac_addr);
1824 			return true;
1825 		}
1826 	}
1827 
1828 	return false;
1829 }
1830 
hdd_delete_peer(struct hdd_station_ctx * sta_ctx,struct qdf_mac_addr * peer_mac_addr)1831 void hdd_delete_peer(struct hdd_station_ctx *sta_ctx,
1832 		     struct qdf_mac_addr *peer_mac_addr)
1833 {
1834 	int i;
1835 	struct qdf_mac_addr *mac_addr;
1836 
1837 	for (i = 0; i < MAX_PEERS; i++) {
1838 		mac_addr = &sta_ctx->conn_info.peer_macaddr[i];
1839 		if (qdf_is_macaddr_equal(mac_addr, peer_mac_addr)) {
1840 			qdf_zero_macaddr(mac_addr);
1841 			return;
1842 		}
1843 	}
1844 }
1845 
hdd_any_valid_peer_present(struct wlan_hdd_link_info * link_info)1846 bool hdd_any_valid_peer_present(struct wlan_hdd_link_info *link_info)
1847 {
1848 	struct hdd_station_ctx *sta_ctx;
1849 	int i;
1850 	struct qdf_mac_addr *mac_addr;
1851 
1852 	sta_ctx = WLAN_HDD_GET_STATION_CTX_PTR(link_info);
1853 	for (i = 0; i < MAX_PEERS; i++) {
1854 		mac_addr = &sta_ctx->conn_info.peer_macaddr[i];
1855 		if (!qdf_is_macaddr_zero(mac_addr) &&
1856 		    !qdf_is_macaddr_broadcast(mac_addr)) {
1857 			hdd_debug("peer: index: %u " QDF_MAC_ADDR_FMT, i,
1858 				  QDF_MAC_ADDR_REF(mac_addr->bytes));
1859 			return true;
1860 		}
1861 	}
1862 
1863 	return false;
1864 }
1865 
1866 /**
1867  * hdd_roam_mic_error_indication_handler() - MIC error indication handler
1868  * @link_info: Link info pointer in HDD adapter
1869  * @roam_info: pointer to roam info
1870  *
1871  * This function indicates the Mic failure to the supplicant
1872  *
1873  * Return: None
1874  */
1875 static void
hdd_roam_mic_error_indication_handler(struct wlan_hdd_link_info * link_info,struct csr_roam_info * roam_info)1876 hdd_roam_mic_error_indication_handler(struct wlan_hdd_link_info *link_info,
1877 				      struct csr_roam_info *roam_info)
1878 {
1879 	struct hdd_adapter *adapter = link_info->adapter;
1880 	tSirMicFailureInfo *mic_failure_info;
1881 
1882 	if (!hdd_cm_is_vdev_associated(link_info))
1883 		return;
1884 
1885 	mic_failure_info = roam_info->u.pMICFailureInfo;
1886 	cfg80211_michael_mic_failure(adapter->dev,
1887 				     mic_failure_info->taMacAddr,
1888 				     mic_failure_info->multicast ?
1889 					NL80211_KEYTYPE_GROUP :
1890 					NL80211_KEYTYPE_PAIRWISE,
1891 				     mic_failure_info->keyId,
1892 				     mic_failure_info->TSC,
1893 				     GFP_KERNEL);
1894 }
1895 
1896 #ifdef FEATURE_WLAN_TDLS
hdd_roam_register_tdlssta(struct hdd_adapter * adapter,const uint8_t * peerMac,uint8_t qos)1897 QDF_STATUS hdd_roam_register_tdlssta(struct hdd_adapter *adapter,
1898 				     const uint8_t *peerMac, uint8_t qos)
1899 {
1900 	QDF_STATUS qdf_status = QDF_STATUS_E_FAILURE;
1901 	struct ol_txrx_desc_type txrx_desc = { 0 };
1902 	void *soc = cds_get_context(QDF_MODULE_ID_SOC);
1903 	enum phy_ch_width ch_width;
1904 	struct wlan_objmgr_vdev *vdev;
1905 
1906 	/*
1907 	 * TDLS sta in BSS should be set as STA type TDLS and STA MAC should
1908 	 * be peer MAC, here we are working on direct Link
1909 	 */
1910 	WLAN_ADDR_COPY(txrx_desc.peer_addr.bytes, peerMac);
1911 
1912 	/* set the QoS field appropriately .. */
1913 	txrx_desc.is_qos_enabled = qos;
1914 
1915 	vdev = hdd_objmgr_get_vdev_by_user(adapter->deflink, WLAN_DP_ID);
1916 	if (!vdev)
1917 		return QDF_STATUS_E_INVAL;
1918 
1919 	qdf_status = ucfg_dp_tdlsta_register_txrx_ops(vdev);
1920 	hdd_objmgr_put_vdev_by_user(vdev, WLAN_DP_ID);
1921 	if (!QDF_IS_STATUS_SUCCESS(qdf_status)) {
1922 		hdd_err("DP tx/rx ops register failed Status: %d", qdf_status);
1923 		return qdf_status;
1924 	}
1925 
1926 	ch_width = ucfg_mlme_get_peer_ch_width(adapter->hdd_ctx->psoc,
1927 					       txrx_desc.peer_addr.bytes);
1928 	txrx_desc.bw = hdd_convert_ch_width_to_cdp_peer_bw(ch_width);
1929 	/* Register the Station with TL...  */
1930 	qdf_status = cdp_peer_register(soc, OL_TXRX_PDEV_ID, &txrx_desc);
1931 	if (!QDF_IS_STATUS_SUCCESS(qdf_status)) {
1932 		hdd_err("cdp_peer_register() failed Status: %d [0x%08X]",
1933 			qdf_status, qdf_status);
1934 		return qdf_status;
1935 	}
1936 
1937 	return qdf_status;
1938 }
1939 
1940 #endif
1941 
1942 #if (LINUX_VERSION_CODE >= KERNEL_VERSION(3, 11, 0))
1943 
hdd_rx_unprot_disassoc(struct net_device * dev,const u8 * buf,size_t len)1944 static void hdd_rx_unprot_disassoc(struct net_device *dev,
1945 				   const u8 *buf, size_t len)
1946 {
1947 	cfg80211_rx_unprot_mlme_mgmt(dev, buf, len);
1948 }
1949 
hdd_rx_unprot_deauth(struct net_device * dev,const u8 * buf,size_t len)1950 static void hdd_rx_unprot_deauth(struct net_device *dev,
1951 				 const u8 *buf, size_t len)
1952 {
1953 	cfg80211_rx_unprot_mlme_mgmt(dev, buf, len);
1954 }
1955 
1956 #else
1957 
hdd_rx_unprot_disassoc(struct net_device * dev,const u8 * buf,size_t len)1958 static void hdd_rx_unprot_disassoc(struct net_device *dev,
1959 				   const u8 *buf, size_t len)
1960 {
1961 	cfg80211_send_unprot_disassoc(dev, buf, len);
1962 }
1963 
hdd_rx_unprot_deauth(struct net_device * dev,const u8 * buf,size_t len)1964 static void hdd_rx_unprot_deauth(struct net_device *dev,
1965 				 const u8 *buf, size_t len)
1966 {
1967 	cfg80211_send_unprot_deauth(dev, buf, len);
1968 }
1969 
1970 #endif /* (LINUX_VERSION_CODE >= KERNEL_VERSION(3, 11, 0)) */
1971 
1972 /**
1973  * hdd_indicate_unprot_mgmt_frame() - indicate unprotected management frame
1974  * @link_info: Link info pointer in HDD adapter
1975  * @frame_length: Length of the unprotected frame being passed
1976  * @frame: Pointer to the frame buffer
1977  * @frame_type: 802.11 frame type
1978  *
1979  * This function forwards the unprotected management frame to the supplicant.
1980  *
1981  * Return: nothing
1982  */
1983 static void
hdd_indicate_unprot_mgmt_frame(struct wlan_hdd_link_info * link_info,uint32_t frame_length,uint8_t * frame,uint8_t frame_type)1984 hdd_indicate_unprot_mgmt_frame(struct wlan_hdd_link_info *link_info,
1985 			       uint32_t frame_length, uint8_t *frame,
1986 			       uint8_t frame_type)
1987 {
1988 	uint8_t type, subtype;
1989 	struct hdd_stats *hdd_stats;
1990 	struct hdd_adapter *adapter = link_info->adapter;
1991 
1992 	hdd_debug("Frame Type = %d Frame Length = %d",
1993 		  frame_type, frame_length);
1994 
1995 	if (hdd_validate_adapter(adapter))
1996 		return;
1997 
1998 	if (!frame_length) {
1999 		hdd_err("Frame Length is Invalid ZERO");
2000 		return;
2001 	}
2002 
2003 	if (!frame) {
2004 		hdd_err("frame is NULL");
2005 		return;
2006 	}
2007 
2008 	type = WLAN_HDD_GET_TYPE_FRM_FC(frame[0]);
2009 	if (type != SIR_MAC_MGMT_FRAME) {
2010 		hdd_warn("Unexpected frame type %d", type);
2011 		return;
2012 	}
2013 
2014 	hdd_stats = &link_info->hdd_stats;
2015 	subtype = WLAN_HDD_GET_SUBTYPE_FRM_FC(frame[0]);
2016 	switch (subtype) {
2017 	case SIR_MAC_MGMT_DISASSOC:
2018 		hdd_rx_unprot_disassoc(adapter->dev, frame, frame_length);
2019 		hdd_stats->hdd_pmf_stats.num_unprot_disassoc_rx++;
2020 		break;
2021 	case SIR_MAC_MGMT_DEAUTH:
2022 		hdd_rx_unprot_deauth(adapter->dev, frame, frame_length);
2023 		hdd_stats->hdd_pmf_stats.num_unprot_deauth_rx++;
2024 		break;
2025 	default:
2026 		hdd_warn("Unexpected frame subtype %d", subtype);
2027 		break;
2028 	}
2029 }
2030 
2031 #ifdef FEATURE_WLAN_ESE
2032 /**
2033  * hdd_indicate_tsm_ie() - send traffic stream metrics ie
2034  * @adapter: pointer to adapter
2035  * @tid: traffic identifier
2036  * @state: state
2037  * @measInterval: measurement interval
2038  *
2039  * This function sends traffic stream metrics IE information to
2040  * the supplicant via wireless event.
2041  *
2042  * Return: none
2043  */
2044 static void
hdd_indicate_tsm_ie(struct hdd_adapter * adapter,uint8_t tid,uint8_t state,uint16_t measInterval)2045 hdd_indicate_tsm_ie(struct hdd_adapter *adapter, uint8_t tid,
2046 		    uint8_t state, uint16_t measInterval)
2047 {
2048 	union iwreq_data wrqu;
2049 	char buf[IW_CUSTOM_MAX + 1];
2050 	int nBytes = 0;
2051 
2052 	if (!adapter)
2053 		return;
2054 
2055 	/* create the event */
2056 	memset(&wrqu, '\0', sizeof(wrqu));
2057 	memset(buf, '\0', sizeof(buf));
2058 
2059 	hdd_debug("TSM Ind tid(%d) state(%d) MeasInt(%d)",
2060 		 tid, state, measInterval);
2061 
2062 	nBytes =
2063 		snprintf(buf, IW_CUSTOM_MAX, "TSMIE=%d:%d:%d", tid, state,
2064 			 measInterval);
2065 
2066 	wrqu.data.pointer = buf;
2067 	wrqu.data.length = nBytes;
2068 	/* send the event */
2069 	hdd_wext_send_event(adapter->dev, IWEVCUSTOM, &wrqu, buf);
2070 }
2071 
2072 /**
2073  * hdd_indicate_ese_adj_ap_rep_ind() - send adjacent AP report indication
2074  * @adapter: pointer to adapter
2075  * @roam_info: pointer to roam info
2076  *
2077  * Return: none
2078  */
2079 static void
hdd_indicate_ese_adj_ap_rep_ind(struct hdd_adapter * adapter,struct csr_roam_info * roam_info)2080 hdd_indicate_ese_adj_ap_rep_ind(struct hdd_adapter *adapter,
2081 				struct csr_roam_info *roam_info)
2082 {
2083 	union iwreq_data wrqu;
2084 	char buf[IW_CUSTOM_MAX + 1];
2085 	int nBytes = 0;
2086 
2087 	if ((!adapter) || (!roam_info))
2088 		return;
2089 
2090 	/* create the event */
2091 	memset(&wrqu, '\0', sizeof(wrqu));
2092 	memset(buf, '\0', sizeof(buf));
2093 
2094 	hdd_debug("CCXADJAPREP=%u", roam_info->tsmRoamDelay);
2095 
2096 	nBytes =
2097 		snprintf(buf, IW_CUSTOM_MAX, "CCXADJAPREP=%u",
2098 			 roam_info->tsmRoamDelay);
2099 
2100 	wrqu.data.pointer = buf;
2101 	wrqu.data.length = nBytes;
2102 
2103 	/* send the event */
2104 	hdd_wext_send_event(adapter->dev, IWEVCUSTOM, &wrqu, buf);
2105 }
2106 
2107 /**
2108  * hdd_indicate_ese_bcn_report_no_results() - beacon report no scan results
2109  * @adapter: pointer to adapter
2110  * @measurementToken: measurement token
2111  * @flag: flag
2112  * @numBss: number of bss
2113  *
2114  * If the measurement is none and no scan results found,
2115  * indicate the supplicant about measurement done.
2116  *
2117  * Return: none
2118  */
2119 void
hdd_indicate_ese_bcn_report_no_results(const struct hdd_adapter * adapter,const uint16_t measurementToken,const bool flag,const uint8_t numBss)2120 hdd_indicate_ese_bcn_report_no_results(const struct hdd_adapter *adapter,
2121 				       const uint16_t measurementToken,
2122 				       const bool flag, const uint8_t numBss)
2123 {
2124 	union iwreq_data wrqu;
2125 	char buf[IW_CUSTOM_MAX];
2126 	char *pos = buf;
2127 	int nBytes = 0, freeBytes = IW_CUSTOM_MAX;
2128 
2129 	memset(&wrqu, '\0', sizeof(wrqu));
2130 	memset(buf, '\0', sizeof(buf));
2131 
2132 	hdd_debug("CCXBCNREP=%d %d %d", measurementToken,
2133 		 flag, numBss);
2134 
2135 	nBytes =
2136 		snprintf(pos, freeBytes, "CCXBCNREP=%d %d %d", measurementToken,
2137 			 flag, numBss);
2138 
2139 	wrqu.data.pointer = buf;
2140 	wrqu.data.length = nBytes;
2141 	/* send the event */
2142 	hdd_wext_send_event(adapter->dev, IWEVCUSTOM, &wrqu, buf);
2143 }
2144 
2145 /**
2146  * hdd_indicate_ese_bcn_report_ind() - send beacon report indication
2147  * @adapter: pointer to adapter
2148  * @roam_info: pointer to roam info
2149  *
2150  * If the measurement is none and no scan results found,
2151  * indicate the supplicant about measurement done.
2152  *
2153  * Return: none
2154  */
2155 static void
hdd_indicate_ese_bcn_report_ind(const struct hdd_adapter * adapter,const struct csr_roam_info * roam_info)2156 hdd_indicate_ese_bcn_report_ind(const struct hdd_adapter *adapter,
2157 				const struct csr_roam_info *roam_info)
2158 {
2159 	union iwreq_data wrqu;
2160 	char buf[IW_CUSTOM_MAX];
2161 	char *pos = buf;
2162 	int nBytes = 0, freeBytes = IW_CUSTOM_MAX;
2163 	uint8_t i = 0, len = 0;
2164 	uint8_t tot_bcn_ieLen = 0;  /* total size of the beacon report data */
2165 	uint8_t lastSent = 0, sendBss = 0;
2166 	int bcnRepFieldSize =
2167 		sizeof(roam_info->pEseBcnReportRsp->bcnRepBssInfo[0].
2168 		       bcnReportFields);
2169 	uint8_t ieLenByte = 1;
2170 	/*
2171 	 * CCXBCNREP=meas_tok<sp>flag<sp>no_of_bss<sp>tot_bcn_ie_len = 18 bytes
2172 	 */
2173 #define ESEBCNREPHEADER_LEN  (18)
2174 
2175 	if ((!adapter) || (!roam_info))
2176 		return;
2177 
2178 	/*
2179 	 * Custom event can pass maximum of 256 bytes of data,
2180 	 * based on the IE len we need to identify how many BSS info can
2181 	 * be filled in to custom event data.
2182 	 */
2183 	/*
2184 	 * meas_tok<sp>flag<sp>no_of_bss<sp>tot_bcn_ie_len bcn_rep_data
2185 	 * bcn_rep_data will have bcn_rep_fields,ie_len,ie without any spaces
2186 	 * CCXBCNREP=meas_tok<sp>flag<sp>no_of_bss<sp>tot_bcn_ie_len = 18 bytes
2187 	 */
2188 
2189 	if ((roam_info->pEseBcnReportRsp->flag >> 1)
2190 	    && (!roam_info->pEseBcnReportRsp->numBss)) {
2191 		hdd_debug("Measurement Done but no scan results");
2192 		/* If the measurement is none and no scan results found,
2193 		 * indicate the supplicant about measurement done
2194 		 */
2195 		hdd_indicate_ese_bcn_report_no_results(
2196 				adapter,
2197 				roam_info->pEseBcnReportRsp->
2198 				measurementToken,
2199 				roam_info->pEseBcnReportRsp->flag,
2200 				roam_info->pEseBcnReportRsp->numBss);
2201 	} else {
2202 		while (lastSent < roam_info->pEseBcnReportRsp->numBss) {
2203 			memset(&wrqu, '\0', sizeof(wrqu));
2204 			memset(buf, '\0', sizeof(buf));
2205 			tot_bcn_ieLen = 0;
2206 			sendBss = 0;
2207 			pos = buf;
2208 			freeBytes = IW_CUSTOM_MAX;
2209 
2210 			for (i = lastSent;
2211 			     i < roam_info->pEseBcnReportRsp->numBss; i++) {
2212 				len =
2213 					bcnRepFieldSize + ieLenByte +
2214 					roam_info->pEseBcnReportRsp->
2215 					bcnRepBssInfo[i].ieLen;
2216 				if ((len + tot_bcn_ieLen) >
2217 				    (IW_CUSTOM_MAX - ESEBCNREPHEADER_LEN)) {
2218 					break;
2219 				}
2220 				tot_bcn_ieLen += len;
2221 				sendBss++;
2222 				hdd_debug("i(%d) sizeof bcnReportFields(%d) IeLength(%d) Length of Ie(%d) totLen(%d)",
2223 					 i, bcnRepFieldSize, 1,
2224 					 roam_info->pEseBcnReportRsp->
2225 					 bcnRepBssInfo[i].ieLen, tot_bcn_ieLen);
2226 			}
2227 
2228 			hdd_debug("Sending %d BSS Info", sendBss);
2229 			hdd_debug("CCXBCNREP=%d %d %d %d",
2230 				 roam_info->pEseBcnReportRsp->measurementToken,
2231 				 roam_info->pEseBcnReportRsp->flag, sendBss,
2232 				 tot_bcn_ieLen);
2233 
2234 			nBytes = snprintf(pos, freeBytes, "CCXBCNREP=%d %d %d ",
2235 					  roam_info->pEseBcnReportRsp->
2236 					  measurementToken,
2237 					  roam_info->pEseBcnReportRsp->flag,
2238 					  sendBss);
2239 			pos += nBytes;
2240 			freeBytes -= nBytes;
2241 
2242 			/* Copy total Beacon report data length */
2243 			qdf_mem_copy(pos, (char *)&tot_bcn_ieLen,
2244 				     sizeof(tot_bcn_ieLen));
2245 			pos += sizeof(tot_bcn_ieLen);
2246 			freeBytes -= sizeof(tot_bcn_ieLen);
2247 
2248 			for (i = 0; i < sendBss; i++) {
2249 				hdd_debug("ChanNum(%d) Spare(%d) MeasDuration(%d)"
2250 				       " PhyType(%d) RecvSigPower(%d) ParentTSF(%u)"
2251 				       " TargetTSF[0](%u) TargetTSF[1](%u) BeaconInterval(%u)"
2252 				       " CapabilityInfo(%d) BSSID(%02X:%02X:%02X:%02X:%02X:%02X)",
2253 				       roam_info->pEseBcnReportRsp->
2254 				       bcnRepBssInfo[i +
2255 						     lastSent].bcnReportFields.
2256 				       ChanNum,
2257 				       roam_info->pEseBcnReportRsp->
2258 				       bcnRepBssInfo[i +
2259 						     lastSent].bcnReportFields.
2260 				       Spare,
2261 				       roam_info->pEseBcnReportRsp->
2262 				       bcnRepBssInfo[i +
2263 						     lastSent].bcnReportFields.
2264 				       MeasDuration,
2265 				       roam_info->pEseBcnReportRsp->
2266 				       bcnRepBssInfo[i +
2267 						     lastSent].bcnReportFields.
2268 				       PhyType,
2269 				       roam_info->pEseBcnReportRsp->
2270 				       bcnRepBssInfo[i +
2271 						     lastSent].bcnReportFields.
2272 				       RecvSigPower,
2273 				       roam_info->pEseBcnReportRsp->
2274 				       bcnRepBssInfo[i +
2275 						     lastSent].bcnReportFields.
2276 				       ParentTsf,
2277 				       roam_info->pEseBcnReportRsp->
2278 				       bcnRepBssInfo[i +
2279 						     lastSent].bcnReportFields.
2280 				       TargetTsf[0],
2281 				       roam_info->pEseBcnReportRsp->
2282 				       bcnRepBssInfo[i +
2283 						     lastSent].bcnReportFields.
2284 				       TargetTsf[1],
2285 				       roam_info->pEseBcnReportRsp->
2286 				       bcnRepBssInfo[i +
2287 						     lastSent].bcnReportFields.
2288 				       BcnInterval,
2289 				       roam_info->pEseBcnReportRsp->
2290 				       bcnRepBssInfo[i +
2291 						     lastSent].bcnReportFields.
2292 				       CapabilityInfo,
2293 				       roam_info->pEseBcnReportRsp->
2294 				       bcnRepBssInfo[i +
2295 						     lastSent].bcnReportFields.
2296 				       Bssid[0],
2297 				       roam_info->pEseBcnReportRsp->
2298 				       bcnRepBssInfo[i +
2299 						     lastSent].bcnReportFields.
2300 				       Bssid[1],
2301 				       roam_info->pEseBcnReportRsp->
2302 				       bcnRepBssInfo[i +
2303 						     lastSent].bcnReportFields.
2304 				       Bssid[2],
2305 				       roam_info->pEseBcnReportRsp->
2306 				       bcnRepBssInfo[i +
2307 						     lastSent].bcnReportFields.
2308 				       Bssid[3],
2309 				       roam_info->pEseBcnReportRsp->
2310 				       bcnRepBssInfo[i +
2311 						     lastSent].bcnReportFields.
2312 				       Bssid[4],
2313 				       roam_info->pEseBcnReportRsp->
2314 				       bcnRepBssInfo[i +
2315 						     lastSent].bcnReportFields.
2316 				       Bssid[5]);
2317 
2318 				/* bcn report fields are copied */
2319 				len =
2320 					sizeof(roam_info->pEseBcnReportRsp->
2321 					       bcnRepBssInfo[i +
2322 							     lastSent].
2323 					       bcnReportFields);
2324 				qdf_mem_copy(pos,
2325 					     (char *)&roam_info->
2326 					     pEseBcnReportRsp->bcnRepBssInfo[i +
2327 									     lastSent].
2328 					     bcnReportFields, len);
2329 				pos += len;
2330 				freeBytes -= len;
2331 
2332 				/* Add 1 byte of ie len */
2333 				len =
2334 					roam_info->pEseBcnReportRsp->
2335 					bcnRepBssInfo[i + lastSent].ieLen;
2336 				qdf_mem_copy(pos, (char *)&len, sizeof(len));
2337 				pos += sizeof(len);
2338 				freeBytes -= sizeof(len);
2339 
2340 				/* copy IE from scan results */
2341 				qdf_mem_copy(pos,
2342 					     (char *)roam_info->
2343 					     pEseBcnReportRsp->bcnRepBssInfo[i +
2344 									     lastSent].
2345 					     pBuf, len);
2346 				pos += len;
2347 				freeBytes -= len;
2348 			}
2349 
2350 			wrqu.data.pointer = buf;
2351 			wrqu.data.length = IW_CUSTOM_MAX - freeBytes;
2352 
2353 			/* send the event */
2354 			hdd_wext_send_event(adapter->dev, IWEVCUSTOM, &wrqu,
2355 					    buf);
2356 			lastSent += sendBss;
2357 		}
2358 	}
2359 }
2360 
2361 #endif /* FEATURE_WLAN_ESE */
2362 
2363 /*
2364  * hdd_roam_channel_switch_handler() - hdd channel switch handler
2365  * @link_info: Link info pointer in HDD adapter
2366  * @roam_info: Pointer to roam info
2367  *
2368  * Return: None
2369  */
2370 static void
hdd_roam_channel_switch_handler(struct wlan_hdd_link_info * link_info,struct csr_roam_info * roam_info)2371 hdd_roam_channel_switch_handler(struct wlan_hdd_link_info *link_info,
2372 				struct csr_roam_info *roam_info)
2373 {
2374 	struct hdd_chan_change_params chan_change = {0};
2375 	QDF_STATUS status;
2376 	struct hdd_adapter *adapter = link_info->adapter;
2377 	struct hdd_context *hdd_ctx = WLAN_HDD_GET_CTX(adapter);
2378 	mac_handle_t mac_handle;
2379 	struct hdd_station_ctx *sta_ctx;
2380 	uint8_t connected_vdev;
2381 	bool notify = true, is_sap_go_moved_before_sta = false;
2382 	struct wlan_objmgr_vdev *vdev;
2383 
2384 	mac_handle = hdd_adapter_get_mac_handle(adapter);
2385 	if (!mac_handle)
2386 		return;
2387 
2388 	/* Enable Roaming on STA interface which was disabled before CSA */
2389 	if (adapter->device_mode == QDF_STA_MODE)
2390 		sme_start_roaming(mac_handle, link_info->vdev_id,
2391 				  REASON_VDEV_RESTART_FROM_HOST,
2392 				  RSO_CHANNEL_SWITCH);
2393 
2394 	sta_ctx = WLAN_HDD_GET_STATION_CTX_PTR(link_info);
2395 	if (sta_ctx) {
2396 		sta_ctx->conn_info.chan_freq = roam_info->chan_info.mhz;
2397 		sta_ctx->conn_info.ch_width = roam_info->chan_info.ch_width;
2398 	}
2399 
2400 	chan_change.chan_freq = roam_info->chan_info.mhz;
2401 	chan_change.chan_params.ch_width =
2402 		roam_info->chan_info.ch_width;
2403 	chan_change.chan_params.sec_ch_offset =
2404 		roam_info->chan_info.sec_ch_offset;
2405 	chan_change.chan_params.mhz_freq_seg0 =
2406 		roam_info->chan_info.band_center_freq1;
2407 	chan_change.chan_params.mhz_freq_seg1 =
2408 		roam_info->chan_info.band_center_freq2;
2409 
2410 	vdev = hdd_objmgr_get_vdev_by_user(link_info, WLAN_OSIF_ID);
2411 	if (!vdev) {
2412 		hdd_err("Invalid vdev");
2413 		return;
2414 	}
2415 
2416 	if ((adapter->device_mode == QDF_STA_MODE ||
2417 	     adapter->device_mode == QDF_P2P_CLIENT_MODE)) {
2418 		if (!wlan_get_connected_vdev_by_bssid(
2419 				hdd_ctx->pdev, sta_ctx->conn_info.bssid.bytes,
2420 				&connected_vdev))
2421 			notify = false;
2422 		else if (link_info->vdev_id != connected_vdev ||
2423 			 !ucfg_cm_is_vdev_active(vdev))
2424 			notify = false;
2425 	}
2426 	if (notify) {
2427 		qdf_sched_work(0, &link_info->chan_change_notify_work);
2428 	} else {
2429 		hdd_err("BSS "QDF_MAC_ADDR_FMT" no connected with vdev %d (%d)",
2430 			QDF_MAC_ADDR_REF(sta_ctx->conn_info.bssid.bytes),
2431 			link_info->vdev_id, connected_vdev);
2432 	}
2433 	status = policy_mgr_set_hw_mode_on_channel_switch(hdd_ctx->psoc,
2434 							  link_info->vdev_id);
2435 	if (QDF_IS_STATUS_ERROR(status))
2436 		hdd_debug("set hw mode change not done");
2437 
2438 	is_sap_go_moved_before_sta =
2439 			wlan_vdev_mlme_is_sap_go_move_before_sta(vdev);
2440 	hdd_objmgr_put_vdev_by_user(vdev, WLAN_OSIF_ID);
2441 
2442 	if (!is_sap_go_moved_before_sta)
2443 		policy_mgr_check_concurrent_intf_and_restart_sap(
2444 		   hdd_ctx->psoc,
2445 		   !!link_info->session.ap.sap_config.acs_cfg.acs_mode);
2446 
2447 	wlan_twt_concurrency_update(hdd_ctx);
2448 	if (adapter->device_mode == QDF_STA_MODE ||
2449 	    adapter->device_mode == QDF_P2P_CLIENT_MODE) {
2450 		vdev = hdd_objmgr_get_vdev_by_user(link_info,
2451 						   WLAN_OSIF_ID);
2452 		if (!vdev)
2453 			return;
2454 
2455 		status = ucfg_if_mgr_deliver_event(
2456 				vdev, WLAN_IF_MGR_EV_STA_CSA_COMPLETE, NULL);
2457 		if (QDF_IS_STATUS_ERROR(status))
2458 			hdd_debug("Failed to deliver CSA complete evt");
2459 
2460 		hdd_objmgr_put_vdev_by_user(vdev, WLAN_OSIF_ID);
2461 	}
2462 }
2463 
2464 #ifdef WLAN_FEATURE_HOST_ROAM
wlan_hdd_ft_set_key_delay(struct wlan_objmgr_vdev * vdev)2465 void wlan_hdd_ft_set_key_delay(struct wlan_objmgr_vdev *vdev)
2466 {
2467 	int errno = 0;
2468 
2469 	if (ucfg_cm_ft_key_ready_for_install(vdev))
2470 		errno =
2471 		wlan_cfg80211_crypto_add_key(vdev,
2472 					     WLAN_CRYPTO_KEY_TYPE_UNICAST,
2473 					     0, false);
2474 	if (errno)
2475 		hdd_err("ft set key failed");
2476 }
2477 #endif
2478 
hdd_sme_roam_callback(void * context,struct csr_roam_info * roam_info,eRoamCmdStatus roam_status,eCsrRoamResult roam_result)2479 QDF_STATUS hdd_sme_roam_callback(void *context,
2480 				 struct csr_roam_info *roam_info,
2481 				 eRoamCmdStatus roam_status,
2482 				 eCsrRoamResult roam_result)
2483 {
2484 	QDF_STATUS qdf_ret_status = QDF_STATUS_SUCCESS;
2485 	struct wlan_hdd_link_info *link_info = context;
2486 	struct hdd_adapter *adapter = link_info->adapter;
2487 	struct hdd_station_ctx *sta_ctx = NULL;
2488 	struct hdd_context *hdd_ctx;
2489 
2490 	hdd_debug("CSR Callback: status=%s (%d) result= %s (%d)",
2491 		  get_e_roam_cmd_status_str(roam_status), roam_status,
2492 		  get_e_csr_roam_result_str(roam_result), roam_result);
2493 
2494 	/* Sanity check */
2495 	if (WLAN_HDD_ADAPTER_MAGIC != adapter->magic) {
2496 		hdd_err("Invalid adapter or adapter has invalid magic");
2497 		return QDF_STATUS_E_FAILURE;
2498 	}
2499 
2500 	sta_ctx = WLAN_HDD_GET_STATION_CTX_PTR(link_info);
2501 	hdd_ctx = WLAN_HDD_GET_CTX(adapter);
2502 
2503 	MTRACE(qdf_trace(QDF_MODULE_ID_HDD, TRACE_CODE_HDD_RX_SME_MSG,
2504 				 link_info->vdev_id, roam_status));
2505 
2506 	switch (roam_status) {
2507 	case eCSR_ROAM_MIC_ERROR_IND:
2508 		hdd_roam_mic_error_indication_handler(link_info, roam_info);
2509 		break;
2510 
2511 	case eCSR_ROAM_SET_KEY_COMPLETE:
2512 	{
2513 		qdf_ret_status =
2514 			hdd_roam_set_key_complete_handler(link_info, roam_info,
2515 							  roam_status,
2516 							  roam_result);
2517 		if (eCSR_ROAM_RESULT_AUTHENTICATED == roam_result)
2518 			hdd_debug("set key complete, session: %d",
2519 				  link_info->vdev_id);
2520 	}
2521 		break;
2522 	case eCSR_ROAM_UNPROT_MGMT_FRAME_IND:
2523 		if (roam_info)
2524 			hdd_indicate_unprot_mgmt_frame(link_info,
2525 						       roam_info->nFrameLength,
2526 						       roam_info->pbFrames,
2527 						       roam_info->frameType);
2528 		break;
2529 #ifdef FEATURE_WLAN_ESE
2530 	case eCSR_ROAM_TSM_IE_IND:
2531 		if (roam_info)
2532 			hdd_indicate_tsm_ie(adapter,
2533 					    roam_info->tsm_ie.tsid,
2534 					    roam_info->tsm_ie.state,
2535 					    roam_info->tsm_ie.msmt_interval);
2536 		break;
2537 	case eCSR_ROAM_ESE_ADJ_AP_REPORT_IND:
2538 	{
2539 		hdd_indicate_ese_adj_ap_rep_ind(adapter, roam_info);
2540 		break;
2541 	}
2542 
2543 	case eCSR_ROAM_ESE_BCN_REPORT_IND:
2544 	{
2545 		hdd_indicate_ese_bcn_report_ind(adapter, roam_info);
2546 		break;
2547 	}
2548 #endif /* FEATURE_WLAN_ESE */
2549 	case eCSR_ROAM_STA_CHANNEL_SWITCH:
2550 		hdd_roam_channel_switch_handler(link_info, roam_info);
2551 		break;
2552 
2553 	case eCSR_ROAM_NDP_STATUS_UPDATE:
2554 		hdd_ndp_event_handler(link_info, roam_info,
2555 				      roam_status, roam_result);
2556 		break;
2557 	case eCSR_ROAM_SAE_COMPUTE:
2558 		if (roam_info)
2559 			wlan_hdd_sae_callback(link_info, roam_info);
2560 		break;
2561 	default:
2562 		break;
2563 	}
2564 	return qdf_ret_status;
2565 }
2566 
2567 #ifdef WLAN_FEATURE_FILS_SK
2568 /**
2569  * hdd_translate_fils_rsn_to_csr_auth() - Translate FILS RSN to CSR auth type
2570  * @auth_suite: auth suite
2571  * @auth_type: pointer to enum csr_akm_type
2572  *
2573  * Return: None
2574  */
hdd_translate_fils_rsn_to_csr_auth(int8_t auth_suite[4],enum csr_akm_type * auth_type)2575 static void hdd_translate_fils_rsn_to_csr_auth(int8_t auth_suite[4],
2576 					enum csr_akm_type *auth_type)
2577 {
2578 	if (!memcmp(auth_suite, ccp_rsn_oui_0e, 4))
2579 		*auth_type = eCSR_AUTH_TYPE_FILS_SHA256;
2580 	else if (!memcmp(auth_suite, ccp_rsn_oui_0f, 4))
2581 		*auth_type = eCSR_AUTH_TYPE_FILS_SHA384;
2582 	else if (!memcmp(auth_suite, ccp_rsn_oui_10, 4))
2583 		*auth_type = eCSR_AUTH_TYPE_FT_FILS_SHA256;
2584 	else if (!memcmp(auth_suite, ccp_rsn_oui_11, 4))
2585 		*auth_type = eCSR_AUTH_TYPE_FT_FILS_SHA384;
2586 }
2587 #else
hdd_translate_fils_rsn_to_csr_auth(int8_t auth_suite[4],enum csr_akm_type * auth_type)2588 static inline void hdd_translate_fils_rsn_to_csr_auth(int8_t auth_suite[4],
2589 					enum csr_akm_type *auth_type)
2590 {
2591 }
2592 #endif
2593 
2594 #ifdef WLAN_FEATURE_SAE
2595 /**
2596  * hdd_translate_sae_rsn_to_csr_auth() - Translate SAE RSN to CSR auth type
2597  * @auth_suite: auth suite
2598  * @auth_type: pointer to enum csr_akm_type
2599  *
2600  * Return: None
2601  */
hdd_translate_sae_rsn_to_csr_auth(int8_t auth_suite[4],enum csr_akm_type * auth_type)2602 static void hdd_translate_sae_rsn_to_csr_auth(int8_t auth_suite[4],
2603 					enum csr_akm_type *auth_type)
2604 {
2605 	if (qdf_mem_cmp(auth_suite, ccp_rsn_oui_80, 4) == 0)
2606 		*auth_type = eCSR_AUTH_TYPE_SAE;
2607 	else if (qdf_mem_cmp(auth_suite, ccp_rsn_oui_90, 4) == 0)
2608 		*auth_type = eCSR_AUTH_TYPE_FT_SAE;
2609 
2610 }
2611 #else
hdd_translate_sae_rsn_to_csr_auth(int8_t auth_suite[4],enum csr_akm_type * auth_type)2612 static inline void hdd_translate_sae_rsn_to_csr_auth(int8_t auth_suite[4],
2613 					enum csr_akm_type *auth_type)
2614 {
2615 }
2616 #endif
2617 
hdd_filter_ft_info(const uint8_t * frame,size_t len,uint32_t * ft_info_len)2618 void *hdd_filter_ft_info(const uint8_t *frame, size_t len,
2619 			 uint32_t *ft_info_len)
2620 {
2621 	uint32_t ft_ie_len, md_ie_len, rsn_ie_len, ie_len;
2622 	const uint8_t *rsn_ie, *md_ie, *ft_ie;
2623 	void *ft_info;
2624 
2625 	ft_ie_len = 0;
2626 	md_ie_len = 0;
2627 	rsn_ie_len = 0;
2628 	ie_len = len - DOT11F_FF_CAPABILITIES_LEN - DOT11F_FF_STATUS_LEN
2629 			   - DOT11F_IE_AID_MAX_LEN - sizeof(tSirMacMgmtHdr);
2630 	rsn_ie = wlan_get_ie_ptr_from_eid(DOT11F_EID_RSN, frame, ie_len);
2631 
2632 	if (rsn_ie) {
2633 		rsn_ie_len = rsn_ie[1] + 2;
2634 		QDF_TRACE_HEX_DUMP(QDF_MODULE_ID_HDD, QDF_TRACE_LEVEL_DEBUG,
2635 			(void *)rsn_ie, rsn_ie_len);
2636 	}
2637 	md_ie = wlan_get_ie_ptr_from_eid(DOT11F_EID_MOBILITYDOMAIN,
2638 					 frame, ie_len);
2639 	if (md_ie) {
2640 		md_ie_len = md_ie[1] + 2;
2641 		QDF_TRACE_HEX_DUMP(QDF_MODULE_ID_HDD, QDF_TRACE_LEVEL_DEBUG,
2642 			(void *)md_ie, md_ie_len);
2643 	}
2644 	ft_ie = wlan_get_ie_ptr_from_eid(DOT11F_EID_FTINFO, frame, ie_len);
2645 	if (ft_ie)
2646 		ft_ie_len = ft_ie[1] + 2;
2647 
2648 	*ft_info_len = rsn_ie_len + md_ie_len + ft_ie_len;
2649 	ft_info = qdf_mem_malloc(*ft_info_len);
2650 	if (!ft_info)
2651 		return NULL;
2652 	if (rsn_ie_len)
2653 		qdf_mem_copy(ft_info, rsn_ie, rsn_ie_len);
2654 	if (md_ie_len)
2655 		qdf_mem_copy(ft_info + rsn_ie_len, md_ie, md_ie_len);
2656 	if (ft_ie_len)
2657 		qdf_mem_copy(ft_info + rsn_ie_len + md_ie_len,
2658 			     ft_ie, ft_ie_len);
2659 	return ft_info;
2660 }
2661 
2662 /**
2663  * hdd_translate_rsn_to_csr_auth_type() - Translate RSN to CSR auth type
2664  * @auth_suite: auth suite
2665  *
2666  * Return: enum csr_akm_type enumeration
2667  */
hdd_translate_rsn_to_csr_auth_type(uint8_t auth_suite[4])2668 enum csr_akm_type hdd_translate_rsn_to_csr_auth_type(uint8_t auth_suite[4])
2669 {
2670 	enum csr_akm_type auth_type = eCSR_AUTH_TYPE_UNKNOWN;
2671 	/* is the auth type supported? */
2672 	if (memcmp(auth_suite, ccp_rsn_oui01, 4) == 0) {
2673 		auth_type = eCSR_AUTH_TYPE_RSN;
2674 	} else if (memcmp(auth_suite, ccp_rsn_oui02, 4) == 0) {
2675 		auth_type = eCSR_AUTH_TYPE_RSN_PSK;
2676 	} else if (memcmp(auth_suite, ccp_rsn_oui04, 4) == 0) {
2677 		/* Check for 11r FT Authentication with PSK */
2678 		auth_type = eCSR_AUTH_TYPE_FT_RSN_PSK;
2679 	} else if (memcmp(auth_suite, ccp_rsn_oui03, 4) == 0) {
2680 		/* Check for 11R FT Authentication with 802.1X */
2681 		auth_type = eCSR_AUTH_TYPE_FT_RSN;
2682 	} else
2683 #ifdef FEATURE_WLAN_ESE
2684 	if (memcmp(auth_suite, ccp_rsn_oui06, 4) == 0) {
2685 		auth_type = eCSR_AUTH_TYPE_CCKM_RSN;
2686 	} else
2687 #endif /* FEATURE_WLAN_ESE */
2688 	if (memcmp(auth_suite, ccp_rsn_oui07, 4) == 0) {
2689 		auth_type = eCSR_AUTH_TYPE_RSN_PSK_SHA256;
2690 	} else if (memcmp(auth_suite, ccp_rsn_oui08, 4) == 0) {
2691 		auth_type = eCSR_AUTH_TYPE_RSN_8021X_SHA256;
2692 	} else if (memcmp(auth_suite, ccp_rsn_oui_18, 4) == 0) {
2693 		auth_type = eCSR_AUTH_TYPE_OWE;
2694 	} else if (memcmp(auth_suite, ccp_rsn_oui_12, 4) == 0) {
2695 		auth_type = eCSR_AUTH_TYPE_DPP_RSN;
2696 	} else if (memcmp(auth_suite, ccp_rsn_oui_0b, 4) == 0) {
2697 		/* Check for Suite B EAP 256 */
2698 		auth_type = eCSR_AUTH_TYPE_SUITEB_EAP_SHA256;
2699 	} else if (memcmp(auth_suite, ccp_rsn_oui_0c, 4) == 0) {
2700 		/* Check for Suite B EAP 384 */
2701 		auth_type = eCSR_AUTH_TYPE_SUITEB_EAP_SHA384;
2702 	} else if (memcmp(auth_suite, ccp_rsn_oui_0d, 4) == 0) {
2703 		/* Check for FT Suite B EAP 384 */
2704 		auth_type = eCSR_AUTH_TYPE_FT_SUITEB_EAP_SHA384;
2705 	} else if (memcmp(auth_suite, ccp_rsn_oui_13, 4) == 0) {
2706 		auth_type = eCSR_AUTH_TYPE_OSEN;
2707 	} else {
2708 		hdd_translate_fils_rsn_to_csr_auth(auth_suite, &auth_type);
2709 		hdd_translate_sae_rsn_to_csr_auth(auth_suite, &auth_type);
2710 	}
2711 
2712 	return auth_type;
2713 }
2714 
2715 /**
2716  * hdd_translate_wpa_to_csr_auth_type() - Translate WPA to CSR auth type
2717  * @auth_suite: auth suite
2718  *
2719  * Return: enum csr_akm_type enumeration
2720  */
hdd_translate_wpa_to_csr_auth_type(uint8_t auth_suite[4])2721 enum csr_akm_type hdd_translate_wpa_to_csr_auth_type(uint8_t auth_suite[4])
2722 {
2723 	enum csr_akm_type auth_type = eCSR_AUTH_TYPE_UNKNOWN;
2724 	/* is the auth type supported? */
2725 	if (memcmp(auth_suite, ccp_wpa_oui01, 4) == 0) {
2726 		auth_type = eCSR_AUTH_TYPE_WPA;
2727 	} else if (memcmp(auth_suite, ccp_wpa_oui02, 4) == 0) {
2728 		auth_type = eCSR_AUTH_TYPE_WPA_PSK;
2729 	} else
2730 #ifdef FEATURE_WLAN_ESE
2731 	if (memcmp(auth_suite, ccp_wpa_oui06, 4) == 0) {
2732 		auth_type = eCSR_AUTH_TYPE_CCKM_WPA;
2733 	} else
2734 #endif /* FEATURE_WLAN_ESE */
2735 	{
2736 		hdd_translate_fils_rsn_to_csr_auth(auth_suite, &auth_type);
2737 	}
2738 
2739 	return auth_type;
2740 }
2741 
2742 /**
2743  * hdd_translate_rsn_to_csr_encryption_type() -
2744  *	Translate RSN to CSR encryption type
2745  * @cipher_suite: cipher suite
2746  *
2747  * Return: eCsrEncryptionType enumeration
2748  */
2749 eCsrEncryptionType
hdd_translate_rsn_to_csr_encryption_type(uint8_t cipher_suite[4])2750 hdd_translate_rsn_to_csr_encryption_type(uint8_t cipher_suite[4])
2751 {
2752 	eCsrEncryptionType cipher_type;
2753 
2754 	if (memcmp(cipher_suite, ccp_rsn_oui04, 4) == 0)
2755 		cipher_type = eCSR_ENCRYPT_TYPE_AES;
2756 	else if (memcmp(cipher_suite, ccp_rsn_oui09, 4) == 0)
2757 		cipher_type = eCSR_ENCRYPT_TYPE_AES_GCMP;
2758 	else if (memcmp(cipher_suite, ccp_rsn_oui0a, 4) == 0)
2759 		cipher_type = eCSR_ENCRYPT_TYPE_AES_GCMP_256;
2760 	else if (memcmp(cipher_suite, ccp_rsn_oui02, 4) == 0)
2761 		cipher_type = eCSR_ENCRYPT_TYPE_TKIP;
2762 	else if (memcmp(cipher_suite, ccp_rsn_oui00, 4) == 0)
2763 		cipher_type = eCSR_ENCRYPT_TYPE_NONE;
2764 	else if (memcmp(cipher_suite, ccp_rsn_oui01, 4) == 0)
2765 		cipher_type = eCSR_ENCRYPT_TYPE_WEP40_STATICKEY;
2766 	else if (memcmp(cipher_suite, ccp_rsn_oui05, 4) == 0)
2767 		cipher_type = eCSR_ENCRYPT_TYPE_WEP104_STATICKEY;
2768 	else
2769 		cipher_type = eCSR_ENCRYPT_TYPE_FAILED;
2770 
2771 	return cipher_type;
2772 }
2773 
2774 /**
2775  * hdd_translate_wpa_to_csr_encryption_type() -
2776  *	Translate WPA to CSR encryption type
2777  * @cipher_suite: cipher suite
2778  *
2779  * Return: eCsrEncryptionType enumeration
2780  */
2781 eCsrEncryptionType
hdd_translate_wpa_to_csr_encryption_type(uint8_t cipher_suite[4])2782 hdd_translate_wpa_to_csr_encryption_type(uint8_t cipher_suite[4])
2783 {
2784 	eCsrEncryptionType cipher_type;
2785 
2786 	if (memcmp(cipher_suite, ccp_wpa_oui04, 4) == 0)
2787 		cipher_type = eCSR_ENCRYPT_TYPE_AES;
2788 	else if (memcmp(cipher_suite, ccp_wpa_oui02, 4) == 0)
2789 		cipher_type = eCSR_ENCRYPT_TYPE_TKIP;
2790 	else if (memcmp(cipher_suite, ccp_wpa_oui00, 4) == 0)
2791 		cipher_type = eCSR_ENCRYPT_TYPE_NONE;
2792 	else if (memcmp(cipher_suite, ccp_wpa_oui01, 4) == 0)
2793 		cipher_type = eCSR_ENCRYPT_TYPE_WEP40_STATICKEY;
2794 	else if (memcmp(cipher_suite, ccp_wpa_oui05, 4) == 0)
2795 		cipher_type = eCSR_ENCRYPT_TYPE_WEP104_STATICKEY;
2796 	else
2797 		cipher_type = eCSR_ENCRYPT_TYPE_FAILED;
2798 
2799 	return cipher_type;
2800 }
2801 
2802 #ifdef FEATURE_WLAN_WAPI
hdd_translate_wapi_to_csr_auth_type(uint8_t auth_suite[4])2803 enum csr_akm_type hdd_translate_wapi_to_csr_auth_type(uint8_t auth_suite[4])
2804 {
2805 	enum csr_akm_type auth_type;
2806 
2807 	if (memcmp(auth_suite, ccp_wapi_oui01, 4) == 0)
2808 		auth_type = eCSR_AUTH_TYPE_WAPI_WAI_CERTIFICATE;
2809 	else if (memcmp(auth_suite, ccp_wapi_oui02, 4) == 0)
2810 		auth_type = eCSR_AUTH_TYPE_WAPI_WAI_PSK;
2811 	else
2812 		auth_type = eCSR_AUTH_TYPE_UNKNOWN;
2813 
2814 	return auth_type;
2815 }
2816 
2817 eCsrEncryptionType
hdd_translate_wapi_to_csr_encryption_type(uint8_t cipher_suite[4])2818 hdd_translate_wapi_to_csr_encryption_type(uint8_t cipher_suite[4])
2819 {
2820 	eCsrEncryptionType cipher_type;
2821 
2822 	if (memcmp(cipher_suite, ccp_wapi_oui01, 4) == 0 ||
2823 		   memcmp(cipher_suite, ccp_wapi_oui02, 4) == 0)
2824 		cipher_type = eCSR_ENCRYPT_TYPE_WPI;
2825 	else
2826 		cipher_type = eCSR_ENCRYPT_TYPE_FAILED;
2827 
2828 	return cipher_type;
2829 }
2830 #endif /* FEATURE_WLAN_WAPI */
2831 
2832 enum cdp_peer_bw
hdd_convert_ch_width_to_cdp_peer_bw(enum phy_ch_width ch_width)2833 hdd_convert_ch_width_to_cdp_peer_bw(enum phy_ch_width ch_width)
2834 {
2835 	switch (ch_width) {
2836 	case CH_WIDTH_20MHZ:
2837 		return CDP_20_MHZ;
2838 	case CH_WIDTH_40MHZ:
2839 		return CDP_40_MHZ;
2840 	case CH_WIDTH_80MHZ:
2841 		return CDP_80_MHZ;
2842 	case CH_WIDTH_160MHZ:
2843 		return CDP_160_MHZ;
2844 	case CH_WIDTH_80P80MHZ:
2845 		return CDP_80P80_MHZ;
2846 	case CH_WIDTH_5MHZ:
2847 		return CDP_5_MHZ;
2848 	case CH_WIDTH_10MHZ:
2849 		return CDP_10_MHZ;
2850 	case CH_WIDTH_320MHZ:
2851 		return CDP_320_MHZ;
2852 	default:
2853 		return CDP_BW_INVALID;
2854 	}
2855 
2856 	return CDP_BW_INVALID;
2857 }
2858 
2859 #ifdef WLAN_FEATURE_FILS_SK
hdd_is_fils_connection(struct hdd_context * hdd_ctx,struct hdd_adapter * adapter)2860 bool hdd_is_fils_connection(struct hdd_context *hdd_ctx,
2861 			    struct hdd_adapter *adapter)
2862 {
2863 	struct wlan_fils_connection_info *fils_info;
2864 
2865 	fils_info = wlan_cm_get_fils_connection_info(hdd_ctx->psoc,
2866 						     adapter->deflink->vdev_id);
2867 	if (fils_info)
2868 		return fils_info->is_fils_connection;
2869 
2870 	return false;
2871 }
2872 #else
hdd_is_fils_connection(struct hdd_context * hdd_ctx,struct hdd_adapter * adapter)2873 bool hdd_is_fils_connection(struct hdd_context *hdd_ctx,
2874 			    struct hdd_adapter *adapter)
2875 {
2876 	return false;
2877 }
2878 #endif
2879 
hdd_roam_profile_init(struct wlan_hdd_link_info * link_info)2880 void hdd_roam_profile_init(struct wlan_hdd_link_info *link_info)
2881 {
2882 	struct csr_roam_profile *roam_profile;
2883 	struct hdd_station_ctx *sta_ctx;
2884 
2885 	hdd_enter();
2886 
2887 	roam_profile = hdd_roam_profile(link_info);
2888 	qdf_mem_zero(roam_profile, sizeof(*roam_profile));
2889 
2890 	sta_ctx = WLAN_HDD_GET_STATION_CTX_PTR(link_info);
2891 
2892 	/* Configure the roaming profile links to SSID and bssid. */
2893 	roam_profile->SSIDs.numOfSSIDs = 0;
2894 	roam_profile->SSIDs.SSIDList = &sta_ctx->conn_info.ssid;
2895 
2896 	roam_profile->BSSIDs.numOfBSSIDs = 0;
2897 	roam_profile->BSSIDs.bssid = &sta_ctx->conn_info.bssid;
2898 
2899 	/* Set the numOfChannels to zero to scan all the channels */
2900 	roam_profile->ChannelInfo.numOfChannels = 0;
2901 	roam_profile->ChannelInfo.freq_list = NULL;
2902 
2903 	roam_profile->BSSType = eCSR_BSS_TYPE_INFRASTRUCTURE;
2904 
2905 	roam_profile->phyMode = eCSR_DOT11_MODE_AUTO;
2906 
2907 	/* Set the default scan mode */
2908 	link_info->adapter->scan_info.scan_mode = eSIR_ACTIVE_SCAN;
2909 
2910 	hdd_clear_roam_profile_ie(link_info->adapter);
2911 	hdd_exit();
2912 }
2913 
2914 struct osif_cm_ops osif_ops = {
2915 	.connect_active_notify_cb = hdd_cm_connect_active_notify,
2916 	.connect_complete_cb = hdd_cm_connect_complete,
2917 	.disconnect_complete_cb = hdd_cm_disconnect_complete,
2918 	.netif_queue_control_cb = hdd_cm_netif_queue_control,
2919 	.napi_serialize_control_cb = hdd_cm_napi_serialize_control,
2920 	.save_gtk_cb = hdd_cm_save_gtk,
2921 #ifdef WLAN_FEATURE_ROAM_OFFLOAD
2922 	.roam_rt_stats_event_cb = wlan_hdd_cfg80211_roam_events_callback,
2923 #endif
2924 #ifdef WLAN_FEATURE_FILS_SK
2925 	.set_hlp_data_cb = hdd_cm_set_hlp_data,
2926 #endif
2927 #ifdef WLAN_FEATURE_PREAUTH_ENABLE
2928 	.ft_preauth_complete_cb = hdd_cm_ft_preauth_complete,
2929 #ifdef FEATURE_WLAN_ESE
2930 	.cckm_preauth_complete_cb = hdd_cm_cckm_preauth_complete,
2931 #endif
2932 #endif
2933 #ifdef WLAN_VENDOR_HANDOFF_CONTROL
2934 	.vendor_handoff_params_cb = hdd_cm_get_vendor_handoff_params,
2935 #endif
2936 	.send_vdev_keys_cb = hdd_cm_send_vdev_keys,
2937 	.get_scan_ie_params_cb = hdd_cm_get_scan_ie_params,
2938 #ifdef WLAN_BOOST_CPU_FREQ_IN_ROAM
2939 	.perfd_set_cpufreq_cb = hdd_cm_perfd_set_cpufreq,
2940 #endif
2941 };
2942 
hdd_cm_register_cb(void)2943 QDF_STATUS hdd_cm_register_cb(void)
2944 {
2945 	QDF_STATUS status;
2946 	osif_cm_set_legacy_cb(&osif_ops);
2947 
2948 	status = osif_cm_register_cb();
2949 	if (QDF_IS_STATUS_ERROR(status))
2950 		return status;
2951 
2952 	/* Overwrite with UTF cb if UTF enabled */
2953 	return cm_utf_register_os_if_cb();
2954 }
2955 
hdd_cm_unregister_cb(void)2956 void hdd_cm_unregister_cb(void)
2957 {
2958 	osif_cm_reset_legacy_cb();
2959 }
2960