+++ /dev/null
-/*  ewrk3.c: A DIGITAL EtherWORKS 3 ethernet driver for Linux.
-
-   Written 1994 by David C. Davies.
-
-   Copyright 1994 Digital Equipment Corporation.
-
-   This software may be used and distributed according to the terms of
-   the GNU General Public License, incorporated herein by reference.
-
-   This driver is written for the Digital Equipment Corporation series
-   of EtherWORKS ethernet cards:
-
-   DE203 Turbo (BNC)
-   DE204 Turbo (TP)
-   DE205 Turbo (TP BNC)
-
-   The driver has been tested on a relatively busy  network using the DE205
-   card and benchmarked with 'ttcp': it transferred 16M  of data at 975kB/s
-   (7.8Mb/s) to a DECstation 5000/200.
-
-   The author may be reached at davies@maniac.ultranet.com.
-
-   =========================================================================
-   This driver has been written  substantially  from scratch, although  its
-   inheritance of style and stack interface from 'depca.c' and in turn from
-   Donald Becker's 'lance.c' should be obvious.
-
-   The  DE203/4/5 boards  all  use a new proprietary   chip in place of the
-   LANCE chip used in prior cards  (DEPCA, DE100, DE200/1/2, DE210, DE422).
-   Use the depca.c driver in the standard distribution  for the LANCE based
-   cards from DIGITAL; this driver will not work with them.
-
-   The DE203/4/5 cards have 2  main modes: shared memory  and I/O only. I/O
-   only makes  all the card accesses through  I/O transactions and  no high
-   (shared)  memory is used. This  mode provides a >48% performance penalty
-   and  is deprecated in this  driver,  although allowed to provide initial
-   setup when hardstrapped.
-
-   The shared memory mode comes in 3 flavours: 2kB, 32kB and 64kB. There is
-   no point in using any mode other than the 2kB  mode - their performances
-   are virtually identical, although the driver has  been tested in the 2kB
-   and 32kB modes. I would suggest you uncomment the line:
-
-   FORCE_2K_MODE;
-
-   to allow the driver to configure the card as a  2kB card at your current
-   base  address, thus leaving more  room to clutter  your  system box with
-   other memory hungry boards.
-
-   As many ISA  and EISA cards  can be supported  under this driver  as you
-   wish, limited primarily  by the available IRQ lines,  rather than by the
-   available I/O addresses  (24 ISA,  16 EISA).   I have  checked different
-   configurations of  multiple  depca cards and  ewrk3 cards  and have  not
-   found a problem yet (provided you have at least depca.c v0.38) ...
-
-   The board IRQ setting   must be at  an unused  IRQ which is  auto-probed
-   using  Donald  Becker's autoprobe  routines.   All  these cards   are at
-   {5,10,11,15}.
-
-   No 16MB memory  limitation should exist with this  driver as DMA is  not
-   used and the common memory area is in low memory on the network card (my
-   current system has 20MB and I've not had problems yet).
-
-   The ability to load  this driver as a  loadable module has been included
-   and used  extensively during the  driver development (to save those long
-   reboot sequences). To utilise this ability, you have to do 8 things:
-
-   0) have a copy of the loadable modules code installed on your system.
-   1) copy ewrk3.c from the  /linux/drivers/net directory to your favourite
-   temporary directory.
-   2) edit the  source code near  line 1898 to reflect  the I/O address and
-   IRQ you're using.
-   3) compile  ewrk3.c, but include -DMODULE in  the command line to ensure
-   that the correct bits are compiled (see end of source code).
-   4) if you are wanting to add a new  card, goto 5. Otherwise, recompile a
-   kernel with the ewrk3 configuration turned off and reboot.
-   5) insmod ewrk3.o
-   [Alan Cox: Changed this so you can insmod ewrk3.o irq=x io=y]
-   [Adam Kropelin: now accepts irq=x1,x2 io=y1,y2 for multiple cards]
-   6) run the net startup bits for your new eth?? interface manually
-   (usually /etc/rc.inet[12] at boot time).
-   7) enjoy!
-
-   Note that autoprobing is not allowed in loadable modules - the system is
-   already up and running and you're messing with interrupts.
-
-   To unload a module, turn off the associated interface
-   'ifconfig eth?? down' then 'rmmod ewrk3'.
-
-   Promiscuous   mode has been  turned  off  in this driver,   but  all the
-   multicast  address bits  have been   turned on. This  improved the  send
-   performance on a busy network by about 13%.
-
-   Ioctl's have now been provided (primarily because  I wanted to grab some
-   packet size statistics). They  are patterned after 'plipconfig.c' from a
-   suggestion by Alan Cox.  Using these  ioctls, you can enable promiscuous
-   mode, add/delete multicast  addresses, change the hardware address,  get
-   packet size distribution statistics and muck around with the control and
-   status register. I'll add others if and when the need arises.
-
-   TO DO:
-   ------
-
-
-   Revision History
-   ----------------
-
-   Version   Date        Description
-
-   0.1     26-aug-94   Initial writing. ALPHA code release.
-   0.11    31-aug-94   Fixed: 2k mode memory base calc.,
-   LeMAC version calc.,
-   IRQ vector assignments during autoprobe.
-   0.12    31-aug-94   Tested working on LeMAC2 (DE20[345]-AC) card.
-   Fixed up MCA hash table algorithm.
-   0.20     4-sep-94   Added IOCTL functionality.
-   0.21    14-sep-94   Added I/O mode.
-   0.21axp 15-sep-94   Special version for ALPHA AXP Linux V1.0.
-   0.22    16-sep-94   Added more IOCTLs & tidied up.
-   0.23    21-sep-94   Added transmit cut through.
-   0.24    31-oct-94   Added uid checks in some ioctls.
-   0.30     1-nov-94   BETA code release.
-   0.31     5-dec-94   Added check/allocate region code.
-   0.32    16-jan-95   Broadcast packet fix.
-   0.33    10-Feb-95   Fix recognition bug reported by <bkm@star.rl.ac.uk>.
-   0.40    27-Dec-95   Rationalise MODULE and autoprobe code.
-   Rewrite for portability & updated.
-   ALPHA support from <jestabro@amt.tay1.dec.com>
-   Added verify_area() calls in ewrk3_ioctl() from
-   suggestion by <heiko@colossus.escape.de>.
-   Add new multicasting code.
-   0.41    20-Jan-96   Fix IRQ set up problem reported by
-   <kenneth@bbs.sas.ntu.ac.sg>.
-   0.42    22-Apr-96   Fix alloc_device() bug <jari@markkus2.fimr.fi>
-   0.43    16-Aug-96   Update alloc_device() to conform to de4x5.c
-   0.44    08-Nov-01   use library crc32 functions <Matt_Domsch@dell.com>
-   0.45    19-Jul-02   fix unaligned access on alpha <martin@bruli.net>
-   0.46    10-Oct-02   Multiple NIC support when module <akropel1@rochester.rr.com>
-   0.47    18-Oct-02   ethtool support <akropel1@rochester.rr.com>
-   0.48    18-Oct-02   cli/sti removal for 2.5 <vda@port.imtp.ilyichevsk.odessa.ua>
-   ioctl locking, signature search cleanup <akropel1@rochester.rr.com>
-
-   =========================================================================
- */
-
-#include <linux/module.h>
-#include <linux/kernel.h>
-#include <linux/sched.h>
-#include <linux/string.h>
-#include <linux/errno.h>
-#include <linux/ioport.h>
-#include <linux/slab.h>
-#include <linux/interrupt.h>
-#include <linux/delay.h>
-#include <linux/init.h>
-#include <linux/crc32.h>
-#include <linux/netdevice.h>
-#include <linux/etherdevice.h>
-#include <linux/skbuff.h>
-#include <linux/ethtool.h>
-#include <linux/time.h>
-#include <linux/types.h>
-#include <linux/unistd.h>
-#include <linux/ctype.h>
-#include <linux/bitops.h>
-
-#include <asm/io.h>
-#include <asm/dma.h>
-#include <asm/uaccess.h>
-
-#include "ewrk3.h"
-
-#define DRV_NAME       "ewrk3"
-#define DRV_VERSION    "0.48"
-
-static char version[] __initdata =
-DRV_NAME ":v" DRV_VERSION " 2002/10/18 davies@maniac.ultranet.com\n";
-
-#ifdef EWRK3_DEBUG
-static int ewrk3_debug = EWRK3_DEBUG;
-#else
-static int ewrk3_debug = 1;
-#endif
-
-#define EWRK3_NDA 0xffe0       /* No Device Address */
-
-#define PROBE_LENGTH    32
-#define ETH_PROM_SIG    0xAA5500FFUL
-
-#ifndef EWRK3_SIGNATURE
-#define EWRK3_SIGNATURE {"DE203","DE204","DE205",""}
-#define EWRK3_STRLEN 8
-#endif
-
-#ifndef EWRK3_RAM_BASE_ADDRESSES
-#define EWRK3_RAM_BASE_ADDRESSES {0xc0000,0xd0000,0x00000}
-#endif
-
-/*
-   ** Sets up the I/O area for the autoprobe.
- */
-#define EWRK3_IO_BASE 0x100    /* Start address for probe search */
-#define EWRK3_IOP_INC 0x20     /* I/O address increment */
-#define EWRK3_TOTAL_SIZE 0x20  /* required I/O address length */
-
-#ifndef MAX_NUM_EWRK3S
-#define MAX_NUM_EWRK3S 21
-#endif
-
-#ifndef EWRK3_EISA_IO_PORTS
-#define EWRK3_EISA_IO_PORTS 0x0c00     /* I/O port base address, slot 0 */
-#endif
-
-#ifndef MAX_EISA_SLOTS
-#define MAX_EISA_SLOTS 16
-#define EISA_SLOT_INC 0x1000
-#endif
-
-#define QUEUE_PKT_TIMEOUT (1*HZ)       /* Jiffies */
-
-/*
-   ** EtherWORKS 3 shared memory window sizes
- */
-#define IO_ONLY         0x00
-#define SHMEM_2K        0x800
-#define SHMEM_32K       0x8000
-#define SHMEM_64K       0x10000
-
-/*
-   ** EtherWORKS 3 IRQ ENABLE/DISABLE
- */
-#define ENABLE_IRQs { \
-  icr |= lp->irq_mask;\
-  outb(icr, EWRK3_ICR);                     /* Enable the IRQs */\
-}
-
-#define DISABLE_IRQs { \
-  icr = inb(EWRK3_ICR);\
-  icr &= ~lp->irq_mask;\
-  outb(icr, EWRK3_ICR);                     /* Disable the IRQs */\
-}
-
-/*
-   ** EtherWORKS 3 START/STOP
- */
-#define START_EWRK3 { \
-  csr = inb(EWRK3_CSR);\
-  csr &= ~(CSR_TXD|CSR_RXD);\
-  outb(csr, EWRK3_CSR);                     /* Enable the TX and/or RX */\
-}
-
-#define STOP_EWRK3 { \
-  csr = (CSR_TXD|CSR_RXD);\
-  outb(csr, EWRK3_CSR);                     /* Disable the TX and/or RX */\
-}
-
-/*
-   ** The EtherWORKS 3 private structure
- */
-#define EWRK3_PKT_STAT_SZ 16
-#define EWRK3_PKT_BIN_SZ  128  /* Should be >=100 unless you
-                                  increase EWRK3_PKT_STAT_SZ */
-
-struct ewrk3_stats {
-       u32 bins[EWRK3_PKT_STAT_SZ];
-       u32 unicast;
-       u32 multicast;
-       u32 broadcast;
-       u32 excessive_collisions;
-       u32 tx_underruns;
-       u32 excessive_underruns;
-};
-
-struct ewrk3_private {
-       char adapter_name[80];  /* Name exported to /proc/ioports */
-       u_long shmem_base;      /* Shared memory start address */
-       void __iomem *shmem;
-       u_long shmem_length;    /* Shared memory window length */
-       struct ewrk3_stats pktStats; /* Private stats counters */
-       u_char irq_mask;        /* Adapter IRQ mask bits */
-       u_char mPage;           /* Maximum 2kB Page number */
-       u_char lemac;           /* Chip rev. level */
-       u_char hard_strapped;   /* Don't allow a full open */
-       u_char txc;             /* Transmit cut through */
-       void __iomem *mctbl;    /* Pointer to the multicast table */
-       u_char led_mask;        /* Used to reserve LED access for ethtool */
-       spinlock_t hw_lock;
-};
-
-/*
-   ** Force the EtherWORKS 3 card to be in 2kB MODE
- */
-#define FORCE_2K_MODE { \
-  shmem_length = SHMEM_2K;\
-  outb(((mem_start - 0x80000) >> 11), EWRK3_MBR);\
-}
-
-/*
-   ** Public Functions
- */
-static int ewrk3_open(struct net_device *dev);
-static netdev_tx_t ewrk3_queue_pkt(struct sk_buff *skb, struct net_device *dev);
-static irqreturn_t ewrk3_interrupt(int irq, void *dev_id);
-static int ewrk3_close(struct net_device *dev);
-static void set_multicast_list(struct net_device *dev);
-static int ewrk3_ioctl(struct net_device *dev, struct ifreq *rq, int cmd);
-static const struct ethtool_ops ethtool_ops_203;
-static const struct ethtool_ops ethtool_ops;
-
-/*
-   ** Private functions
- */
-static int ewrk3_hw_init(struct net_device *dev, u_long iobase);
-static void ewrk3_init(struct net_device *dev);
-static int ewrk3_rx(struct net_device *dev);
-static int ewrk3_tx(struct net_device *dev);
-static void ewrk3_timeout(struct net_device *dev);
-
-static void EthwrkSignature(char *name, char *eeprom_image);
-static int DevicePresent(u_long iobase);
-static void SetMulticastFilter(struct net_device *dev);
-static int EISA_signature(char *name, s32 eisa_id);
-
-static int Read_EEPROM(u_long iobase, u_char eaddr);
-static int Write_EEPROM(short data, u_long iobase, u_char eaddr);
-static u_char get_hw_addr(struct net_device *dev, u_char * eeprom_image, char chipType);
-
-static int ewrk3_probe1(struct net_device *dev, u_long iobase, int irq);
-static int isa_probe(struct net_device *dev, u_long iobase);
-static int eisa_probe(struct net_device *dev, u_long iobase);
-
-static u_char irq[MAX_NUM_EWRK3S+1] = {5, 0, 10, 3, 11, 9, 15, 12};
-
-static char name[EWRK3_STRLEN + 1];
-static int num_ewrks3s;
-
-/*
-   ** Miscellaneous defines...
- */
-#define INIT_EWRK3 {\
-    outb(EEPROM_INIT, EWRK3_IOPR);\
-    mdelay(1);\
-}
-
-#ifndef MODULE
-struct net_device * __init ewrk3_probe(int unit)
-{
-       struct net_device *dev = alloc_etherdev(sizeof(struct ewrk3_private));
-       int err;
-
-       if (!dev)
-               return ERR_PTR(-ENOMEM);
-
-       if (unit >= 0) {
-               sprintf(dev->name, "eth%d", unit);
-               netdev_boot_setup_check(dev);
-       }
-
-       err = ewrk3_probe1(dev, dev->base_addr, dev->irq);
-       if (err)
-               goto out;
-       return dev;
-out:
-       free_netdev(dev);
-       return ERR_PTR(err);
-
-}
-#endif
-
-static int __init ewrk3_probe1(struct net_device *dev, u_long iobase, int irq)
-{
-       int err;
-
-       dev->base_addr = iobase;
-       dev->irq = irq;
-
-       /* Address PROM pattern */
-       err = isa_probe(dev, iobase);
-       if (err != 0)
-               err = eisa_probe(dev, iobase);
-
-       if (err)
-               return err;
-
-       err = register_netdev(dev);
-       if (err)
-               release_region(dev->base_addr, EWRK3_TOTAL_SIZE);
-
-       return err;
-}
-
-static const struct net_device_ops ewrk3_netdev_ops = {
-       .ndo_open               = ewrk3_open,
-       .ndo_start_xmit         = ewrk3_queue_pkt,
-       .ndo_stop               = ewrk3_close,
-       .ndo_set_rx_mode        = set_multicast_list,
-       .ndo_do_ioctl           = ewrk3_ioctl,
-       .ndo_tx_timeout         = ewrk3_timeout,
-       .ndo_change_mtu         = eth_change_mtu,
-       .ndo_set_mac_address    = eth_mac_addr,
-       .ndo_validate_addr      = eth_validate_addr,
-};
-
-static int __init
-ewrk3_hw_init(struct net_device *dev, u_long iobase)
-{
-       struct ewrk3_private *lp;
-       int i, status = 0;
-       u_long mem_start, shmem_length;
-       u_char cr, cmr, icr, nicsr, lemac, hard_strapped = 0;
-       u_char eeprom_image[EEPROM_MAX], chksum, eisa_cr = 0;
-
-       /*
-       ** Stop the EWRK3. Enable the DBR ROM. Disable interrupts and remote boot.
-       ** This also disables the EISA_ENABLE bit in the EISA Control Register.
-        */
-       if (iobase > 0x400)
-               eisa_cr = inb(EISA_CR);
-       INIT_EWRK3;
-
-       nicsr = inb(EWRK3_CSR);
-
-       icr = inb(EWRK3_ICR);
-       icr &= 0x70;
-       outb(icr, EWRK3_ICR);   /* Disable all the IRQs */
-
-       if (nicsr != (CSR_TXD | CSR_RXD))
-               return -ENXIO;
-
-       /* Check that the EEPROM is alive and well and not living on Pluto... */
-       for (chksum = 0, i = 0; i < EEPROM_MAX; i += 2) {
-               union {
-                       short val;
-                       char c[2];
-               } tmp;
-
-               tmp.val = (short) Read_EEPROM(iobase, (i >> 1));
-               eeprom_image[i] = tmp.c[0];
-               eeprom_image[i + 1] = tmp.c[1];
-               chksum += eeprom_image[i] + eeprom_image[i + 1];
-       }
-
-       if (chksum != 0) {      /* Bad EEPROM Data! */
-               printk("%s: Device has a bad on-board EEPROM.\n", dev->name);
-               return -ENXIO;
-       }
-
-       EthwrkSignature(name, eeprom_image);
-       if (*name == '\0')
-               return -ENXIO;
-
-       dev->base_addr = iobase;
-
-       if (iobase > 0x400) {
-               outb(eisa_cr, EISA_CR);         /* Rewrite the EISA CR */
-       }
-       lemac = eeprom_image[EEPROM_CHIPVER];
-       cmr = inb(EWRK3_CMR);
-
-       if (((lemac == LeMAC) && ((cmr & CMR_NO_EEPROM) != CMR_NO_EEPROM)) ||
-           ((lemac == LeMAC2) && !(cmr & CMR_HS))) {
-               printk("%s: %s at %#4lx", dev->name, name, iobase);
-               hard_strapped = 1;
-       } else if ((iobase & 0x0fff) == EWRK3_EISA_IO_PORTS) {
-               /* EISA slot address */
-               printk("%s: %s at %#4lx (EISA slot %ld)",
-                      dev->name, name, iobase, ((iobase >> 12) & 0x0f));
-       } else {        /* ISA port address */
-               printk("%s: %s at %#4lx", dev->name, name, iobase);
-       }
-
-       printk(", h/w address ");
-       if (lemac != LeMAC2)
-               DevicePresent(iobase);  /* need after EWRK3_INIT */
-       status = get_hw_addr(dev, eeprom_image, lemac);
-       printk("%pM\n", dev->dev_addr);
-
-       if (status) {
-               printk("      which has an EEPROM CRC error.\n");
-               return -ENXIO;
-       }
-
-       if (lemac == LeMAC2) {  /* Special LeMAC2 CMR things */
-               cmr &= ~(CMR_RA | CMR_WB | CMR_LINK | CMR_POLARITY | CMR_0WS);
-               if (eeprom_image[EEPROM_MISC0] & READ_AHEAD)
-                       cmr |= CMR_RA;
-               if (eeprom_image[EEPROM_MISC0] & WRITE_BEHIND)
-                       cmr |= CMR_WB;
-               if (eeprom_image[EEPROM_NETMAN0] & NETMAN_POL)
-                       cmr |= CMR_POLARITY;
-               if (eeprom_image[EEPROM_NETMAN0] & NETMAN_LINK)
-                       cmr |= CMR_LINK;
-               if (eeprom_image[EEPROM_MISC0] & _0WS_ENA)
-                       cmr |= CMR_0WS;
-       }
-       if (eeprom_image[EEPROM_SETUP] & SETUP_DRAM)
-               cmr |= CMR_DRAM;
-       outb(cmr, EWRK3_CMR);
-
-       cr = inb(EWRK3_CR);     /* Set up the Control Register */
-       cr |= eeprom_image[EEPROM_SETUP] & SETUP_APD;
-       if (cr & SETUP_APD)
-               cr |= eeprom_image[EEPROM_SETUP] & SETUP_PS;
-       cr |= eeprom_image[EEPROM_MISC0] & FAST_BUS;
-       cr |= eeprom_image[EEPROM_MISC0] & ENA_16;
-       outb(cr, EWRK3_CR);
-
-       /*
-       ** Determine the base address and window length for the EWRK3
-       ** RAM from the memory base register.
-       */
-       mem_start = inb(EWRK3_MBR);
-       shmem_length = 0;
-       if (mem_start != 0) {
-               if ((mem_start >= 0x0a) && (mem_start <= 0x0f)) {
-                       mem_start *= SHMEM_64K;
-                       shmem_length = SHMEM_64K;
-               } else if ((mem_start >= 0x14) && (mem_start <= 0x1f)) {
-                       mem_start *= SHMEM_32K;
-                       shmem_length = SHMEM_32K;
-               } else if ((mem_start >= 0x40) && (mem_start <= 0xff)) {
-                       mem_start = mem_start * SHMEM_2K + 0x80000;
-                       shmem_length = SHMEM_2K;
-               } else {
-                       return -ENXIO;
-               }
-       }
-       /*
-       ** See the top of this source code for comments about
-       ** uncommenting this line.
-       */
-/*          FORCE_2K_MODE; */
-
-       if (hard_strapped) {
-               printk("      is hard strapped.\n");
-       } else if (mem_start) {
-               printk("      has a %dk RAM window", (int) (shmem_length >> 10));
-               printk(" at 0x%.5lx", mem_start);
-       } else {
-               printk("      is in I/O only mode");
-       }
-
-       lp = netdev_priv(dev);
-       lp->shmem_base = mem_start;
-       lp->shmem = ioremap(mem_start, shmem_length);
-       if (!lp->shmem)
-               return -ENOMEM;
-       lp->shmem_length = shmem_length;
-       lp->lemac = lemac;
-       lp->hard_strapped = hard_strapped;
-       lp->led_mask = CR_LED;
-       spin_lock_init(&lp->hw_lock);
-
-       lp->mPage = 64;
-       if (cmr & CMR_DRAM)
-               lp->mPage <<= 1;        /* 2 DRAMS on module */
-
-       sprintf(lp->adapter_name, "%s (%s)", name, dev->name);
-
-       lp->irq_mask = ICR_TNEM | ICR_TXDM | ICR_RNEM | ICR_RXDM;
-
-       if (!hard_strapped) {
-               /*
-               ** Enable EWRK3 board interrupts for autoprobing
-               */
-               icr |= ICR_IE;  /* Enable interrupts */
-               outb(icr, EWRK3_ICR);
-
-               /* The DMA channel may be passed in on this parameter. */
-               dev->dma = 0;
-
-               /* To auto-IRQ we enable the initialization-done and DMA err,
-                  interrupts. For now we will always get a DMA error. */
-               if (dev->irq < 2) {
-#ifndef MODULE
-                       u_char irqnum;
-                       unsigned long irq_mask;
-
-
-                       irq_mask = probe_irq_on();
-
-                       /*
-                       ** Trigger a TNE interrupt.
-                       */
-                       icr |= ICR_TNEM;
-                       outb(1, EWRK3_TDQ);     /* Write to the TX done queue */
-                       outb(icr, EWRK3_ICR);   /* Unmask the TXD interrupt */
-
-                       irqnum = irq[((icr & IRQ_SEL) >> 4)];
-
-                       mdelay(20);
-                       dev->irq = probe_irq_off(irq_mask);
-                       if ((dev->irq) && (irqnum == dev->irq)) {
-                               printk(" and uses IRQ%d.\n", dev->irq);
-                       } else {
-                               if (!dev->irq) {
-                                       printk(" and failed to detect IRQ line.\n");
-                               } else if ((irqnum == 1) && (lemac == LeMAC2)) {
-                                       printk(" and an illegal IRQ line detected.\n");
-                               } else {
-                                       printk(", but incorrect IRQ line detected.\n");
-                               }
-                               iounmap(lp->shmem);
-                               return -ENXIO;
-                       }
-
-                       DISABLE_IRQs;   /* Mask all interrupts */
-
-#endif                         /* MODULE */
-               } else {
-                       printk(" and requires IRQ%d.\n", dev->irq);
-               }
-       }
-
-       if (ewrk3_debug > 1) {
-               printk(version);
-       }
-       /* The EWRK3-specific entries in the device structure. */
-       dev->netdev_ops = &ewrk3_netdev_ops;
-       if (lp->adapter_name[4] == '3')
-               SET_ETHTOOL_OPS(dev, ðtool_ops_203);
-       else
-               SET_ETHTOOL_OPS(dev, ðtool_ops);
-       dev->watchdog_timeo = QUEUE_PKT_TIMEOUT;
-
-       dev->mem_start = 0;
-
-       return 0;
-}
-
-
-static int ewrk3_open(struct net_device *dev)
-{
-       struct ewrk3_private *lp = netdev_priv(dev);
-       u_long iobase = dev->base_addr;
-       int status = 0;
-       u_char icr, csr;
-
-       /*
-          ** Stop the TX and RX...
-        */
-       STOP_EWRK3;
-
-       if (!lp->hard_strapped) {
-               if (request_irq(dev->irq, (void *) ewrk3_interrupt, 0, "ewrk3", dev)) {
-                       printk("ewrk3_open(): Requested IRQ%d is busy\n", dev->irq);
-                       status = -EAGAIN;
-               } else {
-
-                       /*
-                          ** Re-initialize the EWRK3...
-                        */
-                       ewrk3_init(dev);
-
-                       if (ewrk3_debug > 1) {
-                               printk("%s: ewrk3 open with irq %d\n", dev->name, dev->irq);
-                               printk("  physical address: %pM\n", dev->dev_addr);
-                               if (lp->shmem_length == 0) {
-                                       printk("  no shared memory, I/O only mode\n");
-                               } else {
-                                       printk("  start of shared memory: 0x%08lx\n", lp->shmem_base);
-                                       printk("  window length: 0x%04lx\n", lp->shmem_length);
-                               }
-                               printk("  # of DRAMS: %d\n", ((inb(EWRK3_CMR) & 0x02) ? 2 : 1));
-                               printk("  csr:  0x%02x\n", inb(EWRK3_CSR));
-                               printk("  cr:   0x%02x\n", inb(EWRK3_CR));
-                               printk("  icr:  0x%02x\n", inb(EWRK3_ICR));
-                               printk("  cmr:  0x%02x\n", inb(EWRK3_CMR));
-                               printk("  fmqc: 0x%02x\n", inb(EWRK3_FMQC));
-                       }
-                       netif_start_queue(dev);
-                       /*
-                          ** Unmask EWRK3 board interrupts
-                        */
-                       icr = inb(EWRK3_ICR);
-                       ENABLE_IRQs;
-
-               }
-       } else {
-               printk(KERN_ERR "%s: ewrk3 available for hard strapped set up only.\n", dev->name);
-               printk(KERN_ERR "      Run the 'ewrk3setup' utility or remove the hard straps.\n");
-               return -EINVAL;
-       }
-
-       return status;
-}
-
-/*
-   ** Initialize the EtherWORKS 3 operating conditions
- */
-static void ewrk3_init(struct net_device *dev)
-{
-       struct ewrk3_private *lp = netdev_priv(dev);
-       u_char csr, page;
-       u_long iobase = dev->base_addr;
-       int i;
-
-       /*
-          ** Enable any multicasts
-        */
-       set_multicast_list(dev);
-
-       /*
-       ** Set hardware MAC address. Address is initialized from the EEPROM
-       ** during startup but may have since been changed by the user.
-       */
-       for (i=0; i<ETH_ALEN; i++)
-               outb(dev->dev_addr[i], EWRK3_PAR0 + i);
-
-       /*
-          ** Clean out any remaining entries in all the queues here
-        */
-       while (inb(EWRK3_TQ));
-       while (inb(EWRK3_TDQ));
-       while (inb(EWRK3_RQ));
-       while (inb(EWRK3_FMQ));
-
-       /*
-          ** Write a clean free memory queue
-        */
-       for (page = 1; page < lp->mPage; page++) {      /* Write the free page numbers */
-               outb(page, EWRK3_FMQ);  /* to the Free Memory Queue */
-       }
-
-       START_EWRK3;            /* Enable the TX and/or RX */
-}
-
-/*
- *  Transmit timeout
- */
-
-static void ewrk3_timeout(struct net_device *dev)
-{
-       struct ewrk3_private *lp = netdev_priv(dev);
-       u_char icr, csr;
-       u_long iobase = dev->base_addr;
-
-       if (!lp->hard_strapped)
-       {
-               printk(KERN_WARNING"%s: transmit timed/locked out, status %04x, resetting.\n",
-                      dev->name, inb(EWRK3_CSR));
-
-               /*
-                  ** Mask all board interrupts
-                */
-               DISABLE_IRQs;
-
-               /*
-                  ** Stop the TX and RX...
-                */
-               STOP_EWRK3;
-
-               ewrk3_init(dev);
-
-               /*
-                  ** Unmask EWRK3 board interrupts
-                */
-               ENABLE_IRQs;
-
-               dev->trans_start = jiffies; /* prevent tx timeout */
-               netif_wake_queue(dev);
-       }
-}
-
-/*
-   ** Writes a socket buffer to the free page queue
- */
-static netdev_tx_t ewrk3_queue_pkt(struct sk_buff *skb, struct net_device *dev)
-{
-       struct ewrk3_private *lp = netdev_priv(dev);
-       u_long iobase = dev->base_addr;
-       void __iomem *buf = NULL;
-       u_char icr;
-       u_char page;
-
-       spin_lock_irq (&lp->hw_lock);
-       DISABLE_IRQs;
-
-       /* if no resources available, exit, request packet be queued */
-       if (inb (EWRK3_FMQC) == 0) {
-               printk (KERN_WARNING "%s: ewrk3_queue_pkt(): No free resources...\n",
-                       dev->name);
-               printk (KERN_WARNING "%s: ewrk3_queue_pkt(): CSR: %02x ICR: %02x FMQC: %02x\n",
-                       dev->name, inb (EWRK3_CSR), inb (EWRK3_ICR),
-                       inb (EWRK3_FMQC));
-               goto err_out;
-       }
-
-       /*
-        ** Get a free page from the FMQ
-        */
-       if ((page = inb (EWRK3_FMQ)) >= lp->mPage) {
-               printk ("ewrk3_queue_pkt(): Invalid free memory page (%d).\n",
-                    (u_char) page);
-               goto err_out;
-       }
-
-
-       /*
-        ** Set up shared memory window and pointer into the window
-        */
-       if (lp->shmem_length == IO_ONLY) {
-               outb (page, EWRK3_IOPR);
-       } else if (lp->shmem_length == SHMEM_2K) {
-               buf = lp->shmem;
-               outb (page, EWRK3_MPR);
-       } else if (lp->shmem_length == SHMEM_32K) {
-               buf = (((short) page << 11) & 0x7800) + lp->shmem;
-               outb ((page >> 4), EWRK3_MPR);
-       } else if (lp->shmem_length == SHMEM_64K) {
-               buf = (((short) page << 11) & 0xf800) + lp->shmem;
-               outb ((page >> 5), EWRK3_MPR);
-       } else {
-               printk (KERN_ERR "%s: Oops - your private data area is hosed!\n",
-                       dev->name);
-               BUG ();
-       }
-
-       /*
-        ** Set up the buffer control structures and copy the data from
-        ** the socket buffer to the shared memory .
-        */
-       if (lp->shmem_length == IO_ONLY) {
-               int i;
-               u_char *p = skb->data;
-               outb ((char) (TCR_QMODE | TCR_PAD | TCR_IFC), EWRK3_DATA);
-               outb ((char) (skb->len & 0xff), EWRK3_DATA);
-               outb ((char) ((skb->len >> 8) & 0xff), EWRK3_DATA);
-               outb ((char) 0x04, EWRK3_DATA);
-               for (i = 0; i < skb->len; i++) {
-                       outb (*p++, EWRK3_DATA);
-               }
-               outb (page, EWRK3_TQ);  /* Start sending pkt */
-       } else {
-               writeb ((char) (TCR_QMODE | TCR_PAD | TCR_IFC), buf);   /* ctrl byte */
-               buf += 1;
-               writeb ((char) (skb->len & 0xff), buf); /* length (16 bit xfer) */
-               buf += 1;
-               if (lp->txc) {
-                       writeb(((skb->len >> 8) & 0xff) | XCT, buf);
-                       buf += 1;
-                       writeb (0x04, buf);     /* index byte */
-                       buf += 1;
-                       writeb (0x00, (buf + skb->len));        /* Write the XCT flag */
-                       memcpy_toio (buf, skb->data, PRELOAD);  /* Write PRELOAD bytes */
-                       outb (page, EWRK3_TQ);  /* Start sending pkt */
-                       memcpy_toio (buf + PRELOAD,
-                                        skb->data + PRELOAD,
-                                        skb->len - PRELOAD);
-                       writeb (0xff, (buf + skb->len));        /* Write the XCT flag */
-               } else {
-                       writeb ((skb->len >> 8) & 0xff, buf);
-                       buf += 1;
-                       writeb (0x04, buf);     /* index byte */
-                       buf += 1;
-                       memcpy_toio (buf, skb->data, skb->len); /* Write data bytes */
-                       outb (page, EWRK3_TQ);  /* Start sending pkt */
-               }
-       }
-
-       ENABLE_IRQs;
-       spin_unlock_irq (&lp->hw_lock);
-
-       dev->stats.tx_bytes += skb->len;
-       dev_kfree_skb (skb);
-
-       /* Check for free resources: stop Tx queue if there are none */
-       if (inb (EWRK3_FMQC) == 0)
-               netif_stop_queue (dev);
-
-       return NETDEV_TX_OK;
-
-err_out:
-       ENABLE_IRQs;
-       spin_unlock_irq (&lp->hw_lock);
-       return NETDEV_TX_BUSY;
-}
-
-/*
-   ** The EWRK3 interrupt handler.
- */
-static irqreturn_t ewrk3_interrupt(int irq, void *dev_id)
-{
-       struct net_device *dev = dev_id;
-       struct ewrk3_private *lp;
-       u_long iobase;
-       u_char icr, cr, csr;
-
-       lp = netdev_priv(dev);
-       iobase = dev->base_addr;
-
-       /* get the interrupt information */
-       csr = inb(EWRK3_CSR);
-
-       /*
-        ** Mask the EWRK3 board interrupts and turn on the LED
-        */
-       spin_lock(&lp->hw_lock);
-       DISABLE_IRQs;
-
-       cr = inb(EWRK3_CR);
-       cr |= lp->led_mask;
-       outb(cr, EWRK3_CR);
-
-       if (csr & CSR_RNE)      /* Rx interrupt (packet[s] arrived) */
-               ewrk3_rx(dev);
-
-       if (csr & CSR_TNE)      /* Tx interrupt (packet sent) */
-               ewrk3_tx(dev);
-
-       /*
-        ** Now deal with the TX/RX disable flags. These are set when there
-        ** are no more resources. If resources free up then enable these
-        ** interrupts, otherwise mask them - failure to do this will result
-        ** in the system hanging in an interrupt loop.
-        */
-       if (inb(EWRK3_FMQC)) {  /* any resources available? */
-               lp->irq_mask |= ICR_TXDM | ICR_RXDM;    /* enable the interrupt source */
-               csr &= ~(CSR_TXD | CSR_RXD);    /* ensure restart of a stalled TX or RX */
-               outb(csr, EWRK3_CSR);
-               netif_wake_queue(dev);
-       } else {
-               lp->irq_mask &= ~(ICR_TXDM | ICR_RXDM);         /* disable the interrupt source */
-       }
-
-       /* Unmask the EWRK3 board interrupts and turn off the LED */
-       cr &= ~(lp->led_mask);
-       outb(cr, EWRK3_CR);
-       ENABLE_IRQs;
-       spin_unlock(&lp->hw_lock);
-       return IRQ_HANDLED;
-}
-
-/* Called with lp->hw_lock held */
-static int ewrk3_rx(struct net_device *dev)
-{
-       struct ewrk3_private *lp = netdev_priv(dev);
-       u_long iobase = dev->base_addr;
-       int i, status = 0;
-       u_char page;
-       void __iomem *buf = NULL;
-
-       while (inb(EWRK3_RQC) && !status) {     /* Whilst there's incoming data */
-               if ((page = inb(EWRK3_RQ)) < lp->mPage) {       /* Get next entry's buffer page */
-                       /*
-                          ** Set up shared memory window and pointer into the window
-                        */
-                       if (lp->shmem_length == IO_ONLY) {
-                               outb(page, EWRK3_IOPR);
-                       } else if (lp->shmem_length == SHMEM_2K) {
-                               buf = lp->shmem;
-                               outb(page, EWRK3_MPR);
-                       } else if (lp->shmem_length == SHMEM_32K) {
-                               buf = (((short) page << 11) & 0x7800) + lp->shmem;
-                               outb((page >> 4), EWRK3_MPR);
-                       } else if (lp->shmem_length == SHMEM_64K) {
-                               buf = (((short) page << 11) & 0xf800) + lp->shmem;
-                               outb((page >> 5), EWRK3_MPR);
-                       } else {
-                               status = -1;
-                               printk("%s: Oops - your private data area is hosed!\n", dev->name);
-                       }
-
-                       if (!status) {
-                               char rx_status;
-                               int pkt_len;
-
-                               if (lp->shmem_length == IO_ONLY) {
-                                       rx_status = inb(EWRK3_DATA);
-                                       pkt_len = inb(EWRK3_DATA);
-                                       pkt_len |= ((u_short) inb(EWRK3_DATA) << 8);
-                               } else {
-                                       rx_status = readb(buf);
-                                       buf += 1;
-                                       pkt_len = readw(buf);
-                                       buf += 3;
-                               }
-
-                               if (!(rx_status & R_ROK)) {     /* There was an error. */
-                                       dev->stats.rx_errors++; /* Update the error stats. */
-                                       if (rx_status & R_DBE)
-                                               dev->stats.rx_frame_errors++;
-                                       if (rx_status & R_CRC)
-                                               dev->stats.rx_crc_errors++;
-                                       if (rx_status & R_PLL)
-                                               dev->stats.rx_fifo_errors++;
-                               } else {
-                                       struct sk_buff *skb;
-                                       skb = netdev_alloc_skb(dev,
-                                                       pkt_len + 2);
-
-                                       if (skb != NULL) {
-                                               unsigned char *p;
-                                               skb_reserve(skb, 2);    /* Align to 16 bytes */
-                                               p = skb_put(skb, pkt_len);
-
-                                               if (lp->shmem_length == IO_ONLY) {
-                                                       *p = inb(EWRK3_DATA);   /* dummy read */
-                                                       for (i = 0; i < pkt_len; i++) {
-                                                               *p++ = inb(EWRK3_DATA);
-                                                       }
-                                               } else {
-                                                       memcpy_fromio(p, buf, pkt_len);
-                                               }
-
-                                               for (i = 1; i < EWRK3_PKT_STAT_SZ - 1; i++) {
-                                                       if (pkt_len < i * EWRK3_PKT_BIN_SZ) {
-                                                               lp->pktStats.bins[i]++;
-                                                               i = EWRK3_PKT_STAT_SZ;
-                                                       }
-                                               }
-                                               p = skb->data;  /* Look at the dest addr */
-                                               if (is_multicast_ether_addr(p)) {
-                                                       if (is_broadcast_ether_addr(p)) {
-                                                               lp->pktStats.broadcast++;
-                                                       } else {
-                                                               lp->pktStats.multicast++;
-                                                       }
-                                               } else if (ether_addr_equal(p,
-                                                                           dev->dev_addr)) {
-                                                       lp->pktStats.unicast++;
-                                               }
-                                               lp->pktStats.bins[0]++;         /* Duplicates stats.rx_packets */
-                                               if (lp->pktStats.bins[0] == 0) {        /* Reset counters */
-                                                       memset(&lp->pktStats, 0, sizeof(lp->pktStats));
-                                               }
-                                               /*
-                                                  ** Notify the upper protocol layers that there is another
-                                                  ** packet to handle
-                                                */
-                                               skb->protocol = eth_type_trans(skb, dev);
-                                               netif_rx(skb);
-
-                                               /*
-                                                  ** Update stats
-                                                */
-                                               dev->stats.rx_packets++;
-                                               dev->stats.rx_bytes += pkt_len;
-                                       } else {
-                                               printk("%s: Insufficient memory; nuking packet.\n", dev->name);
-                                               dev->stats.rx_dropped++;                /* Really, deferred. */
-                                               break;
-                                       }
-                               }
-                       }
-                       /*
-                          ** Return the received buffer to the free memory queue
-                        */
-                       outb(page, EWRK3_FMQ);
-               } else {
-                       printk("ewrk3_rx(): Illegal page number, page %d\n", page);
-                       printk("ewrk3_rx(): CSR: %02x ICR: %02x FMQC: %02x\n", inb(EWRK3_CSR), inb(EWRK3_ICR), inb(EWRK3_FMQC));
-               }
-       }
-       return status;
-}
-
-/*
-** Buffer sent - check for TX buffer errors.
-** Called with lp->hw_lock held
-*/
-static int ewrk3_tx(struct net_device *dev)
-{
-       struct ewrk3_private *lp = netdev_priv(dev);
-       u_long iobase = dev->base_addr;
-       u_char tx_status;
-
-       while ((tx_status = inb(EWRK3_TDQ)) > 0) {      /* Whilst there's old buffers */
-               if (tx_status & T_VSTS) {       /* The status is valid */
-                       if (tx_status & T_TXE) {
-                               dev->stats.tx_errors++;
-                               if (tx_status & T_NCL)
-                                       dev->stats.tx_carrier_errors++;
-                               if (tx_status & T_LCL)
-                                       dev->stats.tx_window_errors++;
-                               if (tx_status & T_CTU) {
-                                       if ((tx_status & T_COLL) ^ T_XUR) {
-                                               lp->pktStats.tx_underruns++;
-                                       } else {
-                                               lp->pktStats.excessive_underruns++;
-                                       }
-                               } else if (tx_status & T_COLL) {
-                                       if ((tx_status & T_COLL) ^ T_XCOLL) {
-                                               dev->stats.collisions++;
-                                       } else {
-                                               lp->pktStats.excessive_collisions++;
-                                       }
-                               }
-                       } else {
-                               dev->stats.tx_packets++;
-                       }
-               }
-       }
-
-       return 0;
-}
-
-static int ewrk3_close(struct net_device *dev)
-{
-       struct ewrk3_private *lp = netdev_priv(dev);
-       u_long iobase = dev->base_addr;
-       u_char icr, csr;
-
-       netif_stop_queue(dev);
-
-       if (ewrk3_debug > 1) {
-               printk("%s: Shutting down ethercard, status was %2.2x.\n",
-                      dev->name, inb(EWRK3_CSR));
-       }
-       /*
-          ** We stop the EWRK3 here... mask interrupts and stop TX & RX
-        */
-       DISABLE_IRQs;
-
-       STOP_EWRK3;
-
-       /*
-          ** Clean out the TX and RX queues here (note that one entry
-          ** may get added to either the TXD or RX queues if the TX or RX
-          ** just starts processing a packet before the STOP_EWRK3 command
-          ** is received. This will be flushed in the ewrk3_open() call).
-        */
-       while (inb(EWRK3_TQ));
-       while (inb(EWRK3_TDQ));
-       while (inb(EWRK3_RQ));
-
-       if (!lp->hard_strapped) {
-               free_irq(dev->irq, dev);
-       }
-       return 0;
-}
-
-/*
-   ** Set or clear the multicast filter for this adapter.
- */
-static void set_multicast_list(struct net_device *dev)
-{
-       struct ewrk3_private *lp = netdev_priv(dev);
-       u_long iobase = dev->base_addr;
-       u_char csr;
-
-       csr = inb(EWRK3_CSR);
-
-       if (lp->shmem_length == IO_ONLY) {
-               lp->mctbl = NULL;
-       } else {
-               lp->mctbl = lp->shmem + PAGE0_HTE;
-       }
-
-       csr &= ~(CSR_PME | CSR_MCE);
-       if (dev->flags & IFF_PROMISC) {         /* set promiscuous mode */
-               csr |= CSR_PME;
-               outb(csr, EWRK3_CSR);
-       } else {
-               SetMulticastFilter(dev);
-               csr |= CSR_MCE;
-               outb(csr, EWRK3_CSR);
-       }
-}
-
-/*
-   ** Calculate the hash code and update the logical address filter
-   ** from a list of ethernet multicast addresses.
-   ** Little endian crc one liner from Matt Thomas, DEC.
-   **
-   ** Note that when clearing the table, the broadcast bit must remain asserted
-   ** to receive broadcast messages.
- */
-static void SetMulticastFilter(struct net_device *dev)
-{
-       struct ewrk3_private *lp = netdev_priv(dev);
-       struct netdev_hw_addr *ha;
-       u_long iobase = dev->base_addr;
-       int i;
-       char bit, byte;
-       short __iomem *p = lp->mctbl;
-       u16 hashcode;
-       u32 crc;
-
-       spin_lock_irq(&lp->hw_lock);
-
-       if (lp->shmem_length == IO_ONLY) {
-               outb(0, EWRK3_IOPR);
-               outw(PAGE0_HTE, EWRK3_PIR1);
-       } else {
-               outb(0, EWRK3_MPR);
-       }
-
-       if (dev->flags & IFF_ALLMULTI) {
-               for (i = 0; i < (HASH_TABLE_LEN >> 3); i++) {
-                       if (lp->shmem_length == IO_ONLY) {
-                               outb(0xff, EWRK3_DATA);
-                       } else {        /* memset didn't work here */
-                               writew(0xffff, p);
-                               p++;
-                               i++;
-                       }
-               }
-       } else {
-               /* Clear table except for broadcast bit */
-               if (lp->shmem_length == IO_ONLY) {
-                       for (i = 0; i < (HASH_TABLE_LEN >> 4) - 1; i++) {
-                               outb(0x00, EWRK3_DATA);
-                       }
-                       outb(0x80, EWRK3_DATA);
-                       i++;    /* insert the broadcast bit */
-                       for (; i < (HASH_TABLE_LEN >> 3); i++) {
-                               outb(0x00, EWRK3_DATA);
-                       }
-               } else {
-                       memset_io(lp->mctbl, 0, HASH_TABLE_LEN >> 3);
-                       writeb(0x80, lp->mctbl + (HASH_TABLE_LEN >> 4) - 1);
-               }
-
-               /* Update table */
-               netdev_for_each_mc_addr(ha, dev) {
-                       crc = ether_crc_le(ETH_ALEN, ha->addr);
-                       hashcode = crc & ((1 << 9) - 1);        /* hashcode is 9 LSb of CRC */
-
-                       byte = hashcode >> 3;   /* bit[3-8] -> byte in filter */
-                       bit = 1 << (hashcode & 0x07);   /* bit[0-2] -> bit in byte */
-
-                       if (lp->shmem_length == IO_ONLY) {
-                               u_char tmp;
-
-                               outw(PAGE0_HTE + byte, EWRK3_PIR1);
-                               tmp = inb(EWRK3_DATA);
-                               tmp |= bit;
-                               outw(PAGE0_HTE + byte, EWRK3_PIR1);
-                               outb(tmp, EWRK3_DATA);
-                       } else {
-                               writeb(readb(lp->mctbl + byte) | bit, lp->mctbl + byte);
-                       }
-               }
-       }
-
-       spin_unlock_irq(&lp->hw_lock);
-}
-
-/*
-   ** ISA bus I/O device probe
- */
-static int __init isa_probe(struct net_device *dev, u_long ioaddr)
-{
-       int i = num_ewrks3s, maxSlots;
-       int ret = -ENODEV;
-
-       u_long iobase;
-
-       if (ioaddr >= 0x400)
-               goto out;
-
-       if (ioaddr == 0) {      /* Autoprobing */
-               iobase = EWRK3_IO_BASE;         /* Get the first slot address */
-               maxSlots = 24;
-       } else {                /* Probe a specific location */
-               iobase = ioaddr;
-               maxSlots = i + 1;
-       }
-
-       for (; (i < maxSlots) && (dev != NULL);
-            iobase += EWRK3_IOP_INC, i++)
-       {
-               if (request_region(iobase, EWRK3_TOTAL_SIZE, DRV_NAME)) {
-                       if (DevicePresent(iobase) == 0) {
-                               int irq = dev->irq;
-                               ret = ewrk3_hw_init(dev, iobase);
-                               if (!ret)
-                                       break;
-                               dev->irq = irq;
-                       }
-                       release_region(iobase, EWRK3_TOTAL_SIZE);
-               }
-       }
- out:
-
-       return ret;
-}
-
-/*
-   ** EISA bus I/O device probe. Probe from slot 1 since slot 0 is usually
-   ** the motherboard.
- */
-static int __init eisa_probe(struct net_device *dev, u_long ioaddr)
-{
-       int i, maxSlots;
-       u_long iobase;
-       int ret = -ENODEV;
-
-       if (ioaddr < 0x1000)
-               goto out;
-
-       iobase = ioaddr;
-       i = (ioaddr >> 12);
-       maxSlots = i + 1;
-
-       for (i = 1; (i < maxSlots) && (dev != NULL); i++, iobase += EISA_SLOT_INC) {
-               if (EISA_signature(name, EISA_ID) == 0) {
-                       if (request_region(iobase, EWRK3_TOTAL_SIZE, DRV_NAME) &&
-                           DevicePresent(iobase) == 0) {
-                               int irq = dev->irq;
-                               ret = ewrk3_hw_init(dev, iobase);
-                               if (!ret)
-                                       break;
-                               dev->irq = irq;
-                       }
-                       release_region(iobase, EWRK3_TOTAL_SIZE);
-               }
-       }
-
- out:
-       return ret;
-}
-
-
-/*
-   ** Read the EWRK3 EEPROM using this routine
- */
-static int Read_EEPROM(u_long iobase, u_char eaddr)
-{
-       int i;
-
-       outb((eaddr & 0x3f), EWRK3_PIR1);       /* set up 6 bits of address info */
-       outb(EEPROM_RD, EWRK3_IOPR);    /* issue read command */
-       for (i = 0; i < 5000; i++)
-               inb(EWRK3_CSR); /* wait 1msec */
-
-       return inw(EWRK3_EPROM1);       /* 16 bits data return */
-}
-
-/*
-   ** Write the EWRK3 EEPROM using this routine
- */
-static int Write_EEPROM(short data, u_long iobase, u_char eaddr)
-{
-       int i;
-
-       outb(EEPROM_WR_EN, EWRK3_IOPR);         /* issue write enable command */
-       for (i = 0; i < 5000; i++)
-               inb(EWRK3_CSR); /* wait 1msec */
-       outw(data, EWRK3_EPROM1);       /* write data to register */
-       outb((eaddr & 0x3f), EWRK3_PIR1);       /* set up 6 bits of address info */
-       outb(EEPROM_WR, EWRK3_IOPR);    /* issue write command */
-       for (i = 0; i < 75000; i++)
-               inb(EWRK3_CSR); /* wait 15msec */
-       outb(EEPROM_WR_DIS, EWRK3_IOPR);        /* issue write disable command */
-       for (i = 0; i < 5000; i++)
-               inb(EWRK3_CSR); /* wait 1msec */
-
-       return 0;
-}
-
-/*
-   ** Look for a particular board name in the on-board EEPROM.
- */
-static void __init EthwrkSignature(char *name, char *eeprom_image)
-{
-       int i;
-       char *signatures[] = EWRK3_SIGNATURE;
-
-       for (i=0; *signatures[i] != '\0'; i++)
-               if( !strncmp(eeprom_image+EEPROM_PNAME7, signatures[i], strlen(signatures[i])) )
-                       break;
-
-       if (*signatures[i] != '\0') {
-               memcpy(name, eeprom_image+EEPROM_PNAME7, EWRK3_STRLEN);
-               name[EWRK3_STRLEN] = '\0';
-       } else
-               name[0] = '\0';
-}
-
-/*
-   ** Look for a special sequence in the Ethernet station address PROM that
-   ** is common across all EWRK3 products.
-   **
-   ** Search the Ethernet address ROM for the signature. Since the ROM address
-   ** counter can start at an arbitrary point, the search must include the entire
-   ** probe sequence length plus the (length_of_the_signature - 1).
-   ** Stop the search IMMEDIATELY after the signature is found so that the
-   ** PROM address counter is correctly positioned at the start of the
-   ** ethernet address for later read out.
- */
-
-static int __init DevicePresent(u_long iobase)
-{
-       union {
-               struct {
-                       u32 a;
-                       u32 b;
-               } llsig;
-               char Sig[sizeof(u32) << 1];
-       }
-       dev;
-       short sigLength;
-       char data;
-       int i, j, status = 0;
-
-       dev.llsig.a = ETH_PROM_SIG;
-       dev.llsig.b = ETH_PROM_SIG;
-       sigLength = sizeof(u32) << 1;
-
-       for (i = 0, j = 0; j < sigLength && i < PROBE_LENGTH + sigLength - 1; i++) {
-               data = inb(EWRK3_APROM);
-               if (dev.Sig[j] == data) {       /* track signature */
-                       j++;
-               } else {        /* lost signature; begin search again */
-                       if (data == dev.Sig[0]) {
-                               j = 1;
-                       } else {
-                               j = 0;
-                       }
-               }
-       }
-
-       if (j != sigLength) {
-               status = -ENODEV;       /* search failed */
-       }
-       return status;
-}
-
-static u_char __init get_hw_addr(struct net_device *dev, u_char * eeprom_image, char chipType)
-{
-       int i, j, k;
-       u_short chksum;
-       u_char crc, lfsr, sd, status = 0;
-       u_long iobase = dev->base_addr;
-       u16 tmp;
-
-       if (chipType == LeMAC2) {
-               for (crc = 0x6a, j = 0; j < ETH_ALEN; j++) {
-                       sd = dev->dev_addr[j] = eeprom_image[EEPROM_PADDR0 + j];
-                       outb(dev->dev_addr[j], EWRK3_PAR0 + j);
-                       for (k = 0; k < 8; k++, sd >>= 1) {
-                               lfsr = ((((crc & 0x02) >> 1) ^ (crc & 0x01)) ^ (sd & 0x01)) << 7;
-                               crc = (crc >> 1) + lfsr;
-                       }
-               }
-               if (crc != eeprom_image[EEPROM_PA_CRC])
-                       status = -1;
-       } else {
-               for (i = 0, k = 0; i < ETH_ALEN;) {
-                       k <<= 1;
-                       if (k > 0xffff)
-                               k -= 0xffff;
-
-                       k += (u_char) (tmp = inb(EWRK3_APROM));
-                       dev->dev_addr[i] = (u_char) tmp;
-                       outb(dev->dev_addr[i], EWRK3_PAR0 + i);
-                       i++;
-                       k += (u_short) ((tmp = inb(EWRK3_APROM)) << 8);
-                       dev->dev_addr[i] = (u_char) tmp;
-                       outb(dev->dev_addr[i], EWRK3_PAR0 + i);
-                       i++;
-
-                       if (k > 0xffff)
-                               k -= 0xffff;
-               }
-               if (k == 0xffff)
-                       k = 0;
-               chksum = inb(EWRK3_APROM);
-               chksum |= (inb(EWRK3_APROM) << 8);
-               if (k != chksum)
-                       status = -1;
-       }
-
-       return status;
-}
-
-/*
-   ** Look for a particular board name in the EISA configuration space
- */
-static int __init EISA_signature(char *name, s32 eisa_id)
-{
-       u_long i;
-       char *signatures[] = EWRK3_SIGNATURE;
-       char ManCode[EWRK3_STRLEN];
-       union {
-               s32 ID;
-               char Id[4];
-       } Eisa;
-       int status = 0;
-
-       *name = '\0';
-       for (i = 0; i < 4; i++) {
-               Eisa.Id[i] = inb(eisa_id + i);
-       }
-
-       ManCode[0] = (((Eisa.Id[0] >> 2) & 0x1f) + 0x40);
-       ManCode[1] = (((Eisa.Id[1] & 0xe0) >> 5) + ((Eisa.Id[0] & 0x03) << 3) + 0x40);
-       ManCode[2] = (((Eisa.Id[2] >> 4) & 0x0f) + 0x30);
-       ManCode[3] = ((Eisa.Id[2] & 0x0f) + 0x30);
-       ManCode[4] = (((Eisa.Id[3] >> 4) & 0x0f) + 0x30);
-       ManCode[5] = '\0';
-
-       for (i = 0; (*signatures[i] != '\0') && (*name == '\0'); i++) {
-               if (strstr(ManCode, signatures[i]) != NULL) {
-                       strcpy(name, ManCode);
-                       status = 1;
-               }
-       }
-
-       return status;          /* return the device name string */
-}
-
-static void ewrk3_get_drvinfo(struct net_device *dev, struct ethtool_drvinfo *info)
-{
-       int fwrev = Read_EEPROM(dev->base_addr, EEPROM_REVLVL);
-
-       strlcpy(info->driver, DRV_NAME, sizeof(info->driver));
-       strlcpy(info->version, DRV_VERSION, sizeof(info->version));
-       snprintf(info->fw_version, sizeof(info->fw_version), "%d", fwrev);
-       strlcpy(info->bus_info, "N/A", sizeof(info->bus_info));
-       info->eedump_len = EEPROM_MAX;
-}
-
-static int ewrk3_get_settings(struct net_device *dev, struct ethtool_cmd *ecmd)
-{
-       struct ewrk3_private *lp = netdev_priv(dev);
-       unsigned long iobase = dev->base_addr;
-       u8 cr = inb(EWRK3_CR);
-
-       switch (lp->adapter_name[4]) {
-       case '3': /* DE203 */
-               ecmd->supported = SUPPORTED_BNC;
-               ecmd->port = PORT_BNC;
-               break;
-
-       case '4': /* DE204 */
-               ecmd->supported = SUPPORTED_TP;
-               ecmd->port = PORT_TP;
-               break;
-
-       case '5': /* DE205 */
-               ecmd->supported = SUPPORTED_TP | SUPPORTED_BNC | SUPPORTED_AUI;
-               ecmd->autoneg = !(cr & CR_APD);
-               /*
-               ** Port is only valid if autoneg is disabled
-               ** and even then we don't know if AUI is jumpered.
-               */
-               if (!ecmd->autoneg)
-                       ecmd->port = (cr & CR_PSEL) ? PORT_BNC : PORT_TP;
-               break;
-       }
-
-       ecmd->supported |= SUPPORTED_10baseT_Half;
-       ethtool_cmd_speed_set(ecmd, SPEED_10);
-       ecmd->duplex = DUPLEX_HALF;
-       return 0;
-}
-
-static int ewrk3_set_settings(struct net_device *dev, struct ethtool_cmd *ecmd)
-{
-       struct ewrk3_private *lp = netdev_priv(dev);
-       unsigned long iobase = dev->base_addr;
-       unsigned long flags;
-       u8 cr;
-
-       /* DE205 is the only card with anything to set */
-       if (lp->adapter_name[4] != '5')
-               return -EOPNOTSUPP;
-
-       /* Sanity-check parameters */
-       if (ecmd->speed != SPEED_10)
-               return -EINVAL;
-       if (ecmd->port != PORT_TP && ecmd->port != PORT_BNC)
-               return -EINVAL; /* AUI is not software-selectable */
-       if (ecmd->transceiver != XCVR_INTERNAL)
-               return -EINVAL;
-       if (ecmd->duplex != DUPLEX_HALF)
-               return -EINVAL;
-       if (ecmd->phy_address != 0)
-               return -EINVAL;
-
-       spin_lock_irqsave(&lp->hw_lock, flags);
-       cr = inb(EWRK3_CR);
-
-       /* If Autoneg is set, change to Auto Port mode */
-       /* Otherwise, disable Auto Port and set port explicitly */
-       if (ecmd->autoneg) {
-               cr &= ~CR_APD;
-       } else {
-               cr |= CR_APD;
-               if (ecmd->port == PORT_TP)
-                       cr &= ~CR_PSEL;         /* Force TP */
-               else
-                       cr |= CR_PSEL;          /* Force BNC */
-       }
-
-       /* Commit the changes */
-       outb(cr, EWRK3_CR);
-       spin_unlock_irqrestore(&lp->hw_lock, flags);
-       return 0;
-}
-
-static u32 ewrk3_get_link(struct net_device *dev)
-{
-       unsigned long iobase = dev->base_addr;
-       u8 cmr = inb(EWRK3_CMR);
-       /* DE203 has BNC only and link status does not apply */
-       /* On DE204 this is always valid since TP is the only port. */
-       /* On DE205 this reflects TP status even if BNC or AUI is selected. */
-       return !(cmr & CMR_LINK);
-}
-
-static int ewrk3_set_phys_id(struct net_device *dev,
-                            enum ethtool_phys_id_state state)
-{
-       struct ewrk3_private *lp = netdev_priv(dev);
-       unsigned long iobase = dev->base_addr;
-       u8 cr;
-
-       spin_lock_irq(&lp->hw_lock);
-
-       switch (state) {
-       case ETHTOOL_ID_ACTIVE:
-               /* Prevent ISR from twiddling the LED */
-               lp->led_mask = 0;
-               spin_unlock_irq(&lp->hw_lock);
-               return 2;       /* cycle on/off twice per second */
-
-       case ETHTOOL_ID_ON:
-               cr = inb(EWRK3_CR);
-               outb(cr | CR_LED, EWRK3_CR);
-               break;
-
-       case ETHTOOL_ID_OFF:
-               cr = inb(EWRK3_CR);
-               outb(cr & ~CR_LED, EWRK3_CR);
-               break;
-
-       case ETHTOOL_ID_INACTIVE:
-               lp->led_mask = CR_LED;
-               cr = inb(EWRK3_CR);
-               outb(cr & ~CR_LED, EWRK3_CR);
-       }
-       spin_unlock_irq(&lp->hw_lock);
-
-       return 0;
-}
-
-static const struct ethtool_ops ethtool_ops_203 = {
-       .get_drvinfo = ewrk3_get_drvinfo,
-       .get_settings = ewrk3_get_settings,
-       .set_settings = ewrk3_set_settings,
-       .set_phys_id = ewrk3_set_phys_id,
-};
-
-static const struct ethtool_ops ethtool_ops = {
-       .get_drvinfo = ewrk3_get_drvinfo,
-       .get_settings = ewrk3_get_settings,
-       .set_settings = ewrk3_set_settings,
-       .get_link = ewrk3_get_link,
-       .set_phys_id = ewrk3_set_phys_id,
-};
-
-/*
-   ** Perform IOCTL call functions here. Some are privileged operations and the
-   ** effective uid is checked in those cases.
- */
-static int ewrk3_ioctl(struct net_device *dev, struct ifreq *rq, int cmd)
-{
-       struct ewrk3_private *lp = netdev_priv(dev);
-       struct ewrk3_ioctl *ioc = (struct ewrk3_ioctl *) &rq->ifr_ifru;
-       u_long iobase = dev->base_addr;
-       int i, j, status = 0;
-       u_char csr;
-       unsigned long flags;
-       union ewrk3_addr {
-               u_char addr[HASH_TABLE_LEN * ETH_ALEN];
-               u_short val[(HASH_TABLE_LEN * ETH_ALEN) >> 1];
-       };
-
-       union ewrk3_addr *tmp;
-
-       /* All we handle are private IOCTLs */
-       if (cmd != EWRK3IOCTL)
-               return -EOPNOTSUPP;
-
-       tmp = kmalloc(sizeof(union ewrk3_addr), GFP_KERNEL);
-       if(tmp==NULL)
-               return -ENOMEM;
-
-       switch (ioc->cmd) {
-       case EWRK3_GET_HWADDR:  /* Get the hardware address */
-               for (i = 0; i < ETH_ALEN; i++) {
-                       tmp->addr[i] = dev->dev_addr[i];
-               }
-               ioc->len = ETH_ALEN;
-               if (copy_to_user(ioc->data, tmp->addr, ioc->len))
-                       status = -EFAULT;
-               break;
-
-       case EWRK3_SET_HWADDR:  /* Set the hardware address */
-               if (capable(CAP_NET_ADMIN)) {
-                       spin_lock_irqsave(&lp->hw_lock, flags);
-                       csr = inb(EWRK3_CSR);
-                       csr |= (CSR_TXD | CSR_RXD);
-                       outb(csr, EWRK3_CSR);   /* Disable the TX and RX */
-                       spin_unlock_irqrestore(&lp->hw_lock, flags);
-
-                       if (copy_from_user(tmp->addr, ioc->data, ETH_ALEN)) {
-                               status = -EFAULT;
-                               break;
-                       }
-                       spin_lock_irqsave(&lp->hw_lock, flags);
-                       for (i = 0; i < ETH_ALEN; i++) {
-                               dev->dev_addr[i] = tmp->addr[i];
-                               outb(tmp->addr[i], EWRK3_PAR0 + i);
-                       }
-
-                       csr = inb(EWRK3_CSR);
-                       csr &= ~(CSR_TXD | CSR_RXD);    /* Enable the TX and RX */
-                       outb(csr, EWRK3_CSR);
-                       spin_unlock_irqrestore(&lp->hw_lock, flags);
-               } else {
-                       status = -EPERM;
-               }
-
-               break;
-       case EWRK3_SET_PROM:    /* Set Promiscuous Mode */
-               if (capable(CAP_NET_ADMIN)) {
-                       spin_lock_irqsave(&lp->hw_lock, flags);
-                       csr = inb(EWRK3_CSR);
-                       csr |= CSR_PME;
-                       csr &= ~CSR_MCE;
-                       outb(csr, EWRK3_CSR);
-                       spin_unlock_irqrestore(&lp->hw_lock, flags);
-               } else {
-                       status = -EPERM;
-               }
-
-               break;
-       case EWRK3_CLR_PROM:    /* Clear Promiscuous Mode */
-               if (capable(CAP_NET_ADMIN)) {
-                       spin_lock_irqsave(&lp->hw_lock, flags);
-                       csr = inb(EWRK3_CSR);
-                       csr &= ~CSR_PME;
-                       outb(csr, EWRK3_CSR);
-                       spin_unlock_irqrestore(&lp->hw_lock, flags);
-               } else {
-                       status = -EPERM;
-               }
-
-               break;
-       case EWRK3_GET_MCA:     /* Get the multicast address table */
-               spin_lock_irqsave(&lp->hw_lock, flags);
-               if (lp->shmem_length == IO_ONLY) {
-                       outb(0, EWRK3_IOPR);
-                       outw(PAGE0_HTE, EWRK3_PIR1);
-                       for (i = 0; i < (HASH_TABLE_LEN >> 3); i++) {
-                               tmp->addr[i] = inb(EWRK3_DATA);
-                       }
-               } else {
-                       outb(0, EWRK3_MPR);
-                       memcpy_fromio(tmp->addr, lp->shmem + PAGE0_HTE, (HASH_TABLE_LEN >> 3));
-               }
-               spin_unlock_irqrestore(&lp->hw_lock, flags);
-
-               ioc->len = (HASH_TABLE_LEN >> 3);
-               if (copy_to_user(ioc->data, tmp->addr, ioc->len))
-                       status = -EFAULT;
-
-               break;
-       case EWRK3_SET_MCA:     /* Set a multicast address */
-               if (capable(CAP_NET_ADMIN)) {
-                       if (ioc->len > HASH_TABLE_LEN) {
-                               status = -EINVAL;
-                               break;
-                       }
-                       if (copy_from_user(tmp->addr, ioc->data, ETH_ALEN * ioc->len)) {
-                               status = -EFAULT;
-                               break;
-                       }
-                       set_multicast_list(dev);
-               } else {
-                       status = -EPERM;
-               }
-
-               break;
-       case EWRK3_CLR_MCA:     /* Clear all multicast addresses */
-               if (capable(CAP_NET_ADMIN)) {
-                       set_multicast_list(dev);
-               } else {
-                       status = -EPERM;
-               }
-
-               break;
-       case EWRK3_MCA_EN:      /* Enable multicast addressing */
-               if (capable(CAP_NET_ADMIN)) {
-                       spin_lock_irqsave(&lp->hw_lock, flags);
-                       csr = inb(EWRK3_CSR);
-                       csr |= CSR_MCE;
-                       csr &= ~CSR_PME;
-                       outb(csr, EWRK3_CSR);
-                       spin_unlock_irqrestore(&lp->hw_lock, flags);
-               } else {
-                       status = -EPERM;
-               }
-
-               break;
-       case EWRK3_GET_STATS: { /* Get the driver statistics */
-               struct ewrk3_stats *tmp_stats =
-                       kmalloc(sizeof(lp->pktStats), GFP_KERNEL);
-               if (!tmp_stats) {
-                       status = -ENOMEM;
-                       break;
-               }
-
-               spin_lock_irqsave(&lp->hw_lock, flags);
-               memcpy(tmp_stats, &lp->pktStats, sizeof(lp->pktStats));
-               spin_unlock_irqrestore(&lp->hw_lock, flags);
-
-               ioc->len = sizeof(lp->pktStats);
-               if (copy_to_user(ioc->data, tmp_stats, sizeof(lp->pktStats)))
-                       status = -EFAULT;
-               kfree(tmp_stats);
-               break;
-       }
-       case EWRK3_CLR_STATS:   /* Zero out the driver statistics */
-               if (capable(CAP_NET_ADMIN)) {
-                       spin_lock_irqsave(&lp->hw_lock, flags);
-                       memset(&lp->pktStats, 0, sizeof(lp->pktStats));
-                       spin_unlock_irqrestore(&lp->hw_lock,flags);
-               } else {
-                       status = -EPERM;
-               }
-
-               break;
-       case EWRK3_GET_CSR:     /* Get the CSR Register contents */
-               tmp->addr[0] = inb(EWRK3_CSR);
-               ioc->len = 1;
-               if (copy_to_user(ioc->data, tmp->addr, ioc->len))
-                       status = -EFAULT;
-               break;
-       case EWRK3_SET_CSR:     /* Set the CSR Register contents */
-               if (capable(CAP_NET_ADMIN)) {
-                       if (copy_from_user(tmp->addr, ioc->data, 1)) {
-                               status = -EFAULT;
-                               break;
-                       }
-                       outb(tmp->addr[0], EWRK3_CSR);
-               } else {
-                       status = -EPERM;
-               }
-
-               break;
-       case EWRK3_GET_EEPROM:  /* Get the EEPROM contents */
-               if (capable(CAP_NET_ADMIN)) {
-                       for (i = 0; i < (EEPROM_MAX >> 1); i++) {
-                               tmp->val[i] = (short) Read_EEPROM(iobase, i);
-                       }
-                       i = EEPROM_MAX;
-                       tmp->addr[i++] = inb(EWRK3_CMR);                /* Config/Management Reg. */
-                       for (j = 0; j < ETH_ALEN; j++) {
-                               tmp->addr[i++] = inb(EWRK3_PAR0 + j);
-                       }
-                       ioc->len = EEPROM_MAX + 1 + ETH_ALEN;
-                       if (copy_to_user(ioc->data, tmp->addr, ioc->len))
-                               status = -EFAULT;
-               } else {
-                       status = -EPERM;
-               }
-
-               break;
-       case EWRK3_SET_EEPROM:  /* Set the EEPROM contents */
-               if (capable(CAP_NET_ADMIN)) {
-                       if (copy_from_user(tmp->addr, ioc->data, EEPROM_MAX)) {
-                               status = -EFAULT;
-                               break;
-                       }
-                       for (i = 0; i < (EEPROM_MAX >> 1); i++) {
-                               Write_EEPROM(tmp->val[i], iobase, i);
-                       }
-               } else {
-                       status = -EPERM;
-               }
-
-               break;
-       case EWRK3_GET_CMR:     /* Get the CMR Register contents */
-               tmp->addr[0] = inb(EWRK3_CMR);
-               ioc->len = 1;
-               if (copy_to_user(ioc->data, tmp->addr, ioc->len))
-                       status = -EFAULT;
-               break;
-       case EWRK3_SET_TX_CUT_THRU:     /* Set TX cut through mode */
-               if (capable(CAP_NET_ADMIN)) {
-                       lp->txc = 1;
-               } else {
-                       status = -EPERM;
-               }
-
-               break;
-       case EWRK3_CLR_TX_CUT_THRU:     /* Clear TX cut through mode */
-               if (capable(CAP_NET_ADMIN)) {
-                       lp->txc = 0;
-               } else {
-                       status = -EPERM;
-               }
-
-               break;
-       default:
-               status = -EOPNOTSUPP;
-       }
-       kfree(tmp);
-       return status;
-}
-
-#ifdef MODULE
-static struct net_device *ewrk3_devs[MAX_NUM_EWRK3S];
-static int ndevs;
-static int io[MAX_NUM_EWRK3S+1] = { 0x300, 0, };
-
-module_param_array(io, int, NULL, 0);
-module_param_array(irq, byte, NULL, 0);
-MODULE_PARM_DESC(io, "EtherWORKS 3 I/O base address(es)");
-MODULE_PARM_DESC(irq, "EtherWORKS 3 IRQ number(s)");
-
-static __exit void ewrk3_exit_module(void)
-{
-       int i;
-
-       for( i=0; i<ndevs; i++ ) {
-               struct net_device *dev = ewrk3_devs[i];
-               struct ewrk3_private *lp = netdev_priv(dev);
-               ewrk3_devs[i] = NULL;
-               unregister_netdev(dev);
-               release_region(dev->base_addr, EWRK3_TOTAL_SIZE);
-               iounmap(lp->shmem);
-               free_netdev(dev);
-       }
-}
-
-static __init int ewrk3_init_module(void)
-{
-       int i=0;
-
-       while( io[i] && irq[i] ) {
-               struct net_device *dev
-                       = alloc_etherdev(sizeof(struct ewrk3_private));
-
-               if (!dev)
-                       break;
-
-               if (ewrk3_probe1(dev, io[i], irq[i]) != 0) {
-                       free_netdev(dev);
-                       break;
-               }
-
-               ewrk3_devs[ndevs++] = dev;
-               i++;
-       }
-
-       return ndevs ? 0 : -EIO;
-}
-
-
-/* Hack for breakage in new module stuff */
-module_exit(ewrk3_exit_module);
-module_init(ewrk3_init_module);
-#endif                         /* MODULE */
-MODULE_LICENSE("GPL");
 
+++ /dev/null
-/*
-    Written 1994 by David C. Davies.
-
-    Copyright 1994 Digital Equipment Corporation.
-
-    This software may be used and distributed according to  the terms of the
-    GNU General Public License, incorporated herein by reference.
-
-    The author may    be  reached as davies@wanton.lkg.dec.com  or   Digital
-    Equipment Corporation, 550 King Street, Littleton MA 01460.
-
-    =========================================================================
-*/
-
-/*
-** I/O Address Register Map
-*/
-#define EWRK3_CSR    iobase+0x00   /* Control and Status Register */
-#define EWRK3_CR     iobase+0x01   /* Control Register */
-#define EWRK3_ICR    iobase+0x02   /* Interrupt Control Register */
-#define EWRK3_TSR    iobase+0x03   /* Transmit Status Register */
-#define EWRK3_RSVD1  iobase+0x04   /* RESERVED */
-#define EWRK3_RSVD2  iobase+0x05   /* RESERVED */
-#define EWRK3_FMQ    iobase+0x06   /* Free Memory Queue */
-#define EWRK3_FMQC   iobase+0x07   /* Free Memory Queue Counter */
-#define EWRK3_RQ     iobase+0x08   /* Receive Queue */
-#define EWRK3_RQC    iobase+0x09   /* Receive Queue Counter */
-#define EWRK3_TQ     iobase+0x0a   /* Transmit Queue */
-#define EWRK3_TQC    iobase+0x0b   /* Transmit Queue Counter */
-#define EWRK3_TDQ    iobase+0x0c   /* Transmit Done Queue */
-#define EWRK3_TDQC   iobase+0x0d   /* Transmit Done Queue Counter */
-#define EWRK3_PIR1   iobase+0x0e   /* Page Index Register 1 */
-#define EWRK3_PIR2   iobase+0x0f   /* Page Index Register 2 */
-#define EWRK3_DATA   iobase+0x10   /* Data Register */
-#define EWRK3_IOPR   iobase+0x11   /* I/O Page Register */
-#define EWRK3_IOBR   iobase+0x12   /* I/O Base Register */
-#define EWRK3_MPR    iobase+0x13   /* Memory Page Register */
-#define EWRK3_MBR    iobase+0x14   /* Memory Base Register */
-#define EWRK3_APROM  iobase+0x15   /* Address PROM */
-#define EWRK3_EPROM1 iobase+0x16   /* EEPROM Data Register 1 */
-#define EWRK3_EPROM2 iobase+0x17   /* EEPROM Data Register 2 */
-#define EWRK3_PAR0   iobase+0x18   /* Physical Address Register 0 */
-#define EWRK3_PAR1   iobase+0x19   /* Physical Address Register 1 */
-#define EWRK3_PAR2   iobase+0x1a   /* Physical Address Register 2 */
-#define EWRK3_PAR3   iobase+0x1b   /* Physical Address Register 3 */
-#define EWRK3_PAR4   iobase+0x1c   /* Physical Address Register 4 */
-#define EWRK3_PAR5   iobase+0x1d   /* Physical Address Register 5 */
-#define EWRK3_CMR    iobase+0x1e   /* Configuration/Management Register */
-
-/*
-** Control Page Map
-*/
-#define PAGE0_FMQ     0x000         /* Free Memory Queue */
-#define PAGE0_RQ      0x080         /* Receive Queue */
-#define PAGE0_TQ      0x100         /* Transmit Queue */
-#define PAGE0_TDQ     0x180         /* Transmit Done Queue */
-#define PAGE0_HTE     0x200         /* Hash Table Entries */
-#define PAGE0_RSVD    0x240         /* RESERVED */
-#define PAGE0_USRD    0x600         /* User Data */
-
-/*
-** Control and Status Register bit definitions (EWRK3_CSR)
-*/
-#define CSR_RA         0x80        /* Runt Accept */
-#define CSR_PME                0x40        /* Promiscuous Mode Enable */
-#define CSR_MCE                0x20        /* Multicast Enable */
-#define CSR_TNE                0x08        /* TX Done Queue Not Empty */
-#define CSR_RNE                0x04        /* RX Queue Not Empty */
-#define CSR_TXD                0x02        /* TX Disable */
-#define CSR_RXD                0x01        /* RX Disable */
-
-/*
-** Control Register bit definitions (EWRK3_CR)
-*/
-#define CR_APD         0x80    /* Auto Port Disable */
-#define CR_PSEL                0x40    /* Port Select (0->TP port) */
-#define CR_LBCK                0x20    /* LoopBaCK enable */
-#define CR_FDUP                0x10    /* Full DUPlex enable */
-#define CR_FBUS                0x08    /* Fast BUS enable (ISA clk > 8.33MHz) */
-#define CR_EN_16       0x04    /* ENable 16 bit memory accesses */
-#define CR_LED         0x02    /* LED (1-> turn on) */
-
-/*
-** Interrupt Control Register bit definitions (EWRK3_ICR)
-*/
-#define ICR_IE         0x80    /* Interrupt Enable */
-#define ICR_IS         0x60    /* Interrupt Selected */
-#define ICR_TNEM       0x08    /* TNE Mask (0->mask) */
-#define ICR_RNEM       0x04    /* RNE Mask (0->mask) */
-#define ICR_TXDM       0x02    /* TXD Mask (0->mask) */
-#define ICR_RXDM       0x01    /* RXD Mask (0->mask) */
-
-/*
-** Transmit Status Register bit definitions (EWRK3_TSR)
-*/
-#define TSR_NCL                0x80    /* No Carrier Loopback */
-#define TSR_ID         0x40    /* Initially Deferred */
-#define TSR_LCL                0x20    /* Late CoLlision */
-#define TSR_ECL                0x10    /* Excessive CoLlisions */
-#define TSR_RCNTR      0x0f    /* Retries CouNTeR */
-
-/*
-** I/O Page Register bit definitions (EWRK3_IOPR)
-*/
-#define EEPROM_INIT    0xc0    /* EEPROM INIT command */
-#define EEPROM_WR_EN   0xc8    /* EEPROM WRITE ENABLE command */
-#define EEPROM_WR      0xd0    /* EEPROM WRITE command */
-#define EEPROM_WR_DIS  0xd8    /* EEPROM WRITE DISABLE command */
-#define EEPROM_RD      0xe0    /* EEPROM READ command */
-
-/*
-** I/O Base Register bit definitions (EWRK3_IOBR)
-*/
-#define EISA_REGS_EN   0x20    /* Enable EISA ID and Control Registers */
-#define EISA_IOB        0x1f   /* Compare bits for I/O Base Address */
-
-/*
-** I/O Configuration/Management Register bit definitions (EWRK3_CMR)
-*/
-#define CMR_RA          0x80    /* Read Ahead */
-#define CMR_WB          0x40    /* Write Behind */
-#define CMR_LINK        0x20   /* 0->TP */
-#define CMR_POLARITY    0x10   /* Informational */
-#define CMR_NO_EEPROM  0x0c    /* NO_EEPROM<1:0> pin status */
-#define CMR_HS          0x08   /* Hard Strapped pin status (LeMAC2) */
-#define CMR_PNP         0x04    /* Plug 'n Play */
-#define CMR_DRAM        0x02   /* 0-> 1DRAM, 1-> 2 DRAM on board */
-#define CMR_0WS         0x01    /* Zero Wait State */
-
-/*
-** MAC Receive Status Register bit definitions
-*/
-
-#define R_ROK          0x80    /* Receive OK summary */
-#define R_IAM          0x10    /* Individual Address Match */
-#define R_MCM          0x08    /* MultiCast Match */
-#define R_DBE          0x04    /* Dribble Bit Error */
-#define R_CRC          0x02    /* CRC error */
-#define R_PLL          0x01    /* Phase Lock Lost */
-
-/*
-** MAC Transmit Control Register bit definitions
-*/
-
-#define TCR_SQEE       0x40    /* SQE Enable - look for heartbeat  */
-#define TCR_SED        0x20    /* Stop when Error Detected */
-#define TCR_QMODE      0x10    /* Q_MODE */
-#define TCR_LAB         0x08   /* Less Aggressive Backoff */
-#define TCR_PAD        0x04    /* PAD Runt Packets */
-#define TCR_IFC        0x02    /* Insert Frame Check */
-#define TCR_ISA        0x01    /* Insert Source Address */
-
-/*
-** MAC Transmit Status Register bit definitions
-*/
-
-#define T_VSTS         0x80    /* Valid STatuS */
-#define T_CTU          0x40    /* Cut Through Used */
-#define T_SQE          0x20    /* Signal Quality Error */
-#define T_NCL          0x10    /* No Carrier Loopback */
-#define T_LCL           0x08   /* Late Collision */
-#define T_ID           0x04    /* Initially Deferred */
-#define T_COLL         0x03    /* COLLision status */
-#define T_XCOLL         0x03    /* Excessive Collisions */
-#define T_MCOLL         0x02    /* Multiple Collisions */
-#define T_OCOLL         0x01    /* One Collision */
-#define T_NOCOLL        0x00    /* No Collisions */
-#define T_XUR           0x03    /* Excessive Underruns */
-#define T_TXE           0x7f    /* TX Errors */
-
-/*
-** EISA Configuration Register bit definitions
-*/
-
-#define EISA_ID       iobase + 0x0c80  /* EISA ID Registers */
-#define EISA_ID0      iobase + 0x0c80  /* EISA ID Register 0 */
-#define EISA_ID1      iobase + 0x0c81  /* EISA ID Register 1 */
-#define EISA_ID2      iobase + 0x0c82  /* EISA ID Register 2 */
-#define EISA_ID3      iobase + 0x0c83  /* EISA ID Register 3 */
-#define EISA_CR       iobase + 0x0c84  /* EISA Control Register */
-
-/*
-** EEPROM BYTES
-*/
-#define EEPROM_MEMB     0x00
-#define EEPROM_IOB      0x01
-#define EEPROM_EISA_ID0 0x02
-#define EEPROM_EISA_ID1 0x03
-#define EEPROM_EISA_ID2 0x04
-#define EEPROM_EISA_ID3 0x05
-#define EEPROM_MISC0    0x06
-#define EEPROM_MISC1    0x07
-#define EEPROM_PNAME7   0x08
-#define EEPROM_PNAME6   0x09
-#define EEPROM_PNAME5   0x0a
-#define EEPROM_PNAME4   0x0b
-#define EEPROM_PNAME3   0x0c
-#define EEPROM_PNAME2   0x0d
-#define EEPROM_PNAME1   0x0e
-#define EEPROM_PNAME0   0x0f
-#define EEPROM_SWFLAGS  0x10
-#define EEPROM_HWCAT    0x11
-#define EEPROM_NETMAN2  0x12
-#define EEPROM_REVLVL   0x13
-#define EEPROM_NETMAN0  0x14
-#define EEPROM_NETMAN1  0x15
-#define EEPROM_CHIPVER  0x16
-#define EEPROM_SETUP    0x17
-#define EEPROM_PADDR0   0x18
-#define EEPROM_PADDR1   0x19
-#define EEPROM_PADDR2   0x1a
-#define EEPROM_PADDR3   0x1b
-#define EEPROM_PADDR4   0x1c
-#define EEPROM_PADDR5   0x1d
-#define EEPROM_PA_CRC   0x1e
-#define EEPROM_CHKSUM   0x1f
-
-/*
-** EEPROM bytes for checksumming
-*/
-#define EEPROM_MAX      32             /* bytes */
-
-/*
-** EEPROM MISCELLANEOUS FLAGS
-*/
-#define RBE_SHADOW     0x0100  /* Remote Boot Enable Shadow */
-#define READ_AHEAD      0x0080  /* Read Ahead feature */
-#define IRQ_SEL2        0x0070  /* IRQ line selection (LeMAC2) */
-#define IRQ_SEL         0x0060  /* IRQ line selection */
-#define FAST_BUS        0x0008  /* ISA Bus speeds > 8.33MHz */
-#define ENA_16          0x0004  /* Enables 16 bit memory transfers */
-#define WRITE_BEHIND    0x0002  /* Write Behind feature */
-#define _0WS_ENA        0x0001  /* Zero Wait State Enable */
-
-/*
-** EEPROM NETWORK MANAGEMENT FLAGS
-*/
-#define NETMAN_POL      0x04    /* Polarity defeat */
-#define NETMAN_LINK     0x02    /* Link defeat */
-#define NETMAN_CCE      0x01    /* Custom Counters Enable */
-
-/*
-** EEPROM SW FLAGS
-*/
-#define SW_SQE         0x10    /* Signal Quality Error */
-#define SW_LAB         0x08    /* Less Aggressive Backoff */
-#define SW_INIT                0x04    /* Initialized */
-#define SW_TIMEOUT             0x02    /* 0:2.5 mins, 1: 30 secs */
-#define SW_REMOTE              0x01    /* Remote Boot Enable -> 1 */
-
-/*
-** EEPROM SETUP FLAGS
-*/
-#define SETUP_APD      0x80    /* AutoPort Disable */
-#define SETUP_PS       0x40    /* Port Select */
-#define SETUP_MP       0x20    /* MultiPort */
-#define SETUP_1TP      0x10    /* 1 port, TP */
-#define SETUP_1COAX    0x00    /* 1 port, Coax */
-#define SETUP_DRAM     0x02    /* Number of DRAMS on board */
-
-/*
-** EEPROM MANAGEMENT FLAGS
-*/
-#define MGMT_CCE       0x01    /* Custom Counters Enable */
-
-/*
-** EEPROM VERSIONS
-*/
-#define LeMAC           0x11
-#define LeMAC2          0x12
-
-/*
-** Miscellaneous
-*/
-
-#define EEPROM_WAIT_TIME 1000    /* Number of microseconds */
-#define EISA_EN         0x0001   /* Enable EISA bus buffers */
-
-#define HASH_TABLE_LEN   512     /* Bits */
-
-#define XCT 0x80                 /* Transmit Cut Through */
-#define PRELOAD 16               /* 4 long words */
-
-#define MASK_INTERRUPTS   1
-#define UNMASK_INTERRUPTS 0
-
-#define EEPROM_OFFSET(a) ((u_short)((u_long)(a)))
-
-/*
-** Include the IOCTL stuff
-*/
-#include <linux/sockios.h>
-
-#define        EWRK3IOCTL      SIOCDEVPRIVATE
-
-struct ewrk3_ioctl {
-       unsigned short cmd;                /* Command to run */
-       unsigned short len;                /* Length of the data buffer */
-       unsigned char  __user *data;       /* Pointer to the data buffer */
-};
-
-/*
-** Recognised commands for the driver
-*/
-#define EWRK3_GET_HWADDR       0x01 /* Get the hardware address */
-#define EWRK3_SET_HWADDR       0x02 /* Get the hardware address */
-#define EWRK3_SET_PROM         0x03 /* Set Promiscuous Mode */
-#define EWRK3_CLR_PROM         0x04 /* Clear Promiscuous Mode */
-#define EWRK3_SAY_BOO          0x05 /* Say "Boo!" to the kernel log file */
-#define EWRK3_GET_MCA          0x06 /* Get a multicast address */
-#define EWRK3_SET_MCA          0x07 /* Set a multicast address */
-#define EWRK3_CLR_MCA          0x08 /* Clear a multicast address */
-#define EWRK3_MCA_EN           0x09 /* Enable a multicast address group */
-#define EWRK3_GET_STATS        0x0a /* Get the driver statistics */
-#define EWRK3_CLR_STATS        0x0b /* Zero out the driver statistics */
-#define EWRK3_GET_CSR          0x0c /* Get the CSR Register contents */
-#define EWRK3_SET_CSR          0x0d /* Set the CSR Register contents */
-#define EWRK3_GET_EEPROM       0x0e /* Get the EEPROM contents */
-#define EWRK3_SET_EEPROM       0x0f /* Set the EEPROM contents */
-#define EWRK3_GET_CMR          0x10 /* Get the CMR Register contents */
-#define EWRK3_CLR_TX_CUT_THRU          0x11 /* Clear the TX cut through mode */
-#define EWRK3_SET_TX_CUT_THRU  0x12 /* Set the TX cut through mode */