[PATCH v4 15/20] PR: Add ranging session timeout and integrate socket cleanup

Kavita Kavita kavita.kavita at oss.qualcomm.com
Fri May 22 18:23:47 PDT 2026


From: Peddolla Harshavardhan Reddy <peddolla.reddy at oss.qualcomm.com>

Add wpas_pr_ranging_session_timeout() to automatically clean up when
a continuous ranging session expires. When continuous_ranging_session_time
is set, a timer is started after ranging begins; on expiry it stops the
peer measurement, frees pr_pasn_params, and stops the PD wdev.

Cancel the PASN timeout when ranging starts to avoid premature cleanup
while ranging is in progress. Cancel the ranging timeout on measurement
completion.

On final measurement result, only ranging_final_received is set to
block further results. Actual cleanup is deferred to the COMPLETE event
or session timeout to avoid premature teardown.

Integrate wpa_drv_stop_peer_measurement() into wpas_pr_pd_stop() so
the nl_pr socket is always destroyed when the PD wdev is stopped,
ensuring proper cleanup on all termination paths.

Signed-off-by: Peddolla Harshavardhan Reddy <peddolla.reddy at oss.qualcomm.com>
---
 wpa_supplicant/driver_i.h      |  8 +++++
 wpa_supplicant/pr_supplicant.c | 55 ++++++++++++++++++++++++++++++++--
 2 files changed, 61 insertions(+), 2 deletions(-)

diff --git a/wpa_supplicant/driver_i.h b/wpa_supplicant/driver_i.h
index c111224a6..7ff9f454c 100644
--- a/wpa_supplicant/driver_i.h
+++ b/wpa_supplicant/driver_i.h
@@ -772,6 +772,14 @@ wpa_drv_start_peer_measurement(struct wpa_supplicant *wpa_s, const u8 *peer,
 						      params);
 }
 
+static inline void
+wpa_drv_stop_peer_measurement(struct wpa_supplicant *wpa_s)
+{
+	if (!wpa_s->driver->stop_peer_measurement)
+		return;
+	wpa_s->driver->stop_peer_measurement(wpa_s->drv_priv);
+}
+
 #endif /* CONFIG_PR */
 
 static inline int wpa_drv_vendor_cmd(struct wpa_supplicant *wpa_s,
diff --git a/wpa_supplicant/pr_supplicant.c b/wpa_supplicant/pr_supplicant.c
index b9171362d..8873e8798 100644
--- a/wpa_supplicant/pr_supplicant.c
+++ b/wpa_supplicant/pr_supplicant.c
@@ -372,6 +372,28 @@ static void wpas_pr_pasn_result(void *ctx, u8 role, u8 protocol_type,
 }
 
 
+static void wpas_pr_ranging_session_timeout(void *eloop_ctx, void *timeout_ctx)
+{
+	struct wpa_supplicant *wpa_s = eloop_ctx;
+	struct pr_data *pr = wpa_s->global->pr;
+
+	wpa_printf(MSG_DEBUG,
+		   "PR: Ranging session timeout - cleaning up");
+
+	/* Stop peer measurement and cleanup ranging socket */
+	wpa_drv_stop_peer_measurement(wpa_s);
+
+	/* Free ranging params */
+	if (pr && pr->pr_pasn_params) {
+		os_free(pr->pr_pasn_params);
+		pr->pr_pasn_params = NULL;
+		pr->ranging_final_received = false;
+	}
+
+	wpas_pr_pd_stop(wpa_s);
+}
+
+
 /**
  * wpas_pr_trigger_ranging - Trigger FTM ranging after successful PASN auth
  */
@@ -456,6 +478,20 @@ static int wpas_pr_trigger_ranging(struct wpa_supplicant *wpa_s,
 
 	wpa_printf(MSG_DEBUG, "PR: Successfully triggered ranging measurement");
 
+	/* Start session timeout timer if continuous ranging session time is set */
+	if (params->continuous_ranging_session_time > 0) {
+		unsigned int timeout_sec = params->continuous_ranging_session_time / 1000;
+		unsigned int timeout_usec = (params->continuous_ranging_session_time % 1000) * 1000;
+
+		wpa_printf(MSG_DEBUG,
+			   "PR: Starting ranging session timeout timer for %u ms",
+			   params->continuous_ranging_session_time);
+
+		eloop_cancel_timeout(wpas_pr_ranging_session_timeout, wpa_s, NULL);
+		eloop_register_timeout(timeout_sec, timeout_usec,
+				       wpas_pr_ranging_session_timeout, wpa_s, NULL);
+	}
+
 	return 0;
 
 fail:
@@ -483,9 +519,20 @@ static void wpas_pr_ranging_params(void *ctx, const u8 *dev_addr,
 				      protocol_type, freq, op_channel, bw,
 				      format_bw);
 
+	/*
+	 * PASN succeeded - cancel the PASN timeout so it does not fire and
+	 * prematurely stop the PD wdev while ranging is in progress.
+	 * Cleanup happens on COMPLETE event or session timeout.
+	 */
+	eloop_cancel_timeout(wpas_pr_pasn_timeout, wpa_s, NULL);
+
 	/* Trigger ranging measurement after successful PASN authentication */
-	wpas_pr_trigger_ranging(wpa_s, peer_addr, freq, op_class, op_channel,
-				format_bw, protocol_type);
+	if (wpas_pr_trigger_ranging(wpa_s, peer_addr, freq, op_class, op_channel,
+				    format_bw, protocol_type) < 0) {
+		wpa_printf(MSG_DEBUG,
+			   "PR: Failed to trigger ranging, stopping PD wdev");
+		wpas_pr_pd_stop(wpa_s);
+	}
 }
 
 
@@ -721,6 +768,10 @@ void wpas_pr_deinit(struct wpa_supplicant *wpa_s)
 
 void wpas_pr_pd_stop(struct wpa_supplicant *wpa_s)
 {
+	/* Cancel ranging session timeout and stop peer measurement */
+	eloop_cancel_timeout(wpas_pr_ranging_session_timeout, wpa_s, NULL);
+	wpa_drv_stop_peer_measurement(wpa_s);
+
 	if (is_zero_ether_addr(wpa_s->pd_addr)) {
 		wpa_printf(MSG_DEBUG, "PR: pd_stop: no active PD wdev");
 		return;
-- 
2.34.1




More information about the Hostap mailing list