wifi: brcmfmac: Fix use-after-free bug in brcmf_cfg80211_detach
authorZheng Wang <zyytlz.wz@163.com>
Sun, 7 Jan 2024 07:25:04 +0000 (08:25 +0100)
committerKalle Valo <kvalo@kernel.org>
Thu, 18 Jan 2024 13:17:33 +0000 (15:17 +0200)
This is the candidate patch of CVE-2023-47233 :
https://nvd.nist.gov/vuln/detail/CVE-2023-47233

In brcm80211 driver,it starts with the following invoking chain
to start init a timeout worker:

->brcmf_usb_probe
  ->brcmf_usb_probe_cb
    ->brcmf_attach
      ->brcmf_bus_started
        ->brcmf_cfg80211_attach
          ->wl_init_priv
            ->brcmf_init_escan
              ->INIT_WORK(&cfg->escan_timeout_work,
  brcmf_cfg80211_escan_timeout_worker);

If we disconnect the USB by hotplug, it will call
brcmf_usb_disconnect to make cleanup. The invoking chain is :

brcmf_usb_disconnect
  ->brcmf_usb_disconnect_cb
    ->brcmf_detach
      ->brcmf_cfg80211_detach
        ->kfree(cfg);

While the timeout woker may still be running. This will cause
a use-after-free bug on cfg in brcmf_cfg80211_escan_timeout_worker.

Fix it by deleting the timer and canceling the worker in
brcmf_cfg80211_detach.

Fixes: e756af5b30b0 ("brcmfmac: add e-scan support.")
Signed-off-by: Zheng Wang <zyytlz.wz@163.com>
Cc: stable@vger.kernel.org
[arend.vanspriel@broadcom.com: keep timer delete as is and cancel work just before free]
Signed-off-by: Arend van Spriel <arend.vanspriel@broadcom.com>
Signed-off-by: Kalle Valo <kvalo@kernel.org>
Link: https://msgid.link/20240107072504.392713-1-arend.vanspriel@broadcom.com
drivers/net/wireless/broadcom/brcm80211/brcmfmac/cfg80211.c

index 133c5ea6429cd0e17baea181209c4d701e662d0c..52df03243c9f138d5157dfcabc4c88897aba8d75 100644 (file)
@@ -1179,8 +1179,7 @@ s32 brcmf_notify_escan_complete(struct brcmf_cfg80211_info *cfg,
        scan_request = cfg->scan_request;
        cfg->scan_request = NULL;
 
-       if (timer_pending(&cfg->escan_timeout))
-               del_timer_sync(&cfg->escan_timeout);
+       timer_delete_sync(&cfg->escan_timeout);
 
        if (fw_abort) {
                /* Do a scan abort to stop the driver's scan engine */
@@ -8435,6 +8434,7 @@ void brcmf_cfg80211_detach(struct brcmf_cfg80211_info *cfg)
        brcmf_btcoex_detach(cfg);
        wiphy_unregister(cfg->wiphy);
        wl_deinit_priv(cfg);
+       cancel_work_sync(&cfg->escan_timeout_work);
        brcmf_free_wiphy(cfg->wiphy);
        kfree(cfg);
 }