介紹
TM32微控制器提供了輸入捕獲(Input Capture)功能,這是一種用于精確測量外部信號脈沖寬度和周期的強大技術。輸入捕獲通常與定時器(如TIM)的高級控制定時器(TIM1和TIM8)或通用定時器(TIM2至TIM5)配合使用。
輸入捕獲的工作原理
輸入捕獲模式允許用戶在定時器的計數器與一個外部信號(通常是一個邊沿觸發信號)的邊沿同步時,捕獲定時器的當前計數值。通過捕獲信號的兩個連續邊沿之間的定時器計數值,可以計算出信號的脈沖寬度或周期。
輸入捕獲的關鍵特性
- 時間戳功能:能夠記錄信號邊沿的確切時刻。
- 方向檢測:可以檢測信號的上升沿和下降沿,從而判斷信號的頻率和方向。
- 脈沖計數和頻率測量:通過計算兩個連續捕獲事件之間的時間差,可以測量信號的頻率和周期。
- 脈寬調制(PWM)信號分析:可以分析PWM信號的占空比和頻率。
如何使用STM32的輸入捕獲
- 配置定時器和通道:選擇一個定時器,并配置其通道為輸入捕獲模式。
- 選擇輸入信號:將外部信號連接到定時器的相應輸入引腳。
- 配置觸發邊沿:設置捕獲信號是上升沿還是下降沿觸發,或者兩者都觸發。
- 配置預分頻器和計數器:根據輸入信號的頻率和所需的分辨率來配置定時器的預分頻器和自動重裝載寄存器(ARR)。
- 中斷和回調函數:配置輸入捕獲中斷,并在中斷服務例程中讀取捕獲寄存器的值,以計算信號的時間參數。
注意事項
- 時鐘源選擇:確保定時器時鐘源配置正確,以獲得準確的計時。
- 采樣率:根據信號頻率選擇合適的采樣率,以避免信號變化太快而無法準確捕獲。
- 噪聲抑制:可能需要對輸入信號進行去抖動處理,以防止誤觸發。
?哪些定時器有輸入捕獲
-
高級控制定時器(TIM1和TIM8):這些定時器提供了最豐富的功能,包括輸入捕獲、輸出比較、PWM生成等。
-
通用定時器(TIM2至TIM5):這些定時器也支持輸入捕獲,但功能相對于高級控制定時器來說較少。
-
基本定時器(TIM6和TIM7):這些定時器主要用于簡單的時間計數,不支持輸入捕獲功能。
-
低功耗定時器(LPTIM):在某些STM32微控制器中,還可能包括低功耗定時器,它們在低功耗模式下非常有用,但可能不支持輸入捕獲。
?STM32Cude設置
1時鐘源設置
2開啟輸入捕獲
3輸入捕獲的設置
配置選項介紹
-
Polarity Selection:這個選項允許你選擇捕獲信號的邊沿極性。你可以選擇:
- Rising Edge:只在信號的上升沿捕獲計數器的值。
- Falling Edge:只在信號的下降沿捕獲計數器的值。
- Both Edges:在信號的上升沿和下降沿都捕獲計數器的值。
-
IC Selection:這個選項決定了輸入信號的來源。通常,你可以選擇:
- Direct:直接連接到定時器的輸入通道,不經過任何其他硬件處理。
- Indirect:通過一個濾波器或信號處理器連接到定時器的輸入通道。
-
Prescaler Division Ratio:這個選項允許你設置一個預分頻器,用于降低輸入信號的頻率。你可以選擇不進行預分頻(No division),或者選擇2、4、8等分頻比,以便在捕獲之前降低信號的頻率。
-
Input Filter (4 bits value):這個選項允許你設置一個數字濾波器,用于減少輸入信號上的噪聲。濾波器的寬度可以從0到15,其中0表示不使用濾波器,而15表示最強的濾波器設置。濾波器的寬度決定了信號必須保持新電平多長時間才能被視為有效跳變。
?
4開啟中斷
之后生成代碼
代碼設置
有哪些函數
-
HAL_TIM_IC_Init:用于初始化定時器的輸入捕獲通道。
HAL_StatusTypeDef HAL_TIM_IC_Init(TIM_HandleTypeDef *htim);
-
HAL_TIM_IC_ConfigChannel:用于配置定時器的輸入捕獲通道
HAL_StatusTypeDef HAL_TIM_IC_ConfigChannel(TIM_HandleTypeDef *htim, TIM_IC_InitTypeDef *sConfigIC, uint32_t Channel);
-
HAL_TIM_IC_Start:用于啟動輸入捕獲。
HAL_StatusTypeDef HAL_TIM_IC_Start(TIM_HandleTypeDef *htim, uint32_t Channel);
-
HAL_TIM_IC_Start_IT:用于啟動輸入捕獲并使能中斷。
HAL_StatusTypeDef HAL_TIM_IC_Start_IT(TIM_HandleTypeDef *htim, uint32_t Channel);
-
HAL_TIM_IC_Stop:用于停止輸入捕獲。
HAL_StatusTypeDef HAL_TIM_IC_Stop(TIM_HandleTypeDef *htim, uint32_t Channel);
-
HAL_TIM_IC_Stop_IT:用于停止輸入捕獲并禁用中斷。
HAL_StatusTypeDef HAL_TIM_IC_Stop_IT(TIM_HandleTypeDef *htim, uint32_t Channel);
-
HAL_TIM_IRQHandler:用于定時器中斷處理函數,需要在用戶定義的中斷服務例程中調用
-
void HAL_TIM_IRQHandler(TIM_HandleTypeDef *htim);
-
HAL_TIM_IC_CaptureCallback:用于輸入捕獲中斷的回調函數,需要在
HAL_TIM_IRQHandler
中調用。-
是捕獲一次返回一次中斷
void HAL_TIM_IC_CaptureCallback(TIM_HandleTypeDef *htim);
-
2實驗思路將PWM產生的波,用通道1進行捕獲返回捕獲的值
main.h源碼
/* USER CODE BEGIN Header */
/********************************************************************************* @file : main.c* @brief : Main program body******************************************************************************* @attention** Copyright (c) 2024 STMicroelectronics.* All rights reserved.** This software is licensed under terms that can be found in the LICENSE file* in the root directory of this software component.* If no LICENSE file comes with this software, it is provided AS-IS.********************************************************************************/
/* USER CODE END Header */
/* Includes ------------------------------------------------------------------*/
#include "main.h"
#include "tim.h"
#include "usart.h"
#include "gpio.h"/* Private includes ----------------------------------------------------------*/
/* USER CODE BEGIN Includes */
#include "stdio.h"
/* USER CODE END Includes *//* Private typedef -----------------------------------------------------------*/
/* USER CODE BEGIN PTD *//* USER CODE END PTD *//* Private define ------------------------------------------------------------*/
/* USER CODE BEGIN PD *//* USER CODE END PD *//* Private macro -------------------------------------------------------------*/
/* USER CODE BEGIN PM *//* USER CODE END PM *//* Private variables ---------------------------------------------------------*//* USER CODE BEGIN PV *//* USER CODE END PV *//* Private function prototypes -----------------------------------------------*/
void SystemClock_Config(void);
/* USER CODE BEGIN PFP *//* USER CODE END PFP *//* Private user code ---------------------------------------------------------*/
/* USER CODE BEGIN 0 */
void HAL_TIM_IC_CaptureCallback(TIM_HandleTypeDef *htim){//獲取占空比中的頻率 要獲取一個周期的頻率 =頻率/(預分頻+重裝值);重裝值為 第二次計數減去第一次計數uint32_t tim__CNT=__HAL_TIM_GET_COUNTER(htim);//當前計數值uint32_t tim__PSC=TIM2->PSC;//預分頻值uint32_t PAB1_HZ=72000000;//PAB1頻率uint32_t data=PAB1_HZ/(tim__CNT+tim__PSC);//占空的頻率char aa[10];sprintf(aa,"頻率%06d",data);HAL_UART_Transmit(&huart1,(uint8_t*)aa,10,20);
}
/* 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_TIM2_Init();MX_USART1_UART_Init();/* USER CODE BEGIN 2 */HAL_TIM_IC_Start_IT(&htim2,TIM_CHANNEL_1);//啟動捕獲HAL_TIM_PWM_Start(&htim2,TIM_CHANNEL_2);//啟動PWM/* USER CODE END 2 *//* Infinite loop *//* USER CODE BEGIN WHILE */while (1){/* USER CODE END WHILE *//* USER CODE BEGIN 3 */}/* USER CODE END 3 */
}/*** @brief System Clock Configuration* @retval None*/
void SystemClock_Config(void)
{RCC_OscInitTypeDef RCC_OscInitStruct = {0};RCC_ClkInitTypeDef RCC_ClkInitStruct = {0};/** Initializes the RCC Oscillators according to the specified parameters* in the RCC_OscInitTypeDef structure.*/RCC_OscInitStruct.OscillatorType = RCC_OSCILLATORTYPE_HSE;RCC_OscInitStruct.HSEState = RCC_HSE_ON;RCC_OscInitStruct.HSEPredivValue = RCC_HSE_PREDIV_DIV1;RCC_OscInitStruct.HSIState = RCC_HSI_ON;RCC_OscInitStruct.PLL.PLLState = RCC_PLL_ON;RCC_OscInitStruct.PLL.PLLSource = RCC_PLLSOURCE_HSE;RCC_OscInitStruct.PLL.PLLMUL = RCC_PLL_MUL9;if (HAL_RCC_OscConfig(&RCC_OscInitStruct) != HAL_OK){Error_Handler();}/** Initializes the CPU, AHB and APB buses clocks*/RCC_ClkInitStruct.ClockType = RCC_CLOCKTYPE_HCLK|RCC_CLOCKTYPE_SYSCLK|RCC_CLOCKTYPE_PCLK1|RCC_CLOCKTYPE_PCLK2;RCC_ClkInitStruct.SYSCLKSource = RCC_SYSCLKSOURCE_PLLCLK;RCC_ClkInitStruct.AHBCLKDivider = RCC_SYSCLK_DIV1;RCC_ClkInitStruct.APB1CLKDivider = RCC_HCLK_DIV2;RCC_ClkInitStruct.APB2CLKDivider = RCC_HCLK_DIV1;if (HAL_RCC_ClockConfig(&RCC_ClkInitStruct, FLASH_LATENCY_2) != HAL_OK){Error_Handler();}
}/* USER CODE BEGIN 4 *//* USER CODE END 4 *//*** @brief This function is executed in case of error occurrence.* @retval None*/
void Error_Handler(void)
{/* USER CODE BEGIN Error_Handler_Debug *//* User can add his own implementation to report the HAL error return state */__disable_irq();while (1){}/* USER CODE END Error_Handler_Debug */
}#ifdef USE_FULL_ASSERT
/*** @brief Reports the name of the source file and the source line number* where the assert_param error has occurred.* @param file: pointer to the source file name* @param line: assert_param error line source number* @retval None*/
void assert_failed(uint8_t *file, uint32_t line)
{/* USER CODE BEGIN 6 *//* User can add his own implementation to report the file name and line number,ex: printf("Wrong parameters value: file %s on line %d\r\n", file, line) *//* USER CODE END 6 */
}
#endif /* USE_FULL_ASSERT */
總結
輸入捕獲就是在產生輸入波形的信號時產生一個反饋信號