aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--drivers/net/vxge/vxge-config.h7
-rw-r--r--drivers/net/vxge/vxge-main.c53
-rw-r--r--drivers/net/vxge/vxge-main.h3
-rw-r--r--drivers/net/vxge/vxge-traffic.c7
-rw-r--r--drivers/net/vxge/vxge-traffic.h2
5 files changed, 40 insertions, 32 deletions
diff --git a/drivers/net/vxge/vxge-config.h b/drivers/net/vxge/vxge-config.h
index 224acea771ed..62779a520ca1 100644
--- a/drivers/net/vxge/vxge-config.h
+++ b/drivers/net/vxge/vxge-config.h
@@ -978,7 +978,9 @@ struct __vxge_hw_fifo {
978 void *txdlh, 978 void *txdlh,
979 enum vxge_hw_fifo_tcode t_code, 979 enum vxge_hw_fifo_tcode t_code,
980 void *userdata, 980 void *userdata,
981 void **skb_ptr); 981 struct sk_buff ***skb_ptr,
982 int nr_skb,
983 int *more);
982 984
983 void (*txdl_term)( 985 void (*txdl_term)(
984 void *txdlh, 986 void *txdlh,
@@ -1779,7 +1781,8 @@ struct vxge_hw_fifo_attr {
1779 void *txdlh, 1781 void *txdlh,
1780 enum vxge_hw_fifo_tcode t_code, 1782 enum vxge_hw_fifo_tcode t_code,
1781 void *userdata, 1783 void *userdata,
1782 void **skb_ptr); 1784 struct sk_buff ***skb_ptr,
1785 int nr_skb, int *more);
1783 1786
1784 void (*txdl_term)( 1787 void (*txdl_term)(
1785 void *txdlh, 1788 void *txdlh,
diff --git a/drivers/net/vxge/vxge-main.c b/drivers/net/vxge/vxge-main.c
index beee4ab2ed30..4b22513bed40 100644
--- a/drivers/net/vxge/vxge-main.c
+++ b/drivers/net/vxge/vxge-main.c
@@ -87,22 +87,25 @@ static inline int is_vxge_card_up(struct vxgedev *vdev)
87static inline void VXGE_COMPLETE_VPATH_TX(struct vxge_fifo *fifo) 87static inline void VXGE_COMPLETE_VPATH_TX(struct vxge_fifo *fifo)
88{ 88{
89 unsigned long flags = 0; 89 unsigned long flags = 0;
90 struct sk_buff *skb_ptr = NULL; 90 struct sk_buff **skb_ptr = NULL;
91 struct sk_buff **temp, *head, *skb; 91 struct sk_buff **temp;
92 92#define NR_SKB_COMPLETED 128
93 if (spin_trylock_irqsave(&fifo->tx_lock, flags)) { 93 struct sk_buff *completed[NR_SKB_COMPLETED];
94 vxge_hw_vpath_poll_tx(fifo->handle, (void **)&skb_ptr); 94 int more;
95 spin_unlock_irqrestore(&fifo->tx_lock, flags); 95
96 } 96 do {
97 /* free SKBs */ 97 more = 0;
98 head = skb_ptr; 98 skb_ptr = completed;
99 while (head) { 99
100 skb = head; 100 if (spin_trylock_irqsave(&fifo->tx_lock, flags)) {
101 temp = (struct sk_buff **)&skb->cb; 101 vxge_hw_vpath_poll_tx(fifo->handle, &skb_ptr,
102 head = *temp; 102 NR_SKB_COMPLETED, &more);
103 *temp = NULL; 103 spin_unlock_irqrestore(&fifo->tx_lock, flags);
104 dev_kfree_skb_irq(skb); 104 }
105 } 105 /* free SKBs */
106 for (temp = completed; temp != skb_ptr; temp++)
107 dev_kfree_skb_irq(*temp);
108 } while (more) ;
106} 109}
107 110
108static inline void VXGE_COMPLETE_ALL_TX(struct vxgedev *vdev) 111static inline void VXGE_COMPLETE_ALL_TX(struct vxgedev *vdev)
@@ -600,11 +603,10 @@ vxge_rx_1b_compl(struct __vxge_hw_ring *ringh, void *dtr,
600enum vxge_hw_status 603enum vxge_hw_status
601vxge_xmit_compl(struct __vxge_hw_fifo *fifo_hw, void *dtr, 604vxge_xmit_compl(struct __vxge_hw_fifo *fifo_hw, void *dtr,
602 enum vxge_hw_fifo_tcode t_code, void *userdata, 605 enum vxge_hw_fifo_tcode t_code, void *userdata,
603 void **skb_ptr) 606 struct sk_buff ***skb_ptr, int nr_skb, int *more)
604{ 607{
605 struct vxge_fifo *fifo = (struct vxge_fifo *)userdata; 608 struct vxge_fifo *fifo = (struct vxge_fifo *)userdata;
606 struct sk_buff *skb, *head = NULL; 609 struct sk_buff *skb, **done_skb = *skb_ptr;
607 struct sk_buff **temp;
608 int pkt_cnt = 0; 610 int pkt_cnt = 0;
609 611
610 vxge_debug_entryexit(VXGE_TRACE, 612 vxge_debug_entryexit(VXGE_TRACE,
@@ -657,9 +659,12 @@ vxge_xmit_compl(struct __vxge_hw_fifo *fifo_hw, void *dtr,
657 fifo->stats.tx_frms++; 659 fifo->stats.tx_frms++;
658 fifo->stats.tx_bytes += skb->len; 660 fifo->stats.tx_bytes += skb->len;
659 661
660 temp = (struct sk_buff **)&skb->cb; 662 *done_skb++ = skb;
661 *temp = head; 663
662 head = skb; 664 if (--nr_skb <= 0) {
665 *more = 1;
666 break;
667 }
663 668
664 pkt_cnt++; 669 pkt_cnt++;
665 if (pkt_cnt > fifo->indicate_max_pkts) 670 if (pkt_cnt > fifo->indicate_max_pkts)
@@ -668,11 +673,9 @@ vxge_xmit_compl(struct __vxge_hw_fifo *fifo_hw, void *dtr,
668 } while (vxge_hw_fifo_txdl_next_completed(fifo_hw, 673 } while (vxge_hw_fifo_txdl_next_completed(fifo_hw,
669 &dtr, &t_code) == VXGE_HW_OK); 674 &dtr, &t_code) == VXGE_HW_OK);
670 675
676 *skb_ptr = done_skb;
671 vxge_wake_tx_queue(fifo, skb); 677 vxge_wake_tx_queue(fifo, skb);
672 678
673 if (skb_ptr)
674 *skb_ptr = (void *) head;
675
676 vxge_debug_entryexit(VXGE_TRACE, 679 vxge_debug_entryexit(VXGE_TRACE,
677 "%s: %s:%d Exiting...", 680 "%s: %s:%d Exiting...",
678 fifo->ndev->name, __func__, __LINE__); 681 fifo->ndev->name, __func__, __LINE__);
diff --git a/drivers/net/vxge/vxge-main.h b/drivers/net/vxge/vxge-main.h
index 18d824c3ab93..8b3989bc707f 100644
--- a/drivers/net/vxge/vxge-main.h
+++ b/drivers/net/vxge/vxge-main.h
@@ -428,7 +428,8 @@ vxge_rx_1b_compl(struct __vxge_hw_ring *ringh, void *dtr,
428 428
429enum vxge_hw_status 429enum vxge_hw_status
430vxge_xmit_compl(struct __vxge_hw_fifo *fifo_hw, void *dtr, 430vxge_xmit_compl(struct __vxge_hw_fifo *fifo_hw, void *dtr,
431 enum vxge_hw_fifo_tcode t_code, void *userdata, void **skb_ptr); 431 enum vxge_hw_fifo_tcode t_code, void *userdata,
432 struct sk_buff ***skb_ptr, int nr_skbs, int *more);
432 433
433int vxge_close(struct net_device *dev); 434int vxge_close(struct net_device *dev);
434 435
diff --git a/drivers/net/vxge/vxge-traffic.c b/drivers/net/vxge/vxge-traffic.c
index 370f55cbbad7..c249cd25a5d0 100644
--- a/drivers/net/vxge/vxge-traffic.c
+++ b/drivers/net/vxge/vxge-traffic.c
@@ -2508,7 +2508,8 @@ enum vxge_hw_status vxge_hw_vpath_poll_rx(struct __vxge_hw_ring *ring)
2508 * See also: vxge_hw_vpath_poll_tx(). 2508 * See also: vxge_hw_vpath_poll_tx().
2509 */ 2509 */
2510enum vxge_hw_status vxge_hw_vpath_poll_tx(struct __vxge_hw_fifo *fifo, 2510enum vxge_hw_status vxge_hw_vpath_poll_tx(struct __vxge_hw_fifo *fifo,
2511 void **skb_ptr) 2511 struct sk_buff ***skb_ptr, int nr_skb,
2512 int *more)
2512{ 2513{
2513 enum vxge_hw_fifo_tcode t_code; 2514 enum vxge_hw_fifo_tcode t_code;
2514 void *first_txdlh; 2515 void *first_txdlh;
@@ -2520,8 +2521,8 @@ enum vxge_hw_status vxge_hw_vpath_poll_tx(struct __vxge_hw_fifo *fifo,
2520 status = vxge_hw_fifo_txdl_next_completed(fifo, 2521 status = vxge_hw_fifo_txdl_next_completed(fifo,
2521 &first_txdlh, &t_code); 2522 &first_txdlh, &t_code);
2522 if (status == VXGE_HW_OK) 2523 if (status == VXGE_HW_OK)
2523 if (fifo->callback(fifo, first_txdlh, 2524 if (fifo->callback(fifo, first_txdlh, t_code,
2524 t_code, channel->userdata, skb_ptr) != VXGE_HW_OK) 2525 channel->userdata, skb_ptr, nr_skb, more) != VXGE_HW_OK)
2525 status = VXGE_HW_COMPLETIONS_REMAIN; 2526 status = VXGE_HW_COMPLETIONS_REMAIN;
2526 2527
2527 return status; 2528 return status;
diff --git a/drivers/net/vxge/vxge-traffic.h b/drivers/net/vxge/vxge-traffic.h
index 8260b91fd795..461742b4442b 100644
--- a/drivers/net/vxge/vxge-traffic.h
+++ b/drivers/net/vxge/vxge-traffic.h
@@ -2326,7 +2326,7 @@ enum vxge_hw_status vxge_hw_vpath_poll_rx(
2326 2326
2327enum vxge_hw_status vxge_hw_vpath_poll_tx( 2327enum vxge_hw_status vxge_hw_vpath_poll_tx(
2328 struct __vxge_hw_fifo *fifoh, 2328 struct __vxge_hw_fifo *fifoh,
2329 void **skb_ptr); 2329 struct sk_buff ***skb_ptr, int nr_skb, int *more);
2330 2330
2331enum vxge_hw_status vxge_hw_vpath_alarm_process( 2331enum vxge_hw_status vxge_hw_vpath_alarm_process(
2332 struct __vxge_hw_vpath_handle *vpath_handle, 2332 struct __vxge_hw_vpath_handle *vpath_handle,