標(biāo)題: I2C總線入門(PCF8591T和AT24C02的使用) [打印本頁]

作者: piaolin    時(shí)間: 2015-10-29 17:43
標(biāo)題: I2C總線入門(PCF8591T和AT24C02的使用)
1) 最近學(xué)習(xí)51單片機(jī),學(xué)到A/D,D/A轉(zhuǎn)換的時(shí)候發(fā)現(xiàn)我板子上的轉(zhuǎn)換芯片不是書上所講的ADC0804和DAC0832而是PCF8591T,看了一下它的數(shù)據(jù)手冊(cè),發(fā)現(xiàn)它并不是書上所說的并行傳輸數(shù)據(jù),是使用 I2C 總線傳輸?shù)。搞了兩天才搞懂,寫出來給大家分享一下,不足之處請(qǐng)務(wù)必不吝指出。



以上是I2C總線的簡單介紹。


就比如說AT24C02存儲(chǔ)芯片,和PCF8591數(shù)模模數(shù)轉(zhuǎn)換芯片都支持I2C端口。(如下圖)
         



2) 接下來看如何使用I2C總線進(jìn)行通信


以上是I2C總線通信的格式。
由上圖可以看出進(jìn)行通信需要以下幾個(gè)步驟
a.初始化I2C總線
就是把SDA和SCL都變成高電平。

[cpp] view plaincopyprint?


delay()為延時(shí)函數(shù)

[cpp] view plaincopyprint?




b.發(fā)送起始信號(hào)
就是保持SCL為高電平,而SDA從高電平降為低電平(這是I2C總線的規(guī)定,別問我為什么)

[cpp] view plaincopyprint?





c.發(fā)送地址字(芯片的硬件地址)


(8591的數(shù)據(jù)手冊(cè))
    前四位對(duì)同一種芯片來說是固定的,不同的芯片之間不同。就像pcf8591是1001而at24c02是1010
       
    接下來三位A0,A1,A2是可編程的三個(gè)地址位,這里說說的編程并不是通過軟件編程,而是把A0,A1,A2三個(gè)引腳接不同的電壓來確定數(shù)值。接VCC表示1,接GND表示0。為什么要有這三個(gè)呢?因?yàn)橛锌赡苣阍贗2C總線上“并聯(lián)”了不止一個(gè)相同的元件(比如說接了三個(gè)8591),那你如何來分辨你要操作的是哪一個(gè)芯片呢,就是通過設(shè)置A0,A1,A2的數(shù)值,來區(qū)別?删幊痰牡刂芬粋(gè)有三位,也就是說最多可以接8個(gè)相同的芯片在同一個(gè)I2C總線上。
    最后一位是 讀/寫 位,1為讀,0為寫。


@如何寫數(shù)據(jù)
寫數(shù)據(jù)只需要按照時(shí)序圖
1.先將SCL置0(只有它為0的時(shí)候SDA才允許變化)
2.改變SDA是數(shù)值(就是你當(dāng)前要穿的一位是0還是1)
3.把SCL置1(此時(shí)芯片就會(huì)讀取總線上的數(shù)據(jù))
下面是代碼

[cpp] view plaincopyprint?




[cpp] view plaincopyprint?



    發(fā)送地址的時(shí)候只需把地址傳給該函數(shù)即可。
                       
  d.應(yīng)答(ACK)
    每接受或發(fā)送一字節(jié)數(shù)據(jù)后都需要發(fā)送一位應(yīng)答,來表是否收到了前面一個(gè)字節(jié)的數(shù)據(jù)。



[cpp] view plaincopyprint?






e.發(fā)送/接受數(shù)據(jù)(取決于前面地址字的最后一位讀/寫位)
    發(fā)送數(shù)據(jù)和上面的發(fā)送地址調(diào)用同一個(gè)函數(shù),只要穿給他數(shù)據(jù)即可。
    接收數(shù)據(jù)其實(shí)和發(fā)送數(shù)據(jù)差不多,只不過要把接收到的數(shù)據(jù)一位一位拼裝成一字節(jié)數(shù)據(jù),看代碼~

[cpp] view plaincopyprint?





f.應(yīng)答
g.·······如此循環(huán),直到數(shù)據(jù)一個(gè)字一個(gè)字的發(fā)完
h.發(fā)送終止信號(hào)
    就是SCL在高電平的時(shí)候SDA由低電平變成高電平

[cpp] view plaincopyprint?



以上就是整個(gè)數(shù)據(jù)傳輸?shù)倪^程了




為了更好的掌握I2C總線我在此放兩個(gè)例子,一個(gè)是書上(郭天祥的,你們懂的)EPROM存儲(chǔ)定時(shí)時(shí)間的例子,還有就是用PCF8591進(jìn)行D/A轉(zhuǎn)換的例子。

1.EPROM存儲(chǔ)定時(shí)時(shí)間
[cpp] view plaincopyprint?



這是電路圖


2.DA轉(zhuǎn)換

[cpp] view plaincopyprint?








作者: 騰飛的龍    時(shí)間: 2015-10-29 22:58
高手啊學(xué)習(xí)分享學(xué)習(xí)啦
作者: 公子墨    時(shí)間: 2017-7-3 09:45
樓主,感謝分享,我的板子沒有時(shí)鐘輸入端,只有數(shù)據(jù)輸入端,數(shù)據(jù)輸出端,Gnd,關(guān)于數(shù)模轉(zhuǎn)換的那個(gè)怎么弄

作者: chaoself    時(shí)間: 2018-1-26 22:12
高手啊學(xué)習(xí)分享學(xué)習(xí)啦
作者: INSIST    時(shí)間: 2018-3-20 20:21
void write_byte(uchar date) //寫一字節(jié)數(shù)據(jù) {     uchar i,temp;     temp=date;     for(i=0;i<8;i++)     {         temp=temp<<1; //左移一位 移出的一位在CY中         SCL=0;          //只有在scl=0時(shí)sda能變化值         delay();         SDA=CY;         delay();         SCL=1;         delay();     }     SCL=0;     delay();     SDA=1;     delay(); }
作者: INSIST    時(shí)間: 2018-3-20 20:22
可以在詳細(xì)說一下,是怎樣說一字節(jié)的數(shù)據(jù)嗎
作者: QQ572008555    時(shí)間: 2020-2-18 23:00
我目前看了一半 不過大體上都看懂了 后面的還沒看懂 不過具體等實(shí)戰(zhàn)




歡迎光臨 (http://www.torrancerestoration.com/bbs/) Powered by Discuz! X3.1