在MPC5744的bootloader中保留RAM指定位置的数据,需要通过修改链接脚本和启动代码来实现。以下是具体步骤:
1. 使用链接脚本定义保留内存区域
在链接脚本(.ld文件)中创建一个不被初始化的内存段(如.noinit
),确保该段不被.bss
或.data
初始化过程覆盖。
示例链接脚本修改:
SECTIONS {
.noinit (NOLOAD) : {
*(.noinit)
} > SRAM
/* 其他原有段定义保持不变 */
}
NOLOAD
关键字指示加载器不初始化该段。
> SRAM
指定该段位于SRAM中,需根据实际内存布局调整。
2. 在代码中将变量标记为noinit
使用编译器特定的属性将标志变量放入.noinit
段,避免启动代码对其初始化。
GCC编译器示例:
__attribute__((section(".noinit"))) volatile uint32_t boot_flag;
IAR编译器示例:
__no_init volatile uint32_t boot_flag;
3. 修改启动代码跳过保留区域
检查启动代码(如startup.s
或crt0.S
),确保在初始化.bss和.data时不覆盖.noinit
段。
关键代码修改点:
- 清零.bss段:确保循环清零时跳过
.noinit
区域。
- 复制.data段:不影响.noinit,因为它不位于.data中。
示例(伪代码):
/* 清零.bss段的循环 */
la r3, __bss_start__
la r4, __bss_end__
/* 检查是否进入.noinit区域,调整结束地址 */
cmpwi r3, r4
beq bss_done
4. 验证RAM保留行为
- 调试器检查:复位后通过调试器查看标志地址的值是否保留。
- 边界测试:确保其他代码(如APP)不会意外覆盖该区域。
5. 注意事项
- 多核场景:如果是多核MCU,确保其他核不会在复位时修改该区域。
- 编译器兼容性:不同编译器(GCC、IAR、Diab)的noinit语法可能不同。
- 内存对齐:确保标志变量地址对齐,避免访问异常。
通过以上步骤,标志变量在非掉电复位后不会被bootloader的初始化过程清除,从而实现APP到bootloader的状态传递。