blob: 40988d2ad53449ab28eef2316cd184b1a79c813c [file] [log] [blame]
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001/*
Himanshu Agarwal2fdf77a2016-12-29 11:41:00 +05302 * Copyright (c) 2011-2017 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 * \file lim_send_management_frames.c
30 *
31 * \brief Code for preparing and sending 802.11 Management frames
32 *
33 *
34 */
35
36#include "sir_api.h"
37#include "ani_global.h"
38#include "sir_mac_prot_def.h"
39#include "cfg_api.h"
40#include "utils_api.h"
41#include "lim_types.h"
42#include "lim_utils.h"
43#include "lim_security_utils.h"
44#include "lim_prop_exts_utils.h"
45#include "dot11f.h"
46#include "lim_sta_hash_api.h"
47#include "sch_api.h"
48#include "lim_send_messages.h"
49#include "lim_assoc_utils.h"
50#include "lim_ft.h"
51#ifdef WLAN_FEATURE_11W
52#include "wni_cfg.h"
53#endif
54
Prakash Dhavali7090c5f2015-11-02 17:55:19 -080055#include "lim_ft_defs.h"
Prakash Dhavali7090c5f2015-11-02 17:55:19 -080056#include "lim_session.h"
Anurag Chouhan6d760662016-02-20 16:05:43 +053057#include "qdf_types.h"
Anurag Chouhanb2dc16f2016-02-25 11:47:37 +053058#include "qdf_trace.h"
Prakash Dhavali7090c5f2015-11-02 17:55:19 -080059#include "cds_utils.h"
60#include "sme_trace.h"
Prakash Dhavali7090c5f2015-11-02 17:55:19 -080061#include "rrm_api.h"
Prakash Dhavali7090c5f2015-11-02 17:55:19 -080062
63#include "wma_types.h"
Krishna Kumaar Natarajan48a6b4c2017-01-06 16:30:55 -080064#include <cdp_txrx_cmn.h>
Tushnim Bhattacharyya45ed04f2017-03-15 10:15:05 -070065#include <cdp_txrx_peer_ops.h>
Prakash Dhavali7090c5f2015-11-02 17:55:19 -080066
67/**
68 *
69 * \brief This function is called to add the sequence number to the
70 * management frames
71 *
72 * \param pMac Pointer to Global MAC structure
73 *
74 * \param pMacHdr Pointer to MAC management header
75 *
76 * The pMacHdr argument points to the MAC management header. The
77 * sequence number stored in the pMac structure will be incremented
78 * and updated to the MAC management header. The start sequence
79 * number is WLAN_HOST_SEQ_NUM_MIN and the end value is
80 * WLAN_HOST_SEQ_NUM_MAX. After reaching the MAX value, the sequence
81 * number will roll over.
82 *
83 */
Jeff Johnson38112a32016-10-07 07:30:50 -070084static void lim_add_mgmt_seq_num(tpAniSirGlobal pMac, tpSirMacMgmtHdr pMacHdr)
Prakash Dhavali7090c5f2015-11-02 17:55:19 -080085{
86 if (pMac->mgmtSeqNum >= WLAN_HOST_SEQ_NUM_MAX) {
87 pMac->mgmtSeqNum = WLAN_HOST_SEQ_NUM_MIN - 1;
88 }
89
90 pMac->mgmtSeqNum++;
91
92 pMacHdr->seqControl.seqNumLo = (pMac->mgmtSeqNum & LOW_SEQ_NUM_MASK);
93 pMacHdr->seqControl.seqNumHi =
94 ((pMac->mgmtSeqNum & HIGH_SEQ_NUM_MASK) >> HIGH_SEQ_NUM_OFFSET);
95}
96
97/**
98 *
99 * \brief This function is called before sending a p2p action frame
100 * inorder to add sequence numbers to action packets
101 *
102 * \param pMac Pointer to Global MAC structure
103 *
104 * \param pBD Pointer to the frame buffer that needs to be populate
105 *
106 * The pMacHdr argument points to the MAC management header. The
107 * sequence number stored in the pMac structure will be incremented
108 * and updated to the MAC management header. The start sequence
109 * number is WLAN_HOST_SEQ_NUM_MIN and the end value is
110 * WLAN_HOST_SEQ_NUM_MAX. After reaching the MAX value, the sequence
111 * number will roll over.
112 *
113 */
114void lim_populate_p2p_mac_header(tpAniSirGlobal pMac, uint8_t *pBD)
115{
116 tpSirMacMgmtHdr pMacHdr;
117
118 /* / Prepare MAC management header */
119 pMacHdr = (tpSirMacMgmtHdr) (pBD);
120
121 /* Prepare sequence number */
122 lim_add_mgmt_seq_num(pMac, pMacHdr);
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -0700123 pe_debug("seqNumLo=%d, seqNumHi=%d, mgmtSeqNum=%d",
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800124 pMacHdr->seqControl.seqNumLo,
125 pMacHdr->seqControl.seqNumHi, pMac->mgmtSeqNum);
126}
127
128/**
129 * lim_populate_mac_header() - Fill in 802.11 header of frame
130 *
131 * @mac_ctx: Pointer to Global MAC structure
132 * @buf: Pointer to the frame buffer that needs to be populate
133 * @type: 802.11 Type of the frame
134 * @sub_type: 802.11 Subtype of the frame
135 * @peer_addr: dst address
136 * @self_mac_addr: local mac address
137 *
138 * This function is called by various LIM modules to prepare the
139 * 802.11 frame MAC header
140 *
141 * The buf argument points to the beginning of the frame buffer to
142 * which - a) The 802.11 MAC header is set b) Following this MAC header
143 * will be the MGMT frame payload The payload itself is populated by the
144 * caller API
145 *
146 * Return: None
147 */
148
149void lim_populate_mac_header(tpAniSirGlobal mac_ctx, uint8_t *buf,
150 uint8_t type, uint8_t sub_type, tSirMacAddr peer_addr,
151 tSirMacAddr self_mac_addr)
152{
153 tpSirMacMgmtHdr mac_hdr;
154
155 /* Prepare MAC management header */
156 mac_hdr = (tpSirMacMgmtHdr) (buf);
157
158 /* Prepare FC */
159 mac_hdr->fc.protVer = SIR_MAC_PROTOCOL_VERSION;
160 mac_hdr->fc.type = type;
161 mac_hdr->fc.subType = sub_type;
162
163 /* Prepare Address 1 */
Anurag Chouhan600c3a02016-03-01 10:33:54 +0530164 qdf_mem_copy((uint8_t *) mac_hdr->da,
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800165 (uint8_t *) peer_addr, sizeof(tSirMacAddr));
166
167 /* Prepare Address 2 */
168 sir_copy_mac_addr(mac_hdr->sa, self_mac_addr);
169
170 /* Prepare Address 3 */
Anurag Chouhan600c3a02016-03-01 10:33:54 +0530171 qdf_mem_copy((uint8_t *) mac_hdr->bssId,
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800172 (uint8_t *) peer_addr, sizeof(tSirMacAddr));
173
174 /* Prepare sequence number */
175 lim_add_mgmt_seq_num(mac_ctx, mac_hdr);
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -0700176 pe_debug("seqNumLo=%d, seqNumHi=%d, mgmtSeqNum=%d",
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800177 mac_hdr->seqControl.seqNumLo,
178 mac_hdr->seqControl.seqNumHi, mac_ctx->mgmtSeqNum);
179}
180
181/**
182 * lim_send_probe_req_mgmt_frame() - send probe request management frame
183 * @mac_ctx: Pointer to Global MAC structure
184 * @ssid: SSID to be sent in Probe Request frame
185 * @bssid: BSSID to be sent in Probe Request frame
186 * @channel: Channel # on which the Probe Request is going out
187 * @self_macaddr: self MAC address
188 * @dot11mode: self dotllmode
189 * @additional_ielen: if non-zero, include additional_ie in the Probe Request
190 * frame
191 * @additional_ie: if additional_ielen is non zero, include this field in the
192 * Probe Request frame
193 *
194 * This function is called by various LIM modules to send Probe Request frame
195 * during active scan/learn phase.
196 * Probe request is sent out in the following scenarios:
197 * --heartbeat failure: session needed
198 * --join req: session needed
199 * --foreground scan: no session
200 * --background scan: no session
201 * --sch_beacon_processing: to get EDCA parameters: session needed
202 *
203 * Return: tSirRetStatus (eSIR_SUCCESS on success and error codes otherwise)
204 */
205tSirRetStatus
206lim_send_probe_req_mgmt_frame(tpAniSirGlobal mac_ctx,
207 tSirMacSSid *ssid,
208 tSirMacAddr bssid,
209 uint8_t channel,
210 tSirMacAddr self_macaddr,
211 uint32_t dot11mode,
212 uint32_t additional_ielen, uint8_t *additional_ie)
213{
214 tDot11fProbeRequest pr;
215 uint32_t status, bytes, payload;
216 uint8_t *frame;
217 void *packet;
Kapil Guptac03eb072016-08-09 14:01:36 +0530218 QDF_STATUS qdf_status;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800219 tpPESession pesession;
220 uint8_t sessionid;
221 uint8_t *p2pie = NULL;
222 uint8_t txflag = 0;
223 uint8_t sme_sessionid = 0;
224 bool is_vht_enabled = false;
225 uint8_t txPower;
226 uint16_t addn_ielen = additional_ielen;
Kapil Guptac03eb072016-08-09 14:01:36 +0530227 bool extracted_ext_cap_flag = false;
228 tDot11fIEExtCap extracted_ext_cap;
229 tSirRetStatus sir_status;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800230
231 /* The probe req should not send 11ac capabilieties if band is 2.4GHz,
232 * unless enableVhtFor24GHz is enabled in INI. So if enableVhtFor24GHz
233 * is false and dot11mode is 11ac set it to 11n.
234 */
235 if (channel <= SIR_11B_CHANNEL_END &&
236 (false == mac_ctx->roam.configParam.enableVhtFor24GHz) &&
237 (WNI_CFG_DOT11_MODE_11AC == dot11mode ||
238 WNI_CFG_DOT11_MODE_11AC_ONLY == dot11mode))
239 dot11mode = WNI_CFG_DOT11_MODE_11N;
240 /*
241 * session context may or may not be present, when probe request needs
242 * to be sent out. Following cases exist:
243 * --heartbeat failure: session needed
244 * --join req: session needed
245 * --foreground scan: no session
246 * --background scan: no session
247 * --sch_beacon_processing: to get EDCA parameters: session needed
248 * If session context does not exist, some IEs will be populated from
249 * CFGs, e.g. Supported and Extended rate set IEs
250 */
251 pesession = pe_find_session_by_bssid(mac_ctx, bssid, &sessionid);
252
253 if (pesession != NULL)
254 sme_sessionid = pesession->smeSessionId;
255
256 /* The scheme here is to fill out a 'tDot11fProbeRequest' structure */
257 /* and then hand it off to 'dot11f_pack_probe_request' (for */
258 /* serialization). We start by zero-initializing the structure: */
Anurag Chouhan600c3a02016-03-01 10:33:54 +0530259 qdf_mem_set((uint8_t *) &pr, sizeof(pr), 0);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800260
261 /* & delegating to assorted helpers: */
262 populate_dot11f_ssid(mac_ctx, ssid, &pr.SSID);
263
264 if (addn_ielen && additional_ie)
265 p2pie = limGetP2pIEPtr(mac_ctx, additional_ie, addn_ielen);
266
267 /*
268 * Don't include 11b rate if it is a P2P serach or probe request is
269 * sent by P2P Client
270 */
271 if ((WNI_CFG_DOT11_MODE_11B != dot11mode) && (p2pie != NULL) &&
272 (((mac_ctx->lim.gpLimMlmScanReq != NULL) &&
273 mac_ctx->lim.gpLimMlmScanReq->p2pSearch) ||
274 ((pesession != NULL) &&
Anurag Chouhan6d760662016-02-20 16:05:43 +0530275 (QDF_P2P_CLIENT_MODE == pesession->pePersona))
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800276 )
277 ) {
278 /*
279 * In the below API pass channel number > 14, do that it fills
280 * only 11a rates in supported rates
281 */
282 populate_dot11f_supp_rates(mac_ctx, 15, &pr.SuppRates,
283 pesession);
284 } else {
285 populate_dot11f_supp_rates(mac_ctx, channel,
286 &pr.SuppRates, pesession);
287
288 if (WNI_CFG_DOT11_MODE_11B != dot11mode) {
289 populate_dot11f_ext_supp_rates1(mac_ctx, channel,
290 &pr.ExtSuppRates);
291 }
292 }
293
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800294 /*
295 * Table 7-14 in IEEE Std. 802.11k-2008 says
296 * DS params "can" be present in RRM is disabled and "is" present if
297 * RRM is enabled. It should be ok even if we add it into probe req when
298 * RRM is not enabled.
299 */
300 populate_dot11f_ds_params(mac_ctx, &pr.DSParams, channel);
301 /* Call RRM module to get the tx power for management used. */
302 txPower = (uint8_t) rrm_get_mgmt_tx_power(mac_ctx, pesession);
303 populate_dot11f_wfatpc(mac_ctx, &pr.WFATPC, txPower, 0);
304
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800305
306 if (pesession != NULL) {
307 pesession->htCapability = IS_DOT11_MODE_HT(dot11mode);
308 /* Include HT Capability IE */
309 if (pesession->htCapability)
310 populate_dot11f_ht_caps(mac_ctx, pesession, &pr.HTCaps);
311 } else { /* pesession == NULL */
312 if (IS_DOT11_MODE_HT(dot11mode))
313 populate_dot11f_ht_caps(mac_ctx, NULL, &pr.HTCaps);
314 }
315
316 /*
317 * Set channelbonding information as "disabled" when tunned to a
318 * 2.4 GHz channel
319 */
320 if (channel <= SIR_11B_CHANNEL_END) {
321 if (mac_ctx->roam.configParam.channelBondingMode24GHz
322 == PHY_SINGLE_CHANNEL_CENTERED) {
323 pr.HTCaps.supportedChannelWidthSet =
324 eHT_CHANNEL_WIDTH_20MHZ;
325 pr.HTCaps.shortGI40MHz = 0;
326 } else {
327 pr.HTCaps.supportedChannelWidthSet =
328 eHT_CHANNEL_WIDTH_40MHZ;
329 }
330 }
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800331 if (pesession != NULL) {
332 pesession->vhtCapability = IS_DOT11_MODE_VHT(dot11mode);
333 /* Include VHT Capability IE */
334 if (pesession->vhtCapability) {
335 populate_dot11f_vht_caps(mac_ctx, pesession,
336 &pr.VHTCaps);
337 is_vht_enabled = true;
338 }
339 } else {
340 if (IS_DOT11_MODE_VHT(dot11mode)) {
341 populate_dot11f_vht_caps(mac_ctx, pesession,
342 &pr.VHTCaps);
343 is_vht_enabled = true;
344 }
345 }
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800346 if (pesession != NULL)
347 populate_dot11f_ext_cap(mac_ctx, is_vht_enabled, &pr.ExtCap,
348 pesession);
349
Selvaraj, Sridhara521aab2017-03-25 16:42:34 +0530350 if (mac_ctx->roam.configParam.qcn_ie_support)
351 populate_dot11f_qcn_ie(&pr.QCN_IE);
Selvaraj, Sridharc2fe7a32017-02-02 19:20:16 +0530352
Krishna Kumaar Natarajan0103ef82017-02-17 18:15:56 -0800353 if (IS_DOT11_MODE_HE(dot11mode) && NULL != pesession)
354 lim_update_session_he_capable(mac_ctx, pesession);
355
Srinivas Girigowda28fb0122017-03-26 22:21:20 -0700356 pe_debug("Populate HE IEs");
Krishna Kumaar Natarajan0103ef82017-02-17 18:15:56 -0800357 populate_dot11f_he_caps(mac_ctx, pesession, &pr.vendor_he_cap);
358
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800359 if (addn_ielen) {
Kapil Guptac03eb072016-08-09 14:01:36 +0530360 qdf_mem_zero((uint8_t *)&extracted_ext_cap,
361 sizeof(tDot11fIEExtCap));
362 sir_status = lim_strip_extcap_update_struct(mac_ctx,
363 additional_ie,
364 &addn_ielen,
365 &extracted_ext_cap);
366 if (eSIR_SUCCESS != sir_status) {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -0700367 pe_debug("Unable to Stripoff ExtCap IE from Probe Req");
Kapil Guptac03eb072016-08-09 14:01:36 +0530368 } else {
369 struct s_ext_cap *p_ext_cap =
370 (struct s_ext_cap *)
371 extracted_ext_cap.bytes;
372 if (p_ext_cap->interworking_service)
373 p_ext_cap->qos_map = 1;
Hu Wang411e0cc2016-10-28 14:56:01 +0800374 extracted_ext_cap.num_bytes =
375 lim_compute_ext_cap_ie_length
376 (&extracted_ext_cap);
Kapil Guptac03eb072016-08-09 14:01:36 +0530377 extracted_ext_cap_flag =
Hu Wang411e0cc2016-10-28 14:56:01 +0800378 (extracted_ext_cap.num_bytes > 0);
Kapil Guptac03eb072016-08-09 14:01:36 +0530379 }
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800380 }
381
Hu Wang411e0cc2016-10-28 14:56:01 +0800382 /*
383 * Extcap IE now support variable length, merge Extcap IE from addn_ie
384 * may change the frame size. Therefore, MUST merge ExtCap IE before
385 * dot11f get packed payload size.
386 */
387 if (extracted_ext_cap_flag)
Hu Wangfbd279d2016-10-31 18:24:34 +0800388 lim_merge_extcap_struct(&pr.ExtCap, &extracted_ext_cap, true);
Hu Wang411e0cc2016-10-28 14:56:01 +0800389
390 /* That's it-- now we pack it. First, how much space are we going to */
391 status = dot11f_get_packed_probe_request_size(mac_ctx, &pr, &payload);
392 if (DOT11F_FAILED(status)) {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -0700393 pe_err("Failed to calculate the packed size for a Probe Request (0x%08x)",
Hu Wang411e0cc2016-10-28 14:56:01 +0800394 status);
395 /* We'll fall back on the worst case scenario: */
396 payload = sizeof(tDot11fProbeRequest);
397 } else if (DOT11F_WARNED(status)) {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -0700398 pe_warn("There were warnings while calculating the packed size for a Probe Request (0x%08x)",
Hu Wang411e0cc2016-10-28 14:56:01 +0800399 status);
400 }
401
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800402 bytes = payload + sizeof(tSirMacMgmtHdr) + addn_ielen;
403
404 /* Ok-- try to allocate some memory: */
Anurag Chouhanfb54ab02016-02-18 18:00:46 +0530405 qdf_status = cds_packet_alloc((uint16_t) bytes, (void **)&frame,
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800406 (void **)&packet);
Anurag Chouhanfb54ab02016-02-18 18:00:46 +0530407 if (!QDF_IS_STATUS_SUCCESS(qdf_status)) {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -0700408 pe_err("Failed to allocate %d bytes for a Probe Request", bytes);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800409 return eSIR_MEM_ALLOC_FAILED;
410 }
411 /* Paranoia: */
Anurag Chouhan600c3a02016-03-01 10:33:54 +0530412 qdf_mem_set(frame, bytes, 0);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800413
414 /* Next, we fill out the buffer descriptor: */
415 lim_populate_mac_header(mac_ctx, frame, SIR_MAC_MGMT_FRAME,
416 SIR_MAC_MGMT_PROBE_REQ, bssid, self_macaddr);
417
418 /* That done, pack the Probe Request: */
419 status = dot11f_pack_probe_request(mac_ctx, &pr, frame +
420 sizeof(tSirMacMgmtHdr),
421 payload, &payload);
422 if (DOT11F_FAILED(status)) {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -0700423 pe_err("Failed to pack a Probe Request (0x%08x)", status);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800424 cds_packet_free((void *)packet);
425 return eSIR_FAILURE; /* allocated! */
426 } else if (DOT11F_WARNED(status)) {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -0700427 pe_warn("There were warnings while packing a Probe Request (0x%08x)", status);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800428 }
429 /* Append any AddIE if present. */
430 if (addn_ielen) {
Anurag Chouhan600c3a02016-03-01 10:33:54 +0530431 qdf_mem_copy(frame + sizeof(tSirMacMgmtHdr) + payload,
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800432 additional_ie, addn_ielen);
433 payload += addn_ielen;
434 }
435
436 /* If this probe request is sent during P2P Search State, then we need
437 * to send it at OFDM rate.
438 */
439 if ((SIR_BAND_5_GHZ == lim_get_rf_band(channel))
440 || ((mac_ctx->lim.gpLimMlmScanReq != NULL) &&
441 mac_ctx->lim.gpLimMlmScanReq->p2pSearch)
442 /*
443 * For unicast probe req mgmt from Join function we don't set
444 * above variables. So we need to add one more check whether it
445 * is pePersona is P2P_CLIENT or not
446 */
447 || ((pesession != NULL) &&
Anurag Chouhan6d760662016-02-20 16:05:43 +0530448 (QDF_P2P_CLIENT_MODE == pesession->pePersona))
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800449 ) {
450 txflag |= HAL_USE_BD_RATE2_FOR_MANAGEMENT_FRAME;
451 }
452
Anurag Chouhanfb54ab02016-02-18 18:00:46 +0530453 qdf_status =
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800454 wma_tx_frame(mac_ctx, packet,
455 (uint16_t) sizeof(tSirMacMgmtHdr) + payload,
456 TXRX_FRM_802_11_MGMT, ANI_TXDIR_TODS, 7,
457 lim_tx_complete, frame, txflag, sme_sessionid,
458 0);
Anurag Chouhanfb54ab02016-02-18 18:00:46 +0530459 if (!QDF_IS_STATUS_SUCCESS(qdf_status)) {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -0700460 pe_err("could not send Probe Request frame!");
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800461 /* Pkt will be freed up by the callback */
462 return eSIR_FAILURE;
463 }
464
465 return eSIR_SUCCESS;
466} /* End lim_send_probe_req_mgmt_frame. */
467
Jeff Johnson38112a32016-10-07 07:30:50 -0700468static tSirRetStatus lim_get_addn_ie_for_probe_resp(tpAniSirGlobal pMac,
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800469 uint8_t *addIE, uint16_t *addnIELen,
470 uint8_t probeReqP2pIe)
471{
472 /* If Probe request doesn't have P2P IE, then take out P2P IE
473 from additional IE */
474 if (!probeReqP2pIe) {
475 uint8_t *tempbuf = NULL;
476 uint16_t tempLen = 0;
477 int left = *addnIELen;
478 uint8_t *ptr = addIE;
479 uint8_t elem_id, elem_len;
480
481 if (NULL == addIE) {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -0700482 pe_err("NULL addIE pointer");
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800483 return eSIR_FAILURE;
484 }
485
Anurag Chouhan600c3a02016-03-01 10:33:54 +0530486 tempbuf = qdf_mem_malloc(left);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800487 if (NULL == tempbuf) {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -0700488 pe_err("Unable to allocate memory to store addn IE");
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800489 return eSIR_MEM_ALLOC_FAILED;
490 }
491
492 while (left >= 2) {
493 elem_id = ptr[0];
494 elem_len = ptr[1];
495 left -= 2;
496 if (elem_len > left) {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -0700497 pe_err("Invalid IEs eid: %d elem_len: %d left: %d",
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800498 elem_id, elem_len, left);
Anurag Chouhan600c3a02016-03-01 10:33:54 +0530499 qdf_mem_free(tempbuf);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800500 return eSIR_FAILURE;
501 }
502 if (!((SIR_MAC_EID_VENDOR == elem_id) &&
503 (memcmp
504 (&ptr[2], SIR_MAC_P2P_OUI,
505 SIR_MAC_P2P_OUI_SIZE) == 0))) {
Anurag Chouhan600c3a02016-03-01 10:33:54 +0530506 qdf_mem_copy(tempbuf + tempLen, &ptr[0],
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800507 elem_len + 2);
508 tempLen += (elem_len + 2);
509 }
510 left -= elem_len;
511 ptr += (elem_len + 2);
512 }
Anurag Chouhan600c3a02016-03-01 10:33:54 +0530513 qdf_mem_copy(addIE, tempbuf, tempLen);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800514 *addnIELen = tempLen;
Anurag Chouhan600c3a02016-03-01 10:33:54 +0530515 qdf_mem_free(tempbuf);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800516 }
517 return eSIR_SUCCESS;
518}
519
520/**
521 * lim_send_probe_rsp_mgmt_frame() - Send probe response
522 *
523 * @mac_ctx: Handle for mac context
524 * @peer_macaddr: Mac address of requesting peer
525 * @ssid: SSID for response
526 * @n_staid: Station ID, currently unused.
527 * @pe_session: PE session id
528 * @keepalive: Keep alive flag. Currently unused.
529 * @preq_p2pie: P2P IE in incoming probe request
530 *
531 * Builds and sends probe response frame to the requesting peer
532 *
533 * Return: void
534 */
535
536void
537lim_send_probe_rsp_mgmt_frame(tpAniSirGlobal mac_ctx,
538 tSirMacAddr peer_macaddr,
539 tpAniSSID ssid,
540 short n_staid,
541 uint8_t keepalive,
542 tpPESession pe_session, uint8_t preq_p2pie)
543{
544 tDot11fProbeResponse *frm;
545 tSirRetStatus sir_status;
Hu Wang411e0cc2016-10-28 14:56:01 +0800546 uint32_t cfg, payload, bytes = 0, status;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800547 tpSirMacMgmtHdr mac_hdr;
548 uint8_t *frame;
Arif Hussainfbf50682016-06-15 12:57:43 -0700549 void *packet = NULL;
Anurag Chouhanfb54ab02016-02-18 18:00:46 +0530550 QDF_STATUS qdf_status;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800551 uint32_t addn_ie_present = false;
552
553 uint16_t addn_ie_len = 0;
554 uint32_t wps_ap = 0, tmp;
555 uint8_t tx_flag = 0;
556 uint8_t *add_ie = NULL;
557 uint8_t *p2p_ie = NULL;
558 uint8_t noalen = 0;
559 uint8_t total_noalen = 0;
560 uint8_t noa_stream[SIR_MAX_NOA_ATTR_LEN + SIR_P2P_IE_HEADER_LEN];
561 uint8_t noa_ie[SIR_MAX_NOA_ATTR_LEN + SIR_P2P_IE_HEADER_LEN];
562 uint8_t sme_sessionid = 0;
563 bool is_vht_enabled = false;
Padma, Santhosh Kumar92234472017-04-19 18:20:02 +0530564 tDot11fIEExtCap extracted_ext_cap = {0};
Selvaraj, Sridhar94ece202016-06-23 20:44:09 +0530565 bool extracted_ext_cap_flag = false;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800566
567 /* We don't answer requests in this case*/
568 if (ANI_DRIVER_TYPE(mac_ctx) == eDRIVER_TYPE_MFG)
569 return;
570
571 if (NULL == pe_session)
572 return;
573
574 /*
575 * In case when cac timer is running for this SAP session then
576 * avoid sending probe rsp out. It is violation of dfs specification.
577 */
Anurag Chouhan6d760662016-02-20 16:05:43 +0530578 if (((pe_session->pePersona == QDF_SAP_MODE) ||
579 (pe_session->pePersona == QDF_P2P_GO_MODE)) &&
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800580 (true == mac_ctx->sap.SapDfsInfo.is_dfs_cac_timer_running)) {
Anurag Chouhanb2dc16f2016-02-25 11:47:37 +0530581 QDF_TRACE(QDF_MODULE_ID_SAP, QDF_TRACE_LEVEL_INFO,
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800582 FL("CAC timer is running, probe response dropped"));
583 return;
584 }
585 sme_sessionid = pe_session->smeSessionId;
Anurag Chouhan600c3a02016-03-01 10:33:54 +0530586 frm = qdf_mem_malloc(sizeof(tDot11fProbeResponse));
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800587 if (NULL == frm) {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -0700588 pe_err("Unable to allocate memory");
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800589 return;
590 }
591
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800592 /*
593 * Fill out 'frm', after which we'll just hand the struct off to
594 * 'dot11f_pack_probe_response'.
595 */
Anurag Chouhan600c3a02016-03-01 10:33:54 +0530596 qdf_mem_set((uint8_t *) frm, sizeof(tDot11fProbeResponse), 0);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800597
598 /*
599 * Timestamp to be updated by TFP, below.
600 *
601 * Beacon Interval:
602 */
603 if (LIM_IS_AP_ROLE(pe_session)) {
604 frm->BeaconInterval.interval =
605 mac_ctx->sch.schObject.gSchBeaconInterval;
606 } else {
607 sir_status = wlan_cfg_get_int(mac_ctx,
608 WNI_CFG_BEACON_INTERVAL, &cfg);
609 if (eSIR_SUCCESS != sir_status) {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -0700610 pe_err("Failed to get WNI_CFG_BEACON_INTERVAL (%d)",
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800611 sir_status);
612 goto err_ret;
613 }
614 frm->BeaconInterval.interval = (uint16_t) cfg;
615 }
616
617 populate_dot11f_capabilities(mac_ctx, &frm->Capabilities, pe_session);
618 populate_dot11f_ssid(mac_ctx, (tSirMacSSid *) ssid, &frm->SSID);
619 populate_dot11f_supp_rates(mac_ctx, POPULATE_DOT11F_RATES_OPERATIONAL,
620 &frm->SuppRates, pe_session);
621
622 populate_dot11f_ds_params(mac_ctx, &frm->DSParams,
623 pe_session->currentOperChannel);
624 populate_dot11f_ibss_params(mac_ctx, &frm->IBSSParams, pe_session);
625
626 if (LIM_IS_AP_ROLE(pe_session)) {
627 if (pe_session->wps_state != SAP_WPS_DISABLED)
628 populate_dot11f_probe_res_wpsi_es(mac_ctx,
629 &frm->WscProbeRes,
630 pe_session);
631 } else {
632 if (wlan_cfg_get_int(mac_ctx, (uint16_t) WNI_CFG_WPS_ENABLE,
633 &tmp) != eSIR_SUCCESS)
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -0700634 pe_err("Failed to cfg get id %d", WNI_CFG_WPS_ENABLE);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800635
636 wps_ap = tmp & WNI_CFG_WPS_ENABLE_AP;
637
638 if (wps_ap)
639 populate_dot11f_wsc_in_probe_res(mac_ctx,
640 &frm->WscProbeRes);
641
642 if (mac_ctx->lim.wscIeInfo.probeRespWscEnrollmentState ==
643 eLIM_WSC_ENROLL_BEGIN) {
644 populate_dot11f_wsc_registrar_info_in_probe_res(mac_ctx,
645 &frm->WscProbeRes);
646 mac_ctx->lim.wscIeInfo.probeRespWscEnrollmentState =
647 eLIM_WSC_ENROLL_IN_PROGRESS;
648 }
649
650 if (mac_ctx->lim.wscIeInfo.wscEnrollmentState ==
651 eLIM_WSC_ENROLL_END) {
652 de_populate_dot11f_wsc_registrar_info_in_probe_res(
653 mac_ctx, &frm->WscProbeRes);
654 mac_ctx->lim.wscIeInfo.probeRespWscEnrollmentState =
655 eLIM_WSC_ENROLL_NOOP;
656 }
657 }
658
659 populate_dot11f_country(mac_ctx, &frm->Country, pe_session);
660 populate_dot11f_edca_param_set(mac_ctx, &frm->EDCAParamSet, pe_session);
661
662 if (pe_session->dot11mode != WNI_CFG_DOT11_MODE_11B)
663 populate_dot11f_erp_info(mac_ctx, &frm->ERPInfo, pe_session);
664
665 populate_dot11f_ext_supp_rates(mac_ctx,
666 POPULATE_DOT11F_RATES_OPERATIONAL,
667 &frm->ExtSuppRates, pe_session);
668
669 /* Populate HT IEs, when operating in 11n */
670 if (pe_session->htCapability) {
671 populate_dot11f_ht_caps(mac_ctx, pe_session, &frm->HTCaps);
672 populate_dot11f_ht_info(mac_ctx, &frm->HTInfo, pe_session);
673 }
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800674 if (pe_session->vhtCapability) {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -0700675 pe_debug("Populate VHT IE in Probe Response");
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800676 populate_dot11f_vht_caps(mac_ctx, pe_session, &frm->VHTCaps);
677 populate_dot11f_vht_operation(mac_ctx, pe_session,
678 &frm->VHTOperation);
679 /*
680 * we do not support multi users yet.
681 * populate_dot11f_vht_ext_bss_load( mac_ctx,
682 * &frm.VHTExtBssLoad );
683 */
684 is_vht_enabled = true;
685 }
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800686
Krishna Kumaar Natarajan0103ef82017-02-17 18:15:56 -0800687 if (lim_is_session_he_capable(pe_session)) {
Srinivas Girigowda28fb0122017-03-26 22:21:20 -0700688 pe_debug("Populate HE IEs");
Krishna Kumaar Natarajan0103ef82017-02-17 18:15:56 -0800689 populate_dot11f_he_caps(mac_ctx, pe_session,
690 &frm->vendor_he_cap);
691 populate_dot11f_he_operation(mac_ctx, pe_session,
692 &frm->vendor_he_op);
693 }
694
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800695 populate_dot11f_ext_cap(mac_ctx, is_vht_enabled, &frm->ExtCap,
696 pe_session);
697
698 if (pe_session->pLimStartBssReq) {
699 populate_dot11f_wpa(mac_ctx,
700 &(pe_session->pLimStartBssReq->rsnIE),
701 &frm->WPA);
702 populate_dot11f_rsn_opaque(mac_ctx,
703 &(pe_session->pLimStartBssReq->rsnIE),
704 &frm->RSNOpaque);
705 }
706
707 populate_dot11f_wmm(mac_ctx, &frm->WMMInfoAp, &frm->WMMParams,
708 &frm->WMMCaps, pe_session);
709
710#if defined(FEATURE_WLAN_WAPI)
711 if (pe_session->pLimStartBssReq)
712 populate_dot11f_wapi(mac_ctx,
713 &(pe_session->pLimStartBssReq->rsnIE),
714 &frm->WAPI);
715#endif /* defined(FEATURE_WLAN_WAPI) */
716
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800717 if (mac_ctx->lim.gpLimRemainOnChanReq)
718 bytes += (mac_ctx->lim.gpLimRemainOnChanReq->length -
719 sizeof(tSirRemainOnChnReq));
720 else
721 /*
722 * Only use CFG for non-listen mode. This CFG is not working for
723 * concurrency. In listening mode, probe rsp IEs is passed in
724 * the message from SME to PE.
725 */
726 addn_ie_present =
727 (pe_session->addIeParams.probeRespDataLen != 0);
728
729 if (addn_ie_present) {
730
Anurag Chouhan600c3a02016-03-01 10:33:54 +0530731 add_ie = qdf_mem_malloc(
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800732 pe_session->addIeParams.probeRespDataLen);
733 if (NULL == add_ie) {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -0700734 pe_err("add_ie allocation failed");
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800735 goto err_ret;
736 }
737
Anurag Chouhan600c3a02016-03-01 10:33:54 +0530738 qdf_mem_copy(add_ie,
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800739 pe_session->addIeParams.probeRespData_buff,
740 pe_session->addIeParams.probeRespDataLen);
741 addn_ie_len = pe_session->addIeParams.probeRespDataLen;
742
743 if (eSIR_SUCCESS != lim_get_addn_ie_for_probe_resp(mac_ctx,
744 add_ie, &addn_ie_len, preq_p2pie)) {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -0700745 pe_err("Unable to get addn_ie");
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800746 goto err_ret;
747 }
748
749 sir_status = lim_strip_extcap_update_struct(mac_ctx,
750 add_ie, &addn_ie_len,
751 &extracted_ext_cap);
752 if (eSIR_SUCCESS != sir_status) {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -0700753 pe_debug("Unable to strip off ExtCap IE");
Selvaraj, Sridhar94ece202016-06-23 20:44:09 +0530754 } else {
755 extracted_ext_cap_flag = true;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800756 }
757
758 bytes = bytes + addn_ie_len;
759
760 if (preq_p2pie)
761 p2p_ie = limGetP2pIEPtr(mac_ctx, &add_ie[0],
762 addn_ie_len);
763
764 if (p2p_ie != NULL) {
765 /* get NoA attribute stream P2P IE */
766 noalen = lim_get_noa_attr_stream(mac_ctx,
767 noa_stream, pe_session);
768 if (noalen != 0) {
769 total_noalen =
770 lim_build_p2p_ie(mac_ctx, &noa_ie[0],
771 &noa_stream[0], noalen);
772 bytes = bytes + total_noalen;
773 }
774 }
775 }
776
Hu Wang411e0cc2016-10-28 14:56:01 +0800777 /*
778 * Extcap IE now support variable length, merge Extcap IE from addn_ie
779 * may change the frame size. Therefore, MUST merge ExtCap IE before
780 * dot11f get packed payload size.
781 */
782 if (extracted_ext_cap_flag)
Hu Wangfbd279d2016-10-31 18:24:34 +0800783 lim_merge_extcap_struct(&frm->ExtCap, &extracted_ext_cap,
784 true);
Hu Wang411e0cc2016-10-28 14:56:01 +0800785
786 status = dot11f_get_packed_probe_response_size(mac_ctx, frm, &payload);
787 if (DOT11F_FAILED(status)) {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -0700788 pe_err("Probe Response size error (0x%08x)",
Hu Wang411e0cc2016-10-28 14:56:01 +0800789 status);
790 /* We'll fall back on the worst case scenario: */
791 payload = sizeof(tDot11fProbeResponse);
792 } else if (DOT11F_WARNED(status)) {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -0700793 pe_warn("Probe Response size warning (0x%08x)",
Hu Wang411e0cc2016-10-28 14:56:01 +0800794 status);
795 }
796
797 bytes += payload + sizeof(tSirMacMgmtHdr);
798
Anurag Chouhanfb54ab02016-02-18 18:00:46 +0530799 qdf_status = cds_packet_alloc((uint16_t) bytes, (void **)&frame,
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800800 (void **)&packet);
Anurag Chouhanfb54ab02016-02-18 18:00:46 +0530801 if (!QDF_IS_STATUS_SUCCESS(qdf_status)) {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -0700802 pe_err("Probe Response allocation failed");
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800803 goto err_ret;
804 }
805 /* Paranoia: */
Anurag Chouhan600c3a02016-03-01 10:33:54 +0530806 qdf_mem_set(frame, bytes, 0);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800807
808 /* Next, we fill out the buffer descriptor: */
809 lim_populate_mac_header(mac_ctx, frame, SIR_MAC_MGMT_FRAME,
810 SIR_MAC_MGMT_PROBE_RSP, peer_macaddr,
811 pe_session->selfMacAddr);
812
813 mac_hdr = (tpSirMacMgmtHdr) frame;
814
815 sir_copy_mac_addr(mac_hdr->bssId, pe_session->bssId);
816
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800817 /* That done, pack the Probe Response: */
818 status =
819 dot11f_pack_probe_response(mac_ctx, frm,
820 frame + sizeof(tSirMacMgmtHdr),
821 payload, &payload);
822 if (DOT11F_FAILED(status)) {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -0700823 pe_err("Probe Response pack failure (0x%08x)",
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800824 status);
825 goto err_ret;
826 } else if (DOT11F_WARNED(status)) {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -0700827 pe_warn("Probe Response pack warning (0x%08x)", status);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800828 }
829
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -0700830 pe_debug("Sending Probe Response frame to");
Nishank Aggarwal46bd31a2017-03-10 16:23:53 +0530831 lim_print_mac_addr(mac_ctx, peer_macaddr, LOGD);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800832
833 mac_ctx->sys.probeRespond++;
834
835 if (mac_ctx->lim.gpLimRemainOnChanReq)
Anurag Chouhan600c3a02016-03-01 10:33:54 +0530836 qdf_mem_copy(frame + sizeof(tSirMacMgmtHdr) + payload,
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800837 mac_ctx->lim.gpLimRemainOnChanReq->probeRspIe,
838 (mac_ctx->lim.gpLimRemainOnChanReq->length -
839 sizeof(tSirRemainOnChnReq)));
840
841 if (addn_ie_present)
Anurag Chouhan600c3a02016-03-01 10:33:54 +0530842 qdf_mem_copy(frame + sizeof(tSirMacMgmtHdr) + payload,
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800843 &add_ie[0], addn_ie_len);
844
845 if (noalen != 0) {
846 if (total_noalen >
847 (SIR_MAX_NOA_ATTR_LEN + SIR_P2P_IE_HEADER_LEN)) {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -0700848 pe_err("Not able to insert NoA, total len=%d",
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800849 total_noalen);
850 goto err_ret;
851 } else {
Anurag Chouhan600c3a02016-03-01 10:33:54 +0530852 qdf_mem_copy(&frame[bytes - (total_noalen)],
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800853 &noa_ie[0], total_noalen);
854 }
855 }
856
857 if ((SIR_BAND_5_GHZ == lim_get_rf_band(pe_session->currentOperChannel))
Anurag Chouhan6d760662016-02-20 16:05:43 +0530858 || (pe_session->pePersona == QDF_P2P_CLIENT_MODE) ||
859 (pe_session->pePersona == QDF_P2P_GO_MODE)
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800860 )
861 tx_flag |= HAL_USE_BD_RATE2_FOR_MANAGEMENT_FRAME;
862
863 /* Queue Probe Response frame in high priority WQ */
Anurag Chouhanfb54ab02016-02-18 18:00:46 +0530864 qdf_status = wma_tx_frame((tHalHandle) mac_ctx, packet,
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800865 (uint16_t) bytes,
866 TXRX_FRM_802_11_MGMT,
867 ANI_TXDIR_TODS,
868 7, lim_tx_complete, frame, tx_flag,
869 sme_sessionid, 0);
870
871 /* Pkt will be freed up by the callback */
Anurag Chouhanfb54ab02016-02-18 18:00:46 +0530872 if (!QDF_IS_STATUS_SUCCESS(qdf_status))
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -0700873 pe_err("Could not send Probe Response");
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800874
875 if (add_ie != NULL)
Anurag Chouhan600c3a02016-03-01 10:33:54 +0530876 qdf_mem_free(add_ie);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800877
Anurag Chouhan600c3a02016-03-01 10:33:54 +0530878 qdf_mem_free(frm);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800879 return;
880
881err_ret:
882 if (add_ie != NULL)
Anurag Chouhan600c3a02016-03-01 10:33:54 +0530883 qdf_mem_free(add_ie);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800884 if (frm != NULL)
Anurag Chouhan600c3a02016-03-01 10:33:54 +0530885 qdf_mem_free(frm);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800886 if (packet != NULL)
887 cds_packet_free((void *)packet);
888 return;
889
890} /* End lim_send_probe_rsp_mgmt_frame. */
891
892void
893lim_send_addts_req_action_frame(tpAniSirGlobal pMac,
894 tSirMacAddr peerMacAddr,
895 tSirAddtsReqInfo *pAddTS, tpPESession psessionEntry)
896{
897 uint16_t i;
898 uint8_t *pFrame;
899 tDot11fAddTSRequest AddTSReq;
900 tDot11fWMMAddTSRequest WMMAddTSReq;
901 uint32_t nPayload, nBytes, nStatus;
902 tpSirMacMgmtHdr pMacHdr;
903 void *pPacket;
904#ifdef FEATURE_WLAN_ESE
905 uint32_t phyMode;
906#endif
Anurag Chouhanfb54ab02016-02-18 18:00:46 +0530907 QDF_STATUS qdf_status;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800908 uint8_t txFlag = 0;
909 uint8_t smeSessionId = 0;
910
911 if (NULL == psessionEntry) {
912 return;
913 }
914
915 smeSessionId = psessionEntry->smeSessionId;
916
917 if (!pAddTS->wmeTspecPresent) {
Anurag Chouhan600c3a02016-03-01 10:33:54 +0530918 qdf_mem_set((uint8_t *) &AddTSReq, sizeof(AddTSReq), 0);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800919
920 AddTSReq.Action.action = SIR_MAC_QOS_ADD_TS_REQ;
921 AddTSReq.DialogToken.token = pAddTS->dialogToken;
922 AddTSReq.Category.category = SIR_MAC_ACTION_QOS_MGMT;
923 if (pAddTS->lleTspecPresent) {
924 populate_dot11f_tspec(&pAddTS->tspec, &AddTSReq.TSPEC);
925 } else {
926 populate_dot11f_wmmtspec(&pAddTS->tspec,
927 &AddTSReq.WMMTSPEC);
928 }
929
930 if (pAddTS->lleTspecPresent) {
931 AddTSReq.num_WMMTCLAS = 0;
932 AddTSReq.num_TCLAS = pAddTS->numTclas;
933 for (i = 0; i < pAddTS->numTclas; ++i) {
934 populate_dot11f_tclas(pMac, &pAddTS->tclasInfo[i],
935 &AddTSReq.TCLAS[i]);
936 }
937 } else {
938 AddTSReq.num_TCLAS = 0;
939 AddTSReq.num_WMMTCLAS = pAddTS->numTclas;
940 for (i = 0; i < pAddTS->numTclas; ++i) {
941 populate_dot11f_wmmtclas(pMac,
942 &pAddTS->tclasInfo[i],
943 &AddTSReq.WMMTCLAS[i]);
944 }
945 }
946
947 if (pAddTS->tclasProcPresent) {
948 if (pAddTS->lleTspecPresent) {
949 AddTSReq.TCLASSPROC.processing =
950 pAddTS->tclasProc;
951 AddTSReq.TCLASSPROC.present = 1;
952 } else {
953 AddTSReq.WMMTCLASPROC.version = 1;
954 AddTSReq.WMMTCLASPROC.processing =
955 pAddTS->tclasProc;
956 AddTSReq.WMMTCLASPROC.present = 1;
957 }
958 }
959
960 nStatus =
961 dot11f_get_packed_add_ts_request_size(pMac, &AddTSReq, &nPayload);
962 if (DOT11F_FAILED(nStatus)) {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -0700963 pe_err("Failed to calculate the packed size for an Add TS Request (0x%08x)",
964 nStatus);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800965 /* We'll fall back on the worst case scenario: */
966 nPayload = sizeof(tDot11fAddTSRequest);
967 } else if (DOT11F_WARNED(nStatus)) {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -0700968 pe_warn("There were warnings while calculating the packed size for an Add TS Request (0x%08x)",
969 nStatus);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800970 }
971 } else {
Anurag Chouhan600c3a02016-03-01 10:33:54 +0530972 qdf_mem_set((uint8_t *) &WMMAddTSReq, sizeof(WMMAddTSReq), 0);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800973
974 WMMAddTSReq.Action.action = SIR_MAC_QOS_ADD_TS_REQ;
975 WMMAddTSReq.DialogToken.token = pAddTS->dialogToken;
976 WMMAddTSReq.Category.category = SIR_MAC_ACTION_WME;
977
978 /* WMM spec 2.2.10 - status code is only filled in for ADDTS response */
979 WMMAddTSReq.StatusCode.statusCode = 0;
980
981 populate_dot11f_wmmtspec(&pAddTS->tspec, &WMMAddTSReq.WMMTSPEC);
982#ifdef FEATURE_WLAN_ESE
983 lim_get_phy_mode(pMac, &phyMode, psessionEntry);
984
985 if (phyMode == WNI_CFG_PHY_MODE_11G
986 || phyMode == WNI_CFG_PHY_MODE_11A) {
987 pAddTS->tsrsIE.rates[0] = TSRS_11AG_RATE_6MBPS;
988 } else {
989 pAddTS->tsrsIE.rates[0] = TSRS_11B_RATE_5_5MBPS;
990 }
991 populate_dot11_tsrsie(pMac, &pAddTS->tsrsIE,
992 &WMMAddTSReq.ESETrafStrmRateSet,
993 sizeof(uint8_t));
994#endif
995 /* fillWmeTspecIE */
996
997 nStatus =
998 dot11f_get_packed_wmm_add_ts_request_size(pMac, &WMMAddTSReq,
999 &nPayload);
1000 if (DOT11F_FAILED(nStatus)) {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07001001 pe_err("Failed to calculate the packed size for a WMM Add TS Request (0x%08x)",
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001002 nStatus);
1003 /* We'll fall back on the worst case scenario: */
1004 nPayload = sizeof(tDot11fAddTSRequest);
1005 } else if (DOT11F_WARNED(nStatus)) {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07001006 pe_warn("There were warnings while calculating the packed size for a WMM Add TS Request (0x%08x)",
1007 nStatus);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001008 }
1009 }
1010
1011 nBytes = nPayload + sizeof(tSirMacMgmtHdr);
1012
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05301013 qdf_status = cds_packet_alloc((uint16_t) nBytes, (void **)&pFrame,
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001014 (void **)&pPacket);
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05301015 if (!QDF_IS_STATUS_SUCCESS(qdf_status)) {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07001016 pe_err("Failed to allocate %d bytes for an Add TS Request",
1017 nBytes);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001018 return;
1019 }
1020 /* Paranoia: */
Anurag Chouhan600c3a02016-03-01 10:33:54 +05301021 qdf_mem_set(pFrame, nBytes, 0);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001022
1023 /* Next, we fill out the buffer descriptor: */
1024 lim_populate_mac_header(pMac, pFrame, SIR_MAC_MGMT_FRAME,
1025 SIR_MAC_MGMT_ACTION, peerMacAddr, psessionEntry->selfMacAddr);
1026 pMacHdr = (tpSirMacMgmtHdr) pFrame;
1027
1028 sir_copy_mac_addr(pMacHdr->bssId, psessionEntry->bssId);
1029
1030#ifdef WLAN_FEATURE_11W
1031 lim_set_protected_bit(pMac, psessionEntry, peerMacAddr, pMacHdr);
1032#endif
1033
1034 /* That done, pack the struct: */
1035 if (!pAddTS->wmeTspecPresent) {
1036 nStatus = dot11f_pack_add_ts_request(pMac, &AddTSReq,
1037 pFrame +
1038 sizeof(tSirMacMgmtHdr),
1039 nPayload, &nPayload);
1040 if (DOT11F_FAILED(nStatus)) {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07001041 pe_err("Failed to pack an Add TS Request "
1042 "(0x%08x)", nStatus);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001043 cds_packet_free((void *)pPacket);
1044 return; /* allocated! */
1045 } else if (DOT11F_WARNED(nStatus)) {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07001046 pe_warn("There were warnings while packing an Add TS Request (0x%08x)",
1047 nStatus);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001048 }
1049 } else {
1050 nStatus = dot11f_pack_wmm_add_ts_request(pMac, &WMMAddTSReq,
1051 pFrame +
1052 sizeof(tSirMacMgmtHdr),
1053 nPayload, &nPayload);
1054 if (DOT11F_FAILED(nStatus)) {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07001055 pe_err("Failed to pack a WMM Add TS Request (0x%08x)",
1056 nStatus);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001057 cds_packet_free((void *)pPacket);
1058 return; /* allocated! */
1059 } else if (DOT11F_WARNED(nStatus)) {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07001060 pe_warn("There were warnings while packing a WMM Add TS Request (0x%08x)",
1061 nStatus);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001062 }
1063 }
1064
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07001065 pe_debug("Sending an Add TS Request frame to");
1066 lim_print_mac_addr(pMac, peerMacAddr, LOGD);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001067
1068 if ((SIR_BAND_5_GHZ ==
1069 lim_get_rf_band(psessionEntry->currentOperChannel))
Anurag Chouhan6d760662016-02-20 16:05:43 +05301070 || (psessionEntry->pePersona == QDF_P2P_CLIENT_MODE)
1071 || (psessionEntry->pePersona == QDF_P2P_GO_MODE)
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001072 ) {
1073 txFlag |= HAL_USE_BD_RATE2_FOR_MANAGEMENT_FRAME;
1074 }
1075
Anurag Chouhanb2dc16f2016-02-25 11:47:37 +05301076 MTRACE(qdf_trace(QDF_MODULE_ID_PE, TRACE_CODE_TX_MGMT,
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001077 psessionEntry->peSessionId, pMacHdr->fc.subType));
1078
1079 /* Queue Addts Response frame in high priority WQ */
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05301080 qdf_status = wma_tx_frame(pMac, pPacket, (uint16_t) nBytes,
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001081 TXRX_FRM_802_11_MGMT,
1082 ANI_TXDIR_TODS,
1083 7, lim_tx_complete, pFrame, txFlag,
1084 smeSessionId, 0);
Anurag Chouhanb2dc16f2016-02-25 11:47:37 +05301085 MTRACE(qdf_trace(QDF_MODULE_ID_PE, TRACE_CODE_TX_COMPLETE,
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05301086 psessionEntry->peSessionId, qdf_status));
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001087
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07001088 if (!QDF_IS_STATUS_SUCCESS(qdf_status))
1089 pe_err("Could not send an Add TS Request (%X",
1090 qdf_status);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001091} /* End lim_send_addts_req_action_frame. */
1092
1093/**
1094 * lim_send_assoc_rsp_mgmt_frame() - Send assoc response
1095 * @mac_ctx: Handle for mac context
1096 * @status_code: Status code for assoc response frame
1097 * @aid: Association ID
1098 * @peer_addr: Mac address of requesting peer
1099 * @subtype: Assoc/Reassoc
1100 * @sta: Pointer to station node
1101 * @pe_session: PE session id.
1102 *
1103 * Builds and sends association response frame to the requesting peer.
1104 *
1105 * Return: void
1106 */
1107
1108void
1109lim_send_assoc_rsp_mgmt_frame(tpAniSirGlobal mac_ctx,
1110 uint16_t status_code, uint16_t aid, tSirMacAddr peer_addr,
1111 uint8_t subtype, tpDphHashNode sta, tpPESession pe_session)
1112{
1113 static tDot11fAssocResponse frm;
1114 uint8_t *frame;
1115 tpSirMacMgmtHdr mac_hdr;
1116 tSirRetStatus sir_status;
1117 uint8_t lle_mode = 0, addts;
1118 tHalBitVal qos_mode, wme_mode;
Hu Wang411e0cc2016-10-28 14:56:01 +08001119 uint32_t payload, bytes = 0, status;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001120 void *packet;
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05301121 QDF_STATUS qdf_status;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001122 tUpdateBeaconParams beacon_params;
1123 uint8_t tx_flag = 0;
1124 uint32_t addn_ie_len = 0;
1125 uint8_t add_ie[WNI_CFG_ASSOC_RSP_ADDNIE_DATA_LEN];
1126 tpSirAssocReq assoc_req = NULL;
1127 uint8_t sme_session = 0;
1128 bool is_vht = false;
1129 uint16_t stripoff_len = 0;
1130 tDot11fIEExtCap extracted_ext_cap;
1131 bool extracted_flag = false;
1132#ifdef WLAN_FEATURE_11W
1133 uint32_t retry_int;
1134 uint32_t max_retries;
1135#endif
1136
1137 if (NULL == pe_session) {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07001138 pe_err("pe_session is NULL");
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001139 return;
1140 }
1141
1142 sme_session = pe_session->smeSessionId;
1143
Anurag Chouhan600c3a02016-03-01 10:33:54 +05301144 qdf_mem_set((uint8_t *) &frm, sizeof(frm), 0);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001145
1146 limGetQosMode(pe_session, &qos_mode);
1147 limGetWmeMode(pe_session, &wme_mode);
1148
1149 /*
1150 * An Add TS IE is added only if the AP supports it and
1151 * the requesting STA sent a traffic spec.
1152 */
1153 addts = (qos_mode && sta && sta->qos.addtsPresent) ? 1 : 0;
1154
1155 frm.Status.status = status_code;
1156
1157 frm.AID.associd = aid | LIM_AID_MASK;
1158
1159 if (NULL == sta) {
1160 populate_dot11f_supp_rates(mac_ctx,
1161 POPULATE_DOT11F_RATES_OPERATIONAL,
1162 &frm.SuppRates, pe_session);
1163 populate_dot11f_ext_supp_rates(mac_ctx,
1164 POPULATE_DOT11F_RATES_OPERATIONAL,
1165 &frm.ExtSuppRates, pe_session);
1166 } else {
1167 populate_dot11f_assoc_rsp_rates(mac_ctx, &frm.SuppRates,
1168 &frm.ExtSuppRates,
1169 sta->supportedRates.llbRates,
1170 sta->supportedRates.llaRates);
1171 }
1172
1173 if (LIM_IS_AP_ROLE(pe_session) && sta != NULL &&
1174 eSIR_SUCCESS == status_code) {
1175 assoc_req = (tpSirAssocReq)
1176 pe_session->parsedAssocReq[sta->assocId];
1177 /*
1178 * populate P2P IE in AssocRsp when assocReq from the peer
1179 * includes P2P IE
1180 */
1181 if (assoc_req != NULL && assoc_req->addIEPresent)
1182 populate_dot11_assoc_res_p2p_ie(mac_ctx,
1183 &frm.P2PAssocRes,
1184 assoc_req);
1185 }
1186
1187 if (NULL != sta) {
1188 if (eHAL_SET == qos_mode) {
1189 if (sta->lleEnabled) {
1190 lle_mode = 1;
1191 populate_dot11f_edca_param_set(mac_ctx,
1192 &frm.EDCAParamSet, pe_session);
1193 }
1194 }
1195
1196 if ((!lle_mode) && (eHAL_SET == wme_mode) && sta->wmeEnabled) {
1197 populate_dot11f_wmm_params(mac_ctx, &frm.WMMParams,
1198 pe_session);
1199
1200 if (sta->wsmEnabled)
1201 populate_dot11f_wmm_caps(&frm.WMMCaps);
1202 }
1203
1204 if (sta->mlmStaContext.htCapability &&
1205 pe_session->htCapability) {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07001206 pe_debug("Populate HT IEs in Assoc Response");
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001207 populate_dot11f_ht_caps(mac_ctx, pe_session,
1208 &frm.HTCaps);
Krunal Sonief3294b2015-06-12 15:12:19 -07001209 /*
1210 * Check the STA capability and
1211 * update the HTCaps accordingly
1212 */
1213 frm.HTCaps.supportedChannelWidthSet = (
1214 sta->htSupportedChannelWidthSet <
1215 pe_session->htSupportedChannelWidthSet) ?
1216 sta->htSupportedChannelWidthSet :
1217 pe_session->htSupportedChannelWidthSet;
1218 if (!frm.HTCaps.supportedChannelWidthSet)
1219 frm.HTCaps.shortGI40MHz = 0;
1220
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001221 populate_dot11f_ht_info(mac_ctx, &frm.HTInfo,
1222 pe_session);
1223 }
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07001224 pe_debug("SupportedChnlWidth: %d, mimoPS: %d, GF: %d, short GI20:%d, shortGI40: %d, dsssCck: %d, AMPDU Param: %x",
Agrawal Ashishc38e58d2015-09-16 17:17:29 +05301225 frm.HTCaps.supportedChannelWidthSet,
1226 frm.HTCaps.mimoPowerSave,
1227 frm.HTCaps.greenField, frm.HTCaps.shortGI20MHz,
1228 frm.HTCaps.shortGI40MHz,
1229 frm.HTCaps.dsssCckMode40MHz,
1230 frm.HTCaps.maxRxAMPDUFactor);
1231
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001232 if (sta->mlmStaContext.vhtCapability &&
1233 pe_session->vhtCapability) {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07001234 pe_debug("Populate VHT IEs in Assoc Response");
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001235 populate_dot11f_vht_caps(mac_ctx, pe_session,
1236 &frm.VHTCaps);
1237 populate_dot11f_vht_operation(mac_ctx, pe_session,
Kapil Gupta4b2efbb2016-10-03 13:07:20 +05301238 &frm.VHTOperation);
1239 is_vht = true;
Nitesh Shahdb5ea0d2017-03-22 15:17:47 +05301240 } else {
1241 /* Advertise 1x1 if either is HT-STA */
1242 if (frm.HTCaps.present && mac_ctx->hw_dbs_capable)
1243 frm.HTCaps.supportedMCSSet[1] = 0;
Kapil Gupta4b2efbb2016-10-03 13:07:20 +05301244 }
1245 if (pe_session->vhtCapability &&
1246 pe_session->vendor_vht_sap &&
1247 (assoc_req != NULL) &&
1248 assoc_req->vendor_vht_ie.VHTCaps.present) {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07001249 pe_debug("Populate Vendor VHT IEs in Assoc Rsponse");
Kapil Gupta4b2efbb2016-10-03 13:07:20 +05301250 frm.vendor_vht_ie.present = 1;
1251 frm.vendor_vht_ie.type =
1252 pe_session->vendor_specific_vht_ie_type;
1253 frm.vendor_vht_ie.sub_type =
1254 pe_session->vendor_specific_vht_ie_sub_type;
1255
1256 frm.vendor_vht_ie.VHTCaps.present = 1;
1257 populate_dot11f_vht_caps(mac_ctx, pe_session,
1258 &frm.vendor_vht_ie.VHTCaps);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001259 is_vht = true;
1260 }
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001261 populate_dot11f_ext_cap(mac_ctx, is_vht, &frm.ExtCap,
1262 pe_session);
1263
Krishna Kumaar Natarajan0103ef82017-02-17 18:15:56 -08001264 if (lim_is_sta_he_capable(sta) &&
1265 lim_is_session_he_capable(pe_session)) {
Srinivas Girigowda28fb0122017-03-26 22:21:20 -07001266 pe_debug("Populate HE IEs");
Krishna Kumaar Natarajan0103ef82017-02-17 18:15:56 -08001267 populate_dot11f_he_caps(mac_ctx, pe_session,
1268 &frm.vendor_he_cap);
1269 populate_dot11f_he_operation(mac_ctx, pe_session,
1270 &frm.vendor_he_op);
1271 }
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001272#ifdef WLAN_FEATURE_11W
1273 if (eSIR_MAC_TRY_AGAIN_LATER == status_code) {
1274 if (wlan_cfg_get_int
1275 (mac_ctx, WNI_CFG_PMF_SA_QUERY_MAX_RETRIES,
1276 &max_retries) != eSIR_SUCCESS)
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07001277 pe_err("get WNI_CFG_PMF_SA_QUERY_MAX_RETRIES failure");
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001278 else if (wlan_cfg_get_int
1279 (mac_ctx,
1280 WNI_CFG_PMF_SA_QUERY_RETRY_INTERVAL,
1281 &retry_int) != eSIR_SUCCESS)
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07001282 pe_err("get WNI_CFG_PMF_SA_QUERY_RETRY_INTERVAL failure");
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001283 else
1284 populate_dot11f_timeout_interval(mac_ctx,
1285 &frm.TimeoutInterval,
1286 SIR_MAC_TI_TYPE_ASSOC_COMEBACK,
1287 (max_retries -
1288 sta->pmfSaQueryRetryCount)
1289 * retry_int);
1290 }
1291#endif
1292 }
1293
Anurag Chouhan600c3a02016-03-01 10:33:54 +05301294 qdf_mem_set((uint8_t *) &beacon_params, sizeof(beacon_params), 0);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001295
1296 if (LIM_IS_AP_ROLE(pe_session) &&
1297 (pe_session->gLimProtectionControl !=
1298 WNI_CFG_FORCE_POLICY_PROTECTION_DISABLE))
1299 lim_decide_ap_protection(mac_ctx, peer_addr,
1300 &beacon_params, pe_session);
1301
1302 lim_update_short_preamble(mac_ctx, peer_addr, &beacon_params,
1303 pe_session);
1304 lim_update_short_slot_time(mac_ctx, peer_addr, &beacon_params,
1305 pe_session);
1306
1307 /*
1308 * Populate Do11capabilities after updating session with
1309 * Assos req details
1310 */
1311 populate_dot11f_capabilities(mac_ctx, &frm.Capabilities, pe_session);
1312
1313 beacon_params.bssIdx = pe_session->bssIdx;
1314
1315 /* Send message to HAL about beacon parameter change. */
1316 if ((false == mac_ctx->sap.SapDfsInfo.is_dfs_cac_timer_running)
1317 && beacon_params.paramChangeBitmap) {
1318 sch_set_fixed_beacon_fields(mac_ctx, pe_session);
1319 lim_send_beacon_params(mac_ctx, &beacon_params, pe_session);
1320 }
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001321
1322 if (assoc_req != NULL) {
Krishna Kumaar Natarajane4e3a142016-04-01 16:27:51 -07001323 addn_ie_len = pe_session->addIeParams.assocRespDataLen;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001324
1325 /* Nonzero length indicates Assoc rsp IE available */
Krishna Kumaar Natarajane4e3a142016-04-01 16:27:51 -07001326 if (addn_ie_len > 0 &&
1327 addn_ie_len <= WNI_CFG_ASSOC_RSP_ADDNIE_DATA_LEN &&
1328 (bytes + addn_ie_len) <= SIR_MAX_PACKET_SIZE) {
Anurag Chouhan600c3a02016-03-01 10:33:54 +05301329 qdf_mem_copy(add_ie,
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001330 pe_session->addIeParams.assocRespData_buff,
1331 pe_session->addIeParams.assocRespDataLen);
1332
Anurag Chouhan600c3a02016-03-01 10:33:54 +05301333 qdf_mem_set((uint8_t *) &extracted_ext_cap,
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001334 sizeof(extracted_ext_cap), 0);
1335
1336 stripoff_len = addn_ie_len;
1337 sir_status =
1338 lim_strip_extcap_update_struct
1339 (mac_ctx, &add_ie[0], &stripoff_len,
1340 &extracted_ext_cap);
1341 if (eSIR_SUCCESS != sir_status) {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07001342 pe_debug("strip off extcap IE failed");
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001343 } else {
1344 addn_ie_len = stripoff_len;
1345 extracted_flag = true;
1346 }
1347 bytes = bytes + addn_ie_len;
1348 }
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07001349 pe_debug("addn_ie_len: %d for Assoc Resp: %d",
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001350 addn_ie_len, assoc_req->addIEPresent);
1351 }
Hu Wang411e0cc2016-10-28 14:56:01 +08001352
1353 /*
1354 * Extcap IE now support variable length, merge Extcap IE from addn_ie
1355 * may change the frame size. Therefore, MUST merge ExtCap IE before
1356 * dot11f get packed payload size.
1357 */
1358 if (extracted_flag)
Hu Wangfbd279d2016-10-31 18:24:34 +08001359 lim_merge_extcap_struct(&(frm.ExtCap), &extracted_ext_cap,
1360 true);
Hu Wang411e0cc2016-10-28 14:56:01 +08001361
1362 /* Allocate a buffer for this frame: */
1363 status = dot11f_get_packed_assoc_response_size(mac_ctx, &frm, &payload);
1364 if (DOT11F_FAILED(status)) {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07001365 pe_err("get Association Response size failure (0x%08x)",
Hu Wang411e0cc2016-10-28 14:56:01 +08001366 status);
1367 return;
1368 } else if (DOT11F_WARNED(status)) {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07001369 pe_warn("get Association Response size warning (0x%08x)",
Hu Wang411e0cc2016-10-28 14:56:01 +08001370 status);
1371 }
1372
1373 bytes += sizeof(tSirMacMgmtHdr) + payload;
1374
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05301375 qdf_status = cds_packet_alloc((uint16_t) bytes, (void **)&frame,
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001376 (void **)&packet);
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05301377 if (!QDF_IS_STATUS_SUCCESS(qdf_status)) {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07001378 pe_err("cds_packet_alloc failed");
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001379 return;
1380 }
1381 /* Paranoia: */
Anurag Chouhan600c3a02016-03-01 10:33:54 +05301382 qdf_mem_set(frame, bytes, 0);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001383
1384 /* Next, we fill out the buffer descriptor: */
1385 lim_populate_mac_header(mac_ctx, frame, SIR_MAC_MGMT_FRAME,
1386 (LIM_ASSOC == subtype) ?
1387 SIR_MAC_MGMT_ASSOC_RSP : SIR_MAC_MGMT_REASSOC_RSP,
1388 peer_addr,
1389 pe_session->selfMacAddr);
1390 mac_hdr = (tpSirMacMgmtHdr) frame;
1391
1392 sir_copy_mac_addr(mac_hdr->bssId, pe_session->bssId);
1393
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001394 status = dot11f_pack_assoc_response(mac_ctx, &frm,
1395 frame + sizeof(tSirMacMgmtHdr),
1396 payload, &payload);
1397 if (DOT11F_FAILED(status)) {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07001398 pe_err("Association Response pack failure(0x%08x)",
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001399 status);
1400 cds_packet_free((void *)packet);
1401 return;
1402 } else if (DOT11F_WARNED(status)) {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07001403 pe_warn("Association Response pack warning (0x%08x)",
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001404 status);
1405 }
1406
1407 if (subtype == LIM_ASSOC)
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07001408 pe_debug("*** Sending Assoc Resp status %d aid %d to",
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001409 status_code, aid);
1410 else
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07001411 pe_debug("*** Sending ReAssoc Resp status %d aid %d to",
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001412 status_code, aid);
1413
1414 lim_print_mac_addr(mac_ctx, mac_hdr->da, LOG1);
1415
1416 if (addn_ie_len && addn_ie_len <= WNI_CFG_ASSOC_RSP_ADDNIE_DATA_LEN)
Anurag Chouhan600c3a02016-03-01 10:33:54 +05301417 qdf_mem_copy(frame + sizeof(tSirMacMgmtHdr) + payload,
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001418 &add_ie[0], addn_ie_len);
1419
1420 if ((SIR_BAND_5_GHZ ==
1421 lim_get_rf_band(pe_session->currentOperChannel)) ||
Anurag Chouhan6d760662016-02-20 16:05:43 +05301422 (pe_session->pePersona == QDF_P2P_CLIENT_MODE) ||
1423 (pe_session->pePersona == QDF_P2P_GO_MODE))
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001424 tx_flag |= HAL_USE_BD_RATE2_FOR_MANAGEMENT_FRAME;
1425
Anurag Chouhanb2dc16f2016-02-25 11:47:37 +05301426 MTRACE(qdf_trace(QDF_MODULE_ID_PE, TRACE_CODE_TX_MGMT,
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001427 pe_session->peSessionId, mac_hdr->fc.subType));
1428 /* Queue Association Response frame in high priority WQ */
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05301429 qdf_status = wma_tx_frame(mac_ctx, packet, (uint16_t) bytes,
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001430 TXRX_FRM_802_11_MGMT,
1431 ANI_TXDIR_TODS,
1432 7, lim_tx_complete, frame, tx_flag,
1433 sme_session, 0);
Anurag Chouhanb2dc16f2016-02-25 11:47:37 +05301434 MTRACE(qdf_trace(QDF_MODULE_ID_PE, TRACE_CODE_TX_COMPLETE,
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05301435 pe_session->peSessionId, qdf_status));
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001436
1437 /* Pkt will be freed up by the callback */
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05301438 if (!QDF_IS_STATUS_SUCCESS(qdf_status))
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07001439 pe_err("Could not Send Re/AssocRsp, retCode=%X",
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05301440 qdf_status);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001441
1442 /*
1443 * update the ANI peer station count.
1444 * FIXME_PROTECTION : take care of different type of station
1445 * counter inside this function.
1446 */
1447 lim_util_count_sta_add(mac_ctx, sta, pe_session);
1448
1449}
1450
1451void
1452lim_send_delts_req_action_frame(tpAniSirGlobal pMac,
1453 tSirMacAddr peer,
1454 uint8_t wmmTspecPresent,
1455 tSirMacTSInfo *pTsinfo,
1456 tSirMacTspecIE *pTspecIe, tpPESession psessionEntry)
1457{
1458 uint8_t *pFrame;
1459 tpSirMacMgmtHdr pMacHdr;
1460 tDot11fDelTS DelTS;
1461 tDot11fWMMDelTS WMMDelTS;
1462 uint32_t nBytes, nPayload, nStatus;
1463 void *pPacket;
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05301464 QDF_STATUS qdf_status;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001465 uint8_t txFlag = 0;
1466 uint8_t smeSessionId = 0;
1467
1468 if (NULL == psessionEntry) {
1469 return;
1470 }
1471
1472 smeSessionId = psessionEntry->smeSessionId;
1473
1474 if (!wmmTspecPresent) {
Anurag Chouhan600c3a02016-03-01 10:33:54 +05301475 qdf_mem_set((uint8_t *) &DelTS, sizeof(DelTS), 0);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001476
1477 DelTS.Category.category = SIR_MAC_ACTION_QOS_MGMT;
1478 DelTS.Action.action = SIR_MAC_QOS_DEL_TS_REQ;
1479 populate_dot11f_ts_info(pTsinfo, &DelTS.TSInfo);
1480
1481 nStatus = dot11f_get_packed_del_ts_size(pMac, &DelTS, &nPayload);
1482 if (DOT11F_FAILED(nStatus)) {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07001483 pe_err("Failed to calculate the packed size for a Del TS (0x%08x)", nStatus);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001484 /* We'll fall back on the worst case scenario: */
1485 nPayload = sizeof(tDot11fDelTS);
1486 } else if (DOT11F_WARNED(nStatus)) {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07001487 pe_warn("There were warnings while calculating the packed size for a Del TS (0x%08x)",
1488 nStatus);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001489 }
1490 } else {
Anurag Chouhan600c3a02016-03-01 10:33:54 +05301491 qdf_mem_set((uint8_t *) &WMMDelTS, sizeof(WMMDelTS), 0);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001492
1493 WMMDelTS.Category.category = SIR_MAC_ACTION_WME;
1494 WMMDelTS.Action.action = SIR_MAC_QOS_DEL_TS_REQ;
1495 WMMDelTS.DialogToken.token = 0;
1496 WMMDelTS.StatusCode.statusCode = 0;
1497 populate_dot11f_wmmtspec(pTspecIe, &WMMDelTS.WMMTSPEC);
1498 nStatus =
1499 dot11f_get_packed_wmm_del_ts_size(pMac, &WMMDelTS, &nPayload);
1500 if (DOT11F_FAILED(nStatus)) {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07001501 pe_err("Failed to calculate the packed size for a WMM Del TS (0x%08x)", nStatus);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001502 /* We'll fall back on the worst case scenario: */
1503 nPayload = sizeof(tDot11fDelTS);
1504 } else if (DOT11F_WARNED(nStatus)) {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07001505 pe_warn("There were warnings while calculating the packed size for a WMM Del TS (0x%08x)",
1506 nStatus);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001507 }
1508 }
1509
1510 nBytes = nPayload + sizeof(tSirMacMgmtHdr);
1511
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05301512 qdf_status =
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001513 cds_packet_alloc((uint16_t) nBytes, (void **)&pFrame,
1514 (void **)&pPacket);
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05301515 if (!QDF_IS_STATUS_SUCCESS(qdf_status)) {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07001516 pe_err("Failed to allocate %d bytes for an Add TS Response",
1517 nBytes);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001518 return;
1519 }
1520 /* Paranoia: */
Anurag Chouhan600c3a02016-03-01 10:33:54 +05301521 qdf_mem_set(pFrame, nBytes, 0);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001522
1523 /* Next, we fill out the buffer descriptor: */
1524 lim_populate_mac_header(pMac, pFrame, SIR_MAC_MGMT_FRAME,
1525 SIR_MAC_MGMT_ACTION, peer, psessionEntry->selfMacAddr);
1526 pMacHdr = (tpSirMacMgmtHdr) pFrame;
1527
1528 sir_copy_mac_addr(pMacHdr->bssId, psessionEntry->bssId);
1529
1530#ifdef WLAN_FEATURE_11W
1531 lim_set_protected_bit(pMac, psessionEntry, peer, pMacHdr);
1532#endif
1533
1534 /* That done, pack the struct: */
1535 if (!wmmTspecPresent) {
1536 nStatus = dot11f_pack_del_ts(pMac, &DelTS,
1537 pFrame + sizeof(tSirMacMgmtHdr),
1538 nPayload, &nPayload);
1539 if (DOT11F_FAILED(nStatus)) {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07001540 pe_err("Failed to pack a Del TS frame (0x%08x)",
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001541 nStatus);
1542 cds_packet_free((void *)pPacket);
1543 return; /* allocated! */
1544 } else if (DOT11F_WARNED(nStatus)) {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07001545 pe_warn("There were warnings while packing a Del TS frame (0x%08x)",
1546 nStatus);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001547 }
1548 } else {
1549 nStatus = dot11f_pack_wmm_del_ts(pMac, &WMMDelTS,
1550 pFrame + sizeof(tSirMacMgmtHdr),
1551 nPayload, &nPayload);
1552 if (DOT11F_FAILED(nStatus)) {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07001553 pe_err("Failed to pack a WMM Del TS frame (0x%08x)",
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001554 nStatus);
1555 cds_packet_free((void *)pPacket);
1556 return; /* allocated! */
1557 } else if (DOT11F_WARNED(nStatus)) {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07001558 pe_warn("There were warnings while packing a WMM Del TS frame (0x%08x)",
1559 nStatus);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001560 }
1561 }
1562
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07001563 pe_debug("Sending DELTS REQ (size %d) to ", nBytes);
1564 lim_print_mac_addr(pMac, pMacHdr->da, LOGD);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001565
1566 if ((SIR_BAND_5_GHZ ==
1567 lim_get_rf_band(psessionEntry->currentOperChannel))
Anurag Chouhan6d760662016-02-20 16:05:43 +05301568 || (psessionEntry->pePersona == QDF_P2P_CLIENT_MODE)
1569 || (psessionEntry->pePersona == QDF_P2P_GO_MODE)
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001570 ) {
1571 txFlag |= HAL_USE_BD_RATE2_FOR_MANAGEMENT_FRAME;
1572 }
1573
Anurag Chouhanb2dc16f2016-02-25 11:47:37 +05301574 MTRACE(qdf_trace(QDF_MODULE_ID_PE, TRACE_CODE_TX_MGMT,
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001575 psessionEntry->peSessionId, pMacHdr->fc.subType));
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05301576 qdf_status = wma_tx_frame(pMac, pPacket, (uint16_t) nBytes,
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001577 TXRX_FRM_802_11_MGMT,
1578 ANI_TXDIR_TODS,
1579 7, lim_tx_complete, pFrame, txFlag,
1580 smeSessionId, 0);
Anurag Chouhanb2dc16f2016-02-25 11:47:37 +05301581 MTRACE(qdf_trace(QDF_MODULE_ID_PE, TRACE_CODE_TX_COMPLETE,
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05301582 psessionEntry->peSessionId, qdf_status));
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001583 /* Pkt will be freed up by the callback */
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05301584 if (!QDF_IS_STATUS_SUCCESS(qdf_status))
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07001585 pe_err("Failed to send Del TS (%X)!", qdf_status);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001586
1587} /* End lim_send_delts_req_action_frame. */
1588
1589/**
1590 * lim_send_assoc_req_mgmt_frame() - Send association request
1591 * @mac_ctx: Handle to MAC context
1592 * @mlm_assoc_req: Association request information
1593 * @pe_session: PE session information
1594 *
1595 * Builds and transmits association request frame to AP.
1596 *
1597 * Return: Void
1598 */
1599
1600void
1601lim_send_assoc_req_mgmt_frame(tpAniSirGlobal mac_ctx,
1602 tLimMlmAssocReq *mlm_assoc_req,
1603 tpPESession pe_session)
1604{
1605 tDot11fAssocRequest *frm;
1606 uint16_t caps;
1607 uint8_t *frame;
1608 tSirRetStatus sir_status;
1609 tLimMlmAssocCnf assoc_cnf;
Hu Wang411e0cc2016-10-28 14:56:01 +08001610 uint32_t bytes = 0, payload, status;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001611 uint8_t qos_enabled, wme_enabled, wsm_enabled;
1612 void *packet;
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05301613 QDF_STATUS qdf_status;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001614 uint16_t add_ie_len;
1615 uint8_t *add_ie;
1616 uint8_t *wps_ie = NULL;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001617 uint8_t power_caps = false;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001618 uint8_t tx_flag = 0;
1619 uint8_t sme_sessionid = 0;
1620 bool vht_enabled = false;
1621 tDot11fIEExtCap extr_ext_cap;
1622 bool extr_ext_flag = true;
1623 tpSirMacMgmtHdr mac_hdr;
Hu Wangfbd279d2016-10-31 18:24:34 +08001624 uint32_t ie_offset = 0;
1625 uint8_t *p_ext_cap = NULL;
1626 tDot11fIEExtCap bcn_ext_cap;
1627 uint8_t *bcn_ie = NULL;
1628 uint32_t bcn_ie_len = 0;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001629
1630 if (NULL == pe_session) {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07001631 pe_err("pe_session is NULL");
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001632 return;
1633 }
1634
1635 sme_sessionid = pe_session->smeSessionId;
1636
1637 /* check this early to avoid unncessary operation */
1638 if (NULL == pe_session->pLimJoinReq) {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07001639 pe_err("pe_session->pLimJoinReq is NULL");
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001640 return;
1641 }
1642 add_ie_len = pe_session->pLimJoinReq->addIEAssoc.length;
1643 add_ie = pe_session->pLimJoinReq->addIEAssoc.addIEdata;
1644
Anurag Chouhan600c3a02016-03-01 10:33:54 +05301645 frm = qdf_mem_malloc(sizeof(tDot11fAssocRequest));
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001646 if (NULL == frm) {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07001647 pe_err("Unable to allocate memory");
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001648 return;
1649 }
Hu Wang411e0cc2016-10-28 14:56:01 +08001650 qdf_mem_set((uint8_t *) frm, sizeof(tDot11fAssocRequest), 0);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001651
Agrawal Ashish0f94b572016-02-22 13:27:06 +05301652 if (add_ie_len && pe_session->is_ext_caps_present) {
Anurag Chouhan600c3a02016-03-01 10:33:54 +05301653 qdf_mem_set((uint8_t *) &extr_ext_cap, sizeof(tDot11fIEExtCap),
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001654 0);
1655 sir_status = lim_strip_extcap_update_struct(mac_ctx,
1656 add_ie, &add_ie_len, &extr_ext_cap);
1657 if (eSIR_SUCCESS != sir_status) {
1658 extr_ext_flag = false;
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07001659 pe_debug("Unable to Stripoff ExtCap IE from Assoc Req");
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001660 } else {
1661 struct s_ext_cap *p_ext_cap = (struct s_ext_cap *)
1662 extr_ext_cap.bytes;
1663
1664 if (p_ext_cap->interworking_service)
1665 p_ext_cap->qos_map = 1;
Hu Wang411e0cc2016-10-28 14:56:01 +08001666 extr_ext_cap.num_bytes =
1667 lim_compute_ext_cap_ie_length(&extr_ext_cap);
1668 extr_ext_flag = (extr_ext_cap.num_bytes > 0);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001669 }
1670 } else {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07001671 pe_debug("No addn IE or peer dosen't support addnIE for Assoc Req");
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001672 extr_ext_flag = false;
1673 }
1674
1675 caps = mlm_assoc_req->capabilityInfo;
1676#if defined(FEATURE_WLAN_WAPI)
1677 /*
1678 * According to WAPI standard:
1679 * 7.3.1.4 Capability Information field
1680 * In WAPI, non-AP STAs within an ESS set the Privacy subfield to 0
1681 * in transmitted Association or Reassociation management frames.
1682 * APs ignore the Privacy subfield within received Association and
1683 * Reassociation management frames.
1684 */
1685 if (pe_session->encryptType == eSIR_ED_WPI)
1686 ((tSirMacCapabilityInfo *) &caps)->privacy = 0;
1687#endif
1688 swap_bit_field16(caps, (uint16_t *) &frm->Capabilities);
1689
1690 frm->ListenInterval.interval = mlm_assoc_req->listenInterval;
1691 populate_dot11f_ssid2(mac_ctx, &frm->SSID);
1692 populate_dot11f_supp_rates(mac_ctx, POPULATE_DOT11F_RATES_OPERATIONAL,
1693 &frm->SuppRates, pe_session);
1694
1695 qos_enabled = (pe_session->limQosEnabled) &&
1696 SIR_MAC_GET_QOS(pe_session->limCurrentBssCaps);
1697
1698 wme_enabled = (pe_session->limWmeEnabled) &&
1699 LIM_BSS_CAPS_GET(WME, pe_session->limCurrentBssQosCaps);
1700
1701 /* We prefer .11e asociations: */
1702 if (qos_enabled)
1703 wme_enabled = false;
1704
1705 wsm_enabled = (pe_session->limWsmEnabled) && wme_enabled &&
1706 LIM_BSS_CAPS_GET(WSM, pe_session->limCurrentBssQosCaps);
1707
1708 if (pe_session->lim11hEnable &&
1709 pe_session->pLimJoinReq->spectrumMgtIndicator == eSIR_TRUE) {
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001710 power_caps = true;
1711
1712 populate_dot11f_power_caps(mac_ctx, &frm->PowerCaps,
1713 LIM_ASSOC, pe_session);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001714 populate_dot11f_supp_channels(mac_ctx, &frm->SuppChannels,
1715 LIM_ASSOC, pe_session);
1716
1717 }
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001718 if (mac_ctx->rrm.rrmPEContext.rrmEnable &&
1719 SIR_MAC_GET_RRM(pe_session->limCurrentBssCaps)) {
1720 if (power_caps == false) {
1721 power_caps = true;
1722 populate_dot11f_power_caps(mac_ctx, &frm->PowerCaps,
1723 LIM_ASSOC, pe_session);
1724 }
1725 }
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001726 if (qos_enabled)
Naveen Rawatcd118312016-11-22 10:46:21 -08001727 populate_dot11f_qos_caps_station(mac_ctx, pe_session,
1728 &frm->QOSCapsStation);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001729
1730 populate_dot11f_ext_supp_rates(mac_ctx,
1731 POPULATE_DOT11F_RATES_OPERATIONAL, &frm->ExtSuppRates,
1732 pe_session);
1733
Gupta, Kapil54a16992016-01-13 19:34:02 +05301734 if (mac_ctx->rrm.rrmPEContext.rrmEnable &&
1735 SIR_MAC_GET_RRM(pe_session->limCurrentBssCaps))
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001736 populate_dot11f_rrm_ie(mac_ctx, &frm->RRMEnabledCap,
1737 pe_session);
Deepak Dhamdhere641bf322016-01-06 15:19:03 -08001738
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001739 /*
1740 * The join request *should* contain zero or one of the WPA and RSN
1741 * IEs. The payload send along with the request is a
1742 * 'tSirSmeJoinReq'; the IE portion is held inside a 'tSirRSNie':
1743 * typedef struct sSirRSNie
1744 * {
1745 * uint16_t length;
1746 * uint8_t rsnIEdata[SIR_MAC_MAX_IE_LENGTH+2];
1747 * } tSirRSNie, *tpSirRSNie;
1748 * So, we should be able to make the following two calls harmlessly,
1749 * since they do nothing if they don't find the given IE in the
1750 * bytestream with which they're provided.
1751 * The net effect of this will be to faithfully transmit whatever
1752 * security IE is in the join request.
1753 * However, if we're associating for the purpose of WPS
1754 * enrollment, and we've been configured to indicate that by
1755 * eliding the WPA or RSN IE, we just skip this:
1756 */
1757 if (add_ie_len && add_ie)
1758 wps_ie = limGetWscIEPtr(mac_ctx, add_ie, add_ie_len);
1759
1760 if (NULL == wps_ie) {
1761 populate_dot11f_rsn_opaque(mac_ctx,
1762 &(pe_session->pLimJoinReq->rsnIE),
1763 &frm->RSNOpaque);
1764 populate_dot11f_wpa_opaque(mac_ctx,
1765 &(pe_session->pLimJoinReq->rsnIE),
1766 &frm->WPAOpaque);
1767#if defined(FEATURE_WLAN_WAPI)
1768 populate_dot11f_wapi_opaque(mac_ctx,
1769 &(pe_session->pLimJoinReq->rsnIE),
1770 &frm->WAPIOpaque);
1771#endif /* defined(FEATURE_WLAN_WAPI) */
1772 }
1773 /* include WME EDCA IE as well */
1774 if (wme_enabled) {
1775 populate_dot11f_wmm_info_station_per_session(mac_ctx,
1776 pe_session, &frm->WMMInfoStation);
1777
1778 if (wsm_enabled)
1779 populate_dot11f_wmm_caps(&frm->WMMCaps);
1780 }
1781
1782 /*
1783 * Populate HT IEs, when operating in 11n and
1784 * when AP is also operating in 11n mode
1785 */
1786 if (pe_session->htCapability &&
1787 mac_ctx->lim.htCapabilityPresentInBeacon) {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07001788 pe_debug("Populate HT Caps in Assoc Request");
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001789 populate_dot11f_ht_caps(mac_ctx, pe_session, &frm->HTCaps);
Naveen Rawata410c5a2016-09-19 14:22:33 -07001790 QDF_TRACE_HEX_DUMP(QDF_MODULE_ID_PE, QDF_TRACE_LEVEL_DEBUG,
1791 &frm->HTCaps, sizeof(frm->HTCaps));
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001792 }
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07001793 pe_debug("SupportedChnlWidth: %d, mimoPS: %d, GF: %d, short GI20:%d, shortGI40: %d, dsssCck: %d, AMPDU Param: %x",
Agrawal Ashishc38e58d2015-09-16 17:17:29 +05301794 frm->HTCaps.supportedChannelWidthSet,
1795 frm->HTCaps.mimoPowerSave,
1796 frm->HTCaps.greenField, frm->HTCaps.shortGI20MHz,
1797 frm->HTCaps.shortGI40MHz,
1798 frm->HTCaps.dsssCckMode40MHz,
1799 frm->HTCaps.maxRxAMPDUFactor);
1800
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001801 if (pe_session->vhtCapability &&
1802 pe_session->vhtCapabilityPresentInBeacon) {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07001803 pe_debug("Populate VHT IEs in Assoc Request");
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001804 populate_dot11f_vht_caps(mac_ctx, pe_session, &frm->VHTCaps);
Naveen Rawata410c5a2016-09-19 14:22:33 -07001805 QDF_TRACE_HEX_DUMP(QDF_MODULE_ID_PE, QDF_TRACE_LEVEL_DEBUG,
1806 &frm->VHTCaps, sizeof(frm->VHTCaps));
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001807 vht_enabled = true;
Kiran Kumar Lokere1d4094e2016-08-31 19:04:04 -07001808 if (pe_session->enableHtSmps &&
1809 !pe_session->supported_nss_1x1) {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07001810 pe_err("VHT OP mode IE in Assoc Req");
Kiran Kumar Lokere1d4094e2016-08-31 19:04:04 -07001811 populate_dot11f_operating_mode(mac_ctx,
1812 &frm->OperatingMode, pe_session);
1813 }
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001814 }
1815 if (!vht_enabled &&
1816 pe_session->is_vendor_specific_vhtcaps) {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07001817 pe_debug("Populate Vendor VHT IEs in Assoc Request");
Kapil Gupta4b2efbb2016-10-03 13:07:20 +05301818 frm->vendor_vht_ie.present = 1;
1819 frm->vendor_vht_ie.type =
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001820 pe_session->vendor_specific_vht_ie_type;
Kapil Gupta4b2efbb2016-10-03 13:07:20 +05301821 frm->vendor_vht_ie.sub_type =
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001822 pe_session->vendor_specific_vht_ie_sub_type;
1823
Kapil Gupta4b2efbb2016-10-03 13:07:20 +05301824 frm->vendor_vht_ie.VHTCaps.present = 1;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001825 populate_dot11f_vht_caps(mac_ctx, pe_session,
Kapil Gupta4b2efbb2016-10-03 13:07:20 +05301826 &frm->vendor_vht_ie.VHTCaps);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001827 vht_enabled = true;
1828 }
Agrawal Ashish0f94b572016-02-22 13:27:06 +05301829 if (pe_session->is_ext_caps_present)
1830 populate_dot11f_ext_cap(mac_ctx, vht_enabled,
1831 &frm->ExtCap, pe_session);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001832
Selvaraj, Sridhara521aab2017-03-25 16:42:34 +05301833 if (mac_ctx->roam.configParam.qcn_ie_support)
1834 populate_dot11f_qcn_ie(&frm->QCN_IE);
1835
Krishna Kumaar Natarajan0103ef82017-02-17 18:15:56 -08001836 if (lim_is_session_he_capable(pe_session)) {
Srinivas Girigowda28fb0122017-03-26 22:21:20 -07001837 pe_debug("Populate HE IEs");
Krishna Kumaar Natarajan0103ef82017-02-17 18:15:56 -08001838 populate_dot11f_he_caps(mac_ctx, pe_session,
1839 &frm->vendor_he_cap);
1840 }
Selvaraj, Sridharc2fe7a32017-02-02 19:20:16 +05301841
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001842 if (pe_session->pLimJoinReq->is11Rconnection) {
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001843 tSirBssDescription *bssdescr;
1844
1845 bssdescr = &pe_session->pLimJoinReq->bssDescription;
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07001846 pe_debug("mdie = %02x %02x %02x",
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001847 (unsigned int) bssdescr->mdie[0],
1848 (unsigned int) bssdescr->mdie[1],
1849 (unsigned int) bssdescr->mdie[2]);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001850 populate_mdie(mac_ctx, &frm->MobilityDomain,
1851 pe_session->pLimJoinReq->bssDescription.mdie);
1852 } else {
1853 /* No 11r IEs dont send any MDIE */
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07001854 pe_debug("MDIE not present");
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001855 }
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001856
1857#ifdef FEATURE_WLAN_ESE
1858 /*
1859 * ESE Version IE will be included in association request
1860 * when ESE is enabled on DUT through ini and it is also
1861 * advertised by the peer AP to which we are trying to
1862 * associate to.
1863 */
1864 if (pe_session->is_ese_version_ie_present &&
1865 mac_ctx->roam.configParam.isEseIniFeatureEnabled)
1866 populate_dot11f_ese_version(&frm->ESEVersion);
1867 /* For ESE Associations fill the ESE IEs */
1868 if (pe_session->isESEconnection &&
1869 pe_session->pLimJoinReq->isESEFeatureIniEnabled) {
1870#ifndef FEATURE_DISABLE_RM
1871 populate_dot11f_ese_rad_mgmt_cap(&frm->ESERadMgmtCap);
1872#endif
1873 }
1874#endif
1875
Hu Wang411e0cc2016-10-28 14:56:01 +08001876 /*
1877 * Extcap IE now support variable length, merge Extcap IE from addn_ie
1878 * may change the frame size. Therefore, MUST merge ExtCap IE before
1879 * dot11f get packed payload size.
1880 */
1881 if (extr_ext_flag)
Hu Wangfbd279d2016-10-31 18:24:34 +08001882 lim_merge_extcap_struct(&frm->ExtCap, &extr_ext_cap, true);
1883
1884 /* Clear the bits in EXTCAP IE if AP not advertise it in beacon */
1885 if (frm->ExtCap.present && pe_session->is_ext_caps_present) {
1886 ie_offset = DOT11F_FF_TIMESTAMP_LEN +
1887 DOT11F_FF_BEACONINTERVAL_LEN +
1888 DOT11F_FF_CAPABILITIES_LEN;
1889
1890 qdf_mem_zero((uint8_t *)&bcn_ext_cap, sizeof(tDot11fIEExtCap));
1891 if (pe_session->beacon && pe_session->bcnLen > ie_offset) {
1892 bcn_ie = pe_session->beacon + ie_offset;
1893 bcn_ie_len = pe_session->bcnLen - ie_offset;
1894 p_ext_cap = lim_get_ie_ptr_new(mac_ctx,
1895 bcn_ie,
1896 bcn_ie_len,
1897 DOT11F_EID_EXTCAP,
1898 ONE_BYTE);
1899 lim_update_extcap_struct(mac_ctx, p_ext_cap,
1900 &bcn_ext_cap);
1901 lim_merge_extcap_struct(&frm->ExtCap, &bcn_ext_cap,
1902 false);
1903 }
1904 }
Hu Wang411e0cc2016-10-28 14:56:01 +08001905
Arif Hussain6cec6bc2017-02-14 13:46:26 -08001906 if (eSIR_SUCCESS != lim_strip_supp_op_class_update_struct(mac_ctx,
1907 add_ie, &add_ie_len, &frm->SuppOperatingClasses))
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07001908 pe_debug("Unable to Stripoff supp op classes IE from Assoc Req");
Arif Hussain6cec6bc2017-02-14 13:46:26 -08001909
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001910 status = dot11f_get_packed_assoc_request_size(mac_ctx, frm, &payload);
1911 if (DOT11F_FAILED(status)) {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07001912 pe_err("Association Request packet size failure(0x%08x)",
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001913 status);
1914 /* We'll fall back on the worst case scenario: */
1915 payload = sizeof(tDot11fAssocRequest);
1916 } else if (DOT11F_WARNED(status)) {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07001917 pe_warn("Association request packet size warning (0x%08x)",
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001918 status);
1919 }
1920
1921 bytes = payload + sizeof(tSirMacMgmtHdr) + add_ie_len;
1922
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05301923 qdf_status = cds_packet_alloc((uint16_t) bytes, (void **)&frame,
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001924 (void **)&packet);
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05301925 if (!QDF_IS_STATUS_SUCCESS(qdf_status)) {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07001926 pe_err("Failed to allocate %d bytes", bytes);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001927
1928 pe_session->limMlmState = pe_session->limPrevMlmState;
Anurag Chouhanb2dc16f2016-02-25 11:47:37 +05301929 MTRACE(qdf_trace(QDF_MODULE_ID_PE, TRACE_CODE_MLM_STATE,
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001930 pe_session->peSessionId,
1931 pe_session->limMlmState));
1932
1933 /* Update PE session id */
1934 assoc_cnf.sessionId = pe_session->peSessionId;
1935
1936 assoc_cnf.resultCode = eSIR_SME_RESOURCES_UNAVAILABLE;
1937
1938 cds_packet_free((void *)packet);
1939
1940 lim_post_sme_message(mac_ctx, LIM_MLM_ASSOC_CNF,
1941 (uint32_t *) &assoc_cnf);
1942
Anurag Chouhan600c3a02016-03-01 10:33:54 +05301943 qdf_mem_free(frm);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001944 return;
1945 }
1946 /* Paranoia: */
Anurag Chouhan600c3a02016-03-01 10:33:54 +05301947 qdf_mem_set(frame, bytes, 0);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001948
1949 /* Next, we fill out the buffer descriptor: */
1950 lim_populate_mac_header(mac_ctx, frame, SIR_MAC_MGMT_FRAME,
1951 SIR_MAC_MGMT_ASSOC_REQ, pe_session->bssId,
1952 pe_session->selfMacAddr);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001953 /* That done, pack the Assoc Request: */
1954 status = dot11f_pack_assoc_request(mac_ctx, frm,
1955 frame + sizeof(tSirMacMgmtHdr), payload, &payload);
1956 if (DOT11F_FAILED(status)) {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07001957 pe_err("Assoc request pack failure (0x%08x)", status);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001958 cds_packet_free((void *)packet);
Anurag Chouhan600c3a02016-03-01 10:33:54 +05301959 qdf_mem_free(frm);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001960 return;
1961 } else if (DOT11F_WARNED(status)) {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07001962 pe_warn("Assoc request pack warning (0x%08x)", status);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001963 }
1964
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07001965 pe_debug("Sending Association Request length %d to ", bytes);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001966 if (pe_session->assocReq != NULL) {
Anurag Chouhan600c3a02016-03-01 10:33:54 +05301967 qdf_mem_free(pe_session->assocReq);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001968 pe_session->assocReq = NULL;
Naveen Rawat83102ef2015-11-03 10:42:34 -08001969 pe_session->assocReqLen = 0;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001970 }
1971
1972 if (add_ie_len) {
Anurag Chouhan600c3a02016-03-01 10:33:54 +05301973 qdf_mem_copy(frame + sizeof(tSirMacMgmtHdr) + payload,
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001974 add_ie, add_ie_len);
1975 payload += add_ie_len;
1976 }
1977
Anurag Chouhan600c3a02016-03-01 10:33:54 +05301978 pe_session->assocReq = qdf_mem_malloc(payload);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001979 if (NULL == pe_session->assocReq) {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07001980 pe_err("Unable to allocate memory");
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001981 } else {
1982 /*
1983 * Store the Assoc request. This is sent to csr/hdd in
1984 * join cnf response.
1985 */
Anurag Chouhan600c3a02016-03-01 10:33:54 +05301986 qdf_mem_copy(pe_session->assocReq,
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001987 frame + sizeof(tSirMacMgmtHdr), payload);
1988 pe_session->assocReqLen = payload;
1989 }
1990
1991 if ((SIR_BAND_5_GHZ == lim_get_rf_band(pe_session->currentOperChannel))
Anurag Chouhan6d760662016-02-20 16:05:43 +05301992 || (pe_session->pePersona == QDF_P2P_CLIENT_MODE)
1993 || (pe_session->pePersona == QDF_P2P_GO_MODE)
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001994 )
1995 tx_flag |= HAL_USE_BD_RATE2_FOR_MANAGEMENT_FRAME;
1996
Anurag Chouhan6d760662016-02-20 16:05:43 +05301997 if (pe_session->pePersona == QDF_P2P_CLIENT_MODE ||
1998 pe_session->pePersona == QDF_STA_MODE)
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001999 tx_flag |= HAL_USE_PEER_STA_REQUESTED_MASK;
2000
2001#ifdef FEATURE_WLAN_DIAG_SUPPORT
2002 lim_diag_event_report(mac_ctx, WLAN_PE_DIAG_ASSOC_START_EVENT,
2003 pe_session, eSIR_SUCCESS, eSIR_SUCCESS);
2004#endif
2005 mac_hdr = (tpSirMacMgmtHdr) frame;
Anurag Chouhanb2dc16f2016-02-25 11:47:37 +05302006 MTRACE(qdf_trace(QDF_MODULE_ID_PE, TRACE_CODE_TX_MGMT,
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002007 pe_session->peSessionId, mac_hdr->fc.subType));
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05302008 qdf_status =
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002009 wma_tx_frame(mac_ctx, packet,
2010 (uint16_t) (sizeof(tSirMacMgmtHdr) + payload),
2011 TXRX_FRM_802_11_MGMT, ANI_TXDIR_TODS, 7,
2012 lim_tx_complete, frame, tx_flag, sme_sessionid, 0);
Anurag Chouhanb2dc16f2016-02-25 11:47:37 +05302013 MTRACE(qdf_trace
Anurag Chouhan6d760662016-02-20 16:05:43 +05302014 (QDF_MODULE_ID_PE, TRACE_CODE_TX_COMPLETE,
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05302015 pe_session->peSessionId, qdf_status));
2016 if (!QDF_IS_STATUS_SUCCESS(qdf_status)) {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07002017 pe_err("Failed to send Association Request (%X)!",
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05302018 qdf_status);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002019 /* Pkt will be freed up by the callback */
Anurag Chouhan600c3a02016-03-01 10:33:54 +05302020 qdf_mem_free(frm);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002021 return;
2022 }
2023 /* Free up buffer allocated for mlm_assoc_req */
Anurag Chouhan600c3a02016-03-01 10:33:54 +05302024 qdf_mem_free(mlm_assoc_req);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002025 mlm_assoc_req = NULL;
Anurag Chouhan600c3a02016-03-01 10:33:54 +05302026 qdf_mem_free(frm);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002027 return;
2028}
2029
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002030/**
Abhishek Singh7d3bc3e2016-02-03 17:45:01 +05302031 * lim_auth_tx_complete_cnf()- Confirmation for auth sent over the air
Himanshu Agarwal2fdf77a2016-12-29 11:41:00 +05302032 * @context: pointer to global mac
2033 * @buf: buffer
Abhishek Singh7d3bc3e2016-02-03 17:45:01 +05302034 * @tx_complete : Sent status
Himanshu Agarwal2fdf77a2016-12-29 11:41:00 +05302035 * @params; tx completion params
Abhishek Singh7d3bc3e2016-02-03 17:45:01 +05302036 *
2037 * Return: This returns QDF_STATUS
2038 */
2039
Himanshu Agarwal2fdf77a2016-12-29 11:41:00 +05302040static QDF_STATUS lim_auth_tx_complete_cnf(void *context,
2041 qdf_nbuf_t buf,
2042 uint32_t tx_complete,
2043 void *params)
Abhishek Singh7d3bc3e2016-02-03 17:45:01 +05302044{
Himanshu Agarwal2fdf77a2016-12-29 11:41:00 +05302045 tpAniSirGlobal mac_ctx = (tpAniSirGlobal)context;
2046
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07002047 pe_debug("tx_complete= %d", tx_complete);
Abhishek Singh7d3bc3e2016-02-03 17:45:01 +05302048 if (tx_complete) {
2049 mac_ctx->auth_ack_status = LIM_AUTH_ACK_RCD_SUCCESS;
2050 /* 'Change' timer for future activations */
2051 lim_deactivate_and_change_timer(mac_ctx, eLIM_AUTH_RETRY_TIMER);
2052 } else {
2053 mac_ctx->auth_ack_status = LIM_AUTH_ACK_RCD_FAILURE;
2054 }
Himanshu Agarwal8b472bc2017-01-20 20:49:41 +05302055
2056 if (buf)
2057 qdf_nbuf_free(buf);
2058
Abhishek Singh7d3bc3e2016-02-03 17:45:01 +05302059 return QDF_STATUS_SUCCESS;
2060}
2061
2062/**
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002063 * lim_send_auth_mgmt_frame() - Send an Authentication frame
2064 *
2065 * @mac_ctx: Pointer to Global MAC structure
2066 * @auth_frame: Pointer to Authentication frame structure
2067 * @peer_addr: MAC address of destination peer
2068 * @wep_bit: wep bit in frame control for Authentication frame3
2069 * @session: PE session information
2070 *
2071 * This function is called by lim_process_mlm_messages(). Authentication frame
2072 * is formatted and sent when this function is called.
2073 *
2074 * Return: void
2075 */
2076
2077void
2078lim_send_auth_mgmt_frame(tpAniSirGlobal mac_ctx,
2079 tpSirMacAuthFrameBody auth_frame,
2080 tSirMacAddr peer_addr,
Abhishek Singh7d3bc3e2016-02-03 17:45:01 +05302081 uint8_t wep_bit,
2082 tpPESession session, bool wait_for_ack)
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002083{
2084 uint8_t *frame, *body;
2085 uint32_t frame_len = 0, body_len = 0;
2086 tpSirMacMgmtHdr mac_hdr;
2087 void *packet;
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05302088 QDF_STATUS qdf_status;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002089 uint8_t tx_flag = 0;
2090 uint8_t sme_sessionid = 0;
2091 uint16_t ft_ies_length = 0;
2092
2093 if (NULL == session) {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07002094 pe_err("Error: psession Entry is NULL");
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002095 return;
2096 }
2097
2098 sme_sessionid = session->smeSessionId;
2099
Krishna Kumaar Natarajan7e6a23c2016-04-05 14:45:24 -07002100 if (wep_bit == LIM_WEP_IN_FC) {
2101 /*
2102 * Auth frame3 to be sent with encrypted framebody
2103 *
2104 * Allocate buffer for Authenticaton frame of size
2105 * equal to management frame header length plus 2 bytes
2106 * each for auth algorithm number, transaction number,
2107 * status code, 128 bytes for challenge text and
2108 * 4 bytes each for IV & ICV.
2109 */
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07002110 pe_debug("Sending encrypted auth frame to " MAC_ADDRESS_STR,
2111 MAC_ADDR_ARRAY(peer_addr));
Krishna Kumaar Natarajan7e6a23c2016-04-05 14:45:24 -07002112
2113 frame_len = sizeof(tSirMacMgmtHdr) + LIM_ENCR_AUTH_BODY_LEN;
2114 body_len = LIM_ENCR_AUTH_BODY_LEN;
2115
2116 goto alloc_packet;
2117 }
2118
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07002119 pe_info("Sending Auth seq# %d status %d (%d) wait_for_ack %d to "
2120 MAC_ADDRESS_STR,
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002121 auth_frame->authTransactionSeqNumber,
2122 auth_frame->authStatusCode,
2123 (auth_frame->authStatusCode == eSIR_MAC_SUCCESS_STATUS),
Abhishek Singh7d3bc3e2016-02-03 17:45:01 +05302124 wait_for_ack,
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002125 MAC_ADDR_ARRAY(peer_addr));
2126
2127 switch (auth_frame->authTransactionSeqNumber) {
2128 case SIR_MAC_AUTH_FRAME_1:
2129 /*
2130 * Allocate buffer for Authenticaton frame of size
2131 * equal to management frame header length plus 2 bytes
2132 * each for auth algorithm number, transaction number
2133 * and status code.
2134 */
2135
2136 frame_len = sizeof(tSirMacMgmtHdr) +
2137 SIR_MAC_AUTH_CHALLENGE_OFFSET;
2138 body_len = SIR_MAC_AUTH_CHALLENGE_OFFSET;
2139
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002140 if (auth_frame->authAlgoNumber == eSIR_FT_AUTH) {
2141 if (NULL != session->ftPEContext.pFTPreAuthReq &&
2142 0 != session->ftPEContext.pFTPreAuthReq->
2143 ft_ies_length) {
2144 ft_ies_length = session->ftPEContext.
2145 pFTPreAuthReq->ft_ies_length;
2146 frame_len += ft_ies_length;
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07002147 pe_debug("Auth frame, FTIES length added=%d",
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002148 ft_ies_length);
2149 } else {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07002150 pe_debug("Auth frame, Does not contain FTIES!");
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002151 frame_len += (2 + SIR_MDIE_SIZE);
2152 }
2153 }
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002154 break;
2155
2156 case SIR_MAC_AUTH_FRAME_2:
2157 if ((auth_frame->authAlgoNumber == eSIR_OPEN_SYSTEM) ||
2158 ((auth_frame->authAlgoNumber == eSIR_SHARED_KEY) &&
2159 (auth_frame->authStatusCode !=
2160 eSIR_MAC_SUCCESS_STATUS))) {
2161 /*
2162 * Allocate buffer for Authenticaton frame of size
2163 * equal to management frame header length plus
2164 * 2 bytes each for auth algorithm number,
2165 * transaction number and status code.
2166 */
2167
2168 frame_len = sizeof(tSirMacMgmtHdr) +
2169 SIR_MAC_AUTH_CHALLENGE_OFFSET;
2170 body_len = SIR_MAC_AUTH_CHALLENGE_OFFSET;
2171 } else {
2172 /*
2173 * Shared Key algorithm with challenge text
2174 * to be sent.
2175 *
2176 * Allocate buffer for Authenticaton frame of size
2177 * equal to management frame header length plus
2178 * 2 bytes each for auth algorithm number,
2179 * transaction number, status code and 128 bytes
2180 * for challenge text.
2181 */
2182
2183 frame_len = sizeof(tSirMacMgmtHdr) +
2184 sizeof(tSirMacAuthFrame);
2185 body_len = sizeof(tSirMacAuthFrameBody);
2186 }
2187 break;
2188
2189 case SIR_MAC_AUTH_FRAME_3:
Krishna Kumaar Natarajan7e6a23c2016-04-05 14:45:24 -07002190 /*
2191 * Auth frame3 to be sent without encrypted framebody
2192 *
2193 * Allocate buffer for Authenticaton frame of size equal
2194 * to management frame header length plus 2 bytes each
2195 * for auth algorithm number, transaction number and
2196 * status code.
2197 */
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002198
Krishna Kumaar Natarajan7e6a23c2016-04-05 14:45:24 -07002199 frame_len = sizeof(tSirMacMgmtHdr) +
2200 SIR_MAC_AUTH_CHALLENGE_OFFSET;
2201 body_len = SIR_MAC_AUTH_CHALLENGE_OFFSET;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002202 break;
2203
2204 case SIR_MAC_AUTH_FRAME_4:
2205 /*
2206 * Allocate buffer for Authenticaton frame of size equal
2207 * to management frame header length plus 2 bytes each
2208 * for auth algorithm number, transaction number and
2209 * status code.
2210 */
2211
2212 frame_len = sizeof(tSirMacMgmtHdr) +
2213 SIR_MAC_AUTH_CHALLENGE_OFFSET;
2214 body_len = SIR_MAC_AUTH_CHALLENGE_OFFSET;
2215
2216 break;
Krishna Kumaar Natarajan7e6a23c2016-04-05 14:45:24 -07002217 default:
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07002218 pe_err("Invalid auth transaction seq num");
Krishna Kumaar Natarajan7e6a23c2016-04-05 14:45:24 -07002219 return;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002220 } /* switch (auth_frame->authTransactionSeqNumber) */
2221
Krishna Kumaar Natarajan7e6a23c2016-04-05 14:45:24 -07002222alloc_packet:
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05302223 qdf_status = cds_packet_alloc((uint16_t) frame_len, (void **)&frame,
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002224 (void **)&packet);
2225
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05302226 if (!QDF_IS_STATUS_SUCCESS(qdf_status)) {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07002227 pe_err("call to bufAlloc failed for AUTH frame");
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002228 return;
2229 }
2230
Anurag Chouhan600c3a02016-03-01 10:33:54 +05302231 qdf_mem_zero(frame, frame_len);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002232
2233 /* Prepare BD */
2234 lim_populate_mac_header(mac_ctx, frame, SIR_MAC_MGMT_FRAME,
2235 SIR_MAC_MGMT_AUTH, peer_addr, session->selfMacAddr);
2236 mac_hdr = (tpSirMacMgmtHdr) frame;
2237 mac_hdr->fc.wep = wep_bit;
2238
2239 /* Prepare BSSId */
Rajeev Kumarcf835a02016-04-15 15:01:31 -07002240 if (LIM_IS_AP_ROLE(session))
Anurag Chouhan600c3a02016-03-01 10:33:54 +05302241 qdf_mem_copy((uint8_t *) mac_hdr->bssId,
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002242 (uint8_t *) session->bssId,
2243 sizeof(tSirMacAddr));
2244
2245 /* Prepare Authentication frame body */
2246 body = frame + sizeof(tSirMacMgmtHdr);
2247
2248 if (wep_bit == LIM_WEP_IN_FC) {
Anurag Chouhan600c3a02016-03-01 10:33:54 +05302249 qdf_mem_copy(body, (uint8_t *) auth_frame, body_len);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002250
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07002251 pe_debug("Sending Auth seq# 3 to " MAC_ADDRESS_STR,
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002252 MAC_ADDR_ARRAY(mac_hdr->da));
2253
2254 } else {
2255 *((uint16_t *) (body)) =
2256 sir_swap_u16if_needed(auth_frame->authAlgoNumber);
2257 body += sizeof(uint16_t);
2258 body_len -= sizeof(uint16_t);
2259
2260 *((uint16_t *) (body)) =
2261 sir_swap_u16if_needed(
2262 auth_frame->authTransactionSeqNumber);
2263 body += sizeof(uint16_t);
2264 body_len -= sizeof(uint16_t);
2265
2266 *((uint16_t *) (body)) =
2267 sir_swap_u16if_needed(auth_frame->authStatusCode);
2268 body += sizeof(uint16_t);
2269 body_len -= sizeof(uint16_t);
2270 if (body_len <= (sizeof(auth_frame->type) +
2271 sizeof(auth_frame->length) +
2272 sizeof(auth_frame->challengeText)))
Anurag Chouhan600c3a02016-03-01 10:33:54 +05302273 qdf_mem_copy(body, (uint8_t *) &auth_frame->type,
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002274 body_len);
2275
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002276 if ((auth_frame->authAlgoNumber == eSIR_FT_AUTH) &&
2277 (auth_frame->authTransactionSeqNumber ==
2278 SIR_MAC_AUTH_FRAME_1) &&
2279 (session->ftPEContext.pFTPreAuthReq != NULL)) {
2280
2281 if (ft_ies_length > 0) {
Anurag Chouhan600c3a02016-03-01 10:33:54 +05302282 qdf_mem_copy(body,
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002283 session->ftPEContext.
2284 pFTPreAuthReq->ft_ies,
2285 ft_ies_length);
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07002286 pe_debug("Auth1 Frame FTIE is: ");
Srinivas Girigowdab896a562017-03-16 17:41:26 -07002287 QDF_TRACE_HEX_DUMP(QDF_MODULE_ID_PE,
2288 QDF_TRACE_LEVEL_DEBUG,
2289 (uint8_t *) body,
2290 ft_ies_length);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002291 } else if (NULL != session->ftPEContext.
2292 pFTPreAuthReq->pbssDescription) {
2293 /* MDID attr is 54 */
2294 *body = SIR_MDIE_ELEMENT_ID;
2295 body++;
2296 *body = SIR_MDIE_SIZE;
2297 body++;
Anurag Chouhan600c3a02016-03-01 10:33:54 +05302298 qdf_mem_copy(body,
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002299 &session->ftPEContext.pFTPreAuthReq->
2300 pbssDescription->mdie[0],
2301 SIR_MDIE_SIZE);
2302 }
2303 }
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002304
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07002305 pe_debug("*** Sending Auth seq# %d status %d (%d) to "
2306 MAC_ADDRESS_STR,
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002307 auth_frame->authTransactionSeqNumber,
2308 auth_frame->authStatusCode,
2309 (auth_frame->authStatusCode ==
2310 eSIR_MAC_SUCCESS_STATUS),
2311 MAC_ADDR_ARRAY(mac_hdr->da));
2312 }
Srinivas Girigowdab896a562017-03-16 17:41:26 -07002313 QDF_TRACE_HEX_DUMP(QDF_MODULE_ID_PE,
2314 QDF_TRACE_LEVEL_DEBUG,
2315 frame, frame_len);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002316
Deepthi Gowri1de51e32016-09-01 15:47:28 +05302317 if ((NULL != session->ftPEContext.pFTPreAuthReq) &&
2318 (SIR_BAND_5_GHZ == lim_get_rf_band(
2319 session->ftPEContext.pFTPreAuthReq->preAuthchannelNum)))
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002320 tx_flag |= HAL_USE_BD_RATE2_FOR_MANAGEMENT_FRAME;
Deepthi Gowri1de51e32016-09-01 15:47:28 +05302321 else if ((SIR_BAND_5_GHZ ==
2322 lim_get_rf_band(session->currentOperChannel))
2323 || (session->pePersona == QDF_P2P_CLIENT_MODE)
2324 || (session->pePersona == QDF_P2P_GO_MODE))
2325 tx_flag |= HAL_USE_BD_RATE2_FOR_MANAGEMENT_FRAME;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002326
Anurag Chouhan6d760662016-02-20 16:05:43 +05302327 if (session->pePersona == QDF_P2P_CLIENT_MODE ||
2328 session->pePersona == QDF_STA_MODE)
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002329 tx_flag |= HAL_USE_PEER_STA_REQUESTED_MASK;
2330
Anurag Chouhanb2dc16f2016-02-25 11:47:37 +05302331 MTRACE(qdf_trace(QDF_MODULE_ID_PE, TRACE_CODE_TX_MGMT,
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002332 session->peSessionId, mac_hdr->fc.subType));
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002333
Abhishek Singh7d3bc3e2016-02-03 17:45:01 +05302334 if (wait_for_ack) {
2335 mac_ctx->auth_ack_status = LIM_AUTH_ACK_NOT_RCD;
2336 qdf_status = wma_tx_frameWithTxComplete(mac_ctx, packet,
2337 (uint16_t)frame_len,
2338 TXRX_FRM_802_11_MGMT, ANI_TXDIR_TODS,
2339 7, lim_tx_complete, frame,
2340 lim_auth_tx_complete_cnf,
2341 tx_flag, sme_sessionid, false, 0);
2342 MTRACE(qdf_trace(QDF_MODULE_ID_PE, TRACE_CODE_TX_COMPLETE,
2343 session->peSessionId, qdf_status));
2344 if (!QDF_IS_STATUS_SUCCESS(qdf_status)) {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07002345 pe_err("*** Could not send Auth frame, retCode=%X ***",
2346 qdf_status);
Abhishek Singh7d3bc3e2016-02-03 17:45:01 +05302347 mac_ctx->auth_ack_status = LIM_AUTH_ACK_RCD_FAILURE;
2348 /* Pkt will be freed up by the callback */
2349 }
2350 } else {
2351 /* Queue Authentication frame in high priority WQ */
2352 qdf_status = wma_tx_frame(mac_ctx, packet, (uint16_t) frame_len,
2353 TXRX_FRM_802_11_MGMT,
2354 ANI_TXDIR_TODS, 7, lim_tx_complete,
2355 frame, tx_flag, sme_sessionid, 0);
2356 MTRACE(qdf_trace(QDF_MODULE_ID_PE, TRACE_CODE_TX_COMPLETE,
2357 session->peSessionId, qdf_status));
2358 if (!QDF_IS_STATUS_SUCCESS(qdf_status))
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07002359 pe_err("*** Could not send Auth frame, retCode=%X ***",
2360 qdf_status);
Abhishek Singh7d3bc3e2016-02-03 17:45:01 +05302361 }
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002362 return;
2363}
2364
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05302365QDF_STATUS lim_send_deauth_cnf(tpAniSirGlobal pMac)
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002366{
2367 uint16_t aid;
2368 tpDphHashNode pStaDs;
2369 tLimMlmDeauthReq *pMlmDeauthReq;
2370 tLimMlmDeauthCnf mlmDeauthCnf;
2371 tpPESession psessionEntry;
2372
2373 pMlmDeauthReq = pMac->lim.limDisassocDeauthCnfReq.pMlmDeauthReq;
2374 if (pMlmDeauthReq) {
2375 if (tx_timer_running(&pMac->lim.limTimers.gLimDeauthAckTimer)) {
2376 lim_deactivate_and_change_timer(pMac,
2377 eLIM_DEAUTH_ACK_TIMER);
2378 }
2379
2380 psessionEntry = pe_find_session_by_session_id(pMac,
2381 pMlmDeauthReq->sessionId);
2382 if (psessionEntry == NULL) {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07002383 pe_err("session does not exist for given sessionId");
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002384 mlmDeauthCnf.resultCode =
2385 eSIR_SME_INVALID_PARAMETERS;
2386 goto end;
2387 }
2388
2389 pStaDs =
Srinivas Girigowda9efa10e2016-01-04 18:49:40 -08002390 dph_lookup_hash_entry(pMac,
2391 pMlmDeauthReq->peer_macaddr.bytes,
2392 &aid,
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002393 &psessionEntry->dph.dphHashTable);
2394 if (pStaDs == NULL) {
2395 mlmDeauthCnf.resultCode = eSIR_SME_INVALID_PARAMETERS;
2396 goto end;
2397 }
2398
2399 /* / Receive path cleanup with dummy packet */
2400 lim_ft_cleanup_pre_auth_info(pMac, psessionEntry);
2401 lim_cleanup_rx_path(pMac, pStaDs, psessionEntry);
Deepak Dhamdhere262d95a2016-01-10 16:36:53 -08002402 if ((psessionEntry->limSystemRole == eLIM_STA_ROLE) &&
2403 (
Abhishek Singhe0680852015-12-16 14:28:48 +05302404#ifdef FEATURE_WLAN_ESE
Deepak Dhamdhere262d95a2016-01-10 16:36:53 -08002405 (psessionEntry->isESEconnection) ||
Abhishek Singhe0680852015-12-16 14:28:48 +05302406#endif
Deepak Dhamdhere262d95a2016-01-10 16:36:53 -08002407 (psessionEntry->isFastRoamIniFeatureEnabled) ||
2408 (psessionEntry->is11Rconnection))) {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07002409 pe_debug("FT Preauth (%p,%d) Deauth rc %d src = %d",
Deepak Dhamdhere262d95a2016-01-10 16:36:53 -08002410 psessionEntry,
2411 psessionEntry->peSessionId,
2412 pMlmDeauthReq->reasonCode,
2413 pMlmDeauthReq->deauthTrigger);
2414 lim_ft_cleanup(pMac, psessionEntry);
2415 } else {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07002416 pe_debug("No FT Preauth Session Cleanup in role %d"
Deepak Dhamdhere262d95a2016-01-10 16:36:53 -08002417#ifdef FEATURE_WLAN_ESE
2418 " isESE %d"
2419#endif
2420 " isLFR %d"
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07002421 " is11r %d, Deauth reason %d Trigger = %d",
Deepak Dhamdhere262d95a2016-01-10 16:36:53 -08002422 psessionEntry->limSystemRole,
2423#ifdef FEATURE_WLAN_ESE
2424 psessionEntry->isESEconnection,
2425#endif
2426 psessionEntry->isFastRoamIniFeatureEnabled,
2427 psessionEntry->is11Rconnection,
Abhishek Singhe0680852015-12-16 14:28:48 +05302428 pMlmDeauthReq->reasonCode,
Deepak Dhamdhere262d95a2016-01-10 16:36:53 -08002429 pMlmDeauthReq->deauthTrigger);
2430 }
2431 /* Free up buffer allocated for mlmDeauthReq */
Anurag Chouhan600c3a02016-03-01 10:33:54 +05302432 qdf_mem_free(pMlmDeauthReq);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002433 pMac->lim.limDisassocDeauthCnfReq.pMlmDeauthReq = NULL;
2434 }
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05302435 return QDF_STATUS_SUCCESS;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002436end:
Anurag Chouhanc5548422016-02-24 18:33:27 +05302437 qdf_copy_macaddr(&mlmDeauthCnf.peer_macaddr,
Srinivas Girigowda9efa10e2016-01-04 18:49:40 -08002438 &pMlmDeauthReq->peer_macaddr);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002439 mlmDeauthCnf.deauthTrigger = pMlmDeauthReq->deauthTrigger;
2440 mlmDeauthCnf.aid = pMlmDeauthReq->aid;
2441 mlmDeauthCnf.sessionId = pMlmDeauthReq->sessionId;
2442
2443 /* Free up buffer allocated */
2444 /* for mlmDeauthReq */
Anurag Chouhan600c3a02016-03-01 10:33:54 +05302445 qdf_mem_free(pMlmDeauthReq);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002446
2447 lim_post_sme_message(pMac,
2448 LIM_MLM_DEAUTH_CNF, (uint32_t *) &mlmDeauthCnf);
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05302449 return QDF_STATUS_SUCCESS;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002450}
2451
2452/**
2453 * lim_send_disassoc_cnf() - Send disassoc confirmation to SME
2454 *
2455 * @mac_ctx: Handle to MAC context
2456 *
2457 * Sends disassoc confirmation to SME. Removes disassoc request stored
2458 * in lim.
2459 *
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05302460 * Return: QDF_STATUS_SUCCESS
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002461 */
2462
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05302463QDF_STATUS lim_send_disassoc_cnf(tpAniSirGlobal mac_ctx)
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002464{
2465 uint16_t aid;
2466 tpDphHashNode sta_ds;
2467 tLimMlmDisassocCnf disassoc_cnf;
2468 tpPESession pe_session;
2469 tLimMlmDisassocReq *disassoc_req;
2470
2471 disassoc_req = mac_ctx->lim.limDisassocDeauthCnfReq.pMlmDisassocReq;
2472 if (disassoc_req) {
2473 if (tx_timer_running(
2474 &mac_ctx->lim.limTimers.gLimDisassocAckTimer))
2475 lim_deactivate_and_change_timer(mac_ctx,
2476 eLIM_DISASSOC_ACK_TIMER);
2477
2478 pe_session = pe_find_session_by_session_id(
2479 mac_ctx, disassoc_req->sessionId);
2480 if (pe_session == NULL) {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07002481 pe_err("No session for given sessionId");
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002482 disassoc_cnf.resultCode =
2483 eSIR_SME_INVALID_PARAMETERS;
2484 goto end;
2485 }
2486
2487 sta_ds = dph_lookup_hash_entry(mac_ctx,
Srinivas Girigowdadd3c5132016-01-05 19:41:27 -08002488 disassoc_req->peer_macaddr.bytes, &aid,
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002489 &pe_session->dph.dphHashTable);
2490 if (sta_ds == NULL) {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07002491 pe_err("StaDs Null");
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002492 disassoc_cnf.resultCode = eSIR_SME_INVALID_PARAMETERS;
2493 goto end;
2494 }
2495 /* Receive path cleanup with dummy packet */
2496 if (eSIR_SUCCESS !=
2497 lim_cleanup_rx_path(mac_ctx, sta_ds, pe_session)) {
2498 disassoc_cnf.resultCode =
2499 eSIR_SME_RESOURCES_UNAVAILABLE;
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07002500 pe_err("cleanup_rx_path error");
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002501 goto end;
2502 }
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002503 if (LIM_IS_STA_ROLE(pe_session) && (
2504#ifdef FEATURE_WLAN_ESE
2505 (pe_session->isESEconnection) ||
2506#endif
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002507 (pe_session->isFastRoamIniFeatureEnabled) ||
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002508 (pe_session->is11Rconnection)) &&
2509 (disassoc_req->reasonCode !=
2510 eSIR_MAC_DISASSOC_DUE_TO_FTHANDOFF_REASON)) {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07002511 pe_debug("FT Preauth Session (%p %d) Clean up",
2512 pe_session, pe_session->peSessionId);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002513
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002514 /* Delete FT session if there exists one */
2515 lim_ft_cleanup_pre_auth_info(mac_ctx, pe_session);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002516 } else {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07002517 pe_debug("FT Preauth Session %d Clean up"
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002518#ifdef FEATURE_WLAN_ESE
2519 " isESE %d"
2520#endif
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002521 " isLFR %d"
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07002522 " is11r %d reason %d",
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002523 GET_LIM_SYSTEM_ROLE(pe_session),
2524#ifdef FEATURE_WLAN_ESE
2525 pe_session->isESEconnection,
2526#endif
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002527 pe_session->isFastRoamIniFeatureEnabled,
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002528 pe_session->is11Rconnection,
2529 disassoc_req->reasonCode);
2530 }
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002531 /* Free up buffer allocated for mlmDisassocReq */
Anurag Chouhan600c3a02016-03-01 10:33:54 +05302532 qdf_mem_free(disassoc_req);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002533 mac_ctx->lim.limDisassocDeauthCnfReq.pMlmDisassocReq = NULL;
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05302534 return QDF_STATUS_SUCCESS;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002535 } else {
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05302536 return QDF_STATUS_SUCCESS;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002537 }
2538end:
Anurag Chouhan600c3a02016-03-01 10:33:54 +05302539 qdf_mem_copy((uint8_t *) &disassoc_cnf.peerMacAddr,
Srinivas Girigowdadd3c5132016-01-05 19:41:27 -08002540 (uint8_t *) disassoc_req->peer_macaddr.bytes,
Anurag Chouhan6d760662016-02-20 16:05:43 +05302541 QDF_MAC_ADDR_SIZE);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002542 disassoc_cnf.aid = disassoc_req->aid;
2543 disassoc_cnf.disassocTrigger = disassoc_req->disassocTrigger;
2544
2545 /* Update PE session ID */
2546 disassoc_cnf.sessionId = disassoc_req->sessionId;
2547
2548 if (disassoc_req != NULL) {
2549 /* / Free up buffer allocated for mlmDisassocReq */
Anurag Chouhan600c3a02016-03-01 10:33:54 +05302550 qdf_mem_free(disassoc_req);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002551 mac_ctx->lim.limDisassocDeauthCnfReq.pMlmDisassocReq = NULL;
2552 }
2553
2554 lim_post_sme_message(mac_ctx, LIM_MLM_DISASSOC_CNF,
2555 (uint32_t *) &disassoc_cnf);
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05302556 return QDF_STATUS_SUCCESS;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002557}
2558
Himanshu Agarwal2fdf77a2016-12-29 11:41:00 +05302559QDF_STATUS lim_disassoc_tx_complete_cnf(void *context,
2560 qdf_nbuf_t buf,
2561 uint32_t txCompleteSuccess,
2562 void *params)
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002563{
Himanshu Agarwal2fdf77a2016-12-29 11:41:00 +05302564 tpAniSirGlobal pMac = (tpAniSirGlobal)context;
2565
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07002566 pe_debug("txCompleteSuccess: %d", txCompleteSuccess);
Himanshu Agarwal8b472bc2017-01-20 20:49:41 +05302567
2568 if (buf)
2569 qdf_nbuf_free(buf);
2570
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002571 return lim_send_disassoc_cnf(pMac);
2572}
2573
Himanshu Agarwal2fdf77a2016-12-29 11:41:00 +05302574QDF_STATUS lim_deauth_tx_complete_cnf(void *context,
2575 qdf_nbuf_t buf,
2576 uint32_t txCompleteSuccess,
2577 void *params)
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002578{
Himanshu Agarwal2fdf77a2016-12-29 11:41:00 +05302579 tpAniSirGlobal pMac = (tpAniSirGlobal)context;
2580
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07002581 pe_debug("txCompleteSuccess: %d", txCompleteSuccess);
Himanshu Agarwal8b472bc2017-01-20 20:49:41 +05302582
2583 if (buf)
2584 qdf_nbuf_free(buf);
2585
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002586 return lim_send_deauth_cnf(pMac);
2587}
2588
2589/**
2590 * \brief This function is called to send Disassociate frame.
2591 *
2592 *
2593 * \param pMac Pointer to Global MAC structure
2594 *
2595 * \param nReason Indicates the reason that need to be sent in
2596 * Disassociation frame
2597 *
2598 * \param peerMacAddr MAC address of the STA to which Disassociation frame is
2599 * sent
2600 *
2601 *
2602 */
2603
2604void
2605lim_send_disassoc_mgmt_frame(tpAniSirGlobal pMac,
2606 uint16_t nReason,
2607 tSirMacAddr peer,
2608 tpPESession psessionEntry, bool waitForAck)
2609{
2610 tDot11fDisassociation frm;
2611 uint8_t *pFrame;
2612 tpSirMacMgmtHdr pMacHdr;
2613 uint32_t nBytes, nPayload, nStatus;
2614 void *pPacket;
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05302615 QDF_STATUS qdf_status;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002616 uint8_t txFlag = 0;
2617 uint32_t val = 0;
2618 uint8_t smeSessionId = 0;
2619 if (NULL == psessionEntry) {
2620 return;
2621 }
2622
2623 /*
2624 * In case when cac timer is running for this SAP session then
2625 * avoid sending disassoc out. It is violation of dfs specification.
2626 */
Anurag Chouhan6d760662016-02-20 16:05:43 +05302627 if (((psessionEntry->pePersona == QDF_SAP_MODE) ||
2628 (psessionEntry->pePersona == QDF_P2P_GO_MODE)) &&
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002629 (true == pMac->sap.SapDfsInfo.is_dfs_cac_timer_running)) {
Anurag Chouhanb2dc16f2016-02-25 11:47:37 +05302630 QDF_TRACE(QDF_MODULE_ID_SAP, QDF_TRACE_LEVEL_INFO,
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002631 FL
2632 ("CAC timer is running, drop disassoc from going out"));
2633 return;
2634 }
2635 smeSessionId = psessionEntry->smeSessionId;
2636
Anurag Chouhan600c3a02016-03-01 10:33:54 +05302637 qdf_mem_set((uint8_t *) &frm, sizeof(frm), 0);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002638
2639 frm.Reason.code = nReason;
2640
2641 nStatus = dot11f_get_packed_disassociation_size(pMac, &frm, &nPayload);
2642 if (DOT11F_FAILED(nStatus)) {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07002643 pe_err("Failed to calculate the packed size for a Disassociation (0x%08x)",
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002644 nStatus);
2645 /* We'll fall back on the worst case scenario: */
2646 nPayload = sizeof(tDot11fDisassociation);
2647 } else if (DOT11F_WARNED(nStatus)) {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07002648 pe_warn("There were warnings while calculating the packed size for a Disassociation (0x%08x)",
2649 nStatus);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002650 }
2651
2652 nBytes = nPayload + sizeof(tSirMacMgmtHdr);
2653
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05302654 qdf_status = cds_packet_alloc((uint16_t) nBytes, (void **)&pFrame,
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002655 (void **)&pPacket);
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05302656 if (!QDF_IS_STATUS_SUCCESS(qdf_status)) {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07002657 pe_err("Failed to allocate %d bytes for a Disassociation",
2658 nBytes);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002659 return;
2660 }
2661 /* Paranoia: */
Anurag Chouhan600c3a02016-03-01 10:33:54 +05302662 qdf_mem_set(pFrame, nBytes, 0);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002663
2664 /* Next, we fill out the buffer descriptor: */
2665 lim_populate_mac_header(pMac, pFrame, SIR_MAC_MGMT_FRAME,
2666 SIR_MAC_MGMT_DISASSOC, peer, psessionEntry->selfMacAddr);
2667 pMacHdr = (tpSirMacMgmtHdr) pFrame;
2668
2669 /* Prepare the BSSID */
2670 sir_copy_mac_addr(pMacHdr->bssId, psessionEntry->bssId);
2671
2672#ifdef WLAN_FEATURE_11W
2673 lim_set_protected_bit(pMac, psessionEntry, peer, pMacHdr);
2674#endif
2675
2676 nStatus = dot11f_pack_disassociation(pMac, &frm, pFrame +
2677 sizeof(tSirMacMgmtHdr),
2678 nPayload, &nPayload);
2679 if (DOT11F_FAILED(nStatus)) {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07002680 pe_err("Failed to pack a Disassociation (0x%08x)",
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002681 nStatus);
2682 cds_packet_free((void *)pPacket);
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07002683 return;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002684 } else if (DOT11F_WARNED(nStatus)) {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07002685 pe_warn("There were warnings while packing a Disassociation (0x%08x)",
2686 nStatus);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002687 }
2688
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07002689 pe_debug("***Sessionid %d Sending Disassociation frame with "
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002690 "reason %u and waitForAck %d to " MAC_ADDRESS_STR " ,From "
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07002691 MAC_ADDRESS_STR, psessionEntry->peSessionId, nReason,
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002692 waitForAck, MAC_ADDR_ARRAY(pMacHdr->da),
2693 MAC_ADDR_ARRAY(psessionEntry->selfMacAddr));
2694
2695 if ((SIR_BAND_5_GHZ == lim_get_rf_band(psessionEntry->currentOperChannel))
Anurag Chouhan6d760662016-02-20 16:05:43 +05302696 || (psessionEntry->pePersona == QDF_P2P_CLIENT_MODE) ||
2697 (psessionEntry->pePersona == QDF_P2P_GO_MODE)
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002698 ) {
2699 txFlag |= HAL_USE_BD_RATE2_FOR_MANAGEMENT_FRAME;
2700 }
2701
Sushant Kaushik46556062015-12-02 16:57:47 +05302702 txFlag |= HAL_USE_PEER_STA_REQUESTED_MASK;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002703
2704 if (waitForAck) {
Anurag Chouhanb2dc16f2016-02-25 11:47:37 +05302705 MTRACE(qdf_trace(QDF_MODULE_ID_PE, TRACE_CODE_TX_MGMT,
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002706 psessionEntry->peSessionId,
2707 pMacHdr->fc.subType));
2708 /* Queue Disassociation frame in high priority WQ */
2709 /* get the duration from the request */
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05302710 qdf_status =
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002711 wma_tx_frameWithTxComplete(pMac, pPacket, (uint16_t) nBytes,
2712 TXRX_FRM_802_11_MGMT,
2713 ANI_TXDIR_TODS, 7, lim_tx_complete,
2714 pFrame, lim_disassoc_tx_complete_cnf,
2715 txFlag, smeSessionId, false, 0);
Anurag Chouhanb2dc16f2016-02-25 11:47:37 +05302716 MTRACE(qdf_trace
Anurag Chouhan6d760662016-02-20 16:05:43 +05302717 (QDF_MODULE_ID_PE, TRACE_CODE_TX_COMPLETE,
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05302718 psessionEntry->peSessionId, qdf_status));
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002719
2720 val = SYS_MS_TO_TICKS(LIM_DISASSOC_DEAUTH_ACK_TIMEOUT);
2721
2722 if (tx_timer_change
2723 (&pMac->lim.limTimers.gLimDisassocAckTimer, val, 0)
2724 != TX_SUCCESS) {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07002725 pe_err("Unable to change Disassoc ack Timer val");
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002726 return;
2727 } else if (TX_SUCCESS !=
2728 tx_timer_activate(&pMac->lim.limTimers.
2729 gLimDisassocAckTimer)) {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07002730 pe_err("Unable to activate Disassoc ack Timer");
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002731 lim_deactivate_and_change_timer(pMac,
2732 eLIM_DISASSOC_ACK_TIMER);
2733 return;
2734 }
2735 } else {
Anurag Chouhanb2dc16f2016-02-25 11:47:37 +05302736 MTRACE(qdf_trace(QDF_MODULE_ID_PE, TRACE_CODE_TX_MGMT,
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002737 psessionEntry->peSessionId,
2738 pMacHdr->fc.subType));
2739 /* Queue Disassociation frame in high priority WQ */
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05302740 qdf_status = wma_tx_frame(pMac, pPacket, (uint16_t) nBytes,
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002741 TXRX_FRM_802_11_MGMT,
2742 ANI_TXDIR_TODS,
2743 7,
2744 lim_tx_complete, pFrame, txFlag,
2745 smeSessionId, 0);
Anurag Chouhanb2dc16f2016-02-25 11:47:37 +05302746 MTRACE(qdf_trace
Anurag Chouhan6d760662016-02-20 16:05:43 +05302747 (QDF_MODULE_ID_PE, TRACE_CODE_TX_COMPLETE,
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05302748 psessionEntry->peSessionId, qdf_status));
2749 if (!QDF_IS_STATUS_SUCCESS(qdf_status)) {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07002750 pe_err("Failed to send Disassociation (%X)!",
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05302751 qdf_status);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002752 /* Pkt will be freed up by the callback */
2753 }
2754 }
2755} /* End lim_send_disassoc_mgmt_frame. */
2756
2757/**
2758 * \brief This function is called to send a Deauthenticate frame
2759 *
2760 *
2761 * \param pMac Pointer to global MAC structure
2762 *
2763 * \param nReason Indicates the reason that need to be sent in the
2764 * Deauthenticate frame
2765 *
2766 * \param peeer address of the STA to which the frame is to be sent
2767 *
2768 *
2769 */
2770
2771void
2772lim_send_deauth_mgmt_frame(tpAniSirGlobal pMac,
2773 uint16_t nReason,
2774 tSirMacAddr peer,
2775 tpPESession psessionEntry, bool waitForAck)
2776{
2777 tDot11fDeAuth frm;
2778 uint8_t *pFrame;
2779 tpSirMacMgmtHdr pMacHdr;
2780 uint32_t nBytes, nPayload, nStatus;
2781 void *pPacket;
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05302782 QDF_STATUS qdf_status;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002783 uint8_t txFlag = 0;
2784 uint32_t val = 0;
2785#ifdef FEATURE_WLAN_TDLS
2786 uint16_t aid;
2787 tpDphHashNode pStaDs;
2788#endif
2789 uint8_t smeSessionId = 0;
2790
2791 if (NULL == psessionEntry) {
2792 return;
2793 }
2794
2795 /*
2796 * In case when cac timer is running for this SAP session then
2797 * avoid deauth frame out. It is violation of dfs specification.
2798 */
Anurag Chouhan6d760662016-02-20 16:05:43 +05302799 if (((psessionEntry->pePersona == QDF_SAP_MODE) ||
2800 (psessionEntry->pePersona == QDF_P2P_GO_MODE)) &&
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002801 (true == pMac->sap.SapDfsInfo.is_dfs_cac_timer_running)) {
Anurag Chouhanb2dc16f2016-02-25 11:47:37 +05302802 QDF_TRACE(QDF_MODULE_ID_SAP, QDF_TRACE_LEVEL_INFO,
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002803 FL
2804 ("CAC timer is running, drop the deauth from going out"));
2805 return;
2806 }
2807 smeSessionId = psessionEntry->smeSessionId;
2808
Anurag Chouhan600c3a02016-03-01 10:33:54 +05302809 qdf_mem_set((uint8_t *) &frm, sizeof(frm), 0);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002810
2811 frm.Reason.code = nReason;
2812
2813 nStatus = dot11f_get_packed_de_auth_size(pMac, &frm, &nPayload);
2814 if (DOT11F_FAILED(nStatus)) {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07002815 pe_err("Failed to calculate the packed size for a De-Authentication (0x%08x)",
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002816 nStatus);
2817 /* We'll fall back on the worst case scenario: */
2818 nPayload = sizeof(tDot11fDeAuth);
2819 } else if (DOT11F_WARNED(nStatus)) {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07002820 pe_warn("There were warnings while calculating the packed size for a De-Authentication (0x%08x)",
2821 nStatus);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002822 }
2823
2824 nBytes = nPayload + sizeof(tSirMacMgmtHdr);
2825
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05302826 qdf_status = cds_packet_alloc((uint16_t) nBytes, (void **)&pFrame,
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002827 (void **)&pPacket);
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05302828 if (!QDF_IS_STATUS_SUCCESS(qdf_status)) {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07002829 pe_err("Failed to allocate %d bytes for a De-Authentication",
2830 nBytes);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002831 return;
2832 }
2833 /* Paranoia: */
Anurag Chouhan600c3a02016-03-01 10:33:54 +05302834 qdf_mem_set(pFrame, nBytes, 0);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002835
2836 /* Next, we fill out the buffer descriptor: */
2837 lim_populate_mac_header(pMac, pFrame, SIR_MAC_MGMT_FRAME,
2838 SIR_MAC_MGMT_DEAUTH, peer, psessionEntry->selfMacAddr);
2839 pMacHdr = (tpSirMacMgmtHdr) pFrame;
2840
2841 /* Prepare the BSSID */
2842 sir_copy_mac_addr(pMacHdr->bssId, psessionEntry->bssId);
2843
2844#ifdef WLAN_FEATURE_11W
2845 lim_set_protected_bit(pMac, psessionEntry, peer, pMacHdr);
2846#endif
2847
2848 nStatus = dot11f_pack_de_auth(pMac, &frm, pFrame +
2849 sizeof(tSirMacMgmtHdr), nPayload, &nPayload);
2850 if (DOT11F_FAILED(nStatus)) {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07002851 pe_err("Failed to pack a DeAuthentication (0x%08x)",
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002852 nStatus);
2853 cds_packet_free((void *)pPacket);
2854 return;
2855 } else if (DOT11F_WARNED(nStatus)) {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07002856 pe_warn("There were warnings while packing a De-Authentication (0x%08x)",
2857 nStatus);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002858 }
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07002859 pe_debug("***Sessionid %d Sending Deauth frame with "
2860 "reason %u and waitForAck %d to " MAC_ADDRESS_STR
2861 " ,From " MAC_ADDRESS_STR,
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002862 psessionEntry->peSessionId, nReason, waitForAck,
2863 MAC_ADDR_ARRAY(pMacHdr->da),
2864 MAC_ADDR_ARRAY(psessionEntry->selfMacAddr));
2865
2866 if ((SIR_BAND_5_GHZ == lim_get_rf_band(psessionEntry->currentOperChannel))
Anurag Chouhan6d760662016-02-20 16:05:43 +05302867 || (psessionEntry->pePersona == QDF_P2P_CLIENT_MODE) ||
2868 (psessionEntry->pePersona == QDF_P2P_GO_MODE)
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002869 ) {
2870 txFlag |= HAL_USE_BD_RATE2_FOR_MANAGEMENT_FRAME;
2871 }
2872
Sushant Kaushik46556062015-12-02 16:57:47 +05302873 txFlag |= HAL_USE_PEER_STA_REQUESTED_MASK;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002874#ifdef FEATURE_WLAN_TDLS
2875 pStaDs =
2876 dph_lookup_hash_entry(pMac, peer, &aid,
2877 &psessionEntry->dph.dphHashTable);
2878#endif
2879
2880 if (waitForAck) {
Anurag Chouhanb2dc16f2016-02-25 11:47:37 +05302881 MTRACE(qdf_trace(QDF_MODULE_ID_PE, TRACE_CODE_TX_MGMT,
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002882 psessionEntry->peSessionId,
2883 pMacHdr->fc.subType));
2884 /* Queue Disassociation frame in high priority WQ */
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05302885 qdf_status =
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002886 wma_tx_frameWithTxComplete(pMac, pPacket, (uint16_t) nBytes,
2887 TXRX_FRM_802_11_MGMT,
2888 ANI_TXDIR_TODS, 7, lim_tx_complete,
2889 pFrame, lim_deauth_tx_complete_cnf,
2890 txFlag, smeSessionId, false, 0);
Anurag Chouhanb2dc16f2016-02-25 11:47:37 +05302891 MTRACE(qdf_trace
Anurag Chouhan6d760662016-02-20 16:05:43 +05302892 (QDF_MODULE_ID_PE, TRACE_CODE_TX_COMPLETE,
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05302893 psessionEntry->peSessionId, qdf_status));
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002894 /* Pkt will be freed up by the callback lim_tx_complete */
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05302895 if (!QDF_IS_STATUS_SUCCESS(qdf_status)) {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07002896 pe_err("Failed to send De-Authentication (%X)!",
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05302897 qdf_status);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002898
2899 /* Call lim_process_deauth_ack_timeout which will send
2900 * DeauthCnf for this frame
2901 */
2902 lim_process_deauth_ack_timeout(pMac);
2903 return;
2904 }
2905
2906 val = SYS_MS_TO_TICKS(LIM_DISASSOC_DEAUTH_ACK_TIMEOUT);
2907
2908 if (tx_timer_change
2909 (&pMac->lim.limTimers.gLimDeauthAckTimer, val, 0)
2910 != TX_SUCCESS) {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07002911 pe_err("Unable to change Deauth ack Timer val");
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002912 return;
2913 } else if (TX_SUCCESS !=
2914 tx_timer_activate(&pMac->lim.limTimers.
2915 gLimDeauthAckTimer)) {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07002916 pe_err("Unable to activate Deauth ack Timer");
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002917 lim_deactivate_and_change_timer(pMac,
2918 eLIM_DEAUTH_ACK_TIMER);
2919 return;
2920 }
2921 } else {
Anurag Chouhanb2dc16f2016-02-25 11:47:37 +05302922 MTRACE(qdf_trace(QDF_MODULE_ID_PE, TRACE_CODE_TX_MGMT,
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002923 psessionEntry->peSessionId,
2924 pMacHdr->fc.subType));
2925#ifdef FEATURE_WLAN_TDLS
2926 if ((NULL != pStaDs)
2927 && (STA_ENTRY_TDLS_PEER == pStaDs->staType)) {
2928 /* Queue Disassociation frame in high priority WQ */
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05302929 qdf_status =
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002930 wma_tx_frame(pMac, pPacket, (uint16_t) nBytes,
2931 TXRX_FRM_802_11_MGMT, ANI_TXDIR_IBSS,
2932 7, lim_tx_complete, pFrame, txFlag,
2933 smeSessionId, 0);
2934 } else {
2935#endif
2936 /* Queue Disassociation frame in high priority WQ */
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05302937 qdf_status =
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002938 wma_tx_frame(pMac, pPacket, (uint16_t) nBytes,
2939 TXRX_FRM_802_11_MGMT, ANI_TXDIR_TODS,
2940 7, lim_tx_complete, pFrame, txFlag,
2941 smeSessionId, 0);
2942#ifdef FEATURE_WLAN_TDLS
2943 }
2944#endif
Anurag Chouhanb2dc16f2016-02-25 11:47:37 +05302945 MTRACE(qdf_trace(QDF_MODULE_ID_PE, TRACE_CODE_TX_COMPLETE,
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05302946 psessionEntry->peSessionId, qdf_status));
2947 if (!QDF_IS_STATUS_SUCCESS(qdf_status)) {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07002948 pe_err("Failed to send De-Authentication (%X)!",
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05302949 qdf_status);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002950 /* Pkt will be freed up by the callback */
2951 }
2952 }
2953
2954} /* End lim_send_deauth_mgmt_frame. */
2955
2956#ifdef ANI_SUPPORT_11H
2957/**
2958 * \brief Send a Measurement Report Action frame
2959 *
2960 *
2961 * \param pMac Pointer to the global MAC structure
2962 *
2963 * \param pMeasReqFrame Address of a tSirMacMeasReqActionFrame
2964 *
2965 * \return eSIR_SUCCESS on success, eSIR_FAILURE else
2966 *
2967 *
2968 */
2969
2970tSirRetStatus
2971lim_send_meas_report_frame(tpAniSirGlobal pMac,
2972 tpSirMacMeasReqActionFrame pMeasReqFrame,
2973 tSirMacAddr peer, tpPESession psessionEntry)
2974{
2975 tDot11fMeasurementReport frm;
2976 uint8_t *pFrame;
2977 tSirRetStatus nSirStatus;
2978 tpSirMacMgmtHdr pMacHdr;
2979 uint32_t nBytes, nPayload, nStatus;
2980 void *pPacket;
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05302981 QDF_STATUS qdf_status;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002982
Anurag Chouhan600c3a02016-03-01 10:33:54 +05302983 qdf_mem_set((uint8_t *) &frm, sizeof(frm), 0);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002984
2985 frm.Category.category = SIR_MAC_ACTION_SPECTRUM_MGMT;
2986 frm.Action.action = SIR_MAC_ACTION_MEASURE_REPORT_ID;
2987 frm.DialogToken.token = pMeasReqFrame->actionHeader.dialogToken;
2988
2989 switch (pMeasReqFrame->measReqIE.measType) {
2990 case SIR_MAC_BASIC_MEASUREMENT_TYPE:
2991 nSirStatus =
2992 populate_dot11f_measurement_report0(pMac, pMeasReqFrame,
2993 &frm.MeasurementReport);
2994 break;
2995 case SIR_MAC_CCA_MEASUREMENT_TYPE:
2996 nSirStatus =
2997 populate_dot11f_measurement_report1(pMac, pMeasReqFrame,
2998 &frm.MeasurementReport);
2999 break;
3000 case SIR_MAC_RPI_MEASUREMENT_TYPE:
3001 nSirStatus =
3002 populate_dot11f_measurement_report2(pMac, pMeasReqFrame,
3003 &frm.MeasurementReport);
3004 break;
3005 default:
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07003006 pe_err("Unknown measurement type %d in limSen"
3007 "dMeasReportFrame",
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003008 pMeasReqFrame->measReqIE.measType);
3009 return eSIR_FAILURE;
3010 }
3011
3012 if (eSIR_SUCCESS != nSirStatus)
3013 return eSIR_FAILURE;
3014
3015 nStatus = dot11f_get_packed_measurement_report_size(pMac, &frm, &nPayload);
3016 if (DOT11F_FAILED(nStatus)) {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07003017 pe_err("Failed to calculate the packed size for a Measurement Report (0x%08x)",
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003018 nStatus);
3019 /* We'll fall back on the worst case scenario: */
3020 nPayload = sizeof(tDot11fMeasurementReport);
3021 } else if (DOT11F_WARNED(nStatus)) {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07003022 pe_warn("There were warnings while calculating the packed size for a Measurement Report (0x%08x)",
3023 nStatus);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003024 }
3025
3026 nBytes = nPayload + sizeof(tSirMacMgmtHdr);
3027
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05303028 qdf_status =
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003029 cds_packet_alloc(pMac->hHdd, TXRX_FRM_802_11_MGMT,
3030 (uint16_t) nBytes, (void **)&pFrame,
3031 (void **)&pPacket);
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05303032 if (!QDF_IS_STATUS_SUCCESS(qdf_status)) {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07003033 pe_err("Failed to allocate %d bytes for a "
3034 "De-Authentication", nBytes);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003035 return eSIR_FAILURE;
3036 }
3037 /* Paranoia: */
Anurag Chouhan600c3a02016-03-01 10:33:54 +05303038 qdf_mem_set(pFrame, nBytes, 0);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003039
3040 /* Next, we fill out the buffer descriptor: */
3041 lim_populate_mac_header(pMac, pFrame, SIR_MAC_MGMT_FRAME,
3042 SIR_MAC_MGMT_ACTION, peer);
3043 pMacHdr = (tpSirMacMgmtHdr) pFrame;
3044
Anurag Chouhan600c3a02016-03-01 10:33:54 +05303045 qdf_mem_copy(pMacHdr->bssId, psessionEntry->bssId, sizeof(tSirMacAddr));
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003046
3047#ifdef WLAN_FEATURE_11W
3048 lim_set_protected_bit(pMac, psessionEntry, peer, pMacHdr);
3049#endif
3050
3051 nStatus = dot11f_pack_measurement_report(pMac, &frm, pFrame +
3052 sizeof(tSirMacMgmtHdr),
3053 nPayload, &nPayload);
3054 if (DOT11F_FAILED(nStatus)) {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07003055 pe_err("Failed to pack a Measurement Report (0x%08x)",
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003056 nStatus);
3057 cds_packet_free(pMac->hHdd, TXRX_FRM_802_11_MGMT,
3058 (void *)pFrame, (void *)pPacket);
3059 return eSIR_FAILURE; /* allocated! */
3060 } else if (DOT11F_WARNED(nStatus)) {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07003061 pe_warn("There were warnings while packing a Measurement Report (0x%08x)",
3062 nStatus);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003063 }
3064
Anurag Chouhanb2dc16f2016-02-25 11:47:37 +05303065 MTRACE(qdf_trace(QDF_MODULE_ID_PE, TRACE_CODE_TX_MGMT,
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003066 ((psessionEntry) ? psessionEntry->
3067 peSessionId : NO_SESSION), pMacHdr->fc.subType));
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05303068 qdf_status =
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003069 wma_tx_frame(pMac, pPacket, (uint16_t) nBytes,
3070 TXRX_FRM_802_11_MGMT, ANI_TXDIR_TODS, 7,
3071 lim_tx_complete, pFrame, 0, 0);
Anurag Chouhanb2dc16f2016-02-25 11:47:37 +05303072 MTRACE(qdf_trace
Anurag Chouhan6d760662016-02-20 16:05:43 +05303073 (QDF_MODULE_ID_PE, TRACE_CODE_TX_COMPLETE,
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003074 ((psessionEntry) ? psessionEntry->peSessionId : NO_SESSION),
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05303075 qdf_status));
3076 if (!QDF_IS_STATUS_SUCCESS(qdf_status)) {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07003077 pe_err("Failed to send a Measurement Report (%X)!",
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05303078 qdf_status);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003079 /* Pkt will be freed up by the callback */
3080 return eSIR_FAILURE; /* just allocated... */
3081 }
3082
3083 return eSIR_SUCCESS;
3084
3085} /* End lim_send_meas_report_frame. */
3086
3087/**
3088 * \brief Send a TPC Request Action frame
3089 *
3090 *
3091 * \param pMac Pointer to the global MAC datastructure
3092 *
3093 * \param peer MAC address to which the frame should be sent
3094 *
3095 *
3096 */
3097
3098void
3099lim_send_tpc_request_frame(tpAniSirGlobal pMac,
3100 tSirMacAddr peer, tpPESession psessionEntry)
3101{
3102 tDot11fTPCRequest frm;
3103 uint8_t *pFrame;
3104 tpSirMacMgmtHdr pMacHdr;
3105 uint32_t nBytes, nPayload, nStatus;
3106 void *pPacket;
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05303107 QDF_STATUS qdf_status;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003108
Anurag Chouhan600c3a02016-03-01 10:33:54 +05303109 qdf_mem_set((uint8_t *) &frm, sizeof(frm), 0);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003110
3111 frm.Category.category = SIR_MAC_ACTION_SPECTRUM_MGMT;
3112 frm.Action.action = SIR_MAC_ACTION_TPC_REQUEST_ID;
3113 frm.DialogToken.token = 1;
3114 frm.TPCRequest.present = 1;
3115
3116 nStatus = dot11f_get_packed_tpc_request_size(pMac, &frm, &nPayload);
3117 if (DOT11F_FAILED(nStatus)) {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07003118 pe_err("Failed to calculate the packed size for a TPC Request (0x%08x)", nStatus);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003119 /* We'll fall back on the worst case scenario: */
3120 nPayload = sizeof(tDot11fTPCRequest);
3121 } else if (DOT11F_WARNED(nStatus)) {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07003122 pe_warn("There were warnings while calculating the packed size for a TPC Request (0x%08x)",
3123 nStatus);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003124 }
3125
3126 nBytes = nPayload + sizeof(tSirMacMgmtHdr);
3127
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05303128 qdf_status =
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003129 cds_packet_alloc(pMac->hHdd, TXRX_FRM_802_11_MGMT,
3130 (uint16_t) nBytes, (void **)&pFrame,
3131 (void **)&pPacket);
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05303132 if (!QDF_IS_STATUS_SUCCESS(qdf_status)) {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07003133 pe_err("Failed to allocate %d bytes for a TPC"
3134 " Request", nBytes);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003135 return;
3136 }
3137 /* Paranoia: */
Anurag Chouhan600c3a02016-03-01 10:33:54 +05303138 qdf_mem_set(pFrame, nBytes, 0);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003139
3140 /* Next, we fill out the buffer descriptor: */
3141 lim_populate_mac_header(pMac, pFrame, SIR_MAC_MGMT_FRAME,
3142 SIR_MAC_MGMT_ACTION, peer);
3143 pMacHdr = (tpSirMacMgmtHdr) pFrame;
3144
Anurag Chouhan600c3a02016-03-01 10:33:54 +05303145 qdf_mem_copy(pMacHdr->bssId, psessionEntry->bssId, sizeof(tSirMacAddr));
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003146
3147#ifdef WLAN_FEATURE_11W
3148 lim_set_protected_bit(pMac, psessionEntry, peer, pMacHdr);
3149#endif
3150
3151 nStatus = dot11f_pack_tpc_request(pMac, &frm, pFrame +
3152 sizeof(tSirMacMgmtHdr),
3153 nPayload, &nPayload);
3154 if (DOT11F_FAILED(nStatus)) {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07003155 pe_err("Failed to pack a TPC Request (0x%08x)",
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003156 nStatus);
3157 cds_packet_free(pMac->hHdd, TXRX_FRM_802_11_MGMT,
3158 (void *)pFrame, (void *)pPacket);
3159 return; /* allocated! */
3160 } else if (DOT11F_WARNED(nStatus)) {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07003161 pe_warn("There were warnings while packing a TPC Request (0x%08x)",
3162 nStatus);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003163 }
3164
Anurag Chouhanb2dc16f2016-02-25 11:47:37 +05303165 MTRACE(qdf_trace(QDF_MODULE_ID_PE, TRACE_CODE_TX_MGMT,
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003166 ((psessionEntry) ? psessionEntry->
3167 peSessionId : NO_SESSION), pMacHdr->fc.subType));
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05303168 qdf_status =
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003169 wma_tx_frame(pMac, pPacket, (uint16_t) nBytes,
3170 TXRX_FRM_802_11_MGMT, ANI_TXDIR_TODS, 7,
3171 lim_tx_complete, pFrame, 0, 0);
Anurag Chouhanb2dc16f2016-02-25 11:47:37 +05303172 MTRACE(qdf_trace
Anurag Chouhan6d760662016-02-20 16:05:43 +05303173 (QDF_MODULE_ID_PE, TRACE_CODE_TX_COMPLETE,
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003174 ((psessionEntry) ? psessionEntry->peSessionId : NO_SESSION),
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05303175 qdf_status));
3176 if (!QDF_IS_STATUS_SUCCESS(qdf_status)) {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07003177 pe_err("Failed to send a TPC Request (%X)!",
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05303178 qdf_status);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003179 /* Pkt will be freed up by the callback */
3180 }
3181
3182} /* End lim_send_tpc_request_frame. */
3183
3184/**
3185 * \brief Send a TPC Report Action frame
3186 *
3187 *
3188 * \param pMac Pointer to the global MAC datastructure
3189 *
3190 * \param pTpcReqFrame Pointer to the received TPC Request
3191 *
3192 * \return eSIR_SUCCESS on success, eSIR_FAILURE else
3193 *
3194 *
3195 */
3196
3197tSirRetStatus
3198lim_send_tpc_report_frame(tpAniSirGlobal pMac,
3199 tpSirMacTpcReqActionFrame pTpcReqFrame,
3200 tSirMacAddr peer, tpPESession psessionEntry)
3201{
3202 tDot11fTPCReport frm;
3203 uint8_t *pFrame;
3204 tpSirMacMgmtHdr pMacHdr;
3205 uint32_t nBytes, nPayload, nStatus;
3206 void *pPacket;
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05303207 QDF_STATUS qdf_status;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003208
Anurag Chouhan600c3a02016-03-01 10:33:54 +05303209 qdf_mem_set((uint8_t *) &frm, sizeof(frm), 0);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003210
3211 frm.Category.category = SIR_MAC_ACTION_SPECTRUM_MGMT;
3212 frm.Action.action = SIR_MAC_ACTION_TPC_REPORT_ID;
3213 frm.DialogToken.token = pTpcReqFrame->actionHeader.dialogToken;
3214
3215 frm.TPCReport.tx_power = 0;
3216 frm.TPCReport.link_margin = 0;
3217 frm.TPCReport.present = 1;
3218
3219 nStatus = dot11f_get_packed_tpc_report_size(pMac, &frm, &nPayload);
3220 if (DOT11F_FAILED(nStatus)) {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07003221 pe_err("Failed to calculate the packed size for a TPC Report (0x%08x)", nStatus);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003222 /* We'll fall back on the worst case scenario: */
3223 nPayload = sizeof(tDot11fTPCReport);
3224 } else if (DOT11F_WARNED(nStatus)) {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07003225 pe_warn("There were warnings while calculating the packed size for a TPC Report (0x%08x)",
3226 nStatus);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003227 }
3228
3229 nBytes = nPayload + sizeof(tSirMacMgmtHdr);
3230
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05303231 qdf_status =
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003232 cds_packet_alloc(pMac->hHdd, TXRX_FRM_802_11_MGMT,
3233 (uint16_t) nBytes, (void **)&pFrame,
3234 (void **)&pPacket);
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05303235 if (!QDF_IS_STATUS_SUCCESS(qdf_status)) {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07003236 pe_err("Failed to allocate %d bytes for a TPC"
3237 " Report", nBytes);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003238 return eSIR_FAILURE;
3239 }
3240 /* Paranoia: */
Anurag Chouhan600c3a02016-03-01 10:33:54 +05303241 qdf_mem_set(pFrame, nBytes, 0);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003242
3243 /* Next, we fill out the buffer descriptor: */
3244 lim_populate_mac_header(pMac, pFrame, SIR_MAC_MGMT_FRAME,
3245 SIR_MAC_MGMT_ACTION, peer);
3246
3247 pMacHdr = (tpSirMacMgmtHdr) pFrame;
3248
Anurag Chouhan600c3a02016-03-01 10:33:54 +05303249 qdf_mem_copy(pMacHdr->bssId, psessionEntry->bssId, sizeof(tSirMacAddr));
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003250
3251#ifdef WLAN_FEATURE_11W
3252 lim_set_protected_bit(pMac, psessionEntry, peer, pMacHdr);
3253#endif
3254
3255 nStatus = dot11f_pack_tpc_report(pMac, &frm, pFrame +
3256 sizeof(tSirMacMgmtHdr),
3257 nPayload, &nPayload);
3258 if (DOT11F_FAILED(nStatus)) {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07003259 pe_err("Failed to pack a TPC Report (0x%08x)",
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003260 nStatus);
3261 cds_packet_free(pMac->hHdd, TXRX_FRM_802_11_MGMT,
3262 (void *)pFrame, (void *)pPacket);
3263 return eSIR_FAILURE; /* allocated! */
3264 } else if (DOT11F_WARNED(nStatus)) {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07003265 pe_warn("There were warnings while packing a TPC Report (0x%08x)",
3266 nStatus);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003267
Anurag Chouhanb2dc16f2016-02-25 11:47:37 +05303268 MTRACE(qdf_trace(QDF_MODULE_ID_PE, TRACE_CODE_TX_MGMT,
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003269 ((psessionEntry) ? psessionEntry->
3270 peSessionId : NO_SESSION), pMacHdr->fc.subType));
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05303271 qdf_status =
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003272 wma_tx_frame(pMac, pPacket, (uint16_t) nBytes,
3273 TXRX_FRM_802_11_MGMT, ANI_TXDIR_TODS, 7,
3274 lim_tx_complete, pFrame, 0, 0);
Anurag Chouhanb2dc16f2016-02-25 11:47:37 +05303275 MTRACE(qdf_trace
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07003276 (QDF_MODULE_ID_PE, TRACE_CODE_TX_COMPLETE,
3277 ((psessionEntry) ? psessionEntry->peSessionId : NO_SESSION),
3278 qdf_status));
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05303279 if (!QDF_IS_STATUS_SUCCESS(qdf_status)) {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07003280 pe_err("Failed to send a TPC Report (%X)!",
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05303281 qdf_status);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003282 /* Pkt will be freed up by the callback */
3283 return eSIR_FAILURE; /* just allocated... */
3284 }
3285
3286 return eSIR_SUCCESS;
3287
3288} /* End lim_send_tpc_report_frame. */
3289#endif /* ANI_SUPPORT_11H */
3290
3291/**
3292 * \brief Send a Channel Switch Announcement
3293 *
3294 *
3295 * \param pMac Pointer to the global MAC datastructure
3296 *
3297 * \param peer MAC address to which this frame will be sent
3298 *
3299 * \param nMode
3300 *
3301 * \param nNewChannel
3302 *
3303 * \param nCount
3304 *
3305 * \return eSIR_SUCCESS on success, eSIR_FAILURE else
3306 *
3307 *
3308 */
3309
3310tSirRetStatus
3311lim_send_channel_switch_mgmt_frame(tpAniSirGlobal pMac,
3312 tSirMacAddr peer,
3313 uint8_t nMode,
3314 uint8_t nNewChannel,
3315 uint8_t nCount, tpPESession psessionEntry)
3316{
3317 tDot11fChannelSwitch frm;
3318 uint8_t *pFrame;
3319 tpSirMacMgmtHdr pMacHdr;
3320 uint32_t nBytes, nPayload, nStatus; /* , nCfg; */
3321 void *pPacket;
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05303322 QDF_STATUS qdf_status;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003323 uint8_t txFlag = 0;
3324
3325 uint8_t smeSessionId = 0;
3326
3327 if (psessionEntry == NULL) {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07003328 pe_err("Session entry is NULL!!!");
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003329 return eSIR_FAILURE;
3330 }
3331 smeSessionId = psessionEntry->smeSessionId;
3332
Anurag Chouhan600c3a02016-03-01 10:33:54 +05303333 qdf_mem_set((uint8_t *) &frm, sizeof(frm), 0);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003334
3335 frm.Category.category = SIR_MAC_ACTION_SPECTRUM_MGMT;
3336 frm.Action.action = SIR_MAC_ACTION_CHANNEL_SWITCH_ID;
3337 frm.ChanSwitchAnn.switchMode = nMode;
3338 frm.ChanSwitchAnn.newChannel = nNewChannel;
3339 frm.ChanSwitchAnn.switchCount = nCount;
3340 frm.ChanSwitchAnn.present = 1;
3341
3342 nStatus = dot11f_get_packed_channel_switch_size(pMac, &frm, &nPayload);
3343 if (DOT11F_FAILED(nStatus)) {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07003344 pe_err("Failed to calculate the packed size for a Channel Switch (0x%08x)",
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003345 nStatus);
3346 /* We'll fall back on the worst case scenario: */
3347 nPayload = sizeof(tDot11fChannelSwitch);
3348 } else if (DOT11F_WARNED(nStatus)) {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07003349 pe_warn("There were warnings while calculating the packed size for a Channel Switch (0x%08x)",
3350 nStatus);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003351 }
3352
3353 nBytes = nPayload + sizeof(tSirMacMgmtHdr);
3354
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05303355 qdf_status =
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003356 cds_packet_alloc((uint16_t) nBytes, (void **)&pFrame,
3357 (void **)&pPacket);
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05303358 if (!QDF_IS_STATUS_SUCCESS(qdf_status)) {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07003359 pe_err("Failed to allocate %d bytes for a TPC Report", nBytes);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003360 return eSIR_FAILURE;
3361 }
3362 /* Paranoia: */
Anurag Chouhan600c3a02016-03-01 10:33:54 +05303363 qdf_mem_set(pFrame, nBytes, 0);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003364
3365 /* Next, we fill out the buffer descriptor: */
3366 lim_populate_mac_header(pMac, pFrame, SIR_MAC_MGMT_FRAME,
3367 SIR_MAC_MGMT_ACTION, peer,
3368 psessionEntry->selfMacAddr);
3369 pMacHdr = (tpSirMacMgmtHdr) pFrame;
Anurag Chouhan600c3a02016-03-01 10:33:54 +05303370 qdf_mem_copy((uint8_t *) pMacHdr->bssId,
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003371 (uint8_t *) psessionEntry->bssId, sizeof(tSirMacAddr));
3372
3373#ifdef WLAN_FEATURE_11W
3374 lim_set_protected_bit(pMac, psessionEntry, peer, pMacHdr);
3375#endif
3376
3377 nStatus = dot11f_pack_channel_switch(pMac, &frm, pFrame +
3378 sizeof(tSirMacMgmtHdr),
3379 nPayload, &nPayload);
3380 if (DOT11F_FAILED(nStatus)) {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07003381 pe_err("Failed to pack a Channel Switch (0x%08x)",
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003382 nStatus);
3383 cds_packet_free((void *)pPacket);
3384 return eSIR_FAILURE; /* allocated! */
3385 } else if (DOT11F_WARNED(nStatus)) {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07003386 pe_warn("There were warnings while packing a Channel Switch (0x%08x)",
3387 nStatus);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003388 }
3389
3390 if ((SIR_BAND_5_GHZ == lim_get_rf_band(psessionEntry->currentOperChannel))
Anurag Chouhan6d760662016-02-20 16:05:43 +05303391 || (psessionEntry->pePersona == QDF_P2P_CLIENT_MODE) ||
3392 (psessionEntry->pePersona == QDF_P2P_GO_MODE)
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003393 ) {
3394 txFlag |= HAL_USE_BD_RATE2_FOR_MANAGEMENT_FRAME;
3395 }
3396
Anurag Chouhanb2dc16f2016-02-25 11:47:37 +05303397 MTRACE(qdf_trace(QDF_MODULE_ID_PE, TRACE_CODE_TX_MGMT,
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003398 psessionEntry->peSessionId, pMacHdr->fc.subType));
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05303399 qdf_status = wma_tx_frame(pMac, pPacket, (uint16_t) nBytes,
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003400 TXRX_FRM_802_11_MGMT,
3401 ANI_TXDIR_TODS,
3402 7, lim_tx_complete, pFrame, txFlag,
3403 smeSessionId, 0);
Anurag Chouhanb2dc16f2016-02-25 11:47:37 +05303404 MTRACE(qdf_trace(QDF_MODULE_ID_PE, TRACE_CODE_TX_COMPLETE,
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05303405 psessionEntry->peSessionId, qdf_status));
3406 if (!QDF_IS_STATUS_SUCCESS(qdf_status)) {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07003407 pe_err("Failed to send a Channel Switch (%X)!",
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05303408 qdf_status);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003409 /* Pkt will be freed up by the callback */
3410 return eSIR_FAILURE;
3411 }
3412
3413 return eSIR_SUCCESS;
3414
3415} /* End lim_send_channel_switch_mgmt_frame. */
3416
Abhishek Singh518323d2015-10-19 17:42:01 +05303417/**
3418 * lim_send_extended_chan_switch_action_frame()- function to send ECSA
3419 * action frame over the air .
3420 * @mac_ctx: pointer to global mac structure
3421 * @peer: Destination mac.
3422 * @mode: channel switch mode
3423 * @new_op_class: new op class
3424 * @new_channel: new channel to switch
3425 * @count: channel switch count
3426 *
3427 * This function is called to send ECSA frame.
3428 *
3429 * Return: success if frame is sent else return failure
3430 */
3431
3432tSirRetStatus
3433lim_send_extended_chan_switch_action_frame(tpAniSirGlobal mac_ctx,
3434 tSirMacAddr peer, uint8_t mode, uint8_t new_op_class,
3435 uint8_t new_channel, uint8_t count, tpPESession session_entry)
3436{
3437 tDot11fext_channel_switch_action_frame frm;
3438 uint8_t *frame;
3439 tpSirMacMgmtHdr mac_hdr;
3440 uint32_t num_bytes, n_payload, status;
3441 void *packet;
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05303442 QDF_STATUS qdf_status;
Abhishek Singh518323d2015-10-19 17:42:01 +05303443 uint8_t txFlag = 0;
3444 uint8_t sme_session_id = 0;
3445
3446 if (session_entry == NULL) {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07003447 pe_err("Session entry is NULL!!!");
Abhishek Singh518323d2015-10-19 17:42:01 +05303448 return eSIR_FAILURE;
3449 }
3450
3451 sme_session_id = session_entry->smeSessionId;
3452
Anurag Chouhan600c3a02016-03-01 10:33:54 +05303453 qdf_mem_set(&frm, sizeof(frm), 0);
Abhishek Singh518323d2015-10-19 17:42:01 +05303454
3455 frm.Category.category = SIR_MAC_ACTION_PUBLIC_USAGE;
3456 frm.Action.action = SIR_MAC_ACTION_EXT_CHANNEL_SWITCH_ID;
3457
3458 frm.ext_chan_switch_ann_action.switch_mode = mode;
3459 frm.ext_chan_switch_ann_action.op_class = new_op_class;
3460 frm.ext_chan_switch_ann_action.new_channel = new_channel;
3461 frm.ext_chan_switch_ann_action.switch_count = count;
3462
3463
3464 status = dot11f_get_packed_ext_channel_switch_action_frame_size(mac_ctx,
3465 &frm, &n_payload);
3466 if (DOT11F_FAILED(status)) {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07003467 pe_err("Failed to get packed size for Channel Switch 0x%08x",
Abhishek Singh518323d2015-10-19 17:42:01 +05303468 status);
3469 /* We'll fall back on the worst case scenario*/
3470 n_payload = sizeof(tDot11fext_channel_switch_action_frame);
3471 } else if (DOT11F_WARNED(status)) {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07003472 pe_warn("There were warnings while calculating the packed size for a Ext Channel Switch (0x%08x)",
Abhishek Singh518323d2015-10-19 17:42:01 +05303473 status);
3474 }
3475
3476 num_bytes = n_payload + sizeof(tSirMacMgmtHdr);
3477
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05303478 qdf_status = cds_packet_alloc((uint16_t)num_bytes,
Abhishek Singh518323d2015-10-19 17:42:01 +05303479 (void **) &frame, (void **) &packet);
3480
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05303481 if (!QDF_IS_STATUS_SUCCESS(qdf_status)) {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07003482 pe_err("Failed to allocate %d bytes for a Ext Channel Switch",
Abhishek Singh518323d2015-10-19 17:42:01 +05303483 num_bytes);
3484 return eSIR_FAILURE;
3485 }
3486
3487 /* Paranoia*/
Anurag Chouhan600c3a02016-03-01 10:33:54 +05303488 qdf_mem_set(frame, num_bytes, 0);
Abhishek Singh518323d2015-10-19 17:42:01 +05303489
3490 /* Next, we fill out the buffer descriptor */
3491 lim_populate_mac_header(mac_ctx, frame, SIR_MAC_MGMT_FRAME,
3492 SIR_MAC_MGMT_ACTION, peer, session_entry->selfMacAddr);
3493 mac_hdr = (tpSirMacMgmtHdr) frame;
Anurag Chouhan600c3a02016-03-01 10:33:54 +05303494 qdf_mem_copy((uint8_t *) mac_hdr->bssId,
Abhishek Singh518323d2015-10-19 17:42:01 +05303495 (uint8_t *) session_entry->bssId,
3496 sizeof(tSirMacAddr));
3497
3498 status = dot11f_pack_ext_channel_switch_action_frame(mac_ctx, &frm,
3499 frame + sizeof(tSirMacMgmtHdr), n_payload, &n_payload);
3500 if (DOT11F_FAILED(status)) {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07003501 pe_err("Failed to pack a Channel Switch 0x%08x", status);
Abhishek Singh518323d2015-10-19 17:42:01 +05303502 cds_packet_free((void *)packet);
3503 return eSIR_FAILURE;
3504 } else if (DOT11F_WARNED(status)) {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07003505 pe_warn("There were warnings while packing a Channel Switch 0x%08x",
Abhishek Singh518323d2015-10-19 17:42:01 +05303506 status);
3507 }
3508
3509 if ((SIR_BAND_5_GHZ ==
3510 lim_get_rf_band(session_entry->currentOperChannel)) ||
Anurag Chouhan6d760662016-02-20 16:05:43 +05303511 (session_entry->pePersona == QDF_P2P_CLIENT_MODE) ||
3512 (session_entry->pePersona == QDF_P2P_GO_MODE)) {
Abhishek Singh518323d2015-10-19 17:42:01 +05303513 txFlag |= HAL_USE_BD_RATE2_FOR_MANAGEMENT_FRAME;
3514 }
3515
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07003516 pe_debug("Send Ext channel Switch to :"MAC_ADDRESS_STR" with swcount %d, swmode %d , newchannel %d newops %d",
Abhishek Singh518323d2015-10-19 17:42:01 +05303517 MAC_ADDR_ARRAY(mac_hdr->da),
3518 frm.ext_chan_switch_ann_action.switch_count,
3519 frm.ext_chan_switch_ann_action.switch_mode,
3520 frm.ext_chan_switch_ann_action.new_channel,
3521 frm.ext_chan_switch_ann_action.op_class);
3522
Anurag Chouhanb2dc16f2016-02-25 11:47:37 +05303523 MTRACE(qdf_trace(QDF_MODULE_ID_PE, TRACE_CODE_TX_MGMT,
Abhishek Singh518323d2015-10-19 17:42:01 +05303524 session_entry->peSessionId, mac_hdr->fc.subType));
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05303525 qdf_status = wma_tx_frame(mac_ctx, packet, (uint16_t) num_bytes,
Abhishek Singh518323d2015-10-19 17:42:01 +05303526 TXRX_FRM_802_11_MGMT,
3527 ANI_TXDIR_TODS,
3528 7,
3529 lim_tx_complete, frame,
3530 txFlag, sme_session_id, 0);
Anurag Chouhanb2dc16f2016-02-25 11:47:37 +05303531 MTRACE(qdf_trace(QDF_MODULE_ID_PE, TRACE_CODE_TX_COMPLETE,
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05303532 session_entry->peSessionId, qdf_status));
3533 if (!QDF_IS_STATUS_SUCCESS(qdf_status)) {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07003534 pe_err("Failed to send a Ext Channel Switch %X!",
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05303535 qdf_status);
Abhishek Singh518323d2015-10-19 17:42:01 +05303536 /* Pkt will be freed up by the callback */
3537 return eSIR_FAILURE;
3538 }
3539 return eSIR_SUCCESS;
3540} /* End lim_send_extended_chan_switch_action_frame */
3541
Abhishek Singh5695e2a2016-10-28 10:39:12 +05303542
3543/**
3544 * lim_oper_chan_change_confirm_tx_complete_cnf()- Confirmation for oper_chan_change_confirm
3545 * sent over the air
3546 *
Himanshu Agarwal2fdf77a2016-12-29 11:41:00 +05303547 * @context: pointer to global mac
3548 * @buf: buffer
Abhishek Singh5695e2a2016-10-28 10:39:12 +05303549 * @tx_complete : Sent status
Himanshu Agarwal2fdf77a2016-12-29 11:41:00 +05303550 * @params: tx completion params
Abhishek Singh5695e2a2016-10-28 10:39:12 +05303551 *
3552 * Return: This returns QDF_STATUS
3553 */
3554
3555static QDF_STATUS lim_oper_chan_change_confirm_tx_complete_cnf(
Himanshu Agarwal2fdf77a2016-12-29 11:41:00 +05303556 void *context,
3557 qdf_nbuf_t buf,
3558 uint32_t tx_complete,
3559 void *params)
Abhishek Singh5695e2a2016-10-28 10:39:12 +05303560{
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07003561 pe_debug("tx_complete: %d", tx_complete);
Abhishek Singh5695e2a2016-10-28 10:39:12 +05303562 return QDF_STATUS_SUCCESS;
3563}
3564
3565/**
3566 * lim_p2p_oper_chan_change_confirm_action_frame()- function to send
3567 * p2p oper chan change confirm action frame
3568 * @mac_ctx: pointer to global mac structure
3569 * @peer: Destination mac.
3570 * @session_entry: session entry
3571 *
3572 * This function is called to send p2p oper chan change confirm action frame.
3573 *
3574 * Return: success if frame is sent else return failure
3575 */
3576
3577tSirRetStatus
3578lim_p2p_oper_chan_change_confirm_action_frame(tpAniSirGlobal mac_ctx,
3579 tSirMacAddr peer, tpPESession session_entry)
3580{
3581 tDot11fp2p_oper_chan_change_confirm frm;
3582 uint8_t *frame;
3583 tpSirMacMgmtHdr mac_hdr;
3584 uint32_t num_bytes, n_payload, status;
3585 void *packet;
3586 QDF_STATUS qdf_status;
3587 uint8_t tx_flag = 0;
3588 uint8_t sme_session_id = 0;
3589
3590 if (session_entry == NULL) {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07003591 pe_err("Session entry is NULL!!!");
Abhishek Singh5695e2a2016-10-28 10:39:12 +05303592 return eSIR_FAILURE;
3593 }
3594
3595 sme_session_id = session_entry->smeSessionId;
3596
3597 qdf_mem_set(&frm, sizeof(frm), 0);
3598
3599 frm.Category.category = SIR_MAC_ACTION_VENDOR_SPECIFIC_CATEGORY;
3600
3601 qdf_mem_copy(frm.p2p_action_oui.oui_data,
3602 SIR_MAC_P2P_OUI, SIR_MAC_P2P_OUI_SIZE);
3603 frm.p2p_action_subtype.subtype = 0x04;
3604 frm.DialogToken.token = 0x0;
3605
3606 if (session_entry->htCapability) {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07003607 pe_debug("Populate HT Caps in Assoc Request");
Abhishek Singh5695e2a2016-10-28 10:39:12 +05303608 populate_dot11f_ht_caps(mac_ctx, session_entry, &frm.HTCaps);
3609 }
3610
3611 if (session_entry->vhtCapability) {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07003612 pe_debug("Populate VHT Caps in Assoc Request");
Abhishek Singh5695e2a2016-10-28 10:39:12 +05303613 populate_dot11f_vht_caps(mac_ctx, session_entry, &frm.VHTCaps);
3614 populate_dot11f_operating_mode(mac_ctx,
3615 &frm.OperatingMode, session_entry);
3616 }
3617
3618 status = dot11f_get_packed_p2p_oper_chan_change_confirmSize(mac_ctx,
3619 &frm, &n_payload);
3620 if (DOT11F_FAILED(status)) {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07003621 pe_err("Failed to get packed size 0x%08x", status);
Abhishek Singh5695e2a2016-10-28 10:39:12 +05303622 /* We'll fall back on the worst case scenario*/
3623 n_payload = sizeof(tDot11fp2p_oper_chan_change_confirm);
3624 } else if (DOT11F_WARNED(status)) {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07003625 pe_warn("There were warnings while calculating the packed size (0x%08x)",
3626 status);
Abhishek Singh5695e2a2016-10-28 10:39:12 +05303627 }
3628
3629 num_bytes = n_payload + sizeof(tSirMacMgmtHdr);
3630
3631 qdf_status = cds_packet_alloc((uint16_t)num_bytes,
3632 (void **) &frame, (void **) &packet);
3633
3634 if (!QDF_IS_STATUS_SUCCESS(qdf_status)) {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07003635 pe_err("Failed to allocate %d bytes", num_bytes);
Abhishek Singh5695e2a2016-10-28 10:39:12 +05303636 return eSIR_FAILURE;
3637 }
3638
3639 qdf_mem_set(frame, num_bytes, 0);
3640
3641 /* Next, fill out the buffer descriptor */
3642 lim_populate_mac_header(mac_ctx, frame, SIR_MAC_MGMT_FRAME,
3643 SIR_MAC_MGMT_ACTION, peer, session_entry->selfMacAddr);
3644 mac_hdr = (tpSirMacMgmtHdr) frame;
3645 qdf_mem_copy((uint8_t *) mac_hdr->bssId,
3646 (uint8_t *) session_entry->bssId,
3647 sizeof(tSirMacAddr));
3648
3649 status = dot11f_pack_p2p_oper_chan_change_confirm(mac_ctx, &frm,
3650 frame + sizeof(tSirMacMgmtHdr), n_payload, &n_payload);
3651 if (DOT11F_FAILED(status)) {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07003652 pe_err("Failed to pack 0x%08x", status);
Abhishek Singh5695e2a2016-10-28 10:39:12 +05303653 cds_packet_free((void *)packet);
3654 return eSIR_FAILURE;
3655 } else if (DOT11F_WARNED(status)) {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07003656 pe_warn("There were warnings while packing 0x%08x",
Abhishek Singh5695e2a2016-10-28 10:39:12 +05303657 status);
3658 }
3659
3660 if ((SIR_BAND_5_GHZ ==
3661 lim_get_rf_band(session_entry->currentOperChannel)) ||
3662 (session_entry->pePersona == QDF_P2P_CLIENT_MODE) ||
3663 (session_entry->pePersona == QDF_P2P_GO_MODE)) {
3664 tx_flag |= HAL_USE_BD_RATE2_FOR_MANAGEMENT_FRAME;
3665 }
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07003666 pe_debug("Send frame on channel %d to mac "
3667 MAC_ADDRESS_STR, session_entry->currentOperChannel,
Abhishek Singh5695e2a2016-10-28 10:39:12 +05303668 MAC_ADDR_ARRAY(peer));
3669
3670 MTRACE(qdf_trace(QDF_MODULE_ID_PE, TRACE_CODE_TX_MGMT,
3671 session_entry->peSessionId, mac_hdr->fc.subType));
3672
3673 qdf_status = wma_tx_frameWithTxComplete(mac_ctx, packet,
3674 (uint16_t)num_bytes,
3675 TXRX_FRM_802_11_MGMT, ANI_TXDIR_TODS,
3676 7, lim_tx_complete, frame,
3677 lim_oper_chan_change_confirm_tx_complete_cnf,
3678 tx_flag, sme_session_id, false, 0);
3679
3680 MTRACE(qdf_trace(QDF_MODULE_ID_PE, TRACE_CODE_TX_COMPLETE,
3681 session_entry->peSessionId, qdf_status));
3682 if (!QDF_IS_STATUS_SUCCESS(qdf_status)) {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07003683 pe_err("Failed to send status %X!", qdf_status);
Abhishek Singh5695e2a2016-10-28 10:39:12 +05303684 /* Pkt will be freed up by the callback */
3685 return eSIR_FAILURE;
3686 }
3687 return eSIR_SUCCESS;
3688}
3689
3690
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003691tSirRetStatus
3692lim_send_vht_opmode_notification_frame(tpAniSirGlobal pMac,
3693 tSirMacAddr peer,
3694 uint8_t nMode, tpPESession psessionEntry)
3695{
3696 tDot11fOperatingMode frm;
3697 uint8_t *pFrame;
3698 tpSirMacMgmtHdr pMacHdr;
3699 uint32_t nBytes, nPayload = 0, nStatus; /* , nCfg; */
3700 void *pPacket;
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05303701 QDF_STATUS qdf_status;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003702 uint8_t txFlag = 0;
3703
3704 uint8_t smeSessionId = 0;
3705
3706 if (psessionEntry == NULL) {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07003707 pe_err("Session entry is NULL!!!");
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003708 return eSIR_FAILURE;
3709 }
3710 smeSessionId = psessionEntry->smeSessionId;
3711
Anurag Chouhan600c3a02016-03-01 10:33:54 +05303712 qdf_mem_set((uint8_t *) &frm, sizeof(frm), 0);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003713
3714 frm.Category.category = SIR_MAC_ACTION_VHT;
3715 frm.Action.action = SIR_MAC_VHT_OPMODE_NOTIFICATION;
3716 frm.OperatingMode.chanWidth = nMode;
3717 frm.OperatingMode.rxNSS = 0;
3718 frm.OperatingMode.rxNSSType = 0;
3719
3720 nStatus = dot11f_get_packed_operating_mode_size(pMac, &frm, &nPayload);
3721 if (DOT11F_FAILED(nStatus)) {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07003722 pe_err("Failed to calculate the packed size for a Operating Mode (0x%08x)",
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003723 nStatus);
3724 /* We'll fall back on the worst case scenario: */
3725 nPayload = sizeof(tDot11fOperatingMode);
3726 } else if (DOT11F_WARNED(nStatus)) {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07003727 pe_warn("There were warnings while calculating the packed size for a Operating Mode (0x%08x)",
3728 nStatus);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003729 }
3730
3731 nBytes = nPayload + sizeof(tSirMacMgmtHdr);
3732
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05303733 qdf_status =
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003734 cds_packet_alloc((uint16_t) nBytes, (void **)&pFrame,
3735 (void **)&pPacket);
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05303736 if (!QDF_IS_STATUS_SUCCESS(qdf_status)) {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07003737 pe_err("Failed to allocate %d bytes for a Operating Mode Report",
3738 nBytes);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003739 return eSIR_FAILURE;
3740 }
3741 /* Paranoia: */
Anurag Chouhan600c3a02016-03-01 10:33:54 +05303742 qdf_mem_set(pFrame, nBytes, 0);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003743
3744 /* Next, we fill out the buffer descriptor: */
Anurag Chouhan6d760662016-02-20 16:05:43 +05303745 if (psessionEntry->pePersona == QDF_SAP_MODE)
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003746 lim_populate_mac_header(pMac, pFrame, SIR_MAC_MGMT_FRAME,
3747 SIR_MAC_MGMT_ACTION, peer,
3748 psessionEntry->selfMacAddr);
3749 else
3750 lim_populate_mac_header(pMac, pFrame, SIR_MAC_MGMT_FRAME,
3751 SIR_MAC_MGMT_ACTION, psessionEntry->bssId,
3752 psessionEntry->selfMacAddr);
3753 pMacHdr = (tpSirMacMgmtHdr) pFrame;
Anurag Chouhan600c3a02016-03-01 10:33:54 +05303754 qdf_mem_copy((uint8_t *) pMacHdr->bssId,
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003755 (uint8_t *) psessionEntry->bssId, sizeof(tSirMacAddr));
3756 nStatus = dot11f_pack_operating_mode(pMac, &frm, pFrame +
3757 sizeof(tSirMacMgmtHdr),
3758 nPayload, &nPayload);
3759 if (DOT11F_FAILED(nStatus)) {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07003760 pe_err("Failed to pack a Operating Mode (0x%08x)",
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003761 nStatus);
3762 cds_packet_free((void *)pPacket);
3763 return eSIR_FAILURE; /* allocated! */
3764 } else if (DOT11F_WARNED(nStatus)) {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07003765 pe_warn("There were warnings while packing a Operating Mode (0x%08x)",
3766 nStatus);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003767 }
3768 if ((SIR_BAND_5_GHZ == lim_get_rf_band(psessionEntry->currentOperChannel))
Anurag Chouhan6d760662016-02-20 16:05:43 +05303769 || (psessionEntry->pePersona == QDF_P2P_CLIENT_MODE) ||
3770 (psessionEntry->pePersona == QDF_P2P_GO_MODE)
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003771 ) {
3772 txFlag |= HAL_USE_BD_RATE2_FOR_MANAGEMENT_FRAME;
3773 }
3774
Anurag Chouhanb2dc16f2016-02-25 11:47:37 +05303775 MTRACE(qdf_trace(QDF_MODULE_ID_PE, TRACE_CODE_TX_MGMT,
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003776 psessionEntry->peSessionId, pMacHdr->fc.subType));
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05303777 qdf_status = wma_tx_frame(pMac, pPacket, (uint16_t) nBytes,
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003778 TXRX_FRM_802_11_MGMT,
3779 ANI_TXDIR_TODS,
3780 7, lim_tx_complete, pFrame, txFlag,
3781 smeSessionId, 0);
Anurag Chouhanb2dc16f2016-02-25 11:47:37 +05303782 MTRACE(qdf_trace(QDF_MODULE_ID_PE, TRACE_CODE_TX_COMPLETE,
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05303783 psessionEntry->peSessionId, qdf_status));
3784 if (!QDF_IS_STATUS_SUCCESS(qdf_status)) {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07003785 pe_err("Failed to send a Channel Switch (%X)!",
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05303786 qdf_status);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003787 /* Pkt will be freed up by the callback */
3788 return eSIR_FAILURE;
3789 }
3790
3791 return eSIR_SUCCESS;
3792}
3793
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003794/**
3795 * \brief Send a Neighbor Report Request Action frame
3796 *
3797 *
3798 * \param pMac Pointer to the global MAC structure
3799 *
3800 * \param pNeighborReq Address of a tSirMacNeighborReportReq
3801 *
3802 * \param peer mac address of peer station.
3803 *
3804 * \param psessionEntry address of session entry.
3805 *
3806 * \return eSIR_SUCCESS on success, eSIR_FAILURE else
3807 *
3808 *
3809 */
3810
3811tSirRetStatus
3812lim_send_neighbor_report_request_frame(tpAniSirGlobal pMac,
3813 tpSirMacNeighborReportReq pNeighborReq,
3814 tSirMacAddr peer, tpPESession psessionEntry)
3815{
3816 tSirRetStatus statusCode = eSIR_SUCCESS;
3817 tDot11fNeighborReportRequest frm;
3818 uint8_t *pFrame;
3819 tpSirMacMgmtHdr pMacHdr;
3820 uint32_t nBytes, nPayload, nStatus;
3821 void *pPacket;
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05303822 QDF_STATUS qdf_status;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003823 uint8_t txFlag = 0;
3824 uint8_t smeSessionId = 0;
3825
3826 if (psessionEntry == NULL) {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07003827 pe_err("(psession == NULL) in Request to send Neighbor Report request action frame");
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003828 return eSIR_FAILURE;
3829 }
3830 smeSessionId = psessionEntry->smeSessionId;
Anurag Chouhan600c3a02016-03-01 10:33:54 +05303831 qdf_mem_set((uint8_t *) &frm, sizeof(frm), 0);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003832
3833 frm.Category.category = SIR_MAC_ACTION_RRM;
3834 frm.Action.action = SIR_MAC_RRM_NEIGHBOR_REQ;
3835 frm.DialogToken.token = pNeighborReq->dialogToken;
3836
3837 if (pNeighborReq->ssid_present) {
3838 populate_dot11f_ssid(pMac, &pNeighborReq->ssid, &frm.SSID);
3839 }
3840
3841 nStatus =
3842 dot11f_get_packed_neighbor_report_request_size(pMac, &frm, &nPayload);
3843 if (DOT11F_FAILED(nStatus)) {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07003844 pe_err("Failed to calculate the packed size for a Neighbor Report Request(0x%08x)",
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003845 nStatus);
3846 /* We'll fall back on the worst case scenario: */
3847 nPayload = sizeof(tDot11fNeighborReportRequest);
3848 } else if (DOT11F_WARNED(nStatus)) {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07003849 pe_warn("There were warnings while calculating the packed size for a Neighbor Report Request(0x%08x)",
3850 nStatus);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003851 }
3852
3853 nBytes = nPayload + sizeof(tSirMacMgmtHdr);
3854
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05303855 qdf_status =
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003856 cds_packet_alloc((uint16_t) nBytes, (void **)&pFrame,
3857 (void **)&pPacket);
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05303858 if (!QDF_IS_STATUS_SUCCESS(qdf_status)) {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07003859 pe_err("Failed to allocate %d bytes for a Neighbor "
3860 "Report Request", nBytes);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003861 return eSIR_FAILURE;
3862 }
3863 /* Paranoia: */
Anurag Chouhan600c3a02016-03-01 10:33:54 +05303864 qdf_mem_set(pFrame, nBytes, 0);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003865
3866 /* Copy necessary info to BD */
3867 lim_populate_mac_header(pMac, pFrame, SIR_MAC_MGMT_FRAME,
3868 SIR_MAC_MGMT_ACTION, peer, psessionEntry->selfMacAddr);
3869
3870 /* Update A3 with the BSSID */
3871 pMacHdr = (tpSirMacMgmtHdr) pFrame;
3872
3873 sir_copy_mac_addr(pMacHdr->bssId, psessionEntry->bssId);
3874
3875#ifdef WLAN_FEATURE_11W
3876 lim_set_protected_bit(pMac, psessionEntry, peer, pMacHdr);
3877#endif
3878
3879 /* Now, we're ready to "pack" the frames */
3880 nStatus = dot11f_pack_neighbor_report_request(pMac,
3881 &frm,
3882 pFrame +
3883 sizeof(tSirMacMgmtHdr),
3884 nPayload, &nPayload);
3885
3886 if (DOT11F_FAILED(nStatus)) {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07003887 pe_err("Failed to pack an Neighbor Report Request (0x%08x)",
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003888 nStatus);
3889
3890 /* FIXME - Need to convert to tSirRetStatus */
3891 statusCode = eSIR_FAILURE;
3892 goto returnAfterError;
3893 } else if (DOT11F_WARNED(nStatus)) {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07003894 pe_warn("There were warnings while packing Neighbor Report Request (0x%08x)",
3895 nStatus);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003896 }
3897
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07003898 pe_debug("Sending a Neighbor Report Request to");
Nishank Aggarwal46bd31a2017-03-10 16:23:53 +05303899 lim_print_mac_addr(pMac, peer, LOGD);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003900
3901 if ((SIR_BAND_5_GHZ == lim_get_rf_band(psessionEntry->currentOperChannel))
Anurag Chouhan6d760662016-02-20 16:05:43 +05303902 || (psessionEntry->pePersona == QDF_P2P_CLIENT_MODE) ||
3903 (psessionEntry->pePersona == QDF_P2P_GO_MODE)
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003904 ) {
3905 txFlag |= HAL_USE_BD_RATE2_FOR_MANAGEMENT_FRAME;
3906 }
3907
Anurag Chouhanb2dc16f2016-02-25 11:47:37 +05303908 MTRACE(qdf_trace(QDF_MODULE_ID_PE, TRACE_CODE_TX_MGMT,
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003909 psessionEntry->peSessionId, pMacHdr->fc.subType));
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05303910 qdf_status = wma_tx_frame(pMac,
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003911 pPacket,
3912 (uint16_t) nBytes,
3913 TXRX_FRM_802_11_MGMT,
3914 ANI_TXDIR_TODS,
3915 7, lim_tx_complete, pFrame, txFlag,
3916 smeSessionId, 0);
Anurag Chouhanb2dc16f2016-02-25 11:47:37 +05303917 MTRACE(qdf_trace(QDF_MODULE_ID_PE, TRACE_CODE_TX_COMPLETE,
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05303918 psessionEntry->peSessionId, qdf_status));
3919 if (QDF_STATUS_SUCCESS != qdf_status) {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07003920 pe_err("wma_tx_frame FAILED! Status [%d]", qdf_status);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003921 statusCode = eSIR_FAILURE;
3922 /* Pkt will be freed up by the callback */
3923 return statusCode;
3924 } else
3925 return eSIR_SUCCESS;
3926
3927returnAfterError:
3928 cds_packet_free((void *)pPacket);
3929
3930 return statusCode;
3931} /* End lim_send_neighbor_report_request_frame. */
3932
3933/**
3934 * \brief Send a Link Report Action frame
3935 *
3936 *
3937 * \param pMac Pointer to the global MAC structure
3938 *
3939 * \param pLinkReport Address of a tSirMacLinkReport
3940 *
3941 * \param peer mac address of peer station.
3942 *
3943 * \param psessionEntry address of session entry.
3944 *
3945 * \return eSIR_SUCCESS on success, eSIR_FAILURE else
3946 *
3947 *
3948 */
3949
3950tSirRetStatus
3951lim_send_link_report_action_frame(tpAniSirGlobal pMac,
3952 tpSirMacLinkReport pLinkReport,
3953 tSirMacAddr peer, tpPESession psessionEntry)
3954{
3955 tSirRetStatus statusCode = eSIR_SUCCESS;
3956 tDot11fLinkMeasurementReport frm;
3957 uint8_t *pFrame;
3958 tpSirMacMgmtHdr pMacHdr;
3959 uint32_t nBytes, nPayload, nStatus;
3960 void *pPacket;
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05303961 QDF_STATUS qdf_status;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003962 uint8_t txFlag = 0;
3963 uint8_t smeSessionId = 0;
3964
3965 if (psessionEntry == NULL) {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07003966 pe_err("(psession == NULL) in Request to send Link Report action frame");
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003967 return eSIR_FAILURE;
3968 }
3969
Anurag Chouhan600c3a02016-03-01 10:33:54 +05303970 qdf_mem_set((uint8_t *) &frm, sizeof(frm), 0);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003971
3972 frm.Category.category = SIR_MAC_ACTION_RRM;
3973 frm.Action.action = SIR_MAC_RRM_LINK_MEASUREMENT_RPT;
3974 frm.DialogToken.token = pLinkReport->dialogToken;
3975
3976 /* IEEE Std. 802.11 7.3.2.18. for the report element. */
3977 /* Even though TPC report an IE, it is represented using fixed fields since it is positioned */
3978 /* in the middle of other fixed fields in the link report frame(IEEE Std. 802.11k section7.4.6.4 */
3979 /* and frame parser always expects IEs to come after all fixed fields. It is easier to handle */
3980 /* such case this way than changing the frame parser. */
3981 frm.TPCEleID.TPCId = SIR_MAC_TPC_RPT_EID;
3982 frm.TPCEleLen.TPCLen = 2;
3983 frm.TxPower.txPower = pLinkReport->txPower;
3984 frm.LinkMargin.linkMargin = 0;
3985
3986 frm.RxAntennaId.antennaId = pLinkReport->rxAntenna;
3987 frm.TxAntennaId.antennaId = pLinkReport->txAntenna;
3988 frm.RCPI.rcpi = pLinkReport->rcpi;
3989 frm.RSNI.rsni = pLinkReport->rsni;
3990
3991 nStatus =
3992 dot11f_get_packed_link_measurement_report_size(pMac, &frm, &nPayload);
3993 if (DOT11F_FAILED(nStatus)) {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07003994 pe_err("Failed to calculate the packed size for a Link Report (0x%08x)", nStatus);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003995 /* We'll fall back on the worst case scenario: */
3996 nPayload = sizeof(tDot11fLinkMeasurementReport);
3997 } else if (DOT11F_WARNED(nStatus)) {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07003998 pe_warn("There were warnings while calculating the packed size for a Link Report (0x%08x)",
3999 nStatus);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08004000 }
4001
4002 nBytes = nPayload + sizeof(tSirMacMgmtHdr);
4003
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05304004 qdf_status =
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08004005 cds_packet_alloc((uint16_t) nBytes, (void **)&pFrame,
4006 (void **)&pPacket);
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05304007 if (!QDF_IS_STATUS_SUCCESS(qdf_status)) {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07004008 pe_err("Failed to allocate %d bytes for a Link "
4009 "Report", nBytes);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08004010 return eSIR_FAILURE;
4011 }
4012 /* Paranoia: */
Anurag Chouhan600c3a02016-03-01 10:33:54 +05304013 qdf_mem_set(pFrame, nBytes, 0);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08004014
4015 /* Copy necessary info to BD */
4016 lim_populate_mac_header(pMac, pFrame, SIR_MAC_MGMT_FRAME,
4017 SIR_MAC_MGMT_ACTION, peer, psessionEntry->selfMacAddr);
4018
4019 /* Update A3 with the BSSID */
4020 pMacHdr = (tpSirMacMgmtHdr) pFrame;
4021
4022 sir_copy_mac_addr(pMacHdr->bssId, psessionEntry->bssId);
4023
4024#ifdef WLAN_FEATURE_11W
4025 lim_set_protected_bit(pMac, psessionEntry, peer, pMacHdr);
4026#endif
4027
4028 /* Now, we're ready to "pack" the frames */
4029 nStatus = dot11f_pack_link_measurement_report(pMac,
4030 &frm,
4031 pFrame +
4032 sizeof(tSirMacMgmtHdr),
4033 nPayload, &nPayload);
4034
4035 if (DOT11F_FAILED(nStatus)) {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07004036 pe_err("Failed to pack an Link Report (0x%08x)", nStatus);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08004037
4038 /* FIXME - Need to convert to tSirRetStatus */
4039 statusCode = eSIR_FAILURE;
4040 goto returnAfterError;
4041 } else if (DOT11F_WARNED(nStatus)) {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07004042 pe_warn("There were warnings while packing Link Report (0x%08x)",
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08004043 nStatus);
4044 }
4045
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07004046 pe_warn("Sending a Link Report to");
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08004047 lim_print_mac_addr(pMac, peer, LOGW);
4048
4049 if ((SIR_BAND_5_GHZ == lim_get_rf_band(psessionEntry->currentOperChannel))
Anurag Chouhan6d760662016-02-20 16:05:43 +05304050 || (psessionEntry->pePersona == QDF_P2P_CLIENT_MODE) ||
4051 (psessionEntry->pePersona == QDF_P2P_GO_MODE)) {
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08004052 txFlag |= HAL_USE_BD_RATE2_FOR_MANAGEMENT_FRAME;
4053 }
4054
Anurag Chouhanb2dc16f2016-02-25 11:47:37 +05304055 MTRACE(qdf_trace(QDF_MODULE_ID_PE, TRACE_CODE_TX_MGMT,
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08004056 psessionEntry->peSessionId, pMacHdr->fc.subType));
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05304057 qdf_status = wma_tx_frame(pMac,
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08004058 pPacket,
4059 (uint16_t) nBytes,
4060 TXRX_FRM_802_11_MGMT,
4061 ANI_TXDIR_TODS,
4062 7, lim_tx_complete, pFrame, txFlag,
4063 smeSessionId, 0);
Anurag Chouhanb2dc16f2016-02-25 11:47:37 +05304064 MTRACE(qdf_trace(QDF_MODULE_ID_PE, TRACE_CODE_TX_COMPLETE,
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05304065 psessionEntry->peSessionId, qdf_status));
4066 if (QDF_STATUS_SUCCESS != qdf_status) {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07004067 pe_err("wma_tx_frame FAILED! Status [%d]", qdf_status);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08004068 statusCode = eSIR_FAILURE;
4069 /* Pkt will be freed up by the callback */
4070 return statusCode;
4071 } else
4072 return eSIR_SUCCESS;
4073
4074returnAfterError:
4075 cds_packet_free((void *)pPacket);
4076
4077 return statusCode;
4078} /* End lim_send_link_report_action_frame. */
4079
4080/**
4081 * \brief Send a Beacon Report Action frame
4082 *
4083 *
4084 * \param pMac Pointer to the global MAC structure
4085 *
4086 * \param dialog_token dialog token to be used in the action frame.
4087 *
4088 * \param num_report number of reports in pRRMReport.
4089 *
4090 * \param pRRMReport Address of a tSirMacRadioMeasureReport.
4091 *
4092 * \param peer mac address of peer station.
4093 *
4094 * \param psessionEntry address of session entry.
4095 *
4096 * \return eSIR_SUCCESS on success, eSIR_FAILURE else
4097 *
4098 *
4099 */
4100
4101tSirRetStatus
4102lim_send_radio_measure_report_action_frame(tpAniSirGlobal pMac,
4103 uint8_t dialog_token,
4104 uint8_t num_report,
4105 tpSirMacRadioMeasureReport pRRMReport,
4106 tSirMacAddr peer,
4107 tpPESession psessionEntry)
4108{
4109 tSirRetStatus statusCode = eSIR_SUCCESS;
4110 uint8_t *pFrame;
4111 tpSirMacMgmtHdr pMacHdr;
4112 uint32_t nBytes, nPayload, nStatus;
4113 void *pPacket;
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05304114 QDF_STATUS qdf_status;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08004115 uint8_t i;
4116 uint8_t txFlag = 0;
4117 uint8_t smeSessionId = 0;
4118
4119 tDot11fRadioMeasurementReport *frm =
Anurag Chouhan600c3a02016-03-01 10:33:54 +05304120 qdf_mem_malloc(sizeof(tDot11fRadioMeasurementReport));
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08004121 if (!frm) {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07004122 pe_err("Not enough memory to allocate tDot11fRadioMeasurementReport");
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08004123 return eSIR_MEM_ALLOC_FAILED;
4124 }
4125
4126 if (psessionEntry == NULL) {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07004127 pe_err("(psession == NULL) in Request to send Beacon Report action frame");
Anurag Chouhan600c3a02016-03-01 10:33:54 +05304128 qdf_mem_free(frm);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08004129 return eSIR_FAILURE;
4130 }
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08004131
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07004132 pe_debug("dialog_token %d num_report %d",
Padma, Santhosh Kumar93ec7d22016-12-26 15:58:37 +05304133 dialog_token, num_report);
4134
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08004135 frm->Category.category = SIR_MAC_ACTION_RRM;
4136 frm->Action.action = SIR_MAC_RRM_RADIO_MEASURE_RPT;
4137 frm->DialogToken.token = dialog_token;
4138
4139 frm->num_MeasurementReport =
4140 (num_report >
4141 RADIO_REPORTS_MAX_IN_A_FRAME) ? RADIO_REPORTS_MAX_IN_A_FRAME :
4142 num_report;
4143
4144 for (i = 0; i < frm->num_MeasurementReport; i++) {
4145 frm->MeasurementReport[i].type = pRRMReport[i].type;
4146 frm->MeasurementReport[i].token = pRRMReport[i].token;
4147 frm->MeasurementReport[i].late = 0; /* IEEE 802.11k section 7.3.22. (always zero in rrm) */
4148 switch (pRRMReport[i].type) {
4149 case SIR_MAC_RRM_BEACON_TYPE:
4150 populate_dot11f_beacon_report(pMac,
4151 &frm->MeasurementReport[i],
4152 &pRRMReport[i].report.
4153 beaconReport);
4154 frm->MeasurementReport[i].incapable =
4155 pRRMReport[i].incapable;
4156 frm->MeasurementReport[i].refused =
4157 pRRMReport[i].refused;
4158 frm->MeasurementReport[i].present = 1;
4159 break;
4160 default:
4161 frm->MeasurementReport[i].incapable =
4162 pRRMReport[i].incapable;
4163 frm->MeasurementReport[i].refused =
4164 pRRMReport[i].refused;
4165 frm->MeasurementReport[i].present = 1;
4166 break;
4167 }
4168 }
4169
4170 nStatus =
4171 dot11f_get_packed_radio_measurement_report_size(pMac, frm, &nPayload);
4172 if (DOT11F_FAILED(nStatus)) {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07004173 pe_err("Failed to calculate the packed size for a Radio Measure Report (0x%08x)",
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08004174 nStatus);
4175 /* We'll fall back on the worst case scenario: */
4176 nPayload = sizeof(tDot11fLinkMeasurementReport);
Anurag Chouhan600c3a02016-03-01 10:33:54 +05304177 qdf_mem_free(frm);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08004178 return eSIR_FAILURE;
4179 } else if (DOT11F_WARNED(nStatus)) {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07004180 pe_warn("There were warnings while calculating the packed size for a Radio Measure Report (0x%08x)",
4181 nStatus);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08004182 }
4183
4184 nBytes = nPayload + sizeof(tSirMacMgmtHdr);
4185
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05304186 qdf_status =
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08004187 cds_packet_alloc((uint16_t) nBytes, (void **)&pFrame,
4188 (void **)&pPacket);
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05304189 if (!QDF_IS_STATUS_SUCCESS(qdf_status)) {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07004190 pe_err("Failed to allocate %d bytes for a Radio Measure "
4191 "Report", nBytes);
Anurag Chouhan600c3a02016-03-01 10:33:54 +05304192 qdf_mem_free(frm);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08004193 return eSIR_FAILURE;
4194 }
4195 /* Paranoia: */
Anurag Chouhan600c3a02016-03-01 10:33:54 +05304196 qdf_mem_set(pFrame, nBytes, 0);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08004197
4198 /* Copy necessary info to BD */
4199 lim_populate_mac_header(pMac, pFrame, SIR_MAC_MGMT_FRAME,
4200 SIR_MAC_MGMT_ACTION, peer, psessionEntry->selfMacAddr);
4201
4202 /* Update A3 with the BSSID */
4203 pMacHdr = (tpSirMacMgmtHdr) pFrame;
4204
4205 sir_copy_mac_addr(pMacHdr->bssId, psessionEntry->bssId);
4206
4207#ifdef WLAN_FEATURE_11W
4208 lim_set_protected_bit(pMac, psessionEntry, peer, pMacHdr);
4209#endif
4210
4211 /* Now, we're ready to "pack" the frames */
4212 nStatus = dot11f_pack_radio_measurement_report(pMac,
4213 frm,
4214 pFrame +
4215 sizeof(tSirMacMgmtHdr),
4216 nPayload, &nPayload);
4217
4218 if (DOT11F_FAILED(nStatus)) {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07004219 pe_err("Failed to pack an Radio Measure Report (0x%08x)",
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08004220 nStatus);
4221
4222 /* FIXME - Need to convert to tSirRetStatus */
4223 statusCode = eSIR_FAILURE;
4224 goto returnAfterError;
4225 } else if (DOT11F_WARNED(nStatus)) {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07004226 pe_warn("There were warnings while packing Radio Measure Report (0x%08x)",
4227 nStatus);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08004228 }
4229
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07004230 pe_warn("Sending a Radio Measure Report to");
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08004231 lim_print_mac_addr(pMac, peer, LOGW);
4232
4233 if ((SIR_BAND_5_GHZ == lim_get_rf_band(psessionEntry->currentOperChannel))
Anurag Chouhan6d760662016-02-20 16:05:43 +05304234 || (psessionEntry->pePersona == QDF_P2P_CLIENT_MODE) ||
4235 (psessionEntry->pePersona == QDF_P2P_GO_MODE)
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08004236 ) {
4237 txFlag |= HAL_USE_BD_RATE2_FOR_MANAGEMENT_FRAME;
4238 }
4239
Anurag Chouhanb2dc16f2016-02-25 11:47:37 +05304240 MTRACE(qdf_trace(QDF_MODULE_ID_PE, TRACE_CODE_TX_MGMT,
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08004241 psessionEntry->peSessionId, pMacHdr->fc.subType));
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05304242 qdf_status = wma_tx_frame(pMac,
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08004243 pPacket,
4244 (uint16_t) nBytes,
4245 TXRX_FRM_802_11_MGMT,
4246 ANI_TXDIR_TODS,
4247 7, lim_tx_complete, pFrame, txFlag,
4248 smeSessionId, 0);
Anurag Chouhanb2dc16f2016-02-25 11:47:37 +05304249 MTRACE(qdf_trace(QDF_MODULE_ID_PE, TRACE_CODE_TX_COMPLETE,
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05304250 psessionEntry->peSessionId, qdf_status));
4251 if (QDF_STATUS_SUCCESS != qdf_status) {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07004252 pe_err("wma_tx_frame FAILED! Status [%d]", qdf_status);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08004253 statusCode = eSIR_FAILURE;
4254 /* Pkt will be freed up by the callback */
Anurag Chouhan600c3a02016-03-01 10:33:54 +05304255 qdf_mem_free(frm);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08004256 return statusCode;
4257 } else {
Anurag Chouhan600c3a02016-03-01 10:33:54 +05304258 qdf_mem_free(frm);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08004259 return eSIR_SUCCESS;
4260 }
4261
4262returnAfterError:
Anurag Chouhan600c3a02016-03-01 10:33:54 +05304263 qdf_mem_free(frm);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08004264 cds_packet_free((void *)pPacket);
4265 return statusCode;
4266}
4267
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08004268#ifdef WLAN_FEATURE_11W
4269/**
4270 * \brief Send SA query request action frame to peer
4271 *
4272 * \sa lim_send_sa_query_request_frame
4273 *
4274 *
4275 * \param pMac The global tpAniSirGlobal object
4276 *
4277 * \param transId Transaction identifier
4278 *
4279 * \param peer The Mac address of the station to which this action frame is addressed
4280 *
4281 * \param psessionEntry The PE session entry
4282 *
4283 * \return eSIR_SUCCESS if setup completes successfully
4284 * eSIR_FAILURE is some problem is encountered
4285 */
4286
4287tSirRetStatus lim_send_sa_query_request_frame(tpAniSirGlobal pMac, uint8_t *transId,
4288 tSirMacAddr peer,
4289 tpPESession psessionEntry)
4290{
4291
4292 tDot11fSaQueryReq frm; /* SA query request action frame */
4293 uint8_t *pFrame;
4294 tSirRetStatus nSirStatus;
4295 tpSirMacMgmtHdr pMacHdr;
4296 uint32_t nBytes, nPayload, nStatus;
4297 void *pPacket;
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05304298 QDF_STATUS qdf_status;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08004299 uint8_t txFlag = 0;
4300 uint8_t smeSessionId = 0;
4301
Anurag Chouhan600c3a02016-03-01 10:33:54 +05304302 qdf_mem_set((uint8_t *) &frm, sizeof(frm), 0);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08004303 frm.Category.category = SIR_MAC_ACTION_SA_QUERY;
4304 /* 11w action field is :
4305 action: 0 --> SA Query Request action frame
4306 action: 1 --> SA Query Response action frame */
4307 frm.Action.action = SIR_MAC_SA_QUERY_REQ;
4308 /* 11w SA Query Request transId */
Anurag Chouhan600c3a02016-03-01 10:33:54 +05304309 qdf_mem_copy(&frm.TransactionId.transId[0], &transId[0], 2);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08004310
4311 nStatus = dot11f_get_packed_sa_query_req_size(pMac, &frm, &nPayload);
4312 if (DOT11F_FAILED(nStatus)) {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07004313 pe_err("Failed to calculate the packed size for an SA Query Request (0x%08x)",
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08004314 nStatus);
4315 /* We'll fall back on the worst case scenario: */
4316 nPayload = sizeof(tDot11fSaQueryReq);
4317 } else if (DOT11F_WARNED(nStatus)) {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07004318 pe_warn("There were warnings while calculating the packed size for an SA Query Request (0x%08x)",
4319 nStatus);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08004320 }
4321
4322 nBytes = nPayload + sizeof(tSirMacMgmtHdr);
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05304323 qdf_status =
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08004324 cds_packet_alloc(nBytes, (void **)&pFrame, (void **)&pPacket);
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05304325 if (!QDF_IS_STATUS_SUCCESS(qdf_status)) {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07004326 pe_err("Failed to allocate %d bytes for a SA Query Request "
4327 "action frame", nBytes);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08004328 return eSIR_FAILURE;
4329 }
4330 /* Paranoia: */
Anurag Chouhan600c3a02016-03-01 10:33:54 +05304331 qdf_mem_set(pFrame, nBytes, 0);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08004332
4333 /* Copy necessary info to BD */
4334 lim_populate_mac_header(pMac, pFrame, SIR_MAC_MGMT_FRAME,
4335 SIR_MAC_MGMT_ACTION, peer, psessionEntry->selfMacAddr);
4336
4337 /* Update A3 with the BSSID */
4338 pMacHdr = (tpSirMacMgmtHdr) pFrame;
4339
4340 sir_copy_mac_addr(pMacHdr->bssId, psessionEntry->bssId);
4341
4342 /* Since this is a SA Query Request, set the "protect" (aka WEP) bit */
4343 /* in the FC */
4344 lim_set_protected_bit(pMac, psessionEntry, peer, pMacHdr);
4345
4346 /* Pack 11w SA Query Request frame */
4347 nStatus = dot11f_pack_sa_query_req(pMac,
4348 &frm,
4349 pFrame + sizeof(tSirMacMgmtHdr),
4350 nPayload, &nPayload);
4351
4352 if (DOT11F_FAILED(nStatus)) {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07004353 pe_err("Failed to pack an SA Query Request (0x%08x)",
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08004354 nStatus);
4355 /* FIXME - Need to convert to tSirRetStatus */
4356 nSirStatus = eSIR_FAILURE;
4357 goto returnAfterError;
4358 } else if (DOT11F_WARNED(nStatus)) {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07004359 pe_warn("There were warnings while packing SA Query Request (0x%08x)",
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08004360 nStatus);
4361 }
4362
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07004363 pe_debug("Sending an SA Query Request to");
4364 lim_print_mac_addr(pMac, peer, LOGD);
4365 pe_debug("Sending an SA Query Request from ");
4366 lim_print_mac_addr(pMac, psessionEntry->selfMacAddr, LOGD);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08004367
4368 if ((SIR_BAND_5_GHZ == lim_get_rf_band(psessionEntry->currentOperChannel))
4369#ifdef WLAN_FEATURE_P2P
Anurag Chouhan6d760662016-02-20 16:05:43 +05304370 || (psessionEntry->pePersona == QDF_P2P_CLIENT_MODE) ||
4371 (psessionEntry->pePersona == QDF_P2P_GO_MODE)
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08004372#endif
4373 ) {
4374 txFlag |= HAL_USE_BD_RATE2_FOR_MANAGEMENT_FRAME;
4375 }
4376 smeSessionId = psessionEntry->smeSessionId;
4377
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05304378 qdf_status = wma_tx_frame(pMac,
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08004379 pPacket,
4380 (uint16_t) nBytes,
4381 TXRX_FRM_802_11_MGMT,
4382 ANI_TXDIR_TODS,
4383 7, lim_tx_complete, pFrame, txFlag,
4384 smeSessionId, 0);
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05304385 if (QDF_STATUS_SUCCESS != qdf_status) {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07004386 pe_err("wma_tx_frame FAILED! Status [%d]", qdf_status);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08004387 nSirStatus = eSIR_FAILURE;
4388 /* Pkt will be freed up by the callback */
4389 return nSirStatus;
4390 } else {
4391 return eSIR_SUCCESS;
4392 }
4393
4394returnAfterError:
4395 cds_packet_free((void *)pPacket);
4396 return nSirStatus;
4397} /* End lim_send_sa_query_request_frame */
4398
4399/**
4400 * \brief Send SA query response action frame to peer
4401 *
4402 * \sa lim_send_sa_query_response_frame
4403 *
4404 *
4405 * \param pMac The global tpAniSirGlobal object
4406 *
4407 * \param transId Transaction identifier received in SA query request action frame
4408 *
4409 * \param peer The Mac address of the AP to which this action frame is addressed
4410 *
4411 * \param psessionEntry The PE session entry
4412 *
4413 * \return eSIR_SUCCESS if setup completes successfully
4414 * eSIR_FAILURE is some problem is encountered
4415 */
4416
4417tSirRetStatus lim_send_sa_query_response_frame(tpAniSirGlobal pMac,
4418 uint8_t *transId, tSirMacAddr peer,
4419 tpPESession psessionEntry)
4420{
4421
4422 tDot11fSaQueryRsp frm; /* SA query reponse action frame */
4423 uint8_t *pFrame;
4424 tSirRetStatus nSirStatus;
4425 tpSirMacMgmtHdr pMacHdr;
4426 uint32_t nBytes, nPayload, nStatus;
4427 void *pPacket;
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05304428 QDF_STATUS qdf_status;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08004429 uint8_t txFlag = 0;
4430 uint8_t smeSessionId = 0;
4431
4432 smeSessionId = psessionEntry->smeSessionId;
4433
Anurag Chouhan600c3a02016-03-01 10:33:54 +05304434 qdf_mem_set((uint8_t *) &frm, sizeof(frm), 0);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08004435 frm.Category.category = SIR_MAC_ACTION_SA_QUERY;
4436 /*11w action field is :
4437 action: 0 --> SA query request action frame
4438 action: 1 --> SA query response action frame */
4439 frm.Action.action = SIR_MAC_SA_QUERY_RSP;
4440 /*11w SA query response transId is same as
4441 SA query request transId */
Anurag Chouhan600c3a02016-03-01 10:33:54 +05304442 qdf_mem_copy(&frm.TransactionId.transId[0], &transId[0], 2);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08004443
4444 nStatus = dot11f_get_packed_sa_query_rsp_size(pMac, &frm, &nPayload);
4445 if (DOT11F_FAILED(nStatus)) {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07004446 pe_err("Failed to calculate the packed size for a SA Query Response (0x%08x)",
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08004447 nStatus);
4448 /* We'll fall back on the worst case scenario: */
4449 nPayload = sizeof(tDot11fSaQueryRsp);
4450 } else if (DOT11F_WARNED(nStatus)) {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07004451 pe_warn("There were warnings while calculating the packed size for an SA Query Response (0x%08x)",
4452 nStatus);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08004453 }
4454
4455 nBytes = nPayload + sizeof(tSirMacMgmtHdr);
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05304456 qdf_status =
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08004457 cds_packet_alloc(nBytes, (void **)&pFrame, (void **)&pPacket);
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05304458 if (!QDF_IS_STATUS_SUCCESS(qdf_status)) {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07004459 pe_err("Failed to allocate %d bytes for a SA query response"
4460 " action frame", nBytes);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08004461 return eSIR_FAILURE;
4462 }
4463 /* Paranoia: */
Anurag Chouhan600c3a02016-03-01 10:33:54 +05304464 qdf_mem_set(pFrame, nBytes, 0);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08004465
4466 /* Copy necessary info to BD */
4467 lim_populate_mac_header(pMac, pFrame, SIR_MAC_MGMT_FRAME,
4468 SIR_MAC_MGMT_ACTION, peer, psessionEntry->selfMacAddr);
4469
4470 /* Update A3 with the BSSID */
4471 pMacHdr = (tpSirMacMgmtHdr) pFrame;
4472
4473 sir_copy_mac_addr(pMacHdr->bssId, psessionEntry->bssId);
4474
4475 /* Since this is a SA Query Response, set the "protect" (aka WEP) bit */
4476 /* in the FC */
4477 lim_set_protected_bit(pMac, psessionEntry, peer, pMacHdr);
4478
4479 /* Pack 11w SA query response frame */
4480 nStatus = dot11f_pack_sa_query_rsp(pMac,
4481 &frm,
4482 pFrame + sizeof(tSirMacMgmtHdr),
4483 nPayload, &nPayload);
4484
4485 if (DOT11F_FAILED(nStatus)) {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07004486 pe_err("Failed to pack an SA Query Response (0x%08x)",
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08004487 nStatus);
4488 /* FIXME - Need to convert to tSirRetStatus */
4489 nSirStatus = eSIR_FAILURE;
4490 goto returnAfterError;
4491 } else if (DOT11F_WARNED(nStatus)) {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07004492 pe_warn("There were warnings while packing SA Query Response (0x%08x)",
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08004493 nStatus);
4494 }
4495
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07004496 pe_debug("Sending a SA Query Response to");
Srinivas Girigowdaf936d822017-03-19 23:23:59 -07004497 lim_print_mac_addr(pMac, peer, LOGD);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08004498
4499 if ((SIR_BAND_5_GHZ == lim_get_rf_band(psessionEntry->currentOperChannel))
4500#ifdef WLAN_FEATURE_P2P
Anurag Chouhan6d760662016-02-20 16:05:43 +05304501 || (psessionEntry->pePersona == QDF_P2P_CLIENT_MODE) ||
4502 (psessionEntry->pePersona == QDF_P2P_GO_MODE)
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08004503#endif
4504 ) {
4505 txFlag |= HAL_USE_BD_RATE2_FOR_MANAGEMENT_FRAME;
4506 }
4507
Anurag Chouhanb2dc16f2016-02-25 11:47:37 +05304508 MTRACE(qdf_trace(QDF_MODULE_ID_PE, TRACE_CODE_TX_MGMT,
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08004509 psessionEntry->peSessionId, pMacHdr->fc.subType));
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05304510 qdf_status = wma_tx_frame(pMac,
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08004511 pPacket,
4512 (uint16_t) nBytes,
4513 TXRX_FRM_802_11_MGMT,
4514 ANI_TXDIR_TODS,
4515 7, lim_tx_complete, pFrame, txFlag,
4516 smeSessionId, 0);
Anurag Chouhanb2dc16f2016-02-25 11:47:37 +05304517 MTRACE(qdf_trace(QDF_MODULE_ID_PE, TRACE_CODE_TX_COMPLETE,
Anurag Chouhanfb54ab02016-02-18 18:00:46 +05304518 psessionEntry->peSessionId, qdf_status));
4519 if (QDF_STATUS_SUCCESS != qdf_status) {
Srinivas Girigowda7034a8b2017-03-26 19:52:36 -07004520 pe_err("wma_tx_frame FAILED! Status [%d]", qdf_status);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08004521 nSirStatus = eSIR_FAILURE;
4522 /* Pkt will be freed up by the callback */
4523 return nSirStatus;
4524 } else {
4525 return eSIR_SUCCESS;
4526 }
4527
4528returnAfterError:
4529 cds_packet_free((void *)pPacket);
4530 return nSirStatus;
4531} /* End lim_send_sa_query_response_frame */
4532#endif
Krishna Kumaar Natarajan48a6b4c2017-01-06 16:30:55 -08004533
4534/**
4535 * lim_send_addba_response_frame(): Send ADDBA response action frame to peer
4536 * @mac_ctx: mac context
4537 * @peer_mac: Peer MAC address
4538 * @tid: TID for which addba response is being sent
4539 * @session: PE session entry
4540 *
4541 * This function is called when ADDBA request is successful. ADDBA response is
4542 * setup by calling addba_response_setup API and frame is then sent out OTA.
4543 *
4544 * Return: QDF_STATUS
4545 */
4546QDF_STATUS lim_send_addba_response_frame(tpAniSirGlobal mac_ctx,
4547 tSirMacAddr peer_mac, uint16_t tid, tpPESession session)
4548{
4549
4550 tDot11faddba_rsp frm;
4551 uint8_t *frame_ptr;
4552 tpSirMacMgmtHdr mgmt_hdr;
4553 uint32_t num_bytes, payload_size, status;
4554 void *pkt_ptr;
4555 QDF_STATUS qdf_status;
4556 uint8_t tx_flag = 0;
4557 uint8_t sme_sessionid = 0;
4558 uint16_t buff_size, status_code, batimeout;
4559 uint8_t peer_id, dialog_token;
4560 void *soc = cds_get_context(QDF_MODULE_ID_SOC);
4561 void *peer, *pdev;
4562
4563 sme_sessionid = session->smeSessionId;
4564
4565 pdev = cds_get_context(QDF_MODULE_ID_TXRX);
4566 if (!pdev) {
Srinivas Girigowda28fb0122017-03-26 22:21:20 -07004567 pe_err("pdev is NULL");
Krishna Kumaar Natarajan48a6b4c2017-01-06 16:30:55 -08004568 return QDF_STATUS_E_FAILURE;
4569 }
4570
4571 peer = cdp_peer_find_by_addr(soc, pdev, peer_mac, &peer_id);
4572 if (!peer) {
Srinivas Girigowda28fb0122017-03-26 22:21:20 -07004573 pe_err("PEER [%pM] not found", peer_mac);
Krishna Kumaar Natarajan48a6b4c2017-01-06 16:30:55 -08004574 return QDF_STATUS_E_FAILURE;
4575 }
4576
4577 cdp_addba_responsesetup(soc, peer, tid, &dialog_token,
4578 &status_code, &buff_size, &batimeout);
4579
4580 qdf_mem_set((uint8_t *) &frm, sizeof(frm), 0);
4581 frm.Category.category = SIR_MAC_ACTION_BLKACK;
4582 frm.Action.action = SIR_MAC_ADDBA_RSP;
4583
4584 frm.DialogToken.token = dialog_token;
4585 frm.Status.status = status_code;
4586 frm.addba_param_set.tid = tid;
4587 frm.addba_param_set.buff_size = buff_size;
4588 frm.addba_param_set.amsdu_supp = SIR_MAC_BA_POLICY_IMMEDIATE;
4589 frm.addba_param_set.policy = SIR_MAC_BA_AMSDU_SUPPORTED;
4590 frm.ba_timeout.timeout = batimeout;
4591
Srinivas Girigowda28fb0122017-03-26 22:21:20 -07004592 pe_debug("Sending a ADDBA Response from %pM to %pM",
Krishna Kumaar Natarajan48a6b4c2017-01-06 16:30:55 -08004593 session->selfMacAddr, peer_mac);
Srinivas Girigowda28fb0122017-03-26 22:21:20 -07004594 pe_debug("tid: %d, dialog_token: %d, status: %d, buff_size: %d",
Krishna Kumaar Natarajan48a6b4c2017-01-06 16:30:55 -08004595 tid, frm.DialogToken.token, frm.Status.status,
4596 frm.addba_param_set.buff_size);
4597
4598 status = dot11f_get_packed_addba_rsp_size(mac_ctx, &frm, &payload_size);
4599 if (DOT11F_FAILED(status)) {
Srinivas Girigowda28fb0122017-03-26 22:21:20 -07004600 pe_err("Failed to calculate the packed size for a ADDBA Response (0x%08x).",
Krishna Kumaar Natarajan48a6b4c2017-01-06 16:30:55 -08004601 status);
4602 /* We'll fall back on the worst case scenario: */
4603 payload_size = sizeof(tDot11faddba_rsp);
4604 } else if (DOT11F_WARNED(status)) {
Srinivas Girigowda28fb0122017-03-26 22:21:20 -07004605 pe_warn("There were warnings while calculating the packed size for a ADDBA Response (0x%08x).", status);
Krishna Kumaar Natarajan48a6b4c2017-01-06 16:30:55 -08004606 }
4607
4608 num_bytes = payload_size + sizeof(*mgmt_hdr);
4609 qdf_status = cds_packet_alloc(num_bytes, (void **)&frame_ptr,
4610 (void **)&pkt_ptr);
4611 if (!QDF_IS_STATUS_SUCCESS(qdf_status)) {
Srinivas Girigowda28fb0122017-03-26 22:21:20 -07004612 pe_err("Failed to allocate %d bytes for a ADDBA response action frame",
4613 num_bytes);
Krishna Kumaar Natarajan48a6b4c2017-01-06 16:30:55 -08004614 return QDF_STATUS_E_FAILURE;
4615 }
4616 qdf_mem_set(frame_ptr, num_bytes, 0);
4617
4618 lim_populate_mac_header(mac_ctx, frame_ptr, SIR_MAC_MGMT_FRAME,
4619 SIR_MAC_MGMT_ACTION, peer_mac, session->selfMacAddr);
4620
4621 /* Update A3 with the BSSID */
4622 mgmt_hdr = (tpSirMacMgmtHdr) frame_ptr;
4623 sir_copy_mac_addr(mgmt_hdr->bssId, session->bssId);
4624
4625 /* ADDBA Response is a robust mgmt action frame,
4626 * set the "protect" (aka WEP) bit in the FC
4627 */
4628 lim_set_protected_bit(mac_ctx, session, peer_mac, mgmt_hdr);
4629
4630 status = dot11f_pack_addba_rsp(mac_ctx, &frm,
4631 frame_ptr + sizeof(tSirMacMgmtHdr), payload_size,
4632 &payload_size);
4633
4634 if (DOT11F_FAILED(status)) {
Srinivas Girigowda28fb0122017-03-26 22:21:20 -07004635 pe_err("Failed to pack a ADDBA Response (0x%08x)",
Krishna Kumaar Natarajan48a6b4c2017-01-06 16:30:55 -08004636 status);
4637 qdf_status = QDF_STATUS_E_FAILURE;
4638 goto error_addba_rsp;
4639 } else if (DOT11F_WARNED(status)) {
Srinivas Girigowda28fb0122017-03-26 22:21:20 -07004640 pe_warn("There were warnings while packing ADDBA Response (0x%08x)",
Krishna Kumaar Natarajan48a6b4c2017-01-06 16:30:55 -08004641 status);
4642 }
4643
4644
4645 if ((SIR_BAND_5_GHZ == lim_get_rf_band(session->currentOperChannel))
4646#ifdef WLAN_FEATURE_P2P
4647 || (session->pePersona == QDF_P2P_CLIENT_MODE) ||
4648 (session->pePersona == QDF_P2P_GO_MODE)
4649#endif
4650 ) {
4651 tx_flag |= HAL_USE_BD_RATE2_FOR_MANAGEMENT_FRAME;
4652 }
4653
4654 MTRACE(qdf_trace(QDF_MODULE_ID_PE, TRACE_CODE_TX_MGMT,
4655 session->peSessionId, mgmt_hdr->fc.subType));
4656 qdf_status = wma_tx_frame(mac_ctx, pkt_ptr, (uint16_t) num_bytes,
4657 TXRX_FRM_802_11_MGMT, ANI_TXDIR_TODS, 7,
4658 lim_tx_complete, frame_ptr, tx_flag, sme_sessionid, 0);
4659 MTRACE(qdf_trace(QDF_MODULE_ID_PE, TRACE_CODE_TX_COMPLETE,
4660 session->peSessionId, qdf_status));
4661 if (QDF_STATUS_SUCCESS != qdf_status) {
Srinivas Girigowda28fb0122017-03-26 22:21:20 -07004662 pe_err("wma_tx_frame FAILED! Status [%d]",
Krishna Kumaar Natarajan48a6b4c2017-01-06 16:30:55 -08004663 qdf_status);
4664 qdf_status = QDF_STATUS_E_FAILURE;
4665 /*
4666 * wma_tx_frame free memory in certain cases, free pkt_ptr
4667 * only if not freed already.
4668 */
4669 if (pkt_ptr)
4670 cds_packet_free((void *)pkt_ptr);
4671 return qdf_status;
4672 } else {
4673 return eSIR_SUCCESS;
4674 }
4675
4676error_addba_rsp:
4677 cds_packet_free((void *)pkt_ptr);
4678 return qdf_status;
4679}