X-Git-Url: http://pilppa.org/gitweb/gitweb.cgi?a=blobdiff_plain;f=drivers%2Fnet%2Ftg3.c;h=cbfa4df0959232dad61998214cb7a68761cc2443;hb=a6c8700f36cd8f217420bbe26721094824fab8de;hp=5ee14764fd74e0ed5dc56296022588e03577e113;hpb=bc06cffdec85d487c77109dffcd2f285bdc502d3;p=linux-2.6-omap-h63xx.git diff --git a/drivers/net/tg3.c b/drivers/net/tg3.c index 5ee14764fd7..cbfa4df0959 100644 --- a/drivers/net/tg3.c +++ b/drivers/net/tg3.c @@ -64,8 +64,8 @@ #define DRV_MODULE_NAME "tg3" #define PFX DRV_MODULE_NAME ": " -#define DRV_MODULE_VERSION "3.78" -#define DRV_MODULE_RELDATE "July 11, 2007" +#define DRV_MODULE_VERSION "3.81" +#define DRV_MODULE_RELDATE "September 5, 2007" #define TG3_DEF_MAC_MODE 0 #define TG3_DEF_RX_MODE 0 @@ -574,7 +574,7 @@ static void tg3_restart_ints(struct tg3 *tp) static inline void tg3_netif_stop(struct tg3 *tp) { tp->dev->trans_start = jiffies; /* prevent tx timeout */ - netif_poll_disable(tp->dev); + napi_disable(&tp->napi); netif_tx_disable(tp->dev); } @@ -585,7 +585,7 @@ static inline void tg3_netif_start(struct tg3 *tp) * so long as all callers are assured to have free tx slots * (such as after tg3_init_hw) */ - netif_poll_enable(tp->dev); + napi_enable(&tp->napi); tp->hw_status->status |= SD_STATUS_UPDATED; tg3_enable_ints(tp); } @@ -3471,11 +3471,12 @@ next_pkt_nopost: return received; } -static int tg3_poll(struct net_device *netdev, int *budget) +static int tg3_poll(struct napi_struct *napi, int budget) { - struct tg3 *tp = netdev_priv(netdev); + struct tg3 *tp = container_of(napi, struct tg3, napi); + struct net_device *netdev = tp->dev; struct tg3_hw_status *sblk = tp->hw_status; - int done; + int work_done = 0; /* handle link change and other phy events */ if (!(tp->tg3_flags & @@ -3494,7 +3495,7 @@ static int tg3_poll(struct net_device *netdev, int *budget) if (sblk->idx[0].tx_consumer != tp->tx_cons) { tg3_tx(tp); if (unlikely(tp->tg3_flags & TG3_FLAG_TX_RECOVERY_PENDING)) { - netif_rx_complete(netdev); + netif_rx_complete(netdev, napi); schedule_work(&tp->reset_task); return 0; } @@ -3502,20 +3503,10 @@ static int tg3_poll(struct net_device *netdev, int *budget) /* run RX thread, within the bounds set by NAPI. * All RX "locking" is done by ensuring outside - * code synchronizes with dev->poll() + * code synchronizes with tg3->napi.poll() */ - if (sblk->idx[0].rx_producer != tp->rx_rcb_ptr) { - int orig_budget = *budget; - int work_done; - - if (orig_budget > netdev->quota) - orig_budget = netdev->quota; - - work_done = tg3_rx(tp, orig_budget); - - *budget -= work_done; - netdev->quota -= work_done; - } + if (sblk->idx[0].rx_producer != tp->rx_rcb_ptr) + work_done = tg3_rx(tp, budget); if (tp->tg3_flags & TG3_FLAG_TAGGED_STATUS) { tp->last_tag = sblk->status_tag; @@ -3524,13 +3515,12 @@ static int tg3_poll(struct net_device *netdev, int *budget) sblk->status &= ~SD_STATUS_UPDATED; /* if no more work, tell net stack and NIC we're done */ - done = !tg3_has_work(tp); - if (done) { - netif_rx_complete(netdev); + if (!tg3_has_work(tp)) { + netif_rx_complete(netdev, napi); tg3_restart_ints(tp); } - return (done ? 0 : 1); + return work_done; } static void tg3_irq_quiesce(struct tg3 *tp) @@ -3577,7 +3567,7 @@ static irqreturn_t tg3_msi_1shot(int irq, void *dev_id) prefetch(&tp->rx_rcb[tp->rx_rcb_ptr]); if (likely(!tg3_irq_sync(tp))) - netif_rx_schedule(dev); /* schedule NAPI poll */ + netif_rx_schedule(dev, &tp->napi); return IRQ_HANDLED; } @@ -3602,7 +3592,7 @@ static irqreturn_t tg3_msi(int irq, void *dev_id) */ tw32_mailbox(MAILBOX_INTERRUPT_0 + TG3_64BIT_REG_LOW, 0x00000001); if (likely(!tg3_irq_sync(tp))) - netif_rx_schedule(dev); /* schedule NAPI poll */ + netif_rx_schedule(dev, &tp->napi); return IRQ_RETVAL(1); } @@ -3644,7 +3634,7 @@ static irqreturn_t tg3_interrupt(int irq, void *dev_id) sblk->status &= ~SD_STATUS_UPDATED; if (likely(tg3_has_work(tp))) { prefetch(&tp->rx_rcb[tp->rx_rcb_ptr]); - netif_rx_schedule(dev); /* schedule NAPI poll */ + netif_rx_schedule(dev, &tp->napi); } else { /* No work, shared interrupt perhaps? re-enable * interrupts, and flush that PCI write @@ -3690,7 +3680,7 @@ static irqreturn_t tg3_interrupt_tagged(int irq, void *dev_id) tw32_mailbox_f(MAILBOX_INTERRUPT_0 + TG3_64BIT_REG_LOW, 0x00000001); if (tg3_irq_sync(tp)) goto out; - if (netif_rx_schedule_prep(dev)) { + if (netif_rx_schedule_prep(dev, &tp->napi)) { prefetch(&tp->rx_rcb[tp->rx_rcb_ptr]); /* Update last_tag to mark that this status has been * seen. Because interrupt may be shared, we may be @@ -3698,7 +3688,7 @@ static irqreturn_t tg3_interrupt_tagged(int irq, void *dev_id) * if tg3_poll() is not scheduled. */ tp->last_tag = sblk->status_tag; - __netif_rx_schedule(dev); + __netif_rx_schedule(dev, &tp->napi); } out: return IRQ_RETVAL(handled); @@ -3737,7 +3727,7 @@ static int tg3_restart_hw(struct tg3 *tp, int reset_phy) tg3_full_unlock(tp); del_timer_sync(&tp->timer); tp->irq_sync = 0; - netif_poll_enable(tp->dev); + napi_enable(&tp->napi); dev_close(tp->dev); tg3_full_lock(tp, 0); } @@ -3932,7 +3922,7 @@ static int tg3_start_xmit(struct sk_buff *skb, struct net_device *dev) len = skb_headlen(skb); /* We are running in BH disabled context with netif_tx_lock - * and TX reclaim runs via tp->poll inside of a software + * and TX reclaim runs via tp->napi.poll inside of a software * interrupt. Furthermore, IRQ processing runs lockless so we have * no IRQ context deadlocks to worry about either. Rejoice! */ @@ -4087,7 +4077,7 @@ static int tg3_start_xmit_dma_bug(struct sk_buff *skb, struct net_device *dev) len = skb_headlen(skb); /* We are running in BH disabled context with netif_tx_lock - * and TX reclaim runs via tp->poll inside of a software + * and TX reclaim runs via tp->napi.poll inside of a software * interrupt. Furthermore, IRQ processing runs lockless so we have * no IRQ context deadlocks to worry about either. Rejoice! */ @@ -4847,6 +4837,58 @@ static int tg3_poll_fw(struct tg3 *tp) return 0; } +/* Save PCI command register before chip reset */ +static void tg3_save_pci_state(struct tg3 *tp) +{ + u32 val; + + pci_read_config_dword(tp->pdev, TG3PCI_COMMAND, &val); + tp->pci_cmd = val; +} + +/* Restore PCI state after chip reset */ +static void tg3_restore_pci_state(struct tg3 *tp) +{ + u32 val; + + /* Re-enable indirect register accesses. */ + pci_write_config_dword(tp->pdev, TG3PCI_MISC_HOST_CTRL, + tp->misc_host_ctrl); + + /* Set MAX PCI retry to zero. */ + val = (PCISTATE_ROM_ENABLE | PCISTATE_ROM_RETRY_ENABLE); + if (tp->pci_chip_rev_id == CHIPREV_ID_5704_A0 && + (tp->tg3_flags & TG3_FLAG_PCIX_MODE)) + val |= PCISTATE_RETRY_SAME_DMA; + pci_write_config_dword(tp->pdev, TG3PCI_PCISTATE, val); + + pci_write_config_dword(tp->pdev, TG3PCI_COMMAND, tp->pci_cmd); + + /* Make sure PCI-X relaxed ordering bit is clear. */ + pci_read_config_dword(tp->pdev, TG3PCI_X_CAPS, &val); + val &= ~PCIX_CAPS_RELAXED_ORDERING; + pci_write_config_dword(tp->pdev, TG3PCI_X_CAPS, val); + + if (tp->tg3_flags2 & TG3_FLG2_5780_CLASS) { + + /* Chip reset on 5780 will reset MSI enable bit, + * so need to restore it. + */ + if (tp->tg3_flags2 & TG3_FLG2_USING_MSI) { + u16 ctrl; + + pci_read_config_word(tp->pdev, + tp->msi_cap + PCI_MSI_FLAGS, + &ctrl); + pci_write_config_word(tp->pdev, + tp->msi_cap + PCI_MSI_FLAGS, + ctrl | PCI_MSI_FLAGS_ENABLE); + val = tr32(MSGINT_MODE); + tw32(MSGINT_MODE, val | MSGINT_MODE_ENABLE); + } + } +} + static void tg3_stop_fw(struct tg3 *); /* tp->lock is held. */ @@ -4863,6 +4905,12 @@ static int tg3_chip_reset(struct tg3 *tp) */ tp->nvram_lock_cnt = 0; + /* GRC_MISC_CFG core clock reset will clear the memory + * enable bit in PCI register 4 and the MSI enable bit + * on some chips, so we save relevant registers here. + */ + tg3_save_pci_state(tp); + if (GET_ASIC_REV(tp->pci_chip_rev_id) == ASIC_REV_5752 || GET_ASIC_REV(tp->pci_chip_rev_id) == ASIC_REV_5755 || GET_ASIC_REV(tp->pci_chip_rev_id) == ASIC_REV_5787) @@ -4961,50 +5009,14 @@ static int tg3_chip_reset(struct tg3 *tp) pci_write_config_dword(tp->pdev, 0xd8, 0xf5000); } - /* Re-enable indirect register accesses. */ - pci_write_config_dword(tp->pdev, TG3PCI_MISC_HOST_CTRL, - tp->misc_host_ctrl); - - /* Set MAX PCI retry to zero. */ - val = (PCISTATE_ROM_ENABLE | PCISTATE_ROM_RETRY_ENABLE); - if (tp->pci_chip_rev_id == CHIPREV_ID_5704_A0 && - (tp->tg3_flags & TG3_FLAG_PCIX_MODE)) - val |= PCISTATE_RETRY_SAME_DMA; - pci_write_config_dword(tp->pdev, TG3PCI_PCISTATE, val); - - pci_restore_state(tp->pdev); + tg3_restore_pci_state(tp); tp->tg3_flags &= ~TG3_FLAG_CHIP_RESETTING; - /* Make sure PCI-X relaxed ordering bit is clear. */ - pci_read_config_dword(tp->pdev, TG3PCI_X_CAPS, &val); - val &= ~PCIX_CAPS_RELAXED_ORDERING; - pci_write_config_dword(tp->pdev, TG3PCI_X_CAPS, val); - - if (tp->tg3_flags2 & TG3_FLG2_5780_CLASS) { - u32 val; - - /* Chip reset on 5780 will reset MSI enable bit, - * so need to restore it. - */ - if (tp->tg3_flags2 & TG3_FLG2_USING_MSI) { - u16 ctrl; - - pci_read_config_word(tp->pdev, - tp->msi_cap + PCI_MSI_FLAGS, - &ctrl); - pci_write_config_word(tp->pdev, - tp->msi_cap + PCI_MSI_FLAGS, - ctrl | PCI_MSI_FLAGS_ENABLE); - val = tr32(MSGINT_MODE); - tw32(MSGINT_MODE, val | MSGINT_MODE_ENABLE); - } - + val = 0; + if (tp->tg3_flags2 & TG3_FLG2_5780_CLASS) val = tr32(MEMARB_MODE); - tw32(MEMARB_MODE, val | MEMARB_MODE_ENABLE); - - } else - tw32(MEMARB_MODE, MEMARB_MODE_ENABLE); + tw32(MEMARB_MODE, val | MEMARB_MODE_ENABLE); if (tp->pci_chip_rev_id == CHIPREV_ID_5750_A3) { tg3_stop_fw(tp); @@ -5014,7 +5026,7 @@ static int tg3_chip_reset(struct tg3 *tp) tw32(GRC_MODE, tp->grc_mode); if (tp->pci_chip_rev_id == CHIPREV_ID_5705_A0) { - u32 val = tr32(0xc4); + val = tr32(0xc4); tw32(0xc4, val | (1 << 15)); } @@ -5043,7 +5055,7 @@ static int tg3_chip_reset(struct tg3 *tp) if ((tp->tg3_flags2 & TG3_FLG2_PCI_EXPRESS) && tp->pci_chip_rev_id != CHIPREV_ID_5750_A0) { - u32 val = tr32(0x7c00); + val = tr32(0x7c00); tw32(0x7c00, val | (1 << 25)); } @@ -7104,6 +7116,10 @@ static int tg3_open(struct net_device *dev) } else if (pci_enable_msi(tp->pdev) == 0) { u32 msi_mode; + /* Hardware bug - MSI won't work if INTX disabled. */ + if (tp->tg3_flags2 & TG3_FLG2_5780_CLASS) + pci_intx(tp->pdev, 1); + msi_mode = tr32(MSGINT_MODE); tw32(MSGINT_MODE, msi_mode | MSGINT_MODE_ENABLE); tp->tg3_flags2 |= TG3_FLG2_USING_MSI; @@ -7120,6 +7136,8 @@ static int tg3_open(struct net_device *dev) return err; } + napi_enable(&tp->napi); + tg3_full_lock(tp, 0); err = tg3_init_hw(tp, 1); @@ -7147,6 +7165,7 @@ static int tg3_open(struct net_device *dev) tg3_full_unlock(tp); if (err) { + napi_disable(&tp->napi); free_irq(tp->pdev->irq, dev); if (tp->tg3_flags2 & TG3_FLG2_USING_MSI) { pci_disable_msi(tp->pdev); @@ -7172,6 +7191,8 @@ static int tg3_open(struct net_device *dev) tg3_full_unlock(tp); + napi_disable(&tp->napi); + return err; } @@ -7433,6 +7454,7 @@ static int tg3_close(struct net_device *dev) { struct tg3 *tp = netdev_priv(dev); + napi_disable(&tp->napi); cancel_work_sync(&tp->reset_task); netif_stop_queue(dev); @@ -7968,7 +7990,7 @@ static int tg3_set_eeprom(struct net_device *dev, struct ethtool_eeprom *eeprom, buf = data; if (b_offset || odd_len) { buf = kmalloc(len, GFP_KERNEL); - if (buf == 0) + if (!buf) return -ENOMEM; if (b_offset) memcpy(buf, &start, 4); @@ -8397,7 +8419,7 @@ static void tg3_get_ethtool_stats (struct net_device *dev, static int tg3_test_nvram(struct tg3 *tp) { u32 *buf, csum, magic; - int i, j, err = 0, size; + int i, j, k, err = 0, size; if (tg3_nvram_read_swab(tp, 0, &magic) != 0) return -EIO; @@ -8451,7 +8473,6 @@ static int tg3_test_nvram(struct tg3 *tp) u8 data[NVRAM_SELFBOOT_DATA_SIZE]; u8 parity[NVRAM_SELFBOOT_DATA_SIZE]; u8 *buf8 = (u8 *) buf; - int j, k; /* Separate the parity bits and the data bytes. */ for (i = 0, j = 0, k = 0; i < NVRAM_SELFBOOT_HW_SIZE; i++) { @@ -9271,7 +9292,6 @@ static const struct ethtool_ops tg3_ethtool_ops = { .get_ethtool_stats = tg3_get_ethtool_stats, .get_coalesce = tg3_get_coalesce, .set_coalesce = tg3_set_coalesce, - .get_perm_addr = ethtool_op_get_perm_addr, }; static void __devinit tg3_get_eeprom_size(struct tg3 *tp) @@ -10708,7 +10728,6 @@ static int __devinit tg3_get_invariants(struct tg3 *tp) */ if (GET_CHIP_REV(tp->pci_chip_rev_id) == CHIPREV_5700_BX) { u32 pm_reg; - u16 pci_cmd; tp->tg3_flags |= TG3_FLAG_PCIX_TARGET_HWBUG; @@ -11854,7 +11873,7 @@ static int __devinit tg3_init_one(struct pci_dev *pdev, INIT_WORK(&tp->reset_task, tg3_reset_task); tp->regs = ioremap_nocache(tg3reg_base, tg3reg_len); - if (tp->regs == 0UL) { + if (!tp->regs) { printk(KERN_ERR PFX "Cannot map device registers, " "aborting.\n"); err = -ENOMEM; @@ -11874,9 +11893,8 @@ static int __devinit tg3_init_one(struct pci_dev *pdev, dev->set_mac_address = tg3_set_mac_addr; dev->do_ioctl = tg3_ioctl; dev->tx_timeout = tg3_tx_timeout; - dev->poll = tg3_poll; + netif_napi_add(dev, &tp->napi, tg3_poll, 64); dev->ethtool_ops = &tg3_ethtool_ops; - dev->weight = 64; dev->watchdog_timeo = TG3_TX_TIMEOUT; dev->change_mtu = tg3_change_mtu; dev->irq = pdev->irq; @@ -11978,7 +11996,6 @@ static int __devinit tg3_init_one(struct pci_dev *pdev, */ if ((tr32(HOSTCC_MODE) & HOSTCC_MODE_ENABLE) || (tr32(WDMAC_MODE) & WDMAC_MODE_ENABLE)) { - pci_save_state(tp->pdev); tw32(MEMARB_MODE, MEMARB_MODE_ENABLE); tg3_halt(tp, RESET_KIND_SHUTDOWN, 1); } @@ -12007,12 +12024,6 @@ static int __devinit tg3_init_one(struct pci_dev *pdev, tg3_init_coal(tp); - /* Now that we have fully setup the chip, save away a snapshot - * of the PCI config space. We need to restore this after - * GRC_MISC_CFG core clock resets and some resume events. - */ - pci_save_state(tp->pdev); - pci_set_drvdata(pdev, dev); err = register_netdev(dev); @@ -12096,6 +12107,12 @@ static int tg3_suspend(struct pci_dev *pdev, pm_message_t state) struct tg3 *tp = netdev_priv(dev); int err; + /* PCI register 4 needs to be saved whether netif_running() or not. + * MSI address and data need to be saved if using MSI and + * netif_running(). + */ + pci_save_state(pdev); + if (!netif_running(dev)) return 0; @@ -12115,9 +12132,6 @@ static int tg3_suspend(struct pci_dev *pdev, pm_message_t state) tp->tg3_flags &= ~TG3_FLAG_INIT_COMPLETE; tg3_full_unlock(tp); - /* Save MSI address and data for resume. */ - pci_save_state(pdev); - err = tg3_set_power_state(tp, pci_choose_state(pdev, state)); if (err) { tg3_full_lock(tp, 0); @@ -12145,15 +12159,20 @@ static int tg3_resume(struct pci_dev *pdev) struct tg3 *tp = netdev_priv(dev); int err; + pci_restore_state(tp->pdev); + if (!netif_running(dev)) return 0; - pci_restore_state(tp->pdev); - err = tg3_set_power_state(tp, PCI_D0); if (err) return err; + /* Hardware bug - MSI won't work if INTX disabled. */ + if ((tp->tg3_flags2 & TG3_FLG2_5780_CLASS) && + (tp->tg3_flags2 & TG3_FLG2_USING_MSI)) + pci_intx(tp->pdev, 1); + netif_device_attach(dev); tg3_full_lock(tp, 0);