cancel
Showing results for 
Search instead for 
Did you mean: 

STM32F072 Discovery: USB Custom HID slowness

sandervocke
Associate
Posted on November 05, 2016 at 18:27

Hello everyone,

I am trying to get off the ground with the STM32F072 in USB Custom HID mode.

For starters, I followed this simple tutorial: https://www.youtube.com/watch?v=xufZyQf4O7Y

It goes through the following basic steps:

- set up a STM32Cube project with USB in Custom HID

- adjust the report descriptor and increase packet size to 64

- set up a main loop that sends packets every 500ms

That all works fine. Then I wanted to do a speed test to see whether the STM can use the USB FS speed fully (which should be able to send a 64B packet every ms). So I removed the HAL_Delay(500); call.

The result: only 32 packets are now sent per second. I confirmed this with my own application based on hidapi, and also with hidapi's general-purpose ''test receiver''.

Is it normal that the rate of HID transfer is this limited? Should I be able to reach 1000 packets/second? If so, does anyone have a clue what may be limiting the rate in this case? 

Thanks in any case!

#!stm32f072-!usb-!custom_hid
6 REPLIES 6
sandervocke
Associate
Posted on November 06, 2016 at 14:35

I found the answer to my issue. It turns out there is a setting for the ''Polling interval''. By default it is set to 32ms. It is found in usbd_customhid.c:

/* USB CUSTOM_HID device Configuration Descriptor */
__ALIGN_BEGIN 
static
uint8_t USBD_CUSTOM_HID_CfgDesc[USB_CUSTOM_HID_CONFIG_DESC_SIZ] __ALIGN_END =
{
0x09, 
/* bLength: Configuration Descriptor size */
USB_DESC_TYPE_CONFIGURATION, 
/* bDescriptorType: Configuration */
USB_CUSTOM_HID_CONFIG_DESC_SIZ,
/* wTotalLength: Bytes returned */
0x00,
0x01, 
/*bNumInterfaces: 1 interface*/
0x01, 
/*bConfigurationValue: Configuration value*/
0x00, 
/*iConfiguration: Index of string descriptor describing
the configuration*/
0xC0, 
/*bmAttributes: bus powered */
0x32, 
/*MaxPower 100 mA: this current is used for detecting Vbus*/
/************** Descriptor of CUSTOM HID interface ****************/
/* 09 */
0x09, 
/*bLength: Interface Descriptor size*/
USB_DESC_TYPE_INTERFACE,
/*bDescriptorType: Interface descriptor type*/
0x00, 
/*bInterfaceNumber: Number of Interface*/
0x00, 
/*bAlternateSetting: Alternate setting*/
0x02, 
/*bNumEndpoints*/
0x03, 
/*bInterfaceClass: CUSTOM_HID*/
0x00, 
/*bInterfaceSubClass : 1=BOOT, 0=no boot*/
0x00, 
/*nInterfaceProtocol : 0=none, 1=keyboard, 2=mouse*/
0, 
/*iInterface: Index of string descriptor*/
/******************** Descriptor of CUSTOM_HID *************************/
/* 18 */
0x09, 
/*bLength: CUSTOM_HID Descriptor size*/
CUSTOM_HID_DESCRIPTOR_TYPE, 
/*bDescriptorType: CUSTOM_HID*/
0x11, 
/*bCUSTOM_HIDUSTOM_HID: CUSTOM_HID Class Spec release number*/
0x01,
0x00, 
/*bCountryCode: Hardware target country*/
0x01, 
/*bNumDescriptors: Number of CUSTOM_HID class descriptors to follow*/
0x22, 
/*bDescriptorType*/
USBD_CUSTOM_HID_REPORT_DESC_SIZE,
/*wItemLength: Total length of Report descriptor*/
0x00,
/******************** Descriptor of Custom HID endpoints ********************/
/* 27 */
0x07, 
/*bLength: Endpoint Descriptor size*/
USB_DESC_TYPE_ENDPOINT, 
/*bDescriptorType:*/
CUSTOM_HID_EPIN_ADDR, 
/*bEndpointAddress: Endpoint Address (IN)*/
0x03, 
/*bmAttributes: Interrupt endpoint*/
CUSTOM_HID_EPIN_SIZE, 
/*wMaxPacketSize: 2 Byte max */
0x00,
0x01, 
/*bInterval: Polling Interval (20 ms)*/
//CHANGED FROM 0x20
/* 34 */
0x07, 
/* bLength: Endpoint Descriptor size */
USB_DESC_TYPE_ENDPOINT, 
/* bDescriptorType: */
CUSTOM_HID_EPOUT_ADDR, 
/*bEndpointAddress: Endpoint Address (OUT)*/
0x03, 
/* bmAttributes: Interrupt endpoint */
CUSTOM_HID_EPOUT_SIZE, 
/* wMaxPacketSize: 2 Bytes max */
0x00,
0x01, 
/* bInterval: Polling Interval (20 ms) */
//CHANGED FROM 0x20
/* 41 */
} ;

The ''bInterval'' field can be changed to 0x01, after which I saw 1000 packets per second as expected. That still leaves the question for me: is it normal to change this setting? It seems a bit strange to have to change the driver code instead of just the values configured in user code. Thanks!
Posted on February 25, 2017 at 14:14

Same question from me, changing bInterval every time I change something in stm32cubemx gets old after a while, it seems a bit... clunky.

Posted on May 16, 2017 at 12:18

It is absolutely normal to change polling interval. Not sure why CubeMX doesn't allow to change it from UI or in a User modifiable area.

BTW, CubeMX generates wrong comment for this field: bInterval unit is 1 frame for Low/Full speed devices. So 0x20 here means 32 ms, not 20...

Jeanne Joly
Senior III
Posted on January 16, 2018 at 16:44

Hi

76416

and

Tyurin.Denis_Mikhail

,

I was trying to reproduce the use case you refered to, on top of CubeMX4.

It seems that Denis answered vock's question. And for the comment for the bInterval, it has been changed on the latest releases :

0690X00000609OLQAY.png

As far as I understand your question, there is no remaining point.

Feel free to post any comment.

BR. Jeanne

Posted on January 18, 2018 at 23:49

But still 0x20 is 32 ms, not 20

- pa

Posted on January 19, 2018 at 10:53

Sorry

pavel_a

, I was not fully awake when I posted my thread...

I see the issue you highlight. It will be solved soon, I will keep you inform as soon as CubeMX contains this modification.

BR; Jeanne.