Board logo

标题: 模拟I2C源程序(C语言) [打印本页]

作者: 苹果也疯狂    时间: 2015-3-15 21:50     标题: 模拟I2C源程序(C语言)

下面是用普通C51实现的I2C基本电平模拟函数和通用函数。 使用该程序,可以在51上用P1口模拟I2C。



/* 电平模拟函数和基本读写函数

Void IIC_Start(Void);

Void IIC_Stop(Void);

Void SEND_0(Void);

Void SEND_1(Void);

Bit Check_Acknowledge(Void);

Void Write_Byte(Uchar B)Reentrant;

Bit Write_N_Bytes(Uchar *Buffer,Uchar N)Reentrant;

Bit Read_N_Bytes(Uchar SlaveAdr,Uchar N,Uchar *Buffer);

Uchar Read_Byte(Void)Reentrant;

*/



#Include<String.H>

#Include<Reg52.H>

#Include<Intrins.H>

#Include"Aiic_51.H"



Sbit SCL=P1^6;

Sbit SDA=P1^7;



Void DELAY(Uint T)

{

While(T!=0)

T--;

}



Void IIC_Start(Void)

{

//启动I2C总线的函数,当SCL为高电平时使SDA产生一个负跳变

SDA=1;

SCL=1;

DELAY(DELAY_TIME);

SDA=0;

DELAY(DELAY_TIME);

SCL=0;

DELAY(DELAY_TIME);

}



Void IIC_Stop(Void)

{

//终止I2C总线,当SCL为高电平时使SDA产生一个正跳变

SDA=0;

SCL=1;

DELAY(DELAY_TIME);

SDA=1;

DELAY(DELAY_TIME);

SCL=0;

DELAY(DELAY_TIME);

}



Void SEND_0(Void)

{

//发送0,在SCL为高电平时使SDA信号为低

SDA=0;

SCL=1;

DELAY(DELAY_TIME);

SCL=0;

DELAY(DELAY_TIME);

}



Void SEND_1(Void)

{

//发送1,在SCL为高电平时使SDA信号为高

SDA=1;

SCL=1;

DELAY(DELAY_TIME);

SCL=0;

DELAY(DELAY_TIME);

}



Bit Check_Acknowledge(Void)

{

//发送完一个字节后检验设备的应答信号

SDA=1;

SCL=1;

DELAY(DELAY_TIME/2);

F0=SDA;

DELAY(DELAY_TIME/2);

SCL=0;

DELAY(DELAY_TIME);

If(F0==1)

Return FALSE;

Return TRUE;

}



Void Write_Byte(Uchar B)Reentrant

{

//向IIC总线写一个字节

Uchar I;

For(I=0;I<8;I++)

If((B<<I)&0x80)

SEND_1();

Else

SEND_0();

}



Bit Write_N_Bytes(Uchar *Buffer,Uchar N)Reentrant

{

//向I2C总线写N个字节

Uchar I;

IIC_Start();



For(I=0;I<N;I++)

{

Write_Byte(Buffer[I]);

If(!Check_Acknowledge())

{

IIC_Stop();

Return(I==N);

}

}



IIC_Stop();

Return TRUE;

}



Uchar Read_Byte(Void)Reentrant

{

//从I2C总线读一个字节

Uchar B=0,I;

For(I=0;I<8;I++)

{

SDA=1; //释放总线

SCL=1; //接受数据

DELAY(10);

F0=SDA;

DELAY(10);

SCL=0;

If(F0==1)

{

B=B<<1;

B=B|0x01;

}

Else

B=B<<1;

}

Return B;

}



Bit Read_N_Bytes(Uchar SlaveAdr,Uchar N,Uchar *Buffer)

{

//从I2C总线读N个字节

Uchar I;

IIC_Start();

Write_Byte(SlaveAdr); //向总线发送接收器地址

If(!Check_Acknowledge()) //等待接收器应答信号

Return FALSE;

For(I=0;I<N;I++)

{

Buffer[I]=Read_Byte();

If(I!=N)

SEND_0(); //发送应答

Else

SEND_1(); //发送非应答

}

IIC_Stop();

Return TRUE;

}




欢迎光临 电子技术论坛_中国专业的电子工程师学习交流社区-中电网技术论坛 (http://bbs.eccn.com/) Powered by Discuz! 7.0.0