aboutsummaryrefslogtreecommitdiffstats
path: root/net/mac80211/util.c
diff options
context:
space:
mode:
Diffstat (limited to 'net/mac80211/util.c')
-rw-r--r--net/mac80211/util.c126
1 files changed, 31 insertions, 95 deletions
diff --git a/net/mac80211/util.c b/net/mac80211/util.c
index e0431a1d218b..fdf432f14554 100644
--- a/net/mac80211/util.c
+++ b/net/mac80211/util.c
@@ -166,18 +166,13 @@ int ieee80211_get_mesh_hdrlen(struct ieee80211s_hdr *meshhdr)
166 166
167void ieee80211_tx_set_protected(struct ieee80211_tx_data *tx) 167void ieee80211_tx_set_protected(struct ieee80211_tx_data *tx)
168{ 168{
169 struct ieee80211_hdr *hdr = (struct ieee80211_hdr *) tx->skb->data; 169 struct sk_buff *skb = tx->skb;
170 170 struct ieee80211_hdr *hdr;
171 hdr->frame_control |= cpu_to_le16(IEEE80211_FCTL_PROTECTED); 171
172 if (tx->extra_frag) { 172 do {
173 struct ieee80211_hdr *fhdr; 173 hdr = (struct ieee80211_hdr *) skb->data;
174 int i; 174 hdr->frame_control |= cpu_to_le16(IEEE80211_FCTL_PROTECTED);
175 for (i = 0; i < tx->num_extra_frag; i++) { 175 } while ((skb = skb->next));
176 fhdr = (struct ieee80211_hdr *)
177 tx->extra_frag[i]->data;
178 fhdr->frame_control |= cpu_to_le16(IEEE80211_FCTL_PROTECTED);
179 }
180 }
181} 176}
182 177
183int ieee80211_frame_duration(struct ieee80211_local *local, size_t len, 178int ieee80211_frame_duration(struct ieee80211_local *local, size_t len,
@@ -344,42 +339,21 @@ static void __ieee80211_wake_queue(struct ieee80211_hw *hw, int queue,
344{ 339{
345 struct ieee80211_local *local = hw_to_local(hw); 340 struct ieee80211_local *local = hw_to_local(hw);
346 341
347 if (queue >= hw->queues) { 342 if (WARN_ON(queue >= hw->queues))
348 if (local->ampdu_ac_queue[queue - hw->queues] < 0) 343 return;
349 return;
350
351 /*
352 * for virtual aggregation queues, we need to refcount the
353 * internal mac80211 disable (multiple times!), keep track of
354 * driver disable _and_ make sure the regular queue is
355 * actually enabled.
356 */
357 if (reason == IEEE80211_QUEUE_STOP_REASON_AGGREGATION)
358 local->amdpu_ac_stop_refcnt[queue - hw->queues]--;
359 else
360 __clear_bit(reason, &local->queue_stop_reasons[queue]);
361
362 if (local->queue_stop_reasons[queue] ||
363 local->amdpu_ac_stop_refcnt[queue - hw->queues])
364 return;
365
366 /* now go on to treat the corresponding regular queue */
367 queue = local->ampdu_ac_queue[queue - hw->queues];
368 reason = IEEE80211_QUEUE_STOP_REASON_AGGREGATION;
369 }
370 344
371 __clear_bit(reason, &local->queue_stop_reasons[queue]); 345 __clear_bit(reason, &local->queue_stop_reasons[queue]);
372 346
347 if (!skb_queue_empty(&local->pending[queue]) &&
348 local->queue_stop_reasons[queue] ==
349 BIT(IEEE80211_QUEUE_STOP_REASON_PENDING))
350 tasklet_schedule(&local->tx_pending_tasklet);
351
373 if (local->queue_stop_reasons[queue] != 0) 352 if (local->queue_stop_reasons[queue] != 0)
374 /* someone still has this queue stopped */ 353 /* someone still has this queue stopped */
375 return; 354 return;
376 355
377 if (test_bit(queue, local->queues_pending)) { 356 netif_wake_subqueue(local->mdev, queue);
378 set_bit(queue, local->queues_pending_run);
379 tasklet_schedule(&local->tx_pending_tasklet);
380 } else {
381 netif_wake_subqueue(local->mdev, queue);
382 }
383} 357}
384 358
385void ieee80211_wake_queue_by_reason(struct ieee80211_hw *hw, int queue, 359void ieee80211_wake_queue_by_reason(struct ieee80211_hw *hw, int queue,
@@ -405,29 +379,18 @@ static void __ieee80211_stop_queue(struct ieee80211_hw *hw, int queue,
405{ 379{
406 struct ieee80211_local *local = hw_to_local(hw); 380 struct ieee80211_local *local = hw_to_local(hw);
407 381
408 if (queue >= hw->queues) { 382 if (WARN_ON(queue >= hw->queues))
409 if (local->ampdu_ac_queue[queue - hw->queues] < 0) 383 return;
410 return;
411
412 /*
413 * for virtual aggregation queues, we need to refcount the
414 * internal mac80211 disable (multiple times!), keep track of
415 * driver disable _and_ make sure the regular queue is
416 * actually enabled.
417 */
418 if (reason == IEEE80211_QUEUE_STOP_REASON_AGGREGATION)
419 local->amdpu_ac_stop_refcnt[queue - hw->queues]++;
420 else
421 __set_bit(reason, &local->queue_stop_reasons[queue]);
422 384
423 /* now go on to treat the corresponding regular queue */ 385 /*
424 queue = local->ampdu_ac_queue[queue - hw->queues]; 386 * Only stop if it was previously running, this is necessary
425 reason = IEEE80211_QUEUE_STOP_REASON_AGGREGATION; 387 * for correct pending packets handling because there we may
426 } 388 * start (but not wake) the queue and rely on that.
389 */
390 if (!local->queue_stop_reasons[queue])
391 netif_stop_subqueue(local->mdev, queue);
427 392
428 __set_bit(reason, &local->queue_stop_reasons[queue]); 393 __set_bit(reason, &local->queue_stop_reasons[queue]);
429
430 netif_stop_subqueue(local->mdev, queue);
431} 394}
432 395
433void ieee80211_stop_queue_by_reason(struct ieee80211_hw *hw, int queue, 396void ieee80211_stop_queue_by_reason(struct ieee80211_hw *hw, int queue,
@@ -473,15 +436,9 @@ EXPORT_SYMBOL(ieee80211_stop_queues);
473int ieee80211_queue_stopped(struct ieee80211_hw *hw, int queue) 436int ieee80211_queue_stopped(struct ieee80211_hw *hw, int queue)
474{ 437{
475 struct ieee80211_local *local = hw_to_local(hw); 438 struct ieee80211_local *local = hw_to_local(hw);
476 unsigned long flags;
477 439
478 if (queue >= hw->queues) { 440 if (WARN_ON(queue >= hw->queues))
479 spin_lock_irqsave(&local->queue_stop_reason_lock, flags); 441 return true;
480 queue = local->ampdu_ac_queue[queue - hw->queues];
481 spin_unlock_irqrestore(&local->queue_stop_reason_lock, flags);
482 if (queue < 0)
483 return true;
484 }
485 442
486 return __netif_subqueue_stopped(local->mdev, queue); 443 return __netif_subqueue_stopped(local->mdev, queue);
487} 444}
@@ -496,7 +453,7 @@ void ieee80211_wake_queues_by_reason(struct ieee80211_hw *hw,
496 453
497 spin_lock_irqsave(&local->queue_stop_reason_lock, flags); 454 spin_lock_irqsave(&local->queue_stop_reason_lock, flags);
498 455
499 for (i = 0; i < hw->queues + hw->ampdu_queues; i++) 456 for (i = 0; i < hw->queues; i++)
500 __ieee80211_wake_queue(hw, i, reason); 457 __ieee80211_wake_queue(hw, i, reason);
501 458
502 spin_unlock_irqrestore(&local->queue_stop_reason_lock, flags); 459 spin_unlock_irqrestore(&local->queue_stop_reason_lock, flags);
@@ -846,16 +803,9 @@ void ieee80211_send_auth(struct ieee80211_sub_if_data *sdata,
846 struct ieee80211_local *local = sdata->local; 803 struct ieee80211_local *local = sdata->local;
847 struct sk_buff *skb; 804 struct sk_buff *skb;
848 struct ieee80211_mgmt *mgmt; 805 struct ieee80211_mgmt *mgmt;
849 const u8 *ie_auth = NULL;
850 int ie_auth_len = 0;
851
852 if (sdata->vif.type == NL80211_IFTYPE_STATION) {
853 ie_auth_len = sdata->u.mgd.ie_auth_len;
854 ie_auth = sdata->u.mgd.ie_auth;
855 }
856 806
857 skb = dev_alloc_skb(local->hw.extra_tx_headroom + 807 skb = dev_alloc_skb(local->hw.extra_tx_headroom +
858 sizeof(*mgmt) + 6 + extra_len + ie_auth_len); 808 sizeof(*mgmt) + 6 + extra_len);
859 if (!skb) { 809 if (!skb) {
860 printk(KERN_DEBUG "%s: failed to allocate buffer for auth " 810 printk(KERN_DEBUG "%s: failed to allocate buffer for auth "
861 "frame\n", sdata->dev->name); 811 "frame\n", sdata->dev->name);
@@ -877,8 +827,6 @@ void ieee80211_send_auth(struct ieee80211_sub_if_data *sdata,
877 mgmt->u.auth.status_code = cpu_to_le16(0); 827 mgmt->u.auth.status_code = cpu_to_le16(0);
878 if (extra) 828 if (extra)
879 memcpy(skb_put(skb, extra_len), extra, extra_len); 829 memcpy(skb_put(skb, extra_len), extra, extra_len);
880 if (ie_auth)
881 memcpy(skb_put(skb, ie_auth_len), ie_auth, ie_auth_len);
882 830
883 ieee80211_tx_skb(sdata, skb, encrypt); 831 ieee80211_tx_skb(sdata, skb, encrypt);
884} 832}
@@ -891,20 +839,11 @@ void ieee80211_send_probe_req(struct ieee80211_sub_if_data *sdata, u8 *dst,
891 struct ieee80211_supported_band *sband; 839 struct ieee80211_supported_band *sband;
892 struct sk_buff *skb; 840 struct sk_buff *skb;
893 struct ieee80211_mgmt *mgmt; 841 struct ieee80211_mgmt *mgmt;
894 u8 *pos, *supp_rates, *esupp_rates = NULL, *extra_preq_ie = NULL; 842 u8 *pos, *supp_rates, *esupp_rates = NULL;
895 int i, extra_preq_ie_len = 0; 843 int i;
896
897 switch (sdata->vif.type) {
898 case NL80211_IFTYPE_STATION:
899 extra_preq_ie_len = sdata->u.mgd.ie_probereq_len;
900 extra_preq_ie = sdata->u.mgd.ie_probereq;
901 break;
902 default:
903 break;
904 }
905 844
906 skb = dev_alloc_skb(local->hw.extra_tx_headroom + sizeof(*mgmt) + 200 + 845 skb = dev_alloc_skb(local->hw.extra_tx_headroom + sizeof(*mgmt) + 200 +
907 ie_len + extra_preq_ie_len); 846 ie_len);
908 if (!skb) { 847 if (!skb) {
909 printk(KERN_DEBUG "%s: failed to allocate buffer for probe " 848 printk(KERN_DEBUG "%s: failed to allocate buffer for probe "
910 "request\n", sdata->dev->name); 849 "request\n", sdata->dev->name);
@@ -953,9 +892,6 @@ void ieee80211_send_probe_req(struct ieee80211_sub_if_data *sdata, u8 *dst,
953 892
954 if (ie) 893 if (ie)
955 memcpy(skb_put(skb, ie_len), ie, ie_len); 894 memcpy(skb_put(skb, ie_len), ie, ie_len);
956 if (extra_preq_ie)
957 memcpy(skb_put(skb, extra_preq_ie_len), extra_preq_ie,
958 extra_preq_ie_len);
959 895
960 ieee80211_tx_skb(sdata, skb, 0); 896 ieee80211_tx_skb(sdata, skb, 0);
961} 897}