影子寄存器:改ARR下个周期才生效,防波形“断片”

📅 2026/7/29 3:18:49 👁️ 阅读次数 📝 编程学习
影子寄存器:改ARR下个周期才生效,防波形“断片”

短文标题:影子寄存器:改ARR下个周期才生效,防波形“断片”

你有没有想过一个问题:PWM正在输出,你突然改了ARR(周期),波形会不会断一下或出现毛刺?取决于ARPE位。如果没开预装载,修改ARR立即生效——计数中途改周期,可能导致计数器永远达不到新ARR值,产生一个“超长”的异常周期,电机抖动一下。

影子寄存器的双层结构,定时器的ARR、CCR、PSC等寄存器实际上有两层:

  • 预装载寄存器(Preload):软件读写的“窗口”
  • 影子寄存器(Shadow):硬件实际使用的“工作副本”

软件写ARR → 写到预装载寄存器。影子寄存器的值,才是计数器比较的对象。ARPE=0:立即生效(可能突变),ARPE=0时,预装载寄存器直通影子寄存器,写ARR立即生效。计数器正在计数(当前值=800),ARR从1000改成500:

  • 800 > 500,计数器永远达不到新ARR
  • 一直跑到16位定时器的65535才溢出
  • 一个周期变得超级长,波形完全乱掉,电机可能猛抖一下

ARPE=1:下个周期生效(平滑过渡),ARPE=1时,预装载寄存器和影子寄存器隔离。当前周期继续用旧ARR跑,计数到旧ARR值 → 产生更新事件 → 影子寄存器从预装载寄存器加载新ARR → 下个周期用新ARR。

TIM2->CR1 |= TIM_CR1_ARPE; // 使能预装载

TIM2->ARR = 2000; // 修改ARR,下个周期才生效

波形连续,无毛刺。

CCR也是一样,PWM占空比由CCR控制,也有影子寄存器(通过CCMRx寄存器的OCxPE位控制)。修改CCR后,占空比变化同样在更新事件时生效,避免脉冲宽度突变。更新事件的触发时机,更新事件在以下情况产生:

  • 计数器溢出(向上计数:从ARR→0;向下计数:从0→ARR)
  • 软件设置UG位(TIMx_EGR寄存器)

ARPE保护的是更新时机,不影响UG位的立即更新。软件写UG位会强制立即生效。

这个故事的启示,ARPE不是“延迟”,是“优雅交接”。让新ARR在更新事件时生效,不是在周期中间“野蛮插入”。波形平滑,电机不抖,PWM不毛刺。写在最后,动态改变定时器周期或占空比时,设ARPE=1。不设,可能周期突变;设了,平滑过渡。一个bit,决定波形质量。


(本文灵感源于于振南《新概念ARM32单片机》教程第6.4节、第6.7节。)

觉得有用?点赞、转发,让更多人知道“影子寄存器”防突变的作用。