0
  • 聊天消息
  • 系統(tǒng)消息
  • 評(píng)論與回復(fù)
登錄后你可以
  • 下載海量資料
  • 學(xué)習(xí)在線課程
  • 觀看技術(shù)視頻
  • 寫文章/發(fā)帖/加入社區(qū)
會(huì)員中心
創(chuàng)作中心

完善資料讓更多小伙伴認(rèn)識(shí)你,還能領(lǐng)取20積分哦,立即完善>

3天內(nèi)不再提示

GD32 MCU碰到IIC總線卡死怎么辦?

聚沃科技 ? 2024-02-24 09:46 ? 次閱讀

大家在使用MCU IIC通信時(shí),若碰到設(shè)備復(fù)位或者總線干擾等情況,可能會(huì)導(dǎo)致IIC總線卡死,表現(xiàn)上總線上SDA或者SCL其中一根線為低電平,IIC總線一直處于busy狀態(tài)。此時(shí)若代碼上一直等待總線空閑,則可能導(dǎo)致軟件死機(jī),為解決該問題,本視頻提供了軟件配置釋放IIC總線的方法。

首先為大家介紹發(fā)生IIC總線卡死的兩種情況:(1)主機(jī)在發(fā)送 START 信號(hào)后, 控制 SCL 產(chǎn)生 8 個(gè)時(shí)鐘脈沖,然后拉低 SCL 信號(hào)為低電平,在這個(gè)時(shí)候,從設(shè)備輸出應(yīng)答信號(hào),將 SDA 信號(hào)拉為低電平。如果這個(gè)時(shí)候主機(jī)異常復(fù)位, SCL 就會(huì)被釋放為高電平。此時(shí),如果從機(jī)沒有復(fù)位,就會(huì)繼續(xù) I2C 的應(yīng)答,將 SDA一直拉為低電平,直到 SCL 變?yōu)榈碗娖?,才?huì)結(jié)束應(yīng)答信號(hào)。 而由于 I2C 主機(jī)復(fù)位后檢測總線的狀態(tài),如果 SDA 信號(hào)為低電平,則 I2C 總線被占用,會(huì)一直等待 SCL 和 SDA信號(hào)變?yōu)楦唠娖剑虼?,?I2C 主機(jī)等待從機(jī)釋放 SDA 信號(hào)時(shí), I2C 從機(jī)又在等待主機(jī)將 SCL 信號(hào)拉低以釋放應(yīng)答信號(hào),兩者相互等待, I2C 總線進(jìn)入死鎖狀態(tài) ;(2)主機(jī)在發(fā)送 START 信號(hào)后, 控制 SCL 產(chǎn)生 8 個(gè)時(shí)鐘脈沖,然后拉低 SCL 信號(hào)為低電平,在這個(gè)時(shí)候,從設(shè)備輸出應(yīng)答信號(hào),將 SDA 信號(hào)拉為低電平。如果這個(gè)時(shí)候主機(jī)異常復(fù)位, SCL 就會(huì)被釋放為高電平。此時(shí),如果從機(jī)沒有復(fù)位,就會(huì)繼續(xù) I2C 的應(yīng)答,將 SDA一直拉為低電平,直到 SCL 變?yōu)榈碗娖?,才?huì)結(jié)束應(yīng)答信號(hào)。 而由于 I2C 主機(jī)復(fù)位后檢測總線的狀態(tài),如果 SDA 信號(hào)為低電平,則 I2C 總線被占用,會(huì)一直等待 SCL 和 SDA信號(hào)變?yōu)楦唠娖?。因此,?I2C 主機(jī)等待從機(jī)釋放 SDA 信號(hào)時(shí), I2C 從機(jī)又在等待主機(jī)將 SCL 信號(hào)拉低以釋放應(yīng)答信號(hào),兩者相互等待, I2C 總線進(jìn)入死鎖狀態(tài) 。

wKgZomXZShGAD0AVAAC3zH17MmY045.png

以下為兩種復(fù)位IIC總線卡死的軟件方法,大家可以嘗試使用:

(1)將SDA和SCL配置為推挽輸出,強(qiáng)制輸出stop信號(hào)

在 I2C 主機(jī)復(fù)位后,主機(jī)檢測 I2C 總線一直為 BUSY 狀態(tài),且超過設(shè)定的時(shí)間,則總線被鎖死。可通過將 I2C 的 SCL 和 SDA 引腳初始化成普通 GPIO 功能,配置成推挽輸出。 先拉高SCL 信號(hào),在拉高 SDA 信號(hào),模擬產(chǎn)生一個(gè) STOP 信號(hào),然后再配置為 I2C 的引腳復(fù)用功能。配置代碼如下所示。

/*! \brief reset i2c bus \param[in] none \param[out] none \retval none */ void i2c_bus_reset() { GPIO_BC(GPIOB) |= GPIO_PIN_6 | GPIO_PIN_7; gpio_init(GPIOB, GPIO_MODE_OUT_PP, GPIO_OSPEED_50MHZ, GPIO_PIN_6|GPIO_PIN_7); __nop(); __nop(); __nop(); __nop(); __nop(); GPIO_BOP(GPIOB) |= GPIO_PIN_6; __nop(); __nop(); __nop(); __nop(); __nop(); GPIO_BOP(GPIOB) |= GPIO_PIN_7; gpio_init(GPIOB, GPIO_MODE_AF_OD, GPIO_OSPEED_50MHZ, GPIO_PIN_6 | GPIO_PIN_7); } /*! \brief check the I2C is or not busy \param[in] none \param[out] none \retval none */ void check_bus_status(void) { while(i2c_flag_get(I2C0,I2C_FLAG_I2CBSY)) { if(--time_out == 0){ i2c_bus_reset(); } } }

wKgaomXZShiAbcOxAACtlqGCdfA351.png

(2)將SCL配置為推挽輸出,強(qiáng)制輸出9個(gè)clk

在 I2C 主機(jī)中增加 I2C 總線恢復(fù)程序。每次 I2C 主設(shè)備復(fù)位后,如果檢測到 SDA 數(shù)據(jù)線被拉低,則控制 I2C 中的 SCL 時(shí)鐘線產(chǎn)生 9 個(gè)時(shí)鐘脈沖(針對(duì) 8 位數(shù)據(jù)的情況),這樣 I2C 從設(shè)備就可以完成被掛起的操作,從死鎖狀態(tài)中恢復(fù)過來。

I2C 主機(jī)通過將 SCL 引腳初始化為普通 GPIO 功能,配置成推挽輸出。保證連續(xù)發(fā)送 9 個(gè)時(shí)鐘脈沖,為保證后續(xù) I2C 正常通信,先將 I2C 模塊復(fù)位,再置位,最后再配置為 I2C 的引腳復(fù)用功能。配置代碼如下所示。

/*! \brief reset i2c bus \param[in] none \param[out] none \retval none */ void i2c_bus_reset() { uint8_t I = 0; gpio_init(GPIOB, GPIO_MODE_OUT_PP, GPIO_OSPEED_50MHZ, GPIO_PIN_6); /* SCL output clock signal */ for(I = 0; I < 10; i++){ gpio_bit_reset(GPIOB, GPIO_PIN_6); delay_1us(2); gpio_bit_set(GPIOB, GPIO_PIN_6); delay_1us(2); } /* reset I2C */ i2c_software_reset_config(I2C0, I2C_SRESET_RESET); i2c_software_reset_config(I2C0, I2C_SRESET_SET); gpio_init(GPIOB, GPIO_MODE_AF_OD, GPIO_OSPEED_50MHZ, GPIO_PIN_6 | GPIO_PIN_7); } /*! \brief check the I2C is or not busy \param[in] none \param[out] none \retval none */ void check_bus_status(void) { while(i2c_flag_get(I2C0,I2C_FLAG_I2CBSY)) { if(--time_out == 0){ i2c_bus_reset(); } } }

wKgaomXZSh6AfaDhAADGMKXklJo287.png

如有其他問題或建議,歡迎評(píng)論區(qū)討論。

聲明:本文內(nèi)容及配圖由入駐作者撰寫或者入駐合作網(wǎng)站授權(quán)轉(zhuǎn)載。文章觀點(diǎn)僅代表作者本人,不代表電子發(fā)燒友網(wǎng)立場。文章及其配圖僅供工程師學(xué)習(xí)之用,如有內(nèi)容侵權(quán)或者其他違規(guī)問題,請(qǐng)聯(lián)系本站處理。 舉報(bào)投訴
  • 單片機(jī)
    +關(guān)注

    關(guān)注

    6037

    文章

    44558

    瀏覽量

    635213
  • mcu
    mcu
    +關(guān)注

    關(guān)注

    146

    文章

    17148

    瀏覽量

    351182
  • 脈沖
    +關(guān)注

    關(guān)注

    20

    文章

    889

    瀏覽量

    95639
  • IIC
    IIC
    +關(guān)注

    關(guān)注

    11

    文章

    300

    瀏覽量

    38333
收藏 人收藏

    評(píng)論

    相關(guān)推薦

    GD32 MCU進(jìn)入低功耗模式導(dǎo)致無法再進(jìn)行程序下載怎么辦?

    很多朋友在調(diào)試GD32 MCU的低功耗模式時(shí)會(huì)遇到一個(gè)問題:程序中讓MCU進(jìn)入了Sleep、Deepsleep或者Standby模式,之后MCU就無法再下載程序了。這是因?yàn)樵诘凸哪J?/div>
    的頭像 發(fā)表于 01-12 09:41 ?3257次閱讀
    <b class='flag-5'>GD32</b> <b class='flag-5'>MCU</b>進(jìn)入低功耗模式導(dǎo)致無法再進(jìn)行程序下載<b class='flag-5'>怎么辦</b>?

    GD32 MCU 入門教程】GD32 MCU 常見外設(shè)介紹(12)FMC 模塊介紹

    閃存控制器(FMC),提供了片上閃存需要的所有功能。FMC 也提供了頁擦除,整片擦除,以及32 位整字或 16 位半字編程閃存等操作。 GD32 MCU 支持不同類型編程的具體說明如下表 GD32
    的頭像 發(fā)表于 08-21 09:56 ?1126次閱讀
    <b class='flag-5'>GD32</b> <b class='flag-5'>MCU</b> 入門教程】<b class='flag-5'>GD32</b> <b class='flag-5'>MCU</b> 常見外設(shè)介紹(12)FMC 模塊介紹

    GD32 MCU碰到IIC總線卡死怎么辦?#單片機(jī) #嵌入式開發(fā) #IIC #GD32 #stm32

    單片機(jī)嵌入式開發(fā)
    聚沃科技
    發(fā)布于 :2024年02月24日 09:57:10

    GD32單片機(jī)用ISP燒寫工具燒寫程序失敗怎么辦

    GD32單片機(jī)用ISP燒寫工具燒寫程序失敗怎么辦呢?
    發(fā)表于 01-18 06:04

    電腦進(jìn)入系統(tǒng)后卡死怎么辦

    電腦進(jìn)入系統(tǒng)后卡死怎么辦 癥狀:啟動(dòng)剛進(jìn)入系統(tǒng)界面時(shí),點(diǎn)什么都打不開,要等一分鐘左右才能打開。     解決辦法:     一
    發(fā)表于 02-24 13:46 ?1.4w次閱讀

    GD32 MCU Dfu驅(qū)動(dòng)64位Win8

    GD32 MCU Dfu驅(qū)動(dòng)64位Win8
    發(fā)表于 10-08 14:55 ?0次下載

    GD32芯片MCU ISP下載工具

    GD32芯片MCU ISP 下載工具
    發(fā)表于 10-08 14:53 ?18次下載

    推出采用GD32 RISC-V的MCU

    推出采用GD32 RISC-V的MCU ppt分享
    發(fā)表于 07-14 17:15 ?0次下載

    兆易創(chuàng)新GD32 MCU選型手冊(cè),適用于GD32全系列MCU

    兆易創(chuàng)新GD32MCU選型手冊(cè),適用于GD32全系列MCUGD32MCU選型手冊(cè),適用于GD32全系列MCU
    發(fā)表于 10-19 17:26 ?49次下載

    你了解GD32 MCU的命名規(guī)則嗎

    下面為大家介紹GD32 MCU的通用命名規(guī)則,以GD32F303ZGT6為例,其中,GD32代表GD32
    的頭像 發(fā)表于 01-13 09:38 ?3647次閱讀
    你了解<b class='flag-5'>GD32</b> <b class='flag-5'>MCU</b>的命名規(guī)則嗎

    GD32 MCU的選項(xiàng)字節(jié)是什么?

    GD32 MCU的選項(xiàng)字節(jié)是什么,有什么功能呢?選項(xiàng)字節(jié)被誤篡改如何回復(fù)?
    的頭像 發(fā)表于 01-17 09:42 ?1383次閱讀
    <b class='flag-5'>GD32</b> <b class='flag-5'>MCU</b>的選項(xiàng)字節(jié)是什么?

    不同型號(hào)的GD32 MCU如何區(qū)分?

    大家是否碰到過以下應(yīng)用場景:同一套軟件代碼希望跑在不同型號(hào)的GD32 MCU中,但有些地方需要根據(jù)MCU型號(hào)進(jìn)行調(diào)整?或者上位機(jī)或其他MCU
    的頭像 發(fā)表于 01-27 09:32 ?1002次閱讀
    不同型號(hào)的<b class='flag-5'>GD32</b> <b class='flag-5'>MCU</b>如何區(qū)分?

    GD32 MCU 入門教程】GD32 MCU 常見外設(shè)介紹(14)RTC 模塊介紹

    GD32 MCU內(nèi)部提供了一個(gè)RTC(實(shí)時(shí)時(shí)鐘)模塊,通過RTC可以實(shí)現(xiàn)日歷時(shí)鐘、鬧鐘等功能。RTC也可以用于深度睡眠或待機(jī)模式的低功耗喚醒。不同系列的GD32 MCU在RTC設(shè)計(jì)和功
    的頭像 發(fā)表于 08-23 09:18 ?470次閱讀
    【<b class='flag-5'>GD32</b> <b class='flag-5'>MCU</b> 入門教程】<b class='flag-5'>GD32</b> <b class='flag-5'>MCU</b> 常見外設(shè)介紹(14)RTC 模塊介紹

    GD32 MCU 入門教程】GD32 MCU FPU 使用方法

    GD32 MCU FPU 使用方法
    的頭像 發(fā)表于 08-25 09:24 ?598次閱讀
    【<b class='flag-5'>GD32</b> <b class='flag-5'>MCU</b> 入門教程】<b class='flag-5'>GD32</b> <b class='flag-5'>MCU</b> FPU 使用方法

    GD32 MCU入門教程】GD32 MCU GPIO 結(jié)構(gòu)與使用注意事項(xiàng)

    本文是專門為基于GD32 MCU開發(fā)的工程設(shè)計(jì)人員提供,主要介紹了GPIO的功能配置、內(nèi)部結(jié)構(gòu)以及在不同場景使用時(shí)的注意事項(xiàng),旨在幫助GD32 MCU開發(fā)者優(yōu)化對(duì)通用型輸入輸出端口(G
    的頭像 發(fā)表于 09-07 10:34 ?737次閱讀
    【<b class='flag-5'>GD32</b> <b class='flag-5'>MCU</b>入門教程】<b class='flag-5'>GD32</b> <b class='flag-5'>MCU</b> GPIO 結(jié)構(gòu)與使用注意事項(xiàng)