STM32 PWM 笔记:ARR/CCR 的关系与输出配置

什么是 PWM

PWM(Pulse Width Modulation,脉宽调制)的核心思想很简单:在一个固定周期的方波中,高电平占多长时间是可调的。

占空比 = 有效电平时间 / 周期时间 × 100%

这里的"有效电平"取决于电路设计:

  • 有些电路是高电平有效(高电平时 LED 亮)
  • 有些电路是低电平有效(低电平时 LED 亮)。CubeMX 中配置 Polarity = Low,代码中用宏 TIM_OCPOLARITY_LOW

通过调节占空比,PWM 可以实现:

  • LED 调光:高速闪烁,人眼看到的是平均亮度
  • 电机调速:平均电压决定转速
  • 音频生成:不同频率产生不同音调

PWM 模式

这里先明确几个缩写:

  • ARR(Auto-Reload Register):自动重装载寄存器,决定计数上限,也就是 PWM 周期
  • CCR(Capture/Compare Register):捕获/比较寄存器,决定电平翻转点,也就是占空比
  • CNT(Counter):当前计数值,每个时钟周期递增

定时器有两种 PWM 输出模式:

模式CNT < CCR 时CNT ≥ CCR 时
PWM 模式 1输出有效电平输出无效电平
PWM 模式 2输出无效电平输出有效电平

最常用的是 PWM 模式 1。

举例(ARR=999,CCR=300,有效电平=低电平):

PWM 模式 1

  • CNT < 300(0~299):输出低电平(LED 亮)
  • CNT ≥ 300(300~999):输出高电平(LED 灭)
  • → 占空比 30%,LED 亮度约 30%

PWM 模式 2(反向)

  • CNT < 300:输出高电平(LED 灭)
  • CNT ≥ 300:输出低电平(LED 亮)
  • → 占空比 70%,LED 亮度约 70%

简单总结:CNT 的计数范围是 0 ~ ARR;CCR 决定占空比——PWM 模式 1 下 CNT < CCR 输出有效电平,PWM 模式 2 下 CNT ≥ CCR 输出有效电平。两种模式互为反向。

输出通道

一个定时器有多个独立通道,可以同时输出多路 PWM。比如 TIM2 有 CH1~CH4,TIM1 还额外支持互补输出(CH1N 等)。

同一个定时器的所有通道共享 CNT、ARR、PSC,但每个通道有独立的 CCR,可以设置不同的占空比。此外每个通道都有自己的配置寄存器,极性和 PWM 模式也可以单独设置。

参数计算

频率公式

PWM频率 = Fclk / (PSC + 1) / (ARR + 1)
  • Fclk 是定时器时钟源频率
  • PSC 分频后得到计数器的触发频率
  • ARR 决定一个周期的计数长度
  • PWM 频率就是单位时间内完成的周期数

占空比公式

占空比 = CCR / (ARR + 1) × 100%

代码实践

代码部分其实非常简单,重点是理解前面的原理:PWM 是怎么产生的、ARR/CCR 的关系等。

初始化

CubeMX 配置 PSC、ARR、极性等参数后,自动生成的代码会通过 HAL_TIM_PWM_ConfigChannel 完成初始化。

启动 PWM

CubeMX 只管初始化,不启动输出,必须手动调用:

1
HAL_TIM_PWM_Start(&htimX, TIM_CHANNEL_X);  // 放在 MX_TIM_Init() 之后

设置占空比

通过修改 CCR 值来动态调节占空比:

1
__HAL_TIM_SET_COMPARE(&htimX, TIM_CHANNEL_X, value);

:如果设置了 CCR > ARR,硬件不会报错,实际效果是占空比被钳位到 100%(整个周期都是有效电平)。逻辑上这通常不是期望行为,注意控制 CCR 的取值范围。