stm32F4 時基定時器(2)
找了很多的資料,終于把時基定時器的給弄懂了,沒有使用庫函數(shù),直接操作寄存器。
下面介紹STM32中的systick,Systick部分內(nèi)容屬于NVIC控制部分,一共有4個寄存器,名稱和地址分別是:
STK_CSR, 0xE000E010--控制寄存器
STK_LOAD, 0xE000E014--重載寄存器
STK_VAL, 0xE000E018--當(dāng)前值寄存器
STK_CALRB, 0xE000E01C-- 校準(zhǔn)值寄存器
首先看STK_CSR控制寄存器:寄存器內(nèi)有4個位t具有意義:
第0位:ENABLE,Systick使能位(0:關(guān)閉Systick功能;1:開啟Systick功能)
第1位:TICKINT,Systick中斷使能位 (0:關(guān)閉Systick中斷;1:開啟Systick中斷)
第2位:CLKSOURCE,Systick時鐘源選擇(0:使用HCLK/8作為Systick時鐘;1:使用HCLK作為Systick時鐘)
第3位:COUNTFLAG,Systick計數(shù)比較標(biāo)志,如果在上次讀取本寄存器后,SysTick已經(jīng)數(shù)到了0,則該位為1。如果讀取該位,該位將自動清零
STK_VAL當(dāng)前值寄存器:
也是個24位的寄存器,讀取時返回當(dāng)前倒計數(shù)的值,寫它則使之清零,同時還會清除在SysTick控制及狀態(tài)寄存器中的COUNTFLAG標(biāo)志。
STK_CALRB 校準(zhǔn)值寄存器:
這個寄存器好像目前的水平我還用不到,大體意思明白點,
位31NOREF:1=沒有外部參考時鐘(STCLK不可用)0=外部參考時鐘可用
位30 SKEW:1=校準(zhǔn)值不是準(zhǔn)確的1ms 0=校準(zhǔn)值是準(zhǔn)確的1ms
STK_LOAD 重載寄存器:
Systick是一個遞減的定時器,當(dāng)定時器遞減至0時,重載寄存器中的值就會被重裝載,繼續(xù)開始遞減。STK_LOAD 重載寄存器是個24位的寄存器最大計數(shù)0xFFFFFF。
下面我們就應(yīng)用SysTick定時器來裸奔,把它作為一個定時器來用,還是老一套,在寄存器頭文件中添加定義寄存器:
#include "stm32f4_discovery.h"
#define CALIB (*((volatile unsigned long *)0xE000E01C))
#define VAL (*((volatile unsigned long *)0xE000E018))
#define LOAD (*((volatile unsigned long *)0xE000E014))
#define SYSTICK_CSR (*((volatile unsigned long *)0xE000E010))
typedef struct
{
__IO uint32_t CTRL; /*!< Offset: 0x000 (R/W) SysTick Control and Status Register */
__IO uint32_t LOAD; /*!< Offset: 0x004 (R/W) SysTick Reload Value Register */
__IO uint32_t VAL; /*!< Offset: 0x008 (R/W) SysTick Current Value Register */
__I uint32_t CALIB; /*!< Offset: 0x00C (R/ ) SysTick Calibration Register */
} SysTick_Type;
#define SysTick ((SysTick_Type *) SysTick_BASE )
void GPIO_Configuration(void)
{
GPIO_InitTypeDef GPIO_InitStructure;
RCC_AHB1PeriphClockCmd(RCC_AHB1Periph_GPIOE, ENABLE);
/* Configure PD12, PD13, PD14 and PD15 in output pushpull mode */
GPIO_InitStructure.GPIO_Pin = GPIO_Pin_7 " GPIO_Pin_8;
GPIO_InitStructure.GPIO_Mode = GPIO_Mode_OUT;
GPIO_InitStructure.GPIO_OType = GPIO_OType_PP;
GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz;
GPIO_InitStructure.GPIO_PuPd = GPIO_PuPd_NOPULL;
GPIO_Init(GPIOE, &GPIO_InitStructure);
}
void SysTick_Configuration(void)
{
SysTick->VAL =0; //當(dāng)前值寄存器
SysTick->LOAD=72000; //重裝載寄存器,中斷一次1mS
SysTick->CTRL|=0x07;// HCLK作為Systick時鐘,Systick中斷使能位
}
__IO uint32_t TimingDelay = 20000;
int main()
{
while(1)
{
if(TimingDelay == 0)
{
TimingDelay = 20000;
GPIO_SetBits(GPIOE, GPIO_Pin_8);
}
}
}
void SysTick_Handler(void)
{
SysTick->VAL =0;
if (TimingDelay != 0x00)
TimingDelay--;
}