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

基于STM32的Keil、IAR、CubeIDE 中变量不被初始化方法

[复制链接]
STMCU小助手 发布时间:2023-11-26 15:43
01前言9 ]+ }+ U& i' W+ Q  [: R) x6 w- x
有些时候在我们的应用过程中要求变量有连续性,或者现场保留,例如 Bootloader 跳转,某种原因的复位过程中我们有些关键变量不能被初始化,在不同的编译环境下有不同的设置,本文就这个操作做总结,分别介绍使用 Keil,IAR 和 CubeIDE 的操作方法,本文中所用芯片为STM32G431RBT6。3 R* g* @. I, d; ~2 A5 z; D# n. H# t

5 F  f& I$ O7 n3 J3 Z" g$ O02 IAR 实现变量不初始化方法3 F5 F. A9 @! b) T% J, W0 O" Y
IAR 实现相对简单,直接使用“__no_init”这个关键字即可,也就是在变量前面进行修饰:
$ |) |5 s0 C6 W/ k8 N' {% Q) I: E/ H, U

( J: @4 a) K( ?. M* x3 m
微信图片_20231126153703.jpg

% l+ V( c# Q" S- o/ R- K. @9 _. s6 @7 T2 ?& H$ C8 C
为了验证是否执行成功,可以考虑周期性让系统复位,看变量的变化,比如下面的示例程序让系统周期复位,会发现每次 Test_NoInit 数据都是在上次数据基础上增加 10,而不是被初始化后的数据增加 10。! V4 E3 T4 [6 D7 V; t- \! x; l# i/ ~

9 ?& D% u( ^/ S( ~
微信图片_20231126153700.jpg

  V( b3 ^+ t/ P% R
" v( u8 F2 x- E

1 q! ^! b" @6 f5 g) h0 ^03 Keil 实现变量不被初始化方法
; E" b9 O) L  R$ I3 [% bKeil 中没有像 IAR 里面的这个关键字,而且会有版本的区别,下面分别介绍:+ ^- s) m, X4 G0 u

) m8 A& T" [/ ]* o5 p! {( \' o
微信图片_20231126153657.jpg
9 v$ k" {# c) ?% C- s3 D
图1.Keil 不同编译版本
. G4 x/ U$ h3 r* F$ _1 V5 P" |
) b7 D5 U9 d6 c9 S# H4 c- k
为了防止未初始化的变量被初始化为 0,要将未初始化的变量放在一个特殊段内,这个段满足是 ZI 数据段(.bss),它的执行域(region)具有 UNINIT 属性。+ T7 N4 S7 W6 E, ~3 O
# t. T5 ~. z" L0 k
3.1. Arm® Compiler 5 的操作
; V" K' [/ ]% m/ Z修改工程的 linker file 文件,*.sct 文件4 L8 `+ _+ d/ d+ Q8 _( h, Q

+ N9 M; A  n* M6 g) {
& t7 M8 b9 l: I9 R& H
微信图片_20231126153652.jpg

: T) p1 {" J: Y
图2.修改默认 linker file
7 f. y5 U0 r7 Q( t; _9 k  u9 o8 `
, ]7 Y7 M% Y. r
这边将 RAM 划分两个区间,其中 RW_IRAM2 就是我们要的变量不初始化区域,属性为UNINIT,定义一个 region 名字 NO_INIT.1 V- I5 n6 r. p* V  y9 A! \
( }4 d/ }( }6 e& u% N; I

8 o1 X1 g5 d8 W2 Q/ S
微信图片_20231126153649.jpg

+ }: D; M6 p$ k8 ?9 S$ l; s! U# t/ I, V6 p4 H* u- o7 d! U
变量定义到这个 section,这边 AC5 要用到 zero_init 这个修饰。8 {+ R$ y* {% v, j: Z2 r! y
" E$ t+ N! J% Q8 v. x
# o9 s" e! c8 t6 x3 J4 t3 L$ N
微信图片_20231126153639.jpg
% A( J" J  h& S8 Y5 Q7 v
, C5 C6 P2 v$ G, m
4 n* P2 O# _. m/ m) A" a
3.2. Arm® Compiler 6 的操作
" p# t& c. W9 V* m在 AC6 上面需要加入.bss 这个 ZI 定义,如下的 sct 文件修改:
; _$ A4 i0 Q! Q: \, E& z# u
; r* U# N& |+ N1 X0 p. l# A
2 B2 @: o* h2 X* @1 s
微信图片_20231126153642.jpg
* ]$ d$ R$ U- f; j
# i. W& B; C4 L; q3 `( j
' j" h, F, ^1 G& I
变量定义到 section 部分,AC5 和 AC6 也是有区别的,不再支持 zero_init 这个修饰,如下定义:* i' |8 b  h9 ?, X: s
6 {9 M4 W5 j( }% m; M8 w4 }

% i; g/ ^( [) q& j% u" f- a7 F0 z( X4 A& \! }5 ]

; F. t5 k+ O* J6 E  t) u- G对于版本 AC5 和 AC6 具体区别可以参考 Keil 帮助文件中的描述:" G& J- z5 e- D; o5 N; P/ B
' d1 J# ~2 e2 w) T

( d8 a+ `# _" I* U" U6 o
微信图片_20231126153635.jpg
2 N! O7 t5 C" |; B
图3.Keil 帮助文件关于 zero initialized
! Z- Y1 }6 o6 `' A5 q  t& K7 r
* M. G3 p% h* J
  G" U) q( I+ w; ]: }

0 {0 p/ a/ K1 g7 }8 Q  Y% h" h

' T$ n: [7 j2 C; Z$ B( j; f; q+ d' z
# p8 V. h8 W: V% V

2 k. @2 a. j) }+ H: b4 Y& w% t04 CubeIDE 实现变量不初始化方法# F9 A( T' F, {9 [
CubeIDE 的实现和 Keil 有类似的操作,需要修改 linker file 文件*.ld。首先对 RAM 进行划分,划分出不初始化的 RAM 区域:2 T. P+ |# Z% Q3 a, X: D
! V" [/ ?/ K# g, O' L

( g  N2 t( T' [) `' C
微信图片_20231126153632.jpg

2 ]& p8 O- N  Z3 I
图4.划分 RAM 区域

5 e  w" b: H; ^
' X! G" y) @2 ]4 M
. T( [. e9 n& K1 s1 X, j; ]4 ?
增加区域描述,并且加入区域名字:

4 M" J) }; q- }3 E9 {  T6 E+ z4 E8 X, f1 c! Z
. ~7 J& w7 J: c. f5 M) }3 X1 V
微信图片_20231126153629.jpg
7 }0 W7 U( z3 C( o* r3 y
图5.区域描述,名字定义

  ^# N0 W: W7 i
; U5 S& n# t( I4 C% |7 z/ W, [

: d" X1 z1 Z( K1 a( ^, k) e5 O2 N4 ?+ W9 q
定义变量到这个不初始化区域中:& T: ^% }: W4 r* S% p

( U" u, W0 N1 c: {
1 C' K3 ?' r: I
微信图片_20231126153625.jpg

( f% w/ s9 p1 @$ ~) b8 W; ?" k7 }1 {
9 K% q3 p; {/ a" [  t另外,还提醒一点,有些 STM32 系列有专门针对特定 RAM 区复位后是否会被初始化的 Option 配置位。比方 STM32L4 系列,想让 SRAM2 变量不被初始化,得配置选项字节中的 SRAM2_RST位。如下图所示:& y4 D* g3 d3 @: a) H( c4 I- @
, Y* x8 q/ M, G, s2 K
! W. c9 e0 [% B3 Q& }- E
微信图片_20231126153617.jpg

; }$ t7 ^  b7 R" T$ |& T
; J; E2 S9 |" N) }8 k# |

% I* G, \. Y6 n转载自: STM32单片机, z3 _4 B- d8 j, f5 k
如有侵权请联系删除
; C1 r) a/ n7 M3 @. k
; ~% o: X* m" L8 P
3 n) H" }, o8 y9 U
微信图片_20231126153645.jpg
赞 收藏 1 评论0 发布时间:2023-11-26 15:43

举报

0个回答

所属标签

相似技术帖

官网相关资源

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