@@ -57,8 +57,11 @@ void mt76x02_mac_set_beacon(struct mt76x02_dev *dev,
int bcn_len = dev->beacon_ops->slot_size;
int bcn_addr = MT_BEACON_BASE + (bcn_len * dev->beacon_data_count);
- if (!mt76x02_write_beacon(dev, bcn_addr, skb))
+ if (!mt76x02_write_beacon(dev, bcn_addr, skb)) {
+ if (!dev->beacon_data_count)
+ dev->beacon_hang_check++;
dev->beacon_data_count++;
+ }
dev_kfree_skb(skb);
}
EXPORT_SYMBOL_GPL(mt76x02_mac_set_beacon);
@@ -74,6 +77,7 @@ void mt76x02_mac_set_beacon_enable(struct mt76x02_dev *dev,
if (!dev->mt76.beacon_mask)
dev->tbtt_count = 0;
+ dev->beacon_hang_check = 0;
if (enable) {
dev->mt76.beacon_mask |= BIT(mvif->idx);
} else {
@@ -1044,10 +1044,9 @@ static void mt76x02_check_mac_err(struct mt76x02_dev *dev)
return;
}
- if (++dev->beacon_hang_check < 10)
+ if (dev->beacon_hang_check < 10)
return;
- dev->beacon_hang_check = 0;
} else {
u32 val = mt76_rr(dev, 0x10f4);
if (!(val & BIT(29)) || !(val & (BIT(7) | BIT(5))))
@@ -1057,10 +1056,16 @@ static void mt76x02_check_mac_err(struct mt76x02_dev *dev)
dev_err(dev->mt76.dev, "MAC error detected\n");
mt76_wr(dev, MT_MAC_SYS_CTRL, 0);
- mt76x02_wait_for_txrx_idle(&dev->mt76);
+ if (!mt76x02_wait_for_txrx_idle(&dev->mt76)) {
+ dev_err(dev->mt76.dev, "MAC stop failed\n");
+ goto out;
+ }
+ dev->beacon_hang_check = 0;
mt76_set(dev, MT_MAC_SYS_CTRL, MT_MAC_SYS_CTRL_RESET_CSR);
udelay(10);
+
+out:
mt76_wr(dev, MT_MAC_SYS_CTRL,
MT_MAC_SYS_CTRL_ENABLE_TX | MT_MAC_SYS_CTRL_ENABLE_RX);
}
Increment the counter only when writing beacons to the hardware in order to avoid triggering restarts if beacons are disabled. Additionally, avoid resetting the MAC if stopping it failed Signed-off-by: Felix Fietkau <nbd@nbd.name> --- drivers/net/wireless/mediatek/mt76/mt76x02_beacon.c | 6 +++++- drivers/net/wireless/mediatek/mt76/mt76x02_mac.c | 11 ++++++++--- 2 files changed, 13 insertions(+), 4 deletions(-)