mirror of
git://projects.qi-hardware.com/openwrt-xburst.git
synced 2024-12-25 07:03:21 +02:00
rt2x00: merge a fix for random tx stalls
git-svn-id: svn://svn.openwrt.org/openwrt/trunk@30871 3c298f89-4303-0410-b956-a3cf2f4a3e73
This commit is contained in:
parent
92e1c8bfd3
commit
acd288a145
@ -1891,3 +1891,58 @@
|
|||||||
|
|
||||||
if (on)
|
if (on)
|
||||||
REG_SET_BIT(ah, AR_PHY_SFCORR_LOW,
|
REG_SET_BIT(ah, AR_PHY_SFCORR_LOW,
|
||||||
|
--- a/drivers/net/wireless/rt2x00/rt2x00dev.c
|
||||||
|
+++ b/drivers/net/wireless/rt2x00/rt2x00dev.c
|
||||||
|
@@ -430,10 +430,14 @@ void rt2x00lib_txdone(struct queue_entry
|
||||||
|
/*
|
||||||
|
* If the data queue was below the threshold before the txdone
|
||||||
|
* handler we must make sure the packet queue in the mac80211 stack
|
||||||
|
- * is reenabled when the txdone handler has finished.
|
||||||
|
+ * is reenabled when the txdone handler has finished. This has to be
|
||||||
|
+ * serialized with rt2x00mac_tx(), otherwise we can wake up queue
|
||||||
|
+ * before it was stopped.
|
||||||
|
*/
|
||||||
|
+ spin_lock_bh(&entry->queue->tx_lock);
|
||||||
|
if (!rt2x00queue_threshold(entry->queue))
|
||||||
|
rt2x00queue_unpause_queue(entry->queue);
|
||||||
|
+ spin_unlock_bh(&entry->queue->tx_lock);
|
||||||
|
}
|
||||||
|
EXPORT_SYMBOL_GPL(rt2x00lib_txdone);
|
||||||
|
|
||||||
|
--- a/drivers/net/wireless/rt2x00/rt2x00mac.c
|
||||||
|
+++ b/drivers/net/wireless/rt2x00/rt2x00mac.c
|
||||||
|
@@ -152,13 +152,22 @@ void rt2x00mac_tx(struct ieee80211_hw *h
|
||||||
|
if (unlikely(rt2x00queue_write_tx_frame(queue, skb, false)))
|
||||||
|
goto exit_fail;
|
||||||
|
|
||||||
|
+ /*
|
||||||
|
+ * Pausing queue has to be serialized with rt2x00lib_txdone(). Note
|
||||||
|
+ * we should not use spin_lock_bh variant as bottom halve was already
|
||||||
|
+ * disabled before ieee80211_xmit() call.
|
||||||
|
+ */
|
||||||
|
+ spin_lock(&queue->tx_lock);
|
||||||
|
if (rt2x00queue_threshold(queue))
|
||||||
|
rt2x00queue_pause_queue(queue);
|
||||||
|
+ spin_unlock(&queue->tx_lock);
|
||||||
|
|
||||||
|
return;
|
||||||
|
|
||||||
|
exit_fail:
|
||||||
|
+ spin_lock(&queue->tx_lock);
|
||||||
|
rt2x00queue_pause_queue(queue);
|
||||||
|
+ spin_unlock(&queue->tx_lock);
|
||||||
|
exit_free_skb:
|
||||||
|
ieee80211_free_txskb(hw, skb);
|
||||||
|
}
|
||||||
|
--- a/drivers/net/wireless/rt2x00/rt2x00queue.c
|
||||||
|
+++ b/drivers/net/wireless/rt2x00/rt2x00queue.c
|
||||||
|
@@ -619,6 +619,9 @@ int rt2x00queue_write_tx_frame(struct da
|
||||||
|
else if (test_bit(REQUIRE_DMA, &queue->rt2x00dev->cap_flags))
|
||||||
|
rt2x00queue_align_frame(skb);
|
||||||
|
|
||||||
|
+ /*
|
||||||
|
+ * That function must be called with bh disabled.
|
||||||
|
+ */
|
||||||
|
spin_lock(&queue->tx_lock);
|
||||||
|
|
||||||
|
if (unlikely(rt2x00queue_full(queue))) {
|
||||||
|
@ -239,7 +239,7 @@
|
|||||||
.get_entry_state = rt2800pci_get_entry_state,
|
.get_entry_state = rt2800pci_get_entry_state,
|
||||||
--- a/drivers/net/wireless/rt2x00/rt2x00dev.c
|
--- a/drivers/net/wireless/rt2x00/rt2x00dev.c
|
||||||
+++ b/drivers/net/wireless/rt2x00/rt2x00dev.c
|
+++ b/drivers/net/wireless/rt2x00/rt2x00dev.c
|
||||||
@@ -1161,6 +1161,10 @@ int rt2x00lib_probe_dev(struct rt2x00_de
|
@@ -1165,6 +1165,10 @@ int rt2x00lib_probe_dev(struct rt2x00_de
|
||||||
BIT(NL80211_IFTYPE_MESH_POINT) |
|
BIT(NL80211_IFTYPE_MESH_POINT) |
|
||||||
BIT(NL80211_IFTYPE_WDS);
|
BIT(NL80211_IFTYPE_WDS);
|
||||||
|
|
||||||
@ -250,7 +250,7 @@
|
|||||||
/*
|
/*
|
||||||
* Initialize work.
|
* Initialize work.
|
||||||
*/
|
*/
|
||||||
@@ -1284,6 +1288,11 @@ void rt2x00lib_remove_dev(struct rt2x00_
|
@@ -1288,6 +1292,11 @@ void rt2x00lib_remove_dev(struct rt2x00_
|
||||||
*/
|
*/
|
||||||
if (rt2x00dev->drv_data)
|
if (rt2x00dev->drv_data)
|
||||||
kfree(rt2x00dev->drv_data);
|
kfree(rt2x00dev->drv_data);
|
||||||
|
@ -12,7 +12,7 @@
|
|||||||
#endif /* _RT2X00_PLATFORM_H */
|
#endif /* _RT2X00_PLATFORM_H */
|
||||||
--- a/drivers/net/wireless/rt2x00/rt2x00dev.c
|
--- a/drivers/net/wireless/rt2x00/rt2x00dev.c
|
||||||
+++ b/drivers/net/wireless/rt2x00/rt2x00dev.c
|
+++ b/drivers/net/wireless/rt2x00/rt2x00dev.c
|
||||||
@@ -829,6 +829,22 @@ static int rt2x00lib_probe_hw_modes(stru
|
@@ -833,6 +833,22 @@ static int rt2x00lib_probe_hw_modes(stru
|
||||||
unsigned int num_rates;
|
unsigned int num_rates;
|
||||||
unsigned int i;
|
unsigned int i;
|
||||||
|
|
||||||
|
Loading…
Reference in New Issue
Block a user