WDG(看门狗)
看门狗简介独立看门狗能独立工作是指它有独立的时钟源LSI(内部低速时钟40KHZ),即使主时钟出现问题独立看门狗也能正常运行时间精度低就是只有一个最晚界限只要不超过这个界限就不会产生复位信号。窗口看门狗与独立看门狗不同它多了一个最早界限必须在这个窗口内喂狗而且它使用的是APB1的时钟36MHZ独立看门狗框图这个框图类比于时基单元只不过这个是递减计数器每来一个时钟递减一次由图可以看出这个是12位计数器所以最大值是2^12-14095键寄存器作用由图可以看出只有输入键寄存器特定值它才能正常运行工作当程序可能跑飞可能受到电磁干扰时程序可能会做出任何操作而设置一位则很有可能会被程序误操作设置成0或1但0xAAAA,0xCCC就很小可能了这就降低了电路受干扰的能力。独立看门狗的超时时间例如选择四分频TLSI1/40KHZ0.025毫秒最短时间TIWDG0.025410.1毫秒最长时间TIWDG0,02444096409.6毫秒以此类推。窗口看门狗框图注意这里T6用作溢出标志位当T6由1变为0时即由0x40变成0x3F时就会触发复位信号WDGA则是控制看门狗的开关置1打开置0关上可以看到上面还有一个看门狗配置当T6:0大于W6:0时(就是当重置CNT值时会先将CNT值拿出跟W6:0比较发现比它大时就是喂早了)即超出看门狗最早界限就会置1触发复位信号。窗口看门狗工作特性第三点是指在产生复位前一刻会有中断信号提醒一下你要不要干点啥所以可以在这个早期唤醒中断里干一些紧急任务保存重要数据关闭危险设备等。窗口看门狗超时时间这里要x4096是因为PLCK1时钟源到看门狗预分频器会有一个4096的固定分频。这里WDGTB从上到下分别对应0248独立看门狗和窗口看门狗的对比独立看门狗初始化模板intmain(void){OLED_Init();Key_Init();OLED_ShowString(1,1,IWDG TEST:);if(RCC_GetFlagStatus(RCC_FLAG_IWDGRST)SET)//获取看门狗复位标志位{OLED_ShowString(2,1,IWDG RST);Delay_ms(500);OLED_ShowString(2,1, );Delay_ms(100);RCC_ClearFlag();//清除看门狗标志位}else{OLED_ShowString(3,1,RST);Delay_ms(500);OLED_ShowString(3,1, );Delay_ms(100);}IWDG_WriteAccessCmd(IWDG_WriteAccess_Enable);//解除写使能保护//配置1秒10000.025*16*24991IWDG_SetPrescaler(IWDG_Prescaler_16);//配置预分频IWDG_SetReload(2499);//配置重装值IWDG_ReloadCounter();//喂一次狗IWDG_Enable();//使能看门狗while(1){Key_GetNum();IWDG_ReloadCounter();//每搁一秒喂一次狗OLED_ShowString(4,1,FEED);Delay_ms(500);OLED_ShowString(4,1, );Delay_ms(100);}}注意这里调用IWDG_Enable()和IWDG_ReloadCounter()就相当于启动写保护。想要查看是否由独立看门狗引起的复位可以调用RCC_GetFlagStatus(RCC_FLAG_IWDGRST)不过下一次还想查看是否由它引起的复位要在每次查看后手动清除标志位RCC_ClearFlag()如上图调用看门狗函数LSI时钟就会自动打开所以不用手动开启时钟。窗口看门狗初始化配置intmain(void){OLED_Init();Key_Init();OLED_ShowString(1,1,WWDG TEST:);if(RCC_GetFlagStatus(RCC_FLAG_WWDGRST)SET)//获取看门狗复位标志位{OLED_ShowString(2,1,WWDG RST);Delay_ms(500);OLED_ShowString(2,1, );Delay_ms(100);RCC_ClearFlag();//清除看门狗标志位}else{OLED_ShowString(3,1,RST);Delay_ms(500);OLED_ShowString(3,1, );Delay_ms(100);}RCC_APB1PeriphClockCmd(RCC_APB1Periph_WWDG,ENABLE);//配置窗口时间为30ms超过时间为50ms501/36000*4096*8*55WWDG_SetPrescaler(WWDG_Prescaler_8);//配置预分频值WWDG_SetWindowValue(0x40|21);//30msWWDG_Enable(0x40|54);//50ms0x40是将T6位置1while(1){Key_GetNum();OLED_ShowString(4,1,FEED);Delay_ms(20);OLED_ShowString(4,1, );Delay_ms(20);WWDG_SetCounter(0x40|54);//喂狗}}这里WWDG_Enable(0x40 |54)函数与WWDG_SetCounter(0x40 |54)参数相同是因为可以从图中看出为防止计数器数值随意跳动而复位这里使能必须也要喂一次狗这也是为什么WWDG_SetCounter(0x40 |54)要放在后面因为使能函数和喂狗函数太近就会因为两次喂狗时间过早而导致复位。