關鍵字:STM32H5, GPIO
1. 問題現象
客戶反饋,使用 STM32H523RET6 應用中配置了兩個 IO 口,PC9 為輸出模式,內部下拉;PB14 為輸入模式,內部上拉。在程序中將 PC9 引腳輸出高電平,結果觀察到 PB14 的電平被拉低。
圖 1 PC9 輸出低時, PB14 為高
圖 2 PC9 輸出高時,PB14 被拉低
2. 問題重現
使用 NUCLEO-H533RE 板,新建一個 cubemx 工程(cubemx 版本 : v6.13.0),按客戶問題所述配置 PC9 和 PB14, 然后在代碼中驅動 PC9 輸出高,結果很容易就重現了問題。
3. 問題分析
一般來說,在 ST 官方 DEMO 板上很容易重現,就意味著問題能很快解決或者很可能是芯片就是如此設計的。于是查找相關文檔,注意到 PC9 可復用為 UCPD1_DBCC2 引腳,而 PB14則可復用為 UCPD1_CC2 引腳。STM32H5 默認時 UCPD 外設的 DB(Dead Battery)功能是激活的,而這個 DB 特性剛好會影響正常的 GPIO 功能,這個在 AN2552 Rev7 文檔中的第11.3.1 節有相關描述 :
在 DBCCx 引腳(PC9)上檢測到電壓超過 1V 時,則芯片內的 Rd 電阻激活,進而將 CCx 引腳(PB14)拉低。
也許有人會問,我啥也沒做啊,我也沒用到 UCPD 外設,我的電路圖也根本不是圖上這么設計的,芯片怎么會這樣?
這就得回到 USB Type-C 接口的 PD 功能來說了。USB Type-C 口大體上來說數據可分為三個通路:USB3.x 數據通路,USB2.0 數據通路,以及走 CC 線的 PD 協議,當然還有 VBUS 上的電力供應。
CC 線上的 PD 協議正是用于 SOURCE 端和 SINK 端之間進行電力協商的,經典的應用場合就是 SOURCE 端比如手機充電適配器向帶電池的 SINK 端(比如手機)充電,用多大功率,多少電壓,最大電流多少,這個就得協商,協商的過程是通過 300K 的 CC 線來進行的。
圖 3 USB Type-C 口的 CC 線連接
STM32H5 是帶 UCPD 外設,全稱 USB Type-C?/USB Power Delivery interface. 是專門
用于 CC 線上的 PD 協議通信的外設。
如上圖所示,SOURCE 端通過檢測 SINK 端的 Rd 電阻來判斷是否有 SINK 設備連接,只有檢測到這個連接,在 USB Type-C 口上的 VBUS 才會供電過去,否則不會有電供應。這就涉及到一個問題,若 SINK 端是電池設備,且電池耗盡(Dead Battery)時,SOURCE 端還能正常供電嗎?
這里存在一個關鍵邏輯點:當 SINK 端電池耗盡時,SOURCE 端是否仍能檢測到 Rd 電阻?進一步說,假設 SINK 端的 PD 芯片為 STM32,在其未上電前,CC 引腳(PB14)必須對外呈現 Rd 下拉電阻特性——這是 UCPD 協議中 DB(Dead Battery)功能的核心要求。
若 CC 引腳未表現出 Rd 電阻,SOURCE 端會認為 SINK 端不具備受電條件,從而不會通過VBUS 供電。而沒有 VBUS 供電,STM32 就無法上電運行,形成 “無電-無法上電-無法反饋” 的死循環。因此,STM32H5 芯片默認激活 DB 功能,正是為了確保在未上電狀態下,CC 引腳通過內部下拉電阻滿足 SOURCE 端的檢測要求,從而觸發 VBUS 供電流程。
知道了原因,那么解決方法就很簡單,即在代碼中將 DB 功能關閉,才能釋放 DBCCx 引腳作為普通 GPIO 引腳的功能,如 :
同時,因為 UCPD_DBCCx 引腳(PC9)只要一檢測電平>1V,則會將內置的 Rd 電阻激活。如果 DBCC 引腳僅只用于 GPIO 功能,為了避免意外激活 Rd,建議在 DBCC 引腳外加上 100K的下拉電阻。
圖 4 當 DBCC 引腳(PC9)用于 GPIO 功能時的建議電路
這就是整個解決方案了。
4. 后記
在 STM32G0 中,同樣的問題,在 STM32CubeMx 中是可以配置是否在代碼中關閉 DB 特性的。見下圖示意:
圖 5 在 cubemx 中針對 G0 的 DB 功能關閉選項
Cubemx 中針對 H5 這一選項當前版本還未添加,后續版本應該會更新此功能。
?