blob: e68aa7a80fc734bdfcf202f7e3fef029e9497215 [file] [log] [blame]
Jeff Johnson295189b2012-06-20 16:38:30 -07001/*
Rajeev Kumar Sirasanagandla5b21a9c2018-01-08 17:05:11 +05302 * Copyright (c) 2012-2018 The Linux Foundation. All rights reserved.
Kiet Lam842dad02014-02-18 18:44:02 -08003 *
4 * Previously licensed under the ISC license by Qualcomm Atheros, Inc.
5 *
6 *
7 * Permission to use, copy, modify, and/or distribute this software for
8 * any purpose with or without fee is hereby granted, provided that the
9 * above copyright notice and this permission notice appear in all
10 * copies.
11 *
12 * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL
13 * WARRANTIES WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED
14 * WARRANTIES OF MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE
15 * AUTHOR BE LIABLE FOR ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL
16 * DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR
17 * PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER
18 * TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR
19 * PERFORMANCE OF THIS SOFTWARE.
Gopichand Nakkala92f07d82013-01-08 21:16:34 -080020 */
Kiet Lam842dad02014-02-18 18:44:02 -080021
22/*
23 * This file was originally distributed by Qualcomm Atheros, Inc.
24 * under proprietary terms before Copyright ownership was assigned
25 * to the Linux Foundation.
26 */
27
Jeff Johnson295189b2012-06-20 16:38:30 -070028/**=============================================================================
29* wlan_hdd_early_suspend.c
30*
31* \brief power management functions
32*
33* Description
Jeff Johnson295189b2012-06-20 16:38:30 -070034*
35==============================================================================**/
36/* $HEADER$ */
37
38/**-----------------------------------------------------------------------------
39* Include files
40* ----------------------------------------------------------------------------*/
Jeff Johnson295189b2012-06-20 16:38:30 -070041
42#include <linux/pm.h>
43#include <linux/wait.h>
Jeff Johnson295189b2012-06-20 16:38:30 -070044#include <wlan_hdd_includes.h>
45#include <wlan_qct_driver.h>
Rajeev Kumar Sirasanagandla5b21a9c2018-01-08 17:05:11 +053046
47#if (LINUX_VERSION_CODE >= KERNEL_VERSION(3, 19, 0)) && \
48 defined(WLAN_OPEN_SOURCE)
49#include <linux/device.h>
50#include <linux/pm_wakeup.h>
51#else
Jeff Johnson295189b2012-06-20 16:38:30 -070052#include <linux/wakelock.h>
Rajeev Kumar Sirasanagandla5b21a9c2018-01-08 17:05:11 +053053#endif
Jeff Johnson295189b2012-06-20 16:38:30 -070054
55#include "halTypes.h"
56#include "sme_Api.h"
57#include <vos_api.h>
Jeff Johnson295189b2012-06-20 16:38:30 -070058#include <vos_sched.h>
59#include <macInitApi.h>
Jeff Johnson295189b2012-06-20 16:38:30 -070060#include <wlan_qct_sys.h>
61#include <wlan_btc_svc.h>
62#include <wlan_nlink_common.h>
63#include <wlan_hdd_main.h>
64#include <wlan_hdd_assoc.h>
65#include <wlan_hdd_dev_pwr.h>
Jeff Johnson295189b2012-06-20 16:38:30 -070066#include <wlan_nlink_srv.h>
67#include <wlan_hdd_misc.h>
Amar Singhald08ce752014-03-21 16:28:27 -070068#include "wlan_qct_wda.h"
Jeff Johnson295189b2012-06-20 16:38:30 -070069
Jeff Johnson295189b2012-06-20 16:38:30 -070070#include <linux/semaphore.h>
71#include <wlan_hdd_hostapd.h>
Jeff Johnson295189b2012-06-20 16:38:30 -070072#include "cfgApi.h"
Siddharth Bhal7bd19932015-03-03 16:54:36 +053073#include <wlan_logging_sock_svc.h>
Jeff Johnson295189b2012-06-20 16:38:30 -070074
75#ifdef WLAN_BTAMP_FEATURE
76#include "bapApi.h"
77#include "bap_hdd_main.h"
78#include "bap_hdd_misc.h"
79#endif
80
Jeff Johnsone7245742012-09-05 17:12:55 -070081#include <linux/wcnss_wlan.h>
Jeff Johnson295189b2012-06-20 16:38:30 -070082#include <linux/inetdevice.h>
83#include <wlan_hdd_cfg.h>
Gopichand Nakkala870cbae2013-03-15 21:16:09 +053084#include <wlan_hdd_cfg80211.h>
Gopichand Nakkala746a9452013-06-11 12:45:54 +053085#include <net/addrconf.h>
Jeff Johnson295189b2012-06-20 16:38:30 -070086/**-----------------------------------------------------------------------------
87* Preprocessor definitions and constants
88* ----------------------------------------------------------------------------*/
89
90/**-----------------------------------------------------------------------------
91* Type declarations
92* ----------------------------------------------------------------------------*/
93
94/**-----------------------------------------------------------------------------
95* Function and variables declarations
96* ----------------------------------------------------------------------------*/
97#include "wlan_hdd_power.h"
98#include "wlan_hdd_packet_filtering.h"
99
Sameer Thalappile5637f42013-08-07 15:46:55 -0700100#define HDD_SSR_BRING_UP_TIME 180000
Hardik Kantilal Patele1760e12014-01-21 15:57:21 +0530101#define NS_DEFAULT_SLOT_INDEX 4
102#define NS_EXTENDED_SLOT_INDEX 18
Jeff Johnson295189b2012-06-20 16:38:30 -0700103
104static eHalStatus g_full_pwr_status;
105static eHalStatus g_standby_status;
106
107extern VOS_STATUS hdd_post_voss_start_config(hdd_context_t* pHddCtx);
Ravi Kumar Bokka585faca2017-03-01 16:18:41 +0530108extern void hdd_wlan_initial_scan(hdd_adapter_t *pAdapter);
Jeff Johnson295189b2012-06-20 16:38:30 -0700109
110extern struct notifier_block hdd_netdev_notifier;
Jeff Johnson295189b2012-06-20 16:38:30 -0700111extern tVOS_CON_MODE hdd_get_conparam ( void );
Jeff Johnson295189b2012-06-20 16:38:30 -0700112
Madan Mohan Koyyalamudib0e70642012-10-11 12:20:22 -0700113static struct timer_list ssr_timer;
114static bool ssr_timer_started;
Jeff Johnson295189b2012-06-20 16:38:30 -0700115
Mukul Sharma75ee8aa2016-12-01 14:28:10 +0530116void inline check_and_set_suspend_resume_mcbc_filter(hdd_context_t *pHddCtx)
117{
118 hddLog(VOS_TRACE_LEVEL_INFO,
119 FL("offload: sus_res_mcbc_filter_valid: %d sus_res_mcbc_filter: %d configuredMcBcFilter: %d"),
120 pHddCtx->sus_res_mcastbcast_filter_valid,
121 pHddCtx->sus_res_mcastbcast_filter,
122 pHddCtx->configuredMcastBcastFilter);
123 if ( VOS_FALSE == pHddCtx->sus_res_mcastbcast_filter_valid)
124 {
125 pHddCtx->sus_res_mcastbcast_filter =
126 pHddCtx->configuredMcastBcastFilter;
127 pHddCtx->sus_res_mcastbcast_filter_valid = VOS_TRUE;
128 hddLog(VOS_TRACE_LEVEL_INFO,
129 FL("offload: saving sus_res_mcastbcast_filter = %d"),
130 pHddCtx->sus_res_mcastbcast_filter);
131 }
132}
Abhishek Singh937ec542016-01-05 18:03:14 +0530133
134#ifdef FEATURE_WLAN_DIAG_SUPPORT
135/**
136 * hdd_wlan_offload_event()- send offloads event
137 *
138 * @type: offload type
139 * @state: enabled or disabled
140 *
141 * This Function send offloads enable/disable diag event
142 *
143 * Return: void.
144 */
145
146void hdd_wlan_offload_event(uint8_t type, uint8_t state)
147{
148 WLAN_VOS_DIAG_EVENT_DEF(host_offload,
149 struct vos_event_offload_req);
150 vos_mem_zero(&host_offload, sizeof(host_offload));
151
152 host_offload.offload_type = type;
153 host_offload.state = state;
154
155 WLAN_VOS_DIAG_EVENT_REPORT(&host_offload, EVENT_OFFLOAD_REQ);
156}
157#endif /* FEATURE_WLAN_DIAG_SUPPORT */
158
Jeff Johnson295189b2012-06-20 16:38:30 -0700159//Callback invoked by PMC to report status of standby request
160void hdd_suspend_standby_cbk (void *callbackContext, eHalStatus status)
161{
162 hdd_context_t *pHddCtx = (hdd_context_t*)callbackContext;
163 hddLog(VOS_TRACE_LEVEL_INFO, "%s: Standby status = %d", __func__, status);
164 g_standby_status = status;
165
166 if(eHAL_STATUS_SUCCESS == status)
167 {
168 pHddCtx->hdd_ps_state = eHDD_SUSPEND_STANDBY;
169 }
170 else
171 {
172 hddLog(VOS_TRACE_LEVEL_FATAL,"%s: sme_RequestStandby failed",__func__);
173 }
174
175 complete(&pHddCtx->standby_comp_var);
176}
177
178//Callback invoked by PMC to report status of full power request
179void hdd_suspend_full_pwr_callback(void *callbackContext, eHalStatus status)
180{
181 hdd_context_t *pHddCtx = (hdd_context_t*)callbackContext;
182 hddLog(VOS_TRACE_LEVEL_INFO, "%s: Full Power status = %d", __func__, status);
183 g_full_pwr_status = status;
184
185 if(eHAL_STATUS_SUCCESS == status)
186 {
187 pHddCtx->hdd_ps_state = eHDD_SUSPEND_NONE;
188 }
189 else
190 {
191 hddLog(VOS_TRACE_LEVEL_FATAL,"%s: sme_RequestFullPower failed",__func__);
192 }
193
194 complete(&pHddCtx->full_pwr_comp_var);
195}
196
197eHalStatus hdd_exit_standby(hdd_context_t *pHddCtx)
198{
199 eHalStatus status = VOS_STATUS_SUCCESS;
c_hpothuffdb5272013-10-02 16:42:35 +0530200 long ret;
Jeff Johnson295189b2012-06-20 16:38:30 -0700201
202 hddLog(VOS_TRACE_LEVEL_INFO, "%s: WLAN being resumed from standby",__func__);
203 INIT_COMPLETION(pHddCtx->full_pwr_comp_var);
204
205 g_full_pwr_status = eHAL_STATUS_FAILURE;
206 status = sme_RequestFullPower(pHddCtx->hHal, hdd_suspend_full_pwr_callback, pHddCtx,
207 eSME_FULL_PWR_NEEDED_BY_HDD);
208
209 if(status == eHAL_STATUS_PMC_PENDING)
210 {
211 //Block on a completion variable. Can't wait forever though
c_hpothuffdb5272013-10-02 16:42:35 +0530212 ret = wait_for_completion_interruptible_timeout(
213 &pHddCtx->full_pwr_comp_var,
214 msecs_to_jiffies(WLAN_WAIT_TIME_FULL_PWR));
215 if (0 >= ret)
216 {
217 hddLog(VOS_TRACE_LEVEL_ERROR, "%s:wait on full_pwr_comp_var failed %ld",
218 __func__, ret);
219 }
Jeff Johnson295189b2012-06-20 16:38:30 -0700220 status = g_full_pwr_status;
221 if(g_full_pwr_status != eHAL_STATUS_SUCCESS)
222 {
223 hddLog(VOS_TRACE_LEVEL_FATAL,"%s: sme_RequestFullPower failed",__func__);
224 VOS_ASSERT(0);
225 goto failure;
226 }
227 }
228 else if(status != eHAL_STATUS_SUCCESS)
229 {
230 hddLog(VOS_TRACE_LEVEL_FATAL,"%s: sme_RequestFullPower failed - status %d",
231 __func__, status);
232 VOS_ASSERT(0);
233 goto failure;
234 }
235 else
236 pHddCtx->hdd_ps_state = eHDD_SUSPEND_NONE;
237
238failure:
239 //No blocking to reduce latency. No other device should be depending on WLAN
240 //to finish resume and WLAN won't be instantly on after resume
241 return status;
242}
243
244
245//Helper routine to put the chip into standby
246VOS_STATUS hdd_enter_standby(hdd_context_t *pHddCtx)
247{
248 eHalStatus halStatus = eHAL_STATUS_SUCCESS;
249 VOS_STATUS vosStatus = VOS_STATUS_SUCCESS;
c_hpothuffdb5272013-10-02 16:42:35 +0530250 long ret;
Jeff Johnson295189b2012-06-20 16:38:30 -0700251
252 //Disable IMPS/BMPS as we do not want the device to enter any power
253 //save mode on its own during suspend sequence
254 sme_DisablePowerSave(pHddCtx->hHal, ePMC_IDLE_MODE_POWER_SAVE);
255 sme_DisablePowerSave(pHddCtx->hHal, ePMC_BEACON_MODE_POWER_SAVE);
256
257 //Note we do not disable queues unnecessarily. Queues should already be disabled
258 //if STA is disconnected or the queue will be disabled as and when disconnect
259 //happens because of standby procedure.
260
261 //Ensure that device is in full power first. There is scope for optimization
262 //here especially in scenarios where PMC is already in IMPS or REQUEST_IMPS.
263 //Core s/w needs to be optimized to handle this. Until then we request full
264 //power before issuing request for standby.
265 INIT_COMPLETION(pHddCtx->full_pwr_comp_var);
266 g_full_pwr_status = eHAL_STATUS_FAILURE;
267 halStatus = sme_RequestFullPower(pHddCtx->hHal, hdd_suspend_full_pwr_callback,
268 pHddCtx, eSME_FULL_PWR_NEEDED_BY_HDD);
269
270 if(halStatus == eHAL_STATUS_PMC_PENDING)
271 {
272 //Block on a completion variable. Can't wait forever though
c_hpothuffdb5272013-10-02 16:42:35 +0530273 ret = wait_for_completion_interruptible_timeout(
274 &pHddCtx->full_pwr_comp_var,
275 msecs_to_jiffies(WLAN_WAIT_TIME_FULL_PWR));
276 if (0 >= ret)
277 {
278 hddLog(VOS_TRACE_LEVEL_ERROR, "%s:wait on full_pwr_comp_var failed %ld",
279 __func__, ret);
280 }
281
Jeff Johnson295189b2012-06-20 16:38:30 -0700282 if(g_full_pwr_status != eHAL_STATUS_SUCCESS)
283 {
284 hddLog(VOS_TRACE_LEVEL_FATAL,"%s: sme_RequestFullPower Failed",__func__);
285 VOS_ASSERT(0);
286 vosStatus = VOS_STATUS_E_FAILURE;
287 goto failure;
288 }
289 }
290 else if(halStatus != eHAL_STATUS_SUCCESS)
291 {
292 hddLog(VOS_TRACE_LEVEL_FATAL,"%s: sme_RequestFullPower failed - status %d",
293 __func__, halStatus);
294 VOS_ASSERT(0);
295 vosStatus = VOS_STATUS_E_FAILURE;
296 goto failure;
297 }
298
299 if(pHddCtx->hdd_mcastbcast_filter_set == TRUE) {
300 hdd_conf_mcastbcast_filter(pHddCtx, FALSE);
301 pHddCtx->hdd_mcastbcast_filter_set = FALSE;
302 }
303
304 //Request standby. Standby will cause the STA to disassociate first. TX queues
305 //will be disabled (by HDD) when STA disconnects. You do not want to disable TX
306 //queues here. Also do not assert if the failure code is eHAL_STATUS_PMC_NOT_NOW as PMC
307 //will send this failure code in case of concurrent sessions. Power Save cannot be supported
308 //when there are concurrent sessions.
309 INIT_COMPLETION(pHddCtx->standby_comp_var);
310 g_standby_status = eHAL_STATUS_FAILURE;
311 halStatus = sme_RequestStandby(pHddCtx->hHal, hdd_suspend_standby_cbk, pHddCtx);
312
313 if (halStatus == eHAL_STATUS_PMC_PENDING)
314 {
315 //Wait till WLAN device enters standby mode
c_hpothuffdb5272013-10-02 16:42:35 +0530316 ret = wait_for_completion_timeout(&pHddCtx->standby_comp_var,
Jeff Johnson295189b2012-06-20 16:38:30 -0700317 msecs_to_jiffies(WLAN_WAIT_TIME_STANDBY));
c_hpothuffdb5272013-10-02 16:42:35 +0530318 if (0 >= ret)
319 {
320 hddLog(VOS_TRACE_LEVEL_ERROR,
321 FL("wait on standby_comp_var failed %ld"), ret);
322 }
Jeff Johnson295189b2012-06-20 16:38:30 -0700323 if (g_standby_status != eHAL_STATUS_SUCCESS && g_standby_status != eHAL_STATUS_PMC_NOT_NOW)
324 {
325 hddLog(VOS_TRACE_LEVEL_FATAL,"%s: sme_RequestStandby failed",__func__);
326 VOS_ASSERT(0);
327 vosStatus = VOS_STATUS_E_FAILURE;
328 goto failure;
329 }
330 }
331 else if (halStatus != eHAL_STATUS_SUCCESS && halStatus != eHAL_STATUS_PMC_NOT_NOW) {
332 hddLog(VOS_TRACE_LEVEL_FATAL,"%s: sme_RequestStandby failed - status %d",
333 __func__, halStatus);
334 VOS_ASSERT(0);
335 vosStatus = VOS_STATUS_E_FAILURE;
336 goto failure;
337 }
338 else
339 pHddCtx->hdd_ps_state = eHDD_SUSPEND_STANDBY;
340
341failure:
342 //Restore IMPS config
343 if(pHddCtx->cfg_ini->fIsImpsEnabled)
344 sme_EnablePowerSave(pHddCtx->hHal, ePMC_IDLE_MODE_POWER_SAVE);
345
346 //Restore BMPS config
347 if(pHddCtx->cfg_ini->fIsBmpsEnabled)
348 sme_EnablePowerSave(pHddCtx->hHal, ePMC_BEACON_MODE_POWER_SAVE);
349
350 return vosStatus;
351}
352
353
354//Helper routine for Deep sleep entry
355VOS_STATUS hdd_enter_deep_sleep(hdd_context_t *pHddCtx, hdd_adapter_t *pAdapter)
356{
357 eHalStatus halStatus;
358 VOS_STATUS vosStatus = VOS_STATUS_SUCCESS;
c_hpothuffdb5272013-10-02 16:42:35 +0530359 long ret;
Jeff Johnsonbc676b42013-02-14 16:04:08 -0800360
Jeff Johnson295189b2012-06-20 16:38:30 -0700361 //Stop the Interface TX queue.
Padma, Santhosh Kumar9dacb5c2014-12-17 19:22:56 +0530362 hddLog(VOS_TRACE_LEVEL_INFO, FL("Disabling queues"));
Jeff Johnson295189b2012-06-20 16:38:30 -0700363 netif_tx_disable(pAdapter->dev);
364 netif_carrier_off(pAdapter->dev);
365
366 //Disable IMPS,BMPS as we do not want the device to enter any power
367 //save mode on it own during suspend sequence
368 sme_DisablePowerSave(pHddCtx->hHal, ePMC_IDLE_MODE_POWER_SAVE);
369 sme_DisablePowerSave(pHddCtx->hHal, ePMC_BEACON_MODE_POWER_SAVE);
370
371 //Ensure that device is in full power as we will touch H/W during vos_Stop
372 INIT_COMPLETION(pHddCtx->full_pwr_comp_var);
373 g_full_pwr_status = eHAL_STATUS_FAILURE;
374 halStatus = sme_RequestFullPower(pHddCtx->hHal, hdd_suspend_full_pwr_callback,
375 pHddCtx, eSME_FULL_PWR_NEEDED_BY_HDD);
376
377 if(halStatus == eHAL_STATUS_PMC_PENDING)
378 {
379 //Block on a completion variable. Can't wait forever though
c_hpothuffdb5272013-10-02 16:42:35 +0530380 ret = wait_for_completion_interruptible_timeout(
381 &pHddCtx->full_pwr_comp_var,
382 msecs_to_jiffies(WLAN_WAIT_TIME_FULL_PWR));
383 if (0 >= ret)
384 {
385 hddLog(VOS_TRACE_LEVEL_ERROR,
386 FL("wait on full_pwr_comp_var failed %ld"), ret);
387 }
Jeff Johnson295189b2012-06-20 16:38:30 -0700388 if(g_full_pwr_status != eHAL_STATUS_SUCCESS){
389 hddLog(VOS_TRACE_LEVEL_FATAL,"%s: sme_RequestFullPower failed",__func__);
390 VOS_ASSERT(0);
391 }
392 }
393 else if(halStatus != eHAL_STATUS_SUCCESS)
394 {
395 hddLog(VOS_TRACE_LEVEL_FATAL,"%s: Request for Full Power failed",__func__);
396 VOS_ASSERT(0);
397 }
398
399 //Issue a disconnect. This is required to inform the supplicant that
400 //STA is getting disassociated and for GUI to be updated properly
401 INIT_COMPLETION(pAdapter->disconnect_comp_var);
402 halStatus = sme_RoamDisconnect(pHddCtx->hHal, pAdapter->sessionId, eCSR_DISCONNECT_REASON_UNSPECIFIED);
403
404 //Success implies disconnect command got queued up successfully
405 if(halStatus == eHAL_STATUS_SUCCESS)
406 {
407 //Block on a completion variable. Can't wait forever though.
c_hpothuffdb5272013-10-02 16:42:35 +0530408 ret = wait_for_completion_interruptible_timeout(
409 &pAdapter->disconnect_comp_var,
410 msecs_to_jiffies(WLAN_WAIT_TIME_DISCONNECT));
411 if (0 >= ret)
412 {
413 hddLog(VOS_TRACE_LEVEL_ERROR,
414 FL("wait on disconnect_comp_var failed %ld"), ret);
415 }
Jeff Johnson295189b2012-06-20 16:38:30 -0700416 }
417
418
419 //None of the steps should fail after this. Continue even in case of failure
420 vosStatus = vos_stop( pHddCtx->pvosContext );
c_hpothuffdb5272013-10-02 16:42:35 +0530421 if( !VOS_IS_STATUS_SUCCESS( vosStatus ))
422 {
423 hddLog(VOS_TRACE_LEVEL_ERROR, "%s: vos_stop return failed %d",
424 __func__, vosStatus);
425 VOS_ASSERT(0);
Hanumantha Reddy Pothulabd9601a2016-02-12 13:22:27 +0530426 if (isSsrPanicOnFailure())
427 VOS_BUG(0);
c_hpothuffdb5272013-10-02 16:42:35 +0530428 }
Jeff Johnson295189b2012-06-20 16:38:30 -0700429
Jeff Johnson295189b2012-06-20 16:38:30 -0700430 pHddCtx->hdd_ps_state = eHDD_SUSPEND_DEEP_SLEEP;
431
432 //Restore IMPS config
433 if(pHddCtx->cfg_ini->fIsImpsEnabled)
434 sme_EnablePowerSave(pHddCtx->hHal, ePMC_IDLE_MODE_POWER_SAVE);
435
436 //Restore BMPS config
437 if(pHddCtx->cfg_ini->fIsBmpsEnabled)
438 sme_EnablePowerSave(pHddCtx->hHal, ePMC_BEACON_MODE_POWER_SAVE);
439
Jeff Johnson295189b2012-06-20 16:38:30 -0700440 return vosStatus;
441}
442
443VOS_STATUS hdd_exit_deep_sleep(hdd_context_t *pHddCtx, hdd_adapter_t *pAdapter)
444{
445 VOS_STATUS vosStatus;
louisliu462edac2020-06-30 13:33:56 +0800446 eHalStatus halStatus;
Jeff Johnson295189b2012-06-20 16:38:30 -0700447
Jeff Johnson295189b2012-06-20 16:38:30 -0700448 VOS_TRACE( VOS_MODULE_ID_HDD, VOS_TRACE_LEVEL_INFO,
449 "%s: calling hdd_set_sme_config",__func__);
450 vosStatus = hdd_set_sme_config( pHddCtx );
451 VOS_ASSERT( VOS_IS_STATUS_SUCCESS( vosStatus ) );
452 if (!VOS_IS_STATUS_SUCCESS(vosStatus))
453 {
454 VOS_TRACE(VOS_MODULE_ID_HDD, VOS_TRACE_LEVEL_ERROR,
455 "%s: Failed in hdd_set_sme_config",__func__);
Jeff Johnson295189b2012-06-20 16:38:30 -0700456 goto err_deep_sleep;
Jeff Johnson295189b2012-06-20 16:38:30 -0700457 }
458
459 VOS_TRACE( VOS_MODULE_ID_HDD, VOS_TRACE_LEVEL_INFO,
460 "%s: calling vos_start",__func__);
461 vosStatus = vos_start( pHddCtx->pvosContext );
462 VOS_ASSERT( VOS_IS_STATUS_SUCCESS( vosStatus ) );
463 if (!VOS_IS_STATUS_SUCCESS(vosStatus))
464 {
465 VOS_TRACE(VOS_MODULE_ID_HDD, VOS_TRACE_LEVEL_ERROR,
466 "%s: Failed in vos_start",__func__);
Hanumantha Reddy Pothulabd9601a2016-02-12 13:22:27 +0530467 if (isSsrPanicOnFailure())
468 VOS_BUG(0);
Jeff Johnson295189b2012-06-20 16:38:30 -0700469 goto err_deep_sleep;
Jeff Johnson295189b2012-06-20 16:38:30 -0700470 }
471
472 VOS_TRACE( VOS_MODULE_ID_HDD, VOS_TRACE_LEVEL_INFO,
473 "%s: calling hdd_post_voss_start_config",__func__);
474 vosStatus = hdd_post_voss_start_config( pHddCtx );
475 VOS_ASSERT( VOS_IS_STATUS_SUCCESS( vosStatus ) );
476 if (!VOS_IS_STATUS_SUCCESS(vosStatus))
477 {
478 VOS_TRACE(VOS_MODULE_ID_HDD, VOS_TRACE_LEVEL_ERROR,
479 "%s: Failed in hdd_post_voss_start_config",__func__);
480 goto err_voss_stop;
481 }
482
louisliu462edac2020-06-30 13:33:56 +0800483
484 //Open a SME session for future operation
485 halStatus = sme_OpenSession( pHddCtx->hHal, hdd_smeRoamCallback, pHddCtx,
486 (tANI_U8 *)&pAdapter->macAddressCurrent,
487 &pAdapter->sessionId);
488 if ( !HAL_STATUS_SUCCESS( halStatus ) )
489 {
490 hddLog(VOS_TRACE_LEVEL_FATAL,"sme_OpenSession() failed with status code %08d [x%08x]",
491 halStatus, halStatus );
492 goto err_voss_stop;
493
494 }
495
Jeff Johnson295189b2012-06-20 16:38:30 -0700496 pHddCtx->hdd_ps_state = eHDD_SUSPEND_NONE;
497
louisliu462edac2020-06-30 13:33:56 +0800498 //Trigger the initial scan
499 hdd_wlan_initial_scan(pAdapter);
500
Jeff Johnson295189b2012-06-20 16:38:30 -0700501 return VOS_STATUS_SUCCESS;
502
503err_voss_stop:
504 vos_stop(pHddCtx->pvosContext);
Jeff Johnson295189b2012-06-20 16:38:30 -0700505err_deep_sleep:
506 return VOS_STATUS_E_FAILURE;
507
508}
509
Mahesh A Saptasagare5440c72015-01-28 21:21:07 +0530510void __hdd_ipv6_notifier_work_queue(struct work_struct *work)
Atul Mittal37385d72014-03-27 18:15:03 +0530511{
512 hdd_adapter_t* pAdapter =
513 container_of(work, hdd_adapter_t, ipv6NotifierWorkQueue);
514 hdd_context_t *pHddCtx;
515 int status;
516
Hanumantha Reddy Pothula7dc0e6c2015-03-06 15:11:16 +0530517 ENTER();
Mahesh A Saptasagare5440c72015-01-28 21:21:07 +0530518 if (NULL == pAdapter)
519 {
520 hddLog(LOGE, FL("Adapter is invalid"));
521 return;
522 }
Atul Mittal37385d72014-03-27 18:15:03 +0530523
524 pHddCtx = WLAN_HDD_GET_CTX(pAdapter);
525 status = wlan_hdd_validate_context(pHddCtx);
526 if (0 != status)
527 {
Atul Mittal37385d72014-03-27 18:15:03 +0530528 return;
529 }
530
Atul Mittal37385d72014-03-27 18:15:03 +0530531 if ((eConnectionState_Associated ==
532 (WLAN_HDD_GET_STATION_CTX_PTR(pAdapter))->conn_info.connState)
533 && (pHddCtx->hdd_wlan_suspended))
534 {
Mukul Sharma75ee8aa2016-12-01 14:28:10 +0530535 check_and_set_suspend_resume_mcbc_filter(pHddCtx);
Atul Mittal37385d72014-03-27 18:15:03 +0530536 // This invocation being part of the IPv6 registration callback,
537 // set the newly generated ip address to f/w in suspend mode.
538#ifdef WLAN_NS_OFFLOAD
Vinay Krishna Eranna83b0ef72014-11-19 16:56:20 +0530539 if (pHddCtx->cfg_ini->fhostNSOffload)
540 {
541 hdd_conf_ns_offload(pAdapter, 1);
542 }
Atul Mittal37385d72014-03-27 18:15:03 +0530543#endif
544 }
545#ifdef WLAN_FEATURE_PACKET_FILTERING
Vinay Krishna Eranna83b0ef72014-11-19 16:56:20 +0530546 /* wlan_hdd_set_mc_addr_list() is called from the early suspend
Atul Mittal37385d72014-03-27 18:15:03 +0530547 * only so when new ipv6 address is generated the screen may not
548 * on so we need to call it here to update the list in f/w.
549 */
Vinay Krishna Eranna83b0ef72014-11-19 16:56:20 +0530550 wlan_hdd_set_mc_addr_list(pAdapter, TRUE);
Atul Mittal37385d72014-03-27 18:15:03 +0530551#endif
Hanumantha Reddy Pothula7dc0e6c2015-03-06 15:11:16 +0530552 EXIT();
Atul Mittal37385d72014-03-27 18:15:03 +0530553}
554
Mahesh A Saptasagare5440c72015-01-28 21:21:07 +0530555void hdd_ipv6_notifier_work_queue(struct work_struct *work)
556{
557 vos_ssr_protect(__func__);
558 __hdd_ipv6_notifier_work_queue(work);
559 vos_ssr_unprotect(__func__);
560}
Mukul Sharmaa78cf6b2015-02-24 16:59:01 +0530561int __wlan_hdd_ipv6_changed(struct notifier_block *nb,
Vinay Krishna Eranna83b0ef72014-11-19 16:56:20 +0530562 unsigned long data, void *arg)
Atul Mittal37385d72014-03-27 18:15:03 +0530563{
564 struct inet6_ifaddr *ifa = (struct inet6_ifaddr *)arg;
565 struct net_device *ndev = ifa->idev->dev;
Vinay Krishna Eranna55029602015-02-06 15:43:35 +0530566 hdd_adapter_list_node_t *pAdapterNode = NULL, *pNext = NULL;
Atul Mittal37385d72014-03-27 18:15:03 +0530567 hdd_context_t *pHddCtx;
Vinay Krishna Eranna55029602015-02-06 15:43:35 +0530568 VOS_STATUS vos_status;
Atul Mittal37385d72014-03-27 18:15:03 +0530569 int status;
570
Hanumantha Reddy Pothula7dc0e6c2015-03-06 15:11:16 +0530571 ENTER();
Vinay Krishna Eranna55029602015-02-06 15:43:35 +0530572 pHddCtx = container_of(nb, hdd_context_t, ipv6_notifier);
573 status = wlan_hdd_validate_context(pHddCtx);
574 if (0 != status)
Atul Mittal37385d72014-03-27 18:15:03 +0530575 {
Vinay Krishna Eranna55029602015-02-06 15:43:35 +0530576 return NOTIFY_DONE;
577 }
Atul Mittal37385d72014-03-27 18:15:03 +0530578
Vinay Krishna Eranna55029602015-02-06 15:43:35 +0530579 vos_status = hdd_get_front_adapter(pHddCtx, &pAdapterNode);
580 while (NULL != pAdapterNode && VOS_STATUS_SUCCESS == vos_status)
581 {
582 if (pAdapterNode->pAdapter && pAdapterNode->pAdapter->dev == ndev &&
583 (pAdapterNode->pAdapter->device_mode == WLAN_HDD_INFRA_STATION ||
584 pAdapterNode->pAdapter->device_mode == WLAN_HDD_P2P_CLIENT))
585 {
Abhishek Singhe0bc0992016-05-20 17:58:18 +0530586
587 if (eConnectionState_Associated ==
588 WLAN_HDD_GET_STATION_CTX_PTR
589 (pAdapterNode->pAdapter)->conn_info.connState)
590 sme_dhcp_done_ind(pHddCtx->hHal,
591 pAdapterNode->pAdapter->sessionId);
Vinay Krishna Eranna55029602015-02-06 15:43:35 +0530592 if (pHddCtx->cfg_ini->nEnableSuspend ==
Vinay Krishna Eranna83b0ef72014-11-19 16:56:20 +0530593 WLAN_MAP_SUSPEND_TO_MCAST_BCAST_FILTER)
Vinay Krishna Eranna55029602015-02-06 15:43:35 +0530594 {
595 schedule_work(&pAdapterNode->pAdapter->ipv6NotifierWorkQueue);
596 }
597 else
598 {
599 hddLog(LOG1, FL("Not scheduling ipv6 wq nEnableSuspend = %d"),
600 pHddCtx->cfg_ini->nEnableSuspend);
601 }
602 break;
603 }
604 vos_status = hdd_get_next_adapter(pHddCtx, pAdapterNode, &pNext);
605 pAdapterNode = pNext;
Atul Mittal37385d72014-03-27 18:15:03 +0530606 }
Hanumantha Reddy Pothula7dc0e6c2015-03-06 15:11:16 +0530607 EXIT();
Atul Mittal37385d72014-03-27 18:15:03 +0530608 return NOTIFY_DONE;
609}
610
Mukul Sharmaa78cf6b2015-02-24 16:59:01 +0530611int wlan_hdd_ipv6_changed(struct notifier_block *nb,
612 unsigned long data, void *arg)
613{
614 int ret;
615 vos_ssr_protect(__func__);
616 ret = __wlan_hdd_ipv6_changed( nb, data, arg);
617 vos_ssr_unprotect(__func__);
618 return ret;
619}
620
Gopichand Nakkalab03e8082013-05-30 18:09:25 +0530621/*
622 * Function: hdd_conf_hostoffload
623 * Central function to configure the supported offloads,
624 * either enable or disable them.
625 */
626void hdd_conf_hostoffload(hdd_adapter_t *pAdapter, v_BOOL_t fenable)
627{
628 hdd_context_t *pHddCtx = NULL;
629 v_CONTEXT_t *pVosContext = NULL;
630 VOS_STATUS vstatus = VOS_STATUS_E_FAILURE;
631
632 hddLog(VOS_TRACE_LEVEL_INFO, FL("Configuring offloads with flag: %d"),
633 fenable);
634
635 pVosContext = vos_get_global_context(VOS_MODULE_ID_SYS, NULL);
636
637 if (NULL == pVosContext)
638 {
639 hddLog(VOS_TRACE_LEVEL_ERROR, FL(" Global VOS context is Null"));
640 return;
641 }
642
643 //Get the HDD context.
644 pHddCtx = (hdd_context_t *)vos_get_context(VOS_MODULE_ID_HDD, pVosContext );
645
646 if (NULL == pHddCtx)
647 {
648 hddLog(VOS_TRACE_LEVEL_ERROR, "%s: HDD context is Null", __func__);
649 return;
650 }
651
652 if ((WLAN_HDD_INFRA_STATION == pAdapter->device_mode) ||
Arun Khandavalli08bcafd2016-11-08 14:45:48 +0530653 (WLAN_HDD_P2P_CLIENT == pAdapter->device_mode) ||
654 ((WLAN_HDD_SOFTAP == pAdapter->device_mode) &&
655 (pHddCtx->is_ap_mode_wow_supported)))
Gopichand Nakkalab03e8082013-05-30 18:09:25 +0530656 {
657 if (fenable)
658 {
Arun Khandavalli08bcafd2016-11-08 14:45:48 +0530659 if (((WLAN_HDD_INFRA_STATION == pAdapter->device_mode) &&
660 (eConnectionState_Associated ==
661 (WLAN_HDD_GET_STATION_CTX_PTR(pAdapter))->conn_info.connState))
662 || (WLAN_HDD_SOFTAP == pAdapter->device_mode))
Gopichand Nakkalab03e8082013-05-30 18:09:25 +0530663 {
664 if ((pHddCtx->cfg_ini->fhostArpOffload))
665 {
666 /*
667 * Configure the ARP Offload.
668 * Even if it fails we have to reconfigure the MC/BC
669 * filter flag as we want RIVA not to drop BroadCast
670 * Packets
671 */
672 hddLog(VOS_TRACE_LEVEL_INFO,
673 FL("Calling ARP Offload with flag: %d"), fenable);
674 vstatus = hdd_conf_arp_offload(pAdapter, fenable);
675 pHddCtx->configuredMcastBcastFilter &=
676 ~(HDD_MCASTBCASTFILTER_FILTER_ALL_BROADCAST);
677
678 if (!VOS_IS_STATUS_SUCCESS(vstatus))
679 {
Anurag Chouhan8a5f8902016-09-28 18:54:47 +0530680 hddLog(VOS_TRACE_LEVEL_INFO,
Gopichand Nakkalab03e8082013-05-30 18:09:25 +0530681 "Failed to enable ARPOFfloadFeature %d",
682 vstatus);
683 }
684 }
685 //Configure GTK_OFFLOAD
686#ifdef WLAN_FEATURE_GTK_OFFLOAD
687 hdd_conf_gtk_offload(pAdapter, fenable);
688#endif
Gopichand Nakkala746a9452013-06-11 12:45:54 +0530689
690#ifdef WLAN_NS_OFFLOAD
691 if (pHddCtx->cfg_ini->fhostNSOffload)
692 {
693 /*
694 * Configure the NS Offload.
695 * Even if it fails we have to reconfigure the MC/BC filter flag
696 * as we want RIVA not to drop Multicast Packets
697 */
698
699 hddLog(VOS_TRACE_LEVEL_INFO,
700 FL("Calling NS Offload with flag: %d"), fenable);
701 hdd_conf_ns_offload(pAdapter, fenable);
702 pHddCtx->configuredMcastBcastFilter &=
703 ~(HDD_MCASTBCASTFILTER_FILTER_ALL_MULTICAST);
704 }
705#endif
Atul Mittal37385d72014-03-27 18:15:03 +0530706
Gopichand Nakkalab03e8082013-05-30 18:09:25 +0530707 }
708 }
709 else
710 {
711 //Disable ARPOFFLOAD
712 if (pHddCtx->cfg_ini->fhostArpOffload)
713 {
714 vstatus = hdd_conf_arp_offload(pAdapter, fenable);
715 if (!VOS_IS_STATUS_SUCCESS(vstatus))
716 {
717 hddLog(VOS_TRACE_LEVEL_ERROR,
Gopichand Nakkala746a9452013-06-11 12:45:54 +0530718 "Failed to disable ARPOffload Feature %d", vstatus);
Gopichand Nakkalab03e8082013-05-30 18:09:25 +0530719 }
720 }
721 //Disable GTK_OFFLOAD
722#ifdef WLAN_FEATURE_GTK_OFFLOAD
Gopichand Nakkala746a9452013-06-11 12:45:54 +0530723 hdd_conf_gtk_offload(pAdapter, fenable);
724#endif
725
726#ifdef WLAN_NS_OFFLOAD
727 //Disable NSOFFLOAD
728 if (pHddCtx->cfg_ini->fhostNSOffload)
729 {
730 hdd_conf_ns_offload(pAdapter, fenable);
731 }
Mukul Sharma75ee8aa2016-12-01 14:28:10 +0530732 else
733 {
734 hddLog(VOS_TRACE_LEVEL_INFO,
735 FL("ns offload ini is disabled"));
736 }
Gopichand Nakkalab03e8082013-05-30 18:09:25 +0530737#endif
738 }
739 }
740 return;
741}
742
Atul Mittal37385d72014-03-27 18:15:03 +0530743
Gopichand Nakkala746a9452013-06-11 12:45:54 +0530744#ifdef WLAN_NS_OFFLOAD
Vinay Krishna Erannad5b2be22013-12-01 17:00:15 +0530745/**----------------------------------------------------------------------------
746
747 \brief hdd_conf_ns_offload() - Configure NS offload
748
749 Called during SUSPEND to configure the NS offload (MC BC filter) which
750 reduces power consumption.
751
752 \param - pAdapter - Adapter context for which NS offload is to be configured
753 \param - fenable - 0 - disable.
754 1 - enable. (with IPv6 notifier registration)
755 2 - enable. (without IPv6 notifier registration)
756
757 \return - void
758
759 ---------------------------------------------------------------------------*/
760void hdd_conf_ns_offload(hdd_adapter_t *pAdapter, int fenable)
Gopichand Nakkala746a9452013-06-11 12:45:54 +0530761{
762 struct inet6_dev *in6_dev;
763 struct inet6_ifaddr *ifp;
764 struct list_head *p;
Hardik Kantilal Patele1760e12014-01-21 15:57:21 +0530765 int slot_index = NS_DEFAULT_SLOT_INDEX;
Girish Gowli1b6114f2014-05-17 17:17:09 +0530766 tANI_U8 **selfIPv6Addr = NULL;
767 tANI_U8 *selfIPv6AddrValid = NULL;
Gopichand Nakkala746a9452013-06-11 12:45:54 +0530768 tSirHostOffloadReq offLoadRequest;
Madan Mohan Koyyalamudibadffe72013-09-11 13:09:14 +0530769 hdd_context_t *pHddCtx;
Hardik Kantilal Patele1760e12014-01-21 15:57:21 +0530770 tHalHandle halHandle;
Gopichand Nakkala746a9452013-06-11 12:45:54 +0530771
Hardik Kantilal Patele1760e12014-01-21 15:57:21 +0530772 int i = 0, slot = 0;
773 int ret = 0;
Gopichand Nakkala746a9452013-06-11 12:45:54 +0530774 eHalStatus returnStatus;
775
Vinay Krishna Eranna941360f2014-01-16 15:38:22 +0530776 ENTER();
777 hddLog(LOG1, FL(" fenable = %d"), fenable);
778
Hardik Kantilal Patele1760e12014-01-21 15:57:21 +0530779 if (NULL == pAdapter)
780 {
781 hddLog(VOS_TRACE_LEVEL_ERROR, FL("HDD adapter is Null"));
782 return;
783 }
784
785 halHandle = WLAN_HDD_GET_HAL_CTX(pAdapter);
Madan Mohan Koyyalamudibadffe72013-09-11 13:09:14 +0530786 pHddCtx = WLAN_HDD_GET_CTX(pAdapter);
787
Hardik Kantilal Patele1760e12014-01-21 15:57:21 +0530788 ret = wlan_hdd_validate_context(pHddCtx);
Hardik Kantilal Patele1760e12014-01-21 15:57:21 +0530789 if (0 != ret)
790 {
Hardik Kantilal Patele1760e12014-01-21 15:57:21 +0530791 return;
792 }
793
794 if (sme_IsFeatureSupportedByFW(EXTENDED_NSOFFLOAD_SLOT))
795 {
796 slot_index = NS_EXTENDED_SLOT_INDEX;
797 }
798
799 hddLog(VOS_TRACE_LEVEL_INFO, FL("slot_idex = %d"), slot_index);
800
801 selfIPv6AddrValid =
802 (tANI_U8 *)vos_mem_malloc(sizeof(tANI_U8) * slot_index);
803
804 if (NULL == selfIPv6AddrValid)
805 {
806 hddLog (VOS_TRACE_LEVEL_ERROR, FL("Failed to allocate memory for"
807 " selfIPv6AddrValid"));
808 goto end;
809 }
810
811 vos_mem_zero(selfIPv6AddrValid, slot_index * sizeof(tANI_U8));
812
813 selfIPv6Addr = (tANI_U8 **)vos_mem_malloc(sizeof(tANI_U8 *) * slot_index);
814
815 if (NULL == selfIPv6Addr)
816 {
817 hddLog (VOS_TRACE_LEVEL_ERROR, FL("Failed to allocate memory for"
818 " selfIPv6Addr"));
819 goto end;
820 }
821
822 vos_mem_zero(selfIPv6Addr, slot_index * sizeof(tANI_U8 *));
823
824 for (slot = 0; slot < slot_index; slot++)
825 {
826 selfIPv6Addr[slot] =
827 (tANI_U8 *)vos_mem_malloc(SIR_MAC_IPV6_ADDR_LEN);
828 if (NULL == selfIPv6Addr[slot])
829 {
830 hddLog (VOS_TRACE_LEVEL_ERROR, FL("Failed to allocate memory"
831 "for selfIPv6Addr"));
832 goto end;
833 }
834 vos_mem_zero(selfIPv6Addr[slot], SIR_MAC_IPV6_ADDR_LEN);
835 }
836
837 i = 0;
838
Gopichand Nakkala746a9452013-06-11 12:45:54 +0530839 if (fenable)
840 {
841 in6_dev = __in6_dev_get(pAdapter->dev);
842 if (NULL != in6_dev)
843 {
Srinivas Girigowdad26a8072016-10-19 20:26:42 +0530844 read_lock_bh(&in6_dev->lock);
Gopichand Nakkala746a9452013-06-11 12:45:54 +0530845 list_for_each(p, &in6_dev->addr_list)
846 {
Hardik Kantilal Patele1760e12014-01-21 15:57:21 +0530847 if (i >= slot_index)
848 {
849 hddLog (VOS_TRACE_LEVEL_ERROR,
850 FL("IPv6 address list is greater than IPv6"
851 "address supported by firmware"));
852 hddLog (VOS_TRACE_LEVEL_ERROR,
853 FL("FW supported IPv6 address = %d"), slot_index);
854 break;
855 }
Gopichand Nakkala746a9452013-06-11 12:45:54 +0530856 ifp = list_entry(p, struct inet6_ifaddr, if_list);
857 switch(ipv6_addr_src_scope(&ifp->addr))
858 {
859 case IPV6_ADDR_SCOPE_LINKLOCAL:
Hardik Kantilal Patele1760e12014-01-21 15:57:21 +0530860 vos_mem_copy(selfIPv6Addr[i], &ifp->addr.s6_addr,
Gopichand Nakkala746a9452013-06-11 12:45:54 +0530861 sizeof(ifp->addr.s6_addr));
Hardik Kantilal Patele1760e12014-01-21 15:57:21 +0530862 selfIPv6AddrValid[i] = SIR_IPV6_ADDR_VALID;
Hardik Kantilal Patel1341bdf2013-08-22 20:27:15 +0530863 hddLog (VOS_TRACE_LEVEL_INFO,
Hardik Kantilal Patele1760e12014-01-21 15:57:21 +0530864 FL("Found IPV6_ADDR_SCOPE_LINKLOCAL Address : %pI6"),
865 selfIPv6Addr[i]);
Gopichand Nakkala746a9452013-06-11 12:45:54 +0530866 break;
867 case IPV6_ADDR_SCOPE_GLOBAL:
Hardik Kantilal Patele1760e12014-01-21 15:57:21 +0530868 vos_mem_copy(selfIPv6Addr[i], &ifp->addr.s6_addr,
Gopichand Nakkala746a9452013-06-11 12:45:54 +0530869 sizeof(ifp->addr.s6_addr));
Hardik Kantilal Patele1760e12014-01-21 15:57:21 +0530870 selfIPv6AddrValid[i] = SIR_IPV6_ADDR_VALID;
Hardik Kantilal Patel1341bdf2013-08-22 20:27:15 +0530871 hddLog (VOS_TRACE_LEVEL_INFO,
Hardik Kantilal Patele1760e12014-01-21 15:57:21 +0530872 FL("Found IPV6_ADDR_SCOPE_GLOBAL Address : %pI6"),
873 selfIPv6Addr[i]);
Gopichand Nakkala746a9452013-06-11 12:45:54 +0530874 break;
875 default:
Hardik Kantilal Patele1760e12014-01-21 15:57:21 +0530876 hddLog(VOS_TRACE_LEVEL_ERROR,
877 FL("The Scope %d is not supported"),
878 ipv6_addr_src_scope(&ifp->addr));
Gopichand Nakkala746a9452013-06-11 12:45:54 +0530879 }
Hardik Kantilal Patele1760e12014-01-21 15:57:21 +0530880 if (selfIPv6AddrValid[i] == SIR_IPV6_ADDR_VALID)
881 {
882 i++;
883 }
Gopichand Nakkala746a9452013-06-11 12:45:54 +0530884 }
Mukul Sharma115869a2017-06-29 17:38:57 +0530885 /* store actual slots being used */
886 pAdapter->ns_slots = i;
Srinivas Girigowdad26a8072016-10-19 20:26:42 +0530887 read_unlock_bh(&in6_dev->lock);
Hardik Kantilal Patele1760e12014-01-21 15:57:21 +0530888
Gopichand Nakkala746a9452013-06-11 12:45:54 +0530889 vos_mem_zero(&offLoadRequest, sizeof(offLoadRequest));
Hardik Kantilal Patele1760e12014-01-21 15:57:21 +0530890 for (i =0; i < slot_index; i++)
Gopichand Nakkala746a9452013-06-11 12:45:54 +0530891 {
892 if (selfIPv6AddrValid[i])
893 {
894 //Filling up the request structure
895 /* Filling the selfIPv6Addr with solicited address
896 * A Solicited-Node multicast address is created by
897 * taking the last 24 bits of a unicast or anycast
898 * address and appending them to the prefix
899 *
900 * FF02:0000:0000:0000:0000:0001:FFXX:XX
901 *
902 * here XX is the unicast/anycast bits
903 */
904 offLoadRequest.nsOffloadInfo.selfIPv6Addr[0] = 0xFF;
905 offLoadRequest.nsOffloadInfo.selfIPv6Addr[1] = 0x02;
906 offLoadRequest.nsOffloadInfo.selfIPv6Addr[11] = 0x01;
907 offLoadRequest.nsOffloadInfo.selfIPv6Addr[12] = 0xFF;
Hardik Kantilal Patele1760e12014-01-21 15:57:21 +0530908 offLoadRequest.nsOffloadInfo.selfIPv6Addr[13] =
909 selfIPv6Addr[i][13];
910 offLoadRequest.nsOffloadInfo.selfIPv6Addr[14] =
911 selfIPv6Addr[i][14];
912 offLoadRequest.nsOffloadInfo.selfIPv6Addr[15] =
913 selfIPv6Addr[i][15];
Gopichand Nakkala746a9452013-06-11 12:45:54 +0530914 offLoadRequest.nsOffloadInfo.slotIdx = i;
915
916 vos_mem_copy(&offLoadRequest.nsOffloadInfo.targetIPv6Addr[0],
Hardik Kantilal Patele1760e12014-01-21 15:57:21 +0530917 selfIPv6Addr[i], sizeof(tANI_U8)*SIR_MAC_IPV6_ADDR_LEN);
Gopichand Nakkala746a9452013-06-11 12:45:54 +0530918 vos_mem_copy(&offLoadRequest.nsOffloadInfo.selfMacAddr,
919 &pAdapter->macAddressCurrent.bytes,
920 sizeof(tANI_U8)*SIR_MAC_ADDR_LEN);
921
Hardik Kantilal Patele1760e12014-01-21 15:57:21 +0530922 offLoadRequest.nsOffloadInfo.targetIPv6AddrValid[0] =
923 SIR_IPV6_ADDR_VALID;
Gopichand Nakkala746a9452013-06-11 12:45:54 +0530924 offLoadRequest.offloadType = SIR_IPV6_NS_OFFLOAD;
925 offLoadRequest.enableOrDisable = SIR_OFFLOAD_ENABLE;
Abhishek Singh937ec542016-01-05 18:03:14 +0530926 hdd_wlan_offload_event(SIR_IPV6_NS_OFFLOAD,
927 SIR_OFFLOAD_ENABLE);
Gopichand Nakkala746a9452013-06-11 12:45:54 +0530928
Madan Mohan Koyyalamudibadffe72013-09-11 13:09:14 +0530929 hddLog (VOS_TRACE_LEVEL_INFO,
Hardik Kantilal Patele1760e12014-01-21 15:57:21 +0530930 FL("configuredMcastBcastFilter: %d"
931 "NSOffload Slot = %d"),
932 pHddCtx->configuredMcastBcastFilter, i);
Madan Mohan Koyyalamudibadffe72013-09-11 13:09:14 +0530933
Kiet Lamc8e1eb52013-10-24 00:30:49 +0530934 if ((VOS_TRUE == pHddCtx->sus_res_mcastbcast_filter_valid)
Amar Singhald08ce752014-03-21 16:28:27 -0700935 && ((HDD_MCASTBCASTFILTER_FILTER_ALL_MULTICAST ==
936 pHddCtx->sus_res_mcastbcast_filter) ||
937 (HDD_MCASTBCASTFILTER_FILTER_ALL_MULTICAST_BROADCAST ==
938 pHddCtx->sus_res_mcastbcast_filter)) &&
939 (!WDA_IS_MCAST_FLT_ENABLE_IN_FW ||
940 (WDA_IS_MCAST_FLT_ENABLE_IN_FW &&
941 !(pHddCtx->cfg_ini->fEnableMCAddrList))))
Madan Mohan Koyyalamudibadffe72013-09-11 13:09:14 +0530942 {
Madan Mohan Koyyalamudibadffe72013-09-11 13:09:14 +0530943 offLoadRequest.enableOrDisable =
Amar Singhald08ce752014-03-21 16:28:27 -0700944 SIR_OFFLOAD_NS_AND_MCAST_FILTER_ENABLE;
Madan Mohan Koyyalamudibadffe72013-09-11 13:09:14 +0530945 }
Abhishek Singh937ec542016-01-05 18:03:14 +0530946 hdd_wlan_offload_event(
947 SIR_OFFLOAD_NS_AND_MCAST_FILTER_ENABLE,
948 SIR_OFFLOAD_ENABLE);
Mukul Sharma75ee8aa2016-12-01 14:28:10 +0530949 hddLog(VOS_TRACE_LEVEL_INFO,
950 FL("offload: NS filter programmed %d"),
951 offLoadRequest.enableOrDisable);
Gopichand Nakkala746a9452013-06-11 12:45:54 +0530952 vos_mem_copy(&offLoadRequest.params.hostIpv6Addr,
953 &offLoadRequest.nsOffloadInfo.targetIPv6Addr[0],
954 sizeof(tANI_U8)*SIR_MAC_IPV6_ADDR_LEN);
955
956 hddLog (VOS_TRACE_LEVEL_INFO,
Hardik Kantilal Patele1760e12014-01-21 15:57:21 +0530957 FL("Setting NSOffload with solicitedIp: %pI6,"
958 "targetIp: %pI6"),
Gopichand Nakkala746a9452013-06-11 12:45:54 +0530959 offLoadRequest.nsOffloadInfo.selfIPv6Addr,
960 offLoadRequest.nsOffloadInfo.targetIPv6Addr[0]);
961
962 //Configure the Firmware with this
Hardik Kantilal Patele1760e12014-01-21 15:57:21 +0530963 returnStatus = sme_SetHostOffload(halHandle,
Gopichand Nakkala746a9452013-06-11 12:45:54 +0530964 pAdapter->sessionId, &offLoadRequest);
965 if(eHAL_STATUS_SUCCESS != returnStatus)
966 {
967 hddLog(VOS_TRACE_LEVEL_ERROR,
Hardik Kantilal Patele1760e12014-01-21 15:57:21 +0530968 FL("Failed to enable HostOffload feature with"
969 " status: %d"), returnStatus);
Gopichand Nakkala746a9452013-06-11 12:45:54 +0530970 }
971 vos_mem_zero(&offLoadRequest, sizeof(offLoadRequest));
972 }
973 }
974 }
975 else
976 {
977 hddLog(VOS_TRACE_LEVEL_ERROR,
978 FL("IPv6 dev does not exist. Failed to request NSOffload"));
Hardik Kantilal Patele1760e12014-01-21 15:57:21 +0530979 goto end;
Gopichand Nakkala746a9452013-06-11 12:45:54 +0530980 }
981 }
982 else
983 {
984 //Disable NSOffload
985 vos_mem_zero((void *)&offLoadRequest, sizeof(tSirHostOffloadReq));
986 offLoadRequest.enableOrDisable = SIR_OFFLOAD_DISABLE;
987 offLoadRequest.offloadType = SIR_IPV6_NS_OFFLOAD;
Abhishek Singh937ec542016-01-05 18:03:14 +0530988 hdd_wlan_offload_event(SIR_IPV6_NS_OFFLOAD,
989 SIR_OFFLOAD_DISABLE);
Gopichand Nakkala746a9452013-06-11 12:45:54 +0530990
Mukul Sharma115869a2017-06-29 17:38:57 +0530991 for (i = 0; i < pAdapter->ns_slots; i++)
Vinay Krishna Erannab29c6142014-01-07 12:20:51 +0530992 {
c_hpothu86feba52014-10-28 15:51:18 +0530993 hddLog(VOS_TRACE_LEVEL_INFO, FL("Disable Slot= %d"), i);
Vinay Krishna Erannab29c6142014-01-07 12:20:51 +0530994 offLoadRequest.nsOffloadInfo.slotIdx = i;
995 if (eHAL_STATUS_SUCCESS !=
Vinay Krishna Eranna911a3b82014-01-07 12:20:51 +0530996 sme_SetHostOffload(WLAN_HDD_GET_HAL_CTX(pAdapter),
997 pAdapter->sessionId, &offLoadRequest))
Vinay Krishna Erannab29c6142014-01-07 12:20:51 +0530998 {
Hardik Kantilal Patele1760e12014-01-21 15:57:21 +0530999 hddLog(VOS_TRACE_LEVEL_ERROR, FL("Failure to disable"
1000 " %d Slot"), i);
Vinay Krishna Erannab29c6142014-01-07 12:20:51 +05301001 }
1002 }
Mukul Sharma115869a2017-06-29 17:38:57 +05301003 pAdapter->ns_slots = 0;
Gopichand Nakkala746a9452013-06-11 12:45:54 +05301004 }
Hardik Kantilal Patele1760e12014-01-21 15:57:21 +05301005end:
1006 while (slot > 0 && selfIPv6Addr[--slot])
1007 {
1008 vos_mem_free(selfIPv6Addr[slot]);
1009 }
1010 if (selfIPv6Addr)
1011 {
1012 vos_mem_free(selfIPv6Addr);
1013 }
1014 if (selfIPv6AddrValid)
1015 {
1016 vos_mem_free(selfIPv6AddrValid);
1017 }
Hanumantha Reddy Pothula7dc0e6c2015-03-06 15:11:16 +05301018 EXIT();
Gopichand Nakkala746a9452013-06-11 12:45:54 +05301019 return;
1020}
1021#endif
Vinay Krishna Eranna4d055d42013-12-17 17:02:01 +05301022
Mahesh A Saptasagare5440c72015-01-28 21:21:07 +05301023void __hdd_ipv4_notifier_work_queue(struct work_struct *work)
Vinay Krishna Eranna4d055d42013-12-17 17:02:01 +05301024{
1025 hdd_adapter_t* pAdapter =
1026 container_of(work, hdd_adapter_t, ipv4NotifierWorkQueue);
1027 hdd_context_t *pHddCtx;
1028 int status;
1029
Hanumantha Reddy Pothula7dc0e6c2015-03-06 15:11:16 +05301030 ENTER();
Mahesh A Saptasagare5440c72015-01-28 21:21:07 +05301031 if (NULL == pAdapter)
1032 {
1033 hddLog(LOGE, FL("Adapter is invalid"));
1034 return;
1035 }
Vinay Krishna Eranna4d055d42013-12-17 17:02:01 +05301036 pHddCtx = WLAN_HDD_GET_CTX(pAdapter);
1037 status = wlan_hdd_validate_context(pHddCtx);
1038 if (0 != status)
1039 {
Vinay Krishna Eranna4d055d42013-12-17 17:02:01 +05301040 return;
1041 }
1042
1043 if ((eConnectionState_Associated ==
1044 (WLAN_HDD_GET_STATION_CTX_PTR(pAdapter))->conn_info.connState)
Deepthi Gowri5933f402014-01-23 17:48:24 +05301045 && (pHddCtx->hdd_wlan_suspended))
Vinay Krishna Eranna4d055d42013-12-17 17:02:01 +05301046 {
1047 // This invocation being part of the IPv4 registration callback,
1048 // we are passing second parameter as 2 to avoid registration
1049 // of IPv4 notifier again.
Mukul Sharma75ee8aa2016-12-01 14:28:10 +05301050 check_and_set_suspend_resume_mcbc_filter(pHddCtx);
1051 if (pHddCtx->cfg_ini->fhostArpOffload)
1052 {
1053 hdd_conf_arp_offload(pAdapter, 2);
1054 }
1055 else
1056 {
1057 hddLog(VOS_TRACE_LEVEL_INFO,
1058 FL("offload: arp offload ini is disabled in host"));
1059 }
Vinay Krishna Eranna4d055d42013-12-17 17:02:01 +05301060 }
Hanumantha Reddy Pothula7dc0e6c2015-03-06 15:11:16 +05301061 EXIT();
Vinay Krishna Eranna4d055d42013-12-17 17:02:01 +05301062}
1063
Mahesh A Saptasagare5440c72015-01-28 21:21:07 +05301064void hdd_ipv4_notifier_work_queue(struct work_struct *work)
1065{
1066 vos_ssr_protect(__func__);
1067 __hdd_ipv4_notifier_work_queue(work);
1068 vos_ssr_unprotect(__func__);
1069}
1070
Mukul Sharmaa78cf6b2015-02-24 16:59:01 +05301071int __wlan_hdd_ipv4_changed(struct notifier_block *nb,
Vinay Krishna Eranna83b0ef72014-11-19 16:56:20 +05301072 unsigned long data, void *arg)
Vinay Krishna Eranna4d055d42013-12-17 17:02:01 +05301073{
1074 struct in_ifaddr *ifa = (struct in_ifaddr *)arg;
1075 struct in_ifaddr **ifap = NULL;
1076 struct in_device *in_dev;
1077
1078 struct net_device *ndev = ifa->ifa_dev->dev;
Vinay Krishna Eranna55029602015-02-06 15:43:35 +05301079 hdd_adapter_list_node_t *pAdapterNode = NULL, *pNext = NULL;
Vinay Krishna Erannad9cbdb32014-01-16 12:59:10 +05301080 hdd_context_t *pHddCtx;
Vinay Krishna Eranna55029602015-02-06 15:43:35 +05301081 VOS_STATUS vos_status;
Vinay Krishna Erannad9cbdb32014-01-16 12:59:10 +05301082 int status;
Vinay Krishna Erannaf97ef5c2014-12-26 17:47:19 +05301083
Hanumantha Reddy Pothula7dc0e6c2015-03-06 15:11:16 +05301084 ENTER();
Vinay Krishna Eranna55029602015-02-06 15:43:35 +05301085 pHddCtx = container_of(nb, hdd_context_t, ipv4_notifier);
1086 status = wlan_hdd_validate_context(pHddCtx);
1087 if (0 != status)
Vinay Krishna Eranna4d055d42013-12-17 17:02:01 +05301088 {
Vinay Krishna Eranna55029602015-02-06 15:43:35 +05301089 return NOTIFY_DONE;
1090 }
Vinay Krishna Eranna83b0ef72014-11-19 16:56:20 +05301091
Vinay Krishna Eranna55029602015-02-06 15:43:35 +05301092 vos_status = hdd_get_front_adapter(pHddCtx, &pAdapterNode);
1093 while (NULL != pAdapterNode && VOS_STATUS_SUCCESS == vos_status)
1094 {
1095 if (pAdapterNode->pAdapter && pAdapterNode->pAdapter->dev == ndev &&
1096 (pAdapterNode->pAdapter->device_mode == WLAN_HDD_INFRA_STATION ||
1097 pAdapterNode->pAdapter->device_mode == WLAN_HDD_P2P_CLIENT))
1098 {
Abhishek Singhe0bc0992016-05-20 17:58:18 +05301099
1100 if (eConnectionState_Associated ==
1101 WLAN_HDD_GET_STATION_CTX_PTR
1102 (pAdapterNode->pAdapter)->conn_info.connState)
1103 sme_dhcp_done_ind(pHddCtx->hHal,
1104 pAdapterNode->pAdapter->sessionId);
Vinay Krishna Eranna55029602015-02-06 15:43:35 +05301105 if ((pHddCtx->cfg_ini->nEnableSuspend !=
Vinay Krishna Eranna83b0ef72014-11-19 16:56:20 +05301106 WLAN_MAP_SUSPEND_TO_MCAST_BCAST_FILTER)
Vinay Krishna Eranna55029602015-02-06 15:43:35 +05301107 || (!pHddCtx->cfg_ini->fhostArpOffload))
1108 {
1109 hddLog(LOG1, FL("Offload not enabled MCBC=%d, ARPOffload=%d"),
1110 pHddCtx->cfg_ini->nEnableSuspend,
1111 pHddCtx->cfg_ini->fhostArpOffload);
1112 return NOTIFY_DONE;
1113 }
Vinay Krishna Eranna83b0ef72014-11-19 16:56:20 +05301114
Vinay Krishna Eranna55029602015-02-06 15:43:35 +05301115 if ((in_dev =
1116 __in_dev_get_rtnl(pAdapterNode->pAdapter->dev)) != NULL)
1117 {
1118 for (ifap = &in_dev->ifa_list; (ifa = *ifap) != NULL;
1119 ifap = &ifa->ifa_next)
1120 {
1121 if (!strcmp(pAdapterNode->pAdapter->dev->name,
1122 ifa->ifa_label))
1123 {
1124 break; /* found */
1125 }
1126 }
1127 }
1128 if(ifa && ifa->ifa_local)
1129 {
1130 schedule_work(&pAdapterNode->pAdapter->ipv4NotifierWorkQueue);
1131 }
1132 break;
1133 }
1134 vos_status = hdd_get_next_adapter(pHddCtx, pAdapterNode, &pNext);
1135 pAdapterNode = pNext;
Vinay Krishna Eranna4d055d42013-12-17 17:02:01 +05301136 }
Hanumantha Reddy Pothula7dc0e6c2015-03-06 15:11:16 +05301137 EXIT();
Vinay Krishna Eranna4d055d42013-12-17 17:02:01 +05301138 return NOTIFY_DONE;
1139}
1140
Mukul Sharmaa78cf6b2015-02-24 16:59:01 +05301141int wlan_hdd_ipv4_changed(struct notifier_block *nb,
1142 unsigned long data, void *arg)
1143{
1144 int ret;
1145 vos_ssr_protect(__func__);
1146 ret = __wlan_hdd_ipv4_changed( nb, data, arg);
1147 vos_ssr_unprotect(__func__);
1148 return ret;
1149}
1150
Vinay Krishna Eranna4d055d42013-12-17 17:02:01 +05301151/**----------------------------------------------------------------------------
1152
1153 \brief hdd_conf_arp_offload() - Configure ARP offload
1154
1155 Called during SUSPEND to configure the ARP offload (MC BC filter) which
1156 reduces power consumption.
1157
1158 \param - pAdapter -Adapter context for which ARP offload is to be configured
1159 \param - fenable - 0 - disable.
1160 1 - enable. (with IPv4 notifier registration)
1161 2 - enable. (without IPv4 notifier registration)
1162
1163 \return -
1164 VOS_STATUS_SUCCESS - on successful operation
1165 VOS_STATUS_E_FAILURE - on failure of operation
1166-----------------------------------------------------------------------------*/
1167VOS_STATUS hdd_conf_arp_offload(hdd_adapter_t *pAdapter, int fenable)
Jeff Johnson295189b2012-06-20 16:38:30 -07001168{
1169 struct in_ifaddr **ifap = NULL;
1170 struct in_ifaddr *ifa = NULL;
1171 struct in_device *in_dev;
1172 int i = 0;
Jeff Johnson295189b2012-06-20 16:38:30 -07001173 tSirHostOffloadReq offLoadRequest;
Yathish9f22e662012-12-10 14:21:35 -08001174 hdd_context_t *pHddCtx = WLAN_HDD_GET_CTX(pAdapter);
Jeff Johnson295189b2012-06-20 16:38:30 -07001175
Sushant Kaushik87787972015-09-11 16:05:00 +05301176 hddLog(VOS_TRACE_LEVEL_INFO, FL(" fenable = %d "), fenable);
Jeff Johnson295189b2012-06-20 16:38:30 -07001177
Jeff Johnson295189b2012-06-20 16:38:30 -07001178 if(fenable)
1179 {
1180 if ((in_dev = __in_dev_get_rtnl(pAdapter->dev)) != NULL)
1181 {
Gopichand Nakkalab8f0f1a2013-05-23 18:19:48 +05301182 for (ifap = &in_dev->ifa_list; (ifa = *ifap) != NULL;
Jeff Johnson295189b2012-06-20 16:38:30 -07001183 ifap = &ifa->ifa_next)
1184 {
1185 if (!strcmp(pAdapter->dev->name, ifa->ifa_label))
1186 {
1187 break; /* found */
1188 }
1189 }
1190 }
Jeff Johnson295189b2012-06-20 16:38:30 -07001191 if(ifa && ifa->ifa_local)
1192 {
1193 offLoadRequest.offloadType = SIR_IPV4_ARP_REPLY_OFFLOAD;
1194 offLoadRequest.enableOrDisable = SIR_OFFLOAD_ENABLE;
Abhishek Singh937ec542016-01-05 18:03:14 +05301195 hdd_wlan_offload_event(SIR_IPV4_ARP_REPLY_OFFLOAD,
1196 SIR_OFFLOAD_ENABLE);
Jeff Johnson295189b2012-06-20 16:38:30 -07001197
Arif Hussain6d2a3322013-11-17 19:50:10 -08001198 hddLog(VOS_TRACE_LEVEL_INFO, "%s: Enabled", __func__);
Jeff Johnson295189b2012-06-20 16:38:30 -07001199
Amar Singhald53568e2013-09-26 11:03:45 -07001200 if (((HDD_MCASTBCASTFILTER_FILTER_ALL_BROADCAST ==
1201 pHddCtx->sus_res_mcastbcast_filter) ||
1202 (HDD_MCASTBCASTFILTER_FILTER_ALL_MULTICAST_BROADCAST ==
1203 pHddCtx->sus_res_mcastbcast_filter)) &&
1204 (VOS_TRUE == pHddCtx->sus_res_mcastbcast_filter_valid))
Madan Mohan Koyyalamudif55e62a2012-09-24 11:14:27 -07001205 {
Gopichand Nakkalab8f0f1a2013-05-23 18:19:48 +05301206 offLoadRequest.enableOrDisable =
Amar Singhald53568e2013-09-26 11:03:45 -07001207 SIR_OFFLOAD_ARP_AND_BCAST_FILTER_ENABLE;
1208 hddLog(VOS_TRACE_LEVEL_INFO,
1209 "offload: inside arp offload conditional check");
Jeff Johnson295189b2012-06-20 16:38:30 -07001210 }
Abhishek Singh937ec542016-01-05 18:03:14 +05301211 hdd_wlan_offload_event(SIR_OFFLOAD_ARP_AND_BCAST_FILTER_ENABLE,
1212 SIR_OFFLOAD_ENABLE);
Amar Singhald53568e2013-09-26 11:03:45 -07001213
1214 hddLog(VOS_TRACE_LEVEL_INFO, "offload: arp filter programmed = %d",
1215 offLoadRequest.enableOrDisable);
1216
Jeff Johnson295189b2012-06-20 16:38:30 -07001217 //converting u32 to IPV4 address
1218 for(i = 0 ; i < 4; i++)
1219 {
Gopichand Nakkalab8f0f1a2013-05-23 18:19:48 +05301220 offLoadRequest.params.hostIpv4Addr[i] =
Jeff Johnson295189b2012-06-20 16:38:30 -07001221 (ifa->ifa_local >> (i*8) ) & 0xFF ;
1222 }
Gopichand Nakkalab8f0f1a2013-05-23 18:19:48 +05301223 hddLog(VOS_TRACE_LEVEL_INFO, " Enable SME HostOffload: %d.%d.%d.%d",
Jeff Johnson295189b2012-06-20 16:38:30 -07001224 offLoadRequest.params.hostIpv4Addr[0],
1225 offLoadRequest.params.hostIpv4Addr[1],
1226 offLoadRequest.params.hostIpv4Addr[2],
1227 offLoadRequest.params.hostIpv4Addr[3]);
1228
Gopichand Nakkalab8f0f1a2013-05-23 18:19:48 +05301229 if (eHAL_STATUS_SUCCESS !=
1230 sme_SetHostOffload(WLAN_HDD_GET_HAL_CTX(pAdapter),
1231 pAdapter->sessionId, &offLoadRequest))
Jeff Johnson295189b2012-06-20 16:38:30 -07001232 {
1233 hddLog(VOS_TRACE_LEVEL_ERROR, "%s: Failed to enable HostOffload "
Arif Hussain6d2a3322013-11-17 19:50:10 -08001234 "feature", __func__);
Jeff Johnson295189b2012-06-20 16:38:30 -07001235 return VOS_STATUS_E_FAILURE;
1236 }
Jeff Johnson295189b2012-06-20 16:38:30 -07001237 }
1238 else
1239 {
SaidiReddy Yenugaa8b32f92016-07-27 19:29:18 +05301240 hddLog(VOS_TRACE_LEVEL_WARN, FL("IP Address is not assigned"));
Agarwal Ashish971c2882013-10-30 20:11:12 +05301241 return VOS_STATUS_E_AGAIN;
Jeff Johnson295189b2012-06-20 16:38:30 -07001242 }
Vinay Krishna Eranna4d055d42013-12-17 17:02:01 +05301243
Vinay Krishna Eranna4d055d42013-12-17 17:02:01 +05301244 return VOS_STATUS_SUCCESS;
Jeff Johnson295189b2012-06-20 16:38:30 -07001245 }
1246 else
1247 {
1248 vos_mem_zero((void *)&offLoadRequest, sizeof(tSirHostOffloadReq));
1249 offLoadRequest.enableOrDisable = SIR_OFFLOAD_DISABLE;
1250 offLoadRequest.offloadType = SIR_IPV4_ARP_REPLY_OFFLOAD;
Abhishek Singh937ec542016-01-05 18:03:14 +05301251 hdd_wlan_offload_event(SIR_IPV4_ARP_REPLY_OFFLOAD,
1252 SIR_OFFLOAD_DISABLE);
Gopichand Nakkalab8f0f1a2013-05-23 18:19:48 +05301253 if (eHAL_STATUS_SUCCESS !=
1254 sme_SetHostOffload(WLAN_HDD_GET_HAL_CTX(pAdapter),
1255 pAdapter->sessionId, &offLoadRequest))
Jeff Johnson295189b2012-06-20 16:38:30 -07001256 {
1257 hddLog(VOS_TRACE_LEVEL_ERROR, "%s: Failure to disable host "
Arif Hussain6d2a3322013-11-17 19:50:10 -08001258 "offload feature", __func__);
Jeff Johnson295189b2012-06-20 16:38:30 -07001259 return VOS_STATUS_E_FAILURE;
1260 }
1261 return VOS_STATUS_SUCCESS;
1262 }
1263}
1264
Gopichand Nakkalab8ddf462013-02-20 18:53:50 +05301265/*
1266 * This function is called before setting mcbc filters
Gopichand Nakkala746a9452013-06-11 12:45:54 +05301267 * to modify filter value considering Different Offloads
Gopichand Nakkalab8ddf462013-02-20 18:53:50 +05301268*/
Gopichand Nakkala746a9452013-06-11 12:45:54 +05301269void hdd_mcbc_filter_modification(hdd_context_t* pHddCtx,
Gopichand Nakkalab8ddf462013-02-20 18:53:50 +05301270 tANI_U8 *pMcBcFilter)
1271{
Gopichand Nakkala746a9452013-06-11 12:45:54 +05301272 if (NULL == pHddCtx)
1273 {
1274 hddLog(VOS_TRACE_LEVEL_ERROR, FL("NULL HDD context passed"));
1275 return;
1276 }
1277
1278 *pMcBcFilter = pHddCtx->configuredMcastBcastFilter;
1279 if (pHddCtx->cfg_ini->fhostArpOffload)
Gopichand Nakkalab8ddf462013-02-20 18:53:50 +05301280 {
Gopichand Nakkalab8f0f1a2013-05-23 18:19:48 +05301281 /* ARP offload is enabled, do not block bcast packets at RXP
1282 * Will be using Bitmasking to reset the filter. As we have
1283 * disable Broadcast filtering, Anding with the negation
1284 * of Broadcast BIT
1285 */
Agarwal Ashishff451a32015-07-28 01:01:29 +05301286 hddLog(VOS_TRACE_LEVEL_INFO, FL(" ARP offload is enabled"));
Gopichand Nakkala746a9452013-06-11 12:45:54 +05301287 *pMcBcFilter &= ~(HDD_MCASTBCASTFILTER_FILTER_ALL_BROADCAST);
Gopichand Nakkalab8ddf462013-02-20 18:53:50 +05301288 }
Gopichand Nakkala746a9452013-06-11 12:45:54 +05301289
1290#ifdef WLAN_NS_OFFLOAD
1291 if (pHddCtx->cfg_ini->fhostNSOffload)
Gopichand Nakkalab8ddf462013-02-20 18:53:50 +05301292 {
Gopichand Nakkala746a9452013-06-11 12:45:54 +05301293 /* NS offload is enabled, do not block mcast packets at RXP
1294 * Will be using Bitmasking to reset the filter. As we have
1295 * disable Multicast filtering, Anding with the negation
1296 * of Multicast BIT
1297 */
Agarwal Ashishff451a32015-07-28 01:01:29 +05301298 hddLog(VOS_TRACE_LEVEL_INFO, FL(" NS offload is enabled"));
Gopichand Nakkala746a9452013-06-11 12:45:54 +05301299 *pMcBcFilter &= ~(HDD_MCASTBCASTFILTER_FILTER_ALL_MULTICAST);
Gopichand Nakkalab8ddf462013-02-20 18:53:50 +05301300 }
Gopichand Nakkala746a9452013-06-11 12:45:54 +05301301#endif
1302
Amar Singhald08ce752014-03-21 16:28:27 -07001303 if ((pHddCtx->cfg_ini->fEnableMCAddrList) && WDA_IS_MCAST_FLT_ENABLE_IN_FW)
1304 {
1305 *pMcBcFilter &= ~(HDD_MCASTBCASTFILTER_FILTER_ALL_MULTICAST);
1306 }
1307
Gopichand Nakkala746a9452013-06-11 12:45:54 +05301308 pHddCtx->configuredMcastBcastFilter = *pMcBcFilter;
Gopichand Nakkalab8ddf462013-02-20 18:53:50 +05301309}
1310
Jeff Johnson295189b2012-06-20 16:38:30 -07001311void hdd_conf_mcastbcast_filter(hdd_context_t* pHddCtx, v_BOOL_t setfilter)
1312{
1313 eHalStatus halStatus = eHAL_STATUS_FAILURE;
Jeff Johnson295189b2012-06-20 16:38:30 -07001314 tpSirWlanSetRxpFilters wlanRxpFilterParam =
1315 vos_mem_malloc(sizeof(tSirWlanSetRxpFilters));
Agarwal Ashishff451a32015-07-28 01:01:29 +05301316 if (NULL == wlanRxpFilterParam)
Jeff Johnson295189b2012-06-20 16:38:30 -07001317 {
1318 hddLog(VOS_TRACE_LEVEL_FATAL,
1319 "%s: vos_mem_alloc failed ", __func__);
1320 return;
1321 }
Jeff Johnson295189b2012-06-20 16:38:30 -07001322 hddLog(VOS_TRACE_LEVEL_INFO,
1323 "%s: Configuring Mcast/Bcast Filter Setting. setfilter %d", __func__, setfilter);
Gopichand Nakkalab8ddf462013-02-20 18:53:50 +05301324 if (TRUE == setfilter)
1325 {
Gopichand Nakkala746a9452013-06-11 12:45:54 +05301326 hdd_mcbc_filter_modification(pHddCtx,
Gopichand Nakkalab8ddf462013-02-20 18:53:50 +05301327 &wlanRxpFilterParam->configuredMcstBcstFilterSetting);
Gopichand Nakkalab8ddf462013-02-20 18:53:50 +05301328 }
1329 else
Gopichand Nakkalab8f0f1a2013-05-23 18:19:48 +05301330 {
1331 /*Use the current configured value to clear*/
Gopichand Nakkalab8ddf462013-02-20 18:53:50 +05301332 wlanRxpFilterParam->configuredMcstBcstFilterSetting =
Gopichand Nakkalab8f0f1a2013-05-23 18:19:48 +05301333 pHddCtx->configuredMcastBcastFilter;
1334 }
Gopichand Nakkalab8ddf462013-02-20 18:53:50 +05301335
Jeff Johnson295189b2012-06-20 16:38:30 -07001336 wlanRxpFilterParam->setMcstBcstFilter = setfilter;
Jeff Johnson295189b2012-06-20 16:38:30 -07001337 halStatus = sme_ConfigureRxpFilter(pHddCtx->hHal, wlanRxpFilterParam);
Masti, Narayanraddibdc261d2015-01-22 15:59:49 +05301338
1339 if (setfilter && (eHAL_STATUS_SUCCESS == halStatus))
Agarwal Ashishff451a32015-07-28 01:01:29 +05301340 {
Masti, Narayanraddibdc261d2015-01-22 15:59:49 +05301341 pHddCtx->hdd_mcastbcast_filter_set = TRUE;
Agarwal Ashishff451a32015-07-28 01:01:29 +05301342 }
Masti, Narayanraddibdc261d2015-01-22 15:59:49 +05301343
1344 hddLog(VOS_TRACE_LEVEL_INFO, "%s to post set/reset filter to"
1345 "lower mac with status %d"
1346 "configuredMcstBcstFilterSetting = %d"
1347 "setMcstBcstFilter = %d",(eHAL_STATUS_SUCCESS != halStatus) ?
1348 "Failed" : "Success", halStatus,
1349 wlanRxpFilterParam->configuredMcstBcstFilterSetting,
1350 wlanRxpFilterParam->setMcstBcstFilter);
1351
Chilam Ngc4244af2013-04-01 15:37:32 -07001352 if (eHAL_STATUS_SUCCESS != halStatus)
1353 vos_mem_free(wlanRxpFilterParam);
Jeff Johnson295189b2012-06-20 16:38:30 -07001354}
1355
mukul sharmae4abd892016-11-24 22:03:31 +05301356/*
1357 * Enable/Disable McAddrList cfg item in fwr.
1358 */
1359eHalStatus hdd_set_mc_list_cfg_item(hdd_context_t* pHddCtx,
1360 bool value)
1361{
1362 eHalStatus ret_val;
1363
1364 if (ccmCfgSetInt(pHddCtx->hHal, WNI_CFG_ENABLE_MC_ADDR_LIST,
1365 value, NULL, eANI_BOOLEAN_FALSE) == eHAL_STATUS_FAILURE)
1366 {
1367 ret_val = eHAL_STATUS_FAILURE;
Mukul Sharma75ee8aa2016-12-01 14:28:10 +05301368 hddLog(LOGE,
1369 FL("offload: can't pass WNI_CFG_ENABLE_MC_ADDR_LIST to CCM"));
mukul sharmae4abd892016-11-24 22:03:31 +05301370 return ret_val;
1371 }
1372
1373 ret_val = sme_update_cfg_int_param(pHddCtx->hHal,
1374 WNI_CFG_ENABLE_MC_ADDR_LIST);
1375 if (!HAL_STATUS_SUCCESS(ret_val))
1376 {
1377 hddLog(VOS_TRACE_LEVEL_ERROR,
1378 FL("Failed to toggle MC_ADDR_LIST_INI %d "),
1379 ret_val);
1380 return ret_val;
1381 }
1382 /* cache the value configured in fwr */
1383 pHddCtx->mc_list_cfg_in_fwr = value;
mukul sharmae4abd892016-11-24 22:03:31 +05301384 return eHAL_STATUS_SUCCESS;
1385}
1386
1387bool is_mc_list_cfg_disable_required(hdd_context_t* pHddCtx)
1388{
Mukul Sharma75ee8aa2016-12-01 14:28:10 +05301389 hddLog(VOS_TRACE_LEVEL_INFO,
1390 FL("offload: fEnableMCList %d sus_res_mcbc_filter %d mc_list_in_fwr %d"),
1391 pHddCtx->cfg_ini->fEnableMCAddrList,
1392 pHddCtx->sus_res_mcastbcast_filter,
1393 pHddCtx->mc_list_cfg_in_fwr);
1394
mukul sharmae4abd892016-11-24 22:03:31 +05301395 /*
1396 * If MCAddrList is enabled in ini and MCBC filter is set to
1397 * Either Filter None or Filter all BC then, Fwr need to push
1398 * all MC to host. This can be achieved by disabling cfg MCAddrList
1399 * in fwr. As in driver load, firmware have this value to 1 we
1400 * need to set it to 0. Same needs to be reverted on resume.
1401 */
1402 if (pHddCtx->cfg_ini->fEnableMCAddrList &&
1403 WDA_IS_MCAST_FLT_ENABLE_IN_FW &&
1404 ((VOS_TRUE == pHddCtx->sus_res_mcastbcast_filter_valid)&&
1405 ((HDD_MCASTBCASTFILTER_FILTER_NONE ==
1406 pHddCtx->sus_res_mcastbcast_filter) ||
1407 (HDD_MCASTBCASTFILTER_FILTER_ALL_BROADCAST ==
1408 pHddCtx->sus_res_mcastbcast_filter)))
1409 )
1410 {
Mukul Sharma75ee8aa2016-12-01 14:28:10 +05301411 hddLog(VOS_TRACE_LEVEL_INFO,
1412 FL("offload: cfg ini need to disable in fwr"));
mukul sharmae4abd892016-11-24 22:03:31 +05301413 return true;
1414 }
1415 else
1416 {
Mukul Sharma75ee8aa2016-12-01 14:28:10 +05301417 hddLog(VOS_TRACE_LEVEL_INFO,
1418 FL("offload: cfg ini disable not needed "));
mukul sharmae4abd892016-11-24 22:03:31 +05301419 return false;
1420 }
1421}
1422
1423/**
1424 * hdd_mc_addr_list_cfg_config() - To set mc list cfg configuration in fwr
1425 * @pHddCtx: hdd context handle
1426 * @action: true to disable MCAddrList in fwr to get all MC pkt to host
1427 * false to set ini value of MCAddrList in fwr if it was toggled
1428 * Return: none
1429 *
1430 * Ensure Below API is invoked always post modification
1431 * of sus_res_mcastbcast_filter.
1432 */
1433void hdd_mc_addr_list_cfg_config(hdd_context_t* pHddCtx, bool action)
1434{
1435 if (action)
1436 {
1437 /* check host need to disable mc list ini in fwr */
1438 if (is_mc_list_cfg_disable_required(pHddCtx))
1439 {
1440 /*
1441 * Yes Host should disable the mc list in fwr
1442 * But Ensure host might already disable it
1443 * This can happen when user issue set/clear MCBC
1444 * ioctl with 2 to 0 or vice versa.
1445 */
1446 if (pHddCtx->cfg_ini->fEnableMCAddrList ==
1447 pHddCtx->mc_list_cfg_in_fwr)
1448 {
1449 hdd_set_mc_list_cfg_item(pHddCtx,
1450 !pHddCtx->cfg_ini->fEnableMCAddrList);
Mukul Sharma75ee8aa2016-12-01 14:28:10 +05301451 hddLog(VOS_TRACE_LEVEL_INFO,
1452 FL("offload: setting mc_list_cfg_in_fwr: %d"),
1453 !pHddCtx->cfg_ini->fEnableMCAddrList);
mukul sharmae4abd892016-11-24 22:03:31 +05301454 }
1455 }
1456 else
1457 {
1458 /* Host toggled mc list ini in fwr previosuly, set to ini value */
1459 if (pHddCtx->cfg_ini->fEnableMCAddrList !=
1460 pHddCtx->mc_list_cfg_in_fwr)
1461 {
1462 hdd_set_mc_list_cfg_item(pHddCtx,
1463 pHddCtx->cfg_ini->fEnableMCAddrList);
Mukul Sharma75ee8aa2016-12-01 14:28:10 +05301464 hddLog(VOS_TRACE_LEVEL_INFO,
1465 FL("offload: setting mc_list_cfg_in_fwr: %d"),
1466 pHddCtx->cfg_ini->fEnableMCAddrList);
mukul sharmae4abd892016-11-24 22:03:31 +05301467 }
1468 }
1469 }
1470 else
1471 {
1472 /* Host toggled mc list ini in fwr previosuly, set to ini value */
1473 if (pHddCtx->cfg_ini->fEnableMCAddrList !=
1474 pHddCtx->mc_list_cfg_in_fwr)
1475 {
1476 hdd_set_mc_list_cfg_item(pHddCtx,
1477 pHddCtx->cfg_ini->fEnableMCAddrList);
Mukul Sharma75ee8aa2016-12-01 14:28:10 +05301478 hddLog(VOS_TRACE_LEVEL_INFO,
1479 FL("offload: setting mc_list_cfg_in_fwr: %d"),
1480 pHddCtx->cfg_ini->fEnableMCAddrList);
mukul sharmae4abd892016-11-24 22:03:31 +05301481 }
1482 }
1483}
1484
Kapil Gupta2b44acb2016-12-30 16:49:51 +05301485/**
1486 * hdd_suspend_ind_callback: This API will set completion event for suspend
1487 * @pAdapter: hdd_adapter_t
1488 * @status: suspend status
1489 *
1490 * Return: none
1491 */
1492static void hdd_suspend_ind_callback(void *context, VOS_STATUS status)
1493{
1494 hdd_adapter_t *adapter = (hdd_adapter_t *)context;
1495 if (NULL == adapter)
1496 {
1497 hddLog(VOS_TRACE_LEVEL_ERROR,
1498 "%s: HDD adapter is NULL",__func__);
1499 return;
1500 }
1501 hddLog(VOS_TRACE_LEVEL_INFO, FL("suspend status %d"), status);
1502 complete(&adapter->wlan_suspend_comp_var);
1503}
1504
Jeff Johnson295189b2012-06-20 16:38:30 -07001505static void hdd_conf_suspend_ind(hdd_context_t* pHddCtx,
1506 hdd_adapter_t *pAdapter)
1507{
1508 eHalStatus halStatus = eHAL_STATUS_FAILURE;
1509 tpSirWlanSuspendParam wlanSuspendParam =
1510 vos_mem_malloc(sizeof(tSirWlanSuspendParam));
1511
Mukul Sharma75ee8aa2016-12-01 14:28:10 +05301512 check_and_set_suspend_resume_mcbc_filter(pHddCtx);
Jeff Johnson295189b2012-06-20 16:38:30 -07001513 if(NULL == wlanSuspendParam)
1514 {
1515 hddLog(VOS_TRACE_LEVEL_FATAL,
1516 "%s: vos_mem_alloc failed ", __func__);
1517 return;
1518 }
1519
Amar Singhald53568e2013-09-26 11:03:45 -07001520 hddLog(VOS_TRACE_LEVEL_INFO,
Jeff Johnson295189b2012-06-20 16:38:30 -07001521 "%s: send wlan suspend indication", __func__);
1522
1523 if((pHddCtx->cfg_ini->nEnableSuspend == WLAN_MAP_SUSPEND_TO_MCAST_BCAST_FILTER))
1524 {
Gopichand Nakkalab03e8082013-05-30 18:09:25 +05301525 //Configure supported OffLoads
1526 hdd_conf_hostoffload(pAdapter, TRUE);
1527 wlanSuspendParam->configuredMcstBcstFilterSetting = pHddCtx->configuredMcastBcastFilter;
Sushant Kaushik439d4c72014-05-12 16:39:51 +05301528 hddLog(VOS_TRACE_LEVEL_INFO,
1529 FL("saving configuredMcastBcastFilterSetting = %d"),
1530 wlanSuspendParam->configuredMcstBcstFilterSetting);
Jeff Johnson295189b2012-06-20 16:38:30 -07001531#ifdef WLAN_FEATURE_PACKET_FILTERING
madan mohan koyyalamudibfd9cef2013-07-01 18:39:37 +05301532 /* During suspend, configure MC Addr list filter to the firmware
1533 * function takes care of checking necessary conditions before
1534 * configuring.
1535 */
1536 wlan_hdd_set_mc_addr_list(pAdapter, TRUE);
Jeff Johnson295189b2012-06-20 16:38:30 -07001537#endif
Amar Singhald08ce752014-03-21 16:28:27 -07001538
1539 if( (pHddCtx->cfg_ini->fEnableMCAddrList) && WDA_IS_MCAST_FLT_ENABLE_IN_FW)
1540 {
1541
1542 hddLog(VOS_TRACE_LEVEL_INFO, "offload: MCaddrlist: FW capability set ");
1543 pHddCtx->configuredMcastBcastFilter &=
1544 ~(HDD_MCASTBCASTFILTER_FILTER_ALL_MULTICAST);
1545 }
1546
1547 wlanSuspendParam->configuredMcstBcstFilterSetting =
1548 pHddCtx->configuredMcastBcastFilter;
mukul sharmae4abd892016-11-24 22:03:31 +05301549
Kapil Gupta2b44acb2016-12-30 16:49:51 +05301550 wlanSuspendParam->wlan_sus_callback = hdd_suspend_ind_callback;
1551 wlanSuspendParam->context = pAdapter;
mukul sharmae4abd892016-11-24 22:03:31 +05301552 /* mc add list cfg item configuration in fwr */
1553 hdd_mc_addr_list_cfg_config(pHddCtx, true);
1554
Jeff Johnson295189b2012-06-20 16:38:30 -07001555 }
1556
1557 halStatus = sme_ConfigureSuspendInd(pHddCtx->hHal, wlanSuspendParam);
1558 if(eHAL_STATUS_SUCCESS == halStatus)
1559 {
1560 pHddCtx->hdd_mcastbcast_filter_set = TRUE;
Chilam Ngc4244af2013-04-01 15:37:32 -07001561 } else {
c_hpothuffdb5272013-10-02 16:42:35 +05301562 hddLog(VOS_TRACE_LEVEL_ERROR,
1563 FL("sme_ConfigureSuspendInd returned failure %d"), halStatus);
Chilam Ngc4244af2013-04-01 15:37:32 -07001564 vos_mem_free(wlanSuspendParam);
Jeff Johnson295189b2012-06-20 16:38:30 -07001565 }
1566}
1567
Gopichand Nakkala0f276812013-02-24 14:45:51 +05301568static void hdd_conf_resume_ind(hdd_adapter_t *pAdapter)
Jeff Johnson295189b2012-06-20 16:38:30 -07001569{
Chilam Ngc4244af2013-04-01 15:37:32 -07001570 eHalStatus halStatus = eHAL_STATUS_FAILURE;
Yathish9f22e662012-12-10 14:21:35 -08001571 hdd_context_t* pHddCtx = WLAN_HDD_GET_CTX(pAdapter);
Chilam Ngc4244af2013-04-01 15:37:32 -07001572 tpSirWlanResumeParam wlanResumeParam;
Jeff Johnson295189b2012-06-20 16:38:30 -07001573
Gopichand Nakkala0f276812013-02-24 14:45:51 +05301574 hddLog(VOS_TRACE_LEVEL_INFO,
Jeff Johnson295189b2012-06-20 16:38:30 -07001575 "%s: send wlan resume indication", __func__);
1576
Madan Mohan Koyyalamudia6d7eab2013-09-25 10:21:22 +05301577 wlanResumeParam = vos_mem_malloc(sizeof(tSirWlanResumeParam));
1578
1579 if (NULL == wlanResumeParam)
Jeff Johnson295189b2012-06-20 16:38:30 -07001580 {
Madan Mohan Koyyalamudia6d7eab2013-09-25 10:21:22 +05301581 hddLog(VOS_TRACE_LEVEL_FATAL,
1582 "%s: memory allocation failed for wlanResumeParam ", __func__);
1583 return;
Jeff Johnson295189b2012-06-20 16:38:30 -07001584 }
Jeff Johnson295189b2012-06-20 16:38:30 -07001585
Madan Mohan Koyyalamudia6d7eab2013-09-25 10:21:22 +05301586 //Disable supported OffLoads
1587 hdd_conf_hostoffload(pAdapter, FALSE);
1588
1589 wlanResumeParam->configuredMcstBcstFilterSetting =
1590 pHddCtx->configuredMcastBcastFilter;
1591 halStatus = sme_ConfigureResumeReq(pHddCtx->hHal, wlanResumeParam);
1592 if (eHAL_STATUS_SUCCESS != halStatus)
1593 {
c_hpothuffdb5272013-10-02 16:42:35 +05301594 hddLog(VOS_TRACE_LEVEL_ERROR,
1595 "%s: sme_ConfigureResumeReq return failure %d", __func__, halStatus);
Madan Mohan Koyyalamudia6d7eab2013-09-25 10:21:22 +05301596 vos_mem_free(wlanResumeParam);
1597 }
1598
1599 pHddCtx->hdd_mcastbcast_filter_set = FALSE;
mukul sharmae4abd892016-11-24 22:03:31 +05301600 /* mc add list cfg item configuration in fwr */
1601 hdd_mc_addr_list_cfg_config(pHddCtx, false);
Madan Mohan Koyyalamudia6d7eab2013-09-25 10:21:22 +05301602
Amar Singhalf8ba2b82013-12-02 12:54:38 -08001603 if (VOS_TRUE == pHddCtx->sus_res_mcastbcast_filter_valid) {
1604 pHddCtx->configuredMcastBcastFilter =
1605 pHddCtx->sus_res_mcastbcast_filter;
1606 pHddCtx->sus_res_mcastbcast_filter_valid = VOS_FALSE;
1607 }
Amar Singhald53568e2013-09-26 11:03:45 -07001608
1609 hddLog(VOS_TRACE_LEVEL_INFO,
1610 "offload: in hdd_conf_resume_ind, restoring configuredMcastBcastFilter");
1611 hddLog(VOS_TRACE_LEVEL_INFO, "configuredMcastBcastFilter = %d",
1612 pHddCtx->configuredMcastBcastFilter);
Amar Singhal49fdfd52013-08-13 13:25:12 -07001613
Chilam Ngc4244af2013-04-01 15:37:32 -07001614
madan mohan koyyalamudibfd9cef2013-07-01 18:39:37 +05301615#ifdef WLAN_FEATURE_PACKET_FILTERING
1616 /* Filer was applied during suspend inditication
1617 * clear it when we resume.
1618 */
1619 wlan_hdd_set_mc_addr_list(pAdapter, FALSE);
Jeff Johnson295189b2012-06-20 16:38:30 -07001620#endif
1621}
Jeff Johnson295189b2012-06-20 16:38:30 -07001622
Jeff Johnson295189b2012-06-20 16:38:30 -07001623//Suspend routine registered with Android OS
Sameer Thalappil45931fb2013-02-01 11:18:05 -08001624void hdd_suspend_wlan(void)
Jeff Johnson295189b2012-06-20 16:38:30 -07001625{
1626 hdd_context_t *pHddCtx = NULL;
1627 v_CONTEXT_t pVosContext = NULL;
Kapil Gupta2b44acb2016-12-30 16:49:51 +05301628 long ret;
Jeff Johnson295189b2012-06-20 16:38:30 -07001629 VOS_STATUS status;
Gopichand Nakkalaa2fe5b02013-06-06 16:32:28 +05301630 hdd_adapter_t *pAdapter = NULL;
1631 hdd_adapter_list_node_t *pAdapterNode = NULL, *pNext = NULL;
madan mohan koyyalamudi459d6e72013-07-09 23:36:00 +05301632 bool hdd_enter_bmps = FALSE;
Jeff Johnsonbc676b42013-02-14 16:04:08 -08001633
Jeff Johnson295189b2012-06-20 16:38:30 -07001634 hddLog(VOS_TRACE_LEVEL_INFO, "%s: WLAN being suspended by Android OS",__func__);
1635
1636 //Get the global VOSS context.
1637 pVosContext = vos_get_global_context(VOS_MODULE_ID_SYS, NULL);
1638 if(!pVosContext) {
1639 hddLog(VOS_TRACE_LEVEL_FATAL,"%s: Global VOS context is Null", __func__);
1640 return;
1641 }
1642
1643 //Get the HDD context.
1644 pHddCtx = (hdd_context_t *)vos_get_context(VOS_MODULE_ID_HDD, pVosContext );
1645
1646 if(!pHddCtx) {
1647 hddLog(VOS_TRACE_LEVEL_FATAL,"%s: HDD context is Null",__func__);
1648 return;
1649 }
1650
1651 if (pHddCtx->isLogpInProgress) {
1652 hddLog(VOS_TRACE_LEVEL_ERROR,
1653 "%s: Ignore suspend wlan, LOGP in progress!", __func__);
1654 return;
1655 }
1656
Padma, Santhosh Kumar2ee1ad02015-01-12 16:05:47 +05301657 if (pHddCtx->hdd_wlan_suspended)
1658 {
SaidiReddy Yenugaa8b32f92016-07-27 19:29:18 +05301659 hddLog(VOS_TRACE_LEVEL_INFO,
Padma, Santhosh Kumar2ee1ad02015-01-12 16:05:47 +05301660 "%s: Ignore suspend wlan, Already suspended!", __func__);
1661 return;
1662 }
1663
Mahesh A Saptasagar0ea15c22014-10-28 15:26:57 +05301664 pHddCtx->hdd_wlan_suspended = TRUE;
Abhishek Singh37471cd2016-01-05 17:09:57 +05301665 hdd_wlan_suspend_resume_event(HDD_WLAN_EARLY_SUSPEND);
Gopichand Nakkalaa2fe5b02013-06-06 16:32:28 +05301666 hdd_set_pwrparams(pHddCtx);
Jeff Johnson295189b2012-06-20 16:38:30 -07001667 status = hdd_get_front_adapter ( pHddCtx, &pAdapterNode );
1668 while ( NULL != pAdapterNode && VOS_STATUS_SUCCESS == status )
1669 {
1670 pAdapter = pAdapterNode->pAdapter;
1671 if ( (WLAN_HDD_INFRA_STATION != pAdapter->device_mode)
Madan Mohan Koyyalamudi802d7582012-10-31 14:19:40 -07001672 && (WLAN_HDD_SOFTAP != pAdapter->device_mode)
Jeff Johnson295189b2012-06-20 16:38:30 -07001673 && (WLAN_HDD_P2P_CLIENT != pAdapter->device_mode) )
1674
Madan Mohan Koyyalamudi802d7582012-10-31 14:19:40 -07001675 { // we skip this registration for modes other than STA, SAP and P2P client modes.
Jeff Johnson295189b2012-06-20 16:38:30 -07001676 status = hdd_get_next_adapter ( pHddCtx, pAdapterNode, &pNext );
1677 pAdapterNode = pNext;
1678 continue;
1679 }
Sourav Mohapatra47b07a02019-08-22 10:23:18 +05301680 dev_hold(pAdapter->dev);
madan mohan koyyalamudi459d6e72013-07-09 23:36:00 +05301681 /* Avoid multiple enter/exit BMPS in this while loop using
1682 * hdd_enter_bmps flag
1683 */
1684 if (FALSE == hdd_enter_bmps && (BMPS == pmcGetPmcState(pHddCtx->hHal)))
1685 {
1686 hdd_enter_bmps = TRUE;
Jeff Johnson295189b2012-06-20 16:38:30 -07001687
madan mohan koyyalamudi459d6e72013-07-09 23:36:00 +05301688 /* If device was already in BMPS, and dynamic DTIM is set,
1689 * exit(set the device to full power) and enter BMPS again
1690 * to reflect new DTIM value */
1691 wlan_hdd_enter_bmps(pAdapter, DRIVER_POWER_MODE_ACTIVE);
1692
1693 wlan_hdd_enter_bmps(pAdapter, DRIVER_POWER_MODE_AUTO);
1694
1695 pHddCtx->hdd_ignore_dtim_enabled = TRUE;
1696 }
Jeff Johnson295189b2012-06-20 16:38:30 -07001697#ifdef SUPPORT_EARLY_SUSPEND_STANDBY_DEEPSLEEP
1698 if (pHddCtx->cfg_ini->nEnableSuspend == WLAN_MAP_SUSPEND_TO_STANDBY)
1699 {
1700 //stop the interface before putting the chip to standby
Padma, Santhosh Kumar9dacb5c2014-12-17 19:22:56 +05301701 hddLog(VOS_TRACE_LEVEL_INFO, FL("Disabling queues"));
Jeff Johnson295189b2012-06-20 16:38:30 -07001702 netif_tx_disable(pAdapter->dev);
1703 netif_carrier_off(pAdapter->dev);
1704 }
Gopichand Nakkalaa2fe5b02013-06-06 16:32:28 +05301705 else if (pHddCtx->cfg_ini->nEnableSuspend ==
Jeff Johnson295189b2012-06-20 16:38:30 -07001706 WLAN_MAP_SUSPEND_TO_DEEP_SLEEP)
1707 {
1708 //Execute deep sleep procedure
1709 hdd_enter_deep_sleep(pHddCtx, pAdapter);
1710 }
1711#endif
Gopichand Nakkalad36ee622013-05-07 14:13:27 +05301712
Kapil Gupta2b44acb2016-12-30 16:49:51 +05301713 INIT_COMPLETION(pAdapter->wlan_suspend_comp_var);
Gopichand Nakkalad36ee622013-05-07 14:13:27 +05301714 /*Suspend notification sent down to driver*/
1715 hdd_conf_suspend_ind(pHddCtx, pAdapter);
Kapil Gupta2b44acb2016-12-30 16:49:51 +05301716 ret = wait_for_completion_interruptible_timeout(
1717 &pAdapter->wlan_suspend_comp_var,
1718 msecs_to_jiffies(WLAN_WAIT_TIME_FULL_PWR));
1719 if (0 >= ret)
1720 {
1721 hddLog(VOS_TRACE_LEVEL_ERROR, "%s:wait on suspend failed %ld",
1722 __func__, ret);
1723 }
Gopichand Nakkalaa2fe5b02013-06-06 16:32:28 +05301724 status = hdd_get_next_adapter ( pHddCtx, pAdapterNode, &pNext );
Sourav Mohapatra47b07a02019-08-22 10:23:18 +05301725 dev_put(pAdapter->dev);
Gopichand Nakkalaa2fe5b02013-06-06 16:32:28 +05301726 pAdapterNode = pNext;
1727 }
Gopichand Nakkalad36ee622013-05-07 14:13:27 +05301728
Jeff Johnson295189b2012-06-20 16:38:30 -07001729#ifdef SUPPORT_EARLY_SUSPEND_STANDBY_DEEPSLEEP
1730 if(pHddCtx->cfg_ini->nEnableSuspend == WLAN_MAP_SUSPEND_TO_STANDBY)
1731 {
1732 hdd_enter_standby(pHddCtx);
1733 }
1734#endif
Jeff Johnson295189b2012-06-20 16:38:30 -07001735
1736 return;
1737}
1738
Mukul Sharma75ee8aa2016-12-01 14:28:10 +05301739/**
1740 * @brief hdd_ReConfigSuspendDataClearedDuringRoaming() - Reconfigure the
1741 * suspend related data which was cleared during roaming in FWR.
1742 */
1743void hdd_ReConfigSuspendDataClearedDuringRoaming(hdd_context_t *pHddCtx)
1744
1745{
1746 VOS_STATUS vstatus = VOS_STATUS_E_FAILURE;
1747 hdd_adapter_t *pAdapter;
1748 hdd_adapter_list_node_t *pAdapterNode = NULL, *pNext = NULL;
1749
1750 ENTER();
1751
1752 spin_lock(&pHddCtx->filter_lock);
1753 check_and_set_suspend_resume_mcbc_filter(pHddCtx);
1754 spin_unlock(&pHddCtx->filter_lock);
1755
1756 hdd_conf_mcastbcast_filter(pHddCtx, TRUE);
1757 if(pHddCtx->hdd_mcastbcast_filter_set != TRUE)
1758 hddLog(VOS_TRACE_LEVEL_ERROR, FL("Not able to set mcast/bcast filter "));
1759
1760 vstatus = hdd_get_front_adapter ( pHddCtx, &pAdapterNode );
1761 //No need to configure GTK Offload from here because it might possible
1762 //cfg80211_set_rekey_data might not yet came, anyway GTK offload will
1763 //be handled as part of cfg80211_set_rekey_data processing.
1764 while ( NULL != pAdapterNode && VOS_STATUS_SUCCESS == vstatus )
1765 {
1766 pAdapter = pAdapterNode->pAdapter;
1767 if( pAdapter &&
1768 (( pAdapter->device_mode == WLAN_HDD_INFRA_STATION) ||
1769 (pAdapter->device_mode == WLAN_HDD_P2P_CLIENT)))
1770 {
1771 if (pHddCtx->cfg_ini->fhostArpOffload)
1772 {
1773 //Configure ARPOFFLOAD
1774 vstatus = hdd_conf_arp_offload(pAdapter, TRUE);
1775 if (!VOS_IS_STATUS_SUCCESS(vstatus))
1776 {
1777 hddLog(VOS_TRACE_LEVEL_INFO,
1778 FL("Failed to disable ARPOffload Feature %d"), vstatus);
1779 }
1780 }
1781#ifdef WLAN_NS_OFFLOAD
1782 //Configure NSOFFLOAD
1783 if (pHddCtx->cfg_ini->fhostNSOffload)
1784 {
1785 hdd_conf_ns_offload(pAdapter, TRUE);
1786 }
1787#endif
1788#ifdef WLAN_FEATURE_PACKET_FILTERING
1789 /* During suspend, configure MC Addr list filter to the firmware
1790 * function takes care of checking necessary conditions before
1791 * configuring.
1792 */
1793 wlan_hdd_set_mc_addr_list(pAdapter, TRUE);
1794#endif
1795 }
1796 vstatus = hdd_get_next_adapter ( pHddCtx, pAdapterNode, &pNext );
1797 pAdapterNode = pNext;
1798 }
1799 EXIT();
1800}
1801
Jeff Johnson295189b2012-06-20 16:38:30 -07001802static void hdd_PowerStateChangedCB
1803(
1804 v_PVOID_t callbackContext,
1805 tPmcState newState
1806)
1807{
1808 hdd_context_t *pHddCtx = callbackContext;
Mukul Sharmabb94ece2014-04-04 21:22:15 +05301809
Jeff Johnson295189b2012-06-20 16:38:30 -07001810 /* if the driver was not in BMPS during early suspend,
1811 * the dynamic DTIM is now updated at Riva */
1812 if ((newState == BMPS) && pHddCtx->hdd_wlan_suspended
Abhishek Singh0ea13232016-02-12 16:46:10 +05301813 && (pHddCtx->cfg_ini->enableDynamicDTIM ||
1814 pHddCtx->cfg_ini->enableModulatedDTIM)
Jeff Johnson295189b2012-06-20 16:38:30 -07001815 && (pHddCtx->hdd_ignore_dtim_enabled == FALSE))
1816 {
1817 pHddCtx->hdd_ignore_dtim_enabled = TRUE;
1818 }
1819 spin_lock(&pHddCtx->filter_lock);
Agarwal Ashish469b1e52014-01-17 09:13:10 +05301820 if ((newState == BMPS) && pHddCtx->hdd_wlan_suspended)
1821 {
Mukul Sharma75ee8aa2016-12-01 14:28:10 +05301822 check_and_set_suspend_resume_mcbc_filter(pHddCtx);
Jeff Johnson295189b2012-06-20 16:38:30 -07001823 spin_unlock(&pHddCtx->filter_lock);
1824 hdd_conf_mcastbcast_filter(pHddCtx, TRUE);
Jeff Johnson295189b2012-06-20 16:38:30 -07001825 if(pHddCtx->hdd_mcastbcast_filter_set != TRUE)
1826 hddLog(VOS_TRACE_LEVEL_ERROR, "%s: Not able to set mcast/bcast filter ", __func__);
Mukul Sharmabb94ece2014-04-04 21:22:15 +05301827 }
Amar Singhal49fdfd52013-08-13 13:25:12 -07001828 else
Mihir Shete793209f2014-01-06 11:01:12 +05301829 {
1830 /* Android framework can send resume request when the WCN chip is
1831 * in IMPS mode. When the chip exits IMPS mode the firmware will
1832 * restore all the registers to the state they were before the chip
1833 * entered IMPS and so our hardware filter settings confgured by the
1834 * resume request will be lost. So reconfigure the filters on detecting
1835 * a change in the power state of the WCN chip.
1836 */
Agarwal Ashish469b1e52014-01-17 09:13:10 +05301837 spin_unlock(&pHddCtx->filter_lock);
Mihir Shete793209f2014-01-06 11:01:12 +05301838 if (IMPS != newState)
1839 {
Agarwal Ashish469b1e52014-01-17 09:13:10 +05301840 spin_lock(&pHddCtx->filter_lock);
Mihir Shete793209f2014-01-06 11:01:12 +05301841 if (FALSE == pHddCtx->hdd_wlan_suspended)
1842 {
Agarwal Ashish469b1e52014-01-17 09:13:10 +05301843 spin_unlock(&pHddCtx->filter_lock);
Mihir Shete793209f2014-01-06 11:01:12 +05301844 hddLog(VOS_TRACE_LEVEL_INFO,
1845 "Not in IMPS/BMPS and suspended state");
1846 hdd_conf_mcastbcast_filter(pHddCtx, FALSE);
1847 }
Agarwal Ashish469b1e52014-01-17 09:13:10 +05301848 else
1849 {
1850 spin_unlock(&pHddCtx->filter_lock);
1851 }
Mihir Shete793209f2014-01-06 11:01:12 +05301852 }
Agarwal Ashish469b1e52014-01-17 09:13:10 +05301853 }
Jeff Johnson295189b2012-06-20 16:38:30 -07001854}
1855
Jeff Johnson295189b2012-06-20 16:38:30 -07001856void hdd_register_mcast_bcast_filter(hdd_context_t *pHddCtx)
1857{
1858 v_CONTEXT_t pVosContext;
1859 tHalHandle smeContext;
1860
1861 pVosContext = vos_get_global_context(VOS_MODULE_ID_SYS, NULL);
1862 if (NULL == pVosContext)
1863 {
Madan Mohan Koyyalamudi87054ba2012-11-02 13:24:12 -07001864 hddLog(LOGE, "%s: Invalid pContext", __func__);
Jeff Johnson295189b2012-06-20 16:38:30 -07001865 return;
1866 }
1867 smeContext = vos_get_context(VOS_MODULE_ID_SME, pVosContext);
1868 if (NULL == smeContext)
1869 {
Madan Mohan Koyyalamudi87054ba2012-11-02 13:24:12 -07001870 hddLog(LOGE, "%s: Invalid smeContext", __func__);
Jeff Johnson295189b2012-06-20 16:38:30 -07001871 return;
1872 }
1873
1874 spin_lock_init(&pHddCtx->filter_lock);
1875 if (WLAN_MAP_SUSPEND_TO_MCAST_BCAST_FILTER ==
1876 pHddCtx->cfg_ini->nEnableSuspend)
1877 {
1878 pmcRegisterDeviceStateUpdateInd(smeContext,
1879 hdd_PowerStateChangedCB, pHddCtx);
1880 }
1881}
1882
1883void hdd_unregister_mcast_bcast_filter(hdd_context_t *pHddCtx)
1884{
1885 v_CONTEXT_t pVosContext;
1886 tHalHandle smeContext;
1887
1888 pVosContext = vos_get_global_context(VOS_MODULE_ID_SYS, NULL);
1889 if (NULL == pVosContext)
1890 {
Madan Mohan Koyyalamudi87054ba2012-11-02 13:24:12 -07001891 hddLog(LOGE, "%s: Invalid pContext", __func__);
Jeff Johnson295189b2012-06-20 16:38:30 -07001892 return;
1893 }
1894 smeContext = vos_get_context(VOS_MODULE_ID_SME, pVosContext);
1895 if (NULL == smeContext)
1896 {
Madan Mohan Koyyalamudi87054ba2012-11-02 13:24:12 -07001897 hddLog(LOGE, "%s: Invalid smeContext", __func__);
Jeff Johnson295189b2012-06-20 16:38:30 -07001898 return;
1899 }
1900
1901 if (WLAN_MAP_SUSPEND_TO_MCAST_BCAST_FILTER ==
1902 pHddCtx->cfg_ini->nEnableSuspend)
1903 {
1904 pmcDeregisterDeviceStateUpdateInd(smeContext, hdd_PowerStateChangedCB);
1905 }
1906}
Gopichand Nakkalab03e8082013-05-30 18:09:25 +05301907
Gopichand Nakkala870cbae2013-03-15 21:16:09 +05301908#ifdef WLAN_FEATURE_GTK_OFFLOAD
Gopichand Nakkalab03e8082013-05-30 18:09:25 +05301909void hdd_conf_gtk_offload(hdd_adapter_t *pAdapter, v_BOOL_t fenable)
Gopichand Nakkala870cbae2013-03-15 21:16:09 +05301910{
1911 eHalStatus ret;
Gopichand Nakkalad36ee622013-05-07 14:13:27 +05301912 tSirGtkOffloadParams hddGtkOffloadReqParams;
Gopichand Nakkala870cbae2013-03-15 21:16:09 +05301913 hdd_station_ctx_t *pHddStaCtx = WLAN_HDD_GET_STATION_CTX_PTR(pAdapter);
1914
Gopichand Nakkalab03e8082013-05-30 18:09:25 +05301915 if(fenable)
Gopichand Nakkala870cbae2013-03-15 21:16:09 +05301916 {
Gopichand Nakkalab03e8082013-05-30 18:09:25 +05301917 if ((eConnectionState_Associated == pHddStaCtx->conn_info.connState) &&
1918 (GTK_OFFLOAD_ENABLE == pHddStaCtx->gtkOffloadReqParams.ulFlags ))
1919 {
1920 vos_mem_copy(&hddGtkOffloadReqParams,
1921 &pHddStaCtx->gtkOffloadReqParams,
1922 sizeof (tSirGtkOffloadParams));
Gopichand Nakkalad36ee622013-05-07 14:13:27 +05301923
Gopichand Nakkalab03e8082013-05-30 18:09:25 +05301924 ret = sme_SetGTKOffload(WLAN_HDD_GET_HAL_CTX(pAdapter),
1925 &hddGtkOffloadReqParams, pAdapter->sessionId);
1926 if (eHAL_STATUS_SUCCESS != ret)
1927 {
1928 VOS_TRACE(VOS_MODULE_ID_HDD, VOS_TRACE_LEVEL_ERROR,
1929 "%s: sme_SetGTKOffload failed, returned %d",
1930 __func__, ret);
1931 return;
1932 }
1933
1934 VOS_TRACE(VOS_MODULE_ID_HDD, VOS_TRACE_LEVEL_INFO,
1935 "%s: sme_SetGTKOffload successfull", __func__);
1936 }
1937
1938 }
1939 else
1940 {
1941 if ((eConnectionState_Associated == pHddStaCtx->conn_info.connState) &&
1942 (0 == memcmp(&pHddStaCtx->gtkOffloadReqParams.bssId,
1943 &pHddStaCtx->conn_info.bssId, WNI_CFG_BSSID_LEN)) &&
1944 (GTK_OFFLOAD_ENABLE == pHddStaCtx->gtkOffloadReqParams.ulFlags))
1945 {
1946
1947 /* Host driver has previously offloaded GTK rekey */
1948 ret = sme_GetGTKOffload(WLAN_HDD_GET_HAL_CTX(pAdapter),
Gopichand Nakkala870cbae2013-03-15 21:16:09 +05301949 wlan_hdd_cfg80211_update_replayCounterCallback,
1950 pAdapter, pAdapter->sessionId);
Gopichand Nakkalab03e8082013-05-30 18:09:25 +05301951 if (eHAL_STATUS_SUCCESS != ret)
Gopichand Nakkala870cbae2013-03-15 21:16:09 +05301952
Gopichand Nakkalab03e8082013-05-30 18:09:25 +05301953 {
1954 VOS_TRACE(VOS_MODULE_ID_HDD, VOS_TRACE_LEVEL_ERROR,
1955 "%s: sme_GetGTKOffload failed, returned %d",
1956 __func__, ret);
1957 return;
1958 }
1959 else
1960 {
1961 VOS_TRACE(VOS_MODULE_ID_HDD, VOS_TRACE_LEVEL_INFO,
1962 "%s: sme_GetGTKOffload successful",
1963 __func__);
1964
1965 /* Sending GTK offload dissable */
1966 memcpy(&hddGtkOffloadReqParams, &pHddStaCtx->gtkOffloadReqParams,
1967 sizeof (tSirGtkOffloadParams));
1968 hddGtkOffloadReqParams.ulFlags = GTK_OFFLOAD_DISABLE;
1969 ret = sme_SetGTKOffload(WLAN_HDD_GET_HAL_CTX(pAdapter),
Gopichand Nakkalad36ee622013-05-07 14:13:27 +05301970 &hddGtkOffloadReqParams, pAdapter->sessionId);
Gopichand Nakkalab03e8082013-05-30 18:09:25 +05301971 if (eHAL_STATUS_SUCCESS != ret)
1972 {
1973 VOS_TRACE(VOS_MODULE_ID_HDD, VOS_TRACE_LEVEL_ERROR,
1974 "%s: failed to dissable GTK offload, returned %d",
1975 __func__, ret);
1976 return;
1977 }
1978 VOS_TRACE(VOS_MODULE_ID_HDD, VOS_TRACE_LEVEL_INFO,
1979 "%s: successfully dissabled GTK offload request to HAL",
1980 __func__);
1981 }
Gopichand Nakkala870cbae2013-03-15 21:16:09 +05301982 }
Gopichand Nakkala870cbae2013-03-15 21:16:09 +05301983 }
Gopichand Nakkalab03e8082013-05-30 18:09:25 +05301984 return;
Gopichand Nakkala870cbae2013-03-15 21:16:09 +05301985}
1986#endif /*WLAN_FEATURE_GTK_OFFLOAD*/
Jeff Johnson295189b2012-06-20 16:38:30 -07001987
Sameer Thalappil45931fb2013-02-01 11:18:05 -08001988void hdd_resume_wlan(void)
Jeff Johnson295189b2012-06-20 16:38:30 -07001989{
1990 hdd_context_t *pHddCtx = NULL;
1991 hdd_adapter_t *pAdapter = NULL;
1992 hdd_adapter_list_node_t *pAdapterNode = NULL, *pNext = NULL;
1993 VOS_STATUS status;
1994 v_CONTEXT_t pVosContext = NULL;
Mukul Sharma3da767d2017-06-29 18:25:39 +05301995 tPmcState pmc_state;
1996 hdd_adapter_t *first_adapter = NULL;
Jeff Johnsonbc676b42013-02-14 16:04:08 -08001997
Jeff Johnson295189b2012-06-20 16:38:30 -07001998 hddLog(VOS_TRACE_LEVEL_INFO, "%s: WLAN being resumed by Android OS",__func__);
1999
2000 //Get the global VOSS context.
2001 pVosContext = vos_get_global_context(VOS_MODULE_ID_SYS, NULL);
2002 if(!pVosContext) {
2003 hddLog(VOS_TRACE_LEVEL_FATAL,"%s: Global VOS context is Null", __func__);
2004 return;
2005 }
2006
2007 //Get the HDD context.
2008 pHddCtx = (hdd_context_t *)vos_get_context(VOS_MODULE_ID_HDD, pVosContext );
2009
2010 if(!pHddCtx) {
2011 hddLog(VOS_TRACE_LEVEL_FATAL,"%s: HDD context is Null",__func__);
2012 return;
2013 }
2014
Agarwal Ashish971c2882013-10-30 20:11:12 +05302015 if (pHddCtx->isLogpInProgress)
2016 {
Jeff Johnson295189b2012-06-20 16:38:30 -07002017 hddLog(VOS_TRACE_LEVEL_INFO,
2018 "%s: Ignore resume wlan, LOGP in progress!", __func__);
2019 return;
2020 }
2021
Padma, Santhosh Kumar2ee1ad02015-01-12 16:05:47 +05302022 if (!pHddCtx->hdd_wlan_suspended)
2023 {
Ratheesh S P36dbc932015-08-07 14:28:57 +05302024 hddLog(VOS_TRACE_LEVEL_INFO,
Padma, Santhosh Kumar2ee1ad02015-01-12 16:05:47 +05302025 "%s: Ignore resume wlan, Already resumed!", __func__);
2026 return;
2027 }
2028
Jeff Johnson295189b2012-06-20 16:38:30 -07002029 pHddCtx->hdd_wlan_suspended = FALSE;
Abhishek Singh37471cd2016-01-05 17:09:57 +05302030 hdd_wlan_suspend_resume_event(HDD_WLAN_EARLY_RESUME);
Mukul Sharma3da767d2017-06-29 18:25:39 +05302031
2032 /* Get first valid adapter for disable/enable bmps purpose */
2033 status = hdd_get_front_adapter ( pHddCtx, &pAdapterNode );
2034 while ( NULL != pAdapterNode && VOS_STATUS_SUCCESS == status )
2035 {
2036 first_adapter = pAdapterNode->pAdapter;
2037 if (first_adapter != NULL)
2038 break;
2039 status = hdd_get_next_adapter ( pHddCtx, pAdapterNode, &pNext );
2040 pAdapterNode = pNext;
2041 }
2042 pmc_state = pmcGetPmcState(pHddCtx->hHal);
2043 if (BMPS == pmc_state && first_adapter)
2044 {
2045 /* put the device into full power */
2046 hddLog(VOS_TRACE_LEVEL_INFO,
2047 "%s: Disaling bmps during resume", __func__);
2048 wlan_hdd_enter_bmps(first_adapter, DRIVER_POWER_MODE_ACTIVE);
2049 }
2050
Jeff Johnson295189b2012-06-20 16:38:30 -07002051 /*loop through all adapters. Concurrency */
2052 status = hdd_get_front_adapter ( pHddCtx, &pAdapterNode );
2053
2054 while ( NULL != pAdapterNode && VOS_STATUS_SUCCESS == status )
2055 {
2056 pAdapter = pAdapterNode->pAdapter;
2057 if ( (WLAN_HDD_INFRA_STATION != pAdapter->device_mode)
Madan Mohan Koyyalamudi802d7582012-10-31 14:19:40 -07002058 && (WLAN_HDD_SOFTAP != pAdapter->device_mode)
Jeff Johnson295189b2012-06-20 16:38:30 -07002059 && (WLAN_HDD_P2P_CLIENT != pAdapter->device_mode) )
Madan Mohan Koyyalamudi802d7582012-10-31 14:19:40 -07002060 { // we skip this registration for modes other than STA, SAP and P2P client modes.
Jeff Johnson295189b2012-06-20 16:38:30 -07002061 status = hdd_get_next_adapter ( pHddCtx, pAdapterNode, &pNext );
2062 pAdapterNode = pNext;
2063 continue;
2064 }
Gopichand Nakkala870cbae2013-03-15 21:16:09 +05302065
Gopichand Nakkala870cbae2013-03-15 21:16:09 +05302066
Jeff Johnson295189b2012-06-20 16:38:30 -07002067#ifdef SUPPORT_EARLY_SUSPEND_STANDBY_DEEPSLEEP
2068 if(pHddCtx->hdd_ps_state == eHDD_SUSPEND_DEEP_SLEEP)
2069 {
2070 hddLog(VOS_TRACE_LEVEL_INFO, "%s: WLAN being resumed from deep sleep",__func__);
2071 hdd_exit_deep_sleep(pAdapter);
2072 }
2073#endif
2074
2075 if(pHddCtx->hdd_ignore_dtim_enabled == TRUE)
2076 {
2077 /*Switch back to DTIM 1*/
2078 tSirSetPowerParamsReq powerRequest = { 0 };
2079
2080 powerRequest.uIgnoreDTIM = pHddCtx->hdd_actual_ignore_DTIM_value;
2081 powerRequest.uListenInterval = pHddCtx->hdd_actual_LI_value;
Yue Mac24062f2013-05-13 17:01:29 -07002082 powerRequest.uMaxLIModulatedDTIM = pHddCtx->cfg_ini->fMaxLIModulatedDTIM;
Jeff Johnson295189b2012-06-20 16:38:30 -07002083
2084 /*Disabled ModulatedDTIM if enabled on suspend*/
2085 if(pHddCtx->cfg_ini->enableModulatedDTIM)
2086 powerRequest.uDTIMPeriod = 0;
2087
2088 /* Update ignoreDTIM and ListedInterval in CFG with default values */
2089 ccmCfgSetInt(pHddCtx->hHal, WNI_CFG_IGNORE_DTIM, powerRequest.uIgnoreDTIM,
2090 NULL, eANI_BOOLEAN_FALSE);
2091 ccmCfgSetInt(pHddCtx->hHal, WNI_CFG_LISTEN_INTERVAL, powerRequest.uListenInterval,
2092 NULL, eANI_BOOLEAN_FALSE);
2093
2094 VOS_TRACE(VOS_MODULE_ID_HDD, VOS_TRACE_LEVEL_INFO,
Arif Hussain6d2a3322013-11-17 19:50:10 -08002095 "Switch to DTIM%d",powerRequest.uListenInterval);
Tushnim Bhattacharyya3a37def2013-02-24 11:11:15 -08002096 sme_SetPowerParams( WLAN_HDD_GET_HAL_CTX(pAdapter), &powerRequest, FALSE);
Jeff Johnson295189b2012-06-20 16:38:30 -07002097
Mukul Sharma3da767d2017-06-29 18:25:39 +05302098 if (BMPS == pmc_state)
Madan Mohan Koyyalamudi69b34182013-01-16 08:51:40 +05302099 {
Madan Mohan Koyyalamudi69b34182013-01-16 08:51:40 +05302100 pHddCtx->hdd_ignore_dtim_enabled = FALSE;
2101 }
Jeff Johnson295189b2012-06-20 16:38:30 -07002102 }
2103
Gopichand Nakkala0f276812013-02-24 14:45:51 +05302104 hdd_conf_resume_ind(pAdapter);
Jeff Johnson295189b2012-06-20 16:38:30 -07002105 status = hdd_get_next_adapter ( pHddCtx, pAdapterNode, &pNext );
2106 pAdapterNode = pNext;
2107 }
2108
Mukul Sharma3da767d2017-06-29 18:25:39 +05302109 if (BMPS == pmc_state && first_adapter)
2110 {
2111 /* put the device into full power */
2112 hddLog(VOS_TRACE_LEVEL_INFO,
2113 "%s: Enable bmps during resume", __func__);
2114 /* put the device back into BMPS */
2115 wlan_hdd_enter_bmps(first_adapter, DRIVER_POWER_MODE_AUTO);
2116 }
2117
Jeff Johnson295189b2012-06-20 16:38:30 -07002118#ifdef SUPPORT_EARLY_SUSPEND_STANDBY_DEEPSLEEP
2119 if(pHddCtx->hdd_ps_state == eHDD_SUSPEND_STANDBY)
2120 {
2121 hdd_exit_standby(pHddCtx);
2122 }
2123#endif
2124
Jeff Johnson295189b2012-06-20 16:38:30 -07002125 return;
2126}
2127
Jeff Johnson295189b2012-06-20 16:38:30 -07002128VOS_STATUS hdd_wlan_reset_initialization(void)
2129{
Jeff Johnson295189b2012-06-20 16:38:30 -07002130 v_CONTEXT_t pVosContext = NULL;
2131
2132 hddLog(VOS_TRACE_LEVEL_FATAL, "%s: WLAN being reset",__func__);
2133
2134 //Get the global VOSS context.
2135 pVosContext = vos_get_global_context(VOS_MODULE_ID_SYS, NULL);
2136 if(!pVosContext)
2137 {
2138 hddLog(VOS_TRACE_LEVEL_FATAL,"%s: Global VOS context is Null", __func__);
2139 return VOS_STATUS_E_FAILURE;
2140 }
2141
2142 hddLog(VOS_TRACE_LEVEL_FATAL, "%s: Preventing the phone from going to suspend",__func__);
2143
2144 // Prevent the phone from going to sleep
Sushant Kaushik83392fa2015-05-05 17:44:40 +05302145 hdd_prevent_suspend(WIFI_POWER_EVENT_WAKELOCK_DRIVER_REINIT);
Jeff Johnson295189b2012-06-20 16:38:30 -07002146
Jeff Johnson295189b2012-06-20 16:38:30 -07002147 return VOS_STATUS_SUCCESS;
2148}
2149
2150
Sameer Thalappil45931fb2013-02-01 11:18:05 -08002151/*
2152 * Based on the ioctl command recieved by HDD, put WLAN driver
2153 * into the quiet mode. This is the same as the early suspend
2154 * notification that driver used to listen
2155 */
2156void hdd_set_wlan_suspend_mode(bool suspend)
Jeff Johnson295189b2012-06-20 16:38:30 -07002157{
Sandeep Puligilla308288f2014-06-05 22:21:46 +05302158 vos_ssr_protect(__func__);
Sameer Thalappil45931fb2013-02-01 11:18:05 -08002159 if (suspend)
2160 hdd_suspend_wlan();
2161 else
2162 hdd_resume_wlan();
Sandeep Puligilla308288f2014-06-05 22:21:46 +05302163 vos_ssr_unprotect(__func__);
Jeff Johnson295189b2012-06-20 16:38:30 -07002164}
2165
Madan Mohan Koyyalamudib0e70642012-10-11 12:20:22 -07002166static void hdd_ssr_timer_init(void)
2167{
2168 init_timer(&ssr_timer);
2169}
Sameer Thalappil45931fb2013-02-01 11:18:05 -08002170
Madan Mohan Koyyalamudib0e70642012-10-11 12:20:22 -07002171static void hdd_ssr_timer_del(void)
2172{
2173 del_timer(&ssr_timer);
2174 ssr_timer_started = false;
2175}
Sameer Thalappil45931fb2013-02-01 11:18:05 -08002176
Madan Mohan Koyyalamudib0e70642012-10-11 12:20:22 -07002177static void hdd_ssr_timer_cb(unsigned long data)
2178{
2179 hddLog(VOS_TRACE_LEVEL_FATAL, "%s: HDD SSR timer expired", __func__);
Sameer Thalappile5637f42013-08-07 15:46:55 -07002180
2181#ifdef WCN_PRONTO
2182 if (wcnss_hardware_type() == WCNSS_PRONTO_HW)
2183 wcnss_pronto_log_debug_regs();
2184#endif
2185
Madan Mohan Koyyalamudib0e70642012-10-11 12:20:22 -07002186 VOS_BUG(0);
2187}
Sameer Thalappil45931fb2013-02-01 11:18:05 -08002188
Madan Mohan Koyyalamudib0e70642012-10-11 12:20:22 -07002189static void hdd_ssr_timer_start(int msec)
2190{
2191 if(ssr_timer_started)
2192 {
2193 hddLog(VOS_TRACE_LEVEL_FATAL, "%s: trying to start SSR timer when it's running"
2194 ,__func__);
2195 }
2196 ssr_timer.expires = jiffies + msecs_to_jiffies(msec);
2197 ssr_timer.function = hdd_ssr_timer_cb;
2198 add_timer(&ssr_timer);
2199 ssr_timer_started = true;
2200}
Sameer Thalappil45931fb2013-02-01 11:18:05 -08002201
Sen, Devendrade5cfe92017-01-31 18:51:15 +05302202#ifdef FEATURE_WLAN_DIAG_SUPPORT
2203/**
2204 * hdd_wlan_ssr_shutdown_event()- send ssr shutdown state
2205 *
2206 * This Function send send ssr shutdown state diag event
2207 *
2208 * Return: void.
2209 */
2210static void hdd_wlan_ssr_shutdown_event(void)
2211{
2212 WLAN_VOS_DIAG_EVENT_DEF(ssr_shutdown,
2213 struct host_event_wlan_ssr_shutdown);
2214 vos_mem_zero(&ssr_shutdown, sizeof(ssr_shutdown));
2215 ssr_shutdown.status = SSR_SUB_SYSTEM_SHUTDOWN;
2216 WLAN_VOS_DIAG_EVENT_REPORT(&ssr_shutdown,
2217 EVENT_WLAN_SSR_SHUTDOWN_SUBSYSTEM);
2218}
2219#else
2220static inline void hdd_wlan_ssr_shutdown_event(void)
2221{
2222
2223};
2224#endif
2225
Anurag Chouhanf0d0ba12018-02-09 15:13:43 +05302226/**
2227 * hdd_send_hang_reason() - Send hang reason to the userspace
2228 *
2229 * Return: None
2230 */
2231static void hdd_send_hang_reason(hdd_context_t *hdd_ctx)
2232{
2233 unsigned int reason = 0;
2234
2235 if(!hdd_ctx) {
2236 hddLog(VOS_TRACE_LEVEL_FATAL,"%s: HDD context is Null",__func__);
2237 return;
2238 }
2239
2240 vos_get_recovery_reason(&reason);
2241 vos_reset_recovery_reason();
2242 wlan_hdd_send_hang_reason_event(hdd_ctx, reason);
2243}
2244
Jeff Johnson295189b2012-06-20 16:38:30 -07002245/* the HDD interface to WLAN driver shutdown,
2246 * the primary shutdown function in SSR
2247 */
2248VOS_STATUS hdd_wlan_shutdown(void)
2249{
2250 VOS_STATUS vosStatus;
2251 v_CONTEXT_t pVosContext = NULL;
2252 hdd_context_t *pHddCtx = NULL;
2253 pVosSchedContext vosSchedContext = NULL;
2254
2255 hddLog(VOS_TRACE_LEVEL_FATAL, "%s: WLAN driver shutting down! ",__func__);
2256
Madan Mohan Koyyalamudib0e70642012-10-11 12:20:22 -07002257 /* if re-init never happens, then do SSR1 */
2258 hdd_ssr_timer_init();
2259 hdd_ssr_timer_start(HDD_SSR_BRING_UP_TIME);
2260
Jeff Johnson295189b2012-06-20 16:38:30 -07002261 /* Get the global VOSS context. */
2262 pVosContext = vos_get_global_context(VOS_MODULE_ID_SYS, NULL);
2263 if(!pVosContext) {
2264 hddLog(VOS_TRACE_LEVEL_FATAL,"%s: Global VOS context is Null", __func__);
2265 return VOS_STATUS_E_FAILURE;
2266 }
2267 /* Get the HDD context. */
2268 pHddCtx = (hdd_context_t*)vos_get_context(VOS_MODULE_ID_HDD, pVosContext);
2269 if(!pHddCtx) {
2270 hddLog(VOS_TRACE_LEVEL_FATAL,"%s: HDD context is Null",__func__);
2271 return VOS_STATUS_E_FAILURE;
2272 }
c_hpothud662a352013-12-26 15:09:12 +05302273
Abhishek Singh8a3e4dc2017-01-02 10:39:18 +05302274 vos_set_snoc_high_freq_voting(false);
c_hpothud662a352013-12-26 15:09:12 +05302275 //Stop the traffic monitor timer
Mahesh A Saptasagard461e432016-07-20 15:01:40 +05302276 if ((pHddCtx->cfg_ini->dynSplitscan)&& (VOS_TIMER_STATE_RUNNING ==
2277 vos_timer_getCurrentState(&pHddCtx->tx_rx_trafficTmr)))
c_hpothud662a352013-12-26 15:09:12 +05302278 {
2279 vos_timer_stop(&pHddCtx->tx_rx_trafficTmr);
2280 }
Padma, Santhosh Kumar9cd38332015-11-17 12:18:10 +05302281 vos_flush_delayed_work(&pHddCtx->spoof_mac_addr_work);
Abhishek Singh78c691f2017-11-30 13:48:44 +05302282 vos_flush_delayed_work(&pHddCtx->ecsa_chan_change_work);
Kapil Gupta137ef892016-12-13 19:38:00 +05302283 vos_flush_work(&pHddCtx->sap_start_work);
Jeff Johnson295189b2012-06-20 16:38:30 -07002284 hdd_reset_all_adapters(pHddCtx);
Bhargav Shahd0715912015-10-01 18:17:37 +05302285
2286 /* set default value of Tcp delack and stop timer */
2287 hdd_set_default_stop_delack_timer(pHddCtx);
2288
Bala Venkateshbd197a32018-06-06 13:06:10 +05302289 if (VOS_TIMER_STATE_RUNNING ==
2290 vos_timer_getCurrentState(&pHddCtx->tdls_source_timer))
2291 vos_timer_stop(&pHddCtx->tdls_source_timer);
2292
Jeff Johnson295189b2012-06-20 16:38:30 -07002293 /* DeRegister with platform driver as client for Suspend/Resume */
2294 vosStatus = hddDeregisterPmOps(pHddCtx);
2295 if ( !VOS_IS_STATUS_SUCCESS( vosStatus ) )
2296 {
2297 hddLog(VOS_TRACE_LEVEL_FATAL,"%s: hddDeregisterPmOps failed",__func__);
2298 }
2299
2300 vosStatus = hddDevTmUnregisterNotifyCallback(pHddCtx);
2301 if ( !VOS_IS_STATUS_SUCCESS( vosStatus ) )
2302 {
2303 hddLog(VOS_TRACE_LEVEL_FATAL,"%s: hddDevTmUnregisterNotifyCallback failed",__func__);
2304 }
2305
2306 /* Disable IMPS/BMPS as we do not want the device to enter any power
2307 * save mode on its own during reset sequence
2308 */
2309 sme_DisablePowerSave(pHddCtx->hHal, ePMC_IDLE_MODE_POWER_SAVE);
2310 sme_DisablePowerSave(pHddCtx->hHal, ePMC_BEACON_MODE_POWER_SAVE);
2311 sme_DisablePowerSave(pHddCtx->hHal, ePMC_UAPSD_MODE_POWER_SAVE);
2312
2313 vosSchedContext = get_vos_sched_ctxt();
2314
2315 /* Wakeup all driver threads */
2316 if(TRUE == pHddCtx->isMcThreadSuspended){
2317 complete(&vosSchedContext->ResumeMcEvent);
2318 pHddCtx->isMcThreadSuspended= FALSE;
2319 }
2320 if(TRUE == pHddCtx->isTxThreadSuspended){
2321 complete(&vosSchedContext->ResumeTxEvent);
2322 pHddCtx->isTxThreadSuspended= FALSE;
2323 }
2324 if(TRUE == pHddCtx->isRxThreadSuspended){
2325 complete(&vosSchedContext->ResumeRxEvent);
2326 pHddCtx->isRxThreadSuspended= FALSE;
2327 }
2328 /* Reset the Suspend Variable */
2329 pHddCtx->isWlanSuspended = FALSE;
2330
2331 /* Stop all the threads; we do not want any messages to be a processed,
2332 * any more and the best way to ensure that is to terminate the threads
2333 * gracefully.
2334 */
2335 /* Wait for MC to exit */
2336 hddLog(VOS_TRACE_LEVEL_FATAL, "%s: Shutting down MC thread",__func__);
Mahesh A Saptasagar8b42b272016-02-24 16:22:45 +05302337 set_bit(MC_SHUTDOWN_EVENT, &vosSchedContext->mcEventFlag);
2338 set_bit(MC_POST_EVENT, &vosSchedContext->mcEventFlag);
Jeff Johnson295189b2012-06-20 16:38:30 -07002339 wake_up_interruptible(&vosSchedContext->mcWaitQueue);
Mihir Sheteb5425f72013-12-19 09:06:13 +05302340 wait_for_completion(&vosSchedContext->McShutdown);
Bala Venkateshbd197a32018-06-06 13:06:10 +05302341 vosSchedContext->McThread = NULL;
Jeff Johnson295189b2012-06-20 16:38:30 -07002342
2343 /* Wait for TX to exit */
2344 hddLog(VOS_TRACE_LEVEL_FATAL, "%s: Shutting down TX thread",__func__);
Mahesh A Saptasagar8b42b272016-02-24 16:22:45 +05302345 set_bit(TX_SHUTDOWN_EVENT, &vosSchedContext->txEventFlag);
2346 set_bit(TX_POST_EVENT, &vosSchedContext->txEventFlag);
Jeff Johnson295189b2012-06-20 16:38:30 -07002347 wake_up_interruptible(&vosSchedContext->txWaitQueue);
Mihir Sheteb5425f72013-12-19 09:06:13 +05302348 wait_for_completion(&vosSchedContext->TxShutdown);
Bala Venkateshbd197a32018-06-06 13:06:10 +05302349 vosSchedContext->TxThread = NULL;
Jeff Johnson295189b2012-06-20 16:38:30 -07002350
2351 /* Wait for RX to exit */
2352 hddLog(VOS_TRACE_LEVEL_FATAL, "%s: Shutting down RX thread",__func__);
Mahesh A Saptasagar8b42b272016-02-24 16:22:45 +05302353 set_bit(RX_SHUTDOWN_EVENT, &vosSchedContext->rxEventFlag);
2354 set_bit(RX_POST_EVENT, &vosSchedContext->rxEventFlag);
Jeff Johnson295189b2012-06-20 16:38:30 -07002355 wake_up_interruptible(&vosSchedContext->rxWaitQueue);
Mihir Sheteb5425f72013-12-19 09:06:13 +05302356 wait_for_completion(&vosSchedContext->RxShutdown);
Bala Venkateshbd197a32018-06-06 13:06:10 +05302357 vosSchedContext->RxThread = NULL;
Jeff Johnson295189b2012-06-20 16:38:30 -07002358
2359#ifdef WLAN_BTAMP_FEATURE
2360 vosStatus = WLANBAP_Stop(pVosContext);
2361 if (!VOS_IS_STATUS_SUCCESS(vosStatus))
2362 {
2363 VOS_TRACE( VOS_MODULE_ID_VOSS, VOS_TRACE_LEVEL_ERROR,
2364 "%s: Failed to stop BAP",__func__);
2365 }
2366#endif //WLAN_BTAMP_FEATURE
2367 vosStatus = vos_wda_shutdown(pVosContext);
c_hpothuffdb5272013-10-02 16:42:35 +05302368 if (!VOS_IS_STATUS_SUCCESS(vosStatus))
2369 {
2370 VOS_TRACE( VOS_MODULE_ID_VOSS, VOS_TRACE_LEVEL_ERROR,
2371 "%s: Failed to stop wda %d", __func__, vosStatus);
2372 VOS_ASSERT(0);
2373 }
Jeff Johnson295189b2012-06-20 16:38:30 -07002374
2375 hddLog(VOS_TRACE_LEVEL_FATAL, "%s: Doing SME STOP",__func__);
2376 /* Stop SME - Cannot invoke vos_stop as vos_stop relies
2377 * on threads being running to process the SYS Stop
2378 */
Kiet Lama72a2322013-11-15 11:18:11 +05302379 vosStatus = sme_Stop(pHddCtx->hHal, HAL_STOP_TYPE_SYS_RESET);
c_hpothuffdb5272013-10-02 16:42:35 +05302380 if (!VOS_IS_STATUS_SUCCESS(vosStatus))
2381 {
2382 VOS_TRACE( VOS_MODULE_ID_VOSS, VOS_TRACE_LEVEL_ERROR,
2383 "%s: Failed to stop sme %d", __func__, vosStatus);
2384 VOS_ASSERT(0);
2385 }
Jeff Johnson295189b2012-06-20 16:38:30 -07002386
2387 hddLog(VOS_TRACE_LEVEL_FATAL, "%s: Doing MAC STOP",__func__);
2388 /* Stop MAC (PE and HAL) */
2389 vosStatus = macStop(pHddCtx->hHal, HAL_STOP_TYPE_SYS_RESET);
c_hpothuffdb5272013-10-02 16:42:35 +05302390 if (!VOS_IS_STATUS_SUCCESS(vosStatus))
2391 {
2392 VOS_TRACE( VOS_MODULE_ID_VOSS, VOS_TRACE_LEVEL_ERROR,
2393 "%s: Failed to stop mac %d", __func__, vosStatus);
2394 VOS_ASSERT(0);
2395 }
Jeff Johnson295189b2012-06-20 16:38:30 -07002396
2397 hddLog(VOS_TRACE_LEVEL_FATAL, "%s: Doing TL STOP",__func__);
2398 /* Stop TL */
2399 vosStatus = WLANTL_Stop(pVosContext);
c_hpothuffdb5272013-10-02 16:42:35 +05302400 if (!VOS_IS_STATUS_SUCCESS(vosStatus))
2401 {
2402 VOS_TRACE( VOS_MODULE_ID_VOSS, VOS_TRACE_LEVEL_ERROR,
2403 "%s: Failed to stop TL %d", __func__, vosStatus);
2404 VOS_ASSERT(0);
2405 }
Jeff Johnson295189b2012-06-20 16:38:30 -07002406
Jeff Johnson295189b2012-06-20 16:38:30 -07002407 hdd_unregister_mcast_bcast_filter(pHddCtx);
Jeff Johnson295189b2012-06-20 16:38:30 -07002408 hddLog(VOS_TRACE_LEVEL_INFO, "%s: Flush Queues",__func__);
2409 /* Clean up message queues of TX and MC thread */
2410 vos_sched_flush_mc_mqs(vosSchedContext);
2411 vos_sched_flush_tx_mqs(vosSchedContext);
2412 vos_sched_flush_rx_mqs(vosSchedContext);
Siddharth Bhal7bd19932015-03-03 16:54:36 +05302413#ifdef WLAN_LOGGING_SOCK_SVC_ENABLE
2414 wlan_logging_flush_pkt_queue();
c_manjeecfd1efb2015-09-25 19:32:34 +05302415 /*Free fw dump mem in case of SSR/Shutdown */
2416 wlan_set_fwr_mem_dump_state(FW_MEM_DUMP_IDLE);
2417 wlan_free_fwr_mem_dump_buffer();
Siddharth Bhal7bd19932015-03-03 16:54:36 +05302418#endif
Jeff Johnson295189b2012-06-20 16:38:30 -07002419
2420 /* Deinit all the TX and MC queues */
2421 vos_sched_deinit_mqs(vosSchedContext);
2422 hddLog(VOS_TRACE_LEVEL_INFO, "%s: Doing VOS Shutdown",__func__);
2423
2424 /* shutdown VOSS */
2425 vos_shutdown(pVosContext);
Gopichand Nakkala05ab1322013-02-15 11:28:38 +05302426
2427 /*mac context has already been released in mac_close call
2428 so setting it to NULL in hdd context*/
2429 pHddCtx->hHal = (tHalHandle)NULL;
2430
Jeff Johnson295189b2012-06-20 16:38:30 -07002431 if (free_riva_power_on_lock("wlan"))
2432 {
2433 hddLog(VOS_TRACE_LEVEL_ERROR, "%s: failed to free power on lock",
2434 __func__);
2435 }
Sen, Devendrade5cfe92017-01-31 18:51:15 +05302436 hdd_wlan_ssr_shutdown_event();
Anurag Chouhanf0d0ba12018-02-09 15:13:43 +05302437 hdd_send_hang_reason(pHddCtx);
Jeff Johnson295189b2012-06-20 16:38:30 -07002438 hddLog(VOS_TRACE_LEVEL_FATAL, "%s: WLAN driver shutdown complete"
2439 ,__func__);
2440 return VOS_STATUS_SUCCESS;
2441}
2442
Anurag Chouhanb2951ae2017-03-12 13:41:35 +05302443int hdd_dhcp_mdns_offload(hdd_adapter_t *adapter)
Anurag Chouhan7e2a9912017-02-09 20:21:40 +05302444{
2445 hdd_config_t *config;
2446 int status = VOS_STATUS_SUCCESS;
2447 hdd_context_t *hdd_ctx = WLAN_HDD_GET_CTX(adapter);
2448
2449 config = hdd_ctx->cfg_ini;
2450 if (NULL == config) {
2451 VOS_TRACE(VOS_MODULE_ID_HDD, VOS_TRACE_LEVEL_ERROR,
2452 ("cfg_ini is NULL!!"));
2453 return -EINVAL;
2454 }
2455#ifdef DHCP_SERVER_OFFLOAD
2456 /* set dhcp server offload */
2457 if (config->enable_dhcp_srv_offload &&
2458 sme_IsFeatureSupportedByFW(SAP_OFFLOADS)) {
Anurag Chouhanb2951ae2017-03-12 13:41:35 +05302459 vos_event_reset(&adapter->dhcp_status.vos_event);
Anurag Chouhan638f5e22017-03-06 12:28:43 +05302460 status = wlan_hdd_set_dhcp_server_offload(adapter, true);
Anurag Chouhan7e2a9912017-02-09 20:21:40 +05302461 if (!VOS_IS_STATUS_SUCCESS(status))
2462 {
2463 VOS_TRACE(VOS_MODULE_ID_HDD, VOS_TRACE_LEVEL_ERROR,
2464 ("HDD DHCP Server Offload Failed!!"));
2465 return -EINVAL;
2466 }
Anurag Chouhan7e2a9912017-02-09 20:21:40 +05302467 status = vos_wait_single_event(&adapter->dhcp_status.vos_event, 2000);
2468 if (!VOS_IS_STATUS_SUCCESS(status) ||
2469 adapter->dhcp_status.dhcp_offload_status)
2470 {
2471 VOS_TRACE(VOS_MODULE_ID_HDD, VOS_TRACE_LEVEL_ERROR,
2472 ("ERROR: DHCP HDD vos wait for single_event failed!! %d"),
2473 adapter->dhcp_status.dhcp_offload_status);
2474 return -EINVAL;
2475 }
2476#ifdef MDNS_OFFLOAD
2477 if (config->enable_mdns_offload) {
Anurag Chouhanb2951ae2017-03-12 13:41:35 +05302478 vos_event_reset(&adapter->mdns_status.vos_event);
Anurag Chouhan7e2a9912017-02-09 20:21:40 +05302479 status = wlan_hdd_set_mdns_offload(adapter);
2480 if (VOS_IS_STATUS_SUCCESS(status))
2481 {
2482 VOS_TRACE(VOS_MODULE_ID_HDD, VOS_TRACE_LEVEL_ERROR,
2483 ("HDD MDNS Server Offload Failed!!"));
2484 return -EINVAL;
2485 }
Anurag Chouhan7e2a9912017-02-09 20:21:40 +05302486 status = vos_wait_single_event(&adapter->
2487 mdns_status.vos_event, 2000);
2488 if (!VOS_IS_STATUS_SUCCESS(status) ||
2489 adapter->mdns_status.mdns_enable_status ||
2490 adapter->mdns_status.mdns_fqdn_status ||
2491 adapter->mdns_status.mdns_resp_status)
2492 {
2493 VOS_TRACE(VOS_MODULE_ID_HDD, VOS_TRACE_LEVEL_ERROR,
2494 ("MDNS HDD vos wait for single_event failed!! enable %d fqdn %d resp %d"),
2495 adapter->mdns_status.mdns_enable_status,
2496 adapter->mdns_status.mdns_fqdn_status,
2497 adapter->mdns_status.mdns_resp_status);
2498 return -EINVAL;
2499 }
2500 }
2501#endif /* MDNS_OFFLOAD */
2502 } else {
2503 VOS_TRACE(VOS_MODULE_ID_HDD, VOS_TRACE_LEVEL_INFO,
2504 ("DHCP Disabled ini %d, FW %d"),
2505 config->enable_dhcp_srv_offload,
2506 sme_IsFeatureSupportedByFW(SAP_OFFLOADS));
2507 }
2508#endif /* DHCP_SERVER_OFFLOAD */
2509 return status;
2510}
2511
Hanumanth Reddy Pothulad864f312017-01-18 16:16:08 +05302512/**
2513 * hdd_ssr_restart_sap() - restart sap on SSR
2514 * @hdd_ctx: hdd context
2515 *
2516 * Return: nothing
2517 */
2518static void hdd_ssr_restart_sap(hdd_context_t *hdd_ctx)
2519{
2520 VOS_STATUS status;
2521 hdd_adapter_list_node_t *adapter_node = NULL, *next = NULL;
2522 hdd_adapter_t *adapter;
Anurag Chouhanb2951ae2017-03-12 13:41:35 +05302523 hdd_hostapd_state_t *hostapd_state;
Jeff Johnson295189b2012-06-20 16:38:30 -07002524
Hanumanth Reddy Pothulad864f312017-01-18 16:16:08 +05302525 ENTER();
2526
2527 status = hdd_get_front_adapter (hdd_ctx, &adapter_node);
2528 while (NULL != adapter_node && VOS_STATUS_SUCCESS == status) {
2529 adapter = adapter_node->pAdapter;
2530 if (adapter && adapter->device_mode == WLAN_HDD_SOFTAP) {
Hanumanth Reddy Pothula1428c612017-03-06 11:35:34 +05302531 if (test_bit(SOFTAP_INIT_DONE, &adapter->event_flags)) {
2532 hostapd_state =
2533 WLAN_HDD_GET_HOSTAP_STATE_PTR(adapter);
2534 hddLog(VOS_TRACE_LEVEL_INFO, FL("Restart prev SAP session"));
2535 wlan_hdd_start_sap(adapter);
2536 if (!VOS_IS_STATUS_SUCCESS(
2537 hdd_dhcp_mdns_offload(adapter))) {
2538 vos_event_reset(
2539 &hostapd_state->vosEvent);
2540 hddLog(VOS_TRACE_LEVEL_ERROR,
2541 FL("DHCP/MDNS offload Failed!!"));
2542 if (VOS_STATUS_SUCCESS ==
2543 WLANSAP_StopBss(
2544 hdd_ctx->pvosContext)) {
2545 status = vos_wait_single_event(
2546 &hostapd_state->vosEvent
2547 , 10000);
2548 if (!VOS_IS_STATUS_SUCCESS(
2549 status)) {
2550 hddLog(LOGE, FL("SAP Stop Failed"));
2551 return;
2552 }
Anurag Chouhanb2951ae2017-03-12 13:41:35 +05302553 }
2554 }
2555 }
Hanumanth Reddy Pothulad864f312017-01-18 16:16:08 +05302556 }
2557 status = hdd_get_next_adapter(hdd_ctx, adapter_node, &next);
2558 adapter_node = next;
2559 }
2560
2561 EXIT();
2562}
Jeff Johnson295189b2012-06-20 16:38:30 -07002563
Sen, Devendrade5cfe92017-01-31 18:51:15 +05302564#ifdef FEATURE_WLAN_DIAG_SUPPORT
2565/**
2566* hdd_wlan_ssr_reinit_event()- send ssr reinit state
2567*
2568* This Function send send ssr reinit state diag event
2569*
2570* Return: void.
2571*/
2572static void hdd_wlan_ssr_reinit_event(void)
2573{
2574 WLAN_VOS_DIAG_EVENT_DEF(ssr_reinit, struct host_event_wlan_ssr_reinit);
2575 vos_mem_zero(&ssr_reinit, sizeof(ssr_reinit));
2576 ssr_reinit.status = SSR_SUB_SYSTEM_REINIT;
2577 WLAN_VOS_DIAG_EVENT_REPORT(&ssr_reinit,
2578 EVENT_WLAN_SSR_REINIT_SUBSYSTEM);
2579}
2580#else
2581static inline void hdd_wlan_ssr_reinit_event(void)
2582{
2583
2584}
2585#endif
2586
Jeff Johnson295189b2012-06-20 16:38:30 -07002587/* the HDD interface to WLAN driver re-init.
2588 * This is called to initialize/start WLAN driver after a shutdown.
2589 */
2590VOS_STATUS hdd_wlan_re_init(void)
2591{
2592 VOS_STATUS vosStatus;
2593 v_CONTEXT_t pVosContext = NULL;
2594 hdd_context_t *pHddCtx = NULL;
2595 eHalStatus halStatus;
Sameer Thalappilf58d7ec2013-04-25 20:17:12 -07002596#ifdef HAVE_WCNSS_CAL_DOWNLOAD
2597 int max_retries = 0;
2598#endif
Siddharth Bhalc7e79b62014-10-10 22:37:38 +05302599#ifdef HAVE_CBC_DONE
2600 int max_cbc_retries = 0;
2601#endif
Jeff Johnson295189b2012-06-20 16:38:30 -07002602#ifdef WLAN_BTAMP_FEATURE
2603 hdd_config_t *pConfig = NULL;
2604 WLANBAP_ConfigType btAmpConfig;
2605#endif
2606
Katya Nigam82a93062014-06-04 15:15:36 +05302607 struct device *dev = NULL;
Madan Mohan Koyyalamudib0e70642012-10-11 12:20:22 -07002608 hdd_ssr_timer_del();
Sushant Kaushik83392fa2015-05-05 17:44:40 +05302609 hdd_prevent_suspend(WIFI_POWER_EVENT_WAKELOCK_DRIVER_REINIT);
Sameer Thalappil5d7a33f2013-01-30 08:36:16 -08002610
Sameer Thalappilf58d7ec2013-04-25 20:17:12 -07002611#ifdef HAVE_WCNSS_CAL_DOWNLOAD
2612 /* wait until WCNSS driver downloads NV */
Yue Ma120f9ff2014-02-26 14:53:31 -08002613 while (!wcnss_device_ready() && 10 >= ++max_retries) {
Sameer Thalappilf58d7ec2013-04-25 20:17:12 -07002614 msleep(1000);
2615 }
Yue Ma120f9ff2014-02-26 14:53:31 -08002616 if (max_retries >= 10) {
Sameer Thalappilf58d7ec2013-04-25 20:17:12 -07002617 hddLog(VOS_TRACE_LEVEL_FATAL,"%s: WCNSS driver not ready", __func__);
2618 goto err_re_init;
2619 }
2620#endif
2621
Siddharth Bhalc7e79b62014-10-10 22:37:38 +05302622#ifdef HAVE_CBC_DONE
2623 while (!wcnss_cbc_complete() && 20 >= ++max_cbc_retries) {
2624 msleep(1000);
2625 }
2626 if (max_cbc_retries >= 20) {
2627 hddLog(VOS_TRACE_LEVEL_FATAL, "%s:CBC not completed", __func__);
2628 }
2629#endif
2630
Sameer Thalappil9ab2fe52013-10-22 12:50:24 -07002631 vos_set_reinit_in_progress(VOS_MODULE_ID_VOSS, TRUE);
2632
Sameer Thalappil5d7a33f2013-01-30 08:36:16 -08002633 /* The driver should always be initialized in STA mode after SSR */
Hanumanth Reddy Pothulad864f312017-01-18 16:16:08 +05302634 if (VOS_STA_SAP_MODE != hdd_get_conparam())
2635 hdd_set_conparam(0);
Sameer Thalappil5d7a33f2013-01-30 08:36:16 -08002636
Katya Nigam82a93062014-06-04 15:15:36 +05302637 dev = wcnss_wlan_get_device();
2638 if (NULL == dev)
2639 {
2640 hddLog(VOS_TRACE_LEVEL_FATAL,"%s: wcnss dev is NULL",__func__);
2641 goto err_re_init;
2642 }
2643
Jeff Johnson295189b2012-06-20 16:38:30 -07002644 /* Re-open VOSS, it is a re-open b'se control transport was never closed. */
Katya Nigam82a93062014-06-04 15:15:36 +05302645 vosStatus = vos_open(&pVosContext, dev);
Jeff Johnson295189b2012-06-20 16:38:30 -07002646 if (!VOS_IS_STATUS_SUCCESS(vosStatus))
2647 {
2648 hddLog(VOS_TRACE_LEVEL_FATAL,"%s: vos_open failed",__func__);
2649 goto err_re_init;
2650 }
2651
2652 /* Get the HDD context. */
2653 pHddCtx = (hdd_context_t *)vos_get_context(VOS_MODULE_ID_HDD, pVosContext);
2654 if(!pHddCtx)
2655 {
2656 hddLog(VOS_TRACE_LEVEL_FATAL,"%s: HDD context is Null",__func__);
2657 goto err_vosclose;
2658 }
2659
2660 /* Save the hal context in Adapter */
2661 pHddCtx->hHal = (tHalHandle)vos_get_context( VOS_MODULE_ID_SME, pVosContext );
2662 if ( NULL == pHddCtx->hHal )
2663 {
2664 hddLog(VOS_TRACE_LEVEL_FATAL,"%s: HAL context is null",__func__);
2665 goto err_vosclose;
2666 }
2667
2668 /* Set the SME configuration parameters. */
2669 vosStatus = hdd_set_sme_config(pHddCtx);
2670 if ( VOS_STATUS_SUCCESS != vosStatus )
2671 {
2672 hddLog(VOS_TRACE_LEVEL_FATAL,"%s: Failed hdd_set_sme_config",__func__);
2673 goto err_vosclose;
2674 }
2675
Jeff Johnson295189b2012-06-20 16:38:30 -07002676 vosStatus = vos_preStart( pHddCtx->pvosContext );
2677 if ( !VOS_IS_STATUS_SUCCESS( vosStatus ) )
2678 {
2679 hddLog(VOS_TRACE_LEVEL_FATAL,"%s: vos_preStart failed",__func__);
2680 goto err_vosclose;
2681 }
2682
2683 /* In the integrated architecture we update the configuration from
2684 the INI file and from NV before vOSS has been started so that
2685 the final contents are available to send down to the cCPU */
2686 /* Apply the cfg.ini to cfg.dat */
2687 if (FALSE == hdd_update_config_dat(pHddCtx))
2688 {
2689 hddLog(VOS_TRACE_LEVEL_FATAL,"%s: config update failed",__func__ );
2690 goto err_vosclose;
2691 }
2692
2693 /* Set the MAC Address, currently this is used by HAL to add self sta.
2694 * Remove this once self sta is added as part of session open. */
2695 halStatus = cfgSetStr(pHddCtx->hHal, WNI_CFG_STA_ID,
2696 (v_U8_t *)&pHddCtx->cfg_ini->intfMacAddr[0],
2697 sizeof(pHddCtx->cfg_ini->intfMacAddr[0]));
2698 if (!HAL_STATUS_SUCCESS(halStatus))
2699 {
2700 hddLog(VOS_TRACE_LEVEL_ERROR,"%s: Failed to set MAC Address. "
2701 "HALStatus is %08d [x%08x]",__func__, halStatus, halStatus);
2702 goto err_vosclose;
2703 }
2704
2705 /* Start VOSS which starts up the SME/MAC/HAL modules and everything else
2706 Note: Firmware image will be read and downloaded inside vos_start API */
2707 vosStatus = vos_start( pVosContext );
2708 if ( !VOS_IS_STATUS_SUCCESS( vosStatus ) )
2709 {
2710 hddLog(VOS_TRACE_LEVEL_FATAL,"%s: vos_start failed",__func__);
Hanumantha Reddy Pothulabd9601a2016-02-12 13:22:27 +05302711 if (isSsrPanicOnFailure())
2712 VOS_BUG(0);
Jeff Johnson295189b2012-06-20 16:38:30 -07002713 goto err_vosclose;
2714 }
2715
Madan Mohan Koyyalamudi8612ec92012-09-28 15:53:07 -07002716 /* Exchange capability info between Host and FW and also get versioning info from FW */
2717 hdd_exchange_version_and_caps(pHddCtx);
2718
Jeff Johnson295189b2012-06-20 16:38:30 -07002719 vosStatus = hdd_post_voss_start_config( pHddCtx );
2720 if ( !VOS_IS_STATUS_SUCCESS( vosStatus ) )
2721 {
2722 hddLog(VOS_TRACE_LEVEL_FATAL,"%s: hdd_post_voss_start_config failed",
2723 __func__);
2724 goto err_vosstop;
2725 }
2726
Mihir Shete04206452014-11-20 17:50:58 +05302727#ifdef CONFIG_ENABLE_LINUX_REG
Agarwal Ashish6db9d532014-09-30 18:19:10 +05302728 vosStatus = wlan_hdd_init_channels_for_cc(pHddCtx, REINIT);
2729 if ( !VOS_IS_STATUS_SUCCESS( vosStatus ) )
2730 {
2731 hddLog(VOS_TRACE_LEVEL_FATAL, "%s: wlan_hdd_init_channels_for_cc failed",
2732 __func__);
2733 goto err_vosstop;
2734 }
Mihir Shete04206452014-11-20 17:50:58 +05302735#endif
Agarwal Ashish6db9d532014-09-30 18:19:10 +05302736
Jeff Johnson295189b2012-06-20 16:38:30 -07002737#ifdef WLAN_BTAMP_FEATURE
2738 vosStatus = WLANBAP_Open(pVosContext);
2739 if(!VOS_IS_STATUS_SUCCESS(vosStatus))
2740 {
2741 VOS_TRACE( VOS_MODULE_ID_VOSS, VOS_TRACE_LEVEL_ERROR,
2742 "%s: Failed to open BAP",__func__);
2743 goto err_vosstop;
2744 }
2745 vosStatus = BSL_Init(pVosContext);
2746 if(!VOS_IS_STATUS_SUCCESS(vosStatus))
2747 {
2748 VOS_TRACE( VOS_MODULE_ID_VOSS, VOS_TRACE_LEVEL_ERROR,
2749 "%s: Failed to Init BSL",__func__);
2750 goto err_bap_close;
2751 }
2752 vosStatus = WLANBAP_Start(pVosContext);
2753 if (!VOS_IS_STATUS_SUCCESS(vosStatus))
2754 {
2755 VOS_TRACE( VOS_MODULE_ID_VOSS, VOS_TRACE_LEVEL_ERROR,
2756 "%s: Failed to start TL",__func__);
2757 goto err_bap_close;
2758 }
2759 pConfig = pHddCtx->cfg_ini;
2760 btAmpConfig.ucPreferredChannel = pConfig->preferredChannel;
2761 vosStatus = WLANBAP_SetConfig(&btAmpConfig);
2762#endif //WLAN_BTAMP_FEATURE
2763
2764 /* Restart all adapters */
2765 hdd_start_all_adapters(pHddCtx);
Sreelakshmi Konamkif0646d52016-12-09 12:35:31 +05302766 pHddCtx->last_scan_reject_session_id = 0xFF;
2767 pHddCtx->last_scan_reject_reason = 0;
Sreelakshmi Konamki20ebed92016-10-27 12:13:30 +05302768 pHddCtx->last_scan_reject_timestamp = 0;
Abhishek Singhe4b12562017-06-20 16:53:39 +05302769 pHddCtx->scan_reject_cnt = 0;
Jeff Johnson295189b2012-06-20 16:38:30 -07002770 pHddCtx->hdd_mcastbcast_filter_set = FALSE;
Anand N Sunkad0cbc27a2014-09-18 12:58:18 +05302771 pHddCtx->btCoexModeSet = FALSE;
Jeff Johnson295189b2012-06-20 16:38:30 -07002772 hdd_register_mcast_bcast_filter(pHddCtx);
Agarwal Ashish4b87f922014-06-18 03:03:21 +05302773 wlan_hdd_tdls_init(pHddCtx);
Jeff Johnson295189b2012-06-20 16:38:30 -07002774 /* Register with platform driver as client for Suspend/Resume */
2775 vosStatus = hddRegisterPmOps(pHddCtx);
2776 if ( !VOS_IS_STATUS_SUCCESS( vosStatus ) )
2777 {
2778 hddLog(VOS_TRACE_LEVEL_FATAL,"%s: hddRegisterPmOps failed",__func__);
2779 goto err_bap_stop;
2780 }
Hanumantha Reddy Pothulab7dd9972015-07-01 12:24:57 +05302781
2782#ifdef WLAN_LOGGING_SOCK_SVC_ENABLE
2783 if (pHddCtx->cfg_ini->wlanLoggingEnable &&
2784 (pHddCtx->cfg_ini->enableFWLogging ||
2785 pHddCtx->cfg_ini->enableMgmtLogging ||
2786 pHddCtx->cfg_ini->enableContFWLogging))
2787 {
2788 hdd_init_frame_logging(pHddCtx);
2789 }
2790#endif
2791
Jeff Johnson295189b2012-06-20 16:38:30 -07002792 /* Allow the phone to go to sleep */
Sushant Kaushik83392fa2015-05-05 17:44:40 +05302793 hdd_allow_suspend(WIFI_POWER_EVENT_WAKELOCK_DRIVER_REINIT);
Jeff Johnson295189b2012-06-20 16:38:30 -07002794 /* register for riva power on lock */
2795 if (req_riva_power_on_lock("wlan"))
2796 {
2797 hddLog(VOS_TRACE_LEVEL_FATAL,"%s: req riva power on lock failed",
2798 __func__);
2799 goto err_unregister_pmops;
2800 }
Gupta, Kapil7c34b322015-09-30 13:12:35 +05302801 sme_set_rssi_threshold_breached_cb(pHddCtx->hHal, hdd_rssi_threshold_breached_cb);
Sameer Thalappil9ab2fe52013-10-22 12:50:24 -07002802 vos_set_reinit_in_progress(VOS_MODULE_ID_VOSS, FALSE);
Deepthi Gowri1ca95bb2016-01-13 19:47:53 +05302803
2804 sme_register_mgmt_frame_ind_callback(pHddCtx->hHal,hdd_indicate_mgmt_frame);
2805
Dasari Srinivas421bde82014-06-25 12:01:44 +05302806#ifdef WLAN_FEATURE_EXTSCAN
2807 sme_EXTScanRegisterCallback(pHddCtx->hHal,
2808 wlan_hdd_cfg80211_extscan_callback,
2809 pHddCtx);
2810#endif /* WLAN_FEATURE_EXTSCAN */
Padma, Santhosh Kumar2ccac212015-10-20 17:27:27 +05302811
2812#ifdef FEATURE_OEM_DATA_SUPPORT
2813 sme_OemDataRegisterCallback(pHddCtx->hHal,
2814 wlan_hdd_cfg80211_oemdata_callback,
2815 pHddCtx);
2816#endif /* FEATURE_OEM_DATA_SUPPORT */
2817
Jeff Johnson295189b2012-06-20 16:38:30 -07002818 goto success;
2819
2820err_unregister_pmops:
2821 hddDeregisterPmOps(pHddCtx);
2822
2823err_bap_stop:
Jeff Johnson32d95a32012-09-10 13:15:23 -07002824#ifdef CONFIG_HAS_EARLYSUSPEND
2825 hdd_unregister_mcast_bcast_filter(pHddCtx);
2826#endif
2827 hdd_close_all_adapters(pHddCtx);
Jeff Johnson295189b2012-06-20 16:38:30 -07002828#ifdef WLAN_BTAMP_FEATURE
Jeff Johnson32d95a32012-09-10 13:15:23 -07002829 WLANBAP_Stop(pVosContext);
Jeff Johnson295189b2012-06-20 16:38:30 -07002830#endif
2831
2832#ifdef WLAN_BTAMP_FEATURE
2833err_bap_close:
2834 WLANBAP_Close(pVosContext);
2835#endif
2836
2837err_vosstop:
2838 vos_stop(pVosContext);
2839
2840err_vosclose:
Pradeep Kumar Goudagunta22d8e4d2014-07-17 15:03:51 +05302841 if(!isSsrPanicOnFailure())
2842 {
2843 /* If we hit this, it means wlan driver is in bad state and needs
2844 * driver unload and load.
2845 */
Pradeep Kumar Goudagunta22d8e4d2014-07-17 15:03:51 +05302846 vos_set_reinit_in_progress(VOS_MODULE_ID_VOSS, FALSE);
2847 return VOS_STATUS_E_FAILURE;
2848 }
2849
Jeff Johnson295189b2012-06-20 16:38:30 -07002850 vos_close(pVosContext);
2851 vos_sched_close(pVosContext);
2852 if (pHddCtx)
2853 {
Jeff Johnson295189b2012-06-20 16:38:30 -07002854 /* Unregister the Net Device Notifier */
2855 unregister_netdevice_notifier(&hdd_netdev_notifier);
2856 /* Clean up HDD Nlink Service */
2857 send_btc_nlink_msg(WLAN_MODULE_DOWN_IND, 0);
Leo Chang59cdc7e2013-07-10 10:08:21 -07002858#ifdef WLAN_KD_READY_NOTIFIER
2859 nl_srv_exit(pHddCtx->ptt_pid);
2860#else
Jeff Johnson295189b2012-06-20 16:38:30 -07002861 nl_srv_exit();
Leo Chang59cdc7e2013-07-10 10:08:21 -07002862#endif /* WLAN_KD_READY_NOTIFIER */
Jeff Johnson295189b2012-06-20 16:38:30 -07002863 /* Free up dynamically allocated members inside HDD Adapter */
2864 kfree(pHddCtx->cfg_ini);
2865 pHddCtx->cfg_ini= NULL;
2866
Jeff Johnson295189b2012-06-20 16:38:30 -07002867 wiphy_unregister(pHddCtx->wiphy);
Agrawal Ashish33ec71e2015-11-26 20:20:58 +05302868 hdd_wlan_free_wiphy_channels(pHddCtx->wiphy);
Jeff Johnson295189b2012-06-20 16:38:30 -07002869 wiphy_free(pHddCtx->wiphy);
Jeff Johnson295189b2012-06-20 16:38:30 -07002870 }
2871 vos_preClose(&pVosContext);
2872
2873#ifdef MEMORY_DEBUG
2874 vos_mem_exit();
2875#endif
2876
2877err_re_init:
2878 /* Allow the phone to go to sleep */
Sushant Kaushik83392fa2015-05-05 17:44:40 +05302879 hdd_allow_suspend(WIFI_POWER_EVENT_WAKELOCK_DRIVER_REINIT);
Sameer Thalappil9ab2fe52013-10-22 12:50:24 -07002880 vos_set_reinit_in_progress(VOS_MODULE_ID_VOSS, FALSE);
Sameer Thalappil451ebb92013-06-28 15:49:58 -07002881 VOS_BUG(0);
Madan Mohan Koyyalamudicae253a2012-11-06 19:10:35 -08002882 return -EPERM;
Jeff Johnson295189b2012-06-20 16:38:30 -07002883
2884success:
Sen, Devendrade5cfe92017-01-31 18:51:15 +05302885 hdd_wlan_ssr_reinit_event();
Jeff Johnson295189b2012-06-20 16:38:30 -07002886 /* Trigger replay of BTC events */
2887 send_btc_nlink_msg(WLAN_MODULE_DOWN_IND, 0);
Hanumanth Reddy Pothulad864f312017-01-18 16:16:08 +05302888
2889 if (pHddCtx->cfg_ini->sap_internal_restart)
2890 hdd_ssr_restart_sap(pHddCtx);
2891
Jeff Johnson295189b2012-06-20 16:38:30 -07002892 return VOS_STATUS_SUCCESS;
2893}