/*
 * Edgeport USB Serial Converter driver
 *
 * Copyright (C) 2000-2002 Inside Out Networks, All rights reserved.
 * Copyright (C) 2001-2002 Greg Kroah-Hartman <greg@kroah.com>
 *
 *	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.
 *
 * Supports the following devices:
 *	EP/1 EP/2 EP/4 EP/21 EP/22 EP/221 EP/42 EP/421 WATCHPORT
 *
 * For questions or problems with this driver, contact Inside Out
 * Networks technical support, or Peter Berger <pberger@brimson.com>,
 * or Al Borchers <alborchers@steinerpoint.com>.
 */

#include <linux/kernel.h>
#include <linux/jiffies.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/module.h>
#include <linux/spinlock.h>
#include <linux/mutex.h>
#include <linux/serial.h>
#include <linux/kfifo.h>
#include <linux/ioctl.h>
#include <linux/firmware.h>
#include <linux/uaccess.h>
#include <linux/usb.h>
#include <linux/usb/serial.h>

#include "io_16654.h"
#include "io_usbvend.h"
#include "io_ti.h"

#define DRIVER_AUTHOR "Greg Kroah-Hartman <greg@kroah.com> and David Iacovelli"
#define DRIVER_DESC "Edgeport USB Serial Driver"

#define EPROM_PAGE_SIZE		64


/* different hardware types */
#define HARDWARE_TYPE_930	0
#define HARDWARE_TYPE_TIUMP	1

/* IOCTL_PRIVATE_TI_GET_MODE Definitions */
#define	TI_MODE_CONFIGURING	0   /* Device has not entered start device */
#define	TI_MODE_BOOT		1   /* Staying in boot mode		   */
#define TI_MODE_DOWNLOAD	2   /* Made it to download mode		   */
#define TI_MODE_TRANSITIONING	3   /* Currently in boot mode but
				       transitioning to download mode	   */

/* read urb state */
#define EDGE_READ_URB_RUNNING	0
#define EDGE_READ_URB_STOPPING	1
#define EDGE_READ_URB_STOPPED	2

#define EDGE_CLOSING_WAIT	4000	/* in .01 sec */

#define EDGE_OUT_BUF_SIZE	1024


/* Product information read from the Edgeport */
struct product_info {
	int	TiMode;			/* Current TI Mode  */
	__u8	hardware_type;		/* Type of hardware */
} __attribute__((packed));

struct edgeport_port {
	__u16 uart_base;
	__u16 dma_address;
	__u8 shadow_msr;
	__u8 shadow_mcr;
	__u8 shadow_lsr;
	__u8 lsr_mask;
	__u32 ump_read_timeout;		/* Number of milliseconds the UMP will
					   wait without data before completing
					   a read short */
	int baud_rate;
	int close_pending;
	int lsr_event;
	struct async_icount	icount;
	wait_queue_head_t	delta_msr_wait;	/* for handling sleeping while
						   waiting for msr change to
						   happen */
	struct edgeport_serial	*edge_serial;
	struct usb_serial_port	*port;
	__u8 bUartMode;		/* Port type, 0: RS232, etc. */
	spinlock_t ep_lock;
	int ep_read_urb_state;
	int ep_write_urb_in_use;
	struct kfifo write_fifo;
};

struct edgeport_serial {
	struct product_info product_info;
	u8 TI_I2C_Type;			/* Type of I2C in UMP */
	u8 TiReadI2C;			/* Set to TRUE if we have read the
					   I2c in Boot Mode */
	struct mutex es_lock;
	int num_ports_open;
	struct usb_serial *serial;
};


/* Devices that this driver supports */
static const struct usb_device_id edgeport_1port_id_table[] = {
	{ USB_DEVICE(USB_VENDOR_ID_ION, ION_DEVICE_ID_TI_EDGEPORT_1) },
	{ USB_DEVICE(USB_VENDOR_ID_ION, ION_DEVICE_ID_TI_TI3410_EDGEPORT_1) },
	{ USB_DEVICE(USB_VENDOR_ID_ION, ION_DEVICE_ID_TI_TI3410_EDGEPORT_1I) },
	{ USB_DEVICE(USB_VENDOR_ID_ION, ION_DEVICE_ID_WP_PROXIMITY) },
	{ USB_DEVICE(USB_VENDOR_ID_ION, ION_DEVICE_ID_WP_MOTION) },
	{ USB_DEVICE(USB_VENDOR_ID_ION, ION_DEVICE_ID_WP_MOISTURE) },
	{ USB_DEVICE(USB_VENDOR_ID_ION, ION_DEVICE_ID_WP_TEMPERATURE) },
	{ USB_DEVICE(USB_VENDOR_ID_ION, ION_DEVICE_ID_WP_HUMIDITY) },
	{ USB_DEVICE(USB_VENDOR_ID_ION, ION_DEVICE_ID_WP_POWER) },
	{ USB_DEVICE(USB_VENDOR_ID_ION, ION_DEVICE_ID_WP_LIGHT) },
	{ USB_DEVICE(USB_VENDOR_ID_ION, ION_DEVICE_ID_WP_RADIATION) },
	{ USB_DEVICE(USB_VENDOR_ID_ION, ION_DEVICE_ID_WP_DISTANCE) },
	{ USB_DEVICE(USB_VENDOR_ID_ION, ION_DEVICE_ID_WP_ACCELERATION) },
	{ USB_DEVICE(USB_VENDOR_ID_ION, ION_DEVICE_ID_WP_PROX_DIST) },
	{ USB_DEVICE(USB_VENDOR_ID_ION, ION_DEVICE_ID_PLUS_PWR_HP4CD) },
	{ USB_DEVICE(USB_VENDOR_ID_ION, ION_DEVICE_ID_PLUS_PWR_PCI) },
	{ }
};

static const struct usb_device_id edgeport_2port_id_table[] = {
	{ USB_DEVICE(USB_VENDOR_ID_ION, ION_DEVICE_ID_TI_EDGEPORT_2) },
	{ USB_DEVICE(USB_VENDOR_ID_ION, ION_DEVICE_ID_TI_EDGEPORT_2C) },
	{ USB_DEVICE(USB_VENDOR_ID_ION, ION_DEVICE_ID_TI_EDGEPORT_2I) },
	{ USB_DEVICE(USB_VENDOR_ID_ION, ION_DEVICE_ID_TI_EDGEPORT_421) },
	{ USB_DEVICE(USB_VENDOR_ID_ION, ION_DEVICE_ID_TI_EDGEPORT_21) },
	{ USB_DEVICE(USB_VENDOR_ID_ION, ION_DEVICE_ID_TI_EDGEPORT_42) },
	{ USB_DEVICE(USB_VENDOR_ID_ION, ION_DEVICE_ID_TI_EDGEPORT_4) },
	{ USB_DEVICE(USB_VENDOR_ID_ION, ION_DEVICE_ID_TI_EDGEPORT_4I) },
	{ USB_DEVICE(USB_VENDOR_ID_ION, ION_DEVICE_ID_TI_EDGEPORT_22I) },
	{ USB_DEVICE(USB_VENDOR_ID_ION, ION_DEVICE_ID_TI_EDGEPORT_221C) },
	{ USB_DEVICE(USB_VENDOR_ID_ION, ION_DEVICE_ID_TI_EDGEPORT_22C) },
	{ USB_DEVICE(USB_VENDOR_ID_ION, ION_DEVICE_ID_TI_EDGEPORT_21C) },
	/* The 4, 8 and 16 port devices show up as multiple 2 port devices */
	{ USB_DEVICE(USB_VENDOR_ID_ION, ION_DEVICE_ID_TI_EDGEPORT_4S) },
	{ USB_DEVICE(USB_VENDOR_ID_ION, ION_DEVICE_ID_TI_EDGEPORT_8) },
	{ USB_DEVICE(USB_VENDOR_ID_ION, ION_DEVICE_ID_TI_EDGEPORT_8S) },
	{ USB_DEVICE(USB_VENDOR_ID_ION, ION_DEVICE_ID_TI_EDGEPORT_416) },
	{ USB_DEVICE(USB_VENDOR_ID_ION, ION_DEVICE_ID_TI_EDGEPORT_416B) },
	{ }
};

/* Devices that this driver supports */
static const struct usb_device_id id_table_combined[] = {
	{ USB_DEVICE(USB_VENDOR_ID_ION, ION_DEVICE_ID_TI_EDGEPORT_1) },
	{ USB_DEVICE(USB_VENDOR_ID_ION, ION_DEVICE_ID_TI_TI3410_EDGEPORT_1) },
	{ USB_DEVICE(USB_VENDOR_ID_ION, ION_DEVICE_ID_TI_TI3410_EDGEPORT_1I) },
	{ USB_DEVICE(USB_VENDOR_ID_ION, ION_DEVICE_ID_WP_PROXIMITY) },
	{ USB_DEVICE(USB_VENDOR_ID_ION, ION_DEVICE_ID_WP_MOTION) },
	{ USB_DEVICE(USB_VENDOR_ID_ION, ION_DEVICE_ID_WP_MOISTURE) },
	{ USB_DEVICE(USB_VENDOR_ID_ION, ION_DEVICE_ID_WP_TEMPERATURE) },
	{ USB_DEVICE(USB_VENDOR_ID_ION, ION_DEVICE_ID_WP_HUMIDITY) },
	{ USB_DEVICE(USB_VENDOR_ID_ION, ION_DEVICE_ID_WP_POWER) },
	{ USB_DEVICE(USB_VENDOR_ID_ION, ION_DEVICE_ID_WP_LIGHT) },
	{ USB_DEVICE(USB_VENDOR_ID_ION, ION_DEVICE_ID_WP_RADIATION) },
	{ USB_DEVICE(USB_VENDOR_ID_ION, ION_DEVICE_ID_WP_DISTANCE) },
	{ USB_DEVICE(USB_VENDOR_ID_ION, ION_DEVICE_ID_WP_ACCELERATION) },
	{ USB_DEVICE(USB_VENDOR_ID_ION, ION_DEVICE_ID_WP_PROX_DIST) },
	{ USB_DEVICE(USB_VENDOR_ID_ION, ION_DEVICE_ID_PLUS_PWR_HP4CD) },
	{ USB_DEVICE(USB_VENDOR_ID_ION, ION_DEVICE_ID_PLUS_PWR_PCI) },
	{ USB_DEVICE(USB_VENDOR_ID_ION, ION_DEVICE_ID_TI_EDGEPORT_2) },
	{ USB_DEVICE(USB_VENDOR_ID_ION, ION_DEVICE_ID_TI_EDGEPORT_2C) },
	{ USB_DEVICE(USB_VENDOR_ID_ION, ION_DEVICE_ID_TI_EDGEPORT_2I) },
	{ USB_DEVICE(USB_VENDOR_ID_ION, ION_DEVICE_ID_TI_EDGEPORT_421) },
	{ USB_DEVICE(USB_VENDOR_ID_ION, ION_DEVICE_ID_TI_EDGEPORT_21) },
	{ USB_DEVICE(USB_VENDOR_ID_ION, ION_DEVICE_ID_TI_EDGEPORT_42) },
	{ USB_DEVICE(USB_VENDOR_ID_ION, ION_DEVICE_ID_TI_EDGEPORT_4) },
	{ USB_DEVICE(USB_VENDOR_ID_ION, ION_DEVICE_ID_TI_EDGEPORT_4I) },
	{ USB_DEVICE(USB_VENDOR_ID_ION, ION_DEVICE_ID_TI_EDGEPORT_22I) },
	{ USB_DEVICE(USB_VENDOR_ID_ION, ION_DEVICE_ID_TI_EDGEPORT_221C) },
	{ USB_DEVICE(USB_VENDOR_ID_ION, ION_DEVICE_ID_TI_EDGEPORT_22C) },
	{ USB_DEVICE(USB_VENDOR_ID_ION, ION_DEVICE_ID_TI_EDGEPORT_21C) },
	{ USB_DEVICE(USB_VENDOR_ID_ION, ION_DEVICE_ID_TI_EDGEPORT_4S) },
	{ USB_DEVICE(USB_VENDOR_ID_ION, ION_DEVICE_ID_TI_EDGEPORT_8) },
	{ USB_DEVICE(USB_VENDOR_ID_ION, ION_DEVICE_ID_TI_EDGEPORT_8S) },
	{ USB_DEVICE(USB_VENDOR_ID_ION, ION_DEVICE_ID_TI_EDGEPORT_416) },
	{ USB_DEVICE(USB_VENDOR_ID_ION, ION_DEVICE_ID_TI_EDGEPORT_416B) },
	{ }
};

MODULE_DEVICE_TABLE(usb, id_table_combined);

static unsigned char OperationalMajorVersion;
static unsigned char OperationalMinorVersion;
static unsigned short OperationalBuildNumber;

static int closing_wait = EDGE_CLOSING_WAIT;
static bool ignore_cpu_rev;
static int default_uart_mode;		/* RS232 */

static void edge_tty_recv(struct device *dev, struct tty_struct *tty,
			  unsigned char *data, int length);

static void stop_read(struct edgeport_port *edge_port);
static int restart_read(struct edgeport_port *edge_port);

static void edge_set_termios(struct tty_struct *tty,
		struct usb_serial_port *port, struct ktermios *old_termios);
static void edge_send(struct tty_struct *tty);

/* sysfs attributes */
static int edge_create_sysfs_attrs(struct usb_serial_port *port);
static int edge_remove_sysfs_attrs(struct usb_serial_port *port);


static int ti_vread_sync(struct usb_device *dev, __u8 request,
				__u16 value, __u16 index, u8 *data, int size)
{
	int status;

	status = usb_control_msg(dev, usb_rcvctrlpipe(dev, 0), request,
			(USB_TYPE_VENDOR | USB_RECIP_DEVICE | USB_DIR_IN),
			value, index, data, size, 1000);
	if (status < 0)
		return status;
	if (status != size) {
		dev_dbg(&dev->dev, "%s - wanted to write %d, but only wrote %d\n",
			__func__, size, status);
		return -ECOMM;
	}
	return 0;
}

static int ti_vsend_sync(struct usb_device *dev, __u8 request,
				__u16 value, __u16 index, u8 *data, int size)
{
	int status;

	status = usb_control_msg(dev, usb_sndctrlpipe(dev, 0), request,
			(USB_TYPE_VENDOR | USB_RECIP_DEVICE | USB_DIR_OUT),
			value, index, data, size, 1000);
	if (status < 0)
		return status;
	if (status != size) {
		dev_dbg(&dev->dev, "%s - wanted to write %d, but only wrote %d\n",
			__func__, size, status);
		return -ECOMM;
	}
	return 0;
}

static int send_cmd(struct usb_device *dev, __u8 command,
				__u8 moduleid, __u16 value, u8 *data,
				int size)
{
	return ti_vsend_sync(dev, command, value, moduleid, data, size);
}

/* clear tx/rx buffers and fifo in TI UMP */
static int purge_port(struct usb_serial_port *port, __u16 mask)
{
	int port_number = port->number - port->serial->minor;

	dev_dbg(&port->dev, "%s - port %d, mask %x\n", __func__, port_number, mask);

	return send_cmd(port->serial->dev,
					UMPC_PURGE_PORT,
					(__u8)(UMPM_UART1_PORT + port_number),
					mask,
					NULL,
					0);
}

/**
 * read_download_mem - Read edgeport memory from TI chip
 * @dev: usb device pointer
 * @start_address: Device CPU address at which to read
 * @length: Length of above data
 * @address_type: Can read both XDATA and I2C
 * @buffer: pointer to input data buffer
 */
static int read_download_mem(struct usb_device *dev, int start_address,
				int length, __u8 address_type, __u8 *buffer)
{
	int status = 0;
	__u8 read_length;
	__be16 be_start_address;

	dev_dbg(&dev->dev, "%s - @ %x for %d\n", __func__, start_address, length);

	/* Read in blocks of 64 bytes
	 * (TI firmware can't handle more than 64 byte reads)
	 */
	while (length) {
		if (length > 64)
			read_length = 64;
		else
			read_length = (__u8)length;

		if (read_length > 1) {
			dev_dbg(&dev->dev, "%s - @ %x for %d\n", __func__, start_address, read_length);
		}
		be_start_address = cpu_to_be16(start_address);
		status = ti_vread_sync(dev, UMPC_MEMORY_READ,
					(__u16)address_type,
					(__force __u16)be_start_address,
					buffer, read_length);

		if (status) {
			dev_dbg(&dev->dev, "%s - ERROR %x\n", __func__, status);
			return status;
		}

		if (read_length > 1)
			usb_serial_debug_data(&dev->dev, __func__, read_length, buffer);

		/* Update pointers/length */
		start_address += read_length;
		buffer += read_length;
		length -= read_length;
	}

	return status;
}

static int read_ram(struct usb_device *dev, int start_address,
						int length, __u8 *buffer)
{
	return read_download_mem(dev, start_address, length,
					DTK_ADDR_SPACE_XDATA, buffer);
}

/* Read edgeport memory to a given block */
static int read_boot_mem(struct edgeport_serial *serial,
				int start_address, int length, __u8 *buffer)
{
	int status = 0;
	int i;

	for (i = 0; i < length; i++) {
		status = ti_vread_sync(serial->serial->dev,
				UMPC_MEMORY_READ, serial->TI_I2C_Type,
				(__u16)(start_address+i), &buffer[i], 0x01);
		if (status) {
			dev_dbg(&serial->serial->dev->dev, "%s - ERROR %x\n", __func__, status);
			return status;
		}
	}

	dev_dbg(&serial->serial->dev->dev, "%s - start_address = %x, length = %d\n",
		__func__, start_address, length);
	usb_serial_debug_data(&serial->serial->dev->dev, __func__, length, buffer);

	serial->TiReadI2C = 1;

	return status;
}

/* Write given block to TI EPROM memory */
static int write_boot_mem(struct edgeport_serial *serial,
				int start_address, int length, __u8 *buffer)
{
	int status = 0;
	int i;
	u8 *temp;

	/* Must do a read before write */
	if (!serial->TiReadI2C) {
		temp = kmalloc(1, GFP_KERNEL);
		if (!temp) {
			dev_err(&serial->serial->dev->dev,
					"%s - out of memory\n", __func__);
			return -ENOMEM;
		}
		status = read_boot_mem(serial, 0, 1, temp);
		kfree(temp);
		if (status)
			return status;
	}

	for (i = 0; i < length; ++i) {
		status = ti_vsend_sync(serial->serial->dev,
				UMPC_MEMORY_WRITE, buffer[i],
				(__u16)(i + start_address), NULL, 0);
		if (status)
			return status;
	}

	dev_dbg(&serial->serial->dev->dev, "%s - start_sddr = %x, length = %d\n", __func__, start_address, length);
	usb_serial_debug_data(&serial->serial->dev->dev, __func__, length, buffer);

	return status;
}


/* Write edgeport I2C memory to TI chip	*/
static int write_i2c_mem(struct edgeport_serial *serial,
		int start_address, int length, __u8 address_type, __u8 *buffer)
{
	struct device *dev = &serial->serial->dev->dev;
	int status = 0;
	int write_length;
	__be16 be_start_address;

	/* We can only send a maximum of 1 aligned byte page at a time */

	/* calculate the number of bytes left in the first page */
	write_length = EPROM_PAGE_SIZE -
				(start_address & (EPROM_PAGE_SIZE - 1));

	if (write_length > length)
		write_length = length;

	dev_dbg(dev, "%s - BytesInFirstPage Addr = %x, length = %d\n",
		__func__, start_address, write_length);
	usb_serial_debug_data(dev, __func__, write_length, buffer);

	/* Write first page */
	be_start_address = cpu_to_be16(start_address);
	status = ti_vsend_sync(serial->serial->dev,
				UMPC_MEMORY_WRITE, (__u16)address_type,
				(__force __u16)be_start_address,
				buffer,	write_length);
	if (status) {
		dev_dbg(dev, "%s - ERROR %d\n", __func__, status);
		return status;
	}

	length		-= write_length;
	start_address	+= write_length;
	buffer		+= write_length;

	/* We should be aligned now -- can write
	   max page size bytes at a time */
	while (length) {
		if (length > EPROM_PAGE_SIZE)
			write_length = EPROM_PAGE_SIZE;
		else
			write_length = length;

		dev_dbg(dev, "%s - Page Write Addr = %x, length = %d\n",
			__func__, start_address, write_length);
		usb_serial_debug_data(dev, __func__, write_length, buffer);

		/* Write next page */
		be_start_address = cpu_to_be16(start_address);
		status = ti_vsend_sync(serial->serial->dev, UMPC_MEMORY_WRITE,
				(__u16)address_type,
				(__force __u16)be_start_address,
				buffer, write_length);
		if (status) {
			dev_err(dev, "%s - ERROR %d\n", __func__, status);
			return status;
		}

		length		-= write_length;
		start_address	+= write_length;
		buffer		+= write_length;
	}
	return status;
}

/* Examine the UMP DMA registers and LSR
 *
 * Check the MSBit of the X and Y DMA byte count registers.
 * A zero in this bit indicates that the TX DMA buffers are empty
 * then check the TX Empty bit in the UART.
 */
static int tx_active(struct edgeport_port *port)
{
	int status;
	struct out_endpoint_desc_block *oedb;
	__u8 *lsr;
	int bytes_left = 0;

	oedb = kmalloc(sizeof(*oedb), GFP_KERNEL);
	if (!oedb) {
		dev_err(&port->port->dev, "%s - out of memory\n", __func__);
		return -ENOMEM;
	}

	lsr = kmalloc(1, GFP_KERNEL);	/* Sigh, that's right, just one byte,
					   as not all platforms can do DMA
					   from stack */
	if (!lsr) {
		kfree(oedb);
		return -ENOMEM;
	}
	/* Read the DMA Count Registers */
	status = read_ram(port->port->serial->dev, port->dma_address,
						sizeof(*oedb), (void *)oedb);
	if (status)
		goto exit_is_tx_active;

	dev_dbg(&port->port->dev, "%s - XByteCount    0x%X\n", __func__, oedb->XByteCount);

	/* and the LSR */
	status = read_ram(port->port->serial->dev,
			port->uart_base + UMPMEM_OFFS_UART_LSR, 1, lsr);

	if (status)
		goto exit_is_tx_active;
	dev_dbg(&port->port->dev, "%s - LSR = 0x%X\n", __func__, *lsr);

	/* If either buffer has data or we are transmitting then return TRUE */
	if ((oedb->XByteCount & 0x80) != 0)
		bytes_left += 64;

	if ((*lsr & UMP_UART_LSR_TX_MASK) == 0)
		bytes_left += 1;

	/* We return Not Active if we get any kind of error */
exit_is_tx_active:
	dev_dbg(&port->port->dev, "%s - return %d\n", __func__, bytes_left);

	kfree(lsr);
	kfree(oedb);
	return bytes_left;
}

static void chase_port(struct edgeport_port *port, unsigned long timeout,
								int flush)
{
	int baud_rate;
	struct tty_struct *tty = tty_port_tty_get(&port->port->port);
	struct usb_serial *serial = port->port->serial;
	wait_queue_t wait;
	unsigned long flags;

	if (!tty)
		return;

	if (!timeout)
		timeout = (HZ * EDGE_CLOSING_WAIT)/100;

	/* wait for data to drain from the buffer */
	spin_lock_irqsave(&port->ep_lock, flags);
	init_waitqueue_entry(&wait, current);
	add_wait_queue(&tty->write_wait, &wait);
	for (;;) {
		set_current_state(TASK_INTERRUPTIBLE);
		if (kfifo_len(&port->write_fifo) == 0
		|| timeout == 0 || signal_pending(current)
		|| serial->disconnected)
			/* disconnect */
			break;
		spin_unlock_irqrestore(&port->ep_lock, flags);
		timeout = schedule_timeout(timeout);
		spin_lock_irqsave(&port->ep_lock, flags);
	}
	set_current_state(TASK_RUNNING);
	remove_wait_queue(&tty->write_wait, &wait);
	if (flush)
		kfifo_reset_out(&port->write_fifo);
	spin_unlock_irqrestore(&port->ep_lock, flags);
	tty_kref_put(tty);

	/* wait for data to drain from the device */
	timeout += jiffies;
	while ((long)(jiffies - timeout) < 0 && !signal_pending(current)
						&& !serial->disconnected) {
		/* not disconnected */
		if (!tx_active(port))
			break;
		msleep(10);
	}

	/* disconnected */
	if (serial->disconnected)
		return;

	/* wait one more character time, based on baud rate */
	/* (tx_active doesn't seem to wait for the last byte) */
	baud_rate = port->baud_rate;
	if (baud_rate == 0)
		baud_rate = 50;
	msleep(max(1, DIV_ROUND_UP(10000, baud_rate)));
}

static int choose_config(struct usb_device *dev)
{
	/*
	 * There may be multiple configurations on this device, in which case
	 * we would need to read and parse all of them to find out which one
	 * we want. However, we just support one config at this point,
	 * configuration # 1, which is Config Descriptor 0.
	 */

	dev_dbg(&dev->dev, "%s - Number of Interfaces = %d\n",
		__func__, dev->config->desc.bNumInterfaces);
	dev_dbg(&dev->dev, "%s - MAX Power            = %d\n",
		__func__, dev->config->desc.bMaxPower * 2);

	if (dev->config->desc.bNumInterfaces != 1) {
		dev_err(&dev->dev, "%s - bNumInterfaces is not 1, ERROR!\n", __func__);
		return -ENODEV;
	}

	return 0;
}

static int read_rom(struct edgeport_serial *serial,
				int start_address, int length, __u8 *buffer)
{
	int status;

	if (serial->product_info.TiMode == TI_MODE_DOWNLOAD) {
		status = read_download_mem(serial->serial->dev,
					       start_address,
					       length,
					       serial->TI_I2C_Type,
					       buffer);
	} else {
		status = read_boot_mem(serial, start_address, length,
								buffer);
	}
	return status;
}

static int write_rom(struct edgeport_serial *serial, int start_address,
						int length, __u8 *buffer)
{
	if (serial->product_info.TiMode == TI_MODE_BOOT)
		return write_boot_mem(serial, start_address, length,
								buffer);

	if (serial->product_info.TiMode == TI_MODE_DOWNLOAD)
		return write_i2c_mem(serial, start_address, length,
						serial->TI_I2C_Type, buffer);
	return -EINVAL;
}



/* Read a descriptor header from I2C based on type */
static int get_descriptor_addr(struct edgeport_serial *serial,
				int desc_type, struct ti_i2c_desc *rom_desc)
{
	int start_address;
	int status;

	/* Search for requested descriptor in I2C */
	start_address = 2;
	do {
		status = read_rom(serial,
				   start_address,
				   sizeof(struct ti_i2c_desc),
				   (__u8 *)rom_desc);
		if (status)
			return 0;

		if (rom_desc->Type == desc_type)
			return start_address;

		start_address = start_address + sizeof(struct ti_i2c_desc)
							+ rom_desc->Size;

	} while ((start_address < TI_MAX_I2C_SIZE) && rom_desc->Type);

	return 0;
}

/* Validate descriptor checksum */
static int valid_csum(struct ti_i2c_desc *rom_desc, __u8 *buffer)
{
	__u16 i;
	__u8 cs = 0;

	for (i = 0; i < rom_desc->Size; i++)
		cs = (__u8)(cs + buffer[i]);

	if (cs != rom_desc->CheckSum) {
		pr_debug("%s - Mismatch %x - %x", __func__, rom_desc->CheckSum, cs);
		return -EINVAL;
	}
	return 0;
}

/* Make sure that the I2C image is good */
static int check_i2c_image(struct edgeport_serial *serial)
{
	struct device *dev = &serial->serial->dev->dev;
	int status = 0;
	struct ti_i2c_desc *rom_desc;
	int start_address = 2;
	__u8 *buffer;
	__u16 ttype;

	rom_desc = kmalloc(sizeof(*rom_desc), GFP_KERNEL);
	if (!rom_desc) {
		dev_err(dev, "%s - out of memory\n", __func__);
		return -ENOMEM;
	}
	buffer = kmalloc(TI_MAX_I2C_SIZE, GFP_KERNEL);
	if (!buffer) {
		dev_err(dev, "%s - out of memory when allocating buffer\n",
								__func__);
		kfree(rom_desc);
		return -ENOMEM;
	}

	/* Read the first byte (Signature0) must be 0x52 or 0x10 */
	status = read_rom(serial, 0, 1, buffer);
	if (status)
		goto out;

	if (*buffer != UMP5152 && *buffer != UMP3410) {
		dev_err(dev, "%s - invalid buffer signature\n", __func__);
		status = -ENODEV;
		goto out;
	}

	do {
		/* Validate the I2C */
		status = read_rom(serial,
				start_address,
				sizeof(struct ti_i2c_desc),
				(__u8 *)rom_desc);
		if (status)
			break;

		if ((start_address + sizeof(struct ti_i2c_desc) +
					rom_desc->Size) > TI_MAX_I2C_SIZE) {
			status = -ENODEV;
			dev_dbg(dev, "%s - structure too big, erroring out.\n", __func__);
			break;
		}

		dev_dbg(dev, "%s Type = 0x%x\n", __func__, rom_desc->Type);

		/* Skip type 2 record */
		ttype = rom_desc->Type & 0x0f;
		if (ttype != I2C_DESC_TYPE_FIRMWARE_BASIC
			&& ttype != I2C_DESC_TYPE_FIRMWARE_AUTO) {
			/* Read the descriptor data */
			status = read_rom(serial, start_address +
						sizeof(struct ti_i2c_desc),
						rom_desc->Size, buffer);
			if (status)
				break;

			status = valid_csum(rom_desc, buffer);
			if (status)
				break;
		}
		start_address = start_address + sizeof(struct ti_i2c_desc) +
								rom_desc->Size;

	} while ((rom_desc->Type != I2C_DESC_TYPE_ION) &&
				(start_address < TI_MAX_I2C_SIZE));

	if ((rom_desc->Type != I2C_DESC_TYPE_ION) ||
				(start_address > TI_MAX_I2C_SIZE))
		status = -ENODEV;

out:
	kfree(buffer);
	kfree(rom_desc);
	return status;
}

static int get_manuf_info(struct edgeport_serial *serial, __u8 *buffer)
{
	int status;
	int start_address;
	struct ti_i2c_desc *rom_desc;
	struct edge_ti_manuf_descriptor *desc;
	struct device *dev = &serial->serial->dev->dev;

	rom_desc = kmalloc(sizeof(*rom_desc), GFP_KERNEL);
	if (!rom_desc) {
		dev_err(dev, "%s - out of memory\n", __func__);
		return -ENOMEM;
	}
	start_address = get_descriptor_addr(serial, I2C_DESC_TYPE_ION,
								rom_desc);

	if (!start_address) {
		dev_dbg(dev, "%s - Edge Descriptor not found in I2C\n", __func__);
		status = -ENODEV;
		goto exit;
	}

	/* Read the descriptor data */
	status = read_rom(serial, start_address+sizeof(struct ti_i2c_desc),
						rom_desc->Size, buffer);
	if (status)
		goto exit;

	status = valid_csum(rom_desc, buffer);

	desc = (struct edge_ti_manuf_descriptor *)buffer;
	dev_dbg(dev, "%s - IonConfig      0x%x\n", __func__, desc->IonConfig);
	dev_dbg(dev, "%s - Version          %d\n", __func__, desc->Version);
	dev_dbg(dev, "%s - Cpu/Board      0x%x\n", __func__, desc->CpuRev_BoardRev);
	dev_dbg(dev, "%s - NumPorts         %d\n", __func__, desc->NumPorts);
	dev_dbg(dev, "%s - NumVirtualPorts  %d\n", __func__, desc->NumVirtualPorts);
	dev_dbg(dev, "%s - TotalPorts       %d\n", __func__, desc->TotalPorts);

exit:
	kfree(rom_desc);
	return status;
}

/* Build firmware header used for firmware update */
static int build_i2c_fw_hdr(__u8 *header, struct device *dev)
{
	__u8 *buffer;
	int buffer_size;
	int i;
	int err;
	__u8 cs = 0;
	struct ti_i2c_desc *i2c_header;
	struct ti_i2c_image_header *img_header;
	struct ti_i2c_firmware_rec *firmware_rec;
	const struct firmware *fw;
	const char *fw_name = "edgeport/down3.bin";

	/* In order to update the I2C firmware we must change the type 2 record
	 * to type 0xF2.  This will force the UMP to come up in Boot Mode.
	 * Then while in boot mode, the driver will download the latest
	 * firmware (padded to 15.5k) into the UMP ram.  And finally when the
	 * device comes back up in download mode the driver will cause the new
	 * firmware to be copied from the UMP Ram to I2C and the firmware will
	 * update the record type from 0xf2 to 0x02.
	 */

	/* Allocate a 15.5k buffer + 2 bytes for version number
	 * (Firmware Record) */
	buffer_size = (((1024 * 16) - 512 ) +
			sizeof(struct ti_i2c_firmware_rec));

	buffer = kmalloc(buffer_size, GFP_KERNEL);
	if (!buffer) {
		dev_err(dev, "%s - out of memory\n", __func__);
		return -ENOMEM;
	}

	// Set entire image of 0xffs
	memset(buffer, 0xff, buffer_size);

	err = request_firmware(&fw, fw_name, dev);
	if (err) {
		dev_err(dev, "Failed to load image \"%s\" err %d\n",
			fw_name, err);
		kfree(buffer);
		return err;
	}

	/* Save Download Version Number */
	OperationalMajorVersion = fw->data[0];
	OperationalMinorVersion = fw->data[1];
	OperationalBuildNumber = fw->data[2] | (fw->data[3] << 8);

	/* Copy version number into firmware record */
	firmware_rec = (struct ti_i2c_firmware_rec *)buffer;

	firmware_rec->Ver_Major	= OperationalMajorVersion;
	firmware_rec->Ver_Minor	= OperationalMinorVersion;

	/* Pointer to fw_down memory image */
	img_header = (struct ti_i2c_image_header *)&fw->data[4];

	memcpy(buffer + sizeof(struct ti_i2c_firmware_rec),
		&fw->data[4 + sizeof(struct ti_i2c_image_header)],
		le16_to_cpu(img_header->Length));

	release_firmware(fw);

	for (i=0; i < buffer_size; i++) {
		cs = (__u8)(cs + buffer[i]);
	}

	kfree(buffer);

	/* Build new header */
	i2c_header =  (struct ti_i2c_desc *)header;
	firmware_rec =  (struct ti_i2c_firmware_rec*)i2c_header->Data;

	i2c_header->Type	= I2C_DESC_TYPE_FIRMWARE_BLANK;
	i2c_header->Size	= (__u16)buffer_size;
	i2c_header->CheckSum	= cs;
	firmware_rec->Ver_Major	= OperationalMajorVersion;
	firmware_rec->Ver_Minor	= OperationalMinorVersion;

	return 0;
}

/* Try to figure out what type of I2c we have */
static int i2c_type_bootmode(struct edgeport_serial *serial)
{
	struct device *dev = &serial->serial->dev->dev;
	int status;
	u8 *data;

	data = kmalloc(1, GFP_KERNEL);
	if (!data) {
		dev_err(dev, "%s - out of memory\n", __func__);
		return -ENOMEM;
	}

	/* Try to read type 2 */
	status = ti_vread_sync(serial->serial->dev, UMPC_MEMORY_READ,
				DTK_ADDR_SPACE_I2C_TYPE_II, 0, data, 0x01);
	if (status)
		dev_dbg(dev, "%s - read 2 status error = %d\n", __func__, status);
	else
		dev_dbg(dev, "%s - read 2 data = 0x%x\n", __func__, *data);
	if ((!status) && (*data == UMP5152 || *data == UMP3410)) {
		dev_dbg(dev, "%s - ROM_TYPE_II\n", __func__);
		serial->TI_I2C_Type = DTK_ADDR_SPACE_I2C_TYPE_II;
		goto out;
	}

	/* Try to read type 3 */
	status = ti_vread_sync(serial->serial->dev, UMPC_MEMORY_READ,
				DTK_ADDR_SPACE_I2C_TYPE_III, 0,	data, 0x01);
	if (status)
		dev_dbg(dev, "%s - read 3 status error = %d\n", __func__, status);
	else
		dev_dbg(dev, "%s - read 2 data = 0x%x\n", __func__, *data);
	if ((!status) && (*data == UMP5152 || *data == UMP3410)) {
		dev_dbg(dev, "%s - ROM_TYPE_III\n", __func__);
		serial->TI_I2C_Type = DTK_ADDR_SPACE_I2C_TYPE_III;
		goto out;
	}

	dev_dbg(dev, "%s - Unknown\n", __func__);
	serial->TI_I2C_Type = DTK_ADDR_SPACE_I2C_TYPE_II;
	status = -ENODEV;
out:
	kfree(data);
	return status;
}

static int bulk_xfer(struct usb_serial *serial, void *buffer,
						int length, int *num_sent)
{
	int status;

	status = usb_bulk_msg(serial->dev,
			usb_sndbulkpipe(serial->dev,
				serial->port[0]->bulk_out_endpointAddress),
			buffer, length, num_sent, 1000);
	return status;
}

/* Download given firmware image to the device (IN BOOT MODE) */
static int download_code(struct edgeport_serial *serial, __u8 *image,
							int image_length)
{
	int status = 0;
	int pos;
	int transfer;
	int done;

	/* Transfer firmware image */
	for (pos = 0; pos < image_length; ) {
		/* Read the next buffer from file */
		transfer = image_length - pos;
		if (transfer > EDGE_FW_BULK_MAX_PACKET_SIZE)
			transfer = EDGE_FW_BULK_MAX_PACKET_SIZE;

		/* Transfer data */
		status = bulk_xfer(serial->serial, &image[pos],
							transfer, &done);
		if (status)
			break;
		/* Advance buffer pointer */
		pos += done;
	}

	return status;
}

/* FIXME!!! */
static int config_boot_dev(struct usb_device *dev)
{
	return 0;
}

static int ti_cpu_rev(struct edge_ti_manuf_descriptor *desc)
{
	return TI_GET_CPU_REVISION(desc->CpuRev_BoardRev);
}

/**
 * DownloadTIFirmware - Download run-time operating firmware to the TI5052
 *
 * This routine downloads the main operating code into the TI5052, using the
 * boot code already burned into E2PROM or ROM.
 */
static int download_fw(struct edgeport_serial *serial)
{
	struct device *dev = &serial->serial->dev->dev;
	int status = 0;
	int start_address;
	struct edge_ti_manuf_descriptor *ti_manuf_desc;
	struct usb_interface_descriptor *interface;
	int download_cur_ver;
	int download_new_ver;

	/* This routine is entered by both the BOOT mode and the Download mode
	 * We can determine which code is running by the reading the config
	 * descriptor and if we have only one bulk pipe it is in boot mode
	 */
	serial->product_info.hardware_type = HARDWARE_TYPE_TIUMP;

	/* Default to type 2 i2c */
	serial->TI_I2C_Type = DTK_ADDR_SPACE_I2C_TYPE_II;

	status = choose_config(serial->serial->dev);
	if (status)
		return status;

	interface = &serial->serial->interface->cur_altsetting->desc;
	if (!interface) {
		dev_err(dev, "%s - no interface set, error!\n", __func__);
		return -ENODEV;
	}

	/*
	 * Setup initial mode -- the default mode 0 is TI_MODE_CONFIGURING
	 * if we have more than one endpoint we are definitely in download
	 * mode
	 */
	if (interface->bNumEndpoints > 1)
		serial->product_info.TiMode = TI_MODE_DOWNLOAD;
	else
		/* Otherwise we will remain in configuring mode */
		serial->product_info.TiMode = TI_MODE_CONFIGURING;

	/********************************************************************/
	/* Download Mode */
	/********************************************************************/
	if (serial->product_info.TiMode == TI_MODE_DOWNLOAD) {
		struct ti_i2c_desc *rom_desc;

		dev_dbg(dev, "%s - RUNNING IN DOWNLOAD MODE\n", __func__);

		status = check_i2c_image(serial);
		if (status) {
			dev_dbg(dev, "%s - DOWNLOAD MODE -- BAD I2C\n", __func__);
			return status;
		}

		/* Validate Hardware version number
		 * Read Manufacturing Descriptor from TI Based Edgeport
		 */
		ti_manuf_desc = kmalloc(sizeof(*ti_manuf_desc), GFP_KERNEL);
		if (!ti_manuf_desc) {
			dev_err(dev, "%s - out of memory.\n", __func__);
			return -ENOMEM;
		}
		status = get_manuf_info(serial, (__u8 *)ti_manuf_desc);
		if (status) {
			kfree(ti_manuf_desc);
			return status;
		}

		/* Check version number of ION descriptor */
		if (!ignore_cpu_rev && ti_cpu_rev(ti_manuf_desc) < 2) {
			dev_dbg(dev, "%s - Wrong CPU Rev %d (Must be 2)\n",
				__func__, ti_cpu_rev(ti_manuf_desc));
			kfree(ti_manuf_desc);
			return -EINVAL;
  		}

		rom_desc = kmalloc(sizeof(*rom_desc), GFP_KERNEL);
		if (!rom_desc) {
			dev_err(dev, "%s - out of memory.\n", __func__);
			kfree(ti_manuf_desc);
			return -ENOMEM;
		}

		/* Search for type 2 record (firmware record) */
		start_address = get_descriptor_addr(serial,
				I2C_DESC_TYPE_FIRMWARE_BASIC, rom_desc);
		if (start_address != 0) {
			struct ti_i2c_firmware_rec *firmware_version;
			u8 *record;

			dev_dbg(dev, "%s - Found Type FIRMWARE (Type 2) record\n", __func__);

			firmware_version = kmalloc(sizeof(*firmware_version),
								GFP_KERNEL);
			if (!firmware_version) {
				dev_err(dev, "%s - out of memory.\n", __func__);
				kfree(rom_desc);
				kfree(ti_manuf_desc);
				return -ENOMEM;
			}

			/* Validate version number
			 * Read the descriptor data
			 */
			status = read_rom(serial, start_address +
					sizeof(struct ti_i2c_desc),
					sizeof(struct ti_i2c_firmware_rec),
					(__u8 *)firmware_version);
			if (status) {
				kfree(firmware_version);
				kfree(rom_desc);
				kfree(ti_manuf_desc);
				return status;
			}

			/* Check version number of download with current
			   version in I2c */
			download_cur_ver = (firmware_version->Ver_Major << 8) +
					   (firmware_version->Ver_Minor);
			download_new_ver = (OperationalMajorVersion << 8) +
					   (OperationalMinorVersion);

			dev_dbg(dev, "%s - >> FW Versions Device %d.%d  Driver %d.%d\n",
				__func__, firmware_version->Ver_Major,
				firmware_version->Ver_Minor,
				OperationalMajorVersion,
				OperationalMinorVersion);

			/* Check if we have an old version in the I2C and
			   update if necessary */
			if (download_cur_ver < download_new_ver) {
				dev_dbg(dev, "%s - Update I2C dld from %d.%d to %d.%d\n",
					__func__,
					firmware_version->Ver_Major,
					firmware_version->Ver_Minor,
					OperationalMajorVersion,
					OperationalMinorVersion);

				record = kmalloc(1, GFP_KERNEL);
				if (!record) {
					dev_err(dev, "%s - out of memory.\n",
							__func__);
					kfree(firmware_version);
					kfree(rom_desc);
					kfree(ti_manuf_desc);
					return -ENOMEM;
				}
				/* In order to update the I2C firmware we must
				 * change the type 2 record to type 0xF2. This
				 * will force the UMP to come up in Boot Mode.
				 * Then while in boot mode, the driver will
				 * download the latest firmware (padded to
				 * 15.5k) into the UMP ram. Finally when the
				 * device comes back up in download mode the
				 * driver will cause the new firmware to be
				 * copied from the UMP Ram to I2C and the
				 * firmware will update the record type from
				 * 0xf2 to 0x02.
				 */
				*record = I2C_DESC_TYPE_FIRMWARE_BLANK;

				/* Change the I2C Firmware record type to
				   0xf2 to trigger an update */
				status = write_rom(serial, start_address,
						sizeof(*record), record);
				if (status) {
					kfree(record);
					kfree(firmware_version);
					kfree(rom_desc);
					kfree(ti_manuf_desc);
					return status;
				}

				/* verify the write -- must do this in order
				 * for write to complete before we do the
				 * hardware reset
				 */
				status = read_rom(serial,
							start_address,
							sizeof(*record),
							record);
				if (status) {
					kfree(record);
					kfree(firmware_version);
					kfree(rom_desc);
					kfree(ti_manuf_desc);
					return status;
				}

				if (*record != I2C_DESC_TYPE_FIRMWARE_BLANK) {
					dev_err(dev, "%s - error resetting device\n", __func__);
					kfree(record);
					kfree(firmware_version);
					kfree(rom_desc);
					kfree(ti_manuf_desc);
					return -ENODEV;
				}

				dev_dbg(dev, "%s - HARDWARE RESET\n", __func__);

				/* Reset UMP -- Back to BOOT MODE */
				status = ti_vsend_sync(serial->serial->dev,
						UMPC_HARDWARE_RESET,
						0, 0, NULL, 0);

				dev_dbg(dev, "%s - HARDWARE RESET return %d\n", __func__, status);

				/* return an error on purpose. */
				kfree(record);
				kfree(firmware_version);
				kfree(rom_desc);
				kfree(ti_manuf_desc);
				return -ENODEV;
			}
			kfree(firmware_version);
		}
		/* Search for type 0xF2 record (firmware blank record) */
		else if ((start_address = get_descriptor_addr(serial, I2C_DESC_TYPE_FIRMWARE_BLANK, rom_desc)) != 0) {
#define HEADER_SIZE	(sizeof(struct ti_i2c_desc) + \
					sizeof(struct ti_i2c_firmware_rec))
			__u8 *header;
			__u8 *vheader;

			header = kmalloc(HEADER_SIZE, GFP_KERNEL);
			if (!header) {
				dev_err(dev, "%s - out of memory.\n", __func__);
				kfree(rom_desc);
				kfree(ti_manuf_desc);
				return -ENOMEM;
			}

			vheader = kmalloc(HEADER_SIZE, GFP_KERNEL);
			if (!vheader) {
				dev_err(dev, "%s - out of memory.\n", __func__);
				kfree(header);
				kfree(rom_desc);
				kfree(ti_manuf_desc);
				return -ENOMEM;
			}

			dev_dbg(dev, "%s - Found Type BLANK FIRMWARE (Type F2) record\n", __func__);

			/*
			 * In order to update the I2C firmware we must change
			 * the type 2 record to type 0xF2. This will force the
			 * UMP to come up in Boot Mode.  Then while in boot
			 * mode, the driver will download the latest firmware
			 * (padded to 15.5k) into the UMP ram. Finally when the
			 * device comes back up in download mode the driver
			 * will cause the new firmware to be copied from the
			 * UMP Ram to I2C and the firmware will update the
			 * record type from 0xf2 to 0x02.
			 */
			status = build_i2c_fw_hdr(header, dev);
			if (status) {
				kfree(vheader);
				kfree(header);
				kfree(rom_desc);
				kfree(ti_manuf_desc);
				return -EINVAL;
			}

			/* Update I2C with type 0xf2 record with correct
			   size and checksum */
			status = write_rom(serial,
						start_address,
						HEADER_SIZE,
						header);
			if (status) {
				kfree(vheader);
				kfree(header);
				kfree(rom_desc);
				kfree(ti_manuf_desc);
				return -EINVAL;
			}

			/* verify the write -- must do this in order for
			   write to complete before we do the hardware reset */
			status = read_rom(serial, start_address,
							HEADER_SIZE, vheader);

			if (status) {
				dev_dbg(dev, "%s - can't read header back\n", __func__);
				kfree(vheader);
				kfree(header);
				kfree(rom_desc);
				kfree(ti_manuf_desc);
				return status;
			}
			if (memcmp(vheader, header, HEADER_SIZE)) {
				dev_dbg(dev, "%s - write download record failed\n", __func__);
				kfree(vheader);
				kfree(header);
				kfree(rom_desc);
				kfree(ti_manuf_desc);
				return -EINVAL;
			}

			kfree(vheader);
			kfree(header);

			dev_dbg(dev, "%s - Start firmware update\n", __func__);

			/* Tell firmware to copy download image into I2C */
			status = ti_vsend_sync(serial->serial->dev,
					UMPC_COPY_DNLD_TO_I2C, 0, 0, NULL, 0);

		  	dev_dbg(dev, "%s - Update complete 0x%x\n", __func__, status);
			if (status) {
				dev_err(dev,
					"%s - UMPC_COPY_DNLD_TO_I2C failed\n",
								__func__);
				kfree(rom_desc);
				kfree(ti_manuf_desc);
				return status;
			}
		}

		// The device is running the download code
		kfree(rom_desc);
		kfree(ti_manuf_desc);
		return 0;
	}

	/********************************************************************/
	/* Boot Mode */
	/********************************************************************/
	dev_dbg(dev, "%s - RUNNING IN BOOT MODE\n", __func__);

	/* Configure the TI device so we can use the BULK pipes for download */
	status = config_boot_dev(serial->serial->dev);
	if (status)
		return status;

	if (le16_to_cpu(serial->serial->dev->descriptor.idVendor)
							!= USB_VENDOR_ID_ION) {
		dev_dbg(dev, "%s - VID = 0x%x\n", __func__,
			le16_to_cpu(serial->serial->dev->descriptor.idVendor));
		serial->TI_I2C_Type = DTK_ADDR_SPACE_I2C_TYPE_II;
		goto stayinbootmode;
	}

	/* We have an ION device (I2c Must be programmed)
	   Determine I2C image type */
	if (i2c_type_bootmode(serial))
		goto stayinbootmode;

	/* Check for ION Vendor ID and that the I2C is valid */
	if (!check_i2c_image(serial)) {
		struct ti_i2c_image_header *header;
		int i;
		__u8 cs = 0;
		__u8 *buffer;
		int buffer_size;
		int err;
		const struct firmware *fw;
		const char *fw_name = "edgeport/down3.bin";

		/* Validate Hardware version number
		 * Read Manufacturing Descriptor from TI Based Edgeport
		 */
		ti_manuf_desc = kmalloc(sizeof(*ti_manuf_desc), GFP_KERNEL);
		if (!ti_manuf_desc) {
			dev_err(dev, "%s - out of memory.\n", __func__);
			return -ENOMEM;
		}
		status = get_manuf_info(serial, (__u8 *)ti_manuf_desc);
		if (status) {
			kfree(ti_manuf_desc);
			goto stayinbootmode;
		}

		/* Check for version 2 */
		if (!ignore_cpu_rev && ti_cpu_rev(ti_manuf_desc) < 2) {
			dev_dbg(dev, "%s - Wrong CPU Rev %d (Must be 2)\n",
				__func__, ti_cpu_rev(ti_manuf_desc));
			kfree(ti_manuf_desc);
			goto stayinbootmode;
		}

		kfree(ti_manuf_desc);

		/*
		 * In order to update the I2C firmware we must change the type
		 * 2 record to type 0xF2. This will force the UMP to come up
		 * in Boot Mode.  Then while in boot mode, the driver will
		 * download the latest firmware (padded to 15.5k) into the
		 * UMP ram. Finally when the device comes back up in download
		 * mode the driver will cause the new firmware to be copied
		 * from the UMP Ram to I2C and the firmware will update the
		 * record type from 0xf2 to 0x02.
		 *
		 * Do we really have to copy the whole firmware image,
		 * or could we do this in place!
		 */

		/* Allocate a 15.5k buffer + 3 byte header */
		buffer_size = (((1024 * 16) - 512) +
					sizeof(struct ti_i2c_image_header));
		buffer = kmalloc(buffer_size, GFP_KERNEL);
		if (!buffer) {
			dev_err(dev, "%s - out of memory\n", __func__);
			return -ENOMEM;
		}

		/* Initialize the buffer to 0xff (pad the buffer) */
		memset(buffer, 0xff, buffer_size);

		err = request_firmware(&fw, fw_name, dev);
		if (err) {
			dev_err(dev, "Failed to load image \"%s\" err %d\n",
				fw_name, err);
			kfree(buffer);
			return err;
		}
		memcpy(buffer, &fw->data[4], fw->size - 4);
		release_firmware(fw);

		for (i = sizeof(struct ti_i2c_image_header);
				i < buffer_size; i++) {
			cs = (__u8)(cs + buffer[i]);
		}

		header = (struct ti_i2c_image_header *)buffer;

		/* update length and checksum after padding */
		header->Length 	 = cpu_to_le16((__u16)(buffer_size -
					sizeof(struct ti_i2c_image_header)));
		header->CheckSum = cs;

		/* Download the operational code  */
		dev_dbg(dev, "%s - Downloading operational code image (TI UMP)\n", __func__);
		status = download_code(serial, buffer, buffer_size);

		kfree(buffer);

		if (status) {
			dev_dbg(dev, "%s - Error downloading operational code image\n", __func__);
			return status;
		}

		/* Device will reboot */
		serial->product_info.TiMode = TI_MODE_TRANSITIONING;

		dev_dbg(dev, "%s - Download successful -- Device rebooting...\n", __func__);

		/* return an error on purpose */
		return -ENODEV;
	}

stayinbootmode:
	/* Eprom is invalid or blank stay in boot mode */
	dev_dbg(dev, "%s - STAYING IN BOOT MODE\n", __func__);
	serial->product_info.TiMode = TI_MODE_BOOT;

	return 0;
}


static int ti_do_config(struct edgeport_port *port, int feature, int on)
{
	int port_number = port->port->number - port->port->serial->minor;
	on = !!on;	/* 1 or 0 not bitmask */
	return send_cmd(port->port->serial->dev,
			feature, (__u8)(UMPM_UART1_PORT + port_number),
			on, NULL, 0);
}


static int restore_mcr(struct edgeport_port *port, __u8 mcr)
{
	int status = 0;

	dev_dbg(&port->port->dev, "%s - %x\n", __func__, mcr);

	status = ti_do_config(port, UMPC_SET_CLR_DTR, mcr & MCR_DTR);
	if (status)
		return status;
	status = ti_do_config(port, UMPC_SET_CLR_RTS, mcr & MCR_RTS);
	if (status)
		return status;
	return ti_do_config(port, UMPC_SET_CLR_LOOPBACK, mcr & MCR_LOOPBACK);
}

/* Convert TI LSR to standard UART flags */
static __u8 map_line_status(__u8 ti_lsr)
{
	__u8 lsr = 0;

#define MAP_FLAG(flagUmp, flagUart)    \
	if (ti_lsr & flagUmp) \
		lsr |= flagUart;

	MAP_FLAG(UMP_UART_LSR_OV_MASK, LSR_OVER_ERR)	/* overrun */
	MAP_FLAG(UMP_UART_LSR_PE_MASK, LSR_PAR_ERR)	/* parity error */
	MAP_FLAG(UMP_UART_LSR_FE_MASK, LSR_FRM_ERR)	/* framing error */
	MAP_FLAG(UMP_UART_LSR_BR_MASK, LSR_BREAK)	/* break detected */
	MAP_FLAG(UMP_UART_LSR_RX_MASK, LSR_RX_AVAIL)	/* rx data available */
	MAP_FLAG(UMP_UART_LSR_TX_MASK, LSR_TX_EMPTY)	/* tx hold reg empty */

#undef MAP_FLAG

	return lsr;
}

static void handle_new_msr(struct edgeport_port *edge_port, __u8 msr)
{
	struct async_icount *icount;
	struct tty_struct *tty;

	dev_dbg(&edge_port->port->dev, "%s - %02x\n", __func__, msr);

	if (msr & (EDGEPORT_MSR_DELTA_CTS | EDGEPORT_MSR_DELTA_DSR |
			EDGEPORT_MSR_DELTA_RI | EDGEPORT_MSR_DELTA_CD)) {
		icount = &edge_port->icount;

		/* update input line counters */
		if (msr & EDGEPORT_MSR_DELTA_CTS)
			icount->cts++;
		if (msr & EDGEPORT_MSR_DELTA_DSR)
			icount->dsr++;
		if (msr & EDGEPORT_MSR_DELTA_CD)
			icount->dcd++;
		if (msr & EDGEPORT_MSR_DELTA_RI)
			icount->rng++;
		wake_up_interruptible(&edge_port->delta_msr_wait);
	}

	/* Save the new modem status */
	edge_port->shadow_msr = msr & 0xf0;

	tty = tty_port_tty_get(&edge_port->port->port);
	/* handle CTS flow control */
	if (tty && C_CRTSCTS(tty)) {
		if (msr & EDGEPORT_MSR_CTS) {
			tty->hw_stopped = 0;
			tty_wakeup(tty);
		} else {
			tty->hw_stopped = 1;
		}
	}
	tty_kref_put(tty);
}

static void handle_new_lsr(struct edgeport_port *edge_port, int lsr_data,
							__u8 lsr, __u8 data)
{
	struct async_icount *icount;
	__u8 new_lsr = (__u8)(lsr & (__u8)(LSR_OVER_ERR | LSR_PAR_ERR |
						LSR_FRM_ERR | LSR_BREAK));
	struct tty_struct *tty;

	dev_dbg(&edge_port->port->dev, "%s - %02x\n", __func__, new_lsr);

	edge_port->shadow_lsr = lsr;

	if (new_lsr & LSR_BREAK)
		/*
		 * Parity and Framing errors only count if they
		 * occur exclusive of a break being received.
		 */
		new_lsr &= (__u8)(LSR_OVER_ERR | LSR_BREAK);

	/* Place LSR data byte into Rx buffer */
	if (lsr_data) {
		tty = tty_port_tty_get(&edge_port->port->port);
		if (tty) {
			edge_tty_recv(&edge_port->port->dev, tty, &data, 1);
			tty_kref_put(tty);
		}
	}

	/* update input line counters */
	icount = &edge_port->icount;
	if (new_lsr & LSR_BREAK)
		icount->brk++;
	if (new_lsr & LSR_OVER_ERR)
		icount->overrun++;
	if (new_lsr & LSR_PAR_ERR)
		icount->parity++;
	if (new_lsr & LSR_FRM_ERR)
		icount->frame++;
}


static void edge_interrupt_callback(struct urb *urb)
{
	struct edgeport_serial *edge_serial = urb->context;
	struct usb_serial_port *port;
	struct edgeport_port *edge_port;
	struct device *dev;
	unsigned char *data = urb->transfer_buffer;
	int length = urb->actual_length;
	int port_number;
	int function;
	int retval;
	__u8 lsr;
	__u8 msr;
	int status = urb->status;

	switch (status) {
	case 0:
		/* success */
		break;
	case -ECONNRESET:
	case -ENOENT:
	case -ESHUTDOWN:
		/* this urb is terminated, clean up */
		dev_dbg(&urb->dev->dev, "%s - urb shutting down with status: %d\n",
		    __func__, status);
		return;
	default:
		dev_err(&urb->dev->dev, "%s - nonzero urb status received: "
			"%d\n", __func__, status);
		goto exit;
	}

	if (!length) {
		dev_dbg(&urb->dev->dev, "%s - no data in urb\n", __func__);
		goto exit;
	}

	dev = &edge_serial->serial->dev->dev;
	usb_serial_debug_data(dev, __func__, length, data);

	if (length != 2) {
		dev_dbg(dev, "%s - expecting packet of size 2, got %d\n", __func__, length);
		goto exit;
	}

	port_number = TIUMP_GET_PORT_FROM_CODE(data[0]);
	function    = TIUMP_GET_FUNC_FROM_CODE(data[0]);
	dev_dbg(dev, "%s - port_number %d, function %d, info 0x%x\n", __func__,
		port_number, function, data[1]);
	port = edge_serial->serial->port[port_number];
	edge_port = usb_get_serial_port_data(port);
	if (!edge_port) {
		dev_dbg(dev, "%s - edge_port not found\n", __func__);
		return;
	}
	switch (function) {
	case TIUMP_INTERRUPT_CODE_LSR:
		lsr = map_line_status(data[1]);
		if (lsr & UMP_UART_LSR_DATA_MASK) {
			/* Save the LSR event for bulk read
			   completion routine */
			dev_dbg(dev, "%s - LSR Event Port %u LSR Status = %02x\n",
				__func__, port_number, lsr);
			edge_port->lsr_event = 1;
			edge_port->lsr_mask = lsr;
		} else {
			dev_dbg(dev, "%s - ===== Port %d LSR Status = %02x ======\n",
				__func__, port_number, lsr);
			handle_new_lsr(edge_port, 0, lsr, 0);
		}
		break;

	case TIUMP_INTERRUPT_CODE_MSR:	/* MSR */
		/* Copy MSR from UMP */
		msr = data[1];
		dev_dbg(dev, "%s - ===== Port %u MSR Status = %02x ======\n",
			__func__, port_number, msr);
		handle_new_msr(edge_port, msr);
		break;

	default:
		dev_err(&urb->dev->dev,
			"%s - Unknown Interrupt code from UMP %x\n",
			__func__, data[1]);
		break;

	}

exit:
	retval = usb_submit_urb(urb, GFP_ATOMIC);
	if (retval)
		dev_err(&urb->dev->dev,
			"%s - usb_submit_urb failed with result %d\n",
			 __func__, retval);
}

static void edge_bulk_in_callback(struct urb *urb)
{
	struct edgeport_port *edge_port = urb->context;
	struct device *dev = &edge_port->port->dev;
	unsigned char *data = urb->transfer_buffer;
	struct tty_struct *tty;
	int retval = 0;
	int port_number;
	int status = urb->status;

	switch (status) {
	case 0:
		/* success */
		break;
	case -ECONNRESET:
	case -ENOENT:
	case -ESHUTDOWN:
		/* this urb is terminated, clean up */
		dev_dbg(&urb->dev->dev, "%s - urb shutting down with status: %d\n", __func__, status);
		return;
	default:
		dev_err(&urb->dev->dev, "%s - nonzero read bulk status received: %d\n", __func__, status);
	}

	if (status == -EPIPE)
		goto exit;

	if (status) {
		dev_err(&urb->dev->dev, "%s - stopping read!\n", __func__);
		return;
	}

	port_number = edge_port->port->number - edge_port->port->serial->minor;

	if (edge_port->lsr_event) {
		edge_port->lsr_event = 0;
		dev_dbg(dev, "%s ===== Port %u LSR Status = %02x, Data = %02x ======\n",
			__func__, port_number, edge_port->lsr_mask, *data);
		handle_new_lsr(edge_port, 1, edge_port->lsr_mask, *data);
		/* Adjust buffer length/pointer */
		--urb->actual_length;
		++data;
	}

	tty = tty_port_tty_get(&edge_port->port->port);
	if (tty && urb->actual_length) {
		usb_serial_debug_data(dev, __func__, urb->actual_length, data);
		if (edge_port->close_pending)
			dev_dbg(dev, "%s - close pending, dropping data on the floor\n",
								__func__);
		else
			edge_tty_recv(dev, tty, data, urb->actual_length);
		edge_port->icount.rx += urb->actual_length;
	}
	tty_kref_put(tty);

exit:
	/* continue read unless stopped */
	spin_lock(&edge_port->ep_lock);
	if (edge_port->ep_read_urb_state == EDGE_READ_URB_RUNNING)
		retval = usb_submit_urb(urb, GFP_ATOMIC);
	else if (edge_port->ep_read_urb_state == EDGE_READ_URB_STOPPING)
		edge_port->ep_read_urb_state = EDGE_READ_URB_STOPPED;

	spin_unlock(&edge_port->ep_lock);
	if (retval)
		dev_err(dev, "%s - usb_submit_urb failed with result %d\n", __func__, retval);
}

static void edge_tty_recv(struct device *dev, struct tty_struct *tty,
					unsigned char *data, int length)
{
	int queued;

	queued = tty_insert_flip_string(tty, data, length);
	if (queued < length)
		dev_err(dev, "%s - dropping data, %d bytes lost\n",
			__func__, length - queued);
	tty_flip_buffer_push(tty);
}

static void edge_bulk_out_callback(struct urb *urb)
{
	struct usb_serial_port *port = urb->context;
	struct edgeport_port *edge_port = usb_get_serial_port_data(port);
	int status = urb->status;
	struct tty_struct *tty;

	edge_port->ep_write_urb_in_use = 0;

	switch (status) {
	case 0:
		/* success */
		break;
	case -ECONNRESET:
	case -ENOENT:
	case -ESHUTDOWN:
		/* this urb is terminated, clean up */
		dev_dbg(&urb->dev->dev, "%s - urb shutting down with status: %d\n",
		    __func__, status);
		return;
	default:
		dev_err_console(port, "%s - nonzero write bulk status "
			"received: %d\n", __func__, status);
	}

	/* send any buffered data */
	tty = tty_port_tty_get(&port->port);
	edge_send(tty);
	tty_kref_put(tty);
}

static int edge_open(struct tty_struct *tty, struct usb_serial_port *port)
{
	struct edgeport_port *edge_port = usb_get_serial_port_data(port);
	struct edgeport_serial *edge_serial;
	struct usb_device *dev;
	struct urb *urb;
	int port_number;
	int status;
	u16 open_settings;
	u8 transaction_timeout;

	if (edge_port == NULL)
		return -ENODEV;

	port_number = port->number - port->serial->minor;
	switch (port_number) {
	case 0:
		edge_port->uart_base = UMPMEM_BASE_UART1;
		edge_port->dma_address = UMPD_OEDB1_ADDRESS;
		break;
	case 1:
		edge_port->uart_base = UMPMEM_BASE_UART2;
		edge_port->dma_address = UMPD_OEDB2_ADDRESS;
		break;
	default:
		dev_err(&port->dev, "Unknown port number!!!\n");
		return -ENODEV;
	}

	dev_dbg(&port->dev, "%s - port_number = %d, uart_base = %04x, dma_address = %04x\n",
		__func__, port_number, edge_port->uart_base, edge_port->dma_address);

	dev = port->serial->dev;

	memset(&(edge_port->icount), 0x00, sizeof(edge_port->icount));
	init_waitqueue_head(&edge_port->delta_msr_wait);

	/* turn off loopback */
	status = ti_do_config(edge_port, UMPC_SET_CLR_LOOPBACK, 0);
	if (status) {
		dev_err(&port->dev,
				"%s - cannot send clear loopback command, %d\n",
			__func__, status);
		return status;
	}

	/* set up the port settings */
	if (tty)
		edge_set_termios(tty, port, &tty->termios);

	/* open up the port */

	/* milliseconds to timeout for DMA transfer */
	transaction_timeout = 2;

	edge_port->ump_read_timeout =
				max(20, ((transaction_timeout * 3) / 2));

	/* milliseconds to timeout for DMA transfer */
	open_settings = (u8)(UMP_DMA_MODE_CONTINOUS |
			     UMP_PIPE_TRANS_TIMEOUT_ENA |
			     (transaction_timeout << 2));

	dev_dbg(&port->dev, "%s - Sending UMPC_OPEN_PORT\n", __func__);

	/* Tell TI to open and start the port */
	status = send_cmd(dev, UMPC_OPEN_PORT,
		(u8)(UMPM_UART1_PORT + port_number), open_settings, NULL, 0);
	if (status) {
		dev_err(&port->dev, "%s - cannot send open command, %d\n",
							__func__, status);
		return status;
	}

	/* Start the DMA? */
	status = send_cmd(dev, UMPC_START_PORT,
		(u8)(UMPM_UART1_PORT + port_number), 0, NULL, 0);
	if (status) {
		dev_err(&port->dev, "%s - cannot send start DMA command, %d\n",
							__func__, status);
		return status;
	}

	/* Clear TX and RX buffers in UMP */
	status = purge_port(port, UMP_PORT_DIR_OUT | UMP_PORT_DIR_IN);
	if (status) {
		dev_err(&port->dev,
			"%s - cannot send clear buffers command, %d\n",
			__func__, status);
		return status;
	}

	/* Read Initial MSR */
	status = ti_vread_sync(dev, UMPC_READ_MSR, 0,
				(__u16)(UMPM_UART1_PORT + port_number),
				&edge_port->shadow_msr, 1);
	if (status) {
		dev_err(&port->dev, "%s - cannot send read MSR command, %d\n",
							__func__, status);
		return status;
	}

	dev_dbg(&port->dev, "ShadowMSR 0x%X\n", edge_port->shadow_msr);

	/* Set Initial MCR */
	edge_port->shadow_mcr = MCR_RTS | MCR_DTR;
	dev_dbg(&port->dev, "ShadowMCR 0x%X\n", edge_port->shadow_mcr);

	edge_serial = edge_port->edge_serial;
	if (mutex_lock_interruptible(&edge_serial->es_lock))
		return -ERESTARTSYS;
	if (edge_serial->num_ports_open == 0) {
		/* we are the first port to open, post the interrupt urb */
		urb = edge_serial->serial->port[0]->interrupt_in_urb;
		if (!urb) {
			dev_err(&port->dev,
				"%s - no interrupt urb present, exiting\n",
				__func__);
			status = -EINVAL;
			goto release_es_lock;
		}
		urb->context = edge_serial;
		status = usb_submit_urb(urb, GFP_KERNEL);
		if (status) {
			dev_err(&port->dev,
				"%s - usb_submit_urb failed with value %d\n",
					__func__, status);
			goto release_es_lock;
		}
	}

	/*
	 * reset the data toggle on the bulk endpoints to work around bug in
	 * host controllers where things get out of sync some times
	 */
	usb_clear_halt(dev, port->write_urb->pipe);
	usb_clear_halt(dev, port->read_urb->pipe);

	/* start up our bulk read urb */
	urb = port->read_urb;
	if (!urb) {
		dev_err(&port->dev, "%s - no read urb present, exiting\n",
								__func__);
		status = -EINVAL;
		goto unlink_int_urb;
	}
	edge_port->ep_read_urb_state = EDGE_READ_URB_RUNNING;
	urb->context = edge_port;
	status = usb_submit_urb(urb, GFP_KERNEL);
	if (status) {
		dev_err(&port->dev,
			"%s - read bulk usb_submit_urb failed with value %d\n",
				__func__, status);
		goto unlink_int_urb;
	}

	++edge_serial->num_ports_open;

	goto release_es_lock;

unlink_int_urb:
	if (edge_port->edge_serial->num_ports_open == 0)
		usb_kill_urb(port->serial->port[0]->interrupt_in_urb);
release_es_lock:
	mutex_unlock(&edge_serial->es_lock);
	return status;
}

static void edge_close(struct usb_serial_port *port)
{
	struct edgeport_serial *edge_serial;
	struct edgeport_port *edge_port;
	struct usb_serial *serial = port->serial;
	int port_number;

	edge_serial = usb_get_serial_data(port->serial);
	edge_port = usb_get_serial_port_data(port);
	if (edge_serial == NULL || edge_port == NULL)
		return;

	/* The bulkreadcompletion routine will check
	 * this flag and dump add read data */
	edge_port->close_pending = 1;

	/* chase the port close and flush */
	chase_port(edge_port, (HZ * closing_wait) / 100, 1);

	usb_kill_urb(port->read_urb);
	usb_kill_urb(port->write_urb);
	edge_port->ep_write_urb_in_use = 0;

	/* assuming we can still talk to the device,
	 * send a close port command to it */
	dev_dbg(&port->dev, "%s - send umpc_close_port\n", __func__);
	port_number = port->number - port->serial->minor;

	mutex_lock(&serial->disc_mutex);
	if (!serial->disconnected) {
		send_cmd(serial->dev,
				     UMPC_CLOSE_PORT,
				     (__u8)(UMPM_UART1_PORT + port_number),
				     0,
				     NULL,
				     0);
	}
	mutex_unlock(&serial->disc_mutex);

	mutex_lock(&edge_serial->es_lock);
	--edge_port->edge_serial->num_ports_open;
	if (edge_port->edge_serial->num_ports_open <= 0) {
		/* last port is now closed, let's shut down our interrupt urb */
		usb_kill_urb(port->serial->port[0]->interrupt_in_urb);
		edge_port->edge_serial->num_ports_open = 0;
	}
	mutex_unlock(&edge_serial->es_lock);
	edge_port->close_pending = 0;
}

static int edge_write(struct tty_struct *tty, struct usb_serial_port *port,
				const unsigned char *data, int count)
{
	struct edgeport_port *edge_port = usb_get_serial_port_data(port);

	if (count == 0) {
		dev_dbg(&port->dev, "%s - write request of 0 bytes\n", __func__);
		return 0;
	}

	if (edge_port == NULL)
		return -ENODEV;
	if (edge_port->close_pending == 1)
		return -ENODEV;

	count = kfifo_in_locked(&edge_port->write_fifo, data, count,
							&edge_port->ep_lock);
	edge_send(tty);

	return count;
}

static void edge_send(struct tty_struct *tty)
{
	struct usb_serial_port *port = tty->driver_data;
	int count, result;
	struct edgeport_port *edge_port = usb_get_serial_port_data(port);
	unsigned long flags;

	spin_lock_irqsave(&edge_port->ep_lock, flags);

	if (edge_port->ep_write_urb_in_use) {
		spin_unlock_irqrestore(&edge_port->ep_lock, flags);
		return;
	}

	count = kfifo_out(&edge_port->write_fifo,
				port->write_urb->transfer_buffer,
				port->bulk_out_size);

	if (count == 0) {
		spin_unlock_irqrestore(&edge_port->ep_lock, flags);
		return;
	}

	edge_port->ep_write_urb_in_use = 1;

	spin_unlock_irqrestore(&edge_port->ep_lock, flags);

	usb_serial_debug_data(&port->dev, __func__, count, port->write_urb->transfer_buffer);

	/* set up our urb */
	port->write_urb->transfer_buffer_length = count;

	/* send the data out the bulk port */
	result = usb_submit_urb(port->write_urb, GFP_ATOMIC);
	if (result) {
		dev_err_console(port,
			"%s - failed submitting write urb, error %d\n",
				__func__, result);
		edge_port->ep_write_urb_in_use = 0;
		/* TODO: reschedule edge_send */
	} else
		edge_port->icount.tx += count;

	/* wakeup any process waiting for writes to complete */
	/* there is now more room in the buffer for new writes */
	if (tty)
		tty_wakeup(tty);
}

static int edge_write_room(struct tty_struct *tty)
{
	struct usb_serial_port *port = tty->driver_data;
	struct edgeport_port *edge_port = usb_get_serial_port_data(port);
	int room = 0;
	unsigned long flags;

	if (edge_port == NULL)
		return 0;
	if (edge_port->close_pending == 1)
		return 0;

	spin_lock_irqsave(&edge_port->ep_lock, flags);
	room = kfifo_avail(&edge_port->write_fifo);
	spin_unlock_irqrestore(&edge_port->ep_lock, flags);

	dev_dbg(&port->dev, "%s - returns %d\n", __func__, room);
	return room;
}

static int edge_chars_in_buffer(struct tty_struct *tty)
{
	struct usb_serial_port *port = tty->driver_data;
	struct edgeport_port *edge_port = usb_get_serial_port_data(port);
	int chars = 0;
	unsigned long flags;

	if (edge_port == NULL)
		return 0;
	if (edge_port->close_pending == 1)
		return 0;

	spin_lock_irqsave(&edge_port->ep_lock, flags);
	chars = kfifo_len(&edge_port->write_fifo);
	spin_unlock_irqrestore(&edge_port->ep_lock, flags);

	dev_dbg(&port->dev, "%s - returns %d\n", __func__, chars);
	return chars;
}

static void edge_throttle(struct tty_struct *tty)
{
	struct usb_serial_port *port = tty->driver_data;
	struct edgeport_port *edge_port = usb_get_serial_port_data(port);
	int status;

	if (edge_port == NULL)
		return;

	/* if we are implementing XON/XOFF, send the stop character */
	if (I_IXOFF(tty)) {
		unsigned char stop_char = STOP_CHAR(tty);
		status = edge_write(tty, port, &stop_char, 1);
		if (status <= 0) {
			dev_err(&port->dev, "%s - failed to write stop character, %d\n", __func__, status);
		}
	}

	/* if we are implementing RTS/CTS, stop reads */
	/* and the Edgeport will clear the RTS line */
	if (C_CRTSCTS(tty))
		stop_read(edge_port);

}

static void edge_unthrottle(struct tty_struct *tty)
{
	struct usb_serial_port *port = tty->driver_data;
	struct edgeport_port *edge_port = usb_get_serial_port_data(port);
	int status;

	if (edge_port == NULL)
		return;

	/* if we are implementing XON/XOFF, send the start character */
	if (I_IXOFF(tty)) {
		unsigned char start_char = START_CHAR(tty);
		status = edge_write(tty, port, &start_char, 1);
		if (status <= 0) {
			dev_err(&port->dev, "%s - failed to write start character, %d\n", __func__, status);
		}
	}
	/* if we are implementing RTS/CTS, restart reads */
	/* are the Edgeport will assert the RTS line */
	if (C_CRTSCTS(tty)) {
		status = restart_read(edge_port);
		if (status)
			dev_err(&port->dev,
				"%s - read bulk usb_submit_urb failed: %d\n",
							__func__, status);
	}

}

static void stop_read(struct edgeport_port *edge_port)
{
	unsigned long flags;

	spin_lock_irqsave(&edge_port->ep_lock, flags);

	if (edge_port->ep_read_urb_state == EDGE_READ_URB_RUNNING)
		edge_port->ep_read_urb_state = EDGE_READ_URB_STOPPING;
	edge_port->shadow_mcr &= ~MCR_RTS;

	spin_unlock_irqrestore(&edge_port->ep_lock, flags);
}

static int restart_read(struct edgeport_port *edge_port)
{
	struct urb *urb;
	int status = 0;
	unsigned long flags;

	spin_lock_irqsave(&edge_port->ep_lock, flags);

	if (edge_port->ep_read_urb_state == EDGE_READ_URB_STOPPED) {
		urb = edge_port->port->read_urb;
		status = usb_submit_urb(urb, GFP_ATOMIC);
	}
	edge_port->ep_read_urb_state = EDGE_READ_URB_RUNNING;
	edge_port->shadow_mcr |= MCR_RTS;

	spin_unlock_irqrestore(&edge_port->ep_lock, flags);

	return status;
}

static void change_port_settings(struct tty_struct *tty,
		struct edgeport_port *edge_port, struct ktermios *old_termios)
{
	struct device *dev = &edge_port->port->dev;
	struct ump_uart_config *config;
	int baud;
	unsigned cflag;
	int status;
	int port_number = edge_port->port->number -
					edge_port->port->serial->minor;

	dev_dbg(dev, "%s - port %d\n", __func__, edge_port->port->number);

	config = kmalloc (sizeof (*config), GFP_KERNEL);
	if (!config) {
		tty->termios = *old_termios;
		dev_err(dev, "%s - out of memory\n", __func__);
		return;
	}

	cflag = tty->termios.c_cflag;

	config->wFlags = 0;

	/* These flags must be set */
	config->wFlags |= UMP_MASK_UART_FLAGS_RECEIVE_MS_INT;
	config->wFlags |= UMP_MASK_UART_FLAGS_AUTO_START_ON_ERR;
	config->bUartMode = (__u8)(edge_port->bUartMode);

	switch (cflag & CSIZE) {
	case CS5:
		    config->bDataBits = UMP_UART_CHAR5BITS;
		    dev_dbg(dev, "%s - data bits = 5\n", __func__);
		    break;
	case CS6:
		    config->bDataBits = UMP_UART_CHAR6BITS;
		    dev_dbg(dev, "%s - data bits = 6\n", __func__);
		    break;
	case CS7:
		    config->bDataBits = UMP_UART_CHAR7BITS;
		    dev_dbg(dev, "%s - data bits = 7\n", __func__);
		    break;
	default:
	case CS8:
		    config->bDataBits = UMP_UART_CHAR8BITS;
		    dev_dbg(dev, "%s - data bits = 8\n", __func__);
			    break;
	}

	if (cflag & PARENB) {
		if (cflag & PARODD) {
			config->wFlags |= UMP_MASK_UART_FLAGS_PARITY;
			config->bParity = UMP_UART_ODDPARITY;
			dev_dbg(dev, "%s - parity = odd\n", __func__);
		} else {
			config->wFlags |= UMP_MASK_UART_FLAGS_PARITY;
			config->bParity = UMP_UART_EVENPARITY;
			dev_dbg(dev, "%s - parity = even\n", __func__);
		}
	} else {
		config->bParity = UMP_UART_NOPARITY;
		dev_dbg(dev, "%s - parity = none\n", __func__);
	}

	if (cflag & CSTOPB) {
		config->bStopBits = UMP_UART_STOPBIT2;
		dev_dbg(dev, "%s - stop bits = 2\n", __func__);
	} else {
		config->bStopBits = UMP_UART_STOPBIT1;
		dev_dbg(dev, "%s - stop bits = 1\n", __func__);
	}

	/* figure out the flow control settings */
	if (cflag & CRTSCTS) {
		config->wFlags |= UMP_MASK_UART_FLAGS_OUT_X_CTS_FLOW;
		config->wFlags |= UMP_MASK_UART_FLAGS_RTS_FLOW;
		dev_dbg(dev, "%s - RTS/CTS is enabled\n", __func__);
	} else {
		dev_dbg(dev, "%s - RTS/CTS is disabled\n", __func__);
		tty->hw_stopped = 0;
		restart_read(edge_port);
	}

	/* if we are implementing XON/XOFF, set the start and stop
	   character in the device */
	config->cXon  = START_CHAR(tty);
	config->cXoff = STOP_CHAR(tty);

	/* if we are implementing INBOUND XON/XOFF */
	if (I_IXOFF(tty)) {
		config->wFlags |= UMP_MASK_UART_FLAGS_IN_X;
		dev_dbg(dev, "%s - INBOUND XON/XOFF is enabled, XON = %2x, XOFF = %2x\n",
			__func__, config->cXon, config->cXoff);
	} else
		dev_dbg(dev, "%s - INBOUND XON/XOFF is disabled\n", __func__);

	/* if we are implementing OUTBOUND XON/XOFF */
	if (I_IXON(tty)) {
		config->wFlags |= UMP_MASK_UART_FLAGS_OUT_X;
		dev_dbg(dev, "%s - OUTBOUND XON/XOFF is enabled, XON = %2x, XOFF = %2x\n",
			__func__, config->cXon, config->cXoff);
	} else
		dev_dbg(dev, "%s - OUTBOUND XON/XOFF is disabled\n", __func__);

	tty->termios.c_cflag &= ~CMSPAR;

	/* Round the baud rate */
	baud = tty_get_baud_rate(tty);
	if (!baud) {
		/* pick a default, any default... */
		baud = 9600;
	} else
		tty_encode_baud_rate(tty, baud, baud);

	edge_port->baud_rate = baud;
	config->wBaudRate = (__u16)((461550L + baud/2) / baud);

	/* FIXME: Recompute actual baud from divisor here */

	dev_dbg(dev, "%s - baud rate = %d, wBaudRate = %d\n", __func__, baud, config->wBaudRate);

	dev_dbg(dev, "wBaudRate:   %d\n", (int)(461550L / config->wBaudRate));
	dev_dbg(dev, "wFlags:    0x%x\n", config->wFlags);
	dev_dbg(dev, "bDataBits:   %d\n", config->bDataBits);
	dev_dbg(dev, "bParity:     %d\n", config->bParity);
	dev_dbg(dev, "bStopBits:   %d\n", config->bStopBits);
	dev_dbg(dev, "cXon:        %d\n", config->cXon);
	dev_dbg(dev, "cXoff:       %d\n", config->cXoff);
	dev_dbg(dev, "bUartMode:   %d\n", config->bUartMode);

	/* move the word values into big endian mode */
	cpu_to_be16s(&config->wFlags);
	cpu_to_be16s(&config->wBaudRate);

	status = send_cmd(edge_port->port->serial->dev, UMPC_SET_CONFIG,
				(__u8)(UMPM_UART1_PORT + port_number),
				0, (__u8 *)config, sizeof(*config));
	if (status)
		dev_dbg(dev, "%s - error %d when trying to write config to device\n",
			__func__, status);
	kfree(config);
}

static void edge_set_termios(struct tty_struct *tty,
		struct usb_serial_port *port, struct ktermios *old_termios)
{
	struct edgeport_port *edge_port = usb_get_serial_port_data(port);
	unsigned int cflag;

	cflag = tty->termios.c_cflag;

	dev_dbg(&port->dev, "%s - clfag %08x iflag %08x\n", __func__,
		tty->termios.c_cflag, tty->termios.c_iflag);
	dev_dbg(&port->dev, "%s - old clfag %08x old iflag %08x\n", __func__,
		old_termios->c_cflag, old_termios->c_iflag);
	dev_dbg(&port->dev, "%s - port %d\n", __func__, port->number);

	if (edge_port == NULL)
		return;
	/* change the port settings to the new ones specified */
	change_port_settings(tty, edge_port, old_termios);
}

static int edge_tiocmset(struct tty_struct *tty,
					unsigned int set, unsigned int clear)
{
	struct usb_serial_port *port = tty->driver_data;
	struct edgeport_port *edge_port = usb_get_serial_port_data(port);
	unsigned int mcr;
	unsigned long flags;

	spin_lock_irqsave(&edge_port->ep_lock, flags);
	mcr = edge_port->shadow_mcr;
	if (set & TIOCM_RTS)
		mcr |= MCR_RTS;
	if (set & TIOCM_DTR)
		mcr |= MCR_DTR;
	if (set & TIOCM_LOOP)
		mcr |= MCR_LOOPBACK;

	if (clear & TIOCM_RTS)
		mcr &= ~MCR_RTS;
	if (clear & TIOCM_DTR)
		mcr &= ~MCR_DTR;
	if (clear & TIOCM_LOOP)
		mcr &= ~MCR_LOOPBACK;

	edge_port->shadow_mcr = mcr;
	spin_unlock_irqrestore(&edge_port->ep_lock, flags);

	restore_mcr(edge_port, mcr);
	return 0;
}

static int edge_tiocmget(struct tty_struct *tty)
{
	struct usb_serial_port *port = tty->driver_data;
	struct edgeport_port *edge_port = usb_get_serial_port_data(port);
	unsigned int result = 0;
	unsigned int msr;
	unsigned int mcr;
	unsigned long flags;

	spin_lock_irqsave(&edge_port->ep_lock, flags);

	msr = edge_port->shadow_msr;
	mcr = edge_port->shadow_mcr;
	result = ((mcr & MCR_DTR)	? TIOCM_DTR: 0)	  /* 0x002 */
		  | ((mcr & MCR_RTS)	? TIOCM_RTS: 0)   /* 0x004 */
		  | ((msr & EDGEPORT_MSR_CTS)	? TIOCM_CTS: 0)   /* 0x020 */
		  | ((msr & EDGEPORT_MSR_CD)	? TIOCM_CAR: 0)   /* 0x040 */
		  | ((msr & EDGEPORT_MSR_RI)	? TIOCM_RI:  0)   /* 0x080 */
		  | ((msr & EDGEPORT_MSR_DSR)	? TIOCM_DSR: 0);  /* 0x100 */


	dev_dbg(&port->dev, "%s -- %x\n", __func__, result);
	spin_unlock_irqrestore(&edge_port->ep_lock, flags);

	return result;
}

static int edge_get_icount(struct tty_struct *tty,
				struct serial_icounter_struct *icount)
{
	struct usb_serial_port *port = tty->driver_data;
	struct edgeport_port *edge_port = usb_get_serial_port_data(port);
	struct async_icount *ic = &edge_port->icount;

	icount->cts = ic->cts;
	icount->dsr = ic->dsr;
	icount->rng = ic->rng;
	icount->dcd = ic->dcd;
	icount->tx = ic->tx;
        icount->rx = ic->rx;
        icount->frame = ic->frame;
        icount->parity = ic->parity;
        icount->overrun = ic->overrun;
        icount->brk = ic->brk;
        icount->buf_overrun = ic->buf_overrun;
	return 0;
}

static int get_serial_info(struct edgeport_port *edge_port,
				struct serial_struct __user *retinfo)
{
	struct serial_struct tmp;

	if (!retinfo)
		return -EFAULT;

	memset(&tmp, 0, sizeof(tmp));

	tmp.type		= PORT_16550A;
	tmp.line		= edge_port->port->serial->minor;
	tmp.port		= edge_port->port->number;
	tmp.irq			= 0;
	tmp.flags		= ASYNC_SKIP_TEST | ASYNC_AUTO_IRQ;
	tmp.xmit_fifo_size	= edge_port->port->bulk_out_size;
	tmp.baud_base		= 9600;
	tmp.close_delay		= 5*HZ;
	tmp.closing_wait	= closing_wait;

	if (copy_to_user(retinfo, &tmp, sizeof(*retinfo)))
		return -EFAULT;
	return 0;
}

static int edge_ioctl(struct tty_struct *tty,
					unsigned int cmd, unsigned long arg)
{
	struct usb_serial_port *port = tty->driver_data;
	struct edgeport_port *edge_port = usb_get_serial_port_data(port);
	struct async_icount cnow;
	struct async_icount cprev;

	dev_dbg(&port->dev, "%s - port %d, cmd = 0x%x\n", __func__, port->number, cmd);

	switch (cmd) {
	case TIOCGSERIAL:
		dev_dbg(&port->dev, "%s - TIOCGSERIAL\n", __func__);
		return get_serial_info(edge_port,
				(struct serial_struct __user *) arg);
	case TIOCMIWAIT:
		dev_dbg(&port->dev, "%s - TIOCMIWAIT\n", __func__);
		cprev = edge_port->icount;
		while (1) {
			interruptible_sleep_on(&edge_port->delta_msr_wait);
			/* see if a signal did it */
			if (signal_pending(current))
				return -ERESTARTSYS;
			cnow = edge_port->icount;
			if (cnow.rng == cprev.rng && cnow.dsr == cprev.dsr &&
			    cnow.dcd == cprev.dcd && cnow.cts == cprev.cts)
				return -EIO; /* no change => error */
			if (((arg & TIOCM_RNG) && (cnow.rng != cprev.rng)) ||
			    ((arg & TIOCM_DSR) && (cnow.dsr != cprev.dsr)) ||
			    ((arg & TIOCM_CD)  && (cnow.dcd != cprev.dcd)) ||
			    ((arg & TIOCM_CTS) && (cnow.cts != cprev.cts))) {
				return 0;
			}
			cprev = cnow;
		}
		/* not reached */
		break;
	}
	return -ENOIOCTLCMD;
}

static void edge_break(struct tty_struct *tty, int break_state)
{
	struct usb_serial_port *port = tty->driver_data;
	struct edgeport_port *edge_port = usb_get_serial_port_data(port);
	int status;
	int bv = 0;	/* Off */

	/* chase the port close */
	chase_port(edge_port, 0, 0);

	if (break_state == -1)
		bv = 1;	/* On */
	status = ti_do_config(edge_port, UMPC_SET_CLR_BREAK, bv);
	if (status)
		dev_dbg(&port->dev, "%s - error %d sending break set/clear command.\n",
			__func__, status);
}

static int edge_startup(struct usb_serial *serial)
{
	struct edgeport_serial *edge_serial;
	int status;

	/* create our private serial structure */
	edge_serial = kzalloc(sizeof(struct edgeport_serial), GFP_KERNEL);
	if (edge_serial == NULL) {
		dev_err(&serial->dev->dev, "%s - Out of memory\n", __func__);
		return -ENOMEM;
	}
	mutex_init(&edge_serial->es_lock);
	edge_serial->serial = serial;
	usb_set_serial_data(serial, edge_serial);

	status = download_fw(edge_serial);
	if (status) {
		kfree(edge_serial);
		return status;
	}

	return 0;
}

static void edge_disconnect(struct usb_serial *serial)
{
}

static void edge_release(struct usb_serial *serial)
{
	kfree(usb_get_serial_data(serial));
}

static int edge_port_probe(struct usb_serial_port *port)
{
	struct edgeport_port *edge_port;
	int ret;

	edge_port = kzalloc(sizeof(*edge_port), GFP_KERNEL);
	if (!edge_port)
		return -ENOMEM;

	ret = kfifo_alloc(&edge_port->write_fifo, EDGE_OUT_BUF_SIZE,
								GFP_KERNEL);
	if (ret) {
		kfree(edge_port);
		return -ENOMEM;
	}

	spin_lock_init(&edge_port->ep_lock);
	edge_port->port = port;
	edge_port->edge_serial = usb_get_serial_data(port->serial);
	edge_port->bUartMode = default_uart_mode;

	usb_set_serial_port_data(port, edge_port);

	ret = edge_create_sysfs_attrs(port);
	if (ret) {
		kfifo_free(&edge_port->write_fifo);
		kfree(edge_port);
		return ret;
	}

	return 0;
}

static int edge_port_remove(struct usb_serial_port *port)
{
	struct edgeport_port *edge_port;

	edge_port = usb_get_serial_port_data(port);

	edge_remove_sysfs_attrs(port);
	kfifo_free(&edge_port->write_fifo);
	kfree(edge_port);

	return 0;
}

/* Sysfs Attributes */

static ssize_t show_uart_mode(struct device *dev,
	struct device_attribute *attr, char *buf)
{
	struct usb_serial_port *port = to_usb_serial_port(dev);
	struct edgeport_port *edge_port = usb_get_serial_port_data(port);

	return sprintf(buf, "%d\n", edge_port->bUartMode);
}

static ssize_t store_uart_mode(struct device *dev,
	struct device_attribute *attr, const char *valbuf, size_t count)
{
	struct usb_serial_port *port = to_usb_serial_port(dev);
	struct edgeport_port *edge_port = usb_get_serial_port_data(port);
	unsigned int v = simple_strtoul(valbuf, NULL, 0);

	dev_dbg(dev, "%s: setting uart_mode = %d\n", __func__, v);

	if (v < 256)
		edge_port->bUartMode = v;
	else
		dev_err(dev, "%s - uart_mode %d is invalid\n", __func__, v);

	return count;
}

static DEVICE_ATTR(uart_mode, S_IWUSR | S_IRUGO, show_uart_mode,
							store_uart_mode);

static int edge_create_sysfs_attrs(struct usb_serial_port *port)
{
	return device_create_file(&port->dev, &dev_attr_uart_mode);
}

static int edge_remove_sysfs_attrs(struct usb_serial_port *port)
{
	device_remove_file(&port->dev, &dev_attr_uart_mode);
	return 0;
}


static struct usb_serial_driver edgeport_1port_device = {
	.driver = {
		.owner		= THIS_MODULE,
		.name		= "edgeport_ti_1",
	},
	.description		= "Edgeport TI 1 port adapter",
	.id_table		= edgeport_1port_id_table,
	.num_ports		= 1,
	.open			= edge_open,
	.close			= edge_close,
	.throttle		= edge_throttle,
	.unthrottle		= edge_unthrottle,
	.attach			= edge_startup,
	.disconnect		= edge_disconnect,
	.release		= edge_release,
	.port_probe		= edge_port_probe,
	.port_remove		= edge_port_remove,
	.ioctl			= edge_ioctl,
	.set_termios		= edge_set_termios,
	.tiocmget		= edge_tiocmget,
	.tiocmset		= edge_tiocmset,
	.get_icount		= edge_get_icount,
	.write			= edge_write,
	.write_room		= edge_write_room,
	.chars_in_buffer	= edge_chars_in_buffer,
	.break_ctl		= edge_break,
	.read_int_callback	= edge_interrupt_callback,
	.read_bulk_callback	= edge_bulk_in_callback,
	.write_bulk_callback	= edge_bulk_out_callback,
};

static struct usb_serial_driver edgeport_2port_device = {
	.driver = {
		.owner		= THIS_MODULE,
		.name		= "edgeport_ti_2",
	},
	.description		= "Edgeport TI 2 port adapter",
	.id_table		= edgeport_2port_id_table,
	.num_ports		= 2,
	.open			= edge_open,
	.close			= edge_close,
	.throttle		= edge_throttle,
	.unthrottle		= edge_unthrottle,
	.attach			= edge_startup,
	.disconnect		= edge_disconnect,
	.release		= edge_release,
	.port_probe		= edge_port_probe,
	.port_remove		= edge_port_remove,
	.ioctl			= edge_ioctl,
	.set_termios		= edge_set_termios,
	.tiocmget		= edge_tiocmget,
	.tiocmset		= edge_tiocmset,
	.write			= edge_write,
	.write_room		= edge_write_room,
	.chars_in_buffer	= edge_chars_in_buffer,
	.break_ctl		= edge_break,
	.read_int_callback	= edge_interrupt_callback,
	.read_bulk_callback	= edge_bulk_in_callback,
	.write_bulk_callback	= edge_bulk_out_callback,
};

static struct usb_serial_driver * const serial_drivers[] = {
	&edgeport_1port_device, &edgeport_2port_device, NULL
};

module_usb_serial_driver(serial_drivers, id_table_combined);

MODULE_AUTHOR(DRIVER_AUTHOR);
MODULE_DESCRIPTION(DRIVER_DESC);
MODULE_LICENSE("GPL");
MODULE_FIRMWARE("edgeport/down3.bin");

module_param(closing_wait, int, S_IRUGO | S_IWUSR);
MODULE_PARM_DESC(closing_wait, "Maximum wait for data to drain, in .01 secs");

module_param(ignore_cpu_rev, bool, S_IRUGO | S_IWUSR);
MODULE_PARM_DESC(ignore_cpu_rev,
			"Ignore the cpu revision when connecting to a device");

module_param(default_uart_mode, int, S_IRUGO | S_IWUSR);
MODULE_PARM_DESC(default_uart_mode, "Default uart_mode, 0=RS232, ...");
