diff options
-rw-r--r-- | drivers/usb/musb/davinci.c | 5 | ||||
-rw-r--r-- | drivers/usb/musb/musb_host.c | 25 |
2 files changed, 24 insertions, 6 deletions
diff --git a/drivers/usb/musb/davinci.c b/drivers/usb/musb/davinci.c index 992b516efd80..e16ff605c458 100644 --- a/drivers/usb/musb/davinci.c +++ b/drivers/usb/musb/davinci.c | |||
@@ -330,7 +330,6 @@ static irqreturn_t davinci_interrupt(int irq, void *__hci) | |||
330 | mod_timer(&otg_workaround, jiffies + POLL_SECONDS * HZ); | 330 | mod_timer(&otg_workaround, jiffies + POLL_SECONDS * HZ); |
331 | WARNING("VBUS error workaround (delay coming)\n"); | 331 | WARNING("VBUS error workaround (delay coming)\n"); |
332 | } else if (is_host_enabled(musb) && drvvbus) { | 332 | } else if (is_host_enabled(musb) && drvvbus) { |
333 | musb->is_active = 1; | ||
334 | MUSB_HST_MODE(musb); | 333 | MUSB_HST_MODE(musb); |
335 | musb->xceiv->default_a = 1; | 334 | musb->xceiv->default_a = 1; |
336 | musb->xceiv->state = OTG_STATE_A_WAIT_VRISE; | 335 | musb->xceiv->state = OTG_STATE_A_WAIT_VRISE; |
@@ -344,7 +343,9 @@ static irqreturn_t davinci_interrupt(int irq, void *__hci) | |||
344 | portstate(musb->port1_status &= ~USB_PORT_STAT_POWER); | 343 | portstate(musb->port1_status &= ~USB_PORT_STAT_POWER); |
345 | } | 344 | } |
346 | 345 | ||
347 | /* NOTE: this must complete poweron within 100 msec */ | 346 | /* NOTE: this must complete poweron within 100 msec |
347 | * (OTG_TIME_A_WAIT_VRISE) but we don't check for that. | ||
348 | */ | ||
348 | davinci_source_power(musb, drvvbus, 0); | 349 | davinci_source_power(musb, drvvbus, 0); |
349 | DBG(2, "VBUS %s (%s)%s, devctl %02x\n", | 350 | DBG(2, "VBUS %s (%s)%s, devctl %02x\n", |
350 | drvvbus ? "on" : "off", | 351 | drvvbus ? "on" : "off", |
diff --git a/drivers/usb/musb/musb_host.c b/drivers/usb/musb/musb_host.c index 94a2a350a414..d6ed560e8826 100644 --- a/drivers/usb/musb/musb_host.c +++ b/drivers/usb/musb/musb_host.c | |||
@@ -2235,13 +2235,30 @@ static void musb_h_stop(struct usb_hcd *hcd) | |||
2235 | static int musb_bus_suspend(struct usb_hcd *hcd) | 2235 | static int musb_bus_suspend(struct usb_hcd *hcd) |
2236 | { | 2236 | { |
2237 | struct musb *musb = hcd_to_musb(hcd); | 2237 | struct musb *musb = hcd_to_musb(hcd); |
2238 | u8 devctl; | ||
2238 | 2239 | ||
2239 | if (musb->xceiv->state == OTG_STATE_A_SUSPEND) | 2240 | if (!is_host_active(musb)) |
2240 | return 0; | 2241 | return 0; |
2241 | 2242 | ||
2242 | if (is_host_active(musb) && musb->is_active) { | 2243 | switch (musb->xceiv->state) { |
2243 | WARNING("trying to suspend as %s is_active=%i\n", | 2244 | case OTG_STATE_A_SUSPEND: |
2244 | otg_state_string(musb), musb->is_active); | 2245 | return 0; |
2246 | case OTG_STATE_A_WAIT_VRISE: | ||
2247 | /* ID could be grounded even if there's no device | ||
2248 | * on the other end of the cable. NOTE that the | ||
2249 | * A_WAIT_VRISE timers are messy with MUSB... | ||
2250 | */ | ||
2251 | devctl = musb_readb(musb->mregs, MUSB_DEVCTL); | ||
2252 | if ((devctl & MUSB_DEVCTL_VBUS) == MUSB_DEVCTL_VBUS) | ||
2253 | musb->xceiv->state = OTG_STATE_A_WAIT_BCON; | ||
2254 | break; | ||
2255 | default: | ||
2256 | break; | ||
2257 | } | ||
2258 | |||
2259 | if (musb->is_active) { | ||
2260 | WARNING("trying to suspend as %s while active\n", | ||
2261 | otg_state_string(musb)); | ||
2245 | return -EBUSY; | 2262 | return -EBUSY; |
2246 | } else | 2263 | } else |
2247 | return 0; | 2264 | return 0; |