关于断电延时和EEPROM数据保存STC掉电保存数据程序.docx
《关于断电延时和EEPROM数据保存STC掉电保存数据程序.docx》由会员分享,可在线阅读,更多相关《关于断电延时和EEPROM数据保存STC掉电保存数据程序.docx(14页珍藏版)》请在冰豆网上搜索。
![关于断电延时和EEPROM数据保存STC掉电保存数据程序.docx](https://file1.bdocx.com/fileroot1/2023-1/29/e91dbeee-f367-460a-a7fd-ba87ad2d0984/e91dbeee-f367-460a-a7fd-ba87ad2d09841.gif)
关于断电延时和EEPROM数据保存STC掉电保存数据程序
关于断电延时和EEPROM数据保存(申酷!
!
)
EEPROM,申酷,数据,延时,断电
原来想用AD检测断电的,做出来测试几遍不行,听了各位的意见。
就花了一个下午完成用一个I/O断电检测电路。
把法拉电容改小了,节约开支,一个2200uf的普通电容就足够了。
经测试能正常保存数据到EEPROM。
电路见下面的图片链接。
该解决方案的程序:
#include
#include //汇编头文件
#define uchar unsigned char
#define uint unsigned int
sbit p12 = P1^2;
uchar i;
void delay(uint z) //延时ms
{
uint x,y;
for(x=112;x>0;x--)
for(y=z;y>0;y--);
}
void init_232(void) //串口初始化
{
SCON = 0x50;
TMOD |= 0x20;
TH1 = 0xfa; //波特率 9600
TL1 = 0xfa;
PCON |= 0x80;
EA = 1;
ES = 1;
TR1 = 1;
}
void send_char(uchar w) //串口发送一个字符
{
SBUF = w;
while(TI == 0);
TI = 0;
}
void send_string(uchar *s,uint string_length) //串口发送一个字符串
{
uint i = 0;
do
{
send_char(*(s + i));
i++;
}
while(i < string_length);
}
/*EEPROM字符读取*/
uchar eeprom_read(uchar x,y)
{
ISP_ADDRH = x;
ISP_ADDRL = y;
ISP_CONTR = 0x9b;
ISP_CMD = 0x01;
ISP_TRIG = 0x46;
ISP_TRIG = 0xb9;
_nop_();
ISP_CONTR=0;
ISP_CMD=0;
ISP_TRIG=0;
return(ISP_DATA);
}
/*EEPROM字符写入*/
void eeprom_write(uchar x,y,z)
{
ISP_DATA = z;
ISP_ADDRH = x;
ISP_ADDRL = y;
ISP_CONTR = 0x9b;
ISP_CMD = 0x02;
ISP_TRIG = 0x46;
ISP_TRIG = 0xb9;
_nop_();
ISP_CONTR=0;
ISP_CMD=0;
ISP_TRIG=0;
}
/*EEPROM扇区擦除*/
void eeprom_erase(uchar x,y)
{
ISP_ADDRH = x;
ISP_ADDRL = y;
ISP_CONTR = 0x9b;
ISP_CMD = 0x03;
ISP_TRIG = 0x46;
ISP_TRIG = 0xb9;
_nop_();
ISP_CONTR=0;
ISP_CMD=0;
ISP_TRIG=0;
}
void main()
{
init_232();
i = 0;
delay(10);
while
(1)
{
if((p12 == 0) && (i == 0))
{
eeprom_erase(0x10,0x00); //擦除第一扇区
delay
(1);
eeprom_write(0x10,0x00,0x88); //在第一扇区写入88
delay
(1);
i = 1;
}
}
}
/*串口接收中断函数*/
void RS232() interrupt 4
{
uchar ch = 0;
if(RI)
{
ch = SBUF;
RI = 0;
send_char(ch);
}
switch(ch)
{
case 1:
send_char(eeprom_read(0x10,0x00)); //串口助手输入16进制1,读EEPROM第一扇区
break;
case 2:
send_char(eeprom_read(0x12,0x00)); //串口助手输入16进制2,读EEPROM第2扇区
break;
case 3:
eeprom_write(0x10,0x00,0x55); //串口助手输入16进制3,写EEPROM第一扇区55
break;
case 4:
eeprom_write(0x12,0x00,0x66); //串口助手输入16进制4,写EEPROM第2扇区66
break;
case 5:
eeprom_erase(0x10,0x00); //串口助手输入16进制5,擦除EEPROM第一扇区
break;
case 6:
eeprom_erase(0x12,0x00); //串口助手输入16进制6,擦除EEPROM第2扇区
break;
default:
break;
}
}
这是一段stc单片机EEPROM掉电存储程序,麻烦大家帮我看看哈,怎么调用时输出有问题啊,希望给个调用的例子
悬赏分:
0-提问时间2010-8-2119:
32
#include
#include
#include
#include"..\h_files\eeprom.h"
/**************************************************************************************************/
voidisp_iap_enable(void)
{
EA=0;/*关中断*/
ISP_CONTR=ISP_CONTR&0x18;
ISP_CONTR=ISP_CONTR|WAIT_TIME;
ISP_CONTR=ISP_CONTR|0x80;/*ISPEN=1*/
}
/**************************************************************************************************/
voidisp_iap_disable(void)
{
ISP_CONTR=ISP_CONTR&0x7f;/*ISPEN=0*/
ISP_TRIG=0x00;
EA=1;/*开中断*/
}
/**************************************************************************************************/
voidisp_iap_goon(void)
{
isp_iap_enable();/*打开ISP,IAP功能*/
ISP_TRIG=0x46;/*触发ISP,IAP命令字节1*/
ISP_TRIG=0xb9;/*触发ISP,IAP命令字节2*/
_nop_();
}
/**************************************************************************************************/
UINT8byte_read(UINT16byte_addr)
{
ISP_ADDRH=(UINT8)(byte_addr>>8);/*地址赋值*/
ISP_ADDRL=(UINT8)(byte_addr&0x00ff);
ISP_COMD=ISP_COMD&0xf8;/*清除低3位*/
ISP_COMD=ISP_COMD|RE_COMMAND;/*写入读命令*/
isp_iap_goon();/*触发执行*/
isp_iap_disable();/*关闭ISP,IAP功能*/
return(ISP_DATA);/*返回读到的数据*/
}
/**************************************************************************************************/
voidsector_erase(UINT16sector_addr)
{
UINT16i_sector_addr;
i_sector_addr=(sector_addr&0xfe00);/*取扇区地址*/
ISP_ADDRH=(UINT8)(i_sector_addr>>8);
ISP_ADDRL=0x00;
ISP_COMD=ISP_COMD&0xf8;/*清空低3位*/
ISP_COMD=ISP_COMD|ER_COMMAND;/*擦除命令3*/
isp_iap_goon();/*触发执行*/
isp_iap_disable();/*关闭ISP,IAP功能*/
}
/**************************************************************************************************/
voidbyte_write(UINT16byte_addr,UINT8original_data)
{
ISP_ADDRH=(UINT8)(byte_addr>>8);/*取地址*/
ISP_ADDRL=(UINT8)(byte_addr&0x00ff);
ISP_COMD=ISP_COMD&0xf8;/*清空低3位*/
ISP_COMD=ISP_COMD|PR_COMMAND;/*写命令2*/
ISP_DATA=original_data;/*写入数据准备*/
isp_iap_goon();/*触发执行*/
isp_iap_disable();/*关闭ISP,IAP功能*/
}
提问者:
smu_east-一级
网友推荐答案
/************************************************************************************************************************************/
#include
#include
#include
#include
/************************************************************************************************************************************/
#defineUcharunsignedchar
#defineUintunsignedint
#defineUlongunsignedlong
//定义Flash操作等待时间及允许IAP/ISP/EEPROM操作的常数
#defineENABLE_ISP0x83//系统工作时钟<12MHz时,对IAP_CONTR寄存器设置此值
/************************************************************************************************************************************/
sfrIAP_DATA=0xE2;
sfrIAP_ADDRH=0xE3;
sfrIAP_ADDRL=0xE4;
sfrIAP_CMD=0xE5;
sfrIAP_TRIG=0xE6;
sfrIAP_CONTR=0xE7;
/************************************************************************************************************************************/
//全局变量及共用体变量
/************************************************************************************************************************************/
Ucharbuff[8];
Ucharbuff1[8]={0x01,0x02,0x04,0x08,0x10,0x20,0x40,0x80};
unionunion_temp16{Uintun_temp16;Ucharun_temp8[2];}my_unTemp16;//定义共用体,给存储eeprom使用
/************************************************************************************************************************************/
//函数声明区
/************************************************************************************************************************************/
voidRead_8byte(Uchar*buf,Uintadd,Ucharbitt);//读多个字节,调用前需打开IAP功能
voidProgram_8byte(Uchar*buf,Uintadd,Ucharbitt);//写多个字节,调用前需打开IAP功能
voidSector_Erase(Uintadd);//擦除扇区
voidIAP_Disable();//关闭IAP功能
voidDelay();//延时函数
voidmcu_ini(void);//mcu初始化函数
/************************************************************************************************************************************/
//主函数区
/************************************************************************************************************************************/
voidmain(void)
{
Uchari;
P1=0xF0;//演示程序开始,让P1[3:
0]控制的灯亮
Delay();//延时
P1=0x0F;//演示程序开始,让P1[7:
4]控制的灯亮
Delay();//延时
Sector_Erase(0x4000);//擦除整个扇区
Program_8byte(buff1,0x4000,8);
P2=0x55;//P2.7亮
Read_8byte(buff,0x4000,8);
while
(1)//CPU在此无限循环执行此句
{
P0=~buff[i];
Delay();//延时
i++;
if(i==8){i=0;P2^=0xff;Delay();}
//延时
}
}
/********************************************************************************************************************************/
//读一字节,调用前需打开IAP功能,入口:
DPTR=字节地址,返回:
A=读出字节
/********************************************************************************************************************************/
UcharByte_Read(Uintadd)
{
IAP_DATA=0x00;
IAP_CONTR=ENABLE_ISP;//打开IAP功能,设置Flash操作等待时间
IAP_CMD=0x01;//IAP/ISP/EEPROM字节读命令
my_unTemp16.un_temp16=add;
IAP_ADDRH=my_unTemp16.un_temp8[0];//设置目标单元地址的高8位地址
IAP_ADDRL=my_unTemp16.un_temp8[1];//设置目标单元地址的低8位地址
//EA=0;
IAP_TRIG=0x46;//先送5Ah,再送A5h到ISP/IAP触发寄存器,每次都需如此
IAP_TRIG=0xB9;//送完A5h后,ISP/IAP命令立即被触发起动
_nop_();
//EA=1;
return(IAP_DATA);
}
/********************************************************************************************************************************/
//读多个字节,调用前需打开IAP功能,入口:
DPTR=字节地址,返回:
A=读出字节
/********************************************************************************************************************************/
voidRead_8byte(Uchar*buf,Uintadd,Ucharbitt)
{Uchari;
for(i=0;i{
buf[i]=Byte_Read(add+i);
}
IAP_Disable();//关闭IAP功能,清相关的特殊功能寄存器,使CPU处于安全状态,
//一次连续的IAP操作完成之后建议关闭IAP功能,不需要每次都关
}
/********************************************************************************************************************************/
//字节编程,调用前需打开IAP功能,入口:
DPTR=字节地址,A=须编程字节的数据
/********************************************************************************************************************************/
voidByte_Program(Uintadd,Ucharch)
{
IAP_CONTR=ENABLE_ISP;//打开IAP功能,设置Flash操作等待时间
IAP_CMD=0x02;//IAP/ISP/EEPROM字节编程命令
my_unTemp16.un_temp16=add;
IAP_ADDRH=my_unTemp16.un_temp8[0];//设置目标单元地址的高8位地址
IAP_ADDRL=my_unTemp16.un_temp8[1];//设置目标单元地址的低8位地址
IAP_DATA=ch;//要编程的数据先送进IAP_DATA寄存器
//EA=0;
IAP_TRIG=0x46;//先送5Ah,再送A5h到ISP/IAP触发寄存器,每次都需如此
IAP_TRIG=0xB9;//送完A5h后,ISP/IAP命令立即被触发起动
_nop_();
//EA=1;
}
/********************************************************************************************************************************/