1. 程式人生 > >通用定時器——輸入捕獲實驗

通用定時器——輸入捕獲實驗

輸入捕獲模式可以用來測量脈衝寬度或者測量頻率。STM32 的定時器,除了 TIM6 和 TIM7,其他定時器都有輸入捕獲功能。 STM32 的輸入捕獲,簡單的說就是通過檢測 TIMx_CHx 上的邊沿訊號,在邊沿訊號發生跳變(比如上升沿/下降沿)的時候,將當前定時器的值( TIMx_CNT)存放到對應的通道的捕獲/比較暫存器( TIMx_CCRx)裡面,完成一次捕獲。同時還可以配置捕獲時是否觸發中斷/DMA 等。

通用定時器框圖
在輸入捕獲中我們用到的是紅框中的部分

這裡寫圖片描述
以通道1為例,基本工作過程為通過檢測TIMx_CHx上的邊沿訊號,在邊沿訊號發生跳變(比如上升沿/下降沿)的時候,將當前定時器的值(TIMx_CNT)存放到對應的捕獲/比較暫存器(TIMx_CCRx)裡面,完成一次捕獲.

PA0引腳有一個Weak_UP按鍵,設定為上拉模式按下為高電平,擡起為低電平,在此我用到 TIM5_CH1 (PA0)來捕獲高電平脈寬並從串列埠列印捕獲結果,也就是要先設定輸入捕獲為上升沿檢測,記錄發生上升沿的時候 TIM5_CNT 的值。然後配置捕獲訊號為下降沿捕獲,當下降沿到來時,發生捕獲,並記錄此時的 TIM5_CNT 值。這樣,前後兩次 TIM5_CNT 之差,就是高電平的脈寬,同時 TIM5 的計數頻率我們是知道的,從而可以計算出高電平脈寬的準確時間。

在配置輸入捕獲時可分成四步

步驟1:設定輸入捕獲濾波器(通道1為例)

這裡寫圖片描述

捕獲/比較模式暫存器TIMx_CCMR1
輸入捕獲 1 預分頻器 IC1PSC[1:0],這個比較好理解。我們是 1 次邊沿就觸發 1 次捕獲,所以選擇 00 就是了。
輸入捕獲 1 濾波器 IC1F[3:0],這個用來設定輸入取樣頻率和數字濾波器長度。fDTS 則是根據 TIMx_CR1 的 CKD[1:0]的設定來確定的,如果 CKD[1:0]設定為 00,那麼 fDTS = fCK_INT。 N 值就是濾波長度,舉個簡單的例子:假設 IC1F[3:0]=0011(即3),並設定 IC1 對映到通道 1 上,且為上升沿觸發,那麼在捕獲到上升沿的時候,再以 的頻率,連續取樣到 8(即2^3) 次通道 1 的電平,如果都是高電平,則說明卻是一個有效的觸發,就會觸發輸入捕獲中斷(如果開啟了的話)。這樣可以濾除那些高電平脈寬低於 8 個取樣週期的脈衝訊號,從而達到濾波的效果。這裡,我們不做濾波處理,所以設 IC1F[3:0]=0000,只要採集到上升沿,就觸發捕獲

步驟2:設定輸入捕獲極性和輸入捕獲對映通道(通道1為例)(通道1為例)

設定輸入捕獲極性
捕獲/比較使能暫存器:TIMx_CCER,在此我們要用到這個暫存器的最低 2 位, CC1E 和 CC1P 位。
TIMx_CCER 最低 2 位描述
所以,要使能輸入捕獲,必須設定 CC1E=0,而 CC1P 則根據自己的需要來配置CC1S[1:0],這兩個位用於 CCR1 的通道配置。

步驟3:設定輸入捕獲分頻器(通道1為例)

這裡寫圖片描述
捕獲/比較模式暫存器TIMx_CCMR1的位3:0
通過設定TIMx_CCMR1-ICPS[1:0]位,設定捕獲分頻係數,達到分頻目的
我們是 1 次邊沿就觸發 1 次捕獲,所以選擇 00 就是了。

步驟4:捕獲到有效訊號可以開啟中斷

這裡寫圖片描述

實現過程

這裡寫圖片描述
1)開啟 TIM5 時鐘和 GPIOA 時鐘, 配置 PA0 為下拉輸入。

RCC_APB1PeriphClockCmd(RCC_APB1Periph_TIM5, ENABLE); //使能 TIM5 時鐘
RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOA, ENABLE); //使能 GPIOA 時鐘

2) 初始化 TIM5,設定 TIM5 的 ARR 和 PSC

TIM_TimeBaseInitTypeDef TIM_TimeBaseStructure;
TIM_TimeBaseStructure.TIM_Period = arr; //設定計數器自動重灌值
TIM_TimeBaseStructure.TIM_Prescaler =psc; //設定預分頻值
TIM_TimeBaseStructure.TIM_ClockDivision = TIM_CKD_DIV1; // TDTS = Tck_tim
TIM_TimeBaseStructure.TIM_CounterMode = TIM_CounterMode_Up; //TIM 向上計數模式
TIM_TimeBaseInit(TIM5, &TIM_TimeBaseStructure); //根據指定的引數初始化 Tim5

3)設定 TIM5 的輸入比較引數,開啟輸入捕獲

void TIM_ICInit(TIM_TypeDef* TIMx, TIM_ICInitTypeDef* TIM_ICInitStruct);

引數設定結構體 TIM_ICInitTypeDef 的定義:
typedef struct
{
uint16_t TIM_Channel;//設定通道
uint16_t TIM_ICPolarity;//設 置 輸 入 信 號 的 有 效 捕 獲 極 性(如上升沿捕獲)
uint16_t TIM_ICSelection;//設定對映關係
uint16_t TIM_ICPrescaler;//設 置 輸 入 捕 獲 分 頻 系 數
uint16_t TIM_ICFilter;//設定濾波器長度,這裡不使用濾波器, 所以設定為 0
} TIM_ICInitTypeDef;

同時庫函式還提供了單獨設定通道 1 捕獲極性的函式為:
TIM_OC1PolarityConfig(TIM5,TIM_ICPolarity_Falling),

4)使能捕獲和更新中斷(設定 TIM5 的 DIER 暫存器)

TIM_ITConfig( TIM5,TIM_IT_Update|TIM_IT_CC1,ENABLE);//允許更新中斷和捕獲中斷

5)設定中斷分組,編寫中斷服務函式

NVIC_Init();//設定中斷分組
if (TIM_GetITStatus(TIM5, TIM_IT_Update) != RESET){}//判斷是否為更新中斷
if (TIM_GetITStatus(TIM5, TIM_IT_CC1) != RESET){}//判斷是否發生捕獲事件
TIM_ClearITPendingBit(TIM5, TIM_IT_CC1|TIM_IT_Update);//清除中斷和捕獲標誌位

6)使能定時器(設定 TIM5 的 CR1 暫存器)

TIM_Cmd(TIM5,ENABLE ); //使能定時器 5

通過以上 6 步設定,定時器 5 的通道 1 就可以開始輸入捕獲了。

程式碼如下:

timer.h

#ifndef __TIMER_H__
#define __TIMER_H__
#include "sys.h"

void TIM5_Cap_Init(u16 arr,u16 psc);

timer.c

u8  TIM5CH1_CAPTURE_STA = 0;    //輸入捕獲狀態                            
u16 TIM5CH1_CAPTURE_VAL;    //輸入捕獲值

void TIM5_IRQHandler(void)
{
    if((TIM5CH1_CAPTURE_STA&0X80)==0)//還未成功完成上下沿捕獲
    {
        if(TIM_GetITStatus(TIM5,TIM_IT_Update) != RESET)//還未成功捕獲下降沿,定時器溢位,更新事件進入的中斷函式
        {
            if(TIM5CH1_CAPTURE_STA&0X40)//已經捕獲到高電平了
            {
                if((TIM5CH1_CAPTURE_STA&0X3F) == 0X3F)//高電平太長(2的6次方減1)
                {
                    TIM5CH1_CAPTURE_STA|=0X80;//標記成功捕獲了一次
                    TIM5CH1_CAPTURE_VAL=0XFFFF;//設為最大捕獲時間
                }
                else
                {
                    TIM5CH1_CAPTURE_STA++;//每溢位一次,次數加1
                }
            }
        }

        if (TIM_GetITStatus(TIM5, TIM_IT_CC1) != RESET)
        {
            if(TIM5CH1_CAPTURE_STA&0X40)//捕獲到下降沿
            {
                TIM5CH1_CAPTURE_STA |= 0X80;//標記捕獲完成
                TIM5CH1_CAPTURE_VAL = TIM_GetCapture1(TIM5);//用TIM5CH1_CAPTURE_VAL記錄捕獲到的時間資料
                TIM_OC1PolarityConfig(TIM5,TIM_ICPolarity_Rising);//設定為上升沿捕獲 
            }
            else//未開始,第一次捕獲上升沿,做準備工作
            {
                TIM5CH1_CAPTURE_STA = 0;
                TIM5CH1_CAPTURE_VAL = 0;
                TIM_SetCounter(TIM5,0);//清零計時器
                TIM5CH1_CAPTURE_STA |=0X40;//標記捕獲到了上升沿
                TIM_OC1PolarityConfig(TIM5,TIM_ICPolarity_Falling);//設定為下降沿捕獲
            }
        }   
    }
    TIM_ClearITPendingBit(TIM5,TIM_IT_Update | TIM_IT_CC1); //清除中斷標誌位
}

main

int main(void)
{   
    delay_init();//延時函式初始化    
    NVIC_PriorityGroupConfig(NVIC_PriorityGroup_2);//設定NVIC中斷分組2:2位搶佔優先順序,2位響應優先順序
    uart_init(115200);   //串列埠初始化為115200
    LED_Init();
    TIM5_Cap_Init(0XFFFF,72-1);
while(1)
    {

        delay_ms(10);
        TIM_SetCompare2(TIM3,TIM_GetCapture2(TIM3)+1);
        if(TIM_GetCapture2(TIM3) >= 300)
        {
            TIM_SetCompare2(TIM3,0);
        }

        if(TIM5CH1_CAPTURE_STA&0X80)
        {
            temp = TIM5CH1_CAPTURE_STA&0X3F;//得到溢位次數
            temp *= 65536;//溢位次數*每溢位一次用的時間
            temp += TIM5CH1_CAPTURE_VAL;//得到總的高電平時間
            printf("高電平持續時間%d\r\n",temp);

            TIM5CH1_CAPTURE_STA = 0;//開啟下一次捕獲
        }
    }
} 

相關推薦

通用定時——輸入捕獲實驗

輸入捕獲模式可以用來測量脈衝寬度或者測量頻率。STM32 的定時器,除了 TIM6 和 TIM7,其他定時器都有輸入捕獲功能。 STM32 的輸入捕獲,簡單的說就是通過檢測 TIMx_CHx 上的邊沿訊號,在邊沿訊號發生跳變(比如上升沿/下降沿)的時候,將當前定

STM32F103_通用定時輸入捕獲”測量輸入脈衝寬度

一、硬體設計         選用通用定時器TIM5的CH1,其輸入管腳為PA0,在開發板上PA0連線按鍵,當按鍵按下輸入高電平,按鍵鬆開輸入低電平,實驗測量高電平的脈衝寬度。 二、軟體設計     1. 配置中斷向量表的優先順序         因只使用一箇中斷

通用定時PWM輸出實驗

知識回顧 本節知識需要了解通用定時器原理的前提下進行學習 我們將通用定時器分為四個部分: 1,選擇時鐘 2,時基電路 3,輸入捕獲 4,輸出比較 本節定時器PWM輸出主要涉及到定時器框圖右下方部分,即輸出

STM32 通用定時作為輸入捕獲 學習筆記

STM32 通用定時器作為輸入捕獲  通用定時器作為輸入捕獲的使用。我們將用TIM5的通道1(PA0)來做輸入捕獲,捕獲PA0上高電平的脈寬(用 WK_UP 按鍵輸入高電平),通過串列埠列印高電平脈寬時間。   輸入捕獲簡介: 輸入捕獲模式可以用來測量脈衝寬度或者測量頻率。

TIM通用定時(三):PWM輸入捕獲模式

一、概念理解 PWM輸入捕獲模式是輸入捕獲模式的特例,自己理解如下 1. 每個定時器有四個輸入捕獲通道IC1、IC2、IC3、IC4。且IC1 IC2一組,IC3 IC4一組。並且可是設定管腳和暫存器的對應關係。 2. 同一個TIx輸入映射了兩個ICx訊號。 3. 這兩個IC

【STM32】通用定時輸入捕獲(例項:輸入捕獲

STM32F1xx官方資料:《STM32中文參考手冊V10》-第14章  通用定時器通用定時器輸入捕獲概述輸入捕獲的工作原理在通用定時器框圖中,主要涉及到最頂上的一部分(計數時鐘的選擇)、中間部分(時基單元)、左下部分(輸入捕獲輸入捕獲模式可以用來測量脈衝寬度或者測量頻率。S

STM32F107的通用定時中斷實驗總結

1.     STM32F107的通用定時器是指:  TIM2、TIM3、TIM4、TIM5、 STM32F107的高階定時器是指:  TIM1、TIM8 STM32F107的基本定時器是指:  TIM6、TIM7 2.     STM32F107的通用定時器(TIM2、T

STM32F103ZET6 之 通用定時單脈衝模式實驗

由於前面買的核心板,供電老有問題,使得我現在的專案又改用了以前用的F103ZET6微控制器! 1、實驗目的 1)產生脈寬任意可調的單脈衝(在允許的範圍內) 2、硬體:通用定時器3、通用定時器4 3、單脈衝模式介紹 單脈衝模式允許計數器響應一個激勵,並在一個程式可控的延

STM32-通用定時基本定時功能

數字 vision 實現 定義 還要 可能 輸出 給定 禁止 1. STM32的Timer簡介 STM32中一共有11個定時器,其中2個高級控制定時器,4個普通定時器和2個基本定時器,以及2個看門狗定時器和1個系統嘀嗒定時器。其中系統嘀嗒定時器是前文中所描述的Sys

STM32學習筆記(5)——通用定時PWM輸出

part 大小 模式 lan 晶振 kcon 筆記 利用 .cn 1、TIMER輸出PWM基本概念 脈沖寬度調制(PWM),是英文“Pulse Width Modulation”的縮寫,簡稱脈寬調制,是利用微處理器的數字輸出來對模擬

STM32學習筆記(7)——通用定時PWM輸出

nbsp 錯誤 buffer put inter def internal reset 有效 1、TIMER輸出PWM基本概念 脈沖寬度調制(PWM),是英文“Pulse Width Modulation”的縮寫,簡稱脈寬調制,是利

通用定時

1.通用定時器的工作流程:  1)計數器時鐘選擇            內部RCC(TIMx-CLK)  內部觸發輸入口1~4(IT1) 外部捕捉比較腳(TI1FP1~2)外部引腳   2)時基單元

STM32CubeMX學習筆記——STM32H743通用定時PWM

STM32CubeMX學習筆記——STM32H743通用定時器PWM Github 功能簡述 STM32CubeMX配置 Pinout配置 Clock Configuration配置 Configuration

STM32CubeMX學習筆記——STM32H743通用定時

STM32CubeMX學習筆記——STM32H743通用定時器 Github 功能簡述 STM32CubeMX配置 Pinout配置 Clock Configuration配置 Configuration

不使用中斷實現通用定時精確延時

網上大多數延時函式都是通過中斷方式的通用定時器來實現,如果實現1us的延時那麼每1us就來一次中斷,很影響cpu的效率。 本文不使用中斷通過是用通用定時器來實現精確延時。 程式碼如下(基於stm32f103) static void udelay(uint32_t us) { uint

STM32F103微控制器學習—— 通用定時

本篇重點記錄的是STM32F1的通用定時器。 STM32F103ZE有8個定時器,其中2個高階定時器(TIM1、TIM8),4個通用定時器(TIM2、TIM3、TIM4、TIM5),2個基本定時器(TIM6、TIM7)。下表是對這8個定時器的詳

STM32通用定時配置

STM32通用定時器配置 一、STM32通用定時器原理                   

STM32應用簡章之通用定時

① 能定時器時鐘。        RCC_APB1PeriphClockCmd(); ②  初始化定時器,配置ARR,PSC。       TIM_TimeBaseInit(); ③開啟定時器中斷,配置NVIC。       void TIM_ITConfig();

STM32通用定時的基本定時功能實現燈閃爍

/*MAIN.C*/ /* Includes ------------------------------------------------------------------*/#inclu

LED:利用通用定時定時閃爍

F28335有三種32位的I/O口,依次PORTA(GPIO0-GPIO31), PORTB(GPIO32-GPIO63), PORTC(GPIO64-GPIO87),這些口都可以配置為普通的數字IO口同樣也能被配置為外部介面。這樣涉及到了IO的暫存器,