學完本章你將能夠:

  • 設計一組穩定的除錯/遙測 UART 協定,與 ASR 模組口分開。

  • 產出最小化 JSON,讓 PC 或樹莓派輕鬆接。

  • 描述 MQTT 主題規劃,以及 STM32 經 ESP32 AT 或 enticed 乙太網路的接法。

  • 避免在通訊任務裡阻塞到讓看門狗復位。

產品不能只活在麵包板上。工廠測試、App 顯示、雲端紀錄都需要一條 機器可讀的通道。語音指令走內部佇列;對外只報「現在狀態」與 「事件」。

兩條 UART 的理由

口 用途 Nucleo-F429ZI 建議
USART3 人類除錯 + JSON 遙測(VCP) ST-LINK 虛擬 COM
USART6 路徑 A 語音模組 獨立 TX/RX、3.3 V

混在同一條線的後果是:你 |printf| 的 log 被模組當成指令,或模組的 OK 被你的解析器吃掉。若腳位不夠,至少用不同的幀頭(例如遙測 固定以 { 開頭,模組用純文字詞)。

JSON 最小集

不要引完整 JSON 函式庫除非必要。手寫幾個 |snprintf| 即可:

事件另用小物件:{"evt":"wake"}、{"evt":"fault","code":3}。 PC 端用 Python json.loads 即可畫即時儀表。

通訊任務結構

void vTaskComms(void *arg) comms_req_t req; (void)arg; for (;;) if (xQueueReceive(g_comms_q, &req, pdMS_TO_TICKS(1000)) == pdTRUE) comms_handle(&req); else comms_send_telemetry(); /* 週期心跳 */ heartbeat_touch(TASK_COMMS);

CMD_QUERY_TEMP 只是往 |g_comms_q| 丟一筆 REQ_TELEMETRY。Device 任務不讀 DHT22——感測屬於 Sensor 任務, 溫度放在有 mutex 保護的 |g_sensor| 快取。

MQTT(選做)

課堂若要連家用 MQTT:

  • 主題:home/living/voice/state(上報)、 home/living/voice/cmd(下行,用第 13 章的閘道文字行, 例如 CMD LIGHT ON)。

  • 硬體:ESP32 跑 AT 或一個極小 MQTT client;STM32 只出 UART 字串。現成的 MQTT–UART 透明橋在 lab12_assistant_gateway/esp32/mqtt_uart_bridge/。 或 F429 的 ETH + lwIP + coreMQTT(工作量明顯較大)。

  • QoS:狀態用 QoS0 即可;OTA 觸發用 QoS1。

  • 下行命令必須走同一個 |g_cmd_q| 與安全策略(遠端指令 不套本地聆聽窗,但門鎖等高風險輸出受政策管制,見第 13 章), 不能讓雲端繞過狀態機直接 |dev_relay_set(1)|。

ST 的 X-CUBE-CELLULAR / Azure 套件與 Mosquitto 教學很多,本課程只要求 主題與安全邊界正確,不綁定某一家雲。

實驗

firmware/lab10_comms/:每秒一筆 JSON;按鍵或口令變更立即多 一筆 evt。附 tools/serial_plot.py 讀溫度與亮度。 選做檔 mqtt_notes.md 寫 ESP32 接線。

從 PC 送一行 {"cmd":"CMD_LIGHT_ON"} 進 VCP,通訊任務解析後 送入 |g_cmd_q|(僅當 |APP_ALLOW_UART_CMD=1|)。思考實驗室環境 為什麼預設應關掉這個後門。