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

【经验分享】STM32F1位带操作(寄存器、标准库、HAL库)

[复制链接]
STMCU小助手 发布时间:2021-11-30 21:00
位带操作也叫原子操作,也称别名。起作用直接进行位带操作,即直接读取寄存器的X位,或直接写寄存器的X位。
& @# h7 O6 h$ c       STM32的寄存器为32位的,在写入寄存器的x位中,通常操作为;排除寄存器除x外的其它位,在进行赋值。而位带操作可直接写寄存器的x位,使位操作更为便捷。
; j  j; I' [" G+ v  ]  }# f
. \. l' H) a$ u% X1. 实验内容及步骤:
* s1 Q4 j0 x7 q1 Z3 @7 p实验内容:7 j& @  _+ h7 ^/ M4 f: _; v

2 m9 a! ]- C3 V+ u       通过位带操作实现LED灯的翻转,和按键的读取。
: ~) F. {% j4 O  N( H
; {7 h# Q$ A% U4 r       按键按下时,LED亮,松开按键时,LED灭;
' B; O1 ^$ `9 ^- k- k7 J# p& l) r" A3 g* n
步骤:* P, B( B" e% J+ l6 }$ P$ p7 \
4 c. F  X* s  D5 G7 l6 [( Z9 `
       根据原寄存器地址定位位带地址;
) f% Z& |5 h- B6 Q, E+ U3 I( [! @; o6 {4 S% g8 O: ?/ ?. c! o2 K
2. 硬件说明
- p+ s; R) G+ y6 {
& W" }- H2 i: Q/ m# Y; M
20210617101338928.png

. \( ~: y. k9 Q* b8 K6 o& p7 N4 E
! o: F, |; n+ [$ C7 }2 M
20210617101343678.png

" l6 S  W/ `7 s' |7 h. v! ^* s6 N
+ P4 B. [3 t: _3 |! p4 p* }$ J% E* T% g3 t9 w& `, Y  Y+ K
       按键与PE4相连接,按下时低电平(所以GPIOE4应该配置为上拉输入,按下:低电平;松开:高电平)
( w; w' M8 P& O
( Y4 p( z2 L# x; q5 a" j' x       LED与PB5相连,另一端接VCC,(所以GPIOB5应该配置为推挽输出,亮:低电平;灭:高电平)
- X6 A! V9 h* S9 X$ u0 R
0 b# `0 I- x# j3. 位带操作原理
' M+ c" A  z% T5 @- w0 v: ?, p       STM32F1内部是有两个位带区的,如下图所示。- p% A$ J3 {6 P4 t  D

1 G  \7 l' W2 ]+ b& f
20210617105544116.png
# c3 y% N4 W$ W! F  X: s& m: \

' ]5 B  }* S% _, S" k* L: X     位带操作分别有片上外设和片上SRAM。我们用的比较多的通常是片上外设的位带操作,一般用来控制GPIO的反转和读取。
+ P3 t* ~* x. d: }. I3 R4 Z0 k3 Y2 U  m2 z1 }6 s* n
) ^) _) x' O1 A
( T# v" t2 L9 \5 @7 l0 n
其膨胀对应关系图如下图所示,以SRAM位带操作位例,0x2000 0000地址的第一位,映射到0x2200 0000地址。其用法如下所示:
" `  n* G8 J8 R3 X( H5 G6 {8 t, H- ]3 x; |: F5 ?6 i
       当0x2200 0000的内容=1时 => 0x2000 0000的内容=0x01* L9 Y) T! j1 F$ a

/ x0 A8 s: i6 E. L7 L4 _) R+ v* G       当0x2200 0000的内容=0时 => 0x2000 0000的内容=0x00
( @' g% v8 c' N4 R. }) s
1 h: K6 ?$ y- G3 m) D) P4 C& ^       ……………& o/ {3 R' w& H" i6 t

; n7 {5 M+ {6 l1 n* v       当0x2200 0018的内容=1时 => 0x2000 0000的内容=0x40=(二进制)0100 0000* |; w1 x/ ]5 H9 n
) D1 }. g; Z. Z- z
       当0x2200 0018的内容=0时 => 0x2000 0000的内容=0x00( Y/ f' X* d9 W$ `5 g

' T* |3 |  H# ~2 S  t0 j3 n4 t. c2 a
20210617140221772.png
1 {9 I6 a' ]+ w. R% |( V9 S6 q6 H9 x6 r

) v, h& g0 k$ B% P* [, z4. 寄存器说明# G8 D* U( b6 f$ e! Z8 M8 G
       位带映射地址如下图所示。(中文STM32参考手册P29)
8 F! t( T3 y; y! a/ w7 ^3 \, a# ~" y) I
20210617101442958.png
7 f  X7 S5 |' k$ r  y- l* a/ Y. I
+ c  f" ^- f* T" ^# M# x
       位带操作的例子如下图所示(CM3权威指南CnR2), t  D: G, G7 M8 w% Y6 y
1 N( A7 [) |8 h; q4 ]6 K
20210617101509429.png
  n) y5 Y5 l$ g8 W4 b0 o/ m
, K$ l" c8 |% O% K, d4 D1 P  D8 T( h1 F
       根据例子可写成通用的式子。8 _. |' s& q: g
  o# a- {2 r% l- q- w
       bit_word_addr = (IN_ADDR_BASR&0xF0000000|0x02000000)+ (IN_ADDR_BASR&0x000FFFFF)*32+Bit*40 @  c' b4 F/ j# u$ G/ ~5 d
0 E& ~$ E( S: H9 E; b, q* Z6 a
       => 5 u' t  |: }+ s( I8 A
, Q; I4 R) k2 M9 A# t5 R
       bit_word_addr = (IN_ADDR_BASR&0xF0000000|0x02000000)+ ((IN_ADDR_BASR&0x000FFFFF)<<5)+(Bit<<2)
" \! j. o6 p7 X- E, i
% b: [, k8 f$ o- l       如要控制LED灯(PB5)8 ]6 I" a. l  Z( G
5 r' k% a9 d; {) Z/ z
       IN_ADDR_BASR = GPIOB的输出寄存器 = 0X4001 0C00 + 0x0C;5 ^1 I) a/ S" M9 K. [/ b7 o
9 l7 s7 B% V, d& |
       Bit = 57 g" ]. o1 B3 {
) L: c, O0 Q# ?* K
5. 程序设计
( f0 v. Y9 I6 F2 o$ f       代码班的通用位带操作地址转换宏定义如下:7 z' t. ]' C5 E3 J( Y
  1. #define BIT_WORD_ADDR(IN_ADDR,BIT) *(__IO uint32_t*)((IN_ADDR&0xF0000000|0x02000000) +((IN_ADDR&0x000FFFFF)<<5) + (BIT<<2))
复制代码

' `0 i: V5 T. _0 {; j       GPIO的输出位带宏定义如下定义8 V) z  U0 U8 s! C
  1.         #define BPB_OUT(BIT)  BIT_WORD_ADDR((GPIOA_BASE+0x0C),BIT)   
复制代码
BIT为要操作的位。
' U! n6 Y" z9 K: [5 U       在本实验中要操作LED(PB5),因此BIT=5;9 }' f( E# l, |( B% g7 c0 |1 y$ T: a% d
# v- P" n$ N! O3 ^
       GPIO的输入位带宏定义如下定义$ B2 h% U" y7 J
: k: K6 q# |$ L$ [: s& i; a3 L0 ^5 Y
        #define BPE_IN(BIT)  BIT_WORD_ADDR((GPIOE_BASE+0x08),BIT)& m2 W- `% y, R/ P% h
       BIT为要操作的位。" f. C# ^4 J3 K0 X2 V- E

+ M; o; e6 e% ~3 B在本实验中要读取按键(PE4)的值,因此BIT=4;
  B( T6 z( }; g" y
6 }% [4 W. i! ?6 E
" m* h2 {) M8 M6 y1 D- {2 K: d0 Y+ ]% e3 _$ k
位带操作源码:2 W( ?  O, P) n" p8 Z1 X# v  ?9 F& T

# _) N5 G5 l$ N% \源码筛选了关键部分,详细看源码。. A+ A  Z7 i  j2 `* o

) ?2 p9 x2 l4 y( \, V$ u
  1. #define BIT_WORD_ADDR(IN_ADDR,BIT)      *(__IO uint32_t*)((IN_ADDR&0xF0000000|0x02000000) +\7 t" `! T) c' I' O8 c. w
  2.                                                             ((IN_ADDR&0x000FFFFF)<<5) +\' F8 K2 l5 B/ J0 M4 `
  3.                                                              (BIT<<2))- K" ?# [% a4 [. T0 ]
  4. ' ?. T: G' U& f2 y+ ~, v$ _
  5. //GPIO_OUT& C6 v* k# S! E' G% i
  6. #define BPA_OUT(BIT)  BIT_WORD_ADDR((GPIOA_BASE+0x0C),BIT)2 J. P/ M  z8 A
  7. #define BPB_OUT(BIT)  BIT_WORD_ADDR((GPIOB_BASE+0x0C),BIT)
    , P$ b* p1 T4 }0 V2 ]5 n" l" c
  8. #define BPC_OUT(BIT)  BIT_WORD_ADDR((GPIOC_BASE+0x0C),BIT)$ ^7 }) I+ a% M4 d
  9. #define BPD_OUT(BIT)  BIT_WORD_ADDR((GPIOD_BASE+0x0C),BIT)5 i) M" w8 h+ u$ ]1 R  n, h  `
  10. #define BPE_OUT(BIT)  BIT_WORD_ADDR((GPIOE_BASE+0x0C),BIT)
    ( u# h0 ^& U) d+ M  ^
  11. #define BPF_OUT(BIT)  BIT_WORD_ADDR((GPIOF_BASE+0x0C),BIT)6 q7 r2 z: J) {' }& L) r: ?
  12. #define BPG_OUT(BIT)  BIT_WORD_ADDR((GPIOG_BASE+0x0C),BIT)
    - l0 a3 ~: P$ d0 P& S5 {% k3 [
  13. //GPIO_IN, H6 Q* T4 w  {* F
  14. #define BPA_IN(BIT)  BIT_WORD_ADDR((GPIOA_BASE+0x08),BIT)
    6 k3 e5 R( u5 ?* @
  15. #define BPB_IN(BIT)  BIT_WORD_ADDR((GPIOB_BASE+0x08),BIT)
    0 _4 u7 b7 y7 p9 E: c( L/ N8 \
  16. #define BPC_IN(BIT)  BIT_WORD_ADDR((GPIOC_BASE+0x08),BIT)8 y( a3 L) S* Y
  17. #define BPD_IN(BIT)  BIT_WORD_ADDR((GPIOD_BASE+0x08),BIT)& X  o8 C3 U. A7 X' M
  18. #define BPE_IN(BIT)  BIT_WORD_ADDR((GPIOE_BASE+0x08),BIT)' s9 Q( r( G- X) l, _" j5 F
  19. #define BPF_IN(BIT)  BIT_WORD_ADDR((GPIOF_BASE+0x08),BIT)
    3 f" ~+ [- n2 W; s8 F% O
  20. #define BPG_IN(BIT)  BIT_WORD_ADDR((GPIOG_BASE+0x08),BIT)
复制代码
4 A2 K# n$ W* W6 w+ K) x* E6 V& Q
6. 实验结果
2 z$ o0 G; ]% e8 F, w! r( \# k       按键按下后,LED灯亮;
& G  j+ S5 A/ d  d6 k0 p! H
) W. y& a1 E7 C8 |  h: u- j6 |       按键松开后,LED灯灭。/ ~0 d4 r; ]% q

  y0 @+ U0 Y' W3 g+ U3 @- {  U: T: }
/ c+ C& r- b* r5 i3 B/ ^; V8 h% W
- u) ~4 ]+ Q  ]5 N5 F1 o
赞 收藏 评论0 发布时间:2021-11-30 21:00

举报

0个回答

所属标签

相似技术帖

官网相关资源

关于
我们是谁
投资者关系
意法半导体可持续发展举措
创新与技术
意法半导体官网
联系我们
联系ST分支机构
寻找销售人员和分销渠道
社区
媒体中心
活动与培训
隐私策略
隐私策略
Cookies管理
行使您的权利
官方最新发布
人形机器人运动控制、感知与智能配电
半导体创新技术与应用方向
EE架构与软件定义汽车
12V/48V 汽车智能配电(SPD)
区域控制单元(ZCU)与分区架构
关注我们
st-img 微信公众号
st-img 手机版