概述
本文利用中斷實現(xiàn)串口不定長接收(非DMA),使用HAL庫,將接收的數(shù)據(jù)打印出去。
DMA接收請查看:https://blog.csdn.net/qq_24312945/article/details/106557538
硬件準備
首先需要準備一個開發(fā)板,這里我準備的是NUCLEO-F030R8的開發(fā)板:

選擇芯片型號
使用STM32CUBEMX選擇芯片stm32f030r8,如下所示:

配置時鐘源
HSE與LSE分別為外部高速時鐘和低速時鐘,在本文中使用內(nèi)置的時鐘源,故都選擇Disable選項,如下所示:

配置時鐘樹
STM32F0的最高主頻到48M,所以配置48即可:

串口配置
本次實驗使用的串口1進行串口通信,波特率配置為115200。

中斷

GPIO配置

定時器配置
本次實驗使用的是TIM3來進行計數(shù)。

PWM頻率計算如下所示

在上面配置TIM3參數(shù),預分頻系數(shù)設置為480-1, 自動重載值設置為10000-1,那么PWM頻率為48,000,000/((480-1+1)*(10000-1+1))=10Hz,即 100ms一個周期。
生成工程設置
注意在生成工程設置中不能出現(xiàn)中文,不然會報錯。

代碼生成設置
最后設置生成獨立的初始化文件:

生成代碼

配置keil

代碼
在main.c中,先加入頭文件。
/* USER CODE BEGIN Includes */
#include "stdio.h"//printf頭文件
#include "string.h"//memset頭文件
/* USER CODE END Includes */
定義變量存儲。
/* USER CODE BEGIN PV */
uint8_t RxBuff[1];      //進入中斷接收數(shù)據(jù)的數(shù)組
uint8_t DataBuff[5000]; //保存接收到的數(shù)據(jù)的數(shù)組
int RxLine=0;           //接收到的數(shù)據(jù)長度
int Rx_flag=0;                    //接受到數(shù)據(jù)標志
/* USER CODE END PV */
定義printf的重定向函數(shù)fputc。
/* USER CODE BEGIN 0 */
void printf_usart(void);//輸出內(nèi)容
int fputc(int ch, FILE* file)//定義printf的重定向函數(shù)fputc,滿足串口調(diào)試打印
{
    return HAL_UART_Transmit(&huart1, (uint8_t*)&ch, 1, 100);
}
/* USER CODE END 0 */
打開串口和定時器。
/* USER CODE BEGIN 2 */
    HAL_UART_Receive_IT(&huart1, (uint8_t *)RxBuff, 1); //打開串口中斷接收
    HAL_TIM_Base_Start_IT(&htim3);//開啟定時器
  /* USER CODE END 2 */
串口接受代碼,當接受到最后數(shù)據(jù)為FF時候,直接打印,否則等待100ms打印。
/* USER CODE BEGIN 4 */
void printf_usart(void)
{
    printf("數(shù)據(jù)長度=%d
",RxLine); 
    for(int i=0;iprintf("數(shù)據(jù):[%d] = 0x%x
",i,DataBuff[i]);                            
    memset(DataBuff,0,sizeof(DataBuff));  //清空緩存數(shù)組
    //memset()作用:可以方便的清空一個結構類型的變量或數(shù)組。
    //例句:memset(aTxbuffer,0,sizeof(aTxbuffer))  用memset清空aTxbuffer。
    RxLine=0;  //清空接收長度
}
void HAL_TIM_PeriodElapsedCallback(TIM_HandleTypeDef *htim)
{
    if (htim->Instance == htim3.Instance)
    {
            HAL_GPIO_TogglePin(GPIOA,GPIO_PIN_5);
        /* Toggle LED */
            if(Rx_flag==1)
            {
                printf_usart();
                Rx_flag=0;
            }
        }   
}
// 捕獲中斷回調(diào)函數(shù),每次捕獲到信號就會進入這個回調(diào)函數(shù)
void HAL_UART_RxCpltCallback(UART_HandleTypeDef*UartHandle)
{
    RxLine++;                      //每接收到一個數(shù)據(jù),進入回調(diào)數(shù)據(jù)長度加1
    DataBuff[RxLine-1]=RxBuff[0];  //把每次接收到的數(shù)據(jù)保存到緩存數(shù)組
        Rx_flag=1;
    if(RxBuff[0]==0xff)            //接收結束標志位,這個數(shù)據(jù)可以自定義,根據(jù)實際需求,這里只做示例使用,不一定是0xff
    {
            printf_usart();
    }   
    RxBuff[0]=0;
    HAL_UART_Receive_IT(&huart1, (uint8_t *)RxBuff, 1); //每接收一個數(shù)據(jù),就打開一次串口中斷接收,否則只會接收一個數(shù)據(jù)就停止接收
        __HAL_TIM_SET_COUNTER(&htim3, 1); // 計數(shù)清零,從頭開始計
}
/* USER CODE END 4 */
 演示效果
可以看到 發(fā)送11 12 13需要等待100ms左右才能發(fā)送,如果最后加上ff直接發(fā)送。

審核編輯:湯梓紅
- 
                                定時器
                                +關注關注 23文章 3350瀏覽量 121270
- 
                                USART
                                +關注關注 1文章 201瀏覽量 32757
- 
                                stm32cubemx
                                +關注關注 5文章 287瀏覽量 16958
發(fā)布評論請先 登錄
STM32CubeMx入門教程(3):定時器的使用
 
    
CW32L083串口中斷+定時器實現(xiàn)不定長數(shù)據(jù)接收
 
    
STM32CUBEMX(2)--USART通過DMA方式接收不定長數(shù)據(jù)
STM32CUBEMX(8)--USART通過定時器中斷方式接收不定長數(shù)據(jù)
STM32CubeMX串口+DMA接收不定長數(shù)據(jù)的函數(shù)分享
利用STM32單片機的IDLE空閑中斷接收不定長數(shù)據(jù)
【MCU】基于STM32CubeMX定時器中斷實現(xiàn)LED閃爍
 
    
STM32CUBEMX(2)--USART通過DMA方式接收不定長數(shù)據(jù)
 
    
STM32 HAL庫中串口空閑中斷+DMA 實現(xiàn)串口數(shù)據(jù)的不定長接收
 
    
STM32CubeMX HAL庫串口+DMA+IDLE空閑中斷不定長度數(shù)據(jù)接收和發(fā)送
 
    
STM32+串口空閑中斷實現(xiàn)不定長數(shù)據(jù)接收
 
    
 
           
        
 
         STM32CUBEMX(8)--USART通過定時器中斷方式接收不定長數(shù)據(jù)
STM32CUBEMX(8)--USART通過定時器中斷方式接收不定長數(shù)據(jù) 
                 
  
     
     
     
     
            
             
             
                 
             工商網(wǎng)監(jiān)
工商網(wǎng)監(jiān)
        
評論