diff --git a/drivers/wifi/nrf_wifi/inc/fmac_main.h b/drivers/wifi/nrf_wifi/inc/fmac_main.h index 57d4b8b9df5..de6780069b0 100644 --- a/drivers/wifi/nrf_wifi/inc/fmac_main.h +++ b/drivers/wifi/nrf_wifi/inc/fmac_main.h @@ -113,6 +113,8 @@ struct nrf_wifi_ctx_zep { bool rpu_recovery_in_progress; unsigned long last_rpu_recovery_time_ms; unsigned int rpu_recovery_retries; + int rpu_recovery_success; + int rpu_recovery_failure; #endif /* CONFIG_NRF_WIFI_RPU_RECOVERY */ }; diff --git a/drivers/wifi/nrf_wifi/src/net_if.c b/drivers/wifi/nrf_wifi/src/net_if.c index 19b232b6fe3..5c7fb9759f7 100644 --- a/drivers/wifi/nrf_wifi/src/net_if.c +++ b/drivers/wifi/nrf_wifi/src/net_if.c @@ -74,6 +74,7 @@ static void nrf_wifi_rpu_recovery_work_handler(struct k_work *work) nrf_wifi_rpu_recovery_work); struct nrf_wifi_ctx_zep *rpu_ctx_zep = NULL; int ret; + bool recovery_fail = false; if (!vif_ctx_zep) { LOG_ERR("%s: vif_ctx_zep is NULL", __func__); @@ -143,6 +144,8 @@ static void nrf_wifi_rpu_recovery_work_handler(struct k_work *work) /* This indirectly does a cold-boot of RPU */ ret = net_if_down(vif_ctx_zep->zep_net_if_ctx); if (ret) { + rpu_ctx_zep->rpu_recovery_failure++; + recovery_fail = true; LOG_ERR("%s: net_if_down failed: %d", __func__, ret); /* Continue with the recovery */ } @@ -158,6 +161,9 @@ static void nrf_wifi_rpu_recovery_work_handler(struct k_work *work) } rpu_ctx_zep->rpu_recovery_in_progress = false; rpu_ctx_zep->last_rpu_recovery_time_ms = k_uptime_get(); + if (!recovery_fail) { + rpu_ctx_zep->rpu_recovery_success++; + } k_mutex_unlock(&rpu_ctx_zep->rpu_lock); #ifdef CONFIG_NRF_WIFI_RPU_RECOVERY_DEBUG LOG_ERR("%s: RPU recovery done", __func__); diff --git a/drivers/wifi/nrf_wifi/src/wifi_util.c b/drivers/wifi/nrf_wifi/src/wifi_util.c index 528c41fa184..2d2ca2a2b5b 100644 --- a/drivers/wifi/nrf_wifi/src/wifi_util.c +++ b/drivers/wifi/nrf_wifi/src/wifi_util.c @@ -915,6 +915,52 @@ static int nrf_wifi_util_trigger_rpu_recovery(const struct shell *sh, k_mutex_unlock(&ctx->rpu_lock); return ret; } + +static int nrf_wifi_util_rpu_recovery_info(const struct shell *sh, + size_t argc, + const char *argv[]) +{ + struct nrf_wifi_fmac_dev_ctx *fmac_dev_ctx = NULL; + struct nrf_wifi_hal_dev_ctx *hal_dev_ctx = NULL; + unsigned long current_time_ms = nrf_wifi_osal_time_get_curr_ms(); + int ret; + + k_mutex_lock(&ctx->rpu_lock, K_FOREVER); + if (!ctx || !ctx->rpu_ctx) { + shell_fprintf(sh, + SHELL_ERROR, + "RPU context not initialized\n"); + ret = -ENOEXEC; + goto unlock; + } + + fmac_dev_ctx = ctx->rpu_ctx; + hal_dev_ctx = fmac_dev_ctx->hal_dev_ctx; + + shell_fprintf(sh, + SHELL_INFO, + "wdt_irq_received: %d\n" + "wdt_irq_ignored: %d\n" + "last_wakeup_now_asserted_time_ms: %lu milliseconds\n" + "last_wakeup_now_deasserted_time_ms: %lu milliseconds\n" + "last_rpu_sleep_opp_time_ms: %lu milliseconds\n" + "current time: %lu milliseconds\n" + "rpu_recovery_success: %d\n" + "rpu_recovery_failure: %d\n\n", + hal_dev_ctx->wdt_irq_received, + hal_dev_ctx->wdt_irq_ignored, + hal_dev_ctx->last_wakeup_now_asserted_time_ms, + hal_dev_ctx->last_wakeup_now_deasserted_time_ms, + hal_dev_ctx->last_rpu_sleep_opp_time_ms, + current_time_ms, + ctx->rpu_recovery_success, + ctx->rpu_recovery_failure); + + ret = 0; +unlock: + k_mutex_unlock(&ctx->rpu_lock); + return ret; +} #endif /* CONFIG_NRF_WIFI_RPU_RECOVERY */ SHELL_STATIC_SUBCMD_SET_CREATE( @@ -1013,6 +1059,12 @@ SHELL_STATIC_SUBCMD_SET_CREATE( nrf_wifi_util_trigger_rpu_recovery, 1, 0), + SHELL_CMD_ARG(rpu_recovery_info, + NULL, + "Dump RPU recovery information", + nrf_wifi_util_rpu_recovery_info, + 1, + 0), #endif /* CONFIG_NRF_WIFI_RPU_RECOVERY */ SHELL_SUBCMD_SET_END);