
单片机中有EPROM,我用的是STC12C5A60S2,有1K空间的EPROM,是可以断电保存用户数据的,其他型号STC单片机的EPROM大小不一,参考手册,但程序差不多的,程序如下:
/
单片机学习开发板BP-51A - 内部EPROM读写演示程序
版本: V10 (2011/10/13)
作者: BestProvider
说明: STC12C5A60S2单片机有1K字节的内部EPROM,可以用来存放用户数
据(断电不丢失),EPROM分2个扇区,地址为0X0000-0X1FFF和0X2000
-0X3FFF,需要注意的是在进行写 *** 作时,必须先要进行所在扇区
的清除 *** 作
硬件: 本实验需要液晶屏LCD1602来显示数据
参考: 《STC12C5A60S2中文资料》- 第12章 STC12C5A60S2系列单片机
EPROM的应用
/
#include <stc12c5a60s2h>
typedef unsigned char BYTE; // 数据范围0-255
typedef unsigned int WORD; // 数据范围0-65535
typedef bit BOOL ; // 数据范围0-1
#define CMD_IDLE 0
#define CMD_READ 1
#define CMD_WRITE 2
#define CMD_ERASE 3
#define ENABLE_IAP 0X82
BYTE write_data[5]={0,1,2,3,4};
BYTE read_data[5];
BYTE code dis1[ ] = {"EPROM Write/Read"} ;
BYTE code dis2[ ] = {"Data: "} ;
sbit LCD_RS = P2^0; // LCD控制线
sbit LCD_RW = P2^1;
sbit LCD_EN = P2^2;
/ ms级延时 /
//
void delay_ms(WORD n)
{
WORD i=0;
WORD j;
while(i<n)
{
for(j=0;j<1000;j++){}
i++;
}
}
/ 测试LCD忙碌状态 /
//
BOOL lcd_bz()
{
BOOL result;
LCD_RS = 0;
LCD_RW = 1;
LCD_EN = 1;
delay_ms(1);
result = (BOOL)(P0 & 0x80);
LCD_EN = 0;
return result;
}
/ 写入指令数据到LCD /
//
void lcd_wcmd(BYTE cmd)
{
while(lcd_bz());
LCD_RS = 0;
LCD_RW = 0;
LCD_EN = 0;
delay_ms(1);
P0 = cmd;
delay_ms(1);
LCD_EN = 1;
delay_ms(1);
LCD_EN = 0;
}
/ 设定显示位置 /
//
void lcd_pos(BYTE pos)
{
lcd_wcmd(pos | 0x80);
}
/ 写入字符显示数据到LCD /
//
void lcd_wdat(BYTE dat)
{
while(lcd_bz());
LCD_RS = 1;
LCD_RW = 0;
LCD_EN = 0;
P0 = dat;
delay_ms(1);
LCD_EN = 1;
delay_ms(1);
LCD_EN = 0;
}
/ LCD初始化设定 /
//
void lcd_init()
{
lcd_wcmd(0x38);
delay_ms(10);
lcd_wcmd(0x0c);
delay_ms(10);
lcd_wcmd(0x06);
delay_ms(10);
lcd_wcmd(0x01); // 清除LCD的显示内容
delay_ms(10);
}
/ EPROM 扇区清除 /
//
void Iaperasesector(unsigned char addr)
{
IAP_ADDRH=addr;
IAP_ADDRL=0x00;
IAP_CONTR=ENABLE_IAP;
IAP_CMD=CMD_ERASE;
IAP_TRIG=0x5a;
IAP_TRIG=0xa5;
delay_ms(10);
}
/ EPROM 写 *** 作 /
//
void Iapwritebyte()
{
BYTE i;
Iaperasesector(0x00); // 在进行内部EPROM写 *** 作前需进行扇区清除 *** 作
IAP_CONTR=ENABLE_IAP;
for(i=0;i<5;i++)
{
IAP_ADDRH=0x00;
IAP_ADDRL=0x00+i;
IAP_DATA=write_data[i];
IAP_CMD=CMD_WRITE;
IAP_TRIG=0x5a;
IAP_TRIG=0xa5;
delay_ms(10);
}
IAP_CONTR=0x00;
}
/ EPROM 读 *** 作 /
//
void Iapreadbyte()
{
BYTE i;
for(i=0;i<5;i++)
{
IAP_DATA=0;
IAP_CONTR=ENABLE_IAP;
IAP_ADDRH=0x00;
IAP_ADDRL=0x00+i;
IAP_CMD=CMD_READ;
IAP_TRIG=0x5a;
IAP_TRIG=0xa5;
delay_ms(10);
read_data[i]=IAP_DATA;
}
IAP_CONTR=0x00;
}
/ 数据显示 /
//
void Display()
{
BYTE m ;
lcd_pos(0) ; // 设置显示位置为第一行的第1个字符
m = 0 ;
while(dis1[m] != '\0')
{
lcd_wdat(dis1[m]) ; // 显示字符
m++ ;
}
lcd_pos(0x40) ; // 设置显示位置为第二行第1个字符
m = 0 ;
while(dis2[m] != '\0')
{
lcd_wdat(dis2[m]) ; // 显示字符
m++ ;
}
lcd_pos(0x46); // 显示读取的第1个数据
lcd_wdat(0x30+read_data[0]);
lcd_pos(0x48); // 显示读取的第2个数据
lcd_wdat(0x30+read_data[1]);
lcd_pos(0x4a); // 显示读取的第3个数据
lcd_wdat(0x30+read_data[2]);
lcd_pos(0x4c); // 显示读取的第4个数据
lcd_wdat(0x30+read_data[3]);
lcd_pos(0x4e); // 显示读取的第5个数据
lcd_wdat(0x30+read_data[4]);
}
/ 主程序 /
//
main()
{
delay_ms(200); // 通电后延迟200ms,再进行EPROM *** 作
Iapwritebyte(); // 将4个数据存入单片机内部EPROM中
delay_ms(10);
Iapreadbyte(); // 从EPROM中读取数据
lcd_init(); // 初始化LCD
delay_ms(10);
Display(); // 显示读取的数据
while(1);
}
有点差别,关机意味着彻底的关断了单片机的工作,掉电不一样,如果你启动了掉电保护模式(低电压模式),那么单片机在该状态下仍然是在工作的,通过中断可以唤醒,唤醒后,单片机接着掉电前的状态继续运行。
完全可以不使用AT24C02。STC89C52自带4K的EEPROM,你的应用程序可以对其进行编程、读写 *** 作,应该不复杂,可以仔细阅读一下DATASHEET中的相关说明,而且其中还有例程代码。
不过实验的时候要小心,因为这4K存储区出厂时烧录了串口下载程序的代码,如果将这部分程序所在空间给改写了,虽然芯片并未损坏,但将来就无法通过串口升级程序了。一般而言升级用的代码不会太长,所以4K的EEPROM后部的空间应该能用,至少100、200字节的空间应该有,应该够你用的。调试时最好是采用DIP封装(双列直插)的芯片,插拔方便,这样即便将出厂的代码修改或删除掉,仍可以通过编程器再写入恢复原状。关于出厂代码的详情可咨询一下厂商深圳的服务电话,应该可以得到些帮助。
以上就是关于宏晶单片机,如何在断电程序中,保护数据。请附程序全部的内容,包括:宏晶单片机,如何在断电程序中,保护数据。请附程序、stc单片机关机和掉电是不是不同,有什么区别,关机和掉电后程序存储器会不会被清零、stc单片机掉电不丢失数据等相关内容解答,如果想了解更多相关内容,可以关注我们,你们的支持是我们更新的动力!
欢迎分享,转载请注明来源:内存溢出
微信扫一扫
支付宝扫一扫
评论列表(0条)