传感器故障诊断:IMU异常检测、GPS信号丢失、气压计漂移处理
传感器出问题,是无人机坠毁的头号元凶。
我做了这么多年飞控,见过太多因为传感器故障炸机的案例。说白了,飞控再聪明,也架不住传感器给它喂假数据。今天咱们就聊聊三个最要命的传感器故障:IMU异常、GPS丢失、气压计漂移。
一、IMU异常检测:飞控的“内耳”出问题了
IMU就是无人机的内耳。它告诉你飞机现在是什么姿态,朝哪个方向在转。一旦它出问题,飞控就变成了瞎子。
常见的IMU异常有哪些?
- 数据跳变:加速度计或陀螺仪的输出突然出现不合理的大幅跳动
- 数据冻结:传感器数值卡在某个值不动了,飞机明明在动,数据却不变
- 温漂严重:温度变化导致零偏值偏移,悬停时飞机会慢慢往一边偏
- 振动耦合:桨叶振动被传感器误读为姿态变化,导致飞控误判
核心检测逻辑
我个人习惯用“三明治检测法”:
- 范围检测:看数值是否在物理合理范围内。比如加速度计模值应该在0.8g~1.2g之间,超出这个范围直接报警
- 变化率检测:看相邻采样点的差值是否过大。陀螺仪角速度变化率超过500°/s²,基本可以判定是异常跳变
- 一致性检测:如果有双IMU,对比两个传感器的输出。差值超过阈值,说明至少有一个坏了
// IMU异常检测伪代码示例
bool checkIMUHealth(IMUData &data) {
// 1. 加速度计模值检测
float accel_norm = sqrt(data.ax*data.ax + data.ay*data.ay + data.az*data.az);
if (accel_norm < 0.8f || accel_norm > 1.2f) {
return false; // 加速度计异常
}
// 2. 陀螺仪变化率检测
static float last_gyro[3];
float gyro_rate = fabs(data.gx - last_gyro[0]);
if (gyro_rate > 500.0f) {
return false; // 陀螺仪跳变
}
// 3. 双IMU一致性检测(如果有)
if (dual_imu_enabled) {
float diff = fabs(data.gx - imu2_data.gx);
if (diff > 10.0f) {
return false; // 两个IMU不一致
}
}
return true;
}
我的经验之谈
我在项目中遇到过一台无人机,每次飞完3分钟就开始剧烈抖动。查了半天,发现是IMU的减震海绵老化了。高频振动直接传到了传感器上,飞控以为飞机在疯狂翻滚,拼命打舵修正,结果越修正越抖。
嗯,这里要注意:IMU的减震设计比你想的重要得多。别光看算法,机械安装同样关键。
二、GPS信号丢失:从“有定位”到“无头苍蝇”
GPS一丢,无人机就失去了绝对位置信息。你想想看,在几千米外飞着,突然不知道自己在哪了,慌不慌?
GPS丢失的典型场景
- 高楼峡谷:城市飞行时,信号被遮挡,卫星颗数骤降
- 电磁干扰:高压线、基站附近,GPS信号被压制
- 天线遮挡:机身姿态变化导致GPS天线被碳纤维机身挡住
- 卫星几何分布差:虽然能搜到星,但HDOP值很大,定位精度极差
避坑指南
我曾经遇到过一架飞机,GPS信号在悬停时突然从12颗星掉到3颗星。飞控立刻切入了无GPS模式,但因为没有提前做位置预估,飞机直接开始飘移。最后撞树上了。
教训是什么?GPS丢失不可怕,可怕的是丢失后没有平滑过渡。
我建议的处理策略
- 分级预警:卫星颗数<8颗时发出警告,<5颗时强制切换模式
- 位置预估:GPS正常时,用卡尔曼滤波器持续估计位置和速度。GPS丢失后,用IMU积分推算位置,虽然会漂,但比直接丢失强
- 自动返航触发:如果GPS丢失超过5秒,且飞机在远距离,自动触发返航逻辑——前提是返航点已经记录
- 视觉辅助:如果有下视摄像头,可以用光流法辅助定位,减少对GPS的依赖
// GPS丢失处理逻辑
void handleGPSLoss() {
static uint32_t loss_start_time = 0;
if (gps_satellites < 5) {
if (loss_start_time == 0) {
loss_start_time = millis();
// 记录丢失时的位置和速度
last_known_pos = current_pos;
last_known_vel = current_vel;
}
// 用IMU积分推算位置
uint32_t elapsed = millis() - loss_start_time;
estimated_pos = last_known_pos + last_known_vel * elapsed / 1000.0f;
// 超过5秒触发返航
if (elapsed > 5000) {
triggerReturnToLaunch();
}
} else {
loss_start_time = 0; // GPS恢复
}
}
三、气压计漂移:高度数据的“慢性毒药”
气压计这东西,说白了就是个测大气压力的传感器。但它有个毛病——特别怕风、怕温度变化、怕阳光直射。
气压计漂移的几种表现
| 漂移类型 | 原因 | 典型表现 |
|---|---|---|
| 温漂 | 传感器自身发热或环境温度变化 | 悬停时高度缓慢下降或上升 |
| 风压干扰 | 侧风导致气压计进气口压力变化 | 迎风飞行时高度突然跳变 |
| 零偏漂移 | 传感器老化或污染 | 地面校准后,起飞后高度偏差越来越大 |
| 阳光直射 | 光照导致封装内部温度不均 | 飞行一段时间后高度数据缓慢偏移 |
我的处理方案
气压计漂移不能完全消除,但可以大幅抑制。我常用的方法有:
- 硬件隔离:给气压计加海绵罩,避免阳光直射和风直接吹到传感器
- 软件滤波:用低通滤波器,截止频率设在0.5Hz左右,滤掉高频风压干扰
- 融合GPS高度:GPS高度虽然精度差,但长期稳定性好。用互补滤波把气压计和GPS高度融合,短期看气压计,长期看GPS
- 地面校准补偿:起飞前记录地面气压值,飞行中实时减去这个基准值,消除零偏
// 气压计-高度融合(互补滤波)
float fuseAltitude(float baro_alt, float gps_alt, float dt) {
static float fused_alt = 0;
float alpha = 0.98f; // 气压计权重
// 起飞时记录基准
static float baro_baseline = 0;
if (is_ground) {
baro_baseline = baro_alt;
}
// 减去基准
float baro_corrected = baro_alt - baro_baseline;
// 互补滤波
fused_alt = alpha * (fused_alt + baro_corrected) + (1 - alpha) * gps_alt;
return fused_alt;
}
一个小技巧
如果你发现气压计在悬停时高度一直在缓慢下降,别急着怀疑传感器坏了。先看看是不是电机散热把热风吹到了气压计上。我遇到过好几次,把气压计挪个位置就解决了。
四、综合诊断策略:多传感器交叉验证
单个传感器出问题不可怕,可怕的是你没法判断它是不是在说谎。所以,我建议用多传感器交叉验证的方法。
怎么交叉验证?
- IMU vs GPS:IMU积分得到的位移,和GPS测得的位移做对比。偏差太大,说明至少有一个有问题
- 气压计 vs GPS高度:气压计高度变化率,和GPS高度变化率做对比。如果气压计显示在下降,GPS显示在上升,肯定有一个在撒谎
- 加速度计 vs 陀螺仪:加速度计测重力方向,陀螺仪积分得到姿态。两者算出的俯仰角/横滚角应该一致
最后提醒一句
传感器故障诊断,核心不是“修”,而是“判”。判断出哪个传感器坏了,然后果断把它从控制回路里踢出去。宁可用一个精度差但可靠的传感器,也不要让一个坏传感器污染整个系统。
我曾经在测试中,故意让一个IMU输出错误数据。飞控如果没有检测机制,3秒内就会翻机。有了检测机制,至少能撑到手动切换模式。
好了,传感器故障诊断这块就聊到这儿。下一章咱们聊聊执行器故障——电机堵转、舵面卡死这些更刺激的问题。