/*
 * Ours Technology Inc. OTi-6858 USB to serial adapter driver.
 *
 * Copyleft  (C) 2007 Kees Lemmens (adapted for kernel 2.6.20)
 * Copyright (C) 2006 Tomasz Michal Lukaszewski (FIXME: add e-mail)
 * Copyright (C) 2001-2004 Greg Kroah-Hartman (greg@kroah.com)
 * Copyright (C) 2003 IBM Corp.
 *
 * Many thanks to the authors of pl2303 driver: all functions in this file
 * are heavily based on pl2303 code, buffering code is a 1-to-1 copy.
 *
 * Warning! You use this driver on your own risk! The only official
 * description of this device I have is datasheet from manufacturer,
 * and it doesn't contain almost any information needed to write a driver.
 * Almost all knowlegde used while writing this driver was gathered by:
 *  - analyzing traffic between device and the M$ Windows 2000 driver,
 *  - trying different bit combinations and checking pin states
 *    with a voltmeter,
 *  - receiving malformed frames and producing buffer overflows
 *    to learn how errors are reported,
 * So, THIS CODE CAN DESTROY OTi-6858 AND ANY OTHER DEVICES, THAT ARE
 * CONNECTED TO IT!
 *
 * 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.
 *
 * See Documentation/usb/usb-serial.txt for more information on using this driver
 *
 * TODO:
 *  - implement correct flushing for ioctls and oti6858_close()
 *  - check how errors (rx overflow, parity error, framing error) are reported
 *  - implement oti6858_break_ctl()
 *  - implement more ioctls
 *  - test/implement flow control
 *  - allow setting custom baud rates
 */

#include <linux/kernel.h>
#include <linux/errno.h>
#include <linux/init.h>
#include <linux/slab.h>
#include <linux/tty.h>
#include <linux/tty_driver.h>
#include <linux/tty_flip.h>
#include <linux/serial.h>
#include <linux/module.h>
#include <linux/moduleparam.h>
#include <linux/spinlock.h>
#include <linux/usb.h>
#include <linux/usb/serial.h>
#include <asm/uaccess.h>
#include "oti6858.h"

#define OTI6858_DESCRIPTION \
	"Ours Technology Inc. OTi-6858 USB to serial adapter driver"
#define OTI6858_AUTHOR "Tomasz Michal Lukaszewski <FIXME@FIXME>"
#define OTI6858_VERSION "0.1"

static struct usb_device_id id_table [] = {
	{ USB_DEVICE(OTI6858_VENDOR_ID, OTI6858_PRODUCT_ID) },
	{ }
};

MODULE_DEVICE_TABLE(usb, id_table);

static struct usb_driver oti6858_driver = {
	.name =		"oti6858",
	.probe =	usb_serial_probe,
	.disconnect =	usb_serial_disconnect,
	.id_table =	id_table,
	.no_dynamic_id = 	1,
};

static int debug;


/* buffering code, copied from pl2303 driver */
#define PL2303_BUF_SIZE		1024
#define PL2303_TMP_BUF_SIZE	1024

struct oti6858_buf {
	unsigned int	buf_size;
	char		*buf_buf;
	char		*buf_get;
	char		*buf_put;
};

/* requests */
#define	OTI6858_REQ_GET_STATUS		(USB_DIR_IN | USB_TYPE_VENDOR | 0x00)
#define	OTI6858_REQ_T_GET_STATUS	0x01

#define	OTI6858_REQ_SET_LINE		(USB_DIR_OUT | USB_TYPE_VENDOR | 0x00)
#define	OTI6858_REQ_T_SET_LINE		0x00

#define	OTI6858_REQ_CHECK_TXBUFF	(USB_DIR_IN | USB_TYPE_VENDOR | 0x01)
#define	OTI6858_REQ_T_CHECK_TXBUFF	0x00

/* format of the control packet */
struct oti6858_control_pkt {
	u16	divisor;	/* baud rate = 96000000 / (16 * divisor), LE */
#define OTI6858_MAX_BAUD_RATE	3000000
	u8	frame_fmt;
#define FMT_STOP_BITS_MASK	0xc0
#define FMT_STOP_BITS_1		0x00
#define FMT_STOP_BITS_2		0x40	/* 1.5 stop bits if FMT_DATA_BITS_5 */
#define FMT_PARITY_MASK		0x38
#define FMT_PARITY_NONE		0x00
#define FMT_PARITY_ODD		0x08
#define FMT_PARITY_EVEN		0x18
#define FMT_PARITY_MARK		0x28
#define FMT_PARITY_SPACE	0x38
#define FMT_DATA_BITS_MASK	0x03
#define FMT_DATA_BITS_5		0x00
#define FMT_DATA_BITS_6		0x01
#define FMT_DATA_BITS_7		0x02
#define FMT_DATA_BITS_8		0x03
	u8	something;	/* always equals 0x43 */
	u8	control;	/* settings of flow control lines */
#define CONTROL_MASK		0x0c
#define CONTROL_DTR_HIGH	0x08
#define CONTROL_RTS_HIGH	0x04
	u8	tx_status;
#define	TX_BUFFER_EMPTIED	0x09
	u8	pin_state;
#define PIN_MASK		0x3f
#define PIN_RTS			0x20	/* output pin */
#define PIN_CTS			0x10	/* input pin, active low */
#define PIN_DSR			0x08	/* input pin, active low */
#define PIN_DTR			0x04	/* output pin */
#define PIN_RI			0x02	/* input pin, active low */
#define PIN_DCD			0x01	/* input pin, active low */
	u8	rx_bytes_avail;		/* number of bytes in rx buffer */;
};

#define OTI6858_CTRL_PKT_SIZE	sizeof(struct oti6858_control_pkt)
#define OTI6858_CTRL_EQUALS_PENDING(a, priv) \
	(    ((a)->divisor == (priv)->pending_setup.divisor) \
	  && ((a)->control == (priv)->pending_setup.control) \
	  && ((a)->frame_fmt == (priv)->pending_setup.frame_fmt) )

/* function prototypes */
static int oti6858_open(struct usb_serial_port *port, struct file *filp);
static void oti6858_close(struct usb_serial_port *port, struct file *filp);
static void oti6858_set_termios(struct usb_serial_port *port,
				struct ktermios *old);
static int oti6858_ioctl(struct usb_serial_port *port, struct file *file,
			unsigned int cmd, unsigned long arg);
static void oti6858_read_int_callback(struct urb *urb);
static void oti6858_read_bulk_callback(struct urb *urb);
static void oti6858_write_bulk_callback(struct urb *urb);
static int oti6858_write(struct usb_serial_port *port,
			const unsigned char *buf, int count);
static int oti6858_write_room(struct usb_serial_port *port);
static void oti6858_break_ctl(struct usb_serial_port *port, int break_state);
static int oti6858_chars_in_buffer(struct usb_serial_port *port);
static int oti6858_tiocmget(struct usb_serial_port *port, struct file *file);
static int oti6858_tiocmset(struct usb_serial_port *port, struct file *file,
				unsigned int set, unsigned int clear);
static int oti6858_startup(struct usb_serial *serial);
static void oti6858_shutdown(struct usb_serial *serial);

/* functions operating on buffers */
static struct oti6858_buf *oti6858_buf_alloc(unsigned int size);
static void oti6858_buf_free(struct oti6858_buf *pb);
static void oti6858_buf_clear(struct oti6858_buf *pb);
static unsigned int oti6858_buf_data_avail(struct oti6858_buf *pb);
static unsigned int oti6858_buf_space_avail(struct oti6858_buf *pb);
static unsigned int oti6858_buf_put(struct oti6858_buf *pb, const char *buf,
					unsigned int count);
static unsigned int oti6858_buf_get(struct oti6858_buf *pb, char *buf,
					unsigned int count);


/* device info */
static struct usb_serial_driver oti6858_device = {
	.driver = {
		.owner =	THIS_MODULE,
		.name =		"oti6858",
	},
	.id_table =		id_table,
	.num_ports =		1,
	.open =			oti6858_open,
	.close =		oti6858_close,
	.write =		oti6858_write,
	.ioctl =		oti6858_ioctl,
	.break_ctl =		oti6858_break_ctl,
	.set_termios =		oti6858_set_termios,
	.tiocmget =		oti6858_tiocmget,
	.tiocmset =		oti6858_tiocmset,
	.read_bulk_callback =	oti6858_read_bulk_callback,
	.read_int_callback =	oti6858_read_int_callback,
	.write_bulk_callback =	oti6858_write_bulk_callback,
	.write_room =		oti6858_write_room,
	.chars_in_buffer =	oti6858_chars_in_buffer,
	.attach =		oti6858_startup,
	.shutdown =		oti6858_shutdown,
};

struct oti6858_private {
	spinlock_t lock;

	struct oti6858_buf *buf;
	struct oti6858_control_pkt status;

	struct {
		u8 read_urb_in_use;
		u8 write_urb_in_use;
		u8 termios_initialized;
	} flags;
	struct delayed_work delayed_write_work;

	struct {
		u16 divisor;
		u8 frame_fmt;
		u8 control;
	} pending_setup;
	u8 transient;
	u8 setup_done;
	struct delayed_work delayed_setup_work;

	wait_queue_head_t intr_wait;
        struct usb_serial_port *port;   /* USB port with which associated */
};

#undef dbg
/* #define dbg(format, arg...) printk(KERN_INFO "%s: " format "\n", __FILE__, ## arg) */
#define dbg(format, arg...) printk(KERN_INFO "" format "\n", ## arg)

static void setup_line(struct work_struct *work)
{
	struct oti6858_private *priv = container_of(work, struct oti6858_private, delayed_setup_work.work);
	struct usb_serial_port *port = priv->port;
	struct oti6858_control_pkt *new_setup;
	unsigned long flags;
	int result;

	dbg("%s(port = %d)", __FUNCTION__, port->number);

	if ((new_setup = kmalloc(OTI6858_CTRL_PKT_SIZE, GFP_KERNEL)) == NULL) {
		dev_err(&port->dev, "%s(): out of memory!\n", __FUNCTION__);
		/* we will try again */
		schedule_delayed_work(&priv->delayed_setup_work, msecs_to_jiffies(2));
		return;
	}

	result = usb_control_msg(port->serial->dev,
				usb_rcvctrlpipe(port->serial->dev, 0),
				OTI6858_REQ_T_GET_STATUS,
				OTI6858_REQ_GET_STATUS,
				0, 0,
				new_setup, OTI6858_CTRL_PKT_SIZE,
				100);

	if (result != OTI6858_CTRL_PKT_SIZE) {
		dev_err(&port->dev, "%s(): error reading status\n", __FUNCTION__);
		kfree(new_setup);
		/* we will try again */
		schedule_delayed_work(&priv->delayed_setup_work, msecs_to_jiffies(2));
		return;
	}

	spin_lock_irqsave(&priv->lock, flags);
	if (!OTI6858_CTRL_EQUALS_PENDING(new_setup, priv)) {
		new_setup->divisor = priv->pending_setup.divisor;
		new_setup->control = priv->pending_setup.control;
		new_setup->frame_fmt = priv->pending_setup.frame_fmt;

		spin_unlock_irqrestore(&priv->lock, flags);
		result = usb_control_msg(port->serial->dev,
					usb_sndctrlpipe(port->serial->dev, 0),
					OTI6858_REQ_T_SET_LINE,
					OTI6858_REQ_SET_LINE,
					0, 0,
					new_setup, OTI6858_CTRL_PKT_SIZE,
					100);
	} else {
		spin_unlock_irqrestore(&priv->lock, flags);
		result = 0;
	}
	kfree(new_setup);

	spin_lock_irqsave(&priv->lock, flags);
	if (result != OTI6858_CTRL_PKT_SIZE)
		priv->transient = 0;
	priv->setup_done = 1;
	spin_unlock_irqrestore(&priv->lock, flags);

	dbg("%s(): submitting interrupt urb", __FUNCTION__);
	port->interrupt_in_urb->dev = port->serial->dev;
	result = usb_submit_urb(port->interrupt_in_urb, GFP_ATOMIC);
	if (result != 0) {
		dev_err(&port->dev, "%s(): usb_submit_urb() failed"
				" with error %d\n", __FUNCTION__, result);
	}
}

void send_data(struct work_struct *work)
{
	struct oti6858_private *priv = container_of(work, struct oti6858_private, delayed_write_work.work);
	struct usb_serial_port *port = priv->port;
	int count = 0, result;
	unsigned long flags;
	unsigned char allow;

	dbg("%s(port = %d)", __FUNCTION__, port->number);

	spin_lock_irqsave(&priv->lock, flags);
	if (priv->flags.write_urb_in_use) {
		spin_unlock_irqrestore(&priv->lock, flags);
		schedule_delayed_work(&priv->delayed_write_work, msecs_to_jiffies(2));
		return;
	}
	priv->flags.write_urb_in_use = 1;

	count = oti6858_buf_data_avail(priv->buf);
	spin_unlock_irqrestore(&priv->lock, flags);
	if (count > port->bulk_out_size)
		count = port->bulk_out_size;

	if (count != 0) {
		result = usb_control_msg(port->serial->dev,
				usb_rcvctrlpipe(port->serial->dev, 0),
				OTI6858_REQ_T_CHECK_TXBUFF,
				OTI6858_REQ_CHECK_TXBUFF,
				count, 0, &allow, 1, 100);
		if (result != 1 || allow != 0)
			count = 0;
	}

	if (count == 0) {
		priv->flags.write_urb_in_use = 0;

		dbg("%s(): submitting interrupt urb", __FUNCTION__);
		port->interrupt_in_urb->dev = port->serial->dev;
		result = usb_submit_urb(port->interrupt_in_urb, GFP_ATOMIC);
		if (result != 0) {
			dev_err(&port->dev, "%s(): usb_submit_urb() failed"
				" with error %d\n", __FUNCTION__, result);
		}
		return;
	}

	spin_lock_irqsave(&priv->lock, flags);
	oti6858_buf_get(priv->buf, port->write_urb->transfer_buffer, count);
	spin_unlock_irqrestore(&priv->lock, flags);

	port->write_urb->transfer_buffer_length = count;
	port->write_urb->dev = port->serial->dev;
	result = usb_submit_urb(port->write_urb, GFP_ATOMIC);
	if (result != 0) {
		dev_err(&port->dev, "%s(): usb_submit_urb() failed"
			       " with error %d\n", __FUNCTION__, result);
		priv->flags.write_urb_in_use = 0;
	}

	usb_serial_port_softint(port);
}

static int oti6858_startup(struct usb_serial *serial)
{
        struct usb_serial_port *port = serial->port[0];
        struct oti6858_private *priv;
	int i;

	for (i = 0; i < serial->num_ports; ++i) {
		priv = kzalloc(sizeof(struct oti6858_private), GFP_KERNEL);
		if (!priv)
			break;
		priv->buf = oti6858_buf_alloc(PL2303_BUF_SIZE);
		if (priv->buf == NULL) {
			kfree(priv);
			break;
		}

		spin_lock_init(&priv->lock);
		init_waitqueue_head(&priv->intr_wait);
//		INIT_WORK(&priv->setup_work, setup_line, serial->port[i]);
//		INIT_WORK(&priv->write_work, send_data, serial->port[i]);
		priv->port = port;
		INIT_DELAYED_WORK(&priv->delayed_setup_work, setup_line);
		INIT_DELAYED_WORK(&priv->delayed_write_work, send_data);

		usb_set_serial_port_data(serial->port[i], priv);
	}
	if (i == serial->num_ports)
		return 0;

	for (--i; i >= 0; --i) {
		priv = usb_get_serial_port_data(serial->port[i]);
		oti6858_buf_free(priv->buf);
		kfree(priv);
		usb_set_serial_port_data(serial->port[i], NULL);
	}
	return -ENOMEM;
}

static int oti6858_write(struct usb_serial_port *port,
			const unsigned char *buf, int count)
{
	struct oti6858_private *priv = usb_get_serial_port_data(port);
	unsigned long flags;

	dbg("%s(port = %d, count = %d)", __FUNCTION__, port->number, count);

	if (!count)
		return count;

	spin_lock_irqsave(&priv->lock, flags);
	count = oti6858_buf_put(priv->buf, buf, count);
	spin_unlock_irqrestore(&priv->lock, flags);

	return count;
}

static int oti6858_write_room(struct usb_serial_port *port)
{
	struct oti6858_private *priv = usb_get_serial_port_data(port);
	int room = 0;
	unsigned long flags;

	dbg("%s(port = %d)", __FUNCTION__, port->number);

	spin_lock_irqsave(&priv->lock, flags);
	room = oti6858_buf_space_avail(priv->buf);
	spin_unlock_irqrestore(&priv->lock, flags);

	return room;
}

static int oti6858_chars_in_buffer(struct usb_serial_port *port)
{
	struct oti6858_private *priv = usb_get_serial_port_data(port);
	int chars = 0;
	unsigned long flags;

	dbg("%s(port = %d)", __FUNCTION__, port->number);

	spin_lock_irqsave(&priv->lock, flags);
	chars = oti6858_buf_data_avail(priv->buf);
	spin_unlock_irqrestore(&priv->lock, flags);

	return chars;
}

static void oti6858_set_termios(struct usb_serial_port *port,
				struct ktermios *old_termios)
{
	struct oti6858_private *priv = usb_get_serial_port_data(port);
	unsigned long flags;
	unsigned int cflag;
	u8 frame_fmt, control;
	u16 divisor;
	int br;

	dbg("%s(port = %d)", __FUNCTION__, port->number);

	if (!port->tty || !port->tty->termios) {
		dbg("%s(): no tty structures", __FUNCTION__);
		return;
	}

	spin_lock_irqsave(&priv->lock, flags);
	if (!priv->flags.termios_initialized) {
		*(port->tty->termios) = tty_std_termios;
		port->tty->termios->c_cflag = B38400 | CS8 | CREAD | HUPCL | CLOCAL;
		priv->flags.termios_initialized = 1;
		port->tty->termios->c_ispeed = 38400;
		port->tty->termios->c_ospeed = 38400;
	}
	spin_unlock_irqrestore(&priv->lock, flags);

	cflag = port->tty->termios->c_cflag;

	spin_lock_irqsave(&priv->lock, flags);
	divisor = priv->pending_setup.divisor;
	frame_fmt = priv->pending_setup.frame_fmt;
	control = priv->pending_setup.control;
	spin_unlock_irqrestore(&priv->lock, flags);

	frame_fmt &= ~FMT_DATA_BITS_MASK;
	switch (cflag & CSIZE) {
		case CS5:
			frame_fmt |= FMT_DATA_BITS_5;
			break;
		case CS6:
			frame_fmt |= FMT_DATA_BITS_6;
			break;
		case CS7:
			frame_fmt |= FMT_DATA_BITS_7;
			break;
		default:
		case CS8:
			frame_fmt |= FMT_DATA_BITS_8;
			break;
	}

	/* manufacturer claims that this device can work with baud rates
	 * up to 3 Mbps; I've tested it only on 115200 bps, so I can't
	 * guarantee that any other baud rate will work (especially
	 * the higher ones)
	 */
	br = tty_get_baud_rate(port->tty);
	if (br == 0) {
		divisor = 0;
	} else {
		int real_br;
		br = min(br, OTI6858_MAX_BAUD_RATE);

		divisor = (96000000 + 8 * br) / (16 * br);
		real_br = 96000000 / (16 * divisor);
		divisor = cpu_to_le16(divisor);
		tty_encode_baud_rate(port->tty, real_br, real_br);
	}

	frame_fmt &= ~FMT_STOP_BITS_MASK;
	if ((cflag & CSTOPB) != 0) {
		frame_fmt |= FMT_STOP_BITS_2;
	} else {
		frame_fmt |= FMT_STOP_BITS_1;
	}

	frame_fmt &= ~FMT_PARITY_MASK;
	if ((cflag & PARENB) != 0) {
		if ((cflag & PARODD) != 0) {
			frame_fmt |= FMT_PARITY_ODD;
		} else {
			frame_fmt |= FMT_PARITY_EVEN;
		}
	} else {
		frame_fmt |= FMT_PARITY_NONE;
	}

	control &= ~CONTROL_MASK;
	if ((cflag & CRTSCTS) != 0)
		control |= (CONTROL_DTR_HIGH | CONTROL_RTS_HIGH);

	/* change control lines if we are switching to or from B0 */
	/* FIXME:
	spin_lock_irqsave(&priv->lock, flags);
	control = priv->line_control;
	if ((cflag & CBAUD) == B0)
		priv->line_control &= ~(CONTROL_DTR | CONTROL_RTS);
	else
		priv->line_control |= (CONTROL_DTR | CONTROL_RTS);
	if (control != priv->line_control) {
		control = priv->line_control;
		spin_unlock_irqrestore(&priv->lock, flags);
		set_control_lines(serial->dev, control);
	} else {
		spin_unlock_irqrestore(&priv->lock, flags);
	}
	*/

	spin_lock_irqsave(&priv->lock, flags);
	if (divisor != priv->pending_setup.divisor
			|| control != priv->pending_setup.control
			|| frame_fmt != priv->pending_setup.frame_fmt) {
		priv->pending_setup.divisor = divisor;
		priv->pending_setup.control = control;
		priv->pending_setup.frame_fmt = frame_fmt;
	}
	spin_unlock_irqrestore(&priv->lock, flags);
}

static int oti6858_open(struct usb_serial_port *port, struct file *filp)
{
	struct oti6858_private *priv = usb_get_serial_port_data(port);
	struct ktermios tmp_termios;
	struct usb_serial *serial = port->serial;
	struct oti6858_control_pkt *buf;
	unsigned long flags;
	int result;

	dbg("%s(port = %d)", __FUNCTION__, port->number);

	usb_clear_halt(serial->dev, port->write_urb->pipe);
	usb_clear_halt(serial->dev, port->read_urb->pipe);

	if (port->open_count != 1)
		return 0;

	if ((buf = kmalloc(OTI6858_CTRL_PKT_SIZE, GFP_KERNEL)) == NULL) {
		dev_err(&port->dev, "%s(): out of memory!\n", __FUNCTION__);
		return -ENOMEM;
	}

	result = usb_control_msg(serial->dev, usb_rcvctrlpipe(serial->dev, 0),
				OTI6858_REQ_T_GET_STATUS,
				OTI6858_REQ_GET_STATUS,
				0, 0,
				buf, OTI6858_CTRL_PKT_SIZE,
				100);
	if (result != OTI6858_CTRL_PKT_SIZE) {
		/* assume default (after power-on reset) values */
		buf->divisor = cpu_to_le16(0x009c);	/* 38400 bps */
		buf->frame_fmt = 0x03;	/* 8N1 */
		buf->something = 0x43;
		buf->control = 0x4c;	/* DTR, RTS */
		buf->tx_status = 0x00;
		buf->pin_state = 0x5b;	/* RTS, CTS, DSR, DTR, RI, DCD */
		buf->rx_bytes_avail = 0x00;
	}

	spin_lock_irqsave(&priv->lock, flags);
	memcpy(&priv->status, buf, OTI6858_CTRL_PKT_SIZE);
	priv->pending_setup.divisor = buf->divisor;
	priv->pending_setup.frame_fmt = buf->frame_fmt;
	priv->pending_setup.control = buf->control;
	spin_unlock_irqrestore(&priv->lock, flags);
	kfree(buf);

	dbg("%s(): submitting interrupt urb", __FUNCTION__);
	port->interrupt_in_urb->dev = serial->dev;
	result = usb_submit_urb(port->interrupt_in_urb, GFP_KERNEL);
	if (result != 0) {
		dev_err(&port->dev, "%s(): usb_submit_urb() failed"
			       " with error %d\n", __FUNCTION__, result);
		oti6858_close(port, NULL);
		return -EPROTO;
	}

	/* setup termios */
	if (port->tty)
		oti6858_set_termios(port, &tmp_termios);

	return 0;
}

static void oti6858_close(struct usb_serial_port *port, struct file *filp)
{
	struct oti6858_private *priv = usb_get_serial_port_data(port);
	unsigned long flags;
	long timeout;
	wait_queue_t wait;

	dbg("%s(port = %d)", __FUNCTION__, port->number);

	/* wait for data to drain from the buffer */
	spin_lock_irqsave(&priv->lock, flags);
	timeout = 30 * HZ;	/* PL2303_CLOSING_WAIT */
	init_waitqueue_entry(&wait, current);
	add_wait_queue(&port->tty->write_wait, &wait);
	dbg("%s(): entering wait loop", __FUNCTION__);
	for (;;) {
		set_current_state(TASK_INTERRUPTIBLE);
		if (oti6858_buf_data_avail(priv->buf) == 0
		|| timeout == 0 || signal_pending(current)
		|| port->serial->disconnected)
			break;
		spin_unlock_irqrestore(&priv->lock, flags);
		timeout = schedule_timeout(timeout);
		spin_lock_irqsave(&priv->lock, flags);
	}
	set_current_state(TASK_RUNNING);
	remove_wait_queue(&port->tty->write_wait, &wait);
	dbg("%s(): after wait loop", __FUNCTION__);

	/* clear out any remaining data in the buffer */
	oti6858_buf_clear(priv->buf);
	spin_unlock_irqrestore(&priv->lock, flags);

	/* wait for characters to drain from the device */
	/* (this is long enough for the entire 256 byte */
	/* pl2303 hardware buffer to drain with no flow */
	/* control for data rates of 1200 bps or more, */
	/* for lower rates we should really know how much */
	/* data is in the buffer to compute a delay */
	/* that is not unnecessarily long) */
	/* FIXME
	bps = tty_get_baud_rate(port->tty);
	if (bps > 1200)
		timeout = max((HZ*2560)/bps,HZ/10);
	else
	*/
		timeout = 2*HZ;
	schedule_timeout_interruptible(timeout);
	dbg("%s(): after schedule_timeout_interruptible()", __FUNCTION__);

	/* cancel scheduled setup */
	cancel_delayed_work(&priv->delayed_setup_work);
	cancel_delayed_work(&priv->delayed_write_work);
	flush_scheduled_work();

	/* shutdown our urbs */
	dbg("%s(): shutting down urbs", __FUNCTION__);
	usb_kill_urb(port->write_urb);
	usb_kill_urb(port->read_urb);
	usb_kill_urb(port->interrupt_in_urb);

	/*
	if (port->tty && (port->tty->termios->c_cflag) & HUPCL) {
		// drop DTR and RTS
		spin_lock_irqsave(&priv->lock, flags);
		priv->pending_setup.control &= ~CONTROL_MASK;
		spin_unlock_irqrestore(&priv->lock, flags);
	}
	*/
}

static int oti6858_tiocmset(struct usb_serial_port *port, struct file *file,
				unsigned int set, unsigned int clear)
{
	struct oti6858_private *priv = usb_get_serial_port_data(port);
	unsigned long flags;
	u8 control;

	dbg("%s(port = %d, set = 0x%08x, clear = 0x%08x)",
				__FUNCTION__, port->number, set, clear);

	if (!usb_get_intfdata(port->serial->interface))
		return -ENODEV;

	/* FIXME: check if this is correct (active high/low) */
	spin_lock_irqsave(&priv->lock, flags);
	control = priv->pending_setup.control;
	if ((set & TIOCM_RTS) != 0)
		control |= CONTROL_RTS_HIGH;
	if ((set & TIOCM_DTR) != 0)
		control |= CONTROL_DTR_HIGH;
	if ((clear & TIOCM_RTS) != 0)
		control &= ~CONTROL_RTS_HIGH;
	if ((clear & TIOCM_DTR) != 0)
		control &= ~CONTROL_DTR_HIGH;

	if (control != priv->pending_setup.control) {
		priv->pending_setup.control = control;
	}
	spin_unlock_irqrestore(&priv->lock, flags);

	return 0;
}

static int oti6858_tiocmget(struct usb_serial_port *port, struct file *file)
{
	struct oti6858_private *priv = usb_get_serial_port_data(port);
	unsigned long flags;
	unsigned pin_state;
	unsigned result = 0;

	dbg("%s(port = %d)", __FUNCTION__, port->number);

	if (!usb_get_intfdata(port->serial->interface))
		return -ENODEV;

	spin_lock_irqsave(&priv->lock, flags);
	pin_state = priv->status.pin_state & PIN_MASK;
	spin_unlock_irqrestore(&priv->lock, flags);

	/* FIXME: check if this is correct (active high/low) */
	if ((pin_state & PIN_RTS) != 0)
		result |= TIOCM_RTS;
	if ((pin_state & PIN_CTS) != 0)
		result |= TIOCM_CTS;
	if ((pin_state & PIN_DSR) != 0)
		result |= TIOCM_DSR;
	if ((pin_state & PIN_DTR) != 0)
		result |= TIOCM_DTR;
	if ((pin_state & PIN_RI) != 0)
		result |= TIOCM_RI;
	if ((pin_state & PIN_DCD) != 0)
		result |= TIOCM_CD;

	dbg("%s() = 0x%08x", __FUNCTION__, result);

	return result;
}

static int wait_modem_info(struct usb_serial_port *port, unsigned int arg)
{
	struct oti6858_private *priv = usb_get_serial_port_data(port);
	unsigned long flags;
	unsigned int prev, status;
	unsigned int changed;

	spin_lock_irqsave(&priv->lock, flags);
	prev = priv->status.pin_state;
	spin_unlock_irqrestore(&priv->lock, flags);

	while (1) {
		wait_event_interruptible(priv->intr_wait, priv->status.pin_state != prev);
		if (signal_pending(current))
			return -ERESTARTSYS;

		spin_lock_irqsave(&priv->lock, flags);
		status = priv->status.pin_state & PIN_MASK;
		spin_unlock_irqrestore(&priv->lock, flags);

		changed = prev ^ status;
		/* FIXME: check if this is correct (active high/low) */
		if (	((arg & TIOCM_RNG) && (changed & PIN_RI)) ||
			((arg & TIOCM_DSR) && (changed & PIN_DSR)) ||
			((arg & TIOCM_CD)  && (changed & PIN_DCD)) ||
			((arg & TIOCM_CTS) && (changed & PIN_CTS))) {
				return 0;
		}
		prev = status;
	}

	/* NOTREACHED */
	return 0;
}

static int oti6858_ioctl(struct usb_serial_port *port, struct file *file,
			unsigned int cmd, unsigned long arg)
{
	void __user *user_arg = (void __user *) arg;
	unsigned int x;

	dbg("%s(port = %d, cmd = 0x%04x, arg = 0x%08lx)",
				__FUNCTION__, port->number, cmd, arg);

	switch (cmd) {
		case TIOCMBIS:
			if (copy_from_user(&x, user_arg, sizeof(x)))
				return -EFAULT;
			return oti6858_tiocmset(port, NULL, x, 0);

		case TIOCMBIC:
			if (copy_from_user(&x, user_arg, sizeof(x)))
				return -EFAULT;
			return oti6858_tiocmset(port, NULL, 0, x);

		case TIOCMIWAIT:
			dbg("%s(): TIOCMIWAIT", __FUNCTION__);
			return wait_modem_info(port, arg);

		default:
			dbg("%s(): 0x%04x not supported", __FUNCTION__, cmd);
			break;
	}

	return -ENOIOCTLCMD;
}

static void oti6858_break_ctl(struct usb_serial_port *port, int break_state)
{
	int state;

	dbg("%s(port = %d)", __FUNCTION__, port->number);

	state = (break_state == 0) ? 0 : 1;
	dbg("%s(): turning break %s", __FUNCTION__, state ? "on" : "off");

	/* FIXME */
/*
	result = usb_control_msg (serial->dev, usb_sndctrlpipe (serial->dev, 0),
				  BREAK_REQUEST, BREAK_REQUEST_TYPE, state,
				  0, NULL, 0, 100);
	if (result != 0)
		dbg("%s(): error sending break", __FUNCTION__);
 */
}

static void oti6858_shutdown(struct usb_serial *serial)
{
	struct oti6858_private *priv;
	int i;

	dbg("%s()", __FUNCTION__);

	for (i = 0; i < serial->num_ports; ++i) {
		priv = usb_get_serial_port_data(serial->port[i]);
		if (priv) {
			oti6858_buf_free(priv->buf);
			kfree(priv);
			usb_set_serial_port_data(serial->port[i], NULL);
		}
	}
}

static void oti6858_read_int_callback(struct urb *urb)
{
	struct usb_serial_port *port = (struct usb_serial_port *) urb->context;
	struct oti6858_private *priv = usb_get_serial_port_data(port);
	int transient = 0, can_recv = 0, resubmit = 1;
	int status = urb->status;

	dbg("%s(port = %d, status = %d)",
				__FUNCTION__, port->number, status);

	switch (status) {
	case 0:
		/* success */
		break;
	case -ECONNRESET:
	case -ENOENT:
	case -ESHUTDOWN:
		/* this urb is terminated, clean up */
		dbg("%s(): urb shutting down with status: %d",
					__FUNCTION__, status);
		return;
	default:
		dbg("%s(): nonzero urb status received: %d",
					__FUNCTION__, status);
		break;
	}

	if (status == 0 && urb->actual_length == OTI6858_CTRL_PKT_SIZE) {
		struct oti6858_control_pkt *xs = urb->transfer_buffer;
		unsigned long flags;

		spin_lock_irqsave(&priv->lock, flags);

		if (!priv->transient) {
			if (!OTI6858_CTRL_EQUALS_PENDING(xs, priv)) {
				if (xs->rx_bytes_avail == 0) {
					priv->transient = 4;
					priv->setup_done = 0;
					resubmit = 0;
					dbg("%s(): scheduling setup_line()",
					    __FUNCTION__);
					schedule_delayed_work(&priv->delayed_setup_work, 0);
				}
			}
		} else {
			if (OTI6858_CTRL_EQUALS_PENDING(xs, priv)) {
				priv->transient = 0;
			} else if (!priv->setup_done) {
				resubmit = 0;
			} else if (--priv->transient == 0) {
				if (xs->rx_bytes_avail == 0) {
					priv->transient = 4;
					priv->setup_done = 0;
					resubmit = 0;
					dbg("%s(): scheduling setup_line()",
					    __FUNCTION__);
					schedule_delayed_work(&priv->delayed_setup_work, 0);
				}
			}
		}

		if (!priv->transient) {
			if (xs->pin_state != priv->status.pin_state)
				wake_up_interruptible(&priv->intr_wait);
			memcpy(&priv->status, xs, OTI6858_CTRL_PKT_SIZE);
		}

		if (!priv->transient && xs->rx_bytes_avail != 0) {
			can_recv = xs->rx_bytes_avail;
			priv->flags.read_urb_in_use = 1;
		}

		transient = priv->transient;
		spin_unlock_irqrestore(&priv->lock, flags);
	}

	if (can_recv) {
		int result;

		port->read_urb->dev = port->serial->dev;
		result = usb_submit_urb(port->read_urb, GFP_ATOMIC);
		if (result != 0) {
			priv->flags.read_urb_in_use = 0;
			dev_err(&port->dev, "%s(): usb_submit_urb() failed,"
					" error %d\n", __FUNCTION__, result);
		} else {
			resubmit = 0;
		}
	} else if (!transient) {
		unsigned long flags;

		spin_lock_irqsave(&priv->lock, flags);
		if (priv->flags.write_urb_in_use == 0
				&& oti6858_buf_data_avail(priv->buf) != 0) {
			schedule_delayed_work(&priv->delayed_write_work,0);
			resubmit = 0;
		}
		spin_unlock_irqrestore(&priv->lock, flags);
	}

	if (resubmit) {
		int result;

//		dbg("%s(): submitting interrupt urb", __FUNCTION__);
		urb->dev = port->serial->dev;
		result = usb_submit_urb(urb, GFP_ATOMIC);
		if (result != 0) {
			dev_err(&urb->dev->dev,
					"%s(): usb_submit_urb() failed with"
					" error %d\n", __FUNCTION__, result);
		}
	}
}

static void oti6858_read_bulk_callback(struct urb *urb)
{
	struct usb_serial_port *port = (struct usb_serial_port *) urb->context;
	struct oti6858_private *priv = usb_get_serial_port_data(port);
	struct tty_struct *tty;
	unsigned char *data = urb->transfer_buffer;
	unsigned long flags;
	int status = urb->status;
	int result;

	dbg("%s(port = %d, status = %d)",
				__FUNCTION__, port->number, status);

	spin_lock_irqsave(&priv->lock, flags);
	priv->flags.read_urb_in_use = 0;
	spin_unlock_irqrestore(&priv->lock, flags);

	if (status != 0) {
		if (!port->open_count) {
			dbg("%s(): port is closed, exiting", __FUNCTION__);
			return;
		}
		/*
		if (status == -EPROTO) {
			// PL2303 mysteriously fails with -EPROTO reschedule the read
			dbg("%s - caught -EPROTO, resubmitting the urb", __FUNCTION__);
			result = usb_submit_urb(urb, GFP_ATOMIC);
			if (result)
				dev_err(&urb->dev->dev, "%s - failed resubmitting read urb, error %d\n", __FUNCTION__, result);
			return;
		}
		*/
		dbg("%s(): unable to handle the error, exiting", __FUNCTION__);
		return;
	}

	tty = port->tty;
	if (tty != NULL && urb->actual_length > 0) {
		tty_insert_flip_string(tty, data, urb->actual_length);
		tty_flip_buffer_push(tty);
	}

	// schedule the interrupt urb if we are still open */
	if (port->open_count != 0) {
		port->interrupt_in_urb->dev = port->serial->dev;
		result = usb_submit_urb(port->interrupt_in_urb, GFP_ATOMIC);
		if (result != 0) {
			dev_err(&port->dev, "%s(): usb_submit_urb() failed,"
					" error %d\n", __FUNCTION__, result);
		}
	}
}

static void oti6858_write_bulk_callback(struct urb *urb)
{
	struct usb_serial_port *port = (struct usb_serial_port *) urb->context;
	struct oti6858_private *priv = usb_get_serial_port_data(port);
	int status = urb->status;
	int result;

	dbg("%s(port = %d, status = %d)",
				__FUNCTION__, port->number, status);

	switch (status) {
	case 0:
		/* success */
		break;
	case -ECONNRESET:
	case -ENOENT:
	case -ESHUTDOWN:
		/* this urb is terminated, clean up */
		dbg("%s(): urb shutting down with status: %d",
					__FUNCTION__, status);
		priv->flags.write_urb_in_use = 0;
		return;
	default:
		/* error in the urb, so we have to resubmit it */
		dbg("%s(): nonzero write bulk status received: %d",
					__FUNCTION__, status);
		dbg("%s(): overflow in write", __FUNCTION__);

		port->write_urb->transfer_buffer_length = 1;
		port->write_urb->dev = port->serial->dev;
		result = usb_submit_urb(port->write_urb, GFP_ATOMIC);
		if (result) {
			dev_err(&port->dev, "%s(): usb_submit_urb() failed,"
					" error %d\n", __FUNCTION__, result);
		} else {
			return;
		}
	}

	priv->flags.write_urb_in_use = 0;

	// schedule the interrupt urb if we are still open */
	port->interrupt_in_urb->dev = port->serial->dev;
	dbg("%s(): submitting interrupt urb", __FUNCTION__);
	result = usb_submit_urb(port->interrupt_in_urb, GFP_ATOMIC);
	if (result != 0) {
		dev_err(&port->dev, "%s(): failed submitting int urb,"
					" error %d\n", __FUNCTION__, result);
	}
}


/*
 * oti6858_buf_alloc
 *
 * Allocate a circular buffer and all associated memory.
 */
static struct oti6858_buf *oti6858_buf_alloc(unsigned int size)
{
	struct oti6858_buf *pb;

	if (size == 0)
		return NULL;

	pb = kmalloc(sizeof(struct oti6858_buf), GFP_KERNEL);
	if (pb == NULL)
		return NULL;

	pb->buf_buf = kmalloc(size, GFP_KERNEL);
	if (pb->buf_buf == NULL) {
		kfree(pb);
		return NULL;
	}

	pb->buf_size = size;
	pb->buf_get = pb->buf_put = pb->buf_buf;

	return pb;
}

/*
 * oti6858_buf_free
 *
 * Free the buffer and all associated memory.
 */
static void oti6858_buf_free(struct oti6858_buf *pb)
{
	if (pb) {
		kfree(pb->buf_buf);
		kfree(pb);
	}
}

/*
 * oti6858_buf_clear
 *
 * Clear out all data in the circular buffer.
 */
static void oti6858_buf_clear(struct oti6858_buf *pb)
{
	if (pb != NULL) {
		/* equivalent to a get of all data available */
		pb->buf_get = pb->buf_put;
	}
}

/*
 * oti6858_buf_data_avail
 *
 * Return the number of bytes of data available in the circular
 * buffer.
 */
static unsigned int oti6858_buf_data_avail(struct oti6858_buf *pb)
{
	if (pb == NULL)
		return 0;
	return ((pb->buf_size + pb->buf_put - pb->buf_get) % pb->buf_size);
}

/*
 * oti6858_buf_space_avail
 *
 * Return the number of bytes of space available in the circular
 * buffer.
 */
static unsigned int oti6858_buf_space_avail(struct oti6858_buf *pb)
{
	if (pb == NULL)
		return 0;
	return ((pb->buf_size + pb->buf_get - pb->buf_put - 1) % pb->buf_size);
}

/*
 * oti6858_buf_put
 *
 * Copy data data from a user buffer and put it into the circular buffer.
 * Restrict to the amount of space available.
 *
 * Return the number of bytes copied.
 */
static unsigned int oti6858_buf_put(struct oti6858_buf *pb, const char *buf,
					unsigned int count)
{
	unsigned int len;

	if (pb == NULL)
		return 0;

	len  = oti6858_buf_space_avail(pb);
	if (count > len)
		count = len;

	if (count == 0)
		return 0;

	len = pb->buf_buf + pb->buf_size - pb->buf_put;
	if (count > len) {
		memcpy(pb->buf_put, buf, len);
		memcpy(pb->buf_buf, buf+len, count - len);
		pb->buf_put = pb->buf_buf + count - len;
	} else {
		memcpy(pb->buf_put, buf, count);
		if (count < len)
			pb->buf_put += count;
		else /* count == len */
			pb->buf_put = pb->buf_buf;
	}

	return count;
}

/*
 * oti6858_buf_get
 *
 * Get data from the circular buffer and copy to the given buffer.
 * Restrict to the amount of data available.
 *
 * Return the number of bytes copied.
 */
static unsigned int oti6858_buf_get(struct oti6858_buf *pb, char *buf,
					unsigned int count)
{
	unsigned int len;

	if (pb == NULL)
		return 0;

	len = oti6858_buf_data_avail(pb);
	if (count > len)
		count = len;

	if (count == 0)
		return 0;

	len = pb->buf_buf + pb->buf_size - pb->buf_get;
	if (count > len) {
		memcpy(buf, pb->buf_get, len);
		memcpy(buf+len, pb->buf_buf, count - len);
		pb->buf_get = pb->buf_buf + count - len;
	} else {
		memcpy(buf, pb->buf_get, count);
		if (count < len)
			pb->buf_get += count;
		else /* count == len */
			pb->buf_get = pb->buf_buf;
	}

	return count;
}

/* module description and (de)initialization */

static int __init oti6858_init(void)
{
	int retval;

	if ((retval = usb_serial_register(&oti6858_device)) == 0) {
		if ((retval = usb_register(&oti6858_driver)) != 0)
			usb_serial_deregister(&oti6858_device);
		else
			return 0;
	}

	return retval;
}

static void __exit oti6858_exit(void)
{
	usb_deregister(&oti6858_driver);
	usb_serial_deregister(&oti6858_device);
}

module_init(oti6858_init);
module_exit(oti6858_exit);

MODULE_DESCRIPTION(OTI6858_DESCRIPTION);
MODULE_AUTHOR(OTI6858_AUTHOR);
MODULE_VERSION(OTI6858_VERSION);
MODULE_LICENSE("GPL");

module_param(debug, bool, S_IRUGO | S_IWUSR);
MODULE_PARM_DESC(debug, "enable debug output");

