/* suncore.c
 *
 * Common SUN serial routines.  Based entirely
 * upon drivers/sbus/char/sunserial.c which is:
 *
 * Copyright (C) 1997  Eddie C. Dost  (ecd@skynet.be)
 *
 * Adaptation to new UART layer is:
 *
 * Copyright (C) 2002 David S. Miller (davem@redhat.com)
 */

#include <linux/module.h>
#include <linux/kernel.h>
#include <linux/console.h>
#include <linux/tty.h>
#include <linux/errno.h>
#include <linux/string.h>
#include <linux/serial_core.h>
#include <linux/init.h>

#include <asm/prom.h>

#include "suncore.h"

int sunserial_current_minor = 64;

EXPORT_SYMBOL(sunserial_current_minor);

int sunserial_console_match(struct console *con, struct device_node *dp,
			    struct uart_driver *drv, int line)
{
	int off;

	if (!con || of_console_device != dp)
		return 0;

	off = 0;
	if (of_console_options &&
	    *of_console_options == 'b')
		off = 1;

	if ((line & 1) != off)
		return 0;

	con->index = line;
	drv->cons = con;
	add_preferred_console(con->name, line, NULL);

	return 1;
}
EXPORT_SYMBOL(sunserial_console_match);

void
sunserial_console_termios(struct console *con)
{
	struct device_node *dp;
	const char *od, *mode, *s;
	char mode_prop[] = "ttyX-mode";
	int baud, bits, stop, cflag;
	char parity;

	dp = of_find_node_by_path("/options");
	od = of_get_property(dp, "output-device", NULL);
	if (!strcmp(od, "rsc")) {
		mode = of_get_property(of_console_device,
				       "ssp-console-modes", NULL);
		if (!mode)
			mode = "115200,8,n,1,-";
	} else {
		char c;

		c = 'a';
		if (of_console_options)
			c = *of_console_options;

		mode_prop[3] = c;

		mode = of_get_property(dp, mode_prop, NULL);
		if (!mode)
			mode = "9600,8,n,1,-";
	}

	cflag = CREAD | HUPCL | CLOCAL;

	s = mode;
	baud = simple_strtoul(s, NULL, 0);
	s = strchr(s, ',');
	bits = simple_strtoul(++s, NULL, 0);
	s = strchr(s, ',');
	parity = *(++s);
	s = strchr(s, ',');
	stop = simple_strtoul(++s, NULL, 0);
	s = strchr(s, ',');
	/* XXX handshake is not handled here. */

	switch (baud) {
		case 150: cflag |= B150; break;
		case 300: cflag |= B300; break;
		case 600: cflag |= B600; break;
		case 1200: cflag |= B1200; break;
		case 2400: cflag |= B2400; break;
		case 4800: cflag |= B4800; break;
		case 9600: cflag |= B9600; break;
		case 19200: cflag |= B19200; break;
		case 38400: cflag |= B38400; break;
		case 57600: cflag |= B57600; break;
		case 115200: cflag |= B115200; break;
		case 230400: cflag |= B230400; break;
		case 460800: cflag |= B460800; break;
		default: baud = 9600; cflag |= B9600; break;
	}

	switch (bits) {
		case 5: cflag |= CS5; break;
		case 6: cflag |= CS6; break;
		case 7: cflag |= CS7; break;
		case 8: cflag |= CS8; break;
		default: cflag |= CS8; break;
	}

	switch (parity) {
		case 'o': cflag |= (PARENB | PARODD); break;
		case 'e': cflag |= PARENB; break;
		case 'n': default: break;
	}

	switch (stop) {
		case 2: cflag |= CSTOPB; break;
		case 1: default: break;
	}

	con->cflag = cflag;
}

EXPORT_SYMBOL(sunserial_console_termios);

/* Sun serial MOUSE auto baud rate detection.  */
static struct mouse_baud_cflag {
	int baud;
	unsigned int cflag;
} mouse_baud_table[] = {
	{ 1200, B1200 },
	{ 2400, B2400 },
	{ 4800, B4800 },
	{ 9600, B9600 },
	{ -1, ~0 },
	{ -1, ~0 },
};

unsigned int suncore_mouse_baud_cflag_next(unsigned int cflag, int *new_baud)
{
	int i;

	for (i = 0; mouse_baud_table[i].baud != -1; i++)
		if (mouse_baud_table[i].cflag == (cflag & CBAUD))
			break;

	i += 1;
	if (mouse_baud_table[i].baud == -1)
		i = 0;

	*new_baud = mouse_baud_table[i].baud;
	return mouse_baud_table[i].cflag;
}

EXPORT_SYMBOL(suncore_mouse_baud_cflag_next);

/* Basically, when the baud rate is wrong the mouse spits out
 * breaks to us.
 */
int suncore_mouse_baud_detection(unsigned char ch, int is_break)
{
	static int mouse_got_break = 0;
	static int ctr = 0;

	if (is_break) {
		/* Let a few normal bytes go by before we jump the gun
		 * and say we need to try another baud rate.
		 */
		if (mouse_got_break && ctr < 8)
			return 1;

		/* Ok, we need to try another baud. */
		ctr = 0;
		mouse_got_break = 1;
		return 2;
	}
	if (mouse_got_break) {
		ctr++;
		if (ch == 0x87) {
			/* Correct baud rate determined. */
			mouse_got_break = 0;
		}
		return 1;
	}
	return 0;
}

EXPORT_SYMBOL(suncore_mouse_baud_detection);

static int __init suncore_init(void)
{
	return 0;
}

static void __exit suncore_exit(void)
{
}

module_init(suncore_init);
module_exit(suncore_exit);

MODULE_AUTHOR("Eddie C. Dost, David S. Miller");
MODULE_DESCRIPTION("Sun serial common layer");
MODULE_LICENSE("GPL");
