esp-idf-can2usb

May 13, 2026 ยท View on GitHub

CANbus to USB bridge using esp32.
The ESP32-S2/S3/P4 has a full-speed USB OTG peripheral with integrated transceivers and is compliant with the USB 1.1 specification.
On the ESP32-S2/S3, GPIO19 and GPIO20 are used as USB D- and D+.
On the ESP32-P4, GPIO26 and GPIO27 are used as USB D- and D+.

It's purpose is to be a bridge between a CAN-Bus and a USB OTG.
Unlike the standard serial port, the USB OTG port does not display initial output from the ROM bootloader.

slide0001

NOTE for ESP32P4
The full-speed USB OTG port is disabled by default.
It needs to be explicitly enabled.

Software requirement

ESP-IDF V5.0 or later.
ESP-IDF V4.4 release branch reached EOL in July 2024.

Note for ESP-IDF V6
Under ESP-IDF V6.0 or later, this project uses a new twai driver.

Hardware requirements

  1. ESP32-S2/S3/P4 Development board
    Because the ESP32-S2/S3/P4 does support USB OTG.

  2. SN65HVD23x CAN-BUS Transceiver
    SN65HVD23x series has 230/231/232.
    They differ in standby/sleep mode functionality.
    Other features are the same.

  3. Termination resistance
    I used 150 ohms.

  4. USB Connector
    The onboard USB port does not have USB OTG functionality.
    I used this USB Mini femail:
    usb-connector

    ESP32-S2/S3 BOARD          USB CONNECTOR
                               +--+
                               | || VCC
        [GPIO 19]    --------> | || D-
        [GPIO 20]    --------> | || D+
        [  GND  ]    --------> | || GND
                               +--+
    
    ESP32-P4 BOARD             USB CONNECTOR
                               +--+
                               | || VCC
        [GPIO 26]    --------> | || D-
        [GPIO 27]    --------> | || D+
        [  GND  ]    --------> | || GND
                               +--+
    

Wireing

SN65HVD23xESP32-S2/S3ESP32-P4
D(CTX)--GPIO17GPIO2(*1)
GND--GNDGND
Vcc--3.3V3.3V
R(CRX)--GPIO18GPIO3(*1)
Vref--N/CN/C
CANL--To CAN Bus
CANH--To CAN Bus
RS--GNDGND(*2)

(*1) You can change using menuconfig.

(*2) N/C for SN65HVD232

Test Circuit

   +-----------+ +-----------+ +-----------+ 
   | Atmega328 | | Atmega328 | | ESP32-S2  | 
   |           | |           | |           | 
   | Transmit  | | Receive   | | 17    18  | 
   +-----------+ +-----------+ +-----------+ 
     |       |    |        |     |       |   
   +-----------+ +-----------+   |       |   
   |           | |           |   |       |   
   |  MCP2515  | |  MCP2515  |   |       |   
   |           | |           |   |       |   
   +-----------+ +-----------+   |       |   
     |      |      |      |      |       |   
   +-----------+ +-----------+ +-----------+ 
   |           | |           | | D       R | 
   |  MCP2551  | |  MCP2551  | |   VP230   | 
   | H      L  | | H      L  | | H       L | 
   +-----------+ +-----------+ +-----------+ 
     |       |     |       |     |       |   
     +--^^^--+     |       |     +--^^^--+
     |   R1  |     |       |     |   R2  |   
 |---+-------|-----+-------|-----+-------|---| BackBorn H
             |             |             |
             |             |             |
             |             |             |
 |-----------+-------------+-------------+---| BackBorn L

      +--^^^--+:Terminaror register
      R1:120 ohms
      R2:150 ohms(Not working at 120 ohms)

NOTE
3V CAN Trasnceviers like VP230 are fully interoperable with 5V CAN trasnceviers like MCP2551.
Check here.

Installation

git clone https://github.com/nopnop2002/esp-idf-can2usb
cd esp-idf-can2usb
idf.py set-target {esp32s2/esp32s3/esp32p4}
idf.py menuconfig
idf.py flash

Configuration

config-main config-app

Definition from CANbus to USB

When CANbus data is received, it is sent by USB OTG according to csv/can2usb.csv.
The file can2usb.csv has three columns.
In the first column you need to specify the CAN Frame type.
The CAN frame type is either S(Standard frame) or E(Extended frame).
In the second column you have to specify the CAN-ID as a hexdecimal number.
In the last column you have to specify the Frame Name. This project does not use this column.

S,101,Water Temperature
E,101,Water Pressure
S,103,Gas Temperature
E,103,Gas Pressure

Brows data Using Windows Terminal Software

When you connect the USB cable to the USB port on your Windows machine and build the firmware, a new COM port will appear.
Open a new COM port in the terminal software.
I used TeraTerm.
teraterm

Brows data Using Linux Terminal Software

When you connect the USB cable to the USB port on your Linux machine and build the firmware, a new /dev/tty device will appear.
Open a new tty device in the terminal software.
Most occasions, the device is /dev/ttyACM0.
I used screen.
screen

Brows data Using python script

You can use read.py script. python read.py
python

Powerd from USB OTG

After writing the firmware, the ESP32 can get power from the USB OTG.
Stop power supply from the onboard USB port.

    ESP BOARD              USB CONNECTOR
                           +--+
    [  VIN  ]    --------> | || VCC
    [USB_DM ]    --------> | || D-
    [USB DP ]    --------> | || D+
    [  GND  ]    --------> | || GND
                           +--+

Troubleshooting

There is a module of SN65HVD230 like this.
SN65HVD230-1

There is a 120 ohms terminating resistor on the left side.
SN65HVD230-22

I have removed the terminating resistor.
And I used a external resistance of 150 ohms.
A transmission fail is fixed.
SN65HVD230-33

If the transmission fails, these are the possible causes.

  • There is no receiving app on CanBus.
  • The speed does not match the receiver.
  • There is no terminating resistor on the CanBus.
  • There are three terminating resistors on the CanBus.
  • The resistance value of the terminating resistor is incorrect.
  • Stub length in CAN bus is too long. See here.

Reference

https://github.com/nopnop2002/esp-idf-can2mqtt

https://github.com/nopnop2002/esp-idf-can2http

https://github.com/nopnop2002/esp-idf-can2bt

https://github.com/nopnop2002/esp-idf-can2socket

https://github.com/nopnop2002/esp-idf-can2websocket

https://github.com/nopnop2002/esp-idf-CANBus-Monitor