diff --git a/core/cds/inc/cds_sched.h b/core/cds/inc/cds_sched.h index 82c2a8e7bc94..c0d3e1bd32ba 100644 --- a/core/cds/inc/cds_sched.h +++ b/core/cds/inc/cds_sched.h @@ -444,6 +444,7 @@ void cds_ssr_protect_init(void); void cds_ssr_protect(const char *caller_func); void cds_ssr_unprotect(const char *caller_func); bool cds_wait_for_external_threads_completion(const char *caller_func); +void cds_print_external_threads(void); int cds_get_gfp_flags(void); /** diff --git a/core/cds/src/cds_sched.c b/core/cds/src/cds_sched.c index 4c5cb2dae13b..1b1748675146 100644 --- a/core/cds/src/cds_sched.c +++ b/core/cds/src/cds_sched.c @@ -855,12 +855,17 @@ QDF_STATUS cds_sched_close(void *p_cds_context) { QDF_TRACE(QDF_MODULE_ID_QDF, QDF_TRACE_LEVEL_INFO_HIGH, "%s: invoked", __func__); + if (gp_cds_sched_context == NULL) { QDF_TRACE(QDF_MODULE_ID_QDF, QDF_TRACE_LEVEL_ERROR, "%s: gp_cds_sched_context == NULL", __func__); return QDF_STATUS_E_FAILURE; } + #ifdef QCA_CONFIG_SMP + if (!gp_cds_sched_context->ol_rx_thread) + return QDF_STATUS_SUCCESS; + /* Shut down Tlshim Rx thread */ set_bit(RX_SHUTDOWN_EVENT, &gp_cds_sched_context->ol_rx_event_flag); set_bit(RX_POST_EVENT, &gp_cds_sched_context->ol_rx_event_flag); @@ -918,8 +923,7 @@ void cds_ssr_protect_init(void) * Return: * void */ - -static void cds_print_external_threads(void) +void cds_print_external_threads(void) { int i = 0; unsigned long irq_flags; diff --git a/core/hdd/src/wlan_hdd_main.c b/core/hdd/src/wlan_hdd_main.c index dca5fbb955d5..d5337e9eb47f 100644 --- a/core/hdd/src/wlan_hdd_main.c +++ b/core/hdd/src/wlan_hdd_main.c @@ -8754,6 +8754,9 @@ int hdd_wlan_stop_modules(hdd_context_t *hdd_ctx) QDF_STATUS qdf_status; int ret = 0; p_cds_sched_context cds_sched_context = NULL; + bool is_idle_stop = !cds_is_driver_unloading() && + !cds_is_driver_recovering(); + int active_threads; ENTER(); @@ -8773,14 +8776,19 @@ int hdd_wlan_stop_modules(hdd_context_t *hdd_ctx) mutex_lock(&hdd_ctx->iface_change_lock); hdd_ctx->stop_modules_in_progress = true; - if (cds_return_external_threads_count() || hdd_ctx->isWiphySuspended) { - mutex_unlock(&hdd_ctx->iface_change_lock); + active_threads = cds_return_external_threads_count(); + if (active_threads > 0 || hdd_ctx->isWiphySuspended) { hdd_warn("External threads %d wiphy suspend %d", - cds_return_external_threads_count(), - hdd_ctx->isWiphySuspended); - qdf_mc_timer_start(&hdd_ctx->iface_change_timer, - hdd_ctx->config->iface_change_wait_time); - return 0; + active_threads, hdd_ctx->isWiphySuspended); + + cds_print_external_threads(); + + if (is_idle_stop) { + mutex_unlock(&hdd_ctx->iface_change_lock); + qdf_mc_timer_start(&hdd_ctx->iface_change_timer, + hdd_ctx->config->iface_change_wait_time); + return 0; + } } hdd_info("Present Driver Status: %d", hdd_ctx->driver_status); @@ -8837,7 +8845,7 @@ int hdd_wlan_stop_modules(hdd_context_t *hdd_ctx) ol_cds_free(); - if (!cds_is_driver_recovering() && !cds_is_driver_unloading()) { + if (is_idle_stop) { ret = pld_power_off(qdf_ctx->dev); if (ret) hdd_err("CNSS power down failed put device into Low power mode:%d",