mirror of
https://mirrors.bfsu.edu.cn/git/linux.git
synced 2025-01-19 12:24:34 +08:00
wifi: mt76: mt7921s: fix potential hung tasks during chip recovery
During chip recovery (e.g. chip reset), there is a possible situation that kernel worker reset_work is holding the lock and waiting for kernel thread stat_worker to be parked, while stat_worker is waiting for the release of the same lock. It causes a deadlock resulting in the dumping of hung tasks messages and possible rebooting of the device. This patch prevents the execution of stat_worker during the chip recovery. Signed-off-by: Leon Yen <leon.yen@mediatek.com> Signed-off-by: Ming Yen Hsieh <MingYen.Hsieh@mediatek.com> Signed-off-by: Felix Fietkau <nbd@nbd.name>
This commit is contained in:
parent
4a40fcbfe3
commit
ecf0b2b8a3
@ -663,6 +663,7 @@ void mt7921_mac_reset_work(struct work_struct *work)
|
||||
int i, ret;
|
||||
|
||||
dev_dbg(dev->mt76.dev, "chip reset\n");
|
||||
set_bit(MT76_RESET, &dev->mphy.state);
|
||||
dev->hw_full_reset = true;
|
||||
ieee80211_stop_queues(hw);
|
||||
|
||||
@ -691,6 +692,7 @@ void mt7921_mac_reset_work(struct work_struct *work)
|
||||
}
|
||||
|
||||
dev->hw_full_reset = false;
|
||||
clear_bit(MT76_RESET, &dev->mphy.state);
|
||||
pm->suspended = false;
|
||||
ieee80211_wake_queues(hw);
|
||||
ieee80211_iterate_active_interfaces(hw,
|
||||
|
@ -64,7 +64,6 @@ int mt7921e_mac_reset(struct mt792x_dev *dev)
|
||||
mt76_wr(dev, dev->irq_map->host_irq_enable, 0);
|
||||
mt76_wr(dev, MT_PCIE_MAC_INT_ENABLE, 0x0);
|
||||
|
||||
set_bit(MT76_RESET, &dev->mphy.state);
|
||||
set_bit(MT76_MCU_RESET, &dev->mphy.state);
|
||||
wake_up(&dev->mt76.mcu.wait);
|
||||
skb_queue_purge(&dev->mt76.mcu.res_q);
|
||||
@ -115,7 +114,6 @@ int mt7921e_mac_reset(struct mt792x_dev *dev)
|
||||
|
||||
err = __mt7921_start(&dev->phy);
|
||||
out:
|
||||
clear_bit(MT76_RESET, &dev->mphy.state);
|
||||
|
||||
local_bh_disable();
|
||||
napi_enable(&dev->mt76.tx_napi);
|
||||
|
@ -98,7 +98,6 @@ int mt7921s_mac_reset(struct mt792x_dev *dev)
|
||||
mt76_connac_free_pending_tx_skbs(&dev->pm, NULL);
|
||||
mt76_txq_schedule_all(&dev->mphy);
|
||||
mt76_worker_disable(&dev->mt76.tx_worker);
|
||||
set_bit(MT76_RESET, &dev->mphy.state);
|
||||
set_bit(MT76_MCU_RESET, &dev->mphy.state);
|
||||
wake_up(&dev->mt76.mcu.wait);
|
||||
skb_queue_purge(&dev->mt76.mcu.res_q);
|
||||
@ -135,7 +134,6 @@ int mt7921s_mac_reset(struct mt792x_dev *dev)
|
||||
|
||||
err = __mt7921_start(&dev->phy);
|
||||
out:
|
||||
clear_bit(MT76_RESET, &dev->mphy.state);
|
||||
|
||||
mt76_worker_enable(&dev->mt76.tx_worker);
|
||||
|
||||
|
@ -499,7 +499,8 @@ static void mt76s_tx_status_data(struct mt76_worker *worker)
|
||||
dev = container_of(sdio, struct mt76_dev, sdio);
|
||||
|
||||
while (true) {
|
||||
if (test_bit(MT76_REMOVED, &dev->phy.state))
|
||||
if (test_bit(MT76_RESET, &dev->phy.state) ||
|
||||
test_bit(MT76_REMOVED, &dev->phy.state))
|
||||
break;
|
||||
|
||||
if (!dev->drv->tx_status_data(dev, &update))
|
||||
|
Loading…
Reference in New Issue
Block a user