了解BootLoader——基于MPC5744P Bootloader例程

news/2024/7/4 4:52:35 标签: 嵌入式

一、BootLoader的作用:BootLoader是固化在PFlash中的一个程序,其作用可以分为两部分:boot和load。

  (1)boot:MCU上电时首先会运行BootLoader程序(因为它一般位于PFlash最前面的启动区,接下来会谈到启动区Boot location的概念),BootLoader程序会初始化系统时钟、看门狗等以保证系统的正常运行,此外还会初始化CAN(也可以是串口、SPI等)以实现和上位机的通信。

  (2)load:系统初始化完成后,程序会进入等待状态,如果在预定时间内没有接收到上位机的程序下载请求信号(CAN帧),则跳转并执行MCU内部原有的用户应用程序(位于PFlash的其他启动区)。如果在预定时间内接收到来自上位机的程序下载请求信号,则BootLoader程序进入新程序下载状态。下载过程中,上位机与BootLoader程序之间采用一问一答的方式逐行的下载S19文件(用户应用程序的可执行文件)并进行解析,得到程序地址和程序数据,从而将每一行程序数据按照程序地址写入到PFlash中。程序下载完成后,清除RAM,关闭CAN等BootLoader用到的外设,跳转到新的用户应用程序并开始执行。

二、Boot location的概念:Boot location就是每次MCU复位后运行BAM(Boot Assist Module)时寻找合法复位配置半字RCHW(Reset Configuration Harf-Word)和应用程序开始地址(Application Start Address,也可以叫做应用程序复位向量地址(Reset Vector)的区域。复位后CPU将从Boot location0~7依次查找由正确Boot_ID--0x5A组成的合法复位配置半字和应用程序开始地址,从而执行用户应用程序。MPC5744P有8个Boot location,在Flash Memory Map中标明了哪些block可以作为Boot location,如下图:

 

 Boot location的组成如下图所示:

Boot location的起始位置是复位配置半字(RCHW),其结构如下所示。

只有设置了真确的BootID,该Boot location才被识别为可启动的,如BootLoader程序和用户应用程序生成的S19文件:

  

 

 

 

在BootLoader程序的S19文件第二行中,0x00F98000为Boot location_0的起始地址,也就是RCHW的地址,其中存放的数据为0x01_5A,RCHW的VLE位置1,BOOT_ID为0x5A,即配置该Boot location为可启动的。reserve的16-31位默认为0x00

从用户应用程序的S19文件第三行可以看到,0x00FA0004为用户应用程序开始地址(应用程序复位向量地址),其中记录的数据0x0100000为应用程序的复位函数地址,也就是应用程序真正开始执行的地址。因此,一般用如下方法实现到用户应用程序的跳转:

#define APP_StartAddr (*(uint32_t*)0x00FA0004)
(*(void (*)(void))(APP_StartAddr))();

 

三、BootLoader程序和用户应用程序App在PFlash中的位置关系(Flash分配)

对BootLoader程序和用户应用程序的 link_file做如下设置:

MEMORY  //BootLoader
{

    /*16 KB low flash memory block 2 (boot location 0) from 0x00F98000 to 0x00F9BFFF*/  
    /*16 KB low flash memory block 3 (boot location 1) from 0x00F9C000 to 0x00F9FFFF*/
    /* use the low flash memory block 2 and 3(32KB in total) as bootloader area */
    
    flash_rchw : org = 0x00F98000,   len = 0x4
    cpu0_reset_vec : org = 0x00F98004,   len = 0x4
    
    m_text :    org = 0x00F99000, len = 28K    /*code flash for bootloader interrupt vector table, startup and boot codes*/
    
    m_data :    org = 0x40000000,   len = 384K  /*system SRAM*/
    
    local_dmem  : org = 0x50800000,   len = 64K /*CPU core data tightly coupled memory*/         
}
MEMORY  //User App
{

    flash_rchw : org = 0x00FA0000,   len = 0x4
    cpu0_reset_vec : org = 0x00FA0004,   len = 0x4
        
    m_text :    org = 0x1000000, len = 2048K  
    m_data :    org = 0x40000000,   len = 384K
    
    local_dmem  : org = 0x50800000,   len = 64K    
}

则BootLoader和App的在PFlash中的关系如下:

 

 

四、S19文件结构:

五、数据对齐问题:

例程中的对齐函数主体及注释如下:

    stafno = (srcd_t->addr&0x7)>>1;   /* number of uint16_t need to be pre-staffed  */  //if addr is not a multiple of 8-Bytes, get the surplus bytes then >>1
    srcd_t->addr &= 0xFFFFFFF8;           /* align data base address at 4W   */            //about why >>1(divided by 2 regardless odd num addr): maybe there isn't odd address
    
    if(stafno) 
    {
        for(i=srcd_t->dtlen; i>0; i--) 
            srcd_t->data[i+stafno-1] = srcd_t->data[i-1];  // move forward data in number of stafno
        
        srcd_t->dtlen += stafno;    // update dtlen
        
        while(stafno--)    
            srcd_t->data[stafno] = 0xFFFF;           // pre-staff 0xFFFF
    }

    while((srcd_t->dtlen&0x000003)!=0)   // need to append post-staffing uint16_t  //if data num is a multiple of 4(each data is uint_16, so it's a judge of 64bits - 8bytes)
        srcd_t->data[srcd_t->dtlen++] = 0xFFFF; //if not enough 4*uint_16 - 8bytes, padding with 0xFFFF behind data's tail
}
// conclusion: address is aligned with 8bytes by &0xFFFFFFF8, but data field will not move accordingly,
// it just padding with 0xFF in the front of array, so as to accord with origin address(0x0004) correctly
//
//    address     data(uint16)                address     data(uint16)
//    |0x0000|                                |0x0000|<-- 0xFF
//    |0x0002|                     after      |0x0002|    0xFF
//    |0x0004|<-- 0x55(data[0])    =======>>  |0x0004|    0x55
//    |0x0006|    0x66             address    |0x0006|    0x66
//    |0x0008|    0x77             align      |0x0008|    0x77
//    |0x000A|    0x88                        |0x000A|    0x88
//    |0x000C|                                |0x000C|
//
//     note: (1) i guess that 0xFF will not be recognized as a instruction by CPU, so CPU fetch instruction from 0x0000
//                but execute from 0x0004 in fact.
//           (2) and note that the graph above is base on the struct SRecord_t,
//                so that data[0] is always correspond with base address(SRecord->addr)

其中srcd_t的结构如下:

typedef struct {
    uint32_t addr;
    uint32_t  dtlen;  // num of valid data
    uint16_t  data[20];
} SRecord_t;

另外,关于数据对齐问题,可以参考博文:https://blog.csdn.net/maxlovezyy/article/details/70231804

 

六、其他:下图为建立多核工程时的Flash和RAM资源的分配,可以用来参考以加深对程序在内存中的存储的理解

 

转载于:https://www.cnblogs.com/uestcliming666/p/10370488.html


http://www.niftyadmin.cn/n/706651.html

相关文章

【翻译自mos文章】注意: ASMB process exiting due to lack of ASM file activity

注意&#xff1a; ASMB process exiting due to lack of ASM file activity 參考原文&#xff1a; NOTE: ASMB process exiting due to lack of ASM file activity (Doc ID 754110.1) 适用于&#xff1a; Oracle Server - Enterprise Edition - Version 10.1.0.2 to 11.2.0.4 …

java基础(一)-----java的三大特性之封装

面向对象编程有三大特性&#xff1a;封装、继承、多态。本文将介绍java的三大特性之封装 封装 封装从字面上来理解就是包装的意思&#xff0c;专业点就是信息隐藏&#xff0c;是指利用抽象数据类型将数据和基于数据的操作封装在一起&#xff0c;使其构成一个不可分割的独立实体…

08-工厂方法

1. 简介 工厂方法&#xff1a;符合依赖倒置原则、单一职责、开闭原则。 与简单工厂的区别&#xff1a;简单工厂是在一个工厂里生成多个不同的类&#xff0c;而工厂方法是一个对象对应一个生成工厂&#xff0c;这些工厂都实现了一个共同的接口IFactory&#xff0c;很好的符合了依…

ubuntu系统中Qt creator 编辑和应用使用中文输入法

在ubuntu系统的GUI开发过程中遇到在编辑器里面不能使用中文输入法&#xff0c;前提我已经安装了搜狗输入法&#xff0c;但是还是不能使用&#xff0c;原因是QT的库里没有最新fcix的库&#xff0c;、 没有安装搜狗的输入法的 https://pan.baidu.com/s/1pLNo9fX 我这里百度云有链…

剑指offer——面试题10:斐波那契数列

个人答案&#xff1a; 1 #include"iostream"2 #include"stdio.h"3 #include"string.h"4 using namespace std;5 typedef long long ll;6 const int MAXN10000;7 8 ll fib[MAXN];9 ll Fibonacci(int n) 10 { 11 if(fib[n]!-1) 12 ret…

395. Longest Substring with At Least K Repeating Characters

题目要求 Find the length of the longest substring T of a given string (consists of lowercase letters only) such that every character in T appears no less than k times.Example 1:Input: s "aaabb", k 3Output: 3The longest substring is "aaa&qu…

Asp.Net实现JS前台带箭头的流程图方法总结!(个人笔记,信息不全)

Asp.Net实现JS前台带箭头的流程图方法总结&#xff01;&#xff08;持续更新中&#xff09; 一、返回前台json格式 json5 "[{\"Id\":2259,\"Name\":\"高中\"},{\"Id\":2259,\"tName\":\"初中\"},{"Id&…

Java 对象的继承,抽象类,接口

子父级继承 关键字 extends 首先创建一个父类 1 class Fu 2 { 3 String name; 4 int a1; 5 public void word() 6 { 7 System.out.println("工作"); 8 …