aboutsummaryrefslogtreecommitdiffstats
path: root/drivers/net
diff options
context:
space:
mode:
authorMichael Chan <mchan@broadcom.com>2005-09-05 20:53:19 -0400
committerDavid S. Miller <davem@davemloft.net>2005-09-05 20:53:19 -0400
commit61487480dd79acc5e82b08cd29cbcbd3301645fa (patch)
tree79f40bebd2062bfad707eb5f49087c100843a20a /drivers/net
parent9f40dead25957434937f2b1872e9f4b43605f0ad (diff)
[TG3]: Remove status block access in tg3_msi() and add prefetches
Remove unnecessary status block accesses in tg3_msi(). Since MSI is not shared, it is unnecessary to read the status block to determine if there are any new events in the MSI handler. It is also unnecessary to clear the updated bit in the status block. Since the poll list is per-cpu, tg3_poll() will be scheduled to run on the same CPU that received the MSI. Prefetches for the status block and the next rx descriptors are added in tg3_msi() to improve their access times when tg3_poll() runs. In the non-MSI irq handlers, we need to check the status block because interrupts may be shared. Only prefetches for the next rx descriptors are added. Signed-off-by: Michael Chan <mchan@broadcom.com> Signed-off-by: David S. Miller <davem@davemloft.net>
Diffstat (limited to 'drivers/net')
-rw-r--r--drivers/net/tg3.c28
1 files changed, 11 insertions, 17 deletions
diff --git a/drivers/net/tg3.c b/drivers/net/tg3.c
index a174e616eda5..eea418124be1 100644
--- a/drivers/net/tg3.c
+++ b/drivers/net/tg3.c
@@ -36,6 +36,7 @@
36#include <linux/ip.h> 36#include <linux/ip.h>
37#include <linux/tcp.h> 37#include <linux/tcp.h>
38#include <linux/workqueue.h> 38#include <linux/workqueue.h>
39#include <linux/prefetch.h>
39 40
40#include <net/checksum.h> 41#include <net/checksum.h>
41 42
@@ -3278,8 +3279,9 @@ static irqreturn_t tg3_msi(int irq, void *dev_id, struct pt_regs *regs)
3278{ 3279{
3279 struct net_device *dev = dev_id; 3280 struct net_device *dev = dev_id;
3280 struct tg3 *tp = netdev_priv(dev); 3281 struct tg3 *tp = netdev_priv(dev);
3281 struct tg3_hw_status *sblk = tp->hw_status;
3282 3282
3283 prefetch(tp->hw_status);
3284 prefetch(&tp->rx_rcb[tp->rx_rcb_ptr]);
3283 /* 3285 /*
3284 * Writing any value to intr-mbox-0 clears PCI INTA# and 3286 * Writing any value to intr-mbox-0 clears PCI INTA# and
3285 * chip-internal interrupt pending events. 3287 * chip-internal interrupt pending events.
@@ -3288,19 +3290,9 @@ static irqreturn_t tg3_msi(int irq, void *dev_id, struct pt_regs *regs)
3288 * event coalescing. 3290 * event coalescing.
3289 */ 3291 */
3290 tw32_mailbox(MAILBOX_INTERRUPT_0 + TG3_64BIT_REG_LOW, 0x00000001); 3292 tw32_mailbox(MAILBOX_INTERRUPT_0 + TG3_64BIT_REG_LOW, 0x00000001);
3291 tp->last_tag = sblk->status_tag; 3293 if (likely(!tg3_irq_sync(tp)))
3292 rmb();
3293 if (tg3_irq_sync(tp))
3294 goto out;
3295 sblk->status &= ~SD_STATUS_UPDATED;
3296 if (likely(tg3_has_work(tp)))
3297 netif_rx_schedule(dev); /* schedule NAPI poll */ 3294 netif_rx_schedule(dev); /* schedule NAPI poll */
3298 else { 3295
3299 /* No work, re-enable interrupts. */
3300 tw32_mailbox(MAILBOX_INTERRUPT_0 + TG3_64BIT_REG_LOW,
3301 tp->last_tag << 24);
3302 }
3303out:
3304 return IRQ_RETVAL(1); 3296 return IRQ_RETVAL(1);
3305} 3297}
3306 3298
@@ -3330,9 +3322,10 @@ static irqreturn_t tg3_interrupt(int irq, void *dev_id, struct pt_regs *regs)
3330 if (tg3_irq_sync(tp)) 3322 if (tg3_irq_sync(tp))
3331 goto out; 3323 goto out;
3332 sblk->status &= ~SD_STATUS_UPDATED; 3324 sblk->status &= ~SD_STATUS_UPDATED;
3333 if (likely(tg3_has_work(tp))) 3325 if (likely(tg3_has_work(tp))) {
3326 prefetch(&tp->rx_rcb[tp->rx_rcb_ptr]);
3334 netif_rx_schedule(dev); /* schedule NAPI poll */ 3327 netif_rx_schedule(dev); /* schedule NAPI poll */
3335 else { 3328 } else {
3336 /* No work, shared interrupt perhaps? re-enable 3329 /* No work, shared interrupt perhaps? re-enable
3337 * interrupts, and flush that PCI write 3330 * interrupts, and flush that PCI write
3338 */ 3331 */
@@ -3374,9 +3367,10 @@ static irqreturn_t tg3_interrupt_tagged(int irq, void *dev_id, struct pt_regs *r
3374 if (tg3_irq_sync(tp)) 3367 if (tg3_irq_sync(tp))
3375 goto out; 3368 goto out;
3376 sblk->status &= ~SD_STATUS_UPDATED; 3369 sblk->status &= ~SD_STATUS_UPDATED;
3377 if (likely(tg3_has_work(tp))) 3370 if (likely(tg3_has_work(tp))) {
3371 prefetch(&tp->rx_rcb[tp->rx_rcb_ptr]);
3378 netif_rx_schedule(dev); /* schedule NAPI poll */ 3372 netif_rx_schedule(dev); /* schedule NAPI poll */
3379 else { 3373 } else {
3380 /* no work, shared interrupt perhaps? re-enable 3374 /* no work, shared interrupt perhaps? re-enable
3381 * interrupts, and flush that PCI write 3375 * interrupts, and flush that PCI write
3382 */ 3376 */