blob: cd90e9f817cd1ca22d68c0b167c84f0a56e92e54 [file] [log] [blame]
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001/*
Tushnim Bhattacharyyaca50b322015-12-28 17:14:36 -08002 * Copyright (c) 2012-2016 The Linux Foundation. All rights reserved.
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003 *
4 * Previously licensed under the ISC license by Qualcomm Atheros, Inc.
5 *
6 *
7 * Permission to use, copy, modify, and/or distribute this software for
8 * any purpose with or without fee is hereby granted, provided that the
9 * above copyright notice and this permission notice appear in all
10 * copies.
11 *
12 * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL
13 * WARRANTIES WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED
14 * WARRANTIES OF MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE
15 * AUTHOR BE LIABLE FOR ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL
16 * DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR
17 * PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER
18 * TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR
19 * PERFORMANCE OF THIS SOFTWARE.
20 */
21
22/*
23 * This file was originally distributed by Qualcomm Atheros, Inc.
24 * under proprietary terms before Copyright ownership was assigned
25 * to the Linux Foundation.
26 */
27
28/**
29 * DOC: wlan_hdd_assoc.c
30 *
31 * WLAN Host Device Driver implementation
32 *
33 */
34
Archana Ramachandran75c1ca72016-08-22 17:20:25 -070035/* denote that this file does not allow legacy hddLog */
36#define HDD_DISALLOW_LEGACY_HDDLOG 1
37
Prakash Dhavali7090c5f2015-11-02 17:55:19 -080038#include "wlan_hdd_includes.h"
39#include <ani_global.h>
40#include "dot11f.h"
41#include "wlan_hdd_power.h"
Sreelakshmi Konamkic88f5372015-12-22 12:50:15 +053042#include "wlan_hdd_trace.h"
Prakash Dhavali7090c5f2015-11-02 17:55:19 -080043#include <linux/ieee80211.h>
44#include <linux/wireless.h>
45#include <linux/etherdevice.h>
46#include <net/cfg80211.h>
47#include "wlan_hdd_cfg80211.h"
48#include "csr_inside_api.h"
49#include "wlan_hdd_p2p.h"
Prakash Dhavali7090c5f2015-11-02 17:55:19 -080050#include "wlan_hdd_tdls.h"
Prakash Dhavali7090c5f2015-11-02 17:55:19 -080051#include "sme_api.h"
52#include "wlan_hdd_hostapd.h"
53#include <wlan_hdd_ipa.h>
Jeff Johnson2b0a7b82016-05-18 15:08:02 -070054#include "wlan_hdd_lpass.h"
Prakash Dhavali7090c5f2015-11-02 17:55:19 -080055#include <cds_sched.h>
56#include "cds_concurrency.h"
Anurag Chouhan5de8d172016-07-13 14:44:28 +053057#include <cds_utils.h>
Prakash Dhavali7090c5f2015-11-02 17:55:19 -080058#include "sme_power_save_api.h"
59#include "ol_txrx_ctrl_api.h"
60#include "ol_txrx_types.h"
Dhanashri Atre182b0272016-02-17 15:35:07 -080061#include "ol_txrx.h"
Himanshu Agarwal11c874a2016-05-06 18:35:29 +053062#include "ol_rx_fwd.h"
Dhanashri Atreb08959a2016-03-01 17:28:03 -080063#include "cdp_txrx_flow_ctrl_legacy.h"
64#include "cdp_txrx_peer_ops.h"
Varun Reddy Yeturu04251862016-09-16 10:33:19 -070065#include "wlan_hdd_napi.h"
Himanshu Agarwal0527e8f2016-08-11 14:58:34 +053066#include <wlan_logging_sock_svc.h>
Prakash Dhavali7090c5f2015-11-02 17:55:19 -080067
68/* These are needed to recognize WPA and RSN suite types */
69#define HDD_WPA_OUI_SIZE 4
70#define HDD_RSN_OUI_SIZE 4
71uint8_t ccp_wpa_oui00[HDD_WPA_OUI_SIZE] = { 0x00, 0x50, 0xf2, 0x00 };
72uint8_t ccp_wpa_oui01[HDD_WPA_OUI_SIZE] = { 0x00, 0x50, 0xf2, 0x01 };
73uint8_t ccp_wpa_oui02[HDD_WPA_OUI_SIZE] = { 0x00, 0x50, 0xf2, 0x02 };
74uint8_t ccp_wpa_oui03[HDD_WPA_OUI_SIZE] = { 0x00, 0x50, 0xf2, 0x03 };
75uint8_t ccp_wpa_oui04[HDD_WPA_OUI_SIZE] = { 0x00, 0x50, 0xf2, 0x04 };
76uint8_t ccp_wpa_oui05[HDD_WPA_OUI_SIZE] = { 0x00, 0x50, 0xf2, 0x05 };
77
78#ifdef FEATURE_WLAN_ESE
79/* CCKM */
80uint8_t ccp_wpa_oui06[HDD_WPA_OUI_SIZE] = { 0x00, 0x40, 0x96, 0x00 };
81/* CCKM */
82uint8_t ccp_rsn_oui06[HDD_RSN_OUI_SIZE] = { 0x00, 0x40, 0x96, 0x00 };
83#endif /* FEATURE_WLAN_ESE */
84
85/* group cipher */
86uint8_t ccp_rsn_oui00[HDD_RSN_OUI_SIZE] = { 0x00, 0x0F, 0xAC, 0x00 };
87
88/* WEP-40 or RSN */
89uint8_t ccp_rsn_oui01[HDD_RSN_OUI_SIZE] = { 0x00, 0x0F, 0xAC, 0x01 };
90
91/* TKIP or RSN-PSK */
92uint8_t ccp_rsn_oui02[HDD_RSN_OUI_SIZE] = { 0x00, 0x0F, 0xAC, 0x02 };
93
94/* Reserved */
95uint8_t ccp_rsn_oui03[HDD_RSN_OUI_SIZE] = { 0x00, 0x0F, 0xAC, 0x03 };
96
97/* AES-CCMP */
98uint8_t ccp_rsn_oui04[HDD_RSN_OUI_SIZE] = { 0x00, 0x0F, 0xAC, 0x04 };
99
100/* WEP-104 */
101uint8_t ccp_rsn_oui05[HDD_RSN_OUI_SIZE] = { 0x00, 0x0F, 0xAC, 0x05 };
102
103#ifdef WLAN_FEATURE_11W
104/* RSN-PSK-SHA256 */
105uint8_t ccp_rsn_oui07[HDD_RSN_OUI_SIZE] = { 0x00, 0x0F, 0xAC, 0x06 };
106
107/* RSN-8021X-SHA256 */
108uint8_t ccp_rsn_oui08[HDD_RSN_OUI_SIZE] = { 0x00, 0x0F, 0xAC, 0x05 };
109#endif
110
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800111/* Offset where the EID-Len-IE, start. */
112#define FT_ASSOC_RSP_IES_OFFSET 6 /* Capability(2) + AID(2) + Status Code(2) */
113#define FT_ASSOC_REQ_IES_OFFSET 4 /* Capability(2) + LI(2) */
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800114
115#define BEACON_FRAME_IES_OFFSET 12
116#define HDD_PEER_AUTHORIZE_WAIT 10
117
118/**
Gupta, Kapil4cb1d7d2016-04-16 18:16:25 -0700119 * beacon_filter_table - table of IEs used for beacon filtering
120 */
121static const int beacon_filter_table[] = {
122 SIR_MAC_DS_PARAM_SET_EID,
123 SIR_MAC_ERP_INFO_EID,
124 SIR_MAC_EDCA_PARAM_SET_EID,
125 SIR_MAC_QOS_CAPABILITY_EID,
126 SIR_MAC_HT_INFO_EID,
127 SIR_MAC_VHT_OPMODE_EID,
128 SIR_MAC_VHT_OPERATION_EID,
129};
130
131/**
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800132 * hdd_conn_set_authenticated() - set authentication state
133 * @pAdapter: pointer to the adapter
134 * @authState: authentication state
135 *
136 * This function updates the global HDD station context
137 * authentication state.
138 *
139 * Return: none
140 */
141static void
142hdd_conn_set_authenticated(hdd_adapter_t *pAdapter, uint8_t authState)
143{
144 hdd_station_ctx_t *pHddStaCtx = WLAN_HDD_GET_STATION_CTX_PTR(pAdapter);
145 hdd_context_t *pHddCtx = WLAN_HDD_GET_CTX(pAdapter);
146
147 /* save the new connection state */
Archana Ramachandran75c1ca72016-08-22 17:20:25 -0700148 hdd_notice("Authenticated state Changed from oldState:%d to State:%d",
149 pHddStaCtx->conn_info.uIsAuthenticated, authState);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800150 pHddStaCtx->conn_info.uIsAuthenticated = authState;
151
152 /* Check is pending ROC request or not when auth state changed */
153 schedule_delayed_work(&pHddCtx->roc_req_work, 0);
154}
155
156/**
157 * hdd_conn_set_connection_state() - set connection state
158 * @pAdapter: pointer to the adapter
159 * @connState: connection state
160 *
161 * This function updates the global HDD station context connection state.
162 *
163 * Return: none
164 */
165void hdd_conn_set_connection_state(hdd_adapter_t *pAdapter,
166 eConnectionState connState)
167{
168 hdd_station_ctx_t *pHddStaCtx = WLAN_HDD_GET_STATION_CTX_PTR(pAdapter);
169 hdd_context_t *pHddCtx = WLAN_HDD_GET_CTX(pAdapter);
170
171 /* save the new connection state */
Abhishek Singh23edd1c2016-05-05 11:56:06 +0530172 hdd_info("%pS Changed connectionState Changed from oldState:%d to State:%d",
173 (void *)_RET_IP_, pHddStaCtx->conn_info.connState,
174 connState);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800175 pHddStaCtx->conn_info.connState = connState;
176
177 /* Check is pending ROC request or not when connection state changed */
178 schedule_delayed_work(&pHddCtx->roc_req_work, 0);
179}
180
181/**
182 * hdd_conn_get_connection_state() - get connection state
183 * @pAdapter: pointer to the adapter
184 * @pConnState: pointer to connection state
185 *
186 * This function updates the global HDD station context connection state.
187 *
188 * Return: true if (Infra Associated or IBSS Connected)
189 * and sets output parameter pConnState;
190 * false otherwise
191 */
192static inline bool hdd_conn_get_connection_state(hdd_station_ctx_t *pHddStaCtx,
193 eConnectionState *pConnState)
194{
195 bool fConnected = false;
196 eConnectionState connState;
197
198 /* get the connection state. */
199 connState = pHddStaCtx->conn_info.connState;
200
201 if (eConnectionState_Associated == connState ||
202 eConnectionState_IbssConnected == connState ||
203 eConnectionState_IbssDisconnected == connState) {
204 fConnected = true;
205 }
206
207 if (pConnState)
208 *pConnState = connState;
209
210 return fConnected;
211}
212
213/**
214 * hdd_is_connecting() - Function to check connection progress
215 * @hdd_sta_ctx: pointer to global HDD Station context
216 *
217 * Return: true if connecting, false otherwise
218 */
219bool hdd_is_connecting(hdd_station_ctx_t *hdd_sta_ctx)
220{
221 return hdd_sta_ctx->conn_info.connState ==
222 eConnectionState_Connecting;
223}
224
225/**
226 * hdd_conn_is_connected() - Function to check connection status
227 * @pHddStaCtx: pointer to global HDD Station context
228 *
229 * Return: false if any errors encountered, true otherwise
230 */
231bool hdd_conn_is_connected(hdd_station_ctx_t *pHddStaCtx)
232{
233 return hdd_conn_get_connection_state(pHddStaCtx, NULL);
234}
235
236/**
237 * hdd_conn_get_connected_band() - get current connection radio band
238 * @pHddStaCtx: pointer to global HDD Station context
239 *
240 * Return: eCSR_BAND_24 or eCSR_BAND_5G based on current AP connection
241 * eCSR_BAND_ALL if not connected
242 */
243eCsrBand hdd_conn_get_connected_band(hdd_station_ctx_t *pHddStaCtx)
244{
245 uint8_t staChannel = 0;
246
247 if (eConnectionState_Associated == pHddStaCtx->conn_info.connState)
248 staChannel = pHddStaCtx->conn_info.operationChannel;
249
250 if (staChannel > 0 && staChannel < 14)
251 return eCSR_BAND_24;
252 else if (staChannel >= 36 && staChannel <= 184)
253 return eCSR_BAND_5G;
254 else /* If station is not connected return as eCSR_BAND_ALL */
255 return eCSR_BAND_ALL;
256}
257
258/**
259 * hdd_conn_get_connected_cipher_algo() - get current connection cipher type
260 * @pHddStaCtx: pointer to global HDD Station context
261 * @pConnectedCipherAlgo: pointer to connected cipher algo
262 *
263 * Return: false if any errors encountered, true otherwise
264 */
265static inline bool
266hdd_conn_get_connected_cipher_algo(hdd_station_ctx_t *pHddStaCtx,
267 eCsrEncryptionType *pConnectedCipherAlgo)
268{
269 bool fConnected = false;
270
271 fConnected = hdd_conn_get_connection_state(pHddStaCtx, NULL);
272
273 if (pConnectedCipherAlgo)
274 *pConnectedCipherAlgo = pHddStaCtx->conn_info.ucEncryptionType;
275
276 return fConnected;
277}
278
279/**
Gupta, Kapil4cb1d7d2016-04-16 18:16:25 -0700280 * hdd_remove_beacon_filter() - remove beacon filter
281 * @adapter: Pointer to the hdd adapter
282 *
283 * Return: 0 on success and errno on failure
284 */
285static int hdd_remove_beacon_filter(hdd_adapter_t *adapter)
286{
287 QDF_STATUS status;
288 hdd_context_t *hdd_ctx = WLAN_HDD_GET_CTX(adapter);
289
290 status = sme_remove_beacon_filter(hdd_ctx->hHal,
291 adapter->sessionId);
292 if (!QDF_IS_STATUS_SUCCESS(status)) {
293 hdd_err("sme_remove_beacon_filter() failed");
294 return -EFAULT;
295 }
296
297 return 0;
298}
299
300/**
301 * hdd_add_beacon_filter() - add beacon filter
302 * @adapter: Pointer to the hdd adapter
303 *
304 * Return: 0 on success and errno on failure
305 */
306static int hdd_add_beacon_filter(hdd_adapter_t *adapter)
307{
308 int i;
309 uint32_t ie_map[SIR_BCN_FLT_MAX_ELEMS_IE_LIST] = {0};
310 QDF_STATUS status;
311 hdd_context_t *hdd_ctx = WLAN_HDD_GET_CTX(adapter);
312
313 for (i = 0; i < ARRAY_SIZE(beacon_filter_table); i++)
Kapil Gupta80f4a8d2016-09-22 16:54:35 +0530314 qdf_set_bit((beacon_filter_table[i]),
Gupta, Kapil4cb1d7d2016-04-16 18:16:25 -0700315 (unsigned long int *)ie_map);
316
317 status = sme_add_beacon_filter(hdd_ctx->hHal,
318 adapter->sessionId, ie_map);
319 if (!QDF_IS_STATUS_SUCCESS(status)) {
320 hdd_err("sme_add_beacon_filter() failed");
321 return -EFAULT;
322 }
323 return 0;
324}
325
326/**
Anurag Chouhan5de8d172016-07-13 14:44:28 +0530327 * hdd_copy_vht_caps()- copy vht caps info from roam info to
328 * hdd station context.
329 * @hdd_sta_ctx: pointer to hdd station context
330 * @roam_info: pointer to roam info
331 *
332 * Return: None
333 */
334static void hdd_copy_ht_caps(hdd_station_ctx_t *hdd_sta_ctx,
335 tCsrRoamInfo *roam_info)
336{
337 tDot11fIEHTCaps *roam_ht_cap = &roam_info->ht_caps;
338 struct ieee80211_ht_cap *hdd_ht_cap = &hdd_sta_ctx->conn_info.ht_caps;
339 uint32_t i, temp_ht_cap;
340
341 qdf_mem_zero(hdd_ht_cap, sizeof(struct ieee80211_ht_cap));
342
343 if (roam_ht_cap->advCodingCap)
344 hdd_ht_cap->cap_info |= IEEE80211_HT_CAP_LDPC_CODING;
345 if (roam_ht_cap->supportedChannelWidthSet)
346 hdd_ht_cap->cap_info |= IEEE80211_HT_CAP_SUP_WIDTH_20_40;
347 temp_ht_cap = roam_ht_cap->mimoPowerSave &
348 (IEEE80211_HT_CAP_SM_PS >> IEEE80211_HT_CAP_SM_PS_SHIFT);
349 if (temp_ht_cap)
350 hdd_ht_cap->cap_info |=
351 temp_ht_cap << IEEE80211_HT_CAP_SM_PS_SHIFT;
352 if (roam_ht_cap->greenField)
353 hdd_ht_cap->cap_info |= IEEE80211_HT_CAP_GRN_FLD;
354 if (roam_ht_cap->shortGI20MHz)
355 hdd_ht_cap->cap_info |= IEEE80211_HT_CAP_SGI_20;
356 if (roam_ht_cap->shortGI40MHz)
357 hdd_ht_cap->cap_info |= IEEE80211_HT_CAP_SGI_40;
358 if (roam_ht_cap->txSTBC)
359 hdd_ht_cap->cap_info |= IEEE80211_HT_CAP_TX_STBC;
360 temp_ht_cap = roam_ht_cap->rxSTBC & (IEEE80211_HT_CAP_RX_STBC >>
361 IEEE80211_HT_CAP_RX_STBC_SHIFT);
362 if (temp_ht_cap)
363 hdd_ht_cap->cap_info |=
364 temp_ht_cap << IEEE80211_HT_CAP_RX_STBC_SHIFT;
365 if (roam_ht_cap->delayedBA)
366 hdd_ht_cap->cap_info |= IEEE80211_HT_CAP_DELAY_BA;
367 if (roam_ht_cap->maximalAMSDUsize)
368 hdd_ht_cap->cap_info |= IEEE80211_HT_CAP_MAX_AMSDU;
369 if (roam_ht_cap->dsssCckMode40MHz)
370 hdd_ht_cap->cap_info |= IEEE80211_HT_CAP_DSSSCCK40;
371 if (roam_ht_cap->psmp)
372 hdd_ht_cap->cap_info |= IEEE80211_HT_CAP_RESERVED;
373 if (roam_ht_cap->stbcControlFrame)
374 hdd_ht_cap->cap_info |= IEEE80211_HT_CAP_40MHZ_INTOLERANT;
375 if (roam_ht_cap->lsigTXOPProtection)
376 hdd_ht_cap->cap_info |= IEEE80211_HT_CAP_LSIG_TXOP_PROT;
377
378 /* 802.11n HT capability AMPDU settings (for ampdu_params_info) */
379 if (roam_ht_cap->maxRxAMPDUFactor)
380 hdd_ht_cap->ampdu_params_info |=
381 IEEE80211_HT_AMPDU_PARM_FACTOR;
382 temp_ht_cap = roam_ht_cap->mpduDensity &
383 (IEEE80211_HT_AMPDU_PARM_DENSITY >>
384 IEEE80211_HT_AMPDU_PARM_DENSITY_SHIFT);
385 if (temp_ht_cap)
386 hdd_ht_cap->ampdu_params_info |=
387 temp_ht_cap << IEEE80211_HT_AMPDU_PARM_DENSITY_SHIFT;
388
389 /* 802.11n HT extended capabilities masks */
390 if (roam_ht_cap->pco)
391 hdd_ht_cap->extended_ht_cap_info |=
392 IEEE80211_HT_EXT_CAP_PCO;
393 temp_ht_cap = roam_ht_cap->transitionTime &
394 (IEEE80211_HT_EXT_CAP_PCO_TIME >>
395 IEEE80211_HT_EXT_CAP_PCO_TIME_SHIFT);
396 if (temp_ht_cap)
397 hdd_ht_cap->extended_ht_cap_info |=
398 temp_ht_cap << IEEE80211_HT_EXT_CAP_PCO_TIME_SHIFT;
399 temp_ht_cap = roam_ht_cap->mcsFeedback &
400 (IEEE80211_HT_EXT_CAP_MCS_FB >> IEEE80211_HT_EXT_CAP_MCS_FB_SHIFT);
401 if (temp_ht_cap)
402 hdd_ht_cap->extended_ht_cap_info |=
403 temp_ht_cap << IEEE80211_HT_EXT_CAP_MCS_FB_SHIFT;
404
405 /* tx_bf_cap_info capabilities */
406 if (roam_ht_cap->txBF)
407 hdd_ht_cap->tx_BF_cap_info |= TX_BF_CAP_INFO_TX_BF;
408 if (roam_ht_cap->rxStaggeredSounding)
409 hdd_ht_cap->tx_BF_cap_info |=
410 TX_BF_CAP_INFO_RX_STAG_RED_SOUNDING;
411 if (roam_ht_cap->txStaggeredSounding)
412 hdd_ht_cap->tx_BF_cap_info |=
413 TX_BF_CAP_INFO_TX_STAG_RED_SOUNDING;
414 if (roam_ht_cap->rxZLF)
415 hdd_ht_cap->tx_BF_cap_info |= TX_BF_CAP_INFO_RX_ZFL;
416 if (roam_ht_cap->txZLF)
417 hdd_ht_cap->tx_BF_cap_info |= TX_BF_CAP_INFO_TX_ZFL;
418 if (roam_ht_cap->implicitTxBF)
419 hdd_ht_cap->tx_BF_cap_info |= TX_BF_CAP_INFO_IMP_TX_BF;
420 temp_ht_cap = roam_ht_cap->calibration &
421 (TX_BF_CAP_INFO_CALIBRATION >> TX_BF_CAP_INFO_CALIBRATION_SHIFT);
422 if (temp_ht_cap)
423 hdd_ht_cap->tx_BF_cap_info |=
424 temp_ht_cap << TX_BF_CAP_INFO_CALIBRATION_SHIFT;
425 if (roam_ht_cap->explicitCSITxBF)
426 hdd_ht_cap->tx_BF_cap_info |= TX_BF_CAP_INFO_EXP_CSIT_BF;
427 if (roam_ht_cap->explicitUncompressedSteeringMatrix)
428 hdd_ht_cap->tx_BF_cap_info |=
429 TX_BF_CAP_INFO_EXP_UNCOMP_STEER_MAT;
430 temp_ht_cap = roam_ht_cap->explicitBFCSIFeedback &
431 (TX_BF_CAP_INFO_EXP_BF_CSI_FB >>
432 TX_BF_CAP_INFO_EXP_BF_CSI_FB_SHIFT);
433 if (temp_ht_cap)
434 hdd_ht_cap->tx_BF_cap_info |=
435 temp_ht_cap << TX_BF_CAP_INFO_EXP_BF_CSI_FB_SHIFT;
436 temp_ht_cap =
437 roam_ht_cap->explicitUncompressedSteeringMatrixFeedback &
438 (TX_BF_CAP_INFO_EXP_UNCMP_STEER_MAT >>
439 TX_BF_CAP_INFO_EXP_UNCMP_STEER_MAT_SHIFT);
440 if (temp_ht_cap)
441 hdd_ht_cap->tx_BF_cap_info |=
442 temp_ht_cap <<
443 TX_BF_CAP_INFO_EXP_UNCMP_STEER_MAT_SHIFT;
444 temp_ht_cap =
445 roam_ht_cap->explicitCompressedSteeringMatrixFeedback &
446 (TX_BF_CAP_INFO_EXP_CMP_STEER_MAT_FB >>
447 TX_BF_CAP_INFO_EXP_CMP_STEER_MAT_FB_SHIFT);
448 if (temp_ht_cap)
449 hdd_ht_cap->tx_BF_cap_info |=
450 temp_ht_cap <<
451 TX_BF_CAP_INFO_EXP_CMP_STEER_MAT_FB_SHIFT;
452 temp_ht_cap = roam_ht_cap->csiNumBFAntennae &
453 (TX_BF_CAP_INFO_CSI_NUM_BF_ANT >>
454 TX_BF_CAP_INFO_CSI_NUM_BF_ANT_SHIFT);
455 if (temp_ht_cap)
456 hdd_ht_cap->tx_BF_cap_info |=
457 temp_ht_cap << TX_BF_CAP_INFO_CSI_NUM_BF_ANT_SHIFT;
458 temp_ht_cap = roam_ht_cap->uncompressedSteeringMatrixBFAntennae &
459 (TX_BF_CAP_INFO_UNCOMP_STEER_MAT_BF_ANT >>
460 TX_BF_CAP_INFO_UNCOMP_STEER_MAT_BF_ANT_SHIFT);
461 if (temp_ht_cap)
462 hdd_ht_cap->tx_BF_cap_info |=
463 temp_ht_cap <<
464 TX_BF_CAP_INFO_UNCOMP_STEER_MAT_BF_ANT_SHIFT;
465 temp_ht_cap = roam_ht_cap->compressedSteeringMatrixBFAntennae &
466 (TX_BF_CAP_INFO_COMP_STEER_MAT_BF_ANT >>
467 TX_BF_CAP_INFO_COMP_STEER_MAT_BF_ANT_SHIFT);
468 if (temp_ht_cap)
469 hdd_ht_cap->tx_BF_cap_info |=
470 temp_ht_cap <<
471 TX_BF_CAP_INFO_COMP_STEER_MAT_BF_ANT_SHIFT;
472
473 /* antenna selection */
474 if (roam_ht_cap->antennaSelection)
475 hdd_ht_cap->antenna_selection_info |= ANTENNA_SEL_INFO;
476 if (roam_ht_cap->explicitCSIFeedbackTx)
477 hdd_ht_cap->antenna_selection_info |=
478 ANTENNA_SEL_INFO_EXP_CSI_FB_TX;
479 if (roam_ht_cap->antennaIndicesFeedbackTx)
480 hdd_ht_cap->antenna_selection_info |=
481 ANTENNA_SEL_INFO_ANT_ID_FB_TX;
482 if (roam_ht_cap->explicitCSIFeedback)
483 hdd_ht_cap->antenna_selection_info |=
484 ANTENNA_SEL_INFO_EXP_CSI_FB;
485 if (roam_ht_cap->antennaIndicesFeedback)
486 hdd_ht_cap->antenna_selection_info |=
487 ANTENNA_SEL_INFO_ANT_ID_FB;
488 if (roam_ht_cap->rxAS)
489 hdd_ht_cap->antenna_selection_info |=
490 ANTENNA_SEL_INFO_RX_AS;
491 if (roam_ht_cap->txSoundingPPDUs)
492 hdd_ht_cap->antenna_selection_info |=
493 ANTENNA_SEL_INFO_TX_SOUNDING_PPDU;
494
495 /* mcs data rate */
496 for (i = 0; i < IEEE80211_HT_MCS_MASK_LEN; ++i)
497 hdd_ht_cap->mcs.rx_mask[i] =
498 roam_ht_cap->supportedMCSSet[i];
499 hdd_ht_cap->mcs.rx_highest =
500 ((short) (roam_ht_cap->supportedMCSSet[11]) << 8) |
501 ((short) (roam_ht_cap->supportedMCSSet[10]));
502 hdd_ht_cap->mcs.tx_params =
503 roam_ht_cap->supportedMCSSet[12];
504}
505
506#define VHT_CAP_MAX_MPDU_LENGTH_MASK 0x00000003
507#define VHT_CAP_SUPP_CHAN_WIDTH_MASK_SHIFT 2
508#define VHT_CAP_RXSTBC_MASK_SHIFT 8
509#define VHT_CAP_BEAMFORMEE_STS_SHIFT 13
510#define VHT_CAP_BEAMFORMEE_STS_MASK \
511 (0x0000e000 >> VHT_CAP_BEAMFORMEE_STS_SHIFT)
512#define VHT_CAP_SOUNDING_DIMENSIONS_SHIFT 16
513#define VHT_CAP_SOUNDING_DIMENSIONS_MASK \
514 (0x00070000 >> VHT_CAP_SOUNDING_DIMENSIONS_SHIFT)
515#define VHT_CAP_MAX_A_MPDU_LENGTH_EXPONENT_MASK_SHIFT 23
516#define VHT_CAP_MAX_A_MPDU_LENGTH_EXPONENT_MASK \
517 (0x03800000 >> VHT_CAP_MAX_A_MPDU_LENGTH_EXPONENT_MASK_SHIFT)
518#define VHT_CAP_VHT_LINK_ADAPTATION_VHT_MRQ_MFB_SHIFT 26
519
520/**
521 * hdd_copy_ht_caps()- copy ht caps info from roam info to
522 * hdd station context.
523 * @hdd_sta_ctx: pointer to hdd station context
524 * @roam_info: pointer to roam info
525 *
526 * Return: None
527 */
528static void hdd_copy_vht_caps(hdd_station_ctx_t *hdd_sta_ctx,
529 tCsrRoamInfo *roam_info)
530{
531 tDot11fIEVHTCaps *roam_vht_cap = &roam_info->vht_caps;
532 struct ieee80211_vht_cap *hdd_vht_cap =
533 &hdd_sta_ctx->conn_info.vht_caps;
534 uint32_t temp_vht_cap;
535
536 qdf_mem_zero(hdd_vht_cap, sizeof(struct ieee80211_vht_cap));
537
538 temp_vht_cap = roam_vht_cap->maxMPDULen & VHT_CAP_MAX_MPDU_LENGTH_MASK;
539 hdd_vht_cap->vht_cap_info |= temp_vht_cap;
540 temp_vht_cap = roam_vht_cap->supportedChannelWidthSet &
541 (IEEE80211_VHT_CAP_SUPP_CHAN_WIDTH_MASK >>
542 VHT_CAP_SUPP_CHAN_WIDTH_MASK_SHIFT);
543 if (temp_vht_cap)
544 if (roam_vht_cap->supportedChannelWidthSet &
545 (IEEE80211_VHT_CAP_SUPP_CHAN_WIDTH_160MHZ >>
546 VHT_CAP_SUPP_CHAN_WIDTH_MASK_SHIFT))
547 hdd_vht_cap->vht_cap_info |=
548 temp_vht_cap <<
549 IEEE80211_VHT_CAP_SUPP_CHAN_WIDTH_160MHZ;
550 if (roam_vht_cap->supportedChannelWidthSet &
551 (IEEE80211_VHT_CAP_SUPP_CHAN_WIDTH_160_80PLUS80MHZ >>
552 VHT_CAP_SUPP_CHAN_WIDTH_MASK_SHIFT))
553 hdd_vht_cap->vht_cap_info |=
554 temp_vht_cap <<
555 IEEE80211_VHT_CAP_SUPP_CHAN_WIDTH_160_80PLUS80MHZ;
556 if (roam_vht_cap->ldpcCodingCap)
557 hdd_vht_cap->vht_cap_info |= IEEE80211_VHT_CAP_RXLDPC;
558 if (roam_vht_cap->shortGI80MHz)
559 hdd_vht_cap->vht_cap_info |= IEEE80211_VHT_CAP_SHORT_GI_80;
560 if (roam_vht_cap->shortGI160and80plus80MHz)
561 hdd_vht_cap->vht_cap_info |= IEEE80211_VHT_CAP_SHORT_GI_160;
562 if (roam_vht_cap->txSTBC)
563 hdd_vht_cap->vht_cap_info |= IEEE80211_VHT_CAP_TXSTBC;
564 temp_vht_cap = roam_vht_cap->rxSTBC & (IEEE80211_VHT_CAP_RXSTBC_MASK >>
565 VHT_CAP_RXSTBC_MASK_SHIFT);
566 if (temp_vht_cap)
567 hdd_vht_cap->vht_cap_info |=
568 temp_vht_cap << VHT_CAP_RXSTBC_MASK_SHIFT;
569 if (roam_vht_cap->suBeamFormerCap)
570 hdd_vht_cap->vht_cap_info |=
571 IEEE80211_VHT_CAP_SU_BEAMFORMER_CAPABLE;
572 if (roam_vht_cap->suBeamformeeCap)
573 hdd_vht_cap->vht_cap_info |=
574 IEEE80211_VHT_CAP_SU_BEAMFORMEE_CAPABLE;
575 temp_vht_cap = roam_vht_cap->csnofBeamformerAntSup &
576 (VHT_CAP_BEAMFORMEE_STS_MASK);
577 if (temp_vht_cap)
578 hdd_vht_cap->vht_cap_info |=
579 temp_vht_cap << VHT_CAP_BEAMFORMEE_STS_SHIFT;
580 temp_vht_cap = roam_vht_cap->numSoundingDim &
581 (VHT_CAP_SOUNDING_DIMENSIONS_MASK);
582 if (temp_vht_cap)
583 hdd_vht_cap->vht_cap_info |=
584 temp_vht_cap << VHT_CAP_SOUNDING_DIMENSIONS_SHIFT;
585 if (roam_vht_cap->muBeamformerCap)
586 hdd_vht_cap->vht_cap_info |=
587 IEEE80211_VHT_CAP_MU_BEAMFORMER_CAPABLE;
588 if (roam_vht_cap->muBeamformeeCap)
589 hdd_vht_cap->vht_cap_info |=
590 IEEE80211_VHT_CAP_MU_BEAMFORMEE_CAPABLE;
591 if (roam_vht_cap->vhtTXOPPS)
592 hdd_vht_cap->vht_cap_info |=
593 IEEE80211_VHT_CAP_VHT_TXOP_PS;
594 if (roam_vht_cap->htcVHTCap)
595 hdd_vht_cap->vht_cap_info |=
596 IEEE80211_VHT_CAP_HTC_VHT;
597 temp_vht_cap = roam_vht_cap->maxAMPDULenExp &
598 (VHT_CAP_MAX_A_MPDU_LENGTH_EXPONENT_MASK);
599 if (temp_vht_cap)
600 hdd_vht_cap->vht_cap_info |=
601 temp_vht_cap <<
602 VHT_CAP_MAX_A_MPDU_LENGTH_EXPONENT_MASK_SHIFT;
603 temp_vht_cap = roam_vht_cap->vhtLinkAdaptCap &
604 (IEEE80211_VHT_CAP_VHT_LINK_ADAPTATION_VHT_MRQ_MFB >>
605 VHT_CAP_VHT_LINK_ADAPTATION_VHT_MRQ_MFB_SHIFT);
606 if (temp_vht_cap)
607 hdd_vht_cap->vht_cap_info |= temp_vht_cap <<
608 VHT_CAP_VHT_LINK_ADAPTATION_VHT_MRQ_MFB_SHIFT;
609 if (roam_vht_cap->rxAntPattern)
610 hdd_vht_cap->vht_cap_info |=
611 IEEE80211_VHT_CAP_RX_ANTENNA_PATTERN;
612 if (roam_vht_cap->txAntPattern)
613 hdd_vht_cap->vht_cap_info |=
614 IEEE80211_VHT_CAP_TX_ANTENNA_PATTERN;
615 hdd_vht_cap->supp_mcs.rx_mcs_map = roam_vht_cap->rxMCSMap;
616 hdd_vht_cap->supp_mcs.rx_highest =
617 ((uint16_t)roam_vht_cap->rxHighSupDataRate);
618 hdd_vht_cap->supp_mcs.tx_mcs_map = roam_vht_cap->txMCSMap;
619 hdd_vht_cap->supp_mcs.tx_highest =
620 ((uint16_t)roam_vht_cap->txSupDataRate);
621}
622
623/* ht param */
624#define HT_PARAM_CONTROLLED_ACCESS_ONLY 0x10
625#define HT_PARAM_SERVICE_INT_GRAN 0xe0
626#define HT_PARAM_SERVICE_INT_GRAN_SHIFT 5
627
628/* operatinon mode */
629#define HT_OP_MODE_TX_BURST_LIMIT 0x0008
630
631/* stbc_param */
632#define HT_STBC_PARAM_MCS 0x007f
633
634/**
635 * hdd_copy_ht_operation()- copy HT operation element from roam info to
636 * hdd station context.
637 * @hdd_sta_ctx: pointer to hdd station context
638 * @roam_info: pointer to roam info
639 *
640 * Return: None
641 */
642static void hdd_copy_ht_operation(hdd_station_ctx_t *hdd_sta_ctx,
643 tCsrRoamInfo *roam_info)
644{
645 tDot11fIEHTInfo *roam_ht_ops = &roam_info->ht_operation;
646 struct ieee80211_ht_operation *hdd_ht_ops =
647 &hdd_sta_ctx->conn_info.ht_operation;
648 uint32_t i, temp_ht_ops;
649
650 qdf_mem_zero(hdd_ht_ops, sizeof(struct ieee80211_ht_operation));
651
652 hdd_ht_ops->primary_chan = roam_ht_ops->primaryChannel;
653
654 /* HT_PARAMS */
655 temp_ht_ops = roam_ht_ops->secondaryChannelOffset &
656 IEEE80211_HT_PARAM_CHA_SEC_OFFSET;
657 if (temp_ht_ops)
658 hdd_ht_ops->ht_param |= temp_ht_ops;
659 else
660 hdd_ht_ops->ht_param = IEEE80211_HT_PARAM_CHA_SEC_NONE;
661 if (roam_ht_ops->recommendedTxWidthSet)
662 hdd_ht_ops->ht_param |= IEEE80211_HT_PARAM_CHAN_WIDTH_ANY;
663 if (roam_ht_ops->rifsMode)
664 hdd_ht_ops->ht_param |= IEEE80211_HT_PARAM_RIFS_MODE;
665 if (roam_ht_ops->controlledAccessOnly)
666 hdd_ht_ops->ht_param |= HT_PARAM_CONTROLLED_ACCESS_ONLY;
667 temp_ht_ops = roam_ht_ops->serviceIntervalGranularity &
668 (HT_PARAM_SERVICE_INT_GRAN >> HT_PARAM_SERVICE_INT_GRAN_SHIFT);
669 if (temp_ht_ops)
670 hdd_ht_ops->ht_param |= temp_ht_ops <<
671 HT_PARAM_SERVICE_INT_GRAN_SHIFT;
672
673 /* operation mode */
674 temp_ht_ops = roam_ht_ops->opMode &
675 IEEE80211_HT_OP_MODE_PROTECTION;
676 switch (temp_ht_ops) {
677 case IEEE80211_HT_OP_MODE_PROTECTION_NONMEMBER:
678 hdd_ht_ops->operation_mode |=
679 IEEE80211_HT_OP_MODE_PROTECTION_NONMEMBER;
680 break;
681 case IEEE80211_HT_OP_MODE_PROTECTION_20MHZ:
682 hdd_ht_ops->operation_mode |=
683 IEEE80211_HT_OP_MODE_PROTECTION_20MHZ;
684 break;
685 case IEEE80211_HT_OP_MODE_PROTECTION_NONHT_MIXED:
686 hdd_ht_ops->operation_mode |=
687 IEEE80211_HT_OP_MODE_PROTECTION_NONHT_MIXED;
688 break;
689 case IEEE80211_HT_OP_MODE_PROTECTION_NONE:
690 default:
691 hdd_ht_ops->operation_mode |=
692 IEEE80211_HT_OP_MODE_PROTECTION_NONE;
693 }
694 if (roam_ht_ops->nonGFDevicesPresent)
695 hdd_ht_ops->operation_mode |=
696 IEEE80211_HT_OP_MODE_NON_GF_STA_PRSNT;
697 if (roam_ht_ops->transmitBurstLimit)
698 hdd_ht_ops->operation_mode |=
699 HT_OP_MODE_TX_BURST_LIMIT;
700 if (roam_ht_ops->obssNonHTStaPresent)
701 hdd_ht_ops->operation_mode |=
702 IEEE80211_HT_OP_MODE_NON_HT_STA_PRSNT;
703
704 /* stbc_param */
705 temp_ht_ops = roam_ht_ops->basicSTBCMCS &
706 HT_STBC_PARAM_MCS;
707 if (temp_ht_ops)
708 hdd_ht_ops->stbc_param |= temp_ht_ops;
709 if (roam_ht_ops->dualCTSProtection)
710 hdd_ht_ops->stbc_param |=
711 IEEE80211_HT_STBC_PARAM_DUAL_CTS_PROT;
712 if (roam_ht_ops->secondaryBeacon)
713 hdd_ht_ops->stbc_param |=
714 IEEE80211_HT_STBC_PARAM_STBC_BEACON;
715 if (roam_ht_ops->lsigTXOPProtectionFullSupport)
716 hdd_ht_ops->stbc_param |=
717 IEEE80211_HT_STBC_PARAM_LSIG_TXOP_FULLPROT;
718 if (roam_ht_ops->pcoActive)
719 hdd_ht_ops->stbc_param |=
720 IEEE80211_HT_STBC_PARAM_PCO_ACTIVE;
721 if (roam_ht_ops->pcoPhase)
722 hdd_ht_ops->stbc_param |=
723 IEEE80211_HT_STBC_PARAM_PCO_PHASE;
724
725 /* basic MCs set */
726 for (i = 0; i < 16; ++i)
727 hdd_ht_ops->basic_set[i] =
728 roam_ht_ops->basicMCSSet[i];
729}
730
731/**
732 * hdd_copy_vht_operation()- copy VHT operations element from roam info to
733 * hdd station context.
734 * @hdd_sta_ctx: pointer to hdd station context
735 * @roam_info: pointer to roam info
736 *
737 * Return: None
738 */
739static void hdd_copy_vht_operation(hdd_station_ctx_t *hdd_sta_ctx,
740 tCsrRoamInfo *roam_info)
741{
742 tDot11fIEVHTOperation *roam_vht_ops = &roam_info->vht_operation;
743 struct ieee80211_vht_operation *hdd_vht_ops =
744 &hdd_sta_ctx->conn_info.vht_operation;
745
746 qdf_mem_zero(hdd_vht_ops, sizeof(struct ieee80211_vht_operation));
747
748 hdd_vht_ops->chan_width = roam_vht_ops->chanWidth;
749 hdd_vht_ops->center_freq_seg1_idx = roam_vht_ops->chanCenterFreqSeg1;
750 hdd_vht_ops->center_freq_seg2_idx = roam_vht_ops->chanCenterFreqSeg2;
751 hdd_vht_ops->basic_mcs_set = roam_vht_ops->basicMCSSet;
752}
753
754
755/**
756 * hdd_save_bss_info() - save connection info in hdd sta ctx
757 * @adapter: Pointer to adapter
758 * @roam_info: pointer to roam info
759 *
760 * Return: None
761 */
762static void hdd_save_bss_info(hdd_adapter_t *adapter,
763 tCsrRoamInfo *roam_info)
764{
765 hdd_station_ctx_t *hdd_sta_ctx = WLAN_HDD_GET_STATION_CTX_PTR(adapter);
766
767 hdd_sta_ctx->conn_info.freq = cds_chan_to_freq(
768 hdd_sta_ctx->conn_info.operationChannel);
769 if (roam_info->vht_caps.present) {
770 hdd_sta_ctx->conn_info.conn_flag.vht_present = true;
771 hdd_copy_vht_caps(hdd_sta_ctx, roam_info);
772 } else {
773 hdd_sta_ctx->conn_info.conn_flag.vht_present = false;
774 }
775 if (roam_info->ht_caps.present) {
776 hdd_sta_ctx->conn_info.conn_flag.ht_present = true;
777 hdd_copy_ht_caps(hdd_sta_ctx, roam_info);
778 } else {
779 hdd_sta_ctx->conn_info.conn_flag.ht_present = false;
780 }
781 if (roam_info->reassoc)
782 hdd_sta_ctx->conn_info.roam_count++;
783 if (roam_info->hs20vendor_ie.present) {
784 hdd_sta_ctx->conn_info.conn_flag.hs20_present = true;
785 qdf_mem_copy(&hdd_sta_ctx->conn_info.hs20vendor_ie,
786 &roam_info->hs20vendor_ie,
787 sizeof(roam_info->hs20vendor_ie));
788 } else {
789 hdd_sta_ctx->conn_info.conn_flag.hs20_present = false;
790 }
791 if (roam_info->ht_operation.present) {
792 hdd_sta_ctx->conn_info.conn_flag.ht_op_present = true;
793 hdd_copy_ht_operation(hdd_sta_ctx, roam_info);
794 } else {
795 hdd_sta_ctx->conn_info.conn_flag.ht_op_present = false;
796 }
797 if (roam_info->vht_operation.present) {
798 hdd_sta_ctx->conn_info.conn_flag.vht_op_present = true;
799 hdd_copy_vht_operation(hdd_sta_ctx, roam_info);
800 } else {
801 hdd_sta_ctx->conn_info.conn_flag.vht_op_present = false;
802 }
803}
804
805/**
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800806 * hdd_conn_save_connect_info() - save current connection information
807 * @pAdapter: pointer to adapter
808 * @pRoamInfo: pointer to roam info
809 * @eBssType: bss type
810 *
811 * Return: none
812 */
813static void
814hdd_conn_save_connect_info(hdd_adapter_t *pAdapter, tCsrRoamInfo *pRoamInfo,
815 eCsrRoamBssType eBssType)
816{
817 hdd_station_ctx_t *pHddStaCtx = WLAN_HDD_GET_STATION_CTX_PTR(pAdapter);
818 eCsrEncryptionType encryptType = eCSR_ENCRYPT_TYPE_NONE;
819
Anurag Chouhanb2dc16f2016-02-25 11:47:37 +0530820 QDF_ASSERT(pRoamInfo);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800821
822 if (pRoamInfo) {
823 /* Save the BSSID for the connection */
824 if (eCSR_BSS_TYPE_INFRASTRUCTURE == eBssType) {
Anurag Chouhanb2dc16f2016-02-25 11:47:37 +0530825 QDF_ASSERT(pRoamInfo->pBssDesc);
Anurag Chouhanc5548422016-02-24 18:33:27 +0530826 qdf_copy_macaddr(&pHddStaCtx->conn_info.bssId,
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800827 &pRoamInfo->bssid);
828
829 /*
830 * Save the Station ID for this station from
831 * the 'Roam Info'. For IBSS mode, staId is
832 * assigned in NEW_PEER_IND. For reassoc,
833 * the staID doesn't change and it may be invalid
834 * in this structure so no change here.
835 */
836 if (!pRoamInfo->fReassocReq) {
837 pHddStaCtx->conn_info.staId[0] =
838 pRoamInfo->staId;
839 }
840 } else if (eCSR_BSS_TYPE_IBSS == eBssType) {
Anurag Chouhanc5548422016-02-24 18:33:27 +0530841 qdf_copy_macaddr(&pHddStaCtx->conn_info.bssId,
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800842 &pRoamInfo->bssid);
843 } else {
844 /*
845 * can't happen. We need a valid IBSS or Infra setting
846 * in the BSSDescription or we can't function.
847 */
Anurag Chouhanb2dc16f2016-02-25 11:47:37 +0530848 QDF_ASSERT(0);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800849 }
850
851 /* notify WMM */
852 hdd_wmm_connect(pAdapter, pRoamInfo, eBssType);
853
854 if (!pRoamInfo->u.pConnectedProfile) {
Anurag Chouhanb2dc16f2016-02-25 11:47:37 +0530855 QDF_ASSERT(pRoamInfo->u.pConnectedProfile);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800856 } else {
857 /* Get Multicast Encryption Type */
858 encryptType =
859 pRoamInfo->u.pConnectedProfile->mcEncryptionType;
860 pHddStaCtx->conn_info.mcEncryptionType = encryptType;
861 /* Get Unicast Encryption Type */
862 encryptType =
863 pRoamInfo->u.pConnectedProfile->EncryptionType;
864 pHddStaCtx->conn_info.ucEncryptionType = encryptType;
865
866 pHddStaCtx->conn_info.authType =
867 pRoamInfo->u.pConnectedProfile->AuthType;
868
869 pHddStaCtx->conn_info.operationChannel =
870 pRoamInfo->u.pConnectedProfile->operationChannel;
871
872 /* Save the ssid for the connection */
Anurag Chouhan600c3a02016-03-01 10:33:54 +0530873 qdf_mem_copy(&pHddStaCtx->conn_info.SSID.SSID,
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800874 &pRoamInfo->u.pConnectedProfile->SSID,
875 sizeof(tSirMacSSid));
876
877 /* Save dot11mode in which STA associated to AP */
878 pHddStaCtx->conn_info.dot11Mode =
879 pRoamInfo->u.pConnectedProfile->dot11Mode;
880
881 pHddStaCtx->conn_info.proxyARPService =
882 pRoamInfo->u.pConnectedProfile->proxyARPService;
Kanchanapally, Vidyullathae3062812015-05-22 17:28:57 +0530883
884 pHddStaCtx->conn_info.nss = pRoamInfo->chan_info.nss;
885
886 pHddStaCtx->conn_info.rate_flags =
887 pRoamInfo->chan_info.rate_flags;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800888 }
Anurag Chouhan5de8d172016-07-13 14:44:28 +0530889 hdd_save_bss_info(pAdapter, pRoamInfo);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800890 }
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800891}
892
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800893/**
894 * hdd_send_ft_assoc_response() - send fast transition assoc response
895 * @dev: pointer to net device
896 * @pAdapter: pointer to adapter
897 * @pCsrRoamInfo: pointer to roam info
898 *
899 * Send the 11R key information to the supplicant. Only then can the supplicant
900 * generate the PMK-R1. (BTW, the ESE supplicant also needs the Assoc Resp IEs
901 * for the same purpose.)
902 *
903 * Mainly the Assoc Rsp IEs are passed here. For the IMDA this contains the
904 * R1KHID, R0KHID and the MDID. For FT, this consists of the Reassoc Rsp FTIEs.
905 * This is the Assoc Response.
906 *
907 * Return: none
908 */
909static void
910hdd_send_ft_assoc_response(struct net_device *dev,
911 hdd_adapter_t *pAdapter,
912 tCsrRoamInfo *pCsrRoamInfo)
913{
914 union iwreq_data wrqu;
915 char *buff;
916 unsigned int len = 0;
917 u8 *pFTAssocRsp = NULL;
918
919 if (pCsrRoamInfo->nAssocRspLength == 0) {
Archana Ramachandran75c1ca72016-08-22 17:20:25 -0700920 hdd_err("pCsrRoamInfo->nAssocRspLength=%d",
921 (int)pCsrRoamInfo->nAssocRspLength);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800922 return;
923 }
924
925 pFTAssocRsp =
926 (u8 *) (pCsrRoamInfo->pbFrames + pCsrRoamInfo->nBeaconLength +
927 pCsrRoamInfo->nAssocReqLength);
928 if (pFTAssocRsp == NULL) {
Archana Ramachandran75c1ca72016-08-22 17:20:25 -0700929 hdd_err("AssocReq or AssocRsp is NULL");
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800930 return;
931 }
932 /* pFTAssocRsp needs to point to the IEs */
933 pFTAssocRsp += FT_ASSOC_RSP_IES_OFFSET;
Archana Ramachandran75c1ca72016-08-22 17:20:25 -0700934 hdd_notice("AssocRsp is now at %02x%02x",
935 (unsigned int)pFTAssocRsp[0],
936 (unsigned int)pFTAssocRsp[1]);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800937
938 /* We need to send the IEs to the supplicant. */
939 buff = kmalloc(IW_GENERIC_IE_MAX, GFP_ATOMIC);
940 if (buff == NULL) {
Archana Ramachandran75c1ca72016-08-22 17:20:25 -0700941 hdd_err("kmalloc unable to allocate memory");
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800942 return;
943 }
944 /* Send the Assoc Resp, the supplicant needs this for initial Auth. */
945 len = pCsrRoamInfo->nAssocRspLength - FT_ASSOC_RSP_IES_OFFSET;
946 wrqu.data.length = len;
947 memset(buff, 0, IW_GENERIC_IE_MAX);
948 memcpy(buff, pFTAssocRsp, len);
949 wireless_send_event(dev, IWEVASSOCRESPIE, &wrqu, buff);
950
951 kfree(buff);
952}
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800953
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800954/**
955 * hdd_send_ft_event() - send fast transition event
956 * @pAdapter: pointer to adapter
957 *
958 * Send the FTIEs, RIC IEs during FT. This is eventually used to send the
959 * FT events to the supplicant. At the reception of Auth2 we send the RIC
960 * followed by the auth response IEs to the supplicant.
961 * Once both are received in the supplicant, an FT event is generated
962 * to the supplicant.
963 *
964 * Return: none
965 */
966static void hdd_send_ft_event(hdd_adapter_t *pAdapter)
967{
968 uint16_t auth_resp_len = 0;
969 uint32_t ric_ies_length = 0;
970 hdd_context_t *pHddCtx = WLAN_HDD_GET_CTX(pAdapter);
971
972#if defined(KERNEL_SUPPORT_11R_CFG80211)
973 struct cfg80211_ft_event_params ftEvent;
974 uint8_t ftIe[DOT11F_IE_FTINFO_MAX_LEN];
975 uint8_t ricIe[DOT11F_IE_RICDESCRIPTOR_MAX_LEN];
976 struct net_device *dev = pAdapter->dev;
977#else
978 char *buff;
979 union iwreq_data wrqu;
980 uint16_t str_len;
981#endif
982
983#if defined(KERNEL_SUPPORT_11R_CFG80211)
Anurag Chouhan600c3a02016-03-01 10:33:54 +0530984 qdf_mem_zero(ftIe, DOT11F_IE_FTINFO_MAX_LEN);
985 qdf_mem_zero(ricIe, DOT11F_IE_RICDESCRIPTOR_MAX_LEN);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800986
987 sme_get_rici_es(pHddCtx->hHal, pAdapter->sessionId, (u8 *) ricIe,
988 DOT11F_IE_RICDESCRIPTOR_MAX_LEN, &ric_ies_length);
989 if (ric_ies_length == 0) {
Archana Ramachandran75c1ca72016-08-22 17:20:25 -0700990 hdd_warn("RIC IEs is of length 0 not sending RIC Information for now");
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800991 }
992
993 ftEvent.ric_ies = ricIe;
994 ftEvent.ric_ies_len = ric_ies_length;
Archana Ramachandran75c1ca72016-08-22 17:20:25 -0700995 hdd_notice("RIC IEs is of length %d", (int)ric_ies_length);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800996
997 sme_get_ft_pre_auth_response(pHddCtx->hHal, pAdapter->sessionId,
998 (u8 *) ftIe, DOT11F_IE_FTINFO_MAX_LEN,
999 &auth_resp_len);
1000
1001 if (auth_resp_len == 0) {
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07001002 hdd_err("AuthRsp FTIES is of length 0");
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001003 return;
1004 }
1005
1006 sme_set_ft_pre_auth_state(pHddCtx->hHal, pAdapter->sessionId, true);
1007
1008 ftEvent.target_ap = ftIe;
1009
Anurag Chouhan6d760662016-02-20 16:05:43 +05301010 ftEvent.ies = (u8 *) (ftIe + QDF_MAC_ADDR_SIZE);
1011 ftEvent.ies_len = auth_resp_len - QDF_MAC_ADDR_SIZE;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001012
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07001013 hdd_notice("ftEvent.ies_len %zu", ftEvent.ies_len);
1014 hdd_notice("ftEvent.ric_ies_len %zu", ftEvent.ric_ies_len);
1015 hdd_notice("ftEvent.target_ap %2x-%2x-%2x-%2x-%2x-%2x",
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001016 ftEvent.target_ap[0], ftEvent.target_ap[1],
1017 ftEvent.target_ap[2], ftEvent.target_ap[3], ftEvent.target_ap[4],
1018 ftEvent.target_ap[5]);
1019
1020 (void)cfg80211_ft_event(dev, &ftEvent);
1021
1022#else
1023 /* We need to send the IEs to the supplicant */
1024 buff = kmalloc(IW_CUSTOM_MAX, GFP_ATOMIC);
1025 if (buff == NULL) {
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07001026 hdd_err("kmalloc unable to allocate memory");
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001027 return;
1028 }
Anurag Chouhan600c3a02016-03-01 10:33:54 +05301029 qdf_mem_zero(buff, IW_CUSTOM_MAX);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001030
1031 /* Sme needs to send the RIC IEs first */
1032 str_len = strlcpy(buff, "RIC=", IW_CUSTOM_MAX);
1033 sme_get_rici_es(pHddCtx->hHal, pAdapter->sessionId,
1034 (u8 *) &(buff[str_len]), (IW_CUSTOM_MAX - str_len),
1035 &ric_ies_length);
1036 if (ric_ies_length == 0) {
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07001037 hdd_warn("RIC IEs is of length 0 not sending RIC Information for now");
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001038 } else {
1039 wrqu.data.length = str_len + ric_ies_length;
1040 wireless_send_event(pAdapter->dev, IWEVCUSTOM, &wrqu, buff);
1041 }
1042
1043 /* Sme needs to provide the Auth Resp */
Anurag Chouhan600c3a02016-03-01 10:33:54 +05301044 qdf_mem_zero(buff, IW_CUSTOM_MAX);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001045 str_len = strlcpy(buff, "AUTH=", IW_CUSTOM_MAX);
1046 sme_get_ft_pre_auth_response(pHddCtx->hHal, pAdapter->sessionId,
1047 (u8 *) &buff[str_len],
1048 (IW_CUSTOM_MAX - str_len), &auth_resp_len);
1049
1050 if (auth_resp_len == 0) {
1051 kfree(buff);
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07001052 hdd_err("AuthRsp FTIES is of length 0");
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001053 return;
1054 }
1055
1056 wrqu.data.length = str_len + auth_resp_len;
1057 wireless_send_event(pAdapter->dev, IWEVCUSTOM, &wrqu, buff);
1058
1059 kfree(buff);
1060#endif
1061}
1062
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001063#ifdef FEATURE_WLAN_ESE
1064/**
1065 * hdd_send_new_ap_channel_info() - send new ap channel info
1066 * @dev: pointer to net device
1067 * @pAdapter: pointer to adapter
1068 * @pCsrRoamInfo: pointer to roam info
1069 *
1070 * Send the ESE required "new AP Channel info" to the supplicant.
1071 * (This keeps the supplicant "up to date" on the current channel.)
1072 *
1073 * The current (new AP) channel information is passed in.
1074 *
1075 * Return: none
1076 */
1077static void
1078hdd_send_new_ap_channel_info(struct net_device *dev, hdd_adapter_t *pAdapter,
1079 tCsrRoamInfo *pCsrRoamInfo)
1080{
1081 union iwreq_data wrqu;
1082 tSirBssDescription *descriptor = pCsrRoamInfo->pBssDesc;
1083
1084 if (descriptor == NULL) {
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07001085 hdd_err("pCsrRoamInfo->pBssDesc(%p)", descriptor);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001086 return;
1087 }
1088 /*
1089 * Send the Channel event, the supplicant needs this to generate
1090 * the Adjacent AP report.
1091 */
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07001092 hdd_warn("Sending up an SIOCGIWFREQ, channelId(%d)",
1093 descriptor->channelId);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001094 memset(&wrqu, '\0', sizeof(wrqu));
1095 wrqu.freq.m = descriptor->channelId;
1096 wrqu.freq.e = 0;
1097 wrqu.freq.i = 0;
1098 wireless_send_event(pAdapter->dev, SIOCGIWFREQ, &wrqu, NULL);
1099}
1100
1101#endif /* FEATURE_WLAN_ESE */
1102
1103/**
1104 * hdd_send_update_beacon_ies_event() - send update beacons ie event
1105 * @pAdapter: pointer to adapter
1106 * @pCsrRoamInfo: pointer to roam info
1107 *
1108 * Return: none
1109 */
1110static void
1111hdd_send_update_beacon_ies_event(hdd_adapter_t *pAdapter,
1112 tCsrRoamInfo *pCsrRoamInfo)
1113{
1114 union iwreq_data wrqu;
1115 u8 *pBeaconIes;
1116 u8 currentLen = 0;
1117 char *buff;
1118 int totalIeLen = 0, currentOffset = 0, strLen;
1119
1120 memset(&wrqu, '\0', sizeof(wrqu));
1121
1122 if (0 == pCsrRoamInfo->nBeaconLength) {
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07001123 hdd_warn("pCsrRoamInfo->nBeaconFrameLength = 0");
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001124 return;
1125 }
1126 pBeaconIes = (u8 *) (pCsrRoamInfo->pbFrames + BEACON_FRAME_IES_OFFSET);
1127 if (pBeaconIes == NULL) {
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07001128 hdd_warn("Beacon IEs is NULL");
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001129 return;
1130 }
1131 /* pBeaconIes needs to point to the IEs */
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07001132 hdd_notice("Beacon IEs is now at %02x%02x",
1133 (unsigned int)pBeaconIes[0],
1134 (unsigned int)pBeaconIes[1]);
1135 hdd_notice("Beacon IEs length = %d",
1136 pCsrRoamInfo->nBeaconLength - BEACON_FRAME_IES_OFFSET);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001137
1138 /* We need to send the IEs to the supplicant. */
1139 buff = kmalloc(IW_CUSTOM_MAX, GFP_ATOMIC);
1140 if (buff == NULL) {
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07001141 hdd_err("kmalloc unable to allocate memory");
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001142 return;
1143 }
Anurag Chouhan600c3a02016-03-01 10:33:54 +05301144 qdf_mem_zero(buff, IW_CUSTOM_MAX);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001145
1146 strLen = strlcpy(buff, "BEACONIEs=", IW_CUSTOM_MAX);
1147 currentLen = strLen + 1;
1148
1149 totalIeLen = pCsrRoamInfo->nBeaconLength - BEACON_FRAME_IES_OFFSET;
1150 do {
1151 /*
1152 * If the beacon size exceeds max CUSTOM event size, break it
1153 * into chunks of CUSTOM event max size and send it to
1154 * supplicant. Changes are done in supplicant to handle this.
1155 */
Anurag Chouhan600c3a02016-03-01 10:33:54 +05301156 qdf_mem_zero(&buff[strLen + 1], IW_CUSTOM_MAX - (strLen + 1));
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001157 currentLen =
Anurag Chouhan6d760662016-02-20 16:05:43 +05301158 QDF_MIN(totalIeLen, IW_CUSTOM_MAX - (strLen + 1) - 1);
Anurag Chouhan600c3a02016-03-01 10:33:54 +05301159 qdf_mem_copy(&buff[strLen + 1], pBeaconIes + currentOffset,
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001160 currentLen);
1161 currentOffset += currentLen;
1162 totalIeLen -= currentLen;
1163 wrqu.data.length = strLen + 1 + currentLen;
1164 if (totalIeLen)
1165 buff[strLen] = 1; /* more chunks pending */
1166 else
1167 buff[strLen] = 0; /* last chunk */
1168
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07001169 hdd_notice("Beacon IEs length to supplicant = %d",
1170 currentLen);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001171 wireless_send_event(pAdapter->dev, IWEVCUSTOM, &wrqu, buff);
1172 } while (totalIeLen > 0);
1173
1174 kfree(buff);
1175}
1176
1177/**
1178 * hdd_send_association_event() - send association event
1179 * @dev: pointer to net device
1180 * @pCsrRoamInfo: pointer to roam info
1181 *
1182 * Return: none
1183 */
1184static void hdd_send_association_event(struct net_device *dev,
1185 tCsrRoamInfo *pCsrRoamInfo)
1186{
1187 hdd_adapter_t *pAdapter = WLAN_HDD_GET_PRIV_PTR(dev);
1188 hdd_context_t *pHddCtx = WLAN_HDD_GET_CTX(pAdapter);
1189 hdd_station_ctx_t *pHddStaCtx = WLAN_HDD_GET_STATION_CTX_PTR(pAdapter);
1190 union iwreq_data wrqu;
1191 int we_event;
1192 char *msg;
Anurag Chouhan6d760662016-02-20 16:05:43 +05301193 struct qdf_mac_addr peerMacAddr;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001194
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001195 /* Added to find the auth type on the fly at run time */
1196 /* rather than with cfg to see if FT is enabled */
1197 hdd_wext_state_t *pWextState = WLAN_HDD_GET_WEXT_STATE_PTR(pAdapter);
1198 tCsrRoamProfile *pRoamProfile = &(pWextState->roamProfile);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001199
1200 memset(&wrqu, '\0', sizeof(wrqu));
1201 wrqu.ap_addr.sa_family = ARPHRD_ETHER;
1202 we_event = SIOCGIWAP;
1203#ifdef WLAN_FEATURE_ROAM_OFFLOAD
1204 if (NULL != pCsrRoamInfo)
1205 if (pCsrRoamInfo->roamSynchInProgress)
1206 /* change logging before release */
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07001207 hdd_info("LFR3:hdd_send_association_event");
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001208#endif
1209 if (eConnectionState_Associated == pHddStaCtx->conn_info.connState) {
Abhishek Singh1c676222016-05-09 14:20:28 +05301210 tSirSmeChanInfo chan_info;
1211
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001212 if (!pCsrRoamInfo) {
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07001213 hdd_err("STA in associated state but pCsrRoamInfo is null");
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001214 return;
1215 }
1216
Varun Reddy Yeturud5939f82015-12-24 18:14:02 -08001217 if (!hdd_is_roam_sync_in_progress(pCsrRoamInfo))
1218 cds_incr_active_session(pAdapter->device_mode,
1219 pAdapter->sessionId);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001220 memcpy(wrqu.ap_addr.sa_data, pCsrRoamInfo->pBssDesc->bssId,
1221 sizeof(pCsrRoamInfo->pBssDesc->bssId));
1222
1223#ifdef WLAN_FEATURE_P2P_DEBUG
Krunal Sonibe766b02016-03-10 13:00:44 -08001224 if (pAdapter->device_mode == QDF_P2P_CLIENT_MODE) {
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001225 if (global_p2p_connection_status ==
1226 P2P_CLIENT_CONNECTING_STATE_1) {
1227 global_p2p_connection_status =
1228 P2P_CLIENT_CONNECTED_STATE_1;
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07001229 hdd_err("[P2P State] Changing state from Connecting state to Connected State for 8-way Handshake");
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001230 } else if (global_p2p_connection_status ==
1231 P2P_CLIENT_CONNECTING_STATE_2) {
1232 global_p2p_connection_status =
1233 P2P_CLIENT_COMPLETED_STATE;
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07001234 hdd_err("[P2P State] Changing state from Connecting state to P2P Client Connection Completed");
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001235 }
1236 }
1237#endif
1238 pr_info("wlan: " MAC_ADDRESS_STR " connected to "
1239 MAC_ADDRESS_STR "\n",
1240 MAC_ADDR_ARRAY(pAdapter->macAddressCurrent.bytes),
1241 MAC_ADDR_ARRAY(wrqu.ap_addr.sa_data));
1242 hdd_send_update_beacon_ies_event(pAdapter, pCsrRoamInfo);
1243
1244 /*
1245 * Send IWEVASSOCRESPIE Event if WLAN_FEATURE_CIQ_METRICS
1246 * is Enabled Or Send IWEVASSOCRESPIE Event if
Deepak Dhamdhere9f09e752016-01-09 23:17:25 -08001247 * fFTEnable is true.
1248 * Send FT Keys to the supplicant when FT is enabled
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001249 */
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001250 if ((pRoamProfile->AuthType.authType[0] ==
1251 eCSR_AUTH_TYPE_FT_RSN_PSK)
1252 || (pRoamProfile->AuthType.authType[0] ==
1253 eCSR_AUTH_TYPE_FT_RSN)
1254#ifdef FEATURE_WLAN_ESE
1255 || (pRoamProfile->AuthType.authType[0] ==
1256 eCSR_AUTH_TYPE_CCKM_RSN)
1257 || (pRoamProfile->AuthType.authType[0] ==
1258 eCSR_AUTH_TYPE_CCKM_WPA)
1259#endif
1260 ) {
1261 hdd_send_ft_assoc_response(dev, pAdapter, pCsrRoamInfo);
1262 }
Abhishek Singh1c676222016-05-09 14:20:28 +05301263 qdf_copy_macaddr(&peerMacAddr,
1264 &pHddStaCtx->conn_info.bssId);
1265 chan_info.chan_id = pCsrRoamInfo->chan_info.chan_id;
1266 chan_info.mhz = pCsrRoamInfo->chan_info.mhz;
1267 chan_info.info = pCsrRoamInfo->chan_info.info;
1268 chan_info.band_center_freq1 =
1269 pCsrRoamInfo->chan_info.band_center_freq1;
1270 chan_info.band_center_freq2 =
1271 pCsrRoamInfo->chan_info.band_center_freq2;
1272 chan_info.reg_info_1 =
1273 pCsrRoamInfo->chan_info.reg_info_1;
1274 chan_info.reg_info_2 =
1275 pCsrRoamInfo->chan_info.reg_info_2;
1276 /* send peer status indication to oem app */
1277 hdd_send_peer_status_ind_to_oem_app(&peerMacAddr,
1278 ePeerConnected,
1279 pCsrRoamInfo->
1280 timingMeasCap,
1281 pAdapter->sessionId,
1282 &chan_info,
1283 pAdapter->device_mode);
Kabilan Kannan32eb5022016-10-04 12:24:50 -07001284 /* Update tdls module about connection event */
1285 wlan_hdd_tdls_notify_connect(pAdapter, pCsrRoamInfo);
Kabilan Kannan163fd0b2016-06-08 15:21:51 -07001286
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001287#ifdef MSM_PLATFORM
Ravi Joshiae8e9a72016-08-03 17:38:03 -07001288#if defined(CONFIG_ICNSS) || defined(CONFIG_CNSS)
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001289 /* start timer in sta/p2p_cli */
1290 spin_lock_bh(&pHddCtx->bus_bw_lock);
1291 pAdapter->prev_tx_packets = pAdapter->stats.tx_packets;
1292 pAdapter->prev_rx_packets = pAdapter->stats.rx_packets;
Himanshu Agarwal5ac2f7b2016-05-06 20:08:10 +05301293 ol_get_intra_bss_fwd_pkts_count(pAdapter->sessionId,
1294 &pAdapter->prev_fwd_tx_packets,
1295 &pAdapter->prev_fwd_rx_packets);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001296 spin_unlock_bh(&pHddCtx->bus_bw_lock);
1297 hdd_start_bus_bw_compute_timer(pAdapter);
1298#endif
1299#endif
1300 } else if (eConnectionState_IbssConnected == /* IBss Associated */
1301 pHddStaCtx->conn_info.connState) {
Tushnim Bhattacharyyaca50b322015-12-28 17:14:36 -08001302 cds_update_connection_info(pAdapter->sessionId);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001303 memcpy(wrqu.ap_addr.sa_data, pHddStaCtx->conn_info.bssId.bytes,
1304 ETH_ALEN);
Gowri, Deepthi07ac9932016-09-02 15:19:32 +05301305 hdd_err("wlan: new IBSS connection to " MAC_ADDRESS_STR,
1306 MAC_ADDR_ARRAY(pHddStaCtx->conn_info.bssId.bytes));
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001307 } else { /* Not Associated */
Gowri, Deepthi07ac9932016-09-02 15:19:32 +05301308 hdd_err("wlan: disconnected");
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001309 memset(wrqu.ap_addr.sa_data, '\0', ETH_ALEN);
Chandrasekaran, Manishekar6e9aa1b2015-12-02 18:04:00 +05301310 cds_decr_session_set_pcl(pAdapter->device_mode,
1311 pAdapter->sessionId);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001312 wlan_hdd_enable_roaming(pAdapter);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001313
1314#ifdef FEATURE_WLAN_AUTO_SHUTDOWN
1315 wlan_hdd_auto_shutdown_enable(pHddCtx, true);
1316#endif
1317
Abhishek Singh1c676222016-05-09 14:20:28 +05301318 if ((pAdapter->device_mode == QDF_STA_MODE) ||
1319 (pAdapter->device_mode == QDF_P2P_CLIENT_MODE)) {
Anurag Chouhanc5548422016-02-24 18:33:27 +05301320 qdf_copy_macaddr(&peerMacAddr,
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001321 &pHddStaCtx->conn_info.bssId);
1322
1323 /* send peer status indication to oem app */
1324 hdd_send_peer_status_ind_to_oem_app(&peerMacAddr,
Abhishek Singh1c676222016-05-09 14:20:28 +05301325 ePeerDisconnected, 0,
1326 pAdapter->sessionId,
1327 NULL,
1328 pAdapter->device_mode);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001329 }
Jeff Johnsoncef59bb2016-09-23 15:28:47 -07001330 hdd_lpass_notify_disconnect(pAdapter);
Kabilan Kannan32eb5022016-10-04 12:24:50 -07001331 /* Update tdls module about the disconnection event */
1332 wlan_hdd_tdls_notify_disconnect(pAdapter);
1333
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001334#ifdef MSM_PLATFORM
1335 /* stop timer in sta/p2p_cli */
1336 spin_lock_bh(&pHddCtx->bus_bw_lock);
1337 pAdapter->prev_tx_packets = 0;
1338 pAdapter->prev_rx_packets = 0;
Himanshu Agarwal5ac2f7b2016-05-06 20:08:10 +05301339 pAdapter->prev_fwd_tx_packets = 0;
1340 pAdapter->prev_fwd_rx_packets = 0;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001341 spin_unlock_bh(&pHddCtx->bus_bw_lock);
1342 hdd_stop_bus_bw_compute_timer(pAdapter);
1343#endif
1344 }
Tushnim Bhattacharyyaca50b322015-12-28 17:14:36 -08001345 cds_dump_concurrency_info();
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001346 /* Send SCC/MCC Switching event to IPA */
1347 hdd_ipa_send_mcc_scc_msg(pHddCtx, pHddCtx->mcc_mode);
1348
1349 msg = NULL;
1350 /*During the WLAN uninitialization,supplicant is stopped before the
1351 driver so not sending the status of the connection to supplicant */
Rajeev Kumarfec3dbe2016-01-19 15:23:52 -08001352 if (cds_is_load_or_unload_in_progress()) {
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001353 wireless_send_event(dev, we_event, &wrqu, msg);
1354#ifdef FEATURE_WLAN_ESE
1355 if (eConnectionState_Associated ==
1356 pHddStaCtx->conn_info.connState) {
1357 if ((pRoamProfile->AuthType.authType[0] ==
1358 eCSR_AUTH_TYPE_CCKM_RSN) ||
1359 (pRoamProfile->AuthType.authType[0] ==
1360 eCSR_AUTH_TYPE_CCKM_WPA))
1361 hdd_send_new_ap_channel_info(dev, pAdapter,
1362 pCsrRoamInfo);
1363 }
1364#endif
1365 }
1366}
1367
1368/**
1369 * hdd_conn_remove_connect_info() - remove connection info
1370 * @pHddStaCtx: pointer to global HDD station context
1371 * @pCsrRoamInfo: pointer to roam info
1372 *
1373 * Return: none
1374 */
1375static void hdd_conn_remove_connect_info(hdd_station_ctx_t *pHddStaCtx)
1376{
1377 /* Remove staId, bssId and peerMacAddress */
1378 pHddStaCtx->conn_info.staId[0] = 0;
Anurag Chouhan600c3a02016-03-01 10:33:54 +05301379 qdf_mem_zero(&pHddStaCtx->conn_info.bssId, QDF_MAC_ADDR_SIZE);
1380 qdf_mem_zero(&pHddStaCtx->conn_info.peerMacAddress[0],
Anurag Chouhan6d760662016-02-20 16:05:43 +05301381 QDF_MAC_ADDR_SIZE);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001382
1383 /* Clear all security settings */
1384 pHddStaCtx->conn_info.authType = eCSR_AUTH_TYPE_OPEN_SYSTEM;
1385 pHddStaCtx->conn_info.mcEncryptionType = eCSR_ENCRYPT_TYPE_NONE;
1386 pHddStaCtx->conn_info.ucEncryptionType = eCSR_ENCRYPT_TYPE_NONE;
1387
Anurag Chouhan600c3a02016-03-01 10:33:54 +05301388 qdf_mem_zero(&pHddStaCtx->conn_info.Keys, sizeof(tCsrKeys));
1389 qdf_mem_zero(&pHddStaCtx->ibss_enc_key, sizeof(tCsrRoamSetKey));
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001390
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001391 pHddStaCtx->conn_info.proxyARPService = 0;
1392
Anurag Chouhan600c3a02016-03-01 10:33:54 +05301393 qdf_mem_zero(&pHddStaCtx->conn_info.SSID, sizeof(tCsrSSIDInfo));
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001394}
1395
1396/**
1397 * hdd_roam_deregister_sta() - deregister station
1398 * @pAdapter: pointer to adapter
1399 * @staId: station identifier
1400 *
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05301401 * Return: QDF_STATUS enumeration
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001402 */
Deepak Dhamdherea6d2f4c2016-06-04 00:24:52 -07001403QDF_STATUS hdd_roam_deregister_sta(hdd_adapter_t *pAdapter, uint8_t staId)
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001404{
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05301405 QDF_STATUS qdf_status;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001406 hdd_station_ctx_t *pHddStaCtx = WLAN_HDD_GET_STATION_CTX_PTR(pAdapter);
1407
1408 if (eConnectionState_IbssDisconnected ==
1409 pHddStaCtx->conn_info.connState) {
1410 /*
1411 * Do not set the carrier off when the last peer leaves.
1412 * We will set the carrier off while stopping the IBSS.
1413 */
1414 }
1415
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05301416 qdf_status = ol_txrx_clear_peer(staId);
1417 if (!QDF_IS_STATUS_SUCCESS(qdf_status)) {
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07001418 hdd_err("ol_txrx_clear_peer() failed for staID %d. Status(%d) [0x%08X]",
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05301419 staId, qdf_status, qdf_status);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001420 }
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05301421 return qdf_status;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001422}
1423
1424/**
Anurag Chouhan5de8d172016-07-13 14:44:28 +05301425 * hdd_print_bss_info() - print bss info
1426 * @hdd_sta_ctx: pointer to hdd station context
1427 *
1428 * Return: None
1429 */
Jeff Johnson018d7d32016-10-05 14:31:11 -07001430static void hdd_print_bss_info(hdd_station_ctx_t *hdd_sta_ctx)
Anurag Chouhan5de8d172016-07-13 14:44:28 +05301431{
1432 uint32_t *cap_info;
1433
1434 hdd_info("WIFI DATA LOGGER");
1435 hdd_info("channel: %d",
1436 hdd_sta_ctx->conn_info.freq);
1437 hdd_info("dot11mode: %d",
1438 hdd_sta_ctx->conn_info.dot11Mode);
1439 hdd_info("AKM: %d",
1440 hdd_sta_ctx->conn_info.authType);
1441 hdd_info("ssid: %.*s",
1442 hdd_sta_ctx->conn_info.SSID.SSID.length,
1443 hdd_sta_ctx->conn_info.SSID.SSID.ssId);
1444 hdd_info("roam count: %d",
1445 hdd_sta_ctx->conn_info.roam_count);
1446 hdd_info("ant_info: %d",
1447 hdd_sta_ctx->conn_info.txrate.nss);
1448 hdd_info("datarate legacy %d",
1449 hdd_sta_ctx->conn_info.txrate.legacy);
1450 hdd_info("datarate mcs: %d",
1451 hdd_sta_ctx->conn_info.txrate.mcs);
1452 if (hdd_sta_ctx->conn_info.conn_flag.ht_present) {
1453 cap_info = (uint32_t *)&hdd_sta_ctx->conn_info.ht_caps;
1454 hdd_info("ht caps: %x", *cap_info);
1455 }
1456 if (hdd_sta_ctx->conn_info.conn_flag.vht_present) {
1457 cap_info = (uint32_t *)&hdd_sta_ctx->conn_info.vht_caps;
1458 hdd_info("vht caps: %x", *cap_info);
1459 }
1460 if (hdd_sta_ctx->conn_info.conn_flag.hs20_present)
1461 hdd_info("hs20 info: %x",
1462 hdd_sta_ctx->conn_info.hs20vendor_ie.release_num);
1463 hdd_info("signal: %d",
1464 hdd_sta_ctx->conn_info.signal);
1465 hdd_info("noise: %d",
1466 hdd_sta_ctx->conn_info.noise);
1467}
1468
1469/**
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001470 * hdd_dis_connect_handler() - disconnect event handler
1471 * @pAdapter: pointer to adapter
1472 * @pRoamInfo: pointer to roam info
1473 * @roamId: roam identifier
1474 * @roamStatus: roam status
1475 * @roamResult: roam result
1476 *
1477 * This function handles disconnect event:
1478 * 1. Disable transmit queues;
1479 * 2. Clean up internal connection states and data structures;
1480 * 3. Send disconnect indication to supplicant.
1481 *
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05301482 * Return: QDF_STATUS enumeration
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001483 */
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05301484static QDF_STATUS hdd_dis_connect_handler(hdd_adapter_t *pAdapter,
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001485 tCsrRoamInfo *pRoamInfo,
1486 uint32_t roamId,
1487 eRoamCmdStatus roamStatus,
1488 eCsrRoamResult roamResult)
1489{
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05301490 QDF_STATUS status = QDF_STATUS_SUCCESS;
1491 QDF_STATUS vstatus;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001492 struct net_device *dev = pAdapter->dev;
1493 hdd_context_t *pHddCtx = WLAN_HDD_GET_CTX(pAdapter);
1494 hdd_station_ctx_t *pHddStaCtx = WLAN_HDD_GET_STATION_CTX_PTR(pAdapter);
1495 uint8_t sta_id;
1496 bool sendDisconInd = true;
1497
1498 if (dev == NULL) {
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07001499 hdd_err("net_dev is released return");
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05301500 return QDF_STATUS_E_FAILURE;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001501 }
1502 /* notify apps that we can't pass traffic anymore */
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07001503 hdd_notice("Disabling queues");
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001504 wlan_hdd_netif_queue_control(pAdapter, WLAN_NETIF_TX_DISABLE_N_CARRIER,
1505 WLAN_CONTROL_PATH);
1506
1507 if (hdd_ipa_is_enabled(pHddCtx))
1508 hdd_ipa_wlan_evt(pAdapter, pHddStaCtx->conn_info.staId[0],
Mohit Khannafa99aea2016-05-12 21:43:13 -07001509 HDD_IPA_STA_DISCONNECT,
1510 pHddStaCtx->conn_info.bssId.bytes);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001511
1512#ifdef FEATURE_WLAN_AUTO_SHUTDOWN
1513 wlan_hdd_auto_shutdown_enable(pHddCtx, true);
1514#endif
1515
Nirav Shah1da77682016-05-03 20:16:39 +05301516 DPTRACE(qdf_dp_trace_mgmt_pkt(QDF_DP_TRACE_MGMT_PACKET_RECORD,
1517 pAdapter->sessionId,
1518 QDF_PROTO_TYPE_MGMT, QDF_PROTO_MGMT_DISASSOC));
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001519
1520 /* HDD has initiated disconnect, do not send disconnect indication
1521 * to kernel. Sending disconnected event to kernel for userspace
Mahesh A Saptasagarc35e8bf2016-06-17 20:03:46 +05301522 * initiated disconnect will be handled by disconnect handler call
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001523 * to cfg80211_disconnected.
1524 */
1525 if ((eConnectionState_Disconnecting ==
1526 pHddStaCtx->conn_info.connState) ||
1527 (eConnectionState_NotConnected ==
1528 pHddStaCtx->conn_info.connState)) {
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07001529 hdd_notice("HDD has initiated a disconnect, no need to send disconnect indication to kernel");
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001530 sendDisconInd = false;
1531 }
1532
1533 if (pHddStaCtx->conn_info.connState != eConnectionState_Disconnecting) {
1534 INIT_COMPLETION(pAdapter->disconnect_comp_var);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001535 hdd_conn_set_connection_state(pAdapter,
1536 eConnectionState_Disconnecting);
1537 }
1538
1539 hdd_clear_roam_profile_ie(pAdapter);
1540 hdd_wmm_init(pAdapter);
Himanshu Agarwal0527e8f2016-08-11 14:58:34 +05301541 hdd_info("Invoking packetdump deregistration API");
1542 wlan_deregister_txrx_packetdump();
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001543
1544 /* indicate 'disconnect' status to wpa_supplicant... */
1545 hdd_send_association_event(dev, pRoamInfo);
1546 /* indicate disconnected event to nl80211 */
1547 if (roamStatus != eCSR_ROAM_IBSS_LEAVE) {
1548 /*
1549 * Only send indication to kernel if not initiated
1550 * by kernel
1551 */
1552 if (sendDisconInd) {
1553 /*
1554 * To avoid wpa_supplicant sending "HANGED" CMD
1555 * to ICS UI.
1556 */
Kiran Kumar Lokere37d3aa22015-11-03 14:58:26 -08001557 if (eCSR_ROAM_LOSTLINK == roamStatus) {
1558 if (pRoamInfo->reasonCode ==
1559 eSIR_MAC_PEER_STA_REQ_LEAVING_BSS_REASON)
1560 pr_info("wlan: disconnected due to poor signal, rssi is %d dB\n", pRoamInfo->rxRssi);
Mahesh A Saptasagarc35e8bf2016-06-17 20:03:46 +05301561 wlan_hdd_cfg80211_indicate_disconnect(
1562 dev, false,
1563 pRoamInfo->reasonCode);
Kiran Kumar Lokere37d3aa22015-11-03 14:58:26 -08001564 } else {
Mahesh A Saptasagarc35e8bf2016-06-17 20:03:46 +05301565 wlan_hdd_cfg80211_indicate_disconnect(
1566 dev, false,
1567 WLAN_REASON_UNSPECIFIED
1568 );
Kiran Kumar Lokere37d3aa22015-11-03 14:58:26 -08001569 }
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001570
1571 hdd_info("sent disconnected event to nl80211, rssi: %d",
1572 pAdapter->rssi);
1573 }
1574 /*
1575 * During the WLAN uninitialization,supplicant is stopped
1576 * before the driver so not sending the status of the
1577 * connection to supplicant.
1578 */
Rajeev Kumarfec3dbe2016-01-19 15:23:52 -08001579 if (cds_is_load_or_unload_in_progress()) {
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001580#ifdef WLAN_FEATURE_P2P_DEBUG
Krunal Sonibe766b02016-03-10 13:00:44 -08001581 if (pAdapter->device_mode == QDF_P2P_CLIENT_MODE) {
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001582 if (global_p2p_connection_status ==
1583 P2P_CLIENT_CONNECTED_STATE_1) {
1584 global_p2p_connection_status =
1585 P2P_CLIENT_DISCONNECTED_STATE;
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07001586 hdd_err("[P2P State] 8 way Handshake completed and moved to disconnected state");
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001587 } else if (global_p2p_connection_status ==
1588 P2P_CLIENT_COMPLETED_STATE) {
1589 global_p2p_connection_status =
1590 P2P_NOT_ACTIVE;
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07001591 hdd_err("[P2P State] P2P Client is removed and moved to inactive state");
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001592 }
1593 }
1594#endif
1595
1596 }
1597 }
1598
1599 hdd_wmm_adapter_clear(pAdapter);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001600 sme_ft_reset(WLAN_HDD_GET_HAL_CTX(pAdapter), pAdapter->sessionId);
Gupta, Kapil4cb1d7d2016-04-16 18:16:25 -07001601 if (hdd_remove_beacon_filter(pAdapter) != 0)
1602 hdd_err("hdd_remove_beacon_filter() failed");
1603
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001604 if (eCSR_ROAM_IBSS_LEAVE == roamStatus) {
Sreelakshmi Konamki32eadb12015-09-02 15:18:32 +05301605 uint8_t i;
Rakesh Sunkicf1c9ab2016-08-25 14:11:25 -07001606 sta_id = pHddStaCtx->broadcast_staid;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001607 vstatus = hdd_roam_deregister_sta(pAdapter, sta_id);
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05301608 if (!QDF_IS_STATUS_SUCCESS(vstatus)) {
Chandrasekaran, Manishekar34e325a2015-12-18 12:07:22 +05301609 hdd_err("hdd_roam_deregister_sta() failed for staID %d Status=%d [0x%x]",
1610 sta_id, status, status);
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05301611 status = QDF_STATUS_E_FAILURE;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001612 }
1613 pHddCtx->sta_to_adapter[sta_id] = NULL;
Sreelakshmi Konamki32eadb12015-09-02 15:18:32 +05301614 /* Clear all the peer sta register with TL. */
Naveen Rawatc45d1622016-07-05 12:20:09 -07001615 for (i = 0; i < MAX_PEERS; i++) {
Sreelakshmi Konamki32eadb12015-09-02 15:18:32 +05301616 if (0 == pHddStaCtx->conn_info.staId[i])
1617 continue;
1618 sta_id = pHddStaCtx->conn_info.staId[i];
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07001619 hdd_info("Deregister StaID %d", sta_id);
Sreelakshmi Konamki32eadb12015-09-02 15:18:32 +05301620 vstatus = hdd_roam_deregister_sta(pAdapter, sta_id);
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05301621 if (!QDF_IS_STATUS_SUCCESS(vstatus)) {
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07001622 hdd_err("hdd_roamDeregisterSTA() failed to for staID %d. Status= %d [0x%x]",
Sreelakshmi Konamki32eadb12015-09-02 15:18:32 +05301623 sta_id, status, status);
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05301624 status = QDF_STATUS_E_FAILURE;
Sreelakshmi Konamki32eadb12015-09-02 15:18:32 +05301625 }
1626 /* set the staid and peer mac as 0, all other
1627 * reset are done in hdd_connRemoveConnectInfo.
1628 */
1629 pHddStaCtx->conn_info.staId[i] = 0;
Anurag Chouhan600c3a02016-03-01 10:33:54 +05301630 qdf_mem_zero(&pHddStaCtx->conn_info.peerMacAddress[i],
Anurag Chouhan6d760662016-02-20 16:05:43 +05301631 sizeof(struct qdf_mac_addr));
Sreelakshmi Konamki32eadb12015-09-02 15:18:32 +05301632 if (sta_id < (WLAN_MAX_STA_COUNT + 3))
1633 pHddCtx->sta_to_adapter[sta_id] = NULL;
1634 }
1635 } else {
1636 sta_id = pHddStaCtx->conn_info.staId[0];
Abhishek Singhc9941602016-08-09 16:06:22 +05301637
1638 /* clear scan cache for Link Lost */
1639 if (pRoamInfo && !pRoamInfo->reasonCode &&
1640 (eCSR_ROAM_RESULT_DEAUTH_IND == roamResult)) {
1641 wlan_hdd_cfg80211_update_bss_list(pAdapter,
1642 pHddStaCtx->conn_info.bssId.bytes);
1643 sme_remove_bssid_from_scan_list(pHddCtx->hHal,
1644 pHddStaCtx->conn_info.bssId.bytes);
1645 }
Sreelakshmi Konamki32eadb12015-09-02 15:18:32 +05301646 /* We should clear all sta register with TL,
1647 * for now, only one.
1648 */
1649 vstatus = hdd_roam_deregister_sta(pAdapter, sta_id);
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05301650 if (!QDF_IS_STATUS_SUCCESS(vstatus)) {
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07001651 hdd_err("hdd_roam_deregister_sta() failed to for staID %d. Status= %d [0x%x]",
Sreelakshmi Konamki32eadb12015-09-02 15:18:32 +05301652 sta_id, status, status);
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05301653 status = QDF_STATUS_E_FAILURE;
Sreelakshmi Konamki32eadb12015-09-02 15:18:32 +05301654 }
1655 pHddCtx->sta_to_adapter[sta_id] = NULL;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001656 }
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001657 /* Clear saved connection information in HDD */
1658 hdd_conn_remove_connect_info(pHddStaCtx);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001659 hdd_conn_set_connection_state(pAdapter, eConnectionState_NotConnected);
1660#ifdef WLAN_FEATURE_GTK_OFFLOAD
Krunal Sonibe766b02016-03-10 13:00:44 -08001661 if ((QDF_STA_MODE == pAdapter->device_mode) ||
1662 (QDF_P2P_CLIENT_MODE == pAdapter->device_mode)) {
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001663 memset(&pHddStaCtx->gtkOffloadReqParams, 0,
1664 sizeof(tSirGtkOffloadParams));
1665 pHddStaCtx->gtkOffloadReqParams.ulFlags = GTK_OFFLOAD_DISABLE;
1666 }
1667#endif
1668
1669#ifdef FEATURE_WLAN_TDLS
1670 if (eCSR_ROAM_IBSS_LEAVE != roamStatus)
1671 wlan_hdd_tdls_disconnection_callback(pAdapter);
1672#endif
1673
Krunal Sonibe766b02016-03-10 13:00:44 -08001674 if ((QDF_STA_MODE == pAdapter->device_mode) ||
1675 (QDF_P2P_CLIENT_MODE == pAdapter->device_mode)) {
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001676 sme_ps_disable_auto_ps_timer(WLAN_HDD_GET_HAL_CTX
1677 (pAdapter),
1678 pAdapter->sessionId);
1679 }
1680 /* Unblock anyone waiting for disconnect to complete */
1681 complete(&pAdapter->disconnect_comp_var);
Anurag Chouhan5de8d172016-07-13 14:44:28 +05301682 hdd_print_bss_info(pHddStaCtx);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001683 return status;
1684}
1685
1686/**
1687 * hdd_set_peer_authorized_event() - set peer_authorized_event
1688 * @vdev_id: vdevid
1689 *
1690 * Return: None
1691 */
Jeff Johnson018d7d32016-10-05 14:31:11 -07001692static void hdd_set_peer_authorized_event(uint32_t vdev_id)
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001693{
Anurag Chouhan6d760662016-02-20 16:05:43 +05301694 hdd_context_t *hdd_ctx = cds_get_context(QDF_MODULE_ID_HDD);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001695 hdd_adapter_t *adapter = NULL;
1696
1697 adapter = hdd_get_adapter_by_vdev(hdd_ctx, vdev_id);
1698 if (adapter == NULL) {
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07001699 hdd_err("Invalid vdev_id");
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001700 }
1701 complete(&adapter->sta_authorized_event);
1702}
1703
1704/**
1705 * hdd_change_peer_state() - change peer state
1706 * @pAdapter: HDD adapter
1707 * @sta_state: peer state
1708 * @roam_synch_in_progress: roam synch in progress
1709 *
Anurag Chouhanf04e84f2016-03-03 10:12:12 +05301710 * Return: QDF status
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001711 */
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05301712QDF_STATUS hdd_change_peer_state(hdd_adapter_t *pAdapter,
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001713 uint8_t sta_id,
1714 enum ol_txrx_peer_state sta_state,
1715 bool roam_synch_in_progress)
1716{
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05301717 QDF_STATUS err;
Manjunathappa Prakash10d357a2016-03-31 19:20:49 -07001718 uint8_t *peer_mac_addr;
Manjunathappa Prakash2593a642016-04-01 08:53:35 -07001719 struct ol_txrx_pdev_t *pdev = cds_get_context(QDF_MODULE_ID_TXRX);
Manjunathappa Prakash10d357a2016-03-31 19:20:49 -07001720 ol_txrx_peer_handle peer;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001721
1722 if (!pdev) {
1723 hdd_err("Failed to get txrx context");
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05301724 return QDF_STATUS_E_FAULT;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001725 }
1726
1727 if (sta_id >= WLAN_MAX_STA_COUNT) {
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07001728 hdd_err("Invalid sta id :%d", sta_id);
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05301729 return QDF_STATUS_E_INVAL;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001730 }
1731
1732 peer = ol_txrx_peer_find_by_local_id(pdev, sta_id);
1733 if (!peer)
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05301734 return QDF_STATUS_E_FAULT;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001735
Manjunathappa Prakash10d357a2016-03-31 19:20:49 -07001736 peer_mac_addr = ol_txrx_peer_get_peer_mac_addr(peer);
1737 if (peer_mac_addr == NULL) {
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07001738 hdd_err("peer mac addr is NULL");
Manjunathappa Prakash10d357a2016-03-31 19:20:49 -07001739 return QDF_STATUS_E_FAULT;
1740 }
1741
1742 err = ol_txrx_peer_state_update(pdev, peer_mac_addr, sta_state);
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05301743 if (err != QDF_STATUS_SUCCESS) {
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07001744 hdd_err("peer state update failed");
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05301745 return QDF_STATUS_E_FAULT;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001746 }
1747#ifdef WLAN_FEATURE_ROAM_OFFLOAD
1748 if (roam_synch_in_progress)
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05301749 return QDF_STATUS_SUCCESS;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001750#endif
1751
Dhanashri Atreb08959a2016-03-01 17:28:03 -08001752 if (sta_state == OL_TXRX_PEER_STATE_AUTH) {
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001753#ifdef QCA_LL_LEGACY_TX_FLOW_CONTROL
1754 /* make sure event is reset */
1755 INIT_COMPLETION(pAdapter->sta_authorized_event);
1756#endif
1757
Manjunathappa Prakash10d357a2016-03-31 19:20:49 -07001758 err = sme_set_peer_authorized(peer_mac_addr,
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001759 hdd_set_peer_authorized_event,
1760 pAdapter->sessionId);
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05301761 if (err != QDF_STATUS_SUCCESS) {
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07001762 hdd_err("Failed to set the peer state to authorized");
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05301763 return QDF_STATUS_E_FAULT;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001764 }
1765
Krunal Sonibe766b02016-03-10 13:00:44 -08001766 if (pAdapter->device_mode == QDF_STA_MODE ||
1767 pAdapter->device_mode == QDF_P2P_CLIENT_MODE) {
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001768#if defined(QCA_LL_LEGACY_TX_FLOW_CONTROL) || defined(QCA_LL_TX_FLOW_CONTROL_V2)
Houston Hoffman52ec6692016-04-21 16:36:45 -07001769 ol_txrx_vdev_handle vdev;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001770 unsigned long rc;
1771
1772 /* wait for event from firmware to set the event */
1773 rc = wait_for_completion_timeout(
1774 &pAdapter->sta_authorized_event,
1775 msecs_to_jiffies(HDD_PEER_AUTHORIZE_WAIT));
1776 if (!rc) {
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07001777 hdd_notice("timeout waiting for sta_authorized_event");
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001778 }
Manjunathappa Prakash10d357a2016-03-31 19:20:49 -07001779 vdev = ol_txrx_get_vdev_for_peer(peer);
1780 ol_txrx_vdev_unpause(vdev,
1781 OL_TXQ_PAUSE_REASON_PEER_UNAUTHORIZED);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001782#endif
1783 }
1784 }
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05301785 return QDF_STATUS_SUCCESS;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001786}
1787
1788/**
1789 * hdd_roam_register_sta() - register station
1790 * @pAdapter: pointer to adapter
1791 * @pRoamInfo: pointer to roam info
1792 * @staId: station identifier
1793 * @pPeerMacAddress: peer MAC address
1794 * @pBssDesc: pointer to BSS description
1795 *
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05301796 * Return: QDF_STATUS enumeration
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001797 */
Deepak Dhamdhere0f076bd2016-06-02 11:29:21 -07001798QDF_STATUS hdd_roam_register_sta(hdd_adapter_t *pAdapter,
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001799 tCsrRoamInfo *pRoamInfo,
1800 uint8_t staId,
Anurag Chouhan6d760662016-02-20 16:05:43 +05301801 struct qdf_mac_addr *pPeerMacAddress,
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001802 tSirBssDescription *pBssDesc)
1803{
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05301804 QDF_STATUS qdf_status = QDF_STATUS_E_FAILURE;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001805 struct ol_txrx_desc_type staDesc = { 0 };
1806 hdd_station_ctx_t *pHddStaCtx = WLAN_HDD_GET_STATION_CTX_PTR(pAdapter);
Dhanashri Atre182b0272016-02-17 15:35:07 -08001807 struct ol_txrx_ops txrx_ops;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001808
1809 if (NULL == pBssDesc)
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05301810 return QDF_STATUS_E_FAILURE;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001811
1812 /* Get the Station ID from the one saved during the association */
1813 staDesc.sta_id = staId;
1814
1815 /* set the QoS field appropriately */
1816 if (hdd_wmm_is_active(pAdapter))
1817 staDesc.is_qos_enabled = 1;
1818 else
1819 staDesc.is_qos_enabled = 0;
1820
1821#ifdef FEATURE_WLAN_WAPI
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07001822 hdd_notice("WAPI STA Registered: %d",
1823 pAdapter->wapi_info.fIsWapiSta);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001824 if (pAdapter->wapi_info.fIsWapiSta)
1825 staDesc.is_wapi_supported = 1;
1826 else
1827 staDesc.is_wapi_supported = 0;
1828#endif /* FEATURE_WLAN_WAPI */
1829
Dhanashri Atre50141c52016-04-07 13:15:29 -07001830 /* Register the vdev transmit and receive functions */
1831 qdf_mem_zero(&txrx_ops, sizeof(txrx_ops));
1832 txrx_ops.rx.rx = hdd_rx_packet_cbk;
1833 ol_txrx_vdev_register(
1834 ol_txrx_get_vdev_from_vdev_id(pAdapter->sessionId),
1835 pAdapter, &txrx_ops);
1836 pAdapter->tx_fn = txrx_ops.tx.tx;
1837
Dhanashri Atre182b0272016-02-17 15:35:07 -08001838 qdf_status = ol_txrx_register_peer(&staDesc);
1839
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05301840 if (!QDF_IS_STATUS_SUCCESS(qdf_status)) {
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07001841 hdd_warn("ol_txrx_register_peer() failed to register. Status=%d [0x%08X]",
1842 qdf_status, qdf_status);
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05301843 return qdf_status;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001844 }
1845
1846 if (!pRoamInfo->fAuthRequired) {
1847 /*
1848 * Connections that do not need Upper layer auth, transition
1849 * TLSHIM directly to 'Authenticated' state
1850 */
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05301851 qdf_status =
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001852 hdd_change_peer_state(pAdapter, staDesc.sta_id,
Dhanashri Atreb08959a2016-03-01 17:28:03 -08001853 OL_TXRX_PEER_STATE_AUTH,
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001854#ifdef WLAN_FEATURE_ROAM_OFFLOAD
1855 pRoamInfo->roamSynchInProgress
1856#else
1857 false
1858#endif
1859 );
1860
1861 hdd_conn_set_authenticated(pAdapter, true);
1862 } else {
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07001863 hdd_info("ULA auth StaId= %d. Changing TL state to CONNECTED at Join time",
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001864 pHddStaCtx->conn_info.staId[0]);
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05301865 qdf_status =
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001866 hdd_change_peer_state(pAdapter, staDesc.sta_id,
Dhanashri Atreb08959a2016-03-01 17:28:03 -08001867 OL_TXRX_PEER_STATE_CONN,
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001868#ifdef WLAN_FEATURE_ROAM_OFFLOAD
1869 pRoamInfo->roamSynchInProgress
1870#else
1871 false
1872#endif
1873 );
1874 hdd_conn_set_authenticated(pAdapter, false);
1875 }
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05301876 return qdf_status;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001877}
1878
1879/**
1880 * hdd_send_re_assoc_event() - send reassoc event
1881 * @dev: pointer to net device
1882 * @pAdapter: pointer to adapter
1883 * @pCsrRoamInfo: pointer to roam info
1884 * @reqRsnIe: pointer to RSN Information element
1885 * @reqRsnLength: length of RSN IE
1886 *
1887 * Return: none
1888 */
1889static void hdd_send_re_assoc_event(struct net_device *dev,
1890 hdd_adapter_t *pAdapter, tCsrRoamInfo *pCsrRoamInfo,
1891 uint8_t *reqRsnIe, uint32_t reqRsnLength)
1892{
1893 unsigned int len = 0;
1894 u8 *pFTAssocRsp = NULL;
1895 uint8_t *rspRsnIe = kmalloc(IW_GENERIC_IE_MAX, GFP_KERNEL);
Naveen Rawat14298b92015-11-25 16:27:41 -08001896 uint8_t *assoc_req_ies = kmalloc(IW_GENERIC_IE_MAX, GFP_KERNEL);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001897 uint32_t rspRsnLength = 0;
1898 struct ieee80211_channel *chan;
1899 hdd_context_t *pHddCtx = WLAN_HDD_GET_CTX(pAdapter);
1900 uint8_t buf_ssid_ie[2 + SIR_MAC_SSID_EID_MAX]; /* 2 bytes-EID and len */
1901 uint8_t *buf_ptr, ssid_ie_len;
1902 struct cfg80211_bss *bss = NULL;
1903 uint8_t *final_req_ie = NULL;
1904 tCsrRoamConnectedProfile roam_profile;
1905 tHalHandle hal_handle = WLAN_HDD_GET_HAL_CTX(pAdapter);
1906
Jeff Johnsonfdb73432016-10-11 08:07:27 -07001907 qdf_mem_zero(&roam_profile, sizeof(roam_profile));
1908
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001909 if (!rspRsnIe) {
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07001910 hdd_err("Unable to allocate RSN IE");
Naveen Rawatdafda292016-01-06 18:32:14 -08001911 goto done;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001912 }
1913
Naveen Rawat14298b92015-11-25 16:27:41 -08001914 if (!assoc_req_ies) {
1915 hdd_err("Unable to allocate Assoc Req IE");
Naveen Rawatdafda292016-01-06 18:32:14 -08001916 goto done;
Naveen Rawat14298b92015-11-25 16:27:41 -08001917 }
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001918 if (pCsrRoamInfo == NULL) {
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07001919 hdd_err("Invalid CSR roam info");
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001920 goto done;
1921 }
1922
1923 if (pCsrRoamInfo->nAssocRspLength == 0) {
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07001924 hdd_err("Invalid assoc response length");
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001925 goto done;
1926 }
1927
1928 pFTAssocRsp =
1929 (u8 *) (pCsrRoamInfo->pbFrames + pCsrRoamInfo->nBeaconLength +
1930 pCsrRoamInfo->nAssocReqLength);
1931 if (pFTAssocRsp == NULL)
1932 goto done;
1933
1934 /* pFTAssocRsp needs to point to the IEs */
1935 pFTAssocRsp += FT_ASSOC_RSP_IES_OFFSET;
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07001936 hdd_info("AssocRsp is now at %02x%02x",
1937 (unsigned int)pFTAssocRsp[0], (unsigned int)pFTAssocRsp[1]);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001938
1939 /*
1940 * Active session count is decremented upon disconnection, but during
1941 * roaming, there is no disconnect indication and hence active session
1942 * count is not decremented.
1943 * After roaming is completed, active session count is incremented
1944 * as a part of connect indication but effectively after roaming the
1945 * active session count should still be the same and hence upon
1946 * successful reassoc decrement the active session count here.
1947 */
Varun Reddy Yeturud5939f82015-12-24 18:14:02 -08001948 if (!hdd_is_roam_sync_in_progress(pCsrRoamInfo))
Chandrasekaran, Manishekar6e9aa1b2015-12-02 18:04:00 +05301949 cds_decr_session_set_pcl(pAdapter->device_mode,
1950 pAdapter->sessionId);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001951
1952 /* Send the Assoc Resp, the supplicant needs this for initial Auth */
1953 len = pCsrRoamInfo->nAssocRspLength - FT_ASSOC_RSP_IES_OFFSET;
1954 rspRsnLength = len;
Anurag Chouhan600c3a02016-03-01 10:33:54 +05301955 qdf_mem_copy(rspRsnIe, pFTAssocRsp, len);
1956 qdf_mem_zero(rspRsnIe + len, IW_GENERIC_IE_MAX - len);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001957
1958 chan = ieee80211_get_channel(pAdapter->wdev.wiphy,
1959 (int)pCsrRoamInfo->pBssDesc->channelId);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001960 sme_roam_get_connect_profile(hal_handle, pAdapter->sessionId,
1961 &roam_profile);
1962 bss = cfg80211_get_bss(pAdapter->wdev.wiphy, chan,
1963 pCsrRoamInfo->bssid.bytes,
1964 &roam_profile.SSID.ssId[0], roam_profile.SSID.length,
Ryan Hsu535d16a2016-01-18 16:45:12 -08001965#if (LINUX_VERSION_CODE < KERNEL_VERSION(4, 1, 0)) && !defined(WITH_BACKPORTS)
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001966 WLAN_CAPABILITY_ESS, WLAN_CAPABILITY_ESS);
Ryan Hsu535d16a2016-01-18 16:45:12 -08001967#else
1968 IEEE80211_BSS_TYPE_ESS, IEEE80211_PRIVACY_ANY);
1969#endif
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001970
1971 if (bss == NULL)
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07001972 hdd_err("Get BSS returned NULL");
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001973 buf_ptr = buf_ssid_ie;
1974 *buf_ptr = SIR_MAC_SSID_EID;
1975 buf_ptr++;
1976 *buf_ptr = roam_profile.SSID.length; /*len of ssid*/
1977 buf_ptr++;
Anurag Chouhan600c3a02016-03-01 10:33:54 +05301978 qdf_mem_copy(buf_ptr, &roam_profile.SSID.ssId[0],
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001979 roam_profile.SSID.length);
1980 ssid_ie_len = 2 + roam_profile.SSID.length;
Jeff Johnson9991f472016-01-06 16:02:31 -08001981 hdd_notice("SSIDIE:");
Anurag Chouhanb2dc16f2016-02-25 11:47:37 +05301982 QDF_TRACE_HEX_DUMP(QDF_MODULE_ID_HDD, QDF_TRACE_LEVEL_DEBUG,
Jeff Johnson9991f472016-01-06 16:02:31 -08001983 buf_ssid_ie, ssid_ie_len);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001984 final_req_ie = kmalloc(IW_GENERIC_IE_MAX, GFP_KERNEL);
1985 if (final_req_ie == NULL)
1986 goto done;
1987 buf_ptr = final_req_ie;
Anurag Chouhan600c3a02016-03-01 10:33:54 +05301988 qdf_mem_copy(buf_ptr, buf_ssid_ie, ssid_ie_len);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001989 buf_ptr += ssid_ie_len;
Anurag Chouhan600c3a02016-03-01 10:33:54 +05301990 qdf_mem_copy(buf_ptr, reqRsnIe, reqRsnLength);
1991 qdf_mem_copy(rspRsnIe, pFTAssocRsp, len);
1992 qdf_mem_zero(final_req_ie + (ssid_ie_len + reqRsnLength),
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001993 IW_GENERIC_IE_MAX - (ssid_ie_len + reqRsnLength));
Jeff Johnson9991f472016-01-06 16:02:31 -08001994 hdd_notice("Req RSN IE:");
Anurag Chouhanb2dc16f2016-02-25 11:47:37 +05301995 QDF_TRACE_HEX_DUMP(QDF_MODULE_ID_HDD, QDF_TRACE_LEVEL_DEBUG,
Jeff Johnson9991f472016-01-06 16:02:31 -08001996 final_req_ie, (ssid_ie_len + reqRsnLength));
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001997 cfg80211_roamed_bss(dev, bss,
1998 final_req_ie, (ssid_ie_len + reqRsnLength),
1999 rspRsnIe, rspRsnLength, GFP_KERNEL);
2000
Anurag Chouhan600c3a02016-03-01 10:33:54 +05302001 qdf_mem_copy(assoc_req_ies,
Naveen Rawat14298b92015-11-25 16:27:41 -08002002 (u8 *)pCsrRoamInfo->pbFrames + pCsrRoamInfo->nBeaconLength,
2003 pCsrRoamInfo->nAssocReqLength);
2004
2005 hdd_notice("ReAssoc Req IE dump");
Anurag Chouhanb2dc16f2016-02-25 11:47:37 +05302006 QDF_TRACE_HEX_DUMP(QDF_MODULE_ID_HDD, QDF_TRACE_LEVEL_DEBUG,
Naveen Rawat14298b92015-11-25 16:27:41 -08002007 assoc_req_ies, pCsrRoamInfo->nAssocReqLength);
2008
Prashanth Bhattabfc25292015-11-05 11:16:21 -08002009 wlan_hdd_send_roam_auth_event(pHddCtx, pCsrRoamInfo->bssid.bytes,
Naveen Rawat14298b92015-11-25 16:27:41 -08002010 assoc_req_ies, pCsrRoamInfo->nAssocReqLength,
2011 rspRsnIe, rspRsnLength,
Prashanth Bhattabfc25292015-11-05 11:16:21 -08002012 pCsrRoamInfo);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002013done:
Naveen Rawatdf0a7e72016-01-06 18:35:53 -08002014 sme_roam_free_connect_profile(&roam_profile);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002015 if (final_req_ie)
2016 kfree(final_req_ie);
2017 kfree(rspRsnIe);
Naveen Rawat14298b92015-11-25 16:27:41 -08002018 kfree(assoc_req_ies);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002019}
2020
2021/**
Govind Singhedc5cda2015-10-23 17:11:35 +05302022 * hdd_is_roam_sync_in_progress()- Check if roam offloaded
Varun Reddy Yeturud5939f82015-12-24 18:14:02 -08002023 * @roaminfo - Roaming Information
Govind Singhedc5cda2015-10-23 17:11:35 +05302024 *
2025 * Return: roam sync status if roaming offloaded else false
2026 */
2027#ifdef WLAN_FEATURE_ROAM_OFFLOAD
Varun Reddy Yeturud5939f82015-12-24 18:14:02 -08002028bool hdd_is_roam_sync_in_progress(tCsrRoamInfo *roaminfo)
Govind Singhedc5cda2015-10-23 17:11:35 +05302029{
Varun Reddy Yeturud5939f82015-12-24 18:14:02 -08002030 if (roaminfo)
2031 return roaminfo->roamSynchInProgress;
2032 else
2033 return false;
Govind Singhedc5cda2015-10-23 17:11:35 +05302034}
2035#endif
2036
2037
2038/**
2039 * hdd_change_sta_state_authenticated()-
2040 * This function changes STA state to authenticated
2041 * @adapter: pointer to the adapter structure.
2042 * @roaminfo: pointer to the RoamInfo structure.
2043 *
2044 * This is called from hdd_RoamSetKeyCompleteHandler
2045 * in context to eCSR_ROAM_SET_KEY_COMPLETE event from fw.
2046 *
2047 * Return: 0 on success and errno on failure
2048 */
2049static int hdd_change_sta_state_authenticated(hdd_adapter_t *adapter,
2050 tCsrRoamInfo *roaminfo)
2051{
2052 int ret;
Dustin Brownf660fb42016-09-09 12:04:00 -07002053 uint32_t timeout;
Govind Singhedc5cda2015-10-23 17:11:35 +05302054 hdd_station_ctx_t *hddstactx = WLAN_HDD_GET_STATION_CTX_PTR(adapter);
2055
Dustin Brownf660fb42016-09-09 12:04:00 -07002056 timeout = hddstactx->hdd_ReassocScenario ?
2057 AUTO_PS_ENTRY_TIMER_DEFAULT_VALUE :
2058 AUTO_DEFERRED_PS_ENTRY_TIMER_DEFAULT_VALUE;
2059
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07002060 hdd_info("Changing TL state to AUTHENTICATED for StaId= %d",
2061 hddstactx->conn_info.staId[0]);
Govind Singhedc5cda2015-10-23 17:11:35 +05302062
2063 /* Connections that do not need Upper layer authentication,
2064 * transition TL to 'Authenticated' state after the keys are set
2065 */
2066 ret = hdd_change_peer_state(adapter,
2067 hddstactx->conn_info.staId[0],
Dhanashri Atreb08959a2016-03-01 17:28:03 -08002068 OL_TXRX_PEER_STATE_AUTH,
Govind Singhedc5cda2015-10-23 17:11:35 +05302069 hdd_is_roam_sync_in_progress(roaminfo));
2070 hdd_conn_set_authenticated(adapter, true);
Krunal Sonibe766b02016-03-10 13:00:44 -08002071 if ((QDF_STA_MODE == adapter->device_mode) ||
2072 (QDF_P2P_CLIENT_MODE == adapter->device_mode)) {
Govind Singhedc5cda2015-10-23 17:11:35 +05302073 sme_ps_enable_auto_ps_timer(
2074 WLAN_HDD_GET_HAL_CTX(adapter),
2075 adapter->sessionId,
Dustin Brownf660fb42016-09-09 12:04:00 -07002076 timeout);
Govind Singhedc5cda2015-10-23 17:11:35 +05302077 }
2078
2079 return ret;
2080}
2081
2082/**
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002083 * hdd_roam_set_key_complete_handler() - Update the security parameters
2084 * @pAdapter: pointer to adapter
2085 * @pRoamInfo: pointer to roam info
2086 * @roamId: roam id
2087 * @roamStatus: roam status
2088 * @roamResult: roam result
2089 *
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05302090 * Return: QDF_STATUS enumeration
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002091 */
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05302092static QDF_STATUS hdd_roam_set_key_complete_handler(hdd_adapter_t *pAdapter,
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002093 tCsrRoamInfo *pRoamInfo,
2094 uint32_t roamId,
2095 eRoamCmdStatus roamStatus,
2096 eCsrRoamResult roamResult)
2097{
2098 eCsrEncryptionType connectedCipherAlgo;
2099 bool fConnected = false;
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05302100 QDF_STATUS qdf_status = QDF_STATUS_E_FAILURE;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002101 hdd_station_ctx_t *pHddStaCtx = WLAN_HDD_GET_STATION_CTX_PTR(pAdapter);
Sreelakshmi Konamki720f2b72016-02-26 16:44:04 +05302102 tHalHandle hal_ctx = WLAN_HDD_GET_HAL_CTX(pAdapter);
2103 tpAniSirGlobal mac_ctx = PMAC_STRUCT(hal_ctx);
2104
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002105 ENTER();
2106
2107 if (NULL == pRoamInfo) {
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07002108 hdd_info("pRoamInfo is NULL");
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05302109 return QDF_STATUS_E_FAILURE;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002110 }
2111 /*
2112 * if (WPA), tell TL to go to 'authenticated' after the keys are set.
2113 * then go to 'authenticated'. For all other authentication types
2114 * (those that do not require upper layer authentication) we can put TL
2115 * directly into 'authenticated' state.
2116 */
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07002117 hdd_info("Set Key completion roamStatus =%d roamResult=%d "
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002118 MAC_ADDRESS_STR, roamStatus, roamResult,
2119 MAC_ADDR_ARRAY(pRoamInfo->peerMac.bytes));
2120
2121 fConnected = hdd_conn_get_connected_cipher_algo(pHddStaCtx,
2122 &connectedCipherAlgo);
2123 if (fConnected) {
Krunal Sonibe766b02016-03-10 13:00:44 -08002124 if (QDF_IBSS_MODE == pAdapter->device_mode) {
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002125 uint8_t staId;
2126
Anurag Chouhanc5548422016-02-24 18:33:27 +05302127 if (qdf_is_macaddr_broadcast(&pRoamInfo->peerMac)) {
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002128 pHddStaCtx->roam_info.roamingState =
2129 HDD_ROAM_STATE_NONE;
2130 } else {
Deepak Dhamdhere5872c8c2016-06-02 15:51:47 -07002131 qdf_status = hdd_get_peer_sta_id(
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002132 pHddStaCtx,
2133 &pRoamInfo->peerMac,
2134 &staId);
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05302135 if (QDF_STATUS_SUCCESS == qdf_status) {
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07002136 hdd_info("WLAN TL STA Ptk Installed for STAID=%d",
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002137 staId);
2138 pHddStaCtx->roam_info.roamingState =
2139 HDD_ROAM_STATE_NONE;
2140 }
2141 }
2142 } else {
2143 /*
2144 * TODO: Considering getting a state machine in
Govind Singhedc5cda2015-10-23 17:11:35 +05302145 * HDD later.This routine is invoked twice.
2146 * 1)set PTK 2)set GTK.The following if
2147 * statement will be TRUE when setting GTK.
2148 * At this time we don't handle the state in detail.
2149 * Related CR: 174048 - TL not in authenticated state
2150 */
Sreelakshmi Konamki720f2b72016-02-26 16:44:04 +05302151 if (eCSR_ROAM_RESULT_AUTHENTICATED == roamResult) {
Govind Singhedc5cda2015-10-23 17:11:35 +05302152 pHddStaCtx->conn_info.gtk_installed = true;
Sreelakshmi Konamki720f2b72016-02-26 16:44:04 +05302153 /*
2154 * PTK exchange happens in preauthentication
2155 * itself if key_mgmt is FT-PSK, ptk_installed
2156 * was false as there is no set PTK after
2157 * roaming. STA TL state moves to authenticated
2158 * only if ptk_installed is true. So, make
2159 * ptk_installed to true in case of 11R roaming.
2160 */
2161 if (csr_neighbor_roam_is11r_assoc(mac_ctx,
2162 pAdapter->sessionId))
2163 pHddStaCtx->conn_info.ptk_installed =
2164 true;
2165 } else {
Govind Singhedc5cda2015-10-23 17:11:35 +05302166 pHddStaCtx->conn_info.ptk_installed = true;
Sreelakshmi Konamki720f2b72016-02-26 16:44:04 +05302167 }
Govind Singhedc5cda2015-10-23 17:11:35 +05302168
2169 /* In WPA case move STA to authenticated when
2170 * ptk is installed.Earlier in WEP case STA
2171 * was moved to AUTHENTICATED prior to setting
2172 * the unicast key and it was resulting in sending
2173 * few un-encrypted packet. Now in WEP case
2174 * STA state will be moved to AUTHENTICATED
2175 * after we set the unicast and broadcast key.
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002176 */
Govind Singhedc5cda2015-10-23 17:11:35 +05302177 if ((pHddStaCtx->conn_info.ucEncryptionType ==
2178 eCSR_ENCRYPT_TYPE_WEP40) ||
2179 (pHddStaCtx->conn_info.ucEncryptionType ==
2180 eCSR_ENCRYPT_TYPE_WEP104) ||
2181 (pHddStaCtx->conn_info.ucEncryptionType ==
2182 eCSR_ENCRYPT_TYPE_WEP40_STATICKEY) ||
2183 (pHddStaCtx->conn_info.ucEncryptionType ==
2184 eCSR_ENCRYPT_TYPE_WEP104_STATICKEY)) {
2185 if (pHddStaCtx->conn_info.gtk_installed &&
2186 pHddStaCtx->conn_info.ptk_installed)
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05302187 qdf_status =
Govind Singhedc5cda2015-10-23 17:11:35 +05302188 hdd_change_sta_state_authenticated(pAdapter,
2189 pRoamInfo);
2190 } else if (pHddStaCtx->conn_info.ptk_installed) {
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05302191 qdf_status =
Govind Singhedc5cda2015-10-23 17:11:35 +05302192 hdd_change_sta_state_authenticated(pAdapter,
2193 pRoamInfo);
2194 }
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002195
Govind Singhedc5cda2015-10-23 17:11:35 +05302196 if (pHddStaCtx->conn_info.gtk_installed &&
2197 pHddStaCtx->conn_info.ptk_installed) {
2198 pHddStaCtx->conn_info.gtk_installed = false;
2199 pHddStaCtx->conn_info.ptk_installed = false;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002200 }
2201
2202 pHddStaCtx->roam_info.roamingState =
Govind Singhedc5cda2015-10-23 17:11:35 +05302203 HDD_ROAM_STATE_NONE;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002204 }
2205 } else {
2206 /*
2207 * possible disassoc after issuing set key and waiting
2208 * set key complete.
2209 */
2210 pHddStaCtx->roam_info.roamingState = HDD_ROAM_STATE_NONE;
2211 }
2212
2213 EXIT();
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05302214 return QDF_STATUS_SUCCESS;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002215}
2216
2217/**
2218 * hdd_perform_roam_set_key_complete() - perform set key complete
2219 * @pAdapter: pointer to adapter
2220 *
2221 * Return: none
2222 */
2223void hdd_perform_roam_set_key_complete(hdd_adapter_t *pAdapter)
2224{
Anurag Chouhanf04e84f2016-03-03 10:12:12 +05302225 QDF_STATUS qdf_ret_status = QDF_STATUS_SUCCESS;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002226 hdd_station_ctx_t *pHddStaCtx = WLAN_HDD_GET_STATION_CTX_PTR(pAdapter);
2227 tCsrRoamInfo roamInfo;
2228 roamInfo.fAuthRequired = false;
Anurag Chouhan600c3a02016-03-01 10:33:54 +05302229 qdf_mem_copy(roamInfo.bssid.bytes,
Anurag Chouhan6d760662016-02-20 16:05:43 +05302230 pHddStaCtx->roam_info.bssid, QDF_MAC_ADDR_SIZE);
Anurag Chouhan600c3a02016-03-01 10:33:54 +05302231 qdf_mem_copy(roamInfo.peerMac.bytes,
Anurag Chouhan6d760662016-02-20 16:05:43 +05302232 pHddStaCtx->roam_info.peerMac, QDF_MAC_ADDR_SIZE);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002233
Anurag Chouhanf04e84f2016-03-03 10:12:12 +05302234 qdf_ret_status =
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002235 hdd_roam_set_key_complete_handler(pAdapter,
2236 &roamInfo,
2237 pHddStaCtx->roam_info.roamId,
2238 pHddStaCtx->roam_info.roamStatus,
2239 eCSR_ROAM_RESULT_AUTHENTICATED);
Anurag Chouhanf04e84f2016-03-03 10:12:12 +05302240 if (qdf_ret_status != QDF_STATUS_SUCCESS)
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07002241 hdd_err("Set Key complete failure");
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002242
2243 pHddStaCtx->roam_info.deferKeyComplete = false;
2244}
2245
2246/**
2247 * hdd_association_completion_handler() - association completion handler
2248 * @pAdapter: pointer to adapter
2249 * @pRoamInfo: pointer to roam info
2250 * @roamId: roam id
2251 * @roamStatus: roam status
2252 * @roamResult: roam result
2253 *
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05302254 * Return: QDF_STATUS enumeration
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002255 */
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05302256static QDF_STATUS hdd_association_completion_handler(hdd_adapter_t *pAdapter,
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002257 tCsrRoamInfo *pRoamInfo,
2258 uint32_t roamId,
2259 eRoamCmdStatus roamStatus,
2260 eCsrRoamResult roamResult)
2261{
2262 struct net_device *dev = pAdapter->dev;
2263 hdd_context_t *pHddCtx = WLAN_HDD_GET_CTX(pAdapter);
2264 hdd_station_ctx_t *pHddStaCtx = WLAN_HDD_GET_STATION_CTX_PTR(pAdapter);
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05302265 QDF_STATUS qdf_status = QDF_STATUS_E_FAILURE;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002266 uint8_t reqRsnIe[DOT11F_IE_RSN_MAX_LEN];
2267 uint32_t reqRsnLength = DOT11F_IE_RSN_MAX_LEN;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002268 int ft_carrier_on = false;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002269 bool hddDisconInProgress = false;
2270 unsigned long rc;
2271
2272 if (!pHddCtx) {
2273 hdd_err("HDD context is NULL");
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05302274 return QDF_STATUS_E_FAILURE;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002275 }
2276
Anurag Chouhan2c4e0a12016-09-12 14:52:45 +05302277 /* validate config */
2278 if (!pHddCtx->config) {
2279 hdd_err("config is NULL");
2280 return QDF_STATUS_E_NULL_VALUE;
2281 }
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002282 /* HDD has initiated disconnect, do not send connect result indication
2283 * to kernel as it will be handled by __cfg80211_disconnect.
2284 */
Edhar, Mahesh Kumar732f6982016-07-01 11:23:06 +05302285 if (((eConnectionState_Disconnecting ==
2286 pHddStaCtx->conn_info.connState) ||
2287 (eConnectionState_NotConnected ==
2288 pHddStaCtx->conn_info.connState)) &&
2289 ((eCSR_ROAM_RESULT_ASSOCIATED == roamResult) ||
2290 (eCSR_ROAM_ASSOCIATION_FAILURE == roamStatus))) {
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07002291 hdd_info("Disconnect from HDD in progress");
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002292 hddDisconInProgress = true;
2293 }
2294
2295 if (eCSR_ROAM_RESULT_ASSOCIATED == roamResult) {
2296 if (NULL == pRoamInfo) {
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07002297 hdd_err("pRoamInfo is NULL");
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05302298 return QDF_STATUS_E_FAILURE;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002299 }
2300 if (!hddDisconInProgress) {
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002301 hdd_conn_set_connection_state(pAdapter,
2302 eConnectionState_Associated);
2303 }
2304 /* Save the connection info from CSR... */
2305 hdd_conn_save_connect_info(pAdapter, pRoamInfo,
2306 eCSR_BSS_TYPE_INFRASTRUCTURE);
Gupta, Kapil4cb1d7d2016-04-16 18:16:25 -07002307
2308 if (hdd_add_beacon_filter(pAdapter) != 0)
2309 hdd_err("hdd_add_beacon_filter() failed");
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002310#ifdef FEATURE_WLAN_WAPI
2311 if (pRoamInfo->u.pConnectedProfile->AuthType ==
2312 eCSR_AUTH_TYPE_WAPI_WAI_CERTIFICATE
2313 || pRoamInfo->u.pConnectedProfile->AuthType ==
2314 eCSR_AUTH_TYPE_WAPI_WAI_PSK) {
2315 pAdapter->wapi_info.fIsWapiSta = 1;
2316 } else {
2317 pAdapter->wapi_info.fIsWapiSta = 0;
2318 }
2319#endif /* FEATURE_WLAN_WAPI */
2320
2321 /* Indicate 'connect' status to user space */
2322 hdd_send_association_event(dev, pRoamInfo);
2323
Tushnim Bhattacharyyaca50b322015-12-28 17:14:36 -08002324 if (cds_is_mcc_in_24G()) {
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002325 if (pHddCtx->miracast_value)
2326 cds_set_mas(pAdapter, pHddCtx->miracast_value);
2327 }
2328
2329 /* Initialize the Linkup event completion variable */
2330 INIT_COMPLETION(pAdapter->linkup_event_var);
2331
2332 /*
2333 * Sometimes Switching ON the Carrier is taking time to activate
2334 * the device properly. Before allowing any packet to go up to
2335 * the application, device activation has to be ensured for
2336 * proper queue mapping by the kernel. we have registered net
2337 * device notifier for device change notification. With this we
2338 * will come to know that the device is getting
2339 * activated properly.
2340 */
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002341 if (pHddStaCtx->ft_carrier_on == false) {
Deepak Dhamdherea2df6bb2015-10-29 15:11:06 -07002342 /*
2343 * Enable Linkup Event Servicing which allows the net
2344 * device notifier to set the linkup event variable.
2345 */
2346 pAdapter->isLinkUpSvcNeeded = true;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002347
Deepak Dhamdherea2df6bb2015-10-29 15:11:06 -07002348 /* Switch on the Carrier to activate the device */
2349 wlan_hdd_netif_queue_control(pAdapter,
2350 WLAN_NETIF_CARRIER_ON,
2351 WLAN_CONTROL_PATH);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002352
Deepak Dhamdherea2df6bb2015-10-29 15:11:06 -07002353 /*
2354 * Wait for the Link to up to ensure all the queues
2355 * are set properly by the kernel.
2356 */
2357 rc = wait_for_completion_timeout(
2358 &pAdapter->linkup_event_var,
2359 msecs_to_jiffies(ASSOC_LINKUP_TIMEOUT)
2360 );
2361 if (!rc)
2362 hdd_warn("Warning:ASSOC_LINKUP_TIMEOUT");
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002363
Deepak Dhamdherea2df6bb2015-10-29 15:11:06 -07002364 /*
2365 * Disable Linkup Event Servicing - no more service
2366 * required from the net device notifier call.
2367 */
2368 pAdapter->isLinkUpSvcNeeded = false;
2369 } else {
2370 pHddStaCtx->ft_carrier_on = false;
2371 ft_carrier_on = true;
2372 }
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002373 if ((WLAN_MAX_STA_COUNT + 3) > pRoamInfo->staId)
2374 pHddCtx->sta_to_adapter[pRoamInfo->staId] = pAdapter;
2375 else
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07002376 hdd_err("Wrong Staid: %d", pRoamInfo->staId);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002377
2378 pHddCtx->sta_to_adapter[pRoamInfo->staId] = pAdapter;
2379
2380 if (hdd_ipa_is_enabled(pHddCtx))
2381 hdd_ipa_wlan_evt(pAdapter, pRoamInfo->staId,
Mohit Khannafa99aea2016-05-12 21:43:13 -07002382 HDD_IPA_STA_CONNECT,
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002383 pRoamInfo->bssid.bytes);
2384
2385#ifdef FEATURE_WLAN_AUTO_SHUTDOWN
2386 wlan_hdd_auto_shutdown_enable(pHddCtx, false);
2387#endif
2388
Chandrasekaran Manishekar068e25e2016-03-07 11:51:07 +05302389 hdd_info("check for SAP restart");
Naveen Rawat8cc23b02016-07-14 12:22:56 -07002390 cds_check_concurrent_intf_and_restart_sap(pAdapter);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002391
Nirav Shah1da77682016-05-03 20:16:39 +05302392 DPTRACE(qdf_dp_trace_mgmt_pkt(QDF_DP_TRACE_MGMT_PACKET_RECORD,
2393 pAdapter->sessionId,
2394 QDF_PROTO_TYPE_MGMT, QDF_PROTO_MGMT_ASSOC));
2395
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002396 /*
2397 * For reassoc, the station is already registered, all we need
2398 * is to change the state of the STA in TL.
2399 * If authentication is required (WPA/WPA2/DWEP), change TL to
2400 * CONNECTED instead of AUTHENTICATED.
2401 */
2402 if (!pRoamInfo->fReassocReq) {
2403 struct cfg80211_bss *bss;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002404 u8 *pFTAssocRsp = NULL;
2405 unsigned int assocRsplen = 0;
2406 u8 *pFTAssocReq = NULL;
2407 unsigned int assocReqlen = 0;
2408 struct ieee80211_channel *chan;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002409 uint8_t rspRsnIe[DOT11F_IE_RSN_MAX_LEN];
2410 uint32_t rspRsnLength = DOT11F_IE_RSN_MAX_LEN;
2411
2412 /* add bss_id to cfg80211 data base */
2413 bss =
2414 wlan_hdd_cfg80211_update_bss_db(pAdapter,
2415 pRoamInfo);
2416 if (NULL == bss) {
Abhishek Singhcdcc5e72016-09-13 12:45:10 +05302417 hdd_err("wlan: Not able to create BSS entry");
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002418 wlan_hdd_netif_queue_control(pAdapter,
2419 WLAN_NETIF_CARRIER_OFF,
2420 WLAN_CONTROL_PATH);
Abhishek Singhcdcc5e72016-09-13 12:45:10 +05302421 if (!hddDisconInProgress) {
2422 /*
2423 * Here driver was not able to add bss
2424 * in cfg80211 database this can happen
2425 * if connected channel is not valid,
2426 * i.e reg domain was changed during
2427 * connection. Queue disconnect for the
2428 * session if disconnect is not in
2429 * progress.
2430 */
2431 hdd_err("Disconnecting...");
2432 sme_roam_disconnect(
2433 WLAN_HDD_GET_HAL_CTX(pAdapter),
2434 pAdapter->sessionId,
2435 eCSR_DISCONNECT_REASON_UNSPECIFIED);
2436 }
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05302437 return QDF_STATUS_E_FAILURE;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002438 }
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002439 if (pRoamInfo->u.pConnectedProfile->AuthType ==
2440 eCSR_AUTH_TYPE_FT_RSN
2441 || pRoamInfo->u.pConnectedProfile->AuthType ==
2442 eCSR_AUTH_TYPE_FT_RSN_PSK) {
2443
2444 /* Association Response */
2445 pFTAssocRsp =
2446 (u8 *) (pRoamInfo->pbFrames +
2447 pRoamInfo->nBeaconLength +
2448 pRoamInfo->nAssocReqLength);
2449 if (pFTAssocRsp != NULL) {
2450 /*
2451 * pFTAssocRsp needs to point to the IEs
2452 */
2453 pFTAssocRsp += FT_ASSOC_RSP_IES_OFFSET;
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07002454 hdd_info("AssocRsp is now at %02x%02x",
2455 (unsigned int)pFTAssocRsp[0],
2456 (unsigned int)pFTAssocRsp[1]);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002457 assocRsplen =
2458 pRoamInfo->nAssocRspLength -
2459 FT_ASSOC_RSP_IES_OFFSET;
2460 } else {
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07002461 hdd_err("AssocRsp is NULL");
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002462 assocRsplen = 0;
2463 }
2464
2465 /* Association Request */
2466 pFTAssocReq = (u8 *) (pRoamInfo->pbFrames +
2467 pRoamInfo->nBeaconLength);
2468 if (pFTAssocReq != NULL) {
2469 if (!ft_carrier_on) {
2470 /*
2471 * pFTAssocReq needs to point to
2472 * the IEs
2473 */
2474 pFTAssocReq +=
2475 FT_ASSOC_REQ_IES_OFFSET;
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07002476 hdd_info("pFTAssocReq is now at %02x%02x",
2477 (unsigned int)
2478 pFTAssocReq[0],
2479 (unsigned int)
2480 pFTAssocReq[1]);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002481 assocReqlen =
2482 pRoamInfo->nAssocReqLength -
2483 FT_ASSOC_REQ_IES_OFFSET;
2484 } else {
2485 /*
2486 * This should contain only the
2487 * FTIEs
2488 */
2489 assocReqlen =
2490 pRoamInfo->nAssocReqLength;
2491 }
2492 } else {
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07002493 hdd_err("AssocReq is NULL");
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002494 assocReqlen = 0;
2495 }
2496
2497 if (ft_carrier_on) {
2498 if (!hddDisconInProgress) {
2499 /*
2500 * After roaming is completed,
2501 * active session count is
2502 * incremented as a part of
2503 * connect indication but
2504 * effectively the active
2505 * session count should still
2506 * be the same and hence upon
2507 * successful reassoc
2508 * decrement the active session
2509 * count here.
2510 */
Varun Reddy Yeturud5939f82015-12-24 18:14:02 -08002511 if (!hdd_is_roam_sync_in_progress
2512 (pRoamInfo))
2513 cds_decr_session_set_pcl
2514 (pAdapter->device_mode,
2515 pAdapter->sessionId);
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07002516 hdd_info("ft_carrier_on is %d, sending roamed indication",
2517 ft_carrier_on);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002518 chan =
2519 ieee80211_get_channel
2520 (pAdapter->wdev.wiphy,
2521 (int)pRoamInfo->pBssDesc->
2522 channelId);
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07002523 hdd_info(
2524 "assocReqlen %d assocRsplen %d",
2525 assocReqlen,
2526 assocRsplen);
Naveen Rawat14298b92015-11-25 16:27:41 -08002527
2528 hdd_notice(
2529 "Reassoc Req IE dump");
Anurag Chouhanb2dc16f2016-02-25 11:47:37 +05302530 QDF_TRACE_HEX_DUMP(
Anurag Chouhan6d760662016-02-20 16:05:43 +05302531 QDF_MODULE_ID_HDD,
Anurag Chouhanb2dc16f2016-02-25 11:47:37 +05302532 QDF_TRACE_LEVEL_DEBUG,
Naveen Rawat14298b92015-11-25 16:27:41 -08002533 pFTAssocReq,
2534 assocReqlen);
2535
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002536 cfg80211_roamed(dev, chan,
2537 pRoamInfo->
2538 bssid.bytes,
2539 pFTAssocReq,
2540 assocReqlen,
2541 pFTAssocRsp,
2542 assocRsplen,
2543 GFP_KERNEL);
Prashanth Bhattabfc25292015-11-05 11:16:21 -08002544 wlan_hdd_send_roam_auth_event(
2545 pHddCtx,
2546 pRoamInfo->bssid.bytes,
2547 pFTAssocReq,
2548 assocReqlen,
2549 pFTAssocRsp,
2550 assocRsplen,
2551 pRoamInfo);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002552 }
2553 if (sme_get_ftptk_state
2554 (WLAN_HDD_GET_HAL_CTX(pAdapter),
2555 pAdapter->sessionId)) {
2556 sme_set_ftptk_state
2557 (WLAN_HDD_GET_HAL_CTX
2558 (pAdapter),
2559 pAdapter->sessionId,
2560 false);
2561 pRoamInfo->fAuthRequired =
2562 false;
2563
Anurag Chouhan600c3a02016-03-01 10:33:54 +05302564 qdf_mem_copy(pHddStaCtx->
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002565 roam_info.bssid,
2566 pRoamInfo->bssid.bytes,
Anurag Chouhan6d760662016-02-20 16:05:43 +05302567 QDF_MAC_ADDR_SIZE);
Anurag Chouhan600c3a02016-03-01 10:33:54 +05302568 qdf_mem_copy(pHddStaCtx->
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002569 roam_info.peerMac,
2570 pRoamInfo->peerMac.bytes,
Anurag Chouhan6d760662016-02-20 16:05:43 +05302571 QDF_MAC_ADDR_SIZE);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002572 pHddStaCtx->roam_info.roamId =
2573 roamId;
2574 pHddStaCtx->roam_info.
2575 roamStatus = roamStatus;
2576 pHddStaCtx->roam_info.
2577 deferKeyComplete = true;
2578 }
2579 } else if (!hddDisconInProgress) {
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07002580 hdd_info("ft_carrier_on is %d, sending connect indication",
2581 ft_carrier_on);
Anurag Chouhanc4092922016-09-08 15:56:11 +05302582 hdd_connect_result(dev,
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002583 pRoamInfo->
2584 bssid.bytes,
Anurag Chouhanc4092922016-09-08 15:56:11 +05302585 pRoamInfo,
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002586 pFTAssocReq,
2587 assocReqlen,
2588 pFTAssocRsp,
2589 assocRsplen,
2590 WLAN_STATUS_SUCCESS,
Abhishek Singha84d3952016-09-13 13:45:05 +05302591 GFP_KERNEL,
2592 false);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002593 }
Deepak Dhamdhere9f09e752016-01-09 23:17:25 -08002594 } else {
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002595 /*
2596 * wpa supplicant expecting WPA/RSN IE in
2597 * connect result.
2598 */
2599 csr_roam_get_wpa_rsn_req_ie(WLAN_HDD_GET_HAL_CTX
2600 (pAdapter),
2601 pAdapter->sessionId,
2602 &reqRsnLength,
2603 reqRsnIe);
2604
2605 csr_roam_get_wpa_rsn_rsp_ie(WLAN_HDD_GET_HAL_CTX
2606 (pAdapter),
2607 pAdapter->sessionId,
2608 &rspRsnLength,
2609 rspRsnIe);
2610 if (!hddDisconInProgress) {
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002611 if (ft_carrier_on)
2612 hdd_send_re_assoc_event(dev,
2613 pAdapter,
2614 pRoamInfo,
2615 reqRsnIe,
2616 reqRsnLength);
Deepak Dhamdherea2df6bb2015-10-29 15:11:06 -07002617 else {
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07002618 hdd_info("sending connect indication to nl80211:for bssid "
2619 MAC_ADDRESS_STR
2620 " result:%d and Status:%d",
2621 MAC_ADDR_ARRAY
2622 (pRoamInfo->bssid.bytes),
2623 roamResult, roamStatus);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002624
2625 /* inform connect result to nl80211 */
Anurag Chouhanc4092922016-09-08 15:56:11 +05302626 hdd_connect_result(dev,
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002627 pRoamInfo->
2628 bssid.bytes,
Anurag Chouhanc4092922016-09-08 15:56:11 +05302629 pRoamInfo,
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002630 reqRsnIe,
2631 reqRsnLength,
2632 rspRsnIe,
2633 rspRsnLength,
2634 WLAN_STATUS_SUCCESS,
Abhishek Singha84d3952016-09-13 13:45:05 +05302635 GFP_KERNEL,
2636 false);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002637 }
2638 }
2639 }
2640 if (!hddDisconInProgress) {
2641 cfg80211_put_bss(
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002642 pHddCtx->wiphy,
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002643 bss);
2644
2645 /*
2646 * Perform any WMM-related association
2647 * processing.
2648 */
2649 hdd_wmm_assoc(pAdapter, pRoamInfo,
2650 eCSR_BSS_TYPE_INFRASTRUCTURE);
2651
2652 /*
2653 * Start the Queue - Start tx queues before
2654 * hdd_roam_register_sta, since
2655 * hdd_roam_register_sta will flush any cached
2656 * data frames immediately.
2657 */
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07002658 hdd_info("Enabling queues");
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002659 wlan_hdd_netif_queue_control(pAdapter,
2660 WLAN_WAKE_ALL_NETIF_QUEUE,
2661 WLAN_CONTROL_PATH);
2662
2663 /*
2664 * Register the Station with TL after associated
2665 */
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05302666 qdf_status = hdd_roam_register_sta(pAdapter,
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002667 pRoamInfo,
2668 pHddStaCtx->
2669 conn_info.
2670 staId[0],
2671 NULL,
2672 pRoamInfo->
2673 pBssDesc);
2674 }
2675 } else {
2676 /*
2677 * wpa supplicant expecting WPA/RSN IE in connect result
2678 * in case of reassociation also need to indicate it to
2679 * supplicant.
2680 */
2681 csr_roam_get_wpa_rsn_req_ie(
2682 WLAN_HDD_GET_HAL_CTX(pAdapter),
2683 pAdapter->sessionId,
2684 &reqRsnLength, reqRsnIe);
2685
2686 hdd_send_re_assoc_event(dev, pAdapter, pRoamInfo,
2687 reqRsnIe, reqRsnLength);
2688 /* Reassoc successfully */
2689 if (pRoamInfo->fAuthRequired) {
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05302690 qdf_status =
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002691 hdd_change_peer_state(pAdapter,
2692 pHddStaCtx->conn_info.staId[0],
Dhanashri Atreb08959a2016-03-01 17:28:03 -08002693 OL_TXRX_PEER_STATE_CONN,
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002694#ifdef WLAN_FEATURE_ROAM_OFFLOAD
2695 pRoamInfo->roamSynchInProgress
2696#else
2697 false
2698#endif
2699 );
2700 hdd_conn_set_authenticated(pAdapter, false);
2701 } else {
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07002702 hdd_info("staId: %d Changing TL state to AUTHENTICATED",
2703 pHddStaCtx->conn_info.staId[0]);
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05302704 qdf_status =
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002705 hdd_change_peer_state(pAdapter,
2706 pHddStaCtx->conn_info.staId[0],
Dhanashri Atreb08959a2016-03-01 17:28:03 -08002707 OL_TXRX_PEER_STATE_AUTH,
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002708#ifdef WLAN_FEATURE_ROAM_OFFLOAD
2709 pRoamInfo->roamSynchInProgress
2710#else
2711 false
2712#endif
2713 );
2714 hdd_conn_set_authenticated(pAdapter, true);
2715 }
2716
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05302717 if (QDF_IS_STATUS_SUCCESS(qdf_status)) {
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002718 /*
2719 * Perform any WMM-related association
2720 * processing
2721 */
2722 hdd_wmm_assoc(pAdapter, pRoamInfo,
2723 eCSR_BSS_TYPE_INFRASTRUCTURE);
2724 }
2725
2726 /* Start the tx queues */
2727#ifdef WLAN_FEATURE_ROAM_OFFLOAD
2728 if (pRoamInfo->roamSynchInProgress)
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07002729 hdd_info("LFR3:netif_tx_wake_all_queues");
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002730#endif
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07002731 hdd_info("Enabling queues");
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002732 wlan_hdd_netif_queue_control(pAdapter,
2733 WLAN_WAKE_ALL_NETIF_QUEUE,
2734 WLAN_CONTROL_PATH);
2735 }
2736
Padma, Santhosh Kumar724f63d2016-08-09 16:04:31 +05302737#ifdef FEATURE_WLAN_TDLS
2738 wlan_hdd_tdls_connection_callback(pAdapter);
2739#endif
2740
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05302741 if (!QDF_IS_STATUS_SUCCESS(qdf_status)) {
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07002742 hdd_err("STA register with TL failed. status(=%d) [%08X]",
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05302743 qdf_status, qdf_status);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002744 }
2745#ifdef WLAN_FEATURE_11W
Anurag Chouhan600c3a02016-03-01 10:33:54 +05302746 qdf_mem_zero(&pAdapter->hdd_stats.hddPmfStats,
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002747 sizeof(pAdapter->hdd_stats.hddPmfStats));
2748#endif
2749 } else {
Abhishek Singha84d3952016-09-13 13:45:05 +05302750 bool connect_timeout = false;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002751 hdd_wext_state_t *pWextState =
2752 WLAN_HDD_GET_WEXT_STATE_PTR(pAdapter);
2753 if (pRoamInfo)
Gowri, Deepthi07ac9932016-09-02 15:19:32 +05302754 hdd_err("wlan: connection failed with " MAC_ADDRESS_STR
2755 " result:%d and Status:%d",
2756 MAC_ADDR_ARRAY(pRoamInfo->bssid.bytes),
2757 roamResult, roamStatus);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002758 else
Gowri, Deepthi07ac9932016-09-02 15:19:32 +05302759 hdd_err("wlan: connection failed with " MAC_ADDRESS_STR
2760 " result:%d and Status:%d",
2761 MAC_ADDR_ARRAY(pWextState->req_bssId.bytes),
2762 roamResult, roamStatus);
Abhishek Singhc9941602016-08-09 16:06:22 +05302763
2764 if ((eCSR_ROAM_RESULT_SCAN_FOR_SSID_FAILURE == roamResult) ||
2765 (pRoamInfo &&
2766 ((eSIR_SME_JOIN_TIMEOUT_RESULT_CODE ==
2767 pRoamInfo->statusCode) ||
2768 (eSIR_SME_AUTH_TIMEOUT_RESULT_CODE ==
2769 pRoamInfo->statusCode) ||
2770 (eSIR_SME_ASSOC_TIMEOUT_RESULT_CODE ==
2771 pRoamInfo->statusCode)))) {
2772 wlan_hdd_cfg80211_update_bss_list(pAdapter,
2773 pRoamInfo ?
2774 pRoamInfo->bssid.bytes :
2775 pWextState->req_bssId.bytes);
2776 sme_remove_bssid_from_scan_list(pHddCtx->hHal,
2777 pRoamInfo ?
2778 pRoamInfo->bssid.bytes :
2779 pWextState->req_bssId.bytes);
Abhishek Singha84d3952016-09-13 13:45:05 +05302780 connect_timeout = true;
Abhishek Singhc9941602016-08-09 16:06:22 +05302781 }
2782
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002783 /*
2784 * CR465478: Only send up a connection failure result when CSR
2785 * has completed operation - with a ASSOCIATION_FAILURE status.
2786 */
2787 if (eCSR_ROAM_ASSOCIATION_FAILURE == roamStatus
2788 && !hddDisconInProgress) {
Anurag Chouhan5de8d172016-07-13 14:44:28 +05302789 if (pRoamInfo) {
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07002790 hdd_err("send connect failure to nl80211: for bssid "
2791 MAC_ADDRESS_STR
2792 " result:%d and Status:%d reasoncode %d",
2793 MAC_ADDR_ARRAY(pRoamInfo->bssid.bytes),
2794 roamResult, roamStatus,
2795 pRoamInfo->reasonCode);
Anurag Chouhan5de8d172016-07-13 14:44:28 +05302796 pHddStaCtx->conn_info.assoc_status_code =
2797 pRoamInfo->statusCode;
2798 }
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002799 else
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07002800 hdd_err("connect failed: for bssid "
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002801 MAC_ADDRESS_STR
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07002802 " result:%d and Status:%d ",
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002803 MAC_ADDR_ARRAY(pWextState->req_bssId.bytes),
2804 roamResult, roamStatus);
2805
Himanshu Agarwal0527e8f2016-08-11 14:58:34 +05302806 hdd_err("Invoking packetdump deregistration API");
2807 wlan_deregister_txrx_packetdump();
2808
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002809 /* inform association failure event to nl80211 */
2810 if (eCSR_ROAM_RESULT_ASSOC_FAIL_CON_CHANNEL ==
2811 roamResult) {
2812 if (pRoamInfo)
Anurag Chouhanc4092922016-09-08 15:56:11 +05302813 hdd_connect_result(dev,
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002814 pRoamInfo->bssid.bytes,
Anurag Chouhanc4092922016-09-08 15:56:11 +05302815 NULL, NULL, 0, NULL, 0,
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002816 WLAN_STATUS_ASSOC_DENIED_UNSPEC,
Abhishek Singha84d3952016-09-13 13:45:05 +05302817 GFP_KERNEL,
2818 connect_timeout);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002819 else
Anurag Chouhanc4092922016-09-08 15:56:11 +05302820 hdd_connect_result(dev,
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002821 pWextState->req_bssId.bytes,
Anurag Chouhanc4092922016-09-08 15:56:11 +05302822 NULL, NULL, 0, NULL, 0,
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002823 WLAN_STATUS_ASSOC_DENIED_UNSPEC,
Abhishek Singha84d3952016-09-13 13:45:05 +05302824 GFP_KERNEL,
2825 connect_timeout);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002826 } else {
2827 if (pRoamInfo) {
2828 eCsrAuthType authType =
2829 pWextState->roamProfile.AuthType.
2830 authType[0];
Abhishek Singhac2be142015-12-03 16:16:25 +05302831 eCsrEncryptionType encryption_type =
2832 pWextState->roamProfile.
2833 EncryptionType.encryptionType[0];
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002834 bool isWep =
Abhishek Singhac2be142015-12-03 16:16:25 +05302835 (((authType ==
2836 eCSR_AUTH_TYPE_OPEN_SYSTEM) ||
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002837 (authType ==
Abhishek Singhac2be142015-12-03 16:16:25 +05302838 eCSR_AUTH_TYPE_SHARED_KEY)) &&
2839 ((encryption_type ==
2840 eCSR_ENCRYPT_TYPE_WEP40) ||
2841 (encryption_type ==
2842 eCSR_ENCRYPT_TYPE_WEP104) ||
2843 (encryption_type ==
2844 eCSR_ENCRYPT_TYPE_WEP40_STATICKEY) ||
2845 (encryption_type ==
2846 eCSR_ENCRYPT_TYPE_WEP104_STATICKEY)));
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002847 /*
2848 * In case of OPEN-WEP or SHARED-WEP
2849 * authentication, send exact protocol
2850 * reason code. This enables user
2851 * applications to reconnect the station
2852 * with correct configuration.
2853 */
Anurag Chouhanc4092922016-09-08 15:56:11 +05302854 hdd_connect_result(dev,
2855 pRoamInfo->bssid.bytes,
2856 NULL, NULL, 0, NULL, 0,
Abhishek Singhac2be142015-12-03 16:16:25 +05302857 (isWep &&
2858 pRoamInfo->reasonCode) ?
2859 pRoamInfo->reasonCode :
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002860 WLAN_STATUS_UNSPECIFIED_FAILURE,
Abhishek Singha84d3952016-09-13 13:45:05 +05302861 GFP_KERNEL,
2862 connect_timeout);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002863 } else
Anurag Chouhanc4092922016-09-08 15:56:11 +05302864 hdd_connect_result(dev,
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002865 pWextState->req_bssId.bytes,
Anurag Chouhanc4092922016-09-08 15:56:11 +05302866 NULL, NULL, 0, NULL, 0,
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002867 WLAN_STATUS_UNSPECIFIED_FAILURE,
Abhishek Singha84d3952016-09-13 13:45:05 +05302868 GFP_KERNEL,
2869 connect_timeout);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002870 }
Abhishek Singhac2be142015-12-03 16:16:25 +05302871 hdd_clear_roam_profile_ie(pAdapter);
Sandeep Puligilla0241f012016-07-21 10:58:53 -07002872 } else if ((eCSR_ROAM_CANCELLED == roamStatus
2873 && !hddDisconInProgress)) {
Abhishek Singha84d3952016-09-13 13:45:05 +05302874 hdd_connect_result(dev,
Sandeep Puligilla0241f012016-07-21 10:58:53 -07002875 pWextState->req_bssId.bytes,
Abhishek Singha84d3952016-09-13 13:45:05 +05302876 NULL, NULL, 0, NULL, 0,
Sandeep Puligilla0241f012016-07-21 10:58:53 -07002877 WLAN_STATUS_UNSPECIFIED_FAILURE,
Abhishek Singha84d3952016-09-13 13:45:05 +05302878 GFP_KERNEL,
2879 connect_timeout);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002880 }
2881
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002882 /*
2883 * Set connection state to eConnectionState_NotConnected only
2884 * when CSR has completed operation - with a
Sandeep Puligilla0241f012016-07-21 10:58:53 -07002885 * ASSOCIATION_FAILURE or eCSR_ROAM_CANCELLED status.
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002886 */
Sandeep Puligilla0241f012016-07-21 10:58:53 -07002887 if (((eCSR_ROAM_ASSOCIATION_FAILURE == roamStatus) ||
2888 (eCSR_ROAM_CANCELLED == roamStatus))
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002889 && !hddDisconInProgress) {
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002890 hdd_conn_set_connection_state(pAdapter,
2891 eConnectionState_NotConnected);
2892 }
2893 hdd_wmm_init(pAdapter);
2894
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07002895 hdd_info("Disabling queues");
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002896 wlan_hdd_netif_queue_control(pAdapter,
2897 WLAN_NETIF_TX_DISABLE_N_CARRIER,
2898 WLAN_CONTROL_PATH);
2899 }
2900
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05302901 if (QDF_STATUS_SUCCESS != cds_check_and_restart_sap(
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002902 roamResult, pHddStaCtx))
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05302903 return QDF_STATUS_E_FAILURE;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002904
Govind Singh24db1ed2015-12-18 15:54:59 +05302905 if (NULL != pRoamInfo && NULL != pRoamInfo->pBssDesc) {
2906 cds_force_sap_on_scc(roamResult,
2907 pRoamInfo->pBssDesc->channelId);
2908 } else {
2909 hdd_err("pRoamInfo profile is not set properly");
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05302910 return QDF_STATUS_E_FAILURE;
Govind Singh24db1ed2015-12-18 15:54:59 +05302911 }
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002912
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05302913 return QDF_STATUS_SUCCESS;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002914}
2915
2916/**
2917 * hdd_roam_ibss_indication_handler() - update the status of the IBSS
2918 * @pAdapter: pointer to adapter
2919 * @pRoamInfo: pointer to roam info
2920 * @roamId: roam id
2921 * @roamStatus: roam status
2922 * @roamResult: roam result
2923 *
2924 * Here we update the status of the Ibss when we receive information that we
2925 * have started/joined an ibss session.
2926 *
2927 * Return: none
2928 */
2929static void hdd_roam_ibss_indication_handler(hdd_adapter_t *pAdapter,
2930 tCsrRoamInfo *pRoamInfo,
2931 uint32_t roamId,
2932 eRoamCmdStatus roamStatus,
2933 eCsrRoamResult roamResult)
2934{
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07002935 hdd_info("%s: id %d, status %d, result %d",
2936 pAdapter->dev->name, roamId,
2937 roamStatus, roamResult);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002938
2939 switch (roamResult) {
2940 /* both IBSS Started and IBSS Join should come in here. */
2941 case eCSR_ROAM_RESULT_IBSS_STARTED:
2942 case eCSR_ROAM_RESULT_IBSS_JOIN_SUCCESS:
2943 case eCSR_ROAM_RESULT_IBSS_COALESCED:
2944 {
2945 hdd_context_t *pHddCtx =
2946 (hdd_context_t *) pAdapter->pHddCtx;
Chandrasekaran, Manishekar34e325a2015-12-18 12:07:22 +05302947 hdd_station_ctx_t *hdd_sta_ctx =
2948 WLAN_HDD_GET_STATION_CTX_PTR(pAdapter);
Anurag Chouhan6d760662016-02-20 16:05:43 +05302949 struct qdf_mac_addr broadcastMacAddr =
2950 QDF_MAC_ADDR_BROADCAST_INITIALIZER;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002951
2952 if (NULL == pRoamInfo) {
Anurag Chouhanb2dc16f2016-02-25 11:47:37 +05302953 QDF_ASSERT(0);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002954 return;
2955 }
2956
2957 /* When IBSS Started comes from CSR, we need to move
2958 * connection state to IBSS Disconnected (meaning no peers
2959 * are in the IBSS).
2960 */
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002961 hdd_conn_set_connection_state(pAdapter,
2962 eConnectionState_IbssDisconnected);
2963 /* notify wmm */
2964 hdd_wmm_connect(pAdapter, pRoamInfo,
2965 eCSR_BSS_TYPE_IBSS);
Chandrasekaran, Manishekar34e325a2015-12-18 12:07:22 +05302966
Rakesh Sunkicf1c9ab2016-08-25 14:11:25 -07002967 hdd_sta_ctx->broadcast_staid = pRoamInfo->staId;
Chandrasekaran, Manishekar34e325a2015-12-18 12:07:22 +05302968
2969 pHddCtx->sta_to_adapter[pRoamInfo->staId] =
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002970 pAdapter;
2971 hdd_roam_register_sta(pAdapter, pRoamInfo,
Chandrasekaran, Manishekar34e325a2015-12-18 12:07:22 +05302972 pRoamInfo->staId,
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002973 &broadcastMacAddr,
2974 pRoamInfo->pBssDesc);
2975
2976 if (pRoamInfo->pBssDesc) {
2977 struct cfg80211_bss *bss;
2978#if (LINUX_VERSION_CODE >= KERNEL_VERSION(3, 15, 0))
2979 struct ieee80211_channel *chan;
2980 int chan_no;
2981 unsigned int freq;
2982#endif
2983 /* we created the IBSS, notify supplicant */
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07002984 hdd_info("%s: created ibss " MAC_ADDRESS_STR,
2985 pAdapter->dev->name,
2986 MAC_ADDR_ARRAY(
2987 pRoamInfo->pBssDesc->bssId));
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002988
2989 /* we must first give cfg80211 the BSS information */
2990 bss = wlan_hdd_cfg80211_update_bss_db(pAdapter,
2991 pRoamInfo);
2992 if (NULL == bss) {
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07002993 hdd_err("%s: unable to create IBSS entry",
2994 pAdapter->dev->name);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002995 return;
2996 }
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07002997 hdd_info("Enabling queues");
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002998 wlan_hdd_netif_queue_control(pAdapter,
2999 WLAN_START_ALL_NETIF_QUEUE_N_CARRIER,
3000 WLAN_CONTROL_PATH);
3001
3002#if (LINUX_VERSION_CODE >= KERNEL_VERSION(3, 15, 0))
3003 chan_no = pRoamInfo->pBssDesc->channelId;
3004
3005 if (chan_no <= 14)
3006 freq = ieee80211_channel_to_frequency(chan_no,
Dustin Browna30892e2016-10-12 17:28:36 -07003007 NL80211_BAND_2GHZ);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003008 else
3009 freq = ieee80211_channel_to_frequency(chan_no,
Dustin Browna30892e2016-10-12 17:28:36 -07003010 NL80211_BAND_5GHZ);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003011
3012 chan = ieee80211_get_channel(pAdapter->wdev.wiphy, freq);
3013
3014 if (chan)
3015 cfg80211_ibss_joined(pAdapter->dev,
3016 bss->bssid, chan,
3017 GFP_KERNEL);
3018 else
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07003019 hdd_err("%s: chanId: %d, can't find channel",
3020 pAdapter->dev->name,
3021 (int)pRoamInfo->pBssDesc->channelId);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003022#else
3023 cfg80211_ibss_joined(pAdapter->dev, bss->bssid,
3024 GFP_KERNEL);
3025#endif
3026 cfg80211_put_bss(
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003027 pHddCtx->wiphy,
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003028 bss);
3029 }
Krunal Soni2c68f232015-10-26 20:52:51 -07003030 if (eCSR_ROAM_RESULT_IBSS_STARTED == roamResult) {
Tushnim Bhattacharyyaca50b322015-12-28 17:14:36 -08003031 cds_incr_active_session(pAdapter->device_mode,
Krunal Soni2c68f232015-10-26 20:52:51 -07003032 pAdapter->sessionId);
3033 } else if (eCSR_ROAM_RESULT_IBSS_JOIN_SUCCESS == roamResult ||
3034 eCSR_ROAM_RESULT_IBSS_COALESCED == roamResult) {
Tushnim Bhattacharyyaca50b322015-12-28 17:14:36 -08003035 cds_update_connection_info(pAdapter->sessionId);
Krunal Soni2c68f232015-10-26 20:52:51 -07003036 }
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003037 break;
3038 }
3039
3040 case eCSR_ROAM_RESULT_IBSS_START_FAILED:
3041 {
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07003042 hdd_err("%s: unable to create IBSS", pAdapter->dev->name);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003043 break;
3044 }
3045
3046 default:
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07003047 hdd_err("%s: unexpected result %d",
3048 pAdapter->dev->name, (int)roamResult);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003049 break;
3050 }
3051
3052 return;
3053}
3054
3055/**
Deepak Dhamdhere0f076bd2016-06-02 11:29:21 -07003056 * hdd_save_peer() - Save peer MAC address in adapter peer table.
3057 * @sta_ctx: pointer to hdd station context
3058 * @sta_id: station ID
3059 * @peer_mac_addr: mac address of new peer
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003060 *
3061 * This information is passed to iwconfig later. The peer that joined
3062 * last is passed as information to iwconfig.
Deepak Dhamdhere0f076bd2016-06-02 11:29:21 -07003063
3064 * Return: true if success, false otherwise
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003065 */
Deepak Dhamdhere0f076bd2016-06-02 11:29:21 -07003066bool hdd_save_peer(hdd_station_ctx_t *sta_ctx, uint8_t sta_id,
3067 struct qdf_mac_addr *peer_mac_addr)
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003068{
Deepak Dhamdhere0f076bd2016-06-02 11:29:21 -07003069 int idx;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003070
Deepak Dhamdhere0f076bd2016-06-02 11:29:21 -07003071 for (idx = 0; idx < SIR_MAX_NUM_STA_IN_IBSS; idx++) {
3072 if (0 == sta_ctx->conn_info.staId[idx]) {
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07003073 hdd_info("adding peer: %pM, sta_id: %d, at idx: %d",
3074 peer_mac_addr, sta_id, idx);
Deepak Dhamdhere0f076bd2016-06-02 11:29:21 -07003075 sta_ctx->conn_info.staId[idx] = sta_id;
3076 qdf_copy_macaddr(
3077 &sta_ctx->conn_info.peerMacAddress[idx],
3078 peer_mac_addr);
3079 return true;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003080 }
3081 }
Deepak Dhamdhere0f076bd2016-06-02 11:29:21 -07003082 return false;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003083}
3084
3085/**
Deepak Dhamdherea6d2f4c2016-06-04 00:24:52 -07003086 * hdd_delete_peer() - removes peer from hdd station context peer table
3087 * @sta_ctx: pointer to hdd station context
3088 * @sta_id: station ID
3089 *
3090 * Return: None
3091 */
3092void hdd_delete_peer(hdd_station_ctx_t *sta_ctx, uint8_t sta_id)
3093{
3094 int i;
3095
3096 for (i = 0; i < SIR_MAX_NUM_STA_IN_IBSS; i++) {
3097 if (sta_id == sta_ctx->conn_info.staId[i]) {
3098 sta_ctx->conn_info.staId[i] = 0;
3099 return;
3100 }
3101 }
3102
3103 hdd_err(FL("sta_id %d is not present in peer table"), sta_id);
3104}
3105
3106/**
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003107 * roam_remove_ibss_station() - Remove the IBSS peer MAC address in the adapter
3108 * @pAdapter: pointer to adapter
3109 * @staId: station id
3110 *
3111 * Return:
Naveen Rawatc45d1622016-07-05 12:20:09 -07003112 * true if we remove MAX_PEERS or less STA
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003113 * false otherwise.
3114 */
3115static bool roam_remove_ibss_station(hdd_adapter_t *pAdapter, uint8_t staId)
3116{
3117 bool fSuccess = false;
3118 int idx = 0;
3119 uint8_t valid_idx = 0;
3120 uint8_t del_idx = 0;
3121 uint8_t empty_slots = 0;
3122 hdd_station_ctx_t *pHddStaCtx = WLAN_HDD_GET_STATION_CTX_PTR(pAdapter);
3123
Naveen Rawatc45d1622016-07-05 12:20:09 -07003124 for (idx = 0; idx < MAX_PEERS; idx++) {
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003125 if (staId == pHddStaCtx->conn_info.staId[idx]) {
3126 pHddStaCtx->conn_info.staId[idx] = 0;
3127
Anurag Chouhanc5548422016-02-24 18:33:27 +05303128 qdf_zero_macaddr(&pHddStaCtx->conn_info.
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003129 peerMacAddress[idx]);
3130
3131 fSuccess = true;
3132
3133 /*
3134 * Note the deleted Index, if its 0 we need special
3135 * handling.
3136 */
3137 del_idx = idx;
3138
3139 empty_slots++;
3140 } else {
3141 if (pHddStaCtx->conn_info.staId[idx] != 0) {
3142 valid_idx = idx;
3143 } else {
3144 /* Found an empty slot */
3145 empty_slots++;
3146 }
3147 }
3148 }
3149
Naveen Rawatc45d1622016-07-05 12:20:09 -07003150 if (MAX_PEERS == empty_slots) {
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003151 /* Last peer departed, set the IBSS state appropriately */
3152 pHddStaCtx->conn_info.connState =
3153 eConnectionState_IbssDisconnected;
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07003154 hdd_err("Last IBSS Peer Departed!!!");
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003155 }
3156 /* Find next active staId, to have a valid sta trigger for TL. */
3157 if (fSuccess == true) {
3158 if (del_idx == 0) {
3159 if (pHddStaCtx->conn_info.staId[valid_idx] != 0) {
3160 pHddStaCtx->conn_info.staId[0] =
3161 pHddStaCtx->conn_info.staId[valid_idx];
Anurag Chouhanc5548422016-02-24 18:33:27 +05303162 qdf_copy_macaddr(&pHddStaCtx->conn_info.
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003163 peerMacAddress[0],
3164 &pHddStaCtx->conn_info.
3165 peerMacAddress[valid_idx]);
3166
3167 pHddStaCtx->conn_info.staId[valid_idx] = 0;
Anurag Chouhanc5548422016-02-24 18:33:27 +05303168 qdf_zero_macaddr(&pHddStaCtx->conn_info.
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003169 peerMacAddress[valid_idx]);
3170 }
3171 }
3172 }
3173 return fSuccess;
3174}
3175
3176/**
3177 * roam_ibss_connect_handler() - IBSS connection handler
3178 * @pAdapter: pointer to adapter
3179 * @pRoamInfo: pointer to roam info
3180 *
3181 * We update the status of the IBSS to connected in this function.
3182 *
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05303183 * Return: QDF_STATUS enumeration
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003184 */
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05303185static QDF_STATUS roam_ibss_connect_handler(hdd_adapter_t *pAdapter,
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003186 tCsrRoamInfo *pRoamInfo)
3187{
3188 struct cfg80211_bss *bss;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003189 /*
3190 * Set the internal connection state to show 'IBSS Connected' (IBSS with
3191 * a partner stations).
3192 */
3193 hdd_conn_set_connection_state(pAdapter, eConnectionState_IbssConnected);
3194
3195 /* Save the connection info from CSR... */
3196 hdd_conn_save_connect_info(pAdapter, pRoamInfo, eCSR_BSS_TYPE_IBSS);
3197
3198 /* Send the bssid address to the wext. */
3199 hdd_send_association_event(pAdapter->dev, pRoamInfo);
3200 /* add bss_id to cfg80211 data base */
3201 bss = wlan_hdd_cfg80211_update_bss_db(pAdapter, pRoamInfo);
3202 if (NULL == bss) {
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07003203 hdd_err("%s: unable to create IBSS entry",
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003204 pAdapter->dev->name);
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05303205 return QDF_STATUS_E_FAILURE;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003206 }
3207 cfg80211_put_bss(
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003208 WLAN_HDD_GET_CTX(pAdapter)->wiphy,
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003209 bss);
3210
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05303211 return QDF_STATUS_SUCCESS;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003212}
3213
3214/**
3215 * hdd_roam_mic_error_indication_handler() - MIC error indication handler
3216 * @pAdapter: pointer to adapter
3217 * @pRoamInfo: pointer to roam info
3218 * @roamId: roam id
3219 * @roamStatus: roam status
3220 * @roamResult: roam result
3221 *
3222 * This function indicates the Mic failure to the supplicant
3223 *
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05303224 * Return: QDF_STATUS enumeration
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003225 */
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05303226static QDF_STATUS
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003227hdd_roam_mic_error_indication_handler(hdd_adapter_t *pAdapter,
3228 tCsrRoamInfo *pRoamInfo,
3229 uint32_t roamId,
3230 eRoamCmdStatus roamStatus,
3231 eCsrRoamResult roamResult)
3232{
3233 hdd_station_ctx_t *pHddStaCtx = WLAN_HDD_GET_STATION_CTX_PTR(pAdapter);
3234
3235 if (eConnectionState_Associated == pHddStaCtx->conn_info.connState &&
3236 TKIP_COUNTER_MEASURE_STOPED ==
3237 pHddStaCtx->WextState.mTKIPCounterMeasures) {
3238 struct iw_michaelmicfailure msg;
3239 union iwreq_data wreq;
3240 memset(&msg, '\0', sizeof(msg));
3241 msg.src_addr.sa_family = ARPHRD_ETHER;
3242 memcpy(msg.src_addr.sa_data,
3243 pRoamInfo->u.pMICFailureInfo->taMacAddr,
3244 sizeof(pRoamInfo->u.pMICFailureInfo->taMacAddr));
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07003245 hdd_info("MIC MAC " MAC_ADDRESS_STR,
3246 MAC_ADDR_ARRAY(msg.src_addr.sa_data));
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003247
3248 if (pRoamInfo->u.pMICFailureInfo->multicast == eSIR_TRUE)
3249 msg.flags = IW_MICFAILURE_GROUP;
3250 else
3251 msg.flags = IW_MICFAILURE_PAIRWISE;
3252 memset(&wreq, 0, sizeof(wreq));
3253 wreq.data.length = sizeof(msg);
3254 wireless_send_event(pAdapter->dev, IWEVMICHAELMICFAILURE, &wreq,
3255 (char *)&msg);
3256 /* inform mic failure to nl80211 */
3257 cfg80211_michael_mic_failure(pAdapter->dev,
3258 pRoamInfo->u.pMICFailureInfo->
3259 taMacAddr,
3260 ((pRoamInfo->u.pMICFailureInfo->
3261 multicast ==
3262 eSIR_TRUE) ?
3263 NL80211_KEYTYPE_GROUP :
3264 NL80211_KEYTYPE_PAIRWISE),
3265 pRoamInfo->u.pMICFailureInfo->
3266 keyId,
3267 pRoamInfo->u.pMICFailureInfo->TSC,
3268 GFP_KERNEL);
3269
3270 }
3271
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05303272 return QDF_STATUS_SUCCESS;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003273}
3274
3275/**
3276 * roam_roam_connect_status_update_handler() - IBSS connect status update
3277 * @pAdapter: pointer to adapter
3278 * @pRoamInfo: pointer to roam info
3279 * @roamId: roam id
3280 * @roamStatus: roam status
3281 * @roamResult: roam result
3282 *
3283 * The Ibss connection status is updated regularly here in this function.
3284 *
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05303285 * Return: QDF_STATUS enumeration
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003286 */
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05303287static QDF_STATUS
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003288roam_roam_connect_status_update_handler(hdd_adapter_t *pAdapter,
3289 tCsrRoamInfo *pRoamInfo,
3290 uint32_t roamId,
3291 eRoamCmdStatus roamStatus,
3292 eCsrRoamResult roamResult)
3293{
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05303294 QDF_STATUS qdf_status;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003295
3296 hdd_context_t *pHddCtx = WLAN_HDD_GET_CTX(pAdapter);
3297 switch (roamResult) {
3298 case eCSR_ROAM_RESULT_IBSS_NEW_PEER:
3299 {
3300 hdd_station_ctx_t *pHddStaCtx =
3301 WLAN_HDD_GET_STATION_CTX_PTR(pAdapter);
Kai Liu7400c5b2016-09-29 15:28:36 +08003302 struct station_info *stainfo;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003303
Gowri, Deepthi07ac9932016-09-02 15:19:32 +05303304 hdd_err("IBSS New Peer indication from SME "
3305 "with peerMac " MAC_ADDRESS_STR " BSSID: "
3306 MAC_ADDRESS_STR " and stationID= %d",
3307 MAC_ADDR_ARRAY(pRoamInfo->peerMac.bytes),
3308 MAC_ADDR_ARRAY(pHddStaCtx->conn_info.bssId.bytes),
3309 pRoamInfo->staId);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003310
Deepak Dhamdhere0f076bd2016-06-02 11:29:21 -07003311 if (!hdd_save_peer
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003312 (WLAN_HDD_GET_STATION_CTX_PTR(pAdapter),
3313 pRoamInfo->staId,
3314 &pRoamInfo->peerMac)) {
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07003315 hdd_warn("Max reached: Can't register new IBSS peer");
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003316 break;
3317 }
3318
3319 pHddCtx->sta_to_adapter[pRoamInfo->staId] = pAdapter;
3320
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003321 /* Register the Station with TL for the new peer. */
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05303322 qdf_status = hdd_roam_register_sta(pAdapter,
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003323 pRoamInfo,
3324 pRoamInfo->staId,
3325 &pRoamInfo->peerMac,
3326 pRoamInfo->pBssDesc);
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05303327 if (!QDF_IS_STATUS_SUCCESS(qdf_status)) {
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07003328 hdd_err("Cannot register STA with TL for IBSS. Failed with qdf_status = %d [%08X]",
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05303329 qdf_status, qdf_status);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003330 }
3331 pHddStaCtx->ibss_sta_generation++;
Kai Liu7400c5b2016-09-29 15:28:36 +08003332 stainfo = qdf_mem_malloc(sizeof(*stainfo));
3333 if (stainfo == NULL) {
3334 hdd_err("memory allocation for station_info failed");
3335 return QDF_STATUS_E_NOMEM;
3336 }
3337 stainfo->filled = 0;
3338 stainfo->generation = pHddStaCtx->ibss_sta_generation;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003339
3340 cfg80211_new_sta(pAdapter->dev,
3341 (const u8 *)pRoamInfo->peerMac.bytes,
Kai Liu7400c5b2016-09-29 15:28:36 +08003342 stainfo, GFP_KERNEL);
3343 qdf_mem_free(stainfo);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003344
3345 if (eCSR_ENCRYPT_TYPE_WEP40_STATICKEY ==
3346 pHddStaCtx->ibss_enc_key.encType
3347 || eCSR_ENCRYPT_TYPE_WEP104_STATICKEY ==
3348 pHddStaCtx->ibss_enc_key.encType
3349 || eCSR_ENCRYPT_TYPE_TKIP ==
3350 pHddStaCtx->ibss_enc_key.encType
3351 || eCSR_ENCRYPT_TYPE_AES ==
3352 pHddStaCtx->ibss_enc_key.encType) {
3353 pHddStaCtx->ibss_enc_key.keyDirection =
3354 eSIR_TX_RX;
Anurag Chouhanc5548422016-02-24 18:33:27 +05303355 qdf_copy_macaddr(&pHddStaCtx->ibss_enc_key.peerMac,
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003356 &pRoamInfo->peerMac);
3357
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07003358 hdd_info("New peer joined set PTK encType=%d",
3359 pHddStaCtx->ibss_enc_key.encType);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003360
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05303361 qdf_status =
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003362 sme_roam_set_key(WLAN_HDD_GET_HAL_CTX
3363 (pAdapter),
3364 pAdapter->sessionId,
3365 &pHddStaCtx->ibss_enc_key,
3366 &roamId);
3367
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05303368 if (QDF_STATUS_SUCCESS != qdf_status) {
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07003369 hdd_err("sme_roam_set_key failed, status=%d",
3370 qdf_status);
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05303371 return QDF_STATUS_E_FAILURE;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003372 }
3373 }
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07003374 hdd_info("Enabling queues");
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003375 wlan_hdd_netif_queue_control(pAdapter,
3376 WLAN_START_ALL_NETIF_QUEUE_N_CARRIER,
3377 WLAN_CONTROL_PATH);
3378 break;
3379 }
3380
3381 case eCSR_ROAM_RESULT_IBSS_CONNECT:
3382 {
3383
3384 roam_ibss_connect_handler(pAdapter, pRoamInfo);
3385
3386 break;
3387 }
3388 case eCSR_ROAM_RESULT_IBSS_PEER_DEPARTED:
3389 {
3390 hdd_station_ctx_t *pHddStaCtx =
3391 WLAN_HDD_GET_STATION_CTX_PTR(pAdapter);
3392
3393 if (!roam_remove_ibss_station(pAdapter, pRoamInfo->staId))
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07003394 hdd_warn("IBSS peer departed by cannot find peer in our registration table with TL");
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003395
Gowri, Deepthi07ac9932016-09-02 15:19:32 +05303396 hdd_err("IBSS Peer Departed from SME "
3397 "with peerMac " MAC_ADDRESS_STR " BSSID: "
3398 MAC_ADDRESS_STR " and stationID= %d",
3399 MAC_ADDR_ARRAY(pRoamInfo->peerMac.bytes),
3400 MAC_ADDR_ARRAY(pHddStaCtx->conn_info.bssId.bytes),
3401 pRoamInfo->staId);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003402
3403 hdd_roam_deregister_sta(pAdapter, pRoamInfo->staId);
3404
3405 pHddCtx->sta_to_adapter[pRoamInfo->staId] = NULL;
3406 pHddStaCtx->ibss_sta_generation++;
3407
3408 cfg80211_del_sta(pAdapter->dev,
3409 (const u8 *)&pRoamInfo->peerMac.bytes,
3410 GFP_KERNEL);
3411 break;
3412 }
3413 case eCSR_ROAM_RESULT_IBSS_INACTIVE:
3414 {
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07003415 hdd_info("Received eCSR_ROAM_RESULT_IBSS_INACTIVE from SME");
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003416 /* Stop only when we are inactive */
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07003417 hdd_info("Disabling queues");
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003418 wlan_hdd_netif_queue_control(pAdapter,
3419 WLAN_NETIF_TX_DISABLE_N_CARRIER,
3420 WLAN_CONTROL_PATH);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003421 hdd_conn_set_connection_state(pAdapter,
3422 eConnectionState_NotConnected);
3423
3424 /* Send the bssid address to the wext. */
3425 hdd_send_association_event(pAdapter->dev, pRoamInfo);
3426 break;
3427 }
3428 default:
3429 break;
3430
3431 }
3432
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05303433 return QDF_STATUS_SUCCESS;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003434}
3435
3436#ifdef FEATURE_WLAN_TDLS
3437/**
3438 * hdd_roam_register_tdlssta() - register new TDLS station
3439 * @pAdapter: pointer to adapter
3440 * @peerMac: pointer to peer MAC address
3441 * @staId: station identifier
3442 * @ucastSig: unicast signature
Agrawal Ashishd3f22f62016-09-04 13:46:15 +05303443 * @qos: QOS capability of TDLS station/link
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003444 *
3445 * Construct the staDesc and register with TL the new STA.
3446 * This is called as part of ADD_STA in the TDLS setup.
3447 *
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05303448 * Return: QDF_STATUS enumeration
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003449 */
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05303450QDF_STATUS hdd_roam_register_tdlssta(hdd_adapter_t *pAdapter,
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003451 const uint8_t *peerMac, uint16_t staId,
Agrawal Ashishd3f22f62016-09-04 13:46:15 +05303452 uint8_t ucastSig, uint8_t qos)
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003453{
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05303454 QDF_STATUS qdf_status = QDF_STATUS_E_FAILURE;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003455 struct ol_txrx_desc_type staDesc = { 0 };
Dhanashri Atre182b0272016-02-17 15:35:07 -08003456 struct ol_txrx_ops txrx_ops;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003457
3458 /*
3459 * TDLS sta in BSS should be set as STA type TDLS and STA MAC should
3460 * be peer MAC, here we are working on direct Link
3461 */
3462 staDesc.sta_id = staId;
3463
3464 /* set the QoS field appropriately .. */
Agrawal Ashishd3f22f62016-09-04 13:46:15 +05303465 staDesc.is_qos_enabled = qos;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003466
Dhanashri Atre50141c52016-04-07 13:15:29 -07003467 /* Register the vdev transmit and receive functions */
3468 qdf_mem_zero(&txrx_ops, sizeof(txrx_ops));
3469 txrx_ops.rx.rx = hdd_rx_packet_cbk;
3470 ol_txrx_vdev_register(
3471 ol_txrx_get_vdev_from_vdev_id(pAdapter->sessionId),
3472 pAdapter, &txrx_ops);
3473 pAdapter->tx_fn = txrx_ops.tx.tx;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003474
3475 /* Register the Station with TL... */
Dhanashri Atre182b0272016-02-17 15:35:07 -08003476 qdf_status = ol_txrx_register_peer(&staDesc);
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05303477 if (!QDF_IS_STATUS_SUCCESS(qdf_status)) {
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07003478 hdd_err("ol_txrx_register_peer() failed to register. Status=%d [0x%08X]",
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05303479 qdf_status, qdf_status);
3480 return qdf_status;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003481 }
3482
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05303483 return qdf_status;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003484}
3485
3486/**
3487 * hdd_roam_deregister_tdlssta() - deregister new TDLS station
3488 * @pAdapter: pointer to adapter
3489 * @staId: station identifier
3490 *
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05303491 * Return: QDF_STATUS enumeration
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003492 */
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05303493static QDF_STATUS hdd_roam_deregister_tdlssta(hdd_adapter_t *pAdapter,
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003494 uint8_t staId)
3495{
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05303496 QDF_STATUS qdf_status;
3497 qdf_status = ol_txrx_clear_peer(staId);
3498 if (!QDF_IS_STATUS_SUCCESS(qdf_status)) {
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07003499 hdd_warn("ol_txrx_clear_peer() failed for staID %d. Status=%d [0x%08X]",
3500 staId, qdf_status, qdf_status);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003501 }
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05303502 return qdf_status;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003503}
3504
3505/**
Kabilan Kannan14ec97f2016-05-16 23:48:25 -07003506 * hdd_tdls_connection_tracker_update() - update connection tracker state
3507 * @adapter: pointer to adapter
3508 * @roam_info: pointer to roam info
3509 * @hdd_tdls_ctx: tdls context
3510 *
3511 * Return: QDF_STATUS enumeration
3512 */
3513static QDF_STATUS hdd_tdls_connection_tracker_update(hdd_adapter_t *adapter,
3514 tCsrRoamInfo *roam_info,
3515 tdlsCtx_t *hdd_tdls_ctx)
3516{
3517 hddTdlsPeer_t *curr_peer;
3518 hdd_context_t *hdd_ctx = WLAN_HDD_GET_CTX(adapter);
3519
3520 curr_peer = wlan_hdd_tdls_find_peer(adapter,
3521 roam_info->peerMac.bytes, true);
3522
3523 if (!curr_peer) {
3524 hdd_err("curr_peer is null");
3525 return QDF_STATUS_E_FAILURE;
3526 }
3527
3528 mutex_lock(&hdd_ctx->tdls_lock);
3529
3530 if (eTDLS_LINK_CONNECTED ==
3531 curr_peer->link_status) {
3532 hdd_err("Received CONNECTION_TRACKER_NOTIFICATION "
3533 MAC_ADDRESS_STR
3534 " staId: %d, reason: %d",
3535 MAC_ADDR_ARRAY(roam_info->peerMac.bytes),
3536 roam_info->staId,
3537 roam_info->reasonCode);
3538
3539 if (roam_info->reasonCode ==
3540 eWNI_TDLS_PEER_ENTER_BUF_STA ||
3541 roam_info->reasonCode ==
3542 eWNI_TDLS_ENTER_BT_BUSY_MODE)
3543 hdd_ctx->enable_tdls_connection_tracker = true;
3544 else if (roam_info->reasonCode ==
3545 eWNI_TDLS_PEER_EXIT_BUF_STA ||
3546 roam_info->reasonCode ==
3547 eWNI_TDLS_EXIT_BT_BUSY_MODE)
3548 hdd_ctx->enable_tdls_connection_tracker = false;
3549
3550 } else {
3551 hdd_err("TDLS not connected, ignore notification, reason: %d",
3552 roam_info->reasonCode);
3553 }
3554
3555 mutex_unlock(&hdd_ctx->tdls_lock);
3556
3557 return QDF_STATUS_SUCCESS;
3558}
3559
3560
3561
3562
3563/**
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003564 * hdd_roam_tdls_status_update_handler() - TDLS status update handler
3565 * @pAdapter: pointer to adapter
3566 * @pRoamInfo: pointer to roam info
3567 * @roamId: roam id
3568 * @roamStatus: roam status
3569 * @roamResult: roam result
3570 *
3571 * HDD interface between SME and TL to ensure TDLS client registration with
3572 * TL in case of new TDLS client is added and deregistration at the time
3573 * TDLS client is deleted.
3574 *
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05303575 * Return: QDF_STATUS enumeration
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003576 */
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05303577static QDF_STATUS
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003578hdd_roam_tdls_status_update_handler(hdd_adapter_t *pAdapter,
3579 tCsrRoamInfo *pRoamInfo,
3580 uint32_t roamId,
3581 eRoamCmdStatus roamStatus,
3582 eCsrRoamResult roamResult)
3583{
3584 hdd_context_t *pHddCtx = WLAN_HDD_GET_CTX(pAdapter);
3585 tdlsCtx_t *pHddTdlsCtx = WLAN_HDD_GET_TDLS_CTX_PTR(pAdapter);
3586 tSmeTdlsPeerStateParams smeTdlsPeerStateParams;
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05303587 QDF_STATUS status = QDF_STATUS_E_FAILURE;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003588 uint8_t staIdx;
3589 hddTdlsPeer_t *curr_peer;
3590 uint32_t reason;
3591
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07003592 hdd_info("hdd_tdlsStatusUpdate: %s staIdx %d " MAC_ADDRESS_STR,
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003593 roamResult ==
3594 eCSR_ROAM_RESULT_ADD_TDLS_PEER ? "ADD_TDLS_PEER" : roamResult
3595 ==
3596 eCSR_ROAM_RESULT_DELETE_TDLS_PEER ? "DEL_TDLS_PEER" :
3597 roamResult ==
3598 eCSR_ROAM_RESULT_TEARDOWN_TDLS_PEER_IND ? "DEL_TDLS_PEER_IND"
3599 : roamResult ==
3600 eCSR_ROAM_RESULT_DELETE_ALL_TDLS_PEER_IND ?
3601 "DEL_ALL_TDLS_PEER_IND" : roamResult ==
3602 eCSR_ROAM_RESULT_UPDATE_TDLS_PEER ? "UPDATE_TDLS_PEER" :
3603 roamResult ==
3604 eCSR_ROAM_RESULT_LINK_ESTABLISH_REQ_RSP ?
3605 "LINK_ESTABLISH_REQ_RSP" : roamResult ==
3606 eCSR_ROAM_RESULT_TDLS_SHOULD_DISCOVER ? "TDLS_SHOULD_DISCOVER"
3607 : roamResult ==
3608 eCSR_ROAM_RESULT_TDLS_SHOULD_TEARDOWN ? "TDLS_SHOULD_TEARDOWN"
3609 : roamResult ==
3610 eCSR_ROAM_RESULT_TDLS_SHOULD_PEER_DISCONNECTED ?
3611 "TDLS_SHOULD_PEER_DISCONNECTED" : "UNKNOWN", pRoamInfo->staId,
3612 MAC_ADDR_ARRAY(pRoamInfo->peerMac.bytes));
3613
3614 if (!pHddTdlsCtx) {
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07003615 hdd_info("TDLS ctx is null, ignore roamResult (%d)",
3616 roamResult);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003617 return status;
3618 }
3619
3620 switch (roamResult) {
3621 case eCSR_ROAM_RESULT_ADD_TDLS_PEER:
3622 {
3623 if (eSIR_SME_SUCCESS != pRoamInfo->statusCode) {
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07003624 hdd_err("Add Sta failed. status code(=%d)",
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003625 pRoamInfo->statusCode);
Selvaraj, Sridhar5d95e632016-09-14 17:00:38 +05303626 pAdapter->tdlsAddStaStatus = QDF_STATUS_E_FAILURE;
3627
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003628 } else {
3629 /*
3630 * Check if there is available index for this new TDLS
3631 * STA.
3632 */
3633 for (staIdx = 0;
3634 staIdx < pHddCtx->max_num_tdls_sta;
3635 staIdx++) {
3636 if (0 ==
3637 pHddCtx->tdlsConnInfo[staIdx].
3638 staId) {
3639 pHddCtx->tdlsConnInfo[staIdx].
3640 sessionId =
3641 pRoamInfo->sessionId;
3642 pHddCtx->tdlsConnInfo[staIdx].
3643 staId = pRoamInfo->staId;
3644
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07003645 hdd_warn("TDLS: STA IDX at %d is %d "
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003646 "of mac "
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07003647 MAC_ADDRESS_STR,
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003648 staIdx,
3649 pHddCtx->
3650 tdlsConnInfo[staIdx].
3651 staId,
3652 MAC_ADDR_ARRAY
3653 (pRoamInfo->peerMac.bytes));
3654
Anurag Chouhanc5548422016-02-24 18:33:27 +05303655 qdf_copy_macaddr(&pHddCtx->
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003656 tdlsConnInfo
3657 [staIdx].
3658 peerMac,
3659 &pRoamInfo->
3660 peerMac);
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05303661 status = QDF_STATUS_SUCCESS;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003662 break;
3663 }
3664 }
3665 if (staIdx < pHddCtx->max_num_tdls_sta) {
3666 if (-1 ==
3667 wlan_hdd_tdls_set_sta_id(pAdapter,
3668 pRoamInfo->
3669 peerMac.bytes,
3670 pRoamInfo->
3671 staId)) {
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07003672 hdd_err("wlan_hdd_tdls_set_sta_id() failed");
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05303673 return QDF_STATUS_E_FAILURE;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003674 }
3675
3676 (WLAN_HDD_GET_CTX(pAdapter))->
3677 sta_to_adapter[pRoamInfo->staId] =
3678 pAdapter;
3679 /*
3680 * store the ucast signature,
3681 * if required for further reference.
3682 */
3683
3684 wlan_hdd_tdls_set_signature(pAdapter,
3685 pRoamInfo->
3686 peerMac.bytes,
3687 pRoamInfo->
3688 ucastSig);
3689 } else {
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05303690 status = QDF_STATUS_E_FAILURE;
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07003691 hdd_err("no available slot in conn_info. staId %d cannot be stored",
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003692 pRoamInfo->staId);
3693 }
3694 pAdapter->tdlsAddStaStatus = status;
3695 }
3696 complete(&pAdapter->tdls_add_station_comp);
3697 break;
3698 }
3699 case eCSR_ROAM_RESULT_UPDATE_TDLS_PEER:
3700 {
3701 if (eSIR_SME_SUCCESS != pRoamInfo->statusCode) {
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07003702 hdd_err("Add Sta failed. status code(=%d)",
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003703 pRoamInfo->statusCode);
3704 }
3705 /* store the ucast signature which will be used later when
3706 * registering to TL
3707 */
3708 pAdapter->tdlsAddStaStatus = pRoamInfo->statusCode;
3709 complete(&pAdapter->tdls_add_station_comp);
3710 break;
3711 }
3712 case eCSR_ROAM_RESULT_LINK_ESTABLISH_REQ_RSP:
3713 {
3714 if (eSIR_SME_SUCCESS != pRoamInfo->statusCode) {
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07003715 hdd_err("Link Establish Request failed. status(=%d)",
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003716 pRoamInfo->statusCode);
3717 }
3718 complete(&pAdapter->tdls_link_establish_req_comp);
3719 break;
3720 }
3721 case eCSR_ROAM_RESULT_DELETE_TDLS_PEER:
3722 {
3723 for (staIdx = 0; staIdx < pHddCtx->max_num_tdls_sta;
3724 staIdx++) {
3725 if ((pHddCtx->tdlsConnInfo[staIdx].sessionId ==
3726 pRoamInfo->sessionId)
3727 && pRoamInfo->staId ==
3728 pHddCtx->tdlsConnInfo[staIdx].staId) {
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07003729 hdd_warn("HDD: del STA IDX = %x",
3730 pRoamInfo->staId);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003731
3732 curr_peer =
3733 wlan_hdd_tdls_find_peer(pAdapter,
3734 pRoamInfo->
3735 peerMac.bytes,
3736 true);
Agrawal Ashishdd2075b2015-10-30 13:05:27 +05303737 if (NULL != curr_peer) {
3738 hdd_info("Current status for peer " MAC_ADDRESS_STR " is %d",
3739 MAC_ADDR_ARRAY(pRoamInfo->peerMac.bytes),
3740 curr_peer->link_status);
3741 if (TDLS_IS_CONNECTED(curr_peer)) {
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003742 hdd_roam_deregister_tdlssta
3743 (pAdapter,
3744 pRoamInfo->staId);
3745 wlan_hdd_tdls_decrement_peer_count
3746 (pAdapter);
Agrawal Ashishdd2075b2015-10-30 13:05:27 +05303747 } else if (eTDLS_LINK_CONNECTING ==
3748 curr_peer->link_status) {
3749 hdd_roam_deregister_tdlssta
3750 (pAdapter,
3751 pRoamInfo->staId);
3752 }
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003753 }
3754 wlan_hdd_tdls_reset_peer(pAdapter,
3755 pRoamInfo->
3756 peerMac.bytes);
3757
3758 pHddCtx->tdlsConnInfo[staIdx].staId = 0;
3759 pHddCtx->tdlsConnInfo[staIdx].
3760 sessionId = 255;
Anurag Chouhan600c3a02016-03-01 10:33:54 +05303761 qdf_mem_zero(&pHddCtx->
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003762 tdlsConnInfo[staIdx].
3763 peerMac,
Anurag Chouhan6d760662016-02-20 16:05:43 +05303764 QDF_MAC_ADDR_SIZE);
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05303765 status = QDF_STATUS_SUCCESS;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003766 break;
3767 }
3768 }
3769 complete(&pAdapter->tdls_del_station_comp);
3770 }
3771 break;
3772 case eCSR_ROAM_RESULT_TEARDOWN_TDLS_PEER_IND:
3773 {
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07003774 hdd_err("Sending teardown to supplicant with reason code %u",
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003775 pRoamInfo->reasonCode);
3776
3777 curr_peer =
3778 wlan_hdd_tdls_find_peer(pAdapter,
3779 pRoamInfo->peerMac.bytes, true);
3780 wlan_hdd_tdls_indicate_teardown(pAdapter, curr_peer,
3781 pRoamInfo->reasonCode);
Abhishek Singh4ef5fe02016-04-27 12:21:24 +05303782 hdd_send_wlan_tdls_teardown_event(eTDLS_TEARDOWN_BSS_DISCONNECT,
3783 curr_peer->peerMac);
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05303784 status = QDF_STATUS_SUCCESS;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003785 break;
3786 }
3787 case eCSR_ROAM_RESULT_DELETE_ALL_TDLS_PEER_IND:
3788 {
3789 /* 0 staIdx is assigned to AP we dont want to touch that */
3790 for (staIdx = 0; staIdx < pHddCtx->max_num_tdls_sta;
3791 staIdx++) {
3792 if ((pHddCtx->tdlsConnInfo[staIdx].sessionId ==
3793 pRoamInfo->sessionId)
3794 && pHddCtx->tdlsConnInfo[staIdx].staId) {
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07003795 hdd_warn("hdd_tdlsStatusUpdate: staIdx %d "
3796 MAC_ADDRESS_STR,
3797 pHddCtx->tdlsConnInfo[staIdx].
3798 staId,
3799 MAC_ADDR_ARRAY(pHddCtx->
3800 tdlsConnInfo
3801 [staIdx].
3802 peerMac.
3803 bytes));
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003804 wlan_hdd_tdls_reset_peer(pAdapter,
3805 pHddCtx->
3806 tdlsConnInfo
3807 [staIdx].
3808 peerMac.bytes);
3809 hdd_roam_deregister_tdlssta(pAdapter,
3810 pHddCtx->
3811 tdlsConnInfo
3812 [staIdx].
3813 staId);
Anurag Chouhan600c3a02016-03-01 10:33:54 +05303814 qdf_mem_zero(&smeTdlsPeerStateParams,
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003815 sizeof
3816 (smeTdlsPeerStateParams));
3817 smeTdlsPeerStateParams.vdevId =
3818 pHddCtx->tdlsConnInfo[staIdx].
3819 sessionId;
Anurag Chouhan600c3a02016-03-01 10:33:54 +05303820 qdf_mem_copy(&smeTdlsPeerStateParams.
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003821 peerMacAddr,
3822 &pHddCtx->
3823 tdlsConnInfo[staIdx].
3824 peerMac.bytes,
Anurag Chouhan6d760662016-02-20 16:05:43 +05303825 QDF_MAC_ADDR_SIZE);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003826 smeTdlsPeerStateParams.peerState =
3827 eSME_TDLS_PEER_STATE_TEARDOWN;
3828
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07003829 hdd_info("calling sme_update_tdls_peer_state for staIdx %d "
3830 MAC_ADDRESS_STR,
3831 pHddCtx->tdlsConnInfo[staIdx].
3832 staId,
3833 MAC_ADDR_ARRAY(pHddCtx->
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003834 tdlsConnInfo
3835 [staIdx].
3836 peerMac.
3837 bytes));
3838 status =
3839 sme_update_tdls_peer_state(
3840 pHddCtx->hHal,
3841 &smeTdlsPeerStateParams);
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05303842 if (QDF_STATUS_SUCCESS != status) {
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07003843 hdd_err("sme_update_tdls_peer_state failed for "
3844 MAC_ADDRESS_STR,
3845 MAC_ADDR_ARRAY
3846 (pHddCtx->
3847 tdlsConnInfo[staIdx].
3848 peerMac.bytes));
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003849 }
3850 wlan_hdd_tdls_decrement_peer_count
3851 (pAdapter);
3852
Anurag Chouhan600c3a02016-03-01 10:33:54 +05303853 qdf_mem_zero(&pHddCtx->
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003854 tdlsConnInfo[staIdx].
3855 peerMac,
Anurag Chouhan6d760662016-02-20 16:05:43 +05303856 QDF_MAC_ADDR_SIZE);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003857 pHddCtx->tdlsConnInfo[staIdx].staId = 0;
3858 pHddCtx->tdlsConnInfo[staIdx].
3859 sessionId = 255;
3860
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05303861 status = QDF_STATUS_SUCCESS;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003862 }
3863 }
3864 break;
3865 }
3866 case eCSR_ROAM_RESULT_TDLS_SHOULD_DISCOVER:
3867 {
3868 /* ignore TDLS_SHOULD_DISCOVER if any concurrency detected */
Kabilan Kannan163fd0b2016-06-08 15:21:51 -07003869 if (!cds_check_is_tdls_allowed(pAdapter->device_mode)) {
3870 hdd_err("TDLS not allowed, ignore SHOULD_DISCOVER");
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05303871 status = QDF_STATUS_E_FAILURE;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003872 break;
3873 }
3874
Archana Ramachandran7ba24ff2016-04-26 12:29:04 -07003875 if (pHddCtx->tdls_nss_switch_in_progress) {
3876 hdd_err("TDLS antenna switch is in progress, ignore SHOULD_DISCOVER");
3877 status = QDF_STATUS_SUCCESS;
3878 break;
3879 }
3880
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003881 curr_peer =
3882 wlan_hdd_tdls_get_peer(pAdapter,
Kabilan Kannan36090ce2016-05-03 19:28:44 -07003883 pRoamInfo->peerMac.bytes,
3884 true);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003885 if (!curr_peer) {
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07003886 hdd_err("curr_peer is null");
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05303887 status = QDF_STATUS_E_FAILURE;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003888 } else {
3889 if (eTDLS_LINK_CONNECTED ==
3890 curr_peer->link_status) {
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07003891 hdd_err("TDLS link status is connected, ignore SHOULD_DISCOVER");
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003892 } else {
3893 /*
3894 * If external control is enabled then initiate
3895 * TDLS only if forced peer is set otherwise
3896 * ignore should Discover trigger from fw.
3897 */
3898 if (pHddCtx->config->
3899 fTDLSExternalControl
3900 && (false ==
3901 curr_peer->isForcedPeer)) {
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07003902 hdd_info("TDLS ExternalControl enabled but curr_peer is not forced, ignore SHOULD_DISCOVER");
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05303903 status = QDF_STATUS_SUCCESS;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003904 break;
3905 } else {
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07003906 hdd_info("initiate TDLS setup on SHOULD_DISCOVER, fTDLSExternalControl: %d, curr_peer->isForcedPeer: %d, reason: %d",
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003907 pHddCtx->config->
3908 fTDLSExternalControl,
3909 curr_peer->isForcedPeer,
3910 pRoamInfo->reasonCode);
3911 }
3912 wlan_hdd_tdls_pre_setup_init_work
3913 (pHddTdlsCtx, curr_peer);
3914 }
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05303915 status = QDF_STATUS_SUCCESS;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003916 }
3917 break;
3918 }
3919
3920 case eCSR_ROAM_RESULT_TDLS_SHOULD_TEARDOWN:
3921 {
3922 curr_peer =
3923 wlan_hdd_tdls_find_peer(pAdapter,
3924 pRoamInfo->peerMac.bytes, true);
3925 if (!curr_peer) {
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07003926 hdd_err("curr_peer is null");
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05303927 status = QDF_STATUS_E_FAILURE;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003928 } else {
3929 if (eTDLS_LINK_CONNECTED ==
3930 curr_peer->link_status) {
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07003931 hdd_err("Received SHOULD_TEARDOWN for peer "
3932 MAC_ADDRESS_STR
3933 " staId: %d, reason: %d",
3934 MAC_ADDR_ARRAY(pRoamInfo->
3935 peerMac.bytes),
3936 pRoamInfo->staId,
3937 pRoamInfo->reasonCode);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003938
3939 if (pRoamInfo->reasonCode ==
3940 eWNI_TDLS_TEARDOWN_REASON_RSSI ||
3941 pRoamInfo->reasonCode ==
3942 eWNI_TDLS_DISCONNECTED_REASON_PEER_DELETE ||
3943 pRoamInfo->reasonCode ==
3944 eWNI_TDLS_TEARDOWN_REASON_PTR_TIMEOUT ||
3945 pRoamInfo->reasonCode ==
3946 eWNI_TDLS_TEARDOWN_REASON_NO_RESPONSE) {
3947 reason =
3948 eSIR_MAC_TDLS_TEARDOWN_PEER_UNREACHABLE;
3949 } else
3950 reason =
3951 eSIR_MAC_TDLS_TEARDOWN_UNSPEC_REASON;
3952
3953 wlan_hdd_tdls_indicate_teardown
3954 (pHddTdlsCtx->pAdapter, curr_peer,
3955 reason);
Abhishek Singh4ef5fe02016-04-27 12:21:24 +05303956 hdd_send_wlan_tdls_teardown_event(
3957 eTDLS_TEARDOWN_BSS_DISCONNECT,
3958 curr_peer->peerMac);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003959 } else {
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07003960 hdd_err("TDLS link is not connected, ignore SHOULD_TEARDOWN, reason: %d",
3961 pRoamInfo->reasonCode);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003962 }
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05303963 status = QDF_STATUS_SUCCESS;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003964 }
3965 break;
3966 }
3967
3968 case eCSR_ROAM_RESULT_TDLS_SHOULD_PEER_DISCONNECTED:
3969 {
3970 curr_peer =
3971 wlan_hdd_tdls_find_peer(pAdapter,
3972 pRoamInfo->peerMac.bytes, true);
3973 if (!curr_peer) {
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07003974 hdd_err("curr_peer is null");
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05303975 status = QDF_STATUS_E_FAILURE;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003976 } else {
3977 if (eTDLS_LINK_CONNECTED ==
3978 curr_peer->link_status) {
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07003979 hdd_err("Received SHOULD_PEER_DISCONNECTED for peer "
3980 MAC_ADDRESS_STR
3981 " staId: %d, reason: %d",
3982 MAC_ADDR_ARRAY(pRoamInfo->peerMac.bytes),
3983 pRoamInfo->staId,
3984 pRoamInfo->reasonCode);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003985
3986 if (pRoamInfo->reasonCode ==
3987 eWNI_TDLS_TEARDOWN_REASON_RSSI ||
3988 pRoamInfo->reasonCode ==
3989 eWNI_TDLS_DISCONNECTED_REASON_PEER_DELETE ||
3990 pRoamInfo->reasonCode ==
3991 eWNI_TDLS_TEARDOWN_REASON_PTR_TIMEOUT ||
3992 pRoamInfo->reasonCode ==
3993 eWNI_TDLS_TEARDOWN_REASON_NO_RESPONSE) {
3994 reason =
3995 eSIR_MAC_TDLS_TEARDOWN_PEER_UNREACHABLE;
3996 } else
3997 reason =
3998 eSIR_MAC_TDLS_TEARDOWN_UNSPEC_REASON;
3999
4000 wlan_hdd_tdls_indicate_teardown
4001 (pHddTdlsCtx->pAdapter, curr_peer,
4002 reason);
Abhishek Singh4ef5fe02016-04-27 12:21:24 +05304003 hdd_send_wlan_tdls_teardown_event(
4004 eTDLS_TEARDOWN_BSS_DISCONNECT,
4005 curr_peer->peerMac);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08004006 } else {
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07004007 hdd_err("TDLS link is not connected, ignore SHOULD_PEER_DISCONNECTED, reason: %d",
4008 pRoamInfo->reasonCode);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08004009 }
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05304010 status = QDF_STATUS_SUCCESS;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08004011 }
4012 break;
4013 }
Kabilan Kannan14ec97f2016-05-16 23:48:25 -07004014
4015 case eCSR_ROAM_RESULT_TDLS_CONNECTION_TRACKER_NOTIFICATION:
4016 status = hdd_tdls_connection_tracker_update(pAdapter,
4017 pRoamInfo,
4018 pHddTdlsCtx);
4019 break;
4020
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08004021 default:
4022 {
4023 break;
4024 }
4025 }
4026
4027 return status;
4028}
Kabilan Kannan32eb5022016-10-04 12:24:50 -07004029#else
4030
4031static inline QDF_STATUS hdd_roam_deregister_tdlssta(hdd_adapter_t *pAdapter,
4032 uint8_t staId)
4033{
4034 return QDF_STATUS_SUCCESS;
4035}
4036
4037static inline QDF_STATUS
4038hdd_roam_tdls_status_update_handler(hdd_adapter_t *pAdapter,
4039 tCsrRoamInfo *pRoamInfo,
4040 uint32_t roamId,
4041 eRoamCmdStatus roamStatus,
4042 eCsrRoamResult roamResult)
4043{
4044 return QDF_STATUS_SUCCESS;
4045}
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08004046#endif
4047
4048#ifdef WLAN_FEATURE_11W
4049/**
4050 * hdd_indicate_unprot_mgmt_frame() - indicate unprotected management frame
4051 * @pAdapter: pointer to the adapter
4052 * @nFrameLength: Length of the unprotected frame being passed
4053 * @pbFrames: Pointer to the frame buffer
4054 * @frameType: 802.11 frame type
4055 *
4056 * This function forwards the unprotected management frame to the supplicant.
4057 *
4058 * Return: nothing
4059 */
4060static void
4061hdd_indicate_unprot_mgmt_frame(hdd_adapter_t *pAdapter, uint32_t nFrameLength,
4062 uint8_t *pbFrames, uint8_t frameType)
4063{
4064 uint8_t type = 0;
4065 uint8_t subType = 0;
4066
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07004067 hdd_info("Frame Type = %d Frame Length = %d",
4068 frameType, nFrameLength);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08004069
4070 /* Sanity Checks */
4071 if (NULL == pAdapter) {
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07004072 hdd_err("pAdapter is NULL");
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08004073 return;
4074 }
4075
4076 if (NULL == pAdapter->dev) {
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07004077 hdd_err("pAdapter->dev is NULL");
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08004078 return;
4079 }
4080
4081 if (WLAN_HDD_ADAPTER_MAGIC != pAdapter->magic) {
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07004082 hdd_err("pAdapter has invalid magic");
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08004083 return;
4084 }
4085
4086 if (!nFrameLength) {
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07004087 hdd_err("Frame Length is Invalid ZERO");
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08004088 return;
4089 }
4090
4091 if (NULL == pbFrames) {
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07004092 hdd_err("pbFrames is NULL");
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08004093 return;
4094 }
4095
4096 type = WLAN_HDD_GET_TYPE_FRM_FC(pbFrames[0]);
4097 subType = WLAN_HDD_GET_SUBTYPE_FRM_FC(pbFrames[0]);
4098
4099 /* Get pAdapter from Destination mac address of the frame */
4100 if (type == SIR_MAC_MGMT_FRAME && subType == SIR_MAC_MGMT_DISASSOC) {
4101#if (LINUX_VERSION_CODE >= KERNEL_VERSION(3, 11, 0))
4102 cfg80211_rx_unprot_mlme_mgmt(pAdapter->dev, pbFrames,
4103 nFrameLength);
4104#else
4105 cfg80211_send_unprot_disassoc(pAdapter->dev, pbFrames,
4106 nFrameLength);
4107#endif
4108 pAdapter->hdd_stats.hddPmfStats.numUnprotDisassocRx++;
4109 } else if (type == SIR_MAC_MGMT_FRAME &&
4110 subType == SIR_MAC_MGMT_DEAUTH) {
4111#if (LINUX_VERSION_CODE >= KERNEL_VERSION(3, 11, 0))
4112 cfg80211_rx_unprot_mlme_mgmt(pAdapter->dev, pbFrames,
4113 nFrameLength);
4114#else
4115 cfg80211_send_unprot_deauth(pAdapter->dev, pbFrames,
4116 nFrameLength);
4117#endif
4118 pAdapter->hdd_stats.hddPmfStats.numUnprotDeauthRx++;
4119 } else {
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07004120 hdd_err("Frame type %d and subtype %d are not valid",
4121 type, subType);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08004122 return;
4123 }
4124}
4125#endif
4126
Srinivas Girigowda515a9ef2015-12-11 11:00:48 -08004127#ifdef FEATURE_WLAN_ESE
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08004128/**
4129 * hdd_indicate_tsm_ie() - send traffic stream metrics ie
4130 * @pAdapter: pointer to adapter
4131 * @tid: traffic identifier
4132 * @state: state
4133 * @measInterval: measurement interval
4134 *
4135 * This function sends traffic stream metrics IE information to
4136 * the supplicant via wireless event.
4137 *
4138 * Return: none
4139 */
4140static void
4141hdd_indicate_tsm_ie(hdd_adapter_t *pAdapter, uint8_t tid,
4142 uint8_t state, uint16_t measInterval)
4143{
4144 union iwreq_data wrqu;
4145 char buf[IW_CUSTOM_MAX + 1];
4146 int nBytes = 0;
4147
4148 if (NULL == pAdapter)
4149 return;
4150
4151 /* create the event */
4152 memset(&wrqu, '\0', sizeof(wrqu));
4153 memset(buf, '\0', sizeof(buf));
4154
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07004155 hdd_info("TSM Ind tid(%d) state(%d) MeasInt(%d)",
4156 tid, state, measInterval);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08004157
4158 nBytes =
4159 snprintf(buf, IW_CUSTOM_MAX, "TSMIE=%d:%d:%d", tid, state,
4160 measInterval);
4161
4162 wrqu.data.pointer = buf;
4163 wrqu.data.length = nBytes;
4164 /* send the event */
4165 wireless_send_event(pAdapter->dev, IWEVCUSTOM, &wrqu, buf);
4166}
4167
4168/**
4169 * hdd_indicate_cckm_pre_auth() - send cckm preauth indication
4170 * @pAdapter: pointer to adapter
4171 * @pRoamInfo: pointer to roam info
4172 *
4173 * This function sends cckm preauth indication to the supplicant
4174 * via wireless custom event.
4175 *
4176 * Return: none
4177 */
4178static void
4179hdd_indicate_cckm_pre_auth(hdd_adapter_t *pAdapter, tCsrRoamInfo *pRoamInfo)
4180{
4181 union iwreq_data wrqu;
4182 char buf[IW_CUSTOM_MAX + 1];
4183 char *pos = buf;
4184 int nBytes = 0, freeBytes = IW_CUSTOM_MAX;
4185
4186 if ((NULL == pAdapter) || (NULL == pRoamInfo))
4187 return;
4188
4189 /* create the event */
4190 memset(&wrqu, '\0', sizeof(wrqu));
4191 memset(buf, '\0', sizeof(buf));
4192
4193 /* Timestamp0 is lower 32 bits and Timestamp1 is upper 32 bits */
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07004194 hdd_info("CCXPREAUTHNOTIFY=" MAC_ADDRESS_STR " %d:%d",
4195 MAC_ADDR_ARRAY(pRoamInfo->bssid.bytes),
4196 pRoamInfo->timestamp[0], pRoamInfo->timestamp[1]);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08004197
4198 nBytes = snprintf(pos, freeBytes, "CCXPREAUTHNOTIFY=");
4199 pos += nBytes;
4200 freeBytes -= nBytes;
4201
Anurag Chouhan600c3a02016-03-01 10:33:54 +05304202 qdf_mem_copy(pos, pRoamInfo->bssid.bytes, QDF_MAC_ADDR_SIZE);
Anurag Chouhan6d760662016-02-20 16:05:43 +05304203 pos += QDF_MAC_ADDR_SIZE;
4204 freeBytes -= QDF_MAC_ADDR_SIZE;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08004205
4206 nBytes = snprintf(pos, freeBytes, " %u:%u",
4207 pRoamInfo->timestamp[0], pRoamInfo->timestamp[1]);
4208 freeBytes -= nBytes;
4209
4210 wrqu.data.pointer = buf;
4211 wrqu.data.length = (IW_CUSTOM_MAX - freeBytes);
4212
4213 /* send the event */
4214 wireless_send_event(pAdapter->dev, IWEVCUSTOM, &wrqu, buf);
4215}
4216
4217/**
4218 * hdd_indicate_ese_adj_ap_rep_ind() - send adjacent AP report indication
4219 * @pAdapter: pointer to adapter
4220 * @pRoamInfo: pointer to roam info
4221 *
4222 * Return: none
4223 */
4224static void
4225hdd_indicate_ese_adj_ap_rep_ind(hdd_adapter_t *pAdapter,
4226 tCsrRoamInfo *pRoamInfo)
4227{
4228 union iwreq_data wrqu;
4229 char buf[IW_CUSTOM_MAX + 1];
4230 int nBytes = 0;
4231
4232 if ((NULL == pAdapter) || (NULL == pRoamInfo))
4233 return;
4234
4235 /* create the event */
4236 memset(&wrqu, '\0', sizeof(wrqu));
4237 memset(buf, '\0', sizeof(buf));
4238
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07004239 hdd_info("CCXADJAPREP=%u", pRoamInfo->tsmRoamDelay);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08004240
4241 nBytes =
4242 snprintf(buf, IW_CUSTOM_MAX, "CCXADJAPREP=%u",
4243 pRoamInfo->tsmRoamDelay);
4244
4245 wrqu.data.pointer = buf;
4246 wrqu.data.length = nBytes;
4247
4248 /* send the event */
4249 wireless_send_event(pAdapter->dev, IWEVCUSTOM, &wrqu, buf);
4250}
4251
4252/**
4253 * hdd_indicate_ese_bcn_report_no_results() - beacon report no scan results
4254 * @pAdapter: pointer to adapter
4255 * @measurementToken: measurement token
4256 * @flag: flag
4257 * @numBss: number of bss
4258 *
4259 * If the measurement is none and no scan results found,
4260 * indicate the supplicant about measurement done.
4261 *
4262 * Return: none
4263 */
4264void
4265hdd_indicate_ese_bcn_report_no_results(const hdd_adapter_t *pAdapter,
4266 const uint16_t measurementToken,
4267 const bool flag, const uint8_t numBss)
4268{
4269 union iwreq_data wrqu;
4270 char buf[IW_CUSTOM_MAX];
4271 char *pos = buf;
4272 int nBytes = 0, freeBytes = IW_CUSTOM_MAX;
4273
4274 memset(&wrqu, '\0', sizeof(wrqu));
4275 memset(buf, '\0', sizeof(buf));
4276
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07004277 hdd_info("CCXBCNREP=%d %d %d", measurementToken,
4278 flag, numBss);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08004279
4280 nBytes =
4281 snprintf(pos, freeBytes, "CCXBCNREP=%d %d %d", measurementToken,
4282 flag, numBss);
4283
4284 wrqu.data.pointer = buf;
4285 wrqu.data.length = nBytes;
4286 /* send the event */
4287 wireless_send_event(pAdapter->dev, IWEVCUSTOM, &wrqu, buf);
4288}
4289
4290/**
4291 * hdd_indicate_ese_bcn_report_ind() - send beacon report indication
4292 * @pAdapter: pointer to adapter
4293 * @pRoamInfo: pointer to roam info
4294 *
4295 * If the measurement is none and no scan results found,
4296 * indicate the supplicant about measurement done.
4297 *
4298 * Return: none
4299 */
4300static void
4301hdd_indicate_ese_bcn_report_ind(const hdd_adapter_t *pAdapter,
4302 const tCsrRoamInfo *pRoamInfo)
4303{
4304 union iwreq_data wrqu;
4305 char buf[IW_CUSTOM_MAX];
4306 char *pos = buf;
4307 int nBytes = 0, freeBytes = IW_CUSTOM_MAX;
4308 uint8_t i = 0, len = 0;
4309 uint8_t tot_bcn_ieLen = 0; /* total size of the beacon report data */
4310 uint8_t lastSent = 0, sendBss = 0;
4311 int bcnRepFieldSize =
4312 sizeof(pRoamInfo->pEseBcnReportRsp->bcnRepBssInfo[0].
4313 bcnReportFields);
4314 uint8_t ieLenByte = 1;
4315 /*
4316 * CCXBCNREP=meas_tok<sp>flag<sp>no_of_bss<sp>tot_bcn_ie_len = 18 bytes
4317 */
4318#define ESEBCNREPHEADER_LEN (18)
4319
4320 if ((NULL == pAdapter) || (NULL == pRoamInfo))
4321 return;
4322
4323 /*
4324 * Custom event can pass maximum of 256 bytes of data,
4325 * based on the IE len we need to identify how many BSS info can
4326 * be filled in to custom event data.
4327 */
4328 /*
4329 * meas_tok<sp>flag<sp>no_of_bss<sp>tot_bcn_ie_len bcn_rep_data
4330 * bcn_rep_data will have bcn_rep_fields,ie_len,ie without any spaces
4331 * CCXBCNREP=meas_tok<sp>flag<sp>no_of_bss<sp>tot_bcn_ie_len = 18 bytes
4332 */
4333
4334 if ((pRoamInfo->pEseBcnReportRsp->flag >> 1)
4335 && (!pRoamInfo->pEseBcnReportRsp->numBss)) {
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07004336 hdd_info("Measurement Done but no scan results");
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08004337 /* If the measurement is none and no scan results found,
4338 indicate the supplicant about measurement done */
4339 hdd_indicate_ese_bcn_report_no_results(
4340 pAdapter,
4341 pRoamInfo->pEseBcnReportRsp->
4342 measurementToken,
4343 pRoamInfo->pEseBcnReportRsp->flag,
4344 pRoamInfo->pEseBcnReportRsp->numBss);
4345 } else {
4346 while (lastSent < pRoamInfo->pEseBcnReportRsp->numBss) {
4347 memset(&wrqu, '\0', sizeof(wrqu));
4348 memset(buf, '\0', sizeof(buf));
4349 tot_bcn_ieLen = 0;
4350 sendBss = 0;
4351 pos = buf;
4352 freeBytes = IW_CUSTOM_MAX;
4353
4354 for (i = lastSent;
4355 i < pRoamInfo->pEseBcnReportRsp->numBss; i++) {
4356 len =
4357 bcnRepFieldSize + ieLenByte +
4358 pRoamInfo->pEseBcnReportRsp->
4359 bcnRepBssInfo[i].ieLen;
4360 if ((len + tot_bcn_ieLen) >
4361 (IW_CUSTOM_MAX - ESEBCNREPHEADER_LEN)) {
4362 break;
4363 }
4364 tot_bcn_ieLen += len;
4365 sendBss++;
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07004366 hdd_info("i(%d) sizeof bcnReportFields(%d) IeLength(%d) Length of Ie(%d) totLen(%d)",
4367 i, bcnRepFieldSize, 1,
4368 pRoamInfo->pEseBcnReportRsp->
4369 bcnRepBssInfo[i].ieLen, tot_bcn_ieLen);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08004370 }
4371
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07004372 hdd_info("Sending %d BSS Info", sendBss);
4373 hdd_info("CCXBCNREP=%d %d %d %d",
4374 pRoamInfo->pEseBcnReportRsp->measurementToken,
4375 pRoamInfo->pEseBcnReportRsp->flag, sendBss,
4376 tot_bcn_ieLen);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08004377
4378 nBytes = snprintf(pos, freeBytes, "CCXBCNREP=%d %d %d ",
4379 pRoamInfo->pEseBcnReportRsp->
4380 measurementToken,
4381 pRoamInfo->pEseBcnReportRsp->flag,
4382 sendBss);
4383 pos += nBytes;
4384 freeBytes -= nBytes;
4385
4386 /* Copy total Beacon report data length */
Anurag Chouhan600c3a02016-03-01 10:33:54 +05304387 qdf_mem_copy(pos, (char *)&tot_bcn_ieLen,
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08004388 sizeof(tot_bcn_ieLen));
4389 pos += sizeof(tot_bcn_ieLen);
4390 freeBytes -= sizeof(tot_bcn_ieLen);
4391
4392 for (i = 0; i < sendBss; i++) {
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07004393 hdd_info("ChanNum(%d) Spare(%d) MeasDuration(%d)"
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08004394 " PhyType(%d) RecvSigPower(%d) ParentTSF(%u)"
4395 " TargetTSF[0](%u) TargetTSF[1](%u) BeaconInterval(%u)"
4396 " CapabilityInfo(%d) BSSID(%02X:%02X:%02X:%02X:%02X:%02X)",
4397 pRoamInfo->pEseBcnReportRsp->
4398 bcnRepBssInfo[i +
4399 lastSent].bcnReportFields.
4400 ChanNum,
4401 pRoamInfo->pEseBcnReportRsp->
4402 bcnRepBssInfo[i +
4403 lastSent].bcnReportFields.
4404 Spare,
4405 pRoamInfo->pEseBcnReportRsp->
4406 bcnRepBssInfo[i +
4407 lastSent].bcnReportFields.
4408 MeasDuration,
4409 pRoamInfo->pEseBcnReportRsp->
4410 bcnRepBssInfo[i +
4411 lastSent].bcnReportFields.
4412 PhyType,
4413 pRoamInfo->pEseBcnReportRsp->
4414 bcnRepBssInfo[i +
4415 lastSent].bcnReportFields.
4416 RecvSigPower,
4417 pRoamInfo->pEseBcnReportRsp->
4418 bcnRepBssInfo[i +
4419 lastSent].bcnReportFields.
4420 ParentTsf,
4421 pRoamInfo->pEseBcnReportRsp->
4422 bcnRepBssInfo[i +
4423 lastSent].bcnReportFields.
4424 TargetTsf[0],
4425 pRoamInfo->pEseBcnReportRsp->
4426 bcnRepBssInfo[i +
4427 lastSent].bcnReportFields.
4428 TargetTsf[1],
4429 pRoamInfo->pEseBcnReportRsp->
4430 bcnRepBssInfo[i +
4431 lastSent].bcnReportFields.
4432 BcnInterval,
4433 pRoamInfo->pEseBcnReportRsp->
4434 bcnRepBssInfo[i +
4435 lastSent].bcnReportFields.
4436 CapabilityInfo,
4437 pRoamInfo->pEseBcnReportRsp->
4438 bcnRepBssInfo[i +
4439 lastSent].bcnReportFields.
4440 Bssid[0],
4441 pRoamInfo->pEseBcnReportRsp->
4442 bcnRepBssInfo[i +
4443 lastSent].bcnReportFields.
4444 Bssid[1],
4445 pRoamInfo->pEseBcnReportRsp->
4446 bcnRepBssInfo[i +
4447 lastSent].bcnReportFields.
4448 Bssid[2],
4449 pRoamInfo->pEseBcnReportRsp->
4450 bcnRepBssInfo[i +
4451 lastSent].bcnReportFields.
4452 Bssid[3],
4453 pRoamInfo->pEseBcnReportRsp->
4454 bcnRepBssInfo[i +
4455 lastSent].bcnReportFields.
4456 Bssid[4],
4457 pRoamInfo->pEseBcnReportRsp->
4458 bcnRepBssInfo[i +
4459 lastSent].bcnReportFields.
4460 Bssid[5]);
4461
4462 /* bcn report fields are copied */
4463 len =
4464 sizeof(pRoamInfo->pEseBcnReportRsp->
4465 bcnRepBssInfo[i +
4466 lastSent].
4467 bcnReportFields);
Anurag Chouhan600c3a02016-03-01 10:33:54 +05304468 qdf_mem_copy(pos,
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08004469 (char *)&pRoamInfo->
4470 pEseBcnReportRsp->bcnRepBssInfo[i +
4471 lastSent].
4472 bcnReportFields, len);
4473 pos += len;
4474 freeBytes -= len;
4475
4476 /* Add 1 byte of ie len */
4477 len =
4478 pRoamInfo->pEseBcnReportRsp->
4479 bcnRepBssInfo[i + lastSent].ieLen;
Anurag Chouhan600c3a02016-03-01 10:33:54 +05304480 qdf_mem_copy(pos, (char *)&len, sizeof(len));
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08004481 pos += sizeof(len);
4482 freeBytes -= sizeof(len);
4483
4484 /* copy IE from scan results */
Anurag Chouhan600c3a02016-03-01 10:33:54 +05304485 qdf_mem_copy(pos,
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08004486 (char *)pRoamInfo->
4487 pEseBcnReportRsp->bcnRepBssInfo[i +
4488 lastSent].
4489 pBuf, len);
4490 pos += len;
4491 freeBytes -= len;
4492 }
4493
4494 wrqu.data.pointer = buf;
4495 wrqu.data.length = IW_CUSTOM_MAX - freeBytes;
4496
4497 /* send the event */
4498 wireless_send_event(pAdapter->dev, IWEVCUSTOM, &wrqu,
4499 buf);
4500 lastSent += sendBss;
4501 }
4502 }
4503}
4504
Srinivas Girigowda515a9ef2015-12-11 11:00:48 -08004505#endif /* FEATURE_WLAN_ESE */
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08004506
4507/**
Komal Seelam98760ba2015-12-15 11:05:18 +05304508 * hdd_is_8021x_sha256_auth_type() - check authentication type to 8021x_sha256
4509 * @pHddStaCtx: Station Context
4510 *
4511 * API to check if the connection authentication type is 8021x_sha256.
4512 *
4513 * Return: bool
4514 */
4515#ifdef WLAN_FEATURE_11W
4516static inline bool hdd_is_8021x_sha256_auth_type(hdd_station_ctx_t *pHddStaCtx)
4517{
4518 return eCSR_AUTH_TYPE_RSN_8021X_SHA256 ==
4519 pHddStaCtx->conn_info.authType;
4520}
4521#else
4522static inline bool hdd_is_8021x_sha256_auth_type(hdd_station_ctx_t *pHddStaCtx)
4523{
4524 return false;
4525}
4526#endif
4527
4528/**
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08004529 * hdd_sme_roam_callback() - hdd sme roam callback
4530 * @pContext: pointer to adapter context
4531 * @pRoamInfo: pointer to roam info
4532 * @roamId: roam id
4533 * @roamStatus: roam status
4534 * @roamResult: roam result
4535 *
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05304536 * Return: QDF_STATUS enumeration
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08004537 */
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05304538QDF_STATUS
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08004539hdd_sme_roam_callback(void *pContext, tCsrRoamInfo *pRoamInfo, uint32_t roamId,
4540 eRoamCmdStatus roamStatus, eCsrRoamResult roamResult)
4541{
Anurag Chouhanf04e84f2016-03-03 10:12:12 +05304542 QDF_STATUS qdf_ret_status = QDF_STATUS_SUCCESS;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08004543 hdd_adapter_t *pAdapter = (hdd_adapter_t *) pContext;
4544 hdd_wext_state_t *pWextState = NULL;
4545 hdd_station_ctx_t *pHddStaCtx = NULL;
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05304546 QDF_STATUS status = QDF_STATUS_SUCCESS;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08004547 hdd_context_t *pHddCtx = NULL;
Manishekar Chandrasekaranec267592016-05-26 19:10:04 +05304548 struct hdd_chan_change_params chan_change;
Selvaraj, Sridharfe696d22016-08-03 21:34:51 +05304549 struct cfg80211_bss *bss_status;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08004550
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07004551 hdd_info("CSR Callback: status= %d result= %d roamID=%d",
4552 roamStatus, roamResult, roamId);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08004553
4554 /* Sanity check */
4555 if ((NULL == pAdapter) || (WLAN_HDD_ADAPTER_MAGIC != pAdapter->magic)) {
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07004556 hdd_alert("invalid adapter or adapter has invalid magic");
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05304557 return QDF_STATUS_E_FAILURE;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08004558 }
4559
4560 pWextState = WLAN_HDD_GET_WEXT_STATE_PTR(pAdapter);
4561 pHddStaCtx = WLAN_HDD_GET_STATION_CTX_PTR(pAdapter);
4562
Anurag Chouhanb2dc16f2016-02-25 11:47:37 +05304563 MTRACE(qdf_trace(QDF_MODULE_ID_HDD, TRACE_CODE_HDD_RX_SME_MSG,
Sreelakshmi Konamkic88f5372015-12-22 12:50:15 +05304564 pAdapter->sessionId, roamStatus));
4565
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08004566 switch (roamStatus) {
4567 case eCSR_ROAM_SESSION_OPENED:
Sreelakshmi Konamki6f3a8652015-09-25 10:58:15 +05304568 set_bit(SME_SESSION_OPENED, &pAdapter->event_flags);
4569 complete(&pAdapter->session_open_comp_var);
Peng Xu66162de2016-02-11 17:01:20 -08004570 hdd_debug("session %d opened", pAdapter->sessionId);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08004571 break;
4572
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08004573 /*
4574 * We did pre-auth,then we attempted a 11r or ese reassoc.
4575 * reassoc failed due to failure, timeout, reject from ap
4576 * in any case tell the OS, our carrier is off and mark
4577 * interface down.
4578 */
4579 case eCSR_ROAM_FT_REASSOC_FAILED:
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07004580 hdd_err("Reassoc Failed with roamStatus: %d roamResult: %d SessionID: %d",
4581 roamStatus, roamResult, pAdapter->sessionId);
Anurag Chouhanf04e84f2016-03-03 10:12:12 +05304582 qdf_ret_status =
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08004583 hdd_dis_connect_handler(pAdapter, pRoamInfo, roamId,
4584 roamStatus, roamResult);
4585 /*
4586 * Check if Mcast/Bcast Filters are set, if yes
4587 * clear the filters here.
4588 */
4589 if ((WLAN_HDD_GET_CTX(pAdapter))->hdd_mcastbcast_filter_set ==
4590 true) {
4591 (WLAN_HDD_GET_CTX(pAdapter))->
4592 hdd_mcastbcast_filter_set = false;
4593 }
4594 pHddStaCtx->ft_carrier_on = false;
4595 pHddStaCtx->hdd_ReassocScenario = false;
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07004596 hdd_info("hdd_ReassocScenario set to: %d, ReAssoc Failed, session: %d",
4597 pHddStaCtx->hdd_ReassocScenario, pAdapter->sessionId);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08004598 break;
4599
4600 case eCSR_ROAM_FT_START:
4601 /*
4602 * When we roam for ESE and 11r, we dont want the OS to be
4603 * informed that the link is down. So mark the link ready for
4604 * ft_start. After this the eCSR_ROAM_SHOULD_ROAM will
4605 * be received. Where in we will not mark the link down
4606 * Also we want to stop tx at this point when we will be
4607 * doing disassoc at this time. This saves 30-60 msec
4608 * after reassoc.
4609 */
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07004610 hdd_info("Disabling queues");
Varun Reddy Yeturu04251862016-09-16 10:33:19 -07004611 hdd_info("Roam Synch Ind: NAPI Serialize ON");
4612 hdd_napi_serialize(1);
Deepak Dhamdherea2df6bb2015-10-29 15:11:06 -07004613 wlan_hdd_netif_queue_control(pAdapter,
4614 WLAN_NETIF_TX_DISABLE,
4615 WLAN_CONTROL_PATH);
4616 status = hdd_roam_deregister_sta(pAdapter,
4617 pHddStaCtx->conn_info.staId[0]);
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05304618 if (!QDF_IS_STATUS_SUCCESS(status))
Anurag Chouhanf04e84f2016-03-03 10:12:12 +05304619 qdf_ret_status = QDF_STATUS_E_FAILURE;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08004620 pHddStaCtx->ft_carrier_on = true;
4621 pHddStaCtx->hdd_ReassocScenario = true;
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07004622 hdd_info("hdd_ReassocScenario set to: %d, due to eCSR_ROAM_FT_START, session: %d",
4623 pHddStaCtx->hdd_ReassocScenario, pAdapter->sessionId);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08004624 break;
Varun Reddy Yeturu04251862016-09-16 10:33:19 -07004625 case eCSR_ROAM_NAPI_OFF:
4626 hdd_info("After Roam Synch Comp: NAPI Serialize OFF");
4627 hdd_napi_serialize(0);
4628 break;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08004629 case eCSR_ROAM_SHOULD_ROAM:
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08004630 /* notify apps that we can't pass traffic anymore */
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07004631 hdd_info("Disabling queues");
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08004632 wlan_hdd_netif_queue_control(pAdapter,
4633 WLAN_NETIF_TX_DISABLE,
4634 WLAN_CONTROL_PATH);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08004635 if (pHddStaCtx->ft_carrier_on == false) {
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08004636 wlan_hdd_netif_queue_control(pAdapter,
4637 WLAN_NETIF_CARRIER_OFF,
4638 WLAN_CONTROL_PATH);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08004639 }
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08004640 break;
4641 case eCSR_ROAM_LOSTLINK:
4642 if (roamResult == eCSR_ROAM_RESULT_LOSTLINK) {
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07004643 hdd_info("Roaming started due to connection lost");
4644 hdd_info("Disabling queues");
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08004645 wlan_hdd_netif_queue_control(pAdapter,
4646 WLAN_NETIF_TX_DISABLE_N_CARRIER,
4647 WLAN_CONTROL_PATH);
4648 break;
4649 }
4650 case eCSR_ROAM_DISASSOCIATED:
4651 {
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07004652 hdd_info("****eCSR_ROAM_DISASSOCIATED****");
Anurag Chouhanf04e84f2016-03-03 10:12:12 +05304653 qdf_ret_status =
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08004654 hdd_dis_connect_handler(pAdapter, pRoamInfo, roamId,
4655 roamStatus, roamResult);
4656 /* Check if Mcast/Bcast Filters are set, if yes clear the filters here */
4657 pHddCtx = WLAN_HDD_GET_CTX(pAdapter);
4658 if (pHddCtx->hdd_mcastbcast_filter_set == true) {
4659 hdd_conf_mcastbcast_filter(pHddCtx, false);
4660
4661 if (true ==
4662 pHddCtx->sus_res_mcastbcast_filter_valid) {
4663 pHddCtx->configuredMcastBcastFilter =
4664 pHddCtx->sus_res_mcastbcast_filter;
4665 pHddCtx->
4666 sus_res_mcastbcast_filter_valid =
4667 false;
4668 }
4669
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07004670 hdd_info("offload: disassociation happening, restoring configuredMcastBcastFilter");
4671 hdd_info("McastBcastFilter = %d",
4672 pHddCtx->configuredMcastBcastFilter);
4673 hdd_info("offload: already called mcastbcast filter");
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08004674 (WLAN_HDD_GET_CTX(pAdapter))->
4675 hdd_mcastbcast_filter_set = false;
4676 }
4677 /* Call to clear any MC Addr List filter applied after
4678 * successful connection.
4679 */
4680 wlan_hdd_set_mc_addr_list(pAdapter, false);
4681 }
4682 break;
4683 case eCSR_ROAM_IBSS_LEAVE:
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07004684 hdd_info("****eCSR_ROAM_IBSS_LEAVE****");
Anurag Chouhanf04e84f2016-03-03 10:12:12 +05304685 qdf_ret_status =
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08004686 hdd_dis_connect_handler(pAdapter, pRoamInfo, roamId,
4687 roamStatus, roamResult);
4688 break;
4689 case eCSR_ROAM_ASSOCIATION_COMPLETION:
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07004690 hdd_info("****eCSR_ROAM_ASSOCIATION_COMPLETION****");
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08004691 /*
4692 * To Do - address probable memory leak with WEP encryption upon
4693 * successful association.
4694 */
4695 if (eCSR_ROAM_RESULT_ASSOCIATED != roamResult) {
4696 /* Clear saved connection information in HDD */
4697 hdd_conn_remove_connect_info(
4698 WLAN_HDD_GET_STATION_CTX_PTR(pAdapter));
4699 }
Anurag Chouhanf04e84f2016-03-03 10:12:12 +05304700 qdf_ret_status =
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08004701 hdd_association_completion_handler(pAdapter, pRoamInfo,
4702 roamId, roamStatus,
4703 roamResult);
4704#ifdef WLAN_FEATURE_ROAM_OFFLOAD
4705 if (pRoamInfo)
4706 pRoamInfo->roamSynchInProgress = false;
4707#endif
4708 break;
Sandeep Puligilla0241f012016-07-21 10:58:53 -07004709 case eCSR_ROAM_CANCELLED:
4710 hdd_info("****eCSR_ROAM_CANCELLED****");
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08004711 case eCSR_ROAM_ASSOCIATION_FAILURE:
Anurag Chouhanf04e84f2016-03-03 10:12:12 +05304712 qdf_ret_status = hdd_association_completion_handler(pAdapter,
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08004713 pRoamInfo,
4714 roamId,
4715 roamStatus,
4716 roamResult);
4717 break;
4718 case eCSR_ROAM_IBSS_IND:
4719 hdd_roam_ibss_indication_handler(pAdapter, pRoamInfo, roamId,
4720 roamStatus, roamResult);
4721 break;
4722
4723 case eCSR_ROAM_CONNECT_STATUS_UPDATE:
Anurag Chouhanf04e84f2016-03-03 10:12:12 +05304724 qdf_ret_status =
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08004725 roam_roam_connect_status_update_handler(pAdapter,
4726 pRoamInfo,
4727 roamId,
4728 roamStatus,
4729 roamResult);
4730 break;
4731
4732 case eCSR_ROAM_MIC_ERROR_IND:
Anurag Chouhanf04e84f2016-03-03 10:12:12 +05304733 qdf_ret_status =
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08004734 hdd_roam_mic_error_indication_handler(pAdapter,
4735 pRoamInfo,
4736 roamId,
4737 roamStatus,
4738 roamResult);
4739 break;
4740
4741 case eCSR_ROAM_SET_KEY_COMPLETE:
4742 {
Anurag Chouhanf04e84f2016-03-03 10:12:12 +05304743 qdf_ret_status =
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08004744 hdd_roam_set_key_complete_handler(pAdapter, pRoamInfo,
4745 roamId, roamStatus,
4746 roamResult);
4747 if (eCSR_ROAM_RESULT_AUTHENTICATED == roamResult) {
4748 pHddStaCtx->hdd_ReassocScenario = false;
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07004749 hdd_info("hdd_ReassocScenario set to: %d, set key complete, session: %d",
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08004750 pHddStaCtx->hdd_ReassocScenario,
4751 pAdapter->sessionId);
4752 }
4753 }
4754#ifdef WLAN_FEATURE_ROAM_OFFLOAD
4755 if (pRoamInfo != NULL)
4756 pRoamInfo->roamSynchInProgress = false;
4757#endif
4758 break;
Deepak Dhamdhere9f09e752016-01-09 23:17:25 -08004759
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08004760 case eCSR_ROAM_FT_RESPONSE:
4761 hdd_send_ft_event(pAdapter);
4762 break;
Deepak Dhamdhere9f09e752016-01-09 23:17:25 -08004763
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08004764 case eCSR_ROAM_PMK_NOTIFY:
Komal Seelam98760ba2015-12-15 11:05:18 +05304765 if (eCSR_AUTH_TYPE_RSN == pHddStaCtx->conn_info.authType
4766 || hdd_is_8021x_sha256_auth_type(pHddStaCtx)) {
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08004767 /* notify the supplicant of a new candidate */
Anurag Chouhanf04e84f2016-03-03 10:12:12 +05304768 qdf_ret_status =
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08004769 wlan_hdd_cfg80211_pmksa_candidate_notify(
4770 pAdapter, pRoamInfo, 1, false);
4771 }
4772 break;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08004773
4774#ifdef FEATURE_WLAN_LFR_METRICS
4775 case eCSR_ROAM_PREAUTH_INIT_NOTIFY:
4776 /* This event is to notify pre-auth initiation */
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05304777 if (QDF_STATUS_SUCCESS !=
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08004778 wlan_hdd_cfg80211_roam_metrics_preauth(pAdapter,
4779 pRoamInfo)) {
Anurag Chouhanf04e84f2016-03-03 10:12:12 +05304780 qdf_ret_status = QDF_STATUS_E_FAILURE;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08004781 }
4782 break;
4783 case eCSR_ROAM_PREAUTH_STATUS_SUCCESS:
4784 /*
4785 * This event will notify pre-auth completion in case of success
4786 */
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05304787 if (QDF_STATUS_SUCCESS !=
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08004788 wlan_hdd_cfg80211_roam_metrics_preauth_status(pAdapter,
4789 pRoamInfo, 1)) {
Anurag Chouhanf04e84f2016-03-03 10:12:12 +05304790 qdf_ret_status = QDF_STATUS_E_FAILURE;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08004791 }
4792 break;
4793 case eCSR_ROAM_PREAUTH_STATUS_FAILURE:
4794 /*
4795 * This event will notify pre-auth completion incase of failure.
4796 */
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05304797 if (QDF_STATUS_SUCCESS !=
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08004798 wlan_hdd_cfg80211_roam_metrics_preauth_status(pAdapter,
4799 pRoamInfo, 0)) {
Anurag Chouhanf04e84f2016-03-03 10:12:12 +05304800 qdf_ret_status = QDF_STATUS_E_FAILURE;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08004801 }
4802 break;
4803 case eCSR_ROAM_HANDOVER_SUCCESS:
4804 /* This event is to notify handover success.
4805 It will be only invoked on success */
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05304806 if (QDF_STATUS_SUCCESS !=
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08004807 wlan_hdd_cfg80211_roam_metrics_handover(pAdapter,
4808 pRoamInfo)) {
Anurag Chouhanf04e84f2016-03-03 10:12:12 +05304809 qdf_ret_status = QDF_STATUS_E_FAILURE;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08004810 }
4811 break;
4812#endif
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08004813 case eCSR_ROAM_REMAIN_CHAN_READY:
4814 hdd_remain_chan_ready_handler(pAdapter, pRoamInfo->roc_scan_id);
4815 break;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08004816#ifdef FEATURE_WLAN_TDLS
4817 case eCSR_ROAM_TDLS_STATUS_UPDATE:
Anurag Chouhanf04e84f2016-03-03 10:12:12 +05304818 qdf_ret_status =
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08004819 hdd_roam_tdls_status_update_handler(pAdapter, pRoamInfo,
4820 roamId,
4821 roamStatus,
4822 roamResult);
4823 break;
4824 case eCSR_ROAM_RESULT_MGMT_TX_COMPLETE_IND:
4825 wlan_hdd_tdls_mgmt_completion_callback(pAdapter,
4826 pRoamInfo->reasonCode);
4827 break;
4828#endif
4829#ifdef WLAN_FEATURE_11W
4830 case eCSR_ROAM_UNPROT_MGMT_FRAME_IND:
4831 hdd_indicate_unprot_mgmt_frame(pAdapter,
4832 pRoamInfo->nFrameLength,
4833 pRoamInfo->pbFrames,
4834 pRoamInfo->frameType);
4835 break;
4836#endif
Srinivas Girigowda515a9ef2015-12-11 11:00:48 -08004837#ifdef FEATURE_WLAN_ESE
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08004838 case eCSR_ROAM_TSM_IE_IND:
4839 hdd_indicate_tsm_ie(pAdapter, pRoamInfo->tsmIe.tsid,
4840 pRoamInfo->tsmIe.state,
4841 pRoamInfo->tsmIe.msmt_interval);
4842 break;
4843
4844 case eCSR_ROAM_CCKM_PREAUTH_NOTIFY:
4845 {
4846 if (eCSR_AUTH_TYPE_CCKM_WPA ==
4847 pHddStaCtx->conn_info.authType
4848 || eCSR_AUTH_TYPE_CCKM_RSN ==
4849 pHddStaCtx->conn_info.authType) {
4850 hdd_indicate_cckm_pre_auth(pAdapter, pRoamInfo);
4851 }
4852 break;
4853 }
4854
4855 case eCSR_ROAM_ESE_ADJ_AP_REPORT_IND:
4856 {
4857 hdd_indicate_ese_adj_ap_rep_ind(pAdapter, pRoamInfo);
4858 break;
4859 }
4860
4861 case eCSR_ROAM_ESE_BCN_REPORT_IND:
4862 {
4863 hdd_indicate_ese_bcn_report_ind(pAdapter, pRoamInfo);
4864 break;
4865 }
Srinivas Girigowda515a9ef2015-12-11 11:00:48 -08004866#endif /* FEATURE_WLAN_ESE */
Manishekar Chandrasekarancb052172016-04-22 12:19:04 +05304867 case eCSR_ROAM_STA_CHANNEL_SWITCH:
4868 hdd_info("channel switch for session:%d to channel:%d",
4869 pAdapter->sessionId, pRoamInfo->chan_info.chan_id);
4870
Manishekar Chandrasekaranec267592016-05-26 19:10:04 +05304871 chan_change.chan = pRoamInfo->chan_info.chan_id;
4872 chan_change.chan_params.ch_width =
4873 pRoamInfo->chan_info.ch_width;
4874 chan_change.chan_params.sec_ch_offset =
4875 pRoamInfo->chan_info.sec_ch_offset;
4876 chan_change.chan_params.center_freq_seg0 =
4877 pRoamInfo->chan_info.band_center_freq1;
4878 chan_change.chan_params.center_freq_seg1 =
4879 pRoamInfo->chan_info.band_center_freq2;
4880
Manishekar Chandrasekarancb052172016-04-22 12:19:04 +05304881 status = hdd_chan_change_notify(pAdapter, pAdapter->dev,
Manishekar Chandrasekaranec267592016-05-26 19:10:04 +05304882 chan_change);
Manishekar Chandrasekarancb052172016-04-22 12:19:04 +05304883 if (QDF_IS_STATUS_ERROR(status))
4884 hdd_err("channel change notification failed");
4885
4886 status = cds_set_hw_mode_on_channel_switch(pAdapter->sessionId);
4887 if (QDF_IS_STATUS_ERROR(status))
4888 hdd_info("set hw mode change not done");
4889 break;
Selvaraj, Sridharfe696d22016-08-03 21:34:51 +05304890 case eCSR_ROAM_UPDATE_SCAN_RESULT:
4891 if ((NULL != pRoamInfo) && (NULL != pRoamInfo->pBssDesc)) {
4892 bss_status = wlan_hdd_cfg80211_inform_bss_frame(
4893 pAdapter, pRoamInfo->pBssDesc);
4894 if (NULL == bss_status)
4895 hdd_info("UPDATE_SCAN_RESULT returned NULL");
4896 else
4897 cfg80211_put_bss(
4898#if (LINUX_VERSION_CODE >= KERNEL_VERSION(3, 9, 0)) || defined(WITH_BACKPORTS)
4899 (WLAN_HDD_GET_CTX(pAdapter))->wiphy,
4900#endif
4901 bss_status);
4902 }
4903 break;
Deepak Dhamdhere5cdce842016-05-31 10:39:12 -07004904 case eCSR_ROAM_NDP_STATUS_UPDATE:
4905 hdd_ndp_event_handler(pAdapter, pRoamInfo, roamId, roamStatus,
4906 roamResult);
4907 break;
Naveen Rawat8cc23b02016-07-14 12:22:56 -07004908 case eCSR_ROAM_START:
4909 hdd_info("Process ROAM_START from firmware");
4910 wlan_hdd_netif_queue_control(pAdapter,
4911 WLAN_NETIF_TX_DISABLE,
4912 WLAN_CONTROL_PATH);
Varun Reddy Yeturu04251862016-09-16 10:33:19 -07004913 hdd_napi_serialize(1);
Naveen Rawat8cc23b02016-07-14 12:22:56 -07004914 cds_set_connection_in_progress(true);
4915 cds_restart_opportunistic_timer(true);
4916 break;
4917 case eCSR_ROAM_ABORT:
4918 hdd_info("Firmware aborted roaming operation, previous connection is still valid");
Varun Reddy Yeturu04251862016-09-16 10:33:19 -07004919 hdd_napi_serialize(0);
Naveen Rawat8cc23b02016-07-14 12:22:56 -07004920 wlan_hdd_netif_queue_control(pAdapter,
4921 WLAN_WAKE_ALL_NETIF_QUEUE,
4922 WLAN_CONTROL_PATH);
4923 cds_set_connection_in_progress(false);
4924 break;
4925
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08004926 default:
4927 break;
4928 }
Anurag Chouhanf04e84f2016-03-03 10:12:12 +05304929 return qdf_ret_status;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08004930}
4931
4932/**
4933 * hdd_translate_rsn_to_csr_auth_type() - Translate RSN to CSR auth type
4934 * @auth_suite: auth suite
4935 *
4936 * Return: eCsrAuthType enumeration
4937 */
4938eCsrAuthType hdd_translate_rsn_to_csr_auth_type(uint8_t auth_suite[4])
4939{
4940 eCsrAuthType auth_type;
4941 /* is the auth type supported? */
4942 if (memcmp(auth_suite, ccp_rsn_oui01, 4) == 0) {
4943 auth_type = eCSR_AUTH_TYPE_RSN;
4944 } else if (memcmp(auth_suite, ccp_rsn_oui02, 4) == 0) {
4945 auth_type = eCSR_AUTH_TYPE_RSN_PSK;
Deepak Dhamdhere9f09e752016-01-09 23:17:25 -08004946 } else if (memcmp(auth_suite, ccp_rsn_oui04, 4) == 0) {
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08004947 /* Check for 11r FT Authentication with PSK */
4948 auth_type = eCSR_AUTH_TYPE_FT_RSN_PSK;
4949 } else if (memcmp(auth_suite, ccp_rsn_oui03, 4) == 0) {
4950 /* Check for 11R FT Authentication with 802.1X */
4951 auth_type = eCSR_AUTH_TYPE_FT_RSN;
4952 } else
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08004953#ifdef FEATURE_WLAN_ESE
4954 if (memcmp(auth_suite, ccp_rsn_oui06, 4) == 0) {
4955 auth_type = eCSR_AUTH_TYPE_CCKM_RSN;
4956 } else
4957#endif /* FEATURE_WLAN_ESE */
4958#ifdef WLAN_FEATURE_11W
4959 if (memcmp(auth_suite, ccp_rsn_oui07, 4) == 0) {
4960 auth_type = eCSR_AUTH_TYPE_RSN_PSK_SHA256;
4961 } else if (memcmp(auth_suite, ccp_rsn_oui08, 4) == 0) {
4962 auth_type = eCSR_AUTH_TYPE_RSN_8021X_SHA256;
4963 } else
4964#endif
4965 {
4966 auth_type = eCSR_AUTH_TYPE_UNKNOWN;
4967 }
4968 return auth_type;
4969}
4970
4971/**
4972 * hdd_translate_wpa_to_csr_auth_type() - Translate WPA to CSR auth type
4973 * @auth_suite: auth suite
4974 *
4975 * Return: eCsrAuthType enumeration
4976 */
4977eCsrAuthType hdd_translate_wpa_to_csr_auth_type(uint8_t auth_suite[4])
4978{
4979 eCsrAuthType auth_type;
4980 /* is the auth type supported? */
4981 if (memcmp(auth_suite, ccp_wpa_oui01, 4) == 0) {
4982 auth_type = eCSR_AUTH_TYPE_WPA;
4983 } else if (memcmp(auth_suite, ccp_wpa_oui02, 4) == 0) {
4984 auth_type = eCSR_AUTH_TYPE_WPA_PSK;
4985 } else
4986#ifdef FEATURE_WLAN_ESE
4987 if (memcmp(auth_suite, ccp_wpa_oui06, 4) == 0) {
4988 auth_type = eCSR_AUTH_TYPE_CCKM_WPA;
4989 } else
4990#endif /* FEATURE_WLAN_ESE */
4991 {
4992 auth_type = eCSR_AUTH_TYPE_UNKNOWN;
4993 }
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07004994 hdd_info("auth_type: %d", auth_type);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08004995 return auth_type;
4996}
4997
4998/**
4999 * hdd_translate_rsn_to_csr_encryption_type() -
5000 * Translate RSN to CSR encryption type
5001 * @cipher_suite: cipher suite
5002 *
5003 * Return: eCsrEncryptionType enumeration
5004 */
5005eCsrEncryptionType
5006hdd_translate_rsn_to_csr_encryption_type(uint8_t cipher_suite[4])
5007{
5008 eCsrEncryptionType cipher_type;
5009
5010 if (memcmp(cipher_suite, ccp_rsn_oui04, 4) == 0)
5011 cipher_type = eCSR_ENCRYPT_TYPE_AES;
5012 else if (memcmp(cipher_suite, ccp_rsn_oui02, 4) == 0)
5013 cipher_type = eCSR_ENCRYPT_TYPE_TKIP;
5014 else if (memcmp(cipher_suite, ccp_rsn_oui00, 4) == 0)
5015 cipher_type = eCSR_ENCRYPT_TYPE_NONE;
5016 else if (memcmp(cipher_suite, ccp_rsn_oui01, 4) == 0)
5017 cipher_type = eCSR_ENCRYPT_TYPE_WEP40_STATICKEY;
5018 else if (memcmp(cipher_suite, ccp_rsn_oui05, 4) == 0)
5019 cipher_type = eCSR_ENCRYPT_TYPE_WEP104_STATICKEY;
5020 else
5021 cipher_type = eCSR_ENCRYPT_TYPE_FAILED;
5022
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07005023 hdd_info("cipher_type: %d", cipher_type);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08005024 return cipher_type;
5025}
5026
5027/**
5028 * hdd_translate_wpa_to_csr_encryption_type() -
5029 * Translate WPA to CSR encryption type
5030 * @cipher_suite: cipher suite
5031 *
5032 * Return: eCsrEncryptionType enumeration
5033 */
5034eCsrEncryptionType
5035hdd_translate_wpa_to_csr_encryption_type(uint8_t cipher_suite[4])
5036{
5037 eCsrEncryptionType cipher_type;
5038
5039 if (memcmp(cipher_suite, ccp_wpa_oui04, 4) == 0)
5040 cipher_type = eCSR_ENCRYPT_TYPE_AES;
5041 else if (memcmp(cipher_suite, ccp_wpa_oui02, 4) == 0)
5042 cipher_type = eCSR_ENCRYPT_TYPE_TKIP;
5043 else if (memcmp(cipher_suite, ccp_wpa_oui00, 4) == 0)
5044 cipher_type = eCSR_ENCRYPT_TYPE_NONE;
5045 else if (memcmp(cipher_suite, ccp_wpa_oui01, 4) == 0)
5046 cipher_type = eCSR_ENCRYPT_TYPE_WEP40_STATICKEY;
5047 else if (memcmp(cipher_suite, ccp_wpa_oui05, 4) == 0)
5048 cipher_type = eCSR_ENCRYPT_TYPE_WEP104_STATICKEY;
5049 else
5050 cipher_type = eCSR_ENCRYPT_TYPE_FAILED;
5051
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07005052 hdd_info("cipher_type: %d", cipher_type);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08005053 return cipher_type;
5054}
5055
5056/**
5057 * hdd_process_genie() - process gen ie
5058 * @pAdapter: pointer to adapter
5059 * @bssid: pointer to mac address
5060 * @pEncryptType: pointer to encryption type
5061 * @mcEncryptType: pointer to multicast encryption type
5062 * @pAuthType: pointer to auth type
5063 *
5064 * Return: 0 on success, error number otherwise
5065 */
5066static int32_t hdd_process_genie(hdd_adapter_t *pAdapter,
5067 u8 *bssid,
5068 eCsrEncryptionType *pEncryptType,
5069 eCsrEncryptionType *mcEncryptType,
5070 eCsrAuthType *pAuthType,
5071#ifdef WLAN_FEATURE_11W
5072 uint8_t *pMfpRequired, uint8_t *pMfpCapable,
5073#endif
5074 uint16_t gen_ie_len, uint8_t *gen_ie)
5075{
5076 tHalHandle halHandle = WLAN_HDD_GET_HAL_CTX(pAdapter);
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05305077 QDF_STATUS result;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08005078 tDot11fIERSN dot11RSNIE;
5079 tDot11fIEWPA dot11WPAIE;
5080 uint32_t i;
5081 uint8_t *pRsnIe;
5082 uint16_t RSNIeLen;
5083 tPmkidCacheInfo PMKIDCache[4]; /* Local transfer memory */
5084 bool updatePMKCache = false;
5085
5086 /*
5087 * Clear struct of tDot11fIERSN and tDot11fIEWPA specifically
5088 * setting present flag to 0.
5089 */
5090 memset(&dot11WPAIE, 0, sizeof(tDot11fIEWPA));
5091 memset(&dot11RSNIE, 0, sizeof(tDot11fIERSN));
5092
5093 /* Type check */
5094 if (gen_ie[0] == DOT11F_EID_RSN) {
5095 /* Validity checks */
5096 if ((gen_ie_len < DOT11F_IE_RSN_MIN_LEN) ||
5097 (gen_ie_len > DOT11F_IE_RSN_MAX_LEN)) {
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07005098 hdd_err("Invalid DOT11F RSN IE length :%d",
5099 gen_ie_len);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08005100 return -EINVAL;
5101 }
5102 /* Skip past the EID byte and length byte */
5103 pRsnIe = gen_ie + 2;
5104 RSNIeLen = gen_ie_len - 2;
5105 /* Unpack the RSN IE */
5106 dot11f_unpack_ie_rsn((tpAniSirGlobal) halHandle,
5107 pRsnIe, RSNIeLen, &dot11RSNIE);
5108 /* Copy out the encryption and authentication types */
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07005109 hdd_info("pairwise cipher suite count: %d",
5110 dot11RSNIE.pwise_cipher_suite_count);
5111 hdd_info("authentication suite count: %d",
5112 dot11RSNIE.akm_suite_count);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08005113 /*Here we have followed the apple base code,
5114 but probably I suspect we can do something different */
5115 /* dot11RSNIE.akm_suite_count */
5116 /* Just translate the FIRST one */
5117 *pAuthType =
5118 hdd_translate_rsn_to_csr_auth_type(
5119 dot11RSNIE.akm_suites[0]);
5120 /* dot11RSNIE.pwise_cipher_suite_count */
5121 *pEncryptType =
5122 hdd_translate_rsn_to_csr_encryption_type(
5123 dot11RSNIE.pwise_cipher_suites[0]);
5124 /* dot11RSNIE.gp_cipher_suite_count */
5125 *mcEncryptType =
5126 hdd_translate_rsn_to_csr_encryption_type(
5127 dot11RSNIE.gp_cipher_suite);
5128#ifdef WLAN_FEATURE_11W
5129 *pMfpRequired = (dot11RSNIE.RSN_Cap[0] >> 6) & 0x1;
5130 *pMfpCapable = (dot11RSNIE.RSN_Cap[0] >> 7) & 0x1;
5131#endif
5132 /* Set the PMKSA ID Cache for this interface */
5133 for (i = 0; i < dot11RSNIE.pmkid_count; i++) {
5134 if (is_zero_ether_addr(bssid)) {
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07005135 hdd_err("MAC address is all zeroes");
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08005136 break;
5137 }
5138 updatePMKCache = true;
5139 /*
5140 * For right now, I assume setASSOCIATE() has passed
5141 * in the bssid.
5142 */
Anurag Chouhan600c3a02016-03-01 10:33:54 +05305143 qdf_mem_copy(PMKIDCache[i].BSSID.bytes,
Anurag Chouhan6d760662016-02-20 16:05:43 +05305144 bssid, QDF_MAC_ADDR_SIZE);
Anurag Chouhan600c3a02016-03-01 10:33:54 +05305145 qdf_mem_copy(PMKIDCache[i].PMKID,
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08005146 dot11RSNIE.pmkid[i], CSR_RSN_PMKID_SIZE);
5147 }
5148
5149 if (updatePMKCache) {
5150 /*
5151 * Calling csr_roam_set_pmkid_cache to configure the
5152 * PMKIDs into the cache.
5153 */
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07005154 hdd_info("Calling sme_roam_set_pmkid_cache with cache entry %d.",
5155 i);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08005156 /* Finally set the PMKSA ID Cache in CSR */
5157 result =
5158 sme_roam_set_pmkid_cache(halHandle,
5159 pAdapter->sessionId,
5160 PMKIDCache,
5161 dot11RSNIE.pmkid_count,
5162 false);
5163 }
5164 } else if (gen_ie[0] == DOT11F_EID_WPA) {
5165 /* Validity checks */
5166 if ((gen_ie_len < DOT11F_IE_WPA_MIN_LEN) ||
5167 (gen_ie_len > DOT11F_IE_WPA_MAX_LEN)) {
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07005168 hdd_err("Invalid DOT11F WPA IE length :%d",
5169 gen_ie_len);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08005170 return -EINVAL;
5171 }
5172 /* Skip past the EID and length byte - and four byte WiFi OUI */
5173 pRsnIe = gen_ie + 2 + 4;
5174 RSNIeLen = gen_ie_len - (2 + 4);
5175 /* Unpack the WPA IE */
5176 dot11f_unpack_ie_wpa((tpAniSirGlobal) halHandle,
5177 pRsnIe, RSNIeLen, &dot11WPAIE);
5178 /* Copy out the encryption and authentication types */
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07005179 hdd_info("WPA unicast cipher suite count: %d",
5180 dot11WPAIE.unicast_cipher_count);
5181 hdd_info("WPA authentication suite count: %d",
5182 dot11WPAIE.auth_suite_count);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08005183 /* dot11WPAIE.auth_suite_count */
5184 /* Just translate the FIRST one */
5185 *pAuthType =
5186 hdd_translate_wpa_to_csr_auth_type(
5187 dot11WPAIE.auth_suites[0]);
5188 /* dot11WPAIE.unicast_cipher_count */
5189 *pEncryptType =
5190 hdd_translate_wpa_to_csr_encryption_type(
5191 dot11WPAIE.unicast_ciphers[0]);
5192 /* dot11WPAIE.unicast_cipher_count */
5193 *mcEncryptType =
5194 hdd_translate_wpa_to_csr_encryption_type(
5195 dot11WPAIE.multicast_cipher);
5196 } else {
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07005197 hdd_warn("gen_ie[0]: %d", gen_ie[0]);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08005198 return -EINVAL;
5199 }
5200 return 0;
5201}
5202
5203/**
5204 * hdd_set_genie_to_csr() - set genie to csr
5205 * @pAdapter: pointer to adapter
5206 * @RSNAuthType: pointer to auth type
5207 *
5208 * Return: 0 on success, error number otherwise
5209 */
5210int hdd_set_genie_to_csr(hdd_adapter_t *pAdapter, eCsrAuthType *RSNAuthType)
5211{
5212 hdd_wext_state_t *pWextState = WLAN_HDD_GET_WEXT_STATE_PTR(pAdapter);
5213 uint32_t status = 0;
5214 eCsrEncryptionType RSNEncryptType;
5215 eCsrEncryptionType mcRSNEncryptType;
5216#ifdef WLAN_FEATURE_11W
5217 uint8_t RSNMfpRequired = 0;
5218 uint8_t RSNMfpCapable = 0;
5219#endif
5220 u8 bssid[ETH_ALEN]; /* MAC address of assoc peer */
5221 /* MAC address of assoc peer */
5222 /* But, this routine is only called when we are NOT associated. */
Anurag Chouhan600c3a02016-03-01 10:33:54 +05305223 qdf_mem_copy(bssid,
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08005224 pWextState->roamProfile.BSSIDs.bssid,
5225 sizeof(bssid));
5226 if (pWextState->WPARSNIE[0] == DOT11F_EID_RSN
5227 || pWextState->WPARSNIE[0] == DOT11F_EID_WPA) {
5228 /* continue */
5229 } else {
5230 return 0;
5231 }
5232 /* The actual processing may eventually be more extensive than this. */
5233 /* Right now, just consume any PMKIDs that are sent in by the app. */
5234 status = hdd_process_genie(pAdapter, bssid,
5235 &RSNEncryptType,
5236 &mcRSNEncryptType, RSNAuthType,
5237#ifdef WLAN_FEATURE_11W
5238 &RSNMfpRequired, &RSNMfpCapable,
5239#endif
5240 pWextState->WPARSNIE[1] + 2,
5241 pWextState->WPARSNIE);
5242 if (status == 0) {
5243 /*
5244 * Now copy over all the security attributes
5245 * you have parsed out.
5246 */
5247 pWextState->roamProfile.EncryptionType.numEntries = 1;
5248 pWextState->roamProfile.mcEncryptionType.numEntries = 1;
5249
5250 pWextState->roamProfile.EncryptionType.encryptionType[0] = RSNEncryptType; /* Use the cipher type in the RSN IE */
5251 pWextState->roamProfile.mcEncryptionType.encryptionType[0] =
5252 mcRSNEncryptType;
5253
Krunal Sonibe766b02016-03-10 13:00:44 -08005254 if ((QDF_IBSS_MODE == pAdapter->device_mode) &&
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08005255 ((eCSR_ENCRYPT_TYPE_AES == mcRSNEncryptType) ||
5256 (eCSR_ENCRYPT_TYPE_TKIP == mcRSNEncryptType))) {
5257 /*
5258 * For wpa none supplicant sends the WPA IE with unicast
5259 * cipher as eCSR_ENCRYPT_TYPE_NONE ,where as the
5260 * multicast cipher as either AES/TKIP based on group
5261 * cipher configuration mentioned in the
5262 * wpa_supplicant.conf.
5263 */
5264
5265 /* Set the unicast cipher same as multicast cipher */
5266 pWextState->roamProfile.EncryptionType.encryptionType[0]
5267 = mcRSNEncryptType;
5268 }
5269#ifdef WLAN_FEATURE_11W
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07005270 hdd_info("RSNMfpRequired = %d, RSNMfpCapable = %d",
5271 RSNMfpRequired, RSNMfpCapable);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08005272 pWextState->roamProfile.MFPRequired = RSNMfpRequired;
5273 pWextState->roamProfile.MFPCapable = RSNMfpCapable;
5274#endif
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07005275 hdd_info("CSR AuthType = %d, EncryptionType = %d mcEncryptionType = %d",
5276 *RSNAuthType, RSNEncryptType, mcRSNEncryptType);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08005277 }
5278 return 0;
5279}
5280
5281/**
5282 * hdd_set_csr_auth_type() - set csr auth type
5283 * @pAdapter: pointer to adapter
5284 * @RSNAuthType: auth type
5285 *
5286 * Return: 0 on success, error number otherwise
5287 */
5288int hdd_set_csr_auth_type(hdd_adapter_t *pAdapter, eCsrAuthType RSNAuthType)
5289{
5290 hdd_wext_state_t *pWextState = WLAN_HDD_GET_WEXT_STATE_PTR(pAdapter);
5291 tCsrRoamProfile *pRoamProfile = &(pWextState->roamProfile);
5292 hdd_station_ctx_t *pHddStaCtx = WLAN_HDD_GET_STATION_CTX_PTR(pAdapter);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08005293
5294 pRoamProfile->AuthType.numEntries = 1;
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07005295 hdd_info("pHddStaCtx->conn_info.authType = %d",
5296 pHddStaCtx->conn_info.authType);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08005297
5298 switch (pHddStaCtx->conn_info.authType) {
5299 case eCSR_AUTH_TYPE_OPEN_SYSTEM:
5300#ifdef FEATURE_WLAN_ESE
5301 case eCSR_AUTH_TYPE_CCKM_WPA:
5302 case eCSR_AUTH_TYPE_CCKM_RSN:
5303#endif
5304 if (pWextState->wpaVersion & IW_AUTH_WPA_VERSION_DISABLED) {
5305
5306 pRoamProfile->AuthType.authType[0] =
5307 eCSR_AUTH_TYPE_OPEN_SYSTEM;
5308 } else if (pWextState->wpaVersion & IW_AUTH_WPA_VERSION_WPA) {
5309
5310#ifdef FEATURE_WLAN_ESE
5311 if ((RSNAuthType == eCSR_AUTH_TYPE_CCKM_WPA) &&
5312 ((pWextState->authKeyMgmt & IW_AUTH_KEY_MGMT_802_1X)
5313 == IW_AUTH_KEY_MGMT_802_1X)) {
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07005314 hdd_info("set authType to CCKM WPA. AKM also 802.1X.");
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08005315 pRoamProfile->AuthType.authType[0] =
5316 eCSR_AUTH_TYPE_CCKM_WPA;
5317 } else if (RSNAuthType == eCSR_AUTH_TYPE_CCKM_WPA) {
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07005318 hdd_info("Last chance to set authType to CCKM WPA.");
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08005319 pRoamProfile->AuthType.authType[0] =
5320 eCSR_AUTH_TYPE_CCKM_WPA;
5321 } else
5322#endif
5323 if ((pWextState->
5324 authKeyMgmt & IW_AUTH_KEY_MGMT_802_1X)
5325 == IW_AUTH_KEY_MGMT_802_1X) {
5326 pRoamProfile->AuthType.authType[0] =
5327 eCSR_AUTH_TYPE_WPA;
5328 } else
5329 if ((pWextState->authKeyMgmt & IW_AUTH_KEY_MGMT_PSK)
5330 == IW_AUTH_KEY_MGMT_PSK) {
5331 pRoamProfile->AuthType.authType[0] =
5332 eCSR_AUTH_TYPE_WPA_PSK;
5333 } else {
5334 pRoamProfile->AuthType.authType[0] =
5335 eCSR_AUTH_TYPE_WPA_NONE;
5336 }
5337 }
5338 if (pWextState->wpaVersion & IW_AUTH_WPA_VERSION_WPA2) {
5339#ifdef FEATURE_WLAN_ESE
5340 if ((RSNAuthType == eCSR_AUTH_TYPE_CCKM_RSN) &&
5341 ((pWextState->authKeyMgmt & IW_AUTH_KEY_MGMT_802_1X)
5342 == IW_AUTH_KEY_MGMT_802_1X)) {
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07005343 hdd_info("set authType to CCKM RSN. AKM also 802.1X.");
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08005344 pRoamProfile->AuthType.authType[0] =
5345 eCSR_AUTH_TYPE_CCKM_RSN;
5346 } else if (RSNAuthType == eCSR_AUTH_TYPE_CCKM_RSN) {
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07005347 hdd_info("Last chance to set authType to CCKM RSN.");
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08005348 pRoamProfile->AuthType.authType[0] =
5349 eCSR_AUTH_TYPE_CCKM_RSN;
5350 } else
5351#endif
5352
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08005353 if ((RSNAuthType == eCSR_AUTH_TYPE_FT_RSN) &&
5354 ((pWextState->
5355 authKeyMgmt & IW_AUTH_KEY_MGMT_802_1X)
5356 == IW_AUTH_KEY_MGMT_802_1X)) {
5357 pRoamProfile->AuthType.authType[0] =
5358 eCSR_AUTH_TYPE_FT_RSN;
5359 } else if ((RSNAuthType == eCSR_AUTH_TYPE_FT_RSN_PSK)
5360 &&
5361 ((pWextState->
5362 authKeyMgmt & IW_AUTH_KEY_MGMT_PSK)
5363 == IW_AUTH_KEY_MGMT_PSK)) {
5364 pRoamProfile->AuthType.authType[0] =
5365 eCSR_AUTH_TYPE_FT_RSN_PSK;
5366 } else
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08005367
5368#ifdef WLAN_FEATURE_11W
5369 if (RSNAuthType == eCSR_AUTH_TYPE_RSN_PSK_SHA256) {
5370 pRoamProfile->AuthType.authType[0] =
5371 eCSR_AUTH_TYPE_RSN_PSK_SHA256;
5372 } else if (RSNAuthType ==
5373 eCSR_AUTH_TYPE_RSN_8021X_SHA256) {
5374 pRoamProfile->AuthType.authType[0] =
5375 eCSR_AUTH_TYPE_RSN_8021X_SHA256;
5376 } else
5377#endif
5378
5379 if ((pWextState->
5380 authKeyMgmt & IW_AUTH_KEY_MGMT_802_1X)
5381 == IW_AUTH_KEY_MGMT_802_1X) {
5382 pRoamProfile->AuthType.authType[0] =
5383 eCSR_AUTH_TYPE_RSN;
5384 } else
5385 if ((pWextState->authKeyMgmt & IW_AUTH_KEY_MGMT_PSK)
5386 == IW_AUTH_KEY_MGMT_PSK) {
5387 pRoamProfile->AuthType.authType[0] =
5388 eCSR_AUTH_TYPE_RSN_PSK;
5389 } else {
5390 pRoamProfile->AuthType.authType[0] =
5391 eCSR_AUTH_TYPE_UNKNOWN;
5392 }
5393 }
5394 break;
5395
5396 case eCSR_AUTH_TYPE_SHARED_KEY:
5397
5398 pRoamProfile->AuthType.authType[0] = eCSR_AUTH_TYPE_SHARED_KEY;
5399 break;
5400 default:
5401
5402#ifdef FEATURE_WLAN_ESE
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07005403 hdd_info("In default, unknown auth type.");
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08005404#endif /* FEATURE_WLAN_ESE */
5405 pRoamProfile->AuthType.authType[0] = eCSR_AUTH_TYPE_UNKNOWN;
5406 break;
5407 }
5408
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07005409 hdd_info("Set roam Authtype to %d",
5410 pWextState->roamProfile.AuthType.authType[0]);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08005411
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08005412 return 0;
5413}
5414
5415/**
5416 * __iw_set_essid() - This function sets the ssid received from wpa_supplicant
5417 * to the CSR roam profile.
5418 *
5419 * @dev: Pointer to the net device.
5420 * @info: Pointer to the iw_request_info.
5421 * @wrqu: Pointer to the iwreq_data.
5422 * @extra: Pointer to the data.
5423 *
5424 * Return: 0 for success, error number on failure
5425 */
5426static int __iw_set_essid(struct net_device *dev,
5427 struct iw_request_info *info,
5428 union iwreq_data *wrqu, char *extra)
5429{
5430 unsigned long rc;
5431 uint32_t status = 0;
5432 hdd_wext_state_t *pWextState;
5433 hdd_adapter_t *pAdapter = WLAN_HDD_GET_PRIV_PTR(dev);
5434 hdd_context_t *hdd_ctx;
5435 uint32_t roamId;
5436 tCsrRoamProfile *pRoamProfile;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08005437 eCsrAuthType RSNAuthType;
5438 tHalHandle hHal = WLAN_HDD_GET_HAL_CTX(pAdapter);
5439 hdd_station_ctx_t *pHddStaCtx = WLAN_HDD_GET_STATION_CTX_PTR(pAdapter);
5440 int ret;
5441
Jeff Johnsonb25dcb12016-02-11 17:46:42 -08005442 ENTER_DEV(dev);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08005443
5444 hdd_ctx = WLAN_HDD_GET_CTX(pAdapter);
5445 ret = wlan_hdd_validate_context(hdd_ctx);
Abhishek Singh23edd1c2016-05-05 11:56:06 +05305446 if (ret)
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08005447 return ret;
5448
Krunal Sonibe766b02016-03-10 13:00:44 -08005449 if (pAdapter->device_mode != QDF_STA_MODE &&
Jeff Johnsond6e4b632016-10-03 13:49:27 -07005450 pAdapter->device_mode != QDF_IBSS_MODE &&
5451 pAdapter->device_mode != QDF_P2P_CLIENT_MODE) {
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07005452 hdd_warn("device mode %s(%d) is not allowed",
5453 hdd_device_mode_to_string(pAdapter->device_mode),
5454 pAdapter->device_mode);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08005455 return -EINVAL;
5456 }
5457
5458 pWextState = WLAN_HDD_GET_WEXT_STATE_PTR(pAdapter);
5459
5460 if (pWextState->mTKIPCounterMeasures == TKIP_COUNTER_MEASURE_STARTED) {
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07005461 hdd_info("Counter measure is in progress");
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08005462 return -EBUSY;
5463 }
5464 if (SIR_MAC_MAX_SSID_LENGTH < wrqu->essid.length)
5465 return -EINVAL;
5466
5467 pRoamProfile = &pWextState->roamProfile;
Jeff Johnsond6e4b632016-10-03 13:49:27 -07005468 if (hdd_conn_is_connected(pHddStaCtx) ||
5469 (pAdapter->device_mode == QDF_IBSS_MODE)) {
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05305470 QDF_STATUS qdf_status;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08005471
5472 /* Need to issue a disconnect to CSR. */
5473 INIT_COMPLETION(pAdapter->disconnect_comp_var);
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05305474 qdf_status = sme_roam_disconnect(hHal, pAdapter->sessionId,
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08005475 eCSR_DISCONNECT_REASON_UNSPECIFIED);
5476
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05305477 if (QDF_STATUS_SUCCESS == qdf_status) {
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08005478 rc = wait_for_completion_timeout(&pAdapter->
5479 disconnect_comp_var,
5480 msecs_to_jiffies
5481 (WLAN_WAIT_TIME_DISCONNECT));
5482 if (!rc)
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07005483 hdd_err("Disconnect event timed out");
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08005484 }
5485 }
5486
5487 /*
5488 * when cfg80211 defined, wpa_supplicant wext driver uses
5489 * zero-length, null-string ssid for force disconnection.
5490 * after disconnection (if previously connected) and cleaning ssid,
5491 * driver MUST return success.
5492 */
5493 if (0 == wrqu->essid.length)
5494 return 0;
5495
5496 status = hdd_wmm_get_uapsd_mask(pAdapter,
5497 &pWextState->roamProfile.uapsd_mask);
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05305498 if (QDF_STATUS_SUCCESS != status)
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08005499 pWextState->roamProfile.uapsd_mask = 0;
5500
5501 pWextState->roamProfile.SSIDs.numOfSSIDs = 1;
5502
5503 pWextState->roamProfile.SSIDs.SSIDList->SSID.length =
5504 wrqu->essid.length;
5505
Anurag Chouhan600c3a02016-03-01 10:33:54 +05305506 qdf_mem_zero(pWextState->roamProfile.SSIDs.SSIDList->SSID.ssId,
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08005507 sizeof(pWextState->roamProfile.SSIDs.SSIDList->SSID.ssId));
Anurag Chouhan600c3a02016-03-01 10:33:54 +05305508 qdf_mem_copy((void *)(pWextState->roamProfile.SSIDs.SSIDList->SSID.
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08005509 ssId), extra, wrqu->essid.length);
5510 if (IW_AUTH_WPA_VERSION_WPA == pWextState->wpaVersion
5511 || IW_AUTH_WPA_VERSION_WPA2 == pWextState->wpaVersion) {
5512
5513 /* set gen ie */
5514 hdd_set_genie_to_csr(pAdapter, &RSNAuthType);
5515
5516 /* set auth */
5517 hdd_set_csr_auth_type(pAdapter, RSNAuthType);
5518 }
5519#ifdef FEATURE_WLAN_WAPI
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07005520 hdd_notice("Setting WAPI AUTH Type and Encryption Mode values");
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08005521 if (pAdapter->wapi_info.nWapiMode) {
5522 switch (pAdapter->wapi_info.wapiAuthMode) {
5523 case WAPI_AUTH_MODE_PSK:
5524 {
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07005525 hdd_notice("WAPI AUTH TYPE: PSK: %d",
5526 pAdapter->wapi_info.wapiAuthMode);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08005527 pRoamProfile->AuthType.numEntries = 1;
5528 pRoamProfile->AuthType.authType[0] =
5529 eCSR_AUTH_TYPE_WAPI_WAI_PSK;
5530 break;
5531 }
5532 case WAPI_AUTH_MODE_CERT:
5533 {
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07005534 hdd_notice("WAPI AUTH TYPE: CERT: %d",
5535 pAdapter->wapi_info.wapiAuthMode);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08005536 pRoamProfile->AuthType.numEntries = 1;
5537 pRoamProfile->AuthType.authType[0] =
5538 eCSR_AUTH_TYPE_WAPI_WAI_CERTIFICATE;
5539 break;
5540 }
5541 } /* End of switch */
5542 if (pAdapter->wapi_info.wapiAuthMode == WAPI_AUTH_MODE_PSK ||
5543 pAdapter->wapi_info.wapiAuthMode == WAPI_AUTH_MODE_CERT) {
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07005544 hdd_notice("WAPI PAIRWISE/GROUP ENCRYPTION: WPI");
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08005545 pRoamProfile->EncryptionType.numEntries = 1;
5546 pRoamProfile->EncryptionType.encryptionType[0] =
5547 eCSR_ENCRYPT_TYPE_WPI;
5548 pRoamProfile->mcEncryptionType.numEntries = 1;
5549 pRoamProfile->mcEncryptionType.encryptionType[0] =
5550 eCSR_ENCRYPT_TYPE_WPI;
5551 }
5552 }
5553#endif /* FEATURE_WLAN_WAPI */
5554 /* if previous genIE is not NULL, update AssocIE */
5555 if (0 != pWextState->genIE.length) {
5556 memset(&pWextState->assocAddIE, 0,
5557 sizeof(pWextState->assocAddIE));
5558 memcpy(pWextState->assocAddIE.addIEdata,
5559 pWextState->genIE.addIEdata, pWextState->genIE.length);
5560 pWextState->assocAddIE.length = pWextState->genIE.length;
5561 pWextState->roamProfile.pAddIEAssoc =
5562 pWextState->assocAddIE.addIEdata;
5563 pWextState->roamProfile.nAddIEAssocLength =
5564 pWextState->assocAddIE.length;
5565
5566 /* clear previous genIE after use it */
5567 memset(&pWextState->genIE, 0, sizeof(pWextState->genIE));
5568 }
5569
5570 /*
5571 * Assumes it is not WPS Association by default, except when
5572 * pAddIEAssoc has WPS IE.
5573 */
5574 pWextState->roamProfile.bWPSAssociation = false;
5575
5576 if (NULL != wlan_hdd_get_wps_ie_ptr(pWextState->roamProfile.pAddIEAssoc,
5577 pWextState->roamProfile.
5578 nAddIEAssocLength))
5579 pWextState->roamProfile.bWPSAssociation = true;
5580
5581 /* Disable auto BMPS entry by PMC until DHCP is done */
5582 sme_set_dhcp_till_power_active_flag(WLAN_HDD_GET_HAL_CTX(pAdapter),
5583 true);
5584
5585 pWextState->roamProfile.csrPersona = pAdapter->device_mode;
5586
5587 if (eCSR_BSS_TYPE_START_IBSS == pRoamProfile->BSSType) {
Naveen Rawatc77e6e72016-08-05 15:19:03 -07005588 pRoamProfile->ch_params.ch_width = 0;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08005589 hdd_select_cbmode(pAdapter,
Naveen Rawatc77e6e72016-08-05 15:19:03 -07005590 (WLAN_HDD_GET_CTX(pAdapter))->config->AdHocChannel5G,
5591 &pRoamProfile->ch_params);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08005592 }
Naveen Rawatc77e6e72016-08-05 15:19:03 -07005593
Agrawal Ashish6b015762016-05-05 11:22:18 +05305594 /*
5595 * Change conn_state to connecting before sme_roam_connect(),
5596 * because sme_roam_connect() has a direct path to call
5597 * hdd_sme_roam_callback(), which will change the conn_state
5598 * If direct path, conn_state will be accordingly changed to
5599 * NotConnected or Associated by either
5600 * hdd_association_completion_handler() or hdd_dis_connect_handler()
5601 * in sme_RoamCallback()if sme_RomConnect is to be queued,
5602 * Connecting state will remain until it is completed.
5603 *
5604 * If connection state is not changed,
5605 * connection state will remain in eConnectionState_NotConnected state.
5606 * In hdd_association_completion_handler, "hddDisconInProgress" is
5607 * set to true if conn state is eConnectionState_NotConnected.
5608 * If "hddDisconInProgress" is set to true then cfg80211 layer is not
5609 * informed of connect result indication which is an issue.
5610 */
5611 if (QDF_STA_MODE == pAdapter->device_mode ||
Abhishek Singh23edd1c2016-05-05 11:56:06 +05305612 QDF_P2P_CLIENT_MODE == pAdapter->device_mode)
Agrawal Ashish6b015762016-05-05 11:22:18 +05305613 hdd_conn_set_connection_state(pAdapter,
5614 eConnectionState_Connecting);
Agrawal Ashish6b015762016-05-05 11:22:18 +05305615
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08005616 status = sme_roam_connect(hHal, pAdapter->sessionId,
5617 &(pWextState->roamProfile), &roamId);
Agrawal Ashish6b015762016-05-05 11:22:18 +05305618 if ((QDF_STATUS_SUCCESS != status) &&
5619 (QDF_STA_MODE == pAdapter->device_mode ||
5620 QDF_P2P_CLIENT_MODE == pAdapter->device_mode)) {
5621 hdd_err("sme_roam_connect (session %d) failed with status %d. -> NotConnected",
5622 pAdapter->sessionId, status);
5623 /* change back to NotAssociated */
5624 hdd_conn_set_connection_state(pAdapter,
5625 eConnectionState_NotConnected);
5626 }
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08005627 pRoamProfile->ChannelInfo.ChannelList = NULL;
5628 pRoamProfile->ChannelInfo.numOfChannels = 0;
5629
5630 EXIT();
5631 return status;
5632}
5633
5634/**
5635 * iw_set_essid() - set essid handler function
5636 * @dev: Pointer to the net device.
5637 * @info: Pointer to the iw_request_info.
5638 * @wrqu: Pointer to the iwreq_data.
5639 * @extra: Pointer to the data.
5640 *
5641 * Return: 0 for success, error number on failure
5642 */
5643int iw_set_essid(struct net_device *dev,
5644 struct iw_request_info *info,
5645 union iwreq_data *wrqu, char *extra)
5646{
5647 int ret;
5648
5649 cds_ssr_protect(__func__);
5650 ret = __iw_set_essid(dev, info, wrqu, extra);
5651 cds_ssr_unprotect(__func__);
5652
5653 return ret;
5654}
5655
5656/**
5657 * __iw_get_essid() - This function returns the essid to the wpa_supplicant
5658 * @dev: pointer to the net device
5659 * @info: pointer to the iw request info
5660 * @dwrq: pointer to iw_point
5661 * @extra: pointer to the data
5662 *
5663 * Return: 0 on success, error number otherwise
5664 */
5665static int __iw_get_essid(struct net_device *dev,
5666 struct iw_request_info *info,
5667 struct iw_point *dwrq, char *extra)
5668{
5669 hdd_adapter_t *pAdapter = WLAN_HDD_GET_PRIV_PTR(dev);
5670 hdd_context_t *hdd_ctx;
5671 hdd_wext_state_t *wextBuf = WLAN_HDD_GET_WEXT_STATE_PTR(pAdapter);
5672 hdd_station_ctx_t *pHddStaCtx = WLAN_HDD_GET_STATION_CTX_PTR(pAdapter);
5673 int ret;
5674
Jeff Johnsonb25dcb12016-02-11 17:46:42 -08005675 ENTER_DEV(dev);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08005676
5677 hdd_ctx = WLAN_HDD_GET_CTX(pAdapter);
5678 ret = wlan_hdd_validate_context(hdd_ctx);
Abhishek Singh23edd1c2016-05-05 11:56:06 +05305679 if (ret)
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08005680 return ret;
5681
5682 if ((pHddStaCtx->conn_info.connState == eConnectionState_Associated &&
5683 wextBuf->roamProfile.SSIDs.SSIDList->SSID.length > 0) ||
5684 ((pHddStaCtx->conn_info.connState == eConnectionState_IbssConnected
5685 || pHddStaCtx->conn_info.connState ==
5686 eConnectionState_IbssDisconnected)
5687 && wextBuf->roamProfile.SSIDs.SSIDList->SSID.length > 0)) {
5688 dwrq->length = pHddStaCtx->conn_info.SSID.SSID.length;
5689 memcpy(extra, pHddStaCtx->conn_info.SSID.SSID.ssId,
5690 dwrq->length);
5691 dwrq->flags = 1;
5692 } else {
5693 memset(extra, 0, dwrq->length);
5694 dwrq->length = 0;
5695 dwrq->flags = 0;
5696 }
5697 EXIT();
5698 return 0;
5699}
5700
5701/**
5702 * iw_get_essid() - get essid handler function
5703 * @dev: Pointer to the net device.
5704 * @info: Pointer to the iw_request_info.
5705 * @wrqu: Pointer to the iwreq_data.
5706 * @extra: Pointer to the data.
5707 *
5708 * Return: 0 for success, error number on failure
5709 */
5710int iw_get_essid(struct net_device *dev,
5711 struct iw_request_info *info,
5712 struct iw_point *wrqu, char *extra)
5713{
5714 int ret;
5715
5716 cds_ssr_protect(__func__);
5717 ret = __iw_get_essid(dev, info, wrqu, extra);
5718 cds_ssr_unprotect(__func__);
5719
5720 return ret;
5721}
5722
5723/**
5724 * __iw_set_auth() -
5725 * This function sets the auth type received from the wpa_supplicant
5726 * @dev: pointer to the net device
5727 * @info: pointer to the iw request info
5728 * @wrqu: pointer to iwreq_data
5729 * @extra: pointer to the data
5730 *
5731 * Return: 0 on success, error number otherwise
5732 */
5733static int __iw_set_auth(struct net_device *dev, struct iw_request_info *info,
5734 union iwreq_data *wrqu, char *extra)
5735{
5736 hdd_adapter_t *pAdapter = WLAN_HDD_GET_PRIV_PTR(dev);
5737 hdd_context_t *hdd_ctx;
5738 hdd_wext_state_t *pWextState = WLAN_HDD_GET_WEXT_STATE_PTR(pAdapter);
5739 hdd_station_ctx_t *pHddStaCtx = WLAN_HDD_GET_STATION_CTX_PTR(pAdapter);
5740 tCsrRoamProfile *pRoamProfile = &pWextState->roamProfile;
5741 eCsrEncryptionType mcEncryptionType;
5742 eCsrEncryptionType ucEncryptionType;
5743 int ret;
5744
Jeff Johnsonb25dcb12016-02-11 17:46:42 -08005745 ENTER_DEV(dev);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08005746
5747 hdd_ctx = WLAN_HDD_GET_CTX(pAdapter);
5748 ret = wlan_hdd_validate_context(hdd_ctx);
Abhishek Singh23edd1c2016-05-05 11:56:06 +05305749 if (ret)
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08005750 return ret;
5751
5752 switch (wrqu->param.flags & IW_AUTH_INDEX) {
5753 case IW_AUTH_WPA_VERSION:
5754 pWextState->wpaVersion = wrqu->param.value;
5755 break;
5756
5757 case IW_AUTH_CIPHER_PAIRWISE:
5758 {
5759 if (wrqu->param.value & IW_AUTH_CIPHER_NONE) {
5760 ucEncryptionType = eCSR_ENCRYPT_TYPE_NONE;
5761 } else if (wrqu->param.value & IW_AUTH_CIPHER_TKIP) {
5762 ucEncryptionType = eCSR_ENCRYPT_TYPE_TKIP;
5763 } else if (wrqu->param.value & IW_AUTH_CIPHER_CCMP) {
5764 ucEncryptionType = eCSR_ENCRYPT_TYPE_AES;
5765 } else if (wrqu->param.value & IW_AUTH_CIPHER_WEP40) {
5766 if ((IW_AUTH_KEY_MGMT_802_1X
5767 ==
5768 (pWextState->
5769 authKeyMgmt & IW_AUTH_KEY_MGMT_802_1X))
5770 && (eCSR_AUTH_TYPE_OPEN_SYSTEM ==
5771 pHddStaCtx->conn_info.authType))
5772 /*Dynamic WEP key */
5773 ucEncryptionType =
5774 eCSR_ENCRYPT_TYPE_WEP40;
5775 else
5776 /*Static WEP key */
5777 ucEncryptionType =
5778 eCSR_ENCRYPT_TYPE_WEP40_STATICKEY;
5779 } else if (wrqu->param.value & IW_AUTH_CIPHER_WEP104) {
5780 if ((IW_AUTH_KEY_MGMT_802_1X
5781 ==
5782 (pWextState->
5783 authKeyMgmt & IW_AUTH_KEY_MGMT_802_1X))
5784 && (eCSR_AUTH_TYPE_OPEN_SYSTEM ==
5785 pHddStaCtx->conn_info.authType))
5786 /*Dynamic WEP key */
5787 ucEncryptionType =
5788 eCSR_ENCRYPT_TYPE_WEP104;
5789 else
5790 /*Static WEP key */
5791 ucEncryptionType =
5792 eCSR_ENCRYPT_TYPE_WEP104_STATICKEY;
5793 } else {
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07005794 hdd_warn("value %d UNKNOWN IW_AUTH_CIPHER",
5795 wrqu->param.value);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08005796 return -EINVAL;
5797 }
5798
5799 pRoamProfile->EncryptionType.numEntries = 1;
5800 pRoamProfile->EncryptionType.encryptionType[0] =
5801 ucEncryptionType;
5802 }
5803 break;
5804 case IW_AUTH_CIPHER_GROUP:
5805 {
5806 if (wrqu->param.value & IW_AUTH_CIPHER_NONE) {
5807 mcEncryptionType = eCSR_ENCRYPT_TYPE_NONE;
5808 } else if (wrqu->param.value & IW_AUTH_CIPHER_TKIP) {
5809 mcEncryptionType = eCSR_ENCRYPT_TYPE_TKIP;
5810 } else if (wrqu->param.value & IW_AUTH_CIPHER_CCMP) {
5811 mcEncryptionType = eCSR_ENCRYPT_TYPE_AES;
5812 } else if (wrqu->param.value & IW_AUTH_CIPHER_WEP40) {
5813 if ((IW_AUTH_KEY_MGMT_802_1X
5814 ==
5815 (pWextState->
5816 authKeyMgmt & IW_AUTH_KEY_MGMT_802_1X))
5817 && (eCSR_AUTH_TYPE_OPEN_SYSTEM ==
5818 pHddStaCtx->conn_info.authType))
5819 mcEncryptionType =
5820 eCSR_ENCRYPT_TYPE_WEP40;
5821 else
5822 mcEncryptionType =
5823 eCSR_ENCRYPT_TYPE_WEP40_STATICKEY;
5824 } else if (wrqu->param.value & IW_AUTH_CIPHER_WEP104) {
5825 /* Dynamic WEP keys won't work with shared keys */
5826 if ((IW_AUTH_KEY_MGMT_802_1X
5827 ==
5828 (pWextState->
5829 authKeyMgmt & IW_AUTH_KEY_MGMT_802_1X))
5830 && (eCSR_AUTH_TYPE_OPEN_SYSTEM ==
5831 pHddStaCtx->conn_info.authType)) {
5832 mcEncryptionType =
5833 eCSR_ENCRYPT_TYPE_WEP104;
5834 } else {
5835 mcEncryptionType =
5836 eCSR_ENCRYPT_TYPE_WEP104_STATICKEY;
5837 }
5838 } else {
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07005839 hdd_warn("value %d UNKNOWN IW_AUTH_CIPHER",
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08005840 wrqu->param.value);
5841 return -EINVAL;
5842 }
5843
5844 pRoamProfile->mcEncryptionType.numEntries = 1;
5845 pRoamProfile->mcEncryptionType.encryptionType[0] =
5846 mcEncryptionType;
5847 }
5848 break;
5849
5850 case IW_AUTH_80211_AUTH_ALG:
5851 {
5852 /* Save the auth algo here and set auth type to SME Roam profile
5853 in the iw_set_ap_address */
5854 if (wrqu->param.value & IW_AUTH_ALG_OPEN_SYSTEM)
5855 pHddStaCtx->conn_info.authType =
5856 eCSR_AUTH_TYPE_OPEN_SYSTEM;
5857
5858 else if (wrqu->param.value & IW_AUTH_ALG_SHARED_KEY)
5859 pHddStaCtx->conn_info.authType =
5860 eCSR_AUTH_TYPE_SHARED_KEY;
5861
5862 else if (wrqu->param.value & IW_AUTH_ALG_LEAP)
5863 /*Not supported */
5864 pHddStaCtx->conn_info.authType =
5865 eCSR_AUTH_TYPE_OPEN_SYSTEM;
5866 pWextState->roamProfile.AuthType.authType[0] =
5867 pHddStaCtx->conn_info.authType;
5868 }
5869 break;
5870
5871 case IW_AUTH_KEY_MGMT:
5872 {
5873#ifdef FEATURE_WLAN_ESE
5874#define IW_AUTH_KEY_MGMT_CCKM 8 /* Should be in linux/wireless.h */
5875 /*Check for CCKM AKM type */
5876 if (wrqu->param.value & IW_AUTH_KEY_MGMT_CCKM) {
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07005877 hdd_info("CCKM AKM Set %d", wrqu->param.value);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08005878 /* Set the CCKM bit in authKeyMgmt */
5879 /*
5880 * Right now, this breaks all ref to authKeyMgmt because
5881 * our code doesn't realize it is a "bitfield"
5882 */
5883 pWextState->authKeyMgmt |=
5884 IW_AUTH_KEY_MGMT_CCKM;
5885 /* Set the key management to 802.1X */
5886 /* pWextState->authKeyMgmt = IW_AUTH_KEY_MGMT_802_1X; */
5887 pWextState->isESEConnection = true;
5888 /*
5889 * This is test code. I need to actually KNOW whether
5890 * this is an RSN Assoc or WPA.
5891 */
5892 pWextState->collectedAuthType =
5893 eCSR_AUTH_TYPE_CCKM_RSN;
5894 } else if (wrqu->param.value & IW_AUTH_KEY_MGMT_PSK) {
5895 /* Save the key management */
5896 pWextState->authKeyMgmt |= IW_AUTH_KEY_MGMT_PSK;
5897 pWextState->collectedAuthType =
5898 eCSR_AUTH_TYPE_RSN;
5899 } else
5900 if (!(wrqu->param.value & IW_AUTH_KEY_MGMT_802_1X)) {
5901 pWextState->collectedAuthType = eCSR_AUTH_TYPE_NONE;
5902 /* Save the key management anyway */
5903 pWextState->authKeyMgmt = wrqu->param.value;
5904 } else { /* It must be IW_AUTH_KEY_MGMT_802_1X */
5905 /* Save the key management */
5906 pWextState->authKeyMgmt |=
5907 IW_AUTH_KEY_MGMT_802_1X;
5908 pWextState->collectedAuthType =
5909 eCSR_AUTH_TYPE_RSN;
5910 }
5911#else
5912 /* Save the key management */
5913 pWextState->authKeyMgmt = wrqu->param.value;
5914#endif /* FEATURE_WLAN_ESE */
5915 }
5916 break;
5917
5918 case IW_AUTH_TKIP_COUNTERMEASURES:
5919 {
5920 if (wrqu->param.value) {
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07005921 hdd_info("Counter Measure started %d",
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08005922 wrqu->param.value);
5923 pWextState->mTKIPCounterMeasures =
5924 TKIP_COUNTER_MEASURE_STARTED;
5925 } else {
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07005926 hdd_info("Counter Measure stopped=%d",
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08005927 wrqu->param.value);
5928 pWextState->mTKIPCounterMeasures =
5929 TKIP_COUNTER_MEASURE_STOPED;
5930 }
5931 }
5932 break;
5933 case IW_AUTH_DROP_UNENCRYPTED:
5934 case IW_AUTH_WPA_ENABLED:
5935 case IW_AUTH_RX_UNENCRYPTED_EAPOL:
5936 case IW_AUTH_ROAMING_CONTROL:
5937 case IW_AUTH_PRIVACY_INVOKED:
5938
5939 default:
5940
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07005941 hdd_warn("called with unsupported auth type %d",
5942 wrqu->param.flags & IW_AUTH_INDEX);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08005943 break;
5944 }
5945
5946 EXIT();
5947 return 0;
5948}
5949
5950/**
5951 * iw_set_auth() - set auth callback function
5952 * @dev: Pointer to the net device.
5953 * @info: Pointer to the iw_request_info.
5954 * @wrqu: Pointer to the iwreq_data.
5955 * @extra: Pointer to the data.
5956 *
5957 * Return: 0 for success, error number on failure.
5958 */
5959int iw_set_auth(struct net_device *dev, struct iw_request_info *info,
5960 union iwreq_data *wrqu, char *extra)
5961{
5962 int ret;
5963
5964 cds_ssr_protect(__func__);
5965 ret = __iw_set_auth(dev, info, wrqu, extra);
5966 cds_ssr_unprotect(__func__);
5967
5968 return ret;
5969}
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08005970/**
5971 * __iw_get_auth() -
5972 * This function returns the auth type to the wpa_supplicant
5973 * @dev: pointer to the net device
5974 * @info: pointer to the iw request info
5975 * @wrqu: pointer to iwreq_data
5976 * @extra: pointer to the data
5977 *
5978 * Return: 0 on success, error number otherwise
5979 */
5980static int __iw_get_auth(struct net_device *dev, struct iw_request_info *info,
5981 union iwreq_data *wrqu, char *extra)
5982{
5983 hdd_adapter_t *pAdapter = WLAN_HDD_GET_PRIV_PTR(dev);
5984 hdd_context_t *hdd_ctx;
5985 hdd_wext_state_t *pWextState = WLAN_HDD_GET_WEXT_STATE_PTR(pAdapter);
5986 tCsrRoamProfile *pRoamProfile = &pWextState->roamProfile;
5987 int ret;
5988
Jeff Johnsonb25dcb12016-02-11 17:46:42 -08005989 ENTER_DEV(dev);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08005990
5991 hdd_ctx = WLAN_HDD_GET_CTX(pAdapter);
5992 ret = wlan_hdd_validate_context(hdd_ctx);
Abhishek Singh23edd1c2016-05-05 11:56:06 +05305993 if (ret)
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08005994 return ret;
5995
5996 switch (pRoamProfile->negotiatedAuthType) {
5997 case eCSR_AUTH_TYPE_WPA_NONE:
5998 wrqu->param.flags = IW_AUTH_WPA_VERSION;
5999 wrqu->param.value = IW_AUTH_WPA_VERSION_DISABLED;
6000 break;
6001 case eCSR_AUTH_TYPE_WPA:
6002 wrqu->param.flags = IW_AUTH_WPA_VERSION;
6003 wrqu->param.value = IW_AUTH_WPA_VERSION_WPA;
6004 break;
Deepak Dhamdhere9f09e752016-01-09 23:17:25 -08006005
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08006006 case eCSR_AUTH_TYPE_FT_RSN:
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08006007 case eCSR_AUTH_TYPE_RSN:
6008 wrqu->param.flags = IW_AUTH_WPA_VERSION;
6009 wrqu->param.value = IW_AUTH_WPA_VERSION_WPA2;
6010 break;
6011 case eCSR_AUTH_TYPE_OPEN_SYSTEM:
6012 wrqu->param.value = IW_AUTH_ALG_OPEN_SYSTEM;
6013 break;
6014 case eCSR_AUTH_TYPE_SHARED_KEY:
6015 wrqu->param.value = IW_AUTH_ALG_SHARED_KEY;
6016 break;
6017 case eCSR_AUTH_TYPE_UNKNOWN:
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07006018 hdd_info("called with unknown auth type");
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08006019 wrqu->param.value = IW_AUTH_ALG_OPEN_SYSTEM;
6020 break;
6021 case eCSR_AUTH_TYPE_AUTOSWITCH:
6022 wrqu->param.value = IW_AUTH_ALG_OPEN_SYSTEM;
6023 break;
6024 case eCSR_AUTH_TYPE_WPA_PSK:
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07006025 hdd_info("called with WPA PSK auth type");
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08006026 wrqu->param.value = IW_AUTH_ALG_OPEN_SYSTEM;
6027 return -EIO;
Deepak Dhamdhere9f09e752016-01-09 23:17:25 -08006028
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08006029 case eCSR_AUTH_TYPE_FT_RSN_PSK:
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08006030 case eCSR_AUTH_TYPE_RSN_PSK:
6031#ifdef WLAN_FEATURE_11W
6032 case eCSR_AUTH_TYPE_RSN_PSK_SHA256:
6033 case eCSR_AUTH_TYPE_RSN_8021X_SHA256:
6034#endif
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07006035 hdd_info("called with RSN PSK auth type");
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08006036 wrqu->param.value = IW_AUTH_ALG_OPEN_SYSTEM;
6037 return -EIO;
6038 default:
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07006039 hdd_err("called with unknown auth type");
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08006040 wrqu->param.value = IW_AUTH_ALG_OPEN_SYSTEM;
6041 return -EIO;
6042 }
6043 if (((wrqu->param.flags & IW_AUTH_INDEX) == IW_AUTH_CIPHER_PAIRWISE)) {
6044 switch (pRoamProfile->negotiatedUCEncryptionType) {
6045 case eCSR_ENCRYPT_TYPE_NONE:
6046 wrqu->param.value = IW_AUTH_CIPHER_NONE;
6047 break;
6048 case eCSR_ENCRYPT_TYPE_WEP40:
6049 case eCSR_ENCRYPT_TYPE_WEP40_STATICKEY:
6050 wrqu->param.value = IW_AUTH_CIPHER_WEP40;
6051 break;
6052 case eCSR_ENCRYPT_TYPE_TKIP:
6053 wrqu->param.value = IW_AUTH_CIPHER_TKIP;
6054 break;
6055 case eCSR_ENCRYPT_TYPE_WEP104:
6056 case eCSR_ENCRYPT_TYPE_WEP104_STATICKEY:
6057 wrqu->param.value = IW_AUTH_CIPHER_WEP104;
6058 break;
6059 case eCSR_ENCRYPT_TYPE_AES:
6060 wrqu->param.value = IW_AUTH_CIPHER_CCMP;
6061 break;
6062 default:
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07006063 hdd_notice("called with unknown auth type %d",
6064 pRoamProfile->negotiatedUCEncryptionType);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08006065 return -EIO;
6066 }
6067 }
6068
6069 if (((wrqu->param.flags & IW_AUTH_INDEX) == IW_AUTH_CIPHER_GROUP)) {
6070 switch (pRoamProfile->negotiatedMCEncryptionType) {
6071 case eCSR_ENCRYPT_TYPE_NONE:
6072 wrqu->param.value = IW_AUTH_CIPHER_NONE;
6073 break;
6074 case eCSR_ENCRYPT_TYPE_WEP40:
6075 case eCSR_ENCRYPT_TYPE_WEP40_STATICKEY:
6076 wrqu->param.value = IW_AUTH_CIPHER_WEP40;
6077 break;
6078 case eCSR_ENCRYPT_TYPE_TKIP:
6079 wrqu->param.value = IW_AUTH_CIPHER_TKIP;
6080 break;
6081 case eCSR_ENCRYPT_TYPE_WEP104:
6082 case eCSR_ENCRYPT_TYPE_WEP104_STATICKEY:
6083 wrqu->param.value = IW_AUTH_CIPHER_WEP104;
6084 break;
6085 case eCSR_ENCRYPT_TYPE_AES:
6086 wrqu->param.value = IW_AUTH_CIPHER_CCMP;
6087 break;
6088 default:
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07006089 hdd_info("called with unknown auth type %d",
6090 pRoamProfile->negotiatedMCEncryptionType);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08006091 return -EIO;
6092 }
6093 }
6094
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07006095 hdd_info("called with auth type %d",
6096 pRoamProfile->AuthType.authType[0]);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08006097 EXIT();
6098 return 0;
6099}
6100
6101/**
6102 * iw_get_auth() - get auth callback function
6103 * @dev: Pointer to the net device.
6104 * @info: Pointer to the iw_request_info.
6105 * @wrqu: Pointer to the iwreq_data.
6106 * @extra: Pointer to the data.
6107 *
6108 * Return: 0 for success, error number on failure.
6109 */
6110int iw_get_auth(struct net_device *dev, struct iw_request_info *info,
6111 union iwreq_data *wrqu, char *extra)
6112{
6113 int ret;
6114
6115 cds_ssr_protect(__func__);
6116 ret = __iw_get_auth(dev, info, wrqu, extra);
6117 cds_ssr_unprotect(__func__);
6118
6119 return ret;
6120}
6121
6122/**
6123 * __iw_set_ap_address() - set ap address
6124 * @dev: pointer to the net device
6125 * @info: pointer to the iw request info
6126 * @wrqu: pointer to iwreq_data
6127 * @extra: pointer to the data
6128 *
6129 * This function updates the HDD global station context connection info
6130 * BSSID with the MAC address received from the wpa_supplicant.
6131 *
6132 * Return: 0 on success, error number otherwise
6133 */
6134static int __iw_set_ap_address(struct net_device *dev,
6135 struct iw_request_info *info,
6136 union iwreq_data *wrqu, char *extra)
6137{
6138
6139 hdd_adapter_t *adapter;
6140 hdd_context_t *hdd_ctx;
6141 hdd_station_ctx_t *pHddStaCtx =
6142 WLAN_HDD_GET_STATION_CTX_PTR(WLAN_HDD_GET_PRIV_PTR(dev));
6143 uint8_t *pMacAddress = NULL;
6144 int ret;
6145
Jeff Johnsonb25dcb12016-02-11 17:46:42 -08006146 ENTER_DEV(dev);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08006147
6148 adapter = WLAN_HDD_GET_PRIV_PTR(dev);
6149
6150 hdd_ctx = WLAN_HDD_GET_CTX(adapter);
6151 ret = wlan_hdd_validate_context(hdd_ctx);
Abhishek Singh23edd1c2016-05-05 11:56:06 +05306152 if (ret)
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08006153 return ret;
6154
6155 pMacAddress = (uint8_t *) wrqu->ap_addr.sa_data;
Archana Ramachandran75c1ca72016-08-22 17:20:25 -07006156 hdd_info(" " MAC_ADDRESS_STR, MAC_ADDR_ARRAY(pMacAddress));
Anurag Chouhan600c3a02016-03-01 10:33:54 +05306157 qdf_mem_copy(pHddStaCtx->conn_info.bssId.bytes, pMacAddress,
Anurag Chouhan6d760662016-02-20 16:05:43 +05306158 sizeof(struct qdf_mac_addr));
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08006159 EXIT();
6160
6161 return 0;
6162}
6163
6164/**
6165 * iw_set_ap_address() - set ap addresses callback function
6166 * @dev: Pointer to the net device.
6167 * @info: Pointer to the iw_request_info.
6168 * @wrqu: Pointer to the iwreq_data.
6169 * @extra: Pointer to the data.
6170 *
6171 * Return: 0 for success, error number on failure.
6172 */
6173int iw_set_ap_address(struct net_device *dev, struct iw_request_info *info,
6174 union iwreq_data *wrqu, char *extra)
6175{
6176 int ret;
6177
6178 cds_ssr_protect(__func__);
6179 ret = __iw_set_ap_address(dev, info, wrqu, extra);
6180 cds_ssr_unprotect(__func__);
6181
6182 return ret;
6183}
6184
6185/**
6186 * __iw_get_ap_address() - get ap address
6187 * @dev: pointer to the net device
6188 * @info: pointer to the iw request info
6189 * @wrqu: pointer to iwreq_data
6190 * @extra: pointer to the data
6191 *
6192 * This function returns currently associated BSSID.
6193 *
6194 * Return: 0 on success, error number otherwise
6195 */
6196static int __iw_get_ap_address(struct net_device *dev,
6197 struct iw_request_info *info,
6198 union iwreq_data *wrqu, char *extra)
6199{
6200 hdd_adapter_t *adapter = WLAN_HDD_GET_PRIV_PTR(dev);
6201 hdd_context_t *hdd_ctx;
6202 hdd_station_ctx_t *pHddStaCtx =
6203 WLAN_HDD_GET_STATION_CTX_PTR(adapter);
6204 int ret;
6205
Jeff Johnsonb25dcb12016-02-11 17:46:42 -08006206 ENTER_DEV(dev);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08006207
6208 hdd_ctx = WLAN_HDD_GET_CTX(adapter);
6209 ret = wlan_hdd_validate_context(hdd_ctx);
Abhishek Singh23edd1c2016-05-05 11:56:06 +05306210 if (ret)
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08006211 return ret;
6212
6213 if (pHddStaCtx->conn_info.connState == eConnectionState_Associated ||
6214 eConnectionState_IbssConnected == pHddStaCtx->conn_info.connState) {
Anurag Chouhan600c3a02016-03-01 10:33:54 +05306215 qdf_mem_copy(wrqu->ap_addr.sa_data,
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08006216 pHddStaCtx->conn_info.bssId.bytes,
Anurag Chouhan6d760662016-02-20 16:05:43 +05306217 QDF_MAC_ADDR_SIZE);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08006218 } else {
6219 memset(wrqu->ap_addr.sa_data, 0, sizeof(wrqu->ap_addr.sa_data));
6220 }
6221 EXIT();
6222 return 0;
6223}
6224
6225/**
6226 * iw_get_ap_address() - get ap addresses callback function
6227 * @dev: Pointer to the net device.
6228 * @info: Pointer to the iw_request_info.
6229 * @wrqu: Pointer to the iwreq_data.
6230 * @extra: Pointer to the data.
6231 *
6232 * Return: 0 for success, error number on failure.
6233 */
6234int iw_get_ap_address(struct net_device *dev, struct iw_request_info *info,
6235 union iwreq_data *wrqu, char *extra)
6236{
6237 int ret;
6238
6239 cds_ssr_protect(__func__);
6240 ret = __iw_get_ap_address(dev, info, wrqu, extra);
6241 cds_ssr_unprotect(__func__);
6242
6243 return ret;
6244}