[STM32] realize serial communication based on STM32F407 interrupt mode

Posted by jonnyw6969 on Tue, 02 Nov 2021 18:18:23 +0100

1, Interrupt introduction

Specific introduction and reference articles:
[STM32] lighting of interrupt switch based on STM32F407

2, Interrupt mode to realize serial communication

1. New construction

Create an STM2CubeMX project for STM32F407:

2. Project setting

  1. Setting RCC
    Set the high-speed external clock HSE and select the external clock source

  2. Set serial port
    1) Click USART1
    2) Set MODE to asynchronous communication
    3) Basic parameters: baud rate is 115200 Bits/s. The transmission data length is 8 bits. Parity check none, stop bit 1, both receive and transmit are enabled
    4) GPIO pin setting USART1_RX/USART_TX (it is generally set automatically here)
    5) The NVIC Settings column enables to receive interrupts

  3. Clock setting

  4. After setting up Project Manager, generate code:

3. Coding

  1. printf function settings
    Add header file #include "stdio.h" in main.c and usart.c
    In the usart.c file, add the following code to redefine
/* USER CODE BEGIN 1 */

//Add the following code to support the printf function without selecting use MicroLIB	  
//#define PUTCHAR_PROTOTYPE int fputc(int ch, FILE *f)	
#if 1
//#pragma import(__use_no_semihosting)             
//Support functions required by the standard library                 
struct __FILE 
{ 
	int handle; 
}; 

FILE __stdout;       
//Definition_ sys_exit() to avoid using half host mode    
void _sys_exit(int x) 
{ 
	x = x; 
} 
//Redefine fputc function 
int fputc(int ch, FILE *f)
{ 	
	 HAL_UART_Transmit(&huart1, (uint8_t *)&ch, 1, 0x0001);  
	return ch;
}
#endif 
/* USER CODE END 1 */

  1. In the main.c main function, add send data
    /* USER CODE END WHILE */
	  	printf("Hello windows!\r\n");
		HAL_Delay(500);
    /* USER CODE BEGIN 3 */

  1. Add the following definition in main.c to receive serial port data
uint8_t aRxBuffer;			//Receive interrupt buffer
uint8_t Uart1_RxBuff[256];		//Receive buffer
uint8_t Uart1_Rx_Cnt = 0;		//Receive buffer count
uint8_t	cAlmStr[] = "data overflow (Greater than 256)\r\n";

  1. Add a statement that turns on receiving interrupts
/* USER CODE BEGIN 2 */
	HAL_UART_Receive_IT(&huart1, (uint8_t *)&aRxBuffer, 1);
/* USER CODE END 2 */
  1. Add interrupt callback function
/* USER CODE BEGIN 4 */
/**
  * @brief  Rx Transfer completed callbacks.
  * @param  huart pointer to a UART_HandleTypeDef structure that contains
  *                the configuration information for the specified UART module.
  * @retval None
  */
void HAL_UART_RxCpltCallback(UART_HandleTypeDef *huart)
{
  /* Prevent unused argument(s) compilation warning */
  UNUSED(huart);
  /* NOTE: This function Should not be modified, when the callback is needed,
           the HAL_UART_TxCpltCallback could be implemented in the user file
   */
 
	if(Uart1_Rx_Cnt >= 255)  //Overflow judgment
	{
		Uart1_Rx_Cnt = 0;
		memset(Uart1_RxBuff,0x00,sizeof(Uart1_RxBuff));
		HAL_UART_Transmit(&huart1, (uint8_t *)&cAlmStr, sizeof(cAlmStr),0xFFFF);	
	}
	else
	{
		Uart1_RxBuff[Uart1_Rx_Cnt++] = aRxBuffer;   //Receive data transfer
	
		if((Uart1_RxBuff[Uart1_Rx_Cnt-1] == 0x0A)&&(Uart1_RxBuff[Uart1_Rx_Cnt-2] == 0x0D)) //Judgment end bit
		{
			HAL_UART_Transmit(&huart1, (uint8_t *)&Uart1_RxBuff, Uart1_Rx_Cnt,0xFFFF); //Send the received information
			Uart1_Rx_Cnt = 0;
			memset(Uart1_RxBuff,0x00,sizeof(Uart1_RxBuff)); //Empty array
		}
	}
	
	HAL_UART_Receive_IT(&huart1, (uint8_t *)&aRxBuffer, 1);   //Restart receive interrupt
}
/* USER CODE END 4 */


Compile it without error

4. Burning verification

  1. Burn the code into the core board
  2. Communication with XCOM serial port assistant

    The serial port outputs Hello windows every 0.5s
    When sending data below, such as stop, the serial port will enter the interrupt, then send stop, and then return to the original loop to continue sending Hello windows.

3, Summary

  by understanding the relevant knowledge of interrupt, this paper realizes serial communication using stm32ubemx based on STM32F407. The interrupt mode does not have to wait for the data transmission process, but only needs to trigger the interrupt by the interrupt flag bit after receiving and transmitting each byte of data, put a new byte of data or read the received byte of data in the interrupt service program.

4, Reference

[STM32] lighting of interrupt switch based on STM32F407
[embedded 11] HAL library experiment interrupt switch lighting and serial communication

Topics: Embedded system Single-Chip Microcomputer stm32 ARM