目录
一、官方BootLoader(外部Flash)
在F7的固件包例程中,有一个关于BootLoader的例程:
包含了Boot和App两部分:
1、使用IAR打开Boot程序
在memory.h文件中可以定义使用哪些地方做为程序运行区和程序存放区:
2、将此代码编译下载到板子上
3、复位运行代码,此时开发板没有任何现象:
4、接着打开LedToggling例程,编译后打开map文件查看
可以发现此时的代码都存放在了0x90000000起始的外部QSPI-FLASH中:
如果直接使用IAR软件下载程序,会出现下载错误:
5、打开ST的下载软件进行烧写:
连接上ST-Link,软件会自动识别板子的型号,并且找到板载的FLASH芯片
6、找到编译生成的hex文件:
但是打开后,下面的Start Address并不现实当前的起始地址:
为了验证当前的文件的正确性:使用第一个选项栏工具Memory&file edition打开hex文件:
可以发现起始地址是从0x90000000开始的,即文件中包含了地址信息:
7、开始烧写:
烧写完成后,断开ST-Link:
8、按下复位按键可以看到板子上的LED6闪烁,说明成功使用BootLoader引导了外部FLASH中的代码运行:
9、接下来自行移植程序,使用BootLoader引导至外部FLASH,以例程中的STemWin_HelloWorld为例:
10、使用IAR打开工程后,进入工程设置:设置中断向量表的起始地址为外部FLASH的地址:0x90000000
11、设置代码存储区的地址:
12、然后在system_stm32f7xx.c文件中修改向量表偏移地址
将FLASH_BASE直接改为0x90000000:
13、编译,使用上述方法将hex文件下载,可以看到例程运行成功。
二、程序运行在内部SRAM中
1、首先使用CubeMX配置好串口通信,使用DMA的方式接收数据:
2、在主函数开头打开DMA接收,配置缓冲器,接收的字节为1,即每来一个数就产生一次DMA中断:
HAL_UART_Receive_DMA( &huart6, &TEMP_BUFF , 1 );
3、定义一个长数组,用户保存接收到的二进制文件
使用编译预处理命令强制设置变量的地址为0x20020000,此地址后续还有用处:
#define RXD_BUFF_SIZE 1024*100
#define SRAM_FOR_USER_START_ADD 0x20020000
#pragma location = SRAM_FOR_USER_START_ADD
uint8_t UART6_RXD_BUFF[RXD_BUFF_SIZE] = {0};
4、编写接收回调函数
每接收到一个字节,就存到SRAM中的变量的位置,同时计数变量加一:
uint8_t TEMP_BUFF = 0;
uint32_t UART6_RXD_COUNT = 0;
void HAL_UART_RxCpltCallback(UART_HandleTypeDef *huart)
{
if( huart == &huart6 )
{
UART6_RXD_BUFF[UART6_RXD_COUNT] = TEMP_BUFF;
UART6_RXD_COUNT++;
}
}
当使用串口发送bin文件后,程序就会将文件完整得存储在SRAM的以0x20020000为首地址的位置。
5、接下来设置程序跳转:
当按下用户按键的时候,便跳转到刚刚接收到的程序中去:
#define APPLICATION_ADDRESS SRAM_FOR_USER_START_ADD
typedef void (*pFunction)(void);
pFunction JumpToApplication;
JumpToApplication = (pFunction) (*(__IO uint32_t*) (APPLICATION_ADDRESS + 4));
__set_MSP(*(__IO uint32_t*) APPLICATION_ADDRESS);
JumpToApplication();
6、接下来设置APP程序
打开一个按键和LED的程序,修改名称为XX_IAP:
7、在启动文件中修改向量表偏移地址:
8、然后在设置中修改向量表地址,和ROM、RAM的地址:
因为使用了RAM地址中的一部分作为程序存储ROM,为了防止代码执行过程会意外操作代码存储区,所以改小RAM的地址。
9、在输出转换选项卡中选择生成bin文件:
10、编译,不需要下载这个工程,而是将之前的BootLoader的程序下载。
11、代码刚刚烧录后是这个样子的,显示屏显示、LED6闪烁:
串口接收到数据:
12、使用串口助手打开文件,发送:
13、按下用户按键
串口发送回来了好长一大堆数据,这些就是bin文件中的内容,开发板的上的两颗LED已经在闪烁了,说明IAP成功了:
说明一:
尝试过使用外部PSRAM存储程序代码,但是会出现死机问题,程序跑不起来,怀疑是因为在执行APP程序时,外部PSRAM芯片被复位,导致内容丢失。
说明二:
此代码存在局限性:内部SRAM空间太小。只预留了128KB的空间存储代码,而且也导致了可以运行APP的RAM空间只剩余了128KB,所以在遇到占用空间较大的程序时,此代码便不能满足要求,可以采用SD卡、USB更新代码。