IIC实现E2PROM的数据写入与擦除
main函数
#include "reg52.h"
#include "intrins.h"
#include "smg_ca.h"
#include "initial.h"
#include "absacc.h"#define AT24C02_ADDR 0XA0
#define AT24C02_ADDR_Read 1
#define AT24C02_ADDR_Write 0sbit SCL = P2^0;
sbit SDA = P2^1;bit ACK_Flag;void delay(int t)
{while(t--);while(t--);while(t--);while(t--);
}
//延时5us
void Delay_I2c_5us() //debug 后发现延时5.43us。
{_nop_();
}
//
//
//起始信号
void I2cStart()
{SCL = 1;SDA = 1;Delay_I2c_5us(); //保持总线高电平多于4.7usSDA = 0; Delay_I2c_5us(); //保持SCL为高,SDA为低多于4.7us
}
//停止信号
void I2cStop()
{SCL = 0;SDA = 0;SCL = 1;Delay_I2c_5us();SDA = 1;Delay_I2c_5us();
}//
//
//主机读从机的应答,即向从机发送数据
bit ReadACK()
{SCL = 0;//读取SCL为高时,从机的SDA应答状况,根据收到的SDA信号来确定从机是否应答//if(SDA) // NO{SCL = 1;Delay_I2c_5us();return(1);}else // YES{SCL = 1;Delay_I2c_5us();return(0);}
}
//主机发送应答信号,接受从及数据
void SendACK(bit i)
{SCL = 0;if(i)SDA = 1;elseSDA = 0;SCL = 1;Delay_I2c_5us();SCL = 0;SDA = 1; //释放SDA,为主机软件应答后,从机发送数据做准备,若不拉高,则从机无法发送数据,因为从既不具备//操控SDA线的能力}
//
//******************************发送数据************************************//
//
//主机发送一字节的 地址/数据 ,取决于给 I2c_dat 赋的值
void I2cSend_Byte(unsigned char I2c_dat)
{unsigned char i ;for(i=0;i<8;i++){SCL = 0;if(I2c_dat & 0x80)//选择最高位,最高位为1,则给SDA赋值1SDA = 1;else //否则,给SDA赋值0SDA = 0;SCL = 1;Delay_I2c_5us();I2c_dat = I2c_dat << 1; // 把低1位的值转移到最高位上,对最高位进行传输}SCL = 0;SDA = 1;
}
//主机向E2PROM写数据全过程:
//start-addr-ack-write-ack-stop
void AT24C02_Write(unsigned char addr_e2prom,unsigned char e2prom_dat)
{I2cStart();I2cSend_Byte(AT24C02_ADDR + AT24C02_ADDR_Write);//地址 1010 xxx(000) + 0delay(500);if(ReadACK()) //从机拒绝接收数据ACK_Flag = 1;elseACK_Flag = 0;I2cSend_Byte(addr_e2prom);if(ReadACK()) //从机拒绝接收数据ACK_Flag = 1;elseACK_Flag = 0;I2cSend_Byte(e2prom_dat);if(ReadACK()) //从机拒绝接收数据ACK_Flag = 1;elseACK_Flag = 0;I2cStop();
}
//
//*******************************接收数据***********************************//
//
//主机接收从机数据
unsigned char I2cRead_Byte()
{unsigned char i,read_dat;for(i=0;i<8;i++){read_dat <<= 1;SCL = 0;if(SDA)read_dat |= 0x01;SCL = 1;Delay_I2c_5us();}return read_dat;
}
//主机接收从机数据全过程:
//start-address-ack-start-address-read-ack-stop
unsigned char AT24C02_Read(unsigned char addr_e2prom)
{char dat;I2cStart();I2cSend_Byte(AT24C02_ADDR + AT24C02_ADDR_Write);//地址 1010 xxx(000) + 0if(ReadACK()) //从机拒绝接收数据ACK_Flag = 1;elseACK_Flag = 0;I2cSend_Byte(addr_e2prom);ReadACK();I2cStart();I2cSend_Byte(AT24C02_ADDR + AT24C02_ADDR_Read);while(ReadACK()) //从机拒绝接收数据{XBYTE[0x8000] = 0xfe;}ACK_Flag = 0;XBYTE[0x8000] = 0xff;dat = I2cRead_Byte();SendACK(1);I2cStop();return (dat);
}//
void Display_smg(unsigned char num)
{DisPlaySMG_Bit(0,SMGNoDot_CA[num/100]);DelaySMG(150);DisPlaySMG_Bit(1,SMGNoDot_CA[(num%100)/10]);DelaySMG(150);DisPlaySMG_Bit(2,SMGNoDot_CA[num%10]);DelaySMG(150);DisPlay_All(0xff);}
//
void main()
{Initial();AT24C02_Write(2,9);delay(10000);while(1){Display_smg(AT24C02_Read(2));}
}
//
数码管驱动代码:
/*****************************
数码管驱动:
数码管延时/
数码管按位写入/应用于动态显示
数码管全体写入/
*****************************/
#include "absacc.h"void DelaySMG(unsigned char t)
{while(t--);
}void DisPlaySMG_Bit(unsigned char pos,unsigned char dat)
{XBYTE[0XE000] =0xff;XBYTE[0XC000] =0x01 << pos;XBYTE[0XE000] =dat;
}void DisPlay_All(unsigned char dat)
{XBYTE[0XC000] =0xff;XBYTE[0XE000] =dat;}
本文来自互联网用户投稿,文章观点仅代表作者本人,不代表本站立场,不承担相关法律责任。如若转载,请注明出处。 如若内容造成侵权/违法违规/事实不符,请点击【内容举报】进行投诉反馈!
