agg-tx.c (ec034b208dc8aa5dc73ec46c3f27e34c5efbf113) agg-tx.c (40b275b69ee660274b77fb612b0db31fd282fc3f)
1/*
2 * HT handling
3 *
4 * Copyright 2003, Jouni Malinen <jkmaline@cc.hut.fi>
5 * Copyright 2002-2005, Instant802 Networks, Inc.
6 * Copyright 2005-2006, Devicescape Software, Inc.
7 * Copyright 2006-2007 Jiri Benc <jbenc@suse.cz>
8 * Copyright 2007, Michael Wu <flamingice@sourmilk.net>

--- 143 unchanged lines hidden (view full) ---

152 kfree(tid_tx);
153}
154
155int ___ieee80211_stop_tx_ba_session(struct sta_info *sta, u16 tid,
156 enum ieee80211_back_parties initiator,
157 bool tx)
158{
159 struct ieee80211_local *local = sta->local;
1/*
2 * HT handling
3 *
4 * Copyright 2003, Jouni Malinen <jkmaline@cc.hut.fi>
5 * Copyright 2002-2005, Instant802 Networks, Inc.
6 * Copyright 2005-2006, Devicescape Software, Inc.
7 * Copyright 2006-2007 Jiri Benc <jbenc@suse.cz>
8 * Copyright 2007, Michael Wu <flamingice@sourmilk.net>

--- 143 unchanged lines hidden (view full) ---

152 kfree(tid_tx);
153}
154
155int ___ieee80211_stop_tx_ba_session(struct sta_info *sta, u16 tid,
156 enum ieee80211_back_parties initiator,
157 bool tx)
158{
159 struct ieee80211_local *local = sta->local;
160 struct tid_ampdu_tx *tid_tx = sta->ampdu_mlme.tid_tx[tid];
160 struct tid_ampdu_tx *tid_tx;
161 int ret;
162
163 lockdep_assert_held(&sta->ampdu_mlme.mtx);
164
161 int ret;
162
163 lockdep_assert_held(&sta->ampdu_mlme.mtx);
164
165 if (!tid_tx)
166 return -ENOENT;
167
168 spin_lock_bh(&sta->lock);
169
165 spin_lock_bh(&sta->lock);
166
167 tid_tx = rcu_dereference_protected_tid_tx(sta, tid);
168 if (!tid_tx) {
169 spin_unlock_bh(&sta->lock);
170 return -ENOENT;
171 }
172
170 if (test_bit(HT_AGG_STATE_WANT_START, &tid_tx->state)) {
171 /* not even started yet! */
172 ieee80211_assign_tid_tx(sta, tid, NULL);
173 spin_unlock_bh(&sta->lock);
174 call_rcu(&tid_tx->rcu_head, kfree_tid_tx);
175 return 0;
176 }
177

--- 108 unchanged lines hidden (view full) ---

286 ieee80211_wake_queue_by_reason(
287 &local->hw, queue,
288 IEEE80211_QUEUE_STOP_REASON_AGGREGATION);
289 __release(agg_queue);
290}
291
292void ieee80211_tx_ba_session_handle_start(struct sta_info *sta, int tid)
293{
173 if (test_bit(HT_AGG_STATE_WANT_START, &tid_tx->state)) {
174 /* not even started yet! */
175 ieee80211_assign_tid_tx(sta, tid, NULL);
176 spin_unlock_bh(&sta->lock);
177 call_rcu(&tid_tx->rcu_head, kfree_tid_tx);
178 return 0;
179 }
180

--- 108 unchanged lines hidden (view full) ---

289 ieee80211_wake_queue_by_reason(
290 &local->hw, queue,
291 IEEE80211_QUEUE_STOP_REASON_AGGREGATION);
292 __release(agg_queue);
293}
294
295void ieee80211_tx_ba_session_handle_start(struct sta_info *sta, int tid)
296{
294 struct tid_ampdu_tx *tid_tx = sta->ampdu_mlme.tid_tx[tid];
297 struct tid_ampdu_tx *tid_tx;
295 struct ieee80211_local *local = sta->local;
296 struct ieee80211_sub_if_data *sdata = sta->sdata;
297 u16 start_seq_num;
298 int ret;
299
298 struct ieee80211_local *local = sta->local;
299 struct ieee80211_sub_if_data *sdata = sta->sdata;
300 u16 start_seq_num;
301 int ret;
302
300 lockdep_assert_held(&sta->ampdu_mlme.mtx);
303 tid_tx = rcu_dereference_protected_tid_tx(sta, tid);
301
302 /*
303 * While we're asking the driver about the aggregation,
304 * stop the AC queue so that we don't have to worry
305 * about frames that came in while we were doing that,
306 * which would require us to put them to the AC pending
307 * afterwards which just makes the code more complex.
308 */

--- 90 unchanged lines hidden (view full) ---

399 spin_lock_bh(&sta->lock);
400
401 /* we have tried too many times, receiver does not want A-MPDU */
402 if (sta->ampdu_mlme.addba_req_num[tid] > HT_AGG_MAX_RETRIES) {
403 ret = -EBUSY;
404 goto err_unlock_sta;
405 }
406
304
305 /*
306 * While we're asking the driver about the aggregation,
307 * stop the AC queue so that we don't have to worry
308 * about frames that came in while we were doing that,
309 * which would require us to put them to the AC pending
310 * afterwards which just makes the code more complex.
311 */

--- 90 unchanged lines hidden (view full) ---

402 spin_lock_bh(&sta->lock);
403
404 /* we have tried too many times, receiver does not want A-MPDU */
405 if (sta->ampdu_mlme.addba_req_num[tid] > HT_AGG_MAX_RETRIES) {
406 ret = -EBUSY;
407 goto err_unlock_sta;
408 }
409
407 tid_tx = sta->ampdu_mlme.tid_tx[tid];
410 tid_tx = rcu_dereference_protected_tid_tx(sta, tid);
408 /* check if the TID is not in aggregation flow already */
409 if (tid_tx || sta->ampdu_mlme.tid_start_tx[tid]) {
410#ifdef CONFIG_MAC80211_HT_DEBUG
411 printk(KERN_DEBUG "BA request denied - session is not "
412 "idle on tid %u\n", tid);
413#endif /* CONFIG_MAC80211_HT_DEBUG */
414 ret = -EAGAIN;
415 goto err_unlock_sta;

--- 70 unchanged lines hidden (view full) ---

486ieee80211_agg_splice_finish(struct ieee80211_local *local, u16 tid)
487{
488 ieee80211_wake_queue_agg(local, tid);
489}
490
491static void ieee80211_agg_tx_operational(struct ieee80211_local *local,
492 struct sta_info *sta, u16 tid)
493{
411 /* check if the TID is not in aggregation flow already */
412 if (tid_tx || sta->ampdu_mlme.tid_start_tx[tid]) {
413#ifdef CONFIG_MAC80211_HT_DEBUG
414 printk(KERN_DEBUG "BA request denied - session is not "
415 "idle on tid %u\n", tid);
416#endif /* CONFIG_MAC80211_HT_DEBUG */
417 ret = -EAGAIN;
418 goto err_unlock_sta;

--- 70 unchanged lines hidden (view full) ---

489ieee80211_agg_splice_finish(struct ieee80211_local *local, u16 tid)
490{
491 ieee80211_wake_queue_agg(local, tid);
492}
493
494static void ieee80211_agg_tx_operational(struct ieee80211_local *local,
495 struct sta_info *sta, u16 tid)
496{
497 struct tid_ampdu_tx *tid_tx;
498
494 lockdep_assert_held(&sta->ampdu_mlme.mtx);
495
499 lockdep_assert_held(&sta->ampdu_mlme.mtx);
500
501 tid_tx = rcu_dereference_protected_tid_tx(sta, tid);
502
496#ifdef CONFIG_MAC80211_HT_DEBUG
497 printk(KERN_DEBUG "Aggregation is on for tid %d\n", tid);
498#endif
499
500 drv_ampdu_action(local, sta->sdata,
501 IEEE80211_AMPDU_TX_OPERATIONAL,
503#ifdef CONFIG_MAC80211_HT_DEBUG
504 printk(KERN_DEBUG "Aggregation is on for tid %d\n", tid);
505#endif
506
507 drv_ampdu_action(local, sta->sdata,
508 IEEE80211_AMPDU_TX_OPERATIONAL,
502 &sta->sta, tid, NULL,
503 sta->ampdu_mlme.tid_tx[tid]->buf_size);
509 &sta->sta, tid, NULL, tid_tx->buf_size);
504
505 /*
506 * synchronize with TX path, while splicing the TX path
507 * should block so it won't put more packets onto pending.
508 */
509 spin_lock_bh(&sta->lock);
510
510
511 /*
512 * synchronize with TX path, while splicing the TX path
513 * should block so it won't put more packets onto pending.
514 */
515 spin_lock_bh(&sta->lock);
516
511 ieee80211_agg_splice_packets(local, sta->ampdu_mlme.tid_tx[tid], tid);
517 ieee80211_agg_splice_packets(local, tid_tx, tid);
512 /*
513 * Now mark as operational. This will be visible
514 * in the TX path, and lets it go lock-free in
515 * the common case.
516 */
518 /*
519 * Now mark as operational. This will be visible
520 * in the TX path, and lets it go lock-free in
521 * the common case.
522 */
517 set_bit(HT_AGG_STATE_OPERATIONAL, &sta->ampdu_mlme.tid_tx[tid]->state);
523 set_bit(HT_AGG_STATE_OPERATIONAL, &tid_tx->state);
518 ieee80211_agg_splice_finish(local, tid);
519
520 spin_unlock_bh(&sta->lock);
521}
522
523void ieee80211_start_tx_ba_cb(struct ieee80211_vif *vif, u8 *ra, u16 tid)
524{
525 struct ieee80211_sub_if_data *sdata = vif_to_sdata(vif);

--- 17 unchanged lines hidden (view full) ---

543 mutex_unlock(&local->sta_mtx);
544#ifdef CONFIG_MAC80211_HT_DEBUG
545 printk(KERN_DEBUG "Could not find station: %pM\n", ra);
546#endif
547 return;
548 }
549
550 mutex_lock(&sta->ampdu_mlme.mtx);
524 ieee80211_agg_splice_finish(local, tid);
525
526 spin_unlock_bh(&sta->lock);
527}
528
529void ieee80211_start_tx_ba_cb(struct ieee80211_vif *vif, u8 *ra, u16 tid)
530{
531 struct ieee80211_sub_if_data *sdata = vif_to_sdata(vif);

--- 17 unchanged lines hidden (view full) ---

549 mutex_unlock(&local->sta_mtx);
550#ifdef CONFIG_MAC80211_HT_DEBUG
551 printk(KERN_DEBUG "Could not find station: %pM\n", ra);
552#endif
553 return;
554 }
555
556 mutex_lock(&sta->ampdu_mlme.mtx);
551 tid_tx = sta->ampdu_mlme.tid_tx[tid];
557 tid_tx = rcu_dereference_protected_tid_tx(sta, tid);
552
553 if (WARN_ON(!tid_tx)) {
554#ifdef CONFIG_MAC80211_HT_DEBUG
555 printk(KERN_DEBUG "addBA was not requested!\n");
556#endif
557 goto unlock;
558 }
559

--- 61 unchanged lines hidden (view full) ---

621
622 if (!local->ops->ampdu_action)
623 return -EINVAL;
624
625 if (tid >= STA_TID_NUM)
626 return -EINVAL;
627
628 spin_lock_bh(&sta->lock);
558
559 if (WARN_ON(!tid_tx)) {
560#ifdef CONFIG_MAC80211_HT_DEBUG
561 printk(KERN_DEBUG "addBA was not requested!\n");
562#endif
563 goto unlock;
564 }
565

--- 61 unchanged lines hidden (view full) ---

627
628 if (!local->ops->ampdu_action)
629 return -EINVAL;
630
631 if (tid >= STA_TID_NUM)
632 return -EINVAL;
633
634 spin_lock_bh(&sta->lock);
629 tid_tx = sta->ampdu_mlme.tid_tx[tid];
635 tid_tx = rcu_dereference_protected_tid_tx(sta, tid);
630
631 if (!tid_tx) {
632 ret = -ENOENT;
633 goto unlock;
634 }
635
636 if (test_bit(HT_AGG_STATE_STOPPING, &tid_tx->state)) {
637 /* already in progress stopping it */

--- 39 unchanged lines hidden (view full) ---

677#ifdef CONFIG_MAC80211_HT_DEBUG
678 printk(KERN_DEBUG "Could not find station: %pM\n", ra);
679#endif
680 goto unlock;
681 }
682
683 mutex_lock(&sta->ampdu_mlme.mtx);
684 spin_lock_bh(&sta->lock);
636
637 if (!tid_tx) {
638 ret = -ENOENT;
639 goto unlock;
640 }
641
642 if (test_bit(HT_AGG_STATE_STOPPING, &tid_tx->state)) {
643 /* already in progress stopping it */

--- 39 unchanged lines hidden (view full) ---

683#ifdef CONFIG_MAC80211_HT_DEBUG
684 printk(KERN_DEBUG "Could not find station: %pM\n", ra);
685#endif
686 goto unlock;
687 }
688
689 mutex_lock(&sta->ampdu_mlme.mtx);
690 spin_lock_bh(&sta->lock);
685 tid_tx = sta->ampdu_mlme.tid_tx[tid];
691 tid_tx = rcu_dereference_protected_tid_tx(sta, tid);
686
687 if (!tid_tx || !test_bit(HT_AGG_STATE_STOPPING, &tid_tx->state)) {
688#ifdef CONFIG_MAC80211_HT_DEBUG
689 printk(KERN_DEBUG "unexpected callback to A-MPDU stop\n");
690#endif
691 goto unlock_sta;
692 }
693

--- 64 unchanged lines hidden (view full) ---

758 u8 buf_size;
759
760 capab = le16_to_cpu(mgmt->u.action.u.addba_resp.capab);
761 tid = (capab & IEEE80211_ADDBA_PARAM_TID_MASK) >> 2;
762 buf_size = (capab & IEEE80211_ADDBA_PARAM_BUF_SIZE_MASK) >> 6;
763
764 mutex_lock(&sta->ampdu_mlme.mtx);
765
692
693 if (!tid_tx || !test_bit(HT_AGG_STATE_STOPPING, &tid_tx->state)) {
694#ifdef CONFIG_MAC80211_HT_DEBUG
695 printk(KERN_DEBUG "unexpected callback to A-MPDU stop\n");
696#endif
697 goto unlock_sta;
698 }
699

--- 64 unchanged lines hidden (view full) ---

764 u8 buf_size;
765
766 capab = le16_to_cpu(mgmt->u.action.u.addba_resp.capab);
767 tid = (capab & IEEE80211_ADDBA_PARAM_TID_MASK) >> 2;
768 buf_size = (capab & IEEE80211_ADDBA_PARAM_BUF_SIZE_MASK) >> 6;
769
770 mutex_lock(&sta->ampdu_mlme.mtx);
771
766 tid_tx = sta->ampdu_mlme.tid_tx[tid];
772 tid_tx = rcu_dereference_protected_tid_tx(sta, tid);
767 if (!tid_tx)
768 goto out;
769
770 if (mgmt->u.action.u.addba_resp.dialog_token != tid_tx->dialog_token) {
771#ifdef CONFIG_MAC80211_HT_DEBUG
772 printk(KERN_DEBUG "wrong addBA response token, tid %d\n", tid);
773#endif
774 goto out;

--- 39 unchanged lines hidden ---
773 if (!tid_tx)
774 goto out;
775
776 if (mgmt->u.action.u.addba_resp.dialog_token != tid_tx->dialog_token) {
777#ifdef CONFIG_MAC80211_HT_DEBUG
778 printk(KERN_DEBUG "wrong addBA response token, tid %d\n", tid);
779#endif
780 goto out;

--- 39 unchanged lines hidden ---