Files
Gimbal/ARCHITECTURE.md
T
2026-05-29 17:36:34 +08:00

15 KiB
Raw Blame History

项目架构分析报告:Basic_Framework_MC02 (RoboMaster 云台机器人)

概览

这是一个基于 STM32H723 (Cortex-M7) 的 RoboMaster 竞赛机器人控制项目。项目采用 FreeRTOS 实时操作系统,目前配置为单板控制整车(ONE_BOARD 模式),代码组织呈分层架构。项目由 湖南大学岳麓电气 (HNU YueLu EC) 开发。


一、硬件与通信总览

资源 用途
FDCAN1/2/3 电机控制总线(DJI 电机、达妙电机等)
USART1 板间通信 (BoardComm)
USART5 遥控器 (DBUS/DR16)
USART7 VoFA 调试输出
USART10 视觉/上位机 (OpenCV 通信)
SPI1/2 BMI088 IMU 传感器、OLED
I2C2 通用 I2C
OCTOSPI2 外部 Flash (W25Qxx)
TIM1/2/3/12 PWM 输出、编码器输入、DWT 时钟基准
USB Device 虚拟串口 (CDC)
ADC1 模拟量采集
GPIO 电源控制、激光器等

二、分层架构

项目采用 4 层架构:

┌──────────────────────────────────────────────────────────┐
│  application/  应用层                                    │
│  robot.c → robot_cmd → gimbal / chassis / shoot         │
├──────────────────────────────────────────────────────────┤
│  modules/      模块层                                    │
│  motor, imu, referee, remote, vision, algorithm, ...    │
├──────────────────────────────────────────────────────────┤
│  bsp/          板级支持包                               │
│  can, usart, spi, iic, pwm, dwt, log, gpio             │
├──────────────────────────────────────────────────────────┤
│  Drivers/      HAL 驱动层 (CubeMX 生成)                 │
│  STM32H7xx_HAL, CMSIS, FreeRTOS, USB, SEGGER RTT       │
└──────────────────────────────────────────────────────────┘

三、启动与初始化流程

3.1 main() 启动序列

HAL_Init() → SystemClock_Config() → MX_GPIO_Init() → MX_DMA_Init()
→ MX_ADC1_Init() → MX_USB_DEVICE_Init() → MX_TIM/SPI/USART/UART/FDCAN/..._Init()
→ RobotInit()           ← 唯一的用户初始化入口
→ while(1) {}           ← 空循环,所有逻辑在 RTOS 任务中

3.2 RobotInit() 初始化链

RobotInit()
  ├── __disable_irq()                           // 关中断,保证初始化原子性
  ├── BSPInit()
  │     ├── DWT_Init(480)                       // 时钟周期计数器 (CPU=480MHz)
  │     └── BSPLogInit()                        // 日志系统(SEGGER RTT + 串口)
  ├── RobotCMDInit()                            // 核心命令任务初始化
  │     ├── RemoteControlInit(&huart5)          // 遥控器 (DBUS)
  │     ├── PubRegister() x6                    // 注册 6 个消息话题:
  │     │     gimbal_cmd / gimbal_feed          // 云台控制/反馈
  │     │     shoot_cmd / shoot_feed            // 发射控制/反馈
  │     │     chassis_cmd / chassis_feed        // 底盘控制/反馈
  │     ├── PIDInit() x2 (yaw + pitch 跟踪PID) // 视觉跟踪 PID 初始化
  │     ├── VisionKalmanFilterInit()            // 视觉误差卡尔曼滤波器
  │     ├── Vision_Uart_Init(&huart10)          // 视觉串口通信
  │     └── BoardCommInit(&huart1)              // 板间通信
  ├── GimbalInit()                              // 云台电机初始化
  │     ├── INS_Init() → BMI088 SPI 初始化     // IMU 惯导
  │     ├── PubRegister("gimbal_feed") / SubRegister("gimbal_cmd")
  │     ├── DJIMotorInit(GM6020) → yaw 电机    // Yaw: GM6020 直驱
  │     └── DMMotorInit() → pitch 电机         // Pitch: 达妙电机
  ├── OSTaskInit()                              // 创建 RTOS 任务
  │     ├── INS Task (1kHz, AboveNormal)        // 姿态解算最高优先级
  │     ├── Motor Task (1kHz, Normal)           // 电机控制
  │     ├── Daemon Task (100Hz, Normal)         // 看门狗/蜂鸣器
  │     ├── Robot Task (500Hz, Normal)          // 机器人核心控制
  │     └── DMMotorControlInit()                // 达妙大电机初始化
  └── __enable_irq()                            // 开中断

四、FreeRTOS 任务架构

任务 频率 优先级 功能
INS Task 1kHz AboveNormal 阻塞读取 BMI088,进行四元数 EKF 姿态解算
Motor Task 1kHz Normal DJI/LK/HT 电机 PID 闭环计算与 CAN 发送
Robot Task 500Hz Normal 调用 RobotTask() 串联各应用层任务
Daemon Task 100Hz Normal 模块看门狗喂狗检查 + 蜂鸣器控制

五、消息中心 (Pub-Sub)

位于 modules/message_center/,这是应用层内部的核心通信机制:

  • 发布者 (Publisher):以话题名 (topic name) 标识,通过链表管理订阅者
  • 订阅者 (Subscriber):每个订阅者维护一个长度为 1 的 FIFO 队列
  • 支持最多 12 个话题,话题名最长 32 字符

当前消息流:

robot_cmd (CMD) ──→ gimbal_cmd ──→ gimbal 应用
                 ├── chassis_cmd → chassis 应用
                 └── shoot_cmd ──→ shoot 应用

gimbal  ──→ gimbal_feed  ──→ robot_cmd (CMD)
chassis ──→ chassis_feed ──→ robot_cmd (CMD)
shoot   ──→ shoot_feed   ──→ robot_cmd (CMD)

六、应用层模块

6.1 RobotCMD (application/cmd/) — 机器人大脑

核心决策模块,集成以下功能:

功能 说明
遥控器解析 DBUS 协议,摇杆/开关/键鼠
视觉跟踪 OpenCV 视觉数据 → 卡尔曼滤波 → PID 跟踪 → 云台角度控制
画圆模式 遥控器拨轮控制画圆轨迹跟踪
题号状态机 竞赛自动任务状态机,支持 6 种题号,含转向/搜索/跟踪子状态
急停处理 遥控器右侧开关拨下 → 所有电机零力输出
激光控制 GPIO 控制激光笔开关

RobotCMDTask() 执行流程(500Hz):

读取底盘/发射/云台反馈消息 → 判断控制模式(手动/自动/视觉)
→ EmergencyHandler(急停检测) → 推送控制消息给各应用

题号状态机 (YunTaiState):

YUNT_IDLE
  → NO1: 零力模式
  → NO2: 视觉跟踪 + 激光 (等待1.5s后开启激光)
  → NO3: 转向0度 → 视觉跟踪/搜索 → 激光 (3.5s后)
  → NO4_1: 转向-45度 → 视觉跟踪 + 前馈
  → NO4_3: 转向-45度 → 视觉跟踪 (error=60) + 画圆前馈

6.2 Gimbal (application/gimbal/) — 云台控制

  • Yaw 轴:GM6020 (DJI 直驱电机),CAN1 ID=0x01,IMU 反馈替代电机编码器
  • Pitch 轴:达妙电机 (DM Motor),CAN1 ID=0x06/0x16,IMU 反馈
  • 控制模式:
    • GIMBAL_ZERO_FORCE:零力
    • GIMBAL_GYRO_MODE:陀螺仪姿态闭环 (使用 IMU Pitch + YawTotalAngle)
  • 特点:角度/角速度反馈均来自 IMU(替代电机编码器),带有速度和电流前馈

6.3 Chassis (application/chassis/) — 底盘控制

  • 麦克纳姆轮底盘 (Mecanum),4x GM6020 电机
  • 运动学解算:正逆运动学,云台→底盘坐标系变换
  • 支持裁判系统功率限制和超级电容管理

6.4 Shoot (application/shoot/) — 发射控制

  • 摩擦轮:2x M3508 (CAN2 ID=1,2),速度串联电流闭环
  • 拨盘电机:M2006 (CAN2 ID=3),多模式:
    • LOAD_STOP:停止
    • LOAD_1_BULLET:单发(角度闭环,加减角度 = ONE_BULLET_DELTA_ANGLE)
    • LOAD_3_BULLET:三连发
    • LOAD_BURSTFIRE:连发(速度闭环,可调射频)
    • LOAD_REVERSE:反转
  • 弹速模式:15m/s / 18m/s / 30m/s
  • 弹舱盖开关控制

七、模块层 (modules/)

分类 模块 功能
电机 dji_motor DJI GM6020/M3508/M2006 标准电机驱动,串级 PID (角度→速度→电流)
DMMotor 达妙电机 (DM Motor) 驱动
LKmotor (LK9025) LK 电机驱动
HTmotor (HT04) HT04 电机驱动
step_motor 步进电机 (含 X_V2 变体)
servo_motor 舵机控制
motor_task 电机控制统一调度 (MotorControlTask)
姿态 imu/ins_task 惯导解算:四元数 EKF,BMI088 传感器
imu/BMI088driver BMI088 SPI 底层读取
imu/BMI088Middleware BMI088 数据换算
算法 controller 通用 PID 控制器(支持变积分、梯形积分、微分先行、输出滤波等改进)
kalman_filter 标准卡尔曼滤波器 + 自适应 (UseAutoAdjustment)
QuaternionEKF 四元数扩展卡尔曼滤波
crc8/crc16 CRC 校验
user_lib 通用数学/工具函数
通信 remote/remote_control DJI DBUS 遥控器解析 (位域优化)
master_machine 视觉上位机通信 (SeaSky 协议)
referee 裁判系统 (RM Referee Protocol, UI 绘制)
can_comm CAN 通信抽象层(双板情况下的数据转发)
board_comm 板间通信(固定帧格式: 帧头 + 2x int32 + 2x float + 校验)
bluetooth/HC05 HC05 蓝牙模块
opencv OpenCV 视觉数据处理
辅助 message_center Pub-Sub 消息中间件(伪发布订阅,仅做应用间隔离)
daemon 看门狗守护进程(在线检测 + 异常回调)
alarm/buzzer 蜂鸣器告警
vofa 调试数据可视化 (VoFA+ FireWater)
oled OLED 显示屏
super_cap 超级电容管理

八、BSP 驱动层

所有 BSP 驱动采用实例化注册模式(不注册不初始化):

模块 功能
bsp_dwt DWT 时钟周期计数器(精确延时 μs/ms,时间戳获取)
bsp_can CAN 总线收发封装(FIFO+中断,实例化注册)
bsp_usart 串口收发封装(DMA+环形缓冲区,实例化注册)
bsp_spi SPI 通信封装
bsp_iic I2C 通信封装
bsp_pwm PWM 输出(支持 DMA 传输)
bsp_gpio GPIO 管理
bsp_log SEGGER RTT + 串口日志输出(LOGINFO/LOGERROR/LOGWARNING)
bsp_tools RTOS 任务创建工具 (CreateCallbackTask)

九、数据流与控制流总结

                    ┌─────────────┐
                    │  遥控器DBUS  │
                    │  (USART5)   │
                    └──────┬──────┘
                           ↓
              ┌────────────────────────┐
              │      RobotCMD          │
              │   ┌─────────────────┐  │
              │   │ RemoteControlSet│  │ ← 手动模式 (遥控器调试)
              │   │ AutoSet (题号)  │  │ ← 自动模式 (竞赛任务)
              │   └───────┬─────────┘  │
              │           ↓            │
              │   发布: gimbal_cmd     │──→ Gimbal (云台 PID → IMU 反馈)
              │         chassis_cmd    │──→ Chassis (运动学 → 麦轮)
              │         shoot_cmd      │──→ Shoot (摩擦轮/拨盘)
              └────────────────────────┘
                           ↑
              ┌────────────┴───────────┐
              │  反馈: gimbal_feed     │ ← 云台姿态 + 电机角度
              │        chassis_feed    │ ← 底盘速度 + 热量
              │        shoot_feed      │ ← 发射状态
              └────────────────────────┘

   视觉/OpenCV (USART10) ──→ 卡尔曼滤波 ──→ PID ──→ 云台角度控制
   板间通信 (USART1)     ──→ BoardComm  ──→ 题号/坐标数据
   裁判系统               ──→ 热量/弹速/UI 绘制

十、关键设计特点

  1. IMU 替代电机反馈:云台 Yaw/Pitch 使用陀螺仪角度/角速度替代编码器,实现更高精度姿态闭环
  2. 伪 Pub-Sub 模式:应用间通过 message_center 解耦,支持单板/双板条件编译切换(ONE_BOARD / GIMBAL_BOARD / CHASSIS_BOARD)
  3. Daemon 看门狗:每个外设模块注册独立的 DaemonInstance(重载计数 + 离线回调),模块离线时自动触发异常处理
  4. BSP 实例化注册:CAN/串口等外设不注册不初始化,避免资源浪费
  5. 竞赛状态机:完整的题号自动任务流程(转向→搜索→跟踪→激光打击)
  6. 卡尔曼滤波 + PID 级联:视觉误差经过 KF 平滑后由 PID 计算输出,带前馈补偿
  7. 位域优化:遥控器键盘状态使用位域 (Key_t),空间减少 8 倍
  8. 条件编译:单板/双板/电机类型/视觉通信方式均通过宏定义切换

十一、项目规模统计

类别 数量
C 源文件 115 个
ASM 源文件 2 个
应用层模块 4 (robot_cmd, gimbal, chassis, shoot)
模块层子模块 20+ (电机×6, 姿态×3, 算法×5, 通信×7, 辅助×5)
BSP 驱动模块 10
FreeRTOS 任务 4 (默认)
最高控制频率 1kHz
CPU 频率 480MHz (PLL = HSE 8MHz / 2 × 40 / 2)
FLASH 使用 161,556 B / 1 MB (15.41%)
DTCMRAM 使用 60,920 B / 128 KB (46.48%)

十二、电机配置速查

电机 类型 CAN 总线 TX ID 控制闭环 PID 级联
Yaw (云台) GM6020 CAN1 0x01 角度+速度 Angle → Speed (IMU 反馈)
Pitch (云台) DM Motor CAN1 0x06/0x16 角度+速度 Angle → Speed (IMU 反馈)
摩擦轮 左 M3508 CAN2 0x01 速度+电流 Speed → Current
摩擦轮 右 M3508 CAN2 0x02 速度+电流 Speed → Current (反转)
拨盘 M2006 CAN2 0x03 角度/速度+电流 Angle/Speed → Current

十三、关键配置宏 (robot_def.h)

#define ONE_BOARD              // 单板控制整车
#define VISION_USE_UART        // 使用串口发送视觉数据
#define YAW_CHASSIS_ALIGN_ECD  2711   // 云台底盘对齐编码器值
#define PITCH_HORIZON_ECD      3412   // 云台水平位置编码器值
#define ONE_BULLET_DELTA_ANGLE 36     // 单发弹丸拨盘转动角度
#define WHEEL_BASE             350    // 纵向轴距 (mm)
#define TRACK_WIDTH            300    // 横向轮距 (mm)
#define RADIUS_WHEEL           60     // 轮子半径 (mm)