最近在调试系统的时候,发现单片机老是复位,于是想着用程序来判断一个单片机的复位信号是来自于哪里。查找资料发现STM8单片机的复位源总共有9种
●NRST引脚产生的外部复位
● 上电复位(POR)
● 掉电复位(BOR)
● 独立看门狗复位
● 窗口看门狗复位
● 软件复位
● SWIM复位
● 非法操作码复位
● EMS复位:当一些关键的寄存器被破坏或错误加载时产生的复位
但是这9种复位源通过复位寄存器能看到的只有5种
复位状态寄存器(RST_SR)
位7:5 保留,必须保持为0。
位4 EMCF:EMC复位标志
位3 SWIMF:SWIM复位标志位
位2 ILLOPF:非法操作码复位标志位
位1 IWDGF:独立型看门狗复位标志位
位0 WWDGF:窗口型看门狗复位标志位
由于单片机没有用到看门狗,所以这两种看门狗复位用不到,SWIM复位是烧写程序或者仿真时用的。那就只剩下一个EMC复位、非法操作码复位可以判断。但是更希望看到的是单片机是电源不稳引起的掉电复位还是单片机复位引脚被干扰引起的NRST复位。但是寄存器中没有可以判断这两种复位源的标志位。那么能不能自己想办法来判断这两种复位源呢?
首先分析一下掉电复位和NRST复位的区别,掉电复位也就是单片机完全断电,复位后内存中所有的东西会丢失。NRST复位时内存数据没有丢失,内存中的东西还是复位前存储的数据。那么根据这个特性是不是可以在内存中某个地址存数一个标志。复位后去读取这个标志,如果这个标志和存放的一样,说明单片机没有掉电,属于NRST复位。如果读取到的值不是存储的值那么说明单片机断电了,内存中存储的内容丢失了,属于掉电复位。那么这样就能区分开是掉电复位还是NRST复位了。
写个程序测试了一下,测试结果符合预期。
测试代码如下:
#include "iostm8s103F3.h"
#include "main.h"
#include "uart.h"
#include "stdio.h"
void SysClkInit( void )
{
CLK_SWR = 0xe1; //HSI为主时钟源 16MHz CPU时钟频率
CLK_CKDIVR = 0x00; //CPU时钟0分频,系统时钟0分频
}
void main( void )
{
__asm( "sim" ); //禁止中断
SysClkInit();
Uart1_Init( 9600 );
__asm( "rim" ); //开启中断
//复位源判断
if( ( * ( u16* )( 0x000102 ) ) == 0x55 ) //判断0x000100这个地址中存储的值是不是0x55
{
printf( " key reset!rn" ); //值等于0x55说明是程序写进去的,属于按键复位
}
else //如果这个地址的值不等于0x55 说明单片机是刚上电
{
printf( " power reset!rn" ); //属于上电复位 然后将指定的值写入指定的地址,若单片机不断电,这个值就会一直保持不变
* ( u16* )( 0x000102 ) = 0x55;
}
if( RST_SR_WWDGF )
{
printf( "wwdg reset!rn" );
}
if( RST_SR_IWDGF )
{
printf( "iwdg reset!rn" );
}
if( RST_SR_ILLOPF )
{
printf( "illop reset!rn" );
}
if( RST_SR_SWIMF )
{
printf( "swim reset!rn" );
}
if( RST_SR_EMCF )
{
printf( "emcf reset!rn" );
}
//WWDG_CR = 0x80; //启动独立看门狗
// IWDG_KR = 0xCC; //启动窗口看门狗
while( 1 )
{
}
}
每次上电后先判断 0x000102 这个地址的值是不是0x55,如果不是说明单片机是刚上电,内存中的值是随机的。于是将0x000102这个地址中的值改为0x55,如果下一次单片机复位后读到这个地址的值是0x55的话,说明单片机没有掉电。属于复位引脚引起的复位。0x000102这个地址必须保证不会被程序用到,要不然在程序执行过程中值被改写,下次单片机复位后读到的值就不是0x55了。
其余的复位源直接去读取寄存器就可以了。
上一篇:STM8S——Clock control(CLK)
下一篇:STM8S——Analog/digital converter (ADC)
推荐阅读
史海拾趣
1、在自己得到了别人的帮助以后,一定在最后总结一下,请不要一声不吭的走人。 总结的内容包括:1、问题到底出在哪里。2、通过第几楼的方法解决的。 这种总结,对其他人很有用,通过看总结他们可以知道第几楼的方法是对的。 在自己的求助帖最后 ...… 查看全部问答∨ |
pb 5.0 中自带的.net compact framework是1.0的。vs2005用的是2.0的。 因此我想生成印象时将2.0的.net framework包含进去。 于是安装了WinCEPB50-071231-Product-Update-Rollup-Armv4I.msi这个补丁。 在**catalog items中的Applications and Ser ...… 查看全部问答∨ |
我想在日历控件上(MFC的DateTimePicker控件)上弹出TAH(上下文菜单,类似pc上的右键弹出菜单),请问该如何实现,能给个例子吗? 网上的例子都千篇一律的出自codeproject上一位葡萄牙工程师的论文,看了几遍都没看懂,里面很多函数参数不知从何而来.不知大哥能否给小弟指导一下?感激不尽… 查看全部问答∨ |
|
cosmic对Heap的处理效率怎么样啊?(malloc/free) 最近项目中打算使用malloc这个函数(IC:STM8A)有点担心编译器对Heap操作的效率问题 有哪位朋友知道cosmic对Heap处理效率怎么样啊? PS:本人分数很少,望谅解!… 查看全部问答∨ |
本帖最后由 dontium 于 2015-1-23 13:26 编辑 请问有一线性调频信号要用ADS62P48进行采集,ADS62P48前变压器要怎么设计??? … 查看全部问答∨ |
各位高手大家好~有個SPI DMA的問題請大家。小弟使用開發平台為STM32F103ZE。目前若不用DMA的SPI是正常可以使用的。但目前SPI傳的速度不夠快,若照SPI 6Mbps傳送4kB data應該約花5.3 ms,但是目前我從波形上量到的時間約是12~13ms, 因為我的應用上需 ...… 查看全部问答∨ |
设计资源 培训 开发板 精华推荐
- 新突破!超高速内存,为英特尔至强6性能核处理器加速
- 将vRAN站点整合至单服务器,助力运营商降低总体拥有成本
- Allegro MicroSystems 在 2024 年德国慕尼黑电子展上推出先进的磁性和电感式位置感测解决方案
- 左手车钥匙,右手活体检测雷达,UWB上车势在必行!
- 狂飙十年,国产CIS挤上牌桌
- 神盾短刀电池+雷神EM-i超级电混,吉利新能源甩出了两张“王炸”
- 浅谈功能安全之故障(fault),错误(error),失效(failure)
- 智能汽车2.0周期,这几大核心产业链迎来重大机会!
- 美日研发新型电池,宁德时代面临挑战?中国新能源电池产业如何应对?
- Rambus推出业界首款HBM 4控制器IP:背后有哪些技术细节?