答:看门狗是一个12bit的递减计数器。当计数器的值从某个值一直减到0的时候,系统就会产生一个复位信号,CPU收到复位信号,系统复位重新运行。在计数没减到0之前,重置了计数器的值的话,那么就不会产生复位信号,CPU收不到复位信号,系统就会继续正常运行,并不会产生复位,这个重置计数器的动作就是我们说的 “喂狗”。
答:基本功能就是在发生软件问题和程序跑飞时使系统复位,重新启动。可以用于环境比较恶劣的情况下。
答:看门狗分为两类:独立看门狗(IWDG)和窗口看门狗(WWDG)。
窗口看门狗:假如没有定时喂狗,则触发一个中断或产生系统复位(自己决定)。
独立看门狗:假如没有定时喂狗,只会产生系统复位。
独立看门狗(IWDG)由专用的低速时钟(LSI)驱动,即使主时钟发生故障它也仍然有效。
窗口看门狗由从APB1时钟分频后得到的时钟驱动,通过可配置的时间窗口来检测应用程序非正常的过迟或过早的操作。
时钟树框图独立看门狗部分:
看门狗由内部时钟LSI驱动。虽然图中LSI频率为40kHz,但是LSI的频率不是相对稳定的,LSI的频率范围大概为30Khz~60Khz,所以喂狗需要在这个范围之前喂。在估算的时候,以 32Khz 的频率来计算,看门狗对时间的要求不是很精确,所以,时钟有些偏差。
(2)状态寄存器(SR):
RVU位为0时,才能设置重装载值。
PVU位为0时,才能设置预分配。
(4)键寄存器(KR):
写入0xAAAA: 喂狗。
写入0XCCCC:使能看门狗。
写入0X5555: 解除预分频寄存器(PR)和重装载寄存器(RLR)的写保护。
——"Tout"是看门狗溢出时间
——f是看门狗的时钟源频率
——psc是看门狗预分频系数
——rlr是看门狗重装载值
伪代码:
独立看门狗初始化
{
1.打开LSI时钟。
2.往KR中写入0x5555解除PR和RLR的写保护。
3.等待PVU为0。
4.设置分频值。
5.等待RVU为0。
6.设置重载值。0-4095
7.第一次喂狗--往KR中写入0xAAAA。
8.往KR中写入0xCCCC使能看门狗。
}
具体代码:
void Idwg_Init(void)
{
RCC->CSR |=(0x01<<0); //1.打开LSI时钟。
while(!(RCC->CSR &(0x01<<0)));//等待LSI时钟准备就绪
IWDG->KR = 0x5555; //2.往KR寄存器里写入0x5555,解放重装载值和分频值的设置权限
while((IWDG->SR&(0x01<<0)));//3.等待PVU为0。
IWDG->PR &=~(0x7<<0) ; //4.设置预分频值为4分频。
while((IWDG->SR&(0x01<<1)));//5.等待RVU为0。
IWDG->RLR =(15*50-1)&0xfff ; //6.设置重装载值。
IWDG->KR = 0xAAAA;//7.第一次喂狗--往KR中写入0xAAAA。
IWDG->KR = 0xCCCC;//8.往KR中写入0xCCCC使能看门狗。
}
主函数:
延时时间可以自行调整,查看实验结果。当看门狗计数器从重装载值减为0之前没有按时喂狗,则会系统复位重启。
如下面的延时函数延时时间超过定时喂狗的时间,将会复位重启。
int main()
{
Idwg_Init();
printf("重启");
while(1)
{
IWDG->KR = 0xAAAA; //按时喂狗,不然会进行复位重启。
delay_ms(100); //延时时间可以自行调整,查看实验结果。
}
}