3. 飞控任务分析:传感器读取、姿态解算、控制律计算、PWM输出、通信任务
好,咱们进入正题。飞控系统说白了,就是一套「感知-决策-执行」的循环。你想想看,无人机要飞得稳,得先知道自己姿态怎么样,然后算出该给电机多少力,最后把信号发出去。这中间每一步,都是一个独立的任务。
我个人习惯,在写调度代码之前,先把这些任务拆开来看。搞清楚每个任务的特点,才能给它们安排合适的「出场顺序」。今天我就带你过一遍飞控里最常见的五个任务。
3.1 传感器读取任务
这个任务负责从IMU(惯性测量单元)、磁力计、气压计这些芯片里拿数据。嗯,这里要注意,传感器读取是飞控的「眼睛」,眼睛要是花了,后面全白搭。
任务特点:
- 高频率:一般要跑 1kHz 甚至更高。你想想看,无人机稍微一晃,可能就是几十度的偏差,读慢了根本来不及反应。
- I/O 密集型:大部分时间花在等 SPI 或 I2C 总线上。CPU 其实没怎么干活,就是在「等数据」。说白了,这是个典型的「等外设」任务。
- 短小精悍:代码量不大,就是读寄存器、校验、滤波,然后扔到队列里。
避坑指南:我曾经在一个项目里,把传感器读取任务优先级设得太高,结果它一直占着 CPU 等 SPI 传输,导致姿态解算任务饿死了。后来我改成用 DMA + 信号量,读取任务读完就挂起,CPU 让给别人用。这才把问题解决。
3.2 姿态解算任务
这个任务把传感器原始数据「翻译」成我们能理解的姿态角——横滚、俯仰、偏航。说白了,就是算出一个旋转矩阵或者四元数。
任务特点:
- 计算密集型:这里要跑卡尔曼滤波或者互补滤波,全是浮点运算。CPU 占用率很高,我见过有些飞控光姿态解算就吃掉 40% 的算力。
- 中等频率:一般 250Hz 到 500Hz 就够了。频率太高,传感器噪声反而会放大;频率太低,控制跟不上。
- 对实时性敏感:如果这个任务被抢占了,解算结果会滞后,飞控就会「手抖」。
我的经验:我建议把姿态解算任务的优先级设为「次高」。为什么不是最高?因为传感器读取是它的「上游」,读不到数据,解算就是无米之炊。所以传感器读取优先级要更高一点。
3.3 控制律计算任务
这个任务拿到姿态角之后,跟目标角度做差,然后算 PID。输出的是电机应该转多快的控制量。
任务特点:
- 计算密集型:PID 计算本身不复杂,但如果你用了串级 PID(内环角速度、外环角度),再加上前馈、限幅、积分分离,计算量也不小。
- 高频率:内环一般要 1kHz,外环可以低一点,200-400Hz。频率低了,飞控响应慢,飞起来像「喝醉了」。
- 确定性要求高:每次执行的时间必须稳定。如果这次算了 100μs,下次算了 300μs,飞控就会抖动。
注意:控制律计算任务和姿态解算任务之间,通常用队列传递数据。我曾经见过有人用全局变量传,结果解算写到一半,控制律就读走了,导致数据「撕裂」。嗯,队列虽然慢一点,但安全。
3.4 PWM 输出任务
这个任务把控制量转换成 PWM 占空比,然后喂给电调。说白了,就是让电机转起来。
任务特点:
- I/O 密集型:大部分时间在等定时器更新。CPU 其实没怎么干活。
- 频率固定:PWM 频率一般是 50Hz 到 400Hz,取决于电调。这个频率不能乱变,变了电机就「嗡嗡」叫。
- 对抖动极其敏感:PWM 的周期抖动如果超过 10μs,电机就会产生可听见的噪声,甚至影响控制精度。
避坑指南:我曾经把 PWM 输出任务放在一个低优先级线程里,结果它被其他任务频繁抢占,PWM 波形变得乱七八糟。后来我改成用硬件定时器直接输出,CPU 只负责更新比较寄存器,这才把抖动压下去。
3.5 通信任务
这个任务负责跟地面站、遥控器、GPS 模块等设备「聊天」。常见的协议有 MAVLink、SBUS、NMEA 等。
任务特点:
- I/O 密集型:大部分时间在等串口数据。CPU 占用率很低。
- 低频率:一般 10Hz 到 100Hz 就够了。地面站不需要知道每一毫秒的姿态变化。
- 对实时性要求低:丢一包数据没关系,下一包马上就来。但要注意,遥控器信号丢了可是要炸机的。
我的建议:通信任务优先级可以设得最低。但遥控器接收部分要单独处理——我一般用中断或者高优先级任务来解析遥控器信号,确保不会丢控。
3.6 任务特性对比
我把这五个任务的特点整理成了一张表,方便你对比:
| 任务名称 | 类型 | 典型频率 | 实时性要求 | 建议优先级 |
|---|---|---|---|---|
| 传感器读取 | I/O 密集型 | 1kHz | 高 | 最高 |
| 姿态解算 | 计算密集型 | 250-500Hz | 高 | 次高 |
| 控制律计算 | 计算密集型 | 1kHz(内环) | 极高 | 次高 |
| PWM 输出 | I/O 密集型 | 50-400Hz | 极高(防抖动) | 中 |
| 通信任务 | I/O 密集型 | 10-100Hz | 低 | 低 |
3.7 任务调度关系图
下面这张图展示了这些任务之间的数据流和调度关系。你一看就明白了:
从这张图你能看到,数据是从传感器一路流到 PWM 的。通信任务是个「旁观者」,它只负责把状态数据发出去,不参与控制闭环。嗯,这里要注意,通信任务虽然优先级最低,但千万别让它饿死——否则地面站收不到数据,你会以为飞控死机了。