memset((char *)p->scb,0,sizeof(struct scb_struct));
}
+/* set: io,irq,memstart,memend or set it when calling insmod */
+static int irq=9;
+static int io=0x300;
+static long memstart; /* e.g 0xd0000 */
+static long memend; /* e.g 0xd4000 */
+
/**********************************************
* probe the ni5210-card
*/
-int __init ni52_probe(struct net_device *dev)
+struct net_device * __init ni52_probe(int unit)
{
-#ifndef MODULE
- int *port;
+ struct net_device *dev = alloc_etherdev(sizeof(struct priv));
static int ports[] = {0x300, 0x280, 0x360 , 0x320 , 0x340, 0};
-#endif
- int base_addr = dev->base_addr;
+ int *port;
+ int err = 0;
+
+ if (!dev)
+ return ERR_PTR(-ENOMEM);
+
+ if (unit >= 0) {
+ sprintf(dev->name, "eth%d", unit);
+ netdev_boot_setup_check(dev);
+ io = dev->base_addr;
+ irq = dev->irq;
+ memstart = dev->mem_start;
+ memend = dev->mem_end;
+ }
SET_MODULE_OWNER(dev);
- if (base_addr > 0x1ff) /* Check a single specified location. */
- return ni52_probe1(dev, base_addr);
- else if (base_addr > 0) /* Don't probe at all. */
- return -ENXIO;
-
-#ifdef MODULE
- printk("%s: no autoprobing allowed for modules.\n",dev->name);
-#else
- for (port = ports; *port; port++) {
- int ioaddr = *port;
- dev->base_addr = ioaddr;
- if (ni52_probe1(dev, ioaddr) == 0)
- return 0;
- }
-
+ if (io > 0x1ff) { /* Check a single specified location. */
+ err = ni52_probe1(dev, io);
+ } else if (io > 0) { /* Don't probe at all. */
+ err = -ENXIO;
+ } else {
+ for (port = ports; *port && ni52_probe1(dev, *port) ; port++)
+ ;
+ if (*port)
+ goto got_it;
#ifdef FULL_IO_PROBE
- for(dev->base_addr=0x200; dev->base_addr<0x400; dev->base_addr+=8)
- if (ni52_probe1(dev, dev->base_addr) == 0)
- return 0;
-#endif
-
+ for (io = 0x200; io < 0x400 && ni52_probe1(dev, io); io += 8)
+ ;
+ if (io < 0x400)
+ goto got_it;
#endif
-
- dev->base_addr = base_addr;
- return -ENODEV;
+ err = -ENODEV;
+ }
+ if (err)
+ goto out;
+got_it:
+ err = register_netdev(dev);
+ if (err)
+ goto out1;
+ return dev;
+out1:
+ release_region(dev->base_addr, NI52_TOTAL_SIZE);
+out:
+ free_netdev(dev);
+ return ERR_PTR(err);
}
static int __init ni52_probe1(struct net_device *dev,int ioaddr)
{
int i, size, retval;
+ dev->base_addr = ioaddr;
+ dev->irq = irq;
+ dev->mem_start = memstart;
+ dev->mem_end = memend;
+
if (!request_region(ioaddr, NI52_TOTAL_SIZE, dev->name))
return -EBUSY;
goto out;
}
- printk("%s: NI5210 found at %#3lx, ",dev->name,dev->base_addr);
+ printk(KERN_INFO "%s: NI5210 found at %#3lx, ",dev->name,dev->base_addr);
/*
* check (or search) IO-Memory, 8K and 16K
dev->mem_end = dev->mem_start + size; /* set mem_end showed by 'ifconfig' */
#endif
- dev->priv = (void *) kmalloc(sizeof(struct priv),GFP_KERNEL);
- if(dev->priv == NULL) {
- printk("%s: Ooops .. can't allocate private driver memory.\n",dev->name);
- retval = -ENOMEM;
- goto out;
- }
- /* warning: we don't free it on errors */
memset((char *) dev->priv,0,sizeof(struct priv));
((struct priv *) (dev->priv))->memtop = isa_bus_to_virt(dev->mem_start) + size;
if(!dev->irq)
{
printk("?autoirq, Failed to detect IRQ line!\n");
- kfree(dev->priv);
- dev->priv = NULL;
retval = -EAGAIN;
goto out;
}
dev->if_port = 0;
- ether_setup(dev);
-
return 0;
out:
release_region(ioaddr, NI52_TOTAL_SIZE);
}
#ifdef MODULE
-static struct net_device dev_ni52;
-
-/* set: io,irq,memstart,memend or set it when calling insmod */
-static int irq=9;
-static int io=0x300;
-static long memstart; /* e.g 0xd0000 */
-static long memend; /* e.g 0xd4000 */
+static struct net_device *dev_ni52;
MODULE_PARM(io, "i");
MODULE_PARM(irq, "i");
printk("ni52: Autoprobing not allowed for modules.\nni52: Set symbols 'io' 'irq' 'memstart' and 'memend'\n");
return -ENODEV;
}
- dev_ni52.init = ni52_probe;
- dev_ni52.irq = irq;
- dev_ni52.base_addr = io;
- dev_ni52.mem_end = memend;
- dev_ni52.mem_start = memstart;
- if (register_netdev(&dev_ni52) != 0)
- return -EIO;
+ dev_ni52 = ni52_probe(-1);
+ if (IS_ERR(dev_ni52))
+ return PTR_ERR(dev_ni52);
return 0;
}
void cleanup_module(void)
{
- release_region(dev_ni52.base_addr, NI52_TOTAL_SIZE);
- unregister_netdev(&dev_ni52);
- kfree(dev_ni52.priv);
- dev_ni52.priv = NULL;
+ unregister_netdev(dev_ni52);
+ release_region(dev_ni52->base_addr, NI52_TOTAL_SIZE);
+ free_netdev(dev_ni52);
}
#endif /* MODULE */