我通过使用Keil编译示例项目生成了* .o文件,然后用我想要的地址而不是默认的0x08000000
编辑了* sct文件,并使用指定的加载和执行生成了* .elf地址。
我已将* .elf文件加载到闪存中并且有效。它是在指定的地址下载的,但是当我检查内存时,我发现数据已经改变了,因为我没有触及* .o文件并且每次只调用链接器,所以这是有线的。
我的问题是,为什么使用相同的* .o,只需更改地址,我的数据也会受到影响?
答案 0 :(得分:1)
大多数嵌入式平台都必须遵循一些规则。
重置处理程序和向量表必须位于硬件指定的已定义位置。
复位引导区域不能有不同的加载和执行地址区域(LR / ER)。链接器插入脚本,如果这些脚本不重叠,则会将数据从加载区复制到执行区。例如下面的区域RW_IRAM1。由于在正常情况下无法写入闪存,因此失败。
如果未编译为与内存位置无关,则无法在编译后更改内存区域。代码可能包含绝对跳转
例如:foo()
跳转到0x0800400。或者为char x
读取0x0802FFE。
有效分散文件的示例。
LR_IROM1 0x08000000 0x00100000 { ; load region size_region
ER_IROM1 0x08000000 0x00001000 { ; load address = execution address
*.o (RESET, +First) ; boot code
*(InRoot$$Sections) ; linker loader parts, initializes RW_IRAM1
.ANY (+RO) ; your code
}
RW_IRAM1 0x20000000 0x00020000 { ; RW data
.ANY (+RW +ZI)
}
}
您可以为外部存储器添加额外的负载区域(LR)。如果loader application设置了界面 您可以添加额外的区域,例如非易失性存储器仿真。在编程期间预先加载或跳过它。
在这里,您可以找到the linker的所有内容。其中有一段散射加载。