久久ER99热精品一区二区-久久精品99国产精品日本-久久精品免费一区二区三区-久久综合九色综合欧美狠狠

新聞中心

EEPW首頁 > 嵌入式系統 > 設計應用 > 模擬I2C程序設計

模擬I2C程序設計

作者: 時間:2016-11-17 來源:網絡 收藏
#include

#include

本文引用地址:http://cqxgywz.com/article/201611/315483.htm

#define uchar unsigned char
#define DELAY5US _nop_(); _nop_(); _nop_(); _nop_(); //延時5us
#define WriteDeviceAddress 0xa0 //寫I2C外圍器件的尋址地址
#define ReadDeviceAddress 0xa1 //讀I2C外圍器件的尋址地址
//注:寫I2C外圍器件的尋址地址為器件的地址,讀為器件地址加1
uchar E0; //非應答信號標志位
uchar NACK=0; //錯誤標志位

//**************************修改硬件時要修改的部分********************************

sbit SDA = P1^0; //模擬數據線
sbit SCL = P1^1; //模擬時鐘線

void Start(void) //啟動I2C總線子函數
{
SDA=1;
SCL=1;
DELAY5US
SDA=0;
DELAY5US
SCL=0;
}

void Stop(void) //停止I2C總線數據傳送子函數
{
SDA=0;
SCL=1;
DELAY5US
SDA=1;
DELAY5US
SCL=0;
}

void Ack(void) //發送應答位子程序
{
SDA=0;
SCL=1;
DELAY5US
SCL=0;
SDA=1;
}

void NoAck(void) //發送非應答位子程序
{
SDA=1;
SCL=1;
DELAY5US
SCL=0;
SDA=0;
}

void TestAck(void) //應答位檢查子程序,若檢測不到非應答信號,置位E0
{
SDA=1;
SCL=1;
E0=0;
_nop_(); //短延時
if(SDA==1) //如果SDA為1,表明非應答,置位非應答標志E0
E0=1;
SCL=0;
}

void Write8Bit(uchar n) //寫一個字節數據子程序,n為待發送的數據
{
uchar i;
for(i=8;i>0;i--)
{
SDA=(bit)(n&0x80);
SCL=1;
DELAY5US
SCL=0;
SDA=0;
n=n<<1;
}
}

void WriteI2C(uchar *Wdata,uchar RomAddress,uchar number) // 寫n個字節數據子程序
{ //*Wdata為待發送數據的首地址,RomAddress為待I2C外圍器件的數據寫入首地址,number為寫字節的個數
Start(); //啟動
Write8Bit(WriteDeviceAddress); //寫入器件的尋址地址
TestAck(); //應答檢查
if(E0==1)
{
NACK=1; //若非應答表明器件錯誤或已壞,置錯誤標志位NACK
return;
}
Write8Bit(RomAddress); //寫入I2C器件的數據存儲首地址
TestAck(); //應答檢查
if(E0==1)
{
NACK=1; //若非應答表明器件錯誤或已壞,置錯誤標志位NACK
return;
}
for(;number!=0;number--) //循環,逐個字節發送
{
Write8Bit(*Wdata); //寫一個字節
TestAck(); //應答檢查
if(E0==1)
{
NACK=1; //若非應答表明器件錯誤或已壞,置錯誤標志位NACK
return;
}
Wdata++; //指針增加,指向下一個數據
}
Stop(); //全部發送完則停止
}

uchar Read8Bit(void) //讀一個字節數據子程序
{
uchar temp,rbyte=0;
for(temp=8;temp>0;temp--)
{
SDA=1;
SCL=1;
_nop_(); //短延時
rbyte=rbyte<<1;
rbyte=rbyte|((uchar)(SDA));
SCL=0;
}
return(rbyte);
}

void ReadI2C(uchar *RamAddress,uchar RomAddress,uchar bytes) // 讀n個字節數據子程序
{ //RamAddress為接收數據緩沖區的首地址,RomAddress為待I2C外圍器件的數據讀取首地址,bytes為寫字節的個數
Start(); //啟動
Write8Bit(WriteDeviceAddress); //寫入器件的尋址地址
TestAck(); //應答檢查
if(E0==1)
{
NACK=1; //若非應答表明器件錯誤或已壞,置錯誤標志位NACK
return;
}
Write8Bit(RomAddress); //寫入I2C器件內部數據的讀取首地址
TestAck(); //應答檢查
if(E0==1)
{
NACK=1; //若非應答表明器件錯誤或已壞,置錯誤標志位NACK
return;
}
Start(); //重新啟動
Write8Bit(ReadDeviceAddress); //寫入器件的尋址地址
TestAck(); //應答檢查
if(E0==1)
{
NACK=1; //若非應答表明器件錯誤或已壞,置錯誤標志位NACK
return;
}
while(bytes!=1) //循環讀入字節數據
{
*RamAddress=Read8Bit(); //讀入一個字節
Ack(); //應答
RamAddress++; //地址指針遞增
bytes--; //待讀入數據個數遞
}
*RamAddress=Read8Bit(); //讀入最后一個字節數據
NoAck(); //非應答
Stop(); //停止
}



關鍵詞: 模擬I2C程序設

評論


技術專區

關閉