解决PLATFORMIO STM32F407VE工程卡死在启动文件的问题
由于工作原因,需要在linux平台做固件开发,因此在查询了一些资料后,选择了vscode+platformio的方式来搭建STM32的开发环境。但是在调试STM32F407工程的时候出现了一些问题,因此特意记录一下。
环境
Ubuntu 18.04 lts;vscode 1.58.0;platformio core5.1.1 home 3.3.4;MCU STM32F407VET6
问题现象
使用board generic-stm32f407vet6创建的工程还未跳转到main就卡死在启动文件的Infinite_Loop中,如下图。
分析
经过仔细调试发现程序一旦运行到__libc_init_array以后就会跳转到Infinite_Loop,而__libc_init_array查找资料后发现是用来初始化C库的,而为何最后会跳转到Infinite_Loop,实际上是因为我们的HardFault_Handler的中断函数没有定义,所以跳转到默认的中断函数上,我们可以定义一个HardFault_Handler函数,就会发现确实是触发硬件错误中断。如下图。
一开始我以为是启动文件存在问题,反复试了很多次后,却发现board选择STM32F407IGT6就是没问题,并且他和STM32F407VET6共用一个启动文件,没办法,于是我只能反复确认两者编译时需要的文件哪些不同,最后我定位到了STM32F407VE_DEFAULT.ld文件,在./platformio/packages/tool-ldscripts-ststm32中,可以发现这文件是copy自STM32F030C6Tx,连头部注释都没改。如图。
仔细检查该文件,发现在内存定义那有个严重错误。如图。
STM32F407VET6内存大小确实是192KB,但是他其实是有三块内存组成,其中有一块64KB的CCM地址是不连续的。以下为数据手册描述。
到这里问题就简单了,直接将RAM的LENGTH修改为128K,重新编译,运行,解决。
结论
STM32F407VE_DEFAULT.ld文件内存定义存在问题。
解决方法
将./platformio/packages/tool-ldscripts-ststm32/STM32F407VE_DEFAULT.ld中的内存定义改为下图方式