diff options
author | Peter Chen <peter.chen@freescale.com> | 2011-03-16 15:10:45 +0800 |
---|---|---|
committer | Peter Chen <peter.chen@freescale.com> | 2011-03-17 13:41:46 +0800 |
commit | be2206443987c646122cd302dadecee4e4ae8327 (patch) | |
tree | 08618a8b4e5d8250ca55ae2cbcf97d98db8e396f /drivers/usb | |
parent | 3cca1fb9be3e2f5d804d2970bfcc4e276b6a51cd (diff) |
ENGR00140710-2 usb-device: add more device wakeup modes
device driver parts
Following usb device wakeup modes is supported are added:
-vbus failing wakeup: it happens when our SoC suspend and host's vbus failing
(after host(pc) suspends 10 seconds later)
-device receives reset wakeup: it happens follow below steps:
--Find MSC device at pc for soc
--Right-click -> Disable (this will suspend the device)
--let soc go to suspend
--Right-click -> Enable (this will reset the device)
-device receives resume signal from pc: it can be tested by pc HSET tools
Signed-off-by: Peter Chen <peter.chen@freescale.com>
Diffstat (limited to 'drivers/usb')
-rw-r--r-- | drivers/usb/gadget/arcotg_udc.c | 21 |
1 files changed, 16 insertions, 5 deletions
diff --git a/drivers/usb/gadget/arcotg_udc.c b/drivers/usb/gadget/arcotg_udc.c index 68c2e1b9c1cc..142a61585898 100644 --- a/drivers/usb/gadget/arcotg_udc.c +++ b/drivers/usb/gadget/arcotg_udc.c @@ -2262,7 +2262,7 @@ static irqreturn_t fsl_udc_irq(int irq, void *_udc) /* Reset Received */ if (irq_src & USB_STS_RESET) { - VDBG("reset int"); + pr_debug("reset int"); reset_irq(udc); status = IRQ_HANDLED; } @@ -2270,7 +2270,8 @@ static irqreturn_t fsl_udc_irq(int irq, void *_udc) /* Sleep Enable (Suspend) */ if (irq_src & USB_STS_SUSPEND) { VDBG("suspend int"); - suspend_irq(udc); + if (!(udc->usb_state == USB_STATE_SUSPENDED)) + suspend_irq(udc); status = IRQ_HANDLED; } @@ -3148,9 +3149,16 @@ static int udc_suspend(struct fsl_udc *udc) udc->stopped = 1; - /* stop the controller */ - usbcmd = fsl_readl(&dr_regs->usbcmd) & ~USB_CMD_RUN_STOP; - fsl_writel(usbcmd, &dr_regs->usbcmd); + /* The dp should be still pulled up + * if there is usb cable or usb charger on port. + * In that case, the usb device can be remained on suspend state + * and the dp will not be changed. + */ + if (!(fsl_readl(&dr_regs->otgsc) & OTGSC_B_SESSION_VALID)) { + /* stop the controller */ + usbcmd = fsl_readl(&dr_regs->usbcmd) & ~USB_CMD_RUN_STOP; + fsl_writel(usbcmd, &dr_regs->usbcmd); + } dr_phy_low_power_mode(udc, true); printk(KERN_DEBUG "USB Gadget suspend ends\n"); @@ -3216,6 +3224,8 @@ static int fsl_udc_resume(struct platform_device *pdev) mutex_unlock(&udc_resume_mutex); return 0; } + /* prevent the quirk interrupts from resuming */ + disable_irq_nosync(udc_controller->irq); /* * If the controller was stopped at suspend time, then @@ -3269,6 +3279,7 @@ end: dr_clk_gate(false); } --udc_controller->suspended; + enable_irq(udc_controller->irq); mutex_unlock(&udc_resume_mutex); printk(KERN_DEBUG "USB Gadget resume ends\n"); return 0; |