[STM32]HAL库实现自己的BootLoader-BootLoader与OTA-STM32CUBEMX

目录

一、前言

二、BootLoader

三、BootLoader的实现

四、APP程序

五、效果展示

六、拓展


一、前言

听到BootLoader大家一定很熟悉,在很多常见的系统中都会存在BootLoader。本文将介绍BootLoader的含义和简易实现,建议大家学习前掌握些原理基础。

二、BootLoader

Boot系统即设备启动时优先运行的程序,可以帮助我们选择进入哪一个系统。在电脑中,Boot系统也是十分重要的,系统的基础功能和引导功能都是有Boot实现的。

而Loader即载入系统,载入用户真正使用的系统。

系统上电后,先进入Boot程序,由Boot程序决定进入系统,还是等待用户指令。以单片机为例,假设其Flash为20K,那么我可以将其分为两个区域,一个区域用于存储Boot程序,一个区域用于存储应用程序(APP),而Boot程序只烧写一次,用户烧录APP程序时,仅擦除APP区域。

Boot程序作为独立的单片机程序,当然也可以完成擦除和写入Flash的功能,如果我们在Boot程序运行时,将APP对应的Flash信息发送给Boot程序,由Boot程序对Flash中的APP区的擦除和写入,那是不是同样能实现烧写程序的功能。

如果将发送方式改为蓝牙、WIFI等无线形式,是不是就能对APP程序实现远程烧写。既然远程烧写能够实现,那么远程升级的功能应运而生,这就是OTA(On The Air)。

三、BootLoader的实现

配置基础的STM32CUBEMX工程,此处选用芯片为STM32F103C8T6.

此处我只配置了一个串口(波特率256000,自定),用于输出调试信息,并使能DMA和中断。

打开项目工程。此处STM32F103C8T6的Flash为64K,其实地址为0x08000000,则Flash范围为0x0800 0000~0x0800 FFFF,此处我划Boot分区16K,APP分区48K,则Boot分区Flash范围为:0x0800 0000~0x0800 3FFF,Size = 0x4000。

按照下图配置。

如果你使用ST-Link或者其他烧写器的话,在Boot程序工程中要勾选全部擦除

此时,我们让设备等待三秒,随后进入APP。

cpp 复制代码
__asm void MSR_MSP(uint32_t addr)
{
    MSR MSP, r0
    BX r14;
}
 
void App_Loading(void)
{
	APP_FUNC Jump;//定义一个函数指针
	printf("\n%x\n",(*(uint32_t *)APP_ADDR)&0x2FFFFFFF);
	// 栈顶地址是否合法
	if(((*(uint32_t *)APP_ADDR)&0x2FFFFFFF) < (0x20000000+0x400 * RAM_SIZE))
	{
		printf("Start To APP");
		//设置栈指针 
		MSR_MSP(APP_ADDR);
		// 获取复位地址
		Jump=(APP_FUNC)*(volatile uint32_t *)(APP_ADDR+4);	
		//设置栈指针
		__set_MSP(*(volatile uint32_t *)APP_ADDR);
		//关闭所有中断
		__set_PRIMASK(1);
		// 跳转至APP 
		Jump();
	}
	else{
		
		printf("Address Not Found");
		
	}
}

将程序烧写进单片机,Boot程序就已经下载完成了。

注意,使用printf函数需要重写fputc并且勾选MicroLib。

cpp 复制代码
#include "stdio.h"

int fputc(int c, FILE* stream)
{
	uint8_t ch[]={c};
	HAL_UART_Transmit(&huart1,ch,1,0xffff);
	return c;
}

四、APP程序

在自己定制的BootLoader中,APP的程序与日常使用的程序有些许不同,由于在BootLoader中我们更改了一些参数配置,为了能够顺利跳转到APP程序中。但这些配置需要恢复才能让APP程序正常运行。

使用STM32CUBEMX生成一个LED闪烁的程序,使用Keil打开工程。

先配置程序烧写区域,上述中Boot区域占16K,因此APP程序起始地址为0x0800 4000 ,APP程序48K,即Size = 0xC000。

有ST-LINK的情况下,需要设置烧写模式为仅擦除训选择区域,防止擦除Boot程序。

随后在main.c中main函数中添加这两条语句。

cpp 复制代码
	//SCB ->VTOR = FLASH_BASE | OFFSET;
	SCB ->VTOR = FLASH_BASE | 0x4000;
	__set_PRIMASK(0);

五、效果展示

将单片机程序烧写进板子后,打开串口助手,并观察效果。

观察到单片机顺利进入APP程序,并且实现了交替闪烁。

六、拓展

大家可以添加菜单模式,比如通过串口收到某个指令随后进入菜单模式,实现擦除或者其他操作。我实现了一小部分,大家可以看看。源码不需要积分。

本文仅帮助快速实现BootLoader,具体原理讲解将在另一篇博文进行。

BootLoader源工程:BootLoader

APP源工程:简易APP配套BootLoader

相关推荐
lantiandianzi4 小时前
基于单片机的多功能跑步机控制系统
单片机·嵌入式硬件
文弱书生6564 小时前
输出比较简介
stm32
哔哥哔特商务网4 小时前
高集成的MCU方案已成电机应用趋势?
单片机·嵌入式硬件
跟着杰哥学嵌入式4 小时前
单片机进阶硬件部分_day2_项目实践
单片机·嵌入式硬件
电子科技圈5 小时前
IAR与鸿轩科技共同推进汽车未来
科技·嵌入式硬件·mcu·汽车
东芝、铠侠总代136100683936 小时前
浅谈TLP184小型平面光耦
单片机·嵌入式硬件·物联网·平面
lantiandianzi6 小时前
基于单片机中医药柜管理系统的设计
单片机·嵌入式硬件
嵌入式知识大讲堂6 小时前
HDMI数据传输三种使用场景
单片机
黑客呀7 小时前
[系统安全]Rootkit基础
stm32·单片机·系统安全
小A1597 小时前
STM32完全学习——使用SysTick精确延时(阻塞式)
stm32·嵌入式硬件·学习