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

经验分享 | STM32CubeMX 生成时钟获取函数的分析

[复制链接]
STMCU小助手 发布时间:2025-7-30 16:49
$ m- s( W' o" n- c* s! G
$ l) T7 {$ j4 z
1. 问题! ?- v; C$ I( |5 `  G1 }' d
STM32CubeMX 升级到了 V6.13.0 ,与此同时 STM32Cube_FW_H7 也升级到了 V1.12.0 ,在时钟获取数组的定义中出现了问题,造成的问题现象是串口输出内容乱码,经过和 V6.12.1+ STM32Cube_FW_H7_V1.11.2 生成的代码对比,发现是时钟获取函数的数组出现的问题,修改之后即可正常。# q5 r! D: e! M& d

* Q! e. P) z% l) P  T- @/ M

/ `9 N4 ]1 j8 J4 B2. 如何复现
5 U2 I/ `# s7 ]6 r" g2 Q在 ST 官网上下载 STM32CubeMX 6.13.0 链接:Here,选择器件型号为 STM32H743ZIT6,使能 USART3 这个外设,选择使用 STM32Cube_FW_H7_V1.12.0 库来生成代码之后,串口打印出来的内容就是乱码。
( p& X6 s9 I: O$ j6 E. P9 U. d( @2 Z1 k

3 ^/ M- j+ ?! |& u0 A! [时钟配置如下图 1 所示。
2 l) M4 M/ w5 R$ W( I! Y) r
14.png
图1. 默认时钟配置
& h& N8 w7 ?, P0 N7 `- U' \
2.1. 代码分析# X7 x( s- T* b& o- q( f
首先,让我们看一下,不同的版本在生成代码中的主要区别,主要是 D1CorePrescTable 这个数组的内容有变化。5 \  t! W" W! B+ I* r4 @( i* m+ {
15.png
图2. 生成代码对比
9 L! K4 Z1 R$ j- F
3 |2 f$ J* J1 }. D% a2 W8 b& o+ D1 {
由上图可见,数组 D1CorePrescTable 的【4 : 7】内容由原来的{1,2,3,4}变成了 {0,0,0,0},那么这个数组是做什么用的,又为什么会对串口有影响呢?让我们来分析一下代码。, ]$ ~! c! m1 x

; v# u% d3 |' j7 Q
0 p- Q2 i# @2 E0 }" O0 ~2 b$ i0 q$ q
在串口初始化中有如下调用关系:
. Q$ T8 }0 d9 y' I: t  f+ T3 A/ b0 k# {( B/ f7 \/ G& R2 ~, ?  K. p

3 E. `- m4 c- HMX_USART3_UART_Init()àHAL_UART_Init()àUART_SetConfig()àHAL_RCC_GetPCLK1Freq()
" s0 ^) R( {; \
16.png
图3. 代码内容
+ i5 J8 q1 s, j

" ]+ F0 e' \% f! @  X由图 3 中的代码,我们可以看到,这里引用了 D1CorePrescTable 的内容,这里是如何引用的呢?其实是比较巧妙的。" i8 ^' @. n1 o: M% A! p
8 n. V8 e7 @# b+ O
* D! I4 h# e7 i0 o* \. w' a
我们首先看寄存器中是如何配置的。* \0 U2 `! z" [6 q6 J
17.png
图4. 寄存器描述

' ~8 P0 d/ m  T6 h  G8 [5 k2 o. Y3 b
% e1 D) G) k7 a4 I
寄存器中的 D2PPRE1[2:0]是配置 D2 域中 APB1 的分频系数,默认是 0xx,表示不分频;100 是 1/2 分频;101 是 1/4 分频 ; 以此类推。4 ?. m( r+ Y4 ^# Z2 S

6 ~6 I! H, {2 x" ^/ s( k9 ^

  n8 ~; s; w+ {在整个时钟树中的位置如图 5 所示
& K  p  T' Z/ a. _' u) D1 l
18.png
图5. 寄存器在时钟树中位置

4 A: O! g' ^: ?# G- }
# v( d" P6 d# {5 O' _3 O9 R5 s1 u
回到代码,我们单独截取其中一句话。  o6 }. T0 j. a% o7 z5 O! }' U4 ?3 h3 C
19.png
图6. 代码详细内容
; }* f6 v6 _- k# ]  `# Z
1 ]1 k5 D  f3 C% {  \# Y5 [" k0 K
其中的数值定义如图 7 所示. [  Z/ \4 x% Z& g7 q0 q- f
20.png
图7. 代码定义内容
# }/ C/ v6 @' ~2 l

1 Y  V% Q  W" }3 K, L; T这个地方通过读取寄存器(RCC->D2CFGR 中的 D2PPRE1)的配置,就能得到 APB1总线上的时钟分频参数,其先通过函数 HAL_RCC_GetHCLKFreq()得到系统时钟的频率,再将其进行右移操作(右移 1 位代表除以 2)。具体右移多少位就是通过查找 D1CorePrescTable 这个表来决定的。7 W7 X$ E& [: Z4 b' |6 P
+ M8 m2 o9 X$ J8 K' Y, G
9 o6 V: L. G# _/ H: u5 l
比如,这里如果是 1/2 分频,那么 RCC->D2CFGR & RCC_D2CFGR_D2PPRE1) >> RCC_D2CFGR_D2PPRE1_Pos 得到的结果就是 0b100,再和 0x1FU 进行“与操作”得到也是 0b100,即十进制的 4。通过正确的 D1CorePrescTable 表格,即可得到 D1CorePrescTable【4】=1,(注意数组是从 0 开始的)那么就是系统时钟进行右移 1 位的操作,得到除以 2 的效果。7 Q$ D& X0 a+ O; V1 n, b

9 {4 Y3 R1 c9 {
) a0 h) @, Y' ~2 O
正确数组:const uint8_t D1CorePrescTable[16] = {0, 0, 0, 0, 1, 2, 3, 4, 1, 2, 3, 4, 6, 7, 8, 9};
! ~; p; T2 s$ r, M3 ^' O
' h- g& Z6 m7 l, B  {0 t5 C

; v* S, m* L3 k3 Y1 \3 f+ z错误数组:const uint8_t D1CorePrescTable[16] = {0, 0, 0, 0, 0, 0, 0, 0, 1, 2, 3, 4, 6, 7, 8, 9};
$ g+ h' g/ o. ?8 L4 ~
8 V( ^: S! a! t2 @5 g$ n

# W: q# c; F: L但是如果是错误的数组,查到的就是 D1CorePrescTable【4】=0,这是不需要右移的,就是没有经过 1/2 分频,显然是不对正确的。/ R; v1 W! o' _5 a+ L" z

' ?0 X" R4 ]# |. j  C, b, w
" m9 T- x% T! n
这里还有个小问题:如果在 APB1 的时钟是没有经过分频的,那么 RCC->D2CFGR & RCC_D2CFGR_D2PPRE1) >> RCC_D2CFGR_D2PPRE1_Pos 得到的结果就总是小于 4 的(即 0xx,具体参见图 4),查表得到的结果就都是 0,也是没有问题的。但是1/2,1/4,1/8,1/16 这些分频系数都会出现计算错误,所以正确的方式就是手动修改这个参数即可解决问题。
' Y5 p# z$ ?+ w* Q. v% a. Z% d( m0 t$ y- D# @% v, P

- O4 S) t: i- `. Y3. 解决问题
7 `! n3 W. G$ m5 f* y手动修改 system_stm32h7xx.c 中的数组 D1CorePrescTable 中的【4 :7】中数据即可。
4 H5 i2 `% @) `$ J( P( e6 f5 G5 ~8 B; n% J$ @& n
+ I) [# V; o$ H
正确:const uint8_t D1CorePrescTable[16] = {0, 0, 0, 0, 1, 2, 3, 4, 1, 2, 3, 4, 6, 7, 8, 9};$ a, s  s5 B! \7 u# z1 x
7 ~$ z: c. J7 s; s4 f0 Z

# d) @+ Q" \! @6 O& Z同时,提交 bugzilla :197431 (此号码为 ST 内部使用,外部用户无法访问)。* C8 G1 J, d% Y+ j

5 \+ W. o1 u. b8 J9 m. r  i, ^* ]- J
! G2 C# G. T7 i& K9 V2 `+ \0 W
4. 小结( M5 `3 u* Z/ I( [
这个问题,主要是来自时钟计算所需要的表格出错,造成串口波特率计算出来的结果错误。本文简要分析了数组在查表的方式进行的对应运算关系,并对错误范围做出了解释,未来遇到类似的问题都可以使用此方式进行分析。! Z/ l$ k; l4 {9 x/ c! T/ g2 I
————————————————5 L* I4 p6 O  M7 ~; W
5 Z& w1 I& A1 n9 I/ W

* G1 n' T8 t- |& e2 F; j* D9 g                            5 I* d2 k4 u) s4 y5 d7 w- c' k6 h
& I* Y, A+ D$ B% O" H$ ^6 S
收藏 评论0 发布时间:2025-7-30 16:49

举报

0个回答

所属标签

相似技术帖

官网相关资源

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