KEIL MDK 分散加载示例1-更改程序运行基址
KEIL MDK 分散加载示例1-更改程序运行基址
小编我一向主张在实战中学习,不主张直接去去学习规则&定义,太枯燥,在实际应用中去摸索,才会真正理解具体的技术细节,下面我们就通过实际的简单用例来搞清楚分散加载。
更改程序运行基址
我们先来做一个最简单的示例,然后逐步深入。
这里选择一颗简单一些的MCU,LPC824,一颗M0+作为示例(因为其比较简单,作为示例比较合适),我们先来看其默认的分散加载:
加载域地址从0x00000000地址开始,大小为0x8000(32KB),运行域(RO)从0x00000000开始,运行域(RW+ZI)从片内SRAM地址开始0x10000000。
我们尝试让程序从0x00001000地址上开始运行,我们该如何修改?加载域以及RO运行域直接改成0x00001000???可行吗?我们试试,我们把分散加载修改过来试试,看程序能不能运行。
按照上图修改分散加载,我们点击DEBUG,看程序是否能够正常调试,程序进入如下状态:
我们再之前的文章里面介绍过,你可以去查一下芯片的Memory MAP,这个地址空间其实是BOOT ROM(之前文章有过介绍。不知道BOOT ROM是啥的出门左转)你调试一下就会发现程序在里面死循环无法正常运行。
纳尼?不能跑??WHY???分散加载不好使了?????我们仔细分析一下,哪里出了问题,我们之前的文章说过MCU上电从BOOTROM启动起来之后会默认去0x00000000地址上去找MSP,从0x00000004地址上去找PC,但现在程序的加载地址以及运行地址都变成0x00001000了,而不是0x00000000地址了,我们需要告诉MCU,默认地址变了,不是0x00000000。那怎么告诉MCU呢?
其实在M0+/M3/M4内核里面有一个叫VTOR的寄存器(M0核里面我记得是没有),地址是0xE000ED08,这个寄存器用于设置异常&中断向量表默认地址,我们需要在程序运行起来之前设置VTOR寄存器,告诉MCU,地址变成0x00001000了,那怎么做呢?在这里,如下图:
这里有一个仿真器初始化文件,可以在程序下载之前写一些寄存器做一些初始化之类的工作,是一个扩展名为.ini的文件,也有其自己的语法,按照下图编写这个ini文件:
这里简单解释下这个ini文件的意思:FUNC的意思是定义一个函数,Setup()是对应的函数,内容大家都看得懂,直接给MSP以及PC赋值,然后写0xE000ED08(VTOR寄存器)地址,告知MCU地址启动地址改变了,最后一行代码的意思是调用Setup()函数。然后把写好的ini文件放到刚才的位置上,如下图:
我们再次运行一次程序,如下,我们的程序完美运行:
这只是一个最简单的分散加载使用示例,我们会尝试把代码加载到RAM中运行,就像电脑和手机一样;我们也会尝试把单独的一个函数或者一个变量加载到固定地址上;我们还会有把一个Flash空间加载多个image的示例等等。
当然上面提到的.ini文件能做的事情也远不止于此,以后我们还会多次涉及这个文件的用法。