先说结论:控制闭环的精度上限由采样时刻决定,而不是由 ADC 位数决定。
采样误差 = di/dt × 时刻偏移,是线性可算的量。按本文判据,1µs 偏移仍在允许范围,3µs 已经越界。而我们遇到过最糟的一块板子,偏了 2.6µs。
一套 24V 母线、750W 级的差速驱动轮总成,用于厂内物流 AGV,满载爬坡时需要短时大扭矩,平地巡航时又要跑得稳。
驱动侧用的是 AQMD6030BLS-E2 直流无刷电机驱动器,电机控制方式为 FOC(磁场定向控制):连续 25A / 峰值 40A,母线覆盖 12V–60V(48V 下 1000W、60V 下 1250W),四象限运行、刹车电阻制动、能耗制动 12A,136×82×45mm 铝合金机壳,电流采样走双电阻低边分流。
量产调试时出现了一个很"抓人"的现象:同一批板子、同一套 FOC 固件,静置时相电流零点干净利落,一上负载就开始低速抖动,扭矩越大抖得越明显。换更高位的 ADC 没用,改电流环 PI 参数只能把抖动推迟到更大的负载。
最后查出来:采样时刻偏了 1µs。
先还原场景。方案采用中心对齐 PWM(SOP,Synchronous One Point),载波 20kHz,母线 24V,相电感 0.5mH,电流采样走双电阻低边分流。
现象有三条:
团队一开始怀疑 ADC 分辨率不够。25A 额定量程按 12 位 ADC 折算,理论 LSB 约 12mA,分辨率约 0.05%,纸面上完全够用。换成 16 位外部 ADC 之后,抖动幅度只降了一点点。
真正让方向转变的,是一次顺手的测量:把 PWM 驱动信号和 ADC 触发信号同时接示波器,量两者时间差。设计值是 0,实测 1.4µs,而且不同板子在 0.9µs–1.8µs 之间散开。
那一刻就清楚了:控制闭环的精度上限由采样时刻决定,而不是由 ADC 位数决定。
开关周期内相电流不是平的,它以 di/dt 的斜率变化。采晚 1µs,就等于采到 1µs 之后的电流值,误差就是斜率乘时间。
取相电感 0.5mH、相电压 24V:
di/dt = V / L = 24V / 0.5mH = 48A/ms = 0.048A/µs每偏移 1µs,电流读数偏 48mA。按 8mA/LSB 折算:
采样时刻偏移 | 电流误差 | 折算(8mA/LSB) | 相对 10A |
|---|---|---|---|
0.5µs | 24mA | 3 LSB | 0.24% |
1.0µs | 48mA | 6 LSB | 0.48% |
3.0µs | 144mA | 18 LSB | 1.44% |
这张表解释两件事:
第一,1µs 以下的偏移"看起来没事",0.48% 的误差在多数场合确实不影响功能,于是被长期忽略,一直活到量产;
第二,3µs 的偏移已经明显越界。1.44% 的电流误差在速度环里会变成持续的扭矩偏差,低速时表现为"走一下顿一下",高速时被惯性掩盖。
由此得到可直接写进设计文档的判据:
Δt ≤ (允许误差 × I_rated) / (di/dt)若允许误差取额定 1%,即 0.1A:
Δt ≤ 0.1A / 48A/ms ≈ 2.1µs结论很明确:1µs 偏移仍在范围内,3µs 已经越界。
顺带一提,di/dt 不是常数,它随母线电压和电感变化。母线 48V 时同样的偏移,误差直接翻倍:
母线电压 | di/dt | 1µs 偏移误差 | 3µs 偏移误差 |
|---|---|---|---|
24V | 48A/ms | 48mA | 144mA |
36V | 72A/ms | 72mA | 216mA |
48V | 96A/ms | 96mA | 288mA |
60V | 120A/ms | 120mA | 360mA |
换电压等级、换电感量不同的电机,判据都要重算。把这张小表做成选型工具里的一个计算格子,比写进 PPT 有用得多。
时刻对齐只是第一关,第二关是窗口够不够宽。
低边分流电阻只在下管导通期间有电流,采样窗口就是下管导通时间。窗口里还要扣掉两块:
取死区 500ns、建立 800ns,合计需 ≥1.3µs。窗口宽度由占空比和开关频率决定:
T_window = (1 − D) / f_sw按 20kHz(周期 50µs)算:
占空比 D | 低边窗口 (1−D)/f_sw | 是否满足 |
|---|---|---|
0.90 | 6.25µs | 满足 |
0.97 | 1.88µs | 勉强 |
0.99 | 0.63µs | 不满足,需改相电阻或母线电流重构 |
这就是"低速大扭矩时电流采样失真"的定量原因。低速大扭矩意味着反电动势低,要输出大扭矩必须给大相电压,占空比被推到 0.97 以上,窗口只剩 1.88µs 甚至更少。
窗口不够时的四条路:
方案 | 做法 | 代价 |
|---|---|---|
三电阻采样 | 增加第三相分流,两相组合推第三相 | 多一路运放,板面积增加 |
母线电流重构 | 单电阻采样,靠不同矢量时刻反推 | 算法复杂,需最小脉宽处理 |
提高 f_sw | 缩短周期,窗口比例不变但绝对时间更短 | 反而更差,不推荐 |
降额限制 D | 限制最大占空比 | 牺牲高速段能力 |
注意第三行:提高开关频率会让窗口更窄,这是个反直觉但必须记住的约束。
软件轮询的抖动来自中断响应、指令流水线、编译器优化,量级 1–3µs,正好落在判据边界上。正确做法是由 PWM 定时器在载波谷(或峰)产生硬件触发:
中心对齐 PWM 计数波形(示意)
峰 ────────╮ ╭──────── ╭────
│ │ │
谷 ────╮ ╰───────╯ ╰───────╯
▲ ▲ ▲
│ │ │
采样点 采样点 采样点
(谷) (谷) (谷)同一周期内做两次采样再取平均,可抵消 2·f_sw 的纹波分量:
/* 由 PWM 定时器同步触发,双采样取平均 */
uint16_t adc_sample_twice(void)
{
uint16_t a = ADC_GetValue(CHANNEL_IU); /* 载波谷 */
uint16_t b = ADC_GetValue(CHANNEL_IU); /* 下一载波谷 */
return (uint16_t)((a + b) >> 1);
}项目 | 典型值 | 说明 |
|---|---|---|
开关周期(20kHz) | 50µs | — |
死区 | 0.5µs | 上下管切换 |
开关沿振铃消隐 | 0.3µs | 躲开尖峰 |
放大器建立 | 0.8µs | 稳定到 0.1% |
ADC 采样保持 | 0.05µs | 采样电容充电 |
流水线延迟补偿 | 0.2µs | 固定偏移 |
合计占用 | 1.85µs | — |
这张表放在设计评审里非常有效:任何一项超预算,都能立刻定位到是哪一环节吃掉了裕量。
用可编程电流源给分流电阻注入梯形波(斜率已知),比较 ADC 读数与标准表真值:
注入斜率 | 采样间隔 | 理论误差 | 实测误差 | 偏差 |
|---|---|---|---|---|
100A/ms | 1µs | 100mA | 106mA | +6mA |
100A/ms | 2µs | 200mA | 211mA | +11mA |
500A/ms | 1µs | 500mA | 528mA | +28mA |
实测误差与理论基本线性,多出的部分正是固定延迟贡献的常数项。拟合后截距就是固定时刻偏移量,斜率就是 di/dt 的验证值。
一路接 PWM 驱动,一路接 ADC 触发信号,量跳变沿之间的时间差。关键是测量点位置一致:PWM 以 50% 点为参考,ADC 以触发上升沿为参考,单次触发多次平均。
板号 | 设计偏移 | 实测偏移 | 是否超 2.1µs |
|---|---|---|---|
#01 | 0 | 0.9µs | 否 |
#02 | 0 | 1.4µs | 否 |
#03 | 0 | 1.8µs | 否 |
#04(改前) | 0 | 2.6µs | 是 |
从 D = 0.50 扫到 0.99,每档记录偏差:
占空比 | 窗口 | 采样偏差 | 判定 |
|---|---|---|---|
0.50 | 25µs | < 1% | 正常 |
0.90 | 5.0µs | < 1% | 正常 |
0.95 | 2.5µs | 2.3% | 开始偏离 |
0.97 | 1.5µs | 6.8% | 明显失真 |
0.99 | 0.5µs | 21% | 失效 |
实测失效点(约 0.95)与窗口约束基本吻合。误差是渐变而非突变,这意味着"能用"的边界是模糊的,必须靠明确定义的阈值划线,不能靠"跑起来还行"。
三件事:ADC 触发从软件轮询改为定时器硬件触发并补偿固定延迟;双采样改为严格整周期间隔;固件里按占空比切换采样策略。全部落在固件与采样时序上,硬件未动。
指标 | 改前 | 改后 |
|---|---|---|
采样时刻偏移 | 0.9–2.6µs(散差大) | 0.15–0.3µs(一致) |
低速满载抖动幅度 | 4.2% | 0.6% |
电流环带宽 | 800Hz | 1.6kHz |
高占空比扭矩塌陷点 | D ≈ 0.95 | D ≈ 0.985 |
ADC 位数 | 换过 16 位,无改善 | 保持 12 位 |
BOM 成本 | — | 未增加 |
最能说明问题的是"ADC 位数"那一行:从头到尾,真正的瓶颈就不是分辨率。
它不绑定某个型号,而是绑定五个参数:母线电压、相电感、开关频率、峰值电流、采样拓扑。把这五个数代入本文两个公式,就能得到该平台的采样时刻预算。
以 25A / 40A 这一档为例,摊开不同母线电压的预算:
母线电压 | 该档典型功率 | di/dt(L=0.5mH) | 1% 额定允许的 Δt | 3µs 偏移的误差占比 |
|---|---|---|---|---|
24V | 500W | 48A/ms | 2.1µs | 1.44% |
36V | 750W | 72A/ms | 1.4µs | 2.16% |
48V | 1000W | 96A/ms | 1.0µs | 2.88% |
60V | 1250W | 120A/ms | 0.83µs | 3.60% |
注意最后一列:同样 3µs 偏移,24V 下是 1.44%,60V 下变成 3.6%。 同一套固件、同一套时序,换到高压档位就直接越过判据边界。
这也解释了工程上一种常见现象——低压实测一切正常,升到 48V / 60V 后"突然"开始抖。其实不是突然,是裕量被吃完了。
反过来,把这张表当固件验收标准比在代码里写死补偿常数更可靠:每个电压档位分别测一次偏移量,确认都在判据以内才放行。
电流环的精度下限,往往不是被算法决定的,而是被一个不到 2µs 的时间差决定的。
文中 di/dt、窗口与误差数值随母线电压、相电感、开关频率、采样拓扑变化,代入本文判据后须重新计算,不可直接套用。实测数据(采样偏移量、占空比扫描、改前改后对比)来自本团队台架与量产调试记录。本文为原创内容,公式推导为通用电机控制理论。
原创声明:本文系作者授权腾讯云开发者社区发表,未经许可,不得转载。
如有侵权,请联系 cloudcommunity@tencent.com 删除。