This thread has been locked.

If you have a related question, please click the "Ask a related question" button in the top right corner. The newly created question will be automatically linked to this question.

AM3358: USB Host - Assistance opening EP1

Part Number: AM3358
Other Parts Discussed in Thread: AM3352, SYSBIOS

Hello,

I am trying to get the am3358/am3352 CPU running in USB Host mode. I want to access a USB thumbdrive.

In summary, I cannot get EP1 to work. EP0 appears to be working fine.

My question: What is required to open an EP1 in host mode.   Because it is giving me a error when I try to send.  And the Tech Ref is missing critical information.  For details, read on.

I will attempt to include the entire CCS project in a zip.  It's minimal, not bloated with superfluous code, functions, files that complicate things. 

The environment is Bios 6.76.03.01 with XDC 3.55.2.22, using GNUC 7.3.1. Although for this unit development, it is essentially BARE METAL and running it's one task operation.  So this is NOT a BIOS/RTOS issue, as the code would run as a raw C project, bare metal (and I have tried that too.)

I am using the original "AM335X_StarterWare_02_00_01_01" as a beginning point, and attempting to simply open the USB drive and communicate with it.

The doc for it is mostly well explained.  However using it simply fails ONLY to allow communication over EP1.  So there must be some verity small piece of information I am missing.

I have plenty of USB DEVICES working with this code base.  I am confident the hardware and the functions from StarterWare function are adequate.   Except for opening an HOST based EP1.

Here is what I see that is working, and where is doesn't...

I examined the WireShark log for this UBS drive when attached to a PC. I can see all the descriptor commands send as transactions to/from EP0, and also the first inquiry it sends on EP1.

So, naturally the endpoints for this thumbdrive work as expected in the PC.

In the ARM firmware, I can successfully enumerate the device, and perform a GET LUN command which returns successfully. These are all transaction messages on EP0. However it is failing to communicate through the data pipes. I am printing out the data and messages to a UART log of my own messages, which is included at the project ZIP.

I can't output any message inside a ISR, but I can simply write to some memory. So I have a large buffer, and a few functions that simply write a message to that buffer: AddToIntBuffer(), AddHEXToIntBuffer() . Then I can pause or interrupt the execution, and have the CCS IDE do a memory dump of that, so I can see what happens inside the ISR.  (I describe what I see in the ISR memory log in a bit)

The configuration descriptor, as read from the device, matches the one that I sniffed with WireShark. the the value parse correctly. The some data is shown below:

09 02 20 00 01 01 00 80 32 09 04 00 00 02 08 06
50 00 07 05 01 02 00 02 00 07 05 81 02 00 02 00

Which is a descriptor to a Mass storage device, 2 endpoints, class MSC, protocol x50, etc...

The pipe descriptors are shown here:

07 05 01 02 00 02 00        EP 1 OUT   Bulk  512 bytes
07 05 81 02 00 02 00        EP 1 IN    Bulk  512 bytes

So they are all okay.

Here is where things get insane...

When I create the pipes using the function USBHCDPipeAllocSize(), USBHCDPipeConfig(), etc and set the type to "BULK" the first attempt to send the MSC device a query out PIPE 1 gives a PIPE_ERROR.

Here's what's really weird: The value that holds the state is from the global structure "g_sUSBHCD", "eState" member. And it is ONLY set inside the ISR. And every step in the ISR is recorded to my memory log... That member is never set to PIPE_ERROR in the ISR, since it's not recorded anywhere in my ISR log buffer... So I'm lost as to how the eState member gets set to error, if the ISR never set that flag.

So how it is getting set?

More importantly: Why can I not send any data out EP1?

There has to be something simple and easy as to what I am doing wrong and why the EP1 isn't working. But I have yet to find any clue in the code or any of the doc.

Just a few things I've tweaked:

I have tried playing with the "ulInterval" stuff that sets timeouts. No difference.

I have tried changing the DMA type (I am not using CPPI routine at this stage).

I have tried changing the EP type.

When I change the setting of the pipes from BULK to INTERUPT, it actually does send the inquiry request to the device (well, gives me a success anyway) but when I try to read back from the pipe, it gives me a STALL. Maybe that is normal to get a STALL if you set it to INTERRUPT, but try to read a pipe that is BULK. I don't know.

But the same issue about that state flag: The only place that eState member is set is within the ISR, and every step in the ISR is recorded to my memory log. And that member is NEVER set inside the ISR.

I tried reading the TI doc, which is the Tech Ref they call "spruh73". But that was a waste of time. It's missing a BUNCH of information. For example:

Section 16.2.8.2 - Host mode:

"This allows that one packet can be received while another is being read. Double packet buffering is enabled by setting the DPB bit of RXFIFOSZ register (bit 4)."

Well, that RXFIFOSZ register is not defined.

For that matter, neither is HOST_RXTYPE, HOST_RXINTERVAL, INTRRXE, etc... and bunches of other things.

The tech ref leaves a LOT to be desired in documenting this peripheral, and in offering support.

In summary: Can anyone steer me toward some example code that correctly opens EP1 and communicates through it? Or even actual, useful, doc that defines all this missing stuff?

Thanks in advance for any advice on this issue.

-Scotty

PS. Please do NOT suggest using the PDK, as it has all kinds of deficiencies.  It doesn't build on my PC, the precompiled libs are too interdependent with other things that will conflict with our environment, I can't hand trace the code as it's an obfuscated mess with no documentation  (Doxygen generated doc is useless no details, no explanations, no examples...) and I can't build one with debug info to step into anything...   I can't even be confident that the code which came with the PDK matches the precompiled libs...  And I tried to import and create a CCS project, but there are dozens of headers with IDENTICAL names, and no clue how to unravel the -I include paths used (and I've got pages more to be critical of , if anyone wants to hear...)

TestUSBhost.zip

  • Hello Scotty,

    Thanks for the detailed background information. I hope someone from the community can help, but unfortunately, TI has stopped supporting bare-metal SW development for AM335x devices. 

    Regards,

    Jianzhong

  • So...

    You sell a device, which you don't supply adequate documentation for, and won't support either.

    Which is why, every year, I recommend we find another supplier for the thousands and thousands of CPUs we use...

    Atmel, NXP, STMicro...    Companies with engineers who are willing to help.

  • I understood your frustration. For AM335x, we still fully support Linux development.

    We also have newer devices with freeRTOS such as AM62xx, AM243x, AM263x.

  • We also have newer devices with freeRTOS such as AM62xx, AM243x, AM263x.

    And do you publish all the USB information in those Tech Refs?  Or are they also filled with register names and bit names which are not defined anywhere....

    For AM335x, we still fully support Linux development.

    Linux doesn't use pixie dust to access a USB peripheral...  I'm pretty sure it uses actual code to set those registers, located at address 0x4740:xxxx.  

    So, somewhere, is some doc, and source code that allows use of the USB port as a host, and does communicate via EP1.  Because you support it.  Where might that MSC host class code be?

    Perhaps, if the doc was complete and comprehensive, I could solve it myself.  But that's not an option either.

    If we go FreeRTOS, and have to convert 400,000+ lines of C code, plus change all the register settings for all the peripherals, we can also find another chip.

      

  • So, complete silence is the TI solution.  Ignore your customer.

    I can tell my VP we can't meet the 10's of thousands units request for the new feature because TI don't give a ---- about their customers, and will not support the device they sell us.  

    Nor will they provide the documentation in their tech ref to assist us in solving it ourselves.  At least I've got email chains and forum threads to demonstrate it.

    This give me more motivation to press abandoning TI as a supplier.

  • Hello Chris 

    This is a complex topic, and I can some what understand your frustration - happy to get on a call if that helps. 

    I am struggling to find a good engineering solution for you. We stopped supporting Starterware for several years now, and stopped supporting TI RTOS since beginning for beginning of 2022. 

    The USB registers were never documented fully as some of the material is under NDA and we really do not want to encourage or support customers trying to develop complex USB drivers from scratch. 

    I have been tryng to look at historic data to see if there is a 3P offering on USB RTOS that we could connect you to , but have not found any specific ones that I can connect you to.

    I will explore internally to see if there is a customer version of the an NDA TRM for USB that can be provided, i do not know if one exists and what NDA it will require (I will have some more clarification on this next week) - even if it exist, it will likely be provided as is. 

    If you are asking to point to some relevant Linux code, I can explore that choice with our Linux developers, but from experience these drivers are written and structured very differently in Linux vs an RTOS implementation, so this may not set you up for success either. 

    Again, no good options. We are no longer supporting USB in bare metal or RTOS on these family of devices.

    I will internally pursue if there is any option to provide you register details that you seem to be missing. 
    Expect another update mid next week 

    Regards

    Mukul 

  • Hello Chris

    After additional discussion , we are unable to share any additional documentation on this. We have a IP design specification that requires a 3 way NDA between IP company - TI - customer and we do not think this will eventually be of help as we have very rarely provided this doc and we do not think it is conducive of driver development. 

    As mentioned the Starterware support was descoped almost 4-5 yrs back and it was replaced with PDK , which you have already evaluated and rejected - additionally starting 2022 PDK support was also descoped as we no longer support SYSBIOS or TI RTOS. 

    https://e2e.ti.com/support/tools/code-composer-studio-group/ccs/f/code-composer-studio-forum/957703/ccs-starterware-sitara-looking-for-the-example-code-of-usb-host-bulk-on-starterware

    Unfortunately I do not have any additional options to recommend to move this forward. 

    Regards
    Mukul 

  • You latest PDK would help me develop, IF IT BUILT IN WINDOWS.  But the script crashes.  More broken products, which you wouldn't even support BEFORE you wanted away from it.

    If I could, I would build it with debug on, and could trace through to see which one or two settings are different.  But instead it is restricted to only the precompiled libs, and all it's dependencies.

    You say Linux is not compatible with RTOS... DUH  I KNOW that.  I want the drive source so I can try to examine it.  I am NOT thinking that I would take the module and stick it in an RTOS.

    I am an actual software engineer...  have written and used Linux drivers.  I have also traced through Linux driver code to write non-Linux driver code.  And I have written RTOS programs, and know the difference.

    I even attached a FULL demo program. That doesn't need RTOS, doesn't need Linux, and only sets the registers for the the USB EP1.  Anyone who can develop for the Sitara chip could simply load it, and look at the one portion and tell me which settings are incorrect to get the EP1 working.

    Do you have software engineers??

    I have asked for only ONE form of assistance of ANY of these ways.  And your company refuses to offer ANY support.   No matter which of form of several support options I ask, I get some excuse why your company won't do it.

  • We do not support starterware or PDK. 
    We only support Linux based development on AM335x family as of now

    The latest Linux SDK is available from the following page

    https://www.ti.com/tool/PROCESSOR-SDK-AM335X

    I will ask my colleague to point to you some reference code in Linux for AM335x to see if that helps you. 

    Regards

    Mukul 

  • From Linux SDK here are some relevant source file pointers

    The kernel USB frameworks has multiple layers, which drivers are in multiple directorees in kernel source code.

    The MUSB controller drivers are under kernel drivers/usb/musb/ directory. The main files are:

    - musb_reg.h
    defines the MUSB registers and their bits information
    - musb_dsps.c
    the driver to handle the MUSB wrapper for AM335x
    - musb_core.c
    the MUSB core driver, handling common operations for both host and device mode
    - musb_host.c
    the host controller driver for MUSB, handling host operations
    - musb_virthub.c
    the virtual hub driver for MUSB, handling USB hub protocols

    Regards

    Mukul 

  • Okay, now we are getting somewhere...

    I assume the only place I can find these source files are buried in the BIN file that is 4Gig.

    What is the process to extract those source files from a BIN when running a Window environment?

  • The SDK bin file is not for Windows, but suppose to be installed in Linux. Alternatively you could see the kernel MUSB driver source code online at:

    https://git.ti.com/cgit/ti-linux-kernel/ti-linux-kernel/tree/drivers/usb/musb?h=ti-linux-6.1.y