Forum Rule: Always post complete source code & details to reproduce any issue!
Results 1 to 14 of 14

Thread: USB Host Force Detection

  1. #1

    USB Host Force Detection

    Hi,

    I'm trying to get the second high speed USB port on Teensy 3.6 working for my scenario.

    To power the Pi-like device I have a separate 5v power supply, connected power and ground pins of the USB connector to that power supply, D+ and D- to the Teensy's USB pins...

    I've recompiled my Pi's device kernel with g_serial support (so that the device acts like a USB client).

    And here goes the confusing part. When I try to connect the mouse, it is being detected ok every time. But the Pi device was detected only a few times (and when it's detected, the data sending/receiving works ok). If I restart Teensy after the Pi is detected, it's never detected again. Then I start to fiddle with the cables, reboot everything, and eventually sometimes the Pi is there again, but only till first Teensy restart.

    The log from the happy moment of being detected:

    Code:
    USB Host Testing - Serial
    *** Device HID1 46d:c016 - connected ***
      manufacturer: Logitech
      product: Optical USB Mouse
    *** Device HID1 - disconnected ***
    *** Device USERIAL1 525:a4a7 - connected ***
      manufacturer: Linux 4.4.49-s5p4418 with c0040000.dwc2otg
      product: Gadget
    Does anybody have an idea?

    Thanks.

  2. #2
    Senior Member+ KurtE's Avatar
    Join Date
    Jan 2014
    Posts
    5,414
    Sometimes hard to say without seeing more data.

    Some of the first steps I typically advise is to compile the usbhost_t3 library to output debug information.
    You can do that by editing USBHost_t36.h file and about line 60 will be a line like: //#define USBHOST_PRINT_DEBUG

    Uncomment this line (remove the //)

    Assuming you are using the version that is installed by Teensyduino and not downloaded directly from github, this should be located
    <Where your Arduino install is>/hardware/teensy/avr/libraries/USBHost_t36 ...

    This should give a lot more information when you plug in your device.

    Sometimes I will boot up a linux machine and print out information about this device...
    Things like: dmesg | tail -20
    lsusb

    I also output verbose info from lsusb, but often have to look up the exact details of command, something like:
    lsusb -v -d 525:a4a7

    Also note with Serial devices. Sometimes the code has to resort to using a VID:PID (vendor id, product id) to know that this is a Serial device and how to use it. In that same directory you will see serial.cpp that has that mapping table and all of the code.

  3. #3
    @KurtE, thanks for the suggestions! Something is definitely happening under the hood. Also there seems to be a bug somewhere (likely in the USBHost_t36)...

    Teensy is off, the Pi device is started and plugged in to the Teensy's USB. Then I power Teensy up:

    Code:
    USB Host Testing - Serial
    sizeof Device = 36
    sizeof Pipe = 96
    sizeof Transfer = 64
    power up USBHS PHY
     reset waited 5
    USBHS_ASYNCLISTADDR = 0
    USBHS_PERIODICLISTBASE = 1FFF4000
    periodictable = 1FFF4000
    port change: 10001803
        connect
      begin reset
    port change: 18001205
      port enabled
      end recovery
    new_Device: 480 Mbit/sec
    new_Pipe
    Then, while Teensy is on, I do «sudo reboot» on the Pi:

    Code:
    port change: 1C00100A
        disconnect
    disconnect_Device:
    USBDriver (available_drivers) list: 1FFF2A40 -> 1FFF34C0 -> 1FFF2040 -> 1FFF2540 -> 1FFF3880 -> 1FFF2E80
    USBDriver (dev->drivers) list: (empty
    USBDriver (available_drivers) list: 1FFF2A40 -> 1FFF34C0 -> 1FFF2040 -> 1FFF2540 -> 1FFF3880 -> 1FFF2E80
    delete_Pipe 1FFF4400
      shut down async schedule
      Free transfers
        * 536823104 * remove * free
        * 536822912
        * 536822976 * remove * defer free until QH
      Free transfers attached to QH
        * 536822912
        * 536822976
        * 536823040
    * Delete Pipe completed
    removed Device_t from devlist
      disable
    port change: 10001803
        connect
      begin reset
    port change: 18001205
      port enabled
    port change: 1C00100A
        disconnect
      disable
    port change: 10001803
        connect
      begin reset
    port change: 18001205
      port enabled
      end recovery
    new_Device: 480 Mbit/sec
    new_Pipe
    port change: 1C00100A
        disconnect
    disconnect_Device:
    USBDriver (available_drivers) list: 1FFF2A40 -> 1FFF34C0 -> 1FFF2040 -> 1FFF2540 -> 1FFF3880 -> 1FFF2E80
    USBDriver (dev->drivers) list: (empty
    USBDriver (available_drivers) list: 1FFF2A40 -> 1FFF34C0 -> 1FFF2040 -> 1FFF2540 -> 1FFF3880 -> 1FFF2E80
    delete_Pipe 1FFF4400
      shut down async schedule
      Free transfers
        * 536822912 * remove * defer free until QH
        * 536823040 * remove * free
        * 536823104 * remove * defer free until QH
        * 536823104 * remove * defer free until QH
        * 536823104 * remove * defer free until QH
        * 536823104 * remove * defer free until QH
        * 536823104 * remove * defer free until QH
        * 536823104 * remove * defer free until QH
        * 536823104 * remove * defer free until QH
        * 536823104 * remove * defer free until QH
        * 536823104 * remove * defer free until QH
        * 536823104 * remove * defer free until QH
        * 536823104 * remove * defer free until QH
        * 536823104 * remove * defer free until QH
    After the Pi is started again, Teensy is in an infinite loop saying «* 536823104 * remove * defer free until QH»...

  4. #4
    Code:
    lsusb -v -d 525:a4a7
    
    Bus 001 Device 003: ID 0525:a4a7 Netchip Technology, Inc. Linux-USB Serial Gadget (CDC ACM mode)
    Couldn't open device, some information will be missing
    Device Descriptor:
      bLength                18
      bDescriptorType         1
      bcdUSB               2.00
      bDeviceClass            2 Communications
      bDeviceSubClass         0 
      bDeviceProtocol         0 
      bMaxPacketSize0        64
      idVendor           0x0525 Netchip Technology, Inc.
      idProduct          0xa4a7 Linux-USB Serial Gadget (CDC ACM mode)
      bcdDevice            4.04
      iManufacturer           1 
      iProduct                2 
      iSerial                 0 
      bNumConfigurations      1
      Configuration Descriptor:
        bLength                 9
        bDescriptorType         2
        wTotalLength           75
        bNumInterfaces          2
        bConfigurationValue     2
        iConfiguration          4 
        bmAttributes         0xc0
          Self Powered
        MaxPower                2mA
        Interface Association:
          bLength                 8
          bDescriptorType        11
          bFirstInterface         0
          bInterfaceCount         2
          bFunctionClass          2 Communications
          bFunctionSubClass       2 Abstract (modem)
          bFunctionProtocol       1 AT-commands (v.25ter)
          iFunction               7 
        Interface Descriptor:
          bLength                 9
          bDescriptorType         4
          bInterfaceNumber        0
          bAlternateSetting       0
          bNumEndpoints           1
          bInterfaceClass         2 Communications
          bInterfaceSubClass      2 Abstract (modem)
          bInterfaceProtocol      1 AT-commands (v.25ter)
          iInterface              5 
          CDC Header:
            bcdCDC               1.10
          CDC Call Management:
            bmCapabilities       0x00
            bDataInterface          1
          CDC ACM:
            bmCapabilities       0x02
              line coding and serial state
          CDC Union:
            bMasterInterface        0
            bSlaveInterface         1 
          Endpoint Descriptor:
            bLength                 7
            bDescriptorType         5
            bEndpointAddress     0x82  EP 2 IN
            bmAttributes            3
              Transfer Type            Interrupt
              Synch Type               None
              Usage Type               Data
            wMaxPacketSize     0x000a  1x 10 bytes
            bInterval               9
        Interface Descriptor:
          bLength                 9
          bDescriptorType         4
          bInterfaceNumber        1
          bAlternateSetting       0
          bNumEndpoints           2
          bInterfaceClass        10 CDC Data
          bInterfaceSubClass      0 Unused
          bInterfaceProtocol      0 
          iInterface              6 
          Endpoint Descriptor:
            bLength                 7
            bDescriptorType         5
            bEndpointAddress     0x81  EP 1 IN
            bmAttributes            2
              Transfer Type            Bulk
              Synch Type               None
              Usage Type               Data
            wMaxPacketSize     0x0200  1x 512 bytes
            bInterval               0
          Endpoint Descriptor:
            bLength                 7
            bDescriptorType         5
            bEndpointAddress     0x01  EP 1 OUT
            bmAttributes            2
              Transfer Type            Bulk
              Synch Type               None
              Usage Type               Data
            wMaxPacketSize     0x0200  1x 512 bytes
            bInterval               0

  5. #5
    Senior Member+ KurtE's Avatar
    Join Date
    Jan 2014
    Posts
    5,414
    Sounds like something that needs to be debugged.

    Is there an easy to setup RPI image somewhere that I can setup an RPI3 or 0, to try this out...

  6. #6
    As far as I know, Raspberry Pi 3 uses microUSB port for power only and doesn't have the data wires connected anywhere. Raspberry Pi Zero has it connected, but I don't have one yet to see if it's the same there. The device I used called Core4418 (it's a Raspberry Pi-like device, with Linux inside), for that device I needed to recompile the kernel with g_serial support, but as I was reading the info, it seems like the Raspberry Pi Zero has it compiled by default.

    Any tips about where to start with the debugging? It just feels like I've found a viable option (I really hope that I'll be able to achieve a relatively high speed USB using the serial driver) and I would pursue it...

  7. #7
    Senior Member+ KurtE's Avatar
    Join Date
    Jan 2014
    Posts
    5,414
    Not sure yet what it may or may not be. It could turn out there are some handles or the like we are not properly releasing or maybe releasing again...

    I will look through my RPI box and see if I have an RPI ready to try out and see what it does.

    Kurt

  8. #8
    My current finding: the async follow-up callbacks are not being called. And if I uncomment «USBHS_PORTSC1 |= USBHS_PORTSC_PFSC; // force 12 Mbit/sec» line in ehci.cpp, the device starts to be detected. But I need those 480Mbits and when I connect the device to Mac, it's detected as a 480Mbits device...

  9. #9
    Senior Member+ KurtE's Avatar
    Join Date
    Jan 2014
    Posts
    5,414
    It is a long shot, but you might try my WIP for bluetooth branch and see if by chance some of the stuff we fixed helps...

    https://github.com/KurtE/USBHost_t36...WIP2-Bluetooth

  10. #10
    Doesn't seem to help.
    It is a long shot as well, but my current hypothesis is that there might be an interference preventing from 480 Mbits capability... I have pretty short wires between the USB socket and Teensy (about 10 cm), but they are just simple single Arduino wires with the dupont connectors and the USB cables are shielded for a reason. Going to try to solder the socket to Teensy.

    Click image for larger version. 

Name:	usb.jpg 
Views:	13 
Size:	126.5 KB 
ID:	16795

  11. #11
    Senior Member+ KurtE's Avatar
    Join Date
    Jan 2014
    Posts
    5,414
    Let me know how it goes... I have tried running with several different USB to serial adapter types and have not seen this issue.

    But that does not imply that there is not an issue... I found one of the RPI0 boards I have... I know I have another one around here somewhere... Did find a tutorial from Adafruit on how to convert the RPI0 into a USB gadget... So will download it and give it a try... May be a day or two as I probably need to get out soldering station to put on external connector to get to Serial port.... (Unless I find the other one that I had previously soldered).

  12. #12
    Thanks so much!

    I will let you know, but it might take some time. In order to not ruin the whole thing with my unskilled soldering I've ordered a bunch of these: https://www.ebay.com/itm/10Pcs-USB-2...E/143259781474, going to solder one directly to my USB pins on Teensy. It's about one month time to receive those things from China.

    But the interference hypothesis would conform with the fact that I've actually had the successful connection (before I've enabled the debug output flag) several times — it could have been a moment of lesser interference .

    Also, if you will succeed connecting RPI0 as a serial gadget at 480 Mbits speed before I will do my thing, please let me know, I would wait for the delivery with more or less hope .

  13. #13
    So, I've received the USB connector boards and soldered one directly on top of Teensy.

    It's definitely a progress, but seems to be not there yet .

    It all works when I force it to 12 Mbits (in ehci.cpp), I use SerialTest from the examples. The output for 12 Mbits looks like this:

    Code:
    new_Device: 12 Mbit/sec
    new_Pipe
    enumeration:
    enumeration:
    enumeration:
    Device Descriptor:
      12 01 00 02 02 00 00 40 25 05 A7 A4 04 04 01 02 00 01 
        VendorID = 0525, ProductID = A4A7, Version = 0404
        Class/Subclass/Protocol = 2 / 0 / 0
        Number of Configurations = 1
    enumeration:
    enumeration:
    Manufacturer: Linux 4.4.49-s5p4418 with c0040000.dwc2otg
    enumeration:
    Product: Gadget Serial v2.4
    enumeration:
    Config data length = 75
    enumeration:
    Configuration Descriptor:
      09 02 4B 00 02 02 04 C0 01 
        NumInterfaces = 2
        ConfigurationValue = 2
      08 0B 00 02 02 02 01 07 
        Interface Association = 0 through 1
        Class / Subclass / Protocol = 2 / 2 / 7
      09 04 00 00 01 02 02 01 05 
        Interface = 0
        Number of endpoints = 1
        Class/Subclass/Protocol = 2 / 2 / 1
      05 24 00 10 01 
      05 24 01 00 01 
      04 24 02 02 
      05 24 06 00 01 
      07 05 82 03 0A 00 20 
        Endpoint = 2 IN
        Type = Interrupt
        Max Size = 10
        Polling Interval = 32
      09 04 01 00 02 0A 00 00 06 
        Interface = 1
        Number of endpoints = 2
        Class/Subclass/Protocol = 10 / 0 / 0
      07 05 81 02 40 00 00 
        Endpoint = 1 IN
        Type = Bulk
        Max Size = 64
        Polling Interval = 0
      07 05 01 02 40 00 00 
        Endpoint = 1 OUT
        Type = Bulk
        Max Size = 64
        Polling Interval = 0
    enumeration:
    USBSerial claim this=1FFF30C0
    vid=525, pid=A4A7, bDeviceClass = 2, bDeviceSubClass = 0, bDeviceProtocol = 0
    08 0B 00 02 02 02 01 07 09 04 00 00 01 02 02 01 05 05 24 00 10 01 05 24 01 00 01 04 24 02 02 05 24 06 00 01 07 05 82 03 0A 00 20 09 04 01 00 02 0A 00 00 06 07 05 81 02 40 00 00 07 05 01 02 40 00 00 
    USBHub memory usage = 960
    USBHub claim_device this=1FFF2C80
    USBHub memory usage = 960
    USBHub claim_device this=1FFF3700
    HIDParser claim this=1FFF2040
    HIDParser claim this=1FFF2660
    HIDParser claim this=1FFF3AC0
    Descriptor 11 = IAD
    Descriptor 4 = INTERFACE
    USBSerial claim this=1FFF30C0
    vid=525, pid=A4A7, bDeviceClass = 2, bDeviceSubClass = 0, bDeviceProtocol = 0
    09 04 00 00 01 02 02 01 05 05 24 00 10 01 05 24 01 00 01 04 24 02 02 05 24 06 00 01 07 05 82 03 0A 00 20 09 04 01 00 02 0A 00 00 06 07 05 81 02 40 00 00 07 05 01 02 40 00 00 
    HIDParser claim this=1FFF2040
    HIDParser claim this=1FFF2660
    HIDParser claim this=1FFF3AC0
    Descriptor 36 =  ???
    Descriptor 36 =  ???
    Descriptor 36 =  ???
    Descriptor 36 =  ???
    Descriptor 5 = ENDPOINT
    Descriptor 4 = INTERFACE
    USBSerial claim this=1FFF30C0
    vid=525, pid=A4A7, bDeviceClass = 2, bDeviceSubClass = 0, bDeviceProtocol = 0
    09 04 01 00 02 0A 00 00 06 07 05 81 02 40 00 00 07 05 01 02 40 00 00 
    CDC, rxep=1, txep=1
    new_Pipe
    new_Pipe
    Control - CDCACM LINE_CODING
    Descriptor 5 = ENDPOINT
    Descriptor 5 = ENDPOINT
    control callback (serial) 4
    Control - 0x21,0x22, 0x3
    *** Device USERIAL1 525:a4a7 - connected ***
      manufacturer: Linux 4.4.49-s5p4418 with c0040000.dwc2otg
      product: Gadget
    control callback (serial) 6
    CDCACM setup: 00 C2 01 00 00 00 08 
    control callback (serial) 4
    Control - 0x21,0x22, 0x3
    control callback (serial) 0
    But when there is no 12 Mbits enforcement and the devices tries to connect at 480 Mbits the output looks like this:

    Code:
    new_Device: 480 Mbit/sec
    new_Pipe
    enumeration:
    enumeration:
    enumeration:
    Device Descriptor:
      12 01 00 02 02 00 00 40 25 05 A7 A4 04 04 01 02 00 01 
        VendorID = 0525, ProductID = A4A7, Version = 0404
        Class/Subclass/Protocol = 2 / 0 / 0
        Number of Configurations = 1
    enumeration:
    enumeration:
    Manufacturer: Linux 4.4.49-s5p4418 with c0040000.dwc2otg
    enumeration:
    Product: Gadget Serial v2.4
    enumeration:
    Config data length = 75
    enumeration:
    Configuration Descriptor:
      09 02 4B 00 02 02 04 C0 01 
        NumInterfaces = 2
        ConfigurationValue = 2
      08 0B 00 02 02 02 01 07 
        Interface Association = 0 through 1
        Class / Subclass / Protocol = 2 / 2 / 7
      09 04 00 00 01 02 02 01 05 
        Interface = 0
        Number of endpoints = 1
        Class/Subclass/Protocol = 2 / 2 / 1
      05 24 00 10 01 
      05 24 01 00 01 
      04 24 02 02 
      05 24 06 00 01 
      07 05 82 03 0A 00 09 
        Endpoint = 2 IN
        Type = Interrupt
        Max Size = 10
        Polling Interval = 9
      09 04 01 00 02 0A 00 00 06 
        Interface = 1
        Number of endpoints = 2
        Class/Subclass/Protocol = 10 / 0 / 0
      07 05 81 02 00 02 00 
        Endpoint = 1 IN
        Type = Bulk
        Max Size = 512
        Polling Interval = 0
      07 05 01 02 00 02 00 
        Endpoint = 1 OUT
        Type = Bulk
        Max Size = 512
        Polling Interval = 0
    enumeration:
    USBHub memory usage = 960
    USBHub claim_device this=1FFF32C0
    USBHub memory usage = 960
    USBHub claim_device this=1FFF3720
    HIDParser claim this=1FFF2680
    HIDParser claim this=1FFF2CA0
    HIDParser claim this=1FFF3AE0
    USBSerial claim this=1FFF2020
    vid=525, pid=A4A7, bDeviceClass = 2, bDeviceSubClass = 0, bDeviceProtocol = 0
    08 0B 00 02 02 02 01 07 09 04 00 00 01 02 02 01 05 05 24 00 10 01 05 24 01 00 01 04 24 02 02 05 24 06 00 01 07 05 82 03 0A 00 09 09 04 01 00 02 0A 00 00 06 07 05 81 02 00 02 00 07 05 01 02 00 02 00 
    Descriptor 11 = IAD
    Descriptor 4 = INTERFACE
    HIDParser claim this=1FFF2680
    HIDParser claim this=1FFF2CA0
    HIDParser claim this=1FFF3AE0
    USBSerial claim this=1FFF2020
    vid=525, pid=A4A7, bDeviceClass = 2, bDeviceSubClass = 0, bDeviceProtocol = 0
    09 04 00 00 01 02 02 01 05 05 24 00 10 01 05 24 01 00 01 04 24 02 02 05 24 06 00 01 07 05 82 03 0A 00 09 09 04 01 00 02 0A 00 00 06 07 05 81 02 00 02 00 07 05 01 02 00 02 00 
    Descriptor 36 =  ???
    Descriptor 36 =  ???
    Descriptor 36 =  ???
    Descriptor 36 =  ???
    Descriptor 5 = ENDPOINT
    Descriptor 4 = INTERFACE
    HIDParser claim this=1FFF2680
    HIDParser claim this=1FFF2CA0
    HIDParser claim this=1FFF3AE0
    USBSerial claim this=1FFF2020
    vid=525, pid=A4A7, bDeviceClass = 2, bDeviceSubClass = 0, bDeviceProtocol = 0
    09 04 01 00 02 0A 00 00 06 07 05 81 02 00 02 00 07 05 01 02 00 02 00 
    Descriptor 5 = ENDPOINT
    Descriptor 5 = ENDPOINT
    Very similar, but the device is not created. I didn't dig enough yet, but I see «if (descriptors[13] > 64) return false; // size 64 Max» in serial.cpp (at 480 Mbits I'm seeing 512 as Max Size and 64 at 12 Mbits). It might be one of the reasons it's never detected.

    Also there is a second problem now. The device is being detected only once. When I disconnect it and connect again, the process hangs at first «enumeration:» line. It gets detected again when I reboot the Pi... That wasn't an issue before.

    I would appreciate any suggestions.

    Thanks!

  14. #14
    More intermediate results. If I comment all the checks out (starting from «if (descriptors[9] != 7) return false; // length 7» till «if (descriptors[21] != 0) return false;», then hardcode txsize and rxsize to 512, then increase BUFFER_SIZE in USBHost_t36.h, I get a successful 480 Mbits connection for the CDCACM serial. I don't know how stable it is yet, but a couple of manual tests (sending chunks of text longer than 512 symbols in both directions using the serial monitor from the Teensy side and the screen tool from the Pi side) seem to transmit the data correctly in both directions.

    I'll keep testing it, but if the stability will be ok over the long periods of time and with the huge traffic, it's already something workable which gives me hope. Though, I would really like to have it fixed properly. And solve the new problem when I need to reboot the Pi every time I reconnect the device or reflash Teensy.

Posting Permissions

  • You may not post new threads
  • You may not post replies
  • You may not post attachments
  • You may not edit your posts
  •