From fc412aab0d34534ec318b6904bb63cd75487b708 Mon Sep 17 00:00:00 2001 From: Felix Fietkau Date: Thu, 3 Mar 2016 21:40:11 +0100 Subject: [PATCH] mt7603: use a skb queue for status queueing Signed-off-by: Felix Fietkau --- mt7603.h | 22 +++++----------------- mt7603_init.c | 2 +- mt7603_mac.c | 32 +++++++++++++++----------------- 3 files changed, 21 insertions(+), 35 deletions(-) diff --git a/mt7603.h b/mt7603.h index 3fd44f82..e8549280 100644 --- a/mt7603.h +++ b/mt7603.h @@ -85,7 +85,6 @@ struct mt7603_vif { #define MT7603_CB_TXS_FAILED BIT(2) struct mt7603_cb { - struct list_head list; u8 wcid; u8 pktid; u8 flags; @@ -107,7 +106,7 @@ struct mt7603_dev { struct mt76_wcid __rcu *wcid[MT7603_WTBL_SIZE]; spinlock_t status_lock; - struct list_head status_list; + struct sk_buff_head status_list; struct mt7603_sta global_sta; @@ -159,24 +158,13 @@ static inline bool is_mt7628(struct mt7603_dev *dev) static inline struct mt7603_cb *mt7603_skb_cb(struct sk_buff *skb) { - return ((void *) IEEE80211_SKB_CB(skb)->rate_driver_data) + - MT_RATE_DRIVER_DATA_OFFSET; -} - -static inline struct sk_buff *mt7603_cb_skb(struct mt7603_cb *cb) -{ - struct ieee80211_tx_info *info; - void *ptr = cb; - BUILD_BUG_ON(offsetof(struct ieee80211_tx_info, status.ampdu_len) >= (offsetof(struct ieee80211_tx_info, rate_driver_data) + MT_RATE_DRIVER_DATA_OFFSET)); - BUILD_BUG_ON(sizeof(*cb) + MT_RATE_DRIVER_DATA_OFFSET > - sizeof(info->rate_driver_data)); - info = container_of(ptr - MT_RATE_DRIVER_DATA_OFFSET, - struct ieee80211_tx_info, rate_driver_data); - ptr = info; - return container_of(ptr, struct sk_buff, cb); + BUILD_BUG_ON(sizeof(struct mt7603_cb) + MT_RATE_DRIVER_DATA_OFFSET > + IEEE80211_TX_INFO_RATE_DRIVER_DATA_SIZE); + return ((void *) IEEE80211_SKB_CB(skb)->rate_driver_data) + + MT_RATE_DRIVER_DATA_OFFSET; } u32 mt7603_reg_map(struct mt7603_dev *dev, u32 addr); diff --git a/mt7603_init.c b/mt7603_init.c index 3d986925..9a44d7e4 100644 --- a/mt7603_init.c +++ b/mt7603_init.c @@ -342,7 +342,7 @@ int mt7603_register_device(struct mt7603_dev *dev) mutex_init(&dev->mutex); spin_lock_init(&dev->status_lock); - INIT_LIST_HEAD(&dev->status_list); + __skb_queue_head_init(&dev->status_list); INIT_DELAYED_WORK(&dev->mac_work, mt7603_mac_work); tasklet_init(&dev->pre_tbtt_tasklet, mt7603_pre_tbtt_tasklet, (unsigned long) dev); diff --git a/mt7603_mac.c b/mt7603_mac.c index de8ff372..8c52ac13 100644 --- a/mt7603_mac.c +++ b/mt7603_mac.c @@ -703,11 +703,12 @@ int mt7603_tx_prepare_skb(struct mt76_dev *mdev, void *txwi_ptr, pid = msta->pid; cb->wcid = wcid->idx; cb->pktid = pid; - list_add_tail(&cb->list, &dev->status_list); + + __skb_queue_tail(&dev->status_list, skb); spin_unlock_bh(&dev->status_lock); } else { - INIT_LIST_HEAD(&cb->list); + skb->next = skb->prev = NULL; } mt7603_mac_write_txwi(dev, txwi_ptr, skb, q, wcid, sta, pid, key); @@ -793,25 +794,22 @@ mt7603_skb_done(struct mt7603_dev *dev, struct sk_buff *skb, u8 flags) struct sk_buff * mt7603_mac_status_skb(struct mt7603_dev *dev, struct mt7603_sta *sta, int pktid) { - struct mt7603_cb *cb, *tmp; - struct sk_buff *skb = NULL; + struct sk_buff *skb, *tmp; - list_for_each_entry_safe(cb, tmp, &dev->status_list, list) { + skb_queue_walk_safe(&dev->status_list, skb, tmp) { + struct mt7603_cb *cb = mt7603_skb_cb(skb); if (sta && cb->wcid != sta->wcid.idx) continue; - list_del_init(&cb->list); - skb = mt7603_cb_skb(cb); - + __skb_unlink(skb, &dev->status_list); if (cb->pktid == pktid) - break; + return skb; mt7603_skb_done(dev, skb, MT7603_CB_TXS_FAILED | MT7603_CB_TXS_DONE); - skb = NULL; } - return skb; + return NULL; } static bool @@ -886,28 +884,28 @@ void mt7603_tx_complete_skb(struct mt76_dev *mdev, struct mt76_queue *q, struct mt76_queue_entry *e, bool flush) { struct mt7603_dev *dev = container_of(mdev, struct mt7603_dev, mt76); - struct mt7603_cb *cb = mt7603_skb_cb(e->skb); + struct sk_buff *skb = e->skb; bool free = true; if (!e->txwi) { - dev_kfree_skb_any(e->skb); + dev_kfree_skb_any(skb); return; } /* will be freed by tx status handling codepath */ - if (!list_empty(&cb->list)) { + if (skb->prev) { spin_lock_bh(&dev->status_lock); if (!flush) { - mt7603_skb_done(dev, e->skb, MT7603_CB_DMA_DONE); + mt7603_skb_done(dev, skb, MT7603_CB_DMA_DONE); free = false; } else { - list_del_init(&cb->list); + __skb_unlink(skb, &dev->status_list); } spin_unlock_bh(&dev->status_lock); } if (free) - ieee80211_free_txskb(mdev->hw, e->skb); + ieee80211_free_txskb(mdev->hw, skb); } static bool