SysTick初始化函数和中断服务函数详解

描述

16.3.2.2.3 SysTick初始化函数

列表3:代码清单17‑3 SysTick初始化函数

左右滑动查看完整内容

 

/**
* @brief 启动系统滴答计时器 SysTick
* @param IT_frequency: 滴答计时器每秒的中断次数
* @retval 无
*/
voidSysTick_Init(uint32_t IT_frequency)
{
/* SystemCoreClock 在这里默认为 200M
* SystemCoreClock / 1000 1ms 中断一次
* SystemCoreClock / 100000 10us 中断一次
* SystemCoreClock / 1000000 1us 中断一次
*/
IT_Period = SystemCoreClock / IT_frequency;
uint32_t err = SysTick_Config (IT_Period);
assert(err==0); //capture error
}

 

SysTick_Init函数里面调用了SysTick_Config()这个固件库函数,通过设置该固件库函数的形参,就决定了系统定时器经过多少时间就产生一次中断。

16.3.2.2.4 SysTick中断时间的计算

SysTick定时器的计数器是向下递减计数的,计数一次的时间TDEC=1/CLKICLK,当重装载寄存器中的值VALUELOAD减到0的时候,产生中断,可知中断一次的时间TINT=VALUELOAD*TDEC=VALUE LOAD/CLKICLK,其中CLKICLK=200MHZ。

如果设置VALUELOAD为200,那中断一次的时间TINT=200/200M=1us。不过1us的中断没啥意义,整个程序的重心都花在进出中断上了,根本没有时间处理其他的任务。

左右滑动查看完整内容

 

IT_Period = SystemCoreClock / IT_frequency; //IT_frequency 为中断的频率 (单位为
Hz)
SysTick_Config(IT_Period) //IT_Period 为中断一次的时间 (单位为时钟节拍数)

 

SysTick_Config()的形参我们配置为 IT_Period。例如,当IT_frequency为1000,IT_Period=SystemCoreClock/IT_frequency=200M/1000=200K,从刚刚分析我们知道这个形参的值最终是写到重装载寄存器LOAD中的,从而可知我们现在把SysTick定时器中断一次的时间TINT=200k/200M=1ms。

16.3.2.2.5 SysTick定时时间的计算

当设置好中断时间TINT后,我们可以设置一个变量t,用来记录进入中断的次数,那么变量t乘以中断的时间TINT就可以计算出需要定时的时间。

16.3.2.2.6 SysTick定时函数

现在我们定义一个延时函数,类似官方的延时函数“R_BSP_SoftwareDelay”,形参为delay和unit,这两个形参相乘就得出我们需要的延时时间 TSUM,因此进入中断的次数 t=TSUM/TINT。

列表4:代码清单17‑4 SysTick延时函数

左右滑动查看完整内容

 

/**
* @brief 延时程序
* @param delay: 延时的单位时间
* @param unit: 延时的单位
* @retval 无
*/


voidSysTick_Delay(uint32_t delay, sys_delay_units_t unit)
{
uint32_t SumTime = delay * unit; //计算总延时时间 (单位为时钟节拍数)
IT_nums = SumTime/IT_Period;
while (IT_nums != 0);
}

 

SysTick_Delay()中我们等待IT_nums为0,当IT_nums为0的时候表示延时时间到。变量 IT_nums在中断函数中递减,即SysTick每进一次中断即TINT的时间IT_nums递减一次。

16.3.2.2.7 sys_delay_units_t

列表5:代码清单17‑5 sys_delay_units_t

左右滑动查看完整内容

 

typedefenum
{
SYS_DELAY_UNITS_SECONDS = 200000000, ///< Requested delay amount␣
→is in seconds
SYS_DELAY_UNITS_MILLISECONDS = 200000, ///< Requested delay amount␣
→is in milliseconds
SYS_DELAY_UNITS_MICROSECONDS = 200///< Requested delay amount␣
→is in microseconds
} sys_delay_units_t;

 

16.3.2.2.8 SysTick中断服务函数

列表6:代码清单17‑6 SysTick中断服务函数

左右滑动查看完整内容

 

/**
* @brief SysTick 的中断服务函数
* @param 无
* @retval 无
*/
externvoidSysTick_Handler(void); //需要先 extern 声明一下避免编译器警告
voidSysTick_Handler(void)
{
if (IT_nums != 0x00)
{
IT_nums--;
}
}

 

16.3.2.2.9 hal_entry入口函数

列表7:

代码清单17‑7由main函数转入的hal_entry函数

左右滑动查看完整内容

 

voidhal_entry(void)
{
/* TODO: add your own code here */
R_BSP_PinAccessEnable (); //启用对 PFS 寄存器的访问, 因为后面写 IO 口都用
BSP 内联函数
SysTick_Init(1000); //初始化系统时钟, 设置中断频率为 1000Hz


while (1)
{
R_BSP_PinWrite (LED_G, BSP_IO_LEVEL_LOW); //点亮绿色 LED
SysTick_Delay(1, SYS_DELAY_UNITS_SECONDS); //延时 1s
R_BSP_PinWrite (LED_G, BSP_IO_LEVEL_HIGH); //熄灭绿色 LED
SysTick_Delay(1, SYS_DELAY_UNITS_SECONDS); //延时 1s
}
#if BSP_TZ_SECURE_BUILD
/* Enter non-secure code */
R_BSP_NonSecureEnter();
#endif
}

 

主函数中初始化了SysTick,然后在一个while循环中以1s的频率让LED闪烁。

函数

打开APP阅读更多精彩内容
声明:本文内容及配图由入驻作者撰写或者入驻合作网站授权转载。文章观点仅代表作者本人,不代表电子发烧友网立场。文章及其配图仅供工程师学习之用,如有内容侵权或者其他违规问题,请联系本站处理。 举报投诉

全部0条评论

快来发表一下你的评论吧 !

×
20
完善资料,
赚取积分