当前位置:   article > 正文

STM32笔记之 Systick(滴答定时器)_systick_init

systick_init

写在前面: 本文章旨在总结备份、方便以后查询,由于是个人总结,如有不对,欢迎指正;另外,内容大部分来自网络、书籍、和各类手册,如若侵权请告知,马上删帖致歉。

 

目录

一、Systick介绍

二、Systick时钟分析

三、Systick时钟节拍代码实现


 

一、Systick介绍

ARM Cortex-M3内核中有一个 Systick定时器,它是一个 24bit的定时器,可用于系统中的时钟节拍,因此系统滴答定时器能用于 Cortex‐M3处理器芯片的快速移植(ps:正是因为这一特点,大部分在运行 RTOS都基于 Systick来用作时钟节拍,以便移植)

 

附上两张 Cortex-M3简视图,同时再附上两个关于 Cortex-M3核心了解的链接:

《STM32F10xxx Cortex-M3编程手册》

《Cortex™-M3技术参考手册》

 

二、Systick时钟分析

根据时钟树,我们可以看见在 SYSCLK出来后,可能会认为滴答定时器是系统时钟的 1/8,其实不是,滴答定时器的时钟既可以是 HCLK/8,也可以是 HCLK,这个是通过 CTRL寄存器进行设定的(可以通过查看《STM32F10xxx Cortex-M3编程手册》找到)如下图所示:

Systick 相关寄存器介绍:

实现思路:利用 systick定时器为递减计数器,设定初值并使能它后,它会每过一个系统时钟周期计数器进行减,直到计数到 0时,SysTick计数器会自动重装初值并继续计数,同时触发中断。

初值计数:根据上一篇配置的时钟使用 72MHz作为系统时钟,那么计数器每次减一所用的时间是 1/72MHz,假设我们的计数器初值是72000,那么每次计数器减到 0,时间经过(1/72M) * 72000 = 0.001,即1ms。(可以理解为:72MHz的时钟频率,那他表示 1s计数72000000次(周期数),那 1ms就计数72000次,所以计数值为72000) 

 

三、Systick时钟节拍代码实现

bsp.c 源文件

  1. #include "bsp.h"
  2. static __IO u32 TimingDelay = 0;
  3. /* Setup SysTick Timer for 1 msec interrupts.
  4. ------------------------------------------
  5. 1. The SysTick_Config() function is a CMSIS function which configure:
  6. - The SysTick Reload register with value passed as function parameter.
  7. - Configure the SysTick IRQ priority to the lowest value (0x0F).
  8. - Reset the SysTick Counter register.
  9. - Configure the SysTick Counter clock source to be Core Clock Source (HCLK).
  10. - Enable the SysTick Interrupt.
  11. - Start the SysTick Counter.
  12. 2. You can change the SysTick Clock source to be HCLK_Div8 by calling the
  13. SysTick_CLKSourceConfig(SysTick_CLKSource_HCLK_Div8) just after the
  14. SysTick_Config() function call. The SysTick_CLKSourceConfig() is defined
  15. inside the misc.c file.
  16. 3. You can change the SysTick IRQ priority by calling the
  17. NVIC_SetPriority(SysTick_IRQn,...) just after the SysTick_Config() function
  18. call. The NVIC_SetPriority() is defined inside the core_cm3.h file.
  19. 4. To adjust the SysTick time base, use the following formula:
  20. Reload Value = SysTick Counter Clock (Hz) x Desired Time base (s)
  21. - Reload Value is the parameter to be passed for SysTick_Config() function
  22. - Reload Value should not exceed 0xFFFFFF
  23. */
  24. /************************************************
  25. 函数名称 : SysTick_Init
  26. 功 能 : 启动系统滴答定时器 SysTick
  27. 参 数 : 无
  28. 返 回 值 : 无
  29. *************************************************/
  30. void SysTick_Init(void)
  31. {
  32. /* SystemCoreClock / 1000 1ms中断一次
  33. * SystemCoreClock / 100000 10us中断一次
  34. * SystemCoreClock / 1000000 1us中断一次
  35. */
  36. /* 嘀嗒定时器每计数一次为 1/72M,此处计数 72个数,即1uS中断一次 */
  37. if(SysTick_Config(SystemCoreClock / 1000000)) // ST V3.5.0库版本
  38. {
  39. /* Capture error */
  40. while(1);
  41. }
  42. // 关闭滴答定时器
  43. SysTick->CTRL &= ~SysTick_CTRL_ENABLE_Msk;
  44. }
  45. /************************************************
  46. 函数名称 : Delay_us
  47. 功 能 : us延时程序,1us为一个单位
  48. 参 数 : nTime ---- 时间次数
  49. 返 回 值 : 无
  50. *************************************************/
  51. void Delay_us( __IO u32 nTime )
  52. {
  53. TimingDelay = nTime;
  54. // 使能滴答定时器
  55. SysTick->CTRL |= SysTick_CTRL_ENABLE_Msk;
  56. while( TimingDelay != 0 );
  57. // 关闭滴答定时器
  58. SysTick->CTRL &= ~SysTick_CTRL_ENABLE_Msk;
  59. }
  60. /************************************************
  61. 函数名称 : TimingDelay_Decrement
  62. 功 能 : 获取节拍程序
  63. 参 数 : 无
  64. 返 回 值 : 无
  65. 注 意 : 在 SysTick 中断函数 SysTick_Handler()调用
  66. *************************************************/
  67. void TimingDelay_Decrement(void)
  68. {
  69. if(TimingDelay != 0x00)
  70. {
  71. TimingDelay--;
  72. }
  73. }
  74. /*---------------------------- END OF FILE ----------------------------*/

根据上面的注释,选择对应参数传参进行 SysTick_Config() 配置,本篇是制作以微秒为单位的延时定时器,所以传入的参数为 SystemCoreClock / 1000000次,SystemCoreClock的数值,在上一篇 STM32笔记之系统时钟上有讲到

 

bsp.h 头文件

  1. #ifndef __BSP_H
  2. #define __BSP_H
  3. #include "stm32f10x.h"
  4. void SysTick_Init(void);
  5. void Delay_us( __IO u32 nTime );
  6. void TimingDelay_Decrement(void);
  7. void SystemSoftReset(void);
  8. #endif /* __BSP_H */
  9. /*---------------------------- END OF FILE ----------------------------*/

 

接着我们再在 stm32f10x_it.c 文件中的 SysTick_Handler()函数里调用 TimingDelay_Decrement()函数进行计数递减

  1. /**
  2. * @brief This function handles SysTick Handler.
  3. * @param None
  4. * @retval None
  5. */
  6. void SysTick_Handler(void)
  7. {
  8. TimingDelay_Decrement();
  9. }

最后,我们在主函数中调用函数 SysTick_Init() 完成初始化,就可以使用利用 Systick获取节拍的时钟延时 Delay_us()函数了

声明:本文内容由网友自发贡献,不代表【wpsshop博客】立场,版权归原作者所有,本站不承担相应法律责任。如您发现有侵权的内容,请联系我们。转载请注明出处:https://www.wpsshop.cn/w/从前慢现在也慢/article/detail/285211
推荐阅读
相关标签
  

闽ICP备14008679号