代碼如下
#include<i2.h>
void Delay10us() //@11.0592MHz
{
unsigned char i;
i=2;
while (--i);
}
void I2cStart()//I2c開始信號
{
SCL=1;//SCL在高電平時SDA從高電平轉為低電平就是開始信號
Delay10us();
SDA=1;
Delay10us();//保持狀態時間要大于4.7us以便讀取
SDA=0;
Delay10us();//保持狀態時間要大于4us以便讀取
SCL=0;//結束后恢復初始狀態
Delay10us();
}
void I2cStop()//I2c結束信號
{
SCL=1;//SCL在高電平時SDA從低電平轉為高電平就是結束信號
Delay10us();
SDA=0;
Delay10us();//保持狀態時間要大于4.7us以便讀取
SDA=1;
Delay10us();//保持狀態時間要大于4us以便讀取
SCL=0;//結束后恢復初始狀態
Delay10us();
}
u8 I2cSendBaty(u8 dat)//發送一個字節的數據
{
//SCL在高電平時讀取SDA數據在低電平時允許改變SDA數據改變
u8 i,j=0,k=0;
SCL=0;
for(i=0;i<8;i++)
{
j=dat>>(7-i);
SDA=j%2;
Delay10us();
SCL=1;//開始讀取數據
Delay10us();
SCL=0;
}
SDA=1;//開始檢測從機是否接收完成
Delay10us();
SCL=1;
while(SDA)//判斷SDA狀態(低電平時說明接收完成)
{
k++;
if(k>200)//超時判斷
{
SDA=0;
Delay10us();
return 0;//返回接收失敗
}
}
SCL=0;
Delay10us();
return 1;//返回接收完成
}
u8 I2cReadBaty()//讀取一個字節的數據
{
u8 i,dat=0;
SDA=1;
Delay10us();
for(i=0;i<8;i++)
{
SCL=1;
Delay10us();
dat<<=1;
dat|=SDA;
Delay10us();
SCL=0;
Delay10us();
}
return dat;
}
void At24c02Write(u8 Chip_addr,u8 M_addr,u8 dat)//IC芯片寫入數據
{
I2cStart();//數據寫入開始
I2cSendBaty(Chip_addr);//發送儲存芯片地址
I2cSendBaty(M_addr);//發送儲存芯片儲存地址
I2cSendBaty(dat);//發送儲存數據
I2cStop();//I2c結束信號
}
u8 At24c02Read(u8 Chip_addr,u8 M_addr,u8 dat)//IC芯片讀取數據
{
u8 ret=0;
I2cStart();//數據寫入開始
I2cSendBaty(Chip_addr);//發送儲存芯片地址
I2cSendBaty(M_addr);//發送儲存芯片儲存地址
I2cStart();//數據寫入開始
I2cSendBaty(Chip_addr+1);//發送儲存芯片地址
ret= I2cReadBaty();//讀取一個字節的數據
I2cStop();//I2c結束信號
return ret;
} |