Tom Rini 2021-04-23 07:31:36 -04:00
commit 4d85f42716
2 changed files with 28 additions and 0 deletions

View file

@ -346,6 +346,28 @@ static int ehci_disable_async(struct ehci_ctrl *ctrl)
return ret;
}
static int ehci_iaa_cycle(struct ehci_ctrl *ctrl)
{
u32 cmd, status;
int ret;
/* Enable Interrupt on Async Advance Doorbell. */
cmd = ehci_readl(&ctrl->hcor->or_usbcmd);
cmd |= CMD_IAAD;
ehci_writel(&ctrl->hcor->or_usbcmd, cmd);
ret = handshake(&ctrl->hcor->or_usbsts, STS_IAA, STS_IAA,
10 * 1000); /* 10ms timeout */
if (ret < 0)
printf("EHCI fail timeout STS_IAA set\n");
status = ehci_readl(&ctrl->hcor->or_usbsts);
if (status & STS_IAA)
ehci_writel(&ctrl->hcor->or_usbsts, STS_IAA);
return ret;
}
static int
ehci_submit_async(struct usb_device *dev, unsigned long pipe, void *buffer,
int length, struct devrequest *req)
@ -631,6 +653,11 @@ ehci_submit_async(struct usb_device *dev, unsigned long pipe, void *buffer,
flush_dcache_range((unsigned long)&ctrl->qh_list,
ALIGN_END_ADDR(struct QH, &ctrl->qh_list, 1));
/* Set IAAD, poll IAA */
ret = ehci_iaa_cycle(ctrl);
if (ret)
goto fail;
/*
* Invalidate the memory area occupied by buffer
* Don't try to fix the buffer alignment, if it isn't properly

View file

@ -44,6 +44,7 @@ struct ehci_hcor {
#define STS_ASS (1 << 15)
#define STS_PSS (1 << 14)
#define STS_HALT (1 << 12)
#define STS_IAA (1 << 5)
uint32_t or_usbintr;
#define INTR_UE (1 << 0) /* USB interrupt enable */
#define INTR_UEE (1 << 1) /* USB error interrupt enable */