你的浏览器版本过低,可能导致网站不能正常访问!
为了你能正常使用网站功能,请使用这些浏览器。

玩转STM32CubeMX | 定时器中断

[复制链接]
STMCU-管管 发布时间:2020-12-1 12:45
玩转STM32CubeMX | 定时器中断
1.定时器中断
# s: Q/ J9 N. }* f! B
# q% |$ E5 @* ~2 R# PSTM32的定时器功能十分强大,有高级定时器(TIM1和TIM8)、通用定时器(TIM2~TIM5)和基本定时器(TIM6和TIM7);本实验主要介绍难度适中的通用定时器,通用定时器是一个通过可编程预分频器驱动的16位自动装载计数器构成。它适用于多种场合,包括测量输入信号的脉冲长度(输入捕获)或者产生输出波形(输出比较和PWM)。使用定时器预分频器和RCC时钟控制器预分频器,脉冲长度和波形周期可以在几个微秒到几个毫秒间调整。每个定时器都是完全独立的,没有互相共享任何资源。
! B: @0 V' c: H: U4 O) l3 d! l通用TIMx (TIM2、TIM3、TIM4和TIM5)定时器功能包括:6 U/ m9 u7 F) m) {4 X  B

/ k7 t+ N5 V% f  X: X) ~2 ?4 F

4 ]: Z( d* B: M! q/ u- ~可编程的自由运行递减计算器( U  B# K) S0 q' V& o+ L
; P- Z8 H/ x2 a6 |6 \; ~% q

; u* J6 ~8 s& u) {条件复位:当递减计数器的值小于0x40,则产生复位;当递减计数器在窗口外被重新装载,则产生复位4 L1 U  o5 j7 d, `3 k$ w3 o+ N
0 o5 ]4 y& Z: L9 C& |- D. d

# u( Q9 ], o; y$ m3 e2 v& y如果启动了看门狗并且允许中断,当递减计数器等于0x40时产生早期唤醒中断(EWI),它可用于重新装载计数器以避免WWDG复位
/ G  S) S( p! O. V! [
5 M: q1 _- K5 \8 b$ z; i* s) _: ~
" Z) z; X+ E3 P- q; S+ i& d
16位向上、向下、向上/向下自动装载计数器, G* [' S) b: Z* z

+ `7 t3 A, a) O4 ?& A8 o

( _8 d: }( |0 E- B6 o: w& o* P16位可编程(可以实时修改)预分频器,计数器时钟频率的分频系数为1~65536之间的任意数值
: \# C7 D% I8 Q3 O7 ^9 I; D$ x% [! [
, C9 f  f$ N: A) d( c
4个独立通道:输入捕获;输出比较;PWM生成(边缘或中间对齐模式);单脉冲模式输出
; u/ P7 {- ]3 m6 s; K
9 V8 H$ j+ p4 J/ m9 X( z8 y& `

4 |/ N4 K7 y' w/ H' J2 v' Q使用外部信号控制定时器和定时器互连的同步电路
& d: f0 d7 Q* a* Y4 y9 T2 G* ~! p7 U8 s6 Y) h8 u3 o5 u& ?. i

) C- K# Z3 e* t# U; m% M; K- s. B8 {如下事件发生时产生中断/DMA:计数器向上溢出/向下溢出,计数器初始化(通过软件或者内部/外部触发);触发事件(计数器启动、停止、初始化或者由内部/外部触发计数);输入捕获;输出比较' S, e. r8 x% y( m/ N! q

6 e$ V0 f! ~7 x
0 y/ s! R  M$ R  ^( D$ |3 z1 G4 l2 _
支持针对定位的增量(正交)编码器和霍尔传感器电路( l5 k1 h5 Y" Z+ R0 R9 y0 A
9 z; \+ @0 p* f/ P4 B+ o3 L" t
* \- u: M+ o- T# z! J
触发输入作为外部时钟或者按周期的电流管理
9 Q5 v' G6 t5 A) o+ d$ m3 E* ?7 U

" f3 Q, \- u+ Z, N通用定时器框图
' {8 }! ^! K7 D/ ]# `
1.png
定时器时基部分
: V. B! n" F% t  U* `5 j; d/ R5 B
2.png
2.硬件设计1 \% z2 d# x" D5 V1 h& `# o$ w

) k! v/ C9 {4 r4 W

, ]4 N& Y( d% r  [' d# p' R  m( F! w& E2 _. h1 x$ P

! t& k5 d1 e( p" _0 l* F" v: i本实验通过TIM3的中断来控制D1的亮灭,需要用到的硬件资源有:
- E- r8 m0 O* o7 A
' X$ T+ ^, N" |* |& C, d

( O! }. F1 p$ x4 e& W% K·指示灯D1和D2
5 H0 ~- o5 W  l5 g6 G8 N·定时器TIM3) [! M* r1 q' M. B2 ~. O( P- P
3.png
3.软件设计
' ?+ C2 X0 p7 F& ^( ?" u3 I$ E% w; t" n, z5 ?2 V
% w6 y* V# C! L# s- J
3.1 STM32CubeMX设置
+ I' ~1 D" \7 m- q  \6 O& _' p8 o# G; `

' N+ u$ {# T6 d% ]; j➡️ RCC设置外接HSE,时钟设置为72M;TIM3的时钟挂载在APB1 Time Clocks上为72MHz
1 {" U5 t0 _. O( s: m* i- A: w0 l" d3 @

% J( U$ v& y2 V, @% e) C➡️ PC0和PC1设置为GPIO推挽输出模式、上拉、高速、默认输出电平为高电平- C4 U2 {7 C- t' O
; ]4 ~% N+ Y- g; \! E/ h0 c  {
1 k) D/ B$ x0 w7 T! K' s
➡️ 激活TIM3定时器,时钟源选择为内部时钟,PSC预分频设置为7200-1,向上计数,自动重装载值(ARR)设置为10000-1,在NVIC设置中激活TIM3定时器中断;根据公式可算出:计数器时钟CK_CNT = 72M/7200 = 10000Hz,计时器中断时间为 ARR/10000 = 1s
: {0 a, [) j9 r1 {9 _
4.png
➡️输入工程名,选择路径(不要有中文),选择MDK-ARM V5;勾选Generated periphera initialization as a pair of ‘.c/.h’ files per IP ;点击GENERATE CODE,生成工程代码( B. e8 z8 A8 p. i" u5 G+ V
: g' z2 K% l. D& {# _2 ^
7 T& Y' J+ W% Q9 Z! `& H& X
3.2 MDK-ARM软件编程* z5 O( [( b. c9 x6 ^# X/ H, p% z
➡️ 在tim.c文件中可以看到定时器的初始化函数
5 Y$ h  r6 R# a' z4 b
  1. void MX_TIM3_Init(void){/ ?5 e- @5 \* M) o8 u5 Y7 ~3 n
  2.   TIM_ClockConfigTypeDef sClockSourceConfig = {0};4 o( a; F7 f' l  i1 \; K
  3.   TIM_MasterConfigTypeDef sMasterConfig = {0};- _1 g, l6 w% W: B# A2 N5 n% q
  4. " T# @) `( v4 g' Z
  5.   htim3.Instance = TIM3;
    , F; ^; r. S4 ?4 f
  6.   htim3.Init.Prescaler = 7200-1;
    ; @! x, N& d  y
  7.   htim3.Init.CounterMode = TIM_COUNTERMODE_UP;
    ; z7 w' M% G' ?  Q0 u
  8.   htim3.Init.Period = 10000-1;
    " D7 r3 D0 k* i" q- ]( b. m
  9.   htim3.Init.ClockDivision = TIM_CLOCKDIVISION_DIV1;* a  l- Z' r3 X
  10.   htim3.Init.AutoReloadPreload = TIM_AUTORELOAD_PRELOAD_ENABLE;
    . f' H1 P) E+ n- V
  11.   if (HAL_TIM_Base_Init(&htim3) != HAL_OK){9 d, E3 g3 f; D8 k$ n1 m
  12.     Error_Handler();+ H! z; Y9 ^# |$ m! C
  13.   }! d3 Y7 N5 d4 A% i
  14.   sClockSourceConfig.ClockSource = TIM_CLOCKSOURCE_INTERNAL;
    " N8 ^2 H+ ]: ~; S" D9 C9 a
  15.   if (HAL_TIM_ConfigClockSource(&htim3, &sClockSourceConfig) != HAL_OK){. U" V( J# q( K5 ^9 s0 c! T
  16.     Error_Handler();
    # H: p& x! W: C
  17.   }
    ( }/ p: L: r1 |1 |- C$ M* F- l
  18.   sMasterConfig.MasterOutputTrigger = TIM_TRGO_RESET;2 d2 O' W2 Z& ^1 I0 T8 q% Z
  19.   sMasterConfig.MasterSlaveMode = TIM_MASTERSLAVEMODE_DISABLE;
    , @2 Y( i& @- [, r: [
  20.   if (HAL_TIMEx_MasterConfigSynchronization(&htim3, &sMasterConfig) != HAL_OK){
    ( l/ U  d; f$ N" Y; b  T1 J
  21.     Error_Handler();
    : O/ Q" x" n6 ~8 n& s+ q$ g
  22.   }' M' W% s; d7 T
  23. }
复制代码
找到弱符号周期运行回调函数原型,并在tim.c中自定义该回调函数
$ m/ K5 W# D% S" r$ y__weak void HAL_TIM_PeriodElapsedCallback(TIM_HandleTypeDef *htim)
- t) C9 S$ J/ y* \- I9 V
  1. void HAL_TIM_PeriodElapsedCallback(TIM_HandleTypeDef *htim){  i( U# |, Q+ N3 g5 O: ?* _
  2.   if(htim == &htim3){
    + T& @+ {- p' N2 `
  3.     //LED1状态每1s翻转一次
    ! I+ j+ v2 {% g# S" E6 u( a
  4.     HAL_GPIO_TogglePin(GPIOC,GPIO_PIN_0);          R& M- M) p: p0 k+ f$ C" g
  5.   }) ^2 w5 |9 v  u' X' V* y0 n
  6. }
复制代码
➡️ 在main函数中编写相关代码,在while中使LED2每500ms翻转一次
: B" u0 o. C3 J
  1. int main(void){7 ~4 w( |, {% L
  2.   HAL_Init();7 Q* }" X# [! }, V" P$ V3 f
  3.   SystemClock_Config();
    " g6 |  ^9 I% k: P# C, G
  4.   MX_GPIO_Init();, v7 `  R1 O6 J
  5.   MX_TIM3_Init();5 S: I* y5 B, N; ~# |+ y& b( e
  6.   //启动定时器中断模式计数) B- l6 {2 L5 O: ?/ G- u: c/ @
  7.   HAL_TIM_Base_Start_IT(&htim3);               
    % g7 J7 @1 O. X$ i8 D+ h
  8.   while (1){
    : C; b, k" K9 h  i2 M* s! X3 V
  9.     //LED2状态每500ms翻转一次  K6 r" X3 G' Z' ^! ^/ a5 i: [9 t
  10.     HAL_GPIO_TogglePin(GPIOC,GPIO_PIN_1);        - G9 u  J0 J- k' p' q
  11.     HAL_Delay(500);. q. S2 Q+ u# d7 Y7 p8 Q5 b
  12.   }
    $ m) w7 U- Q7 J- \
  13. }
复制代码
4.下载验证
: J) E& t6 e8 p4 D& u' j' G8 D) g1 a编译无误后下载到开发板,可以看到LED1每1s状态翻转一次,LED2每500ms状态翻转一次
; A- @$ `" h) @  G" T
! m8 B+ {3 ]$ D0 W% W  p
收藏 评论0 发布时间:2020-12-1 12:45

举报

0个回答

所属标签

关于
我们是谁
投资者关系
意法半导体可持续发展举措
创新与技术
意法半导体官网
联系我们
联系ST分支机构
寻找销售人员和分销渠道
社区
媒体中心
活动与培训
隐私策略
隐私策略
Cookies管理
行使您的权利
官方最新发布
STM32N6 AI生态系统
STM32MCU,MPU高性能GUI
ST ACEPACK电源模块
意法半导体生物传感器
STM32Cube扩展软件包
关注我们
st-img 微信公众号
st-img 手机版