2023-02-02 08:06 AM
I am using a STM32L073RZT6 MCU and the Cube IDE V1.11. Using the .IOC, I instantiated UART1 on PB7-6 with global interrupts enabled and a DMA service for RX. On the PC side of things I'm using PuTTy as a sniffer and a UART to USB cable for COMS. I have provided screenshots of the configuration, PuTTy output and code snippets below. Each time I transmit a character to the MCU, the rx callback runs twice, but, on the second go around, the rx buffer seems to be reset and transmits 'None'. While I am confused by this added behavior, I mostly am concerned with why it runs the call back twice. Any guidance would be appreciated. Thank you.
/* USER CODE BEGIN PV */
volatile uint8_t uart_tx_buffer[4];
volatile uint8_t uart_rx_buffer[4];
const uint8_t uart_default_msg[8] = {'W', 'A', 'I', 'T', 'I', 'N', 'G', 0x0D};
/* USER CODE END PV */
/* Private function prototypes -----------------------------------------------*/
void SystemClock_Config(void);
static void MX_GPIO_Init(void);
static void MX_DMA_Init(void);
static void MX_USART1_UART_Init(void);
/* USER CODE BEGIN PFP */
/* USER CODE END PFP */
/* Private user code ---------------------------------------------------------*/
/* USER CODE BEGIN 0 */
/* USER CODE END 0 */
/**
* @brief The application entry point.
* @retval int
*/
int main(void)
{
/* USER CODE BEGIN 1 */
/* USER CODE END 1 */
/* MCU Configuration--------------------------------------------------------*/
/* Reset of all peripherals, Initializes the Flash interface and the Systick. */
HAL_Init();
/* USER CODE BEGIN Init */
/* USER CODE END Init */
/* Configure the system clock */
SystemClock_Config();
/* USER CODE BEGIN SysInit */
/* USER CODE END SysInit */
/* Initialize all configured peripherals */
MX_GPIO_Init();
MX_DMA_Init();
MX_USART1_UART_Init();
/* USER CODE BEGIN 2 */
HAL_UART_Receive_DMA(&huart1, uart_rx_buffer, 1);
/* USER CODE END 2 */
/* Infinite loop */
/* USER CODE BEGIN WHILE */
while (1)
{
/* USER CODE END WHILE */
/* USER CODE BEGIN 3 */
HAL_UART_Transmit(&huart1, uart_default_msg, 8, 100);
HAL_Delay(10000);
}
/* USER CODE END 3 */
}
/* USER CODE BEGIN 4 */
void HAL_UART_RxCpltCallback(UART_HandleTypeDef *huart){
int i = 0;
switch(uart_rx_buffer[0]){
case('p'):
uart_tx_buffer[0] = 'p';
uart_tx_buffer[1] = 'u';
uart_tx_buffer[2] = 'l';
uart_tx_buffer[3] = 's';
i++;
HAL_UART_Transmit(&huart1, uart_tx_buffer, 4, 100);
break;
case('h'):
uart_tx_buffer[0] = 'h';
uart_tx_buffer[1] = 'e';
uart_tx_buffer[2] = 'a';
uart_tx_buffer[3] = 't';
i++;
HAL_UART_Transmit(&huart1, uart_tx_buffer, 4, 100);
break;
default:
uart_tx_buffer[0] = 'N';
uart_tx_buffer[1] = 'o';
uart_tx_buffer[2] = 'n';
uart_tx_buffer[3] = 'e';
HAL_UART_Transmit(&huart1, uart_tx_buffer, 4, 100);
i++;
break;
}
// HAL_UART_Receive_DMA(&huart1, uart_rx_buffer, 1);
}
/* USER CODE END 4 */
.
Solved! Go to Solution.
2023-02-02 08:18 AM
How do you transmit the char, pressing ENTER?
You may debug your code and inspect the content of the rx buffer.
hth
KnarfB
2023-02-02 08:18 AM
How do you transmit the char, pressing ENTER?
You may debug your code and inspect the content of the rx buffer.
hth
KnarfB
2023-02-02 08:50 AM
Yes.. yes I am. That makes perfect sense now, thank you.
2023-02-02 09:03 AM
Check out this function: HAL_UARTEx_ReceiveToIdle(_IT/DMA). Its good to know this functions exists if you expect an unknown amount of bytes within a buffer size. An use case would be if you want to receive any word with a length in range from 4 to 8 letters, and you would like to get an interrupt whenever a word comes in, without having to read letter by letter and waiting for an EOT character