UART 应用异常案例分析

judy的头像
judy 发布于:周二, 10/17/2017 - 16:56 ,关键词:

在 Cube 软件包中,为不同系列 MCU、不同外设提供了对应的例程方便开发参考。其中,针对STM324xG-EVAL 平台提供了 UART 中断发送接收的例程。开发者参考了这个例程进行 UART 功能开发,并且为了实现不间断的接收功能,在接收回调函数中,再次调用中断接收函数。在这种情况下,出现了例程执行异常。本文分析了这种情况出现原因及解决方法。

问题描述

测试验证板: STM3240G-EVAL
参考例程路径:
STM32Cube_FW_F4_V1.15.0\Projects\STM324xG_EVAL\Examples\UART\UART_Hyperterminal_IT

基于上述例程,出于前言中交代的应用目的,在接收回调函数 HAL_UART_RxCpltCallback 中,再次调用 HAL_UART_Receive_IT。
随后出现例程执行卡死在下面红色标识的语句处,导致了 UART 中断发送无法正确被执行。

 if(HAL_UART_Receive_IT(&UartHandle, (uint8_t *)aRxBuffer, RXBUFFERSIZE) != HAL_OK)
 {
 /* Turn LED3 on: Transfer error in reception process */
 BSP_LED_On(LED3);
 while(1)
 {
 }
 }
 /*##-4- Wait for the end of the transfer ###################################*/
 /* Before starting a new communication transfer, you need to check the current
 state of the peripheral; if it 抯 busy you need to wait for the end of current
 transfer before starting a new one.
 For simplicity reasons, this example is just waiting till the end of the
 transfer, but application may perform other tasks while transfer operation
 is ongoing. */
 while (HAL_UART_GetState(&UartHandle) != HAL_UART_STATE_READY)
 {
 }
 /*##-5- Send the received Buffer ###########################################*/
 if(HAL_UART_Transmit_IT(&UartHandle, (uint8_t*)aRxBuffer, RXBUFFERSIZE)!= HAL_OK)

问题分析及解决

根据描述,首先考虑到是否由于 UART 始终处于接收忙状态,导致中断发送收到影响。但是 UART 外设具有发送数据寄存器和接收数据寄存器,以及互不影响的接收、发送中断。

继续对问题进行定位,发现在 HAL_UART_GetState 函数中,会同时获取发送和接收状态。这意味着,只有在发送和接收同时处于就绪状态时,中断发送函数才会被执行。而开发者的应用实现中,使得UART 始终处于接收状态,从而判断无法通过。

清楚了产生原因后,问题解决就一目了然了。只需将对发送和接收状态的判断,改写成仅对发送的状
态的判断,如下所示。其中 gState 对应着发送状态。

//while (HAL_UART_GetState(&UartHandle) != HAL_UART_STATE_READY)
 while( UartHandle.gState != HAL_UART_STATE_READY)

总结

在使用 Cube 软件包例程时,最好能够对各驱动接口函数有一定认识。例如上述问题,对于例程来说,没有问题。但是转移到应用时,就需要考虑到例程中调用的判断函数是否符合应用目的了。

而对于各驱动接口函数,在函数定义处,都给出了介绍,包括各参数说明。同时,在 Cube 软件包的Drivers 目录下,提供了对驱动接口函数介绍的文档。

来源:ST

围观 589