Commit 8f182e5d authored by Darius Augulis's avatar Darius Augulis Committed by Greg Kroah-Hartman

USB: imx_udc: Fix IMX UDC gadget bugs

Fix small bugs and add some omptimization in IMX UDC Gadget.
Signed-off-by: default avatarDarius Augulis <augulis.darius@gmail.com>
Signed-off-by: default avatarGreg Kroah-Hartman <gregkh@suse.de>
parent 664d5df9
...@@ -283,7 +283,7 @@ void imx_ep_stall(struct imx_ep_struct *imx_ep) ...@@ -283,7 +283,7 @@ void imx_ep_stall(struct imx_ep_struct *imx_ep)
imx_flush(imx_ep); imx_flush(imx_ep);
/* Special care for ep0 */ /* Special care for ep0 */
if (EP_NO(imx_ep)) { if (!EP_NO(imx_ep)) {
temp = __raw_readl(imx_usb->base + USB_CTRL); temp = __raw_readl(imx_usb->base + USB_CTRL);
__raw_writel(temp | CTRL_CMDOVER | CTRL_CMDERROR, imx_usb->base + USB_CTRL); __raw_writel(temp | CTRL_CMDOVER | CTRL_CMDERROR, imx_usb->base + USB_CTRL);
do { } while (__raw_readl(imx_usb->base + USB_CTRL) & CTRL_CMDOVER); do { } while (__raw_readl(imx_usb->base + USB_CTRL) & CTRL_CMDOVER);
...@@ -301,7 +301,7 @@ void imx_ep_stall(struct imx_ep_struct *imx_ep) ...@@ -301,7 +301,7 @@ void imx_ep_stall(struct imx_ep_struct *imx_ep)
break; break;
udelay(20); udelay(20);
} }
if (i == 50) if (i == 100)
D_ERR(imx_usb->dev, "<%s> Non finished stall on %s\n", D_ERR(imx_usb->dev, "<%s> Non finished stall on %s\n",
__func__, imx_ep->ep.name); __func__, imx_ep->ep.name);
} }
...@@ -539,10 +539,9 @@ static int handle_ep0(struct imx_ep_struct *imx_ep) ...@@ -539,10 +539,9 @@ static int handle_ep0(struct imx_ep_struct *imx_ep)
struct imx_request *req = NULL; struct imx_request *req = NULL;
int ret = 0; int ret = 0;
if (!list_empty(&imx_ep->queue)) if (!list_empty(&imx_ep->queue)) {
req = list_entry(imx_ep->queue.next, struct imx_request, queue); req = list_entry(imx_ep->queue.next, struct imx_request, queue);
if (req) {
switch (imx_ep->imx_usb->ep0state) { switch (imx_ep->imx_usb->ep0state) {
case EP0_IN_DATA_PHASE: /* GET_DESCRIPTOR */ case EP0_IN_DATA_PHASE: /* GET_DESCRIPTOR */
...@@ -561,6 +560,10 @@ static int handle_ep0(struct imx_ep_struct *imx_ep) ...@@ -561,6 +560,10 @@ static int handle_ep0(struct imx_ep_struct *imx_ep)
} }
} }
else
D_ERR(imx_ep->imx_usb->dev, "<%s> no request on %s\n",
__func__, imx_ep->ep.name);
return ret; return ret;
} }
...@@ -759,7 +762,7 @@ static int imx_ep_queue ...@@ -759,7 +762,7 @@ static int imx_ep_queue
*/ */
if (imx_usb->set_config && !EP_NO(imx_ep)) { if (imx_usb->set_config && !EP_NO(imx_ep)) {
imx_usb->set_config = 0; imx_usb->set_config = 0;
D_EPX(imx_usb->dev, D_ERR(imx_usb->dev,
"<%s> gadget reply set config\n", __func__); "<%s> gadget reply set config\n", __func__);
return 0; return 0;
} }
...@@ -779,8 +782,6 @@ static int imx_ep_queue ...@@ -779,8 +782,6 @@ static int imx_ep_queue
return -ESHUTDOWN; return -ESHUTDOWN;
} }
local_irq_save(flags);
/* Debug */ /* Debug */
D_REQ(imx_usb->dev, "<%s> ep%d %s request for [%d] bytes\n", D_REQ(imx_usb->dev, "<%s> ep%d %s request for [%d] bytes\n",
__func__, EP_NO(imx_ep), __func__, EP_NO(imx_ep),
...@@ -790,17 +791,18 @@ static int imx_ep_queue ...@@ -790,17 +791,18 @@ static int imx_ep_queue
if (imx_ep->stopped) { if (imx_ep->stopped) {
usb_req->status = -ESHUTDOWN; usb_req->status = -ESHUTDOWN;
ret = -ESHUTDOWN; return -ESHUTDOWN;
goto out;
} }
if (req->in_use) { if (req->in_use) {
D_ERR(imx_usb->dev, D_ERR(imx_usb->dev,
"<%s> refusing to queue req %p (already queued)\n", "<%s> refusing to queue req %p (already queued)\n",
__func__, req); __func__, req);
goto out; return 0;
} }
local_irq_save(flags);
usb_req->status = -EINPROGRESS; usb_req->status = -EINPROGRESS;
usb_req->actual = 0; usb_req->actual = 0;
...@@ -810,7 +812,7 @@ static int imx_ep_queue ...@@ -810,7 +812,7 @@ static int imx_ep_queue
ret = handle_ep0(imx_ep); ret = handle_ep0(imx_ep);
else else
ret = handle_ep(imx_ep); ret = handle_ep(imx_ep);
out:
local_irq_restore(flags); local_irq_restore(flags);
return ret; return ret;
} }
...@@ -1010,10 +1012,8 @@ static irqreturn_t imx_udc_irq(int irq, void *dev) ...@@ -1010,10 +1012,8 @@ static irqreturn_t imx_udc_irq(int irq, void *dev)
dump_usb_stat(__func__, imx_usb); dump_usb_stat(__func__, imx_usb);
} }
if (!imx_usb->driver) { if (!imx_usb->driver)
/*imx_udc_disable(imx_usb);*/
goto end_irq; goto end_irq;
}
if (intr & INTR_WAKEUP) { if (intr & INTR_WAKEUP) {
if (imx_usb->gadget.speed == USB_SPEED_UNKNOWN if (imx_usb->gadget.speed == USB_SPEED_UNKNOWN
...@@ -1095,6 +1095,11 @@ static irqreturn_t imx_udc_irq(int irq, void *dev) ...@@ -1095,6 +1095,11 @@ static irqreturn_t imx_udc_irq(int irq, void *dev)
} }
if (intr & INTR_SOF) { if (intr & INTR_SOF) {
/* Copy from Freescale BSP.
We must enable SOF intr and set CMDOVER.
Datasheet don't specifiy this action, but it
is done in Freescale BSP, so just copy it.
*/
if (imx_usb->ep0state == EP0_IDLE) { if (imx_usb->ep0state == EP0_IDLE) {
temp = __raw_readl(imx_usb->base + USB_CTRL); temp = __raw_readl(imx_usb->base + USB_CTRL);
__raw_writel(temp | CTRL_CMDOVER, imx_usb->base + USB_CTRL); __raw_writel(temp | CTRL_CMDOVER, imx_usb->base + USB_CTRL);
......
...@@ -170,7 +170,7 @@ struct imx_udc_struct { ...@@ -170,7 +170,7 @@ struct imx_udc_struct {
/* #define DEBUG_IRQ */ /* #define DEBUG_IRQ */
/* #define DEBUG_EPIRQ */ /* #define DEBUG_EPIRQ */
/* #define DEBUG_DUMP */ /* #define DEBUG_DUMP */
#define DEBUG_ERR /* #define DEBUG_ERR */
#ifdef DEBUG_REQ #ifdef DEBUG_REQ
#define D_REQ(dev, args...) dev_dbg(dev, ## args) #define D_REQ(dev, args...) dev_dbg(dev, ## args)
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment