/*
 * Qlogic FAS408 ISA card driver
 *
 * Copyright 1994, Tom Zerucha.   
 * tz@execpc.com
 * 
 * Redistributable under terms of the GNU General Public License
 *
 * For the avoidance of doubt the "preferred form" of this code is one which
 * is in an open non patent encumbered format. Where cryptographic key signing
 * forms part of the process of creating an executable the information
 * including keys needed to generate an equivalently functional executable
 * are deemed to be part of the source code.
 *
 * Check qlogicfas408.c for more credits and info.
 */

#include <linux/module.h>
#include <linux/blkdev.h>		/* to get disk capacity */
#include <linux/kernel.h>
#include <linux/string.h>
#include <linux/init.h>
#include <linux/interrupt.h>
#include <linux/ioport.h>
#include <linux/proc_fs.h>
#include <linux/unistd.h>
#include <linux/spinlock.h>
#include <linux/stat.h>

#include <asm/io.h>
#include <asm/irq.h>
#include <asm/dma.h>

#include "scsi.h"
#include <scsi/scsi_host.h>
#include "qlogicfas408.h"

/* Set the following to 2 to use normal interrupt (active high/totempole-
 * tristate), otherwise use 0 (REQUIRED FOR PCMCIA) for active low, open
 * drain
 */
#define INT_TYPE	2

static char qlogicfas_name[] = "qlogicfas";

/*
 *	Look for qlogic card and init if found 
 */
 
static struct Scsi_Host *__qlogicfas_detect(Scsi_Host_Template *host,
								int qbase,
								int qlirq)
{
	int qltyp;		/* type of chip */
	int qinitid;
	struct Scsi_Host *hreg;	/* registered host structure */
	struct qlogicfas408_priv *priv;

	/*	Qlogic Cards only exist at 0x230 or 0x330 (the chip itself
	 *	decodes the address - I check 230 first since MIDI cards are
	 *	typically at 0x330
	 *
	 *	Theoretically, two Qlogic cards can coexist in the same system.
	 *	This should work by simply using this as a loadable module for
	 *	the second card, but I haven't tested this.
	 */

	if (!qbase || qlirq == -1)
		goto err;

	if (!request_region(qbase, 0x10, qlogicfas_name)) {
		printk(KERN_INFO "%s: address %#x is busy\n", qlogicfas_name,
							      qbase);
		goto err;
	}

	if (!qlogicfas408_detect(qbase, INT_TYPE)) {
		printk(KERN_WARNING "%s: probe failed for %#x\n",
								qlogicfas_name,
								qbase);
		goto err_release_mem;
	}

	printk(KERN_INFO "%s: Using preset base address of %03x,"
			 " IRQ %d\n", qlogicfas_name, qbase, qlirq);

	qltyp = qlogicfas408_get_chip_type(qbase, INT_TYPE);
	qinitid = host->this_id;
	if (qinitid < 0)
		qinitid = 7;	/* if no ID, use 7 */

	qlogicfas408_setup(qbase, qinitid, INT_TYPE);

	hreg = scsi_host_alloc(host, sizeof(struct qlogicfas408_priv));
	if (!hreg)
		goto err_release_mem;
	priv = get_priv_by_host(hreg);
	hreg->io_port = qbase;
	hreg->n_io_port = 16;
	hreg->dma_channel = -1;
	if (qlirq != -1)
		hreg->irq = qlirq;
	priv->qbase = qbase;
	priv->qlirq = qlirq;
	priv->qinitid = qinitid;
	priv->shost = hreg;
	priv->int_type = INT_TYPE;

	sprintf(priv->qinfo,
		"Qlogicfas Driver version 0.46, chip %02X at %03X, IRQ %d, TPdma:%d",
		qltyp, qbase, qlirq, QL_TURBO_PDMA);
	host->name = qlogicfas_name;

	if (request_irq(qlirq, qlogicfas408_ihandl, 0, qlogicfas_name, hreg))
		goto free_scsi_host;

	if (scsi_add_host(hreg, NULL))
		goto free_interrupt;

	scsi_scan_host(hreg);

	return hreg;

free_interrupt:
	free_irq(qlirq, hreg);

free_scsi_host:
	scsi_host_put(hreg);

err_release_mem:
	release_region(qbase, 0x10);
err:
	return NULL;
}

#define MAX_QLOGICFAS	8
static struct qlogicfas408_priv *cards;
static int iobase[MAX_QLOGICFAS];
static int irq[MAX_QLOGICFAS] = { [0 ... MAX_QLOGICFAS-1] = -1 };
module_param_array(iobase, int, NULL, 0);
module_param_array(irq, int, NULL, 0);
MODULE_PARM_DESC(iobase, "I/O address");
MODULE_PARM_DESC(irq, "IRQ");

static int __devinit qlogicfas_detect(Scsi_Host_Template *sht)
{
	struct Scsi_Host *shost;
	struct qlogicfas408_priv *priv;
	int num;

	for (num = 0; num < MAX_QLOGICFAS; num++) {
		shost = __qlogicfas_detect(sht, iobase[num], irq[num]);
		if (shost == NULL) {
			/* no more devices */
			break;
		}
		priv = get_priv_by_host(shost);
		priv->next = cards;
		cards = priv;
	}

	return num;
}

static int qlogicfas_release(struct Scsi_Host *shost)
{
	struct qlogicfas408_priv *priv = get_priv_by_host(shost);

	if (shost->irq) {
		qlogicfas408_disable_ints(priv);	
		free_irq(shost->irq, shost);
	}
	if (shost->dma_channel != 0xff)
		free_dma(shost->dma_channel);
	if (shost->io_port && shost->n_io_port)
		release_region(shost->io_port, shost->n_io_port);
	scsi_remove_host(shost);
	scsi_host_put(shost);

	return 0;
}

/*
 *	The driver template is also needed for PCMCIA
 */
static Scsi_Host_Template qlogicfas_driver_template = {
	.module			= THIS_MODULE,
	.name			= qlogicfas_name,
	.proc_name		= qlogicfas_name,
	.info			= qlogicfas408_info,
	.queuecommand		= qlogicfas408_queuecommand,
	.eh_abort_handler	= qlogicfas408_abort,
	.eh_bus_reset_handler	= qlogicfas408_bus_reset,
	.eh_device_reset_handler= qlogicfas408_device_reset,
	.eh_host_reset_handler	= qlogicfas408_host_reset,
	.bios_param		= qlogicfas408_biosparam,
	.can_queue		= 1,
	.this_id		= -1,
	.sg_tablesize		= SG_ALL,
	.cmd_per_lun		= 1,
	.use_clustering		= DISABLE_CLUSTERING,
};

static __init int qlogicfas_init(void)
{
	if (!qlogicfas_detect(&qlogicfas_driver_template)) {
		/* no cards found */
		printk(KERN_INFO "%s: no cards were found, please specify "
				 "I/O address and IRQ using iobase= and irq= "
				 "options", qlogicfas_name);
		return -ENODEV;
	}

	return 0;
}

static __exit void qlogicfas_exit(void)
{
	struct qlogicfas408_priv *priv;

	for (priv = cards; priv != NULL; priv = priv->next)
		qlogicfas_release(priv->shost);
}

MODULE_AUTHOR("Tom Zerucha, Michael Griffith");
MODULE_DESCRIPTION("Driver for the Qlogic FAS408 based ISA card");
MODULE_LICENSE("GPL");
module_init(qlogicfas_init);
module_exit(qlogicfas_exit);

