Re: Linux USB file storage gadget with new UDC
Hi, It looks like you didn't add the dump_stack() call to the UDC driver's queue function. You need to add it. The attached is the log of dump_stack() call in the UDC driver queue function, for the last few USB request in the USBCV device descriptor test – addressed state. From the log, after Set-Config request is received, the UDC driver queue function is not called. That function is called after Get-Config request is received. I also share the pseudo code of the setup data valid processing, i suspect it may be related to the problem: receive setup data valid interrupt find out the usb request field (bmRequestType, bRequest, wValue, wIndex, wLength) if (USB_CLEAR_FEATURE_REQUEST) call usb_ep_queue() Don't you need to handle this in the hardware, just like USB_SET_FEATURE_REQUEST? USB_SET_FEATURE_REQUEST is handled in software. Thanks, victor [ 83.61] : 80 06 00 02 00 00 09 00 [ 83.61] fsg_setup call ep0_queue Backtrace: [ 83.61] [c020c0fc] (dump_backtrace+0x0/0x110) from [c03eee04] (dump_stack+0x18/0x1c) [ 83.61] r6:0002 r5:c0d6f600 r4:c0da69c0 r3:bf02fa10 [ 83.61] [c03eedec] (dump_stack+0x0/0x1c) from [bf02fa2c] (kagen2_ep_queue+0x1c/0x7b4 [kagen2_udc]) [ 83.61] [bf02fa10] (kagen2_ep_queue+0x0/0x7b4 [kagen2_udc]) from [bf0390b8] (ep0_queue+0x28/0x60 [g_file_storage]) [ 83.61] [bf039090] (ep0_queue+0x0/0x60 [g_file_storage]) from [bf038e10] (fsg_setup+0x3a0/0x3d8 [g_file_storage]) [ 83.61] r5:c0e23e98 r4:c0d6f600 [ 83.61] [bf038a70] (fsg_setup+0x0/0x3d8 [g_file_storage]) from [bf02f8c0] (kagen2_irq+0x388/0x4d8 [kagen2_udc]) [ 83.61] [bf02f538] (kagen2_irq+0x0/0x4d8 [kagen2_udc]) from [c0249644] (handle_irq_event_percpu+0x30/0x178) [ 83.61] r7:0020 r6: r5:c049af70 r4:c0da6840 [ 83.61] [c0249614] (handle_irq_event_percpu+0x0/0x178) from [c02497ec] (handle_irq_event+0x60/0x7c) [ 83.61] [c024978c] (handle_irq_event+0x0/0x7c) from [c024bcac] (handle_edge_irq+0x114/0x16c) [ 83.61] r6:f5006000 r5: r4:c049af70 r3:f5006000 [ 83.61] [c024bb98] (handle_edge_irq+0x0/0x16c) from [c0249054] (generic_handle_irq+0x28/0x38) [ 83.61] r4:0020 r3:c024bb98 [ 83.61] [c024902c] (generic_handle_irq+0x0/0x38) from [c0209c2c] (handle_IRQ+0x68/0x8c) [ 83.61] r4:0020 r3:0040 [ 83.61] [c0209bc4] (handle_IRQ+0x0/0x8c) from [c0208410] (asm_do_IRQ+0x10/0x14) [ 83.61] r5:0013 r4:bf02f500 [ 83.61] [c0208400] (asm_do_IRQ+0x0/0x14) from [c0208f14] (__irq_svc+0x34/0xbc) [ 83.61] Exception stack(0xc0e23f60 to 0xc0e23fa8) [ 83.61] 3f60: 4000 0288001f c2886000 c0df2c00 c0df2c00 bf02f4d8 0013 [ 83.61] 3f80: c0e23fbc c0e22000 c0e23fa8 4001 bf02f500 [ 83.61] 3fa0: 0013 [ 83.61] [bf02f4d8] (chkbusy_thread+0x0/0x60 [kagen2_udc]) from [c022f868] (kthread+0x94/0xa0) [ 83.61] r4:c0d75d58 r3: [ 83.61] [c022f7d4] (kthread+0x0/0xa0) from [c021913c] (do_exit+0x0/0x6f0) [ 83.61] r6:c021913c r5:c022f7d4 r4:c0d75d58 [ 83.61] ept0 in queue len 0x9, buffer 0xc0d6f800 [ 83.61] : 09 02 20 00 01 01 04 c0 01 [ 83.62] : 80 08 00 00 00 00 01 00 [ 83.62] g_file_storage gadget: get configuration 1 1 [ 83.62] fsg_setup call ep0_queue Backtrace: [ 83.62] [c020c0fc] (dump_backtrace+0x0/0x110) from [c03eee04] (dump_stack+0x18/0x1c) [ 83.62] r6:c0da69c0 r5:c0d6f600 r4:c0da69c0 r3:bf02fa10 [ 83.62] [c03eedec] (dump_stack+0x0/0x1c) from [bf02fa2c] (kagen2_ep_queue+0x1c/0x7b4 [kagen2_udc]) [ 83.62] [bf02fa10] (kagen2_ep_queue+0x0/0x7b4 [kagen2_udc]) from [bf0390b8] (ep0_queue+0x28/0x60 [g_file_storage]) [ 83.62] [bf039090] (ep0_queue+0x0/0x60 [g_file_storage]) from [bf038e10] (fsg_setup+0x3a0/0x3d8 [g_file_storage]) [ 83.62] r5:c0e23e98 r4:c0d6f600 [ 83.62] [bf038a70] (fsg_setup+0x0/0x3d8 [g_file_storage]) from [bf02f8c0] (kagen2_irq+0x388/0x4d8 [kagen2_udc]) [ 83.62] [bf02f538] (kagen2_irq+0x0/0x4d8 [kagen2_udc]) from [c0249644] (handle_irq_event_percpu+0x30/0x178) [ 83.62] r7:0020 r6: r5:c049af70 r4:c0da6840 [ 83.62] [c0249614] (handle_irq_event_percpu+0x0/0x178) from [c02497ec] (handle_irq_event+0x60/0x7c) [ 83.62] [c024978c] (handle_irq_event+0x0/0x7c) from [c024bcac] (handle_edge_irq+0x114/0x16c) [ 83.62] r6:f5006000 r5: r4:c049af70 r3:f5006000 [ 83.62] [c024bb98] (handle_edge_irq+0x0/0x16c) from [c0249054] (generic_handle_irq+0x28/0x38) [ 83.62] r4:0020 r3:c024bb98 [ 83.62] [c024902c] (generic_handle_irq+0x0/0x38) from [c0209c2c] (handle_IRQ+0x68/0x8c) [ 83.62] r4:0020 r3:0040 [ 83.62] [c0209bc4] (handle_IRQ+0x0/0x8c) from [c0208410] (asm_do_IRQ+0x10/0x14) [ 83.62] r5:0013 r4:bf02f500 [ 83.62] [c0208400] (asm_do_IRQ+0x0/0x14)
Re: Linux USB file storage gadget with new UDC
Hi, The text capture is incomplete. It is missing lots of packets. In particular, it is missing all the packets between 202489 and 202502. The missing packets are NAK, I added the NAK after Set-Config setup stage. I hide the NAK when i export the packet capture to text format. Also, I don't understand the Dir H(S) part of the capture lines. What do they mean? They are present on every packet. Dir stands for direction, H is high speed, S is super speed. This was never the issue. I'm sure the DATA1 packet of the Set-Config was sent before the Get-Config request. The real question is whether the DATA1 packet was sent before the Set-Config request had been fully processed. To get more information, try adding msleep(100); just before the final return rc; line in do_set_config(). We should be able to see in the analyzer log if this 100-ms delay is present. After i added msleep(100) just before final line in do_set_config(), the USB enumeration fails to complete normally. Here's a second test you can try. In handle_exception(), the FSG_STATE_CONFIG_CHANGE case, comment out the ep0_queue(fsg); line. Without that line the Set-Config request should time out, because the gadget will never complete the status stage. If the request does complete normally, it will prove that the UDC driver isn't working right. After i comment out the ep0_queue(fsg) in FSG_STATE_CONFIG_CHANGE case of handle_exception(), the request does complete, but takes more time to complete. And UDC driver queue function is still being called after the Set-Config request. Thanks, Victor -- To unsubscribe from this list: send the line unsubscribe linux-usb in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
Re: Linux USB file storage gadget with new UDC
Hi, Victor, if you can get hold of a USB bus analyzer, you would be able to see directly when the DATA1 packet does or does not get sent. I am in the process of getting a USB bus analyzer. No -- the problem is that the UDC completes the Set-Config request before it should. In other words, it sends the DATA1 packet when it really should send a NAK packet. In the status stage of Set-Config request, i make the driver sends the NAK packet after it receives the IN packet. However, the next Get-Config request is still sent out by host. With the USB bus analyzer, hopefully i can verify the packets. Why haven't you turned on CONFIG_PRINTK_TIME on your gadget system? I have asked you several times to do this. Without CONFIG_PRINTK_TIME, there is no way to tell how long it took to reach this spot. Ok. I will turn CONFIG_PRINTK_TIME on for debugging. Thanks, victor -- To unsubscribe from this list: send the line unsubscribe linux-usb in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
Re: Linux USB file storage gadget with new UDC
Hi, However, the USB-2 spec says (section 9.2.6.4) that devices should be able to carry out requests with no Data stage (such as Set-Config) within 50 ms. Does your gadget really take longer than that to handle the exception? To find out, collect a usbmon trace showing what happens when your new driver is plugged into a Linux host. I have set the NAK and stall the endpoint 0 after receiving Set-Config request, however, That doesn't make sense. Stalling the endpoint means sending a STALL packet. You can't send both a STALL and a NAK. Get-Config request is still sent out by USBCV host immediately. There should be at least a 50-ms delay, unless the UDC driver is doing something wrong. The latest usbmon trace is attached. From the trace, the timing is within 50ms from Set-Config request to the next request. Does your gadget really take longer than that to handle the exception? Yes, i think there is a delay before gadget calls the handle_exception() routine. So the problem is before handle_exception() of Set-Config request is called, the next request is sent out already by the host. So if the next request is Get-Config, it will not return the latest config value. As can be seen in the gadget driver log below, after Set-Config request is received, another two more requests are received before handle_exception() is called. If there is a way to call handle_exception() immediately after Set-Config request, it would be very helpful. g_file_storage gadget: ep0-setup, length 8: : 00 09 01 00 00 00 00 00 g_file_storage gadget: set configuration and stall endpoint g_file_storage gadget: ep0-setup, length 8: : 80 06 04 03 09 04 ff 00 g_file_storage gadget: get string descriptor ept0 in queue len 0x1a, buffer 0xc1297800 ep0_complete g_file_storage gadget: ep0-in, length 26: : 1a 03 53 00 65 00 6c 00 66 00 2d 00 70 00 6f 00 0010: 77 00 65 00 72 00 65 00 64 00 g_file_storage gadget: ep0-setup, length 8: : 80 06 05 03 09 04 ff 00 g_file_storage gadget: get string descriptor ept0 in queue len 0x1a, buffer 0xc1297800 ep0_complete g_file_storage gadget: ep0-in, length 26: : 1a 03 4d 00 61 00 73 00 73 00 20 00 53 00 74 00 0010: 6f 00 72 00 61 00 67 00 65 00 handle_exception begin handle_exception wait until handle_exception old_state 4 g_file_storage gadget: set interface 0 g_file_storage gadget: high-speed config #1 FSG_STATE_CONFIG_CHANGE 19 21 0 g_file_storage gadget: in handle_exception loop Thanks, victor -- To unsubscribe from this list: send the line unsubscribe linux-usb in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
Re: Linux USB file storage gadget with new UDC
Hi, May i know which part of the do_set_config() or do_set_interface() has to be run in process context? Well, it's not exactly true that the routine has to run in process context. More accurately, it has to run at a time when the main thread isn't using any of the endpoints or request structures, because do_set_interface() deallocates the requests and disables the endpoints. For example, if the main thread was in the middle of executing a SCSI command, do_set_config() would have to wait until it finished. The easiest way to do this is by the exception technique. That way do_set_config() is called by the main thread itself, so it knows the main thread isn't using those structures. Thanks. The USBCV test has tight timing requirement. Once Set-Config request is sent out, USBCV sends out Get-Config request to get the config value immediately. At that time, gadget driver has not yet done the handle_exception. So Get-Config request returns old config value, and USBCV declares the test failed. Please see the log below. Is there any way to speed up the handle_exception or to ask the USBCV host to not send out Get-Config immediately? I have set the NAK and stall the endpoint 0 after receiving Set-Config request, however, Get-Config request is still sent out by USBCV host immediately. g_file_storage gadget: ep0-setup, length 8: : 00 09 00 00 00 00 00 00 g_file_storage gadget: set configuration NAK and stall endpoint g_file_storage gadget: ep0-setup, length 8: : 80 08 00 00 00 00 01 00 g_file_storage gadget: get configuration ept0 in queue len 0x1, buffer 0xc1289800 ep0_complete g_file_storage gadget: ep0-in, length 1: : 01 after kagen2_ep_queue kagen2_ep_queue 31 512 31 [kagen2_ep_queue] 43425355 89d40868 g_file_storage gadget: bulk-out, length 31: : 55 53 42 43 68 08 d4 89 00 00 00 00 00 00 0a 35 0010: 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 g_file_storage gadget: SCSI command: SYNCHRONIZE CACHE; Dc=10, Dn=0; Hc=10, Hn=0 attention condition g_file_storage gadget: after calling do_scsi_command handle_exception begin handle_exception wait until handle_exception old_state 4 g_file_storage gadget: reset config g_file_storage gadget: reset interface FSG_STATE_CONFIG_CHANGE 52 53 0 g_file_storage gadget: in handle_exception loop g_file_storage gadget: in fsg-running loop g_file_storage gadget: in fsg-running loop thanks, victor -- To unsubscribe from this list: send the line unsubscribe linux-usb in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
Re: Linux USB file storage gadget with new UDC
Hi, However, the USB-2 spec says (section 9.2.6.4) that devices should be able to carry out requests with no Data stage (such as Set-Config) within 50 ms. Does your gadget really take longer than that to handle the exception? To find out, collect a usbmon trace showing what happens when your new driver is plugged into a Linux host. I have set the NAK and stall the endpoint 0 after receiving Set-Config request, however, That doesn't make sense. Stalling the endpoint means sending a STALL packet. You can't send both a STALL and a NAK. Get-Config request is still sent out by USBCV host immediately. There should be at least a 50-ms delay, unless the UDC driver is doing something wrong. The latest usbmon trace is attached. From the trace, the timing is within 50ms from Set-Config request to the next request. Does your gadget really take longer than that to handle the exception? Yes, i think there is a delay before gadget calls the handle_exception() routine. So the problem is before handle_exception() of Set-Config request is called, the next request is sent out already by the host. So if the next request is Get-Config, it will not return the latest config value. Thanks, victor usbmon_july12.log Description: Binary data
Re: Linux USB file storage gadget with new UDC
Hi, 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. And yet it _does_ send the packet before usb_ep_queue() is called. I am still studying how Data1 packet is sent out, from the log, usb_ep_queue() is not called, i have no idea now. 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(). May i know which part of the do_set_config() or do_set_interface() has to be run in process context? Thanks, Victor -- To unsubscribe from this list: send the line unsubscribe linux-usb in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
Re: Linux USB file storage gadget with new UDC
Hi, I can't tell what's going on in your log. Look at the FSG_STATE_CONFIG_CHANGE case in handle_exception(). Here's the code: rc = do_set_config(fsg, new_config); if (fsg-ep0_req_tag != exception_req_tag) break; if (rc != 0)// STALL on errors fsg_set_halt(fsg, fsg-ep0); else// Complete the status stage ep0_queue(fsg); break; It calls do_set_config(). After that, fsg-ep0_req_tag should be equal to exception_req_tag and rc should be equal to 0. Therefore the code will call ep0_queue(), which calls usb_ep_queue(). I found out from printk, the fsg-ep0_req_tag and exception_req_tag are not equal, 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. Thanks, victor In fact, the Device Descriptor Test-Addressed State sometimes passes, sometimes fails after my modification. What is the reason of DELAYED_STATUS in USB_REQ_SET_CONFIGURATION, and the use of handle_exception() to call do_set_config()? Thanks, victor -- To unsubscribe from this list: send the line unsubscribe linux-usb in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
Re: Linux USB file storage gadget with new UDC
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 majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
Re: Linux USB file storage gadget with new UDC
Hi, No, that's not right. Set-Config has only two stages, Setup and Status; there is no Data stage. The flow is: Host Device - Setup Packet --- | - Data0 Packet --- |== Setup stage Ack Packet -- | - In Packet -- | Data1 Packet |== Status stage - Ack Packet - | ACK the Status stage of an OUT control transfer, is it referring to the Third ACK packet? So UDC driver should ACK only after Data1 packet is sent via the usb_ep_queue()? I meant the Data1 packet above. The UDC driver should not send this packet until the gadget driver tells it to (by calling usb_ep_queue). Until then, it should send NAK in respond to the In packet. Is the Data1 packet above containing no data, such as this? PID !PID CRC I do not see the gadget driver calling usb_ep_queue() for sending the Data1 packet. Please see the log below. Is there similar code in net2280.c handle_stat0_irqs() that handles Set-Config? g_file_storage gadget: ep0-setup, length 8: : 00 09 00 00 00 00 00 00 g_file_storage gadget: set configuration after kagen2_ep_queue kagen2_ep_queue 31 64 31 [kagen2_ep_queue] 43425355 899e1008 g_file_storage gadget: bulk-out, length 31: : 55 53 42 43 08 10 9e 89 00 00 00 00 00 00 0a 35 0010: 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 g_file_storage gadget: SCSI command: SYNCHRONIZE CACHE; Dc=10, Dn=0; Hc=10, Hn=0 g_file_storage gadget: ep0-setup, length 8: : 80 08 00 00 00 00 01 00 g_file_storage gadget: get configuration ept0 in queue len 0x1, buffer 0xc1289800 ep0_complete g_file_storage gadget: ep0-in, length 1: : 01 attention condition Thanks, victor -- To unsubscribe from this list: send the line unsubscribe linux-usb in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
Re: Linux USB file storage gadget with new UDC
Hi, No, i don't see that (Set-Config request with a config value of 0) Well, then I don't know where the problem is, but obviously the problem occurred before the gadget driver was involved. Either the host sent a wrong packet, or more likely the UDC received the packet incorrectly. Yes, UDC driver has bug. After modifying it, it can receive Set-Config request with a config value of 0. However, the device descriptor test - addressed state still fails. Please see the attached log. The Set-Config request with a config value of 0 is the second last USB request sent from the host. The last USB request is Get-Config, which still returns config value of 1. Thanks, victor # dmesg -c g_file_storage gadget: disconnect or port reset handle_exception begin handle_exception wait until handle_exception old_state 5 g_file_storage gadget: in handle_exception loop g_file_storage gadget: in fsg-running loop g_file_storage gadget: disconnect or port reset handle_exception begin handle_exception wait until handle_exception old_state 5 g_file_storage gadget: in handle_exception loop g_file_storage gadget: in fsg-running loop g_file_storage gadget: ep0-setup, length 8: : 80 06 00 01 00 00 12 00 g_file_storage gadget: get device descriptor exit C ept0 in queue len 0x12, buffer 0xc1289800 ep0_complete g_file_storage gadget: ep0-in, length 18: : 12 01 00 02 00 00 00 40 25 05 a5 a4 33 03 01 02 0010: 00 01 USB_RECIP_DEVICE 0x2 fa is 0x2 exit A g_file_storage gadget: ep0-setup, length 8: : 80 06 00 01 00 00 12 00 g_file_storage gadget: get device descriptor ept0 in queue len 0x12, buffer 0xc1289800 ep0_complete g_file_storage gadget: ep0-in, length 18: : 12 01 00 02 00 00 00 40 25 05 a5 a4 33 03 01 02 0010: 00 01 g_file_storage gadget: ep0-setup, length 8: : 80 06 00 02 00 00 09 00 g_file_storage gadget: get configuration descriptor ept0 in queue len 0x9, buffer 0xc1289800 ep0_complete g_file_storage gadget: ep0-in, length 9: : 09 02 20 00 01 01 04 c0 01 g_file_storage gadget: ep0-setup, length 8: : 00 09 01 00 00 00 00 00 g_file_storage gadget: set configuration g_file_storage gadget: ep0-setup, length 8: : 80 06 00 02 00 00 09 00 g_file_storage gadget: get configuration descriptor ept0 in queue len 0x9, buffer 0xc1289800 ep0_complete g_file_storage gadget: ep0-in, length 9: : 09 02 20 00 01 01 04 c0 01 handle_exception begin handle_exception wait until handle_exception old_state 4 g_file_storage gadget: ep0-setup, length 8: : 80 06 00 02 00 00 20 00 g_file_storage gadget: get configuration descriptor ept0 in queue len 0x20, buffer 0xc1289800 ep0_complete g_file_storage gadget: ep0-in, length 32: : 09 02 20 00 01 01 04 c0 01 09 04 00 00 02 08 06 0010: 50 05 07 05 81 02 40 00 00 07 05 01 02 40 00 00 g_file_storage gadget: set interface 0 g_file_storage gadget: full-speed config #1 g_file_storage gadget: in handle_exception loop [start_transfer] 43425355 899e1008 ept1 out queue len 0x40, buffer 0xc0c44000 before kagen2_ep_queue g_file_storage gadget: disconnect or port reset after kagen2_ep_queue kagen2_ep_queue 31 64 31 [kagen2_ep_queue] 43425355 899e1008 g_file_storage gadget: bulk-out, length 31: : 55 53 42 43 08 10 9e 89 00 00 00 00 00 00 0a 35 0010: 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 g_file_storage gadget: SCSI command: SYNCHRONIZE CACHE; Dc=10, Dn=0; Hc=10, Hn=0 attention condition g_file_storage gadget: after calling do_scsi_command handle_exception begin handle_exception wait until handle_exception old_state 5 g_file_storage gadget: reset config g_file_storage gadget: reset interface g_file_storage gadget: in handle_exception loop g_file_storage gadget: in fsg-running loop g_file_storage gadget: in fsg-running loop g_file_storage gadget: disconnect or port reset handle_exception begin handle_exception wait until handle_exception old_state 5 g_file_storage gadget: in handle_exception loop g_file_storage gadget: in fsg-running loop g_file_storage gadget: ep0-setup, length 8: : 80 06 00 01 00 00 12 00 g_file_storage gadget: get device descriptor exit C ept0 in queue len 0x12, buffer 0xc1289800 ep0_complete g_file_storage gadget: ep0-in, length 18: : 12 01 00 02 00 00 00 40 25 05 a5 a4 33 03 01 02 0010: 00 01 USB_RECIP_DEVICE 0x2 fa is 0x2 exit A g_file_storage gadget: ep0-setup, length 8: : 80 06 00 01 00 00 12 00 g_file_storage gadget: get device descriptor ept0 in queue len 0x12, buffer 0xc1289800 ep0_complete g_file_storage gadget: ep0-in, length 18: : 12 01 00 02 00 00 00 40 25 05 a5 a4 33 03 01 02 0010: 00 01 g_file_storage gadget: ep0-setup, length 8: : 80 06 00 02 00 00 09 00 g_file_storage gadget: get configuration descriptor ept0 in queue len 0x9, buffer 0xc1289800 ep0_complete g_file_storage gadget: ep0-in, length 9: : 09 02 20 00 01 01 04 c0 01 g_file_storage gadget: ep0-setup, length 8: : 00 09 01 00 00 00 00 00
Re: Linux USB file storage gadget with new UDC
Hi, No, i don't see that (Set-Config request with a config value of 0) Well, then I don't know where the problem is, but obviously the problem occurred before the gadget driver was involved. Either the host sent a wrong packet, or more likely the UDC received the packet incorrectly. Yes, UDC driver has bug. After modifying it, it can receive Set-Config request with a config value of 0. However, the device descriptor test - addressed state still fails. Please see the attached log. The Set-Config request with a config value of 0 is the second last USB request sent from the host. The last USB request is Get-Config, which still returns config value of 1. In gadget driver, do_set_config(), if new_config is 0, the new_config is not processed. So config value of zero will never be saved by gadget driver. Isn't it? Thanks, victor -- To unsubscribe from this list: send the line unsubscribe linux-usb in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
Re: Linux USB file storage gadget with new UDC
Hi, Yes, UDC driver has bug. After modifying it, it can receive Set-Config request with a config value of 0. However, the device descriptor test - addressed state still fails. Please see the attached log. The Set-Config request with a config value of 0 is the second last USB request sent from the host. The last USB request is Get-Config, which still returns config value of 1. This looks like another bug in the UDC driver. It performs the Status stage of the Set-Config request before the gadget driver has finished carrying out the request. Notice that the USB_REQ_SET_CONFIGURATION case in standard_setup_req() returns DELAYED_STATUS. As a result, fsg_setup() does not call ep0_queue(), and so usb_ep_queue() doesn't get called. The UDC driver is not supposed to ACK the Status stage of an OUT control transfer until usb_ep_queue() is called. May i verify my understanding of Set-Config request packet flow? Host Device --Setup Packet --Data0 Packet -Ack Packet- -- In Packet Data1 Packet - Ack Packet - - Out Packet - Data1 Packet Ack Packet - ACK the Status stage of an OUT control transfer, is it referring to the Third ACK packet? So UDC driver should ACK only after Data1 packet is sent via the usb_ep_queue()? In gadget driver, do_set_config(), if new_config is 0, the new_config is not processed. So config value of zero will never be saved by gadget driver. Isn't it? Look at do_set_config(): /* Disable the single interface */ if (fsg-config != 0) { DBG(fsg, reset config\n); fsg-config = 0; rc = do_set_interface(fsg, -1); } /* Enable the interface */ if (new_config != 0) { ... } return rc; So if new_config is 0, fsg-config remains set to 0 and the deconfiguration is processed by the do_set_interface() call. Understand now. Thanks. victor -- To unsubscribe from this list: send the line unsubscribe linux-usb in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
Re: Linux USB file storage gadget with new UDC
Hi, g_file_storage gadget: ep0-setup, length 8: : 00 09 01 00 00 00 00 00 g_file_storage gadget: set configuration Yes, that is a Set-Config request with configuraiton value 1. You probably got hold of the wrong part of the log. Elsewhere there should be a Set-Config request with a config value of 0. No, i don't see that (Set-Config request with a config value of 0) g_file_storage gadget: ep0-setup, length 8: : 80 08 00 00 00 00 01 00 g_file_storage gadget: get configuration g_file_storage gadget: ep0-in, length 1: : 01 This is the correct response following the request above. You can test the gadget's behavior with a Linux host. To send a Set-Config request with value N, do echo N /sys/bus/usb/devices/.../bConfigurationValue where the ... part is replaced with the gadget's device path. When i use echo 0 /sys/bus/usb/devices/.../bConfigurationValue, there is no activity in gadget and UDC driver, and the gadget disappear from Linux host. If i use echo 1 /sys/bus/usb/devices/.../bConfigurationValue, the gadget is re-enumerated and re-appear in Linux host. I also observe in gadget driver, there is only one config descriptor with bConfigurationValue of 1. Is bConfigurationValue of 0 meant to disble the device? Thanks, Victor -- To unsubscribe from this list: send the line unsubscribe linux-usb in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
Re: Linux USB file storage gadget with new UDC
Hi, You should not be concerned about variables in the gadget driver. The problem is in the UDC driver. For some examples of what the UDC driver needs to do, look at handle_control_request() in drivers/usb/gadget/dummy_hcd.c or the switch (u.r.bRequest) statement of handle_stat0_irqs() in drivers/usb/gadget/net2280.c. Alan Stern I find some clue. From USB 2.0 Compliance Test Spec, quoted: Address State: 1. Put the device in the configured state following the procedure below. 2. Issue a valid Set Configuration command to the device with configuration value zero. 3. Issue a valid Get Configuration command to the device and verify that device responds with zero. I think the address state test in USB2CV fails because Set-Configuration actually set config #1 and Get-Configuration returns config #1. See the usb requests log below. It seems that the Set Configuration command from USB2CV is issued with config value of one. Isn't it? g_file_storage gadget: ep0-setup, length 8: : 00 09 01 00 00 00 00 00 g_file_storage gadget: set configuration g_file_storage gadget: ep0-setup, length 8: : 80 08 00 00 00 00 01 00 g_file_storage gadget: get configuration g_file_storage gadget: ep0-in, length 1: : 01 Thanks, victor -- To unsubscribe from this list: send the line unsubscribe linux-usb in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
Re: Linux USB file storage gadget with new UDC
Hi, I re-attach the usbmon log. If possible, please show me which line indicates that usb_ep_set_wedge routine is not working, or how to look for the clue. Is it from the control transfer line? Here's an example: f4148f80 308532 S Bo:1:011:1 -115 31 = 55534243 0600 c000 861a 003f00c0 00 f4148f80 308652 C Bo:1:011:1 0 31 f14c5600 308676 S Bi:1:011:1 -115 192 f14c5600 3087787651 C Bi:1:011:1 -121 16 = 0f00 080a0400 f4148f80 3087787674 S Bi:1:011:1 -115 13 f4148f80 3087803018 C Bi:1:011:1 0 13 = 55534253 0600 b000 00 The last line should have failed with a -32 error code, because the IN endpoint is supposed to be halted at this point. I think the GET_STATUS request is not handled by the gadget driver. Isn't it so? That's right. Get-Status, Set-Feature, and Clear-Feature requests must be handled by the UDC driver. Alan Stern The fsg-state in gadget driver, is used for exception handling. Is there any variable to track the USB device state of Figure 9-1 of the USB 2.0 Spec? Now the gadget driver does not pass the USB2.0 CV - Get Device Descriptor - Address State test. So i am trying to find more information. Thanks, victor -- To unsubscribe from this list: send the line unsubscribe linux-usb in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
Re: Linux USB file storage gadget with new UDC
Hi, The problem is in UDC driver. i made the change, it is ok now. Good. I noticed that the usb_ep_set_wedge routine still isn't working right. You might try to fix that. Alan Stern Ok, is the usb_ep_set_wedge routine not working? I can't see that in the log file. Now, in USB 2.0 CV test, there is an error about GET_STATUS request, as shown below. g_file_storage gadget: ep0-setup, length 8: : 82 00 00 00 81 00 02 00 g_file_storage gadget: unknown control req 82.00 v i0081 l2 handle_setup status -95 I think the GET_STATUS request is not handled by the gadget driver. Isn't it so? thanks, victor -- To unsubscribe from this list: send the line unsubscribe linux-usb in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
Re: Linux USB file storage gadget with new UDC
Hi, Ok, is the usb_ep_set_wedge routine not working? I can't see that in the log file. It is not working. This can be seen in the usbmon log. I re-attach the usbmon log. If possible, please show me which line indicates that usb_ep_set_wedge routine is not working, or how to look for the clue. Is it from the control transfer line? Now, in USB 2.0 CV test, there is an error about GET_STATUS request, as shown below. g_file_storage gadget: ep0-setup, length 8: : 82 00 00 00 81 00 02 00 g_file_storage gadget: unknown control req 82.00 v i0081 l2 handle_setup status -95 I think the GET_STATUS request is not handled by the gadget driver. Isn't it so? That's right. Get-Status, Set-Feature, and Clear-Feature requests must be handled by the UDC driver. Alan Stern Should the UDC driver handle Get-Status before or after the call to fsg_setup()? thanks, victor f2e9da80 3086290883 S Ci:1:001:0 s a3 00 0001 0004 4 f2e9da80 3086290911 C Ci:1:001:0 0 4 = 0001 f2e9da80 3086290919 S Ci:1:001:0 s a3 00 0002 0004 4 f2e9da80 3086290923 C Ci:1:001:0 0 4 = 0001 f2e9da80 3086290927 S Ci:1:001:0 s a3 00 0003 0004 4 f2e9da80 3086290931 C Ci:1:001:0 0 4 = 0001 f2e9da80 3086290936 S Ci:1:001:0 s a3 00 0004 0004 4 f2e9da80 3086290940 C Ci:1:001:0 0 4 = 0001 f2e9da80 3086290944 S Ci:1:001:0 s a3 00 0005 0004 4 f2e9da80 3086290958 C Ci:1:001:0 0 4 = 03050400 f2e9da80 3086290963 S Ci:1:001:0 s a3 00 0006 0004 4 f2e9da80 3086290967 C Ci:1:001:0 0 4 = 0001 f6816a80 3086290972 S Ii:1:001:1 -115:2048 4 f2e9da80 3086291359 S Ci:1:001:0 s a3 00 0005 0004 4 f2e9da80 3086291366 C Ci:1:001:0 0 4 = 03050400 f2e9da80 3086291372 S Co:1:001:0 s 23 01 0012 0005 0 f2e9da80 3086291378 C Co:1:001:0 0 0 f2e9d100 3086307426 S Ci:1:001:0 s a3 00 0005 0004 4 f2e9d100 3086307441 C Ci:1:001:0 0 4 = 0305 f2e9d100 3086307450 S Ci:1:003:0 s 80 00 0002 2 f2e9d100 3086307599 C Ci:1:003:0 0 2 = 0300 f2e9d100 3086308101 S Co:1:003:0 s 00 01 0001 0 f2e9d100 3086308971 C Co:1:003:0 0 0 f2e9d100 3086308995 S Ci:1:003:0 s a3 00 0001 0004 4 f2e9d100 3086309344 C Ci:1:003:0 0 4 = 0001 f2e9d100 3086309362 S Ci:1:003:0 s a3 00 0002 0004 4 f2e9d100 3086309718 C Ci:1:003:0 0 4 = 01010100 f2e9d100 3086309736 S Co:1:003:0 s 23 01 0010 0002 0 f2e9d100 3086310093 C Co:1:003:0 0 0 f2e9d100 3086310110 S Ci:1:003:0 s a3 00 0003 0004 4 f2e9d100 3086310466 C Ci:1:003:0 0 4 = 0001 f2e9d100 3086310478 S Ci:1:003:0 s a3 00 0004 0004 4 f2e9d100 3086310842 C Ci:1:003:0 0 4 = 0001 f3369680 3086414872 S Ii:1:003:1 -115:2048 1 f33a1c00 3086414952 S Ci:1:003:0 s a3 00 0002 0004 4 f33a1c00 3086415358 C Ci:1:003:0 0 4 = 0101 f33a1c00 3086415413 S Co:1:003:0 s 23 03 0016 0002 0 f33a1c00 3086415717 C Co:1:003:0 0 0 f33a1c00 3086415763 S Co:1:003:0 s 23 03 0004 0002 0 f33a1c00 3086416093 C Co:1:003:0 0 0 f33a1600 3086430814 S Ci:1:003:0 s a3 00 0002 0004 4 f33a1600 3086431836 C Ci:1:003:0 0 4 = 03011000 f3369680 3086450282 C Ii:1:003:1 0:2048 1 = 04 f3369680 3086450297 S Ii:1:003:1 -115:2048 1 f33fa980 3086486796 S Co:1:003:0 s 23 01 0014 0002 0 f33fa980 3086487826 C Co:1:003:0 0 0 f33fa980 3086487934 S Ci:1:000:0 s 80 06 0100 0040 64 f33fa980 3086488571 C Ci:1:000:0 0 18 = 12010002 0040 2505a5a4 33030102 0001 f33fa980 3086488632 S Co:1:003:0 s 23 03 0004 0002 0 f33fa980 3086488943 C Co:1:003:0 0 0 f33fa080 3086503390 S Ci:1:003:0 s a3 00 0002 0004 4 f33fa080 3086503964 C Ci:1:003:0 0 4 = 03011000 f4147b80 3086558950 S Co:1:003:0 s 23 01 0014 0002 0 f4147b80 3086559441 C Co:1:003:0 0 0 f4147b80 3086559513 S Co:1:000:0 s 00 05 000b 0 f4147b80 3086559683 C Co:1:000:0 0 0 f2eeba00 3086578950 S Ci:1:011:0 s 80 06 0100 0012 18 f2eeba00 3086580189 C Ci:1:011:0 0 18 = 12010002 0040 2505a5a4 33030102 0001 f2eeba00 3086580259 S Ci:1:011:0 s 80 06 0600 000a 10 f2eeba00 3086580806 C Ci:1:011:0 0 10 = 0a060002 0040 0100 f2eeba00 3086580883 S Ci:1:011:0 s 80 06 0200 0009 9 f2eeb500 3086580900 S Co:1:003:0 s 23 03 0016 0202 0 f2eeb500 3086581180 C Co:1:003:0 0 0 f2eeba00 3086581558 C Ci:1:011:0 0 9 = 09022000 010104c0 01 f2eeba00 3086581604 S Ci:1:011:0 s 80 06 0200 0020 32 f2eeba00 3086582182 C Ci:1:011:0 0 32 = 09022000 010104c0 01090400 00020806 50050705 81024000 00070501 0240 f2eeba00 3086582259 S Ci:1:011:0 s 80 06 0300 00ff 255 f2eeba00 3086582933 C Ci:1:011:0 0 4 = 04030904 f2eeba00 3086583014 S Ci:1:011:0 s 80 06 0302 0409 00ff 255 f2eeba00 3086583558 C Ci:1:011:0 0 54 = 36034600 69006c00 65002d00 62006100 63006b00 65006400 20005300 74006f00 f2eeba00 3086583633 S Ci:1:011:0 s 80 06 0301 0409 00ff 255 f2eeba00 3086584558 C Ci:1:011:0 0 58 = 3a034c00 69006e00 75007800 20003300 2e003400 2e003400 2b002000 77006900 f2eeba00 3086584905 S Co:1:011:0 s 00 09 0001 0 f2eeba00 3086585055 C Co:1:011:0 0 0
Re: Linux USB file storage gadget with new UDC
Hi, Yes, i see the bad characters in the log file. I apologize for that, my eyes was in pain after looking thru the log files and did not notice that when i attached the log file. The good news is i can get gadget to work with Lenovo x100e on Ubuntu and Windows. The change is adding more delay after writing to endpoint one IN FIFO register, for the case of writing more than the endpoint buffer size. However, the gadget only work on high-speed mode. If i disable ehci_hcd driver in Ubuntu (force it to be full speed), the same problem of SCSI_READ_10 command asking 4096 bytes and gadget returning the data, and gadget reset, still happens. I can bring up the gadget in full speed mode now, so the SCSI_READ_10 command problem is fixed. It is caused by an error interfacing to hardware. Now there is another problem with SCSI_MODE_SELECT_6 command, when in full speed mode, the data for SCSI_MODE_SELECT_6 command is 72 byte, and somehow the gadget is reset. Is it because gadget is not able to handle the amount of data? Please see the attached gadget log. Normally, in high speed mode, the data of SCSI_MODE_SELECT_6 command is 24 byte. Thanks, victor g_file_storage gadget: reset config g_file_storage gadget: reset interface g_file_storage gadget: in handle_exception loop g_file_storage gadget: in fsg-running loop g_file_storage gadget: in fsg-running loop g_file_storage gadget: ep0-setup, length 8: : 80 06 00 01 00 00 40 00 g_file_storage gadget: get device descriptor ept0 in queue len 0x12, buffer 0xc128f800 ep0_complete g_file_storage gadget: ep0-in, length 18: : 12 01 00 02 00 00 00 40 25 05 a5 a4 33 03 01 02 0010: 00 01 g_file_storage gadget: disconnect or port reset handle_exception begin handle_exception wait until handle_exception old_state 5 g_file_storage gadget: in handle_exception loop g_file_storage gadget: in fsg-running loop USB_RECIP_DEVICE fa is 0x3 exit A g_file_storage gadget: ep0-setup, length 8: : 80 06 00 01 00 00 12 00 g_file_storage gadget: get device descriptor exit C ept0 in queue len 0x12, buffer 0xc128f800 ep0_complete g_file_storage gadget: ep0-in, length 18: : 12 01 00 02 00 00 00 40 25 05 a5 a4 33 03 01 02 0010: 00 01 g_file_storage gadget: ep0-setup, length 8: : 80 06 00 02 00 00 09 00 g_file_storage gadget: get configuration descriptor ept0 in queue len 0x9, buffer 0xc128f800 ep0_complete g_file_storage gadget: ep0-in, length 9: : 09 02 20 00 01 01 04 c0 01 g_file_storage gadget: ep0-setup, length 8: : 00 09 01 00 00 00 00 00 g_file_storage gadget: set configuration handle_exception begin handle_exception wait until handle_exception old_state 4 g_file_storage gadget: set interface 0 g_file_storage gadget: full-speed config #1 EP1 OUT IRQ 0x28 ept0 in queue len 0x0, buffer 0xc128f800 g_file_storage gadget: in handle_exception loop [start_transfer] 800 0 ept1 out queue len 0x40, buffer 0xc134 before kagen2_ep_queue after kagen2_ep_queue kagen2_ep_queue 31 64 31 EP1 OUT IRQ 0x28 [kagen2_ep_queue] 43425355 87a68008 g_file_storage gadget: bulk-out, length 31: : 55 53 42 43 08 80 a6 87 18 00 00 00 00 00 06 15 0010: 10 00 00 18 00 00 00 00 00 00 00 00 00 00 00 g_file_storage gadget: SCSI command: MODE SELECT(6); Dc=6, Do=24; Hc=6, Ho=24 attention condition [start_transfer] 43425355 87a68008 ept1 out queue len 0x40, buffer 0xc134 before kagen2_ep_queue after kagen2_ep_queue kagen2_ep_queue 24 64 24 before kagen2_ep_queue g_file_storage gadget: disconnect or port reset after kagen2_ep_queue kagen2_ep_queue 48 64 24 before kagen2_ep_queue after kagen2_ep_queue kagen2_ep_queue 72 64 24 [kagen2_ep_queue] 800 0 g_file_storage gadget: bulk-out, length 72: : 00 00 00 08 00 00 00 00 00 00 02 00 08 0a 00 00 0010: ff ff 00 00 ff ff ff ff 00 00 00 00 00 00 00 5f 0020: c1 9f 75 00 58 1d 00 00 00 00 00 00 02 00 00 00 0030: 01 00 06 00 00 00 00 00 00 00 00 00 00 00 00 00 0040: 80 00 29 5f 22 e8 c2 4e g_file_storage gadget: bulk_out_complete -- 0, 72/24 g_file_storage gadget: before calling send_status g_file_storage gadget: sending command-failure status g_file_storage gadget: sense data: SK x06, ASC x29, ASCQ x00; info x0 g_file_storage gadget: bulk-in, length 13: : 55 53 42 53 08 80 a6 87 18 00 00 00 01 [start_transfer] 53425355 87a68008 exit C ept1 in queue len 0xd, buffer 0xc135 0: 0x53425355 4: 0x87a68008 8: 0x18 bulk_in_complete -- 0, 13/13 handle_exception begin handle_exception wait until handle_exception old_state 5 g_file_storage gadget: reset config g_file_storage gadget: reset interface g_file_storage gadget: in handle_exception loop g_file_storage gadget: in fsg-running loop g_file_storage gadget: in fsg-running loop g_file_storage gadget: ep0-setup, length 8: : 80 06 00 01 00 00 40 00 g_file_storage gadget: get device descriptor ept0 in queue len 0x12, buffer 0xc128f800 ep0_complete g_file_storage gadget: ep0-in, length 18: : 12 01
Re: Linux USB file storage gadget with new UDC
Hi, There is a mistake in the previous log file, because the fifo size is still set to 512 byte. Now i change it to 64 byte if it is Full speed. The FIFO size should always be set to the value in the endpoint descriptor, no matter what speed the connection is. The log file are attached. The log shows that your 64-byte transfers don't work very well. The first one didn't send any bytes. The second one sent only 4 bytes. And each of the ones after that sent 0 bytes. Alan Stern PS: Something was very wrong with the log file you posted. It is full of bad characters. You can it here: Yes, i see the bad characters in the log file. I apologize for that, my eyes was in pain after looking thru the log files and did not notice that when i attached the log file. The good news is i can get gadget to work with Lenovo x100e on Ubuntu and Windows. The change is adding more delay after writing to endpoint one IN FIFO register, for the case of writing more than the endpoint buffer size. However, the gadget only work on high-speed mode. If i disable ehci_hcd driver in Ubuntu (force it to be full speed), the same problem of SCSI_READ_10 command asking 4096 bytes and gadget returning the data, and gadget reset, still happens. Thanks, victor -- To unsubscribe from this list: send the line unsubscribe linux-usb in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
Re: Linux USB file storage gadget with new UDC
Hi, I did another usbmon capture from the moment usb cable is plugged into the Ubuntu x100e laptop. This time the usbmon does not have -75 error. When the SCSI_READ_10 command request for 4096 bytes of data, and the data is returned by the gadget, usbmon simply shows -108 error. The gadget driver log and usbmon trace are attached. Again, the -108 indicates that the host controller disabled the port. The usbmon trace confirms this. I think the most common reason for disabling a port in this way is that the device tried to transmit a packet across a microframe boundary. The FIFO size in gadget bulk out endpoint 1 is 512 bytes, so i break the 4096 bytes of data into 8 chunks of 512 bytes, before returning them to Ubuntu. I guess it would not be the root cause, won't it? It's hard to say without looking at the signals on the wire. Are you certain the hardware really is sending 512 bytes for each chunk? That's why you need to use a bus analyzer -- to see what's actually going on. I have an important finding. When the problem (SCSI_READ_10 command reads 4096 bytes of data, causing gadget to reset) happens, the PC shows that the gadget is detected as Full-speed device, but gadget reports that it is set to High-speed from: g_file_storage gadget: high-speed config #1 This is printed from do_set_config() in file_storage.c. In UDC driver, it is hardcorded to high speed in UDC driver start function. I changed it to be set depending on hardware value. Now it is: g_file_storage gadget: full-speed config #1 However, in usbmon, the SCSI_READ_10 command still requests for 4096 bytes of data, and this causes gadget to reset. Please see the gadget log, and usbmon trace, and host dmesg log. Thanks, Victor [ 3427.328908] usb 1-5.2: new full speed USB device using ehci_hcd and address 7 [ 3427.421804] usb 1-5.2: not running at top speed; connect to a high speed hub [ 3427.455274] usb-storage 1-5.2:1.0: Quirks match for vid 0525 pid a4a5: 1 [ 3427.457117] scsi3 : usb-storage 1-5.2:1.0 [ 3428.896784] usb 1-5.2: reset full speed USB device using ehci_hcd and address 7 f33fa400 1314593130 C Ci:1:007:0 0 9 = 09022000 010104c0 01 f33fa400 1314593147 S Ci:1:007:0 s 80 06 0200 0020 32 f33fa400 1314593752 C Ci:1:007:0 0 32 = 09022000 010104c0 01090400 00020806 50050705 81024000 00070501 0240 f33fa400 1314593791 S Ci:1:007:0 s 80 06 0300 00ff 255 f33fa400 1314594502 C Ci:1:007:0 0 4 = 04030904 f33fa400 1314594519 S Ci:1:007:0 s 80 06 0302 0409 00ff 255 f33fa400 1314595120 C Ci:1:007:0 0 54 = 36034600 69006c00 65002d00 62006100 63006b00 65006400 20005300 74006f00 f33fa400 1314595918 S Ci:1:007:0 s 80 06 0301 0409 00ff 255 f33fa400 1314596884 C Ci:1:007:0 0 58 = 3a034c00 69006e00 75007800 20003300 2e003400 2e003400 2b002000 77006900 f33fa400 1314597660 S Co:1:007:0 s 00 09 0001 0 f33fa400 1314598122 C Co:1:007:0 0 0 f33fa400 1314599768 S Ci:1:007:0 s 80 06 0304 0409 00ff 255 f33fa400 1314612251 C Ci:1:007:0 0 26 = 1a035300 65006c00 66002d00 70006f00 77006500 72006500 6400 f2e1ee00 1314612435 S Ci:1:007:0 s 80 06 0305 0409 00ff 255 f2e1ee00 1314613115 C Ci:1:007:0 0 26 = 1a034d00 61007300 73002000 53007400 6f007200 61006700 6500 f33a1380 1315254841 S Co:1:003:0 s 23 03 0016 0302 0 f33a1380 1315255168 C Co:1:003:0 0 0 f2e1e400 1315646807 S Ci:1:007:0 s a1 fe 0001 1 f2e1e400 1315647355 C Ci:1:007:0 0 1 = 00 f2e1e400 1315655086 S Bo:1:007:1 -115 31 = 55534243 0100 2400 8612 0024 00 f2e1e400 1315655351 C Bo:1:007:1 0 31 f2ed1a00 1315655414 S Bi:1:007:1 -115 36 f2ed1a00 1315657108 C Bi:1:007:1 0 36 = 0202 1f00 4c696e75 78202020 46696c65 2d53746f 72204761 64676574 f2e1e400 1315657185 S Bi:1:007:1 -115 13 f2e1e400 1315666355 C Bi:1:007:1 0 13 = 55534253 0100 00 f2e1e400 1315708514 S Bo:1:007:1 -115 31 = 55534243 0200 0600 00 f2e1e400 1315708845 C Bo:1:007:1 0 31 f2e1e400 1315708919 S Bi:1:007:1 -115 13 f2e1e400 1315718221 C Bi:1:007:1 0 13 = 55534253 0200 01 f2e1e400 1315718323 S Bo:1:007:1 -115 31 = 55534243 0300 1200 8603 0012 00 f2e1e400 1315718460 C Bo:1:007:1 0 31 f2ed1700 1315718501 S Bi:1:007:1 -115 18 f2ed1700 1315728467 C Bi:1:007:1 0 18 = 7600 000a 2900 f2e1e400 1315728630 S Bi:1:007:1 -115 13 f2e1e400 1315737728 C Bi:1:007:1 0 13 = 55534253 0300 00 f2e1e400 1315738087 S Bo:1:007:1 -115 31 = 55534243 0400 0600 00 f2e1e400 1315738959 C Bo:1:007:1 0 31 f2e1e400 1315739098 S Bi:1:007:1 -115 13 f2e1e400 1315748116 C Bi:1:007:1 0 13 = 55534253 0400 00 f2e1e400 1315748392 S Bo:1:007:1 -115 31 = 55534243 0500 0800 8a25 00 f2e1e400 1315748596 C Bo:1:007:1 0 31 f33faa00 1315748619 S Bi:1:007:1 -115 8 f33faa00 1315758231 C Bi:1:007:1 0 8 =
Re: Linux USB file storage gadget with new UDC
Hi, The usbmon trace shows lots of errors. All those -75 (EOVERFLOW) status codes mean that the gadget sent a packet that was too large, i.e., more than 512 bytes. This happened in all the READ(10) commands except the last one -- none of them succeeded in transferring any data. After the last READ(10) command was sent, the usbmon trace shows that the host's USB port got disabled. Maybe because of the too-long packets. Whatever the reason, that's why the ESHUTDOWN error occurred. The gadget's log does indeed show that the last READ(10) was received twice. The second time is a bug in the UDC driver. No command was sent by the host, so the driver should not have reported that a command was received. Alan Stern I did another usbmon capture from the moment usb cable is plugged into the Ubuntu x100e laptop. This time the usbmon does not have -75 error. When the SCSI_READ_10 command request for 4096 bytes of data, and the data is returned by the gadget, usbmon simply shows -108 error. The gadget driver log and usbmon trace are attached. The FIFO size in gadget bulk out endpoint 1 is 512 bytes, so i break the 4096 bytes of data into 8 chunks of 512 bytes, before returning them to Ubuntu. I guess it would not be the root cause, won't it? thanks, victor # dmesg -c g_file_storage gadget: disconnect or port reset handle_exception begin handle_exception wait until handle_exception old_state 5 g_file_storage gadget: in handle_exception loop g_file_storage gadget: in fsg-running loop g_file_storage gadget: disconnect or port reset handle_exception begin handle_exception wait until handle_exception old_state 5 g_file_storage gadget: in handle_exception loop g_file_storage gadget: in fsg-running loop g_file_storage gadget: ep0-setup, length 8: : 80 06 00 01 00 00 40 00 g_file_storage gadget: get device descriptor ept0 in queue len 0x12, buffer 0xc128f800 ep0_complete g_file_storage gadget: ep0-in, length 18: : 12 01 00 02 00 00 00 40 25 05 a5 a4 33 03 01 02 0010: 00 01 g_file_storage gadget: disconnect or port reset handle_exception begin handle_exception wait until handle_exception old_state 5 g_file_storage gadget: in handle_exception loop g_file_storage gadget: in fsg-running loop USB_RECIP_DEVICE fa is 0x2 exit A g_file_storage gadget: ep0-setup, length 8: : 80 06 00 01 00 00 12 00 g_file_storage gadget: get device descriptor ept0 in queue len 0x12, buffer 0xc128f800 ep0_complete g_file_storage gadget: ep0-in, length 18: : 12 01 00 02 00 00 00 40 25 05 a5 a4 33 03 01 02 0010: 00 01 g_file_storage gadget: ep0-setup, length 8: : 80 06 00 06 00 00 0a 00 g_file_storage gadget: get device qualifier ept0 in queue len 0xa, buffer 0xc128f800 ep0_complete g_file_storage gadget: ep0-in, length 10: : 0a 06 00 02 00 00 00 40 01 00 g_file_storage gadget: ep0-setup, length 8: : 80 06 00 02 00 00 09 00 g_file_storage gadget: get configuration descriptor ept0 in queue len 0x9, buffer 0xc128f800 ep0_complete g_file_storage gadget: ep0-in, length 9: : 09 02 20 00 01 01 04 c0 01 g_file_storage gadget: ep0-setup, length 8: : 80 06 00 02 00 00 20 00 g_file_storage gadget: get configuration descriptor ept0 in queue len 0x20, buffer 0xc128f800 ep0_complete g_file_storage gadget: ep0-in, length 32: : 09 02 20 00 01 01 04 c0 01 09 04 00 00 02 08 06 0010: 50 05 07 05 81 02 00 02 00 07 05 01 02 00 02 01 g_file_storage gadget: ep0-setup, length 8: : 80 06 00 03 00 00 ff 00 g_file_storage gadget: get string descriptor ept0 in queue len 0x4, buffer 0xc128f800 ep0_complete g_file_storage gadget: ep0-in, length 4: : 04 03 09 04 g_file_storage gadget: ep0-setup, length 8: : 80 06 02 03 09 04 ff 00 g_file_storage gadget: get string descriptor ept0 in queue len 0x36, buffer 0xc128f800 ep0_complete g_file_storage gadget: ep0-in, length 54: : 36 03 46 00 69 00 6c 00 65 00 2d 00 62 00 61 00 0010: 63 00 6b 00 65 00 64 00 20 00 53 00 74 00 6f 00 0020: 72 00 61 00 67 00 65 00 20 00 47 00 61 00 64 00 0030: 67 00 65 00 74 00 g_file_storage gadget: ep0-setup, length 8: : 80 06 01 03 09 04 ff 00 g_file_storage gadget: get string descriptor ept0 in queue len 0x3a, buffer 0xc128f800 ep0_complete g_file_storage gadget: ep0-in, length 58: : 3a 03 4c 00 69 00 6e 00 75 00 78 00 20 00 33 00 0010: 2e 00 34 00 2e 00 34 00 2b 00 20 00 77 00 69 00 0020: 74 00 68 00 20 00 6b 00 61 00 67 00 65 00 6e 00 0030: 32 00 5f 00 75 00 73 00 62 00 g_file_storage gadget: ep0-setup, length 8: : 00 09 01 00 00 00 00 00 g_file_storage gadget: set configuration handle_exception begin handle_exception wait until handle_exception old_state 4 g_file_storage gadget: set interface 0 g_file_storage gadget: high-speed config #1 g_file_storage gadget: ep0-setup, length 8: : 80 06 04 03 09 04 ff 00 g_file_storage gadget: get string descriptor ept0 in queue len 0x1a, buffer 0xc128f800 ep0_complete
Re: Linux USB file storage gadget with new UDC
Hi, The hardware handles Set Address request, and i can see the address of the USB gadget being shown in Windows host. Here i attach the gadget driver log for the Device Descriptor Test - Addressed State. The test just failed after Get Configuration request. I can't tell what's wrong. You will have to use a USB bus analyzer. Ok. Today i tested the same mass storage gadget driver on Lenovo x100e Ubuntu. There is a strange problem. After SCSI_READ_10 command data is returned to the Ubuntu host. The gadget driver says: g_file_storage gadget: reset config g_file_storage gadget: reset interface Then the same process to get descriptors and receive SCSI commands are repeated. Is the SCSI_READ_10 command or something else causing the problem? Please see the attached gadget driver log. Thanks, Victor [start_transfer] 0 0 ept1 out queue len 0x200, buffer 0xc134 before kagen2_ep_queue after kagen2_ep_queue kagen2_ep_queue 31 512 31 [kagen2_ep_queue] 43425355 12 g_file_storage gadget: bulk-out, length 31: : 55 53 42 43 12 00 00 00 00 10 00 00 80 00 0a 28 0010: 00 00 00 00 00 00 00 08 00 00 00 00 00 00 00 g_file_storage gadget: SCSI command: READ(10); Dc=10, Di=4096; Hc=10, Hi=4096 g_file_storage gadget-lun0: file read 4096 @ 0 - 4096 [start_transfer] 0 0 ept1 in queue len 0x1000, buffer 0xc134 len_num 4096, iter_num 0 0: 0x0 4: 0x0 8: 0x0 c: 0x0 len_num 3584, iter_num 1 0: 0x6d903ceb 4: 0x736f646b 8: 0x7366 c: 0x10402 len_num 3072, iter_num 2 0: 0xf8 4: 0xfff0 8: 0x0 c: 0x0 len_num 2560, iter_num 3 0: 0x0 4: 0x0 8: 0x0 c: 0x0 len_num 2048, iter_num 4 0: 0xf8 4: 0xfff0 8: 0x0 c: 0x0 len_num 1536, iter_num 5 0: 0x0 4: 0x0 8: 0x0 c: 0x0 len_num 1024, iter_num 6 0: 0x6f007442 4: 0x7000 8: 0xf00 c: 0xc100 len_num 512, iter_num 7 0: 0x0 4: 0x0 8: 0x0 c: 0x0 bulk_in_complete -- 0, 4096/4096 g_file_storage gadget: before calling send_status g_file_storage gadget: bulk-in, length 13: : 55 53 42 53 12 00 00 00 00 00 00 00 00 [start_transfer] 53425355 12 ept1 in queue len 0xd, buffer 0xc0c5c000 0: 0x53425355 4: 0x12 8: 0x0 bulk_in_complete -- 0, 13/13 [start_transfer] 0 0 ept1 out queue len 0x200, buffer 0xc134 before kagen2_ep_queue g_file_storage gadget: disconnect or port reset after kagen2_ep_queue kagen2_ep_queue 31 512 31 [kagen2_ep_queue] 43425355 12 g_file_storage gadget: bulk-out, length 31: : 55 53 42 43 12 00 00 00 00 10 00 00 80 00 0a 28 0010: 00 00 00 00 00 00 00 08 00 00 00 00 00 00 00 g_file_storage gadget: SCSI command: READ(10); Dc=10, Di=4096; Hc=10, Hi=4096 g_file_storage gadget-lun0: file read 4096 @ 0 - 4096 g_file_storage gadget: after calling do_scsi_command handle_exception begin handle_exception wait until handle_exception old_state 5 g_file_storage gadget: reset config g_file_storage gadget: reset interface g_file_storage gadget: in handle_exception loop g_file_storage gadget: in fsg-running loop g_file_storage gadget: in fsg-running loop g_file_storage gadget: ep0-setup, length 8: : 80 06 00 01 00 00 40 00 g_file_storage gadget: get device descriptor ept0 in queue len 0x12, buffer 0xc128b800 ep0_complete g_file_storage gadget: ep0-in, length 18: : 12 01 00 02 00 00 00 40 25 05 a5 a4 33 03 01 02 0010: 00 01 g_file_storage gadget: disconnect or port reset handle_exception begin handle_exception wait until handle_exception old_state 5 g_file_storage gadget: in handle_exception loop g_file_storage gadget: in fsg-running loop USB_RECIP_DEVICE function address is 0x5d exit A g_file_storage gadget: ep0-setup, length 8: : 80 06 00 01 00 00 12 00 g_file_storage gadget: get device descriptor ept0 in queue len 0x12, buffer 0xc128b800 ep0_complete g_file_storage gadget: ep0-in, length 18: : 12 01 00 02 00 00 00 40 25 05 a5 a4 33 03 01 02 0010: 00 01 g_file_storage gadget: ep0-setup, length 8: : 80 06 00 06 00 00 0a 00 g_file_storage gadget: get device qualifier ept0 in queue len 0xa, buffer 0xc128b800 ep0_complete g_file_storage gadget: ep0-in, length 10: : 0a 06 00 02 00 00 00 40 01 00 g_file_storage gadget: ep0-setup, length 8: : 80 06 00 02 00 00 09 00 g_file_storage gadget: get configuration descriptor ept0 in queue len 0x9, buffer 0xc128b800 ep0_complete g_file_storage gadget: ep0-in, length 9: : 09 02 20 00 01 01 04 c0 01 g_file_storage gadget: ep0-setup, length 8: : 80 06 00 02 00 00 20 00 g_file_storage gadget: get configuration descriptor ept0 in queue len 0x20, buffer 0xc128b800 ep0_complete g_file_storage gadget: ep0-in, length 32: : 09 02 20 00 01 01 04 c0 01 09 04 00 00 02 08 06 0010: 50 05 07 05 81 02 00 02 00 07 05 01 02 00 02 01 g_file_storage gadget: ep0-setup, length 8: : 80 06 00 03 00 00 ff 00 g_file_storage gadget: get string descriptor ept0 in queue len 0x4, buffer 0xc128b800 ep0_complete g_file_storage gadget: ep0-in, length 4: : 04 03 09 04 g_file_storage gadget: ep0-setup,
Re: Linux USB file storage gadget with new UDC
Hi, Another possibility is to set up a virtual Windows system inside your Linux host. Then try running the USB CV program on the virtual machine, and use usbmon on the host system to capture the USB traffic. I don't know if that will work, but it might. Thanks. i will find a way to setup the virtual Windows inside Linux host. Ok. Today i tested the same mass storage gadget driver on Lenovo x100e Ubuntu. There is a strange problem. After SCSI_READ_10 command data is returned to the Ubuntu host. The gadget driver says: g_file_storage gadget: reset config g_file_storage gadget: reset interface Then the same process to get descriptors and receive SCSI commands are repeated. Is the SCSI_READ_10 command or something else causing the problem? Please see the attached gadget driver log. Perhaps you will recognize this answer (I have sent it several times before): I can't tell what is happening without seeing _both_ the log file on the gadget _and_ the usbmon trace on the host. Alan Stern Yes, the matching gadget log and usbmon trace are attached in this email. From the usbmon trace, the error (-108) is ESHUTDOWN from SCSI_READ_10 command. From the gadget log, the last SCSI_READ_10 command is received twice. First time it is ok, second time it causes some problem. Which side could cause the ESHUTDOWN error? Thanks, victor [start_transfer] 43425355 35 ept1 out queue len 0x200, buffer 0xc0c44000 before kagen2_ep_queue after kagen2_ep_queue kagen2_ep_queue 31 512 31 [kagen2_ep_queue] 43425355 36 g_file_storage gadget: bulk-out, length 31: : 55 53 42 43 36 00 00 00 12 00 00 00 80 00 06 03 0010: 00 00 00 12 00 00 00 00 00 00 00 00 00 00 00 g_file_storage gadget: SCSI command: REQUEST SENSE; Dc=6, Di=18; Hc=6, Hi=18 g_file_storage gadget: bulk-in, length 18: : 70 00 06 00 00 00 00 0a 00 00 00 00 29 00 00 00 0010: 00 00 [start_transfer] 60070 a00 ept1 in queue len 0x12, buffer 0xc0c44000 0: 0x60070 4: 0xa00 8: 0x0 c: 0x29 bulk_in_complete -- 0, 18/18 g_file_storage gadget: before calling send_status g_file_storage gadget: bulk-in, length 13: : 55 53 42 53 36 00 00 00 00 00 00 00 00 [start_transfer] 53425355 36 ept1 in queue len 0xd, buffer 0xc1338000 0: 0x53425355 4: 0x36 8: 0x0 bulk_in_complete -- 0, 13/13 [start_transfer] 60070 a00 ept1 out queue len 0x200, buffer 0xc0c44000 before kagen2_ep_queue after kagen2_ep_queue kagen2_ep_queue 31 512 31 [kagen2_ep_queue] 43425355 37 g_file_storage gadget: bulk-out, length 31: : 55 53 42 43 37 00 00 00 00 10 00 00 80 00 0a 28 0010: 00 00 00 00 18 00 00 08 00 00 00 00 00 00 00 g_file_storage gadget: SCSI command: READ(10); Dc=10, Di=4096; Hc=10, Hi=4096 g_file_storage gadget-lun0: file read 4096 @ 12288 - 4096 [start_transfer] 0 0 ept1 in queue len 0x1000, buffer 0xc0c44000 len_num 4096, iter_num 0 0: 0x0 4: 0x0 8: 0x0 c: 0x0 len_num 3584, iter_num 1 0: 0x0 4: 0x0 8: 0x0 c: 0x0 len_num 3072, iter_num 2 0: 0x0 4: 0x0 8: 0x0 c: 0x0 len_num 2560, iter_num 3 0: 0x0 4: 0x0 8: 0x0 c: 0x0 len_num 2048, iter_num 4 0: 0x0 4: 0x0 8: 0x0 c: 0x0 len_num 1536, iter_num 5 0: 0x0 4: 0x0 8: 0x0 c: 0x0 len_num 1024, iter_num 6 0: 0x0 4: 0x0 8: 0x0 c: 0x0 len_num 512, iter_num 7 0: 0x0 4: 0x0 8: 0x0 c: 0x0 bulk_in_complete -- 0, 4096/4096 g_file_storage gadget: before calling send_status g_file_storage gadget: bulk-in, length 13: : 55 53 42 53 37 00 00 00 00 00 00 00 00 [start_transfer] 53425355 37 ept1 in queue len 0xd, buffer 0xc1338000 0: 0x53425355 4: 0x37 8: 0x0 bulk_in_complete -- 0, 13/13 [start_transfer] 0 0 ept1 out queue len 0x200, buffer 0xc0c44000 before kagen2_ep_queue after kagen2_ep_queue kagen2_ep_queue 31 512 31 [kagen2_ep_queue] 43425355 38 g_file_storage gadget: bulk-out, length 31: : 55 53 42 43 38 00 00 00 00 10 00 00 80 00 0a 28 0010: 00 00 00 00 00 00 00 08 00 00 00 00 00 00 00 g_file_storage gadget: SCSI command: READ(10); Dc=10, Di=4096; Hc=10, Hi=4096 g_file_storage gadget-lun0: file read 4096 @ 0 - 4096 [start_transfer] 0 0 ept1 in queue len 0x1000, buffer 0xc0c44000 len_num 4096, iter_num 0 0: 0x0 4: 0x0 8: 0x0 c: 0x0 len_num 3584, iter_num 1 0: 0x6d903ceb 4: 0x736f646b 8: 0x7366 c: 0x10402 len_num 3072, iter_num 2 0: 0xf8 4: 0xfff0 8: 0x0 c: 0x0 len_num 2560, iter_num 3 0: 0x0 4: 0x0 8: 0x0 c: 0x0 len_num 2048, iter_num 4 0: 0xf8 4: 0xfff0 8: 0x0 c: 0x0 len_num 1536, iter_num 5 0: 0x0 4: 0x0 8: 0x0 c: 0x0 len_num 1024, iter_num 6 0: 0x6f007442 4: 0x7000 8: 0xf00 c: 0xc100 len_num 512, iter_num 7 0: 0x0 4: 0x0 8: 0x0 c: 0x0 bulk_in_complete -- 0, 4096/4096 g_file_storage gadget: before calling send_status g_file_storage gadget: bulk-in, length 13: : 55 53 42 53 38 00 00 00 00 00 00 00 00 [start_transfer] 53425355 38 ept1 in queue len 0xd, buffer 0xc1338000 0: 0x53425355 4: 0x38 8: 0x0 bulk_in_complete -- 0, 13/13 [start_transfer] 0 0 ept1 out queue len 0x200, buffer 0xc0c44000
Re: Linux USB file storage gadget with new UDC
Hi, Thanks a lot. i understand this part now. Do you notice the Set Address request is not seen by the gadget driver? The Set Address request is handled by the hardware. Could it be the root cause? As gadget driver may expect the address information from the host, and for now UDC driver just ignore the Set Address request ? That may very well be related to the problem. Gadget drivers expect UDC drivers or UDC hardware to handle Set-Address requests automatically. If your UDC or driver doesn't handle them, it could cause a test to fail. The hardware handles Set Address request, and i can see the address of the USB gadget being shown in Windows host. Here i attach the gadget driver log for the Device Descriptor Test - Addressed State. The test just failed after Get Configuration request. Another question, in ep0_complete(): if (req-status == 0 req-context) ((fsg_routine_t) (req-context))(fsg); Is req-context pointing to a function in UDC driver? Thanks, victor # dmesg g_file_storage gadget: ep0-setup, length 8: : 80 06 00 01 00 00 12 00 g_file_storage gadget: get device descriptor ept0 in queue len 0x12, buffer 0xc1289800 ep0_complete g_file_storage gadget: ep0-in, length 18: : 12 01 00 02 00 00 00 40 25 05 a5 a4 33 03 01 02 0010: 00 01 g_file_storage gadget: ep0-setup, length 8: : 80 06 00 06 00 00 0a 00 g_file_storage gadget: get device qualifier ept0 in queue len 0xa, buffer 0xc1289800 ep0_complete g_file_storage gadget: ep0-in, length 10: : 0a 06 00 02 00 00 00 40 01 00 g_file_storage gadget: ep0-setup, length 8: : 80 06 00 02 00 00 09 00 g_file_storage gadget: get configuration descriptor ept0 in queue len 0x9, buffer 0xc1289800 ep0_complete g_file_storage gadget: ep0-in, length 9: : 09 02 20 00 01 01 04 c0 01 g_file_storage gadget: ep0-setup, length 8: : 80 08 00 00 00 00 01 00 g_file_storage gadget: get configuration ept0 in queue len 0x1, buffer 0xc1289800 ep0_complete g_file_storage gadget: ep0-in, length 1: : 01 g_file_storage gadget: ep0-setup, length 8: : 80 08 00 00 00 00 01 00 g_file_storage gadget: get configuration ept0 in queue len 0x1, buffer 0xc1289800 ep0_complete g_file_storage gadget: ep0-in, length 1: : 01 #
Re: Linux USB file storage gadget with new UDC
Hi, The CV log is attached (Dev_desc_test-Address state.html). Is it helpful? It doesn't help very much. Can you get a more verbose log, one that lists all the transfers? It looks like the problem could be that the host and the gadget don't agree on what packets have been sent and received. If that's true, you may need to use a USB bus analyzer to diagnose it. Unfortunately, that USB 2.0 command verifier is not able to generate a more verbose log. The g_file_storage gadget: in handle_exception loop is from the DBG that i added in fsg_main_thread(). I also attach an updated gadget log file, which corresponds to the CV log. I cannot figure out this part of the code about handle_exception(). Is a signal received and handle_exception() is supposed to perform some action? if (exception_in_progress(fsg) || signal_pending(current)) { handle_exception(fsg); DBG(fsg, in handle_exception loop\n); continue; } Okay, now I understand. The in handle_exception loop line in the log is from an exception that happened earlier, before the Get-Config-Descriptor request. The exception was caused by the preceding request, Set-Config: The USB_REQ_SET_CONFIGURATION case in standard_setup_req() calls raise_exception(). The handle_exception() routine then does the real work of changing the configuration, by calling do_set_config(). The Get-Config-Descriptor request just happened to arrive before your DBG line was executed. Thanks a lot. i understand this part now. Do you notice the Set Address request is not seen by the gadget driver? The Set Address request is handled by the hardware. Could it be the root cause? As gadget driver may expect the address information from the host, and for now UDC driver just ignore the Set Address request ? victor -- To unsubscribe from this list: send the line unsubscribe linux-usb in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
Re: Linux USB file storage gadget with new UDC
Hi, When i run USB 2.0 Command Verifier on file gadget and UDC driver, an error in Command Verifier says Device must support being set to Addressed/Configured state. Does it mean the gadget cannot support putting device in addressed state or configured state, as in supporting the Set Address and Set Configuration requests? I don't know what it means. The gadget _does_ support being set to the Addressed and Configured states. If it didn't support these things, you would not have been able to test it at all. Alan Stern The gadget log when Command Verifier says Device must support being set to Addressed/Configured state is attached. The log shows get device descriptor, get configuration descriptor, and set configuration requests are received. I see nothing wrong in gadget log. Does the log indicate any problem that corresponds to the error message in Command Verifier? Thanks, victor # dmesg g_file_storage gadget: disconnect or port reset after kagen2_ep_queue kagen2_ep_queue 31 512 31 [kagen2_ep_queue] 43425355 8a47aaf8 g_file_storage gadget: bulk-out, length 31: : 55 53 42 43 f8 aa 47 8a 00 00 00 00 00 00 0a 35 0010: 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 g_file_storage gadget: SCSI command: SYNCHRONIZE CACHE; Dc=10, Dn=0; Hc=10, Hn=0 attention condition g_file_storage gadget: after calling do_scsi_command g_file_storage gadget: reset config g_file_storage gadget: reset interface g_file_storage gadget: in handle_exception loop g_file_storage gadget: in fsg-running loop g_file_storage gadget: in fsg-running loop g_file_storage gadget: disconnect or port reset g_file_storage gadget: in handle_exception loop g_file_storage gadget: in fsg-running loop g_file_storage gadget: ep0-setup, length 8: : 80 06 00 01 00 00 12 00 g_file_storage gadget: get device descriptor ept0 in queue len 0x12, buffer 0xc1289800 g_file_storage gadget: ep0-in, length 18: : 12 01 00 02 00 00 00 40 25 05 a5 a4 33 03 01 02 0010: 00 01 USB_RECIP_DEVICE g_file_storage gadget: ep0-setup, length 8: : 80 06 00 01 00 00 12 00 g_file_storage gadget: get device descriptor ept0 in queue len 0x12, buffer 0xc1289800 g_file_storage gadget: ep0-in, length 18: : 12 01 00 02 00 00 00 40 25 05 a5 a4 33 03 01 02 0010: 00 01 g_file_storage gadget: ep0-setup, length 8: : 80 06 00 02 00 00 09 00 g_file_storage gadget: get configuration descriptor ept0 in queue len 0x9, buffer 0xc1289800 g_file_storage gadget: ep0-in, length 9: : 09 02 20 00 01 01 04 c0 01 g_file_storage gadget: ep0-setup, length 8: : 00 09 01 00 00 00 00 00 g_file_storage gadget: set configuration g_file_storage gadget: set interface 0 g_file_storage gadget: high-speed config #1 g_file_storage gadget: ep0-setup, length 8: : 80 06 00 02 00 00 09 00 g_file_storage gadget: get configuration descriptor ept0 in queue len 0x9, buffer 0xc1289800 g_file_storage gadget: ep0-in, length 9: : 09 02 20 00 01 01 04 c0 01 g_file_storage gadget: ep0-setup, length 8: : 80 06 00 02 00 00 20 00 g_file_storage gadget: get configuration descriptor ept0 in queue len 0x20, buffer 0xc1289800 g_file_storage gadget: ep0-in, length 32: : 09 02 20 00 01 01 04 c0 01 09 04 00 00 02 08 06 0010: 50 05 07 05 81 02 00 02 00 07 05 01 02 00 02 01 g_file_storage gadget: in handle_exception loop [start_transfer] 43425355 8a47aaf8 ept1 out queue len 0x200, buffer 0xc0c44000 before kagen2_ep_queue g_file_storage gadget: ep0-setup, length 8: : 80 06 00 01 00 00 12 00 g_file_storage gadget: get device descriptor ept0 in queue len 0x12, buffer 0xc1289800 g_file_storage gadget: ep0-in, length 18: : 12 01 00 02 00 00 00 40 25 05 a5 a4 33 03 01 02 0010: 00 01 g_file_storage gadget: ep0-setup, length 8: : 80 06 00 06 00 00 0a 00 g_file_storage gadget: get device qualifier ept0 in queue len 0xa, buffer 0xc1289800 g_file_storage gadget: ep0-in, length 10: : 0a 06 00 02 00 00 00 40 01 00 g_file_storage gadget: ep0-setup, length 8: : 80 06 00 02 00 00 09 00 g_file_storage gadget: get configuration descriptor ept0 in queue len 0x9, buffer 0xc1289800 g_file_storage gadget: ep0-in, length 9: : 09 02 20 00 01 01 04 c0 01 g_file_storage gadget: ep0-setup, length 8: : 80 08 00 00 00 00 01 00 g_file_storage gadget: get configuration ept0 in queue len 0x1, buffer 0xc1289800 g_file_storage gadget: ep0-in, length 1: : 01 g_file_storage gadget: ep0-setup, length 8: : 80 08 00 00 00 00 01 00 g_file_storage gadget: get configuration ept0 in queue len 0x1, buffer 0xc1289800 g_file_storage gadget: ep0-in, length 1: : 01 #
Re: Linux USB file storage gadget with new UDC
Hi, On Thu, May 30, 2013 at 10:44 PM, Alan Stern st...@rowland.harvard.edu wrote: On Thu, 30 May 2013, victor yeo wrote: I tested the g_zero with USB 2.0 Command Verifier. After the Command Verifier is run, the UDC gadget driver queue function is continuously being called, and the linux command prompt is frozen. Please see the attached UDC driver log. It looks like endpoint 1 in direction is called by USB 2.0 Command Verifier continuously. Is this weird? I don't know. You can't tell what's going on just by looking at the gadget. You have to know what the host is doing as well. Alan Stern When i run USB 2.0 Command Verifier on file gadget and UDC driver, an error in Command Verifier says Device must support being set to Addressed/Configured state. Does it mean the gadget cannot support putting device in addressed state or configured state, as in supporting the Set Address and Set Configuration requests? Thanks, Victor -- To unsubscribe from this list: send the line unsubscribe linux-usb in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
Re: Linux USB file storage gadget with new UDC
Hi, Ok. What other gadget driver can i test with UDC driver? Is it the mass storage driver (mass_storage.c)? That is essentially the same as g_file_storage. But there are lots of others. You should start with g_zero and run the testusb suite. See http://www.linux-usb.org/gadget/ and http://www.linux-usb.org/usbtest/ for more information. Those web pages are pretty old and somewhat out of date, but they still have useful stuff. I tested the g_zero with USB 2.0 Command Verifier. After the Command Verifier is run, the UDC gadget driver queue function is continuously being called, and the linux command prompt is frozen. Please see the attached UDC driver log. It looks like endpoint 1 in direction is called by USB 2.0 Command Verifier continuously. Is this weird? thanks, victor # insmod kagen2_udc.ko kagen2_init kagen2_plat_probe 1 kagen2_plat_probe 5 kagen2_plat_probe 6, 0xc2886000 0x1000 read pclk scu 7 irqmask ffbd 7fff val is 0x0 val is 0x8 check USB_OTGST 0x51000801 check USB_OTGIRQ 0x51000810 check USB_IRQINIT 0x70007 check USB_OTGFSM 0xa1d191f check USB_OTGCTRL 0x51300801 kagen2_plat_probe 8 register irq 32 kagen2_init 0 # insmod g_zero.ko bind epname ep1 epname ep1 epname ep1 epname ep1 gadget: Gadget Zero, version: Cinco de Mayo 2008 gadget: zero ready usb_gadget_udc_start 0xbf0386b8 0xbf0364c8 kagen2_start 0xbf0386b8 0xbf0364c8 0xc12d2cf0 0xbf030eb0 usb_gadget_connect # ept0 in queue len 0x12, buffer 0xc12d3000 USB_RECIP_DEVICE exit A ept0 in queue len 0x12, buffer 0xc12d3000 ept0 in queue len 0x9, buffer 0xc12d3000 ept0 in queue len 0x4, buffer 0xc12d3000 ept0 in queue len 0x42, buffer 0xc12d3000 ept0 in queue len 0x20, buffer 0xc12d3000 ept0 in queue len 0x4, buffer 0xc12d3000 ept0 in queue len 0x18, buffer 0xc12d3000 ept0 in queue len 0x4, buffer 0xc12d3000 ept0 in queue len 0x18, buffer 0xc12d3000 ept0 in queue len 0x20, buffer 0xc12d3000 ept0 in queue len 0xa, buffer 0xc12d3000 ept0 in queue len 0x9, buffer 0xc12d3000 ept0 in queue len 0x20, buffer 0xc12d3000 ept0 in queue len 0x4, buffer 0xc12d3000 ept0 in queue len 0x3a, buffer 0xc12d3000 ept0 in queue len 0x18, buffer 0xc12d3000 ept0 in queue len 0x42, buffer 0xc12d3000 ept0 in queue len 0x2a, buffer 0xc12d3000 ept0 in queue len 0x2a, buffer 0xc12d3000 ept0 in queue len 0x12, buffer 0xc12d3000 USB_RECIP_DEVICE exit A ept0 in queue len 0x12, buffer 0xc12d3000 ept0 in queue len 0x9, buffer 0xc12d3000 zero gadget: high-speed config #3: source/sink ept1 in queue len 0x1000, buffer 0xc180d000 len_num 4096, iter_num 0 len_num 3584, iter_num 1 len_num 3072, iter_num 2 len_num 2560, iter_num 3 len_num 2048, iter_num 4 len_num 1536, iter_num 5 len_num 1024, iter_num 6 len_num 512, iter_num 7 ept1 in queue len 0x1000, buffer 0xc180d000 len_num 4096, iter_num 0 len_num 3584, iter_num 1 len_num 3072, iter_num 2 len_num 2560, iter_num 3 len_num 2048, iter_num 4 len_num 1536, iter_num 5 len_num 1024, iter_num 6 len_num 512, iter_num 7 ept1 in queue len 0x1000, buffer 0xc180d000 len_num 4096, iter_num 0 len_num 3584, iter_num 1 len_num 3072, iter_num 2 len_num 2560, iter_num 3 len_num 2048, iter_num 4 len_num 1536, iter_num 5 len_num 1024, iter_num 6 len_num 512, iter_num 7 ept1 in queue len 0x1000, buffer 0xc180d000 len_num 4096, iter_num 0 len_num 3584, iter_num 1 len_num 3072, iter_num 2 len_num 2560, iter_num 3 len_num 2048, iter_num 4 len_num 1536, iter_num 5 len_num 1024, iter_num 6 len_num 512, iter_num 7 ept1 in queue len 0x1000, buffer 0xc180d000 len_num 4096, iter_num 0 len_num 3584, iter_num 1 len_num 3072, iter_num 2 len_num 2560, iter_num 3 len_num 2048, iter_num 4 len_num 1536, iter_num 5 len_num 1024, iter_num 6 len_num 512, iter_num 7 ept1 in queue len 0x1000, buffer 0xc180d000 len_num 4096, iter_num 0 len_num 3584, iter_num 1 len_num 3072, iter_num 2 len_num 2560, iter_num 3 len_num 2048, iter_num 4 len_num 1536, iter_num 5 len_num 1024, iter_num 6 len_num 512, iter_num 7 ept1 in queue len 0x1000, buffer 0xc180d000 len_num 4096, iter_num 0 len_num 3584, iter_num 1 len_num 3072, iter_num 2 len_num 2560, iter_num 3 len_num 2048, iter_num 4 len_num 1536, iter_num 5 len_num 1024, iter_num 6 len_num 512, iter_num 7 ept1 in queue len 0x1000, buffer 0xc180d000 len_num 4096, iter_num 0 len_num 3584, iter_num 1 len_num 3072, iter_num 2 len_num 2560, iter_num 3 len_num 2048, iter_num 4 len_num 1536, iter_num 5 len_num 1024, iter_num 6 len_num 512, iter_num 7 ept1 in queue len 0x1000, buffer 0xc180d000 len_num 4096, iter_num 0 len_num 3584, iter_num 1 len_num 3072, iter_num 2 len_num 2560, iter_num 3 len_num 2048, iter_num 4 len_num 1536, iter_num 5 len_num 1024, iter_num 6 len_num 512, iter_num 7
Re: Linux USB file storage gadget with new UDC
Hi, Is it possible to contribute the code to Linux community? Yes. But first you should test it with other gadget drivers, not just g_file_storage. Ok. What other gadget driver can i test with UDC driver? Is it the mass storage driver (mass_storage.c)? Has the g_file_storage passed the USB 2.0 Command Verifier test? On the other hand, i run the USB 2.0 command verifier to test the gadget, the gadget crashes at BOS descriptor test. I think the gadget is not able to handle BOS descriptor, is the gadget driver setup function returning negative error code for BOS descriptor? The crash dump you attached contained this line: PC is at kagen2_irq+0x290/0x3bc [kagen2_udc] This means the crash occurred inside the UDC driver, not the gadget driver. Yes, the problem was solved just now. Thanks, victor -- To unsubscribe from this list: send the line unsubscribe linux-usb in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
Re: Linux USB file storage gadget with new UDC
Hi, Yes, it is silly. The hardware interrupt is not being generated for every SCSI command received, so the driver has to poll. I put the polling code in a thread, and this dilemma is fixed. Are you sure about this? If it is correct, you should _fix_ the interrupt problem. Don't try to work around it by creating a new thread. Figure out why there isn't an interrupt. Does your driver forget to set an interrupt-enable bit? I still observe the SCSI_WRITE_10 command time out sometimes. When time out happens, the gadget log shows: g_file_storage gadget: invalid CBW: len 512 sig 0x6f007442 g_file_storage gadget: bulk-in set wedge Is it because the gadget expects 31 byte command, but 512 byte data is received instead? No. It is because kagen2_ep_queue returned _before_ a new command was received, probably as a result of your polling thread. Since there was no new command, the data in the buffer was wrong. The full UDC/gadget log is attached. Hope it is useful. If not, i will add in more printk statements. You can see the problem in the log: g_file_storage gadget: bulk-in, length 13: : 55 53 42 53 50 00 00 00 00 00 00 00 00 [start_transfer] 53425355 50 ept1 in queue len 0xd, buffer 0xc0c3c000 0: 0x53425355 4: 0x50 8: 0x0 bulk_in_complete -- 0, 13/13 That was the end of the previous command. Now the gadget waits for a new command to arrive. [start_transfer] 6f007442 7000 ept1 out queue len 0x200, buffer 0xc1338000 before kagen2_ep_queue after kagen2_ep_queue kagen2_ep_queue 512 512 512 [kagen2_ep_queue] 6f007442 7000 kagen2_ep_queue returned but there was no interrupt. This means no new data was received, so the old data is still in the buffer. g_file_storage gadget: bulk_out_complete -- 0, 512/31 g_file_storage gadget: invalid CBW: len 512 sig 0x6f007442 g_file_storage gadget: bulk-in set wedge That 0x6f007442 is the old data from the previous command, as you can see from the log messages (it is the same data that was present when kagen2_ep_queue was called). Now the UDC driver is working on both Linux and Windows host, meaning the read/write operation is ok. I still use the polling method, because waiting for interrupt is not reliable. Is it possible to contribute the code to Linux community? On the other hand, i run the USB 2.0 command verifier to test the gadget, the gadget crashes at BOS descriptor test. I think the gadget is not able to handle BOS descriptor, is the gadget driver setup function returning negative error code for BOS descriptor? Thanks, victor g_file_storage gadget: high-speed config #1 Unable to handle kernel NULL pointer dereference at virtual address pgd = c0204000 [] *pgd= Internal error: Oops - BUG: 817 [#1] PREEMPT ARM Modules linked in: g_file_storage kagen2_udc ath6kl_sdio ath6kl_core ka2000_sdio ka2000_sdhc CPU: 0Not tainted (3.4.4+ #43) PC is at kagen2_irq+0x290/0x3bc [kagen2_udc] LR is at handle_irq_event_percpu+0x30/0x178 pc : [bf02f704]lr : [c02496d0]psr: 6093 sp : c132de98 ip : 0002 fp : c132debc r10: r9 : r8 : r7 : 0020 r6 : 0002 r5 : 0201 r4 : c12a8c00 r3 : r2 : 0001 r1 : c12a8d1c r0 : Flags: nZCv IRQs off FIQs on Mode SVC_32 ISA ARM Segment kernel Control: 0005717f Table: 0130c000 DAC: 0017 Process chkbusy_t (pid: 121, stack limit = 0xc132c270) Stack: (0xc132de98 to 0xc132e000) de80: 0080 0002 dea0: c12b9840 c049cf70 0020 c132dee4 c132dec0 c02496d0 bf02f484 dec0: c049cf70 c132c000 c12b9840 c132df94 c132df04 c132dee8 dee0: c0249878 c02496b0 f5006000 c049cf70 f5006000 c132df1c c132df08 df00: c024bd38 c0249828 c024bc24 0020 c132df34 c132df20 c02490e0 c024bc34 df20: 0040 0020 c132df4c c132df38 c0209c2c c02490c8 bf02f8c0 0013 df40: c132df5c c132df50 c0208410 c0209bd4 c132dfbc c132df60 c0208f14 c0208410 df60: 4000 0288001f c2886000 c12a8c00 c12a8c00 bf02f894 0013 df80: c132dfbc c132c000 c132dfa8 4001 bf02f8c0 dfa0: 0013 c128dd58 c132dff4 c132dfc0 c022f8f4 bf02f8a4 dfc0: c128dd58 c12a8c00 c132dfd0 c132dfd0 c128dd58 dfe0: c022f860 c02191c8 c132dff8 c02191c8 c022f870 08f0 0402 Backtrace: [bf02f474] (kagen2_irq+0x0/0x3bc [kagen2_udc]) from [c02496d0] (handle_irq_event_percpu+0x30/0x178) r7:0020 r6: r5:c049cf70 r4:c12b9840 [c02496a0] (handle_irq_event_percpu+0x0/0x178) from [c0249878] (handle_irq_event+0x60/0x7c) [c0249818] (handle_irq_event+0x0/0x7c) from [c024bd38] (handle_edge_irq+0x114/0x16c) r6:f5006000 r5: r4:c049cf70 r3:f5006000 [c024bc24] (handle_edge_irq+0x0/0x16c) from [c02490e0] (generic_handle_irq+0x28/0x38) r4:0020 r3:c024bc24 [c02490b8] (generic_handle_irq+0x0/0x38) from [c0209c2c] (handle_IRQ+0x68/0x8c)
Re: Linux USB file storage gadget with new UDC
Hi, I am able to solve the SCSI command timeout problem by adding a code to check the hardware register busy bit continuously, in kagen2_ep_queue(): do { read_hardware_register_busy_bit } while (hardware_is_busy) This is silly. Drivers shouldn't poll in this way. That's what interrupts are for. however, it causes the linux prompt to be non-responsive because the checking hardware register code is run continuously. If i add a schedule() to the do-while loop, the kagen2_ep_queue() will not be continued. How to go about fixing this dilemma? I can't say much more without seeing the code. However, you should not need to wait for the hardware to do something -- instead the interrupt handler routine should be called when the hardware is finished. Yes, it is silly. The hardware interrupt is not being generated for every SCSI command received, so the driver has to poll. I put the polling code in a thread, and this dilemma is fixed. I still observe the SCSI_WRITE_10 command time out sometimes. When time out happens, the gadget log shows: g_file_storage gadget: invalid CBW: len 512 sig 0x6f007442 g_file_storage gadget: bulk-in set wedge Is it because the gadget expects 31 byte command, but 512 byte data is received instead? The full UDC/gadget log is attached. Hope it is useful. If not, i will add in more printk statements. Thanks, victor EP1 OUT IRQ 0x28 [start_transfer] f8 6005fff0 ept1 out queue len 0x200, buffer 0xc1338000 before kagen2_ep_queue after kagen2_ep_queue kagen2_ep_queue 31 512 31 [kagen2_ep_queue] 43425355 4d g_file_storage gadget: bulk-out, length 31: : 55 53 42 43 4d 00 00 00 00 02 00 00 00 00 0a 2a 0010: 00 00 00 00 04 00 00 01 00 00 00 00 00 00 00 EP1 OUT IRQ 0x28 g_file_storage gadget: SCSI command: WRITE(10); Dc=10, Do=512; Hc=10, Ho=512 [start_transfer] 43425355 4d ept1 out queue len 0x200, buffer 0xc1338000 before kagen2_ep_queue after kagen2_ep_queue kagen2_ep_queue 512 512 512 [kagen2_ep_queue] f8 fff0 g_file_storage gadget-lun0: file write 512 @ 2048 - 512 g_file_storage gadget: before calling send_status g_file_storage gadget: bulk-in, length 13: : 55 53 42 53 4d 00 00 00 00 00 00 00 00 [start_transfer] 53425355 4d ept1 in queue len 0xd, buffer 0xc0c3c000 0: 0x53425355 4: 0x4d 8: 0x0 bulk_in_complete -- 0, 13/13 EP1 OUT IRQ 0x28 [start_transfer] f8 fff0 ept1 out queue len 0x200, buffer 0xc1338000 before kagen2_ep_queue after kagen2_ep_queue kagen2_ep_queue 31 512 31 [kagen2_ep_queue] 43425355 4e g_file_storage gadget: bulk-out, length 31: : 55 53 42 43 4e 00 00 00 00 02 00 00 00 00 0a 2a 0010: 00 00 00 00 06 00 00 01 00 00 00 00 00 00 00 EP1 OUT IRQ 0x28 g_file_storage gadget: SCSI command: WRITE(10); Dc=10, Do=512; Hc=10, Ho=512 [start_transfer] 43425355 4e ept1 out queue len 0x200, buffer 0xc1338000 before kagen2_ep_queue after kagen2_ep_queue kagen2_ep_queue 512 512 512 [kagen2_ep_queue] 6f007442 7000 g_file_storage gadget-lun0: file write 512 @ 3072 - 512 g_file_storage gadget: before calling send_status g_file_storage gadget: bulk-in, length 13: : 55 53 42 53 4e 00 00 00 00 00 00 00 00 [start_transfer] 53425355 4e ept1 in queue len 0xd, buffer 0xc0c3c000 0: 0x53425355 4: 0x4e 8: 0x0 bulk_in_complete -- 0, 13/13 EP1 OUT IRQ 0x28 [start_transfer] 6f007442 7000 ept1 out queue len 0x200, buffer 0xc1338000 before kagen2_ep_queue after kagen2_ep_queue kagen2_ep_queue 31 512 31 [kagen2_ep_queue] 43425355 4f g_file_storage gadget: bulk-out, length 31: : 55 53 42 43 4f 00 00 00 00 02 00 00 00 00 0a 2a 0010: 00 00 00 00 02 00 00 01 00 00 00 00 00 00 00 EP1 OUT IRQ 0x28 g_file_storage gadget: SCSI command: WRITE(10); Dc=10, Do=512; Hc=10, Ho=512 [start_transfer] 43425355 4f ept1 out queue len 0x200, buffer 0xc1338000 before kagen2_ep_queue after kagen2_ep_queue kagen2_ep_queue 512 512 512 [kagen2_ep_queue] f8 fff0 g_file_storage gadget-lun0: file write 512 @ 1024 - 512 g_file_storage gadget: before calling send_status g_file_storage gadget: bulk-in, length 13: : 55 53 42 53 4f 00 00 00 00 00 00 00 00 [start_transfer] 53425355 4f ept1 in queue len 0xd, buffer 0xc0c3c000 0: 0x53425355 4: 0x4f 8: 0x0 bulk_in_complete -- 0, 13/13 [start_transfer] f8 fff0 ept1 out queue len 0x200, buffer 0xc1338000 before kagen2_ep_queue EP1 OUT IRQ 0x28 after kagen2_ep_queue kagen2_ep_queue 31 512 31 EP1 OUT IRQ 0x28 [kagen2_ep_queue] 43425355 50 g_file_storage gadget: bulk-out, length 31: : 55 53 42 43 50 00 00 00 00 02 00 00 00 00 0a 2a 0010: 00 00 00 00 06 00 00 01 00 00 00 00 00 00 00 g_file_storage gadget: SCSI command: WRITE(10); Dc=10, Do=512; Hc=10, Ho=512 [start_transfer] 43425355 50 ept1 out queue len 0x200, buffer 0xc1338000 before kagen2_ep_queue after kagen2_ep_queue kagen2_ep_queue 512 512 512 [kagen2_ep_queue] 6f007442 7000 g_file_storage gadget-lun0: file write 512 @ 3072 - 512 g_file_storage gadget: before calling send_status g_file_storage gadget: bulk-in, length 13:
Re: Linux USB file storage gadget with new UDC
Hi, Thanks! Indeed, the req-buf pointer was the one causing the crash problem. It happened when combining multiple 512 bytes data. I have fixed this bug. Now my UDC driver is almost ready. That is probably one more SCSI command timeout problem remaining, i am adding more printk to UDC driver and studying it. I am able to solve the SCSI command timeout problem by adding a code to check the hardware register busy bit continuously, in kagen2_ep_queue(): do { read_hardware_register_busy_bit } while (hardware_is_busy) however, it causes the linux prompt to be non-responsive because the checking hardware register code is run continuously. If i add a schedule() to the do-while loop, the kagen2_ep_queue() will not be continued. How to go about fixing this dilemma? thanks, victor -- To unsubscribe from this list: send the line unsubscribe linux-usb in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
Re: Linux USB file storage gadget with new UDC
Hi, When copying a file to the USB gadget, sometimes the USB gadget will hang, sometimes the USB gadget will crash, sometimes the copy is ok. From the UDC driver log, when the USB gadget crashes, the host is sending 16384 bytes of data. It seems that bulk_out_complete() is not able to handle it. [c03282ec] (dev_printk+0x0/0x3c) from [bf035924] (bulk_out_complete+0xc4/0x1a8 [g_file_storage]) r3:152a0e00 r2:a020d0e5 [bf02fac4] (kagen2_ep_queue+0x0/0x680 [kagen2_udc]) from [bf035f9c] (bulk_in_complete+0x24c/0x1010 [g_file_storage]) The meaning of printk of kagen2_ep_queue 512 16384 512 in UDC driver log: ka_req-req.actual is 512 ka_req-req.length is 16384 length from hardware FIFO is 512 Please see the attached UDC driver log and corresponding usbmon trace. I think the log says that bulk_out_complete() crashed when trying to dereference a NULL pointer. Maybe req-buf, maybe req-context, maybe something else. But you already know that bulk_out_complete() crashed; you don't need me to tell you that. What you _do_ need is to find out why the crash occurred. This means finding out which pointer is NULL. Thanks! Indeed, the req-buf pointer was the one causing the crash problem. It happened when combining multiple 512 bytes data. I have fixed this bug. Now my UDC driver is almost ready. That is probably one more SCSI command timeout problem remaining, i am adding more printk to UDC driver and studying it. Thanks, victor -- To unsubscribe from this list: send the line unsubscribe linux-usb in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
Re: Linux USB file storage gadget with new UDC
Hi, Another question from the bulk_out_complete() printout which is shown below. The req-actual is 512 byte. The bh-bulk_out_intended_length is 31. Is this a bug? g_file_storage gadget: get_next_command [start_transfer] 6f007442 7000 ept1 out queue len 0x200, buffer 0xc133 kagen2_ep_queue 512 512 512 g_file_storage gadget: bulk_out_complete -- 0, 512/31 . Well, it's a mistake. It might be a bug. If the host really did send a 13-byte packet then it's definitely a bug. But if the host sent a 512-byte packet then something else is wrong; it would mean the gadget was expecting a CBW packet but the host sent something else. Alan Stern When copying a file to the USB gadget, sometimes the USB gadget will hang, sometimes the USB gadget will crash, sometimes the copy is ok. From the UDC driver log, when the USB gadget crashes, the host is sending 16384 bytes of data. It seems that bulk_out_complete() is not able to handle it. [c03282ec] (dev_printk+0x0/0x3c) from [bf035924] (bulk_out_complete+0xc4/0x1a8 [g_file_storage]) r3:152a0e00 r2:a020d0e5 [bf02fac4] (kagen2_ep_queue+0x0/0x680 [kagen2_udc]) from [bf035f9c] (bulk_in_complete+0x24c/0x1010 [g_file_storage]) The meaning of printk of kagen2_ep_queue 512 16384 512 in UDC driver log: ka_req-req.actual is 512 ka_req-req.length is 16384 length from hardware FIFO is 512 Please see the attached UDC driver log and corresponding usbmon trace. Thanks, victor bulk_in_complete -- 0, 512/512 bulk_in_complete -- 0, 13/13 kagen2_ep_queue 31 512 31 bulk_in_complete -- 0, 512/512 bulk_in_complete -- 0, 13/13 kagen2_ep_queue 31 512 31 EP1 OUT IRQ 0x28 ep1_out: RX DMA done : NULL REQ on OUT EP-1 bulk_in_complete -- 0, 512/512 bulk_in_complete -- 0, 13/13 kagen2_ep_queue 31 512 31 EP1 OUT IRQ 0x28 ep1_out: RX DMA done : NULL REQ on OUT EP-1 kagen2_ep_queue 512 16384 512 kagen2_ep_queue 1024 16384 512 kagen2_ep_queue 1536 16384 512 kagen2_ep_queue 2048 16384 512 kagen2_ep_queue 2560 16384 512 kagen2_ep_queue 3072 16384 512 kagen2_ep_queue 3584 16384 512 kagen2_ep_queue 4096 16384 512 kagen2_ep_queue 4608 16384 512 kagen2_ep_queue 5120 16384 512 kagen2_ep_queue 5632 16384 512 kagen2_ep_queue 6144 16384 512 kagen2_ep_queue 6656 16384 512 kagen2_ep_queue 7168 16384 512 kagen2_ep_queue 7680 16384 512 kagen2_ep_queue 8192 16384 512 kagen2_ep_queue 8704 16384 512 kagen2_ep_queue 9216 16384 512 kagen2_ep_queue 9728 16384 512 kagen2_ep_queue 10240 16384 512 kagen2_ep_queue 10752 16384 512 kagen2_ep_queue 11264 16384 512 kagen2_ep_queue 11776 16384 512 kagen2_ep_queue 12288 16384 512 kagen2_ep_queue 12800 16384 512 kagen2_ep_queue 13312 16384 512 kagen2_ep_queue 13824 16384 512 kagen2_ep_queue 14336 16384 512 kagen2_ep_queue 14848 16384 512 kagen2_ep_queue 15360 16384 512 kagen2_ep_queue 15872 16384 512 kagen2_ep_queue 16384 16384 512 Unable to handle kernel NULL pointer dereference at virtual address 0004 pgd = c0204000 [0004] *pgd= Internal error: Oops - BUG: 17 [#1] PREEMPT ARM Modules linked in: g_file_storage kagen2_udc ath6kl_sdio ath6kl_core ka2000_sdio ka2000_sdhc CPU: 0Not tainted (3.4.4+ #43) PC is at dev_driver_string+0x30/0x44 LR is at __dev_printk+0x38/0x68 pc : [c0327ef8]lr : [c03280c4]psr: 2093 sp : c1333c08 ip : c1333c18 fp : c1333c14 r10: c0c38000 r9 : c12a0e34 r8 : 0001 r7 : c1289600 r6 : c129ec00 r5 : c1333c44 r4 : c129edd0 r3 : 0004 r2 : c1333c44 r1 : c129ec00 r0 : c129ec00 Flags: nzCv IRQs off FIQs on Mode SVC_32 ISA ARM Segment kernel Control: 0005717f Table: 01308000 DAC: 0017 Process file-storage-ga (pid: 123, stack limit = 0xc1332270) Stack: (0xc1333c08 to 0xc1334000) 3c00: c1333c3c c1333c18 c03280c4 c0327ed8 c0208eb8 c0208564 3c20: c129edd0 c12a0e00 c12896bc 0200 c1333c5c c1333c40 c0328320 c032809c 3c40: 0001 a020d0e5 c1333c4c c1333c64 c1333eb4 c1333c68 bf035924 c0328300 3c60: a020d0e5 152a0e00 152a0e00 c1333c78 000a 6013 3c80: c0c38000 c12a0e34 20313320 34660a3e 32613231 32203034 32323434 31363639 3ca0: 20532033 323a6942 3435303a 2d20313a 20353131 36393034 660a3c20 61323134 3cc0: 20303432 32343432 37313435 43203534 3a694220 35303a32 20313a34 30342030 3ce0: 3d203639 30303020 30303030 30302030 30303030 30203030 30303030 20303030 3d00: 30303030 30303030 30303020 30303030 30302030 30303030 30203030 30303030 3d20: 20303030 30303030 30303030 6166640a 34313936 34322030 34353234 34323831 3d40: 42205320 3a323a69 3a343530 312d2031 31203531 0a3c2033 36616664 30343139 3d60: 34343220 38343532 20323934 69422043 303a323a 313a3435 31203020 203d2033 3d80: 33353535 33353234 30613520 30303030 30302030 30303030 30203030 66640a30 3da0: 31393661 32203034 35323434 38353834 20532037 323a6f42 3435303a 2d20313a 3dc0: 20353131 3d203133 35353520 34323433 62352033 30303030 30203030 30303130 3de0: 20303030 30303038 38326130 30303020 30303030 30382033 30303030 30203830 3e00: 30303030 20303030 30303030 640a3030 39366166 20303431 32343432 37383435
Re: Linux USB file storage gadget with new UDC
Hi, All I can tell is that the gadget got hung after receiving the second WRITE command. Can you figure out where it got hung and why? Victor, you don't seem to get the big pattern that keeps repeating here. Every time something does wrong, you tell me about it. Then I point out that you didn't include any debugging information, so you send part of a log. Then I point out that you didn't send the entire log, or you didn't send logs for both the gadget and the host. You end up losing a day or two each time this happens. There's a very simple lesson: When you're asking for help in debugging a problem, _always_ include _all_ the data that might be relevant. Here's another lesson, which I have pointed out a few times before but you still don't seem to have understood: When you want to know where your driver is hanging up, put a bunch of printk statements in it, at all the important spots. Then you'll be able to see, in the log, the last printk that was executed before the hang. That will tell you where the problem is. Thanks. I will add more printk statements gradually. Now i discover if i write to a large text file ( 48k) on USB gadget, linux will crash. The full log of UDC and gadget driver when linux crashes, and corresponding usbmon trace are attached. If these logs are not helpful, i shall add more printk. thanks, victor bulk_in_complete -- 0, 13/13 bulk_in_complete -- 0, 13/13 EP1 OUT IRQ 0x28 ep1_out: RX DMA done : NULL REQ on OUT EP-1 Unable to handle kernel paging request at virtual address 4000 pgd = c0204000 [4000] *pgd= Internal error: Oops - BUG: 817 [#1] PREEMPT ARM Modules linked in: g_file_storage kagen2_udc ath6kl_sdio ath6kl_core ka2000_sdio ka2000_sdhc CPU: 0Not tainted (3.4.4+ #41) PC is at th, wValue, wIndex; unsigned int rdata, rdata1; // setup data valid val = readl(dev-base_addr + 0+0xfb0/0x199c [kagen2_udc] LR is at console_unlock+0x208/0x218 pc : [bf03000c]lr : [c0216824]psr: 2093 sp : c1347c68 ip : c1347b98 fp : c1347eb4 r10: c1328000 r9 : c12b4db4 r8 : 0001 r7 : c12fedd0 r6 : 0200 r5 : c1346000 r4 : c12b4d80 r3 : r2 : 0001 r1 : 015bb795 r0 : 4000 Flags: nzCv IRQs off FIQs on Mode SVC_32 ISA ARM Segment kernel Control: 0005717f Table: 01314000 DAC: 0017 Process file-storage-ga (pid: 122, stack limit = 0xc1346270) Stack: (0xc1347c68 to 0xc1348000) 7c60: 0200 c1347c78 000a 6013 7c80: c1328000 c12b4db4 4f203150 50205455 0a474e49 61760909 203d206c 64616572 7ca0: 6564286c 623e2d76 5f657361 72646461 30202b20 63383178 090a3b29 6c617609 7cc0: 203d2620 7830 3030 0a3b 61760909 3d7c206c 30783020 30323030 7ce0: 3b303030 090a0909 69727709 286c6574 2c6c6176 76656420 61623e2d 615f6573 7d00: 20726464 7830202b 29633831 7d090a3b 6c65090a 69206573 76282066 3d206c61 7d20: 7830203d 0a293832 700a7b09 746e6972 4522286b 4f203150 49205455 30205152 7d40: 5c782578 202c226e 296c6176 09090a3b 70652f2f 756f5f31 65642874 0a3b2976 7d60: 73740909 74654c6b 4253555f 7461642e 203d2061 736e7528 656e6769 6f6c2064 7d80: 6429676e 0a3b7665 61740909 656c6b73 63735f74 75646568 2628656c 4c6b7374 7da0: 555f7465 3b294253 09090a0a 206c6176 6572203d 286c6461 2d766564 7361623e 7dc0: 64615f65 2b207264 31783020 3b293061 7d090a09 6c65090a 69206573 76282066 7de0: 3d206c61 7830203d 0a293432 090a7b09 452f2f09 69203150 5249206e 09090a51 7e00: 206c6176 6572203d 286c6461 2d766564 7361623e 64615f65 2b207264 31783020 7e20: 3b293838 7609090a 26206c61 7830203d 3030 09090a3b 206c6176 7e40: 30203d7c 30303078 30303030 09093b32 7709090a 65746972 6176286c 64202c6c 7e60: 3e2d7665 65736162 6464615f 202b2072 38317830 0a3b2938 090a0909 65090a7d 7e80: 2065736c 28206669 c03ef7b0 c12b4d80 c12fedd0 c1289600 c12896f8 c12896e0 7ea0: 7e00 c1346018 c1347eec c1347eb8 bf035f9c bf02fa88 c12896dc 7ec0: c1289700 c1289600 00c8c000 c12896dc c1289700 c1289600 00c8c000 7ee0: c1347f54 c1347ef0 bf036b14 bf035e64 c12896e0 000a c1347f04 c0209bd4 7f00: c1347fbc be00 7e00 0001 00c8c000 00c88000 7f20: 0001 005f c12896dc c1289600 0001 005f c12896dc 7f40: c1346018 c1347fbc c1347f58 bf038ce8 bf0368d8 bf03a316 bf03a29f 7f60: 0015 c127ea80 c1347f8c c1347f78 c02349c8 c1289604 c13207e0 c1320540 7f80: c1347fac c1347f90 c03f2fc0 c02365d0 c1337e00 c1337e00 c1289600 bf037bc0 7fa0: 0013 c1347ff4 c1347fc0 c022f8f4 bf037bd0 7fc0: c1337e00 c1289600 c1347fd0 c1347fd0 c1337e00 7fe0: c022f860 c02191c8 c1347ff8 c02191c8 c022f870 Backtrace: [bf02fa78] (th, wValue, wIndex; unsigned int rdata, rdata1; // setup data valid val = readl(dev-base_addr + 0+0xa1c/0x199c [kagen2_udc]) from [bf035f9c] (bulk_in_complete+0x24c/0x1010
Re: Linux USB file storage gadget with new UDC
Hi, Thanks. I will add more printk statements gradually. Now i discover if i write to a large text file ( 48k) on USB gadget, linux will crash. The full log of UDC and gadget driver when linux crashes, and corresponding usbmon trace are attached. If these logs are not helpful, i shall add more printk. Unfortunately, I can't get anything useful out of the UDC driver crash log. It looks like the crash occurred somewhere inside the do_write() routine. Perhaps within the call to start_transfer(), or perhaps within the vfs_write() call. Alan Stern Just curious. The crash log shows the following UDC driver code which is responsible to receive endpoint 0 setup data. However, the host PC is sending SCSI_WRITE_10 command at the time of the crash. These two does not correlate, right? unsigned int rdata, rdata1; // setup data valid val = readl(dev-base_addr + 0+0xfb0/0x199c [kagen2_udc] thanks, victor -- To unsubscribe from this list: send the line unsubscribe linux-usb in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
Re: Linux USB file storage gadget with new UDC
Hi, Ok, i just fixed the last three bytes in the bulk-out transfer problem. Please see below for the log. Now the last three bytes are read correctly. After SCSI_WRITE_10 is received, the gadget driver prints g_file_storage gadget: disconnect or port reset, it means USB reset interrupt is received by the UDC driver. I don't know why USB reset interrupt is triggered. Then you need to figure out why. Have you checked the dmesg log and usbmon trace on the host? Incidentally, for debugging it will help if you enable CONFIG_PRINTK_TIME in the gadget's kernel. Thanks, i will enable the CONFIG_PRINTK_TIME. Nonetheless, now the gadget driver and UDC driver are able to process some SCSI_WRITE_10 commands (i ignore the USB reset interrupt in UDC driver). Please see the attached usbmon log. Will the log help? Thanks, victor scsi_write_10_again04.log Description: Binary data
Re: Linux USB file storage gadget with new UDC
Hi, Obviously this disconnect or port reset message is related to the EP1 OUT IRQ 0x28 line above. But why? It looks like another bug. I see you still haven't fixed the last three bytes in the bulk-out transfer. Ok, i just fixed the last three bytes in the bulk-out transfer problem. Please see below for the log. Now the last three bytes are read correctly. After SCSI_WRITE_10 is received, the gadget driver prints g_file_storage gadget: disconnect or port reset, it means USB reset interrupt is received by the UDC driver. I don't know why USB reset interrupt is triggered. [start_transfer] ept1 out queue len 0x200, buffer 0xc1298000 g_file_storage gadget: bulk-out, length 31: : 55 53 42 43 f5 00 00 00 00 02 00 00 00 00 0a 2a 0010: 00 00 00 00 01 00 00 01 00 00 00 00 00 00 00 g_file_storage gadget: SCSI command: WRITE(10); Dc=10, Do=512; Hc=10, Ho=512 [start_transfer] 43425355 f5 ept1 out queue len 0x200, buffer 0xc1298000 g_file_storage gadget: disconnect or port reset g_file_storage gadget: do_scsi_command unlink (ep1) pio kagen2_set_halt 1 0 g_file_storage gadget: bulk-out, length 0: g_file_storage gadget: bulk_out_complete -- 0, 0/512 g_file_storage gadget: reset config g_file_storage gadget: reset interface g_file_storage gadget: handle_exception g_file_storage gadget: ep0-setup, length 8: : 80 06 00 01 00 00 40 00 . Thanks, victor -- To unsubscribe from this list: send the line unsubscribe linux-usb in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
Re: Linux USB file storage gadget with new UDC
Hi, That's right. Interrupts can occur at almost any time (on multiprocessor systems they can occur even when interrupts are disabled on some of the CPUs). I am confused. I add the spinlock functions to kagen2_ep_queue function. spin_lock_irqsave(dev-lock, flags); .. spin_unlock_irqrestore(dev-lock, flags); When kagen2_ep_queue function is called, the error BUG: scheduling while atomic: swapper/0/0x0002 occurs. I test the same spinlock functions in other device module. It is ok in other device module. While the function holds a spinlock, it is not allowed to sleep. The BUG occurs because kagen2_ep_queue must call some function that can sleep. But since you did not provide the rest of the BUG message (including the stack trace), I can't tell what function it calls. The BUG: scheduling while atomic is solved. Need to add extra spinlock functions for req-complete() as below: spin_unlock(dev-lock); req-complete(ep, req); spin_lock(dev-lock); Now, the SCSI_WRITE_10 command is received but the data is not received. There is disconnect or port reset after SCSI_WRITE_10 command. Please see below: [start_transfer] 613e2d71 61757463 ept1 out queue len 0x200, buffer 0xc1338000 g_file_storage gadget: bulk-out, length 31: : 55 53 42 43 f6 00 00 00 00 02 00 00 00 00 0a 2a 0010: 00 00 00 00 01 00 00 01 00 00 00 00 80 b7 21 EP1 OUT IRQ 0x28 g_file_storage gadget: disconnect or port reset g_file_storage gadget: SCSI command: WRITE(10); Dc=10, Do=512; Hc=10, Ho=512 [start_transfer] 43425355 f6 ept1 out queue len 0x200, buffer 0xc1338000 g_file_storage gadget: do_scsi_command unlink (ep1) pio kagen2_set_halt 1 0 g_file_storage gadget: bulk-out, length 0: g_file_storage gadget: bulk_out_complete -- 0, 0/512 g_file_storage gadget: reset config g_file_storage gadget: reset interface g_file_storage gadget: handle_exception g_file_storage gadget: do_scsi_command is from extra DBG statement that i added in file_storage.c. if (do_scsi_command(fsg) || finish_reply(fsg)) { DBG(fsg, do_scsi_command\n); continue; } thanks, victor -- To unsubscribe from this list: send the line unsubscribe linux-usb in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
Re: Linux USB file storage gadget with new UDC
Hi, It is likely that this bug occurs because you don't use a spinlock in kagen2_ep_queue. Does the interrupt handler routine use a spinlock? Spinlock is Not used in interrupt handler routine. Then that's the reason for this bug. [start_transfer] 53425355 10d ept1 out queue len 0x200, buffer 0xc1304000 g_file_storage gadget: bulk-out, length 31: Is the kagen2_ep_queue function gotten interrupted here? So the kagen2_ep_queue and interrupt routine need spinlock for synchronisation? That's right. Interrupts can occur at almost any time (on multiprocessor systems they can occur even when interrupts are disabled on some of the CPUs). I am confused. I add the spinlock functions to kagen2_ep_queue function. spin_lock_irqsave(dev-lock, flags); .. spin_unlock_irqrestore(dev-lock, flags); When kagen2_ep_queue function is called, the error BUG: scheduling while atomic: swapper/0/0x0002 occurs. I test the same spinlock functions in other device module. It is ok in other device module. thanks, victor -- To unsubscribe from this list: send the line unsubscribe linux-usb in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
Re: Linux USB file storage gadget with new UDC
Hi, How the UDC driver know when the request is really complete? An OUT request is really complete when either: The total number of bytes copied into req.buffer (i.e., req.actual) is equal to req.length, or The number of bytes received in the last packet is smaller than ep.maxpacket. I made some changes regarding req.actual. Now the UDC driver still cannot process SCSI_WRITE_10 command. Please see the attached UDC driver log when i try to write to a text file. There should be three SCSI commands in the log: SCSI_REQUEST_SENSE, SCSI_TEST_UNIT_READY and SCSI_WRITE_10. SCSI_WRITE_10 is not received properly. Thanks, victor g_file_storage gadget: bulk-out, length 31: : 55 53 42 43 0d 01 00 00 12 00 00 00 80 00 06 03 0010: 00 00 00 12 00 00 00 00 00 00 00 00 c3 63 4a g_file_storage gadget: SCSI command: REQUEST SENSE; Dc=6, Di=18; Hc=6, Hi=18 g_file_storage gadget: bulk-in, length 18: : 70 00 06 00 00 00 00 0a 00 00 00 00 29 00 00 00 0010: 00 00 [start_transfer] 60070 a00 ept1 in queue len 0x12, buffer 0xc1344000 0: 0x60070 4: 0xa00 8: 0x0 c: 0x29 bulk_in_complete -- 0, 18/18 g_file_storage gadget: bulk-in, length 13: : 55 53 42 53 0d 01 00 00 00 00 00 00 00 [start_transfer] 53425355 10d ept1 in queue len 0xd, buffer 0xc1304000 0: 0x53425355 4: 0x10d 8: 0x0 bulk_in_complete -- 0, 13/13 EP1 OUT IRQ 0x28 ep1_out: RX DMA done : NULL REQ on OUT EP-1 [start_transfer] 60070 a00 ept1 out queue len 0x200, buffer 0xc1344000 g_file_storage gadget: bulk-out, length 31: : 55 53 42 43 0e 01 00 00 00 00 00 00 00 00 06 00 0010: 00 00 00 00 00 00 00 00 00 00 00 00 c3 63 4a g_file_storage gadget: SCSI command: TEST UNIT READY; Dc=6, Dn=0; Hc=6, Hn=0 g_file_storage gadget: bulk-in, length 13: : 55 53 42 53 0e 01 00 00 00 00 00 00 00 [start_transfer] 53425355 10e ept1 in queue len 0xd, buffer 0xc1344000 0: 0x53425355 4: 0x10e 8: 0x0 bulk_in_complete -- 0, 13/13 EP1 OUT IRQ 0x28 ep1_out: RX DMA done : NULL REQ on OUT EP-1 [start_transfer] 53425355 10d ept1 out queue len 0x200, buffer 0xc1304000 g_file_storage gadget: bulk-out, length 31: EP1 OUT IRQ 0x28 epnum 1 in 0 len 0 512 0 g_file_storage gadget: bulk-out, length 0: g_file_storage gadget: bulk_out_complete -- 0, 0/31 g_file_storage gadget: bulk_out_complete -- 0, 0/31 g_file_storage gadget: invalid CBW: len 0 sig 0x43425355 g_file_storage gadget: bulk-in set wedge g_file_storage gadget: get_next_command [start_transfer] 43425355 10f ept1 out queue len 0x200, buffer 0xc1304000
Re: Linux USB file storage gadget with new UDC
Hi, I made some changes regarding req.actual. Now the UDC driver still cannot process SCSI_WRITE_10 command. Please see the attached UDC driver log when i try to write to a text file. There should be three SCSI commands in the log: SCSI_REQUEST_SENSE, SCSI_TEST_UNIT_READY and SCSI_WRITE_10. SCSI_WRITE_10 is not received properly. No, it isn't. Here's what the log says: EP1 OUT IRQ 0x28 ep1_out: RX DMA done : NULL REQ on OUT EP-1 [start_transfer] 53425355 10d ept1 out queue len 0x200, buffer 0xc1304000 g_file_storage gadget: bulk-out, length 31: This is from bulk_out_complete, when the WRITE(10) was received. EP1 OUT IRQ 0x28 epnum 1 in 0 len 0 512 0 g_file_storage gadget: bulk-out, length 0: This line indicates a bug. It means the UDC driver called bulk_out_complete again, even though the previous request was no longer queued and no new requests had been submitted yet. It is likely that this bug occurs because you don't use a spinlock in kagen2_ep_queue. Does the interrupt handler routine use a spinlock? Spinlock is Not used in interrupt handler routine. [start_transfer] 53425355 10d ept1 out queue len 0x200, buffer 0xc1304000 g_file_storage gadget: bulk-out, length 31: Is the kagen2_ep_queue function gotten interrupted here? So the kagen2_ep_queue and interrupt routine need spinlock for synchronisation? EP1 OUT IRQ 0x28 epnum 1 in 0 len 0 512 0 g_file_storage gadget: bulk-out, length 0: Maybe you haven't noticed this, but the REQUEST SENSE and TEST UNIT READY commands weren't received correctly either. The last three bytes in each command should be 0, but they aren't. They are: c3 63 4a. Where did those values come from? Yes, i haven't noticed the c3 63 4a. Clearly the last three bytes should be zero. Maybe the UDC driver has a bug (Do the last 3 bytes matter for file gadget? ). Here is the usbmon trace that corresponds to the UDC log. It is the proof that the last three bytes are zero. Thanks, victor scsi_write_10_again02.log Description: Binary data
Re: Linux USB file storage gadget with new UDC
Hi, Please see the attached kagen2_ep_queue(). As long as it is called, it will queue the request and read packets from hardware, in the same if-else branch for bulk out endpoint. The interrupt handler will NOT accept packet if request is NOT queued. If request is queued, interrupt handler will accept the packet. This code is wrong. See what happens when a request for ep1-out is submitted: /* ep1 OUT endpoint */ else if (in == 0) { // read from EP1 OUT buffer if (num == 1) { unsigned int val; unsigned int val_arr[8]; int i; // get byte count from hardware val = readl(dev-base_addr + 0x008); len = val 0xFF; Why do you expect there to be any data in the hardware FIFO at this point? You said that the hardware will not accept any data if a request is not queued. Well, before this point the request wasn't queued, so there shouldn't be any data. I am sorry for unclear writing. What i mean is: If a request is not queued, the hardware will still accept data, but interrupt controller will not read the data from the hardware FIFO. // read from hardware fifo1 data for (i = 0; i len/4; i++) { val_arr[i] = readl(dev-base_addr + 0x084); } val_arr is declared as an array of 8 unsigned ints. That means its total size is 32 bytes. What happens if len 32? You will end up overwriting part of the stack. Yes! This is a bug. I only thought about the 31 byte CBW for bulk out endpoint. I forgot about the SCSI_WRITE_10 command. Thanks!! list_add_tail(ka_req-queue, ka_ep-queue); ka_req-req.actual = len; memcpy(ka_req-req.buf, val_arr[0], len); ka_req-req.complete(ka_ep-ep, ka_req-req); You should not call req.complete until the request really is complete. For example, what happens here if the host hasn't sent any packets yet? Or what happens if req is waiting to receive 1024 bytes but the host has sent only 512 bytes so far? How the UDC driver know when the request is really complete? Also, all the data gets copied _twice_: once from the hardware FIFO into val_arr, and then again from val_arr into req.buf. That's a waste of time; the data should be copied directly from the FIFO into req.buf. Agree. 2) Repeatedly (many many times), the same SCSI_READ_10 command is received by UDC driver, processed by gadget driver, and UDC driver sends out data and CSW to host. On usbmon trace, only one instance of the SCSI_READ_10 is observed. This is probably because you are copying the same data from the FIFO to req.buffer many times. I am curious about it. After data is read from FIFO, the FIFO will become empty. Still cannot figure out how the same data is read from the FIFO many times. Thanks, victor -- To unsubscribe from this list: send the line unsubscribe linux-usb in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
Re: Linux USB file storage gadget with new UDC
Hi, This is the stack dump when the completion routine is called without an interrupt occurring first, is it useful? Backtrace: [c020c0fc] (dump_backtrace+0x0/0x110) from [c03ef5e4] (dump_stack+0x18/0x1c) r6:bf030da8 r5:c12aec00 r4:c12b4c00 r3:00f8 [c03ef5cc] (dump_stack+0x0/0x1c) from [bf02fecc] (kagen2_ep_queue+0x520/0x598 [kagen2_udc]) [bf02f9ac] (kagen2_ep_queue+0x0/0x598 [kagen2_udc]) from [bf036068] (fsg_lun_open+0x578/0x1278 [g_file_storage]) [bf035f20] (fsg_lun_open+0x430/0x1278 [g_file_storage]) from [bf037cd4] (fsg_main_thread+0x10c/0x155c [g_file_storage]) r8: r7:0001 r6:c12896c0 r5:c12896bc r4:c1289600 [bf037bc8] (fsg_main_thread+0x0/0x155c [g_file_storage]) from [c022f8f4] (kthread+0x94/0xa0) [c022f860] (kthread+0x0/0xa0) from [c02191c8] (do_exit+0x0/0x6f0) r6:c02191c8 r5:c022f860 r4:c1327e00 This shows that kagen2_ep_queue() calls kareq-req.complete. Perhaps indirectly, through another function. If this is true then it's probably a bug. You should check it out. Yes, the kagen2_ep_queue() calls req-req.complete directly. I thought this is necessary to pass the packets to gadget driver for processing? req-req.complete is mapped to bulk_out_complete() or bulk_in_complete(). thanks, victor -- To unsubscribe from this list: send the line unsubscribe linux-usb in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
Re: Linux USB file storage gadget with new UDC
Hi, Yes, the kagen2_ep_queue() calls req-req.complete directly. I thought this is necessary to pass the packets to gadget driver for processing? It is necessary to call req.complete when the request has _completed_! That's why the callback is named complete! req-req.complete is mapped to bulk_out_complete() or bulk_in_complete(). A bulk-out request isn't complete until the data has been received from the host. A bulk-in request isn't complete until the data has been sent to the host (or at least copied into a hardware buffer). kagen2_ep_queue() gets called when the bulk-out request is submitted, right? So the request is not complete at that time. It isn't complete until the host has sent the data. After all, if you haven't received the packets from the host yet, how can you pass the packets to the gadget driver for processing? Alan Stern For bulk out endpoint, I code the kagen2_ep_queue() to read the packets from the USB hardware, then call bulk_out_complete() via req-req.complete. Is this the correct way? Or i should only read the bulk out endpoint when bulk-out endpoint interrupt is received? thanks, victor -- To unsubscribe from this list: send the line unsubscribe linux-usb in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
Re: Linux USB file storage gadget with new UDC
Hi, While kagen2_ep_queue() is running, there shouldn't be any packets in the USB hardware. The hardware should refuse to accept any packets, sending NAKs back to the host, until a request has been submitted and queued. When the request is queued, that's when you should tell the hardware to accept data from the host. After that, each time a packet arrives from the host, either the hardware or the UDC driver should store the packet data in the request's buffer. When the buffer is full or a short packet is received (the UDC driver's interrupt handler will know when this happens) then the UDC driver should call req.complete. Please see the attached kagen2_ep_queue(). As long as it is called, it will queue the request and read packets from hardware, in the same if-else branch for bulk out endpoint. The interrupt handler will NOT accept packet if request is NOT queued. If request is queued, interrupt handler will accept the packet. Somehow, there is still timing problem in UDC driver and it is hard to pin down the root cause. It could be due to interaction of UDC driver queue() and gadget driver fsg_main_thread() main loop. 1) When writing to gen2 gadget, SCSI_READ_10 or or SCSI_REQUEST_SENSE commands are received by UDC driver, but gadget did not process the commands. (cannot get past get_next_command() in fsg_main_thread) 2) Repeatedly (many many times), the same SCSI_READ_10 command is received by UDC driver, processed by gadget driver, and UDC driver sends out data and CSW to host. On usbmon trace, only one instance of the SCSI_READ_10 is observed. 3) More severe case, if removing one printk statement in bulk_in_complete(), USB gadget device cannot be recognised by host. Thanks, victor static int kagen2_ep_queue(struct usb_ep *ep, struct usb_request *req, gfp_t gfp_flags) { struct kagen2_ep *ka_ep; struct kagen2_request *ka_req; struct kagen2 * dev; unsigned phys; int num, len, in; ka_req = container_of(req, struct kagen2_request, req); if (!req || !req-complete || !req-buf || !list_empty(ka_req-queue)) { printk(exit A\n); return -EINVAL; } ka_ep = container_of(ep, struct kagen2_ep, ep); if (!ep || (!ka_ep-desc ka_ep-num != 0)) { printk(exit B\n); return -EINVAL; } dev = ka_ep-dev; if (!dev || !dev-driver || dev-gadget.speed == USB_SPEED_UNKNOWN) { printk(exit C\n); return -ESHUTDOWN; } num = ka_ep-desc-bEndpointAddress USB_ENDPOINT_NUMBER_MASK; in = (ka_ep-desc-bEndpointAddress USB_DIR_IN) != 0; phys = (unsigned)req-buf; len = req-length; printk(KERN_DEBUG ept%d %s queue len 0x%x, buffer 0x%x\n, num, in ? in : out, len, phys); /* ep0 IN endpoint */ if ((len 0) (num == 0) (in != 0)) { req-actual = 0; ep0_in(phys, len, dev); req-actual += len; req-complete(ep, req); list_del_init(ka_req-queue); return 0; } /* ep1 IN endpoint */ else if ((len = 0) (num == 1) (in != 0)) { req-actual = 0; ep1_in(phys, len, dev); req-actual += len; req-complete(ep, req); list_del_init(ka_req-queue); return 0; } /* ep1 OUT endpoint */ else if (in == 0) { // read from EP1 OUT buffer if (num == 1) { unsigned int val; unsigned int val_arr[8]; int i; // get byte count from hardware val = readl(dev-base_addr + 0x008); len = val 0xFF; // read from hardware fifo1 data for (i = 0; i len/4; i++) { val_arr[i] = readl(dev-base_addr + 0x084); } list_add_tail(ka_req-queue, ka_ep-queue); ka_req-req.actual = len; memcpy(ka_req-req.buf, val_arr[0], len); ka_req-req.complete(ka_ep-ep, ka_req-req); list_del_init(ka_req-queue); // clear hardware OUT1CS register val = readl(dev-base_addr + 0x008); val = 0x00ff; writel(val, dev-base_addr + 0x008); } } return 0; }
Re: Linux USB file storage gadget with new UDC
Hi, I change that in UDC driver queue function, adding in a length check: if (len 0) { ka_req-req.complete(ka_ep-ep, ka_req-req); list_del_init(ka_req-queue); } What is len? Is it the packet size? If it is then this check is wrong, because the UDC driver must accept zero-length packets. Yes, it is packet size. So UDC driver must accept zero-length packets sent from USB host? Just before the line that calls ka_req-req.complete, add: WARN_ON(!victor_test); victor_test = 0; Then you'll get a stack dump every time the completion routine is called without an interrupt occurring first. The stack dump will help you to figure out why this is going wrong and where the problem is. This is the stack dump when the completion routine is called without an interrupt occurring first, is it useful? Backtrace: [c020c0fc] (dump_backtrace+0x0/0x110) from [c03ef5e4] (dump_stack+0x18/0x1c) r6:bf030da8 r5:c12aec00 r4:c12b4c00 r3:00f8 [c03ef5cc] (dump_stack+0x0/0x1c) from [bf02fecc] (kagen2_ep_queue+0x520/0x598 [kagen2_udc]) [bf02f9ac] (kagen2_ep_queue+0x0/0x598 [kagen2_udc]) from [bf036068] (fsg_lun_open+0x578/0x1278 [g_file_storage]) [bf035f20] (fsg_lun_open+0x430/0x1278 [g_file_storage]) from [bf037cd4] (fsg_main_thread+0x10c/0x155c [g_file_storage]) r8: r7:0001 r6:c12896c0 r5:c12896bc r4:c1289600 [bf037bc8] (fsg_main_thread+0x0/0x155c [g_file_storage]) from [c022f8f4] (kthread+0x94/0xa0) [c022f860] (kthread+0x0/0xa0) from [c02191c8] (do_exit+0x0/0x6f0) r6:c02191c8 r5:c022f860 r4:c1327e00 Here's an example. This shows the port status immediately after the first port reset in the April 22 usbmon trace: f2f4f740 1985276053 S Ci:2:002:0 s a3 00 0004 0004 4 f2f4f740 1985276154 C Ci:2:002:0 0 4 = 03011000 The 01 in the second byte of the response indicates full speed. If the connection were high speed, the second byte would be 05. See Section 11.24.2.7 in the USB-2.0 specification, and especially the description of bit 10 in Table 11-21 and 11.24.2.7.1.8. Thanks, i found the bit 10 in Table 11-21 Port Status Field. 0 = Full-speed device attached to this port. 1 = High-speed device attached to this port. victor -- To unsubscribe from this list: send the line unsubscribe linux-usb in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
Re: Linux USB file storage gadget with new UDC
Hi, Here is a full log from the beginning which shows another problem. When the SCSI_READ_10 command below is received, there is a disconnect or port reset which causes the (-32) broken pipe problem. You really need to fix the old problems before worrying about new problems. The set_halt still isn't working, and the UDC continues to continues to call bulk_out_complete multiple times without receiving any packets. I change that in UDC driver queue function, adding in a length check: if (len 0) { ka_req-req.complete(ka_ep-ep, ka_req-req); list_del_init(ka_req-queue); } However, i still observe the SCSI command being received by UDC and gadget driver, but not processed by gadget driver. For the UDC and gadget driver log, it looks like the flow cannot get past get_next_command() of fsg_main_thread(). The log is attached. [start_transfer] 43425355 9 ept1 out queue len 0x200, buffer 0xc1338000 g_file_storage gadget: bulk-out, length 31: : 55 53 42 43 09 00 00 00 00 00 00 00 00 00 06 00 0010: 00 00 00 00 00 00 00 00 00 00 00 00 f8 7e 34 g_file_storage gadget: get_next_command The same SCSI command as seen on usbmon log: f2f4fe40 3842078083 S Bo:2:050:1 -115 31 = 55534243 0900 0600 00 f2f4fe40 3842078159 C Bo:2:050:1 0 31 f2f4fe40 3842078182 S Bi:2:050:1 -115 13 f2f4fe40 3872633965 C Bi:2:050:1 -104 0 It would be easier to maintain a stable link if the UDC connected at high speed in the first place. The usbmon log shows that the connection was at full speed (12 Mb/s), not high speed (480 Mb/s) -- which means that this line: g_file_storage gadget: high-speed config #1 in the gadget log indicates another bug in the UDC driver. It told the gadget driver that the connection was high speed, but the connection really was full speed. How to read from usbmon log that the connection was at full speed? Thanks, victor # dmesg [start_transfer] 43425355 9 ept1 out queue len 0x200, buffer 0xc1338000 g_file_storage gadget: bulk-out, length 31: : 55 53 42 43 09 00 00 00 00 00 00 00 00 00 06 00 0010: 00 00 00 00 00 00 00 00 00 00 00 00 f8 7e 34 g_file_storage gadget: get_next_command [start_transfer] 43425355 9 ept1 out queue len 0x200, buffer 0xc1338000 g_file_storage gadget: bulk-out, length 31: : 55 53 42 43 09 00 00 00 00 00 00 00 00 00 06 00 0010: 00 00 00 00 00 00 00 00 00 00 00 00 f8 7e 34 g_file_storage gadget: get_next_command [start_transfer] 43425355 9 ept1 out queue len 0x200, buffer 0xc1338000 g_file_storage gadget: bulk-out, length 31: : 55 53 42 43 09 00 00 00 00 00 00 00 00 00 06 00 0010: 00 00 00 00 00 00 00 00 00 00 00 00 f8 7e 34 g_file_storage gadget: get_next_command [start_transfer] 43425355 9 ept1 out queue len 0x200, buffer 0xc1338000 g_file_storage gadget: bulk-out, length 31: : 55 53 42 43 09 00 00 00 00 00 00 00 00 00 06 00 0010: 00 00 00 00 00 00 00 00 00 00 00 00 f8 7e 34 g_file_storage gadget: get_next_command [start_transfer] 43425355 9 ept1 out queue len 0x200, buffer 0xc1338000 g_file_storage gadget: bulk-out, length 31: : 55 53 42 43 09 00 00 00 00 00 00 00 00 00 06 00 0010: 00 00 00 00 00 00 00 00 00 00 00 00 f8 7e 34 g_file_storage gadget: get_next_command [start_transfer] 43425355 9 ept1 out queue len 0x200, buffer 0xc1338000 g_file_storage gadget: bulk-out, length 31: : 55 53 42 43 09 00 00 00 00 00 00 00 00 00 06 00 0010: 00 00 00 00 00 00 00 00 00 00 00 00 f8 7e 34 g_file_storage gadget: get_next_command [start_transfer] 43425355 9 ept1 out queue len 0x200, buffer 0xc1338000 g_file_storage gadget: bulk-out, length 31: : 55 53 42 43 09 00 00 00 00 00 00 00 00 00 06 00 0010: 00 00 00 00 00 00 00 00 00 00 00 00 f8 7e 34 g_file_storage gadget: get_next_command [start_transfer] 43425355 9 ept1 out queue len 0x200, buffer 0xc1338000 g_file_storage gadget: bulk-out, length 31: : 55 53 42 43 09 00 00 00 00 00 00 00 00 00 06 00 0010: 00 00 00 00 00 00 00 00 00 00 00 00 f8 7e 34 g_file_storage gadget: get_next_command [start_transfer] 43425355 9 ept1 out queue len 0x200, buffer 0xc1338000 g_file_storage gadget: bulk-out, length 31: : 55 53 42 43 09 00 00 00 00 00 00 00 00 00 06 00 0010: 00 00 00 00 00 00 00 00 00 00 00 00 f8 7e 34 g_file_storage gadget: get_next_command [start_transfer] 43425355 9 ept1 out queue len 0x200, buffer 0xc1338000 g_file_storage gadget: bulk-out, length 31: : 55 53 42 43 09 00 00 00 00 00 00 00 00 00 06 00 0010: 00 00 00 00 00 00 00 00 00 00 00 00 f8 7e 34 g_file_storage gadget: get_next_command [start_transfer] 43425355 9 ept1 out queue len 0x200, buffer 0xc1338000 g_file_storage gadget: bulk-out, length 31: : 55 53 42 43 09 00 00 00 00 00 00 00 00 00 06 00 0010: 00 00 00 00 00 00 00 00 00 00 00 00 f8 7e 34
Re: Linux USB file storage gadget with new UDC
Hi, I modified the UDC driver to send out zero length data packet. Now the linux host is able to see the USB gadget as a mass storage device and read from USB gadget. However, writing to USB gadget fails. The SCSI_WRITE_10 command often receives (-104). The usbmon trace showing this failure is attached. Is the bulk-out endpoint unable to receive command and data continuously, due to error in UDC driver? It looks like the data gets received okay. I can't tell what's going wrong because you did not post the gadget log showing the WRITE commands. When writing to USB gadget from Linux host, the SCSI_WRITE_10 command is sent out from the Linux host, but the USB gadget receives zero length packet. And after a long wait of 30 seconds, the Linux host resets the connection (-104). The usbmon trace and the UDC driver log are attached. g_file_storage gadget: bulk-out, length 0: g_file_storage gadget: bulk_out_complete -- 0, 0/31 I think UDC driver receives the zero length packet on bulk out endpoint. Thanks, victor # dmesg [start_transfer] 43425355 c5 ept1 out queue len 0x200, buffer 0xc133c000 g_file_storage gadget: bulk-out, length 0: g_file_storage gadget: bulk_out_complete -- 0, 0/31 [start_transfer] 43425355 c5 ept1 out queue len 0x200, buffer 0xc133c000 g_file_storage gadget: bulk-out, length 0: g_file_storage gadget: bulk_out_complete -- 0, 0/31 [start_transfer] 43425355 c5 ept1 out queue len 0x200, buffer 0xc133c000 g_file_storage gadget: bulk-out, length 0: g_file_storage gadget: bulk_out_complete -- 0, 0/31 [start_transfer] 43425355 c5 ept1 out queue len 0x200, buffer 0xc133c000 g_file_storage gadget: bulk-out, length 0: g_file_storage gadget: bulk_out_complete -- 0, 0/31 [start_transfer] 43425355 c5 ept1 out queue len 0x200, buffer 0xc133c000 g_file_storage gadget: bulk-out, length 0: g_file_storage gadget: bulk_out_complete -- 0, 0/31 [start_transfer] 43425355 c5 ept1 out queue len 0x200, buffer 0xc133c000 g_file_storage gadget: bulk-out, length 0: g_file_storage gadget: bulk_out_complete -- 0, 0/31 [start_transfer] 43425355 c5 ept1 out queue len 0x200, buffer 0xc133c000 g_file_storage gadget: bulk-out, length 0: g_file_storage gadget: bulk_out_complete -- 0, 0/31 [start_transfer] 43425355 c5 ept1 out queue len 0x200, buffer 0xc133c000 g_file_storage gadget: bulk-out, length 0: g_file_storage gadget: bulk_out_complete -- 0, 0/31 [start_transfer] 43425355 c5 ept1 out queue len 0x200, buffer 0xc133c000 g_file_storage gadget: bulk-out, length 0: g_file_storage gadget: bulk_out_complete -- 0, 0/31 [start_transfer] 43425355 c5 ept1 out queue len 0x200, buffer 0xc133c000 g_file_storage gadget: bulk-out, length 0: g_file_storage gadget: bulk_out_complete -- 0, 0/31 [start_transfer] 43425355 c5 ept1 out queue len 0x200, buffer 0xc133c000 g_file_storage gadget: bulk-out, length 0: g_file_storage gadget: bulk_out_complete -- 0, 0/31 [start_transfer] 43425355 c5 ept1 out queue len 0x200, buffer 0xc133c000 g_file_storage gadget: bulk-out, length 0: g_file_storage gadget: bulk_out_complete -- 0, 0/31 [start_transfer] 43425355 c5 ept1 out queue len 0x200, buffer 0xc133c000 g_file_storage gadget: bulk-out, length 0: g_file_storage gadget: bulk_out_complete -- 0, 0/31 [start_transfer] 43425355 c5 ept1 out queue len 0x200, buffer 0xc133c0007g_file_storage gadget: bulk_out_complete -- 0, 0/31 g_file_storage gadget: bulk-out, length 0: g_file_storage gadget: bulk_out_complete -- 0, 0/31 [start_transfer] 43425355 c5 ept1 out queue len 0x200, buffer 0xc133c000 g_file_storage gadget: bulk-out, length 0: g_file_storage gadget: bulk_out_complete -- 0, 0/31 [start_transfer] 43425355 c5 ept1 out queue len 0x200, buffer 0xc133c000 g_file_storage gadget: bulk-out, length 0: g_file_storage gadget: bulk_out_complete -- 0, 0/31 [start_transfer] 43425355 c5 ept1 out queue len 0x200, buffer 0xc133c000 g_file_storage gadget: bulk-out, length 0: g_file_storage gadget: bulk_out_complete -- 0, 0/31 [start_transfer] 43425355 c5 ept1 out queue len 0x200, buffer 0xc133c000 g_file_storage gadget: bulk-out, length 0: g_file_storage gadget: bulk_out_complete -- 0, 0/31 [start_transfer] 43425355 c5 ept1 out queue len 0x200, buffer 0xc133c000 g_file_storage gadget: bulk-out, length 0: g_file_storage gadget: bulk_out_complete -- 0, 0/31 [start_transfer] 43425355 c5 ept1 out queue len 0x200, buffer 0xc133c000 g_file_storage gadget: bulk-out, length 0: g_file_storage gadget: bulk_out_complete -- 0, 0/31 [start_transfer] 43425355 c5 ept1 out queue len 0x200, buffer 0xc133c000 g_file_storage gadget: bulk-out, length 0: g_file_storage gadget: bulk_out_complete -- 0, 0/31 [start_transfer] 43425355 c5 ept1 out queue len 0x200, buffer 0xc133c000 g_file_storage gadget: bulk-out, length 0: usbmon_write_gadget2.log Description: Binary data
Re: Linux USB file storage gadget with new UDC
Hi, From the usbmon trace and driver log, i can only see that TEST UNIT READY command is sent out but UDC driver does not receive it. May i ask, under what circumstances, is gadget driver calling start_transfer() to schedule reading from bulk-out endpoint ? file_storage.c calls start_transfer() whenever it expects the host to send a bulk-out packet. These times include: When the gadget is waiting for the host to send a CBW packet containing a SCSI command; I think the get_next_command() calls start_transfer() to read the next CBW. After unknown command 0xa1 is received, and if UDC driver doesn't halt the endpoint, why the get_next_command() does not call start_transfer() to read the next CBW? Somehow, i don't understand. Thanks, victor -- To unsubscribe from this list: send the line unsubscribe linux-usb in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
Re: Linux USB file storage gadget with new UDC
Hi, I think the get_next_command() calls start_transfer() to read the next CBW. After unknown command 0xa1 is received, and if UDC driver doesn't halt the endpoint, why the get_next_command() does not call start_transfer() to read the next CBW? Somehow, i don't understand. I think that the previous call to start_transfer() never returned. Probably because the usb_ep_queue() routine got hung up. Therefore get_next_command() wasn't executed. Here's an extract from the log you posted, showing the 0xa1 command: [start_transfer] f 40a08 ept1 out queue len 0x200, buffer 0xc12ac000 g_file_storage gadget: bulk-out, length 31: : 55 53 42 43 12 00 00 00 00 02 00 00 80 00 0c a1 0010: 08 2e 00 01 00 00 00 00 ec 00 00 00 f8 9e 34 bulk_out_complete -- 0, 31/31 g_file_storage gadget: SCSI command: Unknown xa1; Dc=12, Du=0; Hc=12, Hi=512 g_file_storage gadget: bulk-in, length 0: [start_transfer] 43425355 12 ept1 in queue len 0x0, buffer 0xc12ac000 g_file_storage gadget: bulk-in set halt I think here is the problem: the bulk-in of length 0. This zero length packet is never sent out nor received by the host. What is this zero length packet? kagen2_set_halt 1 1 g_file_storage gadget: sending command-failure status g_file_storage gadget: sense data: SK x05, ASC x20, ASCQ x00; info x0 g_file_storage gadget: bulk-in, length 13: : 55 53 42 53 12 00 00 00 00 02 00 00 01 [start_transfer] 53425355 12 ept1 in queue len 0xd, buffer 0xc133c000 0: 0x53425355 4: 0x12 8: 0x200 In comparison, the CSW is sent out and received by the host. It looks like the UDC driver get hung up right here, somewhere inside the usb_ep_queue() routine. I think the usb_ep_queue() routine is re-entrant. If one instance of it hangs, the next instance will not be affected. At this point, the host got tired of waiting for the gadget to accept the next CBW, so it issued a port reset. Yes, i fully agree! Thanks, victor -- To unsubscribe from this list: send the line unsubscribe linux-usb in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
Re: Linux USB file storage gadget with new UDC
Hi, Here are another problem. In usbmon trace, the time difference between first SCSI_INQUIRY command and the second TEST_UNIT_READY command is large. So i check the driver log file. When SCSI_INQUIRY is received, start_transfer() is called, then UDC ep_queue function is called, then bulk_out_complete() is called. This sequence is repeated many times. In fact, this problem starts even _before_ the INQUIRY command is received. The log shows that the UDC driver calls the bulk_out_complete routine over and over, even though no packet was received and ka2000_ack_irq didn't run. The same thing happens after the INQUIRY is received. The UDC driver is not supposed to call bulk_out_complete until a transfer has completed. After the gadget was reset, the problem didn't occur any more. Looking at the log, the UDC driver queue function is called repeatedly by start_transfer() before SCSI_INQUIRY is received. Is this ok? [start_transfer] ebfe e5943010 ept1 out queue len 0x200, buffer 0xc133c000 bulk_out_complete -- 0, 0/31 Thanks! This packet is the CSW to the unknown SCSI command 0xa1. So it should not be sent at all, and the UDC driver should send the STALL packet instead of this CSW? No. As long as the Halt feature is set for the bulk-in endpoint, the UDC should send STALL packets. When the host clears the Halt feature, then the UDC should send the CSW packet. Just curious, after this 0xa1 is received and bulk-in endpoint is halted. The Linux host tries to send TEST_UNIT_READY command, and UDC driver could not receive it because endpoint is halted and in reset condition. That sounds very wrong. The bulk-IN endpoint was halted, but the TEST UNIT READY command is sent to the bulk-OUT endpoint. There should be no problem receiving it. When debugging the UDC driver halt problem, i disable setting the halt feature for bulk-in endpoint and does not call fsg_disconnect() when reset interrupt occurs. Now when unknown SCSI command 0xa1 is received, the usbmon trace still shows the same error, and subsequent TEST_UNIT_READY is not received by UDC driver, and (-104) is connection reset error. It seems that UDC and gadget driver somehow still reset the USB connection? Driver has to reset the USB connection when unknown SCSI command is received? f3a2b7c0 486132750 S Bo:2:060:1 -115 31 = 55534243 1200 0002 8ca1 082e0001 ec00 00 f3a2b7c0 486132805 C Bo:2:060:1 0 31 f2c92340 486132814 S Bi:2:060:1 -115 512 f2c92340 486236946 C Bi:2:060:1 -121 13 = 55534253 1200 0002 01 f3a2b7c0 486237000 S Bi:2:060:1 -115 13 f3a2b7c0 493408020 C Bi:2:060:1 -104 0 . f3a2b7c0 493652682 S Bo:2:060:1 -115 31 = 55534243 1300 0600 00 f3a2b7c0 493652755 C Bo:2:060:1 0 31 f3a2b7c0 493652761 S Bi:2:060:1 -115 13 f3a2b7c0 503652077 C Bi:2:060:1 -104 0 Thanks, victor -- To unsubscribe from this list: send the line unsubscribe linux-usb in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
Re: Linux USB file storage gadget with new UDC
Hi, Thanks, i print out additional information in gadget driver and UDC driver. Here are another problem. In usbmon trace, the time difference between first SCSI_INQUIRY command and the second TEST_UNIT_READY command is large. So i check the driver log file. When SCSI_INQUIRY is received, start_transfer() is called, then UDC ep_queue function is called, then bulk_out_complete() is called. This sequence is repeated many times. In fact, this problem starts even _before_ the INQUIRY command is received. The log shows that the UDC driver calls the bulk_out_complete routine over and over, even though no packet was received and ka2000_ack_irq didn't run. The same thing happens after the INQUIRY is received. The UDC driver is not supposed to call bulk_out_complete until a transfer has completed. After the gadget was reset, the problem didn't occur any more. What is the reason that SCSI_INQUIRY is not processed by gadget driver? Is it due to some problem in UDC driver? The INQUIRY _was_ processed by the gadget driver. Yes, the UDC driver has a problem; see above. After that, i can see when the unknown command 0xa1 is received, the UDC driver sets the Halt feature. Look at line 1339 of the UDC log file: g_file_storage gadget: SCSI command: MODE SENSE(6); Dc=6, Di=192; Hc=6, Hi=192 g_file_storage gadget: bulk-in, length 16: : 0f 00 00 00 08 0a 04 00 ff ff 00 00 ff ff ff ff [start_transfer] f 40a08 ept1 in queue len 0x10, buffer 0xc12ac000 0: 0xf 4: 0x40a08 8: 0x c: 0x ka2000_ack_irq(32) bulk_in_complete -- 0, 16/16 At this point the gadget driver tries to do a set-halt: g_file_storage gadget: bulk-in set halt kagen2_set_halt 1 1 When the Halt feature is set, the UDC is supposed to send a STALL packet to the host -- but it did not. Instead it sent this 13-byte bulk-IN packet. g_file_storage gadget: bulk-in, length 13: : 55 53 42 53 08 00 00 00 b0 00 00 00 00 [start_transfer] 53425355 8 ept1 in queue len 0xd, buffer 0xc133c000 0: 0x53425355 4: 0x8 8: 0xb0 bulk_in_complete -- 0, 13/13 The same thing happened when the 0xA1 command was received: g_file_storage gadget: SCSI command: Unknown xa1; Dc=12, Du=0; Hc=12, Hi=512 g_file_storage gadget: bulk-in, length 0: [start_transfer] 43425355 12 ept1 in queue len 0x0, buffer 0xc12ac000 g_file_storage gadget: bulk-in set halt kagen2_set_halt 1 1 Right here, a STALL packet should have been sent. It wasn't. g_file_storage gadget: sending command-failure status g_file_storage gadget: sense data: SK x05, ASC x20, ASCQ x00; info x0 g_file_storage gadget: bulk-in, length 13: : 55 53 42 53 12 00 00 00 00 02 00 00 01 [start_transfer] 53425355 12 ept1 in queue len 0xd, buffer 0xc133c000 0: 0x53425355 4: 0x12 8: 0x200 bulk_in_complete -- 0, 13/13 Instead this packet was sent. Alan Stern Thanks! This packet is the CSW to the unknown SCSI command 0xa1. So it should not be sent at all, and the UDC driver should send the STALL packet instead of this CSW? Just curious, after this 0xa1 is received and bulk-in endpoint is halted. The Linux host tries to send TEST_UNIT_READY command, and UDC driver could not receive it because endpoint is halted and in reset condition. Seems like the set Halt feature is working (but STALL packet is not sent). victor -- To unsubscribe from this list: send the line unsubscribe linux-usb in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
Re: Linux USB file storage gadget with new UDC
Hi, I use kernel 3.4.4, the code in handle_stat1_irqs() is as below. There is no reset or disconnect member function in struct usb_gadget_driver in kernel 3.4.4. if (stat (1 SUSPEND_REQUEST_INTERRUPT)) { if (dev-driver-suspend) dev-driver-suspend (dev-gadget); if (!enable_suspend) stat = ~(1 SUSPEND_REQUEST_INTERRUPT); } else { if (dev-driver-resume) dev-driver-resume (dev-gadget); /* at high speed, note erratum 0133 */ } Okay. I have a hard enough time remembering how the kernel works now; I can't afford to remember how it worked five releases ago. :-) In the 3.4 kernel, when either a reset or a disconnect occurs, the UDC driver should call the gadget driver's -disconnect handler. Another usbmon trace showing 3 SCSI_READ_10 command. This trace shows that the READ(10) commands worked correctly. Good. But it also shows that the gadget did not respond correctly to the 0xA1 command near the end. The UDC was supposed to set the Halt feature for the bulk-in endpoint and send a STALL packet, but it didn't. In gadget driver, when do_scsi_command() receives an unknown command, the return value is -EINVAL. No, the return value is 0. Read the last line of do_scsi_command(): return 0; Will this value be returned to UDC driver, so that UDC driver can set the Halt feature for the bulk-in endpoint and send a STALL packet? For now, UDC driver does not set Halt when unknown SCSI command is received. Look at finish_reply(), near the end of the DATA_DIR_TO_HOST case: /* * For Bulk-only, mark the end of the data with a short * packet. If we are allowed to stall, halt the bulk-in * endpoint. (Note: This violates the Bulk-Only Transport * specification, which requires us to pad the data if we * don't halt the endpoint. Presumably nobody will mind.) */ else { bh-inreq-zero = 1; start_transfer(fsg, fsg-bulk_in, bh-inreq, bh-inreq_busy, bh-state); fsg-next_buffhd_to_fill = bh-next; if (mod_data.can_stall) rc = halt_bulk_in_endpoint(fsg); } And read the fist line in halt_bulk_in_endpoint(): rc = fsg_set_halt(fsg, fsg-bulk_in); And finally, read the last line of fsg_set_halt(): return usb_ep_set_halt(ep); That's when your UDC is supposed to set the Halt feature -- when its usb_ep_set_halt() function is called. If the controller is busy at this time because the bulk-in buffer is full, and it is unable to set the Halt feature, then usb_ep_set_halt() should return -EAGAIN -- see the documentation for usb_ep_set_halt in include/linux/usb/gadget.h. Alan Stern Thanks for the detailed write-up. I have checked the UDC driver set_halt(), it is called by the gadget driver. The full ascii text of usbmon trace for one usb session is also attached. This usbmon trace shows a few EOVERFLOW(-75) error. I don't know why EOVERFLOW error happened. victor scsi_read_10_again10.log Description: Binary data
Re: Linux USB file storage gadget with new UDC
Hi, Thanks for the detailed write-up. I have checked the UDC driver set_halt(), it is called by the gadget driver. The full ascii text of usbmon trace for one usb session is also attached. This usbmon trace shows a few EOVERFLOW(-75) error. I don't know why EOVERFLOW error happened. Because your UDC driver sent a packet that was too big. Here's the first example from the trace: f3a2b6c0 3633034189 S Bo:2:036:1 -115 31 = 55534243 0600 0600 00 f3a2b6c0 3633034326 C Bo:2:036:1 0 31 f3a2b6c0 3633034518 S Bi:2:036:1 -115 13 f3a2b6c0 3633040328 C Bi:2:036:1 -75 0 The first two lines show the host sending a TEST UNIT READY command. The third line shows the host waiting for a 13-byte CSW data packet. The -75 error means that the UDC sent back a data packet containing more than 13 bytes. Alan Stern Thanks, i do not know why UDC sent back a data packet containing more than 13 bytes in response to TEST UNIT READY command. Here is another usbmon trace attached in this email. There are two issues in this usbmon trace. Firstly, the CSW that is sent back in response to SCSI_READ_10 is wrong (wrong tag). f2c92340 2379075608 S Bo:2:047:1 -115 31 = 55534243 1100 0010 8a28 0008 00 f2c92340 2379075737 C Bo:2:047:1 0 31 f2c92ac0 2379075746 S Bi:2:047:1 -115 4096 f2c92ac0 2382204478 C Bi:2:047:1 0 4096 = f2c92340 2382204489 S Bi:2:047:1 -115 13 f2c92340 2382210596 C Bi:2:047:1 0 13 = 55534253 1000 00 Secondly, this CSW shows remote I/O error (-121). f2c92340 2382422538 S Bo:2:047:1 -115 31 = 55534243 1200 0010 8a28 0008 00 f2c92340 2382422588 C Bo:2:047:1 0 31 f3a2b5c0 2382422596 S Bi:2:047:1 -115 4096 f3a2b5c0 2382448965 C Bi:2:047:1 -121 13 = 55534253 1200 0010 01 f2c92340 2382448977 S Bi:2:047:1 -115 13 I am lost. Every time i connect Linux host to the USB gadget, different error scenario is shown in usbmon. victor scsi_read_10_again11.log Description: Binary data
Re: Linux USB file storage gadget with new UDC
Hi, Earlier, i used file=/dev/mmcblk0p1. Now i use file=/mnt/sd/backing_file. This backing_file is a dummy file system that i created. I attached two jpeg files. One show the MBR and Boot Sector of the backing_file. Another shows the usbmon of the Linux Host Why did you send jpeg files? Plain text files are a lot easier to work with. Now I can't copy and paste the lines from your files into this email message. :-( PC. I also attached the udc log which shows the MBR and Boot Sector content which are read from the backing_file. The UDC log indicates that the MBR and boot sectors were read correctly. From the usbmon jpeg, that first SCSI_READ_10 command got a overflow error, the second SCSI_READ_10 command got a connection reset error. Is the overflow error occurred because the host PC cannot handle the data returned from the gadget device? The usbmon log shows that the host sent the gadget a READ(10) command for 8 sectors, which 4096 bytes. It then requested a 4096-byte transfer on the bulk-in endpoint, expecting the gadget to reply with eight packets, each containing 512 bytes (because the bulk-in wMaxPacketSize is 512). But the gadget did not reply correctly. The UDC sent a data packet containing only 256 bytes, instead of 512 bytes. The overflow occurred when it sent a second data packet, again containing the wrong number of bytes. Call the gadget driver's -reset handler. If the -reset pointer is NULL, call the -disconnect handler instead. See the code in net2280.c's handle_stat1_irqs() as an example. Alan Stern i read the net2280.c code. Is it the usb_reset() function, called by stop_activity()? I am sorry if i understand incorrectly. No, it is the handle_stat1_irqs() function, as I wrote above. In particular, this part of the code, which handles both disconnects and resets: if (disconnect || reset) { stop_activity(dev, dev-driver); ep0_start(dev); spin_unlock(dev-lock); if (reset dev-driver-reset) (dev-driver-reset)(dev-gadget); else (dev-driver-disconnect)(dev-gadget); spin_lock(dev-lock); return; } I use kernel 3.4.4, the code in handle_stat1_irqs() is as below. There is no reset or disconnect member function in struct usb_gadget_driver in kernel 3.4.4. if (stat (1 SUSPEND_REQUEST_INTERRUPT)) { if (dev-driver-suspend) dev-driver-suspend (dev-gadget); if (!enable_suspend) stat = ~(1 SUSPEND_REQUEST_INTERRUPT); } else { if (dev-driver-resume) dev-driver-resume (dev-gadget); /* at high speed, note erratum 0133 */ } Another usbmon trace showing 3 SCSI_READ_10 command. This trace shows that the READ(10) commands worked correctly. Good. But it also shows that the gadget did not respond correctly to the 0xA1 command near the end. The UDC was supposed to set the Halt feature for the bulk-in endpoint and send a STALL packet, but it didn't. In gadget driver, when do_scsi_command() receives an unknown command, the return value is -EINVAL. Will this value be returned to UDC driver, so that UDC driver can set the Halt feature for the bulk-in endpoint and send a STALL packet? For now, UDC driver does not set Halt when unknown SCSI command is received. Thanks, victor -- To unsubscribe from this list: send the line unsubscribe linux-usb in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
Re: Linux USB file storage gadget with new UDC
Hi, Now i insmod g_file_storage gadget with file=/mnt/sd/backing_file, the SCSI_READ_10 command is still not working properly. What makes you think that? Because the SCSI_READ_10 is able to read the MBR from the backing file, and after that, SCSI_READ_10 reads all zeroes (fails to read boot sector). g_file_storage gadget: ep0-setup, length 8: : 80 06 00 01 00 00 40 00 g_file_storage gadget: get device descriptor But something is definitely wrong here. Before sending this Get-Device-Descriptor request, the host should have done a USB port reset. Either the host isn't performing the reset correctly or else your UDC driver didn't inform g_file_storage when the reset occurred. Yes, the UDC driver didn't inform g_file_storage when the reset occurred. What is to be done to inform g_file_storage when the reset occurs? Thanks, victor -- To unsubscribe from this list: send the line unsubscribe linux-usb in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
Re: Linux USB file storage gadget with new UDC
Hi, the parameter is file=/dev/mmcblk0p1 Perhaps you have already realized this... mmcblk0p1 is the first partition of the mmcblk0 device. Block 0 of the partition is the boot sector, not the MBR. The MBR is block 0 of the mmcblk0 device. So perhaps you really meant to use: file=/dev/mmcblk0 I see a problem here. The first 32 bytes of the boot sector is correct. The rest of the bytes are , which is wrong. See the usbmon trace below. Are you certain this is wrong? All those 0's could be unoccupied entries in a FAT. For testing purpose, i would like to create a backing file, and then use it with g_file_storage, such as below: # modprobe g_file_storage file=/tmp/backing_file Can i use an ordinary text file as the backing file? I find a link which contains answers to my question above. http://www.linux-usb.org/gadget/file_storage.html Now i insmod g_file_storage gadget with file=/mnt/sd/backing_file, the SCSI_READ_10 command is still not working properly. See the gadget log below. The g_file_storage gadget receives SCSI command: Unknown xa1 from the Linux host near the end of the log. Something is wrong. Thanks, victor g_file_storage gadget: ep0-setup, length 8: : 80 06 00 01 00 00 12 00 g_file_storage gadget: get device descriptor g_file_storage gadget: ep0-in, length 18: : 12 01 00 02 00 00 00 40 25 05 a5 a4 33 03 01 02 0010: 00 01 g_file_storage gadget: ep0-setup, length 8: : 80 06 00 02 00 00 20 00 g_file_storage gadget: get configuration descriptor g_file_storage gadget: ep0-in, length 32: : 09 02 20 00 01 01 04 c0 01 09 04 00 00 02 08 06 0010: 50 05 07 05 81 02 00 02 00 07 05 01 02 00 02 01 g_file_storage gadget: ep0-setup, length 8: : 00 09 01 00 00 00 00 00 g_file_storage gadget: set configuration 0010: 00 00 00 24 00 00 00 00 00 00 00 00 07 00 00 g_file_storage gadget: reset config g_file_storage gadget: reset interface g_file_storage gadget: set interface 0 g_file_storage gadget: high-speed config #1 g_file_storage gadget: bulk-out, length 31: : 55 53 42 43 02 00 00 00 00 00 00 00 00 00 06 00 0010: 00 00 00 00 00 00 00 00 00 00 00 00 07 00 00 g_file_storage gadget: SCSI command: TEST UNIT READY; Dc=6, Dn=0; Hc=6, Hn=0 attention condition g_file_storage gadget: sending command-failure status g_file_storage gadget: sense data: SK x06, ASC x29, ASCQ x00; info x0 g_file_storage gadget: bulk-in, length 13: : 55 53 42 53 02 00 00 00 00 00 00 00 01 g_file_storage gadget: bulk-out, length 31: : 55 53 42 43 03 00 00 00 12 00 00 00 80 00 06 03 0010: 00 00 00 12 00 00 00 00 00 00 00 00 74 f9 02 g_file_storage gadget: SCSI command: REQUEST SENSE; Dc=6, Di=18; Hc=6, Hi=18 g_file_storage gadget: bulk-in, length 18: : 70 00 06 00 00 00 00 0a 00 00 00 00 29 00 00 00 0010: 00 00 g_file_storage gadget: bulk-in, length 13: : 55 53 42 53 03 00 00 00 00 00 00 00 00 g_file_storage gadget: bulk-out, length 31: : 55 53 42 43 04 00 00 00 00 00 00 00 00 00 06 00 0010: 00 00 00 00 00 00 00 00 00 00 00 00 74 f9 02 g_file_storage gadget: SCSI command: TEST UNIT READY; Dc=6, Dn=0; Hc=6, Hn=0 g_file_storage gadget: bulk-in, length 13: : 55 53 42 53 04 00 00 00 00 00 00 00 00 g_file_storage gadget: bulk-out, length 31: : 55 53 42 43 05 00 00 00 24 00 00 00 80 00 06 12 0010: 00 00 00 24 00 00 00 00 00 00 00 00 74 f9 02 g_file_storage gadget: SCSI command: INQUIRY; Dc=6, Di=36; Hc=6, Hi=36 g_file_storage gadget: bulk-in, length 36: : 00 00 02 02 1f 00 00 00 4c 69 6e 75 78 20 20 20 0010: 46 69 6c 65 2d 53 74 6f 72 20 47 61 64 67 65 74 0020: 30 33 33 33 g_file_storage gadget: bulk-in, length 13: : 55 53 42 53 05 00 00 00 00 00 00 00 00 g_file_storage gadget: bulk-out, length 31: : 55 53 42 43 06 00 00 00 00 00 00 00 00 00 06 00 0010: 00 00 00 00 00 00 00 00 00 00 00 00 74 f9 02 g_file_storage gadget: SCSI command: TEST UNIT READY; Dc=6, Dn=0; Hc=6, Hn=0 g_file_storage gadget: bulk-in, length 13: : 55 53 42 53 06 00 00 00 00 00 00 00 00 g_file_storage gadget: bulk-out, length 31: : 55 53 42 43 07 00 00 00 08 00 00 00 80 00 0a 25 0010: 00 00 00 00 00 00 00 00 00 00 00 00 74 f9 02 g_file_storage gadget: SCSI command: READ CAPACITY; Dc=10, Di=8; Hc=10, Hi=8 g_file_storage gadget: bulk-in, length 8: : 00 00 07 ff 00 00 02 00 g_file_storage gadget: bulk-in, length 13: : 55 53 42 53 07 00 00 00 00 00 00 00 00 g_file_storage gadget: bulk-out, length 31: : 55 53 42 43 08 00 00 00 c0 00 00 00 80 00 06 1a 0010: 00 3f 00 c0 00 00 00 00 00 00 00 00 74 f9 02 g_file_storage gadget: SCSI command: MODE SENSE(6); Dc=6, Di=192; Hc=6, Hi=192 g_file_storage gadget: bulk-in, length 16: : 0f 00 00 00 08 0a 04 00 ff ff 00 00 ff ff ff ff g_file_storage gadget: bulk-in set halt g_file_storage gadget: bulk-in, length 13: : 55 53 42 53 08 00 00 00 b0 00 00 00
Re: Linux USB file storage gadget with new UDC
Hi, It looks like the data is wrong, but I have no way of knowing what the data actually should be. Only you know that. f31a9740 4037054141 S Bo:2:071:1 -115 31 = 55534243 0c00 0010 8a28 0008 00 f31a9740 4037054176 C Bo:2:071:1 0 31 f4a555c0 4037054184 S Bi:2:071:1 -115 4096 f4a555c0 4037108430 C Bi:2:071:1 0 4096 = eb58904d 53444f53 352e3000 02402e11 0200 00f8 3f00ff00 0020 Is this different from what you have in the first 32 bytes of your backing file? If it is then your UDC driver is not sending the correct buffer data to the host. The first 32 bytes data is correct. It is the first 32 bytes content of the FAT boot record. I observed further, when first SCSI_READ_10 command is sent with LBA of zero, and the file_offset_tmp of vfs_read() in do_read() is passed in as 0. It reaches SD driver with argument of 0x2002, . Somehow, the address got passed wrongly in the processing of it. In this case, 0x2000 is the FAT boot sector. Shouldn't gadget driver read from MBR (master boot record) as LBA of zero corresponds to MBR? The gadget driver reads from whatever you tell it to read. When you load g-file-storage, what parameters do you put in the modprobe command? Alan Stern the parameter is file=/dev/mmcblk0p1 I see a problem here. The first 32 bytes of the boot sector is correct. The rest of the bytes are , which is wrong. See the usbmon trace below. f59e13c0 2704842730 S Bo:2:007:1 -115 31 = 55534243 2100 0080 8a28 0020 0040 00 f59e13c0 2704842836 C Bo:2:007:1 0 31 f319db40 2704842846 S Bi:2:007:1 -115 4096 f59e16c0 2704842848 S Bi:2:007:1 -115 4096 f59e14c0 2704842850 S Bi:2:007:1 -115 4096 f59e1240 2704842851 S Bi:2:007:1 -115 4096 f59e15c0 2704842852 S Bi:2:007:1 -115 4096 f59e1340 2704842853 S Bi:2:007:1 -115 4096 f59e12c0 2704842854 S Bi:2:007:1 -115 4096 f59e1540 2704842855 S Bi:2:007:1 -115 4096 f319db40 2705432226 C Bi:2:007:1 0 4096 = e52d424f 4f542020 42494e20 1886fc80 7c417c41 838a 7b410300 94b80200 f59e16c0 2705432230 C Bi:2:007:1 0 4096 = f59e14c0 2705432231 C Bi:2:007:1 0 4096 = f59e1240 2705432231 C Bi:2:007:1 0 4096 = f59e15c0 2705432232 C Bi:2:007:1 0 4096 = f59e1340 2705432233 C Bi:2:007:1 0 4096 = f59e12c0 2705432234 C Bi:2:007:1 0 4096 = f59e1540 2705432234 C Bi:2:007:1 0 4096 = f59e13c0 2705432244 S Bi:2:007:1 -115 13 f59e13c0 2705438346 C Bi:2:007:1 0 13 = 55534253 2100 00 Thanks, victor -- To unsubscribe from this list: send the line unsubscribe linux-usb in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
Re: Linux USB file storage gadget with new UDC
Hi, the parameter is file=/dev/mmcblk0p1 Perhaps you have already realized this... mmcblk0p1 is the first partition of the mmcblk0 device. Block 0 of the partition is the boot sector, not the MBR. The MBR is block 0 of the mmcblk0 device. So perhaps you really meant to use: file=/dev/mmcblk0 I see a problem here. The first 32 bytes of the boot sector is correct. The rest of the bytes are , which is wrong. See the usbmon trace below. Are you certain this is wrong? All those 0's could be unoccupied entries in a FAT. For testing purpose, i would like to create a backing file, and then use it with g_file_storage, such as below: # modprobe g_file_storage file=/tmp/backing_file Can i use an ordinary text file as the backing file? Thanks, victor -- To unsubscribe from this list: send the line unsubscribe linux-usb in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
Re: Linux USB file storage gadget with new UDC
Hi, the parameter is file=/dev/mmcblk0p1 Perhaps you have already realized this... mmcblk0p1 is the first partition of the mmcblk0 device. Block 0 of the partition is the boot sector, not the MBR. The MBR is block 0 of the mmcblk0 device. So perhaps you really meant to use: file=/dev/mmcblk0 I see a problem here. The first 32 bytes of the boot sector is correct. The rest of the bytes are , which is wrong. See the usbmon trace below. Are you certain this is wrong? All those 0's could be unoccupied entries in a FAT. For testing purpose, i would like to create a backing file, and then use it with g_file_storage, such as below: # modprobe g_file_storage file=/tmp/backing_file Can i use an ordinary text file as the backing file? I find a link which contains answers to my question above. http://www.linux-usb.org/gadget/file_storage.html Thanks, victor -- To unsubscribe from this list: send the line unsubscribe linux-usb in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
Re: Linux USB file storage gadget with new UDC
Hi, Here is the fresh usbmon trace. Four SCSI commands are shown. The first SCSI_READ_10 command has LBA of 0. The second SCSI_READ_10 command has LBA of 0x00ed2900, which is wrong. Somehow, the first SCSI_READ_10 command got the wrong data, i think. Isn't it? It looks like the data is wrong, but I have no way of knowing what the data actually should be. Only you know that. f31a9740 4037054141 S Bo:2:071:1 -115 31 = 55534243 0c00 0010 8a28 0008 00 f31a9740 4037054176 C Bo:2:071:1 0 31 f4a555c0 4037054184 S Bi:2:071:1 -115 4096 f4a555c0 4037108430 C Bi:2:071:1 0 4096 = eb58904d 53444f53 352e3000 02402e11 0200 00f8 3f00ff00 0020 Is this different from what you have in the first 32 bytes of your backing file? If it is then your UDC driver is not sending the correct buffer data to the host. The first 32 bytes data is correct. It is the first 32 bytes content of the FAT boot record. I observed further, when first SCSI_READ_10 command is sent with LBA of zero, and the file_offset_tmp of vfs_read() in do_read() is passed in as 0. It reaches SD driver with argument of 0x2002, . Somehow, the address got passed wrongly in the processing of it. In this case, 0x2000 is the FAT boot sector. Shouldn't gadget driver read from MBR (master boot record) as LBA of zero corresponds to MBR? Thanks, victor -- To unsubscribe from this list: send the line unsubscribe linux-usb in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
Re: Linux USB file storage gadget with new UDC
Hi, It looks like the data is wrong, but I have no way of knowing what the data actually should be. Only you know that. f31a9740 4037054141 S Bo:2:071:1 -115 31 = 55534243 0c00 0010 8a28 0008 00 f31a9740 4037054176 C Bo:2:071:1 0 31 f4a555c0 4037054184 S Bi:2:071:1 -115 4096 f4a555c0 4037108430 C Bi:2:071:1 0 4096 = eb58904d 53444f53 352e3000 02402e11 0200 00f8 3f00ff00 0020 Is this different from what you have in the first 32 bytes of your backing file? If it is then your UDC driver is not sending the correct buffer data to the host. The first 32 bytes data is correct. It is the first 32 bytes content of the FAT boot record. I observed further, when first SCSI_READ_10 command is sent with LBA of zero, and the file_offset_tmp of vfs_read() in do_read() is passed in as 0. It reaches SD driver with argument of 0x2002, . Somehow, the address got passed wrongly in the processing of it. In this case, 0x2000 is the FAT boot sector. Shouldn't gadget driver read from MBR (master boot record) as LBA of zero corresponds to MBR? The gadget driver reads from whatever you tell it to read. When you load g-file-storage, what parameters do you put in the modprobe command? Alan Stern the parameter is file=/dev/mmcblk0p1 Thanks, victor -- To unsubscribe from this list: send the line unsubscribe linux-usb in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
Re: Linux USB file storage gadget with new UDC
Hi, Thanks. Working on this problem now. Another problem observed for SCSI_READ_10 command, when reading from the SD card, the gadget driver never sends the MBR address, the FAT boot record address, the start of FAT address, and the start of FAT cluster address to the SD card driver. The gadget doesn't make up addresses by itself. It always sends the address the host tells it to send. The address sent by gadget driver is wrong. Then the address sent by the host is wrong. However, I suspect you are mistaken. In your usbmon trace earlier, the very first READ(10) command had a logical block address of 0. That is the address of the MBR. If the driver hadn't failed at that point, the host would have gone on to ask for the address of the boot sector and other things. Yes, the very first READ(10) command has a logical block address of 0 (as shown below). I will generate the fresh usbmon trace the next day, i do not have access to the platform now. f59e13c0 3246885432 S Bo:2:046:1 -115 31 = 55534243 0c00 0010 8a28 0008 00 Here is the fresh usbmon trace. Four SCSI commands are shown. The first SCSI_READ_10 command has LBA of 0. The second SCSI_READ_10 command has LBA of 0x00ed2900, which is wrong. Somehow, the first SCSI_READ_10 command got the wrong data, i think. Isn't it? f31a9740 4037054141 S Bo:2:071:1 -115 31 = 55534243 0c00 0010 8a28 0008 00 f31a9740 4037054176 C Bo:2:071:1 0 31 f4a555c0 4037054184 S Bi:2:071:1 -115 4096 f4a555c0 4037108430 C Bi:2:071:1 0 4096 = eb58904d 53444f53 352e3000 02402e11 0200 00f8 3f00ff00 0020 f31a9740 4037108476 S Bi:2:071:1 -115 13 f31a9740 4037114564 C Bi:2:071:1 0 13 = 55534253 0c00 00 f31a9740 4037114722 S Bo:2:071:1 -115 31 = 55534243 0d00 0600 00 f31a9740 4037114801 C Bo:2:071:1 0 31 f31a9740 4037114805 S Bi:2:071:1 -115 13 f31a9740 4037121303 C Bi:2:071:1 0 13 = 55534253 0d00 00 f31a9740 4037121388 S Bo:2:071:1 -115 31 = 55534243 0e00 0800 8a25 00 f31a9740 4037121550 C Bo:2:071:1 0 31 f4a552c0 4037121559 S Bi:2:071:1 -115 8 f4a552c0 4037127426 C Bi:2:071:1 0 8 = 00ed29c7 0200 f31a9740 4037127435 S Bi:2:071:1 -115 13 f31a9740 4037133064 C Bi:2:071:1 0 13 = 55534253 0e00 00 f31a9740 4037133100 S Bo:2:071:1 -115 31 = 55534243 0f00 0010 8a28 ed29 0008 00 f31a9740 4037133176 C Bo:2:071:1 0 31 f4a552c0 4037133184 S Bi:2:071:1 -115 4096 f4a552c0 4037184441 C Bi:2:071:1 0 4096 = f31a9740 4037184453 S Bi:2:071:1 -115 13 f31a9740 4037190564 C Bi:2:071:1 0 13 = 55534253 0f00 00 Thanks, victor -- To unsubscribe from this list: send the line unsubscribe linux-usb in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
Re: Linux USB file storage gadget with new UDC
Hi, Thanks. Working on this problem now. Another problem observed for SCSI_READ_10 command, when reading from the SD card, the gadget driver never sends the MBR address, the FAT boot record address, the start of FAT address, and the start of FAT cluster address to the SD card driver. The gadget doesn't make up addresses by itself. It always sends the address the host tells it to send. The address sent by gadget driver is wrong. Then the address sent by the host is wrong. However, I suspect you are mistaken. In your usbmon trace earlier, the very first READ(10) command had a logical block address of 0. That is the address of the MBR. If the driver hadn't failed at that point, the host would have gone on to ask for the address of the boot sector and other things. Yes, the very first READ(10) command has a logical block address of 0 (as shown below). I will generate the fresh usbmon trace the next day, i do not have access to the platform now. f59e13c0 3246885432 S Bo:2:046:1 -115 31 = 55534243 0c00 0010 8a28 0008 00 Thanks, victor -- To unsubscribe from this list: send the line unsubscribe linux-usb in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
Re: Linux USB file storage gadget with new UDC
Hi, Here is the gadget log when receiving SCSI_READ_10 from Linux host. g_file_storage gadget: bulk-out, length 31: : 55 53 42 43 0f 00 00 00 00 10 00 00 80 00 0a 28 0010: 00 00 00 00 00 00 00 08 00 00 00 00 e0 f8 02 SCSI CDB: 28 00 00 00 00 00 00 00 08 00 g_file_storage gadget: SCSI command: READ(10); Dc=10, Di=4096; Hc=10, Hi=4096 driver read from SD card . g_file_storage gadget-lun0: file read 4096 @ 0 - 4096 READ_10 reply -5 *** printk added by me*** g_file_storage gadget: bulk-in, length 13: : 55 53 42 53 0f 00 00 00 00 00 00 00 00 This all looks right. There is a problem with SCSI_READ_10 command if looking at usbmon. I pasted the usbmon log that starts from SCSI_READ_10. Basically, the SCSI_READ_10 was received by gadget, processed, sent CSW, followed by control packets. Then another SCSI_READ_10, sent CSW, followed by control packets. Then another SCSI_READ_10, but CSW is not received by host. There must be problems in the UDC driver. CSW is sent by the UDC driver but it is not received by the Linux host. Thanks, victor f59e13c0 3246885432 S Bo:2:046:1 -115 31 = 55534243 0c00 0010 8a28 0008 00 f59e13c0 3246885582 C Bo:2:046:1 0 31 f59e15c0 3246885594 S Bi:2:046:1 -115 4096 f59e15c0 3247150217 C Bi:2:046:1 -75 0 f59e13c0 3247150291 S Bi:2:046:1 -115 13 f59e13c0 3247150450 C Bi:2:046:1 -75 0 f412a840 3247310347 S Ci:2:046:0 s 80 06 0100 0012 18 f412a840 3247313216 C Ci:2:046:0 0 18 = 12010002 0040 2505a5a4 33030102 0001 f412a840 3247313226 S Ci:2:046:0 s 80 06 0200 0020 32 f412a840 3247326452 C Ci:2:046:0 0 32 = 09022000 010104c0 01090400 00020806 50050705 81020002 00070501 02000201 f412a840 3247326511 S Co:2:046:0 s 00 09 0001 0 f412a840 3247339340 C Co:2:046:0 0 0 f59e13c0 3247345346 S Bo:2:046:1 -115 31 = 55534243 0d00 0010 8a28 0008 00 f59e13c0 3247345450 C Bo:2:046:1 0 31 f59e15c0 3247345461 S Bi:2:046:1 -115 4096 f59e15c0 3247352463 C Bi:2:046:1 -75 0 f59e13c0 3247352476 S Bi:2:046:1 -115 13 f59e13c0 3247352712 C Bi:2:046:1 0 0 f59e13c0 3247352720 S Bi:2:046:1 -115 13 f59e13c0 3247359080 C Bi:2:046:1 0 13 = 55534253 0c00 00 f412a840 3247529347 S Ci:2:046:0 s 80 06 0100 0012 18 f412a840 3247530463 C Ci:2:046:0 0 18 = 12010002 0040 2505a5a4 33030102 0001 f412a840 3247530476 S Ci:2:046:0 s 80 06 0200 0020 32 f412a840 3247543866 C Ci:2:046:0 0 32 = 09022000 010104c0 01090400 00020806 50050705 81020002 00070501 02000201 f412a840 3247543906 S Co:2:046:0 s 00 09 0001 0 f412a840 3247556713 C Co:2:046:0 0 0 f59e13c0 3247562349 S Bo:2:046:1 -115 31 = 55534243 0e00 0010 8a28 0008 00 f59e13c0 3247562449 C Bo:2:046:1 0 31 f59e15c0 3247562460 S Bi:2:046:1 -115 4096 f59e15c0 3278472491 C Bi:2:046:1 -104 0 -- To unsubscribe from this list: send the line unsubscribe linux-usb in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
Re: Linux USB file storage gadget with new UDC
Hi, Understand, UDC driver will call driver-setup(), and if the return value is negative, UDC driver has to set dev-protocol_stall = 1 and maybe call usb_ep_set_halt(). However, the hardware won't be able to send out zero length response. Don't be silly; of course it can. Nobody would be foolish enough to design a piece of USB hardware that couldn't send a zero-length DATA packet. I think the purpose of zero length response is to get an ACK from the host. The purpose of the zero-length response is to complete the Status stage of a control-OUT transfer. Thanks, the halt feature is ok now. The SCSI_READ_10 command has a problem. The reply value from do_read is -5, which means -EIO. The for(;;) loop in do_read() was probably broken at if (amount_left == 0). Is this if-statement valid? Here is the gadget log when receiving SCSI_READ_10 from Linux host. g_file_storage gadget: bulk-out, length 31: : 55 53 42 43 0f 00 00 00 00 10 00 00 80 00 0a 28 0010: 00 00 00 00 00 00 00 08 00 00 00 00 e0 f8 02 SCSI CDB: 28 00 00 00 00 00 00 00 08 00 g_file_storage gadget: SCSI command: READ(10); Dc=10, Di=4096; Hc=10, Hi=4096 driver read from SD card . g_file_storage gadget-lun0: file read 4096 @ 0 - 4096 READ_10 reply -5 *** printk added by me*** g_file_storage gadget: bulk-in, length 13: : 55 53 42 53 0f 00 00 00 00 00 00 00 00 Thanks, victor -- To unsubscribe from this list: send the line unsubscribe linux-usb in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
Re: Linux USB file storage gadget with new UDC
Hi, In the log file, is there any invalid request received on endpoint 0? In the usbmon file there is. It is this line: f4ae6f40 1217192721 S Co:2:018:0 s 21 ff 0 ok, i will add code to UDC to instruct hardware to send NAK upon receiving invalid request on endpoint 0. Does it mean that UDC driver has to check for invalid request on endpoint 0? No. The UDC driver has no way to know whether a request is valid or not. Read the description of the setup member of the usb_gadget_driver structure in the header file. I read that. The setup member of the usb_gadget_driver structure is pointing to fsg_setup, in file_storage.c. The fsg_setup() function handles the request on endpoint 0. So how could UDC driver know when to send NAK? Thanks, victor -- To unsubscribe from this list: send the line unsubscribe linux-usb in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
Re: Linux USB file storage gadget with new UDC
Hi, ok, i will add code to UDC to instruct hardware to send NAK upon receiving invalid request on endpoint 0. Does it mean that UDC driver has to check for invalid request on endpoint 0? No. The UDC driver has no way to know whether a request is valid or not. Read the description of the setup member of the usb_gadget_driver structure in the header file. I read that. The setup member of the usb_gadget_driver structure is pointing to fsg_setup, in file_storage.c. The fsg_setup() function handles the request on endpoint 0. So how could UDC driver know when to send NAK? When an invalid request is received, the gadget is supposed to send STALL, not NAK. See the last two lines of the setup description: * USB byte order. Called in_interrupt; this may not sleep. Driver * queues a response to ep0, or returns negative to stall. Driver ... returns negative to stall. That's how the UDC driver knows whether to send a STALL packet -- if the setup callback returns a negative value. Also, it looks like you didn't read this paragraph in the description of usb_ep_queue(): * Control endpoints ... after getting a setup() callback, the driver queues * one response (even if it would be zero length). That enables the * status ack, after transferring data as specified in the response. Setup * functions may return negative error codes to generate protocol stalls. * (Note that some USB device controllers disallow protocol stall responses * in some cases.) When control responses are deferred (the response is * written after the setup callback returns), then usb_ep_set_halt() may be * used on ep0 to trigger protocol stalls. Depending on the controller, * it may not be possible to trigger a status-stage protocol stall when the * data stage is over, that is, from within the response's completion * routine. Notice especially the fourth line. Alan Stern Understand, UDC driver will call driver-setup(), and if the return value is negative, UDC driver has to set dev-protocol_stall = 1 and maybe call usb_ep_set_halt(). However, the hardware won't be able to send out zero length response. I think the purpose of zero length response is to get an ACK from the host. Thanks, victor -- To unsubscribe from this list: send the line unsubscribe linux-usb in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
Re: Linux USB file storage gadget with new UDC
Hi, I have a serial console to access the platform. Today i use Linux as USB host. The log of the usb gadget is attached (gadget-log.txt). The Linux usbmon log file is also attached (usbmon-log.txt). Hopefully the log data will be useful. It looks like you cut out a lot of information from the gadget log. Please don't do that. The logs show that your driver still has several bugs. For example, the start of the gadget log shows that the driver thinks it received a bunch of packets on the bulk-out endpoint, but the usbmon log shows that the host never sent these packets. Your driver does not set the Halt feature for the bulk-in endpoint when it is supposed to. It doesn't even respond with NAK when it receives an invalid request on endpoint 0. When asked to transmit 4096 bytes of data, your driver sent a packet containing more than 512 bytes. I do not know when to set the Halt feature for the bulk-in endpoint. I see gadget code have this line printed out: g_file_storage gadget: bulk-in set halt In the log file, is there any invalid request received on endpoint 0? Regards, victor -- To unsubscribe from this list: send the line unsubscribe linux-usb in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
Re: Linux USB file storage gadget with new UDC
Hi, First you have to figure out why it isn't working. What does the debugging information show? Here is some debugging information: receive GET_DESCRIPTOR, 80, 6 index 0 value 200 len 20 receive SET_CONFIGURATION, 0, 9 index 0 value 1 len 0 set curlun-unit_attention_data to SS_NO_SENSE do_set_config() is called because of FSG_STATE_CONFIG_CHANGE do_set_interface() is called set curlun-unit_attention_data to SS_RESET_OCCURRED receive *UNKNOWN*, a1, fe index 0 value 0 len 1 receive SCSI Inquiry receive SCSI read format capacities, get attention condition, curlun-unit_attention_data is 062900 (SS_RESET_OCCURRED) Up to this point, everything is normal. We need to see what happens next. After the SS_RESET_OCCURRED attention condition, the debug information is: start_transfer is called the driver queue function is called start_transfer is called the driver queue function is called to send out CSW of 13 bytes driver receive EP1 IN interrupt bulk_in_complete is called get_next_command is called driver receive setup data valid interrupt receive GET_DESCRIPTOR, 80, 6 index 0 value 200 len 20 .many control transfers.. May i know if everything is normal here? Thanks, victor -- To unsubscribe from this list: send the line unsubscribe linux-usb in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
Re: Linux USB file storage gadget with new UDC
Hi, On Wed, Mar 20, 2013 at 10:22 PM, Alan Stern st...@rowland.harvard.edu wrote: On Wed, 20 Mar 2013, victor yeo wrote: Thanks, i add processing the pending data from FIFO after queue was called. The UDC driver can process the SCSI INQUIRY command and SCSI READ FORMAT CAPACITIES command now. In the processing of SCSI READ FORMAT CAPACITIES command, there is attention condition. Then the bulk transfer stops completely and control transfer is repeated. What control transfer? those get descriptor requests. How can i solve it? First you have to figure out why it isn't working. What does the debugging information show? Here is some debugging information: receive GET_DESCRIPTOR, 80, 6 index 0 value 200 len 20 receive SET_CONFIGURATION, 0, 9 index 0 value 1 len 0 set curlun-unit_attention_data to SS_NO_SENSE do_set_config() is called because of FSG_STATE_CONFIG_CHANGE do_set_interface() is called set curlun-unit_attention_data to SS_RESET_OCCURRED receive *UNKNOWN*, a1, fe index 0 value 0 len 1 receive SCSI Inquiry receive SCSI read format capacities, get attention condition, curlun-unit_attention_data is 062900 (SS_RESET_OCCURRED) The gadget code is able to process SCSI Inquiry because it does not fulfill the if-condition: if (curlun curlun-unit_attention_data != SS_NO_SENSE fsg-cmnd[0] != INQUIRY fsg-cmnd[0] != REQUEST_SENSE) { Why is curlun-unit_attention_data set to SS_RESET_OCCURRED? Regards, Victor -- To unsubscribe from this list: send the line unsubscribe linux-usb in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
Re: Linux USB file storage gadget with new UDC
Hi, On Fri, Mar 15, 2013 at 01:59:30PM +0800, victor yeo wrote: For bulk transfer, the new UDC driver has one problem. When SCSI Inquiry command is received, the UDC driver interrupt routine will receive it first. However, the queue function is not yet called, and queue buffer is not yet added. Thus, interrupt routine is not able to store the SCSI Inquiry command to the queue buffer. This is a serious problem, what is the way to synchronise UDC driver and file storage gadget driver for SCSI command bulk transfer? don't process the interrupt until you receive a queue. Data will be pending in controller's FIFO until then. change to do exactly that, bulk transfer interrupt come in, don't process, then queue function is called to add queue buffer. After that, no more bulk transfer interrupt come in. regards, victor -- To unsubscribe from this list: send the line unsubscribe linux-usb in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
Re: Linux USB file storage gadget with new UDC
Hi, For bulk transfer, the new UDC driver has one problem. When SCSI Inquiry command is received, the UDC driver interrupt routine will receive it first. However, the queue function is not yet called, and queue buffer is not yet added. Thus, interrupt routine is not able to store the SCSI Inquiry command to the queue buffer. This is a serious problem, what is the way to synchronise UDC driver and file storage gadget driver for SCSI command bulk transfer? Regards, Victor -- To unsubscribe from this list: send the line unsubscribe linux-usb in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
Re: Linux USB file storage gadget with new UDC
Hi, Thanks, i added in UDC driver to call bulk_in_complete for every request over a bulk in ep, now the gadget driver is able to process UDC shouldn't call bulk_in_complete() directly, you should be calling request-complete() instead. Yes, the UDC driver calls the request-complete() which in turn calls the bulk_in_complete(). I am sorry my writing is not clear. When it comes to SCSI Read Format Capacities command, the gadget driver gives attention condition error in check_command() in the code snippet below, and the command is not processed by do_read_format_capacities(). if (curlun curlun-unit_attention_data != SS_NO_SENSE fsg-cmnd[0] != INQUIRY fsg-cmnd[0] != REQUEST_SENSE) { curlun-sense_data = curlun-unit_attention_data; curlun-unit_attention_data = SS_NO_SENSE; return -EINVAL; } Besides the code snippet, the only place that sets unit_attention data to SS_NO_SENSE is in handle_exception(). How is UDC driver able to overcome this problem? SCSI READ CAPACITY also has the same attention condition problem. What can i do now? Victor -- To unsubscribe from this list: send the line unsubscribe linux-usb in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
Re: Linux USB file storage gadget with new UDC
Hi, Thanks, i added in UDC driver to call bulk_in_complete for every request over a bulk in ep, now the gadget driver is able to process the SCSI Inquiry command. When it comes to SCSI Read Format Capacities command, the gadget driver gives attention condition error in check_command() in the code snippet below, and the command is not processed by do_read_format_capacities(). if (curlun curlun-unit_attention_data != SS_NO_SENSE fsg-cmnd[0] != INQUIRY fsg-cmnd[0] != REQUEST_SENSE) { curlun-sense_data = curlun-unit_attention_data; curlun-unit_attention_data = SS_NO_SENSE; return -EINVAL; } Besides the code snippet, the only place that sets unit_attention data to SS_NO_SENSE is in handle_exception(). How is UDC driver able to overcome this problem? What problem? This all sounds perfectly normal. Maybe you should post the kernel debugging log. The problem is READ FORMAT CAPACITIES command is not processed, and no reply is sent back in response to the command. the kernel log does not show any error that is related to SCSI commands. thanks, victor -- To unsubscribe from this list: send the line unsubscribe linux-usb in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
Re: Linux USB file storage gadget with new UDC
Hi, How to set bh-state to BUF_STATE_EMPTY after the buffer is processed? It gets set to BUF_STATE_EMPTY in several different places, depending on the purpose the buffer was used for. See bulk_in_complete (your UDC driver should call this routine for every request over a bulk-IN endpoint, when it is safe for the gadget driver to overwrite the data in the transfer buffer and re-use the request). See also get_next_command, the line just after the call to received_cbw. Thanks, i added in UDC driver to call bulk_in_complete for every request over a bulk in ep, now the gadget driver is able to process the SCSI Inquiry command. When it comes to SCSI Read Format Capacities command, the gadget driver gives attention condition error in check_command() in the code snippet below, and the command is not processed by do_read_format_capacities(). if (curlun curlun-unit_attention_data != SS_NO_SENSE fsg-cmnd[0] != INQUIRY fsg-cmnd[0] != REQUEST_SENSE) { curlun-sense_data = curlun-unit_attention_data; curlun-unit_attention_data = SS_NO_SENSE; return -EINVAL; } Besides the code snippet, the only place that sets unit_attention data to SS_NO_SENSE is in handle_exception(). How is UDC driver able to overcome this problem? victor -- To unsubscribe from this list: send the line unsubscribe linux-usb in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
Re: Linux USB file storage gadget with new UDC
Hi, How to set bh-state to BUF_STATE_EMPTY after the buffer is processed? It gets set to BUF_STATE_EMPTY in several different places, depending on the purpose the buffer was used for. See bulk_in_complete (your UDC driver should call this routine for every request over a bulk-IN endpoint, when it is safe for the gadget driver to overwrite the data in the transfer buffer and re-use the request). See also get_next_command, the line just after the call to received_cbw. Thanks, i added in UDC driver to call bulk_in_complete for every request over a bulk in ep, now the gadget driver is able to process UDC shouldn't call bulk_in_complete() directly, you should be calling request-complete() instead. Yes, the UDC driver calls the request-complete() which in turn calls the bulk_in_complete(). I am sorry my writing is not clear. victor -- To unsubscribe from this list: send the line unsubscribe linux-usb in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
Re: Linux USB file storage gadget with new UDC
Hi, In the udc driver, i can't assign a single ep0 descriptor to both ep0_in_desc and ep0_out_desc. i think i should skip ep0_out_desc. Bear in mind that i only define 3 endpoints in udc driver: ep0, ep1 bulk in, ep1 bulk out. Will it cause any problem to gadget driver? There is no such thing as an ep0 descriptor. Alan Stern When ep1 receives CBW data, the isr routine is called. Then in isr, to get the usb_request: usb_request * req; req = list_entry(dev-ep[2].queue.next, struct kagen2_request, queue); however, the list_empty(dev-ep[2].queue) is true. Where is the appropriate place to add list entry? thanks, victor -- To unsubscribe from this list: send the line unsubscribe linux-usb in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
Re: Linux USB file storage gadget with new UDC
Hi, When ep1 receives CBW data, the isr routine is called. Then in isr, to get the usb_request: usb_request * req; req = list_entry(dev-ep[2].queue.next, struct kagen2_request, queue); however, the list_empty(dev-ep[2].queue) is true. Where is the appropriate place to add list entry? only you will know, but your implementation of ep_queue is a nice bet. i have list_add_tail() in my ep_queue() function. Prior to ep1 receiving data, my ep_queue() is called to send 0x00 to ep0. then it is not called. how to make it to be called by file gadget, in order to queue the request before ep1 interrupt? victor -- To unsubscribe from this list: send the line unsubscribe linux-usb in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
Re: Linux USB file storage gadget with new UDC
Hi, i have list_add_tail() in my ep_queue() function. Prior to ep1 receiving data, my ep_queue() is called to send 0x00 to ep0. then it is not called. how to make it to be called by file gadget, in order to queue the request before ep1 interrupt? This should happen when get_next_command() calls start_transfer(), which calls usb_ep_queue(). I put printk in fsg_main_thread. After insmod g_file_storage, the fsg_main_thread goes to fsg-running. Then it sleeps. When ep1 receives data, get_next_command() is not called, so start_transfer() is not called. The fsg_main_thread is sleeping in sleep_thread(). How to make it wake up? is there anything udc driver has to do to wake up fsg_main_thread? thanks, victor -- To unsubscribe from this list: send the line unsubscribe linux-usb in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
Re: Linux USB file storage gadget with new UDC
Hi, Also, you shouldn't requeue the request yourself, gadget driver owns the request. which request do i requeue? please kindly point that out. Thanks! look at your code. Look what you do after you call complete. is it this code? i will remove the redundant code after complete. ka_ep_p-req.complete(ka_ep_p-ep, req-req); if (num == 0) { ka_ep_p-req.length = 0; usb_ep_queue(ka_ep_p-ep, req-req, 0); ka_ep_p-desc = ep0_in_desc; } you should delete the request from your list. Whatever you do, has to be undone. got it. i add list_del_init() to delete the request from the list. i read the net2272.c, the net2272_enable() is called by gadget driver enable_endpoint(). When i run the gadget driver, enable_endpoint() is called for fsg-bulk_in and fsg-bulk_out. The enable_endpoint() of fsg-intr_in is not called because transport_is_cbi() is false. So how can the endpoint 0 be enabled? endpoint 0 has to be always enabled by the UDC driver. Gadget driver expects endpoint 0 to be ready. i read through the net2272.c, i do not see where the endpoint 0 is enabled. I blindly enable my endpoint zero. i think my code is wrong. kagen2_ep_enable(ka_ep-ep, ep0_in_desc); kagen2_ep_enable(ka_ep-ep, ep0_out_desc); thanks, victor -- To unsubscribe from this list: send the line unsubscribe linux-usb in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
Re: Linux USB file storage gadget with new UDC
Hi, is it this code? i will remove the redundant code after complete. ka_ep_p-req.complete(ka_ep_p-ep, req-req); if (num == 0) { ka_ep_p-req.length = 0; usb_ep_queue(ka_ep_p-ep, req-req, 0); ka_ep_p-desc = ep0_in_desc; } you should delete the request from your list. Whatever you do, has to be undone. got it. i add list_del_init() to delete the request from the list. _init() is unnecessary i read the net2272.c, the net2272_enable() is called by gadget driver enable_endpoint(). When i run the gadget driver, enable_endpoint() is called for fsg-bulk_in and fsg-bulk_out. The enable_endpoint() of fsg-intr_in is not called because transport_is_cbi() is false. So how can the endpoint 0 be enabled? endpoint 0 has to be always enabled by the UDC driver. Gadget driver expects endpoint 0 to be ready. i read through the net2272.c, i do not see where the endpoint 0 is enabled. I blindly enable my endpoint zero. i think my code is wrong. kagen2_ep_enable(ka_ep-ep, ep0_in_desc); kagen2_ep_enable(ka_ep-ep, ep0_out_desc); yeah, you need to enabled it during driver initialization In the udc driver, i can't assign a single ep0 descriptor to both ep0_in_desc and ep0_out_desc. i think i should skip ep0_out_desc. Bear in mind that i only define 3 endpoints in udc driver: ep0, ep1 bulk in, ep1 bulk out. Will it cause any problem to gadget driver? thanks, victor -- To unsubscribe from this list: send the line unsubscribe linux-usb in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
Re: Linux USB file storage gadget with new UDC
Hi, i do not see where req-length is checked in gadget driver. It isn't _checked_; it is _set_ in set_bulk_out_req_length(). req-actual is checked in received_cbw(). g_file_storage gadget: ep0-setup, length 8: : 00 09 01 00 00 00 00 00 g_file_storage gadget: set configuration g_file_storage gadget: ep0-setup, length 8: : a1 fe 00 00 00 00 01 00 g_file_storage gadget: get max LUN g_file_storage gadget: ep0-in, length 1: : 00 g_file_storage gadget: bulk-out, length 31: : 55 53 42 43 a8 48 ed 86 24 00 00 00 80 00 06 12 0010: 00 00 00 24 00 00 00 00 00 00 00 00 00 00 00 g_file_storage gadget: bulk_out_complete -- 0, 31/0 Why is the bulk_out_intended_length field set to 0? Doesn't set_bulk_out_req_length() work right? today i changed my udc driver code, now the set_bulk_out_req_length() sets the bulk_out_intended_length to 512 byte. thanks, victor -- To unsubscribe from this list: send the line unsubscribe linux-usb in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
Re: Linux USB file storage gadget with new UDC
Hi, Ok, rephrase the question, is this the flow for bulk transfer? 1) data is received by Usb mass storage HW, the UDC driver ISR is called to read the data to usb_request buffer 2) bulk_out_complete() in gadget driver, is called to set buffer state to full 3) get_next_command() in gadget driver, is called to read the CBW. 4) do_scsi_command() to process SCSI command encoded in CBW 5) send_status() sends the CSW to host Something like below: OUT Token - ISR - giveback() - bulk_out_complete() - get_next_command() - do_scsi_command() - usb_ep_queue() - OUT/IN Token - ISR - bulk_out_complete() - send_status() For the IN Token, i will just write the data to the HW buffer, and the flow will go to send_status(). I use a different USB cable, now the USB gadget is able to receive bulk transfer data from host PC. I am working on the bulk transfer code. Thank you for the very useful answers. np In fsg_dev structure, there are 3 usb_ep: bulk_in, bulk_out, and intr_in. Why is the intr_out endpoint not defined? because it's not needed. Read the USB Mass Storage Class specification from usb.org Ok. In the gadget driver, it keeps on receiving the same bulk_out data, maybe because the data is not processed. The get_next_command is not called. g_file_storage gadget: bulk-out, length 31: : 55 53 42 43 38 b5 ea 86 24 00 00 00 80 00 06 12 0010: 00 00 00 24 00 00 00 00 00 00 00 00 00 00 00^C g_file_storage gadget: bulk_out_complete -- 0, 31/0 Is it because the bh-bulk_out_intended_length is 0? thanks, victor -- To unsubscribe from this list: send the line unsubscribe linux-usb in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
Re: Linux USB file storage gadget with new UDC
Hi, In fsg_dev structure, there are 3 usb_ep: bulk_in, bulk_out, and intr_in. Why is the intr_out endpoint not defined? because it's not needed. Read the USB Mass Storage Class specification from usb.org Ok. In the gadget driver, it keeps on receiving the same bulk_out data, maybe because the data is not processed. The get_next_command is not called. g_file_storage gadget: bulk-out, length 31: : 55 53 42 43 38 b5 ea 86 24 00 00 00 80 00 06 12 0010: 00 00 00 24 00 00 00 00 00 00 00 00 00 00 00^C g_file_storage gadget: bulk_out_complete -- 0, 31/0 Is it because the bh-bulk_out_intended_length is 0? that data is a CBW. But aparently gadget driver queued 0-bytes, why did you unload data if req-length was zero ? another bug in your udc driver In my udc driver, i set the req-length to the number of bytes i received from HW, which is 31 bytes. Is it necessary to do that? How to know the gadget driver queued 0-bytes? By bh-bulk_out_intended_length ? thanks, victor -- To unsubscribe from this list: send the line unsubscribe linux-usb in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
Re: Linux USB file storage gadget with new UDC
Hi, Ok. In the gadget driver, it keeps on receiving the same bulk_out data, maybe because the data is not processed. The get_next_command is not called. g_file_storage gadget: bulk-out, length 31: : 55 53 42 43 38 b5 ea 86 24 00 00 00 80 00 06 12 0010: 00 00 00 24 00 00 00 00 00 00 00 00 00 00 00^C g_file_storage gadget: bulk_out_complete -- 0, 31/0 Is it because the bh-bulk_out_intended_length is 0? that data is a CBW. But aparently gadget driver queued 0-bytes, why did you unload data if req-length was zero ? another bug in your udc driver In my udc driver, i set the req-length to the number of bytes i received from HW, which is 31 bytes. Is it necessary to do that? How you shouldn't touch req-lenght, you should only update req-actual. req-length is readonly for the UDC. to know the gadget driver queued 0-bytes? By bh-bulk_out_intended_length ? read req-length i removed setting the req-length in udc driver. Now in the bulk_out_complete(), the value of req-length is 512. who set it to 512? thanks, victor -- To unsubscribe from this list: send the line unsubscribe linux-usb in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
Re: Linux USB file storage gadget with new UDC
Hi, In my udc driver, i set the req-length to the number of bytes i received from HW, which is 31 bytes. Is it necessary to do that? How you shouldn't touch req-lenght, you should only update req-actual. req-length is readonly for the UDC. to know the gadget driver queued 0-bytes? By bh-bulk_out_intended_length ? read req-length i removed setting the req-length in udc driver. Now in the bulk_out_complete(), the value of req-length is 512. who set it to 512? Read the code and you will figure it out. Here are the last two setup data and CBW data received. the get_next_command() is not called when CBW data is received. the bulk_out_complete() wakes up the thread, however, get_next_command() still sleeps. i do not see where req-length is checked in gadget driver. g_file_storage gadget: ep0-setup, length 8: : 00 09 01 00 00 00 00 00 g_file_storage gadget: set configuration g_file_storage gadget: ep0-setup, length 8: : a1 fe 00 00 00 00 01 00 g_file_storage gadget: get max LUN g_file_storage gadget: ep0-in, length 1: : 00 g_file_storage gadget: bulk-out, length 31: : 55 53 42 43 a8 48 ed 86 24 00 00 00 80 00 06 12 0010: 00 00 00 24 00 00 00 00 00 00 00 00 00 00 00 g_file_storage gadget: bulk_out_complete -- 0, 31/0 victor -- To unsubscribe from this list: send the line unsubscribe linux-usb in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
Re: Linux USB file storage gadget with new UDC
Hi, Here are the last two setup data and CBW data received. the get_next_command() is not called when CBW data is received. the bulk_out_complete() wakes up the thread, however, get_next_command() still sleeps. i do not see where req-length is checked in gadget driver. g_file_storage gadget: ep0-setup, length 8: : 00 09 01 00 00 00 00 00 g_file_storage gadget: set configuration g_file_storage gadget: ep0-setup, length 8: : a1 fe 00 00 00 00 01 00 g_file_storage gadget: get max LUN g_file_storage gadget: ep0-in, length 1: : 00 g_file_storage gadget: bulk-out, length 31: : 55 53 42 43 a8 48 ed 86 24 00 00 00 80 00 06 12 0010: 00 00 00 24 00 00 00 00 00 00 00 00 00 00 00 g_file_storage gadget: bulk_out_complete -- 0, 31/0 file_storage uses bulk_out_intended_length. You're on your own, to be fair, using a really old kernel, you never posted your UDC driver for review, so you need to fix it all up by yourself. Read the code, add prints, look at other UDC drivers. g_file_storage is next to perfect and proven to work with many, many different setups. Here is my UDC driver code. I use a kthread to poll the hardware register EP0 and EP1 interrupt. I removed the HW register access code. If it is required, i can send the full code. Something could be wrong in my UDC driver. Thanks. #include linux/device.h #include linux/interrupt.h #include linux/io.h #include linux/ioport.h #include linux/kernel.h #include linux/list.h #include linux/module.h #include linux/moduleparam.h #include linux/platform_device.h #include linux/usb/ch9.h #include linux/usb/gadget.h #include linux/kthread.h #include linux/delay.h #define NUM_ENDPOINTS 3 #define EP_MAX_PACKET_SIZE 0x200 #define EP0_MAX_PACKET_SIZE 64 #define QH_MAXNUM 32 /*-*/ #define IO_OFFSET 0x5500 #define __IO_ADDRESS(x) ((x) + IO_OFFSET) #define IO_ADDRESS(pa) IOMEM(__IO_ADDRESS(pa)) #ifdef IOMEM // Override asm/io.h #undef IOMEM #endif // IOMEM #ifdef __ASSEMBLER__ #define IOMEM(x)x #else #define IOMEM(x)((void __force __iomem *)(x)) #endif #define ka2000_readb(a) __raw_readb(IO_ADDRESS(a)) #define ka2000_readw(a) __raw_readw(IO_ADDRESS(a)) #define ka2000_readl(a) __raw_readl(IO_ADDRESS(a)) #define ka2000_writeb(v, a) __raw_writeb(v, IO_ADDRESS(a)) #define ka2000_writew(v, a) __raw_writew(v, IO_ADDRESS(a)) #define ka2000_writel(v, a) __raw_writel(v, IO_ADDRESS(a)) /*-*/ static const char *reqname(unsigned r) { switch (r) { case USB_REQ_GET_STATUS: return GET_STATUS; case USB_REQ_CLEAR_FEATURE: return CLEAR_FEATURE; case USB_REQ_SET_FEATURE: return SET_FEATURE; case USB_REQ_SET_ADDRESS: return SET_ADDRESS; case USB_REQ_GET_DESCRIPTOR: return GET_DESCRIPTOR; case USB_REQ_SET_DESCRIPTOR: return SET_DESCRIPTOR; case USB_REQ_GET_CONFIGURATION: return GET_CONFIGURATION; case USB_REQ_SET_CONFIGURATION: return SET_CONFIGURATION; case USB_REQ_GET_INTERFACE: return GET_INTERFACE; case USB_REQ_SET_INTERFACE: return SET_INTERFACE; default: return *UNKNOWN*; } } static struct usb_endpoint_descriptor ep0_out_desc = { .bLength = sizeof(struct usb_endpoint_descriptor), .bDescriptorType = USB_DT_ENDPOINT, .bEndpointAddress = 0, .bmAttributes = USB_ENDPOINT_XFER_CONTROL, }; static struct usb_endpoint_descriptor ep0_in_desc = { .bLength = sizeof(struct usb_endpoint_descriptor), .bDescriptorType = USB_DT_ENDPOINT, .bEndpointAddress = USB_DIR_IN, .bmAttributes = USB_ENDPOINT_XFER_CONTROL, }; struct kagen2; struct kagen2_request { struct usb_request req; struct list_head queue; unsigned mapped:1, valid:1; }; struct ka_ep { struct usb_ep ep; struct kagen2 * dev; unsigned long irqs; struct usb_request req; struct list_head queue; const struct usb_endpoint_descriptor *desc; unsigned num:8, fifo_size:12, stopped:1, wedged:1, is_in:1, is_iso:1, dma:1, not_empty:1; }; struct ka_udc { struct usb_gadget gadget; struct usb_gadget_driver*driver; }; #define CONFIG_MAX_PKT(n) ((n) 16) #define TERMINATE 1 #define INFO_BYTES(n) ((n) 16) #define INFO_IOC (1 15) #define INFO_ACTIVE (1 7) #define INFO_HALTED (1 6) #define INFO_BUFFER_ERROR (1 5) #define INFO_TX_ERROR (1 3) static struct ka_ep ka_ep_g[NUM_ENDPOINTS]; enum SPEED { LOWSPEED = 0, FULLSPEED = 1, HIGHSPEED = 2, }; enum STATE { DEFAULT = 0,
Re: Linux USB file storage gadget with new UDC
Hi, Here are the last two setup data and CBW data received. the get_next_command() is not called when CBW data is received. the bulk_out_complete() wakes up the thread, however, get_next_command() still sleeps. i do not see where req-length is checked in gadget driver. g_file_storage gadget: ep0-setup, length 8: : 00 09 01 00 00 00 00 00 g_file_storage gadget: set configuration g_file_storage gadget: ep0-setup, length 8: : a1 fe 00 00 00 00 01 00 g_file_storage gadget: get max LUN g_file_storage gadget: ep0-in, length 1: : 00 g_file_storage gadget: bulk-out, length 31: : 55 53 42 43 a8 48 ed 86 24 00 00 00 80 00 06 12 0010: 00 00 00 24 00 00 00 00 00 00 00 00 00 00 00 g_file_storage gadget: bulk_out_complete -- 0, 31/0 file_storage uses bulk_out_intended_length. You're on your own, to be fair, using a really old kernel, you never posted your UDC driver for review, so you need to fix it all up by yourself. Read the code, add prints, look at other UDC drivers. g_file_storage is next to perfect and proven to work with many, many different setups. Here is my UDC driver code. I use a kthread to poll the hardware register EP0 and EP1 interrupt. I removed the HW register access code. you should an interrupt handler to handle interrupts from your device. Also, there are way too many mistakes on your driver, run checkpatch.pl, compile it with sparse, don't hardcode addresses, don't reimplement a bunch of infrastructure the kernel already gives you and check your list_head usage! I have run checkpatch.pl and read the linux/usb/gadget.h. The Soc interrupt controller has problem, so i use a kernel thread to read from USB controller directly. don't reimplement a bunch of infrastructure the kernel already gives you i don't understand this. please kindly show an example. Also, you shouldn't requeue the request yourself, gadget driver owns the request. which request do i requeue? please kindly point that out. Thanks! victor -- To unsubscribe from this list: send the line unsubscribe linux-usb in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
Re: Linux USB file storage gadget with new UDC
Hi, Is there any way to to further debug into why do_scsi_command() is not called? usbmon, printk(), trace_printk(), kernel function tracer, there are many ways choose one and spend some time debugging, I'm sure you'll find the bug. It sounds like the UDC driver now works okay for control transfers but not for bulk transfers. Some code in file_storage.c that i cannot understand. In ep0_complete(), the code snippet: if (req-status == 0 req-context) ((fsg_routine_t) (req-context))(fsg); Does the UDC driver provide the context pointer to file_storage.c? That belongs to the gadget driver. file_storage.c maintains that req-context. Another gadget question: get_next_command() is receiving command from host PC, UDC HW isr routine is also receiving data from host PC. What is the difference between these two? hmm... ISR receives data and bounces it back to gadget driver. What do you mean ? Ok, rephrase the question, is this the flow for bulk transfer? 1) data is received by Usb mass storage HW, the UDC driver ISR is called to read the data to usb_request buffer 2) bulk_out_complete() in gadget driver, is called to set buffer state to full 3) get_next_command() in gadget driver, is called to read the CBW. 4) do_scsi_command() to process SCSI command encoded in CBW 5) send_status() sends the CSW to host i see this code snippet in fsg_main_thread(), i cannot understand it, please tell me what the purpose of this code is. is handle_exception() tries to process error condition? if (exception_in_progress(fsg) || signal_pending(current)) { handle_exception(fsg); } thanks, victor -- To unsubscribe from this list: send the line unsubscribe linux-usb in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
Re: Linux USB file storage gadget with new UDC
Hi, It sounds like the UDC driver now works okay for control transfers but not for bulk transfers. Some code in file_storage.c that i cannot understand. In ep0_complete(), the code snippet: if (req-status == 0 req-context) ((fsg_routine_t) (req-context))(fsg); Does the UDC driver provide the context pointer to file_storage.c? That belongs to the gadget driver. file_storage.c maintains that req-context. Another gadget question: get_next_command() is receiving command from host PC, UDC HW isr routine is also receiving data from host PC. What is the difference between these two? hmm... ISR receives data and bounces it back to gadget driver. What do you mean ? Ok, rephrase the question, is this the flow for bulk transfer? 1) data is received by Usb mass storage HW, the UDC driver ISR is called to read the data to usb_request buffer 2) bulk_out_complete() in gadget driver, is called to set buffer state to full 3) get_next_command() in gadget driver, is called to read the CBW. 4) do_scsi_command() to process SCSI command encoded in CBW 5) send_status() sends the CSW to host Something like below: OUT Token - ISR - giveback() - bulk_out_complete() - get_next_command() - do_scsi_command() - usb_ep_queue() - OUT/IN Token - ISR - bulk_out_complete() - send_status() For the IN Token, i will just write the data to the HW buffer, and the flow will go to send_status(). I use a different USB cable, now the USB gadget is able to receive bulk transfer data from host PC. I am working on the bulk transfer code. Thank you for the very useful answers. victor -- To unsubscribe from this list: send the line unsubscribe linux-usb in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
Re: Linux USB file storage gadget with new UDC
Hi, Ok, rephrase the question, is this the flow for bulk transfer? 1) data is received by Usb mass storage HW, the UDC driver ISR is called to read the data to usb_request buffer 2) bulk_out_complete() in gadget driver, is called to set buffer state to full 3) get_next_command() in gadget driver, is called to read the CBW. 4) do_scsi_command() to process SCSI command encoded in CBW 5) send_status() sends the CSW to host Something like below: OUT Token - ISR - giveback() - bulk_out_complete() - get_next_command() - do_scsi_command() - usb_ep_queue() - OUT/IN Token - ISR - bulk_out_complete() - send_status() For the IN Token, i will just write the data to the HW buffer, and the flow will go to send_status(). I use a different USB cable, now the USB gadget is able to receive bulk transfer data from host PC. I am working on the bulk transfer code. Thank you for the very useful answers. np In fsg_dev structure, there are 3 usb_ep: bulk_in, bulk_out, and intr_in. Why is the intr_out endpoint not defined? thanks, victor -- To unsubscribe from this list: send the line unsubscribe linux-usb in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
Re: Linux USB file storage gadget with new UDC
Hi, ep0_complete() should be called by your UDC driver. Seriously dude, read the documentation and read other drivers to figure out how things should be called. A quick look in the storage drivers would have shown you that ep0_complete() is passed in as req-complete() through the usb_request structure. That structure (well, a pointer to it) is passed to the UDC driver through usb_ep_queue(). All you had to figure out is when it req-complete called. ANY UDC driver would have given you the answer. Likely your UDC driver is still buggy, if you don't call -complete(), you're starving your usb_request queue. Yes, ep0_complete() is called in UDC driver queue function, i just added it in and ep0_complete() is called now. The dmesg output is below. not in queue function, you should call it when completing. Is there any mistake in my understanding of ep0 setup data processing? 1. usb gadget HW IRQ is triggered if ep0 receives data 2. fsg_setup() is called 3. ep0_queue() is called 4. UDC driver queue function is called 5. UDC driver sends data to ep0 HW buffer 6. UDC driver increments req-actual by the amount of transferred bytes 7. UDC driver call ep0_complete() thanks. victor -- To unsubscribe from this list: send the line unsubscribe linux-usb in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
Re: Linux USB file storage gadget with new UDC
Hi, Yes, ep0_complete() is called in UDC driver queue function, i just added it in and ep0_complete() is called now. The dmesg output is below. not in queue function, you should call it when completing. Is there any mistake in my understanding of ep0 setup data processing? 1. usb gadget HW IRQ is triggered if ep0 receives data 2. fsg_setup() is called 3. ep0_queue() is called 4. UDC driver queue function is called 5. UDC driver sends data to ep0 HW buffer 6. UDC driver increments req-actual by the amount of transferred bytes 7. UDC driver call ep0_complete() looks correct Some progress, now i am able to see the dump_msg from ep0_complete(). It looks like the enumeration is ok, but the SCSI Inquiry command is not received by the UDC driver. The do_scsi_command() in fsg_main_thread() is not called. Is this another bug in my UDC driver? below is the debug message from file storage gadget g_file_storage gadget: ep0-setup, length 8: : 80 06 00 01 00 00 40 00 g_file_storage gadget: get device descriptor g_file_storage gadget: ep0-in, length 18: : 12 01 00 02 00 00 00 40 25 05 a5 a4 33 03 01 02 0010: 00 01 g_file_storage gadget: ep0-setup, length 8: : 80 06 00 01 00 00 12 00 g_file_storage gadget: get device descriptor g_file_storage gadget: ep0-in, length 18: : 12 01 00 02 00 00 00 40 25 05 a5 a4 33 03 01 02 0010: 00 01 g_file_storage gadget: ep0-setup, length 8: : 80 06 00 02 00 00 ff 00 g_file_storage gadget: get configuration descriptor g_file_storage gadget: ep0-in, length 32: : 09 02 20 00 01 01 04 c0 01 09 04 00 00 02 08 06 0010: 50 05 07 05 81 02 00 02 00 07 05 01 02 00 02 01 g_file_storage gadget: ep0-setup, length 8: : 80 06 00 03 00 00 ff 00 g_file_storage gadget: ep0-in, length 4: : 04 03 09 04 g_file_storage gadget: ep0-setup, length 8: : 80 06 02 03 09 04 ff 00 g_file_storage gadget: get string descriptor g_file_storage gadget: ep0-in, length 54: : 36 03 46 00 69 00 6c 00 65 00 2d 00 62 00 61 00 0010: 63 00 6b 00 65 00 64 00 20 00 53 00 74 00 6f 00 0020: 72 00 61 00 67 00 65 00 20 00 47 00 61 00 64 00 0030: 67 00 65 00 74 00 g_file_storage gadget: ep0-setup, length 8: : 80 06 00 01 00 00 12 00 g_file_storage gadget: get device descriptor g_file_storage gadget: ep0-in, length 18: : 12 01 00 02 00 00 00 40 25 05 a5 a4 33 03 01 02 0010: 00 01 g_file_storage gadget: ep0-setup, length 8: : 80 06 00 02 00 00 09 00 g_file_storage gadget: get configuration descriptor g_file_storage gadget: ep0-in, length 9: : 09 02 20 00 01 01 04 c0 01 g_file_storage gadget: ep0-setup, length 8: : 80 06 00 02 00 00 20 00 g_file_storage gadget: get configuration descriptor g_file_storage gadget: ep0-in, length 32: : 09 02 20 00 01 01 04 c0 01 09 04 00 00 02 08 06 0010: 50 05 07 05 81 02 00 02 00 07 05 01 02 00 02 01 g_file_storage gadget: ep0-setup, length 8: : 00 09 01 00 00 00 00 00 g_file_storage gadget: set configuration g_file_storage gadget: set interface 0 g_file_storage gadget: high-speed config #1 g_file_storage gadget: ep0-setup, length 8: : a1 fe 00 00 00 00 01 00 g_file_storage gadget: ep0-in, length 1: : 00 g_file_storage gadget: ep0-setup, length 8: : 80 06 01 03 09 04 ff 00 g_file_storage gadget: get string descriptor g_file_storage gadget: ep0-in, length 58: : 3a 03 4c 00 69 00 6e 00 75 00 78 00 20 00 33 00 0010: 2e 00 34 00 2e 00 34 00 2b 00 20 00 77 00 69 00 0020: 74 00 68 00 20 00 6b 00 61 00 67 00 65 00 6e 00 0030: 32 00 5f 00 75 00 73 00 62 00 g_file_storage gadget: ep0-setup, length 8: : 80 06 04 03 09 04 ff 00 g_file_storage gadget: get string descriptor g_file_storage gadget: ep0-in, length 26: : 1a 03 53 00 65 00 6c 00 66 00 2d 00 70 00 6f 00 0010: 77 00 65 00 72 00 65 00 64 00 g_file_storage gadget: ep0-setup, length 8: : 80 06 05 03 09 04 ff 00 g_file_storage gadget: get string descriptor g_file_storage gadget: ep0-in, length 26: : 1a 03 4d 00 61 00 73 00 73 00 20 00 53 00 74 00 0010: 6f 00 72 00 61 00 67 00 65 00 thanks, victor -- To unsubscribe from this list: send the line unsubscribe linux-usb in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
Re: Linux USB file storage gadget with new UDC
Hi, Yes, ep0_complete() is called in UDC driver queue function, i just added it in and ep0_complete() is called now. The dmesg output is below. not in queue function, you should call it when completing. Is there any mistake in my understanding of ep0 setup data processing? 1. usb gadget HW IRQ is triggered if ep0 receives data 2. fsg_setup() is called 3. ep0_queue() is called 4. UDC driver queue function is called 5. UDC driver sends data to ep0 HW buffer 6. UDC driver increments req-actual by the amount of transferred bytes 7. UDC driver call ep0_complete() looks correct Some progress, now i am able to see the dump_msg from ep0_complete(). It looks like the enumeration is ok, but the SCSI Inquiry command is not received by the UDC driver. The do_scsi_command() in fsg_main_thread() is not called. Is this another bug in my UDC driver? I would believe so since so many other controllers work just fine. Is there any way to to further debug into why do_scsi_command() is not called? thanks, victor -- To unsubscribe from this list: send the line unsubscribe linux-usb in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
Re: Linux USB file storage gadget with new UDC
Hi, Is there any mistake in my understanding of ep0 setup data processing? 1. usb gadget HW IRQ is triggered if ep0 receives data 2. fsg_setup() is called 3. ep0_queue() is called 4. UDC driver queue function is called 5. UDC driver sends data to ep0 HW buffer 6. UDC driver increments req-actual by the amount of transferred bytes 7. UDC driver call ep0_complete() looks correct Some progress, now i am able to see the dump_msg from ep0_complete(). It looks like the enumeration is ok, but the SCSI Inquiry command is not received by the UDC driver. The do_scsi_command() in fsg_main_thread() is not called. Is this another bug in my UDC driver? I would believe so since so many other controllers work just fine. Is there any way to to further debug into why do_scsi_command() is not called? usbmon, printk(), trace_printk(), kernel function tracer, there are many ways choose one and spend some time debugging, I'm sure you'll find the bug. It sounds like the UDC driver now works okay for control transfers but not for bulk transfers. Some code in file_storage.c that i cannot understand. In ep0_complete(), the code snippet: if (req-status == 0 req-context) ((fsg_routine_t) (req-context))(fsg); Does the UDC driver provide the context pointer to file_storage.c? Another gadget question: get_next_command() is receiving command from host PC, UDC HW isr routine is also receiving data from host PC. What is the difference between these two? thanks, victor -- To unsubscribe from this list: send the line unsubscribe linux-usb in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
Re: Linux USB file storage gadget with new UDC
Hi, For testing purposes, you probably should use a Linux host. Then you could use usbmon on the host to see what's happening, and there would be more debugging options available. Got it, i will get a PC to install Linux. Did you enable the two debugging options in file_storage.c? And did you remember to enable CONFIG_USB_GADGET_DEBUG in the kernel configuration? What shows up in the dmesg log? Yes, i enable the CONFIG_USB_GADGET_DEBUG and the VERBOSE_DEBUG and DUMP_MSGS in file_storage.c. In dmesg log, there are lot of entries recorded during usb gadget enumeration with host PC. After gadget receives get MAX LUN, the enumeration process gets repeated. Is this the problem?? Please see the dmesg log below. This log looks oddly incomplete. A lot of debugging messages are missing. g_file_storage gadget: ep0-setup, length 8: : 80 06 00 01 00 00 40 00 g_file_storage gadget: get device descriptor For example, right here we should see the device descriptor data that was sent back to the host. I checked the log again, the dmesg log did not contain that info. May i know which part of the gadget code will print out the device descriptor data that was sent back to the host? . Where does the enumeration repeat? I don't see any repeats here, aside from the fact that Windows asks for the same device and config descriptors a few times. Why is the Windows asking for the same device and config descriptors several times? Thanks, victor -- To unsubscribe from this list: send the line unsubscribe linux-usb in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
Re: Linux USB file storage gadget with new UDC
Hi, Replying my email, i set the ep,name to ep1 for bulk out and bulk in endpoints. The ep_matches() in epautoconf.c is able to auto-configure the bulk out to endpoint 1. Are you sure the name string is set to ep1 for both endpoints? (Or ep1in and ep1out?) If the string was instead set to ep or ep-bulk or something like that, then it would make sense for the auto-configured bulk-out endpoint address to be 2. You should add some printk statements to the ep_matches() routine in epautoconf.c so you can see exactly what it is doing. Yes, i change the name string to ep1 for both endpoints [ Before that, it is ep-a, ep-b, and bulk-out endpoint auto-configured to 2 ]. In ep_matches(), the isdigit(ep-name[2]) if-condition is fulfilled. In fsg_bind(), after the usb_ep_autoconfig() for bulk-out returns, the fsg_fs_bulk_out_desc.bEndpointAddress is 1. however, i only see one SCSI_INQUIRY command being sent out, and it is not received by the gadget device. There could be other reasons for this, like an incorrect data toggle value. Are you certain the endpoint address is wrong? Can you post the usbmon trace and the output from lsusb -v for the gadget? Now the endpoint address is ok, i guess. After i do insmod usbmon, g_file_storage, and my UDC driver, the lsusb -v shows nothing. Should my UDC driver provide the info in /sys/bus/usb folder? # ls /sys/bus/usb/ devicesdrivers_autoprobe uevent driversdrivers_probe # lsusb -v # Thanks, victor -- To unsubscribe from this list: send the line unsubscribe linux-usb in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html