C语言程序>>AT24C64

 

/*****************************************************************
程序说明:EEPROM 24C64子程序
注:(1)单片机:AT89S52晶振Fosc:11.0592MHz编程软件:Keil uVision2;
 (2)地址为000;容量为8K;I2C 在时钟线为高时数据被写入
 (3)I2C 开始信号:在时钟线为高时 数据线产生下降沿 
    I2C 结束信号:在时钟线为高时 数据线产生上降沿 
    I2C 主机应答:主机要继续从从机读数据 需给应答信号 即向从机写入0
    I2C 主机无应答:主机不要继续从从机读数据 需给无应答信号 即向从机写入1
    I2C 从机应答:主机向从机写入数据后 从机给应答信号 写入成功为0 失败为1
 (4)AT24C64 写入时 先写到数据缓冲区 要延时5ms
******************************************************************/
//-----------------------------------------------------------------
// 头文件包含
//-----------------------------------------------------------------
#include
//-----------------------------------------------------------------
// EEPROM 24C64系列 接口引脚
//-----------------------------------------------------------------
#define AT24C64_SDA  P3_7  //I2C数据线
#define AT24C64_SCL  P3_6  //I2C时钟线

//-----------------------------------------------------------------
// 数据类型宏定义
//-----------------------------------------------------------------
#define uchar unsigned char
#define uint  unsigned int

//-----------------------------------------------------------------
// 功能程序区
//-----------------------------------------------------------------

// I2C 开始信号
void I2C_Start(void)
{
 AT24C64_SDA=1;     //数据线产生下降沿
 Delay(I2C_TIME);    //延时(I2C_TIM)us
 AT24C64_SCL=1;     //时钟线为高
 Delay(I2C_TIME);    //延时(I2C_TIM)us
 AT24C64_SDA=0;     //
 Delay(I2C_TIME);    //延时(I2C_TIM)us
 AT24C64_SCL=0;     //时钟线拉低
 Delay(I2C_TIME);    //延时(I2C_TIM)us
}

// I2C 结束信号
void I2C_Stop(void)
{
 AT24C64_SDA=0;     //数据线产生上降沿
 Delay(I2C_TIME);    //延时(I2C_TIM)us
 AT24C64_SCL=1;     //时钟线为高
 Delay(I2C_TIME);    //延时(I2C_TIM)us
 AT24C64_SDA=1;     //
 Delay(I2C_TIME);    //延时(I2C_TIM)us
 AT24C64_SCL=0;     //时钟线拉低
 Delay(I2C_TIME);    //延时(I2C_TIM)us
}

// I2C 主机应答
void I2C_Ack(void)
{
 AT24C64_SDA=0;     //数据线为0 向从机写入0
 Delay(I2C_TIME);    //延时(I2C_TIM)us
 AT24C64_SCL=1;     //时钟线为高时数据被写入
 Delay(I2C_TIME);    //延时(I2C_TIM)us
 AT24C64_SCL=0;     //时钟线拉低
 Delay(I2C_TIME);    //延时(I2C_TIM)us
}

// I2C 主机无应答
void I2C_NAck(void)
{
 AT24C64_SDA=1;     //数据线为1 向从机写入1
 Delay(I2C_TIME);    //延时(I2C_TIM)us
 AT24C64_SCL=1;     //时钟线为高时数据被写入
 Delay(I2C_TIME);    //延时(I2C_TIM)us
 AT24C64_SCL=0;     //时钟线拉低
 Delay(I2C_TIME);    //延时(I2C_TIM)us
}

// 函数功能: I2C 从机应答
uchar I2C_Get_Ack(void)
{
 uchar temp;
 AT24C64_SDA=1;     //单片机读数据线时写1
 Delay(I2C_TIME);    //延时(I2C_TIM)us
 AT24C64_SCL=1;     //时钟线为高时数据被读出
 Delay(I2C_TIME);    //延时(I2C_TIM)us
 temp=AT24C64_SDA;    //数据读到端口
 Delay(I2C_TIME);    //延时(I2C_TIM)us
 AT24C64_SCL=0;     //时钟线拉低
 Delay(I2C_TIME);    //延时(I2C_TIM)us
 return temp;     //返回从机应答值
}

// I2C 写入一个字节
uchar I2C_Write_Byte(uchar dat)
{
 uchar i,temp;
 temp=dat;     
 for(i=0;i<8;i++)
 {
  AT24C64_SDA=((dat<  // temp<<=1;     //左移
 // AT24C64_SDA=CY;    //溢出值送到端口
  AT24C64_SCL=1;    //时钟线为高时数据被写入
  Delay(I2C_TIME);   //延时(I2C_TIM)us
  AT24C64_SCL=0;    //时钟线拉低
  Delay(I2C_TIME);   //延时(I2C_TIM)us
 }
 return I2C_Get_Ack();   //返回从机应答信号
}

// 函数功能: I2C 读出一个字节 
uchar I2C_Read_Byte(void)
{
 uchar i,rbyte=0;    
 AT24C64_SDA=1;     //单片机读数据线时写1
 for(i=0;i<8;i++)
 {
  AT24C64_SCL=1;    //时钟线为高时数据被读出
  Delay(I2C_TIME);   //延时(I2C_TIM)us
  if(1==AT24C64_SDA)
  {
   rbyte|=(0x80>>i);  //读取低位
  }
  AT24C64_SCL=0;    //时钟线拉低
  Delay(I2C_TIME);   //延时(I2C_TIM)us
 }
 return rbyte;
}

// AT24C64 写入一个字节
void AT24C64_Write_Byte(uint addr,uchar dat)
{
 I2C_Start();     //开始信号
 I2C_Write_Byte(0xa0);     //写入配置信息 1 0 1 0 A2 A1 A0 R/W
 I2C_Write_Byte(addr>>8);  //写入高位地址
 I2C_Write_Byte(addr);   //写入低位地址
 I2C_Write_Byte(dat);   //写入数据
    I2C_Stop();      //结束信号
 Delay_100us(50);    //延时5ms
}

// AT24C64 写入一页字节
void AT24C64_Write_Page(uint addr,uchar *pbuf)
{
 uchar i;
 I2C_Start();         //开始信号
 I2C_Write_Byte(0xa0);     //写入配置信息 1 0 1 0 A2 A1 A0 R/W
 I2C_Write_Byte(addr>>8);  //写入高位地址
 I2C_Write_Byte(addr);   //写入低位地址
 for(i=0;i<32;i++)
 {
  if(addr>AT24C64_END)  //结束地址(听诊器用)
  {
   addr=AT24C64_START;  //开始地址(听诊器用) 
   I2C_Write_Byte(addr>>8);//写入高位地址
   I2C_Write_Byte(addr); //写入低位地址
  }
  I2C_Write_Byte(pbuf[i]); //写入数据
 }
    I2C_Stop();      //结束信号
 Delay_100us(50);    //延时5ms
}

// AT24C64 读出连续字节
void AT24C64_Current_Addr_Read_Byte(uint length,uchar *pbuf)
{
 uchar i;
 I2C_Start();     //开始信号
 I2C_Write_Byte(0xa1);     //写入配置信息 1 0 1 0 A2 A1 A0 R/W
 for(i=0;i  {
  pbuf[i]=I2C_Read_Byte(); //读出数据
  I2C_Ack();     //主机应答
 }
 pbuf[i]=I2C_Read_Byte();  //读出最后一位数据
 I2C_NAck();      //主机无应答
    I2C_Stop();      //结束信号
}

// AT24C64 读出一字节
uchar AT24C64_Read_Byte(uint addr)
{
 uchar temp;
 I2C_Start();     //开始信号
 I2C_Write_Byte(0xa0);     //写入配置信息 1 0 1 0 A2 A1 A0 R/W
 I2C_Write_Byte(addr>>8);  //写入高位地址
 I2C_Write_Byte(addr);   //写入低位地址
 AT24C64_Current_Addr_Read_Byte(1,&temp);//长度为1
 return temp;
}

// AT24C64 读出连续字节  
void AT24C64_Sequential_Read(uint addr,uint length,uchar *pbuf)
{
 I2C_Start();     //开始信号
 I2C_Write_Byte(0xa0);     //写入配置信息 1 0 1 0 A2 A1 A0 R/W
 I2C_Write_Byte(addr>>8);  //写入高位地址
 I2C_Write_Byte(addr);   //写入低位地址
 AT24C64_Current_Addr_Read_Byte(length,pbuf);//长度为length
}

//-----------------------------------------------------------------
// END of FILE
//-----------------------------------------------------------------

你可能感兴趣的:(单片机)