path: root/wpa_supplicant/wpa_supplicant.c
diff options
authorJouni Malinen <jouni@codeaurora.org>2018-02-07 16:03:58 (GMT)
committerJouni Malinen <j@w1.fi>2018-02-07 16:03:58 (GMT)
commit6a252ece24a0b9b850b2312b8267dc0d59cc9310 (patch)
treea647dfcf1a90404f859179eee7e31b0bf387f660 /wpa_supplicant/wpa_supplicant.c
parent27a8d93b0701364209df47d9aaab0bd84583d87e (diff)
DPP: Fix GAS query removal race condition on DPP_STOP_LISTEN
If a DPP_STOP_LISTEN call happens to be received when there is a pending gas-query radio work that has not yet been started, it was possible for gas_query_stop() to go through gas_query_done() processing with gas->work == NULL and that ended up with the pending GAS query getting freed without removing the pending radio work that hold a reference to the now freed memory. Fix this by removing the pending non-started radio work for the GAS query in this specific corner case. Signed-off-by: Jouni Malinen <jouni@codeaurora.org>
Diffstat (limited to 'wpa_supplicant/wpa_supplicant.c')
1 files changed, 16 insertions, 0 deletions
diff --git a/wpa_supplicant/wpa_supplicant.c b/wpa_supplicant/wpa_supplicant.c
index c35121e..fcb2677 100644
--- a/wpa_supplicant/wpa_supplicant.c
+++ b/wpa_supplicant/wpa_supplicant.c
@@ -4955,6 +4955,22 @@ void radio_remove_works(struct wpa_supplicant *wpa_s,
+void radio_remove_pending_work(struct wpa_supplicant *wpa_s, void *ctx)
+ struct wpa_radio_work *work;
+ struct wpa_radio *radio = wpa_s->radio;
+ dl_list_for_each(work, &radio->work, struct wpa_radio_work, list) {
+ if (work->ctx != ctx)
+ continue;
+ wpa_dbg(wpa_s, MSG_DEBUG, "Free pending radio work '%s'@%p%s",
+ work->type, work, work->started ? " (started)" : "");
+ radio_work_free(work);
+ break;
+ }
static void radio_remove_interface(struct wpa_supplicant *wpa_s)
struct wpa_radio *radio = wpa_s->radio;