📄 i2c.c
字号:
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <ctype.h>
#include <absacc.h>
#include <reg52.h>
#include <usign.h>
#include <float.h>
#include <INTRINS.h>
#include "meter.h"
sbit WP =P2^5;
sbit SCL =P1^6;
sbit SDA =P1^7;
#define SCL_HIGH SCL=1;\
_nop_();\
_nop_();
#define SCL_LOW SCL=0;\
_nop_();\
_nop_();
#define SDA_HIGH SDA=1;\
_nop_();\
_nop_();
#define SDA_LOW SDA=0;\
_nop_();\
_nop_();
#define WRITE256 0xa0 //低64K
#define READ256 0xa1
void I2CStart(void);
void I2CStop(void);
uchar WaitAck(void);
void SendAck(void);
void SendNak(void);
void I2CSendByte(uchar i2c_sb_data);
uchar I2CReceiveByte(void);
/**********************************************************
Function : I2CStart
Description : I2C bus start signal
Input : none
Output : none
***********************************************************/
void I2CStart(void)
{
SDA_HIGH;
SCL_HIGH;
SDA_LOW;
SCL_LOW;
}
/**********************************************************
Function : I2CStop
Description : I2C bus stop signal
Input : none
Output : none
***********************************************************/
void I2CStop(void)
{
SDA_LOW;
SCL_HIGH;
SDA_HIGH;
SCL_LOW;
}
/**********************************************************
Function : WaitAck for check ack
Description : wait I2C slave to respond ack
Input : none
Output : 0 - respond; 1 - no respond
***********************************************************/
uchar WaitAck(void)
{
uchar bAck;
SDA_HIGH;
SCL_HIGH;
if(SDA==0)
bAck=OK;
else
bAck=NOK;
SCL_LOW;
return bAck;
}
/**********************************************************
Function : SendAck
Description : send ack to I2C slave
Input : none
Output : none
***********************************************************/
void SendAck(void)
{
SDA_LOW;
SCL_HIGH;
SCL_LOW;
SDA_HIGH;
}
/**********************************************************
Function : SendNak
Description : send not ack signal to I2C slave
Input : none
Output : none
***********************************************************/
void SendNak(void)
{
SDA_HIGH;
SCL_HIGH;
SCL_LOW;
SDA_LOW;
}
/**********************************************************
Function : I2CSendByte
Description : send a byte to I2C slave
Input : data - the byte to be sent
Output : none
***********************************************************/
void I2CSendByte(uchar bChar)
{
uchar i;
for(i=0;i<8;i++)
{
if( bChar&0x80)
{
SDA_HIGH;
SCL_HIGH;
SCL_LOW;
}
else
{
SDA_LOW;
SCL_HIGH;
SCL_LOW;
}
bChar<<=1;
}
}
/**********************************************************
Function : I2CReceiveByte
Description : Receive a byte from I2C slave
Input : none
Output : the byte received
***********************************************************/
uchar I2CReceiveByte(void)
{
uchar i,bChar;
bChar=0;
SDA=1; //input init
for(i=0;i<8;i++)
{
bChar<<=1;
SCL_HIGH;
if(SDA==1)
bChar|= 0x01;
else
bChar&= 0xfe;
SCL_LOW;
}
return bChar;
}
/*
功能:I2C芯片初始化
输入:none
输出: none
注意:
*/
void vInitI2C(void)
{
WP=1;
SCL_LOW;
SDA_LOW;
}
/*
功能: 读I2C
输入:
Sla: 芯片地址(A0:EEPROM1;A4:EEPROM2)
Address: 片内首地址
Send_Data: 数据地址
len: 长度(<=128)
输出: 0:正确; 1: 错误
注意:
*/
uchar IRcvStr( uchar Sla,uint Address ,uchar *RcvData ,uchar len)
{
uchar i;
I2CStart();
I2CSendByte(Sla); //SEND DEVICE ADDRESS
if(WaitAck())
goto I2CReadError;
I2CSendByte( (uchar)(Address>>8) ); //SEND ADDRESS HIGH
if(WaitAck())
goto I2CReadError;
I2CSendByte( (uchar)Address ); //SEND ADDRESS LOW
if(WaitAck())
goto I2CReadError;
I2CStart();
Sla|=0x01; //read bit=1
I2CSendByte(Sla); //SEND DEVICE ADDRESS
if(WaitAck())
goto I2CReadError;
for(i=0;i<len;i++)
{
RcvData[i]=I2CReceiveByte(); //SEND DATA
if(i==len-1)
SendNak(); //发送完最后字节,发送NAK
else
SendAck();
}
I2CStop();
return OK;
I2CReadError:
I2CStop();
return NOK;
}
/*
功能: 页写I2C
输入:
Sla: 芯片地址(A0:EEPROM1;A4:EEPROM2)
Address: 片内首地址
Send_Data: 数据源地址
len: 长度(<=128)
输出: 0:正确; 1: 时序错误; 2:写入的数据读出后不对
注意: 不能跨页
*/
uchar ISendStr( uchar Sla,uint Address ,uchar *Send_Data ,uchar len )
{
uchar i,bI2CReadData;
// memcpy(abI2CReadData,Send_Data,len); //暂存要写的数据
WP=0;
I2CStart();
I2CSendByte(Sla); //SEND DEVICE ADDRESS
if(WaitAck())
goto I2CWriteError;
I2CSendByte( (uchar)(Address>>8) ); //SEND ADDRESS HIGH
if(WaitAck())
goto I2CWriteError;
I2CSendByte( (uchar)Address ); //SEND ADDRESS LOW
if(WaitAck())
goto I2CWriteError;
for(i=0;i<len;i++)
{
I2CSendByte(Send_Data[i]); //SEND DATA
if(WaitAck())
goto I2CWriteError;
}
I2CStop();
for(;;) //查询是否写完
{
I2CStart();
I2CSendByte(Sla);
if(!WaitAck())
break;
}
WP=1;
_Delay(10);
for(i=0;i<len;i++)
{
IRcvStr(Sla, Address ,&bI2CReadData ,1); //写后读
Address++;
if( bI2CReadData!=Send_Data[i] )
goto I2CWriteError;
}
/*
IRcvStr(Sla, Address ,Send_Data ,len); //写后读
if (memcmp(abI2CReadData, Send_Data, len) == 0 )
return 2;
*/
_Delay(100);
return OK;
I2CWriteError:
I2CStop();
WP=1;
_Delay(100);
// return NOK;
return 0;
}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -