/*
 * Based on drivers/usb/gadget/omap1510_udc.c
 * TI OMAP1510 USB bus interface driver
 *
 * (C) Copyright 2009
 * Vipin Kumar, ST Micoelectronics, vipin.kumar@st.com.
 *
 * See file CREDITS for list of people who contributed to this
 * project.
 *
 * This program is free software; you can redistribute it and/or
 * modify it under the terms of the GNU General Public License as
 * published by the Free Software Foundation; either version 2 of
 * the License, or (at your option) any later version.
 *
 * This program is distributed in the hope that it will be useful,
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
 * GNU General Public License for more details.
 *
 * You should have received a copy of the GNU General Public License
 * along with this program; if not, write to the Free Software
 * Foundation, Inc., 59 Temple Place, Suite 330, Boston,
 * MA 02111-1307 USA
 */

#include <common.h>
#include <asm/io.h>

#include <usbdevice.h>
#include "ep0.h"
#include <usb/designware_udc.h>
#include <asm/arch/hardware.h>

#define UDC_INIT_MDELAY		80	/* Device settle delay */

/* Some kind of debugging output... */
#ifndef DEBUG_DWUSBTTY
#define UDCDBG(str)
#define UDCDBGA(fmt, args...)
#else
#define UDCDBG(str) serial_printf(str "\n")
#define UDCDBGA(fmt, args...) serial_printf(fmt "\n", ##args)
#endif

static struct urb *ep0_urb;
static struct usb_device_instance *udc_device;

static struct plug_regs *const plug_regs_p =
    (struct plug_regs * const)CONFIG_SYS_PLUG_BASE;
static struct udc_regs *const udc_regs_p =
    (struct udc_regs * const)CONFIG_SYS_USBD_BASE;
static struct udc_endp_regs *const outep_regs_p =
    &((struct udc_regs * const)CONFIG_SYS_USBD_BASE)->out_regs[0];
static struct udc_endp_regs *const inep_regs_p =
    &((struct udc_regs * const)CONFIG_SYS_USBD_BASE)->in_regs[0];

/*
 * udc_state_transition - Write the next packet to TxFIFO.
 * @initial:	Initial state.
 * @final:	Final state.
 *
 * Helper function to implement device state changes. The device states and
 * the events that transition between them are:
 *
 *				STATE_ATTACHED
 *				||	/\
 *				\/	||
 *	DEVICE_HUB_CONFIGURED			DEVICE_HUB_RESET
 *				||	/\
 *				\/	||
 *				STATE_POWERED
 *				||	/\
 *				\/	||
 *	DEVICE_RESET				DEVICE_POWER_INTERRUPTION
 *				||	/\
 *				\/	||
 *				STATE_DEFAULT
 *				||	/\
 *				\/	||
 *	DEVICE_ADDRESS_ASSIGNED			DEVICE_RESET
 *				||	/\
 *				\/	||
 *				STATE_ADDRESSED
 *				||	/\
 *				\/	||
 *	DEVICE_CONFIGURED			DEVICE_DE_CONFIGURED
 *				||	/\
 *				\/	||
 *				STATE_CONFIGURED
 *
 * udc_state_transition transitions up (in the direction from STATE_ATTACHED
 * to STATE_CONFIGURED) from the specified initial state to the specified final
 * state, passing through each intermediate state on the way. If the initial
 * state is at or above (i.e. nearer to STATE_CONFIGURED) the final state, then
 * no state transitions will take place.
 *
 * udc_state_transition also transitions down (in the direction from
 * STATE_CONFIGURED to STATE_ATTACHED) from the specified initial state to the
 * specified final state, passing through each intermediate state on the way.
 * If the initial state is at or below (i.e. nearer to STATE_ATTACHED) the final
 * state, then no state transitions will take place.
 *
 * This function must only be called with interrupts disabled.
 */
static void udc_state_transition(usb_device_state_t initial,
				 usb_device_state_t final)
{
	if (initial < final) {
		switch (initial) {
		case STATE_ATTACHED:
			usbd_device_event_irq(udc_device,
					      DEVICE_HUB_CONFIGURED, 0);
			if (final == STATE_POWERED)
				break;
		case STATE_POWERED:
			usbd_device_event_irq(udc_device, DEVICE_RESET, 0);
			if (final == STATE_DEFAULT)
				break;
		case STATE_DEFAULT:
			usbd_device_event_irq(udc_device,
					      DEVICE_ADDRESS_ASSIGNED, 0);
			if (final == STATE_ADDRESSED)
				break;
		case STATE_ADDRESSED:
			usbd_device_event_irq(udc_device, DEVICE_CONFIGURED, 0);
		case STATE_CONFIGURED:
			break;
		default:
			break;
		}
	} else if (initial > final) {
		switch (initial) {
		case STATE_CONFIGURED:
			usbd_device_event_irq(udc_device,
					      DEVICE_DE_CONFIGURED, 0);
			if (final == STATE_ADDRESSED)
				break;
		case STATE_ADDRESSED:
			usbd_device_event_irq(udc_device, DEVICE_RESET, 0);
			if (final == STATE_DEFAULT)
				break;
		case STATE_DEFAULT:
			usbd_device_event_irq(udc_device,
					      DEVICE_POWER_INTERRUPTION, 0);
			if (final == STATE_POWERED)
				break;
		case STATE_POWERED:
			usbd_device_event_irq(udc_device, DEVICE_HUB_RESET, 0);
		case STATE_ATTACHED:
			break;
		default:
			break;
		}
	}
}

/* Stall endpoint */
static void udc_stall_ep(u32 ep_num)
{
	writel(readl(&inep_regs_p[ep_num].endp_cntl) | ENDP_CNTL_STALL,
	       &inep_regs_p[ep_num].endp_cntl);

	writel(readl(&outep_regs_p[ep_num].endp_cntl) | ENDP_CNTL_STALL,
	       &outep_regs_p[ep_num].endp_cntl);
}

static void *get_fifo(int ep_num, int in)
{
	u32 *fifo_ptr = (u32 *)CONFIG_SYS_FIFO_BASE;

	switch (ep_num) {
	case UDC_EP3:
		fifo_ptr += readl(&inep_regs_p[1].endp_bsorfn);
		/* break intentionally left out */

	case UDC_EP1:
		fifo_ptr += readl(&inep_regs_p[0].endp_bsorfn);
		/* break intentionally left out */

	case UDC_EP0:
	default:
		if (in) {
			fifo_ptr +=
			    readl(&outep_regs_p[2].endp_maxpacksize) >> 16;
			/* break intentionally left out */
		} else {
			break;
		}

	case UDC_EP2:
		fifo_ptr += readl(&outep_regs_p[0].endp_maxpacksize) >> 16;
		/* break intentionally left out */
	}

	return (void *)fifo_ptr;
}

static int usbgetpckfromfifo(int epNum, u8 *bufp, u32 len)
{
	u8 *fifo_ptr = (u8 *)get_fifo(epNum, 0);
	u32 i, nw, nb;
	u32 *wrdp;
	u8 *bytp;
	u32 tmp[128];

	if (readl(&udc_regs_p->dev_stat) & DEV_STAT_RXFIFO_EMPTY)
		return -1;

	nw = len / sizeof(u32);
	nb = len % sizeof(u32);

	/* use tmp buf if bufp is not word aligned */
	if ((int)bufp & 0x3)
		wrdp = (u32 *)&tmp[0];
	else
		wrdp = (u32 *)bufp;

	for (i = 0; i < nw; i++) {
		writel(readl(fifo_ptr), wrdp);
		wrdp++;
	}

	bytp = (u8 *)wrdp;
	for (i = 0; i < nb; i++) {
		writeb(readb(fifo_ptr), bytp);
		fifo_ptr++;
		bytp++;
	}
	readl(&outep_regs_p[epNum].write_done);

	/* copy back tmp buffer to bufp if bufp is not word aligned */
	if ((int)bufp & 0x3)
		memcpy(bufp, tmp, len);

	return 0;
}

static void usbputpcktofifo(int epNum, u8 *bufp, u32 len)
{
	u32 i, nw, nb;
	u32 *wrdp;
	u8 *bytp;
	u8 *fifo_ptr = get_fifo(epNum, 1);

	nw = len / sizeof(int);
	nb = len % sizeof(int);
	wrdp = (u32 *)bufp;
	for (i = 0; i < nw; i++) {
		writel(*wrdp, fifo_ptr);
		wrdp++;
	}

	bytp = (u8 *)wrdp;
	for (i = 0; i < nb; i++) {
		writeb(*bytp, fifo_ptr);
		fifo_ptr++;
		bytp++;
	}
}

/*
 * dw_write_noniso_tx_fifo - Write the next packet to TxFIFO.
 * @endpoint:		Endpoint pointer.
 *
 * If the endpoint has an active tx_urb, then the next packet of data from the
 * URB is written to the tx FIFO.  The total amount of data in the urb is given
 * by urb->actual_length.  The maximum amount of data that can be sent in any
 * one packet is given by endpoint->tx_packetSize.  The number of data bytes
 * from this URB that have already been transmitted is given by endpoint->sent.
 * endpoint->last is updated by this routine with the number of data bytes
 * transmitted in this packet.
 *
 */
static void dw_write_noniso_tx_fifo(struct usb_endpoint_instance
				       *endpoint)
{
	struct urb *urb = endpoint->tx_urb;
	int align;

	if (urb) {
		u32 last;

		UDCDBGA("urb->buffer %p, buffer_length %d, actual_length %d",
			urb->buffer, urb->buffer_length, urb->actual_length);

		last = MIN(urb->actual_length - endpoint->sent,
			   endpoint->tx_packetSize);

		if (last) {
			u8 *cp = urb->buffer + endpoint->sent;

			/*
			 * This ensures that USBD packet fifo is accessed
			 * - through word aligned pointer or
			 * - through non word aligned pointer but only
			 *   with a max length to make the next packet
			 *   word aligned
			 */

			align = ((ulong)cp % sizeof(int));
			if (align)
				last = MIN(last, sizeof(int) - align);

			UDCDBGA("endpoint->sent %d, tx_packetSize %d, last %d",
				endpoint->sent, endpoint->tx_packetSize, last);

			usbputpcktofifo(endpoint->endpoint_address &
					USB_ENDPOINT_NUMBER_MASK, cp, last);
		}
		endpoint->last = last;
	}
}

/*
 * Handle SETUP USB interrupt.
 * This function implements TRM Figure 14-14.
 */
static void dw_udc_setup(struct usb_endpoint_instance *endpoint)
{
	u8 *datap = (u8 *)&ep0_urb->device_request;
	int ep_addr = endpoint->endpoint_address;

	UDCDBG("-> Entering device setup");
	usbgetpckfromfifo(ep_addr, datap, 8);

	/* Try to process setup packet */
	if (ep0_recv_setup(ep0_urb)) {
		/* Not a setup packet, stall next EP0 transaction */
		udc_stall_ep(0);
		UDCDBG("can't parse setup packet, still waiting for setup");
		return;
	}

	/* Check direction */
	if ((ep0_urb->device_request.bmRequestType & USB_REQ_DIRECTION_MASK)
	    == USB_REQ_HOST2DEVICE) {
		UDCDBG("control write on EP0");
		if (le16_to_cpu(ep0_urb->device_request.wLength)) {
			/* Stall this request */
			UDCDBG("Stalling unsupported EP0 control write data "
			       "stage.");
			udc_stall_ep(0);
		}
	} else {

		UDCDBG("control read on EP0");
		/*
		 * The ep0_recv_setup function has already placed our response
		 * packet data in ep0_urb->buffer and the packet length in
		 * ep0_urb->actual_length.
		 */
		endpoint->tx_urb = ep0_urb;
		endpoint->sent = 0;
		/*
		 * Write packet data to the FIFO.  dw_write_noniso_tx_fifo
		 * will update endpoint->last with the number of bytes written
		 * to the FIFO.
		 */
		dw_write_noniso_tx_fifo(endpoint);

		writel(0x0, &inep_regs_p[ep_addr].write_done);
	}

	udc_unset_nak(endpoint->endpoint_address);

	UDCDBG("<- Leaving device setup");
}

/*
 * Handle endpoint 0 RX interrupt
 */
static void dw_udc_ep0_rx(struct usb_endpoint_instance *endpoint)
{
	u8 dummy[64];

	UDCDBG("RX on EP0");

	/* Check direction */
	if ((ep0_urb->device_request.bmRequestType
	     & USB_REQ_DIRECTION_MASK) == USB_REQ_HOST2DEVICE) {
		/*
		 * This rx interrupt must be for a control write data
		 * stage packet.
		 *
		 * We don't support control write data stages.
		 * We should never end up here.
		 */

		UDCDBG("Stalling unexpected EP0 control write "
		       "data stage packet");
		udc_stall_ep(0);
	} else {
		/*
		 * This rx interrupt must be for a control read status
		 * stage packet.
		 */
		UDCDBG("ACK on EP0 control read status stage packet");
		u32 len = (readl(&outep_regs_p[0].endp_status) >> 11) & 0xfff;
		usbgetpckfromfifo(0, dummy, len);
	}
}

/*
 * Handle endpoint 0 TX interrupt
 */
static void dw_udc_ep0_tx(struct usb_endpoint_instance *endpoint)
{
	struct usb_device_request *request = &ep0_urb->device_request;
	int ep_addr;

	UDCDBG("TX on EP0");

	/* Check direction */
	if ((request->bmRequestType & USB_REQ_DIRECTION_MASK) ==
	    USB_REQ_HOST2DEVICE) {
		/*
		 * This tx interrupt must be for a control write status
		 * stage packet.
		 */
		UDCDBG("ACK on EP0 control write status stage packet");
	} else {
		/*
		 * This tx interrupt must be for a control read data
		 * stage packet.
		 */
		int wLength = le16_to_cpu(request->wLength);

		/*
		 * Update our count of bytes sent so far in this
		 * transfer.
		 */
		endpoint->sent += endpoint->last;

		/*
		 * We are finished with this transfer if we have sent
		 * all of the bytes in our tx urb (urb->actual_length)
		 * unless we need a zero-length terminating packet.  We
		 * need a zero-length terminating packet if we returned
		 * fewer bytes than were requested (wLength) by the host,
		 * and the number of bytes we returned is an exact
		 * multiple of the packet size endpoint->tx_packetSize.
		 */
		if ((endpoint->sent == ep0_urb->actual_length) &&
		    ((ep0_urb->actual_length == wLength) ||
		     (endpoint->last != endpoint->tx_packetSize))) {
			/* Done with control read data stage. */
			UDCDBG("control read data stage complete");
		} else {
			/*
			 * We still have another packet of data to send
			 * in this control read data stage or else we
			 * need a zero-length terminating packet.
			 */
			UDCDBG("ACK control read data stage packet");
			dw_write_noniso_tx_fifo(endpoint);

			ep_addr = endpoint->endpoint_address;
			writel(0x0, &inep_regs_p[ep_addr].write_done);
		}
	}
}

static struct usb_endpoint_instance *dw_find_ep(int ep)
{
	int i;

	for (i = 0; i < udc_device->bus->max_endpoints; i++) {
		if ((udc_device->bus->endpoint_array[i].endpoint_address &
		     USB_ENDPOINT_NUMBER_MASK) == ep)
			return &udc_device->bus->endpoint_array[i];
	}
	return NULL;
}

/*
 * Handle RX transaction on non-ISO endpoint.
 * The ep argument is a physical endpoint number for a non-ISO IN endpoint
 * in the range 1 to 15.
 */
static void dw_udc_epn_rx(int ep)
{
	int nbytes = 0;
	struct urb *urb;
	struct usb_endpoint_instance *endpoint = dw_find_ep(ep);

	if (endpoint) {
		urb = endpoint->rcv_urb;

		if (urb) {
			u8 *cp = urb->buffer + urb->actual_length;

			nbytes = (readl(&outep_regs_p[ep].endp_status) >> 11) &
			    0xfff;
			usbgetpckfromfifo(ep, cp, nbytes);
			usbd_rcv_complete(endpoint, nbytes, 0);
		}
	}
}

/*
 * Handle TX transaction on non-ISO endpoint.
 * The ep argument is a physical endpoint number for a non-ISO IN endpoint
 * in the range 16 to 30.
 */
static void dw_udc_epn_tx(int ep)
{
	struct usb_endpoint_instance *endpoint = dw_find_ep(ep);

	if (!endpoint)
		return;

	/*
	 * We need to transmit a terminating zero-length packet now if
	 * we have sent all of the data in this URB and the transfer
	 * size was an exact multiple of the packet size.
	 */
	if (endpoint->tx_urb &&
	    (endpoint->last == endpoint->tx_packetSize) &&
	    (endpoint->tx_urb->actual_length - endpoint->sent -
	     endpoint->last == 0)) {
		/* handle zero length packet here */
		writel(0x0, &inep_regs_p[ep].write_done);

	}

	if (endpoint->tx_urb && endpoint->tx_urb->actual_length) {
		/* retire the data that was just sent */
		usbd_tx_complete(endpoint);
		/*
		 * Check to see if we have more data ready to transmit
		 * now.
		 */
		if (endpoint->tx_urb && endpoint->tx_urb->actual_length) {
			/* write data to FIFO */
			dw_write_noniso_tx_fifo(endpoint);
			writel(0x0, &inep_regs_p[ep].write_done);

		} else if (endpoint->tx_urb
			   && (endpoint->tx_urb->actual_length == 0)) {
			/* udc_set_nak(ep); */
		}
	}
}

/*
 * Start of public functions.
 */

/* Called to start packet transmission. */
int udc_endpoint_write(struct usb_endpoint_instance *endpoint)
{
	udc_unset_nak(endpoint->endpoint_address & USB_ENDPOINT_NUMBER_MASK);
	return 0;
}

/* Start to initialize h/w stuff */
int udc_init(void)
{
	int i;
	u32 plug_st;

	udc_device = NULL;

	UDCDBG("starting");

	readl(&plug_regs_p->plug_pending);

	for (i = 0; i < UDC_INIT_MDELAY; i++)
		udelay(1000);

	plug_st = readl(&plug_regs_p->plug_state);
	writel(plug_st | PLUG_STATUS_EN, &plug_regs_p->plug_state);

	writel(~0x0, &udc_regs_p->endp_int);
	writel(~0x0, &udc_regs_p->dev_int_mask);
	writel(~0x0, &udc_regs_p->endp_int_mask);

#ifndef CONFIG_USBD_HS
	writel(DEV_CONF_FS_SPEED | DEV_CONF_REMWAKEUP | DEV_CONF_SELFPOW |
	       DEV_CONF_PHYINT_16, &udc_regs_p->dev_conf);
#else
	writel(DEV_CONF_HS_SPEED | DEV_CONF_REMWAKEUP | DEV_CONF_SELFPOW |
			DEV_CONF_PHYINT_16, &udc_regs_p->dev_conf);
#endif

	writel(DEV_CNTL_SOFTDISCONNECT, &udc_regs_p->dev_cntl);

	/* Clear all interrupts pending */
	writel(DEV_INT_MSK, &udc_regs_p->dev_int);

	return 0;
}

int is_usbd_high_speed(void)
{
	return (readl(&udc_regs_p->dev_stat) & DEV_STAT_ENUM) ? 0 : 1;
}

/*
 * udc_setup_ep - setup endpoint
 * Associate a physical endpoint with endpoint_instance
 */
void udc_setup_ep(struct usb_device_instance *device,
		  u32 ep, struct usb_endpoint_instance *endpoint)
{
	UDCDBGA("setting up endpoint addr %x", endpoint->endpoint_address);
	int ep_addr;
	int ep_num, ep_type;
	int packet_size;
	int buffer_size;
	int attributes;
	char *tt;
	u32 endp_intmask;

	if ((ep != 0) && (udc_device->device_state < STATE_ADDRESSED))
		return;

	tt = getenv("usbtty");
	if (!tt)
		tt = "generic";

	ep_addr = endpoint->endpoint_address;
	ep_num = ep_addr & USB_ENDPOINT_NUMBER_MASK;

	if ((ep_addr & USB_ENDPOINT_DIR_MASK) == USB_DIR_IN) {
		/* IN endpoint */
		packet_size = endpoint->tx_packetSize;
		buffer_size = packet_size * 2;
		attributes = endpoint->tx_attributes;
	} else {
		/* OUT endpoint */
		packet_size = endpoint->rcv_packetSize;
		buffer_size = packet_size * 2;
		attributes = endpoint->rcv_attributes;
	}

	switch (attributes & USB_ENDPOINT_XFERTYPE_MASK) {
	case USB_ENDPOINT_XFER_CONTROL:
		ep_type = ENDP_EPTYPE_CNTL;
		break;
	case USB_ENDPOINT_XFER_BULK:
	default:
		ep_type = ENDP_EPTYPE_BULK;
		break;
	case USB_ENDPOINT_XFER_INT:
		ep_type = ENDP_EPTYPE_INT;
		break;
	case USB_ENDPOINT_XFER_ISOC:
		ep_type = ENDP_EPTYPE_ISO;
		break;
	}

	struct udc_endp_regs *out_p = &outep_regs_p[ep_num];
	struct udc_endp_regs *in_p = &inep_regs_p[ep_num];

	if (!ep_addr) {
		/* Setup endpoint 0 */
		buffer_size = packet_size;

		writel(readl(&in_p->endp_cntl) | ENDP_CNTL_CNAK,
		       &in_p->endp_cntl);

		writel(readl(&out_p->endp_cntl) | ENDP_CNTL_CNAK,
		       &out_p->endp_cntl);

		writel(ENDP_CNTL_CONTROL | ENDP_CNTL_FLUSH, &in_p->endp_cntl);

		writel(buffer_size / sizeof(int), &in_p->endp_bsorfn);

		writel(packet_size, &in_p->endp_maxpacksize);

		writel(ENDP_CNTL_CONTROL | ENDP_CNTL_RRDY, &out_p->endp_cntl);

		writel(packet_size | ((buffer_size / sizeof(int)) << 16),
		       &out_p->endp_maxpacksize);

	} else if ((ep_addr & USB_ENDPOINT_DIR_MASK) == USB_DIR_IN) {
		/* Setup the IN endpoint */
		writel(0x0, &in_p->endp_status);
		writel((ep_type << 4) | ENDP_CNTL_RRDY, &in_p->endp_cntl);
		writel(buffer_size / sizeof(int), &in_p->endp_bsorfn);
		writel(packet_size, &in_p->endp_maxpacksize);

		if (!strcmp(tt, "cdc_acm")) {
			if (ep_type == ENDP_EPTYPE_INT) {
				/* Conf no. 1 Interface no. 0 */
				writel((packet_size << 19) |
				       ENDP_EPDIR_IN | (1 << 7) |
				       (0 << 11) | (ep_type << 5) | ep_num,
				       &udc_regs_p->udc_endp_reg[ep_num]);
			} else {
				/* Conf no. 1 Interface no. 1 */
				writel((packet_size << 19) |
				       ENDP_EPDIR_IN | (1 << 7) |
				       (1 << 11) | (ep_type << 5) | ep_num,
				       &udc_regs_p->udc_endp_reg[ep_num]);
			}
		} else {
			/* Conf no. 1 Interface no. 0 */
			writel((packet_size << 19) |
			       ENDP_EPDIR_IN | (1 << 7) |
			       (0 << 11) | (ep_type << 5) | ep_num,
			       &udc_regs_p->udc_endp_reg[ep_num]);
		}

	} else {
		/* Setup the OUT endpoint */
		writel(0x0, &out_p->endp_status);
		writel((ep_type << 4) | ENDP_CNTL_RRDY, &out_p->endp_cntl);
		writel(packet_size | ((buffer_size / sizeof(int)) << 16),
		       &out_p->endp_maxpacksize);

		if (!strcmp(tt, "cdc_acm")) {
			writel((packet_size << 19) |
			       ENDP_EPDIR_OUT | (1 << 7) |
			       (1 << 11) | (ep_type << 5) | ep_num,
			       &udc_regs_p->udc_endp_reg[ep_num]);
		} else {
			writel((packet_size << 19) |
			       ENDP_EPDIR_OUT | (1 << 7) |
			       (0 << 11) | (ep_type << 5) | ep_num,
			       &udc_regs_p->udc_endp_reg[ep_num]);
		}

	}

	endp_intmask = readl(&udc_regs_p->endp_int_mask);
	endp_intmask &= ~((1 << ep_num) | 0x10000 << ep_num);
	writel(endp_intmask, &udc_regs_p->endp_int_mask);
}

/* Turn on the USB connection by enabling the pullup resistor */
void udc_connect(void)
{
	u32 plug_st, dev_cntl;

	dev_cntl = readl(&udc_regs_p->dev_cntl);
	dev_cntl |= DEV_CNTL_SOFTDISCONNECT;
	writel(dev_cntl, &udc_regs_p->dev_cntl);

	udelay(1000);

	dev_cntl = readl(&udc_regs_p->dev_cntl);
	dev_cntl &= ~DEV_CNTL_SOFTDISCONNECT;
	writel(dev_cntl, &udc_regs_p->dev_cntl);

	plug_st = readl(&plug_regs_p->plug_state);
	plug_st &= ~(PLUG_STATUS_PHY_RESET | PLUG_STATUS_PHY_MODE);
	writel(plug_st, &plug_regs_p->plug_state);
}

/* Turn off the USB connection by disabling the pullup resistor */
void udc_disconnect(void)
{
	u32 plug_st;

	writel(DEV_CNTL_SOFTDISCONNECT, &udc_regs_p->dev_cntl);

	plug_st = readl(&plug_regs_p->plug_state);
	plug_st |= (PLUG_STATUS_PHY_RESET | PLUG_STATUS_PHY_MODE);
	writel(plug_st, &plug_regs_p->plug_state);
}

/* Switch on the UDC */
void udc_enable(struct usb_device_instance *device)
{
	UDCDBGA("enable device %p, status %d", device, device->status);

	/* Save the device structure pointer */
	udc_device = device;

	/* Setup ep0 urb */
	if (!ep0_urb) {
		ep0_urb =
		    usbd_alloc_urb(udc_device, udc_device->bus->endpoint_array);
	} else {
		serial_printf("udc_enable: ep0_urb already allocated %p\n",
			      ep0_urb);
	}

	writel(DEV_INT_SOF, &udc_regs_p->dev_int_mask);
}

/**
 * udc_startup - allow udc code to do any additional startup
 */
void udc_startup_events(struct usb_device_instance *device)
{
	/* The DEVICE_INIT event puts the USB device in the state STATE_INIT. */
	usbd_device_event_irq(device, DEVICE_INIT, 0);

	/*
	 * The DEVICE_CREATE event puts the USB device in the state
	 * STATE_ATTACHED.
	 */
	usbd_device_event_irq(device, DEVICE_CREATE, 0);

	/*
	 * Some USB controller driver implementations signal
	 * DEVICE_HUB_CONFIGURED and DEVICE_RESET events here.
	 * DEVICE_HUB_CONFIGURED causes a transition to the state STATE_POWERED,
	 * and DEVICE_RESET causes a transition to the state STATE_DEFAULT.
	 * The DW USB client controller has the capability to detect when the
	 * USB cable is connected to a powered USB bus, so we will defer the
	 * DEVICE_HUB_CONFIGURED and DEVICE_RESET events until later.
	 */

	udc_enable(device);
}

/*
 * Plug detection interrupt handling
 */
static void dw_udc_plug_irq(void)
{
	if (readl(&plug_regs_p->plug_state) & PLUG_STATUS_ATTACHED) {
		/*
		 * USB cable attached
		 * Turn off PHY reset bit (PLUG detect).
		 * Switch PHY opmode to normal operation (PLUG detect).
		 */
		udc_connect();
		writel(DEV_INT_SOF, &udc_regs_p->dev_int_mask);

		UDCDBG("device attached and powered");
		udc_state_transition(udc_device->device_state, STATE_POWERED);
	} else {
		writel(~0x0, &udc_regs_p->dev_int_mask);

		UDCDBG("device detached or unpowered");
		udc_state_transition(udc_device->device_state, STATE_ATTACHED);
	}
}

/*
 * Device interrupt handling
 */
static void dw_udc_dev_irq(void)
{
	if (readl(&udc_regs_p->dev_int) & DEV_INT_USBRESET) {
		writel(~0x0, &udc_regs_p->endp_int_mask);

		writel(readl(&inep_regs_p[0].endp_cntl) | ENDP_CNTL_FLUSH,
		       &inep_regs_p[0].endp_cntl);

		writel(DEV_INT_USBRESET, &udc_regs_p->dev_int);

		/*
		 * This endpoint0 specific register can be programmed only
		 * after the phy clock is initialized
		 */
		writel((EP0_MAX_PACKET_SIZE << 19) | ENDP_EPTYPE_CNTL,
				&udc_regs_p->udc_endp_reg[0]);

		UDCDBG("device reset in progess");
		udc_state_transition(udc_device->device_state, STATE_DEFAULT);
	}

	/* Device Enumeration completed */
	if (readl(&udc_regs_p->dev_int) & DEV_INT_ENUM) {
		writel(DEV_INT_ENUM, &udc_regs_p->dev_int);

		/* Endpoint interrupt enabled for Ctrl IN & Ctrl OUT */
		writel(readl(&udc_regs_p->endp_int_mask) & ~0x10001,
		       &udc_regs_p->endp_int_mask);

		UDCDBG("default -> addressed");
		udc_state_transition(udc_device->device_state, STATE_ADDRESSED);
	}

	/* The USB will be in SUSPEND in 3 ms */
	if (readl(&udc_regs_p->dev_int) & DEV_INT_INACTIVE) {
		writel(DEV_INT_INACTIVE, &udc_regs_p->dev_int);

		UDCDBG("entering inactive state");
		/* usbd_device_event_irq(udc_device, DEVICE_BUS_INACTIVE, 0); */
	}

	/* SetConfiguration command received */
	if (readl(&udc_regs_p->dev_int) & DEV_INT_SETCFG) {
		writel(DEV_INT_SETCFG, &udc_regs_p->dev_int);

		UDCDBG("entering configured state");
		udc_state_transition(udc_device->device_state,
				     STATE_CONFIGURED);
	}

	/* SetInterface command received */
	if (readl(&udc_regs_p->dev_int) & DEV_INT_SETINTF)
		writel(DEV_INT_SETINTF, &udc_regs_p->dev_int);

	/* USB Suspend detected on cable */
	if (readl(&udc_regs_p->dev_int) & DEV_INT_SUSPUSB) {
		writel(DEV_INT_SUSPUSB, &udc_regs_p->dev_int);

		UDCDBG("entering suspended state");
		usbd_device_event_irq(udc_device, DEVICE_BUS_INACTIVE, 0);
	}

	/* USB Start-Of-Frame detected on cable */
	if (readl(&udc_regs_p->dev_int) & DEV_INT_SOF)
		writel(DEV_INT_SOF, &udc_regs_p->dev_int);
}

/*
 * Endpoint interrupt handling
 */
static void dw_udc_endpoint_irq(void)
{
	while (readl(&udc_regs_p->endp_int) & ENDP0_INT_CTRLOUT) {

		writel(ENDP0_INT_CTRLOUT, &udc_regs_p->endp_int);

		if ((readl(&outep_regs_p[0].endp_status) & ENDP_STATUS_OUTMSK)
		    == ENDP_STATUS_OUT_SETUP) {
			dw_udc_setup(udc_device->bus->endpoint_array + 0);
			writel(ENDP_STATUS_OUT_SETUP,
			       &outep_regs_p[0].endp_status);

		} else if ((readl(&outep_regs_p[0].endp_status) &
			    ENDP_STATUS_OUTMSK) == ENDP_STATUS_OUT_DATA) {
			dw_udc_ep0_rx(udc_device->bus->endpoint_array + 0);
			writel(ENDP_STATUS_OUT_DATA,
			       &outep_regs_p[0].endp_status);

		} else if ((readl(&outep_regs_p[0].endp_status) &
			    ENDP_STATUS_OUTMSK) == ENDP_STATUS_OUT_NONE) {
			/* NONE received */
		}

		writel(0x0, &outep_regs_p[0].endp_status);
	}

	if (readl(&udc_regs_p->endp_int) & ENDP0_INT_CTRLIN) {
		dw_udc_ep0_tx(udc_device->bus->endpoint_array + 0);

		writel(ENDP_STATUS_IN, &inep_regs_p[0].endp_status);
		writel(ENDP0_INT_CTRLIN, &udc_regs_p->endp_int);
	}

	if (readl(&udc_regs_p->endp_int) & ENDP_INT_NONISOOUT_MSK) {
		u32 epnum = 0;
		u32 ep_int = readl(&udc_regs_p->endp_int) &
		    ENDP_INT_NONISOOUT_MSK;

		ep_int >>= 16;
		while (0x0 == (ep_int & 0x1)) {
			ep_int >>= 1;
			epnum++;
		}

		writel((1 << 16) << epnum, &udc_regs_p->endp_int);

		if ((readl(&outep_regs_p[epnum].endp_status) &
		     ENDP_STATUS_OUTMSK) == ENDP_STATUS_OUT_DATA) {

			dw_udc_epn_rx(epnum);
			writel(ENDP_STATUS_OUT_DATA,
			       &outep_regs_p[epnum].endp_status);
		} else if ((readl(&outep_regs_p[epnum].endp_status) &
			    ENDP_STATUS_OUTMSK) == ENDP_STATUS_OUT_NONE) {
			writel(0x0, &outep_regs_p[epnum].endp_status);
		}
	}

	if (readl(&udc_regs_p->endp_int) & ENDP_INT_NONISOIN_MSK) {
		u32 epnum = 0;
		u32 ep_int = readl(&udc_regs_p->endp_int) &
		    ENDP_INT_NONISOIN_MSK;

		while (0x0 == (ep_int & 0x1)) {
			ep_int >>= 1;
			epnum++;
		}

		if (readl(&inep_regs_p[epnum].endp_status) & ENDP_STATUS_IN) {
			writel(ENDP_STATUS_IN,
			       &outep_regs_p[epnum].endp_status);
			dw_udc_epn_tx(epnum);

			writel(ENDP_STATUS_IN,
			       &outep_regs_p[epnum].endp_status);
		}

		writel((1 << epnum), &udc_regs_p->endp_int);
	}
}

/*
 * UDC interrupts
 */
void udc_irq(void)
{
	/*
	 * Loop while we have interrupts.
	 * If we don't do this, the input chain
	 * polling delay is likely to miss
	 * host requests.
	 */
	while (readl(&plug_regs_p->plug_pending))
		dw_udc_plug_irq();

	while (readl(&udc_regs_p->dev_int))
		dw_udc_dev_irq();

	if (readl(&udc_regs_p->endp_int))
		dw_udc_endpoint_irq();
}

/* Flow control */
void udc_set_nak(int epid)
{
	writel(readl(&inep_regs_p[epid].endp_cntl) | ENDP_CNTL_SNAK,
	       &inep_regs_p[epid].endp_cntl);

	writel(readl(&outep_regs_p[epid].endp_cntl) | ENDP_CNTL_SNAK,
	       &outep_regs_p[epid].endp_cntl);
}

void udc_unset_nak(int epid)
{
	u32 val;

	val = readl(&inep_regs_p[epid].endp_cntl);
	val &= ~ENDP_CNTL_SNAK;
	val |= ENDP_CNTL_CNAK;
	writel(val, &inep_regs_p[epid].endp_cntl);

	val = readl(&outep_regs_p[epid].endp_cntl);
	val &= ~ENDP_CNTL_SNAK;
	val |= ENDP_CNTL_CNAK;
	writel(val, &outep_regs_p[epid].endp_cntl);
}
