aboutsummaryrefslogtreecommitdiffstats
path: root/drivers/net/wireless/rt2x00
diff options
context:
space:
mode:
authorGertjan van Wingerde <gwingerde@gmail.com>2011-07-06 16:57:37 -0400
committerJohn W. Linville <linville@tuxdriver.com>2011-07-07 13:20:58 -0400
commit128f8f773d77d41a7dbcaf5d36325a0f4e7955cd (patch)
treef514ad12fb4fc930797e27b4874c846c55989b23 /drivers/net/wireless/rt2x00
parent77b5621bac4a56b83b9081f48d4e7d1accdde400 (diff)
rt2x00: Reduce window of a queue's tx lock.
Currently a lot of actions that can be done without the queue's tx lock being held are done inside the locked area. Move them out to have a leaner and meaner code that operates while the tx lock is being held. Signed-off-by: Gertjan van Wingerde <gwingerde@gmail.com> Acked-by: Helmut Schaa <helmut.schaa@googlemail.com> Signed-off-by: Ivo van Doorn <IvDoorn@gmail.com> Signed-off-by: John W. Linville <linville@tuxdriver.com>
Diffstat (limited to 'drivers/net/wireless/rt2x00')
-rw-r--r--drivers/net/wireless/rt2x00/rt2x00queue.c51
1 files changed, 26 insertions, 25 deletions
diff --git a/drivers/net/wireless/rt2x00/rt2x00queue.c b/drivers/net/wireless/rt2x00/rt2x00queue.c
index a70e7000b528..29edb9fbe6f1 100644
--- a/drivers/net/wireless/rt2x00/rt2x00queue.c
+++ b/drivers/net/wireless/rt2x00/rt2x00queue.c
@@ -565,33 +565,11 @@ int rt2x00queue_write_tx_frame(struct data_queue *queue, struct sk_buff *skb,
565 u8 rate_idx, rate_flags; 565 u8 rate_idx, rate_flags;
566 int ret = 0; 566 int ret = 0;
567 567
568 spin_lock(&queue->tx_lock);
569
570 entry = rt2x00queue_get_entry(queue, Q_INDEX);
571
572 if (unlikely(rt2x00queue_full(queue))) {
573 ERROR(queue->rt2x00dev,
574 "Dropping frame due to full tx queue %d.\n", queue->qid);
575 ret = -ENOBUFS;
576 goto out;
577 }
578
579 if (unlikely(test_and_set_bit(ENTRY_OWNER_DEVICE_DATA,
580 &entry->flags))) {
581 ERROR(queue->rt2x00dev,
582 "Arrived at non-free entry in the non-full queue %d.\n"
583 "Please file bug report to %s.\n",
584 queue->qid, DRV_PROJECT);
585 ret = -EINVAL;
586 goto out;
587 }
588
589 /* 568 /*
590 * Copy all TX descriptor information into txdesc, 569 * Copy all TX descriptor information into txdesc,
591 * after that we are free to use the skb->cb array 570 * after that we are free to use the skb->cb array
592 * for our information. 571 * for our information.
593 */ 572 */
594 entry->skb = skb;
595 rt2x00queue_create_tx_descriptor(queue->rt2x00dev, skb, &txdesc); 573 rt2x00queue_create_tx_descriptor(queue->rt2x00dev, skb, &txdesc);
596 574
597 /* 575 /*
@@ -604,7 +582,6 @@ int rt2x00queue_write_tx_frame(struct data_queue *queue, struct sk_buff *skb,
604 rate_flags = tx_info->control.rates[0].flags; 582 rate_flags = tx_info->control.rates[0].flags;
605 skbdesc = get_skb_frame_desc(skb); 583 skbdesc = get_skb_frame_desc(skb);
606 memset(skbdesc, 0, sizeof(*skbdesc)); 584 memset(skbdesc, 0, sizeof(*skbdesc));
607 skbdesc->entry = entry;
608 skbdesc->tx_rate_idx = rate_idx; 585 skbdesc->tx_rate_idx = rate_idx;
609 skbdesc->tx_rate_flags = rate_flags; 586 skbdesc->tx_rate_flags = rate_flags;
610 587
@@ -633,9 +610,33 @@ int rt2x00queue_write_tx_frame(struct data_queue *queue, struct sk_buff *skb,
633 * for PCI devices. 610 * for PCI devices.
634 */ 611 */
635 if (test_bit(REQUIRE_L2PAD, &queue->rt2x00dev->cap_flags)) 612 if (test_bit(REQUIRE_L2PAD, &queue->rt2x00dev->cap_flags))
636 rt2x00queue_insert_l2pad(entry->skb, txdesc.header_length); 613 rt2x00queue_insert_l2pad(skb, txdesc.header_length);
637 else if (test_bit(REQUIRE_DMA, &queue->rt2x00dev->cap_flags)) 614 else if (test_bit(REQUIRE_DMA, &queue->rt2x00dev->cap_flags))
638 rt2x00queue_align_frame(entry->skb); 615 rt2x00queue_align_frame(skb);
616
617 spin_lock(&queue->tx_lock);
618
619 if (unlikely(rt2x00queue_full(queue))) {
620 ERROR(queue->rt2x00dev,
621 "Dropping frame due to full tx queue %d.\n", queue->qid);
622 ret = -ENOBUFS;
623 goto out;
624 }
625
626 entry = rt2x00queue_get_entry(queue, Q_INDEX);
627
628 if (unlikely(test_and_set_bit(ENTRY_OWNER_DEVICE_DATA,
629 &entry->flags))) {
630 ERROR(queue->rt2x00dev,
631 "Arrived at non-free entry in the non-full queue %d.\n"
632 "Please file bug report to %s.\n",
633 queue->qid, DRV_PROJECT);
634 ret = -EINVAL;
635 goto out;
636 }
637
638 skbdesc->entry = entry;
639 entry->skb = skb;
639 640
640 /* 641 /*
641 * It could be possible that the queue was corrupted and this 642 * It could be possible that the queue was corrupted and this