cancel
Showing results for 
Search instead for 
Did you mean: 

STM32Cube USB Host Driver Interrupt Flood

elmood
Associate III
Posted on January 30, 2016 at 17:47

Hey folks, I've been working on USB host driver for MIDI, and so far I can enumerate the device and get data flowing. But as soon as the device is attached I get crazy numbers of interrupts related to IN transactions. A trace of the USB shows an IN being sent from the STM32 to the connected device about every 3us or so. Each request generates a USB interrupt when the NAK is received. It basically causes the rest of my application to be unresponsive.

A few questions:

- Is there a way to mask these out of the Cube drivers? A quick hack proved that there was some housekeeping that relied on this interrupt.

- Is there a way to slow down the IN requests? I don't need so many per USB frame.

Also a somewhat related question about the overall design of the USB host driver framework: It seems that polling using the BgndProcess callback is the only way to actually transfer data. That would mean that unless I want to run my polling task really fast there would be no way to actually get more bulk transfers per frame anyway, since it has to receive the data and then set up the next transfer.

I guess DMA is possible but the examples all seem to only deal with setting up endpoints and exchanging data on the polling task. Ideally I'd prefer to have a callback that allows me to service each IN request as it arrives, and a way to throttle how fast the IN requests are sent to the device.

Please help, I've been battling this for days!
6 REPLIES 6
elmood
Associate III
Posted on February 08, 2016 at 19:08

Bump. Anyone?

dthedens
Associate II
Posted on February 08, 2016 at 22:03

you do not mention the particular STM32.

But I would not expect an IN at a minimum of Full Speed 1 ms, and High Speed 125 us.

Actually I would expect them to occur based upon the device enumeration where the device tells the Host what polling speed it prefers.

I have not looked at the cube USB stack, so I cannot help, but you are right, 3 us is way, way to fast.
elmood
Associate III
Posted on February 09, 2016 at 16:48

Hi thedens,

Thank you for replying! I'm using the STM32F407. (100 pin package) The FS peripheral is being used as a USB device, and the HS peripheral (with internal FS PHY) is being used to provide the host port, which is the one I'm having trouble with.

AFAIK the bRefresh option on an endpoint determines how fast it will be polled for new data. In my case the class specification sets it to 0. But once per full speed frame would be enough. I assume there is some kind of timer in the host controller hardware that is causing this approx. 3us interval but after staring at the registers I can't see what it might be.

So my goal is to either slow down the IN requests or make sure that only INs that didn't receive a NAK generate an interrupt.

Thanks!

tsuneo
Senior
Posted on February 09, 2016 at 20:08

> But once per full speed frame would be enough.

You may assign the bulk endpoint as an interrupt endpoint of bInterval = 1ms. And then, transactions occur just once per FS frame. On USB line, bulk and interrupt (and Data stage of Control transfer) are carried by the same IN/OUT transactions. Even if host would assign the bulk endpoint as interrupt one, the device doesn't concern.

I measured NAK sequence on OTG-FS host of F469I-DISCO board. NAK interval was around 8us. Almost 50% of this interval was occupied by handling of USB interrupt, which processes NAK. When NAK occurs, the channel is disabled by the hardware. The USB ISR enables the channel for another transaction. And then, another NAK interrupt occurs. I believe there is no timing control for non-periodic queue of this USB core (both of FS/HS). To throttle down, firmware should defer the timing to enable the NAKed channel.

Tsuneo

elmood
Associate III
Posted on February 10, 2016 at 21:42

Hey, thanks for the info. Certainly a 50% overhead servicing NAK interrupts is not going to work for me.

When you say ''firmware should defer the timing to enable the NAKed channel.'' do you mean that I should just wait until the next SOF and then do whatever has to be done? Is there a way to set the Cube firmware to do this?

guy_l
Associate
Posted on October 19, 2016 at 14:10

Hello all.

Anybody managed to solve this? i.e. reduce NAK interrupt frequency in STM32F4xx?

Here's what I tried so far: 

  • I have STM32F407 running as USB Host on both USBH_HS and USBH_FS.
  • USB interrupts took up ~80% of my CPU load.
  • On USBH_HS I was able to mask NAK interrupts (USB_OTG_HCINTMSK_NAKM) and still retain communication with the device.
  • on USBH_FS - once I mask the NAKs - communication with device becomes bad - it is not able to complete enumeration (Get Device Config receives only 64 bytes). if I mask NAKs after enumeration - still there is no response from the device on the data endpoints.
  • I tried to mark the channel as Interrupt as suggested above.

    I ran the following code after enumeration:

    USBx_HC(ch_num)->HCCHAR |= (EP_TYPE_INTR << 18);

    that made the host to stop sending send IN and OUT requests.
  • I tried marking the channel as LOW_SPEED after enumeration, using this code:

    USBx_HC(ch_num)->HCCHAR |= USB_OTG_HCCHAR_LSDEV;

    that made the device not respond to any IN or OUT request, not event with ACK/NAK.

any help will be appreciated.

Thanks.