TIM—基本定時器

本章參考資料:《 STM32F4xx 參考手冊》、《 STM32F4xx 規格書》、庫幫助文檔
stm32f4xx_dsp_stdperiph_lib_um.chm》。
學習本章時,配合《 STM32F4xx 參考手冊》 基本定時器章節一塊兒閱讀,效果會更佳,
特別是涉及到寄存器說明的部分。
特別說明,本書內容是以 STM32F42x 系列控制器資源講解。
編程

TIM 簡介
定時器(Timer)最基本的功能就是定時了,好比定時發送 USART 數據、定時採集 AD
數據等等。若是把定時器與 GPIO 結合起來使用的話能夠實現很是豐富的功能,能夠測量
輸入信號的脈衝寬度,能夠生產輸出波形。定時器生產 PWM 控制電機狀態是工業控制普
遍方法,這方面知識很是有必要深刻了解。
STM32F42xxx 系列控制器有 2 個高級控制定時器、 10 個通用定時器和 2 個基本定時器,
還有 2 個看門狗定時器。看門狗定時器不在本章討論範圍,有專門講解的章節。控制器上
全部定時器都是彼此獨立的,不共享任何資源。各個定時器特性參考表 31-1
後端

再看參考手冊中的描述:函數

以前時鐘章節的博客:學習

咱們程序設定的分頻係數是4和2,因此TIMx_CLK =2乘以PCLK1(由於 基本定時器是掛載在APB1上的) =90M。
spa

基本定時器功能框圖
基本定時器的功能框圖包含了基本定時器最核心內容,掌握了功能框圖,對基本定時
器就有一個總體的把握,在編程時思路就很是清晰,見圖 31-1
首先先看圖 31-1 中綠色框內容,第一個是帶有陰影的方框,方框內容通常是一個寄存
器名稱,好比圖中主體部分的自動重載寄存器(TIMx_ARR)PSC 預分頻器(TIMx_PSC)
這裏要特別突出的是陰影這個標誌的做用,它表示這個寄存器還自帶有影子寄存器,在硬
件結構上實際是有兩個寄存器,源寄存器是咱們能夠進行讀寫操做,而影子寄存器咱們是
徹底沒法操做的,有內部硬件使用。影子寄存器是在程序運行時真正起到做用的,源寄存
器只是給咱們讀寫用的,只有在特定時候(特定事件發生時)才把源寄存器的值拷貝給它的
影子寄存器。多個影子寄存器一塊兒使用能夠到達同步更新多個寄存器內容的目的。
接下來是一個指向右下角的圖標,它表示一個事件,而一個指向右上角的圖標表示中
斷和 DMA 輸出。這個咱們把它放在圖中主體更好理解。圖中的自動重載寄存器有影子寄
存器,它左邊有一個帶有「 U」字母的事件圖標,表示在更新事件生成時就把自動重載寄
存器內容拷貝到影子寄存器內,這個與上面分析是一致。寄存器右邊的事件圖標、中斷和
DMA 輸出圖標表示在自動重載寄存器值與計數器寄存器值相等時生成事件、中斷和 DMA輸出。
3d

 ①時鐘源
定時器要實現計數必須有個時鐘源,基本定時器時鐘只能來自內部時鐘,高級控制定
時器和通用定時器還能夠選擇外部時鐘源或者直接來自其餘定時器等待模式。咱們能夠通
RCC 專用時鐘配置寄存器(RCC_DCKCFGR)TIMPRE 位設置全部定時器的時鐘頻率,
咱們通常設置該位爲默認值 0,使得表 31-1 中可選的最大定時器時鐘爲 90MHz,即基本定
時器的內部時鐘(CK_INT)頻率爲 90MHz
基本定時器只能使用內部時鐘,當 TIM6 TIM7 控制寄存器 1(TIMx_CR1)CEN
1 時,啓動基本定時器,而且預分頻器的時鐘來源就是 CK_INT。對於高級控制定時器
和通用定時器的時鐘源能夠來找控制器外部時鐘、其餘定時器等等模式,較爲複雜,咱們
在相關章節會詳細介紹。
②控制器
定時器控制器控制實現定時器功能,控制定時器復位、使能、計數是其基礎功能,基
本定時器還專門用於 DAC 轉換觸發。
code

③計數器
基本定時器計數過程主要涉及到三個寄存器內容,分別是計數器寄存器(TIMx_CNT)
預分頻器寄存器(TIMx_PSC)、自動重載寄存器(TIMx_ARR),這三個寄存器都是 16 位有效
數字,便可設置值爲 0 65535
首先咱們來看圖 31-1 中預分頻器 PSC,它有一個輸入時鐘 CK_PSC 和一個輸出時鐘
CK_CNT。輸入時鐘 CK_PSC 來源於控制器部分,基本定時器只有內部時鐘源因此
CK_PSC 實際等於 CK_INT,即 90MHz。在不一樣應用場所,常常須要不一樣的定時頻率,通
過設置預分頻器 PSC 的值能夠很是方便獲得不一樣的 CK_CNT,實際計算爲: fCK_CNT
fCK_PSC/(PSC[15:0]+1)
31-2 是將預分頻器 PSC 的值從 1 改成 4 時計數器時鐘變化過程。原來是 1 分頻,
CK_PSC CK_CNT 頻率相同。向 TIMx_PSC 寄存器寫入新值時,並不會立刻更新
CK_CNT 輸出頻率,而是等到更新事件發生時,把 TIMx_PSC 寄存器值更新到影子寄存器
中,使其真正產生效果。更新爲 4 分頻後,在 CK_PSC 連續出現 4 個脈衝後 CK_CNT 才產
生一個脈衝。
blog

 

在定時器使能(CEN 1)時,計數器 COUNTER 根據 CK_CNT 頻率向上計數,即每來
一個 CK_CNT 脈衝, TIMx_CNT 值就加 1。當 TIMx_CNT 值與 TIMx_ARR 的設定值相等
時就自動生成事件並 TIMx_CNT 自動清零,而後自動從新開始計數,如此重複以上過程。
爲此可見,咱們只要設置 CK_PSC TIMx_ARR 這兩個寄存器的值就能夠控制事件生成的
時間,而咱們通常的應用程序就是在事件生成的回調函數中運行的。在 TIMx_CNT 遞增至
TIMx_ARR 值相等,咱們叫作爲定時器上溢。
自動重載寄存器 TIMx_ARR 用來存放於計數器值比較的數值,若是兩個數值相等就生
成事件,將相關事件標誌位置位,生成 DMA 和中斷輸出。 TIMx_ARR 有影子寄存器,可
以經過 TIMx_CR1 寄存器的 ARPE 位控制影子寄存器功能,若是 ARPE 位置 1,影子寄存
器有效,只有在事件更新時才把 TIMx_ARR 值賦給影子寄存器。若是 ARPE 位爲 0,修改
TIMx_ARR 值立刻有效。
事件

 

 爲何要加1,由於參考手冊這樣說的啊:ip

計數器、 自動重裝載寄存器
定時器使能(CEN 置 1)後,計數器 CNT在CK_CNT 驅
動下向上計數,當 TIMx_CNT 值不 TIMx_ARR 的設
定值相等時就自動生成事件並 TIMx_CNT 自動清零,
而後自動從新開始計數,如此重複以上過程。

 

定時時間的計算如何實現0.5S的定時 ?

思考咱們基本定時器的最小定時時間(除了零以外)是多少?分母最大,分子最小的時刻,1/90M hz=0.01111us=11nm;最大定時時間,分母最小,分子最大,65536/(90M/65536)=47.7s。

定時器初始化結構體詳解
標準庫函數對定時器外設創建了四個初始化結構體,基本定時器只用到其中一個即
TIM_TimeBaseInitTypeDef,該結構體成員用於設置定時器基本工做參數,並由定時器基本
初始化配置函數 TIM_TimeBaseInit 調用,這些設定參數將會設置定時器相應的寄存器,達
到配置定時器工做環境的目的。這一章咱們只介紹 TIM_TimeBaseInitTypeDef 結構體,其
他結構體將在相關章節介紹。
初始化結構體和初始化庫函數配合使用是標準庫精髓所在,理解了初始化結構體每一個
成員意義基本上就能夠對該外設運用自如了。初始化結構體定義在 stm32f4xx_tim.h 文件中,
初始化庫函數定義在 stm32f4xx_tim.c 文件中,編程時咱們能夠結合這兩個文件內註釋使用。

(1) TIM_Prescaler:定時器預分頻器設置,時鐘源經該預分頻器纔是定時器時鐘,它設定
TIMx_PSC 寄存器的值。可設置範圍爲 0 65535,實現 1 65536 分頻。
(2) TIM_CounterMode:定時器計數方式,但是在爲向上計數、向下計數以及三種中心對
齊模式。基本定時器只能是向上計數,即 TIMx_CNT 只能從 0 開始遞增,而且無需初
始化。
(3) TIM_Period:定時器週期,實際就是設定自動重載寄存器的值,在事件生成時更新到
影子寄存器。可設置範圍爲 0 65535
(4) TIM_ClockDivision:時鐘分頻,設置定時器時鐘 CK_INT 頻率與數字濾波器採樣時鐘
頻率分頻比,基本定時器沒有此功能,不用設置。
(5) TIM_RepetitionCounter:重複計數器,屬於高級控制寄存器專用寄存器位,利用它可
以很是容易控制輸出 PWM 的個數。這裏不用設置。

雖然定時器基本初始化結構體有 5 個成員,但對於基本定時器只需設置其中兩個就可
以,想一想使用基本定時器就是簡單。

編程實戰:

//#define BASIC_TIM                   TIM6
//#define BASIC_TIM_CLK               RCC_APB1Periph_TIM6

#define BASIC_TIM                   TIM7
#define BASIC_TIM_CLK               RCC_APB1Periph_TIM7

#define BASIC_TIM_IRQn                    TIM7_IRQn
#define BASIC_TIM_IRQHandler    TIM7_IRQHandler


//#define BASIC_TIM_IRQn                    TIM6_DAC_IRQn
//#define BASIC_TIM_IRQHandler    TIM6_DAC_IRQHandler

BH給的課後練習,歷程使用TIM6,完成TIM7的基本定時器,更改中斷源和中斷服務函數名,這個不是單獨只把以前歷程中的6改爲7就行,由於中斷源有些變化,那麼咱們有沒辦法去掉這樣的弊病呢?在我以前用山外庫的時候,就作得很好,因此,我以爲,我須要寫一個更好用的庫函數版本:

經過本身用宏把後端給替換了,這樣在編程的時候,就真的是隻用6改爲7就行,這樣的庫函數對新手使用上來講更方便。

初始化處先清除確保不受干擾,再開啓更新中斷,最後使能定時器:

中斷服務函數中,先確保發生了中斷,而後反轉LED,最後清除中斷髮生標誌,確保下一次中斷服務函數正常工做。

 又發現一點能夠改進的地方:

這裏還須要庫函數使用者去計算時間,而做爲專業的庫函數,應該是本身寫好一個基準,好比定時1ms的,而後我調用一個函數 dealy_ms(50);就表示精確延時50ms,這裏也是能夠經過庫函數配置好一個最小時間基準例如ms級別的,經過形參傳遞參數,而後用這個形參倍數於以前的時間基準,這樣的庫函數,明顯更好。

相關文章
相關標籤/搜索