Skip to content

Commit 295adaf

Browse files
Miriam-Racheljmberg-intel
authored andcommitted
wifi: mac80211: avoid double free in auth/assoc timeout
In case of authentication/association timeout (as detected in ieee80211_iface_work->ieee80211_sta_work), ieee80211_destroy_auth_data is called. At the beginning of it, the pointer to ifmgd::auth_data memory is copied to a local variable. If iface_work is queued again during the execution of the current one, and then the driver is flushing the wiphy_works (for its needs), ieee80211_destroy_auth_data will run again and free auth_data. Then when the execution of the original worker continues, the previously copied pointer will be freed, causing a kernel bug: kernel BUG at mm/slub.c:553! (double free) Same for association timeout (just with ieee80211_destroy_assoc_data and ifmgd::assoc_data) Fix this by NULLifying auth/assoc data right after we copied the pointer to it. That way, even in the scenario above, the code will not handle the same timeout twice. Signed-off-by: Miri Korenblit <[email protected]> Reviewed-by: Johannes Berg <[email protected]> Link: https://patch.msgid.link/20250102161730.0c3f7f781096.I2b458fb53291b06717077a815755288a81274756@changeid Signed-off-by: Johannes Berg <[email protected]>
1 parent b9caeea commit 295adaf

File tree

1 file changed

+4
-2
lines changed

1 file changed

+4
-2
lines changed

net/mac80211/mlme.c

Lines changed: 4 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -4402,6 +4402,8 @@ static void ieee80211_destroy_auth_data(struct ieee80211_sub_if_data *sdata,
44024402

44034403
lockdep_assert_wiphy(sdata->local->hw.wiphy);
44044404

4405+
sdata->u.mgd.auth_data = NULL;
4406+
44054407
if (!assoc) {
44064408
/*
44074409
* we are not authenticated yet, the only timer that could be
@@ -4423,7 +4425,6 @@ static void ieee80211_destroy_auth_data(struct ieee80211_sub_if_data *sdata,
44234425

44244426
cfg80211_put_bss(sdata->local->hw.wiphy, auth_data->bss);
44254427
kfree(auth_data);
4426-
sdata->u.mgd.auth_data = NULL;
44274428
}
44284429

44294430
enum assoc_status {
@@ -4440,6 +4441,8 @@ static void ieee80211_destroy_assoc_data(struct ieee80211_sub_if_data *sdata,
44404441

44414442
lockdep_assert_wiphy(sdata->local->hw.wiphy);
44424443

4444+
sdata->u.mgd.assoc_data = NULL;
4445+
44434446
if (status != ASSOC_SUCCESS) {
44444447
/*
44454448
* we are not associated yet, the only timer that could be
@@ -4478,7 +4481,6 @@ static void ieee80211_destroy_assoc_data(struct ieee80211_sub_if_data *sdata,
44784481
}
44794482

44804483
kfree(assoc_data);
4481-
sdata->u.mgd.assoc_data = NULL;
44824484
}
44834485

44844486
static void ieee80211_auth_challenge(struct ieee80211_sub_if_data *sdata,

0 commit comments

Comments
 (0)