I2C死鎖原因及解決方法是什么

I2C死鎖原因及解決方法是什么,相信很多沒有經(jīng)驗(yàn)的人對(duì)此束手無策,為此本文總結(jié)了問題出現(xiàn)的原因和解決方法,通過這篇文章希望你能解決這個(gè)問題。

創(chuàng)新互聯(lián)建站主要從事成都做網(wǎng)站、網(wǎng)站設(shè)計(jì)、外貿(mào)營銷網(wǎng)站建設(shè)、網(wǎng)頁設(shè)計(jì)、企業(yè)做網(wǎng)站、公司建網(wǎng)站等業(yè)務(wù)。立足成都服務(wù)西市,十多年網(wǎng)站建設(shè)經(jīng)驗(yàn),價(jià)格優(yōu)惠、服務(wù)專業(yè),歡迎來電咨詢建站服務(wù):028-86922220

死鎖總線表現(xiàn)為:SCL為高,SDA一直為低

現(xiàn)象:單片機(jī)采用硬件i2c讀取E2PROM,當(dāng)單片機(jī)復(fù)位時(shí),會(huì)有概率出現(xiàn)再無法與E2PROM通信,此時(shí)SCL為高,SDA一直為低

原因:當(dāng)單片機(jī)正在和E2PROM通信,如果主正好發(fā)生打算發(fā)第9個(gè)時(shí)鐘,此時(shí)SCL為高,而從開始拉低SDA為低做準(zhǔn)備(作為ACK信號(hào)),等待主SCL變低后,從再釋放SDA為高。如果此時(shí)正好單片機(jī)復(fù)位,主SCL還沒來得及變低,直接變成高電平,此時(shí)從還在等待SCL變低,所以一直拉低SDA;而主由于復(fù)位,發(fā)現(xiàn)SDA一直為低,也在等待從釋放SDA為高。因此主從都進(jìn)入一個(gè)相互等待的死鎖狀態(tài)。

解決方法:最好的方法是采用模擬i2c. 但由于已經(jīng)配置成硬件i2c,程序改為上電或復(fù)位改成發(fā)9個(gè)SCL時(shí)鐘信號(hào),使從好釋放SDA。

 最近發(fā)現(xiàn)單片機(jī)(硬件I2C實(shí)現(xiàn))讀取E2PROM時(shí)候,單片機(jī)復(fù)位可能會(huì)引起i2C死鎖,表現(xiàn)為SCL為高,SDA一直為低,后發(fā)現(xiàn)是E2PROM從設(shè)備拉死i2c總線,從設(shè)備斷電之后,SDA變高,上電后通信正常。后來通過拉低SCL信號(hào)線,SDA就會(huì)自動(dòng)變成高電平,i2c總線恢復(fù)。后查看一篇文章,講的不錯(cuò),特摘錄如下:

    在正常情況下,I2C總線協(xié)議能夠保證總線正常的讀寫操作。但是,當(dāng)I2C主設(shè)備異常復(fù)位時(shí)(看門狗動(dòng)作,板上電源異常
導(dǎo)致復(fù)位芯片動(dòng)作,手動(dòng)按鈕復(fù)位等等)有可能導(dǎo)致I2C總線死鎖產(chǎn)生。下面詳細(xì)說明一下總線死鎖產(chǎn)生的原因。

    在I2C主設(shè)備進(jìn)行讀寫操作的過程中.主設(shè)備在開始信號(hào)后控制SCL產(chǎn)生8個(gè)時(shí)鐘脈沖,然后拉低SCL信號(hào)為低電平,在這個(gè)時(shí)候,從設(shè)備輸出應(yīng)答信號(hào),將SDA信號(hào)拉為低電平。如果這個(gè)時(shí)候主設(shè)備異常復(fù)位,SCL就會(huì)被釋放為高電平。此時(shí),如果從設(shè)備沒有復(fù)位,就會(huì)繼續(xù)I2C的應(yīng)答,將SDA一直拉為低電平,直到SCL變?yōu)榈碗娖?,才?huì)結(jié)束應(yīng)答信號(hào)。而對(duì)于I2C主設(shè)備來說.復(fù)位后檢測(cè)SCL和SDA信號(hào),如果發(fā)現(xiàn)SDA信號(hào)為低電平,則會(huì)認(rèn)為I2C總線被占用,會(huì)一直等待SCL和SDA信號(hào)變?yōu)楦唠娖?。這樣,I2C主設(shè)備等待從設(shè)備釋放SDA信號(hào),而同時(shí)I2C從設(shè)備又在等待主設(shè)備將SCL信號(hào)拉低以釋放應(yīng)答信號(hào),兩者相互等待,I2C總線進(jìn)人一種死鎖狀態(tài)。同樣,當(dāng)I2C進(jìn)行讀操作,I2C從設(shè)備應(yīng)答后輸出數(shù)據(jù),如果在這個(gè)時(shí)刻I2C主設(shè)備異常復(fù)位而此時(shí)I2C從設(shè)備輸出的數(shù)據(jù)位正好為0,也會(huì)導(dǎo)致I2C總線進(jìn)入死鎖狀態(tài)。

SCL為高,SDA一直為低原因

從:正常時(shí)序下:SDA信號(hào)是在SCL為低的狀態(tài)下改變,即從應(yīng)答SDA為低電平時(shí),此時(shí)SCL應(yīng)為為低電平(即從設(shè)備是先拉低SDA信號(hào),等待主設(shè)備SCL由高變低,“取走”ACK信號(hào)后,從再釋放SDA為高)。但如果此時(shí)時(shí)序被打亂,例如單片機(jī)i2c通信時(shí)突然復(fù)位,SCL突然變高,則從設(shè)備SDA一直為低,等待SCL變低。

主:SDA被從拉低,故主認(rèn)為i2c總線占用,一直等待SDA變高

這樣主從進(jìn)入一個(gè)相互等待的死鎖過程。

 方法

    最好用模擬I2C實(shí)現(xiàn),則不會(huì)死鎖

    (1)盡量選用帶復(fù)位輸人的I2C從器件。

    (2)將所有的從I2C設(shè)備的電源連接在一起,通過MOS管連接到主電源,而MOS管的導(dǎo)通關(guān)斷由I2C主設(shè)備來實(shí)現(xiàn)。
    (3)在I2C從設(shè)備設(shè)計(jì)看門狗的功能。

    (4)在I2C主設(shè)備中增加I2C總線恢復(fù)程序。每次I2C主設(shè)備復(fù)位后,如果檢測(cè)到SDA數(shù)據(jù)線被拉低,則控制I2C中的
SCL時(shí)鐘線產(chǎn)生9個(gè)時(shí)鐘脈沖(針對(duì)8位數(shù)據(jù)的情況),這樣I2C從設(shè)備就可以完成被掛起的讀操作,從死鎖狀態(tài)中恢復(fù)過來。
這種方法有很大的局限性,因?yàn)榇蟛糠种髟O(shè)備的I2C模塊由內(nèi)置的硬件電路來實(shí)現(xiàn),軟件并不能夠直接控制SCL信號(hào)模擬
產(chǎn)生需要時(shí)鐘脈沖。

  (5)在I2C總線上增加一個(gè)額外的總線恢復(fù)設(shè)備。這個(gè)設(shè)備監(jiān)視I2C總線。當(dāng)設(shè)備檢測(cè)到SDA信號(hào)被拉低超過指定時(shí)間
時(shí),就在SCL總線上產(chǎn)生9個(gè)時(shí)鐘脈沖,使I2C從設(shè)備完成讀操作,從死鎖狀態(tài)上恢復(fù)出來??偩€恢復(fù)設(shè)備需要有具有編程
功能,一般可以用單片機(jī)或CPLD實(shí)現(xiàn)這一功能。

  (6)在I2C上串人一個(gè)具有死鎖恢復(fù)的I2C緩沖器,如Linear公司的LTC4307如圖2所示:LTC4307是一個(gè)雙向的I2C
總線緩沖器,并且具有I2C總線死鎖恢復(fù)的功能。LTC4307總線輸人側(cè)連接主設(shè)備,總線輸出側(cè)連接所有從設(shè)備。當(dāng)LTC4307
檢測(cè)到輸出側(cè)SDA或SCL信號(hào)被拉低30ms時(shí),就自動(dòng)斷開I2C總線輸人側(cè)與輸出側(cè)的連接.并且在輸出側(cè)SCL信號(hào)上產(chǎn)生16個(gè)時(shí)鐘脈沖來釋放總線。當(dāng)總線成功恢復(fù)后,LTC4307會(huì)再次連接輸人輸出側(cè),使總線能夠正常工作

看完上述內(nèi)容,你們掌握I2C死鎖原因及解決方法是什么的方法了嗎?如果還想學(xué)到更多技能或想了解更多相關(guān)內(nèi)容,歡迎關(guān)注創(chuàng)新互聯(lián)行業(yè)資訊頻道,感謝各位的閱讀!

網(wǎng)站名稱:I2C死鎖原因及解決方法是什么
文章源于:http://muchs.cn/article18/jopdgp.html

成都網(wǎng)站建設(shè)公司_創(chuàng)新互聯(lián),為您提供搜索引擎優(yōu)化、微信公眾號(hào)、用戶體驗(yàn)、電子商務(wù)、Google、

廣告

聲明:本網(wǎng)站發(fā)布的內(nèi)容(圖片、視頻和文字)以用戶投稿、用戶轉(zhuǎn)載內(nèi)容為主,如果涉及侵權(quán)請(qǐng)盡快告知,我們將會(huì)在第一時(shí)間刪除。文章觀點(diǎn)不代表本網(wǎng)站立場(chǎng),如需處理請(qǐng)聯(lián)系客服。電話:028-86922220;郵箱:631063699@qq.com。內(nèi)容未經(jīng)允許不得轉(zhuǎn)載,或轉(zhuǎn)載時(shí)需注明來源: 創(chuàng)新互聯(lián)

綿陽服務(wù)器托管