You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

STM32裸机UART通信异常求助:跨设备无接收、同设备数据乱码

问题排查与修正方案

核心问题分析

从现象(跨设备无接收、同设备接收数据乱码)来看,问题集中在GPIO配置错误、波特率计算/寄存器赋值问题以及可能的硬件连接或参数不匹配。

1. GPIO模式赋值错误

配置RX引脚时直接使用GPIOA_MODER = REP_BITS(...),会覆盖之前TX引脚的模式配置,导致TX引脚无法工作在复用功能模式:

// 错误写法:覆盖TX引脚的配置
GPIOA_MODER = REP_BITS(GPIOA_MODER, RX*2, 2, GPIO_MODER_ALT);
// 正确写法:保留原有配置,仅修改RX对应位
GPIOA_MODER |= REP_BITS(GPIOA_MODER, RX*2, 2, GPIO_MODER_ALT);

TX引脚的配置同理,建议用|=而非直接赋值,避免覆盖其他引脚的默认配置。

2. USART BRR寄存器初始化问题

直接用USART1_BRR |= ...赋值会残留寄存器默认值,导致波特率计算错误。正确做法是先清零再赋值:

// 9600波特率(假设APB2时钟为42MHz)
USART1_BRR = 0; // 先清除寄存器残留值
USART1_BRR = (273 << 4) | 7; // 直接写入计算好的波特率值

务必确认APB2总线时钟频率:

  • 若系统时钟为168MHz、APB2预分频为2,则APB2时钟为84MHz,此时9600波特率的BRR应为(546 << 4) | 14(对应0x22C)。
  • 波特率不匹配是乱码的最常见诱因,需先确认时钟树配置正确。

3. 硬件与参数匹配检查

  • 交叉连接与共地:STM32的TX(PA9)必须接ESP32C3的RX,STM32的RX(PA10)接ESP32C3的TX,且两台设备必须共地,否则会出现数据混乱或无接收。
  • 串口参数一致:ESP32C3的Arduino代码需明确指定与STM32匹配的参数:
    void setup() {
      Serial.begin(9600, SERIAL_8N1); // 8位数据位、1停止位、无校验
    }
    
    STM32的USART1_CR1默认是8位数据位(M位为0),无需额外配置,确保参数完全对齐即可。

4. 代码细节优化

  • 将写函数改为可传入参数的形式,方便测试不同数据:
    void uart_write(uint8_t data) {
      while (!(USART1_SR & USART_SR_TXE)); // 等待发送寄存器空
      USART1_DR = data;
      while (!(USART1_SR & USART_SR_TC)); // 等待发送完成
    }
    
  • 确认printf已正确重定向到输出设备(如调试串口或工具),否则无法看到读函数的输出结果。

排查步骤

  1. 修正GPIO配置的赋值方式,重新编译下载到STM32。
  2. 用示波器或逻辑分析仪测量PA9的输出波形,确认波特率符合预期(9600波特率下,每个位时长约104μs)。
  3. 确保设备共地且交叉连接TX/RX,再次测试STM32与ESP32C3的通信。
  4. 若仍有问题,先在两台STM32间测试,确保波特率、参数完全一致,逐步缩小问题范围。

内容的提问来源于stack exchange,提问作者Heliam

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.06.30 07:35:41