STM32F451re采用模板创建新工程创建新线程报错

2019-9-11 14:31 [复制链接] 12 158

目前有个新板子用到STM32F451re,准备采用RT_THREAD,按照BSP制作教程再stm32文件夹下做了一个工程,编译完成后下到板子后在函数:int rtthread_startup(void)里的. @3 \& ]3 A, k' F- N$ m/ x
    /* create init_thread */" k& E4 J& H1 o6 ~
    rt_application_init();' g7 n& e( X+ v9 B

1 p" b6 \" c3 ^# n' L0 j3 W; C进入线程创建函数就跑飞了,MDK提示cannot access memory。
) z* ]+ E: k& K( ?# q. P" |根据提示,以为是rt_system_heap_init((void *)HEAP_BEGIN, (void *)HEAP_END);函数的HEAP_BEGIN,HEAP_END设置有问题。
9 W8 O2 a% E# C核对后是按照BSP制作教程提示的,按照当前片子的rom和ram设置的。
2 b& Q1 @1 p4 u4 d问下有做过的是不是哪里有个细节没处理好,还是创建工程的时候弄错了哪里。7 R# R4 _, h6 e
2 i; Z, x0 B, J- {8 \9 _* T# N
7 m  t. `) Z6 O# K9 E
% I% B' d$ ^+ X- R, o
使用道具 举报 显示全部楼层 回复
最新评论 | 正序浏览
显示全部楼层 |楼层直达:
发表于 2019-9-11 14:41:34 | 显示全部楼层
你的RAM可能是分多段的,可能有一部分是CCM DATA RAM,被你做BSP的时候囊括到整个RAM大小当中去了。做BSP的时候RAM大小要看看芯片的datasheet确定好。
使用道具 举报 回复
发表于 2019-9-11 14:49:22 | 显示全部楼层
WillianChan 发表于 2019-9-11 14:41! M  K. Z4 A3 C" v- `# n2 x
你的RAM可能是分多段的,可能有一部分是CCM DATA RAM,被你做BSP的时候囊括到整个RAM大小当中去了。做BSP的 ...

8 L3 c; x* s: r2 _+ Y/ o看数据手册160K的ram分了两个区,一个128k,一个32k。配置的时候只配置了128k的ram区,编译后在分配内存的时候还是报错了。
使用道具 举报 回复
发表于 2019-9-11 15:19:29 | 显示全部楼层
除了根据教程中的进行设置之外,是否自己在工程中设置了什么东西
使用道具 举报 回复
发表于 2019-9-11 15:36:58 | 显示全部楼层
yangjie 发表于 2019-9-11 15:19
$ k: ?" A3 Z1 A: H除了根据教程中的进行设置之外,是否自己在工程中设置了什么东西

7 I" t( I/ @& j, O7 ?* |# C0 W还在找问题,可能是设置了什么。和L475的例程做了对比,L475的例程直接下到板子可以正常运行,自己做的L451的串口显示version后就飞了,还是在初始任务创建后就挂了。我看重新再来一次。
使用道具 举报 回复
发表于 2019-9-11 16:23:12 | 显示全部楼层
目前问题暂时解决了,采用了bsp\stm32\stm32l475-atk-pandora\board\linker_scripts里的三个文件覆盖了从templates里考出的文件,然后按手册更改了配置文件,更改了board.h文件。实际再下载程序,可以正常运行了,但是查看了linker_scripts里的文件,理解的还是不太一样,link.sct 定义的是ram2,RW_IRAM2 0x10000000 0x00008000  {  ; RW data.ANY (+RW +ZI)。按我的理解,可以改为RAM1 RW_IRAM1 0x20000000 0x00020000。修改后rt_application_init();继续跑飞。
% }8 E  b" q5 E' v  j按照BSP教程的说明,这个地方显得比较模糊,新手还是不好容易理解如何修改配置文件。
使用道具 举报 回复
发表于 2019-9-11 23:20:56 | 显示全部楼层
本帖最后由 hgxj_rt 于 2019-9-11 23:27 编辑
* r8 t% Z; ]2 \9 |. Y) o! g# }5 g* _& k
7 C) k- A( I4 Z* H; ]4 m8 L  e问题找到了
  1. #define STM32_FLASH_START_ADRESS       ((uint32_t)0x08000000)4 y/ Y7 }; q2 Z; `
  2. #define STM32_FLASH_SIZE               (512 * 1024)
    ) ]% Q* G6 D& [6 s) o7 @* T
  3. #define STM32_FLASH_END_ADDRESS        ((uint32_t)(STM32_FLASH_START_ADRESS + STM32_FLASH_SIZE))
    & D  c1 O* l' p
  4. # g  Z7 u5 l) p
  5. #define STM32_SRAM1_SIZE               (96)0 M. x7 R: L% T) u5 e
  6. #define STM32_SRAM1_START              (0x20000000)
    + ~. O2 l# {) j. ]2 \3 x8 e0 y: j: n
  7. #define STM32_SRAM1_END                (STM32_SRAM1_START + STM32_SRAM1_SIZE * 1024)% N8 Z$ [/ K' ~8 K# k4 {8 w" }4 W
  8. $ [: P! |( d6 P' m0 f
  9. #define HEAP_BEGIN                     STM32_SRAM1_START
    - Y7 b0 `3 n* T, J7 c) }, Q5 R
  10. #define HEAP_END                       STM32_SRAM1_END
复制代码
这个是bsp\stm32中board.h对HEAP_BEGIN的定义。
, T4 l- f8 F6 y4 e4 n0 I8 D
  1. #ifdef __CC_ARM
    " J, A  [. a9 v6 T, f
  2. extern int Image$RW_IRAM1$ZI$Limit;  g; a% `; j, f7 x5 x6 N
  3. #define HEAP_BEGIN    (&Image$RW_IRAM1$ZI$Limit)2 H5 S2 P1 v! N+ G$ Q% a9 V
  4. #elif __ICCARM__
    " ]! E' W* W* Y' Q- o6 r0 n
  5. #pragma section="HEAP"* ?9 ?: z  d5 s7 W( |2 R1 w
  6. #define HEAP_BEGIN    (__segment_end("HEAP"))$ a: Q% }  _3 E3 G2 i5 `2 N
  7. #else0 ~8 s: S9 |# E1 E/ y
  8. extern int __bss_end;: ~$ V* G/ Z4 q3 z. O; M
  9. #define HEAP_BEGIN    (&__bss_end)
      w7 D- N4 q7 W- u! @+ n& G
  10. #endif
复制代码
这个是RT-Thread IoT例程对HEAP_BEGIN的定义。
" N, `* M1 i% e/ Q5 t实际仿真RT-Thread IoT例程中HEAP_BEGIN地址为0x20000FF0,rt_system_heap_init((void *)HEAP_BEGIN, (void *)HEAP_END);执行后。6 n, {8 K9 i. ~! b' v9 M
在分配内存就OK了。& N$ [# [& a% W
4 @9 B& N7 n$ E% f" ]. L

# V, d2 M' a2 X0 Q5 i5 l/ j, W/ G, h' F
使用道具 举报 回复
发表于 2019-9-25 15:49:44 | 显示全部楼层
看来这里的冲突主要在于,用作堆的内存空间和用作系统运行的内存空间的分配情况没有说清楚呢。
  z7 p! q4 Y, r0 R: J3 E/ \5 n, Y  {6 c$ M' R
看来这里需要 链接脚本 和 board.h 中的堆设置配置好系统才能正常运行。
使用道具 举报 回复
发表于 2019-9-25 15:58:58 | 显示全部楼层
在 l475-atk-pandora bsp 中,使用 RW_IRAM1 0x20000000 开始的 96k 空间用作堆空间,使用 RW_IRAM2 0x10000000 开始的 32k 内存用作系统的运行内存,这种配置方式算是是一种特殊的分配方式。
使用道具 举报 回复
发表于 2019-9-25 16:02:07 | 显示全部楼层
根据楼主的情况,其实只用 128k 的那块 ram 也并不会出错,只需要在 board.h 里面规定好所使用的那块 ram 的大小即可。
使用道具 举报 回复
发表于 7 天前 | 显示全部楼层
Summer_gift 发表于 2019-9-25 16:02: v) w* E3 v+ v
根据楼主的情况,其实只用 128k 的那块 ram 也并不会出错,只需要在 board.h 里面规定好所使用的那块 ram  ...

) j* G% y8 X( s6 U* u是的,我又重新看了下BSP制作教程 3.2.3 堆内存配置讲解说明了堆分配空间的问题。详细看了BSP中pandora例程,基本明白了,0x10000000 开始的 32k 内存用作系统的运行内存,所以堆分配可以直接用以下代码,
# H! c; @+ s5 \8 F/ X5 H+ }7 q
  1. #define STM32_SRAM1_SIZE               (96). X7 i3 {6 p! E% f  p% b
  2. #define STM32_SRAM1_START              (0x20000000)
    * X) t' i) E: m2 V' ~, E. ~
  3. #define STM32_SRAM1_END                (STM32_SRAM1_START + STM32_SRAM1_SIZE * 1024)+ [9 g& ?+ x1 }* {8 }
  4. #define HEAP_BEGIN                     STM32_SRAM1_START
    - P) z/ y; `) ?+ G! E
  5. #define HEAP_END                       STM32_SRAM1_END
复制代码
& J* S$ D( e6 c- k
我直接复制这个代码到L451工程下,链接脚本没有改为: `5 ^5 o/ j6 O1 m- j
  1. RW_IRAM2 0x10000000 0x00008000  {  ; RW data
    * ]8 J, P, b' _
  2.    .ANY (+RW +ZI)
复制代码

; T) d% `* x- i2 _; `所以程序直接就跑飞了。
/ \) X" |) r7 A- B如果只用 128k  ram,那么用( `) y( f: H/ [, y; q/ S
  1. #define STM32_SRAM1_SIZE               (128)
    / f: X) S0 o" d0 p* e0 ]
  2. #define STM32_SRAM1_START              (0x20000000)
    0 \# @2 E/ I8 w8 \% m  w
  3. #define STM32_SRAM1_END                (STM32_SRAM1_START + STM32_SRAM1_SIZE * 1024)
    , H2 U3 Y  I' f
  4. 9 {$ {# C2 [& j
  5. #ifdef __CC_ARM
    $ m) h( Y! @; m: s" w: _
  6. extern int Image$RW_IRAM1$ZI$Limit;
    % l8 ?* U# p2 ^9 B7 P0 r1 _
  7. #define HEAP_BEGIN      ((void *)&Image$RW_IRAM1$ZI$Limit). i! G6 K( u8 B$ o/ F1 U2 |
  8. #elif __ICCARM__
    " i! }7 j  A/ `4 q7 M6 H# C
  9. #pragma section="CSTACK"/ s: q5 }( g  o
  10. #define HEAP_BEGIN      (__segment_end("CSTACK"))
    * f2 O  f8 {' g9 B
  11. #else5 v4 p) O3 }- \" A, j' Z
  12. extern int __bss_end;& r* h) p: N% T) G7 w: C
  13. #define HEAP_BEGIN      ((void *)&__bss_end)
    % r9 N: a5 |" ?" o
  14. #endif6 B1 P) ^4 f( s7 \
  15. " O- C' N+ i- q# R
  16. #define HEAP_END                       STM32_SRAM1_END
复制代码
6 G5 H/ U( v+ o1 O& B, H( |
是完全可以的
使用道具 举报 回复
发表于 7 天前 | 显示全部楼层
Summer_gift 发表于 2019-9-25 16:024 o+ g" A: O6 M% |. e. \
根据楼主的情况,其实只用 128k 的那块 ram 也并不会出错,只需要在 board.h 里面规定好所使用的那块 ram  ...
8 H3 E8 Q  {5 b: z: i% `! h- w
现在还有个问题,看我说清楚了没,
' I9 I, M0 i/ t- u( ]2 s链接脚本如下:' v  R: \$ B: f6 R3 ]! l5 I4 k
  1. RW_IRAM2 0x10000000 0x00008000  {  ; RW data
    4 D7 E; D* ?8 E$ h, @. _
  2.    .ANY (+RW +ZI)
复制代码
6 o& C# B' |$ D& m/ r( S* D$ A
我的理解就是链接脚本这么写后,就指定了系统的运行内存从0x10000000开始,那么这个在实际编译后是怎么实现的,没太明白。
使用道具 举报 回复
发表于 6 天前 | 显示全部楼层
hgxj_rt 发表于 2019-10-9 23:42( ^; z- E8 [# D* Z5 r8 ^" m* U1 M! M
现在还有个问题,看我说清楚了没,
4 Q# ?1 A9 V7 ]$ F链接脚本如下:

! J& |/ Q  p: C程序在系统运行起来之后,会将相关的数据搬运到你链接脚本指定的位置上去,实现这个功能的这段代码一般是编译器自动给你加上去的,一般不用用户来自己编写。
使用道具 举报 回复
您需要登录后才可以回帖 登录 | 立即注册

本版积分规则

Archiver|手机版|小黑屋|RT-Thread开发者社区 ( 沪ICP备13014002号-1

有害信息举报电话:021-31165890 手机:18930558079

© 2006-2019 上海睿赛德电子科技有限公司

Powered by RT-Thread

快速回复 返回顶部 返回列表