diff options
Diffstat (limited to 'src/hw')
-rw-r--r-- | src/hw/usb-xhci.c | 4 | ||||
-rw-r--r-- | src/hw/usb.c | 13 | ||||
-rw-r--r-- | src/hw/usb.h | 5 |
3 files changed, 20 insertions, 2 deletions
diff --git a/src/hw/usb-xhci.c b/src/hw/usb-xhci.c index ca1fe251..e3052a51 100644 --- a/src/hw/usb-xhci.c +++ b/src/hw/usb-xhci.c @@ -1042,7 +1042,7 @@ xhci_control(struct usb_pipe *p, int dir, const void *cmd, int cmdsize xhci_xfer_data(pipe, dir, data, datalen); xhci_xfer_status(pipe, dir, datalen); - int cc = xhci_event_wait(xhci, &pipe->reqs, 1000); + int cc = xhci_event_wait(xhci, &pipe->reqs, usb_xfer_time(p, datalen)); if (cc != CC_SUCCESS) { dprintf(1, "%s: control xfer failed (cc %d)\n", __func__, cc); return -1; @@ -1062,7 +1062,7 @@ xhci_send_bulk(struct usb_pipe *p, int dir, void *data, int datalen) GET_LOWFLAT(pipe->pipe.cntl), struct usb_xhci_s, usb); xhci_xfer_normal(pipe, data, datalen); - int cc = xhci_event_wait(xhci, &pipe->reqs, 1000); + int cc = xhci_event_wait(xhci, &pipe->reqs, usb_xfer_time(p, datalen)); if (cc != CC_SUCCESS) { dprintf(1, "%s: bulk xfer failed (cc %d)\n", __func__, cc); return -1; diff --git a/src/hw/usb.c b/src/hw/usb.c index 7b8a9f5f..46b46be8 100644 --- a/src/hw/usb.c +++ b/src/hw/usb.c @@ -187,6 +187,19 @@ usb_getFrameExp(struct usbdevice_s *usbdev return (period <= 4) ? 0 : period - 4; } +// Maximum time (in ms) a data transfer should take +int +usb_xfer_time(struct usb_pipe *pipe, int datalen) +{ + // Use the maximum command time (5 seconds), except for + // set_address commands where we don't want to stall the boot if + // the device doesn't actually exist. Add 100ms to account for + // any controller delays. + if (!pipe->devaddr) + return USB_TIME_STATUS + 100; + return USB_TIME_COMMAND + 100; +} + // Find the first endpoing of a given type in an interface description. struct usb_endpoint_descriptor * findEndPointDesc(struct usbdevice_s *usbdev, int type, int dir) diff --git a/src/hw/usb.h b/src/hw/usb.h index 61962964..3a663ce1 100644 --- a/src/hw/usb.h +++ b/src/hw/usb.h @@ -84,6 +84,10 @@ struct usbhub_op_s { #define USB_TIME_DRSTR 50 #define USB_TIME_RSTRCY 10 +#define USB_TIME_STATUS 50 +#define USB_TIME_DATAIN 500 +#define USB_TIME_COMMAND 5000 + #define USB_TIME_SETADDR_RECOVERY 2 #define USB_PID_OUT 0xe1 @@ -237,6 +241,7 @@ void usb_desc2pipe(struct usb_pipe *pipe, struct usbdevice_s *usbdev , struct usb_endpoint_descriptor *epdesc); int usb_getFrameExp(struct usbdevice_s *usbdev , struct usb_endpoint_descriptor *epdesc); +int usb_xfer_time(struct usb_pipe *pipe, int datalen); struct usb_endpoint_descriptor *findEndPointDesc(struct usbdevice_s *usbdev , int type, int dir); void usb_enumerate(struct usbhub_s *hub); |