Bit-banging 與 SPI + DMA
從軟體模擬訊號到硬體加速
📌 前言
在嵌入式系統開發中,Bit-banging 是一種常見的軟體模擬技術,用於實現各種通訊協定,如 SPI、I2C 等。透過直接控制 GPIO 腳位的電平變化,軟體可以模擬出硬體通訊協定的行為。然而,當資料量增加或通訊速度要求較高時,Bit-banging 的效率可能會成為瓶頸。這時,使用 SPI + DMA 的硬體加速方式就顯得尤為重要。
🔧 Bit-banging 的實現
範例程式,展示使用 Bit-banging 輸出 CLOCK 和 DATA 訊號:
// Test Clock
LCM_Printf(0, "Clock Test");
LCM_Printf(1, "...");
U16 serial_pattern[] = {0x55aa, 0x1234, 0x7fff, 0x0001, \
0x4000, 0x2244, 0x6688, 0xffff};
PU16 pattern = serial_pattern;
U16 data;
U16 mask = ((1UL << (15 - 1)));
// prepeare power for VDD pin
if (skt_vdd_prepare(4000, 500)!=SKT_OK) {
return SKT_FAIL;
}
skt_pkg_pin_cfg_cio();
skt_vdd_pwr_on(); TM_Delay_US(500);
while (1) {
if ((*pattern)==0xffff) break;
data = *pattern++;
mask = 0x4000;
// send data
for (U8 i=0; i<15; i++, mask>>=1) {
CLK_LO(); TM_Delay_US(1);
if (data & mask) { DO_HI();}
else { DO_LO();}
TM_Delay_US(1);
CLK_HI(); TM_Delay_US(1);
}
CLK_LO(); TM_Delay_US(1); DO_LO();
}
LCM_Printf(1, "End");
使用邏輯分析儀觀察到的 CLOCK 和 DATA 波型如下所示:
放大後可以看到,由於 Bit-banging 是由軟體控制 GPIO 腳位,每次的切換有延遲,以及由於考慮 Setup Time 和 Hold Time,和無法抵消 MCU 處理迴圈控制邏輯所產生的額外開銷,導致 Clock 的 Duty Cycle 無法達到完美的 50%。
🚀 進階方案:SPI + DMA 的通訊
為了提升通訊效率解放 MCU,可以使用內建的 SPI 模組搭配 DMA 進行資料傳輸。這樣可以讓 SPI 硬體自動處理資料的傳輸,而不需要 MCU 持續地控制 GPIO 腳位。
// 準備好一串燒錄指令波形
uint8_t program_cmd[] = {0xAA, 0xBB, 0xCC};
// 直接交給硬體發送,CPU 可以去跑別的邏輯或準備下一段資料
HAL_SPI_Transmit_DMA(&hspi1, program_cmd, 3);