//24LC256IIC通信程序
# include<pic.h>
# define uch unsigned char
# define unint unsigned int
# define SDA RC4
# define SCL RC3
uch ACK;
void delay(void) //延时
{
unint m;
for(m=0;m<0xffff;m++)
continue;
}
void start (void) // IIC开始
{
TRISC3=0; //置输出
TRISC4=0;
SDA=1;
asm("nop");
SCL=1; //在至少4u秒期间SDA从高电平到低电平
asm("nop");
asm("nop");
asm("nop");
SDA=0;
asm("nop");
asm("nop");
asm("nop");
SCL=0;
asm("nop");
asm("nop");
}
void stop(void) // IIC结束
{ TRISC3=0;
TRISC4=0; //置输出
SDA=0;
asm("nop");
SCL=1; //在至少4u秒期间SDA从低电平到高电平
asm("nop");
asm("nop");
asm("nop");
SDA=1;
asm("nop");
asm("nop");
asm("nop");
SCL=0;
asm("nop");
asm("nop");
}
uch check(void) // 检查应答信号
{
TRISC4=1;
SCL=0;
SCL=1;
if (SDA == 1)
{
ACK = 1;
}
else
{
ACK = 0;
}
SCL=0;
return(ACK);
}
void send(uch data) // 发送一个字节
{
uch bitcount=8; //发送8位
do
{
TRISC3=0; //置输出
TRISC4=0;
if((data&0x80)==0x80)
{
SDA=1; //发送 1
}
else
{
SDA=0; //发送 0
}
SCL=0; // 在时钟大于4u秒期间写数据
SCL=1;
asm("nop");
asm("nop");
asm("nop");
asm("nop");
asm("nop");
SCL=0;
data=data<<1;
bitcount--;
} while(bitcount);
TRISC4=1 ; //释放总线等待应答
asm("nop");
asm("nop");
asm("nop");
asm("nop");
asm("nop");
}
uch recive(void) //接受一个字节
{
uch temp1=0;
uch bitcount1=8;
TRISC4=1; //置输入
TRISC3=0;
do
{ SCL=0; //在时钟大于4u秒期间读数据
SCL=1;
asm("nop");
asm("nop");
if(SDA) //读 1
{
temp1=temp1|0x01;
}
else //读 0
{
temp1=temp1&0xfe;
}
SCL=0;
if(bitcount1-1)
{
temp1=temp1<<1;
}
bitcount1--;
}while(bitcount1);
return(temp1);
}
void ack(void) //发送继续读信号
{
SDA=0;
SCL=0;
SCL=1;
asm("nop");
asm("nop");
asm("nop");
asm("nop");
asm("nop");
SCL=0;
}
void nack(void) //停止继续读
{
SDA=1;
SCL=0;
SCL=1;
asm("nop");
asm("nop");
asm("nop");
asm("nop");
asm("nop");
SCL=0;
}
void wrtoROM(uch *data,unint address,uch num) //给24LC256写数据
{ unint i;
unint adrl=address%256; //低8位地址
unint adrh=address/256; //高8位地址
start(); //起始信号
send(0xa2); //写主控器识别地址,本人是a2
do{;
}while(check()); //等待应答
send(adrh); //送数据高8位地址
do{;
}while(check()); //等待应答
send(adrl); //送数据低8位地址
do
{
;
}while(check()); //等待应答
for(i=0;i<num;i++,data++)
{
send(*data); //发送数据
do{;
}while(check()); //等待应答
}
stop(); //停止
delay(); //延时,下次发数据
}
void rdfromROM(uch *pdata,unint address,uch num2) //从24LC256中读数据
{ unint adrl;
unint adrh;
uch j;
for(j=0;j<num2;j++,pdata++)
{
adrl=address%256; //地址低位
adrh=address/256; //地址高位
start(); //开始
send(0xa2); //写主控器识别地址(写),本人是a2
do{
;
}while(check()); //等待应答
send(adrh); //送高位
do
{
;
}while(check()); //等待应答
send(adrl); //送低位
do
{
;
}while(check()); //等待应答
start(); //开始读数据
send(0xa3); //写主控器识别地址(读)
do
{
;
}while(check()); //等待应答
*pdata=recive();
nack();
stop();
address=address+1; //指向下一个地址
}
}
main()
{ unint h,n;
uch m;
uch str[64]={0x5d,0x5d,0x32,0x18,0x6c,0x88,0xa0,0x1d,0x20,0x08};
SCL=1;
SDA=1;
PORTD=0XFF;
TRISD=0;
for(n=0;n<256;)
{
wrtoROM(str,n,64); //写一页的数据,根据24LC256一页是64个字节
n=n+64; //写下一页数据
}
for(h=0;h<64;h++) //数组清0
{
str[h]=0x21;
}
delay();
rdfromROM(str,0x02,64); //读从地址0开始的一页数据
while(1)
{
for(m=0;m<64;m++)
{
PORTD=str[m];
delay();
PORTD=0XFF;
delay();
}
}
}