aboutsummaryrefslogtreecommitdiffstats
path: root/drivers/net/myri10ge/myri10ge.c
diff options
context:
space:
mode:
authorLinus Torvalds <torvalds@woody.osdl.org>2006-12-29 13:03:54 -0500
committerLinus Torvalds <torvalds@woody.osdl.org>2006-12-29 13:03:54 -0500
commit6c722e90d7ede7db2d2b28a3cc69a8545db67ea1 (patch)
tree2473530190795c11f841db37b7d74df9bcc0416b /drivers/net/myri10ge/myri10ge.c
parent007fb598b4674de82492a9961e82826875012229 (diff)
parent81f4e6c190a0fa016fd7eecaf76a5f95d121afc2 (diff)
Merge branch 'upstream-linus' of master.kernel.org:/pub/scm/linux/kernel/git/jgarzik/netdev-2.6
* 'upstream-linus' of master.kernel.org:/pub/scm/linux/kernel/git/jgarzik/netdev-2.6: (42 commits) r8169: extraneous Cmd{Tx/Rx}Enb write forcedeth: modified comment header NetXen: Reducing ring sizes for IOMMU issue. NetXen: Fix for PPC machines. NetXen: work queue fixes. NetXen: Link status message correction for quad port cards. NetXen: Multiple adapter fix. NetXen: Using correct CHECKSUM flag. NetXen: driver reload fix for newer firmware. NetXen: Adding new device ids. PHY probe not working properly for ibm_emac (PPC4xx) ep93xx: some minor cleanups to the ep93xx eth driver sky2: phy power down needs PCI config write enabled sky2: power management/MSI workaround sky2: dual port NAPI problem via-velocity uses INET interfaces e1000: Do not truncate TSO TCP header with 82544 workaround myri10ge: handle failures in suspend and resume myri10ge: no need to save MSI and PCIe state in the driver myri10ge: make msi configurable at runtime through sysfs ...
Diffstat (limited to 'drivers/net/myri10ge/myri10ge.c')
-rw-r--r--drivers/net/myri10ge/myri10ge.c163
1 files changed, 77 insertions, 86 deletions
diff --git a/drivers/net/myri10ge/myri10ge.c b/drivers/net/myri10ge/myri10ge.c
index 94ac168be593..07cf574197e5 100644
--- a/drivers/net/myri10ge/myri10ge.c
+++ b/drivers/net/myri10ge/myri10ge.c
@@ -199,8 +199,6 @@ struct myri10ge_priv {
199 unsigned long serial_number; 199 unsigned long serial_number;
200 int vendor_specific_offset; 200 int vendor_specific_offset;
201 int fw_multicast_support; 201 int fw_multicast_support;
202 u32 devctl;
203 u16 msi_flags;
204 u32 read_dma; 202 u32 read_dma;
205 u32 write_dma; 203 u32 write_dma;
206 u32 read_write_dma; 204 u32 read_write_dma;
@@ -228,7 +226,7 @@ module_param(myri10ge_small_bytes, int, S_IRUGO | S_IWUSR);
228MODULE_PARM_DESC(myri10ge_small_bytes, "Threshold of small packets\n"); 226MODULE_PARM_DESC(myri10ge_small_bytes, "Threshold of small packets\n");
229 227
230static int myri10ge_msi = 1; /* enable msi by default */ 228static int myri10ge_msi = 1; /* enable msi by default */
231module_param(myri10ge_msi, int, S_IRUGO); 229module_param(myri10ge_msi, int, S_IRUGO | S_IWUSR);
232MODULE_PARM_DESC(myri10ge_msi, "Enable Message Signalled Interrupts\n"); 230MODULE_PARM_DESC(myri10ge_msi, "Enable Message Signalled Interrupts\n");
233 231
234static int myri10ge_intr_coal_delay = 25; 232static int myri10ge_intr_coal_delay = 25;
@@ -721,12 +719,10 @@ static int myri10ge_reset(struct myri10ge_priv *mgp)
721 status |= 719 status |=
722 myri10ge_send_cmd(mgp, MXGEFW_CMD_GET_IRQ_ACK_OFFSET, &cmd, 0); 720 myri10ge_send_cmd(mgp, MXGEFW_CMD_GET_IRQ_ACK_OFFSET, &cmd, 0);
723 mgp->irq_claim = (__iomem __be32 *) (mgp->sram + cmd.data0); 721 mgp->irq_claim = (__iomem __be32 *) (mgp->sram + cmd.data0);
724 if (!mgp->msi_enabled) { 722 status |= myri10ge_send_cmd(mgp, MXGEFW_CMD_GET_IRQ_DEASSERT_OFFSET,
725 status |= myri10ge_send_cmd 723 &cmd, 0);
726 (mgp, MXGEFW_CMD_GET_IRQ_DEASSERT_OFFSET, &cmd, 0); 724 mgp->irq_deassert = (__iomem __be32 *) (mgp->sram + cmd.data0);
727 mgp->irq_deassert = (__iomem __be32 *) (mgp->sram + cmd.data0);
728 725
729 }
730 status |= myri10ge_send_cmd 726 status |= myri10ge_send_cmd
731 (mgp, MXGEFW_CMD_GET_INTR_COAL_DELAY_OFFSET, &cmd, 0); 727 (mgp, MXGEFW_CMD_GET_INTR_COAL_DELAY_OFFSET, &cmd, 0);
732 mgp->intr_coal_delay_ptr = (__iomem __be32 *) (mgp->sram + cmd.data0); 728 mgp->intr_coal_delay_ptr = (__iomem __be32 *) (mgp->sram + cmd.data0);
@@ -1619,6 +1615,41 @@ static void myri10ge_free_rings(struct net_device *dev)
1619 mgp->tx.req_list = NULL; 1615 mgp->tx.req_list = NULL;
1620} 1616}
1621 1617
1618static int myri10ge_request_irq(struct myri10ge_priv *mgp)
1619{
1620 struct pci_dev *pdev = mgp->pdev;
1621 int status;
1622
1623 if (myri10ge_msi) {
1624 status = pci_enable_msi(pdev);
1625 if (status != 0)
1626 dev_err(&pdev->dev,
1627 "Error %d setting up MSI; falling back to xPIC\n",
1628 status);
1629 else
1630 mgp->msi_enabled = 1;
1631 } else {
1632 mgp->msi_enabled = 0;
1633 }
1634 status = request_irq(pdev->irq, myri10ge_intr, IRQF_SHARED,
1635 mgp->dev->name, mgp);
1636 if (status != 0) {
1637 dev_err(&pdev->dev, "failed to allocate IRQ\n");
1638 if (mgp->msi_enabled)
1639 pci_disable_msi(pdev);
1640 }
1641 return status;
1642}
1643
1644static void myri10ge_free_irq(struct myri10ge_priv *mgp)
1645{
1646 struct pci_dev *pdev = mgp->pdev;
1647
1648 free_irq(pdev->irq, mgp);
1649 if (mgp->msi_enabled)
1650 pci_disable_msi(pdev);
1651}
1652
1622static int myri10ge_open(struct net_device *dev) 1653static int myri10ge_open(struct net_device *dev)
1623{ 1654{
1624 struct myri10ge_priv *mgp; 1655 struct myri10ge_priv *mgp;
@@ -1634,10 +1665,13 @@ static int myri10ge_open(struct net_device *dev)
1634 status = myri10ge_reset(mgp); 1665 status = myri10ge_reset(mgp);
1635 if (status != 0) { 1666 if (status != 0) {
1636 printk(KERN_ERR "myri10ge: %s: failed reset\n", dev->name); 1667 printk(KERN_ERR "myri10ge: %s: failed reset\n", dev->name);
1637 mgp->running = MYRI10GE_ETH_STOPPED; 1668 goto abort_with_nothing;
1638 return -ENXIO;
1639 } 1669 }
1640 1670
1671 status = myri10ge_request_irq(mgp);
1672 if (status != 0)
1673 goto abort_with_nothing;
1674
1641 /* decide what small buffer size to use. For good TCP rx 1675 /* decide what small buffer size to use. For good TCP rx
1642 * performance, it is important to not receive 1514 byte 1676 * performance, it is important to not receive 1514 byte
1643 * frames into jumbo buffers, as it confuses the socket buffer 1677 * frames into jumbo buffers, as it confuses the socket buffer
@@ -1677,7 +1711,7 @@ static int myri10ge_open(struct net_device *dev)
1677 "myri10ge: %s: failed to get ring sizes or locations\n", 1711 "myri10ge: %s: failed to get ring sizes or locations\n",
1678 dev->name); 1712 dev->name);
1679 mgp->running = MYRI10GE_ETH_STOPPED; 1713 mgp->running = MYRI10GE_ETH_STOPPED;
1680 return -ENXIO; 1714 goto abort_with_irq;
1681 } 1715 }
1682 1716
1683 if (mgp->mtrr >= 0) { 1717 if (mgp->mtrr >= 0) {
@@ -1708,7 +1742,7 @@ static int myri10ge_open(struct net_device *dev)
1708 1742
1709 status = myri10ge_allocate_rings(dev); 1743 status = myri10ge_allocate_rings(dev);
1710 if (status != 0) 1744 if (status != 0)
1711 goto abort_with_nothing; 1745 goto abort_with_irq;
1712 1746
1713 /* now give firmware buffers sizes, and MTU */ 1747 /* now give firmware buffers sizes, and MTU */
1714 cmd.data0 = dev->mtu + ETH_HLEN + VLAN_HLEN; 1748 cmd.data0 = dev->mtu + ETH_HLEN + VLAN_HLEN;
@@ -1771,6 +1805,9 @@ static int myri10ge_open(struct net_device *dev)
1771abort_with_rings: 1805abort_with_rings:
1772 myri10ge_free_rings(dev); 1806 myri10ge_free_rings(dev);
1773 1807
1808abort_with_irq:
1809 myri10ge_free_irq(mgp);
1810
1774abort_with_nothing: 1811abort_with_nothing:
1775 mgp->running = MYRI10GE_ETH_STOPPED; 1812 mgp->running = MYRI10GE_ETH_STOPPED;
1776 return -ENOMEM; 1813 return -ENOMEM;
@@ -1807,7 +1844,7 @@ static int myri10ge_close(struct net_device *dev)
1807 printk(KERN_ERR "myri10ge: %s never got down irq\n", dev->name); 1844 printk(KERN_ERR "myri10ge: %s never got down irq\n", dev->name);
1808 1845
1809 netif_tx_disable(dev); 1846 netif_tx_disable(dev);
1810 1847 myri10ge_free_irq(mgp);
1811 myri10ge_free_rings(dev); 1848 myri10ge_free_rings(dev);
1812 1849
1813 mgp->running = MYRI10GE_ETH_STOPPED; 1850 mgp->running = MYRI10GE_ETH_STOPPED;
@@ -2481,34 +2518,6 @@ static void myri10ge_select_firmware(struct myri10ge_priv *mgp)
2481 } 2518 }
2482} 2519}
2483 2520
2484static void myri10ge_save_state(struct myri10ge_priv *mgp)
2485{
2486 struct pci_dev *pdev = mgp->pdev;
2487 int cap;
2488
2489 pci_save_state(pdev);
2490 /* now save PCIe and MSI state that Linux will not
2491 * save for us */
2492 cap = pci_find_capability(pdev, PCI_CAP_ID_EXP);
2493 pci_read_config_dword(pdev, cap + PCI_EXP_DEVCTL, &mgp->devctl);
2494 cap = pci_find_capability(pdev, PCI_CAP_ID_MSI);
2495 pci_read_config_word(pdev, cap + PCI_MSI_FLAGS, &mgp->msi_flags);
2496}
2497
2498static void myri10ge_restore_state(struct myri10ge_priv *mgp)
2499{
2500 struct pci_dev *pdev = mgp->pdev;
2501 int cap;
2502
2503 /* restore PCIe and MSI state that linux will not */
2504 cap = pci_find_capability(pdev, PCI_CAP_ID_EXP);
2505 pci_write_config_dword(pdev, cap + PCI_CAP_ID_EXP, mgp->devctl);
2506 cap = pci_find_capability(pdev, PCI_CAP_ID_MSI);
2507 pci_write_config_word(pdev, cap + PCI_MSI_FLAGS, mgp->msi_flags);
2508
2509 pci_restore_state(pdev);
2510}
2511
2512#ifdef CONFIG_PM 2521#ifdef CONFIG_PM
2513 2522
2514static int myri10ge_suspend(struct pci_dev *pdev, pm_message_t state) 2523static int myri10ge_suspend(struct pci_dev *pdev, pm_message_t state)
@@ -2529,11 +2538,10 @@ static int myri10ge_suspend(struct pci_dev *pdev, pm_message_t state)
2529 rtnl_unlock(); 2538 rtnl_unlock();
2530 } 2539 }
2531 myri10ge_dummy_rdma(mgp, 0); 2540 myri10ge_dummy_rdma(mgp, 0);
2532 free_irq(pdev->irq, mgp); 2541 pci_save_state(pdev);
2533 myri10ge_save_state(mgp);
2534 pci_disable_device(pdev); 2542 pci_disable_device(pdev);
2535 pci_set_power_state(pdev, pci_choose_state(pdev, state)); 2543
2536 return 0; 2544 return pci_set_power_state(pdev, pci_choose_state(pdev, state));
2537} 2545}
2538 2546
2539static int myri10ge_resume(struct pci_dev *pdev) 2547static int myri10ge_resume(struct pci_dev *pdev)
@@ -2555,34 +2563,33 @@ static int myri10ge_resume(struct pci_dev *pdev)
2555 mgp->dev->name); 2563 mgp->dev->name);
2556 return -EIO; 2564 return -EIO;
2557 } 2565 }
2558 myri10ge_restore_state(mgp); 2566
2567 status = pci_restore_state(pdev);
2568 if (status)
2569 return status;
2559 2570
2560 status = pci_enable_device(pdev); 2571 status = pci_enable_device(pdev);
2561 if (status < 0) { 2572 if (status) {
2562 dev_err(&pdev->dev, "failed to enable device\n"); 2573 dev_err(&pdev->dev, "failed to enable device\n");
2563 return -EIO; 2574 return status;
2564 } 2575 }
2565 2576
2566 pci_set_master(pdev); 2577 pci_set_master(pdev);
2567 2578
2568 status = request_irq(pdev->irq, myri10ge_intr, IRQF_SHARED,
2569 netdev->name, mgp);
2570 if (status != 0) {
2571 dev_err(&pdev->dev, "failed to allocate IRQ\n");
2572 goto abort_with_enabled;
2573 }
2574
2575 myri10ge_reset(mgp); 2579 myri10ge_reset(mgp);
2576 myri10ge_dummy_rdma(mgp, 1); 2580 myri10ge_dummy_rdma(mgp, 1);
2577 2581
2578 /* Save configuration space to be restored if the 2582 /* Save configuration space to be restored if the
2579 * nic resets due to a parity error */ 2583 * nic resets due to a parity error */
2580 myri10ge_save_state(mgp); 2584 pci_save_state(pdev);
2581 2585
2582 if (netif_running(netdev)) { 2586 if (netif_running(netdev)) {
2583 rtnl_lock(); 2587 rtnl_lock();
2584 myri10ge_open(netdev); 2588 status = myri10ge_open(netdev);
2585 rtnl_unlock(); 2589 rtnl_unlock();
2590 if (status != 0)
2591 goto abort_with_enabled;
2592
2586 } 2593 }
2587 netif_device_attach(netdev); 2594 netif_device_attach(netdev);
2588 2595
@@ -2640,7 +2647,11 @@ static void myri10ge_watchdog(struct work_struct *work)
2640 * when the driver was loaded, or the last time the 2647 * when the driver was loaded, or the last time the
2641 * nic was resumed from power saving mode. 2648 * nic was resumed from power saving mode.
2642 */ 2649 */
2643 myri10ge_restore_state(mgp); 2650 pci_restore_state(mgp->pdev);
2651
2652 /* save state again for accounting reasons */
2653 pci_save_state(mgp->pdev);
2654
2644 } else { 2655 } else {
2645 /* if we get back -1's from our slot, perhaps somebody 2656 /* if we get back -1's from our slot, perhaps somebody
2646 * powered off our card. Don't try to reset it in 2657 * powered off our card. Don't try to reset it in
@@ -2856,23 +2867,6 @@ static int myri10ge_probe(struct pci_dev *pdev, const struct pci_device_id *ent)
2856 goto abort_with_firmware; 2867 goto abort_with_firmware;
2857 } 2868 }
2858 2869
2859 if (myri10ge_msi) {
2860 status = pci_enable_msi(pdev);
2861 if (status != 0)
2862 dev_err(&pdev->dev,
2863 "Error %d setting up MSI; falling back to xPIC\n",
2864 status);
2865 else
2866 mgp->msi_enabled = 1;
2867 }
2868
2869 status = request_irq(pdev->irq, myri10ge_intr, IRQF_SHARED,
2870 netdev->name, mgp);
2871 if (status != 0) {
2872 dev_err(&pdev->dev, "failed to allocate IRQ\n");
2873 goto abort_with_firmware;
2874 }
2875
2876 pci_set_drvdata(pdev, mgp); 2870 pci_set_drvdata(pdev, mgp);
2877 if ((myri10ge_initial_mtu + ETH_HLEN) > MYRI10GE_MAX_ETHER_MTU) 2871 if ((myri10ge_initial_mtu + ETH_HLEN) > MYRI10GE_MAX_ETHER_MTU)
2878 myri10ge_initial_mtu = MYRI10GE_MAX_ETHER_MTU - ETH_HLEN; 2872 myri10ge_initial_mtu = MYRI10GE_MAX_ETHER_MTU - ETH_HLEN;
@@ -2896,7 +2890,7 @@ static int myri10ge_probe(struct pci_dev *pdev, const struct pci_device_id *ent)
2896 2890
2897 /* Save configuration space to be restored if the 2891 /* Save configuration space to be restored if the
2898 * nic resets due to a parity error */ 2892 * nic resets due to a parity error */
2899 myri10ge_save_state(mgp); 2893 pci_save_state(pdev);
2900 2894
2901 /* Setup the watchdog timer */ 2895 /* Setup the watchdog timer */
2902 setup_timer(&mgp->watchdog_timer, myri10ge_watchdog_timer, 2896 setup_timer(&mgp->watchdog_timer, myri10ge_watchdog_timer,
@@ -2907,19 +2901,16 @@ static int myri10ge_probe(struct pci_dev *pdev, const struct pci_device_id *ent)
2907 status = register_netdev(netdev); 2901 status = register_netdev(netdev);
2908 if (status != 0) { 2902 if (status != 0) {
2909 dev_err(&pdev->dev, "register_netdev failed: %d\n", status); 2903 dev_err(&pdev->dev, "register_netdev failed: %d\n", status);
2910 goto abort_with_irq; 2904 goto abort_with_state;
2911 } 2905 }
2912 dev_info(dev, "%s IRQ %d, tx bndry %d, fw %s, WC %s\n", 2906 dev_info(dev, "%d, tx bndry %d, fw %s, WC %s\n",
2913 (mgp->msi_enabled ? "MSI" : "xPIC"),
2914 pdev->irq, mgp->tx.boundary, mgp->fw_name, 2907 pdev->irq, mgp->tx.boundary, mgp->fw_name,
2915 (mgp->mtrr >= 0 ? "Enabled" : "Disabled")); 2908 (mgp->mtrr >= 0 ? "Enabled" : "Disabled"));
2916 2909
2917 return 0; 2910 return 0;
2918 2911
2919abort_with_irq: 2912abort_with_state:
2920 free_irq(pdev->irq, mgp); 2913 pci_restore_state(pdev);
2921 if (mgp->msi_enabled)
2922 pci_disable_msi(pdev);
2923 2914
2924abort_with_firmware: 2915abort_with_firmware:
2925 myri10ge_dummy_rdma(mgp, 0); 2916 myri10ge_dummy_rdma(mgp, 0);
@@ -2970,12 +2961,12 @@ static void myri10ge_remove(struct pci_dev *pdev)
2970 flush_scheduled_work(); 2961 flush_scheduled_work();
2971 netdev = mgp->dev; 2962 netdev = mgp->dev;
2972 unregister_netdev(netdev); 2963 unregister_netdev(netdev);
2973 free_irq(pdev->irq, mgp);
2974 if (mgp->msi_enabled)
2975 pci_disable_msi(pdev);
2976 2964
2977 myri10ge_dummy_rdma(mgp, 0); 2965 myri10ge_dummy_rdma(mgp, 0);
2978 2966
2967 /* avoid a memory leak */
2968 pci_restore_state(pdev);
2969
2979 bytes = myri10ge_max_intr_slots * sizeof(*mgp->rx_done.entry); 2970 bytes = myri10ge_max_intr_slots * sizeof(*mgp->rx_done.entry);
2980 dma_free_coherent(&pdev->dev, bytes, 2971 dma_free_coherent(&pdev->dev, bytes,
2981 mgp->rx_done.entry, mgp->rx_done.bus); 2972 mgp->rx_done.entry, mgp->rx_done.bus);