天天看點

ROS與STM32通信的實作1 通信協定2 原理3 準備工作4 程式設計5 測試

ROS功能包與STM32工程檔案:

藍奏雲:https://huffie.lanzouw.com/iN7w602ti37a

1 通信協定

STM32和ROS端各有一個資料發送函數和資料接收函數,發送和接受的資料以資料包的形式發送。

資料包的内容:

資料頭55aa + 資料位元組數size + 資料共用體 + 校驗crc8 + 資料尾0d0a

2 原理

2.1 收發資料方法簡述

首先,序列槽收發資料是一個位元組一個位元組的傳輸的。一個位元組最大表示資料是255,而往往我們需要傳遞的傳感器資料都是int/float類型的。

傳統的序列槽通信方法是将int/float資料分解成一個個位元組發送出去。

而這裡使用共用體,将資料通過共用體轉換為數組發送。

2.2 資料共用體的使用

共用體的規則:

  • 共用體是結構體内不同成員共享記憶體的機制,各成員記憶體位址一緻
  • 同一時刻隻能通路其中的一個成員
  • 不同成員按照成員類型的性質進行記憶體通路。

共用體的建立:

#include <stdio.h>
#include <string.h>

union Data
{
	int i;
	float f;
	char str[20];
};

int main()
{
	union Data data;
	data.i = 10;
	data.f = 220.5;
	strcpy( data.str, "C Programming");
	printf( "data.i : %d\n", data.i);
	printf( "data.f : %f\n", data.f);
	printf( "data.str : %s\n", data.str);
	return 0;
}
           

最後賦給變量的值占用了記憶體位置,是以同一時間隻能用到一個成員。

如何使用共用體

在通信兩端都定義同樣資料結構的共用體,該共用體包含一個short/int/float類型的變量和一個unsigned char類型的數組,數組大小與變量位元組大小對應。這樣發送和接收資料時,隻發送或接收共用體中unsigned char數組的元素。

[外鍊圖檔轉存失敗,源站可能有防盜鍊機制,建議将圖檔儲存下來直接上傳(img-2H37g76m-1657014428833)(https://gitee.com/huffiema/pictures/raw/master/image/202203251701027-stm32-ros-1.png)]

3 準備工作

3.1 硬體準備

使用STM32序列槽+TTL轉USB子產品(CH340)+Linux裝置。

[外鍊圖檔轉存失敗,源站可能有防盜鍊機制,建議将圖檔儲存下來直接上傳(img-PNRHaaBv-1657014428835)(https://gitee.com/huffiema/pictures/raw/master/image/202203251702390-stm32-ros-2.png)]

注意事項:

  • STM32和ROS的序列槽波特率必須一緻
  • STM32序列槽和USB轉TTL子產品連接配接正确,RX-TX,TX-RX
  • Linux裝置安裝好CH340/CH341驅動
  • 確定序列槽在Linux系統上有超級使用者權限
  • 将ROS功能包中mbot_linux_serial.cpp檔案中的序列槽裝置名字改為自己的裝置名

3.2 序列槽設定

檢視序列槽裝置

Linux裝置插上USB轉TTL子產品後,打開終端,輸入指令:

ls -l /dev/ttyUSB*
           

如果終端出現類似下面的輸出結果,說明序列槽裝置已經被識别

crw-rw---- 1 root dialout 188, 0 3月  25 17:07 /dev/ttyUSB0
           

設定序列槽權限

在終端中輸入下面指令:(注意自己的序列槽裝置名)

sudo chmod 777 /dev/ttyUSB0 
source devel/setup.bash
           

如果沒有任何輸出,說明序列槽裝置設定權限成功。(每次重新啟動或重新插入序列槽裝置後都需要進行這樣的操作)

4 程式設計

4.1 STM32程式設計

工程檔案中提供的是STM32F103的程式,也可以在自己闆子的序列槽收發例程的基礎上進行修改,添加mbotLinuxUsart.c和mbotLinuxUsart.h到工程中即可。

函數調用方式如下:

#include "delay.h"
#include "sys.h"
#include "usart.h"
#include "mbotLinuxUsart.h"//引用該頭檔案是使用,通信協定的前提

//測試發送變量
short testSend1   =5000;
short testSend2   =2000;
short testSend3   =1000;
unsigned char testSend4 = 0x05;

//測試接收變量
int testRece1     =0;
int testRece2     =0;
unsigned char testRece3 = 0x00;

int main(void)
{   
/*************** 硬體初始化 ***************/
    delay_init();                                   //延時函數初始化   
    NVIC_PriorityGroupConfig(NVIC_PriorityGroup_2); //設定中斷優先級分組2
    uart_init(115200);                              //序列槽初始化為115200

/***************循環程式 ***************/
    while(1)
    {
        //将需要發送到ROS的資料,從該函數發出,前三個資料範圍(-32768 - +32767),第四個資料的範圍(0 - 255)
        usartSendData(testSend1,testSend2,testSend3,testSend4);
        //必須的延時
        delay_ms(13);
    } 
}

/*************** 序列槽中斷服務程式 ***************/
void USART1_IRQHandler()
{
    if(USART_GetITStatus(USART1, USART_IT_RXNE) != RESET)
     {
         USART_ClearITPendingBit(USART1,USART_IT_RXNE);//首先清除中斷标志位
         //從ROS接收到的資料,存放到下面三個變量中
         usartReceiveOneData(&testRece1,&testRece2,&testRece3);
     }
}
           

4.2 ROS程式設計

[[01_Ubuntu20.04安裝ROS Noetic|ROS安裝]]過程不再介紹

第一步

首先[[13_ROS系統基本功能的使用詳解(基本指令、節點、服務、啟動檔案、動态參數)]](如果沒建立的話)

mkdir -p ~/catkin_ws/src
cd catkin_ws/src
catkin_init_workspace
           

第二步

将topic_example功能包複制到src目錄下,然後回到工作空間目錄進行編譯

cd ..
catkin_make
           

5 測試

添加序列槽裝置權限

sudo chmod 777 /dev/ttyUSB0
source devel/setup.bash
           

打開新終端,啟動`ros master

roscore
           

打開新終端,啟動測試功能包

rosrun topic_example publish_node
           

可以看到從STM32接收到的資料。

ROS與STM32通信的實作1 通信協定2 原理3 準備工作4 程式設計5 測試
ROS與STM32通信的實作1 通信協定2 原理3 準備工作4 程式設計5 測試
本部落格文章首先釋出于個人部落格:https://www.mahaofei.com/,歡迎大家通路。

繼續閱讀