Sunday, 12 June 2016

STM32 USB CDC VCP

I had a lot of trouble using USB CDC. So I decided to create a small library. The library uses STM32 HAL and the USB middle-ware. The code is for STM32L0. However it can be easily modified for other STM32 lines.


First add VCP.h



Then add VCP.c



Modify usbd_cdc_if.c. I also changed APP_RX_DATA_SIZE and APP_RX_DATA_SIZE to 256


Finally change main.c . Include the VCP.h .



The VCP_read checks if the FIFO has data. If it has data then it sends the data back to the computer using VCP_write.

To see interaction use

picocom -b 9600 /dev/ttyACM0

Then enter some data into the VCP.

 echo "hello world" > /dev/ttyACM0


The response

 Terminal ready
stack=0,i=12,data=hello world

5 comments:

  1. Hello!

    I'm trying to modify this for the stm32f042C6T6 but i'm not sure where to start. I've added the VCP files to the project and modified the usbds_cdc_if.h and included the VCP header in main.c

    When I compile I get errors about overflow in 'RAM' and 'FLASH' region"

    CDC-Uart.elf section `.data' will not fit in region `FLASH' CDC-Uart C/C++ Problem
    CDC-Uart.elf section `._user_heap_stack' will not fit in region `RAM' CDC-Uart C/C++ Problem
    region `FLASH' overflowed by 632 bytes CDC-Uart C/C++ Problem
    region `RAM' overflowed by 876 bytes CDC-Uart C/C++ Problem

    I'm guessing its a memory thing but im not sure where to begin?

    Thanks
    Nathan

    ReplyDelete
    Replies
    1. The chip you are using doesn't have enough RAM to store the buffers.

      Reduce the values bellow:
      FIFO_WIDTH 16
      APP_RX_DATA_SIZE 16
      APP_TX_DATA_SIZE 16
      uint8_t hexbuffer[16];
      uint8_t textbuf[16];

      It will only transmit and receive 16 characters at a time instead of 256 characters.

      Delete
  2. Great work, thanks a lot for sharing! I think this finally also solved my issues with USB CDC as well here, using a STM32L072.

    The key of your solution was to use multiple input FIFO buffers, I think. Otherwise I always had problems with incoming characters not being passed over to my program (e.g. when typing fast or using copy/paste).

    Minor fix:
    I needed to use ".*s" in the printout to prevent sprintf printing garbage characters to the string:
    sprintf(textbuf,"stack=%u,i=%u,data=%.*s\r\n",RX_FIFO.FIFO_POS,Len,Len,(char *)hexbuffer);

    By the way, something I've found out by debugging the CDC stuff for hours: GDB can print variable contents on breakpoints without stopping, like this. Came in quite handy:

    break usbd_cdc_if.c:CDC_Receive_FS
    commands
    silent
    print Buf[0]
    print *Len
    continue
    end

    ReplyDelete
    Replies
    1. Hi,
      I can't able to fix the error, pls share the updated code

      Delete

  3. # no page breaks
    set pagination off

    ReplyDelete