/*
 * Copyright (C) by Hannu Savolainen 1993-1997
 *
 * mad16.c
 *
 * Initialization code for OPTi MAD16 compatible audio chips. Including
 *
 *      OPTi 82C928     MAD16           (replaced by C929)
 *      OAK OTI-601D    Mozart
 *      OAK OTI-605	Mozart		(later version with MPU401 Midi)
 *      OPTi 82C929     MAD16 Pro
 *      OPTi 82C930
 *      OPTi 82C924
 *
 * These audio interface chips don't produce sound themselves. They just
 * connect some other components (OPL-[234] and a WSS compatible codec)
 * to the PC bus and perform I/O, DMA and IRQ address decoding. There is
 * also a UART for the MPU-401 mode (not 82C928/Mozart).
 * The Mozart chip appears to be compatible with the 82C928, although later
 * issues of the card, using the OTI-605 chip, have an MPU-401 compatible Midi
 * port. This port is configured differently to that of the OPTi audio chips.
 *
 *	Changes
 *	
 *	Alan Cox		Clean up, added module selections.
 *
 *	A. Wik			Added support for Opti924 PnP.
 *				Improved debugging support.	16-May-1998
 *				Fixed bug.			16-Jun-1998
 *
 *      Torsten Duwe            Made Opti924 PnP support non-destructive
 *                                                             	23-Dec-1998
 *
 *	Paul Grayson		Added support for Midi on later Mozart cards.
 *								25-Nov-1999
 *	Christoph Hellwig	Adapted to module_init/module_exit.
 *	Arnaldo C. de Melo	got rid of attach_uart401       21-Sep-2000
 *
 *	Pavel Rabel		Clean up                           Nov-2000
 */

#include <linux/config.h>
#include <linux/init.h>
#include <linux/module.h>
#include <linux/gameport.h>
#include <linux/spinlock.h>
#include "sound_config.h"

#include "ad1848.h"
#include "sb.h"
#include "mpu401.h"

static int      mad16_conf;
static int      mad16_cdsel;
static struct gameport *gameport;
static DEFINE_SPINLOCK(lock);

#define C928	1
#define MOZART	2
#define C929	3
#define C930	4
#define C924    5

/*
 *    Registers
 *
 *      The MAD16 occupies I/O ports 0xf8d to 0xf93 (fixed locations).
 *      All ports are inactive by default. They can be activated by
 *      writing 0xE2 or 0xE3 to the password register. The password is valid
 *      only until the next I/O read or write.
 *
 *      82C930 uses 0xE4 as the password and indirect addressing to access
 *      the config registers.
 */

#define MC0_PORT	0xf8c	/* Dummy port */
#define MC1_PORT	0xf8d	/* SB address, CD-ROM interface type, joystick */
#define MC2_PORT	0xf8e	/* CD-ROM address, IRQ, DMA, plus OPL4 bit */
#define MC3_PORT	0xf8f
#define PASSWD_REG	0xf8f
#define MC4_PORT	0xf90
#define MC5_PORT	0xf91
#define MC6_PORT	0xf92
#define MC7_PORT	0xf93
#define MC8_PORT	0xf94
#define MC9_PORT	0xf95
#define MC10_PORT	0xf96
#define MC11_PORT	0xf97
#define MC12_PORT	0xf98

static int      board_type = C928;

static int     *mad16_osp;
static int	c931_detected;	/* minor differences from C930 */
static char	c924pnp;	/* "     "           "    C924 */
static int	debug;  	/* debugging output */

#ifdef DDB
#undef DDB
#endif
#define DDB(x) do {if (debug) x;} while (0)

static unsigned char mad_read(int port)
{
	unsigned long flags;
	unsigned char tmp;

	spin_lock_irqsave(&lock,flags);

	switch (board_type)	/* Output password */
	{
		case C928:
		case MOZART:
			outb((0xE2), PASSWD_REG);
			break;

		case C929:
			outb((0xE3), PASSWD_REG);
			break;

		case C930:
			/* outb(( 0xE4),  PASSWD_REG); */
			break;

		case C924:
			/* the c924 has its ports relocated by -128 if
			   PnP is enabled  -aw */
			if (!c924pnp)
				outb((0xE5), PASSWD_REG); else
				outb((0xE5), PASSWD_REG - 0x80);
			break;
	}

	if (board_type == C930)
	{
		outb((port - MC0_PORT), 0xe0e);	/* Write to index reg */
		tmp = inb(0xe0f);	/* Read from data reg */
	}
	else
		if (!c924pnp)
			tmp = inb(port); else
			tmp = inb(port-0x80);
	spin_unlock_irqrestore(&lock,flags);

	return tmp;
}

static void mad_write(int port, int value)
{
	unsigned long   flags;

	spin_lock_irqsave(&lock,flags);

	switch (board_type)	/* Output password */
	{
		case C928:
		case MOZART:
			outb((0xE2), PASSWD_REG);
			break;

		case C929:
			outb((0xE3), PASSWD_REG);
			break;

		case C930:
			/* outb(( 0xE4),  PASSWD_REG); */
			break;

		case C924:
			if (!c924pnp)
				outb((0xE5), PASSWD_REG); else
				outb((0xE5), PASSWD_REG - 0x80);
			break;
	}

	if (board_type == C930)
	{
		outb((port - MC0_PORT), 0xe0e);	/* Write to index reg */
		outb(((unsigned char) (value & 0xff)), 0xe0f);
	}
	else
		if (!c924pnp)
			outb(((unsigned char) (value & 0xff)), port); else
			outb(((unsigned char) (value & 0xff)), port-0x80);
	spin_unlock_irqrestore(&lock,flags);
}

static int __init detect_c930(void)
{
	unsigned char   tmp = mad_read(MC1_PORT);

	if ((tmp & 0x06) != 0x06)
	{
		DDB(printk("Wrong C930 signature (%x)\n", tmp));
		/* return 0; */
	}
	mad_write(MC1_PORT, 0);

	if (mad_read(MC1_PORT) != 0x06)
	{
		DDB(printk("Wrong C930 signature2 (%x)\n", tmp));
		/* return 0; */
	}
	mad_write(MC1_PORT, tmp);	/* Restore bits */

	mad_write(MC7_PORT, 0);
	if ((tmp = mad_read(MC7_PORT)) != 0)
	{
		DDB(printk("MC7 not writable (%x)\n", tmp));
		return 0;
	}
	mad_write(MC7_PORT, 0xcb);
	if ((tmp = mad_read(MC7_PORT)) != 0xcb)
	{
		DDB(printk("MC7 not writable2 (%x)\n", tmp));
		return 0;
	}

	tmp = mad_read(MC0_PORT+18);
	if (tmp == 0xff || tmp == 0x00)
		return 1;
	/* We probably have a C931 */
	DDB(printk("Detected C931 config=0x%02x\n", tmp));
	c931_detected = 1;

	/*
         * We cannot configure the chip if it is in PnP mode.
         * If we have a CSN assigned (bit 8 in MC13) we first try
         * a software reset, then a software power off, finally
         * Clearing PnP mode. The last option is not
	 * Bit 8 in MC13 
         */
	if ((mad_read(MC0_PORT+13) & 0x80) == 0)
		return 1;

	/* Software reset */
	mad_write(MC9_PORT, 0x02);
	mad_write(MC9_PORT, 0x00);

	if ((mad_read(MC0_PORT+13) & 0x80) == 0)
		return 1;
	
	/* Power off, and on again */
	mad_write(MC9_PORT, 0xc2);
	mad_write(MC9_PORT, 0xc0);

	if ((mad_read(MC0_PORT+13) & 0x80) == 0)
		return 1;
	
#if 0	
	/* Force off PnP mode. This is not recommended because
	 * the PnP bios will not recognize the chip on the next
	 * warm boot and may assignd different resources to other
	 * PnP/PCI cards.
	 */
	mad_write(MC0_PORT+17, 0x04);
#endif
	return 1;
}

static int __init detect_mad16(void)
{
	unsigned char tmp, tmp2, bit;
	int i, port;

	/*
	 * Check that reading a register doesn't return bus float (0xff)
	 * when the card is accessed using password. This may fail in case
	 * the card is in low power mode. Normally at least the power saving
	 * mode bit should be 0.
	 */

	if ((tmp = mad_read(MC1_PORT)) == 0xff)
	{
		DDB(printk("MC1_PORT returned 0xff\n"));
		return 0;
	}
	for (i = 0xf8d; i <= 0xf98; i++)
		if (!c924pnp)
			DDB(printk("Port %0x (init value) = %0x\n", i, mad_read(i)));
		else
			DDB(printk("Port %0x (init value) = %0x\n", i-0x80, mad_read(i)));

	if (board_type == C930)
		return detect_c930();

	/*
	 * Now check that the gate is closed on first I/O after writing
	 * the password. (This is how a MAD16 compatible card works).
	 */

	if ((tmp2 = inb(MC1_PORT)) == tmp)	/* It didn't close */
	{
		DDB(printk("MC1_PORT didn't close after read (0x%02x)\n", tmp2));
		return 0;
	}

	bit  = (c924pnp) ?     0x20 : 0x80;
	port = (c924pnp) ? MC2_PORT : MC1_PORT;

	tmp = mad_read(port);
	mad_write(port, tmp ^ bit);	/* Toggle a bit */
	if ((tmp2 = mad_read(port)) != (tmp ^ bit))	/* Compare the bit */
	{
		mad_write(port, tmp);	/* Restore */
		DDB(printk("Bit revert test failed (0x%02x, 0x%02x)\n", tmp, tmp2));
		return 0;
	}
	mad_write(port, tmp);	/* Restore */
	return 1;		/* Bingo */
}

static int __init wss_init(struct address_info *hw_config)
{
	/*
	 * Check if the IO port returns valid signature. The original MS Sound
	 * system returns 0x04 while some cards (AudioTrix Pro for example)
	 * return 0x00.
	 */

	if ((inb(hw_config->io_base + 3) & 0x3f) != 0x04 &&
	    (inb(hw_config->io_base + 3) & 0x3f) != 0x00)
	{
		DDB(printk("No MSS signature detected on port 0x%x (0x%x)\n", hw_config->io_base, inb(hw_config->io_base + 3)));
		return 0;
	}
	/*
	 * Check that DMA0 is not in use with a 8 bit board.
	 */
	if (hw_config->dma == 0 && inb(hw_config->io_base + 3) & 0x80)
	{
		printk("MSS: Can't use DMA0 with a 8 bit card/slot\n");
		return 0;
	}
	if (hw_config->irq > 9 && inb(hw_config->io_base + 3) & 0x80)
		printk(KERN_ERR "MSS: Can't use IRQ%d with a 8 bit card/slot\n", hw_config->irq);
	return 1;
}

static void __init init_c930(struct address_info *hw_config, int base)
{
	unsigned char cfg = 0;

	cfg |= (0x0f & mad16_conf);

	if(c931_detected)
	{
		/* Bit 0 has reversd meaning. Bits 1 and 2 sese
		   reversed on write.
		   Support only IDE cdrom. IDE port programmed
		   somewhere else. */
		cfg =  (cfg & 0x09) ^ 0x07;
	}
	cfg |= base << 4;
	mad_write(MC1_PORT, cfg);

	/* MC2 is CD configuration. Don't touch it. */

	mad_write(MC3_PORT, 0);	/* Disable SB mode IRQ and DMA */

	/* bit 2 of MC4 reverses it's meaning between the C930
	   and the C931. */
	cfg = c931_detected ? 0x04 : 0x00;

	if(mad16_cdsel & 0x20)
		mad_write(MC4_PORT, 0x62|cfg);  /* opl4 */
	else
		mad_write(MC4_PORT, 0x52|cfg);  /* opl3 */

	mad_write(MC5_PORT, 0x3C);	/* Init it into mode2 */
	mad_write(MC6_PORT, 0x02);	/* Enable WSS, Disable MPU and SB */
	mad_write(MC7_PORT, 0xCB);
	mad_write(MC10_PORT, 0x11);
}

static int __init chip_detect(void)
{
	int i;

	/*
	 *    Then try to detect with the old password
	 */
	board_type = C924;

	DDB(printk("Detect using password = 0xE5\n"));
	
	if (detect_mad16()) {
		return 1;
	}
	
	board_type = C928;

	DDB(printk("Detect using password = 0xE2\n"));

	if (detect_mad16())
	{
		unsigned char model;

		if (((model = mad_read(MC3_PORT)) & 0x03) == 0x03) {
			DDB(printk("mad16.c: Mozart detected\n"));
			board_type = MOZART;
		} else {
			DDB(printk("mad16.c: 82C928 detected???\n"));
			board_type = C928;
		}
		return 1;
	}

	board_type = C929;

	DDB(printk("Detect using password = 0xE3\n"));

	if (detect_mad16())
	{
		DDB(printk("mad16.c: 82C929 detected\n"));
		return 1;
	}

	if (inb(PASSWD_REG) != 0xff)
		return 0;

	/*
	 * First relocate MC# registers to 0xe0e/0xe0f, disable password 
	 */

	outb((0xE4), PASSWD_REG);
	outb((0x80), PASSWD_REG);

	board_type = C930;

	DDB(printk("Detect using password = 0xE4\n"));

	for (i = 0xf8d; i <= 0xf93; i++)
		DDB(printk("port %03x = %02x\n", i, mad_read(i)));

        if(detect_mad16()) {
		DDB(printk("mad16.c: 82C930 detected\n"));
		return 1;
	}

	/* The C931 has the password reg at F8D */
	outb((0xE4), 0xF8D);
	outb((0x80), 0xF8D);
	DDB(printk("Detect using password = 0xE4 for C931\n"));

	if (detect_mad16()) {
		return 1;
	}

	board_type = C924;
	c924pnp++;
	DDB(printk("Detect using password = 0xE5 (again), port offset -0x80\n"));
	if (detect_mad16()) {
		DDB(printk("mad16.c: 82C924 PnP detected\n"));
		return 1;
	}
	
	c924pnp=0;

	return 0;
}

static int __init probe_mad16(struct address_info *hw_config)
{
	int i;
	unsigned char tmp;
	unsigned char cs4231_mode = 0;

	int ad_flags = 0;

	signed char bits;

	static char     dma_bits[4] = {
		1, 2, 0, 3
	};

	int config_port = hw_config->io_base + 0, version_port = hw_config->io_base + 3;
	int dma = hw_config->dma, dma2 = hw_config->dma2;
	unsigned char dma2_bit = 0;
	int base;
	struct resource *ports;

	mad16_osp = hw_config->osp;

	switch (hw_config->io_base) {
	case 0x530:
		base = 0;
		break;
	case 0xe80:
		base = 1;
		break;
	case 0xf40:
		base = 2;
		break;
	case 0x604:
		base = 3;
		break;
	default:
		printk(KERN_ERR "MAD16/Mozart: Bad WSS base address 0x%x\n", hw_config->io_base);
		return 0;
	}

	if (dma != 0 && dma != 1 && dma != 3) {
		printk(KERN_ERR "MSS: Bad DMA %d\n", dma);
		return 0;
	}

	/*
	 *    Check that all ports return 0xff (bus float) when no password
	 *      is written to the password register.
	 */

	DDB(printk("--- Detecting MAD16 / Mozart ---\n"));
	if (!chip_detect())
		return 0;

	switch (hw_config->irq) {
	case 7:
		bits = 8;
		break;
	case 9:
		bits = 0x10;
		break;
	case 10:
		bits = 0x18;
		break;
	case 12:
		bits = 0x20;
		break;
	case 5:	/* Also IRQ5 is possible on C930 */
		if (board_type == C930 || c924pnp) {
			bits = 0x28;
			break;
		}
	default:
		printk(KERN_ERR "MAD16/Mozart: Bad IRQ %d\n", hw_config->irq);
		return 0;
	}

	ports = request_region(hw_config->io_base + 4, 4, "ad1848");
	if (!ports) {
		printk(KERN_ERR "MSS: I/O port conflict\n");
		return 0;
	}
	if (!request_region(hw_config->io_base, 4, "mad16 WSS config")) {
		release_region(hw_config->io_base + 4, 4);
		printk(KERN_ERR "MSS: I/O port conflict\n");
		return 0;
	}

	if (board_type == C930) {
		init_c930(hw_config, base);
		goto got_it;
	}

	for (i = 0xf8d; i <= 0xf93; i++) {
		if (!c924pnp)
			DDB(printk("port %03x = %02x\n", i, mad_read(i)));
		else
			DDB(printk("port %03x = %02x\n", i-0x80, mad_read(i)));
	}

/*
 * Set the WSS address
 */

	tmp = (mad_read(MC1_PORT) & 0x0f) | 0x80;	/* Enable WSS, Disable SB */
	tmp |= base << 4;	/* WSS port select bits */

	/*
	 * Set optional CD-ROM and joystick settings.
	 */

	tmp &= ~0x0f;
	tmp |= (mad16_conf & 0x0f);	/* CD-ROM and joystick bits */
	mad_write(MC1_PORT, tmp);

	tmp = mad16_cdsel;
	mad_write(MC2_PORT, tmp);
	mad_write(MC3_PORT, 0xf0);	/* Disable SB */

	if (board_type == C924)	/* Specific C924 init values */
	{
		mad_write(MC4_PORT, 0xA0);
		mad_write(MC5_PORT, 0x05);
		mad_write(MC6_PORT, 0x03);
	}
	if (!ad1848_detect(ports, &ad_flags, mad16_osp))
		goto fail;

	if (ad_flags & (AD_F_CS4231 | AD_F_CS4248))
		cs4231_mode = 0x02;	/* CS4248/CS4231 sync delay switch */

	if (board_type == C929)
	{
		mad_write(MC4_PORT, 0xa2);
		mad_write(MC5_PORT, 0xA5 | cs4231_mode);
		mad_write(MC6_PORT, 0x03);	/* Disable MPU401 */
	}
	else
	{
		mad_write(MC4_PORT, 0x02);
		mad_write(MC5_PORT, 0x30 | cs4231_mode);
	}

	for (i = 0xf8d; i <= 0xf93; i++) {
		if (!c924pnp)
			DDB(printk("port %03x after init = %02x\n", i, mad_read(i)));
		else
			DDB(printk("port %03x after init = %02x\n", i-0x80, mad_read(i)));
	}

got_it:
	ad_flags = 0;
	if (!ad1848_detect(ports, &ad_flags, mad16_osp))
		goto fail;

	if (!wss_init(hw_config))
		goto fail;

	/*
	 * Set the IRQ and DMA addresses.
	 */
	
	outb((bits | 0x40), config_port);
	if ((inb(version_port) & 0x40) == 0)
		printk(KERN_ERR "[IRQ Conflict?]\n");

	/*
	 * Handle the capture DMA channel
	 */

	if (ad_flags & AD_F_CS4231 && dma2 != -1 && dma2 != dma)
	{
		if (!((dma == 0 && dma2 == 1) ||
			(dma == 1 && dma2 == 0) ||
			(dma == 3 && dma2 == 0)))
		{		/* Unsupported combination. Try to swap channels */
			int tmp = dma;

			dma = dma2;
			dma2 = tmp;
		}
		if ((dma == 0 && dma2 == 1) || (dma == 1 && dma2 == 0) ||
			(dma == 3 && dma2 == 0))
		{
			dma2_bit = 0x04;	/* Enable capture DMA */
		}
		else
		{
			printk("MAD16: Invalid capture DMA\n");
			dma2 = dma;
		}
	}
	else dma2 = dma;

	outb((bits | dma_bits[dma] | dma2_bit), config_port);	/* Write IRQ+DMA setup */

	hw_config->slots[0] = ad1848_init("mad16 WSS", ports,
					  hw_config->irq,
					  dma,
					  dma2, 0,
					  hw_config->osp,
					  THIS_MODULE);
	return 1;

fail:
	release_region(hw_config->io_base + 4, 4);
	release_region(hw_config->io_base, 4);
	return 0;
}

static int __init probe_mad16_mpu(struct address_info *hw_config)
{
	unsigned char tmp;

	if (board_type < C929)	/* Early chip. No MPU support. Just SB MIDI */
	{

#ifdef CONFIG_MAD16_OLDCARD

		tmp = mad_read(MC3_PORT);

		/* 
		 * MAD16 SB base is defined by the WSS base. It cannot be changed 
		 * alone.
		 * Ignore configured I/O base. Use the active setting. 
		 */

		if (mad_read(MC1_PORT) & 0x20)
			hw_config->io_base = 0x240;
		else
			hw_config->io_base = 0x220;

		switch (hw_config->irq)
		{
			case 5:
				tmp = (tmp & 0x3f) | 0x80;
				break;
			case 7:
				tmp = (tmp & 0x3f);
				break;
			case 11:
				tmp = (tmp & 0x3f) | 0x40;
				break;
			default:
				printk(KERN_ERR "mad16/Mozart: Invalid MIDI IRQ\n");
				return 0;
		}

		mad_write(MC3_PORT, tmp | 0x04);
		hw_config->driver_use_1 = SB_MIDI_ONLY;
		if (!request_region(hw_config->io_base, 16, "soundblaster"))
			return 0;
		if (!sb_dsp_detect(hw_config, 0, 0, NULL)) {
			release_region(hw_config->io_base, 16);
			return 0;
		}

		if (mad_read(MC1_PORT) & 0x20)
			hw_config->io_base = 0x240;
		else
			hw_config->io_base = 0x220;

		hw_config->name = "Mad16/Mozart";
		sb_dsp_init(hw_config, THIS_MODULE);
		return 1;
#else
		/* assuming all later Mozart cards are identified as
		 * either 82C928 or Mozart. If so, following code attempts
		 * to set MPU register. TODO - add probing
		 */

		tmp = mad_read(MC8_PORT);

		switch (hw_config->irq)
		{
			case 5:
				tmp |= 0x08;
				break;
			case 7:
				tmp |= 0x10;
				break;
			case 9:
				tmp |= 0x18;
				break;
			case 10:
				tmp |= 0x20;
				break;
			case 11:
				tmp |= 0x28;
				break;
			default:
				printk(KERN_ERR "mad16/MOZART: invalid mpu_irq\n");
				return 0;
		}

		switch (hw_config->io_base)
		{
			case 0x300:
				tmp |= 0x01;
				break;
			case 0x310:
				tmp |= 0x03;
				break;
			case 0x320:
				tmp |= 0x05;
				break;
			case 0x330:
				tmp |= 0x07;
				break;
			default:
				printk(KERN_ERR "mad16/MOZART: invalid mpu_io\n");
				return 0;
		}

		mad_write(MC8_PORT, tmp);	/* write MPU port parameters */
		goto probe_401;
#endif
	}
	tmp = mad_read(MC6_PORT) & 0x83;
	tmp |= 0x80;		/* MPU-401 enable */

	/* Set the MPU base bits */

	switch (hw_config->io_base)
	{
		case 0x300:
			tmp |= 0x60;
			break;
		case 0x310:
			tmp |= 0x40;
			break;
		case 0x320:
			tmp |= 0x20;
			break;
		case 0x330:
			tmp |= 0x00;
			break;
		default:
			printk(KERN_ERR "MAD16: Invalid MIDI port 0x%x\n", hw_config->io_base);
			return 0;
	}

	/* Set the MPU IRQ bits */

	switch (hw_config->irq)
	{
		case 5:
			tmp |= 0x10;
			break;
		case 7:
			tmp |= 0x18;
			break;
		case 9:
			tmp |= 0x00;
			break;
		case 10:
			tmp |= 0x08;
			break;
		default:
			printk(KERN_ERR "MAD16: Invalid MIDI IRQ %d\n", hw_config->irq);
			break;
	}
			
	mad_write(MC6_PORT, tmp);	/* Write MPU401 config */

#ifndef CONFIG_MAD16_OLDCARD
probe_401:
#endif
	hw_config->driver_use_1 = SB_MIDI_ONLY;
	hw_config->name = "Mad16/Mozart";
	return probe_uart401(hw_config, THIS_MODULE);
}

static void __exit unload_mad16(struct address_info *hw_config)
{
	ad1848_unload(hw_config->io_base + 4,
			hw_config->irq,
			hw_config->dma,
			hw_config->dma2, 0);
	release_region(hw_config->io_base, 4);
	sound_unload_audiodev(hw_config->slots[0]);
}

static void __exit unload_mad16_mpu(struct address_info *hw_config)
{
#ifdef CONFIG_MAD16_OLDCARD
	if (board_type < C929)	/* Early chip. No MPU support. Just SB MIDI */
	{
		sb_dsp_unload(hw_config, 0);
		return;
	}
#endif

	unload_uart401(hw_config);
}

static struct address_info cfg;
static struct address_info cfg_mpu;

static int found_mpu;

static int __initdata mpu_io = 0;
static int __initdata mpu_irq = 0;
static int __initdata io = -1;
static int __initdata dma = -1;
static int __initdata dma16 = -1; /* Set this for modules that need it */
static int __initdata irq = -1;
static int __initdata cdtype = 0;
static int __initdata cdirq = 0;
static int __initdata cdport = 0x340;
static int __initdata cddma = -1;
static int __initdata opl4 = 0;
static int __initdata joystick = 0;

module_param(mpu_io, int, 0);
module_param(mpu_irq, int, 0);
module_param(io, int, 0);
module_param(dma, int, 0);
module_param(dma16, int, 0);
module_param(irq, int, 0);
module_param(cdtype, int, 0);
module_param(cdirq, int, 0);
module_param(cdport, int, 0);
module_param(cddma, int, 0);
module_param(opl4, int, 0);
module_param(joystick, bool, 0);
module_param(debug, bool, 0644);

static int __initdata dma_map[2][8] =
{
	{0x03, -1, -1, -1, -1, 0x00, 0x01, 0x02},
	{0x03, -1, 0x01, 0x00, -1, -1, -1, -1}
};

static int __initdata irq_map[16] =
{
	0x00, -1, -1, 0x0A,
	-1, 0x04, -1, 0x08,
	-1, 0x10, 0x14, 0x18,
	-1, -1, -1, -1
};

static int __devinit mad16_register_gameport(int io_port)
{
	if (!request_region(io_port, 1, "mad16 gameport")) {
		printk(KERN_ERR "mad16: gameport address 0x%#x already in use\n", io_port);
		return -EBUSY;
	}

	gameport = gameport_allocate_port();
	if (!gameport) {
		printk(KERN_ERR "mad16: can not allocate memory for gameport\n");
		release_region(io_port, 1);
		return -ENOMEM;
	}

	gameport_set_name(gameport, "MAD16 Gameport");
	gameport_set_phys(gameport, "isa%04x/gameport0", io_port);
	gameport->io = io_port;

	gameport_register_port(gameport);

	return 0;
}

static int __devinit init_mad16(void)
{
	int dmatype = 0;

	printk(KERN_INFO "MAD16 audio driver Copyright (C) by Hannu Savolainen 1993-1996\n");

	printk(KERN_INFO "CDROM ");
	switch (cdtype)
	{
		case 0x00:
			printk("Disabled");
			cdirq = 0;
			break;
		case 0x02:
			printk("Sony CDU31A");
			dmatype = 1;
			if(cddma == -1) cddma = 3;
			break;
		case 0x04:
			printk("Mitsumi");
			dmatype = 0;
			if(cddma == -1) cddma = 5;
			break;
		case 0x06:
			printk("Panasonic Lasermate");
			dmatype = 1;
			if(cddma == -1) cddma = 3;
			break;
		case 0x08:
			printk("Secondary IDE");
			dmatype = 0;
			if(cddma == -1) cddma = 5;
			break;
		case 0x0A:
			printk("Primary IDE");
			dmatype = 0;
			if(cddma == -1) cddma = 5;
			break;
		default:
			printk("\n");
			printk(KERN_ERR "Invalid CDROM type\n");
			return -EINVAL;
	}

	/*
	 *    Build the config words
	 */

	mad16_conf = (joystick ^ 1) | cdtype;
	mad16_cdsel = 0;
	if (opl4)
		mad16_cdsel |= 0x20;

	if(cdtype){
		if (cddma > 7 || cddma < 0 || dma_map[dmatype][cddma] == -1)
		{
			printk("\n");
			printk(KERN_ERR "Invalid CDROM DMA\n");
			return -EINVAL;
		}
		if (cddma)
			printk(", DMA %d", cddma);
		else
			printk(", no DMA");

		if (!cdirq)
			printk(", no IRQ");
		else if (cdirq < 0 || cdirq > 15 || irq_map[cdirq] == -1)
		{
			printk(", invalid IRQ (disabling)");
			cdirq = 0;
		}
		else printk(", IRQ %d", cdirq);

		mad16_cdsel |= dma_map[dmatype][cddma];

		if (cdtype < 0x08)
		{
			switch (cdport)
			{
				case 0x340:
					mad16_cdsel |= 0x00;
					break;
				case 0x330:
					mad16_cdsel |= 0x40;
					break;
				case 0x360:
					mad16_cdsel |= 0x80;
					break;
				case 0x320:
					mad16_cdsel |= 0xC0;
					break;
				default:
					printk(KERN_ERR "Unknown CDROM I/O base %d\n", cdport);
					return -EINVAL;
			}
		}
		mad16_cdsel |= irq_map[cdirq];
	}

	printk(".\n");

	cfg.io_base = io;
	cfg.irq = irq;
	cfg.dma = dma;
	cfg.dma2 = dma16;

	if (cfg.io_base == -1 || cfg.dma == -1 || cfg.irq == -1) {
		printk(KERN_ERR "I/O, DMA and irq are mandatory\n");
		return -EINVAL;
	}

	if (!request_region(MC0_PORT, 12, "mad16"))
		return -EBUSY;

	if (!probe_mad16(&cfg)) {
		release_region(MC0_PORT, 12);
		return -ENODEV;
	}

	cfg_mpu.io_base = mpu_io;
	cfg_mpu.irq = mpu_irq;

	found_mpu = probe_mad16_mpu(&cfg_mpu);

	if (joystick)
		mad16_register_gameport(0x201);

	return 0;
}

static void __exit cleanup_mad16(void)
{
	if (found_mpu)
		unload_mad16_mpu(&cfg_mpu);
	if (gameport) {
		/* the gameport was initialized so we must free it up */
		gameport_unregister_port(gameport);
		gameport = NULL;
		release_region(0x201, 1);
	}
	unload_mad16(&cfg);
	release_region(MC0_PORT, 12);
}

module_init(init_mad16);
module_exit(cleanup_mad16);

#ifndef MODULE
static int __init setup_mad16(char *str)
{
	/* io, irq */
	int ints[8];

	str = get_options(str, ARRAY_SIZE(ints), ints);

	io	 = ints[1];
	irq	 = ints[2];
	dma	 = ints[3];
	dma16	 = ints[4];
	mpu_io	 = ints[5];
	mpu_irq  = ints[6];
	joystick = ints[7];

	return 1;
}

__setup("mad16=", setup_mad16);
#endif
MODULE_LICENSE("GPL");
