/*
 * Linux ARCnet driver - COM20020 chipset support
 *
 * Written 1997 by David Woodhouse.
 * Written 1994-1999 by Avery Pennarun.
 * Written 1999-2000 by Martin Mares <mj@ucw.cz>.
 * Derived from skeleton.c by Donald Becker.
 *
 * Special thanks to Contemporary Controls, Inc. (www.ccontrols.com)
 *  for sponsoring the further development of this driver.
 *
 * **********************
 *
 * The original copyright of skeleton.c was as follows:
 *
 * skeleton.c Written 1993 by Donald Becker.
 * Copyright 1993 United States Government as represented by the
 * Director, National Security Agency.  This software may only be used
 * and distributed according to the terms of the GNU General Public License as
 * modified by SRC, incorporated herein by reference.
 *
 * **********************
 *
 * For more details, see drivers/net/arcnet.c
 *
 * **********************
 */

#define pr_fmt(fmt) "arcnet:" KBUILD_MODNAME ": " fmt

#include <linux/module.h>
#include <linux/moduleparam.h>
#include <linux/kernel.h>
#include <linux/types.h>
#include <linux/ioport.h>
#include <linux/errno.h>
#include <linux/delay.h>
#include <linux/netdevice.h>
#include <linux/init.h>
#include <linux/interrupt.h>
#include <linux/bootmem.h>
#include <linux/io.h>

#include "arcdevice.h"
#include "com20020.h"

/* We cannot (yet) probe for an IO mapped card, although we can check that
 * it's where we were told it was, and even do autoirq.
 */
static int __init com20020isa_probe(struct net_device *dev)
{
	int ioaddr;
	unsigned long airqmask;
	struct arcnet_local *lp = netdev_priv(dev);
	int err;

	if (BUGLVL(D_NORMAL))
		pr_info("%s\n", "COM20020 ISA support (by David Woodhouse et al.)");

	ioaddr = dev->base_addr;
	if (!ioaddr) {
		arc_printk(D_NORMAL, dev, "No autoprobe (yet) for IO mapped cards; you must specify the base address!\n");
		return -ENODEV;
	}
	if (!request_region(ioaddr, ARCNET_TOTAL_SIZE, "arcnet (COM20020)")) {
		arc_printk(D_NORMAL, dev, "IO region %xh-%xh already allocated.\n",
			   ioaddr, ioaddr + ARCNET_TOTAL_SIZE - 1);
		return -ENXIO;
	}
	if (arcnet_inb(ioaddr, COM20020_REG_R_STATUS) == 0xFF) {
		arc_printk(D_NORMAL, dev, "IO address %x empty\n", ioaddr);
		err = -ENODEV;
		goto out;
	}
	if (com20020_check(dev)) {
		err = -ENODEV;
		goto out;
	}

	if (!dev->irq) {
		/* if we do this, we're sure to get an IRQ since the
		 * card has just reset and the NORXflag is on until
		 * we tell it to start receiving.
		 */
		arc_printk(D_INIT_REASONS, dev, "intmask was %02Xh\n",
			   arcnet_inb(ioaddr, COM20020_REG_R_STATUS));
		arcnet_outb(0, ioaddr, COM20020_REG_W_INTMASK);
		airqmask = probe_irq_on();
		arcnet_outb(NORXflag, ioaddr, COM20020_REG_W_INTMASK);
		udelay(1);
		arcnet_outb(0, ioaddr, COM20020_REG_W_INTMASK);
		dev->irq = probe_irq_off(airqmask);

		if ((int)dev->irq <= 0) {
			arc_printk(D_INIT_REASONS, dev, "Autoprobe IRQ failed first time\n");
			airqmask = probe_irq_on();
			arcnet_outb(NORXflag, ioaddr, COM20020_REG_W_INTMASK);
			udelay(5);
			arcnet_outb(0, ioaddr, COM20020_REG_W_INTMASK);
			dev->irq = probe_irq_off(airqmask);
			if ((int)dev->irq <= 0) {
				arc_printk(D_NORMAL, dev, "Autoprobe IRQ failed.\n");
				err = -ENODEV;
				goto out;
			}
		}
	}

	lp->card_name = "ISA COM20020";

	err = com20020_found(dev, 0);
	if (err != 0)
		goto out;

	return 0;

out:
	release_region(ioaddr, ARCNET_TOTAL_SIZE);
	return err;
}

static int node = 0;
static int io = 0x0;		/* <--- EDIT THESE LINES FOR YOUR CONFIGURATION */
static int irq = 0;		/* or use the insmod io= irq= shmem= options */
static char device[9];		/* use eg. device="arc1" to change name */
static int timeout = 3;
static int backplane = 0;
static int clockp = 0;
static int clockm = 0;

module_param(node, int, 0);
module_param_hw(io, int, ioport, 0);
module_param_hw(irq, int, irq, 0);
module_param_string(device, device, sizeof(device), 0);
module_param(timeout, int, 0);
module_param(backplane, int, 0);
module_param(clockp, int, 0);
module_param(clockm, int, 0);

MODULE_LICENSE("GPL");

static struct net_device *my_dev;

static int __init com20020_init(void)
{
	struct net_device *dev;
	struct arcnet_local *lp;

	dev = alloc_arcdev(device);
	if (!dev)
		return -ENOMEM;

	if (node && node != 0xff)
		dev->dev_addr[0] = node;

	dev->netdev_ops = &com20020_netdev_ops;

	lp = netdev_priv(dev);
	lp->backplane = backplane;
	lp->clockp = clockp & 7;
	lp->clockm = clockm & 3;
	lp->timeout = timeout & 3;
	lp->hw.owner = THIS_MODULE;

	dev->base_addr = io;
	dev->irq = irq;

	if (dev->irq == 2)
		dev->irq = 9;

	if (com20020isa_probe(dev)) {
		free_netdev(dev);
		return -EIO;
	}

	my_dev = dev;
	return 0;
}

static void __exit com20020_exit(void)
{
	unregister_netdev(my_dev);
	free_irq(my_dev->irq, my_dev);
	release_region(my_dev->base_addr, ARCNET_TOTAL_SIZE);
	free_netdev(my_dev);
}

#ifndef MODULE
static int __init com20020isa_setup(char *s)
{
	int ints[8];

	s = get_options(s, 8, ints);
	if (!ints[0])
		return 1;

	switch (ints[0]) {
	default:		/* ERROR */
		pr_info("Too many arguments\n");
	case 6:		/* Timeout */
		timeout = ints[6];
	case 5:		/* CKP value */
		clockp = ints[5];
	case 4:		/* Backplane flag */
		backplane = ints[4];
	case 3:		/* Node ID */
		node = ints[3];
	case 2:		/* IRQ */
		irq = ints[2];
	case 1:		/* IO address */
		io = ints[1];
	}
	if (*s)
		snprintf(device, sizeof(device), "%s", s);
	return 1;
}

__setup("com20020=", com20020isa_setup);

#endif				/* MODULE */

module_init(com20020_init)
module_exit(com20020_exit)
