Hi, On Wed, Jan 10, 2024, Pandey, Radhey Shyam wrote: > > Thanks, Thinh. I came across this thread and wanted to check if you > have some fix ready? Would you mind test this change to see if it fixes the issue: diff --git a/drivers/usb/dwc3/gadget.c b/drivers/usb/dwc3/gadget.c index 8d1881adcd80..f40c7b9105cc 100644 --- a/drivers/usb/dwc3/gadget.c +++ b/drivers/usb/dwc3/gadget.c @@ -1808,6 +1808,7 @@ static int dwc3_prepare_trbs(struct dwc3_ep *dep) return ret; } +static void dwc3_gadget_ep_skip_trbs(struct dwc3_ep *dep, struct dwc3_request *req); static void dwc3_gadget_ep_cleanup_cancelled_requests(struct dwc3_ep *dep); static void dwc3_gadget_restore_requests(struct dwc3_ep *dep); @@ -1874,9 +1875,27 @@ static int __dwc3_gadget_kick_transfer(struct dwc3_ep *dep) list_for_each_entry_safe(req, tmp, &dep->started_list, list) dwc3_gadget_move_cancelled_request(req, DWC3_REQUEST_STATUS_DEQUEUED); - /* If ep isn't started, then there's no end transfer pending */ - if (!(dep->flags & DWC3_EP_END_TRANSFER_PENDING)) - dwc3_gadget_ep_cleanup_cancelled_requests(dep); + if ((dep->flags & DWC3_EP_DELAY_START) || + (dep->flags & DWC3_EP_WAIT_TRANSFER_COMPLETE) || + (dep->flags & DWC3_EP_TRANSFER_STARTED)) { + /* If ep isn't started, then there's no end transfer pending */ + if (!(dep->flags & DWC3_EP_END_TRANSFER_PENDING)) + dwc3_gadget_ep_cleanup_cancelled_requests(dep); + } else { + /* + * To be in this condition means usb_ep_queue() isn't + * completed yet. Since the controller hasn't owned the + * requests yet, don't give back the requests on failed + * usb_ep_queue. Simply remove them from the endpoint's + * list. + */ + while (!list_empty(&dep->cancelled_list)) { + req = next_request(&dep->cancelled_list); + dwc3_gadget_ep_skip_trbs(dep, req); + dwc3_gadget_del_and_unmap_request(dep, req, -EINPROGRESS); + req->status = DWC3_REQUEST_STATUS_COMPLETED; + } + } return ret; } BTW, what was the error code returned from usb_ep_queue()? Is it -ETIMEDOUT? Thanks, Thinh