summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorPeter Chen <peter.chen@freescale.com>2011-03-16 15:10:45 +0800
committerAndy Voltz <andy.voltz@timesys.com>2011-06-01 13:21:04 -0400
commit91fc391190d7bc70dd73791d988a99ba9ffba946 (patch)
tree08618a8b4e5d8250ca55ae2cbcf97d98db8e396f
parent45d380fc2a53bde729050b1721624dc25b822c06 (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>
-rw-r--r--drivers/usb/gadget/arcotg_udc.c21
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;