mirror of https://gitee.com/openkylin/linux.git
iwlwifi: fix double free/complete in firmware loading
Linus reported that due to mac80211 failing to register the device (due to WoWLAN) his machine crashed etc. as we double-freed the vmalloc() firmware area. His patch to fix it was very similar to this one but I noticed that there's another bug in the area: we complete the completion before starting, so since we're running in a work struct context stop() could be called while in the middle of start() which will almost certainly lead to issues. Make a modification similar to his to avoid the double- free but also move the completion to another spot so it is only done after start() either finished or failed so that stop() can have a consistent state. Reported-by: Linus Torvalds <torvalds@linux-foundation.org> Signed-off-by: Johannes Berg <johannes.berg@intel.com> Signed-off-by: John W. Linville <linville@tuxdriver.com>
This commit is contained in:
parent
fcb6ff5e2c
commit
f69a23b795
|
@ -861,13 +861,18 @@ static void iwl_ucode_callback(const struct firmware *ucode_raw, void *context)
|
||||||
|
|
||||||
/* We have our copies now, allow OS release its copies */
|
/* We have our copies now, allow OS release its copies */
|
||||||
release_firmware(ucode_raw);
|
release_firmware(ucode_raw);
|
||||||
complete(&drv->request_firmware_complete);
|
|
||||||
|
|
||||||
drv->op_mode = iwl_dvm_ops.start(drv->trans, drv->cfg, &drv->fw);
|
drv->op_mode = iwl_dvm_ops.start(drv->trans, drv->cfg, &drv->fw);
|
||||||
|
|
||||||
if (!drv->op_mode)
|
if (!drv->op_mode)
|
||||||
goto out_free_fw;
|
goto out_unbind;
|
||||||
|
|
||||||
|
/*
|
||||||
|
* Complete the firmware request last so that
|
||||||
|
* a driver unbind (stop) doesn't run while we
|
||||||
|
* are doing the start() above.
|
||||||
|
*/
|
||||||
|
complete(&drv->request_firmware_complete);
|
||||||
return;
|
return;
|
||||||
|
|
||||||
try_again:
|
try_again:
|
||||||
|
|
Loading…
Reference in New Issue