Automatic merge of /spare/repo/netdev-2.6 branch smc91x
author <jgarzik@pretzel.yyz.us> <>
Sat, 4 Jun 2005 21:15:04 +0000 (17:15 -0400)
committerJeff Garzik <jgarzik@pobox.com>
Sat, 4 Jun 2005 21:15:04 +0000 (17:15 -0400)
drivers/net/smc91x.c
drivers/net/smc91x.h

index 5e561ba4433330ee2e49675f2805f3e03457715d..fd80048f7f7ac6f98e09bf6e0456448e7688ccea 100644 (file)
@@ -129,7 +129,7 @@ MODULE_PARM_DESC(nowait, "set to 1 for no wait state");
 /*
  * Transmit timeout, default 5 seconds.
  */
-static int watchdog = 5000;
+static int watchdog = 1000;
 module_param(watchdog, int, 0400);
 MODULE_PARM_DESC(watchdog, "transmit timeout in milliseconds");
 
@@ -660,15 +660,14 @@ static void smc_hardware_send_pkt(unsigned long data)
        SMC_outw(((len & 1) ? (0x2000 | buf[len-1]) : 0), ioaddr, DATA_REG);
 
        /*
-        * If THROTTLE_TX_PKTS is set, we look at the TX_EMPTY flag
-        * before queueing this packet for TX, and if it's clear then
-        * we stop the queue here.  This will have the effect of
-        * having at most 2 packets queued for TX in the chip's memory
-        * at all time. If THROTTLE_TX_PKTS is not set then the queue
-        * is stopped only when memory allocation (MC_ALLOC) does not
-        * succeed right away.
+        * If THROTTLE_TX_PKTS is set, we stop the queue here. This will
+        * have the effect of having at most one packet queued for TX
+        * in the chip's memory at all time.
+        *
+        * If THROTTLE_TX_PKTS is not set then the queue is stopped only
+        * when memory allocation (MC_ALLOC) does not succeed right away.
         */
-       if (THROTTLE_TX_PKTS && !(SMC_GET_INT() & IM_TX_EMPTY_INT))
+       if (THROTTLE_TX_PKTS)
                netif_stop_queue(dev);
 
        /* queue the packet for TX */
@@ -792,17 +791,20 @@ static void smc_tx(struct net_device *dev)
        DBG(2, "%s: TX STATUS 0x%04x PNR 0x%02x\n",
                dev->name, tx_status, packet_no);
 
-       if (!(tx_status & TS_SUCCESS))
+       if (!(tx_status & ES_TX_SUC))
                lp->stats.tx_errors++;
-       if (tx_status & TS_LOSTCAR)
+
+       if (tx_status & ES_LOSTCARR)
                lp->stats.tx_carrier_errors++;
 
-       if (tx_status & TS_LATCOL) {
-               PRINTK("%s: late collision occurred on last xmit\n", dev->name);
+       if (tx_status & (ES_LATCOL | ES_16COL)) {
+               PRINTK("%s: %s occurred on last xmit\n", dev->name,
+                      (tx_status & ES_LATCOL) ?
+                       "late collision" : "too many collisions");
                lp->stats.tx_window_errors++;
                if (!(lp->stats.tx_window_errors & 63) && net_ratelimit()) {
-                       printk(KERN_INFO "%s: unexpectedly large numbers of "
-                              "late collisions. Please check duplex "
+                       printk(KERN_INFO "%s: unexpectedly large number of "
+                              "bad collisions. Please check duplex "
                               "setting.\n", dev->name);
                }
        }
@@ -1236,7 +1238,7 @@ static void smc_10bt_check_media(struct net_device *dev, int init)
        old_carrier = netif_carrier_ok(dev) ? 1 : 0;
 
        SMC_SELECT_BANK(0);
-       new_carrier = SMC_inw(ioaddr, EPH_STATUS_REG) & ES_LINK_OK ? 1 : 0;
+       new_carrier = (SMC_GET_EPH_STATUS() & ES_LINK_OK) ? 1 : 0;
        SMC_SELECT_BANK(2);
 
        if (init || (old_carrier != new_carrier)) {
@@ -1308,15 +1310,16 @@ static irqreturn_t smc_interrupt(int irq, void *dev_id, struct pt_regs *regs)
                if (!status)
                        break;
 
-               if (status & IM_RCV_INT) {
-                       DBG(3, "%s: RX irq\n", dev->name);
-                       smc_rcv(dev);
-               } else if (status & IM_TX_INT) {
+               if (status & IM_TX_INT) {
+                       /* do this before RX as it will free memory quickly */
                        DBG(3, "%s: TX int\n", dev->name);
                        smc_tx(dev);
                        SMC_ACK_INT(IM_TX_INT);
                        if (THROTTLE_TX_PKTS)
                                netif_wake_queue(dev);
+               } else if (status & IM_RCV_INT) {
+                       DBG(3, "%s: RX irq\n", dev->name);
+                       smc_rcv(dev);
                } else if (status & IM_ALLOC_INT) {
                        DBG(3, "%s: Allocation irq\n", dev->name);
                        tasklet_hi_schedule(&lp->tx_task);
@@ -1337,7 +1340,10 @@ static irqreturn_t smc_interrupt(int irq, void *dev_id, struct pt_regs *regs)
                        /* multiple collisions */
                        lp->stats.collisions += card_stats & 0xF;
                } else if (status & IM_RX_OVRN_INT) {
-                       DBG(1, "%s: RX overrun\n", dev->name);
+                       DBG(1, "%s: RX overrun (EPH_ST 0x%04x)\n", dev->name,
+                              ({ int eph_st; SMC_SELECT_BANK(0);
+                                 eph_st = SMC_GET_EPH_STATUS();
+                                 SMC_SELECT_BANK(2); eph_st; }) );
                        SMC_ACK_INT(IM_RX_OVRN_INT);
                        lp->stats.rx_errors++;
                        lp->stats.rx_fifo_errors++;
@@ -1389,7 +1395,7 @@ static void smc_timeout(struct net_device *dev)
 {
        struct smc_local *lp = netdev_priv(dev);
        void __iomem *ioaddr = lp->base;
-       int status, mask, meminfo, fifo;
+       int status, mask, eph_st, meminfo, fifo;
 
        DBG(2, "%s: %s\n", dev->name, __FUNCTION__);
 
@@ -1398,11 +1404,13 @@ static void smc_timeout(struct net_device *dev)
        mask = SMC_GET_INT_MASK();
        fifo = SMC_GET_FIFO();
        SMC_SELECT_BANK(0);
+       eph_st = SMC_GET_EPH_STATUS();
        meminfo = SMC_GET_MIR();
        SMC_SELECT_BANK(2);
        spin_unlock_irq(&lp->lock);
-       PRINTK( "%s: INT 0x%02x MASK 0x%02x MEM 0x%04x FIFO 0x%04x\n",
-               dev->name, status, mask, meminfo, fifo );
+       PRINTK( "%s: TX timeout (INT 0x%02x INTMASK 0x%02x "
+               "MEM 0x%04x FIFO 0x%04x EPH_ST 0x%04x)\n",
+               dev->name, status, mask, meminfo, fifo, eph_st );
 
        smc_reset(dev);
        smc_enable(dev);
@@ -1863,7 +1871,7 @@ static int __init smc_probe(struct net_device *dev, void __iomem *ioaddr)
        SMC_SELECT_BANK(1);
        val = SMC_GET_BASE();
        val = ((val & 0x1F00) >> 3) << SMC_IO_SHIFT;
-       if (((unsigned long)ioaddr & ((PAGE_SIZE-1)<<SMC_IO_SHIFT)) != val) { /*XXX: WTF? */
+       if (((unsigned int)ioaddr & (0x3e0 << SMC_IO_SHIFT)) != val) {
                printk("%s: IOADDR %p doesn't match configuration (%x).\n",
                        CARDNAME, ioaddr, val);
        }
index ddd2688e7d33ee61e76c9fad7e7796a5273ef825..946528e6b742000523f6991cf7925f2c123a3b24 100644 (file)
 
 /* We actually can't write halfwords properly if not word aligned */
 static inline void
-SMC_outw(u16 val, unsigned long ioaddr, int reg)
+SMC_outw(u16 val, void __iomem *ioaddr, int reg)
 {
        if (reg & 2) {
                unsigned int v = val << 16;
@@ -317,7 +317,7 @@ static inline void SMC_outsw (unsigned long a, int r, unsigned char* p, int l)
 #define SMC_insl(a, r, p, l) \
        smc_pxa_dma_insl(a, lp->physaddr, r, dev->dma, p, l)
 static inline void
-smc_pxa_dma_insl(u_long ioaddr, u_long physaddr, int reg, int dma,
+smc_pxa_dma_insl(void __iomem *ioaddr, u_long physaddr, int reg, int dma,
                 u_char *buf, int len)
 {
        dma_addr_t dmabuf;
@@ -355,7 +355,7 @@ smc_pxa_dma_insl(u_long ioaddr, u_long physaddr, int reg, int dma,
 #define SMC_insw(a, r, p, l) \
        smc_pxa_dma_insw(a, lp->physaddr, r, dev->dma, p, l)
 static inline void
-smc_pxa_dma_insw(u_long ioaddr, u_long physaddr, int reg, int dma,
+smc_pxa_dma_insw(void __iomem *ioaddr, u_long physaddr, int reg, int dma,
                 u_char *buf, int len)
 {
        dma_addr_t dmabuf;
@@ -680,14 +680,6 @@ static const char * chip_ids[ 16 ] =  {
        NULL, NULL, NULL};
 
 
-/*
- . Transmit status bits
-*/
-#define TS_SUCCESS 0x0001
-#define TS_LOSTCAR 0x0400
-#define TS_LATCOL  0x0200
-#define TS_16COL   0x0010
-
 /*
  . Receive status bits
 */
@@ -845,6 +837,7 @@ static const char * chip_ids[ 16 ] =  {
 #define SMC_GET_FIFO()         SMC_inw( ioaddr, FIFO_REG )
 #define SMC_GET_PTR()          SMC_inw( ioaddr, PTR_REG )
 #define SMC_SET_PTR(x)         SMC_outw( x, ioaddr, PTR_REG )
+#define SMC_GET_EPH_STATUS()   SMC_inw( ioaddr, EPH_STATUS_REG )
 #define SMC_GET_RCR()          SMC_inw( ioaddr, RCR_REG )
 #define SMC_SET_RCR(x)         SMC_outw( x, ioaddr, RCR_REG )
 #define SMC_GET_REV()          SMC_inw( ioaddr, REV_REG )