/*
* net-3-driver for the NI5210 card (i82586 Ethernet chip)
*
* This is an extension to the Linux operating system, and is covered by the
* same GNU General Public License that covers that work.
*
* Alphacode 0.82 (96/09/29) for Linux 2.0.0 (or later)
* Copyrights (c) 1994,1995,1996 by M.Hipp (hippm@informatik.uni-tuebingen.de)
* [feel free to mail ....]
*
* when using as module: (no autoprobing!)
* compile with:
* gcc -O2 -fomit-frame-pointer -m486 -D__KERNEL__ -DMODULE -c ni52.c
* run with e.g:
* insmod ni52.o io=0x360 irq=9 memstart=0xd0000 memend=0xd4000
*
* CAN YOU PLEASE REPORT ME YOUR PERFORMANCE EXPERIENCES !!.
*
* If you find a bug, please report me:
* The kernel panic output and any kmsg from the ni52 driver
* the ni5210-driver-version and the linux-kernel version
* how many shared memory (memsize) on the netcard,
* bootprom: yes/no, base_addr, mem_start
* maybe the ni5210-card revision and the i82586 version
*
* autoprobe for: base_addr: 0x300,0x280,0x360,0x320,0x340
* mem_start: 0xd0000,0xd2000,0xc8000,0xca000,0xd4000,0xd6000,
* 0xd8000,0xcc000,0xce000,0xda000,0xdc000
*
* sources:
* skeleton.c from Donald Becker
*
* I have also done a look in the following sources: (mail me if you need them)
* crynwr-packet-driver by Russ Nelson
* Garret A. Wollman's (fourth) i82586-driver for BSD
* (before getting an i82596 (yes 596 not 586) manual, the existing drivers helped
* me a lot to understand this tricky chip.)
*
* Known Problems:
* The internal sysbus seems to be slow. So we often lose packets because of
* overruns while receiving from a fast remote host.
* This can slow down TCP connections. Maybe the newer ni5210 cards are better.
* my experience is, that if a machine sends with more than about 500-600K/s
* the fifo/sysbus overflows.
*
* IMPORTANT NOTE:
* On fast networks, it's a (very) good idea to have 16K shared memory. With
* 8K, we can store only 4 receive frames, so it can (easily) happen that a remote
* machine 'overruns' our system.
*
* Known i82586/card problems (I'm sure, there are many more!):
* Running the NOP-mode, the i82586 sometimes seems to forget to report
* every xmit-interrupt until we restart the CU.
* Another MAJOR bug is, that the RU sometimes seems to ignore the EL-Bit
* in the RBD-Struct which indicates an end of the RBD queue.
* Instead, the RU fetches another (randomly selected and
* usually used) RBD and begins to fill it. (Maybe, this happens only if
* the last buffer from the previous RFD fits exact into the queue and
* the next RFD can't fetch an initial RBD. Anyone knows more? )
*
* results from ftp performance tests with Linux 1.2.5
* send and receive about 350-400 KByte/s (peak up to 460 kbytes/s)
* sending in NOP-mode: peak performance up to 530K/s (but better don't run this mode)
*/
/*
* 29.Sept.96: virt_to_bus changes for new memory scheme
* 19.Feb.96: more Mcast changes, module support (MH)
*
* 18.Nov.95: Mcast changes (AC).
*
* 23.April.95: fixed(?) receiving problems by configuring a RFD more
* than the number of RBD's. Can maybe cause other problems.
* 18.April.95: Added MODULE support (MH)
* 17.April.95: MC related changes in init586() and set_multicast_list().
* removed use of 'jiffies' in init586() (MH)
*
* 19.Sep.94: Added Multicast support (not tested yet) (MH)
*
* 18.Sep.94: Workaround for 'EL-Bug'. Removed flexible RBD-handling.
* Now, every RFD has exact one RBD. (MH)
*
* 14.Sep.94: added promiscuous mode, a few cleanups (MH)
*
* 19.Aug.94: changed request_irq() parameter (MH)
*
* 20.July.94: removed cleanup bugs, removed a 16K-mem-probe-bug (MH)
*
* 19.July.94: lotsa cleanups .. (MH)
*
* 17.July.94: some patches ... verified to run with 1.1.29 (MH)
*
* 4.July.94: patches for Linux 1.1.24 (MH)
*
* 26.March.94: patches for Linux 1.0 and iomem-auto-probe (MH)
*
* 30.Sep.93: Added nop-chain .. driver now runs with only one Xmit-Buff, too (MH)
*
* < 30.Sep.93: first versions
*/
static int debuglevel; /* debug-printk 0: off 1: a few 2: more */
static int automatic_resume; /* experimental .. better should be zero */
static int rfdadd; /* rfdadd=1 may be better for 8K MEM cards */
static int fifo=0x8; /* don't change */
/* #define REALLY_SLOW_IO */
#include <linux/module.h>
#include <linux/kernel.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/bitops.h>
#include <asm/io.h>
#include <linux/netdevice.h>
#include