**********************************************
耀攜I2C最唗 winavr20050214
***********************************************/
# define F_CPU 4000000UL
ㄒi nclude <avr/io.h>
ㄒi nclude <avr/delay.h>
#define cbi(sfr, bit) (_SFR_BYTE(sfr) &= ~_BV(bit))
#define sbi(sfr, bit) (_SFR_BYTE(sfr) |= _BV(bit))
#define bit_is_set(sfr, bit) (_SFR_BYTE(sfr) & _BV(bit))
//DDR PORT
//0 0 in,high
//0 1 in,r
//1 0 out=0
//1 1 out=1
#define sda 0
#define scl 1
#define I2C DDRB
#define I2C_read PINB
#define I2C_set PORTB
#define Set_SDA cbi(I2C,sda)
#define Cls_SDA sbi(I2C,sda)
#define Set_SCL cbi(I2C,scl)
#define Cls_SCL sbi(I2C,scl)
#define SDA_High bit_is_set(I2C_read,sda)
//function declaration
void I2C_Delay(void);
void I2C_Start(void);
void I2C_Stop(void);
unsigned char I2C_Write(unsigned char wb);
unsigned char I2C_Read(unsigned char bEnd);
//*****************************************************
//delay 100us
//*****************************************************
void I2C_Delay(void)
{
_delay_us(100);
}
//*****************************************************
//i2c init
//*****************************************************
void I2C_init(void)
{
//DDR PORT
//0 0 in,high
//0 1 in,r
//1 0 out=0
//1 1 out=1
cbi(I2C_set,sda); //sda=1
cbi(I2C,sda); //sda in
cbi(I2C_set,scl); //scl=1;
cbi(I2C,scl); //scl in
}
//*****************************************************
//i2c start
//*****************************************************
void I2C_Start(void)
{
Cls_SCL;
I2C_Delay();
Set_SDA;
I2C_Delay();
Set_SCL;
I2C_Delay();
Cls_SDA;
I2C_Delay();
Cls_SCL;
I2C_Delay();
}
//*****************************************************
//i2c stop
//*****************************************************
void I2C_Stop(void)
{
Cls_SDA;
I2C_Delay();
Set_SCL;
I2C_Delay();
Set_SDA;
I2C_Delay();
Set_SCL;
I2C_Delay();
}
//*****************************************************
//I2C_Write
//*****************************************************
unsigned char I2C_Write(unsigned char wb)
{
unsigned char i,ack=0;
for(i=0;i<8;i++)
{
if( wb&0x80 ) Set_SDA;
else Cls_SDA;
wb=wb<<1;
I2C_Delay();
Set_SCL;
I2C_Delay();
Cls_SCL;
if(i!=7) I2C_Delay();
}
Set_SDA; //release sda line
I2C_Delay();
Set_SCL;
I2C_Delay();
if( SDA_High ) ack=1; //ack error
Cls_SCL;
I2C_Delay();
return ack;
}
//*****************************************************
//I2C_Read
//*****************************************************
unsigned char I2C_Read(unsigned char bEnd)
{
unsigned char i,mb;
Set_SDA; //release sda line
mb=0;
for(i=0;i<8;i++)
{
mb=mb<<1;
I2C_Delay();
Set_SCL;
I2C_Delay();
if( SDA_High ) mb++;
I2C_Delay();
Cls_SCL;
if(i!=7) I2C_Delay();
}
if( bEnd ) Set_SDA; //end read
else Cls_SDA; //ack
I2C_Delay();
Set_SCL;
I2C_Delay();
Cls_SCL;
I2C_Delay();
Set_SDA;
return mb;
}