在 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