當(dāng)前位置:首頁(yè) > 單片機(jī) > 單片機(jī)
[導(dǎo)讀]I2C總線(xiàn)是Philips公司提出的一種集成電路IC器件之間相連接的總線(xiàn)協(xié)議,其目的是使電子系統(tǒng)(不只 限于單片機(jī)系統(tǒng))各個(gè)IC器件之間的連線(xiàn)變得容易。因?yàn)槭褂脗鹘y(tǒng)的并行總線(xiàn)在IC器件之間連接,往往會(huì)使得IC之間連線(xiàn)較多

I2C總線(xiàn)是Philips公司提出的一種集成電路IC器件之間相連接的總線(xiàn)協(xié)議,其目的是使電子系統(tǒng)(不只 限于單片機(jī)系統(tǒng))各個(gè)IC器件之間的連線(xiàn)變得容易。因?yàn)槭褂脗鹘y(tǒng)的并行總線(xiàn)在IC器件之間連接,往往會(huì)使得IC之間連線(xiàn)較多,顯得非常復(fù)雜。而I2C總線(xiàn) 則使IC器件之間只需SDA、SCL兩條連線(xiàn)就可以傳送數(shù)據(jù),因而十分方便。由于I2C在印刷體中不容易書(shū)寫(xiě)(需要上標(biāo)),所以實(shí)際書(shū)寫(xiě)時(shí),還常見(jiàn)到 IIC、I2C等書(shū)寫(xiě)方法,本文采用IIC的寫(xiě)法,敬請(qǐng)注意。關(guān)于IIC總線(xiàn)的知識(shí),請(qǐng)參閱相關(guān)書(shū)籍,此處不再做進(jìn)一步介紹。

下面我們用一個(gè)使用IIC總線(xiàn)連接器件的例子來(lái)簡(jiǎn)單說(shuō)明IIC總線(xiàn)的仿真。

例.EEPROM24C02是采用IIC接口的一種常用2Kbit(256×8bit)的存儲(chǔ)器。編寫(xiě)程序使用AT89C51的IO口模擬實(shí)現(xiàn)IIC總線(xiàn)協(xié)議進(jìn)行通信,并向24C02存儲(chǔ)器內(nèi)從字節(jié)0到字節(jié)FF寫(xiě)入數(shù)字0到FF。

51系列單片機(jī)本身沒(méi)有IIC接口,但一些本身具有IIC接口的單片機(jī)往往是高端產(chǎn)品,一方面價(jià)格不菲,另一方面我們的系統(tǒng)也沒(méi)有必要使用之。通常我們就使用軟件通過(guò)51系列單片機(jī)的IO口來(lái)模擬實(shí)現(xiàn)IIC總線(xiàn)通信。

本例事實(shí)上比較簡(jiǎn)單,但需要對(duì)IIC總線(xiàn)時(shí)序有較好的理解。源文件如下圖所示(采用C51語(yǔ)言編寫(xiě)):







在Keil中編輯好源文件以后,接下來(lái)就可以建立工程文件并生成相應(yīng)的源代碼了,然后我們來(lái)繪制電路圖。
此例的電路圖極其簡(jiǎn)單。只需兩個(gè)IC,即AT89C51和24C02C,和兩個(gè)上拉電阻,而且上拉電阻還可以省略。至于連接,就更為簡(jiǎn)單了。最后得到繪制好的電路圖如下圖所示:



繪制好電路圖,我們就可以將前面剛剛生成的程序源代碼裝入單片機(jī)了,裝入以后,下面我們就可以來(lái)進(jìn)行仿真了。

首先點(diǎn)擊仿真按鈕,系統(tǒng)沒(méi)有什么反映,只有高低電平變化的顏色。我們要想查看結(jié)果,還要用前文中仿真擴(kuò)展 RAM存儲(chǔ)器的方法,先點(diǎn)擊暫停,然后點(diǎn)擊“Debug”菜單下的“I2C Memory Internal Memory – U2”子菜單來(lái)打開(kāi)U2即EEPROM存儲(chǔ)器24C02C的內(nèi)容窗口“I2C Memory Internal Memory – U2”,然后我們就看到了其中的內(nèi)容,也就是我們仿真程序的結(jié)果。如下圖所示:



從圖中我們能清楚地看到我們的仿真結(jié)果,程序完全正確地執(zhí)行了我們的命令。

當(dāng)然,如果你過(guò)早地點(diǎn)擊了暫停按鈕,那么你得到的結(jié)果可能和上圖略有不同,那可能是因?yàn)槌绦蛏形磮?zhí)行完畢。此時(shí)你可以繼續(xù)點(diǎn)擊運(yùn)行按鈕,或者點(diǎn)擊單步按鈕來(lái)仔細(xì)查看程序執(zhí)行過(guò)程中24C02C存儲(chǔ)器內(nèi)容的改變情況。


完整代碼如下:

/*----------------------------------------------------------------

Acess the eeprom--24c04

----------------------------------------------------------------*/

#include


#ifndef INT8U

#define INT8U unsigned char

#endif


#ifndef INT8S

#define INT8S signed char

#endif


#ifndef INT16U

#define INT16U unsigned int

#endif


#define I2C_DELAY; _nop_();_nop_();_nop_();_nop_();_nop_(); // >=4.7uS


//----------------------------------------------------------------

// delay 100us

//----------------------------------------------------------------

void mDelay(INT8U k)

{

INT16U i ;


for(; k>0; k--)

{

for(i=0; i<93; i++)

;

}

}




//----------------------------------------------------------------

//OK

//----------------------------------------------------------------

void I2C_Start(void)

{

SDA = 1;

I2C_DELAY;


SCL = 1;

I2C_DELAY;


SDA = 0;

I2C_DELAY;

I2C_DELAY;

}




//----------------------------------------------------------------

//OK

//----------------------------------------------------------------

void I2C_Stop(void)

{

SDA = 0 ;

I2C_DELAY;


SCL = 1 ;

I2C_DELAY;


SDA = 1 ;

I2C_DELAY;

I2C_DELAY;

}




//----------------------------------------------------------------

//

//----------------------------------------------------------------

void sendAck(void)

{

SCL = 0;

I2C_DELAY;


SDA = 0;

I2C_DELAY;


SCL = 1;

I2C_DELAY;


}



//----------------------------------------------------------------

//

//----------------------------------------------------------------

void sendNoAck(void)

{

SCL = 0;

I2C_DELAY;


SDA = 1;

I2C_DELAY;


SCL = 1;

I2C_DELAY;


}



//----------------------------------------------------------------

// 0 = noACK; 1 = ACK ;

//----------------------------------------------------------------

bit checkAck()

{

bit tempbit;

/*發(fā)送完一個(gè)字節(jié)后檢驗(yàn)設(shè)備的應(yīng)答信號(hào)*/

SDA = 1;

I2C_DELAY;


SCL = 0;

I2C_DELAY;


tempbit = SDA;


SCL = 1;

I2C_DELAY;


if(tempbit==1)

{

return 0; //noACK

}

else

{

return 1; //ACK

}

}




//----------------------------------------------------------------

//OK

// a positive clock edge clock a bit into the ROM

//----------------------------------------------------------------

void writeByte(INT8U datum)

{

INT8U bitCnt = 0 ;


for(bitCnt=0; bitCnt<8; bitCnt++)

{

SCL = 0 ;

I2C_DELAY;


if ((datum&0x80) == 0x80) //if the MSb is 1

SDA = 1 ;

else

SDA = 0 ;

I2C_DELAY;


SCL = 1 ;

I2C_DELAY;


datum<<=1 ;

}


}




//----------------------------------------------------------------

//OK

//----------------------------------------------------------------

INT8U readByte(void)

{

bit tempbit = 1 ;

INT8U temp = 0 ;

INT8U bitCnt ;


SDA = 1 ; // release the bus,ready to receive byte??????????????

I2C_DELAY;


for(bitCnt=0; bitCnt<8; bitCnt++)

{

SCL = 0; //?????????????????????????huan???????????????

I2C_DELAY;


tempbit = SDA ;

if (tempbit)

temp |= 0x01 ;

else

temp &= 0xfe ;


SCL = 1 ;

I2C_DELAY;


if(bitCnt<7)

temp <<= 1 ;


}


return(temp) ;

}




/*~~~~~~~~~~~~~~~~~~~~~~~ API ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~*/


/*-----------------------------------------------------------------

write some bytes to sequential address

-----------------------------------------------------------------*/

void writeToROM(INT8U datum[], INT8U address, INT8U num)

{

bit tempbit ;

INT8U i ;

INT8U *datum_P ;

datum_P = datum ;


I2C_Start() ;


writeByte(0xa0) ;

tempbit = checkAck();


writeByte(address) ;

tempbit = checkAck();


for(i=0; i

{

writeByte(*(datum_P+i)) ;



if(!checkAck())

{

I2C_Stop() ;

mDelay(100) ;

}

}


I2C_Stop() ;

}




/*-----------------------------------------------------------------

read some bytes from ROM`s sequential address

-----------------------------------------------------------------*/

void readFromROM(INT8U datum[], INT8U address, INT8U num)

{

bit tempbit ;

INT8U i ;

INT8U *datum_P ;


datum_P = datum;


I2C_Start() ;


writeByte(0xa0) ;

tempbit = checkAck();


writeByte(address) ;

tempbit = checkAck();


I2C_Start() ;

writeByte(0xa1) ;

tempbit = checkAck();


for(i=0; i

{

*(datum_P+i) = readByte() ;


if(i!=num-1)

{

sendAck() ;

}

else

{

sendNoAck() ;

}

}


I2C_Stop() ;

}




/*-----------------------------------------------------------------

wirte one byte to ROM --random write

-----------------------------------------------------------------*/

void writeOneByte(INT8U addr, INT8U datum)

{

bit tempbit ;

/*write a byte to mem*/


I2C_Start();


writeByte(0xa0);

tempbit = checkAck();


writeByte(addr); /*address*/

tempbit = checkAck();


writeByte(datum); /*the data*/


tempbit = checkAck();


I2C_Stop();

mDelay(100) ;


}




/*-----------------------------------------------------------------

read one byte from rom --random read

-----------------------------------------------------------------*/

INT8U readOneByte(INT8U addr)

{

bit tempbit = 1;

INT8U mydata;

/*read a byte from mem*/


I2C_Start();


writeByte(0xa0);

tempbit = checkAck();


writeByte(addr); /*address*/

tempbit = checkAck();


I2C_Start();


writeByte(0xa1);

tempbit = checkAck();


mydata = readByte();

tempbit = checkAck();


return (mydata) ;


I2C_Stop();

}

本站聲明: 本文章由作者或相關(guān)機(jī)構(gòu)授權(quán)發(fā)布,目的在于傳遞更多信息,并不代表本站贊同其觀(guān)點(diǎn),本站亦不保證或承諾內(nèi)容真實(shí)性等。需要轉(zhuǎn)載請(qǐng)聯(lián)系該專(zhuān)欄作者,如若文章內(nèi)容侵犯您的權(quán)益,請(qǐng)及時(shí)聯(lián)系本站刪除。
換一批
延伸閱讀

9月2日消息,不造車(chē)的華為或?qū)⒋呱龈蟮莫?dú)角獸公司,隨著阿維塔和賽力斯的入局,華為引望愈發(fā)顯得引人矚目。

關(guān)鍵字: 阿維塔 塞力斯 華為

倫敦2024年8月29日 /美通社/ -- 英國(guó)汽車(chē)技術(shù)公司SODA.Auto推出其旗艦產(chǎn)品SODA V,這是全球首款涵蓋汽車(chē)工程師從創(chuàng)意到認(rèn)證的所有需求的工具,可用于創(chuàng)建軟件定義汽車(chē)。 SODA V工具的開(kāi)發(fā)耗時(shí)1.5...

關(guān)鍵字: 汽車(chē) 人工智能 智能驅(qū)動(dòng) BSP

北京2024年8月28日 /美通社/ -- 越來(lái)越多用戶(hù)希望企業(yè)業(yè)務(wù)能7×24不間斷運(yùn)行,同時(shí)企業(yè)卻面臨越來(lái)越多業(yè)務(wù)中斷的風(fēng)險(xiǎn),如企業(yè)系統(tǒng)復(fù)雜性的增加,頻繁的功能更新和發(fā)布等。如何確保業(yè)務(wù)連續(xù)性,提升韌性,成...

關(guān)鍵字: 亞馬遜 解密 控制平面 BSP

8月30日消息,據(jù)媒體報(bào)道,騰訊和網(wǎng)易近期正在縮減他們對(duì)日本游戲市場(chǎng)的投資。

關(guān)鍵字: 騰訊 編碼器 CPU

8月28日消息,今天上午,2024中國(guó)國(guó)際大數(shù)據(jù)產(chǎn)業(yè)博覽會(huì)開(kāi)幕式在貴陽(yáng)舉行,華為董事、質(zhì)量流程IT總裁陶景文發(fā)表了演講。

關(guān)鍵字: 華為 12nm EDA 半導(dǎo)體

8月28日消息,在2024中國(guó)國(guó)際大數(shù)據(jù)產(chǎn)業(yè)博覽會(huì)上,華為常務(wù)董事、華為云CEO張平安發(fā)表演講稱(chēng),數(shù)字世界的話(huà)語(yǔ)權(quán)最終是由生態(tài)的繁榮決定的。

關(guān)鍵字: 華為 12nm 手機(jī) 衛(wèi)星通信

要點(diǎn): 有效應(yīng)對(duì)環(huán)境變化,經(jīng)營(yíng)業(yè)績(jī)穩(wěn)中有升 落實(shí)提質(zhì)增效舉措,毛利潤(rùn)率延續(xù)升勢(shì) 戰(zhàn)略布局成效顯著,戰(zhàn)新業(yè)務(wù)引領(lǐng)增長(zhǎng) 以科技創(chuàng)新為引領(lǐng),提升企業(yè)核心競(jìng)爭(zhēng)力 堅(jiān)持高質(zhì)量發(fā)展策略,塑強(qiáng)核心競(jìng)爭(zhēng)優(yōu)勢(shì)...

關(guān)鍵字: 通信 BSP 電信運(yùn)營(yíng)商 數(shù)字經(jīng)濟(jì)

北京2024年8月27日 /美通社/ -- 8月21日,由中央廣播電視總臺(tái)與中國(guó)電影電視技術(shù)學(xué)會(huì)聯(lián)合牽頭組建的NVI技術(shù)創(chuàng)新聯(lián)盟在BIRTV2024超高清全產(chǎn)業(yè)鏈發(fā)展研討會(huì)上宣布正式成立。 活動(dòng)現(xiàn)場(chǎng) NVI技術(shù)創(chuàng)新聯(lián)...

關(guān)鍵字: VI 傳輸協(xié)議 音頻 BSP

北京2024年8月27日 /美通社/ -- 在8月23日舉辦的2024年長(zhǎng)三角生態(tài)綠色一體化發(fā)展示范區(qū)聯(lián)合招商會(huì)上,軟通動(dòng)力信息技術(shù)(集團(tuán))股份有限公司(以下簡(jiǎn)稱(chēng)"軟通動(dòng)力")與長(zhǎng)三角投資(上海)有限...

關(guān)鍵字: BSP 信息技術(shù)
關(guān)閉
關(guān)閉