#include "bsp.h" #define DEM_CR_TRCENA (1 << 24) #define DWT_CR_CYCCNTENA (1 << 0)' v: w% K' |) D ! i: X- A4 P5 i! |7 t9 S1 ~ ! P' ~- _" V9 d2 \7 B- x* k8 R /** * @description: 初始化DWT,被Bsp_Init调用: @: k. n$ B/ l1 G @ * @return {*}, d! g8 K9 [6 c* I */ void Bsp_Dwt_Init(void). l; D" c) H$ H/ \. D" K# G6 m4 o {2 ~. ]8 k; S& U j# z DEM_CR |= (unsigned int)DEM_CR_TRCENA; /* Enable Cortex-M's DWT CYCCNT reg. */! g8 x, }1 N! X4 |$ j' S" W DWT_CYCCNT = (unsigned int)0u;: c6 d f' n g2 o$ a3 I( n* w DWT_CR |= (unsigned int)DWT_CR_CYCCNTENA;# q b) |5 f, { I- k4 o, I }5 X/ S9 x/ ?+ M" F void Bsp_Delay_Ms(uint32_t _ms) { Bsp_Delay_Us(1000* _ms);) ^ o$ g8 n/ w: B4 U7 z } 7 Y& G; |4 F$ ` void Bsp_Delay_Us(uint32_t _us) {! A/ [5 F8 o+ B* s$ X+ e: H, u+ y uint32_t tCnt, tDelayCnt; uint32_t tStart;/ E2 K/ ]+ @& _' X9 B2 W : R- s) A9 m$ F3 N5 V# a! L/ ~ tStart = DWT_CYCCNT; /* 刚进入时的计数器值 */ tCnt = 0;0 c9 q# V# W/ n" Y# E' t2 ~ tDelayCnt = _us * (SystemCoreClock / 1000000); /* 需要的节拍数 */ while(tCnt < tDelayCnt)1 b, w" H K( Z$ l6 x$ z& p+ o {* \. j# K6 P! J5 b4 n% Q, V/ N tCnt = DWT_CYCCNT - tStart; /* 求减过程中,如果发生第一次32位计数器重新计数,依然可以正确计算 */ , V# L. T$ j1 ^+ z0 L } } void Bsp_Delay_Dwt(uint32_t _dwt) { uint32_t tCnt, tDelayCnt; uint32_t tStart; 0 z1 Q. M9 I2 e& _7 F* h1 R+ X5 S tCnt = 0; tDelayCnt = _dwt; /* 需要的节拍数 */ " k- I9 K* P' z3 R% m$ x' j0 O tStart = DWT_CYCCNT; /* 刚进入时的计数器值 */ * C! H* k+ V" v8 b. r! \5 D8 ]9 ` while(tCnt < tDelayCnt)2 V8 s# V- x/ C& ]/ l {* E/ Y0 r: h( l8 f# |/ N9 x9 o2 @8 i tCnt = DWT_CYCCNT - tStart; /* 求减过程中,如果发生第一次32位计数器重新计数,依然可以正确计算 */ }5 Z1 m) k4 T: }3 V4 j" U: w } 3 Q1 Q, o S$ ]2 B" K. h# p9 R * i. o" S# X" D2 N% k1 j9 ?5 @ void HAL_Delay(uint32_t Delay)2 {# ~5 F0 [0 ^1 t { Bsp_Delay_Ms(Delay); }5 c. K5 u( c4 s+ I @' F; } + ]8 L" r( w6 ^: W F1 E& ]1 x HAL_StatusTypeDef HAL_InitTick (uint32_t TickPriority) {2 q' f9 m$ W' _$ M1 o return HAL_OK;3 y# k/ ] H5 Q }9 a0 @$ `. v. {$ A! X% } uint32_t HAL_GetTick (void) {3 J/ U: Q7 }. w2 H& X$ g static uint32_t ticks = 0U;6 E5 D) W O2 ^( v' E uint32_t i; if (osKernelGetState () == osKernelRunning) {0 _9 d# ^: z* Z0 S return ((uint32_t)osKernelGetTickCount ()); } : p! r( i# u1 w$ D/ H /* 如果RTX5还没有运行,采用下面方式 *// F+ M9 @4 s% D6 H' ]& H for (i = (SystemCoreClock >> 14U); i > 0U; i--) { __NOP(); __NOP(); __NOP(); __NOP(); __NOP(); __NOP();' u5 m& `& w/ Y* r- C/ K __NOP(); __NOP(); __NOP(); __NOP(); __NOP(); __NOP();7 R2 U$ X% z& A5 h# V8 P+ r }* j2 d* Q; k: v return ++ticks; } 8 r5 o3 z/ a* o/ y3 L % \4 m; U1 o. f5 M |
定时器剩余通道是否可以做PWM输出呢?
基于STM32双定时器+ADC+DMA实战经验分享
基于STM32的定时器触发ADC时可能遇到的情形
【NUCLEO-U545RE-Q评测】5. 基本计时器
基于STM32的定时器不按设定超时产生中断
基于stm32用两个16位定时器级联成32位定时器经验分享
基于STM32利用TIMER事件和栈帧体验中断响应经验分享
基于STM32的Timer 结合 DMA 2D 通道实现不同波形输出
基于STM32软件定时器+中断方式模拟PWM经验分享
基于STM32高精度定时器中single-shot计数模式不工作