一般来说,一个定时器输出4路频率相同、占空比不同的PWM波是比较容易的,使用PWM模式即可实现。如果说是输出4路频率不同、占空比不同的PWM就没有现成的模式,是不是无法实现了呢?答案肯定是"不",只要肯思考就肯定有解决方案(计算机是人类发明的,我们所能遇到的大部分问题是可以通过我们的智慧去解决的,这也就是"只要思想不滑坡,方法总比困难多")。那么问题来了,怎么实现?我们知道一个定时器只有一个ARR,而ARR寄存器又决定了频率,这就意味着只能有一个频率,但这是有前提的那就是使用定时器自带的PWM模式。只要我们能自己控制引脚电平的变化,就可以实现4路不同频率、占空比的PWM输出,怎么才能做到呢?没错!就是输出比较模式(翻转模式),下面将介绍通过输出比较模式实现的方法:
1、配置定时器的输出比较通道
输出比较模式配置为翻转,输出极性为高电平(个人认为在翻转模式下输出极性似乎没有作用,当然也有可能是自己知识不够不能理解它的作用)。还有一点很重要,就是要禁用预加载寄存器,至于为什么我们来看一下参考手册上的一段话:
也就是说,如果使能了预装载寄存器,那么CCRx的值只能在发生更新事件时被修改(从影子寄存器中加载),而我们需要的是在任意时刻都可以对CCRx进行更改以达到我们所需要的波形,所以要禁用预装载寄存器。
2、占空比和频率的设置
这是四路PWM波的频率和占空比(72MHZ主频,定时器2在72分频条件下),这里我们也可以封装出相应的函数来进行占空比和频率的设置。
3、输出比较中断处理
下面将以通道1为例进行说明,首先是获取计数器的值,这里用的是TIM_GetCapture()函数,其实其内部就是读取CNT寄存器的值,然后就是根据cc1_flag来设置下次比较触发的值,即分别设置高电平时间和低电平时间,如下图所示:
其中,val1、val2、val3均为TIM_GetCapture的捕获值。
输出引脚极性设置新发现:
1、输出设置高电平有效时,程序按照预期的一样输出PWM波
2、输出设置为低电平有效时,输出的是和预期互补的PWM波
推测:输出极性决定了初始状态下引脚的电平,配置为高电平有效时,引脚初始电平为低电平;配置为低电平有效时,引脚初始电平为高电平。这种区别就会导致翻转设置高低电平相反,产生互补的PWM波。
最终,通过逻辑分析仪抓的波形如下所示:
通过实验,验证了上述推测,在设置输出极性为低电平有效后,将通道1翻转设置条件修改与原来相反,用逻辑分析仪采集波形后发现通道2、3、4均输出互补波形,而通道1输出预期波形,可以判定,输出极性决定了引脚初始状态电平。
4、总结
至此,一个定时器就可以成功输出四路不同频率、占空比的PWM波。实际上核心原理就是根据捕获值(CNT)来设置比较值(CCRx).