📄 slaver_1._c
字号:
/* 段传辉 2008 1.21
TWI 从机的查询和中断接收 依靠广播0X00地址
ICCAVR6.31A chuanhuibh@sina.com
*/
#include"iom8v.h"
#include"UART.h
#include"delay.h"
#define uchar unsigned char
#define STATUS (TWSR&0xf8)
#define SLA_W 0x32
#define SLA_R 0x33
#define TWI_ADDRESS 0x32
#define START 0x08
#define RE_START 0x10
#define MT_SLA_WRITE_ACK 0x18
#define MT_SLA_READ_ACK 0x40
#define MT_DATA_ACK 0x28
#define MT_READ_ACK 0x58
#define TW_SR_DATA_ACK 0x80
void Start(void)
{
TWCR=(1<<TWINT)|(1<<TWSTA)|(1<<TWEN);
while(!(TWCR&(1<<TWINT)));
}
void Stop(void)
{
TWCR=(1<<TWINT)|(1<<TWSTO)|(1<<TWEN);
}
void Load(uchar i)
{
TWDR=i;
TWCR=(1<<TWINT)|(1<<TWEN);
while(!(TWCR&(1<<TWINT)));
}
void Get(unsigned char *d)
{
TWCR=(1<<TWINT)|(1<<TWEN);
while(!(TWCR&(1<<TWINT)));
*d= TWDR;
}/**/
void ERROR(uchar state)
{Stop();
}
/*写一个字节data,成功则返回1,否则
返回0*/
uchar WriteByte(uchar data)
{
//启动I2C
Start();
if(STATUS!=START) {ERROR(STATUS);return 0;}
//发送从机地址(写),等待回应, 错误检测
Load(SLA_W);
if(STATUS!=MT_SLA_WRITE_ACK) {ERROR(STATUS);return 0;}
/*
//发送EEPROM地址,等待回应,错误检测
Load(addr);
if(STATUS!=MT_DATA_ACK) {ERROR(STATUS);return 0;}
*/
//发送数据,等待回应,错误检测
Load(data);
if(STATUS!=MT_DATA_ACK) {ERROR(STATUS);return 0;}
Stop();
return 1;//发送成功,返回1;
}
unsigned char ReadByte(unsigned char addr,
unsigned char *p_data)
{
//启动I2C
Start();
if(STATUS!=START) {ERROR(STATUS);return 0;}
//发送从机地址(写),等待回应, 错误检测
Load(SLA_W);
if(STATUS!=MT_SLA_WRITE_ACK) {ERROR(STATUS);return 0;}
//发送EEPROM地址,等待回应,错误检测
Load(addr);
if(STATUS!=MT_DATA_ACK) {ERROR(STATUS);return 0;}
//再次启动I2C
Start();
if(STATUS!=RE_START) {ERROR(STATUS);return 0;}
//发送从机地址(读),等待回应, 错误检测
Load(SLA_R);
if(STATUS!=MT_SLA_READ_ACK) {ERROR(STATUS);return 0;}
//读取I2C数据
Get(p_data);
if(STATUS!=MT_READ_ACK) {ERROR(STATUS);return 0;}
//发送Stop,结束读I2C操作。
Stop();
return 1;
}/**/
void Init_Io(void)
{
DDRC&=~((1<<PC4)&(1<<PC5)&(1<<PC2));
PORTC|= (1<<PC4)|(1<<PC5)|(1<<PC2);
//TWI接口初始化,从器件模式
TWAR=TWI_ADDRESS | (1<<TWGCE);
TWCR=(1<<TWEA) | (1<<TWEN)|(1<<TWIE);
asm("SEI");
}
void main()
{
// uchar temp1,temp2;
Init_Io();
uart_init();
puts("串口正常工作");
while(1)
{ /*
TWCR=(1<<TWINT)|(1<<TWEA) | (1<<TWEN); //启动一次接收
while((TWCR&(1<<TWINT))==0); //等待有数据被接收
//Delay_nms(100);
temp1=STATUS;
temp2=TWDR;
//putchar(temp1);
if(temp1==0x90)
{
puts("接受到:");
putchar(temp2);
}
*/
}
}
#pragma interrupt_handler TWI_ISR:18
void TWI_ISR(void)
{
uchar temp1,temp2;
temp1=STATUS;
temp2=TWDR;
if(temp1==0x90)
{
puts("接受到:");
putchar(temp2);
}
TWCR=(1<<TWINT)|(1<<TWEA) | (1<<TWEN)|(1<<TWIE); //启动一次接收
}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -