/*
 *      linux/drivers/char/riscom.c  -- RISCom/8 multiport serial driver.
 *
 *      Copyright (C) 1994-1996  Dmitry Gorodchanin (pgmdsg@ibi.com)
 *
 *      This code is loosely based on the Linux serial driver, written by
 *      Linus Torvalds, Theodore T'so and others. The RISCom/8 card
 *      programming info was obtained from various drivers for other OSes
 *	(FreeBSD, ISC, etc), but no source code from those drivers were
 *	directly included in this driver.
 *
 *
 *      This program is free software; you can redistribute it and/or modify
 *      it under the terms of the GNU General Public License as published by
 *      the Free Software Foundation; either version 2 of the License, or
 *      (at your option) any later version.
 *
 *      This program is distributed in the hope that it will be useful,
 *      but WITHOUT ANY WARRANTY; without even the implied warranty of
 *      MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
 *      GNU General Public License for more details.
 *
 *      You should have received a copy of the GNU General Public License
 *      along with this program; if not, write to the Free Software
 *      Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
 *
 *	Revision 1.1
 *
 *	ChangeLog:
 *	Arnaldo Carvalho de Melo <acme@conectiva.com.br> - 27-Jun-2001
 *	- get rid of check_region and several cleanups
 */

#include <linux/module.h>

#include <linux/io.h>
#include <linux/kernel.h>
#include <linux/sched.h>
#include <linux/ioport.h>
#include <linux/interrupt.h>
#include <linux/errno.h>
#include <linux/tty.h>
#include <linux/mm.h>
#include <linux/serial.h>
#include <linux/fcntl.h>
#include <linux/major.h>
#include <linux/init.h>
#include <linux/delay.h>
#include <linux/tty_flip.h>
#include <linux/smp_lock.h>
#include <linux/spinlock.h>
#include <linux/device.h>

#include <linux/uaccess.h>

#include "riscom8.h"
#include "riscom8_reg.h"

/* Am I paranoid or not ? ;-) */
#define RISCOM_PARANOIA_CHECK

/*
 * Crazy InteliCom/8 boards sometimes have swapped CTS & DSR signals.
 * You can slightly speed up things by #undefing the following option,
 * if you are REALLY sure that your board is correct one.
 */

#define RISCOM_BRAIN_DAMAGED_CTS

/*
 * The following defines are mostly for testing purposes. But if you need
 * some nice reporting in your syslog, you can define them also.
 */
#undef RC_REPORT_FIFO
#undef RC_REPORT_OVERRUN


#define RISCOM_LEGAL_FLAGS \
	(ASYNC_HUP_NOTIFY   | ASYNC_SAK          | ASYNC_SPLIT_TERMIOS   | \
	 ASYNC_SPD_HI       | ASYNC_SPEED_VHI    | ASYNC_SESSION_LOCKOUT | \
	 ASYNC_PGRP_LOCKOUT | ASYNC_CALLOUT_NOHUP)

static struct tty_driver *riscom_driver;

static DEFINE_SPINLOCK(riscom_lock);

static struct riscom_board rc_board[RC_NBOARD] =  {
	{
		.base	= RC_IOBASE1,
	},
	{
		.base	= RC_IOBASE2,
	},
	{
		.base	= RC_IOBASE3,
	},
	{
		.base	= RC_IOBASE4,
	},
};

static struct riscom_port rc_port[RC_NBOARD * RC_NPORT];

/* RISCom/8 I/O ports addresses (without address translation) */
static unsigned short rc_ioport[] =  {
#if 1
	0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, 0x09, 0x0a, 0x0b, 0x0c,
#else
	0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, 0x09, 0x0a, 0x0b, 0x0c, 0x10,
	0x11, 0x12, 0x18, 0x28, 0x31, 0x32, 0x39, 0x3a, 0x40, 0x41, 0x61, 0x62,
	0x63, 0x64, 0x6b, 0x70, 0x71, 0x78, 0x7a, 0x7b, 0x7f, 0x100, 0x101
#endif
};
#define RC_NIOPORT	ARRAY_SIZE(rc_ioport)


static int rc_paranoia_check(struct riscom_port const *port,
				    char *name, const char *routine)
{
#ifdef RISCOM_PARANOIA_CHECK
	static const char badmagic[] = KERN_INFO
		"rc: Warning: bad riscom port magic number for device %s in %s\n";
	static const char badinfo[] = KERN_INFO
		"rc: Warning: null riscom port for device %s in %s\n";

	if (!port) {
		printk(badinfo, name, routine);
		return 1;
	}
	if (port->magic != RISCOM8_MAGIC) {
		printk(badmagic, name, routine);
		return 1;
	}
#endif
	return 0;
}

/*
 *
 *  Service functions for RISCom/8 driver.
 *
 */

/* Get board number from pointer */
static inline int board_No(struct riscom_board const *bp)
{
	return bp - rc_board;
}

/* Get port number from pointer */
static inline int port_No(struct riscom_port const *port)
{
	return RC_PORT(port - rc_port);
}

/* Get pointer to board from pointer to port */
static inline struct riscom_board *port_Board(struct riscom_port const *port)
{
	return &rc_board[RC_BOARD(port - rc_port)];
}

/* Input Byte from CL CD180 register */
static inline unsigned char rc_in(struct riscom_board const *bp,
							unsigned short reg)
{
	return inb(bp->base + RC_TO_ISA(reg));
}

/* Output Byte to CL CD180 register */
static inline void rc_out(struct riscom_board const *bp, unsigned short reg,
			  unsigned char val)
{
	outb(val, bp->base + RC_TO_ISA(reg));
}

/* Wait for Channel Command Register ready */
static void rc_wait_CCR(struct riscom_board const *bp)
{
	unsigned long delay;

	/* FIXME: need something more descriptive then 100000 :) */
	for (delay = 100000; delay; delay--)
		if (!rc_in(bp, CD180_CCR))
			return;

	printk(KERN_INFO "rc%d: Timeout waiting for CCR.\n", board_No(bp));
}

/*
 *  RISCom/8 probe functions.
 */

static int rc_request_io_range(struct riscom_board * const bp)
{
	int i;

	for (i = 0; i < RC_NIOPORT; i++)
		if (!request_region(RC_TO_ISA(rc_ioport[i]) + bp->base, 1,
				   "RISCom/8"))  {
			goto out_release;
		}
	return 0;
out_release:
	printk(KERN_INFO "rc%d: Skipping probe at 0x%03x. IO address in use.\n",
			 board_No(bp), bp->base);
	while (--i >= 0)
		release_region(RC_TO_ISA(rc_ioport[i]) + bp->base, 1);
	return 1;
}

static void rc_release_io_range(struct riscom_board * const bp)
{
	int i;

	for (i = 0; i < RC_NIOPORT; i++)
		release_region(RC_TO_ISA(rc_ioport[i]) + bp->base, 1);
}

/* Reset and setup CD180 chip */
static void __init rc_init_CD180(struct riscom_board const *bp)
{
	unsigned long flags;

	spin_lock_irqsave(&riscom_lock, flags);

	rc_out(bp, RC_CTOUT, 0);     	           /* Clear timeout        */
	rc_wait_CCR(bp);			   /* Wait for CCR ready   */
	rc_out(bp, CD180_CCR, CCR_HARDRESET);      /* Reset CD180 chip     */
	spin_unlock_irqrestore(&riscom_lock, flags);
	msleep(50);				   /* Delay 0.05 sec       */
	spin_lock_irqsave(&riscom_lock, flags);
	rc_out(bp, CD180_GIVR, RC_ID);             /* Set ID for this chip */
	rc_out(bp, CD180_GICR, 0);                 /* Clear all bits       */
	rc_out(bp, CD180_PILR1, RC_ACK_MINT);      /* Prio for modem intr  */
	rc_out(bp, CD180_PILR2, RC_ACK_TINT);      /* Prio for tx intr     */
	rc_out(bp, CD180_PILR3, RC_ACK_RINT);      /* Prio for rx intr	   */

	/* Setting up prescaler. We need 4 ticks per 1 ms */
	rc_out(bp, CD180_PPRH, (RC_OSCFREQ/(1000000/RISCOM_TPS)) >> 8);
	rc_out(bp, CD180_PPRL, (RC_OSCFREQ/(1000000/RISCOM_TPS)) & 0xff);

	spin_unlock_irqrestore(&riscom_lock, flags);
}

/* Main probing routine, also sets irq. */
static int __init rc_probe(struct riscom_board *bp)
{
	unsigned char val1, val2;
	int irqs = 0;
	int retries;

	bp->irq = 0;

	if (rc_request_io_range(bp))
		return 1;

	/* Are the I/O ports here ? */
	rc_out(bp, CD180_PPRL, 0x5a);
	outb(0xff, 0x80);
	val1 = rc_in(bp, CD180_PPRL);
	rc_out(bp, CD180_PPRL, 0xa5);
	outb(0x00, 0x80);
	val2 = rc_in(bp, CD180_PPRL);

	if ((val1 != 0x5a) || (val2 != 0xa5))  {
		printk(KERN_ERR "rc%d: RISCom/8 Board at 0x%03x not found.\n",
		       board_No(bp), bp->base);
		goto out_release;
	}

	/* It's time to find IRQ for this board */
	for (retries = 0; retries < 5 && irqs <= 0; retries++) {
		irqs = probe_irq_on();
		rc_init_CD180(bp);		 /* Reset CD180 chip	     */
		rc_out(bp, CD180_CAR, 2);	 /* Select port 2	     */
		rc_wait_CCR(bp);
		rc_out(bp, CD180_CCR, CCR_TXEN); /* Enable transmitter	     */
		rc_out(bp, CD180_IER, IER_TXRDY);/* Enable tx empty intr     */
		msleep(50);
		irqs = probe_irq_off(irqs);
		val1 = rc_in(bp, RC_BSR);	/* Get Board Status reg	     */
		val2 = rc_in(bp, RC_ACK_TINT);  /* ACK interrupt	     */
		rc_init_CD180(bp);	       	/* Reset CD180 again	     */

		if ((val1 & RC_BSR_TINT) || (val2 != (RC_ID | GIVR_IT_TX)))  {
			printk(KERN_ERR "rc%d: RISCom/8 Board at 0x%03x not "
					"found.\n", board_No(bp), bp->base);
			goto out_release;
		}
	}

	if (irqs <= 0)  {
		printk(KERN_ERR "rc%d: Can't find IRQ for RISCom/8 board "
				"at 0x%03x.\n", board_No(bp), bp->base);
		goto out_release;
	}
	bp->irq = irqs;
	bp->flags |= RC_BOARD_PRESENT;

	printk(KERN_INFO "rc%d: RISCom/8 Rev. %c board detected at "
			 "0x%03x, IRQ %d.\n",
	       board_No(bp),
	       (rc_in(bp, CD180_GFRCR) & 0x0f) + 'A',   /* Board revision */
	       bp->base, bp->irq);

	return 0;
out_release:
	rc_release_io_range(bp);
	return 1;
}

/*
 *
 *  Interrupt processing routines.
 *
 */

static struct riscom_port *rc_get_port(struct riscom_board const *bp,
					       unsigned char const *what)
{
	unsigned char channel;
	struct riscom_port *port;

	channel = rc_in(bp, CD180_GICR) >> GICR_CHAN_OFF;
	if (channel < CD180_NCH)  {
		port = &rc_port[board_No(bp) * RC_NPORT + channel];
		if (port->port.flags & ASYNC_INITIALIZED)
			return port;
	}
	printk(KERN_ERR "rc%d: %s interrupt from invalid port %d\n",
	       board_No(bp), what, channel);
	return NULL;
}

static void rc_receive_exc(struct riscom_board const *bp)
{
	struct riscom_port *port;
	struct tty_struct *tty;
	unsigned char status;
	unsigned char ch, flag;

	port = rc_get_port(bp, "Receive");
	if (port == NULL)
		return;

	tty = tty_port_tty_get(&port->port);

#ifdef RC_REPORT_OVERRUN
	status = rc_in(bp, CD180_RCSR);
	if (status & RCSR_OE)
		port->overrun++;
	status &= port->mark_mask;
#else
	status = rc_in(bp, CD180_RCSR) & port->mark_mask;
#endif
	ch = rc_in(bp, CD180_RDR);
	if (!status)
		goto out;
	if (status & RCSR_TOUT)  {
		printk(KERN_WARNING "rc%d: port %d: Receiver timeout. "
				    "Hardware problems ?\n",
		       board_No(bp), port_No(port));
		goto out;

	} else if (status & RCSR_BREAK)  {
		printk(KERN_INFO "rc%d: port %d: Handling break...\n",
		       board_No(bp), port_No(port));
		flag = TTY_BREAK;
		if (tty && (port->port.flags & ASYNC_SAK))
			do_SAK(tty);

	} else if (status & RCSR_PE)
		flag = TTY_PARITY;

	else if (status & RCSR_FE)
		flag = TTY_FRAME;

	else if (status & RCSR_OE)
		flag = TTY_OVERRUN;
	else
		flag = TTY_NORMAL;

	if (tty) {
		tty_insert_flip_char(tty, ch, flag);
		tty_flip_buffer_push(tty);
	}
out:
	tty_kref_put(tty);
}

static void rc_receive(struct riscom_board const *bp)
{
	struct riscom_port *port;
	struct tty_struct *tty;
	unsigned char count;

	port = rc_get_port(bp, "Receive");
	if (port == NULL)
		return;

	tty = tty_port_tty_get(&port->port);

	count = rc_in(bp, CD180_RDCR);

#ifdef RC_REPORT_FIFO
	port->hits[count > 8 ? 9 : count]++;
#endif

	while (count--)  {
		u8 ch = rc_in(bp, CD180_RDR);
		if (tty)
			tty_insert_flip_char(tty, ch, TTY_NORMAL);
	}
	if (tty) {
		tty_flip_buffer_push(tty);
		tty_kref_put(tty);
	}
}

static void rc_transmit(struct riscom_board const *bp)
{
	struct riscom_port *port;
	struct tty_struct *tty;
	unsigned char count;

	port = rc_get_port(bp, "Transmit");
	if (port == NULL)
		return;

	tty = tty_port_tty_get(&port->port);

	if (port->IER & IER_TXEMPTY) {
		/* FIFO drained */
		rc_out(bp, CD180_CAR, port_No(port));
		port->IER &= ~IER_TXEMPTY;
		rc_out(bp, CD180_IER, port->IER);
		goto out;
	}

	if ((port->xmit_cnt <= 0 && !port->break_length)
	    || (tty && (tty->stopped || tty->hw_stopped)))  {
		rc_out(bp, CD180_CAR, port_No(port));
		port->IER &= ~IER_TXRDY;
		rc_out(bp, CD180_IER, port->IER);
		goto out;
	}

	if (port->break_length)  {
		if (port->break_length > 0)  {
			if (port->COR2 & COR2_ETC)  {
				rc_out(bp, CD180_TDR, CD180_C_ESC);
				rc_out(bp, CD180_TDR, CD180_C_SBRK);
				port->COR2 &= ~COR2_ETC;
			}
			count = min_t(int, port->break_length, 0xff);
			rc_out(bp, CD180_TDR, CD180_C_ESC);
			rc_out(bp, CD180_TDR, CD180_C_DELAY);
			rc_out(bp, CD180_TDR, count);
			port->break_length -= count;
			if (port->break_length == 0)
				port->break_length--;
		} else  {
			rc_out(bp, CD180_TDR, CD180_C_ESC);
			rc_out(bp, CD180_TDR, CD180_C_EBRK);
			rc_out(bp, CD180_COR2, port->COR2);
			rc_wait_CCR(bp);
			rc_out(bp, CD180_CCR, CCR_CORCHG2);
			port->break_length = 0;
		}
		goto out;
	}

	count = CD180_NFIFO;
	do {
		rc_out(bp, CD180_TDR, port->port.xmit_buf[port->xmit_tail++]);
		port->xmit_tail = port->xmit_tail & (SERIAL_XMIT_SIZE-1);
		if (--port->xmit_cnt <= 0)
			break;
	} while (--count > 0);

	if (port->xmit_cnt <= 0)  {
		rc_out(bp, CD180_CAR, port_No(port));
		port->IER &= ~IER_TXRDY;
		rc_out(bp, CD180_IER, port->IER);
	}
	if (tty && port->xmit_cnt <= port->wakeup_chars)
		tty_wakeup(tty);
out:
	tty_kref_put(tty);
}

static void rc_check_modem(struct riscom_board const *bp)
{
	struct riscom_port *port;
	struct tty_struct *tty;
	unsigned char mcr;

	port = rc_get_port(bp, "Modem");
	if (port == NULL)
		return;

	tty = tty_port_tty_get(&port->port);

	mcr = rc_in(bp, CD180_MCR);
	if (mcr & MCR_CDCHG) {
		if (rc_in(bp, CD180_MSVR) & MSVR_CD)
			wake_up_interruptible(&port->port.open_wait);
		else if (tty)
			tty_hangup(tty);
	}

#ifdef RISCOM_BRAIN_DAMAGED_CTS
	if (mcr & MCR_CTSCHG)  {
		if (rc_in(bp, CD180_MSVR) & MSVR_CTS)  {
			port->IER |= IER_TXRDY;
			if (tty) {
				tty->hw_stopped = 0;
				if (port->xmit_cnt <= port->wakeup_chars)
					tty_wakeup(tty);
			}
		} else  {
			if (tty)
				tty->hw_stopped = 1;
			port->IER &= ~IER_TXRDY;
		}
		rc_out(bp, CD180_IER, port->IER);
	}
	if (mcr & MCR_DSRCHG)  {
		if (rc_in(bp, CD180_MSVR) & MSVR_DSR)  {
			port->IER |= IER_TXRDY;
			if (tty) {
				tty->hw_stopped = 0;
				if (port->xmit_cnt <= port->wakeup_chars)
					tty_wakeup(tty);
			}
		} else  {
			if (tty)
				tty->hw_stopped = 1;
			port->IER &= ~IER_TXRDY;
		}
		rc_out(bp, CD180_IER, port->IER);
	}
#endif /* RISCOM_BRAIN_DAMAGED_CTS */

	/* Clear change bits */
	rc_out(bp, CD180_MCR, 0);
	tty_kref_put(tty);
}

/* The main interrupt processing routine */
static irqreturn_t rc_interrupt(int dummy, void *dev_id)
{
	unsigned char status;
	unsigned char ack;
	struct riscom_board *bp = dev_id;
	unsigned long loop = 0;
	int handled = 0;

	if (!(bp->flags & RC_BOARD_ACTIVE))
		return IRQ_NONE;

	while ((++loop < 16) && ((status = ~(rc_in(bp, RC_BSR))) &
				 (RC_BSR_TOUT | RC_BSR_TINT |
				  RC_BSR_MINT | RC_BSR_RINT))) {
		handled = 1;
		if (status & RC_BSR_TOUT)
			printk(KERN_WARNING "rc%d: Got timeout. Hardware "
					    "error?\n", board_No(bp));
		else if (status & RC_BSR_RINT) {
			ack = rc_in(bp, RC_ACK_RINT);
			if (ack == (RC_ID | GIVR_IT_RCV))
				rc_receive(bp);
			else if (ack == (RC_ID | GIVR_IT_REXC))
				rc_receive_exc(bp);
			else
				printk(KERN_WARNING "rc%d: Bad receive ack "
						    "0x%02x.\n",
				       board_No(bp), ack);
		} else if (status & RC_BSR_TINT) {
			ack = rc_in(bp, RC_ACK_TINT);
			if (ack == (RC_ID | GIVR_IT_TX))
				rc_transmit(bp);
			else
				printk(KERN_WARNING "rc%d: Bad transmit ack "
						    "0x%02x.\n",
				       board_No(bp), ack);
		} else /* if (status & RC_BSR_MINT) */ {
			ack = rc_in(bp, RC_ACK_MINT);
			if (ack == (RC_ID | GIVR_IT_MODEM))
				rc_check_modem(bp);
			else
				printk(KERN_WARNING "rc%d: Bad modem ack "
						    "0x%02x.\n",
				       board_No(bp), ack);
		}
		rc_out(bp, CD180_EOIR, 0);   /* Mark end of interrupt */
		rc_out(bp, RC_CTOUT, 0);     /* Clear timeout flag    */
	}
	return IRQ_RETVAL(handled);
}

/*
 *  Routines for open & close processing.
 */

/* Called with disabled interrupts */
static int rc_setup_board(struct riscom_board *bp)
{
	int error;

	if (bp->flags & RC_BOARD_ACTIVE)
		return 0;

	error = request_irq(bp->irq, rc_interrupt, IRQF_DISABLED,
			    "RISCom/8", bp);
	if (error)
		return error;

	rc_out(bp, RC_CTOUT, 0);       		/* Just in case         */
	bp->DTR = ~0;
	rc_out(bp, RC_DTR, bp->DTR);	        /* Drop DTR on all ports */

	bp->flags |= RC_BOARD_ACTIVE;

	return 0;
}

/* Called with disabled interrupts */
static void rc_shutdown_board(struct riscom_board *bp)
{
	if (!(bp->flags & RC_BOARD_ACTIVE))
		return;

	bp->flags &= ~RC_BOARD_ACTIVE;

	free_irq(bp->irq, NULL);

	bp->DTR = ~0;
	rc_out(bp, RC_DTR, bp->DTR);	       /* Drop DTR on all ports */

}

/*
 * Setting up port characteristics.
 * Must be called with disabled interrupts
 */
static void rc_change_speed(struct tty_struct *tty, struct riscom_board *bp,
						struct riscom_port *port)
{
	unsigned long baud;
	long tmp;
	unsigned char cor1 = 0, cor3 = 0;
	unsigned char mcor1 = 0, mcor2 = 0;

	port->IER  = 0;
	port->COR2 = 0;
	port->MSVR = MSVR_RTS;

	baud = tty_get_baud_rate(tty);

	/* Select port on the board */
	rc_out(bp, CD180_CAR, port_No(port));

	if (!baud)  {
		/* Drop DTR & exit */
		bp->DTR |= (1u << port_No(port));
		rc_out(bp, RC_DTR, bp->DTR);
		return;
	} else  {
		/* Set DTR on */
		bp->DTR &= ~(1u << port_No(port));
		rc_out(bp, RC_DTR, bp->DTR);
	}

	/*
	 * Now we must calculate some speed depended things
	 */

	/* Set baud rate for port */
	tmp = (((RC_OSCFREQ + baud/2) / baud +
		CD180_TPC/2) / CD180_TPC);

	rc_out(bp, CD180_RBPRH, (tmp >> 8) & 0xff);
	rc_out(bp, CD180_TBPRH, (tmp >> 8) & 0xff);
	rc_out(bp, CD180_RBPRL, tmp & 0xff);
	rc_out(bp, CD180_TBPRL, tmp & 0xff);

	baud = (baud + 5) / 10;   /* Estimated CPS */

	/* Two timer ticks seems enough to wakeup something like SLIP driver */
	tmp = ((baud + HZ/2) / HZ) * 2 - CD180_NFIFO;
	port->wakeup_chars = (tmp < 0) ? 0 : ((tmp >= SERIAL_XMIT_SIZE) ?
					      SERIAL_XMIT_SIZE - 1 : tmp);

	/* Receiver timeout will be transmission time for 1.5 chars */
	tmp = (RISCOM_TPS + RISCOM_TPS/2 + baud/2) / baud;
	tmp = (tmp > 0xff) ? 0xff : tmp;
	rc_out(bp, CD180_RTPR, tmp);

	switch (C_CSIZE(tty)) {
	case CS5:
		cor1 |= COR1_5BITS;
		break;
	case CS6:
		cor1 |= COR1_6BITS;
		break;
	case CS7:
		cor1 |= COR1_7BITS;
		break;
	case CS8:
		cor1 |= COR1_8BITS;
		break;
	}
	if (C_CSTOPB(tty))
		cor1 |= COR1_2SB;

	cor1 |= COR1_IGNORE;
	if (C_PARENB(tty)) {
		cor1 |= COR1_NORMPAR;
		if (C_PARODD(tty))
			cor1 |= COR1_ODDP;
		if (I_INPCK(tty))
			cor1 &= ~COR1_IGNORE;
	}
	/* Set marking of some errors */
	port->mark_mask = RCSR_OE | RCSR_TOUT;
	if (I_INPCK(tty))
		port->mark_mask |= RCSR_FE | RCSR_PE;
	if (I_BRKINT(tty) || I_PARMRK(tty))
		port->mark_mask |= RCSR_BREAK;
	if (I_IGNPAR(tty))
		port->mark_mask &= ~(RCSR_FE | RCSR_PE);
	if (I_IGNBRK(tty)) {
		port->mark_mask &= ~RCSR_BREAK;
		if (I_IGNPAR(tty))
			/* Real raw mode. Ignore all */
			port->mark_mask &= ~RCSR_OE;
	}
	/* Enable Hardware Flow Control */
	if (C_CRTSCTS(tty))  {
#ifdef RISCOM_BRAIN_DAMAGED_CTS
		port->IER |= IER_DSR | IER_CTS;
		mcor1 |= MCOR1_DSRZD | MCOR1_CTSZD;
		mcor2 |= MCOR2_DSROD | MCOR2_CTSOD;
		tty->hw_stopped = !(rc_in(bp, CD180_MSVR) &
						(MSVR_CTS|MSVR_DSR));
#else
		port->COR2 |= COR2_CTSAE;
#endif
	}
	/* Enable Software Flow Control. FIXME: I'm not sure about this */
	/* Some people reported that it works, but I still doubt */
	if (I_IXON(tty))  {
		port->COR2 |= COR2_TXIBE;
		cor3 |= (COR3_FCT | COR3_SCDE);
		if (I_IXANY(tty))
			port->COR2 |= COR2_IXM;
		rc_out(bp, CD180_SCHR1, START_CHAR(tty));
		rc_out(bp, CD180_SCHR2, STOP_CHAR(tty));
		rc_out(bp, CD180_SCHR3, START_CHAR(tty));
		rc_out(bp, CD180_SCHR4, STOP_CHAR(tty));
	}
	if (!C_CLOCAL(tty))  {
		/* Enable CD check */
		port->IER |= IER_CD;
		mcor1 |= MCOR1_CDZD;
		mcor2 |= MCOR2_CDOD;
	}

	if (C_CREAD(tty))
		/* Enable receiver */
		port->IER |= IER_RXD;

	/* Set input FIFO size (1-8 bytes) */
	cor3 |= RISCOM_RXFIFO;
	/* Setting up CD180 channel registers */
	rc_out(bp, CD180_COR1, cor1);
	rc_out(bp, CD180_COR2, port->COR2);
	rc_out(bp, CD180_COR3, cor3);
	/* Make CD180 know about registers change */
	rc_wait_CCR(bp);
	rc_out(bp, CD180_CCR, CCR_CORCHG1 | CCR_CORCHG2 | CCR_CORCHG3);
	/* Setting up modem option registers */
	rc_out(bp, CD180_MCOR1, mcor1);
	rc_out(bp, CD180_MCOR2, mcor2);
	/* Enable CD180 transmitter & receiver */
	rc_wait_CCR(bp);
	rc_out(bp, CD180_CCR, CCR_TXEN | CCR_RXEN);
	/* Enable interrupts */
	rc_out(bp, CD180_IER, port->IER);
	/* And finally set RTS on */
	rc_out(bp, CD180_MSVR, port->MSVR);
}

/* Must be called with interrupts enabled */
static int rc_setup_port(struct tty_struct *tty, struct riscom_board *bp,
						struct riscom_port *port)
{
	unsigned long flags;

	if (port->port.flags & ASYNC_INITIALIZED)
		return 0;

	if (tty_port_alloc_xmit_buf(&port->port) < 0)
		return -ENOMEM;

	spin_lock_irqsave(&riscom_lock, flags);

	clear_bit(TTY_IO_ERROR, &tty->flags);
	if (port->port.count == 1)
		bp->count++;
	port->xmit_cnt = port->xmit_head = port->xmit_tail = 0;
	rc_change_speed(tty, bp, port);
	port->port.flags |= ASYNC_INITIALIZED;

	spin_unlock_irqrestore(&riscom_lock, flags);
	return 0;
}

/* Must be called with interrupts disabled */
static void rc_shutdown_port(struct tty_struct *tty,
			struct riscom_board *bp, struct riscom_port *port)
{
	if (!(port->port.flags & ASYNC_INITIALIZED))
		return;

#ifdef RC_REPORT_OVERRUN
	printk(KERN_INFO "rc%d: port %d: Total %ld overruns were detected.\n",
	       board_No(bp), port_No(port), port->overrun);
#endif
#ifdef RC_REPORT_FIFO
	{
		int i;

		printk(KERN_INFO "rc%d: port %d: FIFO hits [ ",
		       board_No(bp), port_No(port));
		for (i = 0; i < 10; i++)
			printk("%ld ", port->hits[i]);
		printk("].\n");
	}
#endif
	tty_port_free_xmit_buf(&port->port);
	if (C_HUPCL(tty)) {
		/* Drop DTR */
		bp->DTR |= (1u << port_No(port));
		rc_out(bp, RC_DTR, bp->DTR);
	}

	/* Select port */
	rc_out(bp, CD180_CAR, port_No(port));
	/* Reset port */
	rc_wait_CCR(bp);
	rc_out(bp, CD180_CCR, CCR_SOFTRESET);
	/* Disable all interrupts from this port */
	port->IER = 0;
	rc_out(bp, CD180_IER, port->IER);

	set_bit(TTY_IO_ERROR, &tty->flags);
	port->port.flags &= ~ASYNC_INITIALIZED;

	if (--bp->count < 0)  {
		printk(KERN_INFO "rc%d: rc_shutdown_port: "
				 "bad board count: %d\n",
		       board_No(bp), bp->count);
		bp->count = 0;
	}
	/*
	 * If this is the last opened port on the board
	 * shutdown whole board
	 */
	if (!bp->count)
		rc_shutdown_board(bp);
}

static int carrier_raised(struct tty_port *port)
{
	struct riscom_port *p = container_of(port, struct riscom_port, port);
	struct riscom_board *bp = port_Board(p);
	unsigned long flags;
	int CD;
	
	spin_lock_irqsave(&riscom_lock, flags);
	rc_out(bp, CD180_CAR, port_No(p));
	CD = rc_in(bp, CD180_MSVR) & MSVR_CD;
	rc_out(bp, CD180_MSVR, MSVR_RTS);
	bp->DTR &= ~(1u << port_No(p));
	rc_out(bp, RC_DTR, bp->DTR);
	spin_unlock_irqrestore(&riscom_lock, flags);
	return CD;
}

static int rc_open(struct tty_struct *tty, struct file *filp)
{
	int board;
	int error;
	struct riscom_port *port;
	struct riscom_board *bp;

	board = RC_BOARD(tty->index);
	if (board >= RC_NBOARD || !(rc_board[board].flags & RC_BOARD_PRESENT))
		return -ENODEV;

	bp = &rc_board[board];
	port = rc_port + board * RC_NPORT + RC_PORT(tty->index);
	if (rc_paranoia_check(port, tty->name, "rc_open"))
		return -ENODEV;

	error = rc_setup_board(bp);
	if (error)
		return error;

	port->port.count++;
	tty->driver_data = port;
	tty_port_tty_set(&port->port, tty);

	error = rc_setup_port(tty, bp, port);
	if (error == 0)
		error = tty_port_block_til_ready(&port->port, tty, filp);
	return error;
}

static void rc_flush_buffer(struct tty_struct *tty)
{
	struct riscom_port *port = tty->driver_data;
	unsigned long flags;

	if (rc_paranoia_check(port, tty->name, "rc_flush_buffer"))
		return;

	spin_lock_irqsave(&riscom_lock, flags);
	port->xmit_cnt = port->xmit_head = port->xmit_tail = 0;
	spin_unlock_irqrestore(&riscom_lock, flags);

	tty_wakeup(tty);
}

static void rc_close_port(struct tty_port *port)
{
	unsigned long flags;
	struct riscom_port *rp = container_of(port, struct riscom_port, port);
	struct riscom_board *bp = port_Board(rp);
	unsigned long timeout;
	
	/*
	 * At this point we stop accepting input.  To do this, we
	 * disable the receive line status interrupts, and tell the
	 * interrupt driver to stop checking the data ready bit in the
	 * line status register.
	 */

	spin_lock_irqsave(&riscom_lock, flags);
	rp->IER &= ~IER_RXD;
	if (port->flags & ASYNC_INITIALIZED) {
		rp->IER &= ~IER_TXRDY;
		rp->IER |= IER_TXEMPTY;
		rc_out(bp, CD180_CAR, port_No(rp));
		rc_out(bp, CD180_IER, rp->IER);
		/*
		 * Before we drop DTR, make sure the UART transmitter
		 * has completely drained; this is especially
		 * important if there is a transmit FIFO!
		 */
		timeout = jiffies + HZ;
		while (rp->IER & IER_TXEMPTY) {
			spin_unlock_irqrestore(&riscom_lock, flags);
			msleep_interruptible(jiffies_to_msecs(rp->timeout));
			spin_lock_irqsave(&riscom_lock, flags);
			if (time_after(jiffies, timeout))
				break;
		}
	}
	rc_shutdown_port(port->tty, bp, rp);
	spin_unlock_irqrestore(&riscom_lock, flags);
}

static void rc_close(struct tty_struct *tty, struct file *filp)
{
	struct riscom_port *port = tty->driver_data;

	if (!port || rc_paranoia_check(port, tty->name, "close"))
		return;
	tty_port_close(&port->port, tty, filp);
}

static int rc_write(struct tty_struct *tty,
		    const unsigned char *buf, int count)
{
	struct riscom_port *port = tty->driver_data;
	struct riscom_board *bp;
	int c, total = 0;
	unsigned long flags;

	if (rc_paranoia_check(port, tty->name, "rc_write"))
		return 0;

	bp = port_Board(port);

	while (1) {
		spin_lock_irqsave(&riscom_lock, flags);

		c = min_t(int, count, min(SERIAL_XMIT_SIZE - port->xmit_cnt - 1,
					  SERIAL_XMIT_SIZE - port->xmit_head));
		if (c <= 0)
			break;	/* lock continues to be held */

		memcpy(port->port.xmit_buf + port->xmit_head, buf, c);
		port->xmit_head = (port->xmit_head + c) & (SERIAL_XMIT_SIZE-1);
		port->xmit_cnt += c;

		spin_unlock_irqrestore(&riscom_lock, flags);

		buf += c;
		count -= c;
		total += c;
	}

	if (port->xmit_cnt && !tty->stopped && !tty->hw_stopped &&
	    !(port->IER & IER_TXRDY)) {
		port->IER |= IER_TXRDY;
		rc_out(bp, CD180_CAR, port_No(port));
		rc_out(bp, CD180_IER, port->IER);
	}

	spin_unlock_irqrestore(&riscom_lock, flags);

	return total;
}

static int rc_put_char(struct tty_struct *tty, unsigned char ch)
{
	struct riscom_port *port = tty->driver_data;
	unsigned long flags;
	int ret = 0;

	if (rc_paranoia_check(port, tty->name, "rc_put_char"))
		return 0;

	spin_lock_irqsave(&riscom_lock, flags);

	if (port->xmit_cnt >= SERIAL_XMIT_SIZE - 1)
		goto out;

	port->port.xmit_buf[port->xmit_head++] = ch;
	port->xmit_head &= SERIAL_XMIT_SIZE - 1;
	port->xmit_cnt++;
	ret = 1;

out:
	spin_unlock_irqrestore(&riscom_lock, flags);
	return ret;
}

static void rc_flush_chars(struct tty_struct *tty)
{
	struct riscom_port *port = tty->driver_data;
	unsigned long flags;

	if (rc_paranoia_check(port, tty->name, "rc_flush_chars"))
		return;

	if (port->xmit_cnt <= 0 || tty->stopped || tty->hw_stopped)
		return;

	spin_lock_irqsave(&riscom_lock, flags);

	port->IER |= IER_TXRDY;
	rc_out(port_Board(port), CD180_CAR, port_No(port));
	rc_out(port_Board(port), CD180_IER, port->IER);

	spin_unlock_irqrestore(&riscom_lock, flags);
}

static int rc_write_room(struct tty_struct *tty)
{
	struct riscom_port *port = tty->driver_data;
	int	ret;

	if (rc_paranoia_check(port, tty->name, "rc_write_room"))
		return 0;

	ret = SERIAL_XMIT_SIZE - port->xmit_cnt - 1;
	if (ret < 0)
		ret = 0;
	return ret;
}

static int rc_chars_in_buffer(struct tty_struct *tty)
{
	struct riscom_port *port = tty->driver_data;

	if (rc_paranoia_check(port, tty->name, "rc_chars_in_buffer"))
		return 0;

	return port->xmit_cnt;
}

static int rc_tiocmget(struct tty_struct *tty, struct file *file)
{
	struct riscom_port *port = tty->driver_data;
	struct riscom_board *bp;
	unsigned char status;
	unsigned int result;
	unsigned long flags;

	if (rc_paranoia_check(port, tty->name, __func__))
		return -ENODEV;

	bp = port_Board(port);

	spin_lock_irqsave(&riscom_lock, flags);

	rc_out(bp, CD180_CAR, port_No(port));
	status = rc_in(bp, CD180_MSVR);
	result = rc_in(bp, RC_RI) & (1u << port_No(port)) ? 0 : TIOCM_RNG;

	spin_unlock_irqrestore(&riscom_lock, flags);

	result |= ((status & MSVR_RTS) ? TIOCM_RTS : 0)
		| ((status & MSVR_DTR) ? TIOCM_DTR : 0)
		| ((status & MSVR_CD)  ? TIOCM_CAR : 0)
		| ((status & MSVR_DSR) ? TIOCM_DSR : 0)
		| ((status & MSVR_CTS) ? TIOCM_CTS : 0);
	return result;
}

static int rc_tiocmset(struct tty_struct *tty, struct file *file,
		       unsigned int set, unsigned int clear)
{
	struct riscom_port *port = tty->driver_data;
	unsigned long flags;
	struct riscom_board *bp;

	if (rc_paranoia_check(port, tty->name, __func__))
		return -ENODEV;

	bp = port_Board(port);

	spin_lock_irqsave(&riscom_lock, flags);

	if (set & TIOCM_RTS)
		port->MSVR |= MSVR_RTS;
	if (set & TIOCM_DTR)
		bp->DTR &= ~(1u << port_No(port));

	if (clear & TIOCM_RTS)
		port->MSVR &= ~MSVR_RTS;
	if (clear & TIOCM_DTR)
		bp->DTR |= (1u << port_No(port));

	rc_out(bp, CD180_CAR, port_No(port));
	rc_out(bp, CD180_MSVR, port->MSVR);
	rc_out(bp, RC_DTR, bp->DTR);

	spin_unlock_irqrestore(&riscom_lock, flags);

	return 0;
}

static int rc_send_break(struct tty_struct *tty, int length)
{
	struct riscom_port *port = tty->driver_data;
	struct riscom_board *bp = port_Board(port);
	unsigned long flags;

	if (length == 0 || length == -1)
		return -EOPNOTSUPP;

	spin_lock_irqsave(&riscom_lock, flags);

	port->break_length = RISCOM_TPS / HZ * length;
	port->COR2 |= COR2_ETC;
	port->IER  |= IER_TXRDY;
	rc_out(bp, CD180_CAR, port_No(port));
	rc_out(bp, CD180_COR2, port->COR2);
	rc_out(bp, CD180_IER, port->IER);
	rc_wait_CCR(bp);
	rc_out(bp, CD180_CCR, CCR_CORCHG2);
	rc_wait_CCR(bp);

	spin_unlock_irqrestore(&riscom_lock, flags);
	return 0;
}

static int rc_set_serial_info(struct tty_struct *tty, struct riscom_port *port,
				     struct serial_struct __user *newinfo)
{
	struct serial_struct tmp;
	struct riscom_board *bp = port_Board(port);
	int change_speed;

	if (copy_from_user(&tmp, newinfo, sizeof(tmp)))
		return -EFAULT;

	change_speed = ((port->port.flags & ASYNC_SPD_MASK) !=
			(tmp.flags & ASYNC_SPD_MASK));

	if (!capable(CAP_SYS_ADMIN)) {
		if ((tmp.close_delay != port->port.close_delay) ||
		    (tmp.closing_wait != port->port.closing_wait) ||
		    ((tmp.flags & ~ASYNC_USR_MASK) !=
		     (port->port.flags & ~ASYNC_USR_MASK)))
			return -EPERM;
		port->port.flags = ((port->port.flags & ~ASYNC_USR_MASK) |
			       (tmp.flags & ASYNC_USR_MASK));
	} else  {
		port->port.flags = ((port->port.flags & ~ASYNC_FLAGS) |
			       (tmp.flags & ASYNC_FLAGS));
		port->port.close_delay = tmp.close_delay;
		port->port.closing_wait = tmp.closing_wait;
	}
	if (change_speed)  {
		unsigned long flags;

		spin_lock_irqsave(&riscom_lock, flags);
		rc_change_speed(tty, bp, port);
		spin_unlock_irqrestore(&riscom_lock, flags);
	}
	return 0;
}

static int rc_get_serial_info(struct riscom_port *port,
				     struct serial_struct __user *retinfo)
{
	struct serial_struct tmp;
	struct riscom_board *bp = port_Board(port);

	memset(&tmp, 0, sizeof(tmp));
	tmp.type = PORT_CIRRUS;
	tmp.line = port - rc_port;
	tmp.port = bp->base;
	tmp.irq  = bp->irq;
	tmp.flags = port->port.flags;
	tmp.baud_base = (RC_OSCFREQ + CD180_TPC/2) / CD180_TPC;
	tmp.close_delay = port->port.close_delay * HZ/100;
	tmp.closing_wait = port->port.closing_wait * HZ/100;
	tmp.xmit_fifo_size = CD180_NFIFO;
	return copy_to_user(retinfo, &tmp, sizeof(tmp)) ? -EFAULT : 0;
}

static int rc_ioctl(struct tty_struct *tty, struct file *filp,
		    unsigned int cmd, unsigned long arg)
{
	struct riscom_port *port = tty->driver_data;
	void __user *argp = (void __user *)arg;
	int retval;

	if (rc_paranoia_check(port, tty->name, "rc_ioctl"))
		return -ENODEV;

	switch (cmd) {
	case TIOCGSERIAL:
		lock_kernel();
		retval = rc_get_serial_info(port, argp);
		unlock_kernel();
		break;
	case TIOCSSERIAL:
		lock_kernel();
		retval = rc_set_serial_info(tty, port, argp);
		unlock_kernel();
		break;
	default:
		retval = -ENOIOCTLCMD;
	}
	return retval;
}

static void rc_throttle(struct tty_struct *tty)
{
	struct riscom_port *port = tty->driver_data;
	struct riscom_board *bp;
	unsigned long flags;

	if (rc_paranoia_check(port, tty->name, "rc_throttle"))
		return;
	bp = port_Board(port);

	spin_lock_irqsave(&riscom_lock, flags);
	port->MSVR &= ~MSVR_RTS;
	rc_out(bp, CD180_CAR, port_No(port));
	if (I_IXOFF(tty)) {
		rc_wait_CCR(bp);
		rc_out(bp, CD180_CCR, CCR_SSCH2);
		rc_wait_CCR(bp);
	}
	rc_out(bp, CD180_MSVR, port->MSVR);
	spin_unlock_irqrestore(&riscom_lock, flags);
}

static void rc_unthrottle(struct tty_struct *tty)
{
	struct riscom_port *port = tty->driver_data;
	struct riscom_board *bp;
	unsigned long flags;

	if (rc_paranoia_check(port, tty->name, "rc_unthrottle"))
		return;
	bp = port_Board(port);

	spin_lock_irqsave(&riscom_lock, flags);
	port->MSVR |= MSVR_RTS;
	rc_out(bp, CD180_CAR, port_No(port));
	if (I_IXOFF(tty))  {
		rc_wait_CCR(bp);
		rc_out(bp, CD180_CCR, CCR_SSCH1);
		rc_wait_CCR(bp);
	}
	rc_out(bp, CD180_MSVR, port->MSVR);
	spin_unlock_irqrestore(&riscom_lock, flags);
}

static void rc_stop(struct tty_struct *tty)
{
	struct riscom_port *port = tty->driver_data;
	struct riscom_board *bp;
	unsigned long flags;

	if (rc_paranoia_check(port, tty->name, "rc_stop"))
		return;

	bp = port_Board(port);

	spin_lock_irqsave(&riscom_lock, flags);
	port->IER &= ~IER_TXRDY;
	rc_out(bp, CD180_CAR, port_No(port));
	rc_out(bp, CD180_IER, port->IER);
	spin_unlock_irqrestore(&riscom_lock, flags);
}

static void rc_start(struct tty_struct *tty)
{
	struct riscom_port *port = tty->driver_data;
	struct riscom_board *bp;
	unsigned long flags;

	if (rc_paranoia_check(port, tty->name, "rc_start"))
		return;

	bp = port_Board(port);

	spin_lock_irqsave(&riscom_lock, flags);

	if (port->xmit_cnt && port->port.xmit_buf && !(port->IER & IER_TXRDY)) {
		port->IER |= IER_TXRDY;
		rc_out(bp, CD180_CAR, port_No(port));
		rc_out(bp, CD180_IER, port->IER);
	}
	spin_unlock_irqrestore(&riscom_lock, flags);
}

static void rc_hangup(struct tty_struct *tty)
{
	struct riscom_port *port = tty->driver_data;

	if (rc_paranoia_check(port, tty->name, "rc_hangup"))
		return;

	rc_shutdown_port(tty, port_Board(port), port);
	tty_port_hangup(&port->port);
}

static void rc_set_termios(struct tty_struct *tty,
					struct ktermios *old_termios)
{
	struct riscom_port *port = tty->driver_data;
	unsigned long flags;

	if (rc_paranoia_check(port, tty->name, "rc_set_termios"))
		return;

	spin_lock_irqsave(&riscom_lock, flags);
	rc_change_speed(tty, port_Board(port), port);
	spin_unlock_irqrestore(&riscom_lock, flags);

	if ((old_termios->c_cflag & CRTSCTS) &&
	    !(tty->termios->c_cflag & CRTSCTS)) {
		tty->hw_stopped = 0;
		rc_start(tty);
	}
}

static const struct tty_operations riscom_ops = {
	.open  = rc_open,
	.close = rc_close,
	.write = rc_write,
	.put_char = rc_put_char,
	.flush_chars = rc_flush_chars,
	.write_room = rc_write_room,
	.chars_in_buffer = rc_chars_in_buffer,
	.flush_buffer = rc_flush_buffer,
	.ioctl = rc_ioctl,
	.throttle = rc_throttle,
	.unthrottle = rc_unthrottle,
	.set_termios = rc_set_termios,
	.stop = rc_stop,
	.start = rc_start,
	.hangup = rc_hangup,
	.tiocmget = rc_tiocmget,
	.tiocmset = rc_tiocmset,
	.break_ctl = rc_send_break,
};

static const struct tty_port_operations riscom_port_ops = {
	.carrier_raised = carrier_raised,
	.shutdown = rc_close_port,
};


static int __init rc_init_drivers(void)
{
	int error;
	int i;

	riscom_driver = alloc_tty_driver(RC_NBOARD * RC_NPORT);
	if (!riscom_driver)
		return -ENOMEM;

	riscom_driver->owner = THIS_MODULE;
	riscom_driver->name = "ttyL";
	riscom_driver->major = RISCOM8_NORMAL_MAJOR;
	riscom_driver->type = TTY_DRIVER_TYPE_SERIAL;
	riscom_driver->subtype = SERIAL_TYPE_NORMAL;
	riscom_driver->init_termios = tty_std_termios;
	riscom_driver->init_termios.c_cflag =
		B9600 | CS8 | CREAD | HUPCL | CLOCAL;
	riscom_driver->init_termios.c_ispeed = 9600;
	riscom_driver->init_termios.c_ospeed = 9600;
	riscom_driver->flags = TTY_DRIVER_REAL_RAW | TTY_DRIVER_HARDWARE_BREAK;
	tty_set_operations(riscom_driver, &riscom_ops);
	error = tty_register_driver(riscom_driver);
	if (error != 0) {
		put_tty_driver(riscom_driver);
		printk(KERN_ERR "rc: Couldn't register RISCom/8 driver, "
				"error = %d\n", error);
		return 1;
	}
	memset(rc_port, 0, sizeof(rc_port));
	for (i = 0; i < RC_NPORT * RC_NBOARD; i++)  {
		tty_port_init(&rc_port[i].port);
		rc_port[i].port.ops = &riscom_port_ops;
		rc_port[i].magic = RISCOM8_MAGIC;
	}
	return 0;
}

static void rc_release_drivers(void)
{
	tty_unregister_driver(riscom_driver);
	put_tty_driver(riscom_driver);
}

#ifndef MODULE
/*
 * Called at boot time.
 *
 * You can specify IO base for up to RC_NBOARD cards,
 * using line "riscom8=0xiobase1,0xiobase2,.." at LILO prompt.
 * Note that there will be no probing at default
 * addresses in this case.
 *
 */
static int __init riscom8_setup(char *str)
{
	int ints[RC_NBOARD];
	int i;

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

	for (i = 0; i < RC_NBOARD; i++) {
		if (i < ints[0])
			rc_board[i].base = ints[i+1];
		else
			rc_board[i].base = 0;
	}
	return 1;
}

__setup("riscom8=", riscom8_setup);
#endif

static char banner[] __initdata =
	KERN_INFO "rc: SDL RISCom/8 card driver v1.1, (c) D.Gorodchanin "
		  "1994-1996.\n";
static char no_boards_msg[] __initdata =
	KERN_INFO "rc: No RISCom/8 boards detected.\n";

/*
 * This routine must be called by kernel at boot time
 */
static int __init riscom8_init(void)
{
	int i;
	int found = 0;

	printk(banner);

	if (rc_init_drivers())
		return -EIO;

	for (i = 0; i < RC_NBOARD; i++)
		if (rc_board[i].base && !rc_probe(&rc_board[i]))
			found++;
	if (!found)  {
		rc_release_drivers();
		printk(no_boards_msg);
		return -EIO;
	}
	return 0;
}

#ifdef MODULE
static int iobase;
static int iobase1;
static int iobase2;
static int iobase3;
module_param(iobase, int, 0);
module_param(iobase1, int, 0);
module_param(iobase2, int, 0);
module_param(iobase3, int, 0);

MODULE_LICENSE("GPL");
MODULE_ALIAS_CHARDEV_MAJOR(RISCOM8_NORMAL_MAJOR);
#endif /* MODULE */

/*
 * You can setup up to 4 boards (current value of RC_NBOARD)
 * by specifying "iobase=0xXXX iobase1=0xXXX ..." as insmod parameter.
 *
 */
static int __init riscom8_init_module(void)
{
#ifdef MODULE
	int i;

	if (iobase || iobase1 || iobase2 || iobase3) {
		for (i = 0; i < RC_NBOARD; i++)
			rc_board[i].base = 0;
	}

	if (iobase)
		rc_board[0].base = iobase;
	if (iobase1)
		rc_board[1].base = iobase1;
	if (iobase2)
		rc_board[2].base = iobase2;
	if (iobase3)
		rc_board[3].base = iobase3;
#endif /* MODULE */

	return riscom8_init();
}

static void __exit riscom8_exit_module(void)
{
	int i;

	rc_release_drivers();
	for (i = 0; i < RC_NBOARD; i++)
		if (rc_board[i].flags & RC_BOARD_PRESENT)
			rc_release_io_range(&rc_board[i]);

}

module_init(riscom8_init_module);
module_exit(riscom8_exit_module);
