BootLoader程序介绍
BootLoader其实就是一段启动程序,它在芯片启动的时候首先被执行,它可以用来做一些硬件的初始化,当初始化完成之后跳转到对应的应用程序中去。例如,我们可以将Flash分为两个区,一个是启动程序区(0x0800 0000 - 0x0800 2000)大小为8K Bytes,剩下的为应用程序区(0x0800 2000 - 0x0801 0000)。芯片上电时先运行启动程序,然后跳转到应用程序区执行应用程序。
源码实现
基本的BootLoader程序仅实现了代码跳转的功能,因此全部在main.c文件中实现。
源文件
- /*
- ******************************************************************************
- File: main.c
- Info: Generated by Atollic TrueSTUDIO(R) 9.3.0 2020-09-07
- The MIT License (MIT)
- Copyright (c) 2019 STMicroelectronics
- Permission is hereby granted, free of charge, to any person obtaining a copy
- of this software and associated documentation files (the "Software"), to deal
- in the Software without restriction, including without limitation the rights
- to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
- copies of the Software, and to permit persons to whom the Software is
- furnished to do so, subject to the following conditions:
- The above copyright notice and this permission notice shall be included in all
- copies or substantial portions of the Software.
- THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
- IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
- FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
- AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
- LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
- OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
- SOFTWARE.
- ******************************************************************************
- */
- /* Includes */
- #include "stm32f4xx.h"
- #include "delay.h"
- /* Private macro */
- //用户扇区从第5扇区的起始位置开始启动
- #define FLASH_APP_ADDR 0x08010000
- #define MCU_LED GPIOA_OUT(15)
- /* Private variables */
- typedef void (*UserApplication)(void); //定义一个函数类型的参数.
- UserApplication userApp;
- /* Private function prototypes */
- void ConfigLED( );
- void SystemBooting(uint8_t times, uint16_t msDelay);
- void IAPLoadApp(u32 appxaddr);
- /* Private functions */
- /**
- **===========================================================================
- **
- ** Abstract: main program
- **
- **===========================================================================
- */
- int main(void)
- {
- /**
- * IMPORTANT NOTE!
- * The symbol VECT_TAB_SRAM needs to be defined when building the project
- * if code has been located to RAM and interrupts are used.
- * Otherwise the interrupt table located in flash will be used.
- * See also the <system_*.c> file and how the SystemInit() function updates
- * SCB->VTOR register.
- * E.g. SCB->VTOR = 0x20000000;
- */
- /* TODO - Add your application code here */
- delay_init();
- ConfigLED();
- SystemBooting(5,100);
- //从第五扇区起始位置开始加载应用程序
- IAPLoadApp(FLASH_APP_ADDR);
- while(1);
- }
- void ConfigLED( )
- {
- GPIO_InitTypeDef GPIO_InitStructure;
- RCC_AHB1PeriphClockCmd(RCC_AHB1Periph_GPIOA, ENABLE);
- /**
- * System State LED
- */
- GPIO_InitStructure.GPIO_Pin = GPIO_Pin_15;
- GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz;
- GPIO_InitStructure.GPIO_Mode = GPIO_Mode_OUT;
- GPIO_InitStructure.GPIO_OType = GPIO_OType_PP;
- GPIO_InitStructure.GPIO_PuPd = GPIO_PuPd_UP;
- GPIO_Init(GPIOA, &GPIO_InitStructure);
- }
- void SystemBooting(uint8_t times, uint16_t msDelay)
- {
- for (uint8_t i = 0; i < times; i++)
- {
- MCU_LED = 0;
- delay_ms(msDelay);
- MCU_LED = 1;
- delay_ms(msDelay);
- }
- }
- void IAPLoadApp(u32 appxaddr)
- {
- if(((*(vu32*)appxaddr)&0x2FF00000)==0x20000000) //检查栈顶地址是否合法.
- {
- userApp=(UserApplication)*(__IO vu32*)(appxaddr+4); //用户代码区第二个字为程序开始地址(复位地址)
- __set_MSP(*(__IO uint32_t*) appxaddr); //初始化APP堆栈指针(用户代码区的第一个字用于存放栈顶地址)
- userApp(); //跳转到APP.
- }
- }
复制代码
stm32f4_flash.ld
设置BootLoader程序在flash中的位置为第1~2扇区,共32K空间。在笔者的项目中,第3~4扇区用来实现EEPROM的软件仿真,用户程序将从第5扇区开始启动。
- /* Specify the memory areas */
- MEMORY
- {
- FLASH (rx) : ORIGIN = 0x08000000, LENGTH = 32K
- RAM (xrw) : ORIGIN = 0x20000000, LENGTH = 128K
- MEMORY_B1 (rx) : ORIGIN = 0x60000000, LENGTH = 0K
- CCMRAM (rw) : ORIGIN = 0x10000000, LENGTH = 64K
- }
复制代码
使用指南
用户程序需要从第5扇区的起始位置开始下载,同时需要设置中断向量的偏移地址。
设置用户程序下载位置(stm32f4_flash.ld)
在笔者的项目中,设置BootLoader程序在flash中的位置为第1~2扇区,共32K空间。第3~4扇区用来实现EEPROM的软件仿真,共32K空间。用户程序将从第5扇区开始启动。
- /* Memories definition */
- MEMORY
- {
- FLASH (rx) : ORIGIN = 0x8010000, LENGTH = 448K
- RAM (xrw) : ORIGIN = 0x20000000, LENGTH = 128K
- CCMRAM (xrw) : ORIGIN = 0x10000000, LENGTH = 64K
- }
复制代码
修改中断向量表偏移量
在"system_stm32f4xx.c"文件中,修改宏定义:
- /*!< Uncomment the following line if you need to relocate your vector Table in
- Internal SRAM. */
- /* #define VECT_TAB_SRAM */
- #define VECT_TAB_OFFSET 0x10000 /*!< Vector Table base offset field.
- This value must be a multiple of 0x200. */
复制代码
在void SystemInit(void)中将会根据上述宏定义,设置中断向量表的偏移量:
- /* Configure the Vector Table location add offset address ------------------*/
- #ifdef VECT_TAB_SRAM
- SCB->VTOR = SRAM_BASE | VECT_TAB_OFFSET; /* Vector Table Relocation in Internal SRAM */
- #else
- SCB->VTOR = FLASH_BASE | VECT_TAB_OFFSET; /* Vector Table Relocation in Internal FLASH */
- #endif
复制代码
|