第8章 STM32F4独立看门狗简介
第八章 STM32F4独立看门狗简介
1. 导入
STM32F4 的独立看门狗由内部专门的 32Khz 低速时钟(LSI) 驱动,即使主时钟发生故障,它也仍然有效。这里需要注意独立看门狗的时钟是一个内部 RC 时钟,所以并不是准确的 32Khz,而是在 15~47Khz 之间的一个可变化的时钟,只是我们在估算的时候,以 32Khz 的频率来计算,看门狗对时间的要求不是很精确,所以,时钟有些偏差,都是可以接受的。
2. 相关寄存器讲解
独立看门狗有几个寄存器与我们这节相关,我们分别介绍这几个寄存器:
2.1 关键字寄存器IWDG_KR
在关键字寄存器(IWDG_KR)中写入 0xCCCC,开始启用独立看门狗;此时计数器开始从其复位值 0xFFF 递减计数。当计数器计数到末尾 0x000 时,会产生一个复位信号(IWDG_RESET)。无论何时,只要关键字寄存器 IWDG_KR 中被写入 0xAAAA, IWDG_RLR 中的值就会被重新加载到计数器中从而避免产生看门狗复位 。
IWDG_PR 和 IWDG_RLR 寄存器具有写保护功能。要修改这两个寄存器的值,必须先向IWDG_KR 寄存器中写入 0x5555。 将其他值写入这个寄存器将会打乱操作顺序,寄存器将重新被保护。重装载操作(即写入 0xAAAA)也会启动写保护功能。
2.2 预分频寄存器(IWDG_PR)
接下来,我们介绍预分频寄存器(IWDG_PR),该寄存器用来设置看门狗时钟的分频系数,最低为 4,最高位 256,该寄存器是一个 32 位的寄存器,但是我们只用了最低 3 位,其他都是保留位。
2.3 重载寄存器IWDG_RLR
在介绍完 IWDG_PR 之后,我们介绍一下重装载寄存器 IWDG_RLR。该寄存器用来保存重装载到计数器中的值。该寄存器也是一个 32 位寄存器,但是只有低 12 位是有效的。
只要对以上三个寄存器进行相应的设置,我们就可以启动 STM32F4 的独立看门狗。独立看门狗相关 的库函数操作函数在文件 stm32f4xx_hal_iwdg.c 和对应的头文件stm32f4xx_hal_iwdg.h 中。
3. 库函数配置独立看门狗步骤
3.1 启动IWDG外设时钟
在 STM32 的 RCC (时钟控制) 寄存器中,需要启用与看门狗相关的外设时钟,通常是 LSI 时钟,代码如下:
__HAL_RCC_LSI_ENABLE(); // 启用 LSI 时钟源
此时,IWDG 将基于 LSI 时钟运行,LSI 是一个低速内部时钟,通常频率为 32.768 kHz。
3.2 配置IWDG的预分频器和重装载值
IWDG 的计数器是基于 LSI 时钟的。配置预分频器和重装载值,决定看门狗超时时间。
IWDG_HandleTypeDef hiwdg;
hiwdg.Instance = IWDG; // 选择 IWDG 外设
hiwdg.Init.Prescaler = IWDG_PRESCALER_64; // 设置预分频器(例如预分频 64)
hiwdg.Init.Reload = 4095; // 设置重装载值(最大值为 4095)
hiwdg.Init.Window = IWDG_WINDOW_DISABLE; // 禁用窗口模式(也可以根据需求启用)
hiwdg.Init.WriteAccess = IWDG_WRITEACCESS_ENABLE; // 启用写入权限
hiwdg.Init.ReadAccess = IWDG_READACCESS_ENABLE; // 启用读取权限
if (HAL_IWDG_Init(&hiwdg) != HAL_OK) {
// 错误处理
}
- Prescaler:设置 IWDG 计数器的分频系数(例如
IWDG_PRESCALER_64
会将 LSI 时钟分频 64)。 - Reload:设置重装载值,它控制看门狗超时时间。
- Window:窗口模式,可设置为启用/禁用,如果启用窗口模式,看门狗重装载值必须在窗口时间内重新喂狗。
- WriteAccess:允许写操作到 IWDG。
3.3 启动IWDG
配置完成后,需要启动 IWDG 外设。这是通过设置 IWDG 控制寄存器的启动位来完成的:
HAL_IWDG_Start(&hiwdg); // 启动 IWDG
3.4 喂狗操作
看门狗计数器启动后,如果系统运行正常,每隔一定时间需要喂一次狗,即重置计数器。可以使用以下函数来喂狗:
HAL_IWDG_Refresh(&hiwdg); // 喂狗,重置计数器
3.5 完整配置示例
下面是一个完整的 STM32 HAL 库配置独立看门狗的代码示例:
#include "stm32f4xx_hal.h"
IWDG_HandleTypeDef hiwdg;
void SystemClock_Config(void) {
// 配置系统时钟,这里略过
}
int main(void) {
HAL_Init(); // 初始化 HAL 库
SystemClock_Config(); // 配置系统时钟
// 启用 LSI 时钟源(独立看门狗需要 LSI 时钟)
__HAL_RCC_LSI_ENABLE();
// 配置 IWDG
hiwdg.Instance = IWDG;
hiwdg.Init.Prescaler = IWDG_PRESCALER_64; // 设置预分频器
hiwdg.Init.Reload = 4095; // 设置重装载值,最大值 4095
hiwdg.Init.Window = IWDG_WINDOW_DISABLE; // 禁用窗口模式
hiwdg.Init.WriteAccess = IWDG_WRITEACCESS_ENABLE; // 启用写访问权限
hiwdg.Init.ReadAccess = IWDG_READACCESS_ENABLE; // 启用读访问权限
// 初始化 IWDG
if (HAL_IWDG_Init(&hiwdg) != HAL_OK) {
// 错误处理
while(1);
}
// 启动 IWDG
HAL_IWDG_Start(&hiwdg);
while (1) {
// 在主循环中定期喂狗,防止系统复位
HAL_IWDG_Refresh(&hiwdg);
// 模拟一些主任务
HAL_Delay(500); // 延时 500 ms
}
}
4. 小结
-
超时时间:超时时间由
Prescaler
和Reload
决定。计算公式为:Timeout=Prescaler×Reload/LSI频率
假设 LSI 时钟为 32.768 kHz,若设置
Prescaler = 64
和Reload = 4095
,则超时时间为:Timeout=64×4095/32768≈8秒
因此,超时时间约为 8 秒。
-
窗口模式:如果启用了窗口模式(
IWDG_WINDOW_ENABLE
),则在该窗口内必须喂狗,否则会触发看门狗复位。 -
看门狗复位:若未在超时前喂狗,IWDG 会复位系统。
2024.9.29 第一次修订,后期不再维护
2024.12.22 重写配置步骤