[PATCH] skge: whitespace fixes
[powerpc.git] / drivers / net / e100.c
index 2c8c14e..d0fa244 100644 (file)
 #include <linux/delay.h>
 #include <linux/init.h>
 #include <linux/pci.h>
+#include <linux/dma-mapping.h>
 #include <linux/netdevice.h>
 #include <linux/etherdevice.h>
 #include <linux/mii.h>
 
 #define DRV_NAME               "e100"
 #define DRV_EXT                "-NAPI"
-#define DRV_VERSION            "3.3.6-k2"DRV_EXT
+#define DRV_VERSION            "3.4.8-k2"DRV_EXT
 #define DRV_DESCRIPTION                "Intel(R) PRO/100 Network Driver"
-#define DRV_COPYRIGHT          "Copyright(c) 1999-2004 Intel Corporation"
+#define DRV_COPYRIGHT          "Copyright(c) 1999-2005 Intel Corporation"
 #define PFX                    DRV_NAME ": "
 
 #define E100_WATCHDOG_PERIOD   (2 * HZ)
@@ -210,11 +211,17 @@ static struct pci_device_id e100_id_table[] = {
        INTEL_8255X_ETHERNET_DEVICE(0x1069, 6),
        INTEL_8255X_ETHERNET_DEVICE(0x106A, 6),
        INTEL_8255X_ETHERNET_DEVICE(0x106B, 6),
+       INTEL_8255X_ETHERNET_DEVICE(0x1091, 7),
+       INTEL_8255X_ETHERNET_DEVICE(0x1092, 7),
+       INTEL_8255X_ETHERNET_DEVICE(0x1093, 7),
+       INTEL_8255X_ETHERNET_DEVICE(0x1094, 7),
+       INTEL_8255X_ETHERNET_DEVICE(0x1095, 7),
        INTEL_8255X_ETHERNET_DEVICE(0x1209, 0),
        INTEL_8255X_ETHERNET_DEVICE(0x1229, 0),
        INTEL_8255X_ETHERNET_DEVICE(0x2449, 2),
        INTEL_8255X_ETHERNET_DEVICE(0x2459, 2),
        INTEL_8255X_ETHERNET_DEVICE(0x245D, 2),
+       INTEL_8255X_ETHERNET_DEVICE(0x27DC, 7),
        { 0, }
 };
 MODULE_DEVICE_TABLE(pci, e100_id_table);
@@ -777,7 +784,7 @@ static int e100_eeprom_save(struct nic *nic, u16 start, u16 count)
        return 0;
 }
 
-#define E100_WAIT_SCB_TIMEOUT 40
+#define E100_WAIT_SCB_TIMEOUT 20000 /* we might have to wait 100ms!!! */
 static inline int e100_exec_cmd(struct nic *nic, u8 cmd, dma_addr_t dma_addr)
 {
        unsigned long flags;
@@ -847,6 +854,10 @@ static inline int e100_exec_cb(struct nic *nic, struct sk_buff *skb,
                         * because the controller is too busy, so
                         * let's just queue the command and try again
                         * when another command is scheduled. */
+                       if(err == -ENOSPC) {
+                               //request a reset
+                               schedule_work(&nic->tx_timeout_task);
+                       }
                        break;
                } else {
                        nic->cuc_cmd = cuc_resume;
@@ -891,7 +902,7 @@ static void mdio_write(struct net_device *netdev, int addr, int reg, int data)
 
 static void e100_get_defaults(struct nic *nic)
 {
-       struct param_range rfds = { .min = 64, .max = 256, .count = 64 };
+       struct param_range rfds = { .min = 16, .max = 256, .count = 64 };
        struct param_range cbs  = { .min = 64, .max = 256, .count = 64 };
 
        pci_read_config_byte(nic->pdev, PCI_REVISION_ID, &nic->rev_id);
@@ -906,8 +917,9 @@ static void e100_get_defaults(struct nic *nic)
        /* Quadwords to DMA into FIFO before starting frame transmit */
        nic->tx_threshold = 0xE0;
 
-       nic->tx_command = cpu_to_le16(cb_tx | cb_i | cb_tx_sf |
-               ((nic->mac >= mac_82558_D101_A4) ? cb_cid : 0));
+       /* no interrupt for every tx completion, delay = 256us if not 557*/
+       nic->tx_command = cpu_to_le16(cb_tx | cb_tx_sf |
+               ((nic->mac >= mac_82558_D101_A4) ? cb_cid : cb_i));
 
        /* Template for a freshly allocated RFD */
        nic->blank_rfd.command = cpu_to_le16(cb_el);
@@ -971,7 +983,8 @@ static void e100_configure(struct nic *nic, struct cb *cb, struct sk_buff *skb)
        if(nic->flags & multicast_all)
                config->multicast_all = 0x1;            /* 1=accept, 0=no */
 
-       if(!(nic->flags & wol_magic))
+       /* disable WoL when up */
+       if(netif_running(nic->netdev) || !(nic->flags & wol_magic))
                config->magic_packet_disable = 0x1;     /* 1=off, 0=on */
 
        if(nic->mac >= mac_82558_D101_A4) {
@@ -1080,11 +1093,16 @@ static int e100_phy_init(struct nic *nic)
        }
 
        if((nic->mac >= mac_82550_D102) || ((nic->flags & ich) && 
-               (mdio_read(netdev, nic->mii.phy_id, MII_TPISTATUS) & 0x8000) && 
-               (nic->eeprom[eeprom_cnfg_mdix] & eeprom_mdix_enabled)))
-               /* enable/disable MDI/MDI-X auto-switching */
-               mdio_write(netdev, nic->mii.phy_id, MII_NCONFIG,
-                       nic->mii.force_media ? 0 : NCONFIG_AUTO_SWITCH);
+          (mdio_read(netdev, nic->mii.phy_id, MII_TPISTATUS) & 0x8000))) {
+               /* enable/disable MDI/MDI-X auto-switching.
+                  MDI/MDI-X auto-switching is disabled for 82551ER/QM chips */
+               if((nic->mac == mac_82551_E) || (nic->mac == mac_82551_F) ||
+                  (nic->mac == mac_82551_10) || (nic->mii.force_media) || 
+                  !(nic->eeprom[eeprom_cnfg_mdix] & eeprom_mdix_enabled)) 
+                       mdio_write(netdev, nic->mii.phy_id, MII_NCONFIG, 0);
+               else
+                       mdio_write(netdev, nic->mii.phy_id, MII_NCONFIG, NCONFIG_AUTO_SWITCH);
+       }
 
        return 0;
 }
@@ -1288,12 +1306,15 @@ static inline void e100_xmit_prepare(struct nic *nic, struct cb *cb,
        struct sk_buff *skb)
 {
        cb->command = nic->tx_command;
+       /* interrupt every 16 packets regardless of delay */
+       if((nic->cbs_avail & ~15) == nic->cbs_avail) cb->command |= cb_i;
        cb->u.tcb.tbd_array = cb->dma_addr + offsetof(struct cb, u.tcb.tbd);
        cb->u.tcb.tcb_byte_count = 0;
        cb->u.tcb.threshold = nic->tx_threshold;
        cb->u.tcb.tbd_count = 1;
        cb->u.tcb.tbd.buf_addr = cpu_to_le32(pci_map_single(nic->pdev,
                skb->data, skb->len, PCI_DMA_TODEVICE));
+       // check for mapping failure?
        cb->u.tcb.tbd.size = cpu_to_le16(skb->len);
 }
 
@@ -1650,8 +1671,10 @@ static irqreturn_t e100_intr(int irq, void *dev_id, struct pt_regs *regs)
        if(stat_ack & stat_ack_rnr)
                nic->ru_running = RU_SUSPENDED;
 
-       e100_disable_irq(nic);
-       netif_rx_schedule(netdev);
+       if(likely(netif_rx_schedule_prep(netdev))) {
+               e100_disable_irq(nic);
+               __netif_rx_schedule(netdev);
+       }
 
        return IRQ_HANDLED;
 }
@@ -1718,6 +1741,7 @@ static int e100_change_mtu(struct net_device *netdev, int new_mtu)
        return 0;
 }
 
+#ifdef CONFIG_PM
 static int e100_asf(struct nic *nic)
 {
        /* ASF can be enabled from eeprom */
@@ -1726,6 +1750,7 @@ static int e100_asf(struct nic *nic)
           !(nic->eeprom[eeprom_config_asf] & eeprom_gcl) &&
           ((nic->eeprom[eeprom_smbus_addr] & 0xFF) != 0xFE));
 }
+#endif
 
 static int e100_up(struct nic *nic)
 {
@@ -1743,8 +1768,11 @@ static int e100_up(struct nic *nic)
        if((err = request_irq(nic->pdev->irq, e100_intr, SA_SHIRQ,
                nic->netdev->name, nic->netdev)))
                goto err_no_irq;
-       e100_enable_irq(nic);
        netif_wake_queue(nic->netdev);
+       netif_poll_enable(nic->netdev);
+       /* enable ints _after_ enabling poll, preventing a race between
+        * disable ints+schedule */
+       e100_enable_irq(nic);
        return 0;
 
 err_no_irq:
@@ -1758,11 +1786,13 @@ err_rx_clean_list:
 
 static void e100_down(struct nic *nic)
 {
+       /* wait here for poll to complete */
+       netif_poll_disable(nic->netdev);
+       netif_stop_queue(nic->netdev);
        e100_hw_reset(nic);
        free_irq(nic->pdev->irq, nic->netdev);
        del_timer_sync(&nic->watchdog);
        netif_carrier_off(nic->netdev);
-       netif_stop_queue(nic->netdev);
        e100_clean_cbs(nic);
        e100_rx_clean_list(nic);
 }
@@ -1933,7 +1963,6 @@ static int e100_set_wol(struct net_device *netdev, struct ethtool_wolinfo *wol)
        else
                nic->flags &= ~wol_magic;
 
-       pci_enable_wake(nic->pdev, 0, nic->flags & (wol_magic | e100_asf(nic)));
        e100_exec_cb(nic, NULL, e100_configure);
 
        return 0;
@@ -2265,7 +2294,7 @@ static int __devinit e100_probe(struct pci_dev *pdev,
                goto err_out_disable_pdev;
        }
 
-       if((err = pci_set_dma_mask(pdev, 0xFFFFFFFFULL))) {
+       if((err = pci_set_dma_mask(pdev, DMA_32BIT_MASK))) {
                DPRINTK(PROBE, ERR, "No usable DMA configuration, aborting.\n");
                goto err_out_free_res;
        }
@@ -2313,11 +2342,11 @@ static int __devinit e100_probe(struct pci_dev *pdev,
                goto err_out_iounmap;
        }
 
-       e100_phy_init(nic);
-
        if((err = e100_eeprom_load(nic)))
                goto err_out_free;
 
+       e100_phy_init(nic);
+
        memcpy(netdev->dev_addr, nic->eeprom, ETH_ALEN);
        if(!is_valid_ether_addr(netdev->dev_addr)) {
                DPRINTK(PROBE, ERR, "Invalid MAC address from "
@@ -2331,7 +2360,8 @@ static int __devinit e100_probe(struct pci_dev *pdev,
           (nic->eeprom[eeprom_id] & eeprom_id_wol))
                nic->flags |= wol_magic;
 
-       pci_enable_wake(pdev, 0, nic->flags & (wol_magic | e100_asf(nic)));
+       /* ack any pending wake events, disable PME */
+       pci_enable_wake(pdev, 0, 0);
 
        strcpy(netdev->name, "eth%d");
        if((err = register_netdev(netdev))) {
@@ -2403,6 +2433,8 @@ static int e100_resume(struct pci_dev *pdev)
 
        pci_set_power_state(pdev, PCI_D0);
        pci_restore_state(pdev);
+       /* ack any pending wake events, disable PME */
+       pci_enable_wake(pdev, 0, 0);
        if(e100_hw_init(nic))
                DPRINTK(HW, ERR, "e100_hw_init failed\n");
 
@@ -2414,6 +2446,20 @@ static int e100_resume(struct pci_dev *pdev)
 }
 #endif
 
+
+static void e100_shutdown(struct pci_dev *pdev)
+{
+       struct net_device *netdev = pci_get_drvdata(pdev);
+       struct nic *nic = netdev_priv(netdev);
+
+#ifdef CONFIG_PM
+       pci_enable_wake(pdev, 0, nic->flags & (wol_magic | e100_asf(nic)));
+#else
+       pci_enable_wake(pdev, 0, nic->flags & (wol_magic));
+#endif
+}
+
+
 static struct pci_driver e100_driver = {
        .name =         DRV_NAME,
        .id_table =     e100_id_table,
@@ -2423,6 +2469,7 @@ static struct pci_driver e100_driver = {
        .suspend =      e100_suspend,
        .resume =       e100_resume,
 #endif
+       .shutdown =     e100_shutdown,
 };
 
 static int __init e100_init_module(void)