最近用Mega16做一个步进电机的项目,以后把项目全部的内容贴上来跟大家分享呵呵,现在讨论一个防止EEPROM读写出错的小办法,我编写熔丝位是用AVRstudio里面的Jtag下载功能来烧熔丝位的,连上Jtag,AVRstudio的Jtag功能fuse选项里,把熔丝位中的Preserve EEPROM memory through the Chip Erase cycle钩上,Brown-out detection level at VCC=4.0V钩上,Brown-out detection enabled钩上,就可以解决读写EEPROM时出错的机会了。
如果再加上用直接地址访问法,而不用变量定义法,会更好的避免EEPROM读写问题,例如我就定义了
//定义eeprom变量的地址
#define eeprom_step_num 0xA0
#define eeprom_step_r_max 0xB0
#define eeprom_step_l_max 0xC0
然后程序就没有再跑飞了!^_^
在其它论坛上还有一些讨论EEPROM读写错误的贴,我节选了一些,留作参考:
EEPROM掉电丢数据这个特点可不是AVR独有的。很多年前在89C51+24C02的系统里面就遇到过,我不知道铁电有什么比24C02更牛的地方,居然能保证不丢数据。原因很简单,就是掉电过程中,电压降低到MCU无法正常工作的程度,程序跑飞了,单片机引脚状态完全不可控,某次掉电就可能发出错误的写24C02的指令。上电的时候因为RESET处于有效状态,MCU引脚状态完全确定(对于51来说就是全1),是不可能误操作24C02的。解决方案很简单,加一片MAX813L,当电压低于4.6V就锁定89C51,问题彻底解决。这么多年也没见24C02被误改写。
最早的一批AVR内置了EEPROM却没有BOD,所以EEPROM被误改写是家常便饭,ATMEL很快发现了这个问题,新推出的AVR全都含有BOD乐。AVR的情况比较复杂,振荡方式和复位方式都有多种,所以不仅掉电会改写EEPROM(原因同上),上电也会!RESET过程结束前,必须有若干XTAL,MCU内部寄存器(包括软件不可见的)才会清零,如果RESET结束了才来时钟,上电就是程序乱飞,同样有可能改写EEPROM。用RC振荡方式问题不大,有电就能振起来,用石英晶体就会出问题,我测过89C51的,上电后20ms才振起来,如果电源上有大的滤波电容,VCC的上升斜率变小,晶体起振时间会变得更长!有存储示波器的朋友可以自己测一下,对晶振的起振有个感性认识。
我遇到过的问题,m8里面有写eeprom的程序段,数据已经写入到eeprom了。
不停的开关电,eeprom里的值有可能随机改变,不见得是0x00,0xFF
原因是不是上电时,程序指针跑飞到写eeprom那段,导致往eeprom随机地址写了随机数。
后来,采用isp下载2次程序,最后版本的程序是删除了写eeprom程序段,保留读eeprom段。
这样的话,开关电很多次,里面的eeprom没见有改动。
如果系统实际运行时,需要对eeprom写操作,可考虑存多几次数据,用校验方法来处理数据改变。
偶的应用一般要用到EEPROM存储的数据比较少,一般采取反码冗余备份校验的方式,需要存储的数据按照原码和反码存两份,需要读取时分别读取原码和反码,进行校验,若校验不通过,则根据一定的算法恢复数据或者采取缺省值.
我遇到过的问题,m8里面有写eeprom的程序段,数据已经写入到eeprom了。
不停的开关电,eeprom里的值有可能随机改变,不见得是0x00,0xFF
我也是一样BOD使能 就OK了 不过我还是不放心,我用两份数据,最后加校验,启动的时候读eeprom数据 如果有异常 检测出错误数据组,然后用正确的恢复。如果两组数据均遭毒手,用flash里面的默认数据覆盖。
一般我在eeprom里间三分拷贝,位置隔的比较远
以下是马潮老师的解决办法:
作为一个正式的系统或产品,当系统基本功能调试完成后,一旦进行现场测试阶段,请注意马上改写熔丝位的配置,启用AVR的电源检测(BOD)功能。
对于5V系统,设置BOD电平为4.0V;对于3V系统,设置BOD电平为2.7V。然后允许BOD检测。
这样,一旦AVR的供电电压低于BOD电平,AVR进入RESET(不执行程序了)。而当电源恢复到BOD电平以上,AVR才正式开始从头执行程序。保证了系统的可靠性!
原因分析如下:
AVR是宽电压工作的芯片,当电压跌至2.5V,系统程序还能工作。这是有2个可怕的现象可能出现,
1。外围芯片工作已经混乱,AVR读到的东西不正确,造成程序的执行发生逻辑错误(不是AVR本身的原因)。
2。当电源低到临界点,如2.4V时,并且在此互上互下的,AVR本身的程序执行也不正常,取指令、读数据都可能发生错误,或程序乱飞、不稳定(AVR本身的原因,实际任何的单片机都是这样的),非常容易造成EEPROM、FALSH的破坏。有人问51怎么不会?实际上51也是这样,只是51内部没有直接写EEPROM、FLASH的指令,它的程序乱飞留不下痕迹。还有人有疑问:外挂EEPROM,掉电时怎么不会改写?实际是外挂EEPROM,当电压低于4V(2.7V)时,它已经不工作了,程序去改内容也改不了。而AVR内部的东西在临界电压时都能工作,但非常不稳定。
AVR的BOD功能必须要使用,我早期使用51时,凡是产品外部都要使用电源监测芯片,现在AVR自己本身就有该功能,一定要使用。