|
以下是一個(gè)24C02的存取函數(shù),可以正常使用,想請(qǐng)教一下如果是24C04以上的,內(nèi)部地址是10位二進(jìn)制的,超過了一次所能發(fā)送的8位數(shù)據(jù),這應(yīng)該怎么弄呢
單片機(jī)源程序如下:
#include <STC89C5xRC.H>
#include <intrins.h>
#define uint unsigned int
#define uchar unsigned char
sbit SDA=P2^7;
sbit SCL=P2^6;
sbit led=P1^6;
void delay(uint z)
{
uint x,y;
for(x=z;x>0;x--)
for(y=114;y>0;y--);
}
void start( )
{
SDA=1; //發(fā)送起始條件的數(shù)據(jù)信號(hào)
_nop_( );
SCL=1;
_nop_( ); //起始條件建立時(shí)間大于4.7us,延時(shí)
_nop_( );
_nop_( );
_nop_( );
_nop_( );
SDA=0; //發(fā)送起始信號(hào)
_nop_( ); //起始條件鎖定時(shí)間大于4μ
_nop_( );
_nop_( );
_nop_( );
_nop_( );
SCL=0; //鉗住I2C總線,準(zhǔn)備發(fā)送或接收數(shù)據(jù)
_nop_( );
_nop_( ); //SCL置低,準(zhǔn)備接收或發(fā)送數(shù)據(jù)
}
void stop( )
{
SDA=0; //發(fā)送結(jié)束條件的數(shù)據(jù)信號(hào)
_nop_( ); //發(fā)送結(jié)束條件的時(shí)鐘信號(hào)
SCL=1; //結(jié)束條件建立時(shí)間大于4μ
_nop_( );
_nop_( );
_nop_( );
_nop_( );
_nop_( );
SDA=1; //發(fā)送I2C總線結(jié)束信號(hào)
_nop_( );
_nop_( );
_nop_( );
_nop_( ); //延時(shí)保持4.7US以上
}
void write(uchar a)
{
uchar b,shu;
for(b=0;b<8;b++) //要傳送的數(shù)據(jù)長(zhǎng)度為8位
{
shu=a<<b; //把即將發(fā)送的數(shù)據(jù)的位移到最高位
if((shu&0x80)!=0) //判斷最高位是否為0
SDA=1; //不等于0說明最明當(dāng)前要發(fā)送的數(shù)據(jù)為1
else SDA=0; //否則數(shù)據(jù)為0
SCL=1; //置時(shí)鐘線為高,通知被控器開始接收數(shù)據(jù)位
_nop_( );
_nop_( ); //保證時(shí)鐘高電平周期大于4μ
_nop_( );
_nop_( );
_nop_( );
SCL=0;
}
_nop_( );
SDA=1; //8位發(fā)送完后釋放數(shù)據(jù)線,準(zhǔn)備接收應(yīng)答位
_nop_( );
SCL=1;
_nop_( );
}
bit ack( ) //等待應(yīng)答函數(shù)
{
bit h;
SDA=1;
_nop_( );
SCL=1; //SDA和SCL全部置高
_nop_( );
_nop_( );
_nop_( );
_nop_( );
SCL=0; //等待4.7US以上,把SCL置低
_nop_( );
_nop_( );
_nop_( );
_nop_( );
h=SDA; //等待4.7SU以上讀取SDA應(yīng)答信號(hào)
return h; //應(yīng)答成功則是0,沒有應(yīng)答則是1
}
uchar reade( ) //接收數(shù)據(jù)
{
uchar d,g;
SDA=1; //數(shù)據(jù)線置高電平
for(d=0;d<8;d++)
{
_nop_( );
_nop_( );
SCL=0;
_nop_( );
_nop_( );
_nop_( );
_nop_( ); //SCL低電平,數(shù)據(jù)變化
SCL=1;
_nop_( );
_nop_( ); //SCL高電平,數(shù)據(jù)穩(wěn)定
if(SDA==1)
g=(g<<1)|0x01; //如果讀到的數(shù)據(jù)是1就是最低位置1
else
g=g<<1; //否則讀到是0,直接左移1位(左移后右補(bǔ)0)
}
return g; //經(jīng)過8次讀取移位,把g返回
}
void main( )
{
start( ); //啟動(dòng)總線
write(0xa0); //器件地址(發(fā)送)
led=ack( ); //等待應(yīng)答
// led=~led;
write(0x03); //發(fā)送器件內(nèi)部地址
led=ack( ); //等待應(yīng)答
//led=~led;
write(0xfe); //發(fā)送第一組數(shù)據(jù)
ack( ); //等待應(yīng)答
write(0x35); //發(fā)送第二組數(shù)據(jù)(器件內(nèi)部地址指針自動(dòng)+1,不用重新指定地址)
ack( );
write(0xb2);
ack( );
write(0xc3);
ack( );
write(0x24);
ack( );
led=~led;
stop( ); //發(fā)送完成,停止總線
led=~led;
delay(100);
start( ); //讀。ㄩ_始-器件地址(發(fā))- 器件內(nèi)部地址 - 開始 - 器件地址(收)- 接收數(shù)據(jù) -發(fā)應(yīng)答或停止接收
write(0xa0);
ack( );
led=~led;
write(0x03);
ack( );
led=~led;
start( );
write(0xa1);
ack( );
led=~led;
P1=reade( );
stop( );
delay(1000);
start( );
write(0xa0);
ack( );
led=~led;
write(0x03);
ack( );
led=~led;
start( );
write(0xa1);
ack( );
led=~led;
P1=reade( );
stop( );
delay(1000);
start( );
write(0xa0);
ack( );
led=~led;
write(0x04);
ack( );
led=~led;
start( );
write(0xa1);
ack( );
led=~led;
P1=reade( );
stop( );
delay(1000);
start( );
write(0xa0);
ack( );
led=~led;
write(0x05);
ack( );
led=~led;
start( );
write(0xa1);
ack( );
led=~led;
P1=reade( );
stop( );
delay(1000);
start( );
write(0xa0);
ack( );
led=~led;
write(0x06);
ack( );
led=~led;
start( );
write(0xa1);
ack( );
led=~led;
P1=reade( );
stop( );
delay(1000);
start( );
write(0xa0);
ack( );
led=~led;
write(0x04);
ack( );
led=~led;
start( );
write(0xa1);
ack( );
led=~led;
P1=reade( );
stop( );
while(1);
}
|
|