blob: 3c6b59b2327ee2c5c4b4bc9d64339a887f14b65a [file] [log] [blame]
Jeff Johnson295189b2012-06-20 16:38:30 -07001/*
Gopichand Nakkala92f07d82013-01-08 21:16:34 -08002 * Copyright (c) 2012-2013, The Linux Foundation. All rights reserved.
3 *
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/*
Jeff Johnson32d95a32012-09-10 13:15:23 -070022 * Copyright (c) 2012, The Linux Foundation. All rights reserved.
Jeff Johnson295189b2012-06-20 16:38:30 -070023 *
24 * Previously licensed under the ISC license by Qualcomm Atheros, Inc.
25 *
26 *
27 * Permission to use, copy, modify, and/or distribute this software for
28 * any purpose with or without fee is hereby granted, provided that the
29 * above copyright notice and this permission notice appear in all
30 * copies.
31 *
32 * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL
33 * WARRANTIES WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED
34 * WARRANTIES OF MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE
35 * AUTHOR BE LIABLE FOR ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL
36 * DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR
37 * PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER
38 * TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR
39 * PERFORMANCE OF THIS SOFTWARE.
40 */
41
42/**========================================================================
43
44 \file wlan_hdd_hostapd.c
45 \brief WLAN Host Device Driver implementation
46
47 Copyright 2008 (c) Qualcomm, Incorporated. All Rights Reserved.
48
49 Qualcomm Confidential and Proprietary.
50
51 ========================================================================*/
52/**=========================================================================
53 EDIT HISTORY FOR FILE
54
55
56 This section contains comments describing changes made to the module.
57 Notice that changes are listed in reverse chronological order.
58
59 $Header:$ $DateTime: $ $Author: $
60
61
62 when who what, where, why
63 -------- --- --------------------------------------------------------
64 04/5/09 Shailender Created module.
65 06/03/10 js - Added support to hostapd driven deauth/disassoc/mic failure
66 ==========================================================================*/
67/*--------------------------------------------------------------------------
68 Include Files
69 ------------------------------------------------------------------------*/
70
71#include <linux/version.h>
72#include <linux/module.h>
73#include <linux/kernel.h>
74#include <linux/init.h>
75#include <linux/wireless.h>
76#include <linux/semaphore.h>
77#include <vos_api.h>
78#include <vos_sched.h>
79#include <linux/etherdevice.h>
80#include <wlan_hdd_includes.h>
81#include <qc_sap_ioctl.h>
82#include <wlan_hdd_hostapd.h>
83#include <sapApi.h>
84#include <sapInternal.h>
85#include <wlan_qct_tl.h>
86#include <wlan_hdd_softap_tx_rx.h>
87#include <wlan_hdd_main.h>
88#include <linux/netdevice.h>
89#include <linux/mmc/sdio_func.h>
90#include "wlan_nlink_common.h"
91#include "wlan_btc_svc.h"
92#include <bap_hdd_main.h>
Jeff Johnson295189b2012-06-20 16:38:30 -070093#include "wlan_hdd_p2p.h"
Leo Chang614d2072013-08-22 14:59:44 -070094#include "cfgApi.h"
95#include "wniCfgAp.h"
Jeff Johnson295189b2012-06-20 16:38:30 -070096
97#define IS_UP(_dev) \
98 (((_dev)->flags & (IFF_RUNNING|IFF_UP)) == (IFF_RUNNING|IFF_UP))
99#define IS_UP_AUTO(_ic) \
100 (IS_UP((_ic)->ic_dev) && (_ic)->ic_roaming == IEEE80211_ROAMING_AUTO)
101#define WE_WLAN_VERSION 1
102#define STATS_CONTEXT_MAGIC 0x53544154
Yathish Hanumapuradoddi Shivanna7b659402013-03-25 14:12:32 -0700103#define WE_GET_STA_INFO_SIZE 30
104/* WEXT limition: MAX allowed buf len for any *
105 * IW_PRIV_TYPE_CHAR is 2Kbytes *
106 */
107#define WE_SAP_MAX_STA_INFO 0x7FF
Jeff Johnson295189b2012-06-20 16:38:30 -0700108
Jeff Johnson295189b2012-06-20 16:38:30 -0700109#define SAP_24GHZ_CH_COUNT (14)
Leo Chang614d2072013-08-22 14:59:44 -0700110
111#define SAP_MAX_GET_ASSOC_STAS_TIMEOUT 500
112/* Max possible supported rate count
113 * Legacy 14 + 11N MCS 8 + 11AC MCS 10 */
114#define SAP_MAX_SUPPORTED_RATE_COUNT 32
115#define SAP_LEGACY_RATE_MASK 0x007F
116#define SAP_GET_STAS_RATE_TIMEOUT 1000
117#define SAP_AC_MCS_MAP_MASK 0x03
118#define SAP_AC_MCS_MAP_OFFSET 7
119
120#define SAP_LEGACY_RATE_COUNT SIR_NUM_11B_RATES + SIR_NUM_11A_RATES
121#define SAP_11N_RATE_COUNT 8
122
123#define SAP_RATE_SUPPORT_MAP_LEGACY_MASK 0x0001
124#define SAP_RATE_SUPPORT_MAP_N_MASK 0x001E
125#define SAP_RATE_SUPPORT_MAP_AC_MASK 0x07E0
126
127#define SAP_MAX_24_CHANNEL_NUMBER 14
128#define SAP_GET_STAS_COOKIE 0xC000C1EE
129
130/* Temp put here, will locate correct location
131 * work on progress with UMAC */
132/* Should syn with FW definition */
133typedef enum
134{
135 WNI_CFG_FIXED_RATE_SAP_AUTO,
136 WNI_CFG_FIXED_RATE_11B_LONG_1_MBPS,
137 WNI_CFG_FIXED_RATE_11B_LONG_2_MBPS,
138 WNI_CFG_FIXED_RATE_11B_LONG_5_5_MBPS,
139 WNI_CFG_FIXED_RATE_11B_LONG_11_MBPS,
140 WNI_CFG_FIXED_RATE_11A_6_MBPS,
141 WNI_CFG_FIXED_RATE_11A_9_MBPS,
142 WNI_CFG_FIXED_RATE_11A_12_MBPS,
143 WNI_CFG_FIXED_RATE_11A_18_MBPS,
144 WNI_CFG_FIXED_RATE_11A_24_MBPS,
145 WNI_CFG_FIXED_RATE_11A_36_MBPS,
146 WNI_CFG_FIXED_RATE_11A_48_MBPS,
147 WNI_CFG_FIXED_RATE_11A_54_MBPS,
148 WNI_CFG_FIXED_RATE_MCS_1NSS_MM_6_5_MBPS,
149 WNI_CFG_FIXED_RATE_MCS_1NSS_MM_13_MBPS,
150 WNI_CFG_FIXED_RATE_MCS_1NSS_MM_19_5_MBPS,
151 WNI_CFG_FIXED_RATE_MCS_1NSS_MM_26_MBPS,
152 WNI_CFG_FIXED_RATE_MCS_1NSS_MM_39_MBPS,
153 WNI_CFG_FIXED_RATE_MCS_1NSS_MM_52_MBPS,
154 WNI_CFG_FIXED_RATE_MCS_1NSS_MM_58_5_MBPS,
155 WNI_CFG_FIXED_RATE_MCS_1NSS_MM_65_MBPS,
156 WNI_CFG_FIXED_RATE_MCS_1NSS_MM_SG_7_2_MBPS,
157 WNI_CFG_FIXED_RATE_MCS_1NSS_MM_SG_14_4_MBPS,
158 WNI_CFG_FIXED_RATE_MCS_1NSS_MM_SG_21_7_MBPS,
159 WNI_CFG_FIXED_RATE_MCS_1NSS_MM_SG_28_9_MBPS,
160 WNI_CFG_FIXED_RATE_MCS_1NSS_MM_SG_43_3_MBPS,
161 WNI_CFG_FIXED_RATE_MCS_1NSS_MM_SG_57_8_MBPS,
162 WNI_CFG_FIXED_RATE_MCS_1NSS_MM_SG_65_MBPS,
163 WNI_CFG_FIXED_RATE_MCS_1NSS_MM_SG_72_2_MBPS,
164 WNI_CFG_FIXED_RATE_MCS_40MHZ_1NSS_MM_13_5_MBPS,
165 WNI_CFG_FIXED_RATE_MCS_40MHZ_1NSS_MM_27_MBPS, /* 30 */
166 WNI_CFG_FIXED_RATE_MCS_40MHZ_1NSS_MM_40_5_MBPS,
167 WNI_CFG_FIXED_RATE_MCS_40MHZ_1NSS_MM_54_MBPS,
168 WNI_CFG_FIXED_RATE_MCS_40MHZ_1NSS_MM_81_MBPS,
169 WNI_CFG_FIXED_RATE_MCS_40MHZ_1NSS_MM_108_MBPS,
170 WNI_CFG_FIXED_RATE_MCS_40MHZ_1NSS_MM_121_5_MBPS,
171 WNI_CFG_FIXED_RATE_MCS_40MHZ_1NSS_MM_135_MBPS,
172 WNI_CFG_FIXED_RATE_MCS_40MHZ_1NSS_MM_SG_15_MBPS,
173 WNI_CFG_FIXED_RATE_MCS_40MHZ_1NSS_MM_SG_30_MBPS,
174 WNI_CFG_FIXED_RATE_MCS_40MHZ_1NSS_MM_SG_45_MBPS,
175 WNI_CFG_FIXED_RATE_MCS_40MHZ_1NSS_MM_SG_60_MBPS,
176 WNI_CFG_FIXED_RATE_MCS_40MHZ_1NSS_MM_SG_90_MBPS,
177 WNI_CFG_FIXED_RATE_MCS_40MHZ_1NSS_MM_SG_120_MBPS,
178 WNI_CFG_FIXED_RATE_MCS_40MHZ_1NSS_MM_SG_135_MBPS,
179 WNI_CFG_FIXED_RATE_MCS_40MHZ_1NSS_MM_SG_150_MBPS,
180 WNI_CFG_FIXED_RATE_MCS_40MHZ_1NSS_GF_13_5_MBPS,
181 WNI_CFG_FIXED_RATE_MCS_40MHZ_1NSS_GF_27_MBPS,
182 WNI_CFG_FIXED_RATE_MCS_40MHZ_1NSS_GF_40_5_MBPS,
183 WNI_CFG_FIXED_RATE_MCS_40MHZ_1NSS_GF_54_MBPS,
184 WNI_CFG_FIXED_RATE_MCS_40MHZ_1NSS_GF_81_MBPS,
185 WNI_CFG_FIXED_RATE_MCS_40MHZ_1NSS_GF_108_MBPS,
186 WNI_CFG_FIXED_RATE_MCS_40MHZ_1NSS_GF_121_5_MBPS,
187 WNI_CFG_FIXED_RATE_MCS_40MHZ_1NSS_GF_135_MBPS,
188 WNI_CFG_FIXED_RATE_VHT_SIMO_CB_NGI_6_5MBPS,
189 WNI_CFG_FIXED_RATE_VHT_SIMO_CB_NGI_13MBPS,
190 WNI_CFG_FIXED_RATE_VHT_SIMO_CB_NGI_19_5MBPS,
191 WNI_CFG_FIXED_RATE_VHT_SIMO_CB_NGI_26MBPS,
192 WNI_CFG_FIXED_RATE_VHT_SIMO_CB_NGI_39MBPS,
193 WNI_CFG_FIXED_RATE_VHT_SIMO_CB_NGI_52MBPS,
194 WNI_CFG_FIXED_RATE_VHT_SIMO_CB_NGI_58_5MBPS,
195 WNI_CFG_FIXED_RATE_VHT_SIMO_CB_NGI_65MBPS, /* 60 */
196 WNI_CFG_FIXED_RATE_VHT_SIMO_CB_NGI_78MBPS,
197 WNI_CFG_FIXED_RATE_VHT_SIMO_CB_NGI_86_5_MBPS,
198 WNI_CFG_FIXED_RATE_VHT_SIMO_CB_SGI_21_667MBPS,
199 WNI_CFG_FIXED_RATE_VHT_SIMO_CB_SGI_28_889MBPS,
200 WNI_CFG_FIXED_RATE_VHT_SIMO_CB_SGI_43_333MBPS,
201 WNI_CFG_FIXED_RATE_VHT_SIMO_CB_SGI_57_778MBPS,
202 WNI_CFG_FIXED_RATE_VHT_SIMO_CB_SGI_65MBPS,
203 WNI_CFG_FIXED_RATE_VHT_SIMO_CB_SGI_72_222MBPS,
204 WNI_CFG_FIXED_RATE_VHT_SIMO_CB_SGI_86_667MBPS,
205 WNI_CFG_FIXED_RATE_VHT_SIMO_CB_SGI_96_1_MBPS,
206 WNI_CFG_FIXED_RATE_VHT_40MHZ_SIMO_CB_NGI_13_5MBPS,
207 WNI_CFG_FIXED_RATE_VHT_40MHZ_SIMO_CB_NGI_27MBPS,
208 WNI_CFG_FIXED_RATE_VHT_40MHZ_SIMO_CB_NGI_40_5MBPS,
209 WNI_CFG_FIXED_RATE_VHT_40MHZ_SIMO_CB_NGI_54MBPS,
210 WNI_CFG_FIXED_RATE_VHT_40MHZ_SIMO_CB_NGI_81MBPS,
211 WNI_CFG_FIXED_RATE_VHT_40MHZ_SIMO_CB_NGI_108MBPS,
212 WNI_CFG_FIXED_RATE_VHT_40MHZ_SIMO_CB_NGI_121_5MBPS,
213 WNI_CFG_FIXED_RATE_VHT_40MHZ_SIMO_CB_NGI_135MBPS,
214 WNI_CFG_FIXED_RATE_VHT_40MHZ_SIMO_CB_NGI_RESERVED,
215 WNI_CFG_FIXED_RATE_VHT_40MHZ_SIMO_CB_NGI_162MBPS,
216 WNI_CFG_FIXED_RATE_VHT_40MHZ_SIMO_CB_NGI_180MBPS,
217 WNI_CFG_FIXED_RATE_VHT_40MHZ_SIMO_CB_SGI_15MBPS,
218 WNI_CFG_FIXED_RATE_VHT_40MHZ_SIMO_CB_SGI_30MBPS,
219 WNI_CFG_FIXED_RATE_VHT_40MHZ_SIMO_CB_SGI_45MBPS,
220 WNI_CFG_FIXED_RATE_VHT_40MHZ_SIMO_CB_SGI_60MBPS,
221 WNI_CFG_FIXED_RATE_VHT_40MHZ_SIMO_CB_SGI_90MBPS,
222 WNI_CFG_FIXED_RATE_VHT_40MHZ_SIMO_CB_SGI_120MBPS,
223 WNI_CFG_FIXED_RATE_VHT_40MHZ_SIMO_CB_SGI_135MBPS,
224 WNI_CFG_FIXED_RATE_VHT_40MHZ_SIMO_CB_SGI_150MBPS,
225 WNI_CFG_FIXED_RATE_VHT_40MHZ_SIMO_CB_SGI_RESERVED, /* 90 */
226 WNI_CFG_FIXED_RATE_VHT_40MHZ_SIMO_CB_SGI_180MBPS,
227 WNI_CFG_FIXED_RATE_VHT_40MHZ_SIMO_CB_SGI_200MBPS,
228 WNI_CFG_FIXED_RATE_VHT_80MHZ_SIMO_CB_NGI_29_25MBPS,
229 WNI_CFG_FIXED_RATE_VHT_80MHZ_SIMO_CB_NGI_58_5MBPS,
230 WNI_CFG_FIXED_RATE_VHT_80MHZ_SIMO_CB_NGI_87_75MBPS,
231 WNI_CFG_FIXED_RATE_VHT_80MHZ_SIMO_CB_NGI_117MBPS,
232 WNI_CFG_FIXED_RATE_VHT_80MHZ_SIMO_CB_NGI_175_5MBPS,
233 WNI_CFG_FIXED_RATE_VHT_80MHZ_SIMO_CB_NGI_234MBPS,
234 WNI_CFG_FIXED_RATE_VHT_80MHZ_SIMO_CB_NGI_263_25MBPS,
235 WNI_CFG_FIXED_RATE_VHT_80MHZ_SIMO_CB_NGI_292_5MBPS,
236 WNI_CFG_FIXED_RATE_VHT_80MHZ_SIMO_CB_NGI_RESERVED,
237 WNI_CFG_FIXED_RATE_VHT_80MHZ_SIMO_CB_NGI_351MBPS,
238 WNI_CFG_FIXED_RATE_VHT_80MHZ_SIMO_CB_NGI_390MBPS,
239 WNI_CFG_FIXED_RATE_VHT_80MHZ_SIMO_CB_SGI_32_5MBPS,
240 WNI_CFG_FIXED_RATE_VHT_80MHZ_SIMO_CB_SGI_65MBPS,
241 WNI_CFG_FIXED_RATE_VHT_80MHZ_SIMO_CB_SGI_97_5MBPS,
242 WNI_CFG_FIXED_RATE_VHT_80MHZ_SIMO_CB_SGI_130MBPS,
243 WNI_CFG_FIXED_RATE_VHT_80MHZ_SIMO_CB_SGI_195MBPS,
244 WNI_CFG_FIXED_RATE_VHT_80MHZ_SIMO_CB_SGI_260MBPS,
245 WNI_CFG_FIXED_RATE_VHT_80MHZ_SIMO_CB_SGI_292_5MBPS,
246 WNI_CFG_FIXED_RATE_VHT_80MHZ_SIMO_CB_SGI_325MBPS,
247 WNI_CFG_FIXED_RATE_VHT_80MHZ_SIMO_CB_SGI_RESERVED,
248 WNI_CFG_FIXED_RATE_VHT_80MHZ_SIMO_CB_SGI_390MBPS,
249 WNI_CFG_FIXED_RATE_VHT_80MHZ_SIMO_CB_SGI_433_33MBPS,
250 WNI_CFG_LDPC_FIXED_RATE_VHT_SIMO_CB_NGI_6_5MBPS,
251 WNI_CFG_LDPC_FIXED_RATE_VHT_SIMO_CB_NGI_13MBPS,
252 WNI_CFG_LDPC_FIXED_RATE_VHT_SIMO_CB_NGI_19_5MBPS,
253 WNI_CFG_LDPC_FIXED_RATE_VHT_SIMO_CB_NGI_26MBPS,
254 WNI_CFG_LDPC_FIXED_RATE_VHT_SIMO_CB_NGI_39MBPS,
255 WNI_CFG_LDPC_FIXED_RATE_VHT_SIMO_CB_NGI_52MBPS, /* 120 */
256 WNI_CFG_LDPC_FIXED_RATE_VHT_SIMO_CB_NGI_58_5MBPS,
257 WNI_CFG_LDPC_FIXED_RATE_VHT_SIMO_CB_NGI_65MBPS,
258 WNI_CFG_LDPC_FIXED_RATE_VHT_SIMO_CB_NGI_78MBPS,
259 WNI_CFG_LDPC_FIXED_RATE_VHT_SIMO_CB_NGI_86_5_MBPS,
260 WNI_CFG_LDPC_FIXED_RATE_VHT_SIMO_CB_SGI_7_2222MBPS,
261 WNI_CFG_LDPC_FIXED_RATE_VHT_SIMO_CB_SGI_14_444MBPS,
262 WNI_CFG_LDPC_FIXED_RATE_VHT_SIMO_CB_SGI_21_667MBPS,
263 WNI_CFG_LDPC_FIXED_RATE_VHT_SIMO_CB_SGI_28_889MBPS,
264 WNI_CFG_LDPC_FIXED_RATE_VHT_SIMO_CB_SGI_43_333MBPS,
265 WNI_CFG_LDPC_FIXED_RATE_VHT_SIMO_CB_SGI_57_778MBPS,
266 WNI_CFG_LDPC_FIXED_RATE_VHT_SIMO_CB_SGI_65MBPS,
267 WNI_CFG_LDPC_FIXED_RATE_VHT_SIMO_CB_SGI_72_222MBPS,
268 WNI_CFG_LDPC_FIXED_RATE_VHT_SIMO_CB_SGI_86_667MBPS,
269 WNI_CFG_LDPC_FIXED_RATE_VHT_SIMO_CB_SGI_96_1_MBPS,
270 WNI_CFG_LDPC_FIXED_RATE_VHT_40MHZ_SIMO_CB_NGI_13_5MBPS,
271 WNI_CFG_LDPC_FIXED_RATE_VHT_40MHZ_SIMO_CB_NGI_27MBPS,
272 WNI_CFG_LDPC_FIXED_RATE_VHT_40MHZ_SIMO_CB_NGI_40_5MBPS,
273 WNI_CFG_LDPC_FIXED_RATE_VHT_40MHZ_SIMO_CB_NGI_54MBPS,
274 WNI_CFG_LDPC_FIXED_RATE_VHT_40MHZ_SIMO_CB_NGI_81MBPS,
275 WNI_CFG_LDPC_FIXED_RATE_VHT_40MHZ_SIMO_CB_NGI_108MBPS,
276 WNI_CFG_LDPC_FIXED_RATE_VHT_40MHZ_SIMO_CB_NGI_121_5MBPS,
277 WNI_CFG_LDPC_FIXED_RATE_VHT_40MHZ_SIMO_CB_NGI_135MBPS,
278 WNI_CFG_LDPC_FIXED_RATE_VHT_40MHZ_SIMO_CB_NGI_RESERVED,
279 WNI_CFG_LDPC_FIXED_RATE_VHT_40MHZ_SIMO_CB_NGI_162MBPS,
280 WNI_CFG_LDPC_FIXED_RATE_VHT_40MHZ_SIMO_CB_NGI_180MBPS,
281 WNI_CFG_LDPC_FIXED_RATE_VHT_40MHZ_SIMO_CB_SGI_15MBPS,
282 WNI_CFG_LDPC_FIXED_RATE_VHT_40MHZ_SIMO_CB_SGI_30MBPS,
283 WNI_CFG_LDPC_FIXED_RATE_VHT_40MHZ_SIMO_CB_SGI_45MBPS,
284 WNI_CFG_LDPC_FIXED_RATE_VHT_40MHZ_SIMO_CB_SGI_60MBPS,
285 WNI_CFG_LDPC_FIXED_RATE_VHT_40MHZ_SIMO_CB_SGI_90MBPS, /* 150 */
286 WNI_CFG_LDPC_FIXED_RATE_VHT_40MHZ_SIMO_CB_SGI_120MBPS,
287 WNI_CFG_LDPC_FIXED_RATE_VHT_40MHZ_SIMO_CB_SGI_135MBPS,
288 WNI_CFG_LDPC_FIXED_RATE_VHT_40MHZ_SIMO_CB_SGI_150MBPS,
289 WNI_CFG_LDPC_FIXED_RATE_VHT_40MHZ_SIMO_CB_SGI_RESERVED,
290 WNI_CFG_LDPC_FIXED_RATE_VHT_40MHZ_SIMO_CB_SGI_180MBPS,
291 WNI_CFG_LDPC_FIXED_RATE_VHT_40MHZ_SIMO_CB_SGI_200MBPS,
292 WNI_CFG_LDPC_FIXED_RATE_VHT_80MHZ_SIMO_CB_NGI_29_25MBPS,
293 WNI_CFG_LDPC_FIXED_RATE_VHT_80MHZ_SIMO_CB_NGI_58_5MBPS,
294 WNI_CFG_LDPC_FIXED_RATE_VHT_80MHZ_SIMO_CB_NGI_87_75MBPS,
295 WNI_CFG_LDPC_FIXED_RATE_VHT_80MHZ_SIMO_CB_NGI_117MBPS,
296 WNI_CFG_LDPC_FIXED_RATE_VHT_80MHZ_SIMO_CB_NGI_175_5MBPS,
297 WNI_CFG_LDPC_FIXED_RATE_VHT_80MHZ_SIMO_CB_NGI_234MBPS,
298 WNI_CFG_LDPC_FIXED_RATE_VHT_80MHZ_SIMO_CB_NGI_263_25MBPS,
299 WNI_CFG_LDPC_FIXED_RATE_VHT_80MHZ_SIMO_CB_NGI_292_5MBPS,
300 WNI_CFG_LDPC_FIXED_RATE_VHT_80MHZ_SIMO_CB_NGI_RESERVED,
301 WNI_CFG_LDPC_FIXED_RATE_VHT_80MHZ_SIMO_CB_NGI_351MBPS,
302 WNI_CFG_LDPC_FIXED_RATE_VHT_80MHZ_SIMO_CB_NGI_390MBPS,
303 WNI_CFG_LDPC_FIXED_RATE_VHT_80MHZ_SIMO_CB_SGI_32_5MBPS,
304 WNI_CFG_LDPC_FIXED_RATE_VHT_80MHZ_SIMO_CB_SGI_65MBPS,
305 WNI_CFG_LDPC_FIXED_RATE_VHT_80MHZ_SIMO_CB_SGI_97_5MBPS,
306 WNI_CFG_LDPC_FIXED_RATE_VHT_80MHZ_SIMO_CB_SGI_130MBPS,
307 WNI_CFG_LDPC_FIXED_RATE_VHT_80MHZ_SIMO_CB_SGI_195MBPS,
308 WNI_CFG_LDPC_FIXED_RATE_VHT_80MHZ_SIMO_CB_SGI_260MBPS,
309 WNI_CFG_LDPC_FIXED_RATE_VHT_80MHZ_SIMO_CB_SGI_292_5MBPS,
310 WNI_CFG_LDPC_FIXED_RATE_VHT_80MHZ_SIMO_CB_SGI_325MBPS,
311 WNI_CFG_LDPC_FIXED_RATE_VHT_80MHZ_SIMO_CB_SGI_RESERVED,
312 WNI_CFG_LDPC_FIXED_RATE_VHT_80MHZ_SIMO_CB_SGI_390MBPS,
313 WNI_CFG_LDPC_FIXED_RATE_VHT_80MHZ_SIMO_CB_SGI_433_33MBPS,
314 WNI_CFG_FIXED_RATE_11A_DUP_6_MBPS,
315 WNI_CFG_FIXED_RATE_11A_DUP_9_MBPS, /* 180 */
316 WNI_CFG_FIXED_RATE_11A_DUP_12_MBPS,
317 WNI_CFG_FIXED_RATE_11A_DUP_18_MBPS,
318 WNI_CFG_FIXED_RATE_11A_DUP_24_MBPS,
319 WNI_CFG_FIXED_RATE_11A_DUP_36_MBPS,
320 WNI_CFG_FIXED_RATE_11A_DUP_48_MBPS,
321 WNI_CFG_FIXED_RATE_11A_DUP_54_MBPS,
322 WNI_CFG_FIXED_RATE_11A_80MHZ_DUP_6_MBPS,
323 WNI_CFG_FIXED_RATE_11A_80MHZDUP_9_MBPS,
324 WNI_CFG_FIXED_RATE_11A_80MHZ_DUP_12_MBPS,
325 WNI_CFG_FIXED_RATE_11A_80MHZ_DUP_18_MBPS,
326 WNI_CFG_FIXED_RATE_11A_80MHZ_DUP_24_MBPS,
327 WNI_CFG_FIXED_RATE_11A_80MHZ_DUP_36_MBPS,
328 WNI_CFG_FIXED_RATE_11A_80MHZ_DUP_48_MBPS,
329 WNI_CFG_FIXED_RATE_11A_80MHZ_DUP_54_MBPS,
330 WNI_CFG_LDPC_FIXED_RATE_MCS_1NSS_MM_6_5_MBPS,
331 WNI_CFG_LDPC_FIXED_RATE_MCS_1NSS_MM_13_MBPS,
332 WNI_CFG_LDPC_FIXED_RATE_MCS_1NSS_MM_19_5_MBPS,
333 WNI_CFG_LDPC_FIXED_RATE_MCS_1NSS_MM_26_MBPS,
334 WNI_CFG_LDPC_FIXED_RATE_MCS_1NSS_MM_39_MBPS,
335 WNI_CFG_LDPC_FIXED_RATE_MCS_1NSS_MM_52_MBPS,
336 WNI_CFG_LDPC_FIXED_RATE_MCS_1NSS_MM_58_5_MBPS,
337 WNI_CFG_LDPC_FIXED_RATE_MCS_1NSS_MM_65_MBPS,
338 WNI_CFG_LDPC_FIXED_RATE_MCS_1NSS_MM_SG_7_2_MBPS,
339 WNI_CFG_LDPC_FIXED_RATE_MCS_1NSS_MM_SG_14_4_MBPS,
340 WNI_CFG_LDPC_FIXED_RATE_MCS_1NSS_MM_SG_21_7_MBPS,
341 WNI_CFG_LDPC_FIXED_RATE_MCS_1NSS_MM_SG_28_9_MBPS,
342 WNI_CFG_LDPC_FIXED_RATE_MCS_1NSS_MM_SG_43_3_MBPS,
343 WNI_CFG_LDPC_FIXED_RATE_MCS_1NSS_MM_SG_57_8_MBPS,
344 WNI_CFG_LDPC_FIXED_RATE_MCS_1NSS_MM_SG_65_MBPS,
345 WNI_CFG_LDPC_FIXED_RATE_MCS_1NSS_MM_SG_72_2_MBPS, /* 210 */
346 WNI_CFG_LDPC_FIXED_RATE_MCS_40MHZ_1NSS_MM_13_5_MBPS,
347 WNI_CFG_LDPC_FIXED_RATE_MCS_40MHZ_1NSS_MM_27_MBPS,
348 WNI_CFG_LDPC_FIXED_RATE_MCS_40MHZ_1NSS_MM_40_5_MBPS,
349 WNI_CFG_LDPC_FIXED_RATE_MCS_40MHZ_1NSS_MM_54_MBPS,
350 WNI_CFG_LDPC_FIXED_RATE_MCS_40MHZ_1NSS_MM_81_MBPS,
351 WNI_CFG_LDPC_FIXED_RATE_MCS_40MHZ_1NSS_MM_108_MBPS,
352 WNI_CFG_LDPC_FIXED_RATE_MCS_40MHZ_1NSS_MM_121_5_MBPS,
353 WNI_CFG_LDPC_FIXED_RATE_MCS_40MHZ_1NSS_MM_135_MBPS,
354 WNI_CFG_LDPC_FIXED_RATE_MCS_40MHZ_1NSS_MM_SG_15_MBPS,
355 WNI_CFG_LDPC_FIXED_RATE_MCS_40MHZ_1NSS_MM_SG_30_MBPS,
356 WNI_CFG_LDPC_FIXED_RATE_MCS_40MHZ_1NSS_MM_SG_45_MBPS,
357 WNI_CFG_LDPC_FIXED_RATE_MCS_40MHZ_1NSS_MM_SG_60_MBPS,
358 WNI_CFG_LDPC_FIXED_RATE_MCS_40MHZ_1NSS_MM_SG_90_MBPS,
359 WNI_CFG_LDPC_FIXED_RATE_MCS_40MHZ_1NSS_MM_SG_120_MBPS,
360 WNI_CFG_LDPC_FIXED_RATE_MCS_40MHZ_1NSS_MM_SG_135_MBPS,
361 WNI_CFG_LDPC_FIXED_RATE_MCS_40MHZ_1NSS_MM_SG_150_MBPS
362} eCfgFixedRateCfgType;
363
364/* Legacy IDX based rate table */
365typedef struct
366{
367 v_U16_t legacy_rate_index;
368 v_U32_t legacy_rate;
369} supported_legacy_rate_t;
370static const supported_legacy_rate_t legacy_rate[] =
371{
372/* IDX Rate, 100kbps */
373 {2, 10},
374 {4, 20},
375 {11, 55},
376 {12, 60},
377 {18, 90},
378 {24, 120},
379 {36, 180},
380 {48, 240},
381 {66, 330},
382 {72, 360},
383 {96, 480},
384 {108, 540}
385};
386
387/* 11N MCS based rate table */
388typedef struct
389{
390 v_U8_t mcs_index_11n;
391 v_U32_t rate_11n[4];
392} supported_11n_rate_t;
393static const supported_11n_rate_t mcs_rate_11n[] =
394{
395/* MCS L20 L40 S20 S40 */
396 {0, {65, 135, 72, 150}},
397 {1, {130, 270, 144, 300}},
398 {2, {195, 405, 217, 450}},
399 {3, {260, 540, 289, 600}},
400 {4, {390, 810, 433, 900}},
401 {5, {520, 1080, 578, 1200}},
402 {6, {585, 1215, 650, 1350}},
403 {7, {650, 1350, 722, 1500}}
404};
405
406/* 11AC MCS based rate table */
407typedef struct
408{
409 v_U8_t mcs_index_11ac;
410 v_U16_t cb80_rate_11ac[2];
411 v_U16_t cb40_rate_11ac[2];
412 v_U16_t cb20_rate_11ac[2];
413} supported_11ac_rate_t;
414static const supported_11ac_rate_t mcs_rate_11ac[] =
415{
416/* MCS L80 S80 L40 S40 L20 S40*/
417 {0, {293, 325}, {135, 150}, {65, 72}},
418 {1, {585, 650}, {270, 300}, {130, 144}},
419 {2, {878, 975}, {405, 450}, {195, 217}},
420 {3, {1170, 1300}, {540, 600}, {260, 289}},
421 {4, {1755, 1950}, {810, 900}, {390, 433}},
422 {5, {2340, 2600}, {1080, 1200}, {520, 578}},
423 {6, {2633, 2925}, {1215, 1350}, {585, 650}},
424 {7, {2925, 3250}, {1350, 1500}, {650, 722}},
425 {8, {3510, 3900}, {1620, 1800}, {780, 867}},
426 {9, {3900, 4333}, {1800, 2000}, {860, 867}}
427};
428
429typedef struct
430{
431 eCfgFixedRateCfgType eRateCfg;
432 v_U16_t rate;
433} rate_cfg_item_mapping_t;
434
435static rate_cfg_item_mapping_t legacy_rate_mapping[] =
436{
437 {WNI_CFG_FIXED_RATE_11B_LONG_1_MBPS, 10},
438 {WNI_CFG_FIXED_RATE_11B_LONG_2_MBPS, 20},
439 {WNI_CFG_FIXED_RATE_11B_LONG_5_5_MBPS, 55},
440 {WNI_CFG_FIXED_RATE_11B_LONG_11_MBPS, 110},
441 {WNI_CFG_FIXED_RATE_11A_6_MBPS, 60},
442 {WNI_CFG_FIXED_RATE_11A_9_MBPS, 90},
443 {WNI_CFG_FIXED_RATE_11A_12_MBPS, 120},
444 {WNI_CFG_FIXED_RATE_11A_18_MBPS, 180},
445 {WNI_CFG_FIXED_RATE_11A_24_MBPS, 240},
446 {WNI_CFG_FIXED_RATE_11A_36_MBPS, 360},
447 {WNI_CFG_FIXED_RATE_11A_48_MBPS, 480},
448 {WNI_CFG_FIXED_RATE_11A_54_MBPS, 540}
449};
450static rate_cfg_item_mapping_t n_l20_rate_mapping[] =
451{
452 {WNI_CFG_FIXED_RATE_MCS_1NSS_MM_6_5_MBPS, 65},
453 {WNI_CFG_FIXED_RATE_MCS_1NSS_MM_13_MBPS, 130},
454 {WNI_CFG_FIXED_RATE_MCS_1NSS_MM_19_5_MBPS, 195},
455 {WNI_CFG_FIXED_RATE_MCS_1NSS_MM_26_MBPS, 260},
456 {WNI_CFG_FIXED_RATE_MCS_1NSS_MM_39_MBPS, 390},
457 {WNI_CFG_FIXED_RATE_MCS_1NSS_MM_52_MBPS, 520},
458 {WNI_CFG_FIXED_RATE_MCS_1NSS_MM_58_5_MBPS, 585},
459 {WNI_CFG_FIXED_RATE_MCS_1NSS_MM_65_MBPS, 650}
460};
461static rate_cfg_item_mapping_t n_s20_rate_mapping[] =
462{
463 {WNI_CFG_FIXED_RATE_MCS_1NSS_MM_SG_7_2_MBPS, 72},
464 {WNI_CFG_FIXED_RATE_MCS_1NSS_MM_SG_14_4_MBPS, 144},
465 {WNI_CFG_FIXED_RATE_MCS_1NSS_MM_SG_21_7_MBPS, 217},
466 {WNI_CFG_FIXED_RATE_MCS_1NSS_MM_SG_28_9_MBPS, 289},
467 {WNI_CFG_FIXED_RATE_MCS_1NSS_MM_SG_43_3_MBPS, 433},
468 {WNI_CFG_FIXED_RATE_MCS_1NSS_MM_SG_57_8_MBPS, 578},
469 {WNI_CFG_FIXED_RATE_MCS_1NSS_MM_SG_65_MBPS, 650},
470 {WNI_CFG_FIXED_RATE_MCS_1NSS_MM_SG_72_2_MBPS, 722}
471};
472static rate_cfg_item_mapping_t n_l40_rate_mapping[] =
473{
474 {WNI_CFG_FIXED_RATE_MCS_40MHZ_1NSS_MM_13_5_MBPS, 135},
475 {WNI_CFG_FIXED_RATE_MCS_40MHZ_1NSS_MM_27_MBPS, 270},
476 {WNI_CFG_FIXED_RATE_MCS_40MHZ_1NSS_MM_40_5_MBPS, 405},
477 {WNI_CFG_FIXED_RATE_MCS_40MHZ_1NSS_MM_54_MBPS, 540},
478 {WNI_CFG_FIXED_RATE_MCS_40MHZ_1NSS_MM_81_MBPS, 810},
479 {WNI_CFG_FIXED_RATE_MCS_40MHZ_1NSS_MM_108_MBPS, 1080},
480 {WNI_CFG_FIXED_RATE_MCS_40MHZ_1NSS_MM_121_5_MBPS, 1215},
481 {WNI_CFG_FIXED_RATE_MCS_40MHZ_1NSS_MM_135_MBPS, 1350}
482};
483static rate_cfg_item_mapping_t n_s40_rate_mapping[] =
484{
485 {WNI_CFG_FIXED_RATE_MCS_40MHZ_1NSS_MM_SG_15_MBPS, 150},
486 {WNI_CFG_FIXED_RATE_MCS_40MHZ_1NSS_MM_SG_30_MBPS, 300},
487 {WNI_CFG_FIXED_RATE_MCS_40MHZ_1NSS_MM_SG_45_MBPS, 450},
488 {WNI_CFG_FIXED_RATE_MCS_40MHZ_1NSS_MM_SG_60_MBPS, 600},
489 {WNI_CFG_FIXED_RATE_MCS_40MHZ_1NSS_MM_SG_90_MBPS, 900},
490 {WNI_CFG_FIXED_RATE_MCS_40MHZ_1NSS_MM_SG_120_MBPS, 1200},
491 {WNI_CFG_FIXED_RATE_MCS_40MHZ_1NSS_MM_SG_135_MBPS, 1350},
492 {WNI_CFG_FIXED_RATE_MCS_40MHZ_1NSS_MM_SG_150_MBPS, 1500}
493};
494
495#ifdef WLAN_FEATURE_11AC
496static rate_cfg_item_mapping_t ac_l20_rate_mapping[] =
497{
498 {WNI_CFG_LDPC_FIXED_RATE_VHT_SIMO_CB_NGI_6_5MBPS, 65},
499 {WNI_CFG_LDPC_FIXED_RATE_VHT_SIMO_CB_NGI_13MBPS, 130},
500 {WNI_CFG_LDPC_FIXED_RATE_VHT_SIMO_CB_NGI_19_5MBPS, 195},
501 {WNI_CFG_LDPC_FIXED_RATE_VHT_SIMO_CB_NGI_26MBPS, 260},
502 {WNI_CFG_LDPC_FIXED_RATE_VHT_SIMO_CB_NGI_39MBPS, 390},
503 {WNI_CFG_LDPC_FIXED_RATE_VHT_SIMO_CB_NGI_52MBPS, 520},
504 {WNI_CFG_LDPC_FIXED_RATE_VHT_SIMO_CB_NGI_58_5MBPS, 585},
505 {WNI_CFG_LDPC_FIXED_RATE_VHT_SIMO_CB_NGI_65MBPS, 650},
506 {WNI_CFG_LDPC_FIXED_RATE_VHT_SIMO_CB_NGI_78MBPS, 780},
507 {WNI_CFG_LDPC_FIXED_RATE_VHT_SIMO_CB_NGI_86_5_MBPS, 865}
508};
509static rate_cfg_item_mapping_t ac_s20_rate_mapping[] =
510{
511 {WNI_CFG_LDPC_FIXED_RATE_VHT_SIMO_CB_SGI_7_2222MBPS, 72},
512 {WNI_CFG_LDPC_FIXED_RATE_VHT_SIMO_CB_SGI_14_444MBPS, 144},
513 {WNI_CFG_LDPC_FIXED_RATE_VHT_SIMO_CB_SGI_21_667MBPS, 217},
514 {WNI_CFG_LDPC_FIXED_RATE_VHT_SIMO_CB_SGI_28_889MBPS, 289},
515 {WNI_CFG_LDPC_FIXED_RATE_VHT_SIMO_CB_SGI_43_333MBPS, 433},
516 {WNI_CFG_LDPC_FIXED_RATE_VHT_SIMO_CB_SGI_57_778MBPS, 578},
517 {WNI_CFG_LDPC_FIXED_RATE_VHT_SIMO_CB_SGI_65MBPS, 650},
518 {WNI_CFG_LDPC_FIXED_RATE_VHT_SIMO_CB_SGI_72_222MBPS, 722},
519 {WNI_CFG_LDPC_FIXED_RATE_VHT_SIMO_CB_SGI_86_667MBPS, 867},
520 {WNI_CFG_LDPC_FIXED_RATE_VHT_SIMO_CB_SGI_96_1_MBPS, 961}
521};
522static rate_cfg_item_mapping_t ac_l40_rate_mapping[] =
523{
524 {WNI_CFG_LDPC_FIXED_RATE_VHT_40MHZ_SIMO_CB_NGI_13_5MBPS, 135},
525 {WNI_CFG_LDPC_FIXED_RATE_VHT_40MHZ_SIMO_CB_NGI_27MBPS, 270},
526 {WNI_CFG_LDPC_FIXED_RATE_VHT_40MHZ_SIMO_CB_NGI_40_5MBPS, 405},
527 {WNI_CFG_LDPC_FIXED_RATE_VHT_40MHZ_SIMO_CB_NGI_54MBPS, 540},
528 {WNI_CFG_LDPC_FIXED_RATE_VHT_40MHZ_SIMO_CB_NGI_81MBPS, 810},
529 {WNI_CFG_LDPC_FIXED_RATE_VHT_40MHZ_SIMO_CB_NGI_108MBPS, 1080},
530 {WNI_CFG_LDPC_FIXED_RATE_VHT_40MHZ_SIMO_CB_NGI_121_5MBPS, 1215},
531 {WNI_CFG_LDPC_FIXED_RATE_VHT_40MHZ_SIMO_CB_NGI_135MBPS, 1350},
532 {WNI_CFG_LDPC_FIXED_RATE_VHT_40MHZ_SIMO_CB_NGI_162MBPS, 1620},
533 {WNI_CFG_LDPC_FIXED_RATE_VHT_40MHZ_SIMO_CB_NGI_180MBPS, 1800}
534};
535static rate_cfg_item_mapping_t ac_s40_rate_mapping[] =
536{
537 {WNI_CFG_LDPC_FIXED_RATE_VHT_40MHZ_SIMO_CB_SGI_15MBPS, 150},
538 {WNI_CFG_LDPC_FIXED_RATE_VHT_40MHZ_SIMO_CB_SGI_30MBPS, 300},
539 {WNI_CFG_LDPC_FIXED_RATE_VHT_40MHZ_SIMO_CB_SGI_45MBPS, 450},
540 {WNI_CFG_LDPC_FIXED_RATE_VHT_40MHZ_SIMO_CB_SGI_60MBPS, 600},
541 {WNI_CFG_LDPC_FIXED_RATE_VHT_40MHZ_SIMO_CB_SGI_90MBPS, 900},
542 {WNI_CFG_LDPC_FIXED_RATE_VHT_40MHZ_SIMO_CB_SGI_120MBPS, 1200},
543 {WNI_CFG_LDPC_FIXED_RATE_VHT_40MHZ_SIMO_CB_SGI_135MBPS, 1350},
544 {WNI_CFG_LDPC_FIXED_RATE_VHT_40MHZ_SIMO_CB_SGI_150MBPS, 1500},
545 {WNI_CFG_LDPC_FIXED_RATE_VHT_40MHZ_SIMO_CB_SGI_180MBPS, 1800},
546 {WNI_CFG_LDPC_FIXED_RATE_VHT_40MHZ_SIMO_CB_SGI_200MBPS, 2000}
547};
548static rate_cfg_item_mapping_t ac_l80_rate_mapping[] =
549{
550 {WNI_CFG_LDPC_FIXED_RATE_VHT_80MHZ_SIMO_CB_NGI_29_25MBPS, 293},
551 {WNI_CFG_LDPC_FIXED_RATE_VHT_80MHZ_SIMO_CB_NGI_58_5MBPS, 585},
552 {WNI_CFG_LDPC_FIXED_RATE_VHT_80MHZ_SIMO_CB_NGI_87_75MBPS, 878},
553 {WNI_CFG_LDPC_FIXED_RATE_VHT_80MHZ_SIMO_CB_NGI_117MBPS, 1170},
554 {WNI_CFG_LDPC_FIXED_RATE_VHT_80MHZ_SIMO_CB_NGI_175_5MBPS, 1755},
555 {WNI_CFG_LDPC_FIXED_RATE_VHT_80MHZ_SIMO_CB_NGI_234MBPS, 2340},
556 {WNI_CFG_LDPC_FIXED_RATE_VHT_80MHZ_SIMO_CB_NGI_263_25MBPS, 2633},
557 {WNI_CFG_LDPC_FIXED_RATE_VHT_80MHZ_SIMO_CB_NGI_292_5MBPS, 2925},
558 {WNI_CFG_LDPC_FIXED_RATE_VHT_80MHZ_SIMO_CB_NGI_351MBPS, 3510},
559 {WNI_CFG_LDPC_FIXED_RATE_VHT_80MHZ_SIMO_CB_NGI_390MBPS, 3900}
560};
561static rate_cfg_item_mapping_t ac_s80_rate_mapping[] =
562{
563 {WNI_CFG_LDPC_FIXED_RATE_VHT_80MHZ_SIMO_CB_SGI_32_5MBPS, 325},
564 {WNI_CFG_LDPC_FIXED_RATE_VHT_80MHZ_SIMO_CB_SGI_65MBPS, 650},
565 {WNI_CFG_LDPC_FIXED_RATE_VHT_80MHZ_SIMO_CB_SGI_97_5MBPS, 975},
566 {WNI_CFG_LDPC_FIXED_RATE_VHT_80MHZ_SIMO_CB_SGI_130MBPS, 1300},
567 {WNI_CFG_LDPC_FIXED_RATE_VHT_80MHZ_SIMO_CB_SGI_195MBPS, 1950},
568 {WNI_CFG_LDPC_FIXED_RATE_VHT_80MHZ_SIMO_CB_SGI_260MBPS, 2600},
569 {WNI_CFG_LDPC_FIXED_RATE_VHT_80MHZ_SIMO_CB_SGI_292_5MBPS, 2925},
570 {WNI_CFG_LDPC_FIXED_RATE_VHT_80MHZ_SIMO_CB_SGI_325MBPS, 3250},
571 {WNI_CFG_LDPC_FIXED_RATE_VHT_80MHZ_SIMO_CB_SGI_390MBPS, 3900},
572 {WNI_CFG_LDPC_FIXED_RATE_VHT_80MHZ_SIMO_CB_SGI_433_33MBPS, 4333}
573};
574#endif /* WLAN_FEATURE_11AC */
575
576typedef enum
577{
578 RATE_CFG_RATE_LEGACY,
579 RATE_CFG_RATE_11N_MCS_LGI_20,
580 RATE_CFG_RATE_11N_MCS_SGI_20,
581 RATE_CFG_RATE_11N_MCS_LGI_40,
582 RATE_CFG_RATE_11N_MCS_SGI_40,
583 RATE_CFG_RATE_11AC_MCS_LGI_20,
584 RATE_CFG_RATE_11AC_MCS_SGI_20,
585 RATE_CFG_RATE_11AC_MCS_LGI_40,
586 RATE_CFG_RATE_11AC_MCS_SGI_40,
587 RATE_CFG_RATE_11AC_MCS_LGI_80,
588 RATE_CFG_RATE_11AC_MCS_SGI_80
589} rate_cfg_supported_rate_t;
590
591typedef enum
592{
593 RATE_CFG_RATE_11AC_MAX_MCS_7,
594 RATE_CFG_RATE_11AC_MAX_MCS_8,
595 RATE_CFG_RATE_11AC_MAX_MCS_9
596} rate_cfg_11ac_max_mcs_t;
597
598typedef enum
599{
600 RATE_CFG_RATE_BW_20,
601 RATE_CFG_RATE_BW_40,
602 RATE_CFG_RATE_BW_80
603} rate_cfg_supported_bw_t;
604
605typedef enum
606{
607 RATE_CFG_RATE_GI_LONG,
608 RATE_CFG_RATE_GI_SHORT
609} rate_cfg_gi_t;
610
Jeff Johnson295189b2012-06-20 16:38:30 -0700611/*---------------------------------------------------------------------------
612 * Function definitions
613 *-------------------------------------------------------------------------*/
614/**---------------------------------------------------------------------------
615
616 \brief hdd_hostapd_open() - HDD Open function for hostapd interface
617
618 This is called in response to ifconfig up
619
620 \param - dev Pointer to net_device structure
621
622 \return - 0 for success non-zero for failure
623
624 --------------------------------------------------------------------------*/
625int hdd_hostapd_open (struct net_device *dev)
626{
627 ENTER();
628
629 //Turn ON carrier state
630 netif_carrier_on(dev);
631 //Enable all Tx queues
632 netif_tx_start_all_queues(dev);
633
634 EXIT();
635 return 0;
636}
637/**---------------------------------------------------------------------------
638
639 \brief hdd_hostapd_stop() - HDD stop function for hostapd interface
640
641 This is called in response to ifconfig down
642
643 \param - dev Pointer to net_device structure
644
645 \return - 0 for success non-zero for failure
646
647 --------------------------------------------------------------------------*/
648int hdd_hostapd_stop (struct net_device *dev)
649{
650 ENTER();
651
652 //Stop all tx queues
653 netif_tx_disable(dev);
654
655 //Turn OFF carrier state
656 netif_carrier_off(dev);
657
658 EXIT();
659 return 0;
660}
661/**---------------------------------------------------------------------------
662
663 \brief hdd_hostapd_uninit() - HDD uninit function
664
665 This is called during the netdev unregister to uninitialize all data
666associated with the device
667
668 \param - dev Pointer to net_device structure
669
670 \return - void
671
672 --------------------------------------------------------------------------*/
673static void hdd_hostapd_uninit (struct net_device *dev)
674{
675 hdd_adapter_t *pHostapdAdapter = netdev_priv(dev);
676
677 ENTER();
678
679 if (pHostapdAdapter && pHostapdAdapter->pHddCtx)
680 {
681 hdd_deinit_adapter(pHostapdAdapter->pHddCtx, pHostapdAdapter);
682
683 /* after uninit our adapter structure will no longer be valid */
684 pHostapdAdapter->dev = NULL;
685 }
686
687 EXIT();
688}
689
690
691/**============================================================================
692 @brief hdd_hostapd_hard_start_xmit() - Function registered with the Linux OS for
693 transmitting packets. There are 2 versions of this function. One that uses
694 locked queue and other that uses lockless queues. Both have been retained to
695 do some performance testing
696 @param skb : [in] pointer to OS packet (sk_buff)
697 @param dev : [in] pointer to Libra network device
698
699 @return : NET_XMIT_DROP if packets are dropped
700 : NET_XMIT_SUCCESS if packet is enqueued succesfully
701 ===========================================================================*/
702int hdd_hostapd_hard_start_xmit(struct sk_buff *skb, struct net_device *dev)
703{
704 return 0;
705}
706int hdd_hostapd_change_mtu(struct net_device *dev, int new_mtu)
707{
708 return 0;
709}
710
711int hdd_hostapd_ioctl(struct net_device *dev, struct ifreq *ifr, int cmd)
712{
713 hdd_adapter_t *pAdapter = WLAN_HDD_GET_PRIV_PTR(dev);
714 hdd_priv_data_t priv_data;
715 tANI_U8 *command = NULL;
716 int ret = 0;
717
718 if (NULL == pAdapter)
719 {
720 VOS_TRACE( VOS_MODULE_ID_HDD, VOS_TRACE_LEVEL_FATAL,
Madan Mohan Koyyalamudi87054ba2012-11-02 13:24:12 -0700721 "%s: HDD adapter context is Null", __func__);
Jeff Johnson295189b2012-06-20 16:38:30 -0700722 ret = -ENODEV;
723 goto exit;
724 }
725
Jeff Johnsone7245742012-09-05 17:12:55 -0700726 if ((!ifr) || (!ifr->ifr_data))
Jeff Johnson295189b2012-06-20 16:38:30 -0700727 {
728 ret = -EINVAL;
729 goto exit;
730 }
731
732 if (copy_from_user(&priv_data, ifr->ifr_data, sizeof(hdd_priv_data_t)))
733 {
734 ret = -EFAULT;
735 goto exit;
736 }
737
Mingcheng Zhuc7608ae2013-11-04 15:11:01 -0800738 if (priv_data.total_len <= 0 ||
739 priv_data.total_len == INT_MAX)
740 {
741 /* below we allocate one more byte for command buffer.
742 * To avoid addition overflow total_len should be
743 * smaller than INT_MAX. */
744 VOS_TRACE( VOS_MODULE_ID_HDD, VOS_TRACE_LEVEL_FATAL,
745 "%s: integer out of range\n", __func__);
746 ret = -EFAULT;
747 goto exit;
748 }
749
750 command = kmalloc((priv_data.total_len + 1), GFP_KERNEL);
Jeff Johnson295189b2012-06-20 16:38:30 -0700751 if (!command)
752 {
753 VOS_TRACE( VOS_MODULE_ID_HDD, VOS_TRACE_LEVEL_FATAL,
Madan Mohan Koyyalamudi87054ba2012-11-02 13:24:12 -0700754 "%s: failed to allocate memory\n", __func__);
Jeff Johnson295189b2012-06-20 16:38:30 -0700755 ret = -ENOMEM;
756 goto exit;
757 }
758
759 if (copy_from_user(command, priv_data.buf, priv_data.total_len))
760 {
761 ret = -EFAULT;
762 goto exit;
763 }
764
Mingcheng Zhuc7608ae2013-11-04 15:11:01 -0800765 command[priv_data.total_len] = '\0';
766
Jeff Johnson295189b2012-06-20 16:38:30 -0700767 if ((SIOCDEVPRIVATE + 1) == cmd)
768 {
769 VOS_TRACE( VOS_MODULE_ID_HDD, VOS_TRACE_LEVEL_FATAL,
770 "***HOSTAPD*** : Received %s cmd from Wi-Fi GUI***", command);
771
Jeff Johnson295189b2012-06-20 16:38:30 -0700772 if(strncmp(command, "P2P_SET_NOA", 11) == 0 )
773 {
774 hdd_setP2pNoa(dev, command);
775 }
776 else if( strncmp(command, "P2P_SET_PS", 10) == 0 )
777 {
778 hdd_setP2pOpps(dev, command);
779 }
Madan Mohan Koyyalamudi1bed5982012-10-22 14:38:06 -0700780
781 /*
782 command should be a string having format
783 SET_SAP_CHANNEL_LIST <num of channels> <the channels seperated by spaces>
784 */
Madan Mohan Koyyalamudi5aef2af2012-10-05 11:56:27 -0700785 if(strncmp(command, "SET_SAP_CHANNEL_LIST", 20) == 0)
Madan Mohan Koyyalamudi1bed5982012-10-22 14:38:06 -0700786 {
787 VOS_TRACE( VOS_MODULE_ID_HDD, VOS_TRACE_LEVEL_INFO,
Madan Mohan Koyyalamudi87054ba2012-11-02 13:24:12 -0700788 " Received Command to Set Preferred Channels for SAP in %s", __func__);
Madan Mohan Koyyalamudi1bed5982012-10-22 14:38:06 -0700789
Mahesh Kumar Kalikot Veetil2aad8d82013-02-07 12:31:28 -0800790 ret = sapSetPreferredChannel(command);
Madan Mohan Koyyalamudi5aef2af2012-10-05 11:56:27 -0700791 }
Jeff Johnson295189b2012-06-20 16:38:30 -0700792 }
793exit:
794 if (command)
795 {
796 kfree(command);
797 }
798 return ret;
799}
800
801/**---------------------------------------------------------------------------
802
803 \brief hdd_hostapd_set_mac_address() -
804 This function sets the user specified mac address using
805 the command ifconfig wlanX hw ether <mac adress>.
806
807 \param - dev - Pointer to the net device.
808 - addr - Pointer to the sockaddr.
809 \return - 0 for success, non zero for failure
810
811 --------------------------------------------------------------------------*/
812
813static int hdd_hostapd_set_mac_address(struct net_device *dev, void *addr)
814{
815 struct sockaddr *psta_mac_addr = addr;
816 ENTER();
817 memcpy(dev->dev_addr, psta_mac_addr->sa_data, ETH_ALEN);
818 EXIT();
819 return 0;
820}
821void hdd_hostapd_inactivity_timer_cb(v_PVOID_t usrDataForCallback)
822{
823 struct net_device *dev = (struct net_device *)usrDataForCallback;
824 v_BYTE_t we_custom_event[64];
825 union iwreq_data wrqu;
826#ifdef DISABLE_CONCURRENCY_AUTOSAVE
827 VOS_STATUS vos_status;
828 hdd_adapter_t *pHostapdAdapter;
829 hdd_ap_ctx_t *pHddApCtx;
830#endif /*DISABLE_CONCURRENCY_AUTOSAVE */
831
832 /* event_name space-delimiter driver_module_name */
833 /* Format of the event is "AUTO-SHUT.indication" " " "module_name" */
834 char * autoShutEvent = "AUTO-SHUT.indication" " " KBUILD_MODNAME;
835 int event_len = strlen(autoShutEvent) + 1; /* For the NULL at the end */
836
837 ENTER();
838
839#ifdef DISABLE_CONCURRENCY_AUTOSAVE
840 if (vos_concurrent_sessions_running())
841 {
842 /*
843 This timer routine is going to be called only when AP
844 persona is up.
845 If there are concurrent sessions running we do not want
846 to shut down the Bss.Instead we run the timer again so
847 that if Autosave is enabled next time and other session
848 was down only then we bring down AP
849 */
850 pHostapdAdapter = netdev_priv(dev);
851 pHddApCtx = WLAN_HDD_GET_AP_CTX_PTR(pHostapdAdapter);
852 vos_status = vos_timer_start(
853 &pHddApCtx->hdd_ap_inactivity_timer,
854 (WLAN_HDD_GET_CTX(pHostapdAdapter))->cfg_ini->nAPAutoShutOff
855 * 1000);
856 if (!VOS_IS_STATUS_SUCCESS(vos_status))
857 {
858 hddLog(LOGE, FL("Failed to init AP inactivity timer"));
859 }
860 EXIT();
861 return;
862 }
863#endif /*DISABLE_CONCURRENCY_AUTOSAVE */
864 memset(&we_custom_event, '\0', sizeof(we_custom_event));
865 memcpy(&we_custom_event, autoShutEvent, event_len);
866
867 memset(&wrqu, 0, sizeof(wrqu));
868 wrqu.data.length = event_len;
869
870 hddLog(LOG1, FL("Shutting down AP interface due to inactivity"));
871 wireless_send_event(dev, IWEVCUSTOM, &wrqu, (char *)we_custom_event);
872
873 EXIT();
874}
875
Madan Mohan Koyyalamudi167b95e2012-11-27 15:53:38 -0800876VOS_STATUS hdd_change_mcc_go_beacon_interval(hdd_adapter_t *pHostapdAdapter)
877{
878 v_CONTEXT_t pVosContext = (WLAN_HDD_GET_CTX(pHostapdAdapter))->pvosContext;
879 ptSapContext pSapCtx = NULL;
880 eHalStatus halStatus = eHAL_STATUS_FAILURE;
881 v_PVOID_t hHal = NULL;
882
883 VOS_TRACE( VOS_MODULE_ID_SAP, VOS_TRACE_LEVEL_INFO_HIGH,
884 "%s: UPDATE Beacon Params", __func__);
885
886 if(VOS_STA_SAP_MODE == vos_get_conparam ( )){
887 pSapCtx = VOS_GET_SAP_CB(pVosContext);
888 if ( NULL == pSapCtx )
889 {
890 VOS_TRACE( VOS_MODULE_ID_SAP, VOS_TRACE_LEVEL_ERROR,
891 "%s: Invalid SAP pointer from pvosGCtx", __func__);
892 return VOS_STATUS_E_FAULT;
893 }
894
895 hHal = VOS_GET_HAL_CB(pSapCtx->pvosGCtx);
896 if ( NULL == hHal ){
897 VOS_TRACE( VOS_MODULE_ID_SAP, VOS_TRACE_LEVEL_ERROR,
898 "%s: Invalid HAL pointer from pvosGCtx", __func__);
899 return VOS_STATUS_E_FAULT;
900 }
901 halStatus = sme_ChangeMCCBeaconInterval(hHal, pSapCtx->sessionId);
902 if(halStatus == eHAL_STATUS_FAILURE ){
903 VOS_TRACE( VOS_MODULE_ID_SAP, VOS_TRACE_LEVEL_ERROR,
904 "%s: Failed to update Beacon Params", __func__);
905 return VOS_STATUS_E_FAILURE;
906 }
907 }
908 return VOS_STATUS_SUCCESS;
909}
910
911void hdd_clear_all_sta(hdd_adapter_t *pHostapdAdapter, v_PVOID_t usrDataForCallback)
912{
913 v_U8_t staId = 0;
914 struct net_device *dev;
915 dev = (struct net_device *)usrDataForCallback;
916
917 hddLog(LOGE, FL("Clearing all the STA entry....\n"));
918 for (staId = 0; staId < WLAN_MAX_STA_COUNT; staId++)
919 {
920 if ( pHostapdAdapter->aStaInfo[staId].isUsed &&
921 ( staId != (WLAN_HDD_GET_AP_CTX_PTR(pHostapdAdapter))->uBCStaId))
922 {
923 //Disconnect all the stations
924 hdd_softap_sta_disassoc(pHostapdAdapter, &pHostapdAdapter->aStaInfo[staId].macAddrSTA.bytes[0]);
925 }
926 }
927}
928
929static int hdd_stop_p2p_link(hdd_adapter_t *pHostapdAdapter,v_PVOID_t usrDataForCallback)
930{
931 struct net_device *dev;
932 VOS_STATUS status = VOS_STATUS_SUCCESS;
933 dev = (struct net_device *)usrDataForCallback;
934 ENTER();
935 if(test_bit(SOFTAP_BSS_STARTED, &pHostapdAdapter->event_flags))
936 {
937 if ( VOS_STATUS_SUCCESS == (status = WLANSAP_StopBss((WLAN_HDD_GET_CTX(pHostapdAdapter))->pvosContext) ) )
938 {
939 VOS_TRACE(VOS_MODULE_ID_HDD, VOS_TRACE_LEVEL_ERROR, FL("Deleting P2P link!!!!!!"));
940 }
941 clear_bit(SOFTAP_BSS_STARTED, &pHostapdAdapter->event_flags);
942 }
943 EXIT();
944 return (status == VOS_STATUS_SUCCESS) ? 0 : -EBUSY;
945}
Jeff Johnson295189b2012-06-20 16:38:30 -0700946
947VOS_STATUS hdd_hostapd_SAPEventCB( tpSap_Event pSapEvent, v_PVOID_t usrDataForCallback)
948{
949 hdd_adapter_t *pHostapdAdapter;
950 hdd_ap_ctx_t *pHddApCtx;
951 hdd_hostapd_state_t *pHostapdState;
952 struct net_device *dev;
953 eSapHddEvent sapEvent;
954 union iwreq_data wrqu;
955 v_BYTE_t *we_custom_event_generic = NULL;
956 int we_event = 0;
957 int i = 0;
958 v_U8_t staId;
959 VOS_STATUS vos_status;
960 v_BOOL_t bWPSState;
961 v_BOOL_t bApActive = FALSE;
962 v_BOOL_t bAuthRequired = TRUE;
963 tpSap_AssocMacAddr pAssocStasArray = NULL;
964 char unknownSTAEvent[IW_CUSTOM_MAX+1];
965 char maxAssocExceededEvent[IW_CUSTOM_MAX+1];
966 v_BYTE_t we_custom_start_event[64];
967 char *startBssEvent;
Madan Mohan Koyyalamudi69fc3ad2012-11-28 16:04:56 -0800968 hdd_context_t *pHddCtx;
Madan Mohan Koyyalamudicd784992013-01-11 15:30:36 -0800969 hdd_scaninfo_t *pScanInfo = NULL;
Jeff Johnson5f12e902013-04-03 10:21:46 -0700970 struct iw_michaelmicfailure msg;
Jeff Johnson295189b2012-06-20 16:38:30 -0700971
972 dev = (struct net_device *)usrDataForCallback;
973 pHostapdAdapter = netdev_priv(dev);
Madan Mohan Koyyalamudie1b791f2013-07-24 12:53:33 +0530974
975 if ((NULL == pHostapdAdapter) ||
976 (WLAN_HDD_ADAPTER_MAGIC != pHostapdAdapter->magic))
977 {
978 VOS_TRACE(VOS_MODULE_ID_HDD, VOS_TRACE_LEVEL_FATAL,
979 "invalid adapter or adapter has invalid magic");
980 return eHAL_STATUS_FAILURE;
981 }
982
Jeff Johnson295189b2012-06-20 16:38:30 -0700983 pHostapdState = WLAN_HDD_GET_HOSTAP_STATE_PTR(pHostapdAdapter);
984 pHddApCtx = WLAN_HDD_GET_AP_CTX_PTR(pHostapdAdapter);
985 sapEvent = pSapEvent->sapHddEventCode;
986 memset(&wrqu, '\0', sizeof(wrqu));
Madan Mohan Koyyalamudi69fc3ad2012-11-28 16:04:56 -0800987 pHddCtx = (hdd_context_t*)(pHostapdAdapter->pHddCtx);
Jeff Johnson295189b2012-06-20 16:38:30 -0700988
989 switch(sapEvent)
990 {
991 case eSAP_START_BSS_EVENT :
Jeff Johnson0299d0a2013-10-30 12:37:43 -0700992 hddLog(LOG1, FL("BSS configured status = %s, channel = %u, bc sta Id = %d\n"),
Jeff Johnson295189b2012-06-20 16:38:30 -0700993 pSapEvent->sapevt.sapStartBssCompleteEvent.status ? "eSAP_STATUS_FAILURE" : "eSAP_STATUS_SUCCESS",
994 pSapEvent->sapevt.sapStartBssCompleteEvent.operatingChannel,
995 pSapEvent->sapevt.sapStartBssCompleteEvent.staId);
996
997 pHostapdState->vosStatus = pSapEvent->sapevt.sapStartBssCompleteEvent.status;
998 vos_status = vos_event_set(&pHostapdState->vosEvent);
999
1000 if (!VOS_IS_STATUS_SUCCESS(vos_status) || pHostapdState->vosStatus)
1001 {
1002 VOS_TRACE(VOS_MODULE_ID_HDD, VOS_TRACE_LEVEL_ERROR, ("ERROR: startbss event failed!!\n"));
1003 goto stopbss;
1004 }
1005 else
1006 {
1007 pHddApCtx->uBCStaId = pSapEvent->sapevt.sapStartBssCompleteEvent.staId;
1008 //@@@ need wep logic here to set privacy bit
1009 hdd_softap_Register_BC_STA(pHostapdAdapter, pHddApCtx->uPrivacy);
1010 }
1011
1012 if (0 != (WLAN_HDD_GET_CTX(pHostapdAdapter))->cfg_ini->nAPAutoShutOff)
1013 {
1014 // AP Inactivity timer init and start
1015 vos_status = vos_timer_init( &pHddApCtx->hdd_ap_inactivity_timer, VOS_TIMER_TYPE_SW,
1016 hdd_hostapd_inactivity_timer_cb, (v_PVOID_t)dev );
1017 if (!VOS_IS_STATUS_SUCCESS(vos_status))
1018 hddLog(LOGE, FL("Failed to init AP inactivity timer\n"));
1019
1020 vos_status = vos_timer_start( &pHddApCtx->hdd_ap_inactivity_timer, (WLAN_HDD_GET_CTX(pHostapdAdapter))->cfg_ini->nAPAutoShutOff * 1000);
1021 if (!VOS_IS_STATUS_SUCCESS(vos_status))
1022 hddLog(LOGE, FL("Failed to init AP inactivity timer\n"));
1023
1024 }
1025 pHddApCtx->operatingChannel = pSapEvent->sapevt.sapStartBssCompleteEvent.operatingChannel;
1026 pHostapdState->bssState = BSS_START;
1027
1028 // Send current operating channel of SoftAP to BTC-ES
1029 send_btc_nlink_msg(WLAN_BTC_SOFTAP_BSS_START, 0);
1030
Jeff Johnson295189b2012-06-20 16:38:30 -07001031 //Check if there is any group key pending to set.
1032 if( pHddApCtx->groupKey.keyLength )
1033 {
Jeff Johnson43971f52012-07-17 12:26:56 -07001034 if( VOS_STATUS_SUCCESS != WLANSAP_SetKeySta(
Jeff Johnson295189b2012-06-20 16:38:30 -07001035 (WLAN_HDD_GET_CTX(pHostapdAdapter))->pvosContext,
1036 &pHddApCtx->groupKey ) )
1037 {
1038 VOS_TRACE( VOS_MODULE_ID_HDD, VOS_TRACE_LEVEL_ERROR,
1039 "%s: WLANSAP_SetKeySta failed", __func__);
1040 }
1041 pHddApCtx->groupKey.keyLength = 0;
1042 }
1043 else if ( pHddApCtx->wepKey[0].keyLength )
1044 {
1045 int i=0;
1046 for ( i = 0; i < CSR_MAX_NUM_KEY; i++ )
1047 {
Jeff Johnson43971f52012-07-17 12:26:56 -07001048 if( VOS_STATUS_SUCCESS != WLANSAP_SetKeySta(
Jeff Johnson295189b2012-06-20 16:38:30 -07001049 (WLAN_HDD_GET_CTX(pHostapdAdapter))->pvosContext,
1050 &pHddApCtx->wepKey[i] ) )
1051 {
1052 VOS_TRACE( VOS_MODULE_ID_HDD, VOS_TRACE_LEVEL_ERROR,
1053 "%s: WLANSAP_SetKeySta failed idx %d", __func__, i);
1054 }
1055 pHddApCtx->wepKey[i].keyLength = 0;
1056 }
1057 }
Jeff Johnson295189b2012-06-20 16:38:30 -07001058 //Fill the params for sending IWEVCUSTOM Event with SOFTAP.enabled
1059 startBssEvent = "SOFTAP.enabled";
1060 memset(&we_custom_start_event, '\0', sizeof(we_custom_start_event));
1061 memcpy(&we_custom_start_event, startBssEvent, strlen(startBssEvent));
1062 memset(&wrqu, 0, sizeof(wrqu));
1063 wrqu.data.length = strlen(startBssEvent);
1064 we_event = IWEVCUSTOM;
1065 we_custom_event_generic = we_custom_start_event;
Sudhir Sattayappa Kohalli90e4c752013-03-21 14:25:04 -07001066 hdd_dump_concurrency_info(pHddCtx);
Jeff Johnson295189b2012-06-20 16:38:30 -07001067 break; //Event will be sent after Switch-Case stmt
1068
1069 case eSAP_STOP_BSS_EVENT:
1070 hddLog(LOG1, FL("BSS stop status = %s\n"),pSapEvent->sapevt.sapStopBssCompleteEvent.status ?
1071 "eSAP_STATUS_FAILURE" : "eSAP_STATUS_SUCCESS");
1072
Madan Mohan Koyyalamudi5aef2af2012-10-05 11:56:27 -07001073 //Free up Channel List incase if it is set
Madan Mohan Koyyalamudi1bed5982012-10-22 14:38:06 -07001074 sapCleanupChannelList();
Madan Mohan Koyyalamudi5aef2af2012-10-05 11:56:27 -07001075
Jeff Johnson295189b2012-06-20 16:38:30 -07001076 pHddApCtx->operatingChannel = 0; //Invalidate the channel info.
Jeff Johnson295189b2012-06-20 16:38:30 -07001077 goto stopbss;
1078 case eSAP_STA_SET_KEY_EVENT:
1079 //TODO: forward the message to hostapd once implementtation is done for now just print
1080 hddLog(LOG1, FL("SET Key: configured status = %s\n"),pSapEvent->sapevt.sapStationSetKeyCompleteEvent.status ?
1081 "eSAP_STATUS_FAILURE" : "eSAP_STATUS_SUCCESS");
1082 return VOS_STATUS_SUCCESS;
1083 case eSAP_STA_DEL_KEY_EVENT:
1084 //TODO: forward the message to hostapd once implementtation is done for now just print
1085 hddLog(LOG1, FL("Event received %s\n"),"eSAP_STA_DEL_KEY_EVENT");
1086 return VOS_STATUS_SUCCESS;
1087 case eSAP_STA_MIC_FAILURE_EVENT:
1088 {
Jeff Johnson295189b2012-06-20 16:38:30 -07001089 memset(&msg, '\0', sizeof(msg));
1090 msg.src_addr.sa_family = ARPHRD_ETHER;
Kumar Pavan0cf0cf22012-12-13 15:13:41 -08001091 memcpy(msg.src_addr.sa_data, &pSapEvent->sapevt.sapStationMICFailureEvent.staMac, sizeof(v_MACADDR_t));
Jeff Johnson295189b2012-06-20 16:38:30 -07001092 hddLog(LOG1, "MIC MAC "MAC_ADDRESS_STR"\n", MAC_ADDR_ARRAY(msg.src_addr.sa_data));
Jeff Johnson43971f52012-07-17 12:26:56 -07001093 if(pSapEvent->sapevt.sapStationMICFailureEvent.multicast == eSAP_TRUE)
Jeff Johnson295189b2012-06-20 16:38:30 -07001094 msg.flags = IW_MICFAILURE_GROUP;
1095 else
1096 msg.flags = IW_MICFAILURE_PAIRWISE;
1097 memset(&wrqu, 0, sizeof(wrqu));
1098 wrqu.data.length = sizeof(msg);
1099 we_event = IWEVMICHAELMICFAILURE;
1100 we_custom_event_generic = (v_BYTE_t *)&msg;
1101 }
Jeff Johnson295189b2012-06-20 16:38:30 -07001102 /* inform mic failure to nl80211 */
1103 cfg80211_michael_mic_failure(dev,
1104 pSapEvent->sapevt.
1105 sapStationMICFailureEvent.staMac.bytes,
Jeff Johnson43971f52012-07-17 12:26:56 -07001106 ((pSapEvent->sapevt.sapStationMICFailureEvent.multicast == eSAP_TRUE) ?
Jeff Johnson295189b2012-06-20 16:38:30 -07001107 NL80211_KEYTYPE_GROUP :
1108 NL80211_KEYTYPE_PAIRWISE),
1109 pSapEvent->sapevt.sapStationMICFailureEvent.keyId,
1110 pSapEvent->sapevt.sapStationMICFailureEvent.TSC,
1111 GFP_KERNEL);
Jeff Johnson295189b2012-06-20 16:38:30 -07001112 break;
1113
1114 case eSAP_STA_ASSOC_EVENT:
1115 case eSAP_STA_REASSOC_EVENT:
1116 wrqu.addr.sa_family = ARPHRD_ETHER;
1117 memcpy(wrqu.addr.sa_data, &pSapEvent->sapevt.sapStationAssocReassocCompleteEvent.staMac,
Kumar Pavan0cf0cf22012-12-13 15:13:41 -08001118 sizeof(v_MACADDR_t));
Jeff Johnson295189b2012-06-20 16:38:30 -07001119 hddLog(LOG1, " associated "MAC_ADDRESS_STR"\n", MAC_ADDR_ARRAY(wrqu.addr.sa_data));
1120 we_event = IWEVREGISTERED;
1121
1122 WLANSAP_Get_WPS_State((WLAN_HDD_GET_CTX(pHostapdAdapter))->pvosContext, &bWPSState);
1123
1124 if ( (eCSR_ENCRYPT_TYPE_NONE == pHddApCtx->ucEncryptType) ||
1125 ( eCSR_ENCRYPT_TYPE_WEP40_STATICKEY == pHddApCtx->ucEncryptType ) ||
1126 ( eCSR_ENCRYPT_TYPE_WEP104_STATICKEY == pHddApCtx->ucEncryptType ) )
1127 {
1128 bAuthRequired = FALSE;
1129 }
1130
1131 if (bAuthRequired || bWPSState == eANI_BOOLEAN_TRUE )
1132 {
1133 hdd_softap_RegisterSTA( pHostapdAdapter,
1134 TRUE,
1135 pHddApCtx->uPrivacy,
1136 pSapEvent->sapevt.sapStationAssocReassocCompleteEvent.staId,
1137 0,
1138 0,
1139 (v_MACADDR_t *)wrqu.addr.sa_data,
1140 pSapEvent->sapevt.sapStationAssocReassocCompleteEvent.wmmEnabled);
1141 }
1142 else
1143 {
1144 hdd_softap_RegisterSTA( pHostapdAdapter,
1145 FALSE,
1146 pHddApCtx->uPrivacy,
1147 pSapEvent->sapevt.sapStationAssocReassocCompleteEvent.staId,
1148 0,
1149 0,
1150 (v_MACADDR_t *)wrqu.addr.sa_data,
1151 pSapEvent->sapevt.sapStationAssocReassocCompleteEvent.wmmEnabled);
Amar Singhal6144c002013-05-03 16:11:42 -07001152 }
1153
Jeff Johnson295189b2012-06-20 16:38:30 -07001154 // Stop AP inactivity timer
1155 if (pHddApCtx->hdd_ap_inactivity_timer.state == VOS_TIMER_STATE_RUNNING)
1156 {
1157 vos_status = vos_timer_stop(&pHddApCtx->hdd_ap_inactivity_timer);
1158 if (!VOS_IS_STATUS_SUCCESS(vos_status))
1159 hddLog(LOGE, FL("Failed to start AP inactivity timer\n"));
1160 }
Sameer Thalappil50dc0092013-02-19 17:23:33 -08001161#ifdef WLAN_OPEN_SOURCE
Madan Mohan Koyyalamudi69fc3ad2012-11-28 16:04:56 -08001162 if (wake_lock_active(&pHddCtx->sap_wake_lock))
1163 {
1164 wake_unlock(&pHddCtx->sap_wake_lock);
1165 }
Amar Singhal6144c002013-05-03 16:11:42 -07001166 wake_lock_timeout(&pHddCtx->sap_wake_lock, msecs_to_jiffies(HDD_SAP_WAKE_LOCK_DURATION));
Sameer Thalappil50dc0092013-02-19 17:23:33 -08001167#endif
Jeff Johnson295189b2012-06-20 16:38:30 -07001168#if (LINUX_VERSION_CODE >= KERNEL_VERSION(2,6,38))
1169 {
1170 struct station_info staInfo;
1171 v_U16_t iesLen = pSapEvent->sapevt.sapStationAssocReassocCompleteEvent.iesLen;
1172
1173 memset(&staInfo, 0, sizeof(staInfo));
1174 if (iesLen <= MAX_ASSOC_IND_IE_LEN )
1175 {
1176 staInfo.assoc_req_ies =
1177 (const u8 *)&pSapEvent->sapevt.sapStationAssocReassocCompleteEvent.ies[0];
1178 staInfo.assoc_req_ies_len = iesLen;
Madan Mohan Koyyalamudi1b4afb02012-10-22 15:25:16 -07001179#if (LINUX_VERSION_CODE >= KERNEL_VERSION(3,0,31))
Jeff Johnson04dd8a82012-06-29 20:41:40 -07001180 staInfo.filled |= STATION_INFO_ASSOC_REQ_IES;
1181#endif
Jeff Johnson295189b2012-06-20 16:38:30 -07001182 cfg80211_new_sta(dev,
1183 (const u8 *)&pSapEvent->sapevt.sapStationAssocReassocCompleteEvent.staMac.bytes[0],
1184 &staInfo, GFP_KERNEL);
1185 }
1186 else
1187 {
1188 hddLog(LOGE, FL(" Assoc Ie length is too long \n"));
1189 }
1190 }
1191#endif
Madan Mohan Koyyalamudicd784992013-01-11 15:30:36 -08001192 pScanInfo = &pHddCtx->scan_info;
1193 // Lets do abort scan to ensure smooth authentication for client
1194 if ((pScanInfo != NULL) && pScanInfo->mScanPending)
1195 {
Madan Mohan Koyyalamudiff3a7152013-06-13 14:47:55 +05301196 hdd_abort_mac_scan(pHddCtx, pHostapdAdapter->sessionId);
Madan Mohan Koyyalamudicd784992013-01-11 15:30:36 -08001197 }
Jeff Johnson295189b2012-06-20 16:38:30 -07001198
1199 break;
1200 case eSAP_STA_DISASSOC_EVENT:
1201 memcpy(wrqu.addr.sa_data, &pSapEvent->sapevt.sapStationDisassocCompleteEvent.staMac,
Kumar Pavan0cf0cf22012-12-13 15:13:41 -08001202 sizeof(v_MACADDR_t));
Jeff Johnson295189b2012-06-20 16:38:30 -07001203 hddLog(LOG1, " disassociated "MAC_ADDRESS_STR"\n", MAC_ADDR_ARRAY(wrqu.addr.sa_data));
1204 if (pSapEvent->sapevt.sapStationDisassocCompleteEvent.reason == eSAP_USR_INITATED_DISASSOC)
1205 hddLog(LOG1," User initiated disassociation");
1206 else
1207 hddLog(LOG1," MAC initiated disassociation");
1208 we_event = IWEVEXPIRED;
1209 vos_status = hdd_softap_GetStaId(pHostapdAdapter, &pSapEvent->sapevt.sapStationDisassocCompleteEvent.staMac, &staId);
1210 if (!VOS_IS_STATUS_SUCCESS(vos_status))
1211 {
Madan Mohan Koyyalamudi8bdd3112012-09-24 13:55:14 -07001212 VOS_TRACE(VOS_MODULE_ID_HDD, VOS_TRACE_LEVEL_ERROR, FL("ERROR: HDD Failed to find sta id!!"));
Jeff Johnson295189b2012-06-20 16:38:30 -07001213 return VOS_STATUS_E_FAILURE;
1214 }
1215 hdd_softap_DeregisterSTA(pHostapdAdapter, staId);
1216
1217 if (0 != (WLAN_HDD_GET_CTX(pHostapdAdapter))->cfg_ini->nAPAutoShutOff)
1218 {
1219 spin_lock_bh( &pHostapdAdapter->staInfo_lock );
1220 // Start AP inactivity timer if no stations associated with it
1221 for (i = 0; i < WLAN_MAX_STA_COUNT; i++)
1222 {
1223 if (pHostapdAdapter->aStaInfo[i].isUsed && i != (WLAN_HDD_GET_AP_CTX_PTR(pHostapdAdapter))->uBCStaId)
1224 {
1225 bApActive = TRUE;
1226 break;
1227 }
1228 }
1229 spin_unlock_bh( &pHostapdAdapter->staInfo_lock );
1230
1231 if (bApActive == FALSE)
1232 {
1233 if (pHddApCtx->hdd_ap_inactivity_timer.state == VOS_TIMER_STATE_STOPPED)
1234 {
1235 vos_status = vos_timer_start(&pHddApCtx->hdd_ap_inactivity_timer, (WLAN_HDD_GET_CTX(pHostapdAdapter))->cfg_ini->nAPAutoShutOff * 1000);
1236 if (!VOS_IS_STATUS_SUCCESS(vos_status))
1237 hddLog(LOGE, FL("Failed to init AP inactivity timer\n"));
1238 }
1239 else
1240 VOS_ASSERT(vos_timer_getCurrentState(&pHddApCtx->hdd_ap_inactivity_timer) == VOS_TIMER_STATE_STOPPED);
1241 }
1242 }
Jeff Johnson295189b2012-06-20 16:38:30 -07001243#if (LINUX_VERSION_CODE >= KERNEL_VERSION(2,6,38))
1244 cfg80211_del_sta(dev,
1245 (const u8 *)&pSapEvent->sapevt.sapStationDisassocCompleteEvent.staMac.bytes[0],
1246 GFP_KERNEL);
1247#endif
Madan Mohan Koyyalamudi167b95e2012-11-27 15:53:38 -08001248 //Update the beacon Interval if it is P2P GO
1249 hdd_change_mcc_go_beacon_interval(pHostapdAdapter);
Jeff Johnson295189b2012-06-20 16:38:30 -07001250 break;
1251 case eSAP_WPS_PBC_PROBE_REQ_EVENT:
1252 {
1253 static const char * message ="MLMEWPSPBCPROBEREQ.indication";
1254 union iwreq_data wreq;
1255
1256 down(&pHddApCtx->semWpsPBCOverlapInd);
1257 pHddApCtx->WPSPBCProbeReq.probeReqIELen = pSapEvent->sapevt.sapPBCProbeReqEvent.WPSPBCProbeReq.probeReqIELen;
1258
1259 vos_mem_copy(pHddApCtx->WPSPBCProbeReq.probeReqIE, pSapEvent->sapevt.sapPBCProbeReqEvent.WPSPBCProbeReq.probeReqIE,
1260 pHddApCtx->WPSPBCProbeReq.probeReqIELen);
1261
1262 vos_mem_copy(pHddApCtx->WPSPBCProbeReq.peerMacAddr, pSapEvent->sapevt.sapPBCProbeReqEvent.WPSPBCProbeReq.peerMacAddr, sizeof(v_MACADDR_t));
1263 hddLog(LOG1, "WPS PBC probe req "MAC_ADDRESS_STR"\n", MAC_ADDR_ARRAY(pHddApCtx->WPSPBCProbeReq.peerMacAddr));
1264 memset(&wreq, 0, sizeof(wreq));
1265 wreq.data.length = strlen(message); // This is length of message
1266 wireless_send_event(dev, IWEVCUSTOM, &wreq, (char *)message);
1267
1268 return VOS_STATUS_SUCCESS;
1269 }
1270 case eSAP_ASSOC_STA_CALLBACK_EVENT:
1271 pAssocStasArray = pSapEvent->sapevt.sapAssocStaListEvent.pAssocStas;
1272 if (pSapEvent->sapevt.sapAssocStaListEvent.noOfAssocSta != 0)
1273 { // List of associated stations
1274 for (i = 0; i < pSapEvent->sapevt.sapAssocStaListEvent.noOfAssocSta; i++)
1275 {
1276 hddLog(LOG1,"Associated Sta Num %d:assocId=%d, staId=%d, staMac="MAC_ADDRESS_STR,
1277 i+1,
1278 pAssocStasArray->assocId,
1279 pAssocStasArray->staId,
1280 MAC_ADDR_ARRAY(pAssocStasArray->staMac.bytes));
1281 pAssocStasArray++;
1282 }
1283 }
1284 vos_mem_free(pSapEvent->sapevt.sapAssocStaListEvent.pAssocStas);// Release caller allocated memory here
1285 return VOS_STATUS_SUCCESS;
Jeff Johnson295189b2012-06-20 16:38:30 -07001286 case eSAP_INDICATE_MGMT_FRAME:
1287 hdd_indicateMgmtFrame( pHostapdAdapter,
1288 pSapEvent->sapevt.sapManagementFrameInfo.nFrameLength,
1289 pSapEvent->sapevt.sapManagementFrameInfo.pbFrames,
1290 pSapEvent->sapevt.sapManagementFrameInfo.frameType,
Chilam NG571c65a2013-01-19 12:27:36 +05301291 pSapEvent->sapevt.sapManagementFrameInfo.rxChan, 0);
Jeff Johnson295189b2012-06-20 16:38:30 -07001292 return VOS_STATUS_SUCCESS;
1293 case eSAP_REMAIN_CHAN_READY:
1294 hdd_remainChanReadyHandler( pHostapdAdapter );
1295 return VOS_STATUS_SUCCESS;
1296 case eSAP_SEND_ACTION_CNF:
1297 hdd_sendActionCnf( pHostapdAdapter,
1298 ( eSAP_STATUS_SUCCESS ==
1299 pSapEvent->sapevt.sapActionCnf.actionSendSuccess ) ?
1300 TRUE : FALSE );
1301 return VOS_STATUS_SUCCESS;
Jeff Johnson295189b2012-06-20 16:38:30 -07001302 case eSAP_UNKNOWN_STA_JOIN:
1303 snprintf(unknownSTAEvent, IW_CUSTOM_MAX, "JOIN_UNKNOWN_STA-%02x:%02x:%02x:%02x:%02x:%02x",
1304 pSapEvent->sapevt.sapUnknownSTAJoin.macaddr.bytes[0],
1305 pSapEvent->sapevt.sapUnknownSTAJoin.macaddr.bytes[1],
1306 pSapEvent->sapevt.sapUnknownSTAJoin.macaddr.bytes[2],
1307 pSapEvent->sapevt.sapUnknownSTAJoin.macaddr.bytes[3],
1308 pSapEvent->sapevt.sapUnknownSTAJoin.macaddr.bytes[4],
1309 pSapEvent->sapevt.sapUnknownSTAJoin.macaddr.bytes[5]);
1310 we_event = IWEVCUSTOM; /* Discovered a new node (AP mode). */
1311 wrqu.data.pointer = unknownSTAEvent;
1312 wrqu.data.length = strlen(unknownSTAEvent);
1313 we_custom_event_generic = (v_BYTE_t *)unknownSTAEvent;
1314 hddLog(LOG1,"%s\n", unknownSTAEvent);
1315 break;
1316
1317 case eSAP_MAX_ASSOC_EXCEEDED:
1318 snprintf(maxAssocExceededEvent, IW_CUSTOM_MAX, "Peer %02x:%02x:%02x:%02x:%02x:%02x denied"
1319 " assoc due to Maximum Mobile Hotspot connections reached. Please disconnect"
1320 " one or more devices to enable the new device connection",
1321 pSapEvent->sapevt.sapMaxAssocExceeded.macaddr.bytes[0],
1322 pSapEvent->sapevt.sapMaxAssocExceeded.macaddr.bytes[1],
1323 pSapEvent->sapevt.sapMaxAssocExceeded.macaddr.bytes[2],
1324 pSapEvent->sapevt.sapMaxAssocExceeded.macaddr.bytes[3],
1325 pSapEvent->sapevt.sapMaxAssocExceeded.macaddr.bytes[4],
1326 pSapEvent->sapevt.sapMaxAssocExceeded.macaddr.bytes[5]);
1327 we_event = IWEVCUSTOM; /* Discovered a new node (AP mode). */
1328 wrqu.data.pointer = maxAssocExceededEvent;
1329 wrqu.data.length = strlen(maxAssocExceededEvent);
1330 we_custom_event_generic = (v_BYTE_t *)maxAssocExceededEvent;
1331 hddLog(LOG1,"%s\n", maxAssocExceededEvent);
1332 break;
1333 case eSAP_STA_ASSOC_IND:
1334 return VOS_STATUS_SUCCESS;
Madan Mohan Koyyalamudi167b95e2012-11-27 15:53:38 -08001335
1336 case eSAP_DISCONNECT_ALL_P2P_CLIENT:
1337 hddLog(LOG1, FL(" Disconnecting all the P2P Clients....\n"));
1338 hdd_clear_all_sta(pHostapdAdapter, usrDataForCallback);
1339 return VOS_STATUS_SUCCESS;
1340
1341 case eSAP_MAC_TRIG_STOP_BSS_EVENT :
1342 hdd_stop_p2p_link(pHostapdAdapter, usrDataForCallback);
1343 return VOS_STATUS_SUCCESS;
1344
Jeff Johnson295189b2012-06-20 16:38:30 -07001345 default:
1346 hddLog(LOG1,"SAP message is not handled\n");
1347 goto stopbss;
1348 return VOS_STATUS_SUCCESS;
1349 }
1350 wireless_send_event(dev, we_event, &wrqu, (char *)we_custom_event_generic);
1351 return VOS_STATUS_SUCCESS;
1352
1353stopbss :
1354 {
1355 v_BYTE_t we_custom_event[64];
1356 char *stopBssEvent = "STOP-BSS.response";//17
1357 int event_len = strlen(stopBssEvent);
1358
1359 hddLog(LOG1, FL("BSS stop status = %s"),
1360 pSapEvent->sapevt.sapStopBssCompleteEvent.status ?
1361 "eSAP_STATUS_FAILURE" : "eSAP_STATUS_SUCCESS");
1362
1363 /* Change the BSS state now since, as we are shutting things down,
1364 * we don't want interfaces to become re-enabled */
1365 pHostapdState->bssState = BSS_STOP;
1366
Gopichand Nakkalaf8fe15d2013-05-27 13:55:40 +05301367 if (0 != (WLAN_HDD_GET_CTX(pHostapdAdapter))->cfg_ini->nAPAutoShutOff)
1368 {
1369 if (VOS_TIMER_STATE_RUNNING == pHddApCtx->hdd_ap_inactivity_timer.state)
1370 {
1371 vos_status = vos_timer_stop(&pHddApCtx->hdd_ap_inactivity_timer);
1372 if (!VOS_IS_STATUS_SUCCESS(vos_status))
1373 hddLog(LOGE, FL("Failed to stop AP inactivity timer"));
1374 }
1375
1376 vos_status = vos_timer_destroy(&pHddApCtx->hdd_ap_inactivity_timer);
1377 if (!VOS_IS_STATUS_SUCCESS(vos_status))
1378 hddLog(LOGE, FL("Failed to Destroy AP inactivity timer"));
1379 }
1380
Jeff Johnson295189b2012-06-20 16:38:30 -07001381 /* Stop the pkts from n/w stack as we are going to free all of
1382 * the TX WMM queues for all STAID's */
1383 hdd_hostapd_stop(dev);
1384
1385 /* reclaim all resources allocated to the BSS */
1386 hdd_softap_stop_bss(pHostapdAdapter);
1387
Amar Singhal37e6f052013-03-05 16:16:54 -08001388 /* once the event is set, structure dev/pHostapdAdapter should
1389 * not be touched since they are now subject to being deleted
1390 * by another thread */
1391 if (eSAP_STOP_BSS_EVENT == sapEvent)
1392 vos_event_set(&pHostapdState->vosEvent);
1393
Jeff Johnson295189b2012-06-20 16:38:30 -07001394 /* notify userspace that the BSS has stopped */
1395 memset(&we_custom_event, '\0', sizeof(we_custom_event));
1396 memcpy(&we_custom_event, stopBssEvent, event_len);
1397 memset(&wrqu, 0, sizeof(wrqu));
1398 wrqu.data.length = event_len;
1399 we_event = IWEVCUSTOM;
1400 we_custom_event_generic = we_custom_event;
1401 wireless_send_event(dev, we_event, &wrqu, (char *)we_custom_event_generic);
Sudhir Sattayappa Kohalli90e4c752013-03-21 14:25:04 -07001402 hdd_dump_concurrency_info(pHddCtx);
Jeff Johnson295189b2012-06-20 16:38:30 -07001403 }
1404 return VOS_STATUS_SUCCESS;
1405}
1406int hdd_softap_unpackIE(
1407 tHalHandle halHandle,
1408 eCsrEncryptionType *pEncryptType,
1409 eCsrEncryptionType *mcEncryptType,
1410 eCsrAuthType *pAuthType,
1411 u_int16_t gen_ie_len,
1412 u_int8_t *gen_ie )
1413{
1414 tDot11fIERSN dot11RSNIE;
1415 tDot11fIEWPA dot11WPAIE;
1416
1417 tANI_U8 *pRsnIe;
1418 tANI_U16 RSNIeLen;
1419
1420 if (NULL == halHandle)
1421 {
1422 hddLog(LOGE, FL("Error haHandle returned NULL\n"));
1423 return -EINVAL;
1424 }
1425
1426 // Validity checks
1427 if ((gen_ie_len < VOS_MIN(DOT11F_IE_RSN_MIN_LEN, DOT11F_IE_WPA_MIN_LEN)) ||
1428 (gen_ie_len > VOS_MAX(DOT11F_IE_RSN_MAX_LEN, DOT11F_IE_WPA_MAX_LEN)) )
1429 return -EINVAL;
1430 // Type check
1431 if ( gen_ie[0] == DOT11F_EID_RSN)
1432 {
1433 // Validity checks
1434 if ((gen_ie_len < DOT11F_IE_RSN_MIN_LEN ) ||
1435 (gen_ie_len > DOT11F_IE_RSN_MAX_LEN) )
1436 {
1437 return VOS_STATUS_E_FAILURE;
1438 }
1439 // Skip past the EID byte and length byte
1440 pRsnIe = gen_ie + 2;
1441 RSNIeLen = gen_ie_len - 2;
1442 // Unpack the RSN IE
1443 memset(&dot11RSNIE, 0, sizeof(tDot11fIERSN));
1444 dot11fUnpackIeRSN((tpAniSirGlobal) halHandle,
1445 pRsnIe,
1446 RSNIeLen,
1447 &dot11RSNIE);
1448 // Copy out the encryption and authentication types
1449 hddLog(LOG1, FL("%s: pairwise cipher suite count: %d\n"),
Madan Mohan Koyyalamudi87054ba2012-11-02 13:24:12 -07001450 __func__, dot11RSNIE.pwise_cipher_suite_count );
Jeff Johnson295189b2012-06-20 16:38:30 -07001451 hddLog(LOG1, FL("%s: authentication suite count: %d\n"),
Madan Mohan Koyyalamudi87054ba2012-11-02 13:24:12 -07001452 __func__, dot11RSNIE.akm_suite_count);
Jeff Johnson295189b2012-06-20 16:38:30 -07001453 /*Here we have followed the apple base code,
1454 but probably I suspect we can do something different*/
1455 //dot11RSNIE.akm_suite_count
1456 // Just translate the FIRST one
1457 *pAuthType = hdd_TranslateRSNToCsrAuthType(dot11RSNIE.akm_suites[0]);
1458 //dot11RSNIE.pwise_cipher_suite_count
1459 *pEncryptType = hdd_TranslateRSNToCsrEncryptionType(dot11RSNIE.pwise_cipher_suites[0]);
1460 //dot11RSNIE.gp_cipher_suite_count
1461 *mcEncryptType = hdd_TranslateRSNToCsrEncryptionType(dot11RSNIE.gp_cipher_suite);
1462 // Set the PMKSA ID Cache for this interface
1463
1464 // Calling csrRoamSetPMKIDCache to configure the PMKIDs into the cache
1465 } else
1466 if (gen_ie[0] == DOT11F_EID_WPA)
1467 {
1468 // Validity checks
1469 if ((gen_ie_len < DOT11F_IE_WPA_MIN_LEN ) ||
1470 (gen_ie_len > DOT11F_IE_WPA_MAX_LEN))
1471 {
1472 return VOS_STATUS_E_FAILURE;
1473 }
1474 // Skip past the EID byte and length byte - and four byte WiFi OUI
1475 pRsnIe = gen_ie + 2 + 4;
1476 RSNIeLen = gen_ie_len - (2 + 4);
1477 // Unpack the WPA IE
1478 memset(&dot11WPAIE, 0, sizeof(tDot11fIEWPA));
1479 dot11fUnpackIeWPA((tpAniSirGlobal) halHandle,
1480 pRsnIe,
1481 RSNIeLen,
1482 &dot11WPAIE);
1483 // Copy out the encryption and authentication types
1484 hddLog(LOG1, FL("%s: WPA unicast cipher suite count: %d\n"),
Madan Mohan Koyyalamudi87054ba2012-11-02 13:24:12 -07001485 __func__, dot11WPAIE.unicast_cipher_count );
Jeff Johnson295189b2012-06-20 16:38:30 -07001486 hddLog(LOG1, FL("%s: WPA authentication suite count: %d\n"),
Madan Mohan Koyyalamudi87054ba2012-11-02 13:24:12 -07001487 __func__, dot11WPAIE.auth_suite_count);
Jeff Johnson295189b2012-06-20 16:38:30 -07001488 //dot11WPAIE.auth_suite_count
1489 // Just translate the FIRST one
1490 *pAuthType = hdd_TranslateWPAToCsrAuthType(dot11WPAIE.auth_suites[0]);
1491 //dot11WPAIE.unicast_cipher_count
1492 *pEncryptType = hdd_TranslateWPAToCsrEncryptionType(dot11WPAIE.unicast_ciphers[0]);
1493 //dot11WPAIE.unicast_cipher_count
1494 *mcEncryptType = hdd_TranslateWPAToCsrEncryptionType(dot11WPAIE.multicast_cipher);
1495 }
1496 else
1497 {
Madan Mohan Koyyalamudi87054ba2012-11-02 13:24:12 -07001498 hddLog(LOGW, FL("%s: gen_ie[0]: %d\n"), __func__, gen_ie[0]);
Jeff Johnson295189b2012-06-20 16:38:30 -07001499 return VOS_STATUS_E_FAILURE;
1500 }
1501 return VOS_STATUS_SUCCESS;
1502}
Leo Chang614d2072013-08-22 14:59:44 -07001503
1504/**---------------------------------------------------------------------------
1505
1506 \brief hdd_hostapd_set_mc_rate_cb() -
1507
1508 This is called to notify associated stas information ready
1509
1510 \param - sapEvent Pointer to get associated stas event
1511 \param - apDriver SoftAP context
1512
1513 \return - none
1514
1515 --------------------------------------------------------------------------*/
1516void hdd_hostapd_set_mc_rate_cb
1517(
1518 tSap_Event *sapEvent,
1519 void *apDriver
1520)
1521{
1522 hdd_ap_ctx_t *apCtxt;
1523
1524 if ((NULL == apDriver) || (NULL == sapEvent))
1525 {
1526 VOS_TRACE(VOS_MODULE_ID_HDD, VOS_TRACE_LEVEL_ERROR,
1527 "%s : Invalid arguments", __func__);
1528 return;
1529 }
1530
1531 apCtxt = (hdd_ap_ctx_t *)apDriver;
1532
1533 /* there is a race condition that exists between this callback function
1534 and the caller since the caller could time out either before or
1535 while this code is executing. we'll assume the timeout hasn't
1536 occurred, but we'll verify that right before complete our work */
1537 if (SAP_GET_STAS_COOKIE == apCtxt->getStasCookie)
1538 {
1539 vos_mem_copy((void *)&apCtxt->getStasEventBuffer,
1540 (void *)sapEvent,
1541 sizeof(tSap_Event));
1542 complete(&apCtxt->sap_get_associated_stas_complete);
1543 }
1544 else
1545 {
1546 VOS_TRACE(VOS_MODULE_ID_HDD, VOS_TRACE_LEVEL_ERROR,
1547 "%s : Invalid cookie", __func__);
1548 }
1549 return;
1550}
1551
1552/**---------------------------------------------------------------------------
1553
1554 \brief hdd_hostapd_set_mc_rate_update
1555
1556 This is called to find rate and send cfg command to FW
1557
1558 \param - sapEvent Pointer to get associated stas event
1559 \param - pHostapdAdapter SoftAP Adapter Context
1560
1561 \return - int, 0 success
1562 negative fail
1563
1564 --------------------------------------------------------------------------*/
1565static int hdd_hostapd_set_mc_rate_update
1566(
1567 tSap_Event *sapEvent,
1568 hdd_adapter_t *pHostapdAdapter
1569)
1570{
1571 tHalHandle hHal;
1572 hdd_ap_ctx_t *apCtxt;
1573 tSap_AssocMacAddr *assocSta;
1574 rate_cfg_11ac_max_mcs_t supportedAcMaxMcs = RATE_CFG_RATE_11AC_MAX_MCS_7;
1575 rate_cfg_supported_bw_t bandWidth;
1576 rate_cfg_gi_t gi;
1577 rate_cfg_item_mapping_t *nMappingTable = NULL;
1578 rate_cfg_item_mapping_t *acMappingTable = NULL;
1579 v_U8_t stasLoop, ratesLoop;
1580 v_U8_t rateArrayOrder;
1581 v_U8_t mcsTable11n;
1582 v_U16_t targetCfgId = 0;
1583 v_U16_t targetCfgValue = 0;
1584 v_U16_t currentRate;
1585 v_U16_t combinedSupportMap = 0xFFFF;
1586 v_U16_t supportMap = 0x0000;
1587 v_U16_t supportedChannelCount = 0;
1588 v_U32_t legacyRates[SAP_LEGACY_RATE_COUNT];
1589 int rc = 0;
1590 tSirRetStatus cfdStat;
1591
1592 if ((NULL == pHostapdAdapter) || (NULL == sapEvent))
1593 {
1594 VOS_TRACE(VOS_MODULE_ID_HDD, VOS_TRACE_LEVEL_ERROR,
1595 "%s : Invalid arguments", __func__);
1596 return -1;
1597 }
1598
1599 apCtxt = WLAN_HDD_GET_AP_CTX_PTR(pHostapdAdapter);
1600 hHal = WLAN_HDD_GET_HAL_CTX(pHostapdAdapter);
1601 VOS_TRACE(VOS_MODULE_ID_HDD, VOS_TRACE_LEVEL_INFO,
1602 "setMcRateCB NUM SAT %d, targetMCRate %d, current channel %d",
1603 sapEvent->sapevt.sapAssocStaListEvent.noOfAssocSta,
1604 apCtxt->targetMCRate,
1605 apCtxt->operatingChannel);
1606
1607 if (!sapEvent->sapevt.sapAssocStaListEvent.noOfAssocSta)
1608 {
1609 VOS_TRACE(VOS_MODULE_ID_HDD, VOS_TRACE_LEVEL_ERROR,
1610 "Not connected any STA yet");
1611 return -1;
1612 }
1613
1614 for (stasLoop = 0;
1615 stasLoop < sapEvent->sapevt.sapAssocStaListEvent.noOfAssocSta;
1616 stasLoop++)
1617 {
Leo Chang473d4e92013-09-13 16:12:33 -07001618 vos_mem_zero((v_U8_t *)legacyRates, sizeof(legacyRates));
Leo Chang614d2072013-08-22 14:59:44 -07001619 rateArrayOrder = 0;
1620 mcsTable11n = 0;
1621 supportedChannelCount = 0;
1622 assocSta = sapEvent->sapevt.sapAssocStaListEvent.pAssocStas++;
1623 VOS_TRACE(VOS_MODULE_ID_HDD, VOS_TRACE_LEVEL_INFO,
1624 "ASSOSID %d, OPM %d, nBM %d, SGI40 %d, SGI20 %d, S40 %d",
1625 assocSta->assocId,
1626 assocSta->supportedRates.opRateMode,
1627 assocSta->supportedRates.aniEnhancedRateBitmap,
1628 assocSta->ShortGI40Mhz,
1629 assocSta->ShortGI20Mhz,
1630 assocSta->Support40Mhz);
1631
1632 /* Legacy Rate */
1633 for (ratesLoop = 0; ratesLoop < SIR_NUM_11B_RATES; ratesLoop++)
1634 {
1635 currentRate = assocSta->supportedRates.llbRates[ratesLoop] &
1636 SAP_LEGACY_RATE_MASK;
1637
1638 /* To fix KW error report */
1639 if (SAP_LEGACY_RATE_COUNT <= rateArrayOrder)
1640 {
1641 VOS_TRACE(VOS_MODULE_ID_HDD, VOS_TRACE_LEVEL_ERROR,
1642 "%s, Invalid array Size, break", __func__);
1643 break;
1644 }
1645
1646 /* Make 100kbps order */
1647 legacyRates[rateArrayOrder] = (currentRate * 100) / 20;
1648 rateArrayOrder++;
1649 if (currentRate)
1650 {
1651 supportedChannelCount++;
1652 }
1653 }
1654 for (ratesLoop = 0; ratesLoop < SIR_NUM_11A_RATES; ratesLoop++)
1655 {
1656 currentRate = assocSta->supportedRates.llaRates[ratesLoop] &
1657 SAP_LEGACY_RATE_MASK;
1658 /* To fix KW error report */
1659 if (SAP_LEGACY_RATE_COUNT <= rateArrayOrder)
1660 {
1661 VOS_TRACE(VOS_MODULE_ID_HDD, VOS_TRACE_LEVEL_ERROR,
1662 "%s, Invalid array Size, break", __func__);
1663 break;
1664 }
1665
1666 /* Make 100kbps order */
1667 legacyRates[rateArrayOrder] = (currentRate * 100) / 20;
1668 rateArrayOrder++;
1669 if (currentRate)
1670 {
1671 supportedChannelCount++;
1672 }
1673 }
1674 if (supportedChannelCount)
1675 {
1676 for (ratesLoop = 0; ratesLoop < SAP_LEGACY_RATE_COUNT; ratesLoop++)
1677 {
1678 if (legacyRates[ratesLoop] == apCtxt->targetMCRate)
1679 {
1680 supportMap |= (1 << RATE_CFG_RATE_LEGACY);
1681 break;
1682 }
1683 }
1684 }
1685
1686 /* 11N */
1687 if (eSTA_11n <= assocSta->supportedRates.opRateMode)
1688 {
1689 if (assocSta->Support40Mhz)
1690 {
1691 mcsTable11n |= 0x01;
1692 if (assocSta->ShortGI40Mhz)
1693 {
1694 mcsTable11n |= 0x02;
1695 supportMap |= (1 << RATE_CFG_RATE_11N_MCS_SGI_40);
1696 nMappingTable = n_s40_rate_mapping;
1697 }
1698 else
1699 {
1700 supportMap |= (1 << RATE_CFG_RATE_11N_MCS_LGI_40);
1701 nMappingTable = n_l40_rate_mapping;
1702 }
1703 }
1704 else
1705 {
1706 if (assocSta->ShortGI20Mhz)
1707 {
1708 mcsTable11n |= 0x02;
1709 supportMap |= (1 << RATE_CFG_RATE_11N_MCS_SGI_20);
1710 nMappingTable = n_s20_rate_mapping;
1711 }
1712 else
1713 {
1714 supportMap |= (1 << RATE_CFG_RATE_11N_MCS_LGI_20);
1715 nMappingTable = n_l20_rate_mapping;
1716 }
1717 }
1718 }
1719
1720#ifdef WLAN_FEATURE_11AC
1721 /* 11AC */
1722 if (eSTA_11ac <= assocSta->supportedRates.opRateMode)
1723 {
1724 /* Find supported MAX MCS */
1725 supportedAcMaxMcs = assocSta->supportedRates.vhtRxMCSMap &
1726 SAP_AC_MCS_MAP_MASK;
1727 supportedAcMaxMcs += SAP_AC_MCS_MAP_OFFSET;
1728 /* Find channel characteristics from MAX rate */
1729 if (mcs_rate_11ac[supportedAcMaxMcs].cb80_rate_11ac[0] ==
1730 assocSta->supportedRates.vhtRxHighestDataRate)
1731 {
1732 supportMap |= (1 << RATE_CFG_RATE_11AC_MCS_LGI_80);
1733 bandWidth = RATE_CFG_RATE_BW_80;
1734 gi = RATE_CFG_RATE_GI_LONG;
1735 acMappingTable = ac_l80_rate_mapping;
1736 }
1737 else if (mcs_rate_11ac[supportedAcMaxMcs].cb80_rate_11ac[1] ==
1738 assocSta->supportedRates.vhtRxHighestDataRate)
1739 {
1740 supportMap |= (1 << RATE_CFG_RATE_11AC_MCS_SGI_80);
1741 bandWidth = RATE_CFG_RATE_BW_80;
1742 gi = RATE_CFG_RATE_GI_SHORT;
1743 acMappingTable = ac_s80_rate_mapping;
1744 }
1745 else if (mcs_rate_11ac[supportedAcMaxMcs].cb40_rate_11ac[0] ==
1746 assocSta->supportedRates.vhtRxHighestDataRate)
1747 {
1748 supportMap |= (1 << RATE_CFG_RATE_11AC_MCS_LGI_40);
1749 bandWidth = RATE_CFG_RATE_BW_40;
1750 gi = RATE_CFG_RATE_GI_LONG;
1751 acMappingTable = ac_l40_rate_mapping;
1752 }
1753 else if (mcs_rate_11ac[supportedAcMaxMcs].cb40_rate_11ac[1] ==
1754 assocSta->supportedRates.vhtRxHighestDataRate)
1755 {
1756 supportMap |= (1 << RATE_CFG_RATE_11AC_MCS_SGI_40);
1757 bandWidth = RATE_CFG_RATE_BW_40;
1758 gi = RATE_CFG_RATE_GI_SHORT;
1759 acMappingTable = ac_s40_rate_mapping;
1760 }
1761 else if (mcs_rate_11ac[supportedAcMaxMcs].cb20_rate_11ac[0] ==
1762 assocSta->supportedRates.vhtRxHighestDataRate)
1763 {
1764 supportMap |= (1 << RATE_CFG_RATE_11AC_MCS_LGI_20);
1765 bandWidth = RATE_CFG_RATE_BW_20;
1766 gi = RATE_CFG_RATE_GI_LONG;
1767 acMappingTable = ac_l20_rate_mapping;
1768 }
1769 else if (mcs_rate_11ac[supportedAcMaxMcs].cb20_rate_11ac[1] ==
1770 assocSta->supportedRates.vhtRxHighestDataRate)
1771 {
1772 supportMap |= (1 << RATE_CFG_RATE_11AC_MCS_SGI_20);
1773 bandWidth = RATE_CFG_RATE_BW_20;
1774 gi = RATE_CFG_RATE_GI_SHORT;
1775 acMappingTable = ac_s20_rate_mapping;
1776 }
1777 }
1778#endif /* WLAN_FEATURE_11AC */
1779 combinedSupportMap &= supportMap;
1780 }
1781
1782 if ((!combinedSupportMap) &&
1783 (!sapEvent->sapevt.sapAssocStaListEvent.noOfAssocSta))
1784 {
1785 VOS_TRACE(VOS_MODULE_ID_HDD, VOS_TRACE_LEVEL_ERROR,
1786 "%s, No Common supported rate, discard", __func__);
1787 return -1;
1788 }
1789
1790 /* Select target band */
1791 if (apCtxt->operatingChannel <=
1792 SAP_MAX_24_CHANNEL_NUMBER)
1793 {
1794 targetCfgId = WNI_CFG_FIXED_RATE_MULTICAST_24GHZ;
1795 }
1796 else
1797 {
1798 targetCfgId = WNI_CFG_FIXED_RATE_MULTICAST_5GHZ;
1799 }
1800
1801 /* First find from legacy */
1802 if (combinedSupportMap & SAP_RATE_SUPPORT_MAP_LEGACY_MASK)
1803 {
1804 for (ratesLoop = 0; ratesLoop < SAP_LEGACY_RATE_COUNT; ratesLoop++)
1805 {
1806 if (apCtxt->targetMCRate ==
1807 legacy_rate_mapping[ratesLoop].rate)
1808 {
1809 targetCfgValue = legacy_rate_mapping[ratesLoop].eRateCfg;
1810 break;
1811 }
1812 }
1813 }
1814
1815 /* If available same on 11N, update target rate */
1816 if ((combinedSupportMap & SAP_RATE_SUPPORT_MAP_N_MASK) &&
1817 (NULL != nMappingTable))
1818 {
1819 for (ratesLoop = 0; ratesLoop < SAP_11N_RATE_COUNT; ratesLoop++)
1820 {
1821 if (apCtxt->targetMCRate == nMappingTable[ratesLoop].rate)
1822 {
1823 targetCfgValue = nMappingTable[ratesLoop].eRateCfg;
1824 break;
1825 }
1826 }
1827 }
1828
1829#ifdef WLAN_FEATURE_11AC
1830 /* If available same on 11AC, update target rate */
1831 if ((combinedSupportMap & SAP_RATE_SUPPORT_MAP_AC_MASK) &&
1832 (NULL != acMappingTable))
1833 {
1834 for (ratesLoop = 0; ratesLoop < supportedAcMaxMcs; ratesLoop++)
1835 {
1836 if (apCtxt->targetMCRate == acMappingTable[ratesLoop].rate)
1837 {
1838 targetCfgValue = acMappingTable[ratesLoop].eRateCfg;
1839 break;
1840 }
1841 }
1842 }
1843#endif /* WLAN_FEATURE_11AC */
1844
1845 /* Finally send config to FW */
1846 if (targetCfgId && targetCfgValue)
1847 {
1848 VOS_TRACE(VOS_MODULE_ID_HDD, VOS_TRACE_LEVEL_INFO,
1849 "%s, Target Band %d, cfg value %d",
1850 __func__, targetCfgId, targetCfgValue);
1851 cfdStat = cfgSetInt((tpAniSirGlobal)hHal,
1852 targetCfgId,
1853 targetCfgValue);
1854 if (eSIR_SUCCESS != cfdStat)
1855 {
1856 VOS_TRACE(VOS_MODULE_ID_HDD, VOS_TRACE_LEVEL_ERROR,
1857 "%s, CFG Fail %d",
1858 __func__, cfdStat);
1859 rc = -1;
1860 }
1861 }
1862
1863 return rc;
1864};
1865
1866/**---------------------------------------------------------------------------
1867
1868 \brief hdd_hostapd_set_mc_rate() -
1869
1870 This is called user application set forcefully MC rate
1871
1872 \param - pHostapdAdapter Pointer to adapter structure
1873 \param - targetRateHkbps MC rate to set, hundreds kbps order
1874
1875 \return - int, 0 success
1876 negative fail
1877
1878 --------------------------------------------------------------------------*/
1879int hdd_hostapd_set_mc_rate
1880(
1881 hdd_adapter_t *pHostapdAdapter,
1882 int targetRateHkbps
1883)
1884{
1885 tHalHandle hHal;
1886 hdd_ap_ctx_t *apCtxt;
1887 eHalStatus smeStatus;
1888 int rc;
1889
1890 if ((NULL == pHostapdAdapter) || (0 == targetRateHkbps))
1891 {
1892 VOS_TRACE(VOS_MODULE_ID_HDD, VOS_TRACE_LEVEL_ERROR,
1893 "%s : Invalid arguments", __func__);
1894 return -1;
1895 }
1896
1897 apCtxt = WLAN_HDD_GET_AP_CTX_PTR(pHostapdAdapter);
1898 hHal = WLAN_HDD_GET_HAL_CTX(pHostapdAdapter);
1899 VOS_TRACE(VOS_MODULE_ID_HDD, VOS_TRACE_LEVEL_INFO,
1900 "hdd_hostapd_setMcRate %d", targetRateHkbps);
1901
1902 init_completion(&apCtxt->sap_get_associated_stas_complete);
1903
1904 apCtxt->getStasCookie = SAP_GET_STAS_COOKIE;
1905 apCtxt->targetMCRate = targetRateHkbps;
1906 apCtxt->getStasEventBuffer.sapevt.sapAssocStaListEvent.noOfAssocSta = 0;
1907 apCtxt->assocStasBuffer = (tSap_AssocMacAddr *)vos_mem_malloc(
1908 sizeof(tSap_AssocMacAddr) * HAL_NUM_ASSOC_STA);
1909 if (NULL == apCtxt->assocStasBuffer)
1910 {
1911 VOS_TRACE(VOS_MODULE_ID_HDD, VOS_TRACE_LEVEL_ERROR,
1912 "%s : Buffer Alloc fail", __func__);
1913 return -1;
1914 }
1915 smeStatus = sme_RoamGetAssociatedStas(hHal,
1916 pHostapdAdapter->sessionId,
1917 VOS_MODULE_ID_HDD,
1918 (void *)apCtxt,
1919 hdd_hostapd_set_mc_rate_cb,
1920 (tANI_U8 *)apCtxt->assocStasBuffer);
1921 if (smeStatus)
1922 {
1923 apCtxt->getStasCookie = 0;
1924 vos_mem_free(apCtxt->assocStasBuffer);
1925 apCtxt->assocStasBuffer = NULL;
1926 VOS_TRACE(VOS_MODULE_ID_HDD, VOS_TRACE_LEVEL_ERROR,
1927 "%s : SME Issue fail", __func__);
1928 return -1;
1929 }
1930
1931 /* Wait for completion */
1932 rc = wait_for_completion_interruptible_timeout(
1933 &apCtxt->sap_get_associated_stas_complete,
1934 msecs_to_jiffies(SAP_MAX_GET_ASSOC_STAS_TIMEOUT));
1935
1936 /* either we have a response or we timed out
1937 either way, first invalidate our cookie */
1938 apCtxt->getStasCookie = 0;
1939 if (0 >= rc)
1940 {
1941 VOS_TRACE(VOS_MODULE_ID_HDD, VOS_TRACE_LEVEL_ERROR,
1942 "%s : Wait timeout or interrupted", __func__);
1943
1944 /* there is a race condition such that the callback
1945 function could be executing at the same time we are. of
1946 primary concern is if the callback function had already
1947 verified the "magic" but hasn't yet set the completion
1948 variable. Since the completion variable is on our
1949 stack, we'll delay just a bit to make sure the data is
1950 still valid if that is the case */
1951 vos_sleep(50);
1952 /* we'll now try to test memory */
1953 }
1954
1955 rc = hdd_hostapd_set_mc_rate_update(
1956 &apCtxt->getStasEventBuffer,
1957 pHostapdAdapter);
1958 vos_mem_free(apCtxt->assocStasBuffer);
1959 apCtxt->assocStasBuffer = NULL;
1960
1961 return rc;
1962}
1963
Jeff Johnson295189b2012-06-20 16:38:30 -07001964int
1965static iw_softap_setparam(struct net_device *dev,
1966 struct iw_request_info *info,
1967 union iwreq_data *wrqu, char *extra)
1968{
1969 hdd_adapter_t *pHostapdAdapter = (netdev_priv(dev));
1970 tHalHandle hHal = WLAN_HDD_GET_HAL_CTX(pHostapdAdapter);
1971 int *value = (int *)extra;
1972 int sub_cmd = value[0];
1973 int set_value = value[1];
1974 eHalStatus status;
1975 int ret = 0; /* success */
1976 v_CONTEXT_t pVosContext = (WLAN_HDD_GET_CTX(pHostapdAdapter))->pvosContext;
1977
1978 switch(sub_cmd)
1979 {
1980
1981 case QCSAP_PARAM_CLR_ACL:
Jeff Johnson43971f52012-07-17 12:26:56 -07001982 if ( VOS_STATUS_SUCCESS != WLANSAP_ClearACL( pVosContext ))
Jeff Johnson295189b2012-06-20 16:38:30 -07001983 {
1984 ret = -EIO;
1985 }
1986 break;
1987
1988 case QCSAP_PARAM_ACL_MODE:
1989 if ((eSAP_ALLOW_ALL < (eSapMacAddrACL)set_value) ||
1990 (eSAP_ACCEPT_UNLESS_DENIED > (eSapMacAddrACL)set_value))
1991 {
1992 hddLog(LOGE, FL("Invalid ACL Mode value %d"), set_value);
1993 ret = -EINVAL;
1994 }
1995 else
1996 {
1997 WLANSAP_SetMode(pVosContext, set_value);
1998 }
1999 break;
2000 case QCSAP_PARAM_MAX_ASSOC:
2001 if (WNI_CFG_ASSOC_STA_LIMIT_STAMIN > set_value)
2002 {
2003 hddLog(LOGE, FL("Invalid setMaxAssoc value %d"), set_value);
2004 ret = -EINVAL;
2005 }
2006 else
2007 {
2008 if (WNI_CFG_ASSOC_STA_LIMIT_STAMAX < set_value)
2009 {
2010 hddLog(LOGW, FL("setMaxAssoc value %d higher than max allowed %d."
2011 "Setting it to max allowed and continuing"),
2012 set_value, WNI_CFG_ASSOC_STA_LIMIT_STAMAX);
2013 set_value = WNI_CFG_ASSOC_STA_LIMIT_STAMAX;
2014 }
2015 status = ccmCfgSetInt(hHal, WNI_CFG_ASSOC_STA_LIMIT,
2016 set_value, NULL, eANI_BOOLEAN_FALSE);
2017 if ( status != eHAL_STATUS_SUCCESS )
2018 {
2019 hddLog(LOGE, FL("setMaxAssoc failure, status %d"),
2020 status);
2021 ret = -EIO;
2022 }
2023 }
2024 break;
2025
2026 case QCSAP_PARAM_HIDE_SSID:
2027 {
2028 eHalStatus status = eHAL_STATUS_SUCCESS;
2029 status = sme_HideSSID(hHal, pHostapdAdapter->sessionId, set_value);
2030 if(eHAL_STATUS_SUCCESS != status)
2031 {
2032 hddLog(VOS_TRACE_LEVEL_ERROR,
2033 "%s: QCSAP_PARAM_HIDE_SSID failed",
Madan Mohan Koyyalamudi87054ba2012-11-02 13:24:12 -07002034 __func__);
Jeff Johnson295189b2012-06-20 16:38:30 -07002035 return status;
2036 }
2037 break;
2038 }
2039
Leo Chang614d2072013-08-22 14:59:44 -07002040 case QCSAP_PARAM_SET_MC_RATE:
2041 {
2042 if (hdd_hostapd_set_mc_rate(pHostapdAdapter, set_value))
2043 {
2044 hddLog(VOS_TRACE_LEVEL_ERROR,
2045 "%s: SET_MC_RATE failed", __func__);
2046 }
2047 break;
2048 }
2049
Jeff Johnson295189b2012-06-20 16:38:30 -07002050 default:
2051 hddLog(LOGE, FL("Invalid setparam command %d value %d"),
2052 sub_cmd, set_value);
2053 ret = -EINVAL;
2054 break;
2055 }
2056
2057 return ret;
2058}
2059
2060
2061int
2062static iw_softap_getparam(struct net_device *dev,
2063 struct iw_request_info *info,
2064 union iwreq_data *wrqu, char *extra)
2065{
2066 hdd_adapter_t *pHostapdAdapter = (netdev_priv(dev));
2067 tHalHandle hHal = WLAN_HDD_GET_HAL_CTX(pHostapdAdapter);
2068 int *value = (int *)extra;
2069 int sub_cmd = value[0];
2070 eHalStatus status;
2071 int ret = 0; /* success */
2072 v_CONTEXT_t pVosContext = (WLAN_HDD_GET_CTX(pHostapdAdapter))->pvosContext;
2073
2074 switch (sub_cmd)
2075 {
2076 case QCSAP_PARAM_MAX_ASSOC:
2077 status = ccmCfgGetInt(hHal, WNI_CFG_ASSOC_STA_LIMIT, (tANI_U32 *)value);
2078 if (eHAL_STATUS_SUCCESS != status)
2079 {
2080 ret = -EIO;
2081 }
2082 break;
2083
2084 case QCSAP_PARAM_CLR_ACL:
Jeff Johnson43971f52012-07-17 12:26:56 -07002085 if ( VOS_STATUS_SUCCESS != WLANSAP_ClearACL( pVosContext ))
Jeff Johnson295189b2012-06-20 16:38:30 -07002086 {
2087 ret = -EIO;
2088 }
2089 *value = 0;
2090 break;
2091
2092 case QCSAP_PARAM_MODULE_DOWN_IND:
2093 {
2094 VOS_TRACE(VOS_MODULE_ID_HDD, VOS_TRACE_LEVEL_INFO,
Madan Mohan Koyyalamudi87054ba2012-11-02 13:24:12 -07002095 "%s: sending WLAN_MODULE_DOWN_IND", __func__);
Jeff Johnson295189b2012-06-20 16:38:30 -07002096 send_btc_nlink_msg(WLAN_MODULE_DOWN_IND, 0);
2097#ifdef WLAN_BTAMP_FEATURE
2098 VOS_TRACE(VOS_MODULE_ID_HDD, VOS_TRACE_LEVEL_INFO,
Madan Mohan Koyyalamudi87054ba2012-11-02 13:24:12 -07002099 "%s: Take down AMP PAL", __func__);
Jeff Johnson295189b2012-06-20 16:38:30 -07002100 BSL_Deinit(vos_get_global_context(VOS_MODULE_ID_HDD, NULL));
2101#endif
2102 *value = 0;
2103 break;
Jeff Johnson43971f52012-07-17 12:26:56 -07002104 }
2105
2106 case QCSAP_PARAM_GET_WLAN_DBG:
2107 {
2108 vos_trace_display();
2109 *value = 0;
2110 break;
2111 }
2112
2113 case QCSAP_PARAM_AUTO_CHANNEL:
2114 {
2115 *value = (WLAN_HDD_GET_CTX(pHostapdAdapter))->cfg_ini->apAutoChannelSelection;
2116 break;
2117 }
2118
Jeff Johnson295189b2012-06-20 16:38:30 -07002119 default:
2120 hddLog(LOGE, FL("Invalid getparam command %d"), sub_cmd);
2121 ret = -EINVAL;
2122 break;
2123
2124 }
2125
2126 return ret;
2127}
2128
2129/* Usage:
2130 BLACK_LIST = 0
2131 WHITE_LIST = 1
2132 ADD MAC = 0
2133 REMOVE MAC = 1
2134
2135 mac addr will be accepted as a 6 octet mac address with each octet inputted in hex
2136 for e.g. 00:0a:f5:11:22:33 will be represented as 0x00 0x0a 0xf5 0x11 0x22 0x33
2137 while using this ioctl
2138
2139 Syntax:
2140 iwpriv softap.0 modify_acl
2141 <6 octet mac addr> <list type> <cmd type>
2142
2143 Examples:
2144 eg 1. to add a mac addr 00:0a:f5:89:89:90 to the black list
2145 iwpriv softap.0 modify_acl 0x00 0x0a 0xf5 0x89 0x89 0x90 0 0
2146 eg 2. to delete a mac addr 00:0a:f5:89:89:90 from white list
2147 iwpriv softap.0 modify_acl 0x00 0x0a 0xf5 0x89 0x89 0x90 1 1
2148*/
2149int iw_softap_modify_acl(struct net_device *dev, struct iw_request_info *info,
2150 union iwreq_data *wrqu, char *extra)
2151{
2152 hdd_adapter_t *pHostapdAdapter = (netdev_priv(dev));
2153 v_CONTEXT_t pVosContext = (WLAN_HDD_GET_CTX(pHostapdAdapter))->pvosContext;
2154 v_BYTE_t *value = (v_BYTE_t*)extra;
2155 v_U8_t pPeerStaMac[VOS_MAC_ADDR_SIZE];
2156 int listType, cmd, i;
2157 int ret = 0; /* success */
2158
2159 ENTER();
2160 for (i=0; i<VOS_MAC_ADDR_SIZE; i++)
2161 {
2162 pPeerStaMac[i] = *(value+i);
2163 }
2164 listType = (int)(*(value+i));
2165 i++;
2166 cmd = (int)(*(value+i));
2167
2168 hddLog(LOG1, "%s: SAP Modify ACL arg0 %02x:%02x:%02x:%02x:%02x:%02x arg1 %d arg2 %d\n",
Madan Mohan Koyyalamudi87054ba2012-11-02 13:24:12 -07002169 __func__, pPeerStaMac[0], pPeerStaMac[1], pPeerStaMac[2],
Jeff Johnson295189b2012-06-20 16:38:30 -07002170 pPeerStaMac[3], pPeerStaMac[4], pPeerStaMac[5], listType, cmd);
2171
2172 if (WLANSAP_ModifyACL(pVosContext, pPeerStaMac,(eSapACLType)listType,(eSapACLCmdType)cmd)
2173 != VOS_STATUS_SUCCESS)
2174 {
2175 hddLog(LOGE, FL("Modify ACL failed\n"));
2176 ret = -EIO;
2177 }
2178 EXIT();
2179 return ret;
2180}
2181
2182int
2183static iw_softap_getchannel(struct net_device *dev,
2184 struct iw_request_info *info,
2185 union iwreq_data *wrqu, char *extra)
2186{
2187 hdd_adapter_t *pHostapdAdapter = (netdev_priv(dev));
2188
Jeff Johnson43971f52012-07-17 12:26:56 -07002189 int *value = (int *)extra;
Jeff Johnson295189b2012-06-20 16:38:30 -07002190
Jeff Johnson43971f52012-07-17 12:26:56 -07002191 *value = (WLAN_HDD_GET_AP_CTX_PTR(pHostapdAdapter))->operatingChannel;
Jeff Johnson295189b2012-06-20 16:38:30 -07002192 return 0;
2193}
2194
Jeff Johnsone7245742012-09-05 17:12:55 -07002195int
schang86c22c42013-03-13 18:41:24 -07002196static iw_softap_set_max_tx_power(struct net_device *dev,
Jeff Johnsone7245742012-09-05 17:12:55 -07002197 struct iw_request_info *info,
2198 union iwreq_data *wrqu, char *extra)
2199{
2200 hdd_adapter_t *pHostapdAdapter = (netdev_priv(dev));
2201 tHalHandle hHal = WLAN_HDD_GET_HAL_CTX(pHostapdAdapter);
schang86c22c42013-03-13 18:41:24 -07002202 int *value = (int *)extra;
Jeff Johnsone7245742012-09-05 17:12:55 -07002203 int set_value;
2204 tSirMacAddr bssid = {0xFF,0xFF,0xFF,0xFF,0xFF,0xFF};
2205 tSirMacAddr selfMac = {0xFF,0xFF,0xFF,0xFF,0xFF,0xFF};
2206
schang86c22c42013-03-13 18:41:24 -07002207 if (NULL == value)
Jeff Johnsone7245742012-09-05 17:12:55 -07002208 return -ENOMEM;
2209
Leo Changd37675a2013-08-01 13:19:45 -07002210 /* Assign correct slef MAC address */
2211 vos_mem_copy(bssid, pHostapdAdapter->macAddressCurrent.bytes,
2212 VOS_MAC_ADDR_SIZE);
2213 vos_mem_copy(selfMac, pHostapdAdapter->macAddressCurrent.bytes,
2214 VOS_MAC_ADDR_SIZE);
2215
schang86c22c42013-03-13 18:41:24 -07002216 set_value = value[0];
2217 if (eHAL_STATUS_SUCCESS != sme_SetMaxTxPower(hHal, bssid, selfMac, set_value))
2218 {
2219 hddLog(VOS_TRACE_LEVEL_ERROR, "%s: Setting maximum tx power failed",
Madan Mohan Koyyalamudi87054ba2012-11-02 13:24:12 -07002220 __func__);
schang86c22c42013-03-13 18:41:24 -07002221 return -EIO;
2222 }
2223
2224 return 0;
2225}
2226
2227int
Madan Mohan Koyyalamudia96f5442013-05-10 11:32:06 +05302228static iw_display_data_path_snapshot(struct net_device *dev,
2229 struct iw_request_info *info,
2230 union iwreq_data *wrqu, char *extra)
2231{
2232
2233 /* Function intitiating dumping states of
2234 * HDD(WMM Tx Queues)
2235 * TL State (with Per Client infor)
2236 * DXE Snapshot (Called at the end of TL Snapshot)
2237 */
2238 hdd_adapter_t *pHostapdAdapter = (netdev_priv(dev));
2239 hddLog(LOGE, "%s: called for SAP",__func__);
2240 hdd_wmm_tx_snapshot(pHostapdAdapter);
2241 WLANTL_TLDebugMessage(VOS_TRUE);
2242 return 0;
2243}
2244
2245int
schang86c22c42013-03-13 18:41:24 -07002246static iw_softap_set_tx_power(struct net_device *dev,
2247 struct iw_request_info *info,
2248 union iwreq_data *wrqu, char *extra)
2249{
2250 hdd_adapter_t *pHostapdAdapter = (netdev_priv(dev));
2251 v_CONTEXT_t pVosContext = (WLAN_HDD_GET_CTX(pHostapdAdapter))->pvosContext;
2252 tHalHandle hHal = WLAN_HDD_GET_HAL_CTX(pHostapdAdapter);
2253 int *value = (int *)extra;
2254 int set_value;
2255 ptSapContext pSapCtx = NULL;
2256
2257 if (NULL == value)
2258 return -ENOMEM;
2259
2260 pSapCtx = VOS_GET_SAP_CB(pVosContext);
2261 if (NULL == pSapCtx)
2262 {
2263 VOS_TRACE(VOS_MODULE_ID_SAP, VOS_TRACE_LEVEL_ERROR,
2264 "%s: Invalid SAP pointer from pvosGCtx", __func__);
2265 return VOS_STATUS_E_FAULT;
Jeff Johnsone7245742012-09-05 17:12:55 -07002266 }
2267
2268 set_value = value[0];
schang86c22c42013-03-13 18:41:24 -07002269 if (eHAL_STATUS_SUCCESS != sme_SetTxPower(hHal, pSapCtx->sessionId, set_value))
Jeff Johnsone7245742012-09-05 17:12:55 -07002270 {
schang86c22c42013-03-13 18:41:24 -07002271 hddLog(VOS_TRACE_LEVEL_ERROR, "%s: Setting tx power failed",
Jeff Johnsone7245742012-09-05 17:12:55 -07002272 __func__);
2273 return -EIO;
2274 }
2275
2276 return 0;
2277}
2278
Kiet Lambcf38522013-10-26 18:28:27 +05302279/**---------------------------------------------------------------------------
2280
2281 \brief iw_softap_set_trafficmonitor() -
2282 This function dynamically enable/disable traffic monitor functonality
2283 the command iwpriv wlanX setTrafficMon <value>.
2284
2285 \param - dev - Pointer to the net device.
2286 - addr - Pointer to the sockaddr.
2287 \return - 0 for success, non zero for failure
2288
2289 --------------------------------------------------------------------------*/
2290
2291static int iw_softap_set_trafficmonitor(struct net_device *dev,
2292 struct iw_request_info *info,
2293 union iwreq_data *wrqu, char *extra)
2294{
2295 hdd_adapter_t *pAdapter = WLAN_HDD_GET_PRIV_PTR(dev);
2296 int *isSetTrafficMon = (int *)wrqu->data.pointer;
2297 hdd_context_t *pHddCtx;
2298 int status;
2299
2300 if (NULL == pAdapter)
2301 {
2302 VOS_TRACE( VOS_MODULE_ID_SAP, VOS_TRACE_LEVEL_ERROR,
2303 "%s: HDD adapter is Null", __func__);
2304 return -ENODEV;
2305 }
2306
2307 pHddCtx = WLAN_HDD_GET_CTX(pAdapter);
2308
2309 status = wlan_hdd_validate_context(pHddCtx);
2310
2311 if (0 != status)
2312 {
2313 VOS_TRACE( VOS_MODULE_ID_HDD, VOS_TRACE_LEVEL_ERROR,
2314 "%s: HDD context is not valid", __func__);
2315 return status;
2316 }
2317
2318 hddLog(VOS_TRACE_LEVEL_INFO, "%s : ", __func__);
2319
2320 if (NULL == isSetTrafficMon)
2321 {
2322 VOS_TRACE(VOS_MODULE_ID_SAP, VOS_TRACE_LEVEL_ERROR,
2323 "%s: Invalid SAP pointer from extra", __func__);
2324 return -ENOMEM;
2325 }
2326
2327 if (TRUE == *isSetTrafficMon)
2328 {
2329 pHddCtx->cfg_ini->enableTrafficMonitor= TRUE;
2330 if (VOS_STATUS_SUCCESS != hdd_start_trafficMonitor(pAdapter))
2331 {
2332 VOS_TRACE( VOS_MODULE_ID_HDD_SOFTAP, VOS_TRACE_LEVEL_ERROR,
2333 "%s: failed to Start Traffic Monitor timer ", __func__ );
2334 return -EIO;
2335 }
2336 }
2337 else if (FALSE == *isSetTrafficMon)
2338 {
2339 pHddCtx->cfg_ini->enableTrafficMonitor= FALSE;
2340 if (VOS_STATUS_SUCCESS != hdd_stop_trafficMonitor(pAdapter))
2341 {
2342 VOS_TRACE( VOS_MODULE_ID_HDD_SOFTAP, VOS_TRACE_LEVEL_ERROR,
2343 "%s: failed to Stop Traffic Monitor timer ", __func__ );
2344 return -EIO;
2345 }
2346
2347 }
2348 return 0;
2349}
2350
Jeff Johnson295189b2012-06-20 16:38:30 -07002351#define IS_BROADCAST_MAC(x) (((x[0] & x[1] & x[2] & x[3] & x[4] & x[5]) == 0xff) ? 1 : 0)
2352
2353int
2354static iw_softap_getassoc_stamacaddr(struct net_device *dev,
2355 struct iw_request_info *info,
2356 union iwreq_data *wrqu, char *extra)
2357{
2358 hdd_adapter_t *pHostapdAdapter = (netdev_priv(dev));
2359 unsigned char *pmaclist;
2360 hdd_station_info_t *pStaInfo = pHostapdAdapter->aStaInfo;
2361 int cnt = 0, len;
2362
2363
2364 pmaclist = wrqu->data.pointer + sizeof(unsigned long int);
2365 len = wrqu->data.length;
2366
2367 spin_lock_bh( &pHostapdAdapter->staInfo_lock );
2368 while((cnt < WLAN_MAX_STA_COUNT) && (len > (sizeof(v_MACADDR_t)+1))) {
2369 if (TRUE == pStaInfo[cnt].isUsed) {
2370
2371 if(!IS_BROADCAST_MAC(pStaInfo[cnt].macAddrSTA.bytes)) {
2372 memcpy((void *)pmaclist, (void *)&(pStaInfo[cnt].macAddrSTA), sizeof(v_MACADDR_t));
2373 pmaclist += sizeof(v_MACADDR_t);
2374 len -= sizeof(v_MACADDR_t);
2375 }
2376 }
2377 cnt++;
2378 }
2379 spin_unlock_bh( &pHostapdAdapter->staInfo_lock );
2380
2381 *pmaclist = '\0';
2382
2383 wrqu->data.length -= len;
2384
2385 *(unsigned long int *)(wrqu->data.pointer) = wrqu->data.length;
2386
2387 return 0;
2388}
2389
2390/* Usage:
2391 mac addr will be accepted as a 6 octet mac address with each octet inputted in hex
2392 for e.g. 00:0a:f5:11:22:33 will be represented as 0x00 0x0a 0xf5 0x11 0x22 0x33
2393 while using this ioctl
2394
2395 Syntax:
2396 iwpriv softap.0 disassoc_sta <6 octet mac address>
2397
2398 e.g.
2399 disassociate sta with mac addr 00:0a:f5:11:22:33 from softap
2400 iwpriv softap.0 disassoc_sta 0x00 0x0a 0xf5 0x11 0x22 0x33
2401*/
2402
2403int
2404static iw_softap_disassoc_sta(struct net_device *dev,
2405 struct iw_request_info *info,
2406 union iwreq_data *wrqu, char *extra)
2407{
2408 hdd_adapter_t *pHostapdAdapter = (netdev_priv(dev));
2409 v_U8_t *peerMacAddr;
2410
2411 ENTER();
Gopichand Nakkala252c9ef2013-02-27 17:01:23 +05302412 /* iwpriv tool or framework calls this ioctl with
2413 * data passed in extra (less than 16 octets);
Jeff Johnson295189b2012-06-20 16:38:30 -07002414 */
Gopichand Nakkala252c9ef2013-02-27 17:01:23 +05302415 peerMacAddr = (v_U8_t *)(extra);
Jeff Johnson295189b2012-06-20 16:38:30 -07002416
2417 hddLog(LOG1, "data %02x:%02x:%02x:%02x:%02x:%02x",
2418 peerMacAddr[0], peerMacAddr[1], peerMacAddr[2],
2419 peerMacAddr[3], peerMacAddr[4], peerMacAddr[5]);
2420 hdd_softap_sta_disassoc(pHostapdAdapter, peerMacAddr);
2421 EXIT();
2422 return 0;
2423}
2424
2425int
2426static iw_softap_ap_stats(struct net_device *dev,
2427 struct iw_request_info *info,
2428 union iwreq_data *wrqu, char *extra)
2429{
2430 hdd_adapter_t *pHostapdAdapter = (netdev_priv(dev));
2431 WLANTL_TRANSFER_STA_TYPE statBuffer;
2432 char *pstatbuf;
2433 int len = wrqu->data.length;
2434 pstatbuf = wrqu->data.pointer;
2435
2436 WLANSAP_GetStatistics((WLAN_HDD_GET_CTX(pHostapdAdapter))->pvosContext, &statBuffer, (v_BOOL_t)wrqu->data.flags);
2437
Sameer Thalappilb0a30232013-09-27 15:37:48 -07002438 len = scnprintf(pstatbuf, len,
Jeff Johnson295189b2012-06-20 16:38:30 -07002439 "RUF=%d RMF=%d RBF=%d "
2440 "RUB=%d RMB=%d RBB=%d "
2441 "TUF=%d TMF=%d TBF=%d "
2442 "TUB=%d TMB=%d TBB=%d",
2443 (int)statBuffer.rxUCFcnt, (int)statBuffer.rxMCFcnt, (int)statBuffer.rxBCFcnt,
2444 (int)statBuffer.rxUCBcnt, (int)statBuffer.rxMCBcnt, (int)statBuffer.rxBCBcnt,
2445 (int)statBuffer.txUCFcnt, (int)statBuffer.txMCFcnt, (int)statBuffer.txBCFcnt,
2446 (int)statBuffer.txUCBcnt, (int)statBuffer.txMCBcnt, (int)statBuffer.txBCBcnt
2447 );
2448
2449 wrqu->data.length -= len;
2450 return 0;
2451}
2452
2453int
2454static iw_softap_commit(struct net_device *dev,
2455 struct iw_request_info *info,
2456 union iwreq_data *wrqu, char *extra)
2457{
2458 VOS_STATUS vos_status = VOS_STATUS_SUCCESS;
2459 hdd_adapter_t *pHostapdAdapter = (netdev_priv(dev));
2460 hdd_hostapd_state_t *pHostapdState;
2461 v_CONTEXT_t pVosContext = (WLAN_HDD_GET_CTX(pHostapdAdapter))->pvosContext;
2462 tpWLAN_SAPEventCB pSapEventCallback;
2463 tsap_Config_t *pConfig;
2464 s_CommitConfig_t *pCommitConfig;
2465 struct qc_mac_acl_entry *acl_entry = NULL;
2466 v_SINT_t i = 0, num_mac = 0;
2467 v_U32_t status = 0;
2468 eCsrAuthType RSNAuthType;
2469 eCsrEncryptionType RSNEncryptType;
2470 eCsrEncryptionType mcRSNEncryptType;
2471
2472 pHostapdState = WLAN_HDD_GET_HOSTAP_STATE_PTR(pHostapdAdapter);
2473 pCommitConfig = (s_CommitConfig_t *)extra;
2474
2475 pConfig = kmalloc(sizeof(tsap_Config_t), GFP_KERNEL);
2476 if(NULL == pConfig) {
2477 hddLog(LOG1, "VOS unable to allocate memory\n");
2478 return -ENOMEM;
2479 }
2480 pConfig->beacon_int = pCommitConfig->beacon_int;
2481 pConfig->channel = pCommitConfig->channel;
2482
2483 /*Protection parameter to enable or disable*/
2484 pConfig->protEnabled = (WLAN_HDD_GET_CTX(pHostapdAdapter))->cfg_ini->apProtEnabled;
2485 pConfig->dtim_period = pCommitConfig->dtim_period;
2486 switch(pCommitConfig->hw_mode )
2487 {
2488 case eQC_DOT11_MODE_11A:
2489 pConfig->SapHw_mode = eSAP_DOT11_MODE_11a;
2490 break;
2491 case eQC_DOT11_MODE_11B:
2492 pConfig->SapHw_mode = eSAP_DOT11_MODE_11b;
2493 break;
2494 case eQC_DOT11_MODE_11G:
2495 pConfig->SapHw_mode = eSAP_DOT11_MODE_11g;
2496 break;
2497
2498 case eQC_DOT11_MODE_11N:
2499 pConfig->SapHw_mode = eSAP_DOT11_MODE_11n;
2500 break;
2501 case eQC_DOT11_MODE_11G_ONLY:
2502 pConfig->SapHw_mode = eSAP_DOT11_MODE_11g_ONLY;
2503 break;
2504 case eQC_DOT11_MODE_11N_ONLY:
2505 pConfig->SapHw_mode = eSAP_DOT11_MODE_11n_ONLY;
2506 break;
2507 default:
2508 pConfig->SapHw_mode = eSAP_DOT11_MODE_11n;
2509 break;
2510
2511 }
2512
2513 pConfig->ieee80211d = pCommitConfig->qcsap80211d;
2514 vos_mem_copy(pConfig->countryCode, pCommitConfig->countryCode, 3);
2515 if(pCommitConfig->authType == eQC_AUTH_TYPE_SHARED_KEY)
2516 pConfig->authType = eSAP_SHARED_KEY;
2517 else if(pCommitConfig->authType == eQC_AUTH_TYPE_OPEN_SYSTEM)
2518 pConfig->authType = eSAP_OPEN_SYSTEM;
2519 else
2520 pConfig->authType = eSAP_AUTO_SWITCH;
2521
2522 pConfig->privacy = pCommitConfig->privacy;
2523 (WLAN_HDD_GET_AP_CTX_PTR(pHostapdAdapter))->uPrivacy = pCommitConfig->privacy;
2524 pConfig->wps_state = pCommitConfig->wps_state;
2525 pConfig->fwdWPSPBCProbeReq = 1; // Forward WPS PBC probe request frame up
2526 pConfig->RSNWPAReqIELength = pCommitConfig->RSNWPAReqIELength;
2527 if(pConfig->RSNWPAReqIELength){
2528 pConfig->pRSNWPAReqIE = &pCommitConfig->RSNWPAReqIE[0];
2529 if ((pConfig->pRSNWPAReqIE[0] == DOT11F_EID_RSN) || (pConfig->pRSNWPAReqIE[0] == DOT11F_EID_WPA)){
2530 // The actual processing may eventually be more extensive than this.
2531 // Right now, just consume any PMKIDs that are sent in by the app.
2532 status = hdd_softap_unpackIE(
Jeff Johnson295189b2012-06-20 16:38:30 -07002533 vos_get_context( VOS_MODULE_ID_PE, pVosContext),
Jeff Johnson295189b2012-06-20 16:38:30 -07002534 &RSNEncryptType,
2535 &mcRSNEncryptType,
2536 &RSNAuthType,
2537 pConfig->pRSNWPAReqIE[1]+2,
2538 pConfig->pRSNWPAReqIE );
2539
2540 if( VOS_STATUS_SUCCESS == status )
2541 {
2542 // Now copy over all the security attributes you have parsed out
2543 //TODO: Need to handle mixed mode
2544 pConfig->RSNEncryptType = RSNEncryptType; // Use the cipher type in the RSN IE
2545 pConfig->mcRSNEncryptType = mcRSNEncryptType;
Gopichand Nakkala66c0bd02013-04-10 11:36:29 +05302546 hddLog( LOG1, FL("CSR AuthType = %d, EncryptionType = %d mcEncryptionType = %d\n"),
Jeff Johnson295189b2012-06-20 16:38:30 -07002547 RSNAuthType, RSNEncryptType, mcRSNEncryptType);
2548 }
2549 }
2550 }
2551 else
2552 {
2553 /* If no RSNIE, set encrypt type to NONE*/
2554 pConfig->RSNEncryptType = eCSR_ENCRYPT_TYPE_NONE;
2555 pConfig->mcRSNEncryptType = eCSR_ENCRYPT_TYPE_NONE;
2556 hddLog( LOG1, FL("EncryptionType = %d mcEncryptionType = %d\n"),
2557 pConfig->RSNEncryptType, pConfig->mcRSNEncryptType);
2558 }
2559
Chilam Ngc4244af2013-04-01 15:37:32 -07002560 if (pConfig->RSNWPAReqIELength > QCSAP_MAX_OPT_IE) {
2561 hddLog(LOGE, FL("RSNWPAReqIELength: %d too large"), pConfig->RSNWPAReqIELength);
2562 kfree(pConfig);
2563 return -EIO;
2564 }
2565
Jeff Johnson295189b2012-06-20 16:38:30 -07002566 pConfig->SSIDinfo.ssidHidden = pCommitConfig->SSIDinfo.ssidHidden;
2567 pConfig->SSIDinfo.ssid.length = pCommitConfig->SSIDinfo.ssid.length;
2568 vos_mem_copy(pConfig->SSIDinfo.ssid.ssId, pCommitConfig->SSIDinfo.ssid.ssId, pConfig->SSIDinfo.ssid.length);
2569 vos_mem_copy(pConfig->self_macaddr.bytes, pHostapdAdapter->macAddressCurrent.bytes, sizeof(v_MACADDR_t));
2570
2571 pConfig->SapMacaddr_acl = pCommitConfig->qc_macaddr_acl;
2572
2573 // ht_capab is not what the name conveys,this is used for protection bitmap
2574 pConfig->ht_capab = (WLAN_HDD_GET_CTX(pHostapdAdapter))->cfg_ini->apProtection;
2575
Gopichand Nakkalac005b7c2013-05-14 16:04:14 +05302576 if (pCommitConfig->num_accept_mac > MAX_ACL_MAC_ADDRESS)
2577 num_mac = pConfig->num_accept_mac = MAX_ACL_MAC_ADDRESS;
Jeff Johnson295189b2012-06-20 16:38:30 -07002578 else
2579 num_mac = pConfig->num_accept_mac = pCommitConfig->num_accept_mac;
2580 acl_entry = pCommitConfig->accept_mac;
2581 for (i = 0; i < num_mac; i++)
2582 {
2583 vos_mem_copy(&pConfig->accept_mac[i], acl_entry->addr, sizeof(v_MACADDR_t));
2584 acl_entry++;
2585 }
Gopichand Nakkalac005b7c2013-05-14 16:04:14 +05302586 if (pCommitConfig->num_deny_mac > MAX_ACL_MAC_ADDRESS)
2587 num_mac = pConfig->num_deny_mac = MAX_ACL_MAC_ADDRESS;
Jeff Johnson295189b2012-06-20 16:38:30 -07002588 else
2589 num_mac = pConfig->num_deny_mac = pCommitConfig->num_deny_mac;
2590 acl_entry = pCommitConfig->deny_mac;
2591 for (i = 0; i < num_mac; i++)
2592 {
2593 vos_mem_copy(&pConfig->deny_mac[i], acl_entry->addr, sizeof(v_MACADDR_t));
2594 acl_entry++;
2595 }
2596 //Uapsd Enabled Bit
2597 pConfig->UapsdEnable = (WLAN_HDD_GET_CTX(pHostapdAdapter))->cfg_ini->apUapsdEnabled;
2598 //Enable OBSS protection
2599 pConfig->obssProtEnabled = (WLAN_HDD_GET_CTX(pHostapdAdapter))->cfg_ini->apOBSSProtEnabled;
2600 (WLAN_HDD_GET_AP_CTX_PTR(pHostapdAdapter))->apDisableIntraBssFwd = (WLAN_HDD_GET_CTX(pHostapdAdapter))->cfg_ini->apDisableIntraBssFwd;
2601
2602 hddLog(LOGW, FL("SOftAP macaddress : "MAC_ADDRESS_STR"\n"), MAC_ADDR_ARRAY(pHostapdAdapter->macAddressCurrent.bytes));
2603 hddLog(LOGW,FL("ssid =%s\n"), pConfig->SSIDinfo.ssid.ssId);
2604 hddLog(LOGW,FL("beaconint=%d, channel=%d\n"), (int)pConfig->beacon_int, (int)pConfig->channel);
2605 hddLog(LOGW,FL("hw_mode=%x\n"), pConfig->SapHw_mode);
2606 hddLog(LOGW,FL("privacy=%d, authType=%d\n"), pConfig->privacy, pConfig->authType);
2607 hddLog(LOGW,FL("RSN/WPALen=%d, \n"),(int)pConfig->RSNWPAReqIELength);
2608 hddLog(LOGW,FL("Uapsd = %d\n"),pConfig->UapsdEnable);
2609 hddLog(LOGW,FL("ProtEnabled = %d, OBSSProtEnabled = %d\n"),pConfig->protEnabled, pConfig->obssProtEnabled);
2610 hddLog(LOGW,FL("DisableIntraBssFwd = %d\n"),(WLAN_HDD_GET_AP_CTX_PTR(pHostapdAdapter))->apDisableIntraBssFwd);
2611
2612 pSapEventCallback = hdd_hostapd_SAPEventCB;
2613 pConfig->persona = pHostapdAdapter->device_mode;
2614 if(WLANSAP_StartBss(pVosContext, pSapEventCallback, pConfig,(v_PVOID_t)dev) != VOS_STATUS_SUCCESS)
2615 {
2616 hddLog(LOGE,FL("SAP Start Bss fail\n"));
2617 }
2618
2619 kfree(pConfig);
2620
2621 hddLog(LOG1, FL("Waiting for Scan to complete(auto mode) and BSS to start"));
2622 vos_status = vos_wait_single_event(&pHostapdState->vosEvent, 10000);
2623
2624 if (!VOS_IS_STATUS_SUCCESS(vos_status))
2625 {
2626 VOS_TRACE(VOS_MODULE_ID_HDD, VOS_TRACE_LEVEL_ERROR, ("ERROR: HDD vos wait for single_event failed!!\n"));
2627 VOS_ASSERT(0);
2628 }
2629
2630 pHostapdState->bCommit = TRUE;
2631 if(pHostapdState->vosStatus)
2632 {
Madan Mohan Koyyalamudicae253a2012-11-06 19:10:35 -08002633 return -EIO;
Jeff Johnson295189b2012-06-20 16:38:30 -07002634 }
2635 else
2636 {
2637 set_bit(SOFTAP_BSS_STARTED, &pHostapdAdapter->event_flags);
2638 WLANSAP_Update_WpsIe ( pVosContext );
2639 return 0;
2640 }
2641}
2642static
2643int iw_softap_setmlme(struct net_device *dev,
2644 struct iw_request_info *info,
2645 union iwreq_data *wrqu, char *extra)
2646{
2647 struct sQcSapreq_mlme *pmlme;
2648 hdd_adapter_t *pHostapdAdapter = (hdd_adapter_t*)(netdev_priv(dev));
2649 v_MACADDR_t destAddress;
2650 pmlme = (struct sQcSapreq_mlme *)(wrqu->name);
2651 /* NOTE: this address is not valid incase of TKIP failure, since not filled */
2652 vos_mem_copy(&destAddress.bytes, pmlme->im_macaddr, sizeof(v_MACADDR_t));
2653 switch(pmlme->im_op)
2654 {
2655 case QCSAP_MLME_AUTHORIZE:
2656 hdd_softap_change_STA_state( pHostapdAdapter, &destAddress, WLANTL_STA_AUTHENTICATED);
2657 break;
2658 case QCSAP_MLME_ASSOC:
2659 //TODO:inform to TL after associating (not needed as we do in sapCallback)
2660 break;
2661 case QCSAP_MLME_UNAUTHORIZE:
2662 //TODO: send the disassoc to station
2663 //hdd_softap_change_STA_state( pHostapdAdapter, pmlme->im_macaddr, WLANTL_STA_AUTHENTICATED);
2664 break;
2665 case QCSAP_MLME_DISASSOC:
2666 hdd_softap_sta_disassoc(pHostapdAdapter,pmlme->im_macaddr);
2667 break;
2668 case QCSAP_MLME_DEAUTH:
2669 hdd_softap_sta_deauth(pHostapdAdapter,pmlme->im_macaddr);
2670 break;
2671 case QCSAP_MLME_MICFAILURE:
2672 hdd_softap_tkip_mic_fail_counter_measure(pHostapdAdapter,pmlme->im_reason);
2673 break;
2674 default:
2675 break;
2676 }
2677 return 0;
2678}
2679
2680static int iw_softap_set_channel_range(struct net_device *dev,
2681 struct iw_request_info *info,
2682 union iwreq_data *wrqu, char *extra)
2683{
2684 hdd_adapter_t *pHostapdAdapter = (netdev_priv(dev));
2685 tHalHandle hHal = WLAN_HDD_GET_HAL_CTX(pHostapdAdapter);
Madan Mohan Koyyalamudi543172b2012-12-05 16:40:18 -08002686 hdd_context_t *pHddCtx = WLAN_HDD_GET_CTX(pHostapdAdapter);
Jeff Johnson295189b2012-06-20 16:38:30 -07002687
2688 int *value = (int *)extra;
2689 int startChannel = value[0];
2690 int endChannel = value[1];
2691 int band = value[2];
Jeff Johnson43971f52012-07-17 12:26:56 -07002692 VOS_STATUS status;
Jeff Johnson295189b2012-06-20 16:38:30 -07002693 int ret = 0; /* success */
2694
2695 status = WLANSAP_SetChannelRange(hHal,startChannel,endChannel,band);
2696 if(status != VOS_STATUS_SUCCESS)
2697 {
2698 hddLog( LOGE, FL("iw_softap_set_channel_range: startChannel = %d, endChannel = %d band = %d\n"),
2699 startChannel,endChannel, band);
2700 ret = -EINVAL;
2701 }
Gopichand Nakkalaf7e53c52013-01-07 14:52:52 -08002702
2703 pHddCtx->is_dynamic_channel_range_set = 1;
2704
Jeff Johnson295189b2012-06-20 16:38:30 -07002705 return ret;
2706}
2707
2708int iw_softap_get_channel_list(struct net_device *dev,
2709 struct iw_request_info *info,
2710 union iwreq_data *wrqu, char *extra)
2711{
2712 v_U32_t num_channels = 0;
2713 v_U8_t i = 0;
2714 v_U8_t bandStartChannel = RF_CHAN_1;
2715 v_U8_t bandEndChannel = RF_CHAN_165;
2716 v_U32_t temp_num_channels = 0;
2717 hdd_adapter_t *pHostapdAdapter = (netdev_priv(dev));
2718 tHalHandle hHal = WLAN_HDD_GET_HAL_CTX(pHostapdAdapter);
2719 v_REGDOMAIN_t domainIdCurrentSoftap;
Jeff Johnson295189b2012-06-20 16:38:30 -07002720 tpChannelListInfo channel_list = (tpChannelListInfo) extra;
Madan Mohan Koyyalamudibb7b43a2012-10-11 14:55:09 -07002721 eCsrBand curBand = eCSR_BAND_ALL;
2722
2723 if (eHAL_STATUS_SUCCESS != sme_GetFreqBand(hHal, &curBand))
2724 {
2725 hddLog(LOGE,FL("not able get the current frequency band\n"));
2726 return -EIO;
2727 }
Jeff Johnson295189b2012-06-20 16:38:30 -07002728 wrqu->data.length = sizeof(tChannelListInfo);
2729 ENTER();
2730
Madan Mohan Koyyalamudibb7b43a2012-10-11 14:55:09 -07002731 if (eCSR_BAND_24 == curBand)
2732 {
2733 bandStartChannel = RF_CHAN_1;
2734 bandEndChannel = RF_CHAN_14;
2735 }
2736 else if (eCSR_BAND_5G == curBand)
2737 {
2738 bandStartChannel = RF_CHAN_36;
2739 bandEndChannel = RF_CHAN_165;
2740 }
2741
Gopichand Nakkala29d00192013-06-20 19:03:52 +05302742 hddLog(LOG1, FL("\n curBand = %d, bandStartChannel = %hu, "
2743 "bandEndChannel = %hu "), curBand,
Madan Mohan Koyyalamudibb7b43a2012-10-11 14:55:09 -07002744 bandStartChannel, bandEndChannel );
2745
Jeff Johnson295189b2012-06-20 16:38:30 -07002746 for( i = bandStartChannel; i <= bandEndChannel; i++ )
2747 {
2748 if( NV_CHANNEL_ENABLE == regChannels[i].enabled )
2749 {
2750 channel_list->channels[num_channels] = rfChannels[i].channelNum;
2751 num_channels++;
2752 }
2753 }
2754
2755 /* remove indoor channels if the domain is FCC, channels 36 - 48 */
2756
2757 temp_num_channels = num_channels;
2758
2759 if(eHAL_STATUS_SUCCESS != sme_getSoftApDomain(hHal,(v_REGDOMAIN_t *) &domainIdCurrentSoftap))
2760 {
2761 hddLog(LOG1,FL("Failed to get Domain ID, %d \n"),domainIdCurrentSoftap);
Madan Mohan Koyyalamudicae253a2012-11-06 19:10:35 -08002762 return -EIO;
Jeff Johnson295189b2012-06-20 16:38:30 -07002763 }
2764
2765 if(REGDOMAIN_FCC == domainIdCurrentSoftap)
2766 {
2767 for(i = 0; i < temp_num_channels; i++)
2768 {
2769
2770 if((channel_list->channels[i] > 35) &&
2771 (channel_list->channels[i] < 49))
2772 {
2773 vos_mem_move(&channel_list->channels[i],
2774 &channel_list->channels[i+1],
2775 temp_num_channels - (i-1));
2776 num_channels--;
2777 temp_num_channels--;
2778 i--;
2779 }
2780 }
2781 }
2782
2783 hddLog(LOG1,FL(" number of channels %d\n"), num_channels);
2784
2785 if (num_channels > IW_MAX_FREQUENCIES)
2786 {
2787 num_channels = IW_MAX_FREQUENCIES;
2788 }
2789
2790 channel_list->num_channels = num_channels;
2791 EXIT();
2792
2793 return 0;
2794}
2795
2796static
2797int iw_get_genie(struct net_device *dev,
2798 struct iw_request_info *info,
2799 union iwreq_data *wrqu, char *extra)
2800{
2801 hdd_adapter_t *pHostapdAdapter = (netdev_priv(dev));
2802 v_CONTEXT_t pVosContext = (WLAN_HDD_GET_CTX(pHostapdAdapter))->pvosContext;
2803 eHalStatus status;
2804 v_U32_t length = DOT11F_IE_RSN_MAX_LEN;
2805 v_U8_t genIeBytes[DOT11F_IE_RSN_MAX_LEN];
2806 ENTER();
2807 hddLog(LOG1,FL("getGEN_IE ioctl\n"));
2808 // Actually retrieve the RSN IE from CSR. (We previously sent it down in the CSR Roam Profile.)
2809 status = WLANSap_getstationIE_information(pVosContext,
2810 &length,
2811 genIeBytes);
2812 wrqu->data.length = VOS_MIN((u_int16_t) length, DOT11F_IE_RSN_MAX_LEN);
2813 vos_mem_copy( wrqu->data.pointer, (v_VOID_t*)genIeBytes, wrqu->data.length);
2814
2815 hddLog(LOG1,FL(" RSN IE of %d bytes returned\n"), wrqu->data.length );
2816
2817
2818 EXIT();
2819 return 0;
2820}
2821static
2822int iw_get_WPSPBCProbeReqIEs(struct net_device *dev,
2823 struct iw_request_info *info,
2824 union iwreq_data *wrqu, char *extra)
2825{
2826 hdd_adapter_t *pHostapdAdapter = (netdev_priv(dev));
2827 sQcSapreq_WPSPBCProbeReqIES_t *pWPSPBCProbeReqIEs;
2828 hdd_ap_ctx_t *pHddApCtx = WLAN_HDD_GET_AP_CTX_PTR(pHostapdAdapter);
2829 ENTER();
2830
2831 hddLog(LOG1,FL("get_WPSPBCProbeReqIEs ioctl\n"));
2832
2833 pWPSPBCProbeReqIEs = (sQcSapreq_WPSPBCProbeReqIES_t *)(wrqu->data.pointer);
2834 pWPSPBCProbeReqIEs->probeReqIELen = pHddApCtx->WPSPBCProbeReq.probeReqIELen;
2835 vos_mem_copy(pWPSPBCProbeReqIEs->probeReqIE, pHddApCtx->WPSPBCProbeReq.probeReqIE, pWPSPBCProbeReqIEs->probeReqIELen);
2836 vos_mem_copy(pWPSPBCProbeReqIEs->macaddr, pHddApCtx->WPSPBCProbeReq.peerMacAddr, sizeof(v_MACADDR_t));
2837 wrqu->data.length = 12 + pWPSPBCProbeReqIEs->probeReqIELen;
2838 hddLog(LOG1, FL("Macaddress : "MAC_ADDRESS_STR"\n"), MAC_ADDR_ARRAY(pWPSPBCProbeReqIEs->macaddr));
2839 up(&pHddApCtx->semWpsPBCOverlapInd);
2840 EXIT();
2841 return 0;
2842}
2843
2844/**---------------------------------------------------------------------------
2845
2846 \brief iw_set_auth_hostap() -
2847 This function sets the auth type received from the wpa_supplicant.
2848
2849 \param - dev - Pointer to the net device.
2850 - info - Pointer to the iw_request_info.
2851 - wrqu - Pointer to the iwreq_data.
2852 - extra - Pointer to the data.
2853 \return - 0 for success, non zero for failure
2854
2855 --------------------------------------------------------------------------*/
2856int iw_set_auth_hostap(struct net_device *dev,struct iw_request_info *info,
2857 union iwreq_data *wrqu,char *extra)
2858{
2859 hdd_adapter_t *pAdapter = WLAN_HDD_GET_PRIV_PTR(dev);
2860 hdd_wext_state_t *pWextState = WLAN_HDD_GET_WEXT_STATE_PTR(pAdapter);
2861
2862 ENTER();
2863 switch(wrqu->param.flags & IW_AUTH_INDEX)
2864 {
2865 case IW_AUTH_TKIP_COUNTERMEASURES:
2866 {
2867 if(wrqu->param.value) {
2868 hddLog(VOS_TRACE_LEVEL_INFO_HIGH,
2869 "Counter Measure started %d", wrqu->param.value);
2870 pWextState->mTKIPCounterMeasures = TKIP_COUNTER_MEASURE_STARTED;
2871 }
2872 else {
2873 hddLog(VOS_TRACE_LEVEL_INFO_HIGH,
2874 "Counter Measure stopped=%d", wrqu->param.value);
2875 pWextState->mTKIPCounterMeasures = TKIP_COUNTER_MEASURE_STOPED;
2876 }
2877
2878 hdd_softap_tkip_mic_fail_counter_measure(pAdapter,
2879 wrqu->param.value);
2880 }
2881 break;
2882
2883 default:
2884
Madan Mohan Koyyalamudi87054ba2012-11-02 13:24:12 -07002885 hddLog(LOGW, "%s called with unsupported auth type %d", __func__,
Jeff Johnson295189b2012-06-20 16:38:30 -07002886 wrqu->param.flags & IW_AUTH_INDEX);
2887 break;
2888 }
2889
2890 EXIT();
2891 return 0;
2892}
2893
2894static int iw_set_ap_encodeext(struct net_device *dev,
2895 struct iw_request_info *info,
2896 union iwreq_data *wrqu, char *extra)
2897{
2898 hdd_adapter_t *pHostapdAdapter = (netdev_priv(dev));
2899 v_CONTEXT_t pVosContext = (WLAN_HDD_GET_CTX(pHostapdAdapter))->pvosContext;
2900 hdd_ap_ctx_t *pHddApCtx = WLAN_HDD_GET_AP_CTX_PTR(pHostapdAdapter);
Jeff Johnson43971f52012-07-17 12:26:56 -07002901 int retval = 0;
2902 VOS_STATUS vstatus;
Jeff Johnson295189b2012-06-20 16:38:30 -07002903 struct iw_encode_ext *ext = (struct iw_encode_ext*)extra;
2904 v_U8_t groupmacaddr[WNI_CFG_BSSID_LEN] = {0xFF,0xFF,0xFF,0xFF,0xFF,0xFF};
2905 int key_index;
2906 struct iw_point *encoding = &wrqu->encoding;
2907 tCsrRoamSetKey setKey;
2908// tCsrRoamRemoveKey RemoveKey;
2909 int i;
Jeff Johnson43971f52012-07-17 12:26:56 -07002910
Jeff Johnson295189b2012-06-20 16:38:30 -07002911 ENTER();
2912
2913 key_index = encoding->flags & IW_ENCODE_INDEX;
2914
2915 if(key_index > 0) {
2916
2917 /*Convert from 1-based to 0-based keying*/
2918 key_index--;
2919 }
2920 if(!ext->key_len) {
2921#if 0
2922 /*Set the encrytion type to NONE*/
2923#if 0
2924 pRoamProfile->EncryptionType.encryptionType[0] = eCSR_ENCRYPT_TYPE_NONE;
2925#endif
2926
2927 RemoveKey.keyId = key_index;
2928 if(ext->ext_flags & IW_ENCODE_EXT_GROUP_KEY) {
2929 /*Key direction for group is RX only*/
2930 vos_mem_copy(RemoveKey.peerMac,groupmacaddr,WNI_CFG_BSSID_LEN);
2931 }
2932 else {
2933 vos_mem_copy(RemoveKey.peerMac,ext->addr.sa_data,WNI_CFG_BSSID_LEN);
2934 }
2935 switch(ext->alg)
2936 {
2937 case IW_ENCODE_ALG_NONE:
2938 RemoveKey.encType = eCSR_ENCRYPT_TYPE_NONE;
2939 break;
2940 case IW_ENCODE_ALG_WEP:
2941 RemoveKey.encType = (ext->key_len== 5) ? eCSR_ENCRYPT_TYPE_WEP40:eCSR_ENCRYPT_TYPE_WEP104;
2942 break;
2943 case IW_ENCODE_ALG_TKIP:
2944 RemoveKey.encType = eCSR_ENCRYPT_TYPE_TKIP;
Jeff Johnson43971f52012-07-17 12:26:56 -07002945 break;
Jeff Johnson295189b2012-06-20 16:38:30 -07002946 case IW_ENCODE_ALG_CCMP:
2947 RemoveKey.encType = eCSR_ENCRYPT_TYPE_AES;
2948 break;
2949 default:
2950 RemoveKey.encType = eCSR_ENCRYPT_TYPE_NONE;
2951 break;
2952 }
2953 VOS_TRACE(VOS_MODULE_ID_HDD, VOS_TRACE_LEVEL_INFO, "%s: Remove key cipher_alg:%d key_len%d *pEncryptionType :%d \n",
Madan Mohan Koyyalamudi87054ba2012-11-02 13:24:12 -07002954 __func__,(int)ext->alg,(int)ext->key_len,RemoveKey.encType);
Jeff Johnson295189b2012-06-20 16:38:30 -07002955 VOS_TRACE(VOS_MODULE_ID_HDD, VOS_TRACE_LEVEL_INFO, "%s: Peer Mac = "MAC_ADDRESS_STR"\n",
Madan Mohan Koyyalamudi87054ba2012-11-02 13:24:12 -07002956 __func__, MAC_ADDR_ARRAY(RemoveKey.peerMac));
Jeff Johnson295189b2012-06-20 16:38:30 -07002957 );
Jeff Johnson43971f52012-07-17 12:26:56 -07002958 vstatus = WLANSAP_DelKeySta( pVosContext, &RemoveKey);
2959 if ( vstatus != VOS_STATUS_SUCCESS )
Jeff Johnson295189b2012-06-20 16:38:30 -07002960 {
2961 VOS_TRACE(VOS_MODULE_ID_HDD, VOS_TRACE_LEVEL_ERROR, "[%4d] WLANSAP_DeleteKeysSta returned ERROR status= %d",
Jeff Johnson43971f52012-07-17 12:26:56 -07002962 __LINE__, vstatus );
2963 retval = -EINVAL;
Jeff Johnson295189b2012-06-20 16:38:30 -07002964 }
Jeff Johnson43971f52012-07-17 12:26:56 -07002965#endif
2966 return retval;
Jeff Johnson295189b2012-06-20 16:38:30 -07002967
Jeff Johnson43971f52012-07-17 12:26:56 -07002968 }
Jeff Johnson295189b2012-06-20 16:38:30 -07002969
2970 vos_mem_zero(&setKey,sizeof(tCsrRoamSetKey));
2971
2972 setKey.keyId = key_index;
2973 setKey.keyLength = ext->key_len;
2974
2975 if(ext->key_len <= CSR_MAX_KEY_LEN) {
2976 vos_mem_copy(&setKey.Key[0],ext->key,ext->key_len);
2977 }
2978
2979 if(ext->ext_flags & IW_ENCODE_EXT_GROUP_KEY) {
2980 /*Key direction for group is RX only*/
2981 setKey.keyDirection = eSIR_RX_ONLY;
2982 vos_mem_copy(setKey.peerMac,groupmacaddr,WNI_CFG_BSSID_LEN);
2983 }
2984 else {
2985
2986 setKey.keyDirection = eSIR_TX_RX;
2987 vos_mem_copy(setKey.peerMac,ext->addr.sa_data,WNI_CFG_BSSID_LEN);
2988 }
2989 if(ext->ext_flags & IW_ENCODE_EXT_SET_TX_KEY)
2990 {
2991 setKey.keyDirection = eSIR_TX_DEFAULT;
2992 vos_mem_copy(setKey.peerMac,ext->addr.sa_data,WNI_CFG_BSSID_LEN);
2993 }
2994
2995 /*For supplicant pae role is zero*/
2996 setKey.paeRole = 0;
2997
2998 switch(ext->alg)
2999 {
3000 case IW_ENCODE_ALG_NONE:
3001 setKey.encType = eCSR_ENCRYPT_TYPE_NONE;
3002 break;
3003
3004 case IW_ENCODE_ALG_WEP:
3005 setKey.encType = (ext->key_len== 5) ? eCSR_ENCRYPT_TYPE_WEP40:eCSR_ENCRYPT_TYPE_WEP104;
3006 pHddApCtx->uPrivacy = 1;
Madan Mohan Koyyalamudi87054ba2012-11-02 13:24:12 -07003007 hddLog(LOG1, "(%s) uPrivacy=%d", __func__, pHddApCtx->uPrivacy);
Jeff Johnson295189b2012-06-20 16:38:30 -07003008 break;
3009
3010 case IW_ENCODE_ALG_TKIP:
3011 {
3012 v_U8_t *pKey = &setKey.Key[0];
3013
3014 setKey.encType = eCSR_ENCRYPT_TYPE_TKIP;
3015
3016 vos_mem_zero(pKey, CSR_MAX_KEY_LEN);
3017
3018 /*Supplicant sends the 32bytes key in this order
3019
3020 |--------------|----------|----------|
3021 | Tk1 |TX-MIC | RX Mic |
3022 |--------------|----------|----------|
3023 <---16bytes---><--8bytes--><--8bytes-->
3024
3025 */
3026 /*Sme expects the 32 bytes key to be in the below order
3027
3028 |--------------|----------|----------|
3029 | Tk1 |RX-MIC | TX Mic |
3030 |--------------|----------|----------|
3031 <---16bytes---><--8bytes--><--8bytes-->
3032 */
3033 /* Copy the Temporal Key 1 (TK1) */
3034 vos_mem_copy(pKey,ext->key,16);
3035
3036 /*Copy the rx mic first*/
3037 vos_mem_copy(&pKey[16],&ext->key[24],8);
3038
3039 /*Copy the tx mic */
3040 vos_mem_copy(&pKey[24],&ext->key[16],8);
3041
3042 }
3043 break;
3044
3045 case IW_ENCODE_ALG_CCMP:
3046 setKey.encType = eCSR_ENCRYPT_TYPE_AES;
3047 break;
3048
3049 default:
3050 setKey.encType = eCSR_ENCRYPT_TYPE_NONE;
3051 break;
3052 }
3053
3054 VOS_TRACE(VOS_MODULE_ID_HDD, VOS_TRACE_LEVEL_INFO,
Gopichand Nakkala66c0bd02013-04-10 11:36:29 +05303055 ("%s:EncryptionType:%d key_len:%d, KeyId:%d"), __func__, setKey.encType, setKey.keyLength,
Jeff Johnson295189b2012-06-20 16:38:30 -07003056 setKey.keyId);
3057 for(i=0; i< ext->key_len; i++)
3058 VOS_TRACE(VOS_MODULE_ID_HDD, VOS_TRACE_LEVEL_INFO,
3059 ("%02x"), setKey.Key[i]);
3060 VOS_TRACE(VOS_MODULE_ID_HDD, VOS_TRACE_LEVEL_INFO,
3061 ("\n"));
Jeff Johnson43971f52012-07-17 12:26:56 -07003062
3063 vstatus = WLANSAP_SetKeySta( pVosContext, &setKey);
3064 if ( vstatus != VOS_STATUS_SUCCESS )
Jeff Johnson295189b2012-06-20 16:38:30 -07003065 {
3066 VOS_TRACE( VOS_MODULE_ID_HDD, VOS_TRACE_LEVEL_ERROR,
Jeff Johnson43971f52012-07-17 12:26:56 -07003067 "[%4d] WLANSAP_SetKeySta returned ERROR status= %d", __LINE__, vstatus );
3068 retval = -EINVAL;
3069 }
Jeff Johnson295189b2012-06-20 16:38:30 -07003070
Jeff Johnson43971f52012-07-17 12:26:56 -07003071 return retval;
Jeff Johnson295189b2012-06-20 16:38:30 -07003072}
Jeff Johnson43971f52012-07-17 12:26:56 -07003073
3074
Jeff Johnson295189b2012-06-20 16:38:30 -07003075static int iw_set_ap_mlme(struct net_device *dev,
3076 struct iw_request_info *info,
3077 union iwreq_data *wrqu,
3078 char *extra)
3079{
3080#if 0
3081 hdd_adapter_t *pAdapter = (netdev_priv(dev));
3082 struct iw_mlme *mlme = (struct iw_mlme *)extra;
3083
3084 ENTER();
3085
3086 //reason_code is unused. By default it is set to eCSR_DISCONNECT_REASON_UNSPECIFIED
3087 switch (mlme->cmd) {
3088 case IW_MLME_DISASSOC:
3089 case IW_MLME_DEAUTH:
3090 hddLog(LOG1, "Station disassociate");
3091 if( pAdapter->conn_info.connState == eConnectionState_Associated )
3092 {
3093 eCsrRoamDisconnectReason reason = eCSR_DISCONNECT_REASON_UNSPECIFIED;
3094
3095 if( mlme->reason_code == HDD_REASON_MICHAEL_MIC_FAILURE )
3096 reason = eCSR_DISCONNECT_REASON_MIC_ERROR;
3097
3098 status = sme_RoamDisconnect( pAdapter->hHal,pAdapter->sessionId, reason);
3099
3100 //clear all the reason codes
3101 if (status != 0)
3102 {
Madan Mohan Koyyalamudi87054ba2012-11-02 13:24:12 -07003103 hddLog(LOGE,"%s %d Command Disassociate/Deauthenticate : csrRoamDisconnect failure returned %d \n", __func__, (int)mlme->cmd, (int)status );
Jeff Johnson295189b2012-06-20 16:38:30 -07003104 }
3105
3106 netif_stop_queue(dev);
3107 netif_carrier_off(dev);
3108 }
3109 else
3110 {
Madan Mohan Koyyalamudi87054ba2012-11-02 13:24:12 -07003111 hddLog(LOGE,"%s %d Command Disassociate/Deauthenticate called but station is not in associated state \n", __func__, (int)mlme->cmd );
Jeff Johnson295189b2012-06-20 16:38:30 -07003112 }
3113 default:
Madan Mohan Koyyalamudi87054ba2012-11-02 13:24:12 -07003114 hddLog(LOGE,"%s %d Command should be Disassociate/Deauthenticate \n", __func__, (int)mlme->cmd );
Jeff Johnson295189b2012-06-20 16:38:30 -07003115 return -EINVAL;
3116 }//end of switch
3117 EXIT();
3118#endif
3119 return 0;
3120// return status;
3121}
3122
3123static int iw_get_ap_rts_threshold(struct net_device *dev,
3124 struct iw_request_info *info,
3125 union iwreq_data *wrqu, char *extra)
3126{
3127 hdd_adapter_t *pHostapdAdapter = (netdev_priv(dev));
3128 v_U32_t status = 0;
3129
3130 status = hdd_wlan_get_rts_threshold(pHostapdAdapter, wrqu);
3131
3132 return status;
3133}
3134
3135static int iw_get_ap_frag_threshold(struct net_device *dev,
3136 struct iw_request_info *info,
3137 union iwreq_data *wrqu, char *extra)
3138{
3139 hdd_adapter_t *pHostapdAdapter = (netdev_priv(dev));
3140 v_U32_t status = 0;
3141
3142 status = hdd_wlan_get_frag_threshold(pHostapdAdapter, wrqu);
3143
3144 return status;
3145}
3146
3147static int iw_get_ap_freq(struct net_device *dev, struct iw_request_info *info,
3148 struct iw_freq *fwrq, char *extra)
3149{
Jeff Johnsone7245742012-09-05 17:12:55 -07003150 v_U32_t status = FALSE, channel = 0, freq = 0;
Jeff Johnson295189b2012-06-20 16:38:30 -07003151 hdd_adapter_t *pHostapdAdapter = (netdev_priv(dev));
3152 tHalHandle hHal;
3153 hdd_hostapd_state_t *pHostapdState;
Jeff Johnsone7245742012-09-05 17:12:55 -07003154 hdd_ap_ctx_t *pHddApCtx = WLAN_HDD_GET_AP_CTX_PTR(pHostapdAdapter);
Jeff Johnson295189b2012-06-20 16:38:30 -07003155
3156 ENTER();
3157
3158 if ((WLAN_HDD_GET_CTX(pHostapdAdapter))->isLogpInProgress) {
3159 VOS_TRACE(VOS_MODULE_ID_HDD, VOS_TRACE_LEVEL_INFO,
3160 "%s:LOGP in Progress. Ignore!!!",__func__);
3161 return status;
3162 }
3163
3164 pHostapdState = WLAN_HDD_GET_HOSTAP_STATE_PTR(pHostapdAdapter);
3165 hHal = WLAN_HDD_GET_HAL_CTX(pHostapdAdapter);
3166
3167 if(pHostapdState->bssState == BSS_STOP )
3168 {
3169 if (ccmCfgGetInt(hHal, WNI_CFG_CURRENT_CHANNEL, &channel)
3170 != eHAL_STATUS_SUCCESS)
3171 {
3172 return -EIO;
3173 }
3174 else
3175 {
3176 status = hdd_wlan_get_freq(channel, &freq);
Jeff Johnsone7245742012-09-05 17:12:55 -07003177 if( TRUE == status)
3178 {
3179 /* Set Exponent parameter as 6 (MHZ) in struct iw_freq
3180 * iwlist & iwconfig command shows frequency into proper
3181 * format (2.412 GHz instead of 246.2 MHz)*/
3182 fwrq->m = freq;
3183 fwrq->e = MHZ;
3184 }
Jeff Johnson295189b2012-06-20 16:38:30 -07003185 }
3186 }
3187 else
3188 {
3189 channel = pHddApCtx->operatingChannel;
3190 status = hdd_wlan_get_freq(channel, &freq);
Jeff Johnsone7245742012-09-05 17:12:55 -07003191 if( TRUE == status)
3192 {
3193 /* Set Exponent parameter as 6 (MHZ) in struct iw_freq
3194 * iwlist & iwconfig command shows frequency into proper
3195 * format (2.412 GHz instead of 246.2 MHz)*/
3196 fwrq->m = freq;
3197 fwrq->e = MHZ;
3198 }
Jeff Johnson295189b2012-06-20 16:38:30 -07003199 }
Jeff Johnsone7245742012-09-05 17:12:55 -07003200 return 0;
Jeff Johnson295189b2012-06-20 16:38:30 -07003201}
3202
Madan Mohan Koyyalamudi0c2ba1b2013-10-01 19:47:50 +05303203static int iw_get_mode(struct net_device *dev,
3204 struct iw_request_info *info,
3205 union iwreq_data *wrqu,
3206 char *extra)
3207{
3208 int status = 0;
3209
3210 wrqu->mode = IW_MODE_MASTER;
3211
3212 return status;
3213}
3214
Jeff Johnson295189b2012-06-20 16:38:30 -07003215static int iw_softap_setwpsie(struct net_device *dev,
3216 struct iw_request_info *info,
3217 union iwreq_data *wrqu,
3218 char *extra)
3219{
3220 hdd_adapter_t *pHostapdAdapter = (netdev_priv(dev));
3221 v_CONTEXT_t pVosContext = (WLAN_HDD_GET_CTX(pHostapdAdapter))->pvosContext;
3222 hdd_hostapd_state_t *pHostapdState;
3223 eHalStatus halStatus= eHAL_STATUS_SUCCESS;
3224 u_int8_t *wps_genie = wrqu->data.pointer;
3225 u_int8_t *pos;
3226 tpSap_WPSIE pSap_WPSIe;
3227 u_int8_t WPSIeType;
3228 u_int16_t length;
3229 ENTER();
3230
3231 if(!wrqu->data.length)
3232 return 0;
3233
3234 pSap_WPSIe = vos_mem_malloc(sizeof(tSap_WPSIE));
3235 if (NULL == pSap_WPSIe)
3236 {
3237 hddLog(LOGE, "VOS unable to allocate memory\n");
3238 return -ENOMEM;
3239 }
3240 vos_mem_zero(pSap_WPSIe, sizeof(tSap_WPSIE));
3241
Madan Mohan Koyyalamudi87054ba2012-11-02 13:24:12 -07003242 hddLog(LOG1,"%s WPS IE type[0x%X] IE[0x%X], LEN[%d]\n", __func__, wps_genie[0], wps_genie[1], wps_genie[2]);
Jeff Johnson295189b2012-06-20 16:38:30 -07003243 WPSIeType = wps_genie[0];
3244 if ( wps_genie[0] == eQC_WPS_BEACON_IE)
3245 {
3246 pSap_WPSIe->sapWPSIECode = eSAP_WPS_BEACON_IE;
3247 wps_genie = wps_genie + 1;
3248 switch ( wps_genie[0] )
3249 {
3250 case DOT11F_EID_WPA:
3251 if (wps_genie[1] < 2 + 4)
3252 {
3253 vos_mem_free(pSap_WPSIe);
3254 return -EINVAL;
3255 }
3256 else if (memcmp(&wps_genie[2], "\x00\x50\xf2\x04", 4) == 0)
3257 {
Madan Mohan Koyyalamudi87054ba2012-11-02 13:24:12 -07003258 hddLog (LOG1, "%s Set WPS BEACON IE(len %d)",__func__, wps_genie[1]+2);
Jeff Johnson295189b2012-06-20 16:38:30 -07003259 pos = &wps_genie[6];
3260 while (((size_t)pos - (size_t)&wps_genie[6]) < (wps_genie[1] - 4) )
3261 {
3262 switch((u_int16_t)(*pos<<8) | *(pos+1))
3263 {
3264 case HDD_WPS_ELEM_VERSION:
3265 pos += 4;
3266 pSap_WPSIe->sapwpsie.sapWPSBeaconIE.Version = *pos;
3267 hddLog(LOG1, "WPS version %d\n", pSap_WPSIe->sapwpsie.sapWPSBeaconIE.Version);
3268 pSap_WPSIe->sapwpsie.sapWPSBeaconIE.FieldPresent |= WPS_BEACON_VER_PRESENT;
3269 pos += 1;
3270 break;
3271
3272 case HDD_WPS_ELEM_WPS_STATE:
3273 pos +=4;
3274 pSap_WPSIe->sapwpsie.sapWPSBeaconIE.wpsState = *pos;
3275 hddLog(LOG1, "WPS State %d\n", pSap_WPSIe->sapwpsie.sapWPSBeaconIE.wpsState);
3276 pSap_WPSIe->sapwpsie.sapWPSBeaconIE.FieldPresent |= WPS_BEACON_STATE_PRESENT;
3277 pos += 1;
3278 break;
3279 case HDD_WPS_ELEM_APSETUPLOCK:
3280 pos += 4;
3281 pSap_WPSIe->sapwpsie.sapWPSBeaconIE.APSetupLocked = *pos;
3282 hddLog(LOG1, "AP setup lock %d\n", pSap_WPSIe->sapwpsie.sapWPSBeaconIE.APSetupLocked);
3283 pSap_WPSIe->sapwpsie.sapWPSBeaconIE.FieldPresent |= WPS_BEACON_APSETUPLOCK_PRESENT;
3284 pos += 1;
3285 break;
3286 case HDD_WPS_ELEM_SELECTEDREGISTRA:
3287 pos += 4;
3288 pSap_WPSIe->sapwpsie.sapWPSBeaconIE.SelectedRegistra = *pos;
3289 hddLog(LOG1, "Selected Registra %d\n", pSap_WPSIe->sapwpsie.sapWPSBeaconIE.SelectedRegistra);
3290 pSap_WPSIe->sapwpsie.sapWPSBeaconIE.FieldPresent |= WPS_BEACON_SELECTEDREGISTRA_PRESENT;
3291 pos += 1;
3292 break;
3293 case HDD_WPS_ELEM_DEVICE_PASSWORD_ID:
3294 pos += 4;
3295 pSap_WPSIe->sapwpsie.sapWPSBeaconIE.DevicePasswordID = (*pos<<8) | *(pos+1);
3296 hddLog(LOG1, "Password ID: %x\n", pSap_WPSIe->sapwpsie.sapWPSBeaconIE.DevicePasswordID);
3297 pSap_WPSIe->sapwpsie.sapWPSBeaconIE.FieldPresent |= WPS_BEACON_DEVICEPASSWORDID_PRESENT;
3298 pos += 2;
3299 break;
3300 case HDD_WPS_ELEM_REGISTRA_CONF_METHODS:
3301 pos += 4;
3302 pSap_WPSIe->sapwpsie.sapWPSBeaconIE.SelectedRegistraCfgMethod = (*pos<<8) | *(pos+1);
3303 hddLog(LOG1, "Select Registra Config Methods: %x\n", pSap_WPSIe->sapwpsie.sapWPSBeaconIE.SelectedRegistraCfgMethod);
3304 pSap_WPSIe->sapwpsie.sapWPSBeaconIE.FieldPresent |= WPS_BEACON_SELECTEDREGISTRACFGMETHOD_PRESENT;
3305 pos += 2;
3306 break;
3307
3308 case HDD_WPS_ELEM_UUID_E:
3309 pos += 2;
3310 length = *pos<<8 | *(pos+1);
3311 pos += 2;
3312 vos_mem_copy(pSap_WPSIe->sapwpsie.sapWPSBeaconIE.UUID_E, pos, length);
3313 pSap_WPSIe->sapwpsie.sapWPSBeaconIE.FieldPresent |= WPS_BEACON_UUIDE_PRESENT;
3314 pos += length;
3315 break;
3316 case HDD_WPS_ELEM_RF_BANDS:
3317 pos += 4;
3318 pSap_WPSIe->sapwpsie.sapWPSBeaconIE.RFBand = *pos;
3319 hddLog(LOG1, "RF band: %d\n", pSap_WPSIe->sapwpsie.sapWPSBeaconIE.RFBand);
3320 pSap_WPSIe->sapwpsie.sapWPSBeaconIE.FieldPresent |= WPS_BEACON_RF_BANDS_PRESENT;
3321 pos += 1;
3322 break;
3323
3324 default:
3325 hddLog (LOGW, "UNKNOWN TLV in WPS IE(%x)\n", (*pos<<8 | *(pos+1)));
3326 vos_mem_free(pSap_WPSIe);
3327 return -EINVAL;
3328 }
3329 }
3330 }
3331 else {
3332 hddLog (LOGE, "%s WPS IE Mismatch %X",
Madan Mohan Koyyalamudi87054ba2012-11-02 13:24:12 -07003333 __func__, wps_genie[0]);
Jeff Johnson295189b2012-06-20 16:38:30 -07003334 }
3335 break;
3336
3337 default:
Madan Mohan Koyyalamudi87054ba2012-11-02 13:24:12 -07003338 hddLog (LOGE, "%s Set UNKNOWN IE %X",__func__, wps_genie[0]);
Jeff Johnson295189b2012-06-20 16:38:30 -07003339 vos_mem_free(pSap_WPSIe);
3340 return 0;
3341 }
3342 }
3343 else if( wps_genie[0] == eQC_WPS_PROBE_RSP_IE)
3344 {
3345 pSap_WPSIe->sapWPSIECode = eSAP_WPS_PROBE_RSP_IE;
3346 wps_genie = wps_genie + 1;
3347 switch ( wps_genie[0] )
3348 {
3349 case DOT11F_EID_WPA:
3350 if (wps_genie[1] < 2 + 4)
3351 {
3352 vos_mem_free(pSap_WPSIe);
3353 return -EINVAL;
3354 }
3355 else if (memcmp(&wps_genie[2], "\x00\x50\xf2\x04", 4) == 0)
3356 {
Madan Mohan Koyyalamudi87054ba2012-11-02 13:24:12 -07003357 hddLog (LOG1, "%s Set WPS PROBE RSP IE(len %d)",__func__, wps_genie[1]+2);
Jeff Johnson295189b2012-06-20 16:38:30 -07003358 pos = &wps_genie[6];
3359 while (((size_t)pos - (size_t)&wps_genie[6]) < (wps_genie[1] - 4) )
3360 {
3361 switch((u_int16_t)(*pos<<8) | *(pos+1))
3362 {
3363 case HDD_WPS_ELEM_VERSION:
3364 pos += 4;
3365 pSap_WPSIe->sapwpsie.sapWPSProbeRspIE.Version = *pos;
3366 hddLog(LOG1, "WPS version %d\n", pSap_WPSIe->sapwpsie.sapWPSProbeRspIE.Version);
3367 pSap_WPSIe->sapwpsie.sapWPSProbeRspIE.FieldPresent |= WPS_PROBRSP_VER_PRESENT;
3368 pos += 1;
3369 break;
3370
3371 case HDD_WPS_ELEM_WPS_STATE:
3372 pos +=4;
3373 pSap_WPSIe->sapwpsie.sapWPSProbeRspIE.wpsState = *pos;
3374 hddLog(LOG1, "WPS State %d\n", pSap_WPSIe->sapwpsie.sapWPSProbeRspIE.wpsState);
3375 pSap_WPSIe->sapwpsie.sapWPSProbeRspIE.FieldPresent |= WPS_PROBRSP_STATE_PRESENT;
3376 pos += 1;
3377 break;
3378 case HDD_WPS_ELEM_APSETUPLOCK:
3379 pos += 4;
3380 pSap_WPSIe->sapwpsie.sapWPSProbeRspIE.APSetupLocked = *pos;
3381 hddLog(LOG1, "AP setup lock %d\n", pSap_WPSIe->sapwpsie.sapWPSProbeRspIE.APSetupLocked);
3382 pSap_WPSIe->sapwpsie.sapWPSProbeRspIE.FieldPresent |= WPS_PROBRSP_APSETUPLOCK_PRESENT;
3383 pos += 1;
3384 break;
3385 case HDD_WPS_ELEM_SELECTEDREGISTRA:
3386 pos += 4;
3387 pSap_WPSIe->sapwpsie.sapWPSProbeRspIE.SelectedRegistra = *pos;
3388 hddLog(LOG1, "Selected Registra %d\n", pSap_WPSIe->sapwpsie.sapWPSProbeRspIE.SelectedRegistra);
3389 pSap_WPSIe->sapwpsie.sapWPSProbeRspIE.FieldPresent |= WPS_PROBRSP_SELECTEDREGISTRA_PRESENT;
3390 pos += 1;
3391 break;
3392 case HDD_WPS_ELEM_DEVICE_PASSWORD_ID:
3393 pos += 4;
3394 pSap_WPSIe->sapwpsie.sapWPSProbeRspIE.DevicePasswordID = (*pos<<8) | *(pos+1);
3395 hddLog(LOG1, "Password ID: %d\n", pSap_WPSIe->sapwpsie.sapWPSProbeRspIE.DevicePasswordID);
3396 pSap_WPSIe->sapwpsie.sapWPSProbeRspIE.FieldPresent |= WPS_PROBRSP_DEVICEPASSWORDID_PRESENT;
3397 pos += 2;
3398 break;
3399 case HDD_WPS_ELEM_REGISTRA_CONF_METHODS:
3400 pos += 4;
3401 pSap_WPSIe->sapwpsie.sapWPSProbeRspIE.SelectedRegistraCfgMethod = (*pos<<8) | *(pos+1);
3402 hddLog(LOG1, "Select Registra Config Methods: %x\n", pSap_WPSIe->sapwpsie.sapWPSProbeRspIE.SelectedRegistraCfgMethod);
3403 pSap_WPSIe->sapwpsie.sapWPSProbeRspIE.FieldPresent |= WPS_PROBRSP_SELECTEDREGISTRACFGMETHOD_PRESENT;
3404 pos += 2;
3405 break;
3406 case HDD_WPS_ELEM_RSP_TYPE:
3407 pos += 4;
3408 pSap_WPSIe->sapwpsie.sapWPSProbeRspIE.ResponseType = *pos;
3409 hddLog(LOG1, "Config Methods: %d\n", pSap_WPSIe->sapwpsie.sapWPSProbeRspIE.ResponseType);
3410 pSap_WPSIe->sapwpsie.sapWPSProbeRspIE.FieldPresent |= WPS_PROBRSP_RESPONSETYPE_PRESENT;
3411 pos += 1;
3412 break;
3413 case HDD_WPS_ELEM_UUID_E:
3414 pos += 2;
3415 length = *pos<<8 | *(pos+1);
3416 pos += 2;
3417 vos_mem_copy(pSap_WPSIe->sapwpsie.sapWPSProbeRspIE.UUID_E, pos, length);
3418 pSap_WPSIe->sapwpsie.sapWPSProbeRspIE.FieldPresent |= WPS_PROBRSP_UUIDE_PRESENT;
3419 pos += length;
3420 break;
3421
3422 case HDD_WPS_ELEM_MANUFACTURER:
3423 pos += 2;
3424 length = *pos<<8 | *(pos+1);
3425 pos += 2;
3426 pSap_WPSIe->sapwpsie.sapWPSProbeRspIE.Manufacture.num_name = length;
3427 vos_mem_copy(pSap_WPSIe->sapwpsie.sapWPSProbeRspIE.Manufacture.name, pos, length);
3428 pSap_WPSIe->sapwpsie.sapWPSProbeRspIE.FieldPresent |= WPS_PROBRSP_MANUFACTURE_PRESENT;
3429 pos += length;
3430 break;
3431
3432 case HDD_WPS_ELEM_MODEL_NAME:
3433 pos += 2;
3434 length = *pos<<8 | *(pos+1);
3435 pos += 2;
3436 pSap_WPSIe->sapwpsie.sapWPSProbeRspIE.ModelName.num_text = length;
3437 vos_mem_copy(pSap_WPSIe->sapwpsie.sapWPSProbeRspIE.ModelName.text, pos, length);
3438 pSap_WPSIe->sapwpsie.sapWPSProbeRspIE.FieldPresent |= WPS_PROBRSP_MODELNAME_PRESENT;
3439 pos += length;
3440 break;
3441 case HDD_WPS_ELEM_MODEL_NUM:
3442 pos += 2;
3443 length = *pos<<8 | *(pos+1);
3444 pos += 2;
3445 pSap_WPSIe->sapwpsie.sapWPSProbeRspIE.ModelNumber.num_text = length;
3446 vos_mem_copy(pSap_WPSIe->sapwpsie.sapWPSProbeRspIE.ModelNumber.text, pos, length);
3447 pSap_WPSIe->sapwpsie.sapWPSProbeRspIE.FieldPresent |= WPS_PROBRSP_MODELNUMBER_PRESENT;
3448 pos += length;
3449 break;
3450 case HDD_WPS_ELEM_SERIAL_NUM:
3451 pos += 2;
3452 length = *pos<<8 | *(pos+1);
3453 pos += 2;
3454 pSap_WPSIe->sapwpsie.sapWPSProbeRspIE.SerialNumber.num_text = length;
3455 vos_mem_copy(pSap_WPSIe->sapwpsie.sapWPSProbeRspIE.SerialNumber.text, pos, length);
3456 pSap_WPSIe->sapwpsie.sapWPSProbeRspIE.FieldPresent |= WPS_PROBRSP_SERIALNUMBER_PRESENT;
3457 pos += length;
3458 break;
3459 case HDD_WPS_ELEM_PRIMARY_DEVICE_TYPE:
3460 pos += 4;
3461 pSap_WPSIe->sapwpsie.sapWPSProbeRspIE.PrimaryDeviceCategory = (*pos<<8 | *(pos+1));
3462 hddLog(LOG1, "primary dev category: %d\n", pSap_WPSIe->sapwpsie.sapWPSProbeRspIE.PrimaryDeviceCategory);
3463 pos += 2;
3464
3465 vos_mem_copy(pSap_WPSIe->sapwpsie.sapWPSProbeRspIE.PrimaryDeviceOUI, pos, HDD_WPS_DEVICE_OUI_LEN);
3466 hddLog(LOG1, "primary dev oui: %02x, %02x, %02x, %02x\n", pos[0], pos[1], pos[2], pos[3]);
3467 pos += 4;
3468 pSap_WPSIe->sapwpsie.sapWPSProbeRspIE.DeviceSubCategory = (*pos<<8 | *(pos+1));
3469 hddLog(LOG1, "primary dev sub category: %d\n", pSap_WPSIe->sapwpsie.sapWPSProbeRspIE.DeviceSubCategory);
3470 pos += 2;
3471 pSap_WPSIe->sapwpsie.sapWPSProbeRspIE.FieldPresent |= WPS_PROBRSP_PRIMARYDEVICETYPE_PRESENT;
3472 break;
3473 case HDD_WPS_ELEM_DEVICE_NAME:
3474 pos += 2;
3475 length = *pos<<8 | *(pos+1);
3476 pos += 2;
3477 pSap_WPSIe->sapwpsie.sapWPSProbeRspIE.DeviceName.num_text = length;
3478 vos_mem_copy(pSap_WPSIe->sapwpsie.sapWPSProbeRspIE.DeviceName.text, pos, length);
3479 pos += length;
3480 pSap_WPSIe->sapwpsie.sapWPSProbeRspIE.FieldPresent |= WPS_PROBRSP_DEVICENAME_PRESENT;
3481 break;
3482 case HDD_WPS_ELEM_CONFIG_METHODS:
3483 pos += 4;
3484 pSap_WPSIe->sapwpsie.sapWPSProbeRspIE.ConfigMethod = (*pos<<8) | *(pos+1);
3485 hddLog(LOG1, "Config Methods: %d\n", pSap_WPSIe->sapwpsie.sapWPSProbeRspIE.SelectedRegistraCfgMethod);
3486 pos += 2;
3487 pSap_WPSIe->sapwpsie.sapWPSProbeRspIE.FieldPresent |= WPS_PROBRSP_CONFIGMETHODS_PRESENT;
3488 break;
3489
3490 case HDD_WPS_ELEM_RF_BANDS:
3491 pos += 4;
3492 pSap_WPSIe->sapwpsie.sapWPSProbeRspIE.RFBand = *pos;
3493 hddLog(LOG1, "RF band: %d\n", pSap_WPSIe->sapwpsie.sapWPSProbeRspIE.RFBand);
3494 pos += 1;
3495 pSap_WPSIe->sapwpsie.sapWPSProbeRspIE.FieldPresent |= WPS_PROBRSP_RF_BANDS_PRESENT;
3496 break;
3497 } // switch
3498 }
3499 }
3500 else
3501 {
Madan Mohan Koyyalamudi87054ba2012-11-02 13:24:12 -07003502 hddLog (LOGE, "%s WPS IE Mismatch %X",__func__, wps_genie[0]);
Jeff Johnson295189b2012-06-20 16:38:30 -07003503 }
3504
3505 } // switch
3506 }
3507 halStatus = WLANSAP_Set_WpsIe(pVosContext, pSap_WPSIe);
3508 pHostapdState = WLAN_HDD_GET_HOSTAP_STATE_PTR(pHostapdAdapter);
3509 if( pHostapdState->bCommit && WPSIeType == eQC_WPS_PROBE_RSP_IE)
3510 {
3511 //hdd_adapter_t *pHostapdAdapter = (netdev_priv(dev));
3512 //v_CONTEXT_t pVosContext = pHostapdAdapter->pvosContext;
3513 WLANSAP_Update_WpsIe ( pVosContext );
3514 }
3515
3516 vos_mem_free(pSap_WPSIe);
3517 EXIT();
3518 return halStatus;
3519}
3520
3521static int iw_softap_stopbss(struct net_device *dev,
3522 struct iw_request_info *info,
3523 union iwreq_data *wrqu,
3524 char *extra)
3525{
3526 hdd_adapter_t *pHostapdAdapter = (netdev_priv(dev));
3527 VOS_STATUS status = VOS_STATUS_SUCCESS;
3528 ENTER();
3529 if(test_bit(SOFTAP_BSS_STARTED, &pHostapdAdapter->event_flags))
3530 {
3531 if ( VOS_STATUS_SUCCESS == (status = WLANSAP_StopBss((WLAN_HDD_GET_CTX(pHostapdAdapter))->pvosContext) ) )
3532 {
3533 hdd_hostapd_state_t *pHostapdState = WLAN_HDD_GET_HOSTAP_STATE_PTR(pHostapdAdapter);
3534
3535 status = vos_wait_single_event(&pHostapdState->vosEvent, 10000);
3536
3537 if (!VOS_IS_STATUS_SUCCESS(status))
3538 {
3539 VOS_TRACE(VOS_MODULE_ID_HDD, VOS_TRACE_LEVEL_ERROR,
3540 ("ERROR: HDD vos wait for single_event failed!!\n"));
3541 VOS_ASSERT(0);
3542 }
3543 }
3544 clear_bit(SOFTAP_BSS_STARTED, &pHostapdAdapter->event_flags);
3545 }
3546 EXIT();
3547 return (status == VOS_STATUS_SUCCESS) ? 0 : -EBUSY;
3548}
3549
3550static int iw_softap_version(struct net_device *dev,
3551 struct iw_request_info *info,
Jeff Johnson4824d4c2013-02-12 14:23:57 -08003552 union iwreq_data *wrqu,
Jeff Johnson295189b2012-06-20 16:38:30 -07003553 char *extra)
3554{
Jeff Johnson295189b2012-06-20 16:38:30 -07003555 hdd_adapter_t *pHostapdAdapter = (netdev_priv(dev));
Jeff Johnson4824d4c2013-02-12 14:23:57 -08003556
Jeff Johnson295189b2012-06-20 16:38:30 -07003557 ENTER();
Jeff Johnson4824d4c2013-02-12 14:23:57 -08003558 hdd_wlan_get_version(pHostapdAdapter, wrqu, extra);
Jeff Johnson295189b2012-06-20 16:38:30 -07003559 EXIT();
Jeff Johnson295189b2012-06-20 16:38:30 -07003560 return 0;
3561}
Gopichand Nakkala976e3252013-01-03 15:45:56 -08003562
Yathish Hanumapuradoddi Shivanna7b659402013-03-25 14:12:32 -07003563VOS_STATUS hdd_softap_get_sta_info(hdd_adapter_t *pAdapter, v_U8_t *pBuf, int buf_len)
Gopichand Nakkala976e3252013-01-03 15:45:56 -08003564{
3565 v_U8_t i;
Yathish Hanumapuradoddi Shivanna7b659402013-03-25 14:12:32 -07003566 int len = 0;
3567 const char sta_info_header[] = "staId staAddress\n";
3568
Sameer Thalappilb0a30232013-09-27 15:37:48 -07003569 len = scnprintf(pBuf, buf_len, sta_info_header);
Yathish Hanumapuradoddi Shivanna7b659402013-03-25 14:12:32 -07003570 pBuf += len;
3571 buf_len -= len;
Gopichand Nakkala976e3252013-01-03 15:45:56 -08003572
3573 for (i = 0; i < WLAN_MAX_STA_COUNT; i++)
3574 {
3575 if(pAdapter->aStaInfo[i].isUsed)
3576 {
Sameer Thalappilb0a30232013-09-27 15:37:48 -07003577 len = scnprintf(pBuf, buf_len, "%*d .%02x:%02x:%02x:%02x:%02x:%02x\n",
Yathish Hanumapuradoddi Shivanna7b659402013-03-25 14:12:32 -07003578 strlen("staId"),
Gopichand Nakkala976e3252013-01-03 15:45:56 -08003579 pAdapter->aStaInfo[i].ucSTAId,
3580 pAdapter->aStaInfo[i].macAddrSTA.bytes[0],
3581 pAdapter->aStaInfo[i].macAddrSTA.bytes[1],
3582 pAdapter->aStaInfo[i].macAddrSTA.bytes[2],
3583 pAdapter->aStaInfo[i].macAddrSTA.bytes[3],
3584 pAdapter->aStaInfo[i].macAddrSTA.bytes[4],
3585 pAdapter->aStaInfo[i].macAddrSTA.bytes[5]);
Yathish Hanumapuradoddi Shivanna7b659402013-03-25 14:12:32 -07003586 pBuf += len;
3587 buf_len -= len;
3588 }
3589 if(WE_GET_STA_INFO_SIZE > buf_len)
3590 {
3591 break;
Gopichand Nakkala976e3252013-01-03 15:45:56 -08003592 }
3593 }
3594 return VOS_STATUS_SUCCESS;
3595}
3596
3597static int iw_softap_get_sta_info(struct net_device *dev,
3598 struct iw_request_info *info,
3599 union iwreq_data *wrqu,
3600 char *extra)
3601{
3602 hdd_adapter_t *pHostapdAdapter = (netdev_priv(dev));
3603 VOS_STATUS status;
3604 ENTER();
Yathish Hanumapuradoddi Shivanna4171f7d2013-04-08 20:05:56 -07003605 status = hdd_softap_get_sta_info(pHostapdAdapter, extra, WE_SAP_MAX_STA_INFO);
Gopichand Nakkala976e3252013-01-03 15:45:56 -08003606 if ( !VOS_IS_STATUS_SUCCESS( status ) ) {
3607 hddLog(VOS_TRACE_LEVEL_ERROR, "%s Failed!!!\n",__func__);
3608 return -EINVAL;
3609 }
3610 wrqu->data.length = strlen(extra);
3611 EXIT();
3612 return 0;
3613}
3614
Jeff Johnson295189b2012-06-20 16:38:30 -07003615static int iw_set_ap_genie(struct net_device *dev,
3616 struct iw_request_info *info,
3617 union iwreq_data *wrqu,
3618 char *extra)
3619{
3620
3621 hdd_adapter_t *pHostapdAdapter = (netdev_priv(dev));
3622 v_CONTEXT_t pVosContext = (WLAN_HDD_GET_CTX(pHostapdAdapter))->pvosContext;
3623 eHalStatus halStatus= eHAL_STATUS_SUCCESS;
3624 u_int8_t *genie = wrqu->data.pointer;
3625
3626 ENTER();
3627
3628 if(!wrqu->data.length)
3629 {
3630 EXIT();
3631 return 0;
3632 }
3633
3634 switch (genie[0])
3635 {
3636 case DOT11F_EID_WPA:
3637 case DOT11F_EID_RSN:
3638 if((WLAN_HDD_GET_AP_CTX_PTR(pHostapdAdapter))->uPrivacy == 0)
3639 {
3640 hdd_softap_Deregister_BC_STA(pHostapdAdapter);
3641 hdd_softap_Register_BC_STA(pHostapdAdapter, 1);
3642 }
3643 (WLAN_HDD_GET_AP_CTX_PTR(pHostapdAdapter))->uPrivacy = 1;
3644 halStatus = WLANSAP_Set_WPARSNIes(pVosContext, wrqu->data.pointer, wrqu->data.length);
3645 break;
3646
3647 default:
Madan Mohan Koyyalamudi87054ba2012-11-02 13:24:12 -07003648 hddLog (LOGE, "%s Set UNKNOWN IE %X",__func__, genie[0]);
Jeff Johnson295189b2012-06-20 16:38:30 -07003649 halStatus = 0;
3650 }
3651
3652 EXIT();
3653 return halStatus;
3654}
3655
3656static VOS_STATUS wlan_hdd_get_classAstats_for_station(hdd_adapter_t *pAdapter, u8 staid)
3657{
3658 eHalStatus hstatus;
3659 long lrc;
3660 struct statsContext context;
3661
3662 if (NULL == pAdapter)
3663 {
3664 hddLog(VOS_TRACE_LEVEL_ERROR,"%s: Padapter is NULL", __func__);
3665 return VOS_STATUS_E_FAULT;
3666 }
3667
3668 init_completion(&context.completion);
3669 context.pAdapter = pAdapter;
3670 context.magic = STATS_CONTEXT_MAGIC;
3671 hstatus = sme_GetStatistics( WLAN_HDD_GET_HAL_CTX(pAdapter),
3672 eCSR_HDD,
3673 SME_GLOBAL_CLASSA_STATS,
3674 hdd_GetClassA_statisticsCB,
3675 0, // not periodic
3676 FALSE, //non-cached results
3677 staid,
3678 &context);
3679 if (eHAL_STATUS_SUCCESS != hstatus)
3680 {
3681 hddLog(VOS_TRACE_LEVEL_ERROR,
3682 "%s: Unable to retrieve statistics for link speed",
Madan Mohan Koyyalamudi87054ba2012-11-02 13:24:12 -07003683 __func__);
Jeff Johnson295189b2012-06-20 16:38:30 -07003684 }
3685 else
3686 {
3687 lrc = wait_for_completion_interruptible_timeout(&context.completion,
3688 msecs_to_jiffies(WLAN_WAIT_TIME_STATS));
3689 context.magic = 0;
3690 if (lrc <= 0)
3691 {
3692 hddLog(VOS_TRACE_LEVEL_ERROR,
3693 "%s: SME %s while retrieving link speed",
Madan Mohan Koyyalamudi87054ba2012-11-02 13:24:12 -07003694 __func__, (0 == lrc) ? "timeout" : "interrupt");
Jeff Johnson295189b2012-06-20 16:38:30 -07003695 msleep(50);
3696 }
3697 }
3698 return VOS_STATUS_SUCCESS;
3699}
3700
3701int iw_get_softap_linkspeed(struct net_device *dev,
3702 struct iw_request_info *info,
3703 union iwreq_data *wrqu,
3704 char *extra)
3705
3706{
3707 hdd_adapter_t *pHostapdAdapter = (netdev_priv(dev));
Gopichand Nakkala8a2b1442013-05-29 15:33:14 +05303708 hdd_context_t *pHddCtx;
Jeff Johnson295189b2012-06-20 16:38:30 -07003709 char *pLinkSpeed = (char*)extra;
Gopichand Nakkala8a2b1442013-05-29 15:33:14 +05303710 v_U32_t link_speed;
Jeff Johnson295189b2012-06-20 16:38:30 -07003711 unsigned short staId;
Gopichand Nakkala8a2b1442013-05-29 15:33:14 +05303712 int len = sizeof(v_U32_t)+1;
Jeff Johnson295189b2012-06-20 16:38:30 -07003713 v_BYTE_t macAddress[VOS_MAC_ADDR_SIZE];
3714 VOS_STATUS status;
Gopichand Nakkala8a2b1442013-05-29 15:33:14 +05303715 int rc, valid;
3716
3717 pHddCtx = WLAN_HDD_GET_CTX(pHostapdAdapter);
3718
3719 valid = wlan_hdd_validate_context(pHddCtx);
3720
3721 if (0 != valid)
3722 {
3723 hddLog(VOS_TRACE_LEVEL_ERROR, FL("HDD context not valid"));
3724 return valid;
3725 }
Jeff Johnson295189b2012-06-20 16:38:30 -07003726
Madan Mohan Koyyalamudie68989b2013-09-10 01:15:19 +05303727 hddLog(VOS_TRACE_LEVEL_INFO, "%s wrqu->data.length= %d\n", __func__, wrqu->data.length);
3728 status = hdd_string_to_hex ((char *)wrqu->data.pointer, wrqu->data.length, macAddress );
3729
3730 if (!VOS_IS_STATUS_SUCCESS(status ))
Jeff Johnson295189b2012-06-20 16:38:30 -07003731 {
Madan Mohan Koyyalamudie68989b2013-09-10 01:15:19 +05303732 hddLog(VOS_TRACE_LEVEL_ERROR, FL("String to Hex conversion Failed"));
Jeff Johnson295189b2012-06-20 16:38:30 -07003733 }
3734
Kiet Lam61589852013-09-19 17:10:58 +05303735 /* If no mac address is passed and/or its length is less than 17,
Madan Mohan Koyyalamudie68989b2013-09-10 01:15:19 +05303736 * link speed for first connected client will be returned.
3737 */
Kiet Lam61589852013-09-19 17:10:58 +05303738 if (!VOS_IS_STATUS_SUCCESS(status ) || wrqu->data.length < 17)
Madan Mohan Koyyalamudie68989b2013-09-10 01:15:19 +05303739 {
3740 status = hdd_softap_GetConnectedStaId(pHostapdAdapter, (void *)(&staId));
3741 }
3742 else
3743 {
3744 status = hdd_softap_GetStaId(pHostapdAdapter,
3745 (v_MACADDR_t *)macAddress, (void *)(&staId));
3746 }
Jeff Johnson295189b2012-06-20 16:38:30 -07003747
Gopichand Nakkala8a2b1442013-05-29 15:33:14 +05303748 if (!VOS_IS_STATUS_SUCCESS(status))
Jeff Johnson295189b2012-06-20 16:38:30 -07003749 {
Gopichand Nakkala8a2b1442013-05-29 15:33:14 +05303750 hddLog(VOS_TRACE_LEVEL_ERROR, FL("ERROR: HDD Failed to find sta id!!"));
Jeff Johnson295189b2012-06-20 16:38:30 -07003751 link_speed = 0;
3752 }
3753 else
3754 {
3755 status = wlan_hdd_get_classAstats_for_station(pHostapdAdapter , staId);
Gopichand Nakkala8a2b1442013-05-29 15:33:14 +05303756
Jeff Johnson295189b2012-06-20 16:38:30 -07003757 if (!VOS_IS_STATUS_SUCCESS(status ))
3758 {
Gopichand Nakkala8a2b1442013-05-29 15:33:14 +05303759 hddLog(VOS_TRACE_LEVEL_ERROR, FL("Unable to retrieve SME statistics"));
Jeff Johnson295189b2012-06-20 16:38:30 -07003760 return -EINVAL;
3761 }
Gopichand Nakkala8a2b1442013-05-29 15:33:14 +05303762
3763 WLANTL_GetSTALinkCapacity(pHddCtx->pvosContext,
3764 staId, &link_speed);
3765
3766 link_speed = link_speed / 10;
3767
3768 if (0 == link_speed)
3769 {
3770 /* The linkspeed returned by HAL is in units of 500kbps.
3771 * converting it to mbps.
3772 * This is required to support legacy firmware which does
3773 * not return link capacity.
3774 */
3775 link_speed =(int)pHostapdAdapter->hdd_stats.ClassA_stat.tx_rate/2;
3776 }
Jeff Johnson295189b2012-06-20 16:38:30 -07003777 }
3778
3779 wrqu->data.length = len;
Jeff Johnson02797792013-10-26 19:17:13 -07003780 rc = snprintf(pLinkSpeed, len, "%u", link_speed);
Gopichand Nakkala8a2b1442013-05-29 15:33:14 +05303781
Jeff Johnson295189b2012-06-20 16:38:30 -07003782 if ((rc < 0) || (rc >= len))
3783 {
3784 // encoding or length error?
Gopichand Nakkala8a2b1442013-05-29 15:33:14 +05303785 hddLog(VOS_TRACE_LEVEL_ERROR,FL( "Unable to encode link speed"));
Jeff Johnson295189b2012-06-20 16:38:30 -07003786 return -EIO;
3787 }
3788
3789 return 0;
3790}
3791
3792static const iw_handler hostapd_handler[] =
3793{
3794 (iw_handler) NULL, /* SIOCSIWCOMMIT */
3795 (iw_handler) NULL, /* SIOCGIWNAME */
3796 (iw_handler) NULL, /* SIOCSIWNWID */
3797 (iw_handler) NULL, /* SIOCGIWNWID */
3798 (iw_handler) NULL, /* SIOCSIWFREQ */
3799 (iw_handler) iw_get_ap_freq, /* SIOCGIWFREQ */
3800 (iw_handler) NULL, /* SIOCSIWMODE */
Madan Mohan Koyyalamudi0c2ba1b2013-10-01 19:47:50 +05303801 (iw_handler) iw_get_mode, /* SIOCGIWMODE */
Jeff Johnson295189b2012-06-20 16:38:30 -07003802 (iw_handler) NULL, /* SIOCSIWSENS */
3803 (iw_handler) NULL, /* SIOCGIWSENS */
3804 (iw_handler) NULL, /* SIOCSIWRANGE */
3805 (iw_handler) NULL, /* SIOCGIWRANGE */
3806 (iw_handler) NULL, /* SIOCSIWPRIV */
3807 (iw_handler) NULL, /* SIOCGIWPRIV */
3808 (iw_handler) NULL, /* SIOCSIWSTATS */
3809 (iw_handler) NULL, /* SIOCGIWSTATS */
3810 (iw_handler) NULL, /* SIOCSIWSPY */
3811 (iw_handler) NULL, /* SIOCGIWSPY */
3812 (iw_handler) NULL, /* SIOCSIWTHRSPY */
3813 (iw_handler) NULL, /* SIOCGIWTHRSPY */
3814 (iw_handler) NULL, /* SIOCSIWAP */
3815 (iw_handler) NULL, /* SIOCGIWAP */
3816 (iw_handler) iw_set_ap_mlme, /* SIOCSIWMLME */
3817 (iw_handler) NULL, /* SIOCGIWAPLIST */
3818 (iw_handler) NULL, /* SIOCSIWSCAN */
3819 (iw_handler) NULL, /* SIOCGIWSCAN */
3820 (iw_handler) NULL, /* SIOCSIWESSID */
3821 (iw_handler) NULL, /* SIOCGIWESSID */
3822 (iw_handler) NULL, /* SIOCSIWNICKN */
3823 (iw_handler) NULL, /* SIOCGIWNICKN */
3824 (iw_handler) NULL, /* -- hole -- */
3825 (iw_handler) NULL, /* -- hole -- */
3826 (iw_handler) NULL, /* SIOCSIWRATE */
3827 (iw_handler) NULL, /* SIOCGIWRATE */
3828 (iw_handler) NULL, /* SIOCSIWRTS */
3829 (iw_handler) iw_get_ap_rts_threshold, /* SIOCGIWRTS */
3830 (iw_handler) NULL, /* SIOCSIWFRAG */
3831 (iw_handler) iw_get_ap_frag_threshold, /* SIOCGIWFRAG */
3832 (iw_handler) NULL, /* SIOCSIWTXPOW */
3833 (iw_handler) NULL, /* SIOCGIWTXPOW */
3834 (iw_handler) NULL, /* SIOCSIWRETRY */
3835 (iw_handler) NULL, /* SIOCGIWRETRY */
3836 (iw_handler) NULL, /* SIOCSIWENCODE */
3837 (iw_handler) NULL, /* SIOCGIWENCODE */
3838 (iw_handler) NULL, /* SIOCSIWPOWER */
3839 (iw_handler) NULL, /* SIOCGIWPOWER */
3840 (iw_handler) NULL, /* -- hole -- */
3841 (iw_handler) NULL, /* -- hole -- */
3842 (iw_handler) iw_set_ap_genie, /* SIOCSIWGENIE */
3843 (iw_handler) NULL, /* SIOCGIWGENIE */
3844 (iw_handler) iw_set_auth_hostap, /* SIOCSIWAUTH */
3845 (iw_handler) NULL, /* SIOCGIWAUTH */
3846 (iw_handler) iw_set_ap_encodeext, /* SIOCSIWENCODEEXT */
3847 (iw_handler) NULL, /* SIOCGIWENCODEEXT */
3848 (iw_handler) NULL, /* SIOCSIWPMKSA */
3849};
3850
Madan Mohan Koyyalamudia53c4dc2012-11-13 10:35:42 -08003851#define IW_PRIV_TYPE_OPTIE (IW_PRIV_TYPE_BYTE | QCSAP_MAX_OPT_IE)
Jeff Johnson295189b2012-06-20 16:38:30 -07003852#define IW_PRIV_TYPE_MLME \
Madan Mohan Koyyalamudia53c4dc2012-11-13 10:35:42 -08003853 (IW_PRIV_TYPE_BYTE | sizeof(struct ieee80211req_mlme))
Jeff Johnson295189b2012-06-20 16:38:30 -07003854
3855static const struct iw_priv_args hostapd_private_args[] = {
3856 { QCSAP_IOCTL_SETPARAM,
3857 IW_PRIV_TYPE_INT | IW_PRIV_SIZE_FIXED | 2, 0, "setparam" },
3858 { QCSAP_IOCTL_SETPARAM,
3859 IW_PRIV_TYPE_INT | IW_PRIV_SIZE_FIXED | 1, 0, "" },
3860 { QCSAP_PARAM_MAX_ASSOC,
3861 IW_PRIV_TYPE_INT | IW_PRIV_SIZE_FIXED | 1, 0, "setMaxAssoc" },
3862 { QCSAP_PARAM_HIDE_SSID,
3863 IW_PRIV_TYPE_INT | IW_PRIV_SIZE_FIXED | 1, 0, "hideSSID" },
Leo Chang614d2072013-08-22 14:59:44 -07003864 { QCSAP_PARAM_SET_MC_RATE,
3865 IW_PRIV_TYPE_INT | IW_PRIV_SIZE_FIXED | 1, 0, "setMcRate" },
Jeff Johnson295189b2012-06-20 16:38:30 -07003866 { QCSAP_IOCTL_GETPARAM,
3867 IW_PRIV_TYPE_INT | IW_PRIV_SIZE_FIXED | 1,
3868 IW_PRIV_TYPE_INT | IW_PRIV_SIZE_FIXED | 1, "getparam" },
3869 { QCSAP_IOCTL_GETPARAM, 0,
3870 IW_PRIV_TYPE_INT | IW_PRIV_SIZE_FIXED | 1, "" },
3871 { QCSAP_PARAM_MAX_ASSOC, 0,
3872 IW_PRIV_TYPE_INT | IW_PRIV_SIZE_FIXED | 1, "getMaxAssoc" },
Jeff Johnson43971f52012-07-17 12:26:56 -07003873 { QCSAP_PARAM_GET_WLAN_DBG, 0,
3874 IW_PRIV_TYPE_INT | IW_PRIV_SIZE_FIXED | 1, "getwlandbg" },
3875 { QCSAP_PARAM_AUTO_CHANNEL, 0,
3876 IW_PRIV_TYPE_INT | IW_PRIV_SIZE_FIXED | 1, "getAutoChannel" },
Jeff Johnson295189b2012-06-20 16:38:30 -07003877 { QCSAP_PARAM_MODULE_DOWN_IND, 0,
3878 IW_PRIV_TYPE_INT | IW_PRIV_SIZE_FIXED | 1, "moduleDownInd" },
3879 { QCSAP_PARAM_CLR_ACL, 0,
3880 IW_PRIV_TYPE_INT | IW_PRIV_SIZE_FIXED | 1, "setClearAcl" },
3881 { QCSAP_PARAM_ACL_MODE,
3882 IW_PRIV_TYPE_INT | IW_PRIV_SIZE_FIXED | 1, 0, "setAclMode" },
3883 { QCSAP_IOCTL_COMMIT,
3884 IW_PRIV_TYPE_BYTE | sizeof(struct s_CommitConfig) | IW_PRIV_SIZE_FIXED, 0, "commit" },
3885 { QCSAP_IOCTL_SETMLME,
3886 IW_PRIV_TYPE_BYTE | sizeof(struct sQcSapreq_mlme)| IW_PRIV_SIZE_FIXED, 0, "setmlme" },
3887 { QCSAP_IOCTL_GET_STAWPAIE,
3888 IW_PRIV_TYPE_BYTE | IW_PRIV_SIZE_FIXED | 1, 0, "get_staWPAIE" },
3889 { QCSAP_IOCTL_SETWPAIE,
3890 IW_PRIV_TYPE_BYTE | QCSAP_MAX_WSC_IE | IW_PRIV_SIZE_FIXED, 0, "setwpaie" },
3891 { QCSAP_IOCTL_STOPBSS,
3892 IW_PRIV_TYPE_BYTE | IW_PRIV_SIZE_FIXED, 0, "stopbss" },
3893 { QCSAP_IOCTL_VERSION, 0,
3894 IW_PRIV_TYPE_CHAR | QCSAP_MAX_WSC_IE, "version" },
Gopichand Nakkala976e3252013-01-03 15:45:56 -08003895 { QCSAP_IOCTL_GET_STA_INFO, 0,
3896 IW_PRIV_TYPE_CHAR | WE_SAP_MAX_STA_INFO, "get_sta_info" },
Jeff Johnson295189b2012-06-20 16:38:30 -07003897 { QCSAP_IOCTL_GET_WPS_PBC_PROBE_REQ_IES,
3898 IW_PRIV_TYPE_BYTE | sizeof(sQcSapreq_WPSPBCProbeReqIES_t) | IW_PRIV_SIZE_FIXED | 1, 0, "getProbeReqIEs" },
3899 { QCSAP_IOCTL_GET_CHANNEL, 0,
Jeff Johnson43971f52012-07-17 12:26:56 -07003900 IW_PRIV_TYPE_INT | IW_PRIV_SIZE_FIXED | 1, "getchannel" },
Jeff Johnson295189b2012-06-20 16:38:30 -07003901 { QCSAP_IOCTL_ASSOC_STA_MACADDR, 0,
3902 IW_PRIV_TYPE_BYTE | /*((WLAN_MAX_STA_COUNT*6)+100)*/1 , "get_assoc_stamac" },
3903 { QCSAP_IOCTL_DISASSOC_STA,
3904 IW_PRIV_TYPE_BYTE | IW_PRIV_SIZE_FIXED | 6 , 0, "disassoc_sta" },
3905 { QCSAP_IOCTL_AP_STATS,
3906 IW_PRIV_TYPE_BYTE | QCSAP_MAX_WSC_IE, 0, "ap_stats" },
3907 { QCSAP_IOCTL_PRIV_GET_SOFTAP_LINK_SPEED,
3908 IW_PRIV_TYPE_CHAR | 18,
Gopichand Nakkala8a2b1442013-05-29 15:33:14 +05303909 IW_PRIV_TYPE_CHAR | 5, "getLinkSpeed" },
Jeff Johnson295189b2012-06-20 16:38:30 -07003910
3911 { QCSAP_IOCTL_PRIV_SET_THREE_INT_GET_NONE,
3912 IW_PRIV_TYPE_INT | IW_PRIV_SIZE_FIXED | 3, 0, "" },
3913 /* handlers for sub-ioctl */
3914 { WE_SET_WLAN_DBG,
3915 IW_PRIV_TYPE_INT | IW_PRIV_SIZE_FIXED | 3,
3916 0,
3917 "setwlandbg" },
3918
3919 /* handlers for main ioctl */
3920 { QCSAP_IOCTL_PRIV_SET_VAR_INT_GET_NONE,
3921 IW_PRIV_TYPE_INT | MAX_VAR_ARGS,
3922 0,
3923 "" },
3924
3925 /* handlers for sub-ioctl */
3926 { WE_LOG_DUMP_CMD,
3927 IW_PRIV_TYPE_INT | MAX_VAR_ARGS,
3928 0,
3929 "dump" },
Jeff Johnson295189b2012-06-20 16:38:30 -07003930 { WE_P2P_NOA_CMD,
3931 IW_PRIV_TYPE_INT | MAX_VAR_ARGS,
3932 0,
3933 "SetP2pPs" },
Madan Mohan Koyyalamudid5f04ca2012-11-06 15:51:26 -08003934 /* handlers for sub ioctl */
3935 {
3936 WE_MCC_CONFIG_CREDENTIAL,
3937 IW_PRIV_TYPE_INT | MAX_VAR_ARGS,
3938 0,
3939 "setMccCrdnl" },
3940
3941 /* handlers for sub ioctl */
3942 {
3943 WE_MCC_CONFIG_PARAMS,
3944 IW_PRIV_TYPE_INT | MAX_VAR_ARGS,
3945 0,
3946 "setMccConfig" },
3947
Jeff Johnson295189b2012-06-20 16:38:30 -07003948 /* handlers for main ioctl */
3949 { QCSAP_IOCTL_MODIFY_ACL,
3950 IW_PRIV_TYPE_BYTE | IW_PRIV_SIZE_FIXED | 8,
3951 0,
3952 "modify_acl" },
3953
3954 /* handlers for main ioctl */
3955 { QCSAP_IOCTL_GET_CHANNEL_LIST,
3956 0,
3957 IW_PRIV_TYPE_BYTE | sizeof(tChannelListInfo),
3958 "getChannelList" },
3959
Jeff Johnsone7245742012-09-05 17:12:55 -07003960 /* handlers for main ioctl */
3961 { QCSAP_IOCTL_SET_TX_POWER,
3962 IW_PRIV_TYPE_INT| IW_PRIV_SIZE_FIXED | 1,
3963 0,
Madan Mohan Koyyalamudid12bf052012-11-27 19:07:55 +05303964 "setTxPower" },
schang86c22c42013-03-13 18:41:24 -07003965
3966 /* handlers for main ioctl */
3967 { QCSAP_IOCTL_SET_MAX_TX_POWER,
3968 IW_PRIV_TYPE_INT| IW_PRIV_SIZE_FIXED | 1,
3969 0,
3970 "setTxMaxPower" },
Kiet Lambcf38522013-10-26 18:28:27 +05303971
3972 { QCSAP_IOCTL_DATAPATH_SNAP_SHOT,
3973 IW_PRIV_TYPE_NONE | IW_PRIV_TYPE_NONE,
3974 0,
3975 "dataSnapshot" },
3976
3977 /* handlers for main ioctl */
3978 { QCSAP_IOCTL_SET_TRAFFIC_MONITOR,
3979 IW_PRIV_TYPE_INT| IW_PRIV_SIZE_FIXED | 1,
3980 0,
3981 "setTrafficMon" },
Jeff Johnson295189b2012-06-20 16:38:30 -07003982};
Jeff Johnsone7245742012-09-05 17:12:55 -07003983
Jeff Johnson295189b2012-06-20 16:38:30 -07003984static const iw_handler hostapd_private[] = {
3985 [QCSAP_IOCTL_SETPARAM - SIOCIWFIRSTPRIV] = iw_softap_setparam, //set priv ioctl
3986 [QCSAP_IOCTL_GETPARAM - SIOCIWFIRSTPRIV] = iw_softap_getparam, //get priv ioctl
3987 [QCSAP_IOCTL_COMMIT - SIOCIWFIRSTPRIV] = iw_softap_commit, //get priv ioctl
3988 [QCSAP_IOCTL_SETMLME - SIOCIWFIRSTPRIV] = iw_softap_setmlme,
3989 [QCSAP_IOCTL_GET_STAWPAIE - SIOCIWFIRSTPRIV] = iw_get_genie, //get station genIE
3990 [QCSAP_IOCTL_SETWPAIE - SIOCIWFIRSTPRIV] = iw_softap_setwpsie,
3991 [QCSAP_IOCTL_STOPBSS - SIOCIWFIRSTPRIV] = iw_softap_stopbss, // stop bss
3992 [QCSAP_IOCTL_VERSION - SIOCIWFIRSTPRIV] = iw_softap_version, // get driver version
3993 [QCSAP_IOCTL_GET_WPS_PBC_PROBE_REQ_IES - SIOCIWFIRSTPRIV] = iw_get_WPSPBCProbeReqIEs,
3994 [QCSAP_IOCTL_GET_CHANNEL - SIOCIWFIRSTPRIV] = iw_softap_getchannel,
3995 [QCSAP_IOCTL_ASSOC_STA_MACADDR - SIOCIWFIRSTPRIV] = iw_softap_getassoc_stamacaddr,
3996 [QCSAP_IOCTL_DISASSOC_STA - SIOCIWFIRSTPRIV] = iw_softap_disassoc_sta,
3997 [QCSAP_IOCTL_AP_STATS - SIOCIWFIRSTPRIV] = iw_softap_ap_stats,
3998 [QCSAP_IOCTL_PRIV_SET_THREE_INT_GET_NONE - SIOCIWFIRSTPRIV] = iw_set_three_ints_getnone,
3999 [QCSAP_IOCTL_PRIV_SET_VAR_INT_GET_NONE - SIOCIWFIRSTPRIV] = iw_set_var_ints_getnone,
4000 [QCSAP_IOCTL_SET_CHANNEL_RANGE - SIOCIWFIRSTPRIV] = iw_softap_set_channel_range,
4001 [QCSAP_IOCTL_MODIFY_ACL - SIOCIWFIRSTPRIV] = iw_softap_modify_acl,
4002 [QCSAP_IOCTL_GET_CHANNEL_LIST - SIOCIWFIRSTPRIV] = iw_softap_get_channel_list,
Gopichand Nakkala976e3252013-01-03 15:45:56 -08004003 [QCSAP_IOCTL_GET_STA_INFO - SIOCIWFIRSTPRIV] = iw_softap_get_sta_info,
Jeff Johnsone7245742012-09-05 17:12:55 -07004004 [QCSAP_IOCTL_PRIV_GET_SOFTAP_LINK_SPEED - SIOCIWFIRSTPRIV] = iw_get_softap_linkspeed,
4005 [QCSAP_IOCTL_SET_TX_POWER - SIOCIWFIRSTPRIV] = iw_softap_set_tx_power,
schang86c22c42013-03-13 18:41:24 -07004006 [QCSAP_IOCTL_SET_MAX_TX_POWER - SIOCIWFIRSTPRIV] = iw_softap_set_max_tx_power,
Madan Mohan Koyyalamudia96f5442013-05-10 11:32:06 +05304007 [QCSAP_IOCTL_DATAPATH_SNAP_SHOT - SIOCIWFIRSTPRIV] = iw_display_data_path_snapshot,
Kiet Lambcf38522013-10-26 18:28:27 +05304008 [QCSAP_IOCTL_SET_TRAFFIC_MONITOR - SIOCIWFIRSTPRIV] = iw_softap_set_trafficmonitor,
Jeff Johnson295189b2012-06-20 16:38:30 -07004009};
4010const struct iw_handler_def hostapd_handler_def = {
4011 .num_standard = sizeof(hostapd_handler) / sizeof(hostapd_handler[0]),
4012 .num_private = sizeof(hostapd_private) / sizeof(hostapd_private[0]),
4013 .num_private_args = sizeof(hostapd_private_args) / sizeof(hostapd_private_args[0]),
4014 .standard = (iw_handler *)hostapd_handler,
4015 .private = (iw_handler *)hostapd_private,
4016 .private_args = hostapd_private_args,
4017 .get_wireless_stats = NULL,
4018};
4019#if LINUX_VERSION_CODE > KERNEL_VERSION(2,6,29)
4020struct net_device_ops net_ops_struct = {
4021 .ndo_open = hdd_hostapd_open,
4022 .ndo_stop = hdd_hostapd_stop,
4023 .ndo_uninit = hdd_hostapd_uninit,
4024 .ndo_start_xmit = hdd_softap_hard_start_xmit,
4025 .ndo_tx_timeout = hdd_softap_tx_timeout,
4026 .ndo_get_stats = hdd_softap_stats,
4027 .ndo_set_mac_address = hdd_hostapd_set_mac_address,
4028 .ndo_do_ioctl = hdd_hostapd_ioctl,
4029 .ndo_change_mtu = hdd_hostapd_change_mtu,
4030 .ndo_select_queue = hdd_hostapd_select_queue,
4031 };
4032#endif
4033
4034int hdd_set_hostapd(hdd_adapter_t *pAdapter)
4035{
4036 return VOS_STATUS_SUCCESS;
4037}
4038
4039void hdd_set_ap_ops( struct net_device *pWlanHostapdDev )
4040{
4041#if LINUX_VERSION_CODE > KERNEL_VERSION(2,6,29)
4042 pWlanHostapdDev->netdev_ops = &net_ops_struct;
4043#else
4044 pWlanHostapdDev->open = hdd_hostapd_open;
4045 pWlanHostapdDev->stop = hdd_hostapd_stop;
4046 pWlanHostapdDev->uninit = hdd_hostapd_uninit;
4047 pWlanHostapdDev->hard_start_xmit = hdd_softap_hard_start_xmit;
4048 pWlanHostapdDev->tx_timeout = hdd_softap_tx_timeout;
4049 pWlanHostapdDev->get_stats = hdd_softap_stats;
4050 pWlanHostapdDev->set_mac_address = hdd_hostapd_set_mac_address;
4051 pWlanHostapdDev->do_ioctl = hdd_hostapd_ioctl;
4052#endif
4053}
4054
4055VOS_STATUS hdd_init_ap_mode( hdd_adapter_t *pAdapter )
4056{
4057 hdd_hostapd_state_t * phostapdBuf;
4058 struct net_device *dev = pAdapter->dev;
Kiran Kumar Lokere0ad5cd32013-06-25 11:26:22 -07004059 hdd_context_t *pHddCtx = WLAN_HDD_GET_CTX(pAdapter);
Jeff Johnson295189b2012-06-20 16:38:30 -07004060 VOS_STATUS status;
4061 ENTER();
4062 // Allocate the Wireless Extensions state structure
4063 phostapdBuf = WLAN_HDD_GET_HOSTAP_STATE_PTR( pAdapter );
4064
Kiran Kumar Lokere0ad5cd32013-06-25 11:26:22 -07004065 sme_SetCurrDeviceMode(pHddCtx->hHal, pAdapter->device_mode);
4066
Jeff Johnson295189b2012-06-20 16:38:30 -07004067 // Zero the memory. This zeros the profile structure.
4068 memset(phostapdBuf, 0,sizeof(hdd_hostapd_state_t));
4069
4070 // Set up the pointer to the Wireless Extensions state structure
4071 // NOP
4072 status = hdd_set_hostapd(pAdapter);
4073 if(!VOS_IS_STATUS_SUCCESS(status)) {
4074 VOS_TRACE(VOS_MODULE_ID_HDD, VOS_TRACE_LEVEL_ERROR, ("ERROR: hdd_set_hostapd failed!!\n"));
4075 return status;
4076 }
4077
4078 status = vos_event_init(&phostapdBuf->vosEvent);
4079 if (!VOS_IS_STATUS_SUCCESS(status))
4080 {
4081 VOS_TRACE(VOS_MODULE_ID_HDD, VOS_TRACE_LEVEL_ERROR, ("ERROR: Hostapd HDD vos event init failed!!\n"));
4082 return status;
4083 }
4084
4085 init_completion(&pAdapter->session_close_comp_var);
4086 init_completion(&pAdapter->session_open_comp_var);
4087
4088 sema_init(&(WLAN_HDD_GET_AP_CTX_PTR(pAdapter))->semWpsPBCOverlapInd, 1);
4089
4090 // Register as a wireless device
4091 dev->wireless_handlers = (struct iw_handler_def *)& hostapd_handler_def;
4092
4093 //Initialize the data path module
4094 status = hdd_softap_init_tx_rx(pAdapter);
4095 if ( !VOS_IS_STATUS_SUCCESS( status ))
4096 {
Madan Mohan Koyyalamudi87054ba2012-11-02 13:24:12 -07004097 hddLog(VOS_TRACE_LEVEL_FATAL, "%s: hdd_softap_init_tx_rx failed", __func__);
Jeff Johnson295189b2012-06-20 16:38:30 -07004098 }
Madan Mohan Koyyalamudi8c6dec82013-09-26 15:56:13 +05304099
4100 status = hdd_wmm_adapter_init( pAdapter );
4101 if (!VOS_IS_STATUS_SUCCESS(status))
4102 {
4103 hddLog(VOS_TRACE_LEVEL_ERROR,
Jeff Johnson0299d0a2013-10-30 12:37:43 -07004104 "hdd_wmm_adapter_init() failed with status code %08d [x%08x]",
Madan Mohan Koyyalamudi8c6dec82013-09-26 15:56:13 +05304105 status, status );
4106 goto error_wmm_init;
4107 }
4108
4109 set_bit(WMM_INIT_DONE, &pAdapter->event_flags);
4110
Jeff Johnson295189b2012-06-20 16:38:30 -07004111 wlan_hdd_set_monitor_tx_adapter( WLAN_HDD_GET_CTX(pAdapter), pAdapter );
Madan Mohan Koyyalamudi8c6dec82013-09-26 15:56:13 +05304112
4113 return status;
4114
4115error_wmm_init:
4116 hdd_softap_deinit_tx_rx( pAdapter );
Jeff Johnson295189b2012-06-20 16:38:30 -07004117 EXIT();
4118 return status;
4119}
4120
4121hdd_adapter_t* hdd_wlan_create_ap_dev( hdd_context_t *pHddCtx, tSirMacAddr macAddr, tANI_U8 *iface_name )
4122{
4123 struct net_device *pWlanHostapdDev = NULL;
4124 hdd_adapter_t *pHostapdAdapter = NULL;
4125 v_CONTEXT_t pVosContext= NULL;
4126
Jeff Johnson295189b2012-06-20 16:38:30 -07004127 pWlanHostapdDev = alloc_netdev_mq(sizeof(hdd_adapter_t), iface_name, ether_setup, NUM_TX_QUEUES);
Jeff Johnson295189b2012-06-20 16:38:30 -07004128
4129 if (pWlanHostapdDev != NULL)
4130 {
4131 pHostapdAdapter = netdev_priv(pWlanHostapdDev);
4132
4133 //Init the net_device structure
4134 ether_setup(pWlanHostapdDev);
4135
4136 //Initialize the adapter context to zeros.
4137 vos_mem_zero(pHostapdAdapter, sizeof( hdd_adapter_t ));
4138 pHostapdAdapter->dev = pWlanHostapdDev;
4139 pHostapdAdapter->pHddCtx = pHddCtx;
4140 pHostapdAdapter->magic = WLAN_HDD_ADAPTER_MAGIC;
4141
4142 //Get the Global VOSS context.
4143 pVosContext = vos_get_global_context(VOS_MODULE_ID_SYS, NULL);
4144 //Save the adapter context in global context for future.
4145 ((VosContextType*)(pVosContext))->pHDDSoftAPContext = (v_VOID_t*)pHostapdAdapter;
4146
4147 //Init the net_device structure
4148 strlcpy(pWlanHostapdDev->name, (const char *)iface_name, IFNAMSIZ);
4149
4150 hdd_set_ap_ops( pHostapdAdapter->dev );
4151
4152 pWlanHostapdDev->tx_queue_len = NET_DEV_TX_QUEUE_LEN;
4153 pWlanHostapdDev->watchdog_timeo = HDD_TX_TIMEOUT;
4154 pWlanHostapdDev->mtu = HDD_DEFAULT_MTU;
4155
4156 vos_mem_copy(pWlanHostapdDev->dev_addr, (void *)macAddr,sizeof(tSirMacAddr));
4157 vos_mem_copy(pHostapdAdapter->macAddressCurrent.bytes, (void *)macAddr, sizeof(tSirMacAddr));
4158
4159 pWlanHostapdDev->destructor = free_netdev;
Jeff Johnson295189b2012-06-20 16:38:30 -07004160 pWlanHostapdDev->ieee80211_ptr = &pHostapdAdapter->wdev ;
4161 pHostapdAdapter->wdev.wiphy = pHddCtx->wiphy;
4162 pHostapdAdapter->wdev.netdev = pWlanHostapdDev;
4163 init_completion(&pHostapdAdapter->tx_action_cnf_event);
Jeff Johnson295189b2012-06-20 16:38:30 -07004164 init_completion(&pHostapdAdapter->cancel_rem_on_chan_var);
4165 init_completion(&pHostapdAdapter->rem_on_chan_ready_event);
4166#if (LINUX_VERSION_CODE >= KERNEL_VERSION(2,6,38))
4167 init_completion(&pHostapdAdapter->offchannel_tx_event);
4168#endif
4169
Jeff Johnson295189b2012-06-20 16:38:30 -07004170 SET_NETDEV_DEV(pWlanHostapdDev, pHddCtx->parent_dev);
4171 }
4172 return pHostapdAdapter;
4173}
4174
4175VOS_STATUS hdd_register_hostapd( hdd_adapter_t *pAdapter, tANI_U8 rtnl_lock_held )
4176{
4177 struct net_device *dev = pAdapter->dev;
4178 VOS_STATUS status = VOS_STATUS_SUCCESS;
4179
4180 ENTER();
4181
4182 if( rtnl_lock_held )
4183 {
Madan Mohan Koyyalamudid8ac8662012-11-06 19:04:56 -08004184 if (strnchr(dev->name, strlen(dev->name), '%')) {
Jeff Johnson295189b2012-06-20 16:38:30 -07004185 if( dev_alloc_name(dev, dev->name) < 0 )
4186 {
4187 hddLog(VOS_TRACE_LEVEL_FATAL, "%s:Failed:dev_alloc_name", __func__);
4188 return VOS_STATUS_E_FAILURE;
4189 }
4190 }
4191 if (register_netdevice(dev))
4192 {
4193 hddLog(VOS_TRACE_LEVEL_FATAL,
4194 "%s:Failed:register_netdevice", __func__);
4195 return VOS_STATUS_E_FAILURE;
4196 }
4197 }
4198 else
4199 {
4200 if (register_netdev(dev))
4201 {
4202 hddLog(VOS_TRACE_LEVEL_FATAL, "%s: Failed:register_netdev", __func__);
4203 return VOS_STATUS_E_FAILURE;
4204 }
4205 }
4206 set_bit(NET_DEVICE_REGISTERED, &pAdapter->event_flags);
4207
4208 EXIT();
4209 return status;
4210}
4211
4212VOS_STATUS hdd_unregister_hostapd(hdd_adapter_t *pAdapter)
4213{
4214 ENTER();
4215
4216 hdd_softap_deinit_tx_rx(pAdapter);
4217
4218 /* if we are being called during driver unload, then the dev has already
4219 been invalidated. if we are being called at other times, then we can
4220 detatch the wireless device handlers */
4221 if (pAdapter->dev)
4222 {
4223 pAdapter->dev->wireless_handlers = NULL;
4224 }
4225 EXIT();
4226 return 0;
4227}