/*
 * Copyright (C) 2016 Cadence Design Systems - https://www.cadence.com/
 * Copyright 2018 NXP
 *
 * SPDX-License-Identifier:     GPL-2.0
 */
#include <common.h>
#include <malloc.h>
#include <asm/dma-mapping.h>
#include <asm/io.h>
#include <linux/bug.h>
#include <linux/list.h>
#include <linux/compat.h>

#include <linux/usb/ch9.h>
#include <linux/usb/gadget.h>
#include <linux/usb/composite.h>

#include "linux-compat.h"
#include "core.h"
#include "gadget-export.h"
#include "gadget.h"
#include "io.h"

/*-------------------------------------------------------------------------*/
/* Function declarations */

static void select_ep(struct usb_ss_dev *usb_ss, u32 ep);
static int usb_ss_allocate_trb_pool(struct usb_ss_endpoint *usb_ss_ep);
static void cdns_ep_stall_flush(struct usb_ss_endpoint *usb_ss_ep);
static void cdns_ep0_config(struct usb_ss_dev *usb_ss);
static void cdns_gadget_unconfig(struct usb_ss_dev *usb_ss);
static void cdns_ep0_run_transfer(struct usb_ss_dev *usb_ss,
	dma_addr_t dma_addr, unsigned int length, int erdy);
static int cdns_ep_run_transfer(struct usb_ss_endpoint *usb_ss_ep);
static int cdns_get_setup_ret(struct usb_ss_dev *usb_ss,
	struct usb_ctrlrequest *ctrl_req);
static int cdns_req_ep0_set_address(struct usb_ss_dev *usb_ss,
	struct usb_ctrlrequest *ctrl_req);
static int cdns_req_ep0_get_status(struct usb_ss_dev *usb_ss,
	struct usb_ctrlrequest *ctrl_req);
static int cdns_req_ep0_handle_feature(struct usb_ss_dev *usb_ss,
	struct usb_ctrlrequest *ctrl_req, int set);
static int cdns_req_ep0_set_sel(struct usb_ss_dev *usb_ss,
	struct usb_ctrlrequest *ctrl_req);
static int cdns_req_ep0_set_isoch_delay(struct usb_ss_dev *usb_ss,
	struct usb_ctrlrequest *ctrl_req);
static int cdns_req_ep0_set_configuration(struct usb_ss_dev *usb_ss,
	struct usb_ctrlrequest *ctrl_req);
static int cdns_ep0_standard_request(struct usb_ss_dev *usb_ss,
	struct usb_ctrlrequest *ctrl_req);
static void cdns_ep0_setup_phase(struct usb_ss_dev *usb_ss);
static int cdns_check_ep_interrupt_proceed(struct usb_ss_endpoint *usb_ss_ep);
static void cdns_check_ep0_interrupt_proceed(struct usb_ss_dev *usb_ss,
	int dir);
static void cdns_check_usb_interrupt_proceed(struct usb_ss_dev *usb_ss,
	u32 usb_ists);
#ifdef CDNS_THREADED_IRQ_HANDLING
static irqreturn_t cdns_irq_handler(int irq, void *_usb_ss);
#endif
static int usb_ss_gadget_ep0_enable(struct usb_ep *ep,
	const struct usb_endpoint_descriptor *desc);
static int usb_ss_gadget_ep0_disable(struct usb_ep *ep);
static int usb_ss_gadget_ep0_set_halt(struct usb_ep *ep, int value);
static int usb_ss_gadget_ep0_queue(struct usb_ep *ep,
	struct usb_request *request, gfp_t gfp_flags);
static int usb_ss_gadget_ep_enable(struct usb_ep *ep,
	const struct usb_endpoint_descriptor *desc);
static int usb_ss_gadget_ep_disable(struct usb_ep *ep);
static struct usb_request *usb_ss_gadget_ep_alloc_request(struct usb_ep *ep,
	gfp_t gfp_flags);
static void usb_ss_gadget_ep_free_request(struct usb_ep *ep,
	struct usb_request *request);
static int usb_ss_gadget_ep_queue(struct usb_ep *ep,
	struct usb_request *request, gfp_t gfp_flags);
static int usb_ss_gadget_ep_dequeue(struct usb_ep *ep,
	struct usb_request *request);
static int usb_ss_gadget_ep_set_halt(struct usb_ep *ep, int value);
static int usb_ss_gadget_ep_set_wedge(struct usb_ep *ep);
static int usb_ss_gadget_get_frame(struct usb_gadget *gadget);
static int usb_ss_gadget_wakeup(struct usb_gadget *gadget);
static int usb_ss_gadget_set_selfpowered(struct usb_gadget *gadget,
	int is_selfpowered);
static int usb_ss_gadget_pullup(struct usb_gadget *gadget, int is_on);
static int usb_ss_gadget_udc_start(struct usb_gadget *gadget,
	struct usb_gadget_driver *driver);
static int usb_ss_gadget_udc_stop(struct usb_gadget *gadget);
static int usb_ss_init_ep(struct usb_ss_dev *usb_ss);
static int usb_ss_init_ep0(struct usb_ss_dev *usb_ss);
static void __cdns3_gadget_start(struct usb_ss_dev *usb_ss);
static void cdns_prepare_setup_packet(struct usb_ss_dev *usb_ss);
static void cdns_ep_config(struct usb_ss_endpoint *usb_ss_ep);

static const char *const speed_names[] = {
	[USB_SPEED_UNKNOWN] = "UNKNOWN",
	[USB_SPEED_LOW] = "low-speed",
	[USB_SPEED_FULL] = "full-speed",
	[USB_SPEED_HIGH] = "high-speed",
	[USB_SPEED_WIRELESS] = "wireless",
	[USB_SPEED_SUPER] = "super-speed",
};

const char *usb_speed_string(enum usb_device_speed speed)
{
	if (speed < 0 || speed >= ARRAY_SIZE(speed_names))
		speed = USB_SPEED_UNKNOWN;
	return speed_names[speed];
}

static struct usb_endpoint_descriptor cdns3_gadget_ep0_desc = {
	.bLength	= USB_DT_ENDPOINT_SIZE,
	.bDescriptorType = USB_DT_ENDPOINT,
	.bmAttributes	= USB_ENDPOINT_XFER_CONTROL,
};

static u32 gadget_readl(struct usb_ss_dev *usb_ss, uint32_t __iomem *reg)
{
	return cdns_readl(reg);
}

static void gadget_writel(struct usb_ss_dev *usb_ss,
		uint32_t __iomem *reg, u32 value)
{
	cdns_writel(reg, value);
}

/**
 * next_request - returns next request from list
 * @list: list containing requests
 *
 * Returns request or NULL if no requests in list
 */
static struct usb_request *next_request(struct list_head *list)
{
	if (list_empty(list))
		return NULL;
	return list_first_entry(list, struct usb_request, list);
}

/**
 * select_ep - selects endpoint
 * @usb_ss: extended gadget object
 * @ep: endpoint address
 */
static void select_ep(struct usb_ss_dev *usb_ss, u32 ep)
{
	if (!usb_ss || !usb_ss->regs) {
		dev_err(&usb_ss->dev, "Failed to select endpoint!\n");
		return;
	}

	gadget_writel(usb_ss, &usb_ss->regs->ep_sel, ep);
}

/**
 * usb_ss_allocate_trb_pool - Allocates TRB's pool for selected endpoint
 * @usb_ss_ep: extended endpoint object
 *
 * Function will return 0 on success or -ENOMEM on allocation error
 */
static int usb_ss_allocate_trb_pool(struct usb_ss_endpoint *usb_ss_ep)
{
	if (usb_ss_ep->trb_pool)
		return 0;

	usb_ss_ep->trb_pool = dma_alloc_coherent(
			sizeof(struct usb_ss_trb) * USB_SS_TRBS_NUM,
			(unsigned long *)&usb_ss_ep->trb_pool_dma);

	if (!usb_ss_ep->trb_pool) {
		dev_err(&(usb_ss_ep->usb_ss->dev),
				"Failed to allocate TRB pool for endpoint %s\n",
				usb_ss_ep->name);
		return -ENOMEM;
	}

	memset(usb_ss_ep->trb_pool, 0, sizeof(struct usb_ss_trb) * USB_SS_TRBS_NUM);

	return 0;
}

/**
 * cdns_ep_stall_flush - Stalls and flushes selected endpoint
 * @usb_ss_ep: extended endpoint object
 *
 * Endpoint must be selected before call to this function
 */
static void cdns_ep_stall_flush(struct usb_ss_endpoint *usb_ss_ep)
{
	struct usb_ss_dev *usb_ss = usb_ss_ep->usb_ss;

	gadget_writel(usb_ss, &usb_ss->regs->ep_cmd,
		EP_CMD__DFLUSH__MASK | EP_CMD__ERDY__MASK |
		EP_CMD__SSTALL__MASK);

	/* wait for DFLUSH cleared */
	while (gadget_readl(usb_ss,
		&usb_ss->regs->ep_cmd) & EP_CMD__DFLUSH__MASK)
		;

	usb_ss_ep->stalled_flag = 1;
}

/**
 * cdns_ep0_config - Configures default endpoint
 * @usb_ss: extended gadget object
 *
 * Functions sets parameters: maximal packet size and enables interrupts
 */
static void cdns_ep0_config(struct usb_ss_dev *usb_ss)
{
	u32 max_packet_size = 0;

	switch (usb_ss->gadget.speed) {
	case USB_SPEED_UNKNOWN:
		max_packet_size = ENDPOINT_MAX_PACKET_SIZE_0;
		usb_ss->gadget.ep0->maxpacket = ENDPOINT_MAX_PACKET_SIZE_0;
		cdns3_gadget_ep0_desc.wMaxPacketSize = cpu_to_le16(0);
		break;

	case USB_SPEED_LOW:
		max_packet_size = ENDPOINT_MAX_PACKET_SIZE_8;
		usb_ss->gadget.ep0->maxpacket = ENDPOINT_MAX_PACKET_SIZE_8;
		cdns3_gadget_ep0_desc.wMaxPacketSize = cpu_to_le16(8);
		break;

	case USB_SPEED_FULL:
		max_packet_size = ENDPOINT_MAX_PACKET_SIZE_64;
		usb_ss->gadget.ep0->maxpacket = ENDPOINT_MAX_PACKET_SIZE_64;
		cdns3_gadget_ep0_desc.wMaxPacketSize = cpu_to_le16(64);
		break;

	case USB_SPEED_HIGH:
		max_packet_size = ENDPOINT_MAX_PACKET_SIZE_64;
		usb_ss->gadget.ep0->maxpacket = ENDPOINT_MAX_PACKET_SIZE_64;
		cdns3_gadget_ep0_desc.wMaxPacketSize = cpu_to_le16(64);
		break;

	case USB_SPEED_WIRELESS:
		max_packet_size = ENDPOINT_MAX_PACKET_SIZE_64;
		usb_ss->gadget.ep0->maxpacket = ENDPOINT_MAX_PACKET_SIZE_64;
		cdns3_gadget_ep0_desc.wMaxPacketSize = cpu_to_le16(64);
		break;

	case USB_SPEED_SUPER:
		max_packet_size = ENDPOINT_MAX_PACKET_SIZE_512;
		usb_ss->gadget.ep0->maxpacket = ENDPOINT_MAX_PACKET_SIZE_512;
		cdns3_gadget_ep0_desc.wMaxPacketSize = cpu_to_le16(512);
		break;
	}

	/* init ep out */
	select_ep(usb_ss, USB_DIR_OUT);

	gadget_writel(usb_ss, &usb_ss->regs->ep_cfg,
		EP_CFG__ENABLE__MASK |
		EP_CFG__MAXPKTSIZE__WRITE(max_packet_size));
	gadget_writel(usb_ss, &usb_ss->regs->ep_sts_en,
		EP_STS_EN__SETUPEN__MASK |
		EP_STS_EN__DESCMISEN__MASK |
		EP_STS_EN__TRBERREN__MASK);

	/* init ep in */
	select_ep(usb_ss, USB_DIR_IN);

	gadget_writel(usb_ss, &usb_ss->regs->ep_cfg,
		EP_CFG__ENABLE__MASK |
		EP_CFG__MAXPKTSIZE__WRITE(max_packet_size));
	gadget_writel(usb_ss, &usb_ss->regs->ep_sts_en,
		EP_STS_EN__SETUPEN__MASK |
		EP_STS_EN__TRBERREN__MASK);

	cdns_prepare_setup_packet(usb_ss);
}

/**
 * cdns_gadget_unconfig - Unconfigures device controller
 * @usb_ss: extended gadget object
 */
static void cdns_gadget_unconfig(struct usb_ss_dev *usb_ss)
{
	/* RESET CONFIGURATION */
	gadget_writel(usb_ss, &usb_ss->regs->usb_conf,
		USB_CONF__CFGRST__MASK);

	usb_ss->hw_configured_flag = 0;
}

/**
 * cdns_ep0_run_transfer - Do transfer on default endpoint hardware
 * @usb_ss: extended gadget object
 * @dma_addr: physical address where data is/will be stored
 * @length: data length
 * @erdy: set it to 1 when ERDY packet should be sent -
 *        exit from flow control state
 */
static void cdns_ep0_run_transfer(struct usb_ss_dev *usb_ss,
		dma_addr_t dma_addr, unsigned int length, int erdy)
{
	usb_ss->trb_ep0[0] = TRB_SET_DATA_BUFFER_POINTER(dma_addr);
	usb_ss->trb_ep0[1] = TRB_SET_TRANSFER_LENGTH((u32)length);
	usb_ss->trb_ep0[2] = TRB_SET_CYCLE_BIT |
		TRB_SET_INT_ON_COMPLETION | TRB_TYPE_NORMAL;

	cdns_flush_cache((uintptr_t)usb_ss->trb_ep0, 20);
	cdns_flush_cache((uintptr_t)dma_addr, length);

	dev_dbg(&usb_ss->dev, "DRBL(%02X)\n",
		usb_ss->ep0_data_dir ? USB_DIR_IN : USB_DIR_OUT);

	select_ep(usb_ss, usb_ss->ep0_data_dir
		? USB_DIR_IN : USB_DIR_OUT);

	gadget_writel(usb_ss, &usb_ss->regs->ep_traddr,
			EP_TRADDR__TRADDR__WRITE(usb_ss->trb_ep0_dma));
	gadget_writel(usb_ss, &usb_ss->regs->ep_cmd,
		EP_CMD__DRDY__MASK); /* drbl */

	if (erdy)
		gadget_writel(usb_ss, &usb_ss->regs->ep_cmd,
			EP_CMD__ERDY__MASK);
}

/**
 * cdns_ep_run_transfer - Do transfer on no-default endpoint hardware
 * @usb_ss_ep: extended endpoint object
 *
 * Returns zero on success or negative value on failure
 */
static int cdns_ep_run_transfer(struct usb_ss_endpoint *usb_ss_ep)
{
	dma_addr_t trb_dma;
	struct usb_request *request = next_request(&usb_ss_ep->request_list);
	struct usb_ss_dev *usb_ss = usb_ss_ep->usb_ss;
	struct usb_ss_trb *trb;

	if (request == NULL)
		return -EINVAL;

	dev_dbg(&usb_ss->dev, "DRBL(%02X)\n",
		usb_ss_ep->endpoint.desc->bEndpointAddress);

	usb_ss_ep->hw_pending_flag = 1;
	trb_dma = request->dma;

	/* must allocate buffer aligned to 8 */
	if (request->dma % ADDR_MODULO_8) {
		memcpy(usb_ss_ep->cpu_addr, request->buf, request->length);
		trb_dma = usb_ss_ep->dma_addr;
	}

	cdns_flush_cache((uintptr_t)trb_dma, request->length);

	trb = usb_ss_ep->trb_pool;

	/* fill TRB */
	trb->offset0 = trb_dma;

	trb->offset4 = TRB_SET_BURST_LENGTH(16) |
		TRB_SET_TRANSFER_LENGTH(request->length);

	trb->offset8 = TRB_SET_CYCLE_BIT
		| TRB_SET_INT_ON_COMPLETION
		| TRB_SET_INT_ON_SHORT_PACKET
		| TRB_TYPE_NORMAL;

	cdns_flush_cache((uintptr_t)trb, sizeof(struct usb_ss_trb));

	/* arm transfer on selected endpoint */
	select_ep(usb_ss_ep->usb_ss,
			usb_ss_ep->endpoint.desc->bEndpointAddress);

	gadget_writel(usb_ss, &usb_ss->regs->ep_traddr,
			EP_TRADDR__TRADDR__WRITE(usb_ss_ep->trb_pool_dma));
	gadget_writel(usb_ss, &usb_ss->regs->ep_cmd,
		EP_CMD__DRDY__MASK); /* DRDY */
	return 0;
}

/**
 * cdns_get_setup_ret - Returns status of handling setup packet
 * Setup is handled by gadget driver
 * @usb_ss: extended gadget object
 * @ctrl_req: pointer to received setup packet
 *
 * Returns zero on success or negative value on failure
 */
static int cdns_get_setup_ret(struct usb_ss_dev *usb_ss,
		struct usb_ctrlrequest *ctrl_req)
{
	int ret;

	spin_unlock(&usb_ss->lock);
	usb_ss->setup_pending = 1;
	ret = usb_ss->gadget_driver->setup(&usb_ss->gadget, ctrl_req);
	usb_ss->setup_pending = 0;
	spin_lock(&usb_ss->lock);
	return ret;
}

static void cdns_prepare_setup_packet(struct usb_ss_dev *usb_ss)
{
	usb_ss->ep0_data_dir = 0;
	cdns_ep0_run_transfer(usb_ss, usb_ss->setup_dma, 8, 0);
}

/**
 * cdns_req_ep0_set_address - Handling of SET_ADDRESS standard USB request
 * @usb_ss: extended gadget object
 * @ctrl_req: pointer to received setup packet
 *
 * Returns 0 if success, error code on error
 */
static int cdns_req_ep0_set_address(struct usb_ss_dev *usb_ss,
		struct usb_ctrlrequest *ctrl_req)
{
	enum usb_device_state device_state = usb_ss->gadget.state;
	u32 reg;
	u32 addr;

	addr = le16_to_cpu(ctrl_req->wValue);

	if (addr > DEVICE_ADDRESS_MAX) {
		dev_err(&usb_ss->dev,
			"Device address (%d) cannot be greater than %d\n",
				addr, DEVICE_ADDRESS_MAX);
		return -EINVAL;
	}

	if (device_state == USB_STATE_CONFIGURED) {
		dev_err(&usb_ss->dev, "USB device already configured\n");
		return -EINVAL;
	}

	reg = gadget_readl(usb_ss, &usb_ss->regs->usb_cmd);

	gadget_writel(usb_ss, &usb_ss->regs->usb_cmd, reg
			| USB_CMD__FADDR__WRITE(addr)
			| USB_CMD__SET_ADDR__MASK);

	usb_gadget_set_state(&usb_ss->gadget,
		(addr ? USB_STATE_ADDRESS : USB_STATE_DEFAULT));

	cdns_prepare_setup_packet(usb_ss);

	gadget_writel(usb_ss, &usb_ss->regs->ep_cmd,
		EP_CMD__ERDY__MASK | EP_CMD__REQ_CMPL__MASK);
	return 0;
}

/**
 * cdns_req_ep0_get_status - Handling of GET_STATUS standard USB request
 * @usb_ss: extended gadget object
 * @ctrl_req: pointer to received setup packet
 *
 * Returns 0 if success, error code on error
 */
static int cdns_req_ep0_get_status(struct usb_ss_dev *usb_ss,
		struct usb_ctrlrequest *ctrl_req)
{
	u16 usb_status = 0;
	unsigned int length = 2;
	u32 recip = ctrl_req->bRequestType & USB_RECIP_MASK;
	u32 reg;

	switch (recip) {
	case USB_RECIP_DEVICE:
		reg = gadget_readl(usb_ss, &usb_ss->regs->usb_sts);

		if (reg & USB_STS__U1ENS__MASK)
			usb_status |= 1uL << USB_DEV_STAT_U1_ENABLED;

		if (reg & USB_STS__U2ENS__MASK)
			usb_status |= 1uL << USB_DEV_STAT_U2_ENABLED;

		if (usb_ss->wake_up_flag)
			usb_status |= 1uL << USB_DEVICE_REMOTE_WAKEUP;

		/* self powered */
		usb_status |= 1uL << USB_DEVICE_SELF_POWERED;
		break;

	case USB_RECIP_INTERFACE:
		return cdns_get_setup_ret(usb_ss, ctrl_req);

	case USB_RECIP_ENDPOINT:
		/* check if endpoint is stalled */
		select_ep(usb_ss, ctrl_req->wIndex);
		if (gadget_readl(usb_ss, &usb_ss->regs->ep_sts)
			& EP_STS__STALL__MASK)
			usb_status = 1;
		break;

	default:
		return -EINVAL;
	}

	*(u16 *)usb_ss->setup = cpu_to_le16(usb_status);

	usb_ss->actual_ep0_request = NULL;
	cdns_ep0_run_transfer(usb_ss, usb_ss->setup_dma, length, 1);
	return 0;
}

/**
 * cdns_req_ep0_handle_feature -
 * Handling of GET/SET_FEATURE standard USB request
 *
 * @usb_ss: extended gadget object
 * @ctrl_req: pointer to received setup packet
 * @set: must be set to 1 for SET_FEATURE request
 *
 * Returns 0 if success, error code on error
 */
static int cdns_req_ep0_handle_feature(struct usb_ss_dev *usb_ss,
		struct usb_ctrlrequest *ctrl_req, int set)
{
	u32 recip = ctrl_req->bRequestType & USB_RECIP_MASK;
	struct usb_ss_endpoint *usb_ss_ep;
	u32 reg;
	u8 tmode = 0;

	switch (recip) {
	case USB_RECIP_DEVICE:

		switch (ctrl_req->wValue) {
		case USB_DEVICE_U1_ENABLE:
			if (usb_ss->gadget.state != USB_STATE_CONFIGURED)
				return -EINVAL;
			if (usb_ss->gadget.speed != USB_SPEED_SUPER)
				return -EINVAL;

			reg = gadget_readl(usb_ss, &usb_ss->regs->usb_conf);
			if (set)
				/* set U1EN */
				reg |= USB_CONF__U1EN__MASK;
			else
				/* set U1 disable */
				reg |= USB_CONF__U1DS__MASK;
			gadget_writel(usb_ss, &usb_ss->regs->usb_conf, reg);
			break;

		case USB_DEVICE_U2_ENABLE:
			if (usb_ss->gadget.state != USB_STATE_CONFIGURED)
				return -EINVAL;
			if (usb_ss->gadget.speed != USB_SPEED_SUPER)
				return -EINVAL;

			reg = gadget_readl(usb_ss, &usb_ss->regs->usb_conf);
			if (set)
				/* set U2EN */
				reg |= USB_CONF__U2EN__MASK;
			else
				/* set U2 disable */
				reg |= USB_CONF__U2DS__MASK;
			gadget_writel(usb_ss, &usb_ss->regs->usb_conf, reg);
			break;

		case USB_DEVICE_A_ALT_HNP_SUPPORT:
			break;

		case USB_DEVICE_A_HNP_SUPPORT:
			break;

		case USB_DEVICE_B_HNP_ENABLE:
			if (!usb_ss->gadget.b_hnp_enable && set)
				usb_ss->gadget.b_hnp_enable = 1;
			break;

		case USB_DEVICE_REMOTE_WAKEUP:
			usb_ss->wake_up_flag = !!set;
			break;

		case USB_DEVICE_TEST_MODE:
			if (usb_ss->gadget.state != USB_STATE_CONFIGURED)
				return -EINVAL;
			if (usb_ss->gadget.speed != USB_SPEED_HIGH &&
				usb_ss->gadget.speed !=	USB_SPEED_FULL)
				return -EINVAL;
			if (ctrl_req->wLength != 0 ||
				ctrl_req->bRequestType & USB_DIR_IN) {
				dev_err(&usb_ss->dev, "req is error\n");
				return -EINVAL;
			}
			tmode = le16_to_cpu(ctrl_req->wIndex) >> 8;
			switch (tmode) {
			case TEST_J:
			case TEST_K:
			case TEST_SE0_NAK:
			case TEST_PACKET:
				reg = gadget_readl(usb_ss,
					&usb_ss->regs->usb_cmd);
				tmode -= 1;
				reg |= USB_CMD__STMODE |
					USB_CMD__TMODE_SEL(tmode);
				gadget_writel(usb_ss, &usb_ss->regs->usb_cmd,
						reg);
				dev_info(&usb_ss->dev,
					"set test mode, val=0x%x", reg);
				break;
			default:
				return -EINVAL;
			}
			break;

		default:
			return -EINVAL;
		}
		break;

	case USB_RECIP_INTERFACE:
		return cdns_get_setup_ret(usb_ss, ctrl_req);

	case USB_RECIP_ENDPOINT:
		select_ep(usb_ss, ctrl_req->wIndex);

		if (set) {
			/* set stall */
			gadget_writel(usb_ss, &usb_ss->regs->ep_cmd,
			EP_CMD__SSTALL__MASK);

			/* handle non zero endpoint software endpoint */
			if (ctrl_req->wIndex & 0x7F) {
				usb_ss_ep = usb_ss->eps[CAST_EP_ADDR_TO_INDEX(
						ctrl_req->wIndex)];
				usb_ss_ep->stalled_flag = 1;
			}
		} else {
			struct usb_request *request;

			if (ctrl_req->wIndex & 0x7F) {
				if (usb_ss->eps[CAST_EP_ADDR_TO_INDEX(
					ctrl_req->wIndex)]->wedge_flag)
					goto jmp_wedge;
			}

			/* clear stall */
			gadget_writel(usb_ss, &usb_ss->regs->ep_cmd,
			EP_CMD__CSTALL__MASK | EP_CMD__EPRST__MASK);
			/* wait for EPRST cleared */
			while (gadget_readl(usb_ss, &usb_ss->regs->ep_cmd)
					& EP_CMD__EPRST__MASK)
				;

			/* handle non zero endpoint software endpoint */
			if (ctrl_req->wIndex & 0x7F) {
				usb_ss_ep = usb_ss->eps[CAST_EP_ADDR_TO_INDEX(
						ctrl_req->wIndex)];
				usb_ss_ep->stalled_flag = 0;

				request = next_request(
						&usb_ss_ep->request_list);
				if (request)
					cdns_ep_run_transfer(usb_ss_ep);
			}
		}
jmp_wedge:
		select_ep(usb_ss, 0x00);
		break;

	default:
		return -EINVAL;
	}

	gadget_writel(usb_ss, &usb_ss->regs->ep_cmd,
		EP_CMD__ERDY__MASK | EP_CMD__REQ_CMPL__MASK);

	return 0;
}

/**
 * cdns_req_ep0_set_sel - Handling of SET_SEL standard USB request
 * @usb_ss: extended gadget object
 * @ctrl_req: pointer to received setup packet
 *
 * Returns 0 if success, error code on error
 */
static int cdns_req_ep0_set_sel(struct usb_ss_dev *usb_ss,
		struct usb_ctrlrequest *ctrl_req)
{
	if (usb_ss->gadget.state < USB_STATE_ADDRESS)
		return -EINVAL;

	if (ctrl_req->wLength != 6) {
		dev_err(&usb_ss->dev, "Set SEL should be 6 bytes, got %d\n",
				ctrl_req->wLength);
		return -EINVAL;
	}

	usb_ss->ep0_data_dir = 0;
	usb_ss->actual_ep0_request = NULL;
	cdns_ep0_run_transfer(usb_ss, usb_ss->setup_dma, 6, 1);

	return 0;
}

/**
 * cdns_req_ep0_set_isoch_delay -
 * Handling of GET_ISOCH_DELAY standard USB request
 * @usb_ss: extended gadget object
 * @ctrl_req: pointer to received setup packet
 *
 * Returns 0 if success, error code on error
 */
static int cdns_req_ep0_set_isoch_delay(struct usb_ss_dev *usb_ss,
		struct usb_ctrlrequest *ctrl_req)
{
	if (ctrl_req->wIndex || ctrl_req->wLength)
		return -EINVAL;

	usb_ss->isoch_delay = ctrl_req->wValue;
	gadget_writel(usb_ss, &usb_ss->regs->ep_cmd,
	EP_CMD__ERDY__MASK | EP_CMD__REQ_CMPL__MASK);
	return 0;
}

/**
 * cdns_req_ep0_set_configuration - Handling of SET_CONFIG standard USB request
 * @usb_ss: extended gadget object
 * @ctrl_req: pointer to received setup packet
 *
 * Returns 0 if success, 0x7FFF on deferred status stage, error code on error
 */
static int cdns_req_ep0_set_configuration(struct usb_ss_dev *usb_ss,
		struct usb_ctrlrequest *ctrl_req)
{
	enum usb_device_state device_state = usb_ss->gadget.state;
	u32 config = le16_to_cpu(ctrl_req->wValue);
	struct usb_ep *ep;
	struct usb_ss_endpoint *usb_ss_ep, *temp_ss_ep;
	int i, result = 0;

	switch (device_state) {
	case USB_STATE_ADDRESS:
		/* Configure non-control EPs */
		list_for_each_entry_safe(usb_ss_ep, temp_ss_ep,
			&usb_ss->ep_match_list, ep_match_pending_list) {
			cdns_ep_config(usb_ss_ep);
			list_del(&usb_ss_ep->ep_match_pending_list);
		}

		list_for_each_entry(ep, &(usb_ss->gadget.ep_list), ep_list) {
			usb_ss_ep = to_usb_ss_ep(ep);
			if (usb_ss_ep->used)
				cdns_ep_config(usb_ss_ep);
		}

#ifdef CDNS_THREADED_IRQ_HANDLING
		usb_ss->ep_ien = gadget_readl(usb_ss, &usb_ss->regs->ep_ien)
			| EP_IEN__EOUTEN0__MASK | EP_IEN__EINEN0__MASK;
#endif
		result = cdns_get_setup_ret(usb_ss, ctrl_req);

		if (result != 0)
			return result;

		if (config) {
			if (!usb_ss->hw_configured_flag) {
				/* SET CONFIGURATION */
				gadget_writel(usb_ss, &usb_ss->regs->usb_conf,
					USB_CONF__CFGSET__MASK);
				gadget_writel(usb_ss, &usb_ss->regs->ep_cmd,
					EP_CMD__ERDY__MASK |
					EP_CMD__REQ_CMPL__MASK);
				/* wait until configuration set */
				while (!(gadget_readl(usb_ss,
					&usb_ss->regs->usb_sts)
					& USB_STS__CFGSTS__MASK))
					;
				usb_ss->hw_configured_flag = 1;

				list_for_each_entry(ep,
					&usb_ss->gadget.ep_list,
					ep_list) {
					if (to_usb_ss_ep(ep)->enabled)
						cdns_ep_run_transfer(
							to_usb_ss_ep(ep));
				}
			}

			usb_gadget_set_state(&usb_ss->gadget,
						USB_STATE_CONFIGURED);

		} else {
			cdns_gadget_unconfig(usb_ss);
			for (i = 0; i < usb_ss->ep_nums; i++)
				usb_ss->eps[i]->enabled = 0;
			usb_gadget_set_state(&usb_ss->gadget,
				USB_STATE_ADDRESS);
		}
		break;

	case USB_STATE_CONFIGURED:
		result = cdns_get_setup_ret(usb_ss, ctrl_req);
		if (!config && !result) {
			cdns_gadget_unconfig(usb_ss);
			for (i = 0; i < usb_ss->ep_nums; i++)
				usb_ss->eps[i]->enabled = 0;
			usb_gadget_set_state(&usb_ss->gadget,
				USB_STATE_ADDRESS);
		}
		break;

	default:
		result = -EINVAL;
	}

	return result;
}

/**
 * cdns_ep0_standard_request - Handling standard USB requests
 * @usb_ss: extended gadget object
 * @ctrl_req: pointer to received setup packet
 *
 * Returns 0 if success, error code on error
 */
static int cdns_ep0_standard_request(struct usb_ss_dev *usb_ss,
		struct usb_ctrlrequest *ctrl_req)
{
	switch (ctrl_req->bRequest) {
	case USB_REQ_SET_ADDRESS:
		return cdns_req_ep0_set_address(usb_ss, ctrl_req);
	case USB_REQ_SET_CONFIGURATION:
		return cdns_req_ep0_set_configuration(usb_ss, ctrl_req);
	case USB_REQ_GET_STATUS:
		return cdns_req_ep0_get_status(usb_ss, ctrl_req);
	case USB_REQ_CLEAR_FEATURE:
		return cdns_req_ep0_handle_feature(usb_ss, ctrl_req, 0);
	case USB_REQ_SET_FEATURE:
		return cdns_req_ep0_handle_feature(usb_ss, ctrl_req, 1);
	case USB_REQ_SET_SEL:
		return cdns_req_ep0_set_sel(usb_ss, ctrl_req);
	case USB_REQ_SET_ISOCH_DELAY:
		return cdns_req_ep0_set_isoch_delay(usb_ss, ctrl_req);
	default:
		return cdns_get_setup_ret(usb_ss, ctrl_req);
	}
}

/**
 * cdns_ep0_setup_phase - Handling setup USB requests
 * @usb_ss: extended gadget object
 */
static void cdns_ep0_setup_phase(struct usb_ss_dev *usb_ss)
{
	int result;
	struct usb_ctrlrequest *ctrl_req =
			(struct usb_ctrlrequest *)usb_ss->setup;

	if ((ctrl_req->bRequestType & USB_TYPE_MASK) == USB_TYPE_STANDARD)
		result = cdns_ep0_standard_request(usb_ss, ctrl_req);
	else
		result = cdns_get_setup_ret(usb_ss, ctrl_req);

	if (result != 0 && result != USB_GADGET_DELAYED_STATUS) {
		dev_dbg(&usb_ss->dev, "STALL(00) %d\n", result);

		/* set_stall on ep0 */
		select_ep(usb_ss, 0x00);
		gadget_writel(usb_ss, &usb_ss->regs->ep_cmd,
			EP_CMD__SSTALL__MASK);
		gadget_writel(usb_ss, &usb_ss->regs->ep_cmd,
			EP_CMD__ERDY__MASK | EP_CMD__REQ_CMPL__MASK);
		return;
	}
}

/**
 * cdns_check_ep_interrupt_proceed - Processes interrupt related to endpoint
 * @usb_ss_ep: extended endpoint object
 *
 * Returns 0
 */
static int cdns_check_ep_interrupt_proceed(struct usb_ss_endpoint *usb_ss_ep)
{
	struct usb_ss_dev *usb_ss = usb_ss_ep->usb_ss;
	struct usb_request *request;
	u32 ep_sts_reg;

	select_ep(usb_ss, usb_ss_ep->address);
	ep_sts_reg = gadget_readl(usb_ss, &usb_ss->regs->ep_sts);

	dev_dbg(&usb_ss->dev, "EP_STS: %08X\n", ep_sts_reg);

	if (ep_sts_reg & EP_STS__TRBERR__MASK) {
		gadget_writel(usb_ss,
			&usb_ss->regs->ep_sts, EP_STS__TRBERR__MASK);

		dev_dbg(&usb_ss->dev, "TRBERR(%02X)\n",
			usb_ss_ep->endpoint.desc->bEndpointAddress);
	}

	if (ep_sts_reg & EP_STS__ISOERR__MASK) {
		gadget_writel(usb_ss,
			&usb_ss->regs->ep_sts, EP_STS__ISOERR__MASK);
		dev_dbg(&usb_ss->dev, "ISOERR(%02X)\n",
			usb_ss_ep->endpoint.desc->bEndpointAddress);
	}

	if (ep_sts_reg & EP_STS__OUTSMM__MASK) {
		gadget_writel(usb_ss, &usb_ss->regs->ep_sts,
			EP_STS__OUTSMM__MASK);
		dev_dbg(&usb_ss->dev, "OUTSMM(%02X)\n",
			usb_ss_ep->endpoint.desc->bEndpointAddress);
	}

	if (ep_sts_reg & EP_STS__NRDY__MASK) {
		gadget_writel(usb_ss,
			&usb_ss->regs->ep_sts, EP_STS__NRDY__MASK);
		dev_dbg(&usb_ss->dev, "NRDY(%02X)\n",
			usb_ss_ep->endpoint.desc->bEndpointAddress);
	}

	if ((ep_sts_reg & EP_STS__IOC__MASK)
			|| (ep_sts_reg & EP_STS__ISP__MASK)) {
		cdns_flush_cache((uintptr_t)usb_ss_ep->trb_pool, sizeof(struct usb_ss_trb));

		gadget_writel(usb_ss, &usb_ss->regs->ep_sts,
		EP_STS__IOC__MASK | EP_STS__ISP__MASK);

		/* get just completed request */
		request = next_request(&usb_ss_ep->request_list);
		usb_gadget_unmap_request(&usb_ss->gadget, request,
			usb_ss_ep->endpoint.desc->bEndpointAddress
			& ENDPOINT_DIR_MASK);

		request->status = 0;
		request->actual =
			le32_to_cpu(((u32 *)usb_ss_ep->trb_pool)[1])
			& ACTUAL_TRANSFERRED_BYTES_MASK;

		dev_dbg(&usb_ss->dev, "IOC(%02X) %d\n",
			usb_ss_ep->endpoint.desc->bEndpointAddress,
			request->actual);

		list_del(&request->list);

		usb_ss_ep->hw_pending_flag = 0;
		if (request->complete) {
			spin_unlock(&usb_ss->lock);
			usb_gadget_giveback_request(&usb_ss_ep->endpoint,
				request);
			spin_lock(&usb_ss->lock);
		}

		/* handle deferred STALL */
		if (usb_ss_ep->stalled_flag) {
			cdns_ep_stall_flush(usb_ss_ep);
			return 0;
		}

		/* exit if hardware transfer already started */
		if (usb_ss_ep->hw_pending_flag)
			return 0;

		/* if any request queued run it! */
		if (!list_empty(&usb_ss_ep->request_list))
			cdns_ep_run_transfer(usb_ss_ep);
	}

	if (ep_sts_reg & EP_STS__DESCMIS__MASK) {
		gadget_writel(usb_ss,
			&usb_ss->regs->ep_sts, EP_STS__DESCMIS__MASK);
		dev_dbg(&usb_ss->dev, "DESCMIS(%02X)\n",
			usb_ss_ep->endpoint.desc->bEndpointAddress);
	}

	return 0;
}

/**
 * cdns_check_ep0_interrupt_proceed - Processes interrupt related to endpoint 0
 * @usb_ss: extended gadget object
 * @dir: 1 for IN direction, 0 for OUT direction
 */
static void cdns_check_ep0_interrupt_proceed(struct usb_ss_dev *usb_ss, int dir)
{
	u32 ep_sts_reg;
	int i;

	select_ep(usb_ss, 0 | (dir ? USB_DIR_IN : USB_DIR_OUT));
	ep_sts_reg = gadget_readl(usb_ss, &usb_ss->regs->ep_sts);

	dev_dbg(&usb_ss->dev, "EP_STS: %08X\n", ep_sts_reg);

	if ((ep_sts_reg & EP_STS__SETUP__MASK) && (dir == 0)) {
		cdns_flush_cache((uintptr_t)usb_ss->setup, 8);

		dev_dbg(&usb_ss->dev, "SETUP(%02X)\n", 0x00);

		gadget_writel(usb_ss, &usb_ss->regs->ep_sts,
			EP_STS__SETUP__MASK |
			EP_STS__IOC__MASK | EP_STS__ISP__MASK);

		dev_dbg(&usb_ss->dev, "SETUP: ");
		for (i = 0; i < 8; i++)
			dev_dbg(&usb_ss->dev, "%02X ", usb_ss->setup[i]);
		dev_dbg(&usb_ss->dev, "\nSTATE: %d\n", usb_ss->gadget.state);
		usb_ss->ep0_data_dir = usb_ss->setup[0] & USB_DIR_IN;
		cdns_ep0_setup_phase(usb_ss);
		ep_sts_reg &= ~(EP_STS__SETUP__MASK |
			EP_STS__IOC__MASK |
			EP_STS__ISP__MASK);
	}

	if (ep_sts_reg & EP_STS__TRBERR__MASK) {
		gadget_writel(usb_ss,
			&usb_ss->regs->ep_sts, EP_STS__TRBERR__MASK);
		dev_dbg(&usb_ss->dev, "TRBERR(%02X)\n",
			dir ? USB_DIR_IN : USB_DIR_OUT);
	}

	if (ep_sts_reg & EP_STS__DESCMIS__MASK) {
		gadget_writel(usb_ss,
			&usb_ss->regs->ep_sts, EP_STS__DESCMIS__MASK);

		dev_dbg(&usb_ss->dev, "DESCMIS(%02X)\n",
			dir ? USB_DIR_IN : USB_DIR_OUT);

		if (dir == 0 && !usb_ss->setup_pending) {
			usb_ss->ep0_data_dir = 0;
			cdns_ep0_run_transfer(usb_ss,
				usb_ss->setup_dma, 8, 0);
		}
	}

	if ((ep_sts_reg & EP_STS__IOC__MASK) ||
		(ep_sts_reg & EP_STS__ISP__MASK)) {
		cdns_flush_cache((uintptr_t)usb_ss->trb_ep0, 20);

		gadget_writel(usb_ss,
			&usb_ss->regs->ep_sts, EP_STS__IOC__MASK);
		if (usb_ss->actual_ep0_request) {
			usb_gadget_unmap_request(&usb_ss->gadget,
					usb_ss->actual_ep0_request,
					usb_ss->ep0_data_dir);

			usb_ss->actual_ep0_request->actual =
				le32_to_cpu((usb_ss->trb_ep0)[1])
				& ACTUAL_TRANSFERRED_BYTES_MASK;

			dev_dbg(&usb_ss->dev, "IOC(%02X) %d\n",
				dir ? USB_DIR_IN : USB_DIR_OUT,
				usb_ss->actual_ep0_request->actual);
			list_del_init(&usb_ss->actual_ep0_request->list);
		}

		if (usb_ss->actual_ep0_request &&
			usb_ss->actual_ep0_request->complete) {
			spin_unlock(&usb_ss->lock);
			usb_ss->actual_ep0_request->complete(usb_ss->gadget.ep0,
					usb_ss->actual_ep0_request);
			spin_lock(&usb_ss->lock);
		}
		cdns_prepare_setup_packet(usb_ss);
		gadget_writel(usb_ss,
			&usb_ss->regs->ep_cmd, EP_CMD__REQ_CMPL__MASK);
	}
}

/**
 * cdns_check_usb_interrupt_proceed - Processes interrupt related to device
 * @usb_ss: extended gadget object
 * @usb_ists: bitmap representation of device's reported interrupts
 * (usb_ists register value)
 */
static void cdns_check_usb_interrupt_proceed(struct usb_ss_dev *usb_ss,
		u32 usb_ists)
{
	int interrupt_bit = ffs(usb_ists) - 1;
	int speed;
	u32 val;

	dev_dbg(&usb_ss->dev, "USB interrupt detected\n");

	switch (interrupt_bit) {
	case USB_ISTS__CON2I__SHIFT:
		/* FS/HS Connection detected */
		dev_dbg(&usb_ss->dev,
			"[Interrupt] FS/HS Connection detected\n");
		val = gadget_readl(usb_ss, &usb_ss->regs->usb_sts);
		speed = USB_STS__USBSPEED__READ(val);
		if (speed == USB_SPEED_WIRELESS)
			speed = USB_SPEED_SUPER;
		dev_dbg(&usb_ss->dev, "Speed value: %s (%d), usbsts:0x%x\n",
			usb_speed_string(speed), speed, val);
		usb_ss->gadget.speed = speed;
		usb_ss->is_connected = 1;
		usb_gadget_set_state(&usb_ss->gadget, USB_STATE_POWERED);
		cdns_ep0_config(usb_ss);
		break;

	case USB_ISTS__CONI__SHIFT:
		/* SS Connection detected */
		dev_dbg(&usb_ss->dev, "[Interrupt] SS Connection detected\n");
		val = gadget_readl(usb_ss, &usb_ss->regs->usb_sts);
		speed = USB_STS__USBSPEED__READ(val);
		if (speed == USB_SPEED_WIRELESS)
			speed = USB_SPEED_SUPER;
		dev_dbg(&usb_ss->dev, "Speed value: %s (%d), usbsts:0x%x\n",
			usb_speed_string(speed), speed, val);
		usb_ss->gadget.speed = speed;
		usb_ss->is_connected = 1;
		usb_gadget_set_state(&usb_ss->gadget, USB_STATE_POWERED);
		cdns_ep0_config(usb_ss);
		break;

	case USB_ISTS__DIS2I__SHIFT:
	case USB_ISTS__DISI__SHIFT:
		/* SS Disconnection detected */
		val = gadget_readl(usb_ss, &usb_ss->regs->usb_sts);
		dev_dbg(&usb_ss->dev,
			"[Interrupt] Disconnection detected: usbsts:0x%x\n",
			val);
		if (usb_ss->gadget_driver &&
			usb_ss->gadget_driver->disconnect) {
			spin_unlock(&usb_ss->lock);
			usb_ss->gadget_driver->disconnect(&usb_ss->gadget);
			spin_lock(&usb_ss->lock);
		}
		usb_ss->gadget.speed = USB_SPEED_UNKNOWN;
		usb_gadget_set_state(&usb_ss->gadget, USB_STATE_NOTATTACHED);
		usb_ss->is_connected = 0;
		cdns_gadget_unconfig(usb_ss);
		break;

	case USB_ISTS__L2ENTI__SHIFT:
		dev_dbg(&usb_ss->dev,
			 "[Interrupt] Device suspended\n");
		break;

	case USB_ISTS__L2EXTI__SHIFT:
		dev_dbg(&usb_ss->dev, "[Interrupt] L2 exit detected\n");
		/*
		 * Exit from standby mode
		 * on L2 exit (Suspend in HS/FS or SS)
		 */
		break;
	case USB_ISTS__U3EXTI__SHIFT:
		/*
		 * Exit from standby mode
		 * on U3 exit (Suspend in HS/FS or SS)
		 */
		dev_dbg(&usb_ss->dev, "[Interrupt] U3 exit detected\n");
		break;

		/* resets cases */
	case USB_ISTS__UWRESI__SHIFT:
	case USB_ISTS__UHRESI__SHIFT:
	case USB_ISTS__U2RESI__SHIFT:
		dev_dbg(&usb_ss->dev, "[Interrupt] Reset detected\n");
		speed = USB_STS__USBSPEED__READ(
				gadget_readl(usb_ss, &usb_ss->regs->usb_sts));
		if (speed == USB_SPEED_WIRELESS)
			speed = USB_SPEED_SUPER;
		usb_gadget_set_state(&usb_ss->gadget, USB_STATE_DEFAULT);
		usb_ss->gadget.speed = speed;
		cdns_gadget_unconfig(usb_ss);
		cdns_ep0_config(usb_ss);
		break;
	default:
		break;
	}

	/* Clear interrupt bit */
	gadget_writel(usb_ss, &usb_ss->regs->usb_ists, (1uL << interrupt_bit));
}

#ifdef CDNS_THREADED_IRQ_HANDLING
static irqreturn_t cdns_irq_handler(int irq, void *_usb_ss)
{
	struct usb_ss_dev *usb_ss = _usb_ss;

	usb_ss->usb_ien = gadget_readl(usb_ss, &usb_ss->regs->usb_ien);
	usb_ss->ep_ien = gadget_readl(usb_ss, &usb_ss->regs->ep_ien);

	if (!gadget_readl(usb_ss, &usb_ss->regs->usb_ists) &&
		!gadget_readl(usb_ss, &usb_ss->regs->ep_ists)) {
		dev_dbg(&usb_ss->dev, "--BUBBLE INTERRUPT 0 !!!\n");
		if (gadget_readl(usb_ss, &usb_ss->regs->usb_sts) &
				USB_STS__CFGSTS__MASK)
			return IRQ_HANDLED;
		return IRQ_NONE;
	}

	gadget_writel(usb_ss, &usb_ss->regs->usb_ien, 0);
	gadget_writel(usb_ss, &usb_ss->regs->ep_ien, 0);

	gadget_readl(usb_ss, &usb_ss->regs->dma_axi_ctrl);
	return IRQ_WAKE_THREAD;
}
#endif

/**
 * cdns_irq_handler - irq line interrupt handler
 * @cdns: cdns3 instance
 *
 * Returns IRQ_HANDLED when interrupt raised by USBSS_DEV,
 * IRQ_NONE when interrupt raised by other device connected
 * to the irq line
 */
static int cdns_irq_handler_thread(struct cdns3 *cdns)
{
	struct usb_ss_dev *usb_ss =
		container_of(cdns->gadget_dev, struct usb_ss_dev, dev);
	u32 reg;
	int ret = IRQ_NONE;
	unsigned long flags;

	spin_lock_irqsave(&usb_ss->lock, flags);

	/* check USB device interrupt */
	reg = gadget_readl(usb_ss, &usb_ss->regs->usb_ists);
	if (reg) {
		dev_dbg(&usb_ss->dev, "usb_ists: %08X\n", reg);
		cdns_check_usb_interrupt_proceed(usb_ss, reg);
		ret = IRQ_HANDLED;
	}

	/* check endpoint interrupt */
	reg = gadget_readl(usb_ss, &usb_ss->regs->ep_ists);
	if (reg != 0) {
		dev_dbg(&usb_ss->dev, "ep_ists: %08X\n", reg);
	} else {
		if (gadget_readl(usb_ss, &usb_ss->regs->usb_sts) &
				USB_STS__CFGSTS__MASK)
			ret = IRQ_HANDLED;
		goto irqend;
	}

	/* handle default endpoint OUT */
	if (reg & EP_ISTS__EOUT0__MASK) {
		cdns_check_ep0_interrupt_proceed(usb_ss, 0);
		ret = IRQ_HANDLED;
	}

	/* handle default endpoint IN */
	if (reg & EP_ISTS__EIN0__MASK) {
		cdns_check_ep0_interrupt_proceed(usb_ss, 1);
		ret = IRQ_HANDLED;
	}

	/* check if interrupt from non default endpoint, if no exit */
	reg &= ~(EP_ISTS__EOUT0__MASK | EP_ISTS__EIN0__MASK);
	if (!reg)
		goto irqend;

	do {
		unsigned int bit_pos = ffs(reg);
		u32 bit_mask = 1 << (bit_pos - 1);

		dev_dbg(&usb_ss->dev, "Interrupt on index: %d bitmask %08X\n",
				CAST_EP_REG_POS_TO_INDEX(bit_pos), bit_mask);
		cdns_check_ep_interrupt_proceed(
				usb_ss->eps[CAST_EP_REG_POS_TO_INDEX(bit_pos)]);
		reg &= ~bit_mask;
		ret = IRQ_HANDLED;
	} while (reg);

irqend:

	spin_unlock_irqrestore(&usb_ss->lock, flags);
#ifdef CDNS_THREADED_IRQ_HANDLING
	local_irq_save(flags);
	gadget_writel(usb_ss, &usb_ss->regs->usb_ien, usb_ss->usb_ien);
	gadget_writel(usb_ss, &usb_ss->regs->ep_ien, usb_ss->ep_ien);
	local_irq_restore(flags);
#endif
	return ret;
}

/**
 * usb_ss_gadget_ep0_enable
 * Function shouldn't be called by gadget driver,
 * endpoint 0 is allways active
 */
static int usb_ss_gadget_ep0_enable(struct usb_ep *ep,
		const struct usb_endpoint_descriptor *desc)
{
	return -EINVAL;
}

/**
 * usb_ss_gadget_ep0_disable
 * Function shouldn't be called by gadget driver,
 * endpoint 0 is allways active
 */
static int usb_ss_gadget_ep0_disable(struct usb_ep *ep)
{
	return -EINVAL;
}

/**
 * usb_ss_gadget_ep0_set_halt
 * @ep: pointer to endpoint zero object
 * @value: 1 for set stall, 0 for clear stall
 *
 * Returns 0
 */
static int usb_ss_gadget_ep0_set_halt(struct usb_ep *ep, int value)
{
	/* TODO */
	return 0;
}

/**
 * usb_ss_gadget_ep0_queue Transfer data on endpoint zero
 * @ep: pointer to endpoint zero object
 * @request: pointer to request object
 * @gfp_flags: gfp flags
 *
 * Returns 0 on success, error code elsewhere
 */
static int usb_ss_gadget_ep0_queue(struct usb_ep *ep,
		struct usb_request *request, gfp_t gfp_flags)
{
	int ret;
	unsigned long flags;
	int erdy_sent = 0;
	/* get extended endpoint */
	struct usb_ss_endpoint *usb_ss_ep =
		to_usb_ss_ep(ep);
	struct usb_ss_dev *usb_ss = usb_ss_ep->usb_ss;

	dev_dbg(&usb_ss->dev, "QUEUE(%02X) %d\n",
		usb_ss->ep0_data_dir ? USB_DIR_IN : USB_DIR_OUT,
		request->length);

	/* send STATUS stage */
	if (request->length == 0 && request->zero == 0) {
		spin_lock_irqsave(&usb_ss->lock, flags);
		select_ep(usb_ss, 0x00);
		if (!usb_ss->hw_configured_flag) {
			gadget_writel(usb_ss, &usb_ss->regs->usb_conf,
			USB_CONF__CFGSET__MASK); /* SET CONFIGURATION */
			cdns_prepare_setup_packet(usb_ss);
			gadget_writel(usb_ss, &usb_ss->regs->ep_cmd,
				EP_CMD__ERDY__MASK | EP_CMD__REQ_CMPL__MASK);
			/* wait until configuration set */
			while (!(gadget_readl(usb_ss, &usb_ss->regs->usb_sts)
					& USB_STS__CFGSTS__MASK))
				;
			erdy_sent = 1;
			usb_ss->hw_configured_flag = 1;

			list_for_each_entry(ep,
				&usb_ss->gadget.ep_list,
				ep_list) {
				if (to_usb_ss_ep(ep)->enabled)
					cdns_ep_run_transfer(
						to_usb_ss_ep(ep));
			}
		}
		if (!erdy_sent)
			gadget_writel(usb_ss, &usb_ss->regs->ep_cmd,
			EP_CMD__ERDY__MASK | EP_CMD__REQ_CMPL__MASK);
		if (request->complete)
			request->complete(usb_ss->gadget.ep0, request);
		spin_unlock_irqrestore(&usb_ss->lock, flags);
		return 0;
	}

	spin_lock_irqsave(&usb_ss->lock, flags);
	ret = usb_gadget_map_request(&usb_ss->gadget, request,
			usb_ss->ep0_data_dir);
	if (ret) {
		dev_err(&usb_ss->dev, "failed to map request\n");
		return -EINVAL;
	}

	usb_ss->actual_ep0_request = request;
	cdns_ep0_run_transfer(usb_ss, request->dma, request->length, 1);
	list_add_tail(&request->list, &usb_ss_ep->request_list);
	spin_unlock_irqrestore(&usb_ss->lock, flags);

	return 0;
}

/**
 * cdns_ep_config Configure hardware endpoint
 * @usb_ss_ep: extended endpoint object
 */
static void cdns_ep_config(struct usb_ss_endpoint *usb_ss_ep)
{
	struct usb_ss_dev *usb_ss = usb_ss_ep->usb_ss;
	u32 ep_cfg = 0;
	u32 max_packet_size = 0;
	u32 bEndpointAddress = usb_ss_ep->num | usb_ss_ep->dir;
	u32 interrupt_mask = 0;
	bool is_iso_ep = (usb_ss_ep->type == USB_ENDPOINT_XFER_ISOC);

	dev_dbg(&usb_ss->dev, "%s: %s addr=0x%x, speed %d, is_iso_ep %d\n", __func__,
			usb_ss_ep->name, bEndpointAddress, usb_ss->gadget.speed, is_iso_ep);

	if (is_iso_ep) {
		ep_cfg = EP_CFG__EPTYPE__WRITE(USB_ENDPOINT_XFER_ISOC);
		interrupt_mask = INTERRUPT_MASK;
	} else {
		ep_cfg = EP_CFG__EPTYPE__WRITE(USB_ENDPOINT_XFER_BULK);
	}

	switch (usb_ss->gadget.speed) {
	case USB_SPEED_UNKNOWN:
		max_packet_size = ENDPOINT_MAX_PACKET_SIZE_0;
		break;

	case USB_SPEED_LOW:
		max_packet_size = ENDPOINT_MAX_PACKET_SIZE_8;
		break;

	case USB_SPEED_FULL:
		max_packet_size = (is_iso_ep ?
			ENDPOINT_MAX_PACKET_SIZE_1023 :
			ENDPOINT_MAX_PACKET_SIZE_64);
		break;

	case USB_SPEED_HIGH:
		max_packet_size = (is_iso_ep ?
			ENDPOINT_MAX_PACKET_SIZE_1024 :
			ENDPOINT_MAX_PACKET_SIZE_512);
		break;

	case USB_SPEED_WIRELESS:
		max_packet_size = ENDPOINT_MAX_PACKET_SIZE_512;
		break;

	case USB_SPEED_SUPER:
		max_packet_size = ENDPOINT_MAX_PACKET_SIZE_1024;
		break;
	}

	ep_cfg |= EP_CFG__MAXPKTSIZE__WRITE(max_packet_size);

	if (is_iso_ep) {
		ep_cfg |= EP_CFG__BUFFERING__WRITE(1);
		ep_cfg |= EP_CFG__MAXBURST__WRITE(0);
	} else {
		ep_cfg |= EP_CFG__BUFFERING__WRITE(3);
		ep_cfg |= EP_CFG__MAXBURST__WRITE(15);
	}

	select_ep(usb_ss, bEndpointAddress);
	gadget_writel(usb_ss, &usb_ss->regs->ep_cfg, ep_cfg);
	gadget_writel(usb_ss, &usb_ss->regs->ep_sts_en,
		EP_STS_EN__TRBERREN__MASK | interrupt_mask);

	/* enable interrupt for selected endpoint */
	ep_cfg = gadget_readl(usb_ss, &usb_ss->regs->ep_ien);
	ep_cfg |= CAST_EP_ADDR_TO_BIT_POS(bEndpointAddress);
	gadget_writel(usb_ss, &usb_ss->regs->ep_ien, ep_cfg);
}

/**
 * usb_ss_gadget_ep_enable Enable endpoint
 * @ep: endpoint object
 * @desc: endpoint descriptor
 *
 * Returns 0 on success, error code elsewhere
 */
static int usb_ss_gadget_ep_enable(struct usb_ep *ep,
		const struct usb_endpoint_descriptor *desc)
{
	struct usb_ss_endpoint *usb_ss_ep;
	struct usb_ss_dev *usb_ss;
	unsigned long flags;
	int ret;
	u32 ep_cfg;

	usb_ss_ep = to_usb_ss_ep(ep);
	usb_ss = usb_ss_ep->usb_ss;

	if (!ep || !desc || desc->bDescriptorType != USB_DT_ENDPOINT) {
		dev_err(&usb_ss->dev, "usb-ss: invalid parameters\n");
		return -EINVAL;
	}

	if (!desc->wMaxPacketSize) {
		dev_err(&usb_ss->dev, "usb-ss: missing wMaxPacketSize\n");
		return -EINVAL;
	}

	ret = usb_ss_allocate_trb_pool(usb_ss_ep);
	if (ret)
		return ret;

	if (!usb_ss_ep->cpu_addr) {
		usb_ss_ep->cpu_addr = dma_alloc_coherent(4096,
			(unsigned long *)&usb_ss_ep->dma_addr);

		if (!usb_ss_ep->cpu_addr)
			return -ENOMEM;
	}

	dev_dbg(&usb_ss->dev, "Enabling endpoint: %s, addr=0x%x\n",
		ep->name, desc->bEndpointAddress);
	spin_lock_irqsave(&usb_ss->lock, flags);
	select_ep(usb_ss, desc->bEndpointAddress);
	ep_cfg = gadget_readl(usb_ss, &usb_ss->regs->ep_cfg);
	ep_cfg |= EP_CFG__ENABLE__MASK;
	gadget_writel(usb_ss, &usb_ss->regs->ep_cfg, ep_cfg);

	usb_ss_ep->enabled = 1;
	ep->desc = desc;
	usb_ss_ep->hw_pending_flag = 0;
	spin_unlock_irqrestore(&usb_ss->lock, flags);

	return 0;
}

static int usb_ss_gadget_match_ep(struct usb_gadget *gadget,
		struct usb_ep *ep,
		struct usb_endpoint_descriptor *desc)
{
	struct usb_ss_dev __maybe_unused *usb_ss = gadget_to_usb_ss(gadget);
	struct usb_ss_endpoint *usb_ss_ep;
	unsigned long flags;

	usb_ss_ep = to_usb_ss_ep(ep);

	dev_dbg(&usb_ss->dev, "match endpoint: %s\n", usb_ss_ep->name);

	u8 num = simple_strtoul(&ep->name[2], NULL, 10);

	spin_lock_irqsave(&usb_ss->lock, flags);
	usb_ss_ep->num  = num;
	usb_ss_ep->used = true;
	usb_ss_ep->endpoint.desc = desc;
	usb_ss_ep->dir  = usb_endpoint_dir_in(desc) ? USB_DIR_IN : USB_DIR_OUT;
	usb_ss_ep->type = usb_endpoint_type(desc);
	usb_ss_ep->address = desc->bEndpointAddress;
	spin_unlock_irqrestore(&usb_ss->lock, flags);

	return 1;
}

static void usb_ss_free_trb_pool(struct usb_ss_endpoint *usb_ss_ep)
{
	if (usb_ss_ep->trb_pool) {
		dma_free_coherent(usb_ss_ep->trb_pool);
		usb_ss_ep->trb_pool = NULL;
	}

	if (usb_ss_ep->cpu_addr) {
		dma_free_coherent(usb_ss_ep->cpu_addr);
		usb_ss_ep->cpu_addr = NULL;
	}
}

/**
 * usb_ss_gadget_ep_disable Disable endpoint
 * @ep: endpoint object
 *
 * Returns 0 on success, error code elsewhere
 */
static int usb_ss_gadget_ep_disable(struct usb_ep *ep)
{
	struct usb_ss_endpoint *usb_ss_ep;
	struct usb_ss_dev *usb_ss;
	unsigned long flags;
	int ret = 0;
	struct usb_request *request;
	u32 ep_cfg;

	if (!ep) {
		pr_debug("usb-ss: invalid parameters\n");
		return -EINVAL;
	}

	usb_ss_ep = to_usb_ss_ep(ep);
	usb_ss = usb_ss_ep->usb_ss;

	spin_lock_irqsave(&usb_ss->lock, flags);
	if (!usb_ss->start_gadget) {
		dev_dbg(&usb_ss->dev,
			"Disabling endpoint at disconnection: %s\n", ep->name);
		spin_unlock_irqrestore(&usb_ss->lock, flags);
		return 0;
	}

	dev_dbg(&usb_ss->dev,
		"Disabling endpoint: %s\n", ep->name);

	while (!list_empty(&usb_ss_ep->request_list)) {

		request = next_request(&usb_ss_ep->request_list);
		usb_gadget_unmap_request(&usb_ss->gadget, request,
				ep->desc->bEndpointAddress & USB_DIR_IN);
		request->status = -ESHUTDOWN;
		list_del(&request->list);
		spin_unlock(&usb_ss->lock);
		usb_gadget_giveback_request(ep, request);
		spin_lock(&usb_ss->lock);
	}

	select_ep(usb_ss, ep->desc->bEndpointAddress);
	ep_cfg = gadget_readl(usb_ss, &usb_ss->regs->ep_cfg);
	ep_cfg &= ~EP_CFG__ENABLE__MASK;
	gadget_writel(usb_ss, &usb_ss->regs->ep_cfg, ep_cfg);
	ep->desc = NULL;
	usb_ss_ep->enabled = 0;

	spin_unlock_irqrestore(&usb_ss->lock, flags);

	return ret;
}

/**
 * usb_ss_gadget_ep_alloc_request Allocates request
 * @ep: endpoint object associated with request
 * @gfp_flags: gfp flags
 *
 * Returns allocated request address, NULL on allocation error
 */
static struct usb_request *usb_ss_gadget_ep_alloc_request(struct usb_ep *ep,
		gfp_t gfp_flags)
{
	struct usb_request *request;

	request = kzalloc(sizeof(struct usb_request), gfp_flags);
	if (!request)
		return NULL;

	return request;
}

/**
 * usb_ss_gadget_ep_free_request Free memory occupied by request
 * @ep: endpoint object associated with request
 * @request: request to free memory
 */
static void usb_ss_gadget_ep_free_request(struct usb_ep *ep,
		struct usb_request *request)
{
	kfree(request);
}

/**
 * usb_ss_gadget_ep_queue Transfer data on endpoint
 * @ep: endpoint object
 * @request: request object
 * @gfp_flags: gfp flags
 *
 * Returns 0 on success, error code elsewhere
 */
static int usb_ss_gadget_ep_queue(struct usb_ep *ep,
		struct usb_request *request, gfp_t gfp_flags)
{
	struct usb_ss_endpoint *usb_ss_ep =
		to_usb_ss_ep(ep);
	struct usb_ss_dev *usb_ss = usb_ss_ep->usb_ss;
	unsigned long flags;
	int ret = 0;
	int empty_list = 0;

	spin_lock_irqsave(&usb_ss->lock, flags);

	request->actual = 0;
	request->status = -EINPROGRESS;

	dev_dbg(&usb_ss->dev,
		"Queuing endpoint: %s\n", usb_ss_ep->name);

	dev_dbg(&usb_ss->dev, "QUEUE(%02X) %d\n",
		ep->desc->bEndpointAddress, request->length);

	ret = usb_gadget_map_request(&usb_ss->gadget, request,
			ep->desc->bEndpointAddress & USB_DIR_IN);

	if (ret) {
		spin_unlock_irqrestore(&usb_ss->lock, flags);
		return ret;
	}

	empty_list = list_empty(&usb_ss_ep->request_list);
	list_add_tail(&request->list, &usb_ss_ep->request_list);

	if (!usb_ss->hw_configured_flag) {
		spin_unlock_irqrestore(&usb_ss->lock, flags);
		return 0;
	}

	if (empty_list) {
		if (!usb_ss_ep->stalled_flag)
			cdns_ep_run_transfer(usb_ss_ep);
	}
	spin_unlock_irqrestore(&usb_ss->lock, flags);

	return ret;
}

/**
 * usb_ss_gadget_ep_dequeue Remove request from transfer queue
 * @ep: endpoint object associated with request
 * @request: request object
 *
 * Returns 0 on success, error code elsewhere
 */
static int usb_ss_gadget_ep_dequeue(struct usb_ep *ep,
		struct usb_request *request)
{
	struct usb_ss_endpoint *usb_ss_ep =
		to_usb_ss_ep(ep);
	struct usb_ss_dev *usb_ss = usb_ss_ep->usb_ss;
	struct usb_request *req, *req_temp;
	unsigned long flags;

	spin_lock_irqsave(&usb_ss->lock, flags);
	if (!usb_ss->start_gadget) {
		dev_dbg(&usb_ss->dev,
			"DEQUEUE at disconnection: %s\n", ep->name);
		spin_unlock_irqrestore(&usb_ss->lock, flags);
		return 0;
	}
	dev_dbg(&usb_ss->dev, "DEQUEUE(%02X) %d\n",
		usb_ss_ep->address, request->length);

	list_for_each_entry_safe(req, req_temp,
		&usb_ss_ep->request_list, list) {
		if (request == req) {
			request->status = -ECONNRESET;
			usb_gadget_unmap_request(&usb_ss->gadget, request,
				usb_ss_ep->address & USB_DIR_IN);
			list_del_init(&request->list);
			if (request->complete) {
				spin_unlock(&usb_ss->lock);
				usb_gadget_giveback_request
					(&usb_ss_ep->endpoint, request);
				spin_lock(&usb_ss->lock);
			}
			break;
		}
	}

	spin_unlock_irqrestore(&usb_ss->lock, flags);
	return 0;
}

/**
 * usb_ss_gadget_ep_set_halt Sets/clears stall on selected endpoint
 * @ep: endpoint object to set/clear stall on
 * @value: 1 for set stall, 0 for clear stall
 *
 * Returns 0 on success, error code elsewhere
 */
static int usb_ss_gadget_ep_set_halt(struct usb_ep *ep, int value)
{
	struct usb_ss_endpoint *usb_ss_ep =
		to_usb_ss_ep(ep);
	struct usb_ss_dev *usb_ss = usb_ss_ep->usb_ss;
	unsigned long flags;

	/* return error when endpoint disabled */
	if (!usb_ss_ep->enabled)
		return -EPERM;

	/* if actual transfer is pending defer setting stall on this endpoint */
	if (usb_ss_ep->hw_pending_flag && value) {
		usb_ss_ep->stalled_flag = 1;
		return 0;
	}

	dev_dbg(&usb_ss->dev, "HALT(%02X) %d\n", usb_ss_ep->address, value);

	spin_lock_irqsave(&usb_ss->lock, flags);

	select_ep(usb_ss, ep->desc->bEndpointAddress);
	if (value) {
		cdns_ep_stall_flush(usb_ss_ep);
	} else {
		/*
		 * TODO:
		 * epp->wedgeFlag = 0;
		 */
		usb_ss_ep->wedge_flag = 0;
		gadget_writel(usb_ss, &usb_ss->regs->ep_cmd,
		EP_CMD__CSTALL__MASK | EP_CMD__EPRST__MASK);
		/* wait for EPRST cleared */
		while (gadget_readl(usb_ss,
			&usb_ss->regs->ep_cmd) & EP_CMD__EPRST__MASK)
			;
		usb_ss_ep->stalled_flag = 0;
	}
	usb_ss_ep->hw_pending_flag = 0;

	spin_unlock_irqrestore(&usb_ss->lock, flags);

	return 0;
}

/**
 * usb_ss_gadget_ep_set_wedge Set wedge on selected endpoint
 * @ep: endpoint object
 *
 * Returns 0
 */
static int usb_ss_gadget_ep_set_wedge(struct usb_ep *ep)
{
	struct usb_ss_endpoint *usb_ss_ep = to_usb_ss_ep(ep);
	struct usb_ss_dev __maybe_unused *usb_ss = usb_ss_ep->usb_ss;

	dev_dbg(&usb_ss->dev, "WEDGE(%02X)\n", usb_ss_ep->address);
	usb_ss_gadget_ep_set_halt(ep, 1);
	usb_ss_ep->wedge_flag = 1;
	return 0;
}

static const struct usb_ep_ops usb_ss_gadget_ep0_ops = {
	.enable = usb_ss_gadget_ep0_enable,
	.disable = usb_ss_gadget_ep0_disable,
	.alloc_request = usb_ss_gadget_ep_alloc_request,
	.free_request = usb_ss_gadget_ep_free_request,
	.queue = usb_ss_gadget_ep0_queue,
	.dequeue = usb_ss_gadget_ep_dequeue,
	.set_halt = usb_ss_gadget_ep0_set_halt,
	.set_wedge = usb_ss_gadget_ep_set_wedge,
};

static const struct usb_ep_ops usb_ss_gadget_ep_ops = {
	.enable = usb_ss_gadget_ep_enable,
	.disable = usb_ss_gadget_ep_disable,
	.alloc_request = usb_ss_gadget_ep_alloc_request,
	.free_request = usb_ss_gadget_ep_free_request,
	.queue = usb_ss_gadget_ep_queue,
	.dequeue = usb_ss_gadget_ep_dequeue,
	.set_halt = usb_ss_gadget_ep_set_halt,
	.set_wedge = usb_ss_gadget_ep_set_wedge,
};

/**
 * usb_ss_gadget_get_frame Returns number of actual ITP frame
 * @gadget: gadget object
 *
 * Returns number of actual ITP frame
 */
static int usb_ss_gadget_get_frame(struct usb_gadget *gadget)
{
	struct usb_ss_dev *usb_ss = gadget_to_usb_ss(gadget);

	dev_dbg(&usb_ss->dev, "usb_ss_gadget_get_frame\n");
	return gadget_readl(usb_ss, &usb_ss->regs->usb_iptn);
}

static int usb_ss_gadget_wakeup(struct usb_gadget *gadget)
{
	struct usb_ss_dev __maybe_unused *usb_ss = gadget_to_usb_ss(gadget);

	dev_dbg(&usb_ss->dev, "usb_ss_gadget_wakeup\n");
	return 0;
}

static int usb_ss_gadget_set_selfpowered(struct usb_gadget *gadget,
		int is_selfpowered)
{
	struct usb_ss_dev __maybe_unused *usb_ss = gadget_to_usb_ss(gadget);

	dev_dbg(&usb_ss->dev, "usb_ss_gadget_set_selfpowered: %d\n",
		is_selfpowered);
	return 0;
}

static int usb_ss_gadget_pullup(struct usb_gadget *gadget, int is_on)
{
	struct usb_ss_dev *usb_ss = gadget_to_usb_ss(gadget);

	if (!usb_ss->start_gadget)
		return 0;

	dev_dbg(&usb_ss->dev, "usb_ss_gadget_pullup: %d\n", is_on);

	if (is_on)
		gadget_writel(usb_ss, &usb_ss->regs->usb_conf,
				USB_CONF__DEVEN__MASK);
	else
		gadget_writel(usb_ss, &usb_ss->regs->usb_conf,
				USB_CONF__DEVDS__MASK);

	return 0;
}

/**
 * usb_ss_gadget_udc_start Gadget start
 * @gadget: gadget object
 * @driver: driver which operates on this gadget
 *
 * Returns 0 on success, error code elsewhere
 */
static int usb_ss_gadget_udc_start(struct usb_gadget *gadget,
		struct usb_gadget_driver *driver)
{
	struct usb_ss_dev *usb_ss = gadget_to_usb_ss(gadget);
	unsigned long flags;

	if (usb_ss->gadget_driver) {
		dev_err(&usb_ss->dev, "%s is already bound\n",
				usb_ss->gadget.name);
		return -EBUSY;
	}

	dev_dbg(&usb_ss->dev, "%s begins\n", __func__);

	spin_lock_irqsave(&usb_ss->lock, flags);
	usb_ss->gadget_driver = driver;
	if (!usb_ss->start_gadget) {
		spin_unlock_irqrestore(&usb_ss->lock, flags);
		return 0;
	}

	__cdns3_gadget_start(usb_ss);
	spin_unlock_irqrestore(&usb_ss->lock, flags);
	dev_dbg(&usb_ss->dev, "%s ends\n", __func__);

	return 0;
}

/**
 * usb_ss_gadget_udc_stop Stops gadget
 * @gadget: gadget object
 *
 * Returns 0
 */
static int usb_ss_gadget_udc_stop(struct usb_gadget *gadget)
{
	struct usb_ss_dev *usb_ss = gadget_to_usb_ss(gadget);
	struct usb_ep *ep;
	struct usb_ss_endpoint *usb_ss_ep;
	int i;
	u32 bEndpointAddress;

	usb_ss->gadget_driver = NULL;
	if (!usb_ss->start_gadget)
		return 0;

	list_for_each_entry(ep, &usb_ss->gadget.ep_list, ep_list) {
		usb_ss_ep = to_usb_ss_ep(ep);
		bEndpointAddress = usb_ss_ep->num | usb_ss_ep->dir;
		usb_ss_ep->used = false;
		select_ep(usb_ss, bEndpointAddress);
		gadget_writel(usb_ss, &usb_ss->regs->ep_cmd,
			EP_CMD__EPRST__MASK);
		while (gadget_readl(usb_ss, &usb_ss->regs->ep_cmd)
			& EP_CMD__EPRST__MASK)
			;
	}

	/* disable interrupt for device */
	gadget_writel(usb_ss, &usb_ss->regs->usb_ien, 0);
	gadget_writel(usb_ss, &usb_ss->regs->usb_conf, USB_CONF__DEVDS__MASK);

	for (i = 0; i < usb_ss->ep_nums ; i++)
		usb_ss_free_trb_pool(usb_ss->eps[i]);

	return 0;
}

static const struct usb_gadget_ops usb_ss_gadget_ops = {
	.get_frame = usb_ss_gadget_get_frame,
	.wakeup = usb_ss_gadget_wakeup,
	.set_selfpowered = usb_ss_gadget_set_selfpowered,
	.pullup = usb_ss_gadget_pullup,
	.udc_start = usb_ss_gadget_udc_start,
	.udc_stop = usb_ss_gadget_udc_stop,
	.match_ep = usb_ss_gadget_match_ep,

};

/**
 * usb_ss_init_ep Initializes software endpoints of gadget
 * @usb_ss: extended gadget object
 *
 * Returns 0 on success, error code elsewhere
 */
static int usb_ss_init_ep(struct usb_ss_dev *usb_ss)
{
	struct usb_ss_endpoint *usb_ss_ep;
	u32 ep_enabled_reg, iso_ep_reg, bulk_ep_reg;
	int i;
	int ep_reg_pos, ep_dir, ep_number;
	int found_endpoints = 0;

	/* Read it from USB_CAP3 to USB_CAP5 */
	ep_enabled_reg = 0x00ff00ff;
	iso_ep_reg = 0x00fe00fe;
	bulk_ep_reg = 0x00fe00fe;

	dev_dbg(&usb_ss->dev, "Initializing non-zero endpoints\n");
	dev_dbg(&usb_ss->dev,
		"ep_enabled_reg: 0x%x, iso_ep_reg: 0x%x, bulk_ep_reg:0x%x\n",
		ep_enabled_reg, iso_ep_reg, bulk_ep_reg);

	for (i = 0; i < USB_SS_ENDPOINTS_MAX_COUNT; i++) {
		ep_number = (i / 2) + 1;
		ep_dir = i % 2;
		ep_reg_pos = (16 * ep_dir) + ep_number;

		if (!(ep_enabled_reg & (1uL << ep_reg_pos)))
			continue;

		/* create empty endpoint object */
		usb_ss_ep = devm_kzalloc(&usb_ss->dev, sizeof(*usb_ss_ep),
		GFP_KERNEL);
		if (!usb_ss_ep)
			return -ENOMEM;

		/* set parent of endpoint object */
		usb_ss_ep->usb_ss = usb_ss;

		/* set index of endpoint in endpoints container */
		usb_ss->eps[found_endpoints++] = usb_ss_ep;

		/* set name of endpoint */
		snprintf(usb_ss_ep->name, sizeof(usb_ss_ep->name), "ep%d%s",
				ep_number, !!ep_dir ? "in" : "out");
		usb_ss_ep->endpoint.name = usb_ss_ep->name;
		dev_dbg(&usb_ss->dev, "Initializing endpoint: %s\n",
				usb_ss_ep->name);

		usb_ep_set_maxpacket_limit(&usb_ss_ep->endpoint,
		ENDPOINT_MAX_PACKET_LIMIT);
		usb_ss_ep->endpoint.max_streams = ENDPOINT_MAX_STREAMS;
		usb_ss_ep->endpoint.ops = &usb_ss_gadget_ep_ops;
		if (ep_dir)
			usb_ss_ep->caps.dir_in = 1;
		else
			usb_ss_ep->caps.dir_out = 1;

		/* check endpoint type */
		if (iso_ep_reg & (1uL << ep_reg_pos))
			usb_ss_ep->caps.type_iso = 1;

		if (bulk_ep_reg & (1uL << ep_reg_pos)) {
			usb_ss_ep->caps.type_bulk = 1;
			usb_ss_ep->caps.type_int = 1;
			usb_ss_ep->endpoint.maxburst = 15;
		}

		list_add_tail(&usb_ss_ep->endpoint.ep_list,
				&usb_ss->gadget.ep_list);
		INIT_LIST_HEAD(&usb_ss_ep->request_list);
		INIT_LIST_HEAD(&usb_ss_ep->ep_match_pending_list);
	}
	usb_ss->ep_nums = found_endpoints;
	return 0;
}

/**
 * usb_ss_init_ep0 Initializes software endpoint 0 of gadget
 * @usb_ss: extended gadget object
 *
 * Returns 0 on success, error code elsewhere
 */
static int usb_ss_init_ep0(struct usb_ss_dev *usb_ss)
{
	struct usb_ss_endpoint *ep0;

	dev_dbg(&usb_ss->dev, "Initializing EP0\n");
	ep0 = devm_kzalloc(&usb_ss->dev, sizeof(struct usb_ss_endpoint),
		GFP_KERNEL);

	if (!ep0)
		return -ENOMEM;

	/* fill CDNS fields */
	ep0->usb_ss = usb_ss;
	sprintf(ep0->name, "ep0");

	/* fill linux fields */
	ep0->endpoint.ops = &usb_ss_gadget_ep0_ops;
	ep0->endpoint.maxburst = 1;
	usb_ep_set_maxpacket_limit(&ep0->endpoint, ENDPOINT0_MAX_PACKET_LIMIT);
	ep0->address = 0;
	ep0->enabled = 1;
	ep0->caps.type_control = 1;
	ep0->caps.dir_in = 1;
	ep0->caps.dir_out = 1;
	ep0->endpoint.name = ep0->name;
	ep0->endpoint.desc = &cdns3_gadget_ep0_desc;
	usb_ss->gadget.ep0 = &ep0->endpoint;
	INIT_LIST_HEAD(&ep0->request_list);

	return 0;
}

static void cdns3_gadget_release(struct device *dev)
{
	struct usb_ss_dev *usb_ss = container_of(dev, struct usb_ss_dev, dev);

	kfree(usb_ss);
}

static int __cdns3_gadget_init(struct cdns3 *cdns)
{
	struct usb_ss_dev *usb_ss;
	int ret;
	struct device *dev;

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

	dev = &usb_ss->dev;
	dev->release = cdns3_gadget_release;
	dev->parent = cdns->dev;
	dev_set_name(dev, "gadget-cdns3-dev");
	cdns->gadget_dev = dev;
	usb_ss->sysdev = cdns->dev;
	ret = device_register(dev);
	if (ret)
		goto err1;

	usb_ss->regs = cdns->dev_regs;

	/* fill gadget fields */
	usb_ss->gadget.ops = &usb_ss_gadget_ops;
#ifdef CONFIG_USB_CDNS3_GADGET_FORCE_HIGHSPEED
	usb_ss->gadget.max_speed = USB_SPEED_HIGH;
#else
	usb_ss->gadget.max_speed = USB_SPEED_SUPER;
#endif
	usb_ss->gadget.speed = USB_SPEED_UNKNOWN;
	usb_ss->gadget.name = "cdns3-gadget";
	usb_ss->is_connected = 0;
	spin_lock_init(&usb_ss->lock);

	usb_ss->in_standby_mode = 1;

	/* initialize endpoint container */
	INIT_LIST_HEAD(&usb_ss->gadget.ep_list);
	INIT_LIST_HEAD(&usb_ss->ep_match_list);
	ret = usb_ss_init_ep0(usb_ss);
	if (ret) {
		dev_err(dev, "Failed to create endpoint 0\n");
		ret = -ENOMEM;
		goto err2;
	}

	ret = usb_ss_init_ep(usb_ss);
	if (ret) {
		dev_err(dev, "Failed to create non zero endpoints\n");
		ret = -ENOMEM;
		goto err2;
	}

	/* allocate memory for default endpoint TRB */
	usb_ss->trb_ep0 = (u32 *)dma_alloc_coherent(20, (unsigned long *)&usb_ss->trb_ep0_dma);
	if (!usb_ss->trb_ep0) {
		dev_err(dev, "Failed to allocate memory for ep0 TRB\n");
		ret = -ENOMEM;
		goto err2;
	}

	/* allocate memory for setup packet buffer */
	usb_ss->setup = (u8 *)dma_alloc_coherent(8, (unsigned long *)&usb_ss->setup_dma);
	if (!usb_ss->setup) {
		dev_err(dev, "Failed to allocate memory for SETUP buffer\n");
		ret = -ENOMEM;
		goto err3;
	}

	/* add USB gadget device */
	ret = usb_add_gadget_udc(&usb_ss->dev, &usb_ss->gadget);
	if (ret < 0) {
		dev_err(dev, "Failed to register USB device controller\n");
		goto err4;
	}

	return 0;

err4:
	dma_free_coherent(usb_ss->setup);
err3:
	dma_free_coherent(usb_ss->trb_ep0);
err2:
err1:
	cdns->gadget_dev = NULL;

	return ret;
}

/**
 * cdns3_gadget_remove: parent must call this to remove UDC
 *
 * cdns: cdns3 instance
 *
 */
void cdns3_gadget_remove(struct cdns3 *cdns)
{
	struct usb_ss_dev *usb_ss;

	if (!cdns->roles[CDNS3_ROLE_GADGET])
		return;

	usb_ss = container_of(cdns->gadget_dev, struct usb_ss_dev, dev);
	usb_del_gadget_udc(&usb_ss->gadget);
	dma_free_coherent(usb_ss->setup);
	dma_free_coherent(usb_ss->trb_ep0);
	device_unregister(cdns->gadget_dev);
	cdns->gadget_dev = NULL;
}

static void __cdns3_gadget_start(struct usb_ss_dev *usb_ss)
{
	u32 usb_conf_reg = 0;

	/* configure endpoint 0 hardware */
	cdns_ep0_config(usb_ss);

	/* enable interrupts for endpoint 0 (in and out) */
	gadget_writel(usb_ss, &usb_ss->regs->ep_ien,
	EP_IEN__EOUTEN0__MASK | EP_IEN__EINEN0__MASK);

	/* enable interrupt for device */
	gadget_writel(usb_ss, &usb_ss->regs->usb_ien,
			USB_IEN__U2RESIEN__MASK
			| USB_ISTS__DIS2I__MASK
			| USB_IEN__CON2IEN__MASK
			| USB_IEN__UHRESIEN__MASK
			| USB_IEN__UWRESIEN__MASK
			| USB_IEN__DISIEN__MASK
			| USB_IEN__CONIEN__MASK
			| USB_IEN__U3EXTIEN__MASK
			| USB_IEN__L2ENTIEN__MASK
			| USB_IEN__L2EXTIEN__MASK);

	usb_conf_reg = USB_CONF__CLK2OFFDS__MASK |
			USB_CONF__L1DS__MASK;
	if (usb_ss->gadget.max_speed == USB_SPEED_HIGH)
		usb_conf_reg |= USB_CONF__USB3DIS__MASK;
	gadget_writel(usb_ss, &usb_ss->regs->usb_conf, usb_conf_reg);

	gadget_writel(usb_ss, &usb_ss->regs->usb_conf,
			USB_CONF__U1DS__MASK
			| USB_CONF__U2DS__MASK
			/*
			 * TODO:
			 * | USB_CONF__L1EN__MASK
			 */
			);

	gadget_writel(usb_ss, &usb_ss->regs->usb_conf, USB_CONF__DEVEN__MASK);

	gadget_writel(usb_ss, &usb_ss->regs->dbg_link1,
		DBG_LINK1__LFPS_MIN_GEN_U1_EXIT_SET__MASK |
		DBG_LINK1__LFPS_MIN_GEN_U1_EXIT__WRITE(0x3C));
}

static int cdns3_gadget_start(struct cdns3 *cdns)
{
	struct usb_ss_dev *usb_ss = container_of(cdns->gadget_dev,
			struct usb_ss_dev, dev);
	unsigned long flags;

	dev_dbg(&usb_ss->dev, "%s begins\n", __func__);

	pm_runtime_get_sync(cdns->dev);
	spin_lock_irqsave(&usb_ss->lock, flags);
	usb_ss->start_gadget = 1;
	if (!usb_ss->gadget_driver) {
		spin_unlock_irqrestore(&usb_ss->lock, flags);
		return 0;
	}

	__cdns3_gadget_start(usb_ss);
	usb_ss->in_standby_mode = 0;
	spin_unlock_irqrestore(&usb_ss->lock, flags);
	dev_dbg(&usb_ss->dev, "%s ends\n", __func__);

	return 0;
}

static void __cdns3_gadget_stop(struct cdns3 *cdns)
{
	struct usb_ss_dev *usb_ss;
	unsigned long flags;

	usb_ss = container_of(cdns->gadget_dev, struct usb_ss_dev, dev);
	if (usb_ss->gadget_driver)
		usb_ss->gadget_driver->disconnect(&usb_ss->gadget);
	usb_gadget_disconnect(&usb_ss->gadget);
	spin_lock_irqsave(&usb_ss->lock, flags);
	/* disable interrupt for device */
	gadget_writel(usb_ss, &usb_ss->regs->usb_ien, 0);
	gadget_writel(usb_ss, &usb_ss->regs->usb_conf, USB_CONF__DEVDS__MASK);
	usb_ss->start_gadget = 0;
	spin_unlock_irqrestore(&usb_ss->lock, flags);
}

static void cdns3_gadget_stop(struct cdns3 *cdns)
{
	if (cdns->role == CDNS3_ROLE_GADGET)
		__cdns3_gadget_stop(cdns);
}

/**
 * cdns3_gadget_init - initialize device structure
 *
 * cdns: cdns3 instance
 *
 * This function initializes the gadget.
 */
int cdns3_gadget_init(struct cdns3 *cdns)
{
	struct cdns3_role_driver *rdrv;

	rdrv = devm_kzalloc(cdns->dev, sizeof(*rdrv), GFP_KERNEL);
	if (!rdrv)
		return -ENOMEM;

	rdrv->start	= cdns3_gadget_start;
	rdrv->stop	= cdns3_gadget_stop;
	rdrv->irq	= cdns_irq_handler_thread;
	rdrv->name	= "gadget";
	cdns->roles[CDNS3_ROLE_GADGET] = rdrv;
	return __cdns3_gadget_init(cdns);
}
