diff options
author | Lorenzo Bianconi <lorenzo@kernel.org> | 2021-04-18 19:45:36 +0300 |
---|---|---|
committer | Felix Fietkau <nbd@nbd.name> | 2021-04-21 21:55:53 +0300 |
commit | ec7bd7b4a9c0e7e90d23b4f6a7dca2c713fe93ab (patch) | |
tree | 0c0877393a7fafcc5f0aac4ae526d8045ccf9bc4 /drivers/net/wireless | |
parent | 4f9b3aeb837a9df029b56179be7b0505de4400de (diff) | |
download | linux-ec7bd7b4a9c0e7e90d23b4f6a7dca2c713fe93ab.tar.xz |
mt76: connac: check wake refcount in mcu_fw_pmctrl
In order to avoid synchronization races between tx and rx path, rely on
mt76_connac_skip_fw_pmctrl putting the chip in sleep mode for mt7921 and
mt7663 devices
Signed-off-by: Lorenzo Bianconi <lorenzo@kernel.org>
Signed-off-by: Felix Fietkau <nbd@nbd.name>
Diffstat (limited to 'drivers/net/wireless')
-rw-r--r-- | drivers/net/wireless/mediatek/mt76/mt7615/mcu.c | 2 | ||||
-rw-r--r-- | drivers/net/wireless/mediatek/mt76/mt76_connac.h | 12 | ||||
-rw-r--r-- | drivers/net/wireless/mediatek/mt76/mt7921/mcu.c | 2 |
3 files changed, 14 insertions, 2 deletions
diff --git a/drivers/net/wireless/mediatek/mt76/mt7615/mcu.c b/drivers/net/wireless/mediatek/mt76/mt7615/mcu.c index 5890fee98d97..45c6fb5832b8 100644 --- a/drivers/net/wireless/mediatek/mt76/mt7615/mcu.c +++ b/drivers/net/wireless/mediatek/mt76/mt7615/mcu.c @@ -358,7 +358,7 @@ static int mt7615_mcu_fw_pmctrl(struct mt7615_dev *dev) mutex_lock(&dev->pm.mutex); - if (test_and_set_bit(MT76_STATE_PM, &mphy->state)) + if (mt76_connac_skip_fw_pmctrl(mphy, &dev->pm)) goto out; mt7622_trigger_hif_int(dev, true); diff --git a/drivers/net/wireless/mediatek/mt76/mt76_connac.h b/drivers/net/wireless/mediatek/mt76/mt76_connac.h index 85846eab8d7d..116d800c9f9d 100644 --- a/drivers/net/wireless/mediatek/mt76/mt76_connac.h +++ b/drivers/net/wireless/mediatek/mt76/mt76_connac.h @@ -116,6 +116,18 @@ mt76_connac_pm_unref(struct mt76_connac_pm *pm) spin_unlock_bh(&pm->wake.lock); } +static inline bool +mt76_connac_skip_fw_pmctrl(struct mt76_phy *phy, struct mt76_connac_pm *pm) +{ + bool ret; + + spin_lock_bh(&pm->wake.lock); + ret = pm->wake.count || test_and_set_bit(MT76_STATE_PM, &phy->state); + spin_unlock_bh(&pm->wake.lock); + + return ret; +} + static inline void mt76_connac_mutex_acquire(struct mt76_dev *dev, struct mt76_connac_pm *pm) __acquires(&dev->mutex) diff --git a/drivers/net/wireless/mediatek/mt76/mt7921/mcu.c b/drivers/net/wireless/mediatek/mt76/mt7921/mcu.c index 44f02cbf9cc7..1204f5d324f8 100644 --- a/drivers/net/wireless/mediatek/mt76/mt7921/mcu.c +++ b/drivers/net/wireless/mediatek/mt76/mt7921/mcu.c @@ -1304,7 +1304,7 @@ int mt7921_mcu_fw_pmctrl(struct mt7921_dev *dev) mutex_lock(&dev->pm.mutex); - if (test_and_set_bit(MT76_STATE_PM, &mphy->state)) + if (mt76_connac_skip_fw_pmctrl(mphy, &dev->pm)) goto out; for (i = 0; i < MT7921_DRV_OWN_RETRY_COUNT; i++) { |