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

【经验分享】STM32H7的内部Flash和QSPI Flash都运行程序的混合方式(强烈推荐)

[复制链接]
STMCU小助手 发布时间:2021-11-6 23:02
83.1 初学者重要提示9 B! x' ^! ^( F' g" |0 ?3 y  x6 U
  QSPI Flash的相关知识点可以看第78章和79章。
9 ]% p+ r" _. D: h% {+ r  操作本章配套例子前务必先将QSPI Flash的下载算法放到MDK安装目录。4 u. {+ e7 x; c" T
  本章节与第28章的时间关键代码在ITCM执行的设置思路是一样的,可以让大家对本章节的方法有个更全面的认识。0 a; a5 y0 @8 j* `, p  W
83.2 内部Flash和QSPI Flash混合执行程序的优势$ Q0 X2 T9 g' V. W. E
现在大家使用H750或H743在外置QSPI Flash执行程序,都倾向于制作个BOOT,再制作一个运行在外置QSPI Flash的APP程序。即本教程第82章讲解的内容。" E: g: A. Q. X0 Y# v; Z

/ ?! [, U5 a5 ^5 z3 I% n6 \: P7 Y本章要实现的这种方式对于我们想外置QSPI Flash运行程序,在调试测试阶段更加方便,甚至是项目使用,可以性能最大化。
- F+ k& B9 ?9 v* X) D5 m5 W- V7 r1 C) W
& Z5 }: w1 U4 N* s# n83.3 下载算法存放位置- w9 T/ k2 h1 R( E2 ?+ t2 ~
编译例子:V7-060_QSPI Flash的MDK下载算法制作,生成的算法文件位于此路径下:
. I) K! r3 [* z+ W( a* W# J& v/ m1 P" e4 M
618b073cf66c2944fcdb610aef0e67ea.png

4 X$ w3 |5 V* ~0 [8 b, P6 g! y; O$ y2 E8 A
生成算法文件后,需要大家将其存到到MDK安装目录,有两个位置可以存放,任选其一,推荐第2种:
4 b" G7 T2 n0 q" Z7 ^3 F/ _# L& O  h- A) P
  第1种:存放到MDK的STM32H7软包安装目录里面:\Keil\STM32H7xx_DFP\2.6.0\CMSIS\Flash(软包版本不同,数值2.6.0不同)。& z2 l9 y; }3 D$ y  f# w
  第2种:MDK的安装目录 \ARM\Flash里面。
$ J4 Q- V1 p+ l
b192c51eb80b27959d7c06b80a142d6e.png

, o9 Y: [" q) `- U$ d( i4 D$ l7 A! Z+ U0 r
83.4 内部Flash和QSPI Flash混合执行程序说明3 a* }2 w. C- a% I1 Y1 r+ V$ p
混合程序的设置注意以下两点即可。9 Z9 {3 @  F# E' s4 T
6 \6 w( G% R& {' {4 C. w
83.4.1 初始化QSPI Flash并设置内存映射模式8 P' {  e, x( z
在bsp.c文件中初始在bsp.c文件中初始QSPI Flash并设置为内存映射模式。注意,配置好时钟后,优先初始化QSPI Flash并设置为内存映射模式:
* L& Y% l: U6 T" N: n  x2 V
7 L. e3 A5 q6 x% l+ c9 c
  1. /*
    ) k1 v6 r# R" D
  2. *********************************************************************************************************
    . e" ~2 @3 Y7 C# d: Z
  3. *    函 数 名: bsp_Init
    , I0 A" i5 D9 x& E: E7 o. B& x
  4. *    功能说明: 初始化所有的硬件设备。该函数配置CPU寄存器和外设的寄存器并初始化一些全局变量。只需要调用一次, @/ h1 X" T1 G, h# s! _; ]
  5. *    形    参:无* ^0 O% l, e# }; H, D
  6. *    返 回 值: 无$ l+ l1 \! i  U; b
  7. *********************************************************************************************************) W+ i! a* ^  _+ J# x& n
  8. */
    5 e( G3 \1 J0 ~. I
  9. void bsp_Init(void)
    " g+ A4 b& `( m+ U( E& U
  10. {; g7 x! |! R/ e5 T1 b/ N
  11.     /* 配置MPU */
    ! `/ L$ t2 Z! V: g; i! }. m" X
  12.     MPU_Config();# S# x6 `1 w9 Q7 j- N& {' ~

  13. 2 U+ I9 E$ g. E
  14.     /* 使能L1 Cache */
    * ~0 }4 g8 {, e
  15.     CPU_CACHE_Enable();
    ' O1 M8 I( Z9 q
  16. ( Y3 u, i! C6 O* P3 ^+ n
  17.     /* 8 D$ l9 U% f* v% L
  18.        STM32H7xx HAL 库初始化,此时系统用的还是H7自带的64MHz,HSI时钟:5 ~9 ^+ j) q0 |" b0 i
  19.        - 调用函数HAL_InitTick,初始化滴答时钟中断1ms。
    ) U) K9 r! A7 n+ c' [5 T5 t
  20.        - 设置NVIV优先级分组为4。
    5 h; s0 Y3 u/ ?$ K9 m- F/ s
  21.      */' ]. L8 Q+ M& s& d+ O2 s
  22.     HAL_Init();2 k  A$ [- @( \+ B# c7 z3 z/ ~6 e2 f

  23. 0 W& c5 {* D. a+ W& ^4 ?
  24.     /* " I0 j  k' C; `; l, s; ?" l
  25.        配置系统时钟到400MHz
    3 g8 R2 c! Q! g0 T7 H8 C  d: Z
  26.        - 切换使用HSE。
    9 r1 y. g- A6 f+ u0 \% Q) N! Y
  27.        - 此函数会更新全局变量SystemCoreClock,并重新配置HAL_InitTick。5 d$ F: z, o, S" V
  28.     */
    4 e9 n" K/ a0 R. g; n
  29.     SystemClock_Config();
    , [9 u0 p  l" l" O3 T
  30. 3 d. ~* w; b( V- y$ D9 }( g8 W4 I
  31.     /*
    ) l. U% q8 U0 n
  32.        Event Recorder:9 P& x# \$ X) f3 f: f+ e% a
  33.        - 可用于代码执行时间测量,MDK5.25及其以上版本才支持,IAR不支持。3 B$ O9 d5 ~. C6 Y
  34.        - 默认不开启,如果要使能此选项,务必看V7开发板用户手册第8章0 ~7 R* Z7 \6 e. Z4 a4 p: O
  35.     */   
    # O+ C! v2 n) a  n4 N: w, Z
  36. #if Enable_EventRecorder == 1  . `3 Q" t/ t3 S3 X8 B5 f* _1 ]
  37.     /* 初始化EventRecorder并开启 */; z' b* y- G8 ?4 o: D  l* U
  38.     EventRecorderInitialize(EventRecordAll, 1U);
      ^" w+ c& ~4 P, ]' h) d- o  |! @
  39.     EventRecorderStart();" k5 e# b, L. C- k/ `
  40. #endif
    9 \# q- o* G4 V/ N) r
  41. ! O9 b$ |6 K8 W4 i  Q* ]+ l" ~+ T
  42.     /* 针对不同的应用程序,添加需要的底层驱动模块初始化函数 */
    ) r. ?* Q% n! z5 O
  43.     bsp_InitQSPI_W25Q256();  /* 配置SPI总线 */   
    & z) E8 r( A3 c# s3 ^
  44.      QSPI_MemoryMapped();
    4 d$ V. @0 B$ ?/ \; m
  45. " T- L* r# c. {, A0 r
  46. bsp_InitDWT();      /* 初始化DWT时钟周期计数器 */      
    + ^) E1 w# N  L1 _8 y8 p! x4 @
  47.     bsp_InitKey();        /* 按键初始化,要放在滴答定时器之前,因为按钮检测是通过滴答定时器扫描 */
    ) p% n9 Q  X: J! d1 D$ o
  48.     bsp_InitTimer();      /* 初始化滴答定时器 */, c  l- V" v! Y- }: D. ?
  49.     bsp_InitUart();        /* 初始化串口 */) f# y! Q- R+ ~) e2 C+ A+ |# c5 A% N
  50.     bsp_InitExtIO();    /* 初始化FMC总线74HC574扩展IO. 必须在 bsp_InitLed()前执行 */   
    ' f& M5 x/ E$ `6 ?4 j% T+ N6 k
  51.     bsp_InitLed();        /* 初始化LED */   
    - G+ x9 o" p* z/ v/ D
  52.     bsp_InitExtSDRAM(); /* 初始化SDRAM */
    ; E. q, V# j4 R7 [( ~7 F8 d+ L" K

  53. 3 y4 B  t, H( ^1 S) X* F0 f9 p
  54.     bsp_InitI2C();        /* 初始化I2C总线 */% Y* v7 Q, e8 P" }5 p6 E3 a5 Q
  55.     TOUCH_InitHard();   /* 初始化触摸芯片,LCD面板型号的检查也在此函数,所以要在函数LCD_InitHard前调用 */
    1 p; c2 n- `2 l2 r, P9 ?) x
  56.     LCD_InitHard();     /* 初始化LCD */
    3 d3 w# q0 B, [8 N
  57. }
复制代码

( K# w1 E9 e2 I! n83.4.2 设置运行在内部Flash和QSPI Flash的程序* o& \6 i* l& x# B# [
由于我们要把QSPI Flash初始化并设置为内存映射模式后才可以使用QSPI Flash运行程序,所以要在QSPI Flash运行程序之前的所有操作都在内部Flash里面实现,主要是滴答定时器,RCC,QSPI和HAL库等相关配置。其它所有程序都可以在外部QSPI Flash执行:
  L! \  ?4 P: J& v
( `1 W0 {- y7 |+ g/ [7 l! U- v/ j
5afe81e1cd5b95f9c13119726de64582.png

$ Y+ U6 i) V' Z  r, \) @7 \$ ?2 P8 U* p4 _
+ D7 v$ u# u* P! P7 _+ C
83.5 内部Flash和QSPI Flash程序调试下载配置; b7 ?1 v( X) Z, }8 z. ]
将下面两个地方配置后,就可以像使用内部Flash一样使用QSPI Flash进行调试了。并且这种方式可以方便的调试程序,内部Flash和外部Flash都做调试。
1 w5 \$ x6 j$ `0 E. d* k7 X; m
0 G! E$ c4 ?& Q& @% t- q6 [; X# }83.5.1 下载配置: a' N: h) G* s3 J& B1 E2 Q) P
注意这里一定要够大,否则会提示算法文件无法加载:( A- n) M5 P9 ]6 V
5 {% T! @5 ~) [3 h% [. s, _
96d039e1657c72042027eb7e46ffc33a.png
+ G1 w# b1 o, O* Q$ b' e8 U

0 \1 g' ?6 N5 D3 [5 a. d我们这里是将其加到DTCM中,即首地址为0x20000000,大家也可以存储到任意其它RAM地址,只要空间还够加载算法文件即可。推荐使用AXI SRAM(地址0x24000000),因为这块RAM空间足够大。
  W) Q& D( q$ X  Z+ ?# Y* G! E- U; y& Y' n
如果要下载程序到内部Flash和外部QSPI Flash里面,需要做如下配置,两个下载算法都要添加进来:% n0 z5 Y/ {9 ?% ?7 m2 D
7 u: ]2 B- j5 w: z
9c03364b94f34e5f8e8b1e9b708430a6.png

9 y6 _% B( g: \) \- d" ]" y  S& Y8 n' [4 x; j" H( R( t
83.5.2 调试配置
2 k. M# J, M+ q* v* j& B注意这里一定要够大,否则会提示算法文件无法加载:4 L4 h& O- g$ f* @4 r" f
8 ~- }, ^4 P- e6 f
6b0758d3dd4db39b7189a03d59f0eca0.png

0 B* x! W- L* a& R8 y' Z" X7 P) P
9 @5 N( G4 S/ |! w我们这里是将其加到DTCM中,即首地址为0x20000000,大家也可以存储到任意其它RAM地址,只要空间还够加载算法文件即可。% v! j1 x/ K6 _) o4 I& X

3 M' d8 i/ P, O, m5 W  d如果要做调试下载,需要做如下配置:
8 Z# C0 y' n+ O0 G8 K: Q% _' w" z# b" T# F' q
93ce012aea4a1b38d8cd796b00fd7e32.png
5 c) ]6 _: E$ G( g6 x
. V1 [4 f5 h$ Q
83.5.3 程序调试效果# H4 e# X4 n0 r6 l5 X. @
调试效果如下:
% {* W- y) C( c( l) p: M9 S$ o( i
! {4 X7 p' n" ]
48019aea182ba08be716467429994567.png
& z9 P* i0 E; y8 }' Z7 n; E1 `
8 T6 L; u& d3 v( [( c0 N' N5 C# ]
83.6 实验例程说明
4 T+ _6 n- L  _. C本章节配套例子:V7-064_内部Flash和QSPI Flash都运行程序的混合方式,无需单独制作BOOT和APP(强烈推荐)
" z2 g8 R0 u/ r5 q/ \/ V" b1 {6 H2 x5 e6 w9 f: |
编译此程序弹出的警告不用管,可以选择屏蔽此警告:
% w+ }- ]2 y1 W8 K1 s& S  ]
% o$ _( H- }, ^$ `1 {
1beb9dad80a6c5a7a1e6927282b23199.png

& }* g$ x% O" Q; b3 L2 o( [2 J1 E5 @2 v2 [" \
83.7 总结
8 o* }3 Z  N. i9 {本章节就为大家讲解这么,为了熟练掌握,大家可以尝试自己实现一个内部Flash和外部Flash混合运行的程序。/ E6 h6 F5 B' f$ w% T$ Z* m; p
. A) r; G7 a7 w+ r
) M$ c# V) V4 X1 a0 v
' P  j: f" @/ m6 U* X
681a23ba44bd11addce0fa9aae797dbd.png
927401ada0fef49a78ac8029e372a755.png
5c95b0f51dbecf9eac259ddcf6b3da55.png
75afb2342189857e8fa086fc0af08462.png
bfe6b8c0ea19b535e2fb06c6618577f6.png
b00b09a901596bcedb07c31790d8d3d9.png
618b073cf66c2944fcdb610aef0e67ea.png
赞 收藏 评论0 发布时间:2021-11-6 23:02

举报

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