Arduino Uno + STM32 Bluepill + STM32 Blackpill CAN Communication
by alaminashik in Circuits > Microcontrollers
29 Views, 0 Favorites, 0 Comments
Arduino Uno + STM32 Bluepill + STM32 Blackpill CAN Communication
CAN (Controller Area Network) communication is a reliable and efficient method of data exchange between electronic devices and microcontrollers. It has become very popular because of its ease of use, less number of wires. robustness and many more.
In this article, I will describe in details the use of this communication protocol using three different development boards, where one board will act as a master and the other two are slaves.
The master will periodically ask for data from the slaves, and they will respond with data to the master. Interrupts are used to ensure stability of the communication.
Note: Using MCP2515 CAN module with STM microcontrollers requires re-routing of wires on the PCB, this must be done carefully! (Step 4 and Step 5)
Supplies
List of things I used:
- 1 x Arduino Uno R3 dev board LINK
- 1 x STM32F103 Bluepill dev board LINK
- 1 x STM32F411 Blackpill dev board LINK
- 3 x MCP2515 CAN controller & Transceiver Module LINK
- 16 x Female-to-Female Jumper Wires LINK
- 7 x Male-to-Female Jumper Wires LINK
- 4 x Male-to-Male Jumper Wires LINK
- USB cables to connect dev boards to computer
- Soldering Iron (LINK), lead (LINK), and expertise!
Theory
This is one of the method for communicating between MCU's in a circuit. This is commonly used in vehicles and acts as the nervous system that connects the ECU (electronic control unit) in the vehicle.
Core concept:
- The communication of this protocol uses two wires: CANH and CANL.
- The standard voltage level of this CAN protocol is strictly 5V.
- It uses differential signalling:
- Recessive bit (logic 1) → both lines ≈ 2.5 V (no difference).
- Dominant bit (logic 0) → CAN_H ≈ 3.5 V, CAN_L ≈ 1.5 V (difference ≈ 2 V).
- When no data is being transferred using the bus wires, they both remain at 2.5V as shown on the diagram.
- When an MCU enquires data from the bus, both CANH and CANL becomes dominant bit, this triggers the start of frame.
- The MCP2515 is a CAN controller IC which communicates via SPI with the microcontrollers.
Data:
- There are varieties of CAN communications, but for our MCP2515 it can only send up to 8 bytes of data at ones.
- The data frame also contains, the unique address, Data length and acknowledge field.
- For sending higher bytes of data, several packets can be made and sent out sequentially.
To learn more about CAN protocol, check out these links:
https://www.picotech.com/library/knowledge-bases/oscilloscopes/can-bus-serial-protocol-decoding
https://medium.com/@sjindhirapooja/can-standard-data-frame-format-846b8f9fc749
Circuit Diagram
This is the complete circuit diagram of the setup.
All the CAN modules are connected via the SPI connection of the microcontrollers. Check if the correct wires are connected, as the pin configuration differs for all the development boards.
Make sure the two-pin jumper caps at the two end modules (Arduino and Black Pill) are connected, which shorts the communication lines parallel to an on-board 120 ohm resistor. This is to prevent signal reflections by matching the cable's impedance, which ensures stable and reliable communication.
An individual close-up of the circuit is written in the following steps.
Note: The interrupt (INT) pin is essential for proper data communication. It basically alerts the sender/receiver that someone wants to send/receive data.
Power supply can be provided from the same USB hub or computer; it will not interfere with the signal transmission.
Part 1: Arduino Uno (Master) & Code
Arduino Uno contains one default SPI, which can be directly connected to the module.
The connections are:
Coding
The following code is uploaded to Arduino UNO, and it works as follows:
- Initializing the libraries, variables, chip select (CS), and interrupt (INT) pins.
- The code under void setup() starts communication with the computer, with the module, and sets the interrupt pin as input (this can also be used as an interrupt, which is done for the slaves)
- The code under void askSlave() basically sends a single byte with the slave address to trigger a particular slave to send its data.
- The code under responseFromSlave() basically reads the data sent on the CAN bus
Part 2: STM32 Bluepill (Slave) & Code
The STM32F103C8T6 Blue Pill contains two SPIs, and one of which is connected to the CAN module.
The standard CAN communication works at 5V, but the pins of the blue pill are 3.3V-tolerant, so we need to make some adjustments (given in step 8) to power the MCP2515 by 3.3V and the TJA1050 by 5V.
The connections are:
Coding
If you don't know how to upload code to an STM board, check out this link from pcb-hero to learn more.
The following code is uploaded to the bluepill board, and it works as follows:
- Initializing the libraries, variables, chip select (CS), and interrupt (INT) pins.
- The code under void setup() starts the CAN communication, and attaches the interrupt pin to call the canInterrupt function every time this pin is physically triggered(by master).
- The code under canInterrupt basically reads the data and address sent by master. It then compares its address and if its a match, it will sent its data.
Part 3: STM32 Blackpill (Slave) & Code
The STM32F401 Black Pill has three SPIs, and we will use the first one only.
The standard CAN communication works at 5V, but the pins of the black pill are 3.3V-tolerant, so we need to make some adjustments (given in step 8) to power the MCP2515 by 3.3V and the TJA1050 by 5V.
The connections are:
Coding
If you don't know how to upload code to an STM board, check out this link from pcb-hero to learn more.
The following code is uploaded to the blackpill board, and it works as follows:
- Initializing the libraries, variables, chip select (CS), and interrupt (INT) pins.
- The code under void setup() starts the CAN communication, and attaches the interrupt pin to call the canInterrupt function every time this pin is physically triggered(by the master).
- The code under canInterrupt basically reads the data and address sent by the master. It then compares its address, and if it's a match, it will send its data.
Output From Master
The master keeps asking the slaves in sequence for data. This output shows the serial monitor only one slave (black pill) connected, and so only one slave is responding.
This can be done for multiple slaves.
Refer to the code above and match the output.
Output From Slaves
The master is asking 3 different slaves in sequence. This shows the output serial monitor of one of the slaves (Blue Pill). Whenever the asking address matches the slave's address, it will respond with a data "hi" and address. Otherwise, it ignores by saying "Master is asking data from someone else".
This is the same for the black pill as well. This ensures successful communication between the devices.
Troubleshot & Power Management
- Ensure both ends of the communication bus are connected to 120 ohm resistors. These resistors are already present on the CAN module, you just have to short the 2 male header pins.
- One important thing is that the standard CAN communication uses 5V to operate, and each bus holds 2.5V while not communicating. Thus, we need to modify the MCS2515 CAN board for the STM microcontrollers.
- As shown in the picture above, cut the wire that powers the TJA1050 IC with 3.3V, and connect it to the 5V of the microcontroller.
- As shown in the second picture, the red silicon wire is powering the TJA1050 by 5V.
and Done! cheers!