wlcore: count packets held per AC in each vif
authorArik Nemtsov <arik@wizery.com>
Tue, 27 Nov 2012 06:44:58 +0000 (08:44 +0200)
committerLuciano Coelho <coelho@ti.com>
Wed, 5 Dec 2012 07:43:33 +0000 (09:43 +0200)
This accounting will help find a vif that has data in a specific AC.
Otherwise we have to traverse all the links, which can be lengthy for
the AP case.

Signed-off-by: Arik Nemtsov <arik@wizery.com>
Signed-off-by: Luciano Coelho <coelho@ti.com>
drivers/net/wireless/ti/wlcore/debugfs.c
drivers/net/wireless/ti/wlcore/main.c
drivers/net/wireless/ti/wlcore/ps.c
drivers/net/wireless/ti/wlcore/tx.c
drivers/net/wireless/ti/wlcore/wlcore_i.h

index e61fc2b..f115fba 100644 (file)
@@ -577,6 +577,10 @@ static ssize_t vifs_state_read(struct file *file, char __user *user_buf,
                        VIF_STATE_PRINT_INT(ap.ucast_rate_idx[3]);
                }
                VIF_STATE_PRINT_INT(last_tx_hlid);
+               VIF_STATE_PRINT_INT(tx_queue_count[0]);
+               VIF_STATE_PRINT_INT(tx_queue_count[1]);
+               VIF_STATE_PRINT_INT(tx_queue_count[2]);
+               VIF_STATE_PRINT_INT(tx_queue_count[3]);
                VIF_STATE_PRINT_LHEX(links_map[0]);
                VIF_STATE_PRINT_NSTR(ssid, wlvif->ssid_len);
                VIF_STATE_PRINT_INT(band);
index 7b1fc91..56ed379 100644 (file)
@@ -1206,6 +1206,8 @@ static void wl1271_op_tx(struct ieee80211_hw *hw,
        skb_queue_tail(&wl->links[hlid].tx_queue[q], skb);
 
        wl->tx_queue_count[q]++;
+       if (wlvif)
+               wlvif->tx_queue_count[q]++;
 
        /*
         * The workqueue is slow to process the tx_queue and we need stop
index ffcd843..9b7b6e2 100644 (file)
@@ -239,11 +239,12 @@ static void wl1271_ps_filter_frames(struct wl1271 *wl, u8 hlid)
        struct ieee80211_tx_info *info;
        unsigned long flags;
        int filtered[NUM_TX_QUEUES];
+       struct wl1271_link *lnk = &wl->links[hlid];
 
        /* filter all frames currently in the low level queues for this hlid */
        for (i = 0; i < NUM_TX_QUEUES; i++) {
                filtered[i] = 0;
-               while ((skb = skb_dequeue(&wl->links[hlid].tx_queue[i]))) {
+               while ((skb = skb_dequeue(&lnk->tx_queue[i]))) {
                        filtered[i]++;
 
                        if (WARN_ON(wl12xx_is_dummy_packet(wl, skb)))
@@ -257,8 +258,11 @@ static void wl1271_ps_filter_frames(struct wl1271 *wl, u8 hlid)
        }
 
        spin_lock_irqsave(&wl->wl_lock, flags);
-       for (i = 0; i < NUM_TX_QUEUES; i++)
+       for (i = 0; i < NUM_TX_QUEUES; i++) {
                wl->tx_queue_count[i] -= filtered[i];
+               if (lnk->wlvif)
+                       lnk->wlvif->tx_queue_count[i] -= filtered[i];
+       }
        spin_unlock_irqrestore(&wl->wl_lock, flags);
 
        wl1271_handle_tx_low_watermark(wl);
index c711c91..1ac8681 100644 (file)
@@ -514,6 +514,10 @@ static struct sk_buff *wl12xx_lnk_skb_dequeue(struct wl1271 *wl,
                spin_lock_irqsave(&wl->wl_lock, flags);
                WARN_ON_ONCE(wl->tx_queue_count[q] <= 0);
                wl->tx_queue_count[q]--;
+               if (lnk->wlvif) {
+                       WARN_ON_ONCE(lnk->wlvif->tx_queue_count[q] <= 0);
+                       lnk->wlvif->tx_queue_count[q]--;
+               }
                spin_unlock_irqrestore(&wl->wl_lock, flags);
        }
 
@@ -628,6 +632,8 @@ static void wl1271_skb_queue_head(struct wl1271 *wl, struct wl12xx_vif *wlvif,
 
        spin_lock_irqsave(&wl->wl_lock, flags);
        wl->tx_queue_count[q]++;
+       if (wlvif)
+               wlvif->tx_queue_count[q]++;
        spin_unlock_irqrestore(&wl->wl_lock, flags);
 }
 
@@ -977,10 +983,11 @@ void wl1271_tx_reset_link_queues(struct wl1271 *wl, u8 hlid)
        unsigned long flags;
        struct ieee80211_tx_info *info;
        int total[NUM_TX_QUEUES];
+       struct wl1271_link *lnk = &wl->links[hlid];
 
        for (i = 0; i < NUM_TX_QUEUES; i++) {
                total[i] = 0;
-               while ((skb = skb_dequeue(&wl->links[hlid].tx_queue[i]))) {
+               while ((skb = skb_dequeue(&lnk->tx_queue[i]))) {
                        wl1271_debug(DEBUG_TX, "link freeing skb 0x%p", skb);
 
                        if (!wl12xx_is_dummy_packet(wl, skb)) {
@@ -995,8 +1002,11 @@ void wl1271_tx_reset_link_queues(struct wl1271 *wl, u8 hlid)
        }
 
        spin_lock_irqsave(&wl->wl_lock, flags);
-       for (i = 0; i < NUM_TX_QUEUES; i++)
+       for (i = 0; i < NUM_TX_QUEUES; i++) {
                wl->tx_queue_count[i] -= total[i];
+               if (lnk->wlvif)
+                       lnk->wlvif->tx_queue_count[i] -= total[i];
+       }
        spin_unlock_irqrestore(&wl->wl_lock, flags);
 
        wl1271_handle_tx_low_watermark(wl);
@@ -1020,6 +1030,8 @@ void wl12xx_tx_reset_wlvif(struct wl1271 *wl, struct wl12xx_vif *wlvif)
        }
        wlvif->last_tx_hlid = 0;
 
+       for (i = 0; i < NUM_TX_QUEUES; i++)
+               wlvif->tx_queue_count[i] = 0;
 }
 /* caller must hold wl->mutex and TX must be stopped */
 void wl12xx_tx_reset(struct wl1271 *wl)
index 9ffbfc1..670d12f 100644 (file)
@@ -359,6 +359,9 @@ struct wl12xx_vif {
        /* the hlid of the last transmitted skb */
        int last_tx_hlid;
 
+       /* counters of packets per AC, across all links in the vif */
+       int tx_queue_count[NUM_TX_QUEUES];
+
        unsigned long links_map[BITS_TO_LONGS(WL12XX_MAX_LINKS)];
 
        u8 ssid[IEEE80211_MAX_SSID_LEN + 1];