📄 i2c.c
字号:
#include <avr/io.h>
//#include <avr/twi.h>
//#include "styte.h"
#include "i2c.h"
#define TW_WRITE 0
#define TW_READ 1
#define max 3
//uchar twista;
void TWI_init( void )
{
//DDRC|=0x00;
//PORTC|=0x03;
TWBR = 0x03;//设置波特率
TWSR= 0X1;//设置预分频因子,则SCL频率为92160Hz
}
uchar twi_write_byte(uchar sla,uchar address,uchar write_data) //
{
uchar twst,n=0x0,rv=0xff;
restart:
if(n++>=max)
goto error;
begin:
TWCR = _BV(TWINT) | _BV(TWSTA) | _BV(TWEN);//发送开始信号
while((TWCR & _BV(TWINT))==0x0);//等待发送完毕
switch(twst = (TWSR&0xf8))
{
case 0x10: //TW_REP_START://有可能出现
case 0x08: //TW_START:
break;
case 0x38: //TW_MT_ARB_LOST:
goto begin;
default:
goto error;
}
TWDR = sla | TW_WRITE;//发送SLA+W
TWCR = _BV(TWINT) | _BV(TWEN);//清TWINT,开始传输
while((TWCR & _BV(TWINT))==0x0);//等待传输完毕
switch(twst = (TWSR&0xf8))
{
case 0x18: //TW_MT_SLA_ACK:
break;
case 0x20: //TW_MT_SLA_NACK://器件忙,有可能处于内部写周期
goto restart;
case 0x38: // TW_MT_ARB_LOST:
goto begin;
default:
goto error;
}
/* TWDR = address>>8;//传输地址高8位
TWCR = _BV(TWINT) | _BV(TWEN);//清TWINT,开始传输
while((TWCR & _BV(TWINT))==0x0);//等待传输完毕
switch((twst = TW_STATUS))
{
case TW_MT_DATA_ACK:
break;
case TW_MT_DATA_NACK:
goto quit;
case TW_MT_ARB_LOST:
goto begin;
default:
goto error;
} */
TWDR = address;//传输地址低8位
TWCR = _BV(TWINT) | _BV(TWEN);//清TWINT,开始传输
while((TWCR & _BV(TWINT))==0x0);//等待传输完毕
switch(twst = (TWSR&0xf8))
{
case 0x28: //TW_MT_DATA_ACK:
break;
case 0x30: //TW_MT_DATA_NACK:
goto quit;
case 0x38: //TW_MT_ARB_LOST:
goto begin;
default:
goto error;
}
TWDR = write_data;
TWCR = _BV(TWINT) | _BV(TWEN);//清TWINT,开始传输
while((TWCR & _BV(TWINT))==0x0);//等待传输完毕
switch(twst = (TWSR&0xf8))
{
case 0x28: //TW_MT_DATA_ACK:
break;
default:
goto error;
}
quit:
TWCR = _BV(TWINT) | _BV(TWSTO) | _BV(TWEN);//发送停止信号
return rv;
error:
rv=0x00;
goto quit;
}
uchar twi_write_str(uchar sla,uchar address,uchar *p,uchar len)
{
uchar i,twst,n=0x0,rv=0xff;
restart:
if(n++>=max)
goto error;
begin:
TWCR = _BV(TWINT) | _BV(TWSTA) | _BV(TWEN);//发送开始信号
while((TWCR & _BV(TWINT))==0x0);//等待发送完毕
switch(twst = (TWSR&0xf8))
{
case 0x10: //TW_REP_START://有可能出现
case 0x08: //TW_START:
break;
case 0x38: //TW_MT_ARB_LOST:
goto begin;
default:
goto error;
}
TWDR = sla | TW_WRITE;//发送SLA+W
TWCR = _BV(TWINT) | _BV(TWEN);//清TWINT,开始传输
while((TWCR & _BV(TWINT))==0x0);//等待传输完毕
switch(twst = (TWSR&0xf8))
{
case 0x18: //TW_MT_SLA_ACK:
break;
case 0x20: //TW_MT_SLA_NACK://器件忙,有可能处于内部写周期
goto restart;
case 0x38: //TW_MT_ARB_LOST:
goto begin;
default:
goto error;
}
/* TWDR = address>>8;//传输地址高8位
TWCR = _BV(TWINT) | _BV(TWEN);//清TWINT,开始传输
while((TWCR & _BV(TWINT))==0x0);//等待传输完毕
switch((twst = TW_STATUS))
{
case TW_MT_DATA_ACK:
break;
case TW_MT_DATA_NACK:
goto quit;
case TW_MT_ARB_LOST:
goto begin;
default:
goto error;
} */
TWDR = address;//传输地址低8位
TWCR = _BV(TWINT) | _BV(TWEN);//清TWINT,开始传输
while((TWCR & _BV(TWINT))==0x0);//等待传输完毕
switch(twst = (TWSR&0xf8))
{
case 0x28: //TW_MT_DATA_ACK:
break;
case 0x30: //TW_MT_DATA_NACK:
goto quit;
case 0x38: //TW_MT_ARB_LOST:
goto begin;
default:
goto error;
}
for(i=0;i<len;i++)
{
TWDR = *p;
p++;
TWCR = _BV(TWINT) | _BV(TWEN);//清TWINT,开始传输
while((TWCR & _BV(TWINT))==0x0);//等待传输完毕
switch(twst =(TWSR&0xf8))
{
case 0x28://TW_MT_DATA_ACK:
break;
default:
goto error;
}
}
quit:
TWCR = _BV(TWINT) | _BV(TWSTO) | _BV(TWEN);//发送停止信号
return rv;
error:
rv=0x00;
goto quit;
}
uchar twi_read_byte( uchar sla,uchar address) //读字节,地址,寄存器地址。
{
uchar twst,n=0x0,rv=0xff;
restart:
if(n++>=max)
goto error;
begin:
TWCR = _BV(TWINT) | _BV(TWSTA) | _BV(TWEN);//发送开始信号
while((TWCR & _BV(TWINT))==0x0);//等待发送完毕
switch(twst = (TWSR&0xf8))
{
case 0x10://TW_REP_START://有可能出现
case 0x08://TW_START:
break;
case 0x38://TW_MT_ARB_LOST:
goto begin;
default:
goto error;
}
TWDR = sla | TW_WRITE;//发送SLA+W
TWCR = _BV(TWINT) | _BV(TWEN);//清TWINT,开始传输
while((TWCR & _BV(TWINT))==0x0);//等待传输完毕
switch(twst = (TWSR&0xf8))
{
case 0x18://TW_MT_SLA_ACK:
break;
case 0x20://TW_MT_SLA_NACK://器件忙,有可能处于内部写周期
goto restart;
case 0x38://TW_MT_ARB_LOST:
goto begin;
default:
goto error;
}
/* TWDR = address>>8;//传输地址高8位
TWCR = _BV(TWINT) | _BV(TWEN);//清TWINT,开始传输
while((TWCR & _BV(TWINT))==0x0);//等待传输完毕
switch((twst = TW_STATUS))
{
case TW_MT_DATA_ACK:
break;
case TW_MT_DATA_NACK:
goto quit;
case TW_MT_ARB_LOST:
goto begin;
default:
goto error;
}*/
TWDR = address;//传输地址低8位
TWCR = _BV(TWINT) | _BV(TWEN);//清TWINT,开始传输
while((TWCR & _BV(TWINT))==0x0);//等待传输完毕
switch(twst = (TWSR&0xf8))
{
case 0x28://TW_MT_DATA_ACK:
break;
case 0x30://TW_MT_DATA_NACK:
goto quit;
case 0x38://TW_MT_ARB_LOST:
goto begin;
default:
goto error;
}
TWCR = _BV(TWINT) | _BV(TWSTA) | _BV(TWEN);//发送(重新)开始信号
while((TWCR & _BV(TWINT))==0x0);//等待发送完毕
switch(twst = (TWSR&0xf8))
{
case 0x10://TW_REP_START://正确的状态
break;
case 0x38://TW_MT_ARB_LOST:
goto begin;
default:
goto error;
}
TWDR = sla | TW_READ;//发送SLA+R
TWCR = _BV(TWINT) | _BV(TWEN);//清TWINT,开始传输
while((TWCR & _BV(TWINT))==0x0);//等待传输完毕
switch(twst = (TWSR&0xf8)) //twst=16
{
case 0x40://TW_MR_SLA_ACK:
break;
case 0x48://TW_MR_SLA_NACK://器件忙,有可能处于内部写周期
goto restart;
case 0x38://TW_MR_ARB_LOST:
goto begin;
default:
goto error;
}
TWCR = _BV(TWINT) | _BV(TWEN) ;//清TWINT,开始传输
while((TWCR & _BV(TWINT))==0x0);//等待传输完毕
while((TWCR & _BV(TWINT))==0x0);//等待传输完毕
while((TWCR & _BV(TWINT))==0x0);//等待传输完毕
switch(twst = (TWSR&0xf8))
{
case 0x58://TW_MR_DATA_NACK:
rv = TWDR;
break;
default:
goto error;
}
quit:
TWCR = _BV(TWINT) | _BV(TWSTO) | _BV(TWEN);//发送停止信号
return rv;
error:
rv=0x00;
goto quit;
}
uchar twi_read_str( uchar sla,uchar address,uchar *p,uchar len) //读字符串,
{
uchar i,twst,n=0x0,rv=0xff;
restart:
if(n++>=max)
goto error;
begin:
TWCR = _BV(TWINT) | _BV(TWSTA) | _BV(TWEN);//发送开始信号
while((TWCR & _BV(TWINT))==0x0);//等待发送完毕
switch(twst = (TWSR&0xf8))
{
case 0x10://TW_REP_START://有可能出现
case 0x08://TW_START:
break;
case 0x38://TW_MT_ARB_LOST:
goto begin;
default:
goto error;
}
TWDR = sla | TW_WRITE;//发送SLA+W
TWCR = _BV(TWINT) | _BV(TWEN);//清TWINT,开始传输
while((TWCR & _BV(TWINT))==0x0);//等待传输完毕
switch(twst = (TWSR&0xf8))
{
case 0x18://TW_MT_SLA_ACK:
break;
case 0x20://TW_MT_SLA_NACK://器件忙,有可能处于内部写周期
goto restart;
case 0x38://TW_MT_ARB_LOST:
goto begin;
default:
goto error;
}
/* TWDR = address>>8;//传输地址高8位
TWCR = _BV(TWINT) | _BV(TWEN);//清TWINT,开始传输
while((TWCR & _BV(TWINT))==0x0);//等待传输完毕
switch((twst = TW_STATUS))
{
case TW_MT_DATA_ACK:
break;
case TW_MT_DATA_NACK:
goto quit;
case TW_MT_ARB_LOST:
goto begin;
default:
goto error;
}*/
TWDR = address;//传输地址低8位
TWCR = _BV(TWINT) | _BV(TWEN);//清TWINT,开始传输
while((TWCR & _BV(TWINT))==0x0);//等待传输完毕
switch(twst = (TWSR&0xf8))
{
case 0x28://TW_MT_DATA_ACK:
break;
case 0x30://TW_MT_DATA_NACK:
goto quit;
case 0x38://TW_MT_ARB_LOST:
goto begin;
default:
goto error;
}
TWCR = _BV(TWINT) | _BV(TWSTA) | _BV(TWEN);//发送(重新)开始信号
while((TWCR & _BV(TWINT))==0x0);//等待发送完毕
switch(twst =(TWSR&0xf8))
{
case 0x10://TW_REP_START://正确的状态
break;
case 0x38://TW_MT_ARB_LOST:
goto begin;
default:
goto error;
}
TWDR = sla | TW_READ;//发送SLA+R
TWCR = _BV(TWINT) | _BV(TWEN);//清TWINT,开始传输
while((TWCR & _BV(TWINT))==0x0);//等待传输完毕
switch(twst = (TWSR&0xf8))
{
case 0x40://TW_MR_SLA_ACK:
break;
case 0x48://TW_MR_SLA_NACK://器件忙,有可能处于内部写周期
goto restart;
case 0x38://TW_MR_ARB_LOST:
goto begin;
default:
goto error;
}
for(i=0;i<len;i++)
{
if(i==(len-1))
{
TWCR = _BV(TWINT) | _BV(TWEN) ;//清TWINT,开始传输(无应答)
}
else
{
TWCR = _BV(TWINT) | _BV(TWEN) | _BV(TWEA) ;//清TWINT,开始传输(有应答)
}
while((TWCR & _BV(TWINT))==0x0);//等待传输完毕
switch(twst =(TWSR&0xf8))
{
case 0x58://TW_MR_DATA_NACK:
case 0x50://TW_MR_DATA_ACK:
*p = TWDR;
p++;
break;
default:
goto error;
}
}
quit:
TWCR = _BV(TWINT) | _BV(TWSTO) | _BV(TWEN);//发送停止信号
return rv;
error:
rv=0x00;
goto quit;
}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -