首页 > 解决方案 > 使用 HAL 在 STM32F303 上进行串行通信 - Rx 不工作

问题描述

我正在使用连接到我自己的 PCB 的 STM32F303RE Nucleo 板进行 RS-232 串行通信,但我无法弄清楚为什么此代码在某些情况下不起作用。

我使用 HAL 函数(HAL_UART_Transmit 和 HAL_UART_Receive)进行通信,使用 Nucleo 上的 USB 连接器用于 usart2,并使用我自己的 PCB 上的 9 针 RS-232 串行端口用于 usart1。两种 usart 配置均由 HAL 设置。

当我仅使用 USB 连接 (usart2) 进行通信(使用 Putty 终端)时,代码运行良好。当我将 usart1 用于 Tx 并将 usart2 用于 Rx 时,仍然没有问题。当我将 usart2 用于 Tx 并将 usart1 用于 Rx 时,它也可以正常工作。

问题是当我尝试将 usart1(这是我的 RS-232 电缆)用于 Tx 和 Rx 时。我的处理器可以很好地传输初始数据,但是在接收数据时,没有任何东西进入接收的数据寄存器。我有一些代码可以简单地回显传输线上收到的任何数据,并且在此配置中没有任何内容。再一次 - 代码在 usart1 和 usart2 的所有其他配置中都可以正常工作,用于发送和接收,但是当我尝试在 usart1 (RS-232) 上完成所有操作时没有 Rx

这是我正在使用的相关代码部分。COMTYPE 设置为 &huart1 或 &huart2(在问题情况下,它设置为 &huart1)

主循环(接收到的数据用于菜单系统中的 switch 语句):

    HAL_UART_Transmit(COMTYPE, prompt, sizeof(prompt), TIMEOUT);
    cmd_size = UART_getstr(command);

    cmd_num = parse_menu_input(command, cmd_size);
    converted = (uint8_t)cmd_num + '0';


    // error parsing command for menu selection
    if(cmd_num == -1){
        HAL_UART_Transmit(COMTYPE, parse_error, sizeof(parse_error), TIMEOUT);
    }
    else{
        menu_switch(cmd_num);
    }
}

包含 Rx 功能和回显 (Tx) 功能的功能:

int UART_getstr(uint8_t* command){

int x = 0;              // tracker for buffer pointer
int chars = 0;
uint8_t buffer;     // single char storage for UART receive

while(1){       

    // get single char from UART_Receive
    HAL_UART_Receive(COMTYPE, &buffer, 1, HAL_MAX_DELAY);
    // echo back function
    HAL_UART_Transmit(COMTYPE, &buffer, sizeof(char), TIMEOUT);

    // write value of received char to "command" array
    command[x] = buffer;

    // increment the number of valid chars
    chars++;

    // stop adding chars to command after [Enter] pressed
    if(command[x] == '\r'){
        chars--;
        break;
    }
    // correct for storing DELETE as char in buffer
    if(command[x] == 0x7F){
        command -= 1;
        chars -= 2;
    }
    else{
        x++;
    }
}
command[x] = '\0';

// return length of command buffer
return chars; }

我不明白为什么完全相同的代码会在 4 种情况下的 3 种情况下工作,但不能在第 4 种情况下工作。我检查了串行电缆,其余的 RS-232 硬件在仅用于 Tx 或仅用于 Rx 时功能正常。但是在尝试同时使用 RS-232 时,Rx 似乎被某些东西阻塞了。

编辑:添加 UART 初始化代码(由 HAL 生成):

/* USART1 init function */
static void MX_USART1_UART_Init(void)
{

  huart1.Instance = USART1;
  huart1.Init.BaudRate = 115200;
  huart1.Init.WordLength = UART_WORDLENGTH_8B;
  huart1.Init.StopBits = UART_STOPBITS_1;
  huart1.Init.Parity = UART_PARITY_NONE;
  huart1.Init.Mode = UART_MODE_TX_RX;
  huart1.Init.HwFlowCtl = UART_HWCONTROL_NONE;
  huart1.Init.OverSampling = UART_OVERSAMPLING_16;
  huart1.Init.OneBitSampling = UART_ONE_BIT_SAMPLE_DISABLE;
  huart1.AdvancedInit.AdvFeatureInit = UART_ADVFEATURE_NO_INIT;
  if (HAL_UART_Init(&huart1) != HAL_OK)
  {
    _Error_Handler(__FILE__, __LINE__);
  }

}

/* USART2 init function */
static void MX_USART2_UART_Init(void)
{

  huart2.Instance = USART2;
  huart2.Init.BaudRate = 115200;
  huart2.Init.WordLength = UART_WORDLENGTH_8B;
  huart2.Init.StopBits = UART_STOPBITS_1;
  huart2.Init.Parity = UART_PARITY_NONE;
  huart2.Init.Mode = UART_MODE_TX_RX;
  huart2.Init.HwFlowCtl = UART_HWCONTROL_NONE;
  huart2.Init.OverSampling = UART_OVERSAMPLING_16;
  huart2.Init.OneBitSampling = UART_ONE_BIT_SAMPLE_DISABLE;
  huart2.AdvancedInit.AdvFeatureInit = UART_ADVFEATURE_NO_INIT;
  if (HAL_UART_Init(&huart2) != HAL_OK)
  {
    _Error_Handler(__FILE__, __LINE__);
  }

}

标签: serial-portembeddedstm32halusart

解决方案


推荐阅读