Rosserial & STM32

The ROS robotic operating system is a fairly powerful platform for creating robotic systems, which includes everything necessary for developing your projects from the simplest software components called “nodes” and the data exchange protocol to the simulation environment of a real Gazebo robotic platform. Mostly ROS is used in conjunction with such microcontrollers on the Arduino platform. The Internet is full of all sorts of tutorials on a bunch of ROS and Arduino.

There is currently no information on the use of the ROS robotic operating system in conjunction with the STM32 microcontroller. The Internet is only full of questions.



Get started


To work with STM32 we need STM32CubeMX and SystemworkbenchforSTM32. There is plenty of information about their installation on the network, we will not dwell on this.

To configure the controller, go to STM32CubeMX.

Create a new project.



We’ll select a microcontroller, I have STM32f103c8t6.



In the periphery, we indicate that an external quartz resonator is connected, we have 2 of them. We



configure the outputs through which you can enable debugging of the controller (looking ahead, if the project is in C ++, debugging may not work)



Let's configure port 13 of port C, to it has a built-in LED.



Set up the UART pins.



Go to Lock_configuration and make the settings as in the picture.



Let's move on to more detailed configuration of the periphery


UART

Setting the data rate.



DMA setup.





Configure interrupt, you need to specify a global interrupt on UART



GPIO setup




Project build setup




We are waiting for it to gather.



We open the project,



Creating a project for System Workbench For STM32


By opening this project in SW4STM32, adding some peripheral control, assembling it, and flashing the controller, I did not get any result.

Therefore, we create a new project according to the following instructions, and transfer the configuration obtained by STM32CubeMX.

Creating a project for System Workbench For STM32


1) Click File> New> C Project

2) C Project
1) Enter the name of the project
2) Choose the type of project: Executable> Ac6 STM32 MCU Project
3) Select Toolchains: Ac6 STM32 MCU GCC
4) Click "Next"



3) Select the microcontroller
1 ) Click “Create a new custom board”
1) Save Definition of a new board
2) Enter the name of the new board: STM32F103
3) Select the chip of the board: STM32F1
4) Select the MCU: STM32F103RCTx
5) Click “OK”.
2) Select the board you just created!
1) Select a series: STM32F1
2) Select a board: STM32F103
3) Click "Next"



4) Connect the HAL libraries



5) Click "Finish"

Adding Files


We copy the contents of the src and inc files created by the cube into our files, we also copy STM32F103C8Tx_FLASH.ld.



To check the operability of STM32 itself and the code in the while loop, write the following lines

      HAL_GPIO_TogglePin(GPIOC, GPIO_PIN_13);
      HAL_Delay(100);

Here we just blink the LED.

During assembly, problems may occur in the stm32f1xx_hal_msp.c file. The

error associated with the void function HAL_MspInit (void) is fixed as follows.
We open the folder with the HAL_Driver library, go to / src, open the stm32f1xx_hal_msp_template.c file and comment out the same function:



We reassemble (it should assemble without errors) I

forgot to mention the st-flash utility for the controller firmware.

$ sudo apt-get install cmake 
$ sudo apt-get install libusb-1.0.0 
$ git clone github.com/texane/stlink.git 
$ cd stlink 
$ make release 
$ cd build/Release; sudo make install 
$ sudo ldconfig 

Using ST link

Verifying ST link detection:

$ st-info —probe 

In response, we should see something like:

Found 1 stlink programmers 
serial: 563f7206513f52504832153f 
openocd: "\x56\x3f\x72\x06\x51\x3f\x52\x50\x48\x32\x15\x3f" 
flash: 262144 (pagesize: 2048) 
sram: 65536 
chipid: 0x0414 
descr: F1 High-density device 

To flush the controller, go to the folder of our project and flash the controller through the following command:

cd workspace/ros_stm32_2/
st-flash write Debug/ros_stm32_2.bin 0x8000000

Checked. Everything works. We move on.

Since the ROS libraries are written in C ++, we translate our project into a C ++ project, and change the file format main.c, stm32f1xx_hal_msp.c, stm32f1xx_it.c to .cpp We

clone my repository with the libraries and the necessary files for rosserial to work on STM32.

git clone https://gitlab.com/ivliev123/ros_lib

We insert the cloned folder into the project





Let's go to the project settings (Properties), first of all, connect the library, go ...







Change the linker





Perform the optimization





Well, now we will make some changes to main.cpp, since it is almost empty, the first thing we do is connect the ROS library, and libraries for interactions with ROS topics, or rather with the data types of these topics.

#include 
#include 
#include 

Create a node that publishes this topic and accepts

void led_cb( const std_msgs::UInt16& cmd_msg){
          HAL_GPIO_TogglePin(GPIOC, GPIO_PIN_13);
}
ros::NodeHandle nh;
std_msgs::String str_msg;
ros::Publisher chatter("chatter", &str_msg);
ros::Subscriber sub("led", led_cb);

Initialize the node and topics in main.

        nh.initNode();
        nh.advertise(chatter);
        nh.subscribe(sub);

We also add variables to work with time and what we will publish.

const char * hello = "Hello World!!";
int chatter_interval = 1000.0 / 2;
int chatter_last = HAL_GetTick();

In the while loop, we will have the following. We will publish our phrase after a certain time.

        if (nh.connected())
        {
            if(HAL_GetTick() - chatter_last > chatter_interval)
            {
                str_msg.data = hello;
                chatter.publish(&str_msg);
                chatter_last = HAL_GetTick();
            }
        }
        nh.spinOnce();

Putting together a project.

The following errors may appear:







Reassemble and flash.

Now directly interacting with ROS.
In one terminal, run ROS.

roscore

In the next run the node.

rosrun rosserial_python serial_node.py /dev/ttyUSB0

We get the following

[INFO] [1551788593.109252]: ROS Serial Python Node
[INFO] [1551788593.124198]: Connecting to /dev/ttyUSB0 at 57600 baud
[INFO] [1551788595.233498]: Requesting topics...
[INFO] [1551788595.258554]: Note: publish buffer size is 2048 bytes
[INFO] [1551788595.259532]: Setup publisher on chatter [std_msgs/String]
[INFO] [1551788595.275572]: Note: subscribe buffer size is 2048 bytes
[INFO] [1551788595.276682]: Setup subscriber on led [std_msgs/UInt16]

Next, in a new terminal window, look at the topics

rostopic list 

We get the following topics:

/chatter
/diagnostics
/led
/rosout
/rosout_agg

In the topic of the chatter, the controller publishes the phrase.

We can listen to it through the team

rostopic echo /chatter 



Now send the data to the topic led.

rostopic pub /led std_msgs/UInt16 "data: 0" 

And we have to change the state of the LED.

Also popular now: