我用MSP430模拟时序读写24C32不成功。
程序如下:
#include "MSP430G2553.h"
#define uchar unsigned char
#define uint unsigned int
//sbit sda=P1^1;//;模拟I2C 数据
// sbit scl=P1^0;//;模拟I2C 时钟
#define sda_1 P1OUT|=BIT3
#define sda_0 P1OUT&=~BIT3
#define scl_1 P1OUT|=BIT1
#define scl_0 P1OUT&=~BIT1
unsigned char data[3];
void delay1(uint z)//延时为 1ms
{
uchar x,x1;
for(;z>0;z--)
{
for(x=0;x<114;x++)
{
for(x1=0;x1<96;x1++);
}
}
}
void delay()//5us延时
{
unsigned char i,j;
for(i=0;i<96;i++)
{
j=j;
j=j;
j=j;
}
}
void star()//开始
{
sda_1;
delay();//5us延时
scl_1;
delay();//5us延时
sda_0;
delay();//5us延时
}
void stop()//停止
{
sda_0;
delay();//5us延时
scl_1;
delay();//5us延时
sda_1;
delay();//5us延时
}
void ack()//应答
{
uchar z=0;
P1DIR&=~BIT3;
P1REN|=BIT3;
delay();
delay();
//
while((P1IN&0X08)&&(z<200))z++;//条件判断, sda=1,则没有应答。如果没有应答则延时:z<50,z++;后返回
scl_0;
delay();//5us延时
P1DIR|=BIT3;
P1REN&=~BIT3;
delay();
delay();
//
}
///写一个数据函数
//器件写地址 slave_write_address
//字节高地址 byte_High_address
//字节低地址 byte_Low_address
//待写入数据 data_data
void write(uchar slave_write_address,uchar byte_High_address,uchar
byte_Low_address,uchar data_data)//写一个数据
{
uchar temp,temp1,i,ii;
star();//开始
for(ii=0;ii<4;ii++)//根据 24CXX文档资料,和时序图,按顺序送:器件写地址,字节地址,数据
{
if(ii==0)
{
temp=slave_write_address;//送 器件写地址
temp1=slave_write_address;
}
else if(ii==1)
{
temp=byte_High_address;//送 字节高地址
temp1=byte_High_address;
}
else if(ii==2)
{
temp=byte_Low_address;//送 字节低地址
temp1=byte_Low_address;
}
else if(ii==3)
{
temp=data_data;//送 数据
temp1=data_data;
}
for(i=0;i<8;i++)
{
scl_0;
delay();//5us延时
temp=temp1;
temp=temp&0x80;// 相 与 后,把不相关的位清零
if(temp==0x80)//根据前面 相 与 后,判断 temp是否等于0x80,是则该位为 1
sda_1;
else
sda_0;
delay();//5us延时
scl_1;
delay();//5us延时
scl_0;
delay();//5us延时
temp1=temp1<<1;//向左移出1位
}
sda_1;
delay();//5us延时
scl_1;
delay();//5us延时
ack();
}
stop();//停止
}
///读一个数据函数
//器件写地址 slave_write_address
//器件读地址 slave_read_address
//字节高地址 byte_High_address
//字节低地址 byte_Low_address
//读出的数据 data_data
unsigned char read(uchar slave_write_address,uchar byte_High_address,uchar byte_Low_address,uchar
slave_read_address)//读一个数据
{
uchar temp,temp1,i,ii,x,data_data;
star();//开始
for(ii=0;ii<4;ii++)//根据 24CXX文档资料,和时序图,按顺序送:器件写地址,字节地址,器件读地址
{
if(ii==0)
{
temp=slave_write_address;//送 器件写地址
temp1=slave_write_address;
}
else if(ii==1)
{
temp=byte_High_address;//送 字节高地址
temp1=byte_High_address;
}
else if(ii==2)
{
temp=byte_Low_address;//送 字节低地址
temp1=byte_Low_address;
}
else if(ii==3)
{
star();//开始
temp=slave_read_address;//送 器件读地址
temp1=slave_read_address;
}
for(i=0;i<8;i++)//开始读数据
{
scl_0;
delay();//5us延时
temp=temp1;
temp=temp&0x80;// 相 与 后,把不相关的位清零
if(temp==0x80)//根据前面 相 与 后,判断 temp是否等于0x80,是则该位为 1
sda_1;
else
sda_0;
delay();//5us延时
delay();//5us延时
scl_1;
delay();//5us延时
scl_0;
delay();//5us延时
temp1=temp1<<1;//向左移出1位
}
sda_1;
delay();//5us延时
scl_1;
delay();//5us延时
delay();//5us延时
ack();//应答
}
delay();
for(x=0;x<8;x++)
{
data_data=data_data<<1;//向左移入1位
//sda=1;
P1DIR&=~BIT3;
P1REN|=BIT3;
delay();//5us延时
delay();//5us延时
scl_0;
delay();//5us延时
scl_1;
delay();//5us延时
if(P1IN&0X08)//判断 数据线是否是高电平
data_data|=0x01;//把读到的数据 或 0X01
//else
//data_data|=0x00;
}
ack();//应答
stop();//停止
P1DIR|=BIT3;
P1REN&=~BIT3;
return data_data;//返回读到的数据
}
int main( void )
{
// Stop watchdog timer to prevent time out reset
WDTCTL = WDTPW + WDTHOLD;
P1SEL&=~(BIT1+BIT3);
P1DIR|=BIT0+BIT1+BIT3;
//write(0xa0,0x00,0x01,0x66);//向器件写一个数据:
//(0xa0 是器件写地址;0x00 是字节高地址;0x01 是字节低地址;0x66 是待写入的数据)
//delay1(5);//写与读的时间间隔应大于5ms,取决于器件 24C02的响应速度
//向器件读一个数据
//把读出的数据送 P1口显示
//data[0]=read(0xa0,0x00,0x01,0xa1);//向器件读一个数据:
//(0xa0 是器件写地址;0x00 是字节高地址;0x01 是字节低地址;0xa1 是器件读地址)
while(1)
{
data[0]=read(0xa0,0x00,0x02,0xa1);//向器件读一个数据: ;
delay1(1);
}
//return 0;
}
请高手指教,谢谢!下面贴出波形图。
|