Fedora kernel-2.6.17-1.2142_FC4 patched with stable patch-2.6.17.4-vs2.0.2-rc26.diff
[linux-2.6.git] / drivers / net / arm / am79c961a.c
index 9b659e3..09d5c3f 100644 (file)
  */
 #include <linux/kernel.h>
 #include <linux/types.h>
-#include <linux/fcntl.h>
 #include <linux/interrupt.h>
 #include <linux/ioport.h>
-#include <linux/in.h>
 #include <linux/slab.h>
 #include <linux/string.h>
 #include <linux/errno.h>
 #include <linux/netdevice.h>
 #include <linux/etherdevice.h>
-#include <linux/skbuff.h>
 #include <linux/delay.h>
 #include <linux/init.h>
 #include <linux/crc32.h>
 #include <linux/bitops.h>
+#include <linux/platform_device.h>
 
-#include <asm/system.h>
-#include <asm/irq.h>
+#include <asm/hardware.h>
 #include <asm/io.h>
-#include <asm/dma.h>
+#include <asm/system.h>
 
 #define TX_BUFFERS 15
 #define RX_BUFFERS 25
@@ -85,7 +82,7 @@ static inline unsigned short read_ireg(u_long base_addr, u_int reg)
        u_short v;
        __asm__(
        "str%?h %1, [%2]        @ NAT_RAP\n\t"
-       "str%?h %0, [%2, #8]    @ NET_IDP\n\t"
+       "ldr%?h %0, [%2, #8]    @ NET_IDP\n\t"
        : "=r" (v)
        : "r" (reg), "r" (ISAIO_BASE + 0x0464));
        return v;
@@ -283,12 +280,15 @@ static void am79c961_timer(unsigned long data)
        lnkstat = read_ireg(dev->base_addr, ISALED0) & ISALED0_LNKST;
        carrier = netif_carrier_ok(dev);
 
-       if (lnkstat && !carrier)
+       if (lnkstat && !carrier) {
                netif_carrier_on(dev);
-       else if (!lnkstat && carrier)
+               printk("%s: link up\n", dev->name);
+       } else if (!lnkstat && carrier) {
                netif_carrier_off(dev);
+               printk("%s: link down\n", dev->name);
+       }
 
-       mod_timer(&priv->timer, jiffies + 5*HZ);
+       mod_timer(&priv->timer, jiffies + msecs_to_jiffies(500));
 }
 
 /*
@@ -668,17 +668,24 @@ static void __init am79c961_banner(void)
                printk(KERN_INFO "%s", version);
 }
 
-static int __init am79c961_init(void)
+static int __init am79c961_probe(struct platform_device *pdev)
 {
+       struct resource *res;
        struct net_device *dev;
        struct dev_priv *priv;
        int i, ret;
 
+       res = platform_get_resource(pdev, IORESOURCE_IO, 0);
+       if (!res)
+               return -ENODEV;
+
        dev = alloc_etherdev(sizeof(struct dev_priv));
        ret = -ENOMEM;
        if (!dev)
                goto out;
 
+       SET_NETDEV_DEV(dev, &pdev->dev);
+
        priv = netdev_priv(dev);
 
        /*
@@ -686,10 +693,12 @@ static int __init am79c961_init(void)
         * The PNP initialisation should have been
         * done by the ether bootp loader.
         */
-       dev->base_addr = 0x220;
-       dev->irq = IRQ_EBSA110_ETHERNET;
+       dev->base_addr = res->start;
+       dev->irq = platform_get_irq(pdev, 0);
 
-       ret = -ENODEV;
+       ret = -ENODEV;
+       if (dev->irq < 0)
+               goto nodev;
        if (!request_region(dev->base_addr, 0x18, dev->name))
                goto nodev;
 
@@ -708,14 +717,10 @@ static int __init am79c961_init(void)
            inb(dev->base_addr + 4) != 0x2b)
                goto release;
 
-       am79c961_banner();
-       printk(KERN_INFO "%s: ether address ", dev->name);
-
-       /* Retrive and print the ethernet address. */
-       for (i = 0; i < 6; i++) {
+       for (i = 0; i < 6; i++)
                dev->dev_addr[i] = inb(dev->base_addr + i * 2) & 0xff;
-               printk (i == 5 ? "%02x\n" : "%02x:", dev->dev_addr[i]);
-       }
+
+       am79c961_banner();
 
        spin_lock_init(&priv->chip_lock);
        init_timer(&priv->timer);
@@ -736,8 +741,15 @@ static int __init am79c961_init(void)
 #endif
 
        ret = register_netdev(dev);
-       if (ret == 0)
+       if (ret == 0) {
+               printk(KERN_INFO "%s: ether address ", dev->name);
+
+               /* Retrive and print the ethernet address. */
+               for (i = 0; i < 6; i++)
+                       printk (i == 5 ? "%02x\n" : "%02x:", dev->dev_addr[i]);
+
                return 0;
+       }
 
 release:
        release_region(dev->base_addr, 0x18);
@@ -747,4 +759,16 @@ out:
        return ret;
 }
 
+static struct platform_driver am79c961_driver = {
+       .probe          = am79c961_probe,
+       .driver         = {
+               .name   = "am79c961",
+       },
+};
+
+static int __init am79c961_init(void)
+{
+       return platform_driver_register(&am79c961_driver);
+}
+
 __initcall(am79c961_init);