1. MavLink 基本介绍
1.1 介绍
MAVLink是一个非常轻量化的开源的消息协议,用于无人机之间的通信以及无人机机载设备之间的通信。
1.2 优点
标准化,通用化,高效,稳定,扩展性强,提供开放的API,二次开发简单,可自定义xml消息格式文件并生成C、C++,C#,Java,Python,Lua,JavaScript,TypeScript等编程语言的开发库。
1.3 版本
STX:数据包起始标志,0xFD;
LEN:PAYLOAD的长度;
SEQ:数据包序号,0~255,每次发送一个数据包,序号就会累加,循环往复;
SYS ID:设备系统级的ID,表明自己的ID身份;
COMP ID:设备组件级的ID,一个相同系统可能有多个不同组件都使用MAVLink进行通信;
PAYLOAD:存放通信数据,可能是信息、命令等;
1.4 打包与解包
以C/C++ 为例,mavlink 库中提供了通用的接口,mavlink_msg_*_encode/decode 函数,可以帮助我们快速打包或者解包一个 mavlink 数据。
对于一个 mavlink 数据帧来说,它首先是通用的 mavlink_message_t 类型(基类),然后才是具体的如 mavlink_scaled_pressure_t 类型(派生类)。
对于发送者而言,不必具体关心帧头校验等具体的协议组成,我们只需要了解具体的 MSG_ID 和对应的 Payload 即可;比如发送scaled_pressure 消息:
可以传入system_id,component_id,Payload (可以直接是结构体形式,或者散列形式),(MSG_ID由pack函数内部自动填充);最后通过参数msg输出为一个 mavlink_message_t 类型,然后通过mavlink_msg_to_send_buffer函数即可将该类型转换为buffer,然后传递给底层串口/网络套接字发送出去。
对于接收者而言,将从底层传入的buffer数据按照 char 类型依次传入 mavlink_parse_char 函数,如果在某次传入了一个char后返回了true,即得到了一个完整的 mavlink_message_t 类型,代表接收到一个数据。
然后通过 switch-case 语句来分拣ID:
最后在自定义处理函数中调用mavlink_msg_scaled_pressure_decode函数即可将数据填充进入结构体,用户只需要从结构体内取数据即可。
因此对于开发者而言,我们更加关注消息的名字,ID,Payload组成以及system_id,component_id(表明发送者的身份)
我们可以在 MAVLINK Common Message Set (common.xml) | MAVLink Guide 中查看某一个MSG的ID和定义:
1.5 MAVLink三大概念
1.5.1 msg
消息是MAVLink通信的基本数据单元,用于在飞控和地面站之间传输具体的数据结构,例如传感器数据、状态信息、控制指令等。每个消息对应一个唯一的msgid,并包含多个字段(如GPS坐标、姿态角、心跳包等)。
方向性:消息是双向的,飞控和地面站均可发送和接收。例如,飞控通过HEARTBEAT消息(msgid=0)告知状态,地面站通过GLOBAL_POSITION_INT(msgid=33)接收位置信息。
1.5.2 enum
枚举是预定义的常量值,用于表示状态、模式或参数类型。例如,MAV_MODE枚举定义飞行模式(如GUIDED、AUTO),MAV_CMD枚举定义指令类型(如MAV_CMD_NAV_WAYPOINT)。
作用:提供标准化标签,确保双方对参数含义理解一致。例如,custom_mode=4在枚举中被定义为引导模式。
1.5.3 cmd
指令是具体的操作命令(一种特殊的msg),通常通过COMMAND_LONG(msgid=76)或MISSION_ITEM消息发送,例如解锁、起飞、设置航点等。每个指令对应一个MAV_CMD枚举值,并包含最多(固定)7个参数。
方向性:主要由上位机发起(如QGC发送MAV_CMD_NAV_TAKEOFF),但飞控可能返回响应(如COMMAND_ACK)。
2. MavLink 通信简单解析
2.1 飞控上电默认自发外传的状态数据
MSG ID |
MSG 名称 |
MSG 解释 |
0 |
MAVLINK_MSG_ID_HEARTBEAT |
心跳帧 |
1 |
MAVLINK_MSG_ID_SYS_STATUS |
电压,传感器,丢包率 |
2 |
MAVLINK_MSG_ID_SYSTEM_TIME |