Introduce mt76_queue stopped parameter in order to run
ieee80211_wake_queue only when mac80211 queues have been
previously stopped and avoid to disable interrupts when it is
not necessary.
Move ieee80211_stop_queue out of q->lock critical section
Signed-off-by: Lorenzo Bianconi <[email protected]>
---
drivers/net/wireless/mediatek/mt76/dma.c | 5 ++++-
drivers/net/wireless/mediatek/mt76/mt76.h | 1 +
drivers/net/wireless/mediatek/mt76/tx.c | 12 +++++++++---
drivers/net/wireless/mediatek/mt76/usb.c | 6 +++++-
4 files changed, 19 insertions(+), 5 deletions(-)
diff --git a/drivers/net/wireless/mediatek/mt76/dma.c b/drivers/net/wireless/mediatek/mt76/dma.c
index 6eedc0ec7661..99e341cb1f92 100644
--- a/drivers/net/wireless/mediatek/mt76/dma.c
+++ b/drivers/net/wireless/mediatek/mt76/dma.c
@@ -180,7 +180,10 @@ mt76_dma_tx_cleanup(struct mt76_dev *dev, enum mt76_txq_id qid, bool flush)
else
mt76_dma_sync_idx(dev, q);
- wake = wake && qid < IEEE80211_NUM_ACS && q->queued < q->ndesc - 8;
+ wake = wake && q->stopped &&
+ qid < IEEE80211_NUM_ACS && q->queued < q->ndesc - 8;
+ if (wake)
+ q->stopped = false;
if (!q->queued)
wake_up(&dev->tx_wait);
diff --git a/drivers/net/wireless/mediatek/mt76/mt76.h b/drivers/net/wireless/mediatek/mt76/mt76.h
index 5dfb0601f101..3152b8c73c4a 100644
--- a/drivers/net/wireless/mediatek/mt76/mt76.h
+++ b/drivers/net/wireless/mediatek/mt76/mt76.h
@@ -126,6 +126,7 @@ struct mt76_queue {
int ndesc;
int queued;
int buf_size;
+ bool stopped;
u8 buf_offset;
u8 hw_idx;
diff --git a/drivers/net/wireless/mediatek/mt76/tx.c b/drivers/net/wireless/mediatek/mt76/tx.c
index 5a349fe3e576..97215c3a30d1 100644
--- a/drivers/net/wireless/mediatek/mt76/tx.c
+++ b/drivers/net/wireless/mediatek/mt76/tx.c
@@ -258,8 +258,9 @@ mt76_tx(struct mt76_dev *dev, struct ieee80211_sta *sta,
{
struct ieee80211_tx_info *info = IEEE80211_SKB_CB(skb);
struct ieee80211_hdr *hdr = (struct ieee80211_hdr *) skb->data;
- struct mt76_queue *q;
int qid = skb_get_queue_mapping(skb);
+ struct mt76_queue *q;
+ bool stop;
if (WARN_ON(qid >= MT_TXQ_PSD)) {
qid = MT_TXQ_BE;
@@ -289,9 +290,14 @@ mt76_tx(struct mt76_dev *dev, struct ieee80211_sta *sta,
dev->queue_ops->tx_queue_skb(dev, q, skb, wcid, sta);
dev->queue_ops->kick(dev, q);
- if (q->queued > q->ndesc - 8)
- ieee80211_stop_queue(dev->hw, skb_get_queue_mapping(skb));
+ stop = q->queued > q->ndesc - 8 && !q->stopped;
+ if (stop)
+ q->stopped = true;
+
spin_unlock_bh(&q->lock);
+
+ if (stop)
+ ieee80211_stop_queue(dev->hw, skb_get_queue_mapping(skb));
}
EXPORT_SYMBOL_GPL(mt76_tx);
diff --git a/drivers/net/wireless/mediatek/mt76/usb.c b/drivers/net/wireless/mediatek/mt76/usb.c
index ae6ada370597..4c1abd492405 100644
--- a/drivers/net/wireless/mediatek/mt76/usb.c
+++ b/drivers/net/wireless/mediatek/mt76/usb.c
@@ -655,7 +655,11 @@ static void mt76u_tx_tasklet(unsigned long data)
spin_lock_bh(&q->lock);
}
mt76_txq_schedule(dev, q);
- wake = i < IEEE80211_NUM_ACS && q->queued < q->ndesc - 8;
+
+ wake = q->stopped && q->queued < q->ndesc - 8;
+ if (wake)
+ q->stopped = false;
+
if (!q->queued)
wake_up(&dev->tx_wait);
--
2.20.1
On Wed, Feb 27, 2019 at 10:40:41PM +0100, Lorenzo Bianconi wrote:
> @@ -289,9 +290,14 @@ mt76_tx(struct mt76_dev *dev, struct ieee80211_sta *sta,
> dev->queue_ops->tx_queue_skb(dev, q, skb, wcid, sta);
> dev->queue_ops->kick(dev, q);
>
> - if (q->queued > q->ndesc - 8)
> - ieee80211_stop_queue(dev->hw, skb_get_queue_mapping(skb));
> + stop = q->queued > q->ndesc - 8 && !q->stopped;
> + if (stop)
> + q->stopped = true;
> +
> spin_unlock_bh(&q->lock);
> +
> + if (stop)
> + ieee80211_stop_queue(dev->hw, skb_get_queue_mapping(skb));
I don't think taking this outside of spin_lock section is beneficial.
Actually is better to do this faster than slower to prevent enqueue
frames by mac80211 and then dropped them due to lack of space in
mt76 queue.
Stanislaw
> On Wed, Feb 27, 2019 at 10:40:41PM +0100, Lorenzo Bianconi wrote:
> > @@ -289,9 +290,14 @@ mt76_tx(struct mt76_dev *dev, struct ieee80211_sta *sta,
> > dev->queue_ops->tx_queue_skb(dev, q, skb, wcid, sta);
> > dev->queue_ops->kick(dev, q);
> >
> > - if (q->queued > q->ndesc - 8)
> > - ieee80211_stop_queue(dev->hw, skb_get_queue_mapping(skb));
> > + stop = q->queued > q->ndesc - 8 && !q->stopped;
> > + if (stop)
> > + q->stopped = true;
> > +
> > spin_unlock_bh(&q->lock);
> > +
> > + if (stop)
> > + ieee80211_stop_queue(dev->hw, skb_get_queue_mapping(skb));
>
> I don't think taking this outside of spin_lock section is beneficial.
> Actually is better to do this faster than slower to prevent enqueue
> frames by mac80211 and then dropped them due to lack of space in
> mt76 queue.
ack, I will send a v2 moving it back.
Regards,
Lorenzo
>
> Stanislaw