Hi, > Than either there is a bug in the UDC (or the UDC driver), or else the > host doesn't wait for the Set-Config request to complete before sending > the next request. What were the values of fsg->ep0_req_tag and > exception_req_tag? >From the printk added, the values of fsg->ep0_req_tag and exception_req_tag are: fsg->ep0_req_tag 163, exception_req_tag 161 fsg->ep0_req_tag 168, exception_req_tag 167 fsg->ep0_req_tag 176, exception_req_tag 173 > By searching through the code in file_storage.c, you can easily see > that fsg->ep0_req_tag gets set in only one place: the first line of > fsg_setup(). It is a counter -- it goes up by one every time a new > SETUP packet is received, marking the start of a new control transfer. > > You can also see that handle_exception() sets exception_req_tag to > the value of fsg->exception_req_tag, and raise_exception() sets > fsg->exception_req_tag to the value of fsg->ep0_req_tag. This means > that exception_req_tag holds the counter value as of the time the > exception started. > > If the values are different, it means that another control transfer > started (fsg_setup() was called) between the time when the original > exception was raised and the time when it was handled. If the UDC is > working correctly, the only way for this to happen is if the host sends > another control request without waiting for the first one to finish. > >> and rc is 0. In standard_setup_req(), case >> USB_REQ_SET_CONFIGURATION, once i add the following code >> >> if (w_value == 0) >> fsg->config = 0; >> >> just before the break; statement, the "Device Descriptor >> Test-Addressed State" can pass. It seems that Get-Config request from >> host cannot wait, so i have to return the latest config value in >> response to the request. > > Almost certainly, the problem is that the UDC told the host that the > Set-Config request was finished before it should have. The host > thought the request was finished, so it sent the next request -- the > Get-Config -- but the gadget driver was still carrying out the > Set-Config. Yes, this should be the root cause. For the setup stage of Set-Config request, the UDC driver can handle it well. But for the status stage of Set-Config request, somehow it is not handled correctly. When UDC driver receives the endpoint 0 IN token, it only clears the interrupt request. It will not send the Data1 packet unless usb_ep_queue() is called. Somehow, before handle_exception() gets the chance to call do_set_config(), host sends next request. > DELAYED_STATUS tells fsg_setup() not to call ep0_queue(). It means > that the request isn't finished yet, so the status isn't known. The > status will be reported later, when the request is finished. > > handle_exception() is used for things that cannot be carried out in > interrupt context. fsg_setup() runs in an interrupt handler, so it > can't call do_set_config() or do_set_interface() -- those routines need > to run in process context. Therefore the USB_REQ_SET_CONFIGURATION > code raises an exception; when the fsg thread handles the exception, it > calls do_set_config(). > > When your UDC driver calls the gadget driver's .setup() function, how > does it handle the return value? The code is as below: status = dev->driver->setup(&dev->gadget, &usb_ctrlrequest); if (status < 0) { dev->protocol_stall = 1; } else if (status == (DELAYED_STATUS)) { /*NAK the IN packet from host*/ } Thanks, victor -- To unsubscribe from this list: send the line "unsubscribe linux-usb" in the body of a message to majordomo@xxxxxxxxxxxxxxx More majordomo info at http://vger.kernel.org/majordomo-info.html