酸汤面的串口

从官方的demo来看,串口分为ComDMA、ComIT、ComPolling三个例程,字面意思是DMA、中断、轮询。
其中还有个球猫老师早就知道空闲中断,就是闲得就中断...

建立一个叫Echo的工程,打开串口中断,确认115200-N-8-1,还得打开debuger的自动reset and run

uint8_t usart_rx_buffer[128];

HAL_UART_Receive_IT(&huart2, (uint8_t*)usart_rx_buffer, 1);  

void HAL_UART_RxCpltCallback(UART_HandleTypeDef *huart)  
{  
    if(huart ->Instance == USART2){  
        printf("%c",usart_rx_buffer[0]);  
        HAL_UART_Receive_IT(&huart2, (uint8_t*)usart_rx_buffer, 1);  
    }  
}

进阶空闲中断
../Src/main.c(110): warning: #223-D: function "memset" declared implicitly
增加#include "string.h"

main.h中定义

#define RX_BUF_MAX_LEN     512 
typedef struct 
{  
  uint8_t rx_buff[RX_BUF_MAX_LEN];
  uint16_t len;
  uint8_t flag;
} USRAT_RX;

main.c中定义

USRAT_RX usart_rx;
uint8_t recv_buf;

stm32g0xx_it.c中定义

extern uint8_t recv_buf;
extern USRAT_RX usart_rx;

修改

void USART2_IRQHandler(void)
{
  /* USER CODE BEGIN USART2_IRQn 0 */
  if(__HAL_UART_GET_FLAG(&huart2,UART_FLAG_RXNE) != RESET) {  
  /* USER CODE END USART2_IRQn 0 */
  HAL_UART_IRQHandler(&huart2);
  /* USER CODE BEGIN USART2_IRQn 1 */
        usart_rx.rx_buff[usart_rx.len++] = recv_buf;  
    if(usart_rx.len>RX_BUF_MAX_LEN){
      usart_rx.flag = 1;
    }  
  }  
  if(__HAL_UART_GET_FLAG(&huart2, UART_FLAG_IDLE) != RESET) {  
    __HAL_UART_CLEAR_IDLEFLAG(&huart2);
    usart_rx.flag = 1;
    if(usart_rx.len==0){
      usart_rx.flag = 0;  
    }  
  }  
  HAL_UART_Receive_IT(&huart2,&recv_buf,1);
  /* USER CODE END USART2_IRQn 1 */
}

main.c中初始化

memset(&usart_rx, 0, sizeof(USRAT_RX));
HAL_UART_Receive_IT(&huart2,&recv_buf,1);
__HAL_UART_ENABLE_IT(&huart2,UART_IT_IDLE);

while中输出

if(usart_rx.flag){
  printf("%s",usart_rx.rx_buff); 
  memset(&usart_rx, 0, sizeof(USRAT_RX));
}

DMA+空闲,初始化

memset(&usart_rx, 0, sizeof(USRAT_RX));
__HAL_UART_ENABLE_IT(&huart2,UART_IT_IDLE);
HAL_UART_Receive_DMA(&huart2, (uint8_t*)usart_rx.rx_buff, RX_BUF_MAX_LEN); 

中断

  if(__HAL_UART_GET_FLAG(&huart2, UART_FLAG_IDLE) != RESET) {  
    __HAL_UART_CLEAR_IDLEFLAG(&huart2);
    HAL_UART_DMAStop(&huart2);
    usart_rx.len  = RX_BUF_MAX_LEN - __HAL_DMA_GET_COUNTER(&hdma_usart2_rx);
    usart_rx.flag = 1;  
    if(usart_rx.len == 0){
      usart_rx.flag = 0;  
      HAL_UART_Receive_DMA(&huart2, (uint8_t*)usart_rx.rx_buff, RX_BUF_MAX_LEN); 
      HAL_UART_DMAResume(&huart2);
    }  
  }  

循环输出

if(usart_rx.flag){
  printf("%s",usart_rx.rx_buff); 
  memset(&usart_rx, 0, sizeof(USRAT_RX));
  HAL_UART_Receive_DMA(&huart2, (uint8_t*)usart_rx.rx_buff, RX_BUF_MAX_LEN);
  HAL_UART_DMAResume(&huart2);
}  

参考文献:
https://blog.csdn.net/qq_33894122/article/details/83962012
https://www.cnblogs.com/ZzJan/p/13530768.html
https://blog.csdn.net/qq_30592147/article/details/83514409
https://blog.csdn.net/qq_39758638/article/details/107211476
https://blog.csdn.net/weifengdq/article/details/102941293

标签: none

添加新评论