GPIO模拟IIC通信代码

偶尔会用到,自己记录一下。

宏定义需要根据所用的单片机修改一下。

下面代码里的文字为了方便阅读,所以不加注释

#define uchar unsigned char

#define SET_IIC_SCL(x) (PORT6_5 = (x))    
#define SET_IIC_SDA(x) (PORT6_0 = (x))
#define GET_IIC_SDA     PORT6_0

如果MCU不具备开漏输出的功能,在接收数据的时候需要把IO口方向设为输入。
硬件电路SDA需要加个上拉电阻,SCL可以不用。
#define SET_IIC_SDA_Input() 	IOCP_W(P6CR, 0xdb)
#define SET_IIC_SDA_Output() 	IOCP_W(P6CR, 0xda)

void Delay_Us(uchar us)  延时函数,根据单片机主频调整
{
	uchar i = 4;
	while(us--)
	{
		while(i--);
		i=4;
	}
}

void IIC_Delay(void)
{
	Delay_Us(5);
}

void IIC_Start(void)  启动信号
{
	SET_IIC_SDA(1);
	IIC_Delay();

	SET_IIC_SCL(1);
	IIC_Delay();

	SET_IIC_SDA(0);
	IIC_Delay();

	SET_IIC_SCL(0);
	IIC_Delay();
}

void IIC_Stop(void)  停止信号
{
	SET_IIC_SCL(0);
	IIC_Delay();
	
	SET_IIC_SDA(0);
	IIC_Delay();

	SET_IIC_SCL(1);
	IIC_Delay();

	SET_IIC_SDA(1);
	IIC_Delay();
}

void IIC_NACK(void)  非应答
{
	SET_IIC_SCL(0);
	IIC_Delay();

	SET_IIC_SDA(1);
	IIC_Delay();

	SET_IIC_SCL(1);
	IIC_Delay();

	SET_IIC_SCL(0);
	IIC_Delay();
}

void IIC_ACK(void)  应答
{
	SET_IIC_SCL(0);
	IIC_Delay();

	SET_IIC_SDA(0);
	IIC_Delay();

	SET_IIC_SCL(1);
	IIC_Delay();

	SET_IIC_SCL(0);
	IIC_Delay();
}

uchar IIC_Wait_Ack(void)  检测应答,返回0表示发送成功
{	 
	SET_IIC_SDA_Input();

	SET_IIC_SCL(1);
	IIC_Delay();
 
	if(GET_IIC_SDA)
	{
		IIC_Stop();
		return 1;	
	}

	SET_IIC_SCL(0);	
	SET_IIC_SDA_Output();
	   
	return 0;  
} 

uchar IIC_Write(uchar data)  写单字节,返回0表示写成功
{
	uchar i;

	SET_IIC_SDA_Output();
	SET_IIC_SCL(0);
	IIC_Delay();

	for(i=0; i<8; i++)
	{
		if(data&(0x80>>i))
			SET_IIC_SDA(1);
		else
			SET_IIC_SDA(0);

		IIC_Delay();
		SET_IIC_SCL(1);
		IIC_Delay();
		SET_IIC_SCL(0);
		IIC_Delay();
	}

	return IIC_Wait_Ack();
}

uchar IIC_Read(void)  读单字节
{
	uchar data = 0;
	uchar i;

	SET_IIC_SCL(0);
	IIC_Delay();
	SET_IIC_SDA_Input();
	
	for(i=0; i<8; i++)
	{
		IIC_Delay();
		SET_IIC_SCL(1);
		IIC_Delay();

		if(GET_IIC_SDA)
			data |= 0x80>>i;

		SET_IIC_SCL(0);
	}

	IIC_Delay();
	SET_IIC_SDA_Output();

	return data;
}

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

秋至日丶

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值