From dbc886e319c6d9264d53f92fcd0af9a609ffb262 Mon Sep 17 00:00:00 2001 From: Rajeev Kumar Date: Tue, 19 Jan 2016 12:56:04 -0800 Subject: [PATCH] qcacld-3.0: Add CDS SSR ready check for driver unload Driver unload is not waiting for external threads to exit before starting clean up process. Add CDS SSR ready check for driver unload such that driver unload waits for all external threads to exit before cleaning up driver data structures. Change-Id: Ic5ac1b770dea8e470ed8dcce50a4f66451f918f1 CRs-Fixed: 964151 --- core/cds/inc/cds_sched.h | 4 +--- core/cds/src/cds_sched.c | 10 +++++----- core/hdd/src/wlan_hdd_driver_ops.c | 5 ++++- 3 files changed, 10 insertions(+), 9 deletions(-) diff --git a/core/cds/inc/cds_sched.h b/core/cds/inc/cds_sched.h index 9d77986c3789..3ccf3cb8c6c3 100644 --- a/core/cds/inc/cds_sched.h +++ b/core/cds/inc/cds_sched.h @@ -438,9 +438,7 @@ void cdf_timer_module_init(void); void cds_ssr_protect_init(void); void cds_ssr_protect(const char *caller_func); void cds_ssr_unprotect(const char *caller_func); -bool cds_is_ssr_ready(const char *caller_func); +bool cds_wait_for_external_threads_completion(const char *caller_func); int cds_get_gfp_flags(void); -#define cds_wait_for_work_thread_completion(func) cds_is_ssr_ready(func) - #endif /* #if !defined __CDS_SCHED_H */ diff --git a/core/cds/src/cds_sched.c b/core/cds/src/cds_sched.c index e67485031f78..077bfc346896 100644 --- a/core/cds/src/cds_sched.c +++ b/core/cds/src/cds_sched.c @@ -1,5 +1,5 @@ /* - * Copyright (c) 2014-2015 The Linux Foundation. All rights reserved. + * Copyright (c) 2014-2016 The Linux Foundation. All rights reserved. * * Previously licensed under the ISC license by Qualcomm Atheros, Inc. * @@ -1230,14 +1230,14 @@ void cds_ssr_unprotect(const char *caller_func) } /** - * cds_is_ssr_ready() - check if the calling execution can proceed with ssr - * + * cds_wait_for_external_threads_completion() - wait for external threads + * completion before proceeding further * @caller_func: name of calling function. * * Return: true if there is no active entry points in driver * false if there is at least one active entry in driver */ -bool cds_is_ssr_ready(const char *caller_func) +bool cds_wait_for_external_threads_completion(const char *caller_func) { int count = MAX_SSR_WAIT_ITERATIONS; @@ -1260,7 +1260,7 @@ bool cds_is_ssr_ready(const char *caller_func) } CDF_TRACE(CDF_MODULE_ID_CDF, CDF_TRACE_LEVEL_INFO, - "Allowing SSR for %s", caller_func); + "Allowing SSR/Driver unload for %s", caller_func); return true; } diff --git a/core/hdd/src/wlan_hdd_driver_ops.c b/core/hdd/src/wlan_hdd_driver_ops.c index 65462ac3ed10..c366b909185f 100644 --- a/core/hdd/src/wlan_hdd_driver_ops.c +++ b/core/hdd/src/wlan_hdd_driver_ops.c @@ -310,6 +310,9 @@ static void wlan_hdd_remove(void) cds_set_driver_loaded(false); cds_set_unload_in_progress(true); + if (!cds_wait_for_external_threads_completion(__func__)) + hdd_err("External threads are still active attempting driver unload anyway"); + hdd_cnss_driver_unloading(); hif_ctx = cds_get_context(CDF_MODULE_ID_HIF); @@ -354,7 +357,7 @@ static void wlan_hdd_shutdown(void) !WLAN_IS_EPPING_ENABLED(cds_get_conparam())) hif_pktlogmod_exit(hif_ctx); - if (!cds_is_ssr_ready(__func__)) + if (!cds_wait_for_external_threads_completion(__func__)) hdd_err("Host is not ready for SSR, attempting anyway"); if (!WLAN_IS_EPPING_ENABLED(cds_get_conparam())) {