aboutsummaryrefslogtreecommitdiffstats
path: root/net/mac80211
diff options
context:
space:
mode:
authorFelix Fietkau <nbd@openwrt.org>2015-03-27 16:30:37 -0400
committerJohannes Berg <johannes.berg@intel.com>2015-04-01 14:44:34 -0400
commitba8c3d6f16a1f9305c23ac1d2fd3992508c5ac03 (patch)
treec03bbdf0affccbd1f3a4fd0c239e59bb44f28e99 /net/mac80211
parentcef2fc1ce4326f7f24c3cf938b94a661fbe773e3 (diff)
mac80211: add an intermediate software queue implementation
This allows drivers to request per-vif and per-sta-tid queues from which they can pull frames. This makes it easier to keep the hardware queues short, and to improve fairness between clients and vifs. The task of scheduling packet transmission is left up to the driver - queueing is controlled by mac80211. Drivers can only dequeue packets by calling ieee80211_tx_dequeue. This makes it possible to add active queue management later without changing drivers using this code. This can also be used as a starting point to implement A-MSDU aggregation in a way that does not add artificially induced latency. Signed-off-by: Felix Fietkau <nbd@openwrt.org> [resolved minor context conflict, minor changes, endian annotations] Signed-off-by: Johannes Berg <johannes.berg@intel.com>
Diffstat (limited to 'net/mac80211')
-rw-r--r--net/mac80211/agg-tx.c44
-rw-r--r--net/mac80211/driver-ops.h12
-rw-r--r--net/mac80211/ieee80211_i.h21
-rw-r--r--net/mac80211/iface.c23
-rw-r--r--net/mac80211/main.c3
-rw-r--r--net/mac80211/rx.c13
-rw-r--r--net/mac80211/sta_info.c83
-rw-r--r--net/mac80211/sta_info.h2
-rw-r--r--net/mac80211/trace.h31
-rw-r--r--net/mac80211/tx.c115
-rw-r--r--net/mac80211/util.c22
11 files changed, 350 insertions, 19 deletions
diff --git a/net/mac80211/agg-tx.c b/net/mac80211/agg-tx.c
index 20522492d8cc..cce9d425c718 100644
--- a/net/mac80211/agg-tx.c
+++ b/net/mac80211/agg-tx.c
@@ -188,6 +188,43 @@ ieee80211_wake_queue_agg(struct ieee80211_sub_if_data *sdata, int tid)
188 __release(agg_queue); 188 __release(agg_queue);
189} 189}
190 190
191static void
192ieee80211_agg_stop_txq(struct sta_info *sta, int tid)
193{
194 struct ieee80211_txq *txq = sta->sta.txq[tid];
195 struct txq_info *txqi;
196
197 if (!txq)
198 return;
199
200 txqi = to_txq_info(txq);
201
202 /* Lock here to protect against further seqno updates on dequeue */
203 spin_lock_bh(&txqi->queue.lock);
204 set_bit(IEEE80211_TXQ_STOP, &txqi->flags);
205 spin_unlock_bh(&txqi->queue.lock);
206}
207
208static void
209ieee80211_agg_start_txq(struct sta_info *sta, int tid, bool enable)
210{
211 struct ieee80211_txq *txq = sta->sta.txq[tid];
212 struct txq_info *txqi;
213
214 if (!txq)
215 return;
216
217 txqi = to_txq_info(txq);
218
219 if (enable)
220 set_bit(IEEE80211_TXQ_AMPDU, &txqi->flags);
221 else
222 clear_bit(IEEE80211_TXQ_AMPDU, &txqi->flags);
223
224 clear_bit(IEEE80211_TXQ_STOP, &txqi->flags);
225 drv_wake_tx_queue(sta->sdata->local, txqi);
226}
227
191/* 228/*
192 * splice packets from the STA's pending to the local pending, 229 * splice packets from the STA's pending to the local pending,
193 * requires a call to ieee80211_agg_splice_finish later 230 * requires a call to ieee80211_agg_splice_finish later
@@ -247,6 +284,7 @@ static void ieee80211_remove_tid_tx(struct sta_info *sta, int tid)
247 ieee80211_assign_tid_tx(sta, tid, NULL); 284 ieee80211_assign_tid_tx(sta, tid, NULL);
248 285
249 ieee80211_agg_splice_finish(sta->sdata, tid); 286 ieee80211_agg_splice_finish(sta->sdata, tid);
287 ieee80211_agg_start_txq(sta, tid, false);
250 288
251 kfree_rcu(tid_tx, rcu_head); 289 kfree_rcu(tid_tx, rcu_head);
252} 290}
@@ -418,6 +456,8 @@ void ieee80211_tx_ba_session_handle_start(struct sta_info *sta, int tid)
418 */ 456 */
419 clear_bit(HT_AGG_STATE_WANT_START, &tid_tx->state); 457 clear_bit(HT_AGG_STATE_WANT_START, &tid_tx->state);
420 458
459 ieee80211_agg_stop_txq(sta, tid);
460
421 /* 461 /*
422 * Make sure no packets are being processed. This ensures that 462 * Make sure no packets are being processed. This ensures that
423 * we have a valid starting sequence number and that in-flight 463 * we have a valid starting sequence number and that in-flight
@@ -440,6 +480,8 @@ void ieee80211_tx_ba_session_handle_start(struct sta_info *sta, int tid)
440 ieee80211_agg_splice_finish(sdata, tid); 480 ieee80211_agg_splice_finish(sdata, tid);
441 spin_unlock_bh(&sta->lock); 481 spin_unlock_bh(&sta->lock);
442 482
483 ieee80211_agg_start_txq(sta, tid, false);
484
443 kfree_rcu(tid_tx, rcu_head); 485 kfree_rcu(tid_tx, rcu_head);
444 return; 486 return;
445 } 487 }
@@ -669,6 +711,8 @@ static void ieee80211_agg_tx_operational(struct ieee80211_local *local,
669 ieee80211_agg_splice_finish(sta->sdata, tid); 711 ieee80211_agg_splice_finish(sta->sdata, tid);
670 712
671 spin_unlock_bh(&sta->lock); 713 spin_unlock_bh(&sta->lock);
714
715 ieee80211_agg_start_txq(sta, tid, true);
672} 716}
673 717
674void ieee80211_start_tx_ba_cb(struct ieee80211_vif *vif, u8 *ra, u16 tid) 718void ieee80211_start_tx_ba_cb(struct ieee80211_vif *vif, u8 *ra, u16 tid)
diff --git a/net/mac80211/driver-ops.h b/net/mac80211/driver-ops.h
index 0a39d3db951a..26e1ca8a474a 100644
--- a/net/mac80211/driver-ops.h
+++ b/net/mac80211/driver-ops.h
@@ -1367,4 +1367,16 @@ drv_tdls_recv_channel_switch(struct ieee80211_local *local,
1367 trace_drv_return_void(local); 1367 trace_drv_return_void(local);
1368} 1368}
1369 1369
1370static inline void drv_wake_tx_queue(struct ieee80211_local *local,
1371 struct txq_info *txq)
1372{
1373 struct ieee80211_sub_if_data *sdata = vif_to_sdata(txq->txq.vif);
1374
1375 if (!check_sdata_in_driver(sdata))
1376 return;
1377
1378 trace_drv_wake_tx_queue(local, sdata, txq);
1379 local->ops->wake_tx_queue(&local->hw, &txq->txq);
1380}
1381
1370#endif /* __MAC80211_DRIVER_OPS */ 1382#endif /* __MAC80211_DRIVER_OPS */
diff --git a/net/mac80211/ieee80211_i.h b/net/mac80211/ieee80211_i.h
index 3c1512b0442c..04b32f3e0395 100644
--- a/net/mac80211/ieee80211_i.h
+++ b/net/mac80211/ieee80211_i.h
@@ -811,6 +811,19 @@ struct mac80211_qos_map {
811 struct rcu_head rcu_head; 811 struct rcu_head rcu_head;
812}; 812};
813 813
814enum txq_info_flags {
815 IEEE80211_TXQ_STOP,
816 IEEE80211_TXQ_AMPDU,
817};
818
819struct txq_info {
820 struct sk_buff_head queue;
821 unsigned long flags;
822
823 /* keep last! */
824 struct ieee80211_txq txq;
825};
826
814struct ieee80211_sub_if_data { 827struct ieee80211_sub_if_data {
815 struct list_head list; 828 struct list_head list;
816 829
@@ -853,6 +866,7 @@ struct ieee80211_sub_if_data {
853 bool control_port_no_encrypt; 866 bool control_port_no_encrypt;
854 int encrypt_headroom; 867 int encrypt_headroom;
855 868
869 atomic_t txqs_len[IEEE80211_NUM_ACS];
856 struct ieee80211_tx_queue_params tx_conf[IEEE80211_NUM_ACS]; 870 struct ieee80211_tx_queue_params tx_conf[IEEE80211_NUM_ACS];
857 struct mac80211_qos_map __rcu *qos_map; 871 struct mac80211_qos_map __rcu *qos_map;
858 872
@@ -1450,6 +1464,10 @@ static inline struct ieee80211_local *hw_to_local(
1450 return container_of(hw, struct ieee80211_local, hw); 1464 return container_of(hw, struct ieee80211_local, hw);
1451} 1465}
1452 1466
1467static inline struct txq_info *to_txq_info(struct ieee80211_txq *txq)
1468{
1469 return container_of(txq, struct txq_info, txq);
1470}
1453 1471
1454static inline int ieee80211_bssid_match(const u8 *raddr, const u8 *addr) 1472static inline int ieee80211_bssid_match(const u8 *raddr, const u8 *addr)
1455{ 1473{
@@ -1906,6 +1924,9 @@ static inline bool ieee80211_can_run_worker(struct ieee80211_local *local)
1906 return true; 1924 return true;
1907} 1925}
1908 1926
1927void ieee80211_init_tx_queue(struct ieee80211_sub_if_data *sdata,
1928 struct sta_info *sta,
1929 struct txq_info *txq, int tid);
1909void ieee80211_send_auth(struct ieee80211_sub_if_data *sdata, 1930void ieee80211_send_auth(struct ieee80211_sub_if_data *sdata,
1910 u16 transaction, u16 auth_alg, u16 status, 1931 u16 transaction, u16 auth_alg, u16 status,
1911 const u8 *extra, size_t extra_len, const u8 *bssid, 1932 const u8 *extra, size_t extra_len, const u8 *bssid,
diff --git a/net/mac80211/iface.c b/net/mac80211/iface.c
index a0cd97fd0c49..b4ac596a7cb7 100644
--- a/net/mac80211/iface.c
+++ b/net/mac80211/iface.c
@@ -969,6 +969,13 @@ static void ieee80211_do_stop(struct ieee80211_sub_if_data *sdata,
969 } 969 }
970 spin_unlock_irqrestore(&local->queue_stop_reason_lock, flags); 970 spin_unlock_irqrestore(&local->queue_stop_reason_lock, flags);
971 971
972 if (sdata->vif.txq) {
973 struct txq_info *txqi = to_txq_info(sdata->vif.txq);
974
975 ieee80211_purge_tx_queue(&local->hw, &txqi->queue);
976 atomic_set(&sdata->txqs_len[txqi->txq.ac], 0);
977 }
978
972 if (local->open_count == 0) 979 if (local->open_count == 0)
973 ieee80211_clear_tx_pending(local); 980 ieee80211_clear_tx_pending(local);
974 981
@@ -1654,6 +1661,7 @@ int ieee80211_if_add(struct ieee80211_local *local, const char *name,
1654{ 1661{
1655 struct net_device *ndev = NULL; 1662 struct net_device *ndev = NULL;
1656 struct ieee80211_sub_if_data *sdata = NULL; 1663 struct ieee80211_sub_if_data *sdata = NULL;
1664 struct txq_info *txqi;
1657 int ret, i; 1665 int ret, i;
1658 int txqs = 1; 1666 int txqs = 1;
1659 1667
@@ -1673,10 +1681,18 @@ int ieee80211_if_add(struct ieee80211_local *local, const char *name,
1673 ieee80211_assign_perm_addr(local, wdev->address, type); 1681 ieee80211_assign_perm_addr(local, wdev->address, type);
1674 memcpy(sdata->vif.addr, wdev->address, ETH_ALEN); 1682 memcpy(sdata->vif.addr, wdev->address, ETH_ALEN);
1675 } else { 1683 } else {
1684 int size = ALIGN(sizeof(*sdata) + local->hw.vif_data_size,
1685 sizeof(void *));
1686 int txq_size = 0;
1687
1688 if (local->ops->wake_tx_queue)
1689 txq_size += sizeof(struct txq_info) +
1690 local->hw.txq_data_size;
1691
1676 if (local->hw.queues >= IEEE80211_NUM_ACS) 1692 if (local->hw.queues >= IEEE80211_NUM_ACS)
1677 txqs = IEEE80211_NUM_ACS; 1693 txqs = IEEE80211_NUM_ACS;
1678 1694
1679 ndev = alloc_netdev_mqs(sizeof(*sdata) + local->hw.vif_data_size, 1695 ndev = alloc_netdev_mqs(size + txq_size,
1680 name, name_assign_type, 1696 name, name_assign_type,
1681 ieee80211_if_setup, txqs, 1); 1697 ieee80211_if_setup, txqs, 1);
1682 if (!ndev) 1698 if (!ndev)
@@ -1711,6 +1727,11 @@ int ieee80211_if_add(struct ieee80211_local *local, const char *name,
1711 memcpy(sdata->vif.addr, ndev->dev_addr, ETH_ALEN); 1727 memcpy(sdata->vif.addr, ndev->dev_addr, ETH_ALEN);
1712 memcpy(sdata->name, ndev->name, IFNAMSIZ); 1728 memcpy(sdata->name, ndev->name, IFNAMSIZ);
1713 1729
1730 if (txq_size) {
1731 txqi = netdev_priv(ndev) + size;
1732 ieee80211_init_tx_queue(sdata, NULL, txqi, 0);
1733 }
1734
1714 sdata->dev = ndev; 1735 sdata->dev = ndev;
1715 } 1736 }
1716 1737
diff --git a/net/mac80211/main.c b/net/mac80211/main.c
index 51e0332a4589..df3051d96aff 100644
--- a/net/mac80211/main.c
+++ b/net/mac80211/main.c
@@ -1039,6 +1039,9 @@ int ieee80211_register_hw(struct ieee80211_hw *hw)
1039 1039
1040 local->dynamic_ps_forced_timeout = -1; 1040 local->dynamic_ps_forced_timeout = -1;
1041 1041
1042 if (!local->hw.txq_ac_max_pending)
1043 local->hw.txq_ac_max_pending = 64;
1044
1042 result = ieee80211_wep_init(local); 1045 result = ieee80211_wep_init(local);
1043 if (result < 0) 1046 if (result < 0)
1044 wiphy_debug(local->hw.wiphy, "Failed to initialize wep: %d\n", 1047 wiphy_debug(local->hw.wiphy, "Failed to initialize wep: %d\n",
diff --git a/net/mac80211/rx.c b/net/mac80211/rx.c
index 5b60bcf00ec3..bc59c8a20a39 100644
--- a/net/mac80211/rx.c
+++ b/net/mac80211/rx.c
@@ -1184,6 +1184,7 @@ static void sta_ps_start(struct sta_info *sta)
1184 struct ieee80211_sub_if_data *sdata = sta->sdata; 1184 struct ieee80211_sub_if_data *sdata = sta->sdata;
1185 struct ieee80211_local *local = sdata->local; 1185 struct ieee80211_local *local = sdata->local;
1186 struct ps_data *ps; 1186 struct ps_data *ps;
1187 int tid;
1187 1188
1188 if (sta->sdata->vif.type == NL80211_IFTYPE_AP || 1189 if (sta->sdata->vif.type == NL80211_IFTYPE_AP ||
1189 sta->sdata->vif.type == NL80211_IFTYPE_AP_VLAN) 1190 sta->sdata->vif.type == NL80211_IFTYPE_AP_VLAN)
@@ -1197,6 +1198,18 @@ static void sta_ps_start(struct sta_info *sta)
1197 drv_sta_notify(local, sdata, STA_NOTIFY_SLEEP, &sta->sta); 1198 drv_sta_notify(local, sdata, STA_NOTIFY_SLEEP, &sta->sta);
1198 ps_dbg(sdata, "STA %pM aid %d enters power save mode\n", 1199 ps_dbg(sdata, "STA %pM aid %d enters power save mode\n",
1199 sta->sta.addr, sta->sta.aid); 1200 sta->sta.addr, sta->sta.aid);
1201
1202 if (!sta->sta.txq[0])
1203 return;
1204
1205 for (tid = 0; tid < ARRAY_SIZE(sta->sta.txq); tid++) {
1206 struct txq_info *txqi = to_txq_info(sta->sta.txq[tid]);
1207
1208 if (!skb_queue_len(&txqi->queue))
1209 set_bit(tid, &sta->txq_buffered_tids);
1210 else
1211 clear_bit(tid, &sta->txq_buffered_tids);
1212 }
1200} 1213}
1201 1214
1202static void sta_ps_end(struct sta_info *sta) 1215static void sta_ps_end(struct sta_info *sta)
diff --git a/net/mac80211/sta_info.c b/net/mac80211/sta_info.c
index 81cc499fa4a9..12971b71d0fa 100644
--- a/net/mac80211/sta_info.c
+++ b/net/mac80211/sta_info.c
@@ -106,6 +106,16 @@ static void __cleanup_single_sta(struct sta_info *sta)
106 atomic_dec(&ps->num_sta_ps); 106 atomic_dec(&ps->num_sta_ps);
107 } 107 }
108 108
109 if (sta->sta.txq[0]) {
110 for (i = 0; i < ARRAY_SIZE(sta->sta.txq); i++) {
111 struct txq_info *txqi = to_txq_info(sta->sta.txq[i]);
112 int n = skb_queue_len(&txqi->queue);
113
114 ieee80211_purge_tx_queue(&local->hw, &txqi->queue);
115 atomic_sub(n, &sdata->txqs_len[txqi->txq.ac]);
116 }
117 }
118
109 for (ac = 0; ac < IEEE80211_NUM_ACS; ac++) { 119 for (ac = 0; ac < IEEE80211_NUM_ACS; ac++) {
110 local->total_ps_buffered -= skb_queue_len(&sta->ps_tx_buf[ac]); 120 local->total_ps_buffered -= skb_queue_len(&sta->ps_tx_buf[ac]);
111 ieee80211_purge_tx_queue(&local->hw, &sta->ps_tx_buf[ac]); 121 ieee80211_purge_tx_queue(&local->hw, &sta->ps_tx_buf[ac]);
@@ -218,6 +228,8 @@ void sta_info_free(struct ieee80211_local *local, struct sta_info *sta)
218 228
219 sta_dbg(sta->sdata, "Destroyed STA %pM\n", sta->sta.addr); 229 sta_dbg(sta->sdata, "Destroyed STA %pM\n", sta->sta.addr);
220 230
231 if (sta->sta.txq[0])
232 kfree(to_txq_info(sta->sta.txq[0]));
221 kfree(rcu_dereference_raw(sta->sta.rates)); 233 kfree(rcu_dereference_raw(sta->sta.rates));
222 kfree(sta); 234 kfree(sta);
223} 235}
@@ -268,11 +280,12 @@ struct sta_info *sta_info_alloc(struct ieee80211_sub_if_data *sdata,
268 const u8 *addr, gfp_t gfp) 280 const u8 *addr, gfp_t gfp)
269{ 281{
270 struct ieee80211_local *local = sdata->local; 282 struct ieee80211_local *local = sdata->local;
283 struct ieee80211_hw *hw = &local->hw;
271 struct sta_info *sta; 284 struct sta_info *sta;
272 struct timespec uptime; 285 struct timespec uptime;
273 int i; 286 int i;
274 287
275 sta = kzalloc(sizeof(*sta) + local->hw.sta_data_size, gfp); 288 sta = kzalloc(sizeof(*sta) + hw->sta_data_size, gfp);
276 if (!sta) 289 if (!sta)
277 return NULL; 290 return NULL;
278 291
@@ -304,11 +317,25 @@ struct sta_info *sta_info_alloc(struct ieee80211_sub_if_data *sdata,
304 for (i = 0; i < ARRAY_SIZE(sta->chain_signal_avg); i++) 317 for (i = 0; i < ARRAY_SIZE(sta->chain_signal_avg); i++)
305 ewma_init(&sta->chain_signal_avg[i], 1024, 8); 318 ewma_init(&sta->chain_signal_avg[i], 1024, 8);
306 319
307 if (sta_prepare_rate_control(local, sta, gfp)) { 320 if (local->ops->wake_tx_queue) {
308 kfree(sta); 321 void *txq_data;
309 return NULL; 322 int size = sizeof(struct txq_info) +
323 ALIGN(hw->txq_data_size, sizeof(void *));
324
325 txq_data = kcalloc(ARRAY_SIZE(sta->sta.txq), size, gfp);
326 if (!txq_data)
327 goto free;
328
329 for (i = 0; i < ARRAY_SIZE(sta->sta.txq); i++) {
330 struct txq_info *txq = txq_data + i * size;
331
332 ieee80211_init_tx_queue(sdata, sta, txq, i);
333 }
310 } 334 }
311 335
336 if (sta_prepare_rate_control(local, sta, gfp))
337 goto free_txq;
338
312 for (i = 0; i < IEEE80211_NUM_TIDS; i++) { 339 for (i = 0; i < IEEE80211_NUM_TIDS; i++) {
313 /* 340 /*
314 * timer_to_tid must be initialized with identity mapping 341 * timer_to_tid must be initialized with identity mapping
@@ -329,7 +356,7 @@ struct sta_info *sta_info_alloc(struct ieee80211_sub_if_data *sdata,
329 if (sdata->vif.type == NL80211_IFTYPE_AP || 356 if (sdata->vif.type == NL80211_IFTYPE_AP ||
330 sdata->vif.type == NL80211_IFTYPE_AP_VLAN) { 357 sdata->vif.type == NL80211_IFTYPE_AP_VLAN) {
331 struct ieee80211_supported_band *sband = 358 struct ieee80211_supported_band *sband =
332 local->hw.wiphy->bands[ieee80211_get_sdata_band(sdata)]; 359 hw->wiphy->bands[ieee80211_get_sdata_band(sdata)];
333 u8 smps = (sband->ht_cap.cap & IEEE80211_HT_CAP_SM_PS) >> 360 u8 smps = (sband->ht_cap.cap & IEEE80211_HT_CAP_SM_PS) >>
334 IEEE80211_HT_CAP_SM_PS_SHIFT; 361 IEEE80211_HT_CAP_SM_PS_SHIFT;
335 /* 362 /*
@@ -354,6 +381,13 @@ struct sta_info *sta_info_alloc(struct ieee80211_sub_if_data *sdata,
354 sta_dbg(sdata, "Allocated STA %pM\n", sta->sta.addr); 381 sta_dbg(sdata, "Allocated STA %pM\n", sta->sta.addr);
355 382
356 return sta; 383 return sta;
384
385free_txq:
386 if (sta->sta.txq[0])
387 kfree(to_txq_info(sta->sta.txq[0]));
388free:
389 kfree(sta);
390 return NULL;
357} 391}
358 392
359static int sta_info_insert_check(struct sta_info *sta) 393static int sta_info_insert_check(struct sta_info *sta)
@@ -623,6 +657,8 @@ static void __sta_info_recalc_tim(struct sta_info *sta, bool ignore_pending)
623 657
624 indicate_tim |= 658 indicate_tim |=
625 sta->driver_buffered_tids & tids; 659 sta->driver_buffered_tids & tids;
660 indicate_tim |=
661 sta->txq_buffered_tids & tids;
626 } 662 }
627 663
628 done: 664 done:
@@ -1072,7 +1108,7 @@ void ieee80211_sta_ps_deliver_wakeup(struct sta_info *sta)
1072 struct ieee80211_sub_if_data *sdata = sta->sdata; 1108 struct ieee80211_sub_if_data *sdata = sta->sdata;
1073 struct ieee80211_local *local = sdata->local; 1109 struct ieee80211_local *local = sdata->local;
1074 struct sk_buff_head pending; 1110 struct sk_buff_head pending;
1075 int filtered = 0, buffered = 0, ac; 1111 int filtered = 0, buffered = 0, ac, i;
1076 unsigned long flags; 1112 unsigned long flags;
1077 struct ps_data *ps; 1113 struct ps_data *ps;
1078 1114
@@ -1091,10 +1127,22 @@ void ieee80211_sta_ps_deliver_wakeup(struct sta_info *sta)
1091 1127
1092 BUILD_BUG_ON(BITS_TO_LONGS(IEEE80211_NUM_TIDS) > 1); 1128 BUILD_BUG_ON(BITS_TO_LONGS(IEEE80211_NUM_TIDS) > 1);
1093 sta->driver_buffered_tids = 0; 1129 sta->driver_buffered_tids = 0;
1130 sta->txq_buffered_tids = 0;
1094 1131
1095 if (!(local->hw.flags & IEEE80211_HW_AP_LINK_PS)) 1132 if (!(local->hw.flags & IEEE80211_HW_AP_LINK_PS))
1096 drv_sta_notify(local, sdata, STA_NOTIFY_AWAKE, &sta->sta); 1133 drv_sta_notify(local, sdata, STA_NOTIFY_AWAKE, &sta->sta);
1097 1134
1135 if (sta->sta.txq[0]) {
1136 for (i = 0; i < ARRAY_SIZE(sta->sta.txq); i++) {
1137 struct txq_info *txqi = to_txq_info(sta->sta.txq[i]);
1138
1139 if (!skb_queue_len(&txqi->queue))
1140 continue;
1141
1142 drv_wake_tx_queue(local, txqi);
1143 }
1144 }
1145
1098 skb_queue_head_init(&pending); 1146 skb_queue_head_init(&pending);
1099 1147
1100 /* sync with ieee80211_tx_h_unicast_ps_buf */ 1148 /* sync with ieee80211_tx_h_unicast_ps_buf */
@@ -1276,8 +1324,10 @@ ieee80211_sta_ps_deliver_response(struct sta_info *sta,
1276 /* if we already have frames from software, then we can't also 1324 /* if we already have frames from software, then we can't also
1277 * release from hardware queues 1325 * release from hardware queues
1278 */ 1326 */
1279 if (skb_queue_empty(&frames)) 1327 if (skb_queue_empty(&frames)) {
1280 driver_release_tids |= sta->driver_buffered_tids & tids; 1328 driver_release_tids |= sta->driver_buffered_tids & tids;
1329 driver_release_tids |= sta->txq_buffered_tids & tids;
1330 }
1281 1331
1282 if (driver_release_tids) { 1332 if (driver_release_tids) {
1283 /* If the driver has data on more than one TID then 1333 /* If the driver has data on more than one TID then
@@ -1448,6 +1498,9 @@ ieee80211_sta_ps_deliver_response(struct sta_info *sta,
1448 1498
1449 sta_info_recalc_tim(sta); 1499 sta_info_recalc_tim(sta);
1450 } else { 1500 } else {
1501 unsigned long tids = sta->txq_buffered_tids & driver_release_tids;
1502 int tid;
1503
1451 /* 1504 /*
1452 * We need to release a frame that is buffered somewhere in the 1505 * We need to release a frame that is buffered somewhere in the
1453 * driver ... it'll have to handle that. 1506 * driver ... it'll have to handle that.
@@ -1467,8 +1520,22 @@ ieee80211_sta_ps_deliver_response(struct sta_info *sta,
1467 * that the TID(s) became empty before returning here from the 1520 * that the TID(s) became empty before returning here from the
1468 * release function. 1521 * release function.
1469 * Either way, however, when the driver tells us that the TID(s) 1522 * Either way, however, when the driver tells us that the TID(s)
1470 * became empty we'll do the TIM recalculation. 1523 * became empty or we find that a txq became empty, we'll do the
1524 * TIM recalculation.
1471 */ 1525 */
1526
1527 if (!sta->sta.txq[0])
1528 return;
1529
1530 for (tid = 0; tid < ARRAY_SIZE(sta->sta.txq); tid++) {
1531 struct txq_info *txqi = to_txq_info(sta->sta.txq[tid]);
1532
1533 if (!(tids & BIT(tid)) || skb_queue_len(&txqi->queue))
1534 continue;
1535
1536 sta_info_recalc_tim(sta);
1537 break;
1538 }
1472 } 1539 }
1473} 1540}
1474 1541
diff --git a/net/mac80211/sta_info.h b/net/mac80211/sta_info.h
index 97f25b9e52be..691d8a1f94a5 100644
--- a/net/mac80211/sta_info.h
+++ b/net/mac80211/sta_info.h
@@ -275,6 +275,7 @@ struct sta_ampdu_mlme {
275 * entered power saving state, these are also delivered to 275 * entered power saving state, these are also delivered to
276 * the station when it leaves powersave or polls for frames 276 * the station when it leaves powersave or polls for frames
277 * @driver_buffered_tids: bitmap of TIDs the driver has data buffered on 277 * @driver_buffered_tids: bitmap of TIDs the driver has data buffered on
278 * @txq_buffered_tids: bitmap of TIDs that mac80211 has txq data buffered on
278 * @rx_packets: Number of MSDUs received from this STA 279 * @rx_packets: Number of MSDUs received from this STA
279 * @rx_bytes: Number of bytes received from this STA 280 * @rx_bytes: Number of bytes received from this STA
280 * @last_rx: time (in jiffies) when last frame was received from this STA 281 * @last_rx: time (in jiffies) when last frame was received from this STA
@@ -369,6 +370,7 @@ struct sta_info {
369 struct sk_buff_head ps_tx_buf[IEEE80211_NUM_ACS]; 370 struct sk_buff_head ps_tx_buf[IEEE80211_NUM_ACS];
370 struct sk_buff_head tx_filtered[IEEE80211_NUM_ACS]; 371 struct sk_buff_head tx_filtered[IEEE80211_NUM_ACS];
371 unsigned long driver_buffered_tids; 372 unsigned long driver_buffered_tids;
373 unsigned long txq_buffered_tids;
372 374
373 /* Updated from RX path only, no locking requirements */ 375 /* Updated from RX path only, no locking requirements */
374 unsigned long rx_packets; 376 unsigned long rx_packets;
diff --git a/net/mac80211/trace.h b/net/mac80211/trace.h
index e9e462b349e5..790bd45081c4 100644
--- a/net/mac80211/trace.h
+++ b/net/mac80211/trace.h
@@ -2312,6 +2312,37 @@ TRACE_EVENT(drv_tdls_recv_channel_switch,
2312 ) 2312 )
2313); 2313);
2314 2314
2315TRACE_EVENT(drv_wake_tx_queue,
2316 TP_PROTO(struct ieee80211_local *local,
2317 struct ieee80211_sub_if_data *sdata,
2318 struct txq_info *txq),
2319
2320 TP_ARGS(local, sdata, txq),
2321
2322 TP_STRUCT__entry(
2323 LOCAL_ENTRY
2324 VIF_ENTRY
2325 STA_ENTRY
2326 __field(u8, ac)
2327 __field(u8, tid)
2328 ),
2329
2330 TP_fast_assign(
2331 struct ieee80211_sta *sta = txq->txq.sta;
2332
2333 LOCAL_ASSIGN;
2334 VIF_ASSIGN;
2335 STA_ASSIGN;
2336 __entry->ac = txq->txq.ac;
2337 __entry->tid = txq->txq.tid;
2338 ),
2339
2340 TP_printk(
2341 LOCAL_PR_FMT VIF_PR_FMT STA_PR_FMT " ac:%d tid:%d",
2342 LOCAL_PR_ARG, VIF_PR_ARG, STA_PR_ARG, __entry->ac, __entry->tid
2343 )
2344);
2345
2315#ifdef CONFIG_MAC80211_MESSAGE_TRACING 2346#ifdef CONFIG_MAC80211_MESSAGE_TRACING
2316#undef TRACE_SYSTEM 2347#undef TRACE_SYSTEM
2317#define TRACE_SYSTEM mac80211_msg 2348#define TRACE_SYSTEM mac80211_msg
diff --git a/net/mac80211/tx.c b/net/mac80211/tx.c
index 9f7fb4eec37b..667111ee6a20 100644
--- a/net/mac80211/tx.c
+++ b/net/mac80211/tx.c
@@ -767,12 +767,22 @@ ieee80211_tx_h_rate_ctrl(struct ieee80211_tx_data *tx)
767 return TX_CONTINUE; 767 return TX_CONTINUE;
768} 768}
769 769
770static __le16 ieee80211_tx_next_seq(struct sta_info *sta, int tid)
771{
772 u16 *seq = &sta->tid_seq[tid];
773 __le16 ret = cpu_to_le16(*seq);
774
775 /* Increase the sequence number. */
776 *seq = (*seq + 0x10) & IEEE80211_SCTL_SEQ;
777
778 return ret;
779}
780
770static ieee80211_tx_result debug_noinline 781static ieee80211_tx_result debug_noinline
771ieee80211_tx_h_sequence(struct ieee80211_tx_data *tx) 782ieee80211_tx_h_sequence(struct ieee80211_tx_data *tx)
772{ 783{
773 struct ieee80211_tx_info *info = IEEE80211_SKB_CB(tx->skb); 784 struct ieee80211_tx_info *info = IEEE80211_SKB_CB(tx->skb);
774 struct ieee80211_hdr *hdr = (struct ieee80211_hdr *)tx->skb->data; 785 struct ieee80211_hdr *hdr = (struct ieee80211_hdr *)tx->skb->data;
775 u16 *seq;
776 u8 *qc; 786 u8 *qc;
777 int tid; 787 int tid;
778 788
@@ -823,13 +833,10 @@ ieee80211_tx_h_sequence(struct ieee80211_tx_data *tx)
823 833
824 qc = ieee80211_get_qos_ctl(hdr); 834 qc = ieee80211_get_qos_ctl(hdr);
825 tid = *qc & IEEE80211_QOS_CTL_TID_MASK; 835 tid = *qc & IEEE80211_QOS_CTL_TID_MASK;
826 seq = &tx->sta->tid_seq[tid];
827 tx->sta->tx_msdu[tid]++; 836 tx->sta->tx_msdu[tid]++;
828 837
829 hdr->seq_ctrl = cpu_to_le16(*seq); 838 if (!tx->sta->sta.txq[0])
830 839 hdr->seq_ctrl = ieee80211_tx_next_seq(tx->sta, tid);
831 /* Increase the sequence number. */
832 *seq = (*seq + 0x10) & IEEE80211_SCTL_SEQ;
833 840
834 return TX_CONTINUE; 841 return TX_CONTINUE;
835} 842}
@@ -1070,7 +1077,7 @@ static bool ieee80211_tx_prep_agg(struct ieee80211_tx_data *tx,
1070 * nothing -- this aggregation session is being started 1077 * nothing -- this aggregation session is being started
1071 * but that might still fail with the driver 1078 * but that might still fail with the driver
1072 */ 1079 */
1073 } else { 1080 } else if (!tx->sta->sta.txq[tid]) {
1074 spin_lock(&tx->sta->lock); 1081 spin_lock(&tx->sta->lock);
1075 /* 1082 /*
1076 * Need to re-check now, because we may get here 1083 * Need to re-check now, because we may get here
@@ -1211,13 +1218,102 @@ ieee80211_tx_prepare(struct ieee80211_sub_if_data *sdata,
1211 return TX_CONTINUE; 1218 return TX_CONTINUE;
1212} 1219}
1213 1220
1221static void ieee80211_drv_tx(struct ieee80211_local *local,
1222 struct ieee80211_vif *vif,
1223 struct ieee80211_sta *pubsta,
1224 struct sk_buff *skb)
1225{
1226 struct ieee80211_hdr *hdr = (struct ieee80211_hdr *) skb->data;
1227 struct ieee80211_sub_if_data *sdata = vif_to_sdata(vif);
1228 struct ieee80211_tx_info *info = IEEE80211_SKB_CB(skb);
1229 struct ieee80211_tx_control control = {
1230 .sta = pubsta,
1231 };
1232 struct ieee80211_txq *txq = NULL;
1233 struct txq_info *txqi;
1234 u8 ac;
1235
1236 if (info->control.flags & IEEE80211_TX_CTRL_PS_RESPONSE)
1237 goto tx_normal;
1238
1239 if (!ieee80211_is_data(hdr->frame_control))
1240 goto tx_normal;
1241
1242 if (pubsta) {
1243 u8 tid = skb->priority & IEEE80211_QOS_CTL_TID_MASK;
1244
1245 txq = pubsta->txq[tid];
1246 } else if (vif) {
1247 txq = vif->txq;
1248 }
1249
1250 if (!txq)
1251 goto tx_normal;
1252
1253 ac = txq->ac;
1254 txqi = to_txq_info(txq);
1255 atomic_inc(&sdata->txqs_len[ac]);
1256 if (atomic_read(&sdata->txqs_len[ac]) >= local->hw.txq_ac_max_pending)
1257 netif_stop_subqueue(sdata->dev, ac);
1258
1259 skb_queue_tail(&txqi->queue, skb);
1260 drv_wake_tx_queue(local, txqi);
1261
1262 return;
1263
1264tx_normal:
1265 drv_tx(local, &control, skb);
1266}
1267
1268struct sk_buff *ieee80211_tx_dequeue(struct ieee80211_hw *hw,
1269 struct ieee80211_txq *txq)
1270{
1271 struct ieee80211_local *local = hw_to_local(hw);
1272 struct ieee80211_sub_if_data *sdata = vif_to_sdata(txq->vif);
1273 struct txq_info *txqi = container_of(txq, struct txq_info, txq);
1274 struct ieee80211_hdr *hdr;
1275 struct sk_buff *skb = NULL;
1276 u8 ac = txq->ac;
1277
1278 spin_lock_bh(&txqi->queue.lock);
1279
1280 if (test_bit(IEEE80211_TXQ_STOP, &txqi->flags))
1281 goto out;
1282
1283 skb = __skb_dequeue(&txqi->queue);
1284 if (!skb)
1285 goto out;
1286
1287 atomic_dec(&sdata->txqs_len[ac]);
1288 if (__netif_subqueue_stopped(sdata->dev, ac))
1289 ieee80211_propagate_queue_wake(local, sdata->vif.hw_queue[ac]);
1290
1291 hdr = (struct ieee80211_hdr *)skb->data;
1292 if (txq->sta && ieee80211_is_data_qos(hdr->frame_control)) {
1293 struct sta_info *sta = container_of(txq->sta, struct sta_info,
1294 sta);
1295 struct ieee80211_tx_info *info = IEEE80211_SKB_CB(skb);
1296
1297 hdr->seq_ctrl = ieee80211_tx_next_seq(sta, txq->tid);
1298 if (test_bit(IEEE80211_TXQ_AMPDU, &txqi->flags))
1299 info->flags |= IEEE80211_TX_CTL_AMPDU;
1300 else
1301 info->flags &= ~IEEE80211_TX_CTL_AMPDU;
1302 }
1303
1304out:
1305 spin_unlock_bh(&txqi->queue.lock);
1306
1307 return skb;
1308}
1309EXPORT_SYMBOL(ieee80211_tx_dequeue);
1310
1214static bool ieee80211_tx_frags(struct ieee80211_local *local, 1311static bool ieee80211_tx_frags(struct ieee80211_local *local,
1215 struct ieee80211_vif *vif, 1312 struct ieee80211_vif *vif,
1216 struct ieee80211_sta *sta, 1313 struct ieee80211_sta *sta,
1217 struct sk_buff_head *skbs, 1314 struct sk_buff_head *skbs,
1218 bool txpending) 1315 bool txpending)
1219{ 1316{
1220 struct ieee80211_tx_control control;
1221 struct sk_buff *skb, *tmp; 1317 struct sk_buff *skb, *tmp;
1222 unsigned long flags; 1318 unsigned long flags;
1223 1319
@@ -1275,10 +1371,9 @@ static bool ieee80211_tx_frags(struct ieee80211_local *local,
1275 spin_unlock_irqrestore(&local->queue_stop_reason_lock, flags); 1371 spin_unlock_irqrestore(&local->queue_stop_reason_lock, flags);
1276 1372
1277 info->control.vif = vif; 1373 info->control.vif = vif;
1278 control.sta = sta;
1279 1374
1280 __skb_unlink(skb, skbs); 1375 __skb_unlink(skb, skbs);
1281 drv_tx(local, &control, skb); 1376 ieee80211_drv_tx(local, vif, sta, skb);
1282 } 1377 }
1283 1378
1284 return true; 1379 return true;
diff --git a/net/mac80211/util.c b/net/mac80211/util.c
index d1742a7d9ea4..482b85c19a36 100644
--- a/net/mac80211/util.c
+++ b/net/mac80211/util.c
@@ -308,6 +308,11 @@ void ieee80211_propagate_queue_wake(struct ieee80211_local *local, int queue)
308 for (ac = 0; ac < n_acs; ac++) { 308 for (ac = 0; ac < n_acs; ac++) {
309 int ac_queue = sdata->vif.hw_queue[ac]; 309 int ac_queue = sdata->vif.hw_queue[ac];
310 310
311 if (local->ops->wake_tx_queue &&
312 (atomic_read(&sdata->txqs_len[ac]) >
313 local->hw.txq_ac_max_pending))
314 continue;
315
311 if (ac_queue == queue || 316 if (ac_queue == queue ||
312 (sdata->vif.cab_queue == queue && 317 (sdata->vif.cab_queue == queue &&
313 local->queue_stop_reasons[ac_queue] == 0 && 318 local->queue_stop_reasons[ac_queue] == 0 &&
@@ -3352,3 +3357,20 @@ u8 *ieee80211_add_wmm_info_ie(u8 *buf, u8 qosinfo)
3352 3357
3353 return buf; 3358 return buf;
3354} 3359}
3360
3361void ieee80211_init_tx_queue(struct ieee80211_sub_if_data *sdata,
3362 struct sta_info *sta,
3363 struct txq_info *txqi, int tid)
3364{
3365 skb_queue_head_init(&txqi->queue);
3366 txqi->txq.vif = &sdata->vif;
3367
3368 if (sta) {
3369 txqi->txq.sta = &sta->sta;
3370 sta->sta.txq[tid] = &txqi->txq;
3371 txqi->txq.ac = ieee802_1d_to_ac[tid & 7];
3372 } else {
3373 sdata->vif.txq = &txqi->txq;
3374 txqi->txq.ac = IEEE80211_AC_BE;
3375 }
3376}