如何在AVR中实现零占空比PWM而不出现毛刺?

问题描述 投票:0回答:5

我尝试在 ATmega2560 上使用硬件 PWM,使用 TC0(8 位定时器),在快速 PWM 模式下。我需要动态调整占空比,其中包括零占空比。然而,这似乎并不容易,甚至不可能。引用数据表:

OCR0A 寄存器的极值代表特殊情况 当在快速 PWM 模式下生成 PWM 波形输出时。如果 OCR0A 设置为等于 BOTTOM,输出将是一个窄尖峰 每个 MAX+1 定时器时钟周期。将 OCR0A 设置为等于 MAX 将 导致持续高或低输出(取决于极性 由 COM0A1:0 位设置的输出)。

因此,将 OCR0A 设置为 0(=BOTTOM)实际上不会导致零占空比,我的测试证实了这一点。需要采取其他方法。

首先,我已经教授了如何使用 OCR0A=MAX 特殊情况,如上面引用中所述。结合暂时切换到反向模式,这将导致零占空比。然而,由于 COM0A1:0 位不是双缓冲的(并且与 OCR0A 不同步),如果在输出为高电平时切换模式(它将保持高电平直到下一次溢出),则可能会导致输出出现毛刺)。 OCR0A 更改和模式更改以什么顺序完成似乎并不重要,两者都可能出现故障。

我还考虑了另一种解决方案,通过设置 COM0A1:0=0 来关闭 PWM。这将立即将输出设置为 PORT 寄存器中的值,该值为零。但仍然存在从零输出回到非零占空比的问题。根据我在数据表中读到的内容,设置 COM0A1:0 来重新启用 PWM 会立即将输出引脚切换到 PWM 的输出,这可能是一个不正确的值,直到下一次比较匹配或定时器溢出。因此,出现了故障。

整体上反转 PWM 可能是适用的,但问题就变成了实现全占空比,并存在对称问题。

请注意,在通过 PORT 强制引脚输出时,无法启用 PWM 波形生成,如数据表中所述:

比较输出模式(COM0x1:0)位有两个功能。这 波形发生器使用 COM0x1:0 位来定义输出 下一个比较匹配时比较 (OC0x) 状态。另外,COM0x1:0 位控制 OC0x 引脚输出源。

没有办法让 PWM 运行一个周期左右并在准备好时切换到它 - 启用 PWM 立即强制引脚输出。

更新。 相位校正(中心对齐)PWM 模式不存在此问题,在我的情况下是可以接受的。我已经尝试过并确认它适用于零占空比和全占空比。

embedded microcontroller avr atmel pwm
5个回答
6
投票

您有两个选择:

  1. 如果您使用快速 pwm: 您可以使用反向 pwm。您需要做的就是将 OC 引脚设置为反转模式并反转您的 pwm 比较值。然而 - 你现在有 100% 占空比的故障

  2. 使用相位校正pwm。缺点是最大频率减半了。


5
投票

我刚刚遇到了同样的问题,但需要在 atmega2560 上坚持使用快速 PWM 设置。

我找到的解决方案是暂时将输出引脚置于正常端口操作(即,当需要零占空比时,将 TCCRnA 寄存器的 COMnX1 和 COMnX1 位设置为零:

TCCR1A &= (0<<COM1A1) & (0<<COM1A1);


2
投票

在快速pwm模式下,占空比为: (OCRx+1)/(TOP+1) * 100% 因此,在同相模式下永远无法达到 0%,在反相模式下永远无法达到 100%。


0
投票

还有另一种选择,只需将引脚方向更改为这样输入即可:

DDRB &= ~(1<<PB1);

..当您想要实现零占空比时。我知道这是某种黑客行为,有时并不希望执行这样的事情,但无论如何它是有效的。


0
投票

我知道已经有一段时间了,但今天我在 ATTINY2313 的 PB2 和 PD4 引脚上遇到了这个问题。 (在 0% 的情况下)将相邻引脚声明为输出,然后直接连接到 PB2,并通过电阻器将 PB2 连接到其目标(MOSFET 等),这是否是一个“硬件”解决方案?如果占空比不为 0%,只需将其设置为输入?作为低电平输出,它将充当流过的非常小的电流的接收器,对吧?或者我在这里遗漏了一些非常明显的东西?

© www.soinside.com 2019 - 2024. All rights reserved.