diff options
Diffstat (limited to 'drivers/usb/musb/musb_gadget_ep0.c')
-rw-r--r-- | drivers/usb/musb/musb_gadget_ep0.c | 54 |
1 files changed, 43 insertions, 11 deletions
diff --git a/drivers/usb/musb/musb_gadget_ep0.c b/drivers/usb/musb/musb_gadget_ep0.c index e40d7647caf..631aab86240 100644 --- a/drivers/usb/musb/musb_gadget_ep0.c +++ b/drivers/usb/musb/musb_gadget_ep0.c @@ -45,6 +45,11 @@ /* ep0 is always musb->endpoints[0].ep_in */ #define next_ep0_request(musb) next_in_request(&(musb)->endpoints[0]) +/* OTG 2.0 Specification 6.2.3 GetStatus commands */ +#ifdef CONFIG_USB_OTG_20 +#define OTG_STATUS_SELECT 0xF +#endif + /* * locking note: we use only the controller lock, for simpler correctness. * It's always held with IRQs blocked. @@ -80,21 +85,33 @@ static int service_tx_status_request( int handled = 1; u8 result[2], epnum = 0; const u8 recip = ctrlrequest->bRequestType & USB_RECIP_MASK; - +#ifdef CONFIG_USB_OTG_20 + unsigned int otg_recip = ctrlrequest->wIndex >> 12; +#endif result[1] = 0; switch (recip) { case USB_RECIP_DEVICE: - result[0] = musb->is_self_powered << USB_DEVICE_SELF_POWERED; - result[0] |= musb->may_wakeup << USB_DEVICE_REMOTE_WAKEUP; - if (musb->g.is_otg) { - result[0] |= musb->g.b_hnp_enable - << USB_DEVICE_B_HNP_ENABLE; - result[0] |= musb->g.a_alt_hnp_support - << USB_DEVICE_A_ALT_HNP_SUPPORT; - result[0] |= musb->g.a_hnp_support - << USB_DEVICE_A_HNP_SUPPORT; +#ifdef CONFIG_USB_OTG_20 + if (!(otg_recip == OTG_STATUS_SELECT)) { +#endif + result[0] = musb->is_self_powered << + USB_DEVICE_SELF_POWERED; + result[0] |= musb->may_wakeup << + USB_DEVICE_REMOTE_WAKEUP; + if (musb->g.is_otg) { + result[0] |= musb->g.b_hnp_enable + << USB_DEVICE_B_HNP_ENABLE; + result[0] |= musb->g.a_alt_hnp_support + << USB_DEVICE_A_ALT_HNP_SUPPORT; + result[0] |= musb->g.a_hnp_support + << USB_DEVICE_A_HNP_SUPPORT; + } +#ifdef CONFIG_USB_OTG_20 + } else { + result[0] = 1 & musb->g.otg_hnp_reqd; } +#endif break; case USB_RECIP_INTERFACE: @@ -356,7 +373,22 @@ __acquires(musb->lock) musb->test_mode_nr = MUSB_TEST_PACKET; break; - +#ifdef CONFIG_USB_OTG_20 + case 6: + if (!musb->g.is_otg) + goto stall; + musb->g.otg_srp_reqd = 1; + + mod_timer(&musb->otg_timer, + jiffies + + msecs_to_jiffies(TTST_SRP)); + break; + case 7: + if (!musb->g.is_otg) + goto stall; + musb->g.otg_hnp_reqd = 1; + break; +#endif case 0xc0: /* TEST_FORCE_HS */ pr_debug("TEST_FORCE_HS\n"); |