/*
 * Detection routine for the NCR53c710 based Amiga SCSI Controllers for Linux.
 *		Amiga MacroSystemUS WarpEngine SCSI controller.
 *		Amiga Technologies/DKB A4091 SCSI controller.
 *
 * Written 1997 by Alan Hourihane <alanh@fairlite.demon.co.uk>
 * plus modifications of the 53c7xx.c driver to support the Amiga.
 *
 * Rewritten to use 53c700.c by Kars de Jong <jongk@linux-m68k.org>
 */

#include <linux/module.h>
#include <linux/init.h>
#include <linux/interrupt.h>
#include <linux/zorro.h>
#include <linux/slab.h>

#include <asm/amigahw.h>
#include <asm/amigaints.h>

#include <scsi/scsi_host.h>
#include <scsi/scsi_transport_spi.h>

#include "53c700.h"

MODULE_AUTHOR("Alan Hourihane <alanh@fairlite.demon.co.uk> / Kars de Jong <jongk@linux-m68k.org>");
MODULE_DESCRIPTION("Amiga Zorro NCR53C710 driver");
MODULE_LICENSE("GPL");


static struct scsi_host_template zorro7xx_scsi_driver_template = {
	.proc_name	= "zorro7xx",
	.this_id	= 7,
	.module		= THIS_MODULE,
};

static struct zorro_driver_data {
	const char *name;
	unsigned long offset;
	int absolute;	/* offset is absolute address */
} zorro7xx_driver_data[] = {
	{ .name = "PowerUP 603e+", .offset = 0xf40000, .absolute = 1 },
	{ .name = "WarpEngine 40xx", .offset = 0x40000 },
	{ .name = "A4091", .offset = 0x800000 },
	{ .name = "GForce 040/060", .offset = 0x40000 },
	{ 0 }
};

static struct zorro_device_id zorro7xx_zorro_tbl[] = {
	{
		.id = ZORRO_PROD_PHASE5_BLIZZARD_603E_PLUS,
		.driver_data = (unsigned long)&zorro7xx_driver_data[0],
	},
	{
		.id = ZORRO_PROD_MACROSYSTEMS_WARP_ENGINE_40xx,
		.driver_data = (unsigned long)&zorro7xx_driver_data[1],
	},
	{
		.id = ZORRO_PROD_CBM_A4091_1,
		.driver_data = (unsigned long)&zorro7xx_driver_data[2],
	},
	{
		.id = ZORRO_PROD_CBM_A4091_2,
		.driver_data = (unsigned long)&zorro7xx_driver_data[2],
	},
	{
		.id = ZORRO_PROD_GVP_GFORCE_040_060,
		.driver_data = (unsigned long)&zorro7xx_driver_data[3],
	},
	{ 0 }
};
MODULE_DEVICE_TABLE(zorro, zorro7xx_zorro_tbl);

static int zorro7xx_init_one(struct zorro_dev *z,
			     const struct zorro_device_id *ent)
{
	struct Scsi_Host *host;
	struct NCR_700_Host_Parameters *hostdata;
	struct zorro_driver_data *zdd;
	unsigned long board, ioaddr;

	board = zorro_resource_start(z);
	zdd = (struct zorro_driver_data *)ent->driver_data;

	if (zdd->absolute) {
		ioaddr = zdd->offset;
	} else {
		ioaddr = board + zdd->offset;
	}

	if (!zorro_request_device(z, zdd->name)) {
		printk(KERN_ERR "zorro7xx: cannot reserve region 0x%lx, abort\n",
		       board);
		return -EBUSY;
	}

	hostdata = kzalloc(sizeof(struct NCR_700_Host_Parameters), GFP_KERNEL);
	if (!hostdata) {
		printk(KERN_ERR "zorro7xx: Failed to allocate host data\n");
		goto out_release;
	}

	/* Fill in the required pieces of hostdata */
	if (ioaddr > 0x01000000)
		hostdata->base = ioremap(ioaddr, zorro_resource_len(z));
	else
		hostdata->base = ZTWO_VADDR(ioaddr);

	hostdata->clock = 50;
	hostdata->chip710 = 1;

	/* Settings for at least WarpEngine 40xx */
	hostdata->ctest7_extra = CTEST7_TT1;

	zorro7xx_scsi_driver_template.name = zdd->name;

	/* and register the chip */
	host = NCR_700_detect(&zorro7xx_scsi_driver_template, hostdata,
			      &z->dev);
	if (!host) {
		printk(KERN_ERR "zorro7xx: No host detected; "
				"board configuration problem?\n");
		goto out_free;
	}

	host->this_id = 7;
	host->base = ioaddr;
	host->irq = IRQ_AMIGA_PORTS;

	if (request_irq(host->irq, NCR_700_intr, IRQF_SHARED, "zorro7xx-scsi",
			host)) {
		printk(KERN_ERR "zorro7xx: request_irq failed\n");
		goto out_put_host;
	}

	zorro_set_drvdata(z, host);
	scsi_scan_host(host);

	return 0;

 out_put_host:
	scsi_host_put(host);
 out_free:
	if (ioaddr > 0x01000000)
		iounmap(hostdata->base);
	kfree(hostdata);
 out_release:
	zorro_release_device(z);

	return -ENODEV;
}

static void zorro7xx_remove_one(struct zorro_dev *z)
{
	struct Scsi_Host *host = zorro_get_drvdata(z);
	struct NCR_700_Host_Parameters *hostdata = shost_priv(host);

	scsi_remove_host(host);

	NCR_700_release(host);
	kfree(hostdata);
	free_irq(host->irq, host);
	zorro_release_device(z);
}

static struct zorro_driver zorro7xx_driver = {
	.name	  = "zorro7xx-scsi",
	.id_table = zorro7xx_zorro_tbl,
	.probe	  = zorro7xx_init_one,
	.remove	  = zorro7xx_remove_one,
};

static int __init zorro7xx_scsi_init(void)
{
	return zorro_register_driver(&zorro7xx_driver);
}

static void __exit zorro7xx_scsi_exit(void)
{
	zorro_unregister_driver(&zorro7xx_driver);
}

module_init(zorro7xx_scsi_init);
module_exit(zorro7xx_scsi_exit);
