4. 参数系统架构:存储、命名与元数据
参数系统是 ArduPilot 的“神经中枢”。你调的所有参数,最终都要存下来、读出来、传出去。这一章我带你拆开看看,里面到底怎么运作的。
4.1 参数存储机制:FRAM / EEPROM / SD 卡
ArduPilot 支持三种存储介质。优先级从高到低:FRAM > EEPROM > SD 卡。说白了,板子上有 FRAM 就用 FRAM,没有就用 EEPROM,实在不行才写 SD 卡。
| 存储介质 | 写入寿命 | 速度 | 典型硬件 |
|---|---|---|---|
| FRAM | 10¹⁴ 次(几乎无限) | 纳秒级 | Pixhawk 系列(FMUv2+) |
| EEPROM | 10⁵ 次 | 毫秒级 | 早期 APM 板、部分 F4 飞控 |
| SD 卡(文件) | 取决于卡质量 | 较慢 | 无 FRAM/EEPROM 的备用方案 |
我个人习惯,拿到一块新飞控,第一件事就是看 STORAGE_TYPE 参数。它决定了参数存哪。默认是 0(自动检测),但有时候自动检测会翻车。
STORAGE_TYPE=2 改用 SD 卡存储,才稳住。
存储流程其实很简单:
- 参数变更时,标记“脏位”(dirty flag)。
- 主循环每 1.5 秒检查一次脏位。
- 有脏位就批量写入存储介质。
- 写入完成后清除脏位。
为什么要批量?因为每次写入都有开销。攒一批再写,效率高得多。你想想看,如果每次调一个参数就写一次,EEPROM 很快就挂了。
4.2 参数 ID 命名规范
ArduPilot 的参数名不是随便起的。它有一套严格的命名规则。看懂命名,你就看懂了一半的参数系统。
标准格式:模块前缀_参数组_参数名
举个例子:ATC_ANG_RLL_P
- ATC — 模块前缀,这里是 Attitude Controller(姿态控制器)
- ANG — 参数组,Angle(角度环)
- RLL — 具体对象,Roll(横滚)
- P — 参数名,P 增益
再拆几个常见的:
| 参数名 | 模块 | 组 | 含义 |
|---|---|---|---|
INS_ACC2_OFFS_X |
INS | ACC2 | 第二个加速度计 X 轴偏移 |
MOT_PWM_MIN |
MOT | PWM | 电机最小 PWM 值 |
GPS_TYPE |
GPS | (无) | GPS 模块类型 |
BATT2_MONITOR |
BATT | 2 | 第二块电池的监控方式 |
嗯,这里要注意:参数名最长 16 个字符。超过会被截断。我见过有人写 ATC_ANG_RLL_FLTE(滤波器时间常数),刚好 16 个字符,卡在边界上。设计参数名时,心里要绷着这根弦。
4.3 参数分组:Group 与 Param
ArduPilot 内部用 Group 和 Param 两层结构管理参数。Group 是容器,Param 是具体参数。
看一段伪代码你就明白了:
class Parameters {
struct {
AP_Int8 type; // GPS_TYPE
AP_Int16 baudrate; // GPS_BAUDRATE
AP_Int8 auto_config;// GPS_AUTO_CONFIG
} gps; // 这是一个 Group
struct {
AP_Float p; // ATC_ANG_RLL_P
AP_Float i; // ATC_ANG_RLL_I
AP_Float d; // ATC_ANG_RLL_D
} atc_ang_rll; // 这是另一个 Group
};
每个 Group 对应一个参数前缀。比如 gps 组对应 GPS_ 开头的参数。atc_ang_rll 组对应 ATC_ANG_RLL_ 开头的参数。
为什么要分组?两个原因:
- 代码组织 — 相关参数放在一起,维护起来清爽。
- 批量操作 — 可以一次性读写整个 Group,效率高。
我记得有一次调试四轴,发现 ATC_ANG_RLL_P 和 ATC_ANG_PIT_P 总是要成对调。后来我干脆写了个脚本,同时读写整个 ATC_ANG_ 组。省事多了。
4.4 参数元数据:min / max / unit
每个参数都带着“身份证”。元数据就是这张身份证。它告诉地面站和飞控:这个参数能设多大、能设多小、单位是什么。
元数据包含以下字段:
| 字段 | 含义 | 示例 |
|---|---|---|
min |
最小值 | 0.0 |
max |
最大值 | 90.0 |
unit |
单位 | deg/s, m, A, Hz |
increment |
步进值 | 0.1 |
default |
默认值 | 4.5 |
元数据在代码里是这样定义的:
// @Param: P
// @DisplayName: Roll angle P gain
// @Description: P gain for roll angle control
// @Range: 0.0 90.0
// @Increment: 0.1
// @User: Standard
AP_Float p;
注意看 @Range: 0.0 90.0。这就是元数据。Mission Planner 读到这个注释,就知道滑块范围是 0 到 90,步进 0.1。
ATC_ANG_RLL_P 写到 200,结果飞控直接拒绝写入,返回 PARAM_VALUE 的 param_result 为 PARAM_RESULT_INVALID。
单位字段特别有用。比如 ATC_ANG_RLL_P 的单位是 deg/s,你一看就知道这个增益是把角度误差换算成角速度。理解单位,就是理解物理意义。
4.5 参数系统整体架构图
下面这张图把参数系统的全貌串起来了。从地面站到存储介质,整个链路一目了然。
从这张图你能看到,参数系统不是简单的“存-读”两件事。它包含了协议解析、分组管理、元数据校验、存储调度等多个环节。每个环节都可能成为瓶颈或坑点。
好了,参数系统的骨架就这些。存储介质选型、命名规范、分组结构、元数据约束,这四个东西构成了 ArduPilot 参数系统的基石。理解它们,你调参的时候就不会“盲调”。