cancel
Showing results for 
Search instead for 
Did you mean: 

Modifying code and recompiling randomly breaks USB CDC

Teemu Ikonen
Associate II
Posted on September 19, 2017 at 15:47

Hi,

I've generated basic USB CDC sample with the CubeMX and have lots of trouble getting it to work reliably. Device appears as COM port in Windows but Terminal app (like Putty) sometimes fails to open it.

The pattern seems to be that when I modify code, like add single irrelevant line or call things like 'puts' that is never executed, the app links and loads and device shows up as COM port but Terminal app suddenly fails to connect. When this happens it's consistent, it never works or always works.

Randomly adding dummy code lines (like 'int k = sizeof(int);')  or littering it with HAL_Delay sometimes cures it but I've not understood what is the root cause of this problem.

Here is main loop that appears to work, but for example if I uncomment any of the puts statements code sometimes fails. Note that even when puts is not ever called, just linking it can cause the issue.

int main(void)

{

initialise_monitor_handles(); // semihosting, required for prints to work

// Reset of all peripherals, Initializes the Flash interface and the Systick.

HAL_Init();

// Configure the system clock

SystemClock_Config();

// Initialize all configured peripherals

MX_GPIO_Init();

MX_USB_DEVICE_Init();

// set red led on

BSP_LED_Init(LED6); // blue

BSP_LED_Init(LED5); // red

BSP_LED_On(LED5);

// Need to check when CDC_Init_FS has been called instead of wait

HAL_Delay(500);

USBD_CDC_ReceivePacket(&hUsbDeviceFS);

uint8_t msg[] = 'Hello World!\r\n';

int c = 0;

//puts('For');

HAL_Delay(500);

for(;;) {

     CDC_Transmit_FS(msg, sizeof(msg)-1);

     HAL_Delay(200);

     if(c++ > 500000) {

       // not called but just uncommenting this line will cause Terminal app to fail

       //puts('Sent');

     }

}

return 0;

}
1 REPLY 1
Teemu Ikonen
Associate II
Posted on September 19, 2017 at 18:08

Ok some progress. It appears this could be caused by random heap corruption triggered by the USB device library.

Interrupt handler calls USBD_CDC_Init and this function allocates memory with a 'malloc' (see USBD_malloc). This is very bad. I removed references to malloc/free and now things look a lot more stable.

static USBD_CDC_HandleTypeDef CDCClassData;

...

//pdev->pClassData = USBD_malloc(sizeof (USBD_CDC_HandleTypeDef));

pdev->pClassData = &CDCClassData;

...

Details of the issue

https://community.st.com/0D50X00009Xkft5SAB