记忆中的大空间?

时间:2014-05-04 21:45:19

标签: c memory embedded arm

我昨天开始实施的嵌入式编程非常新,我注意到了一些我觉得很奇怪的东西。我有一个非常简单的程序,什么都不做,但返回0。

int main() {

    return 0;
}

当我在IAR Embedded Workbench中运行时,我有一个内存视图显示程序内存。我注意到在内存中有一些内存,但它是一个空白空间的大块,然后再次有内存(我吮吸解释:P所以这里是一个内存的图像)

enter image description here

请帮助我理解这比现在多一点。我真的不知道要搜索什么,因为我对此很新。

3 个答案:

答案 0 :(得分:2)

前两行是8个中断向量,表示为最后一个字节最高的32位指令。也就是说,以4个字节为一组读取它们,最后一个字节为最后一个,然后通过常用方法转换为指令。前几个向量,包括存储单元0的复位,结果是LDR指令,它将立即地址加载到PC寄存器中。这会导致处理器跳转到该地址。 (复位向量也是设备开启时运行的第一条指令。)

您可以通过互联网搜索查看LDR指令here的结构,或许多其他地方。如果我们将复位向量18 f0 95 e5写为e5 95 f0 18,那么我们会看到PC寄存器加载的地址位于偏移量0x20处。

因此接下来的两行是前两行中的指令所引用的存储器位置。复位向量将PC发送到0x00000080,这是程序的C运行时启动的位置。 (其他向量将PC发送到程序结束附近的0x00000170。此指令的内容留给读者。)

通常,C运行时是添加到程序前端的代码,它将全局变量从闪存加载到RAM中,并将未初始化的RAM设置为0.之后程序启动。

你原来的问题是:为什么未使用闪存有这么大的差距?答案是闪存实际上不是很重要,所以我们可以浪费一点,并且在那里有额外的空间可以实现前向兼容性。如果我们需要增加向量表大小,那么我们不需要移动代码。事实上,无论如何,这种中断模型已在新的ARM Cortex处理器中进行了更改。

答案 1 :(得分:1)

UncleO是对的,但这里有一些额外的信息。

项目的链接器命令文件(IAR EW的* .icf)确定节在内存中的位置。 (在Project-> Options-> Linker-> Config下查看以识别您的链接器配置文件。)如果您使用文本编辑器查看链接器命令文件,您可能能够识别它找到名为.intvec的部分的位置(或者类似的)在地址0x00000000处。然后它可能会在地址0x00000080处找到另一个部分(可能是.text)。

您还可以查看.map文件中标识的这些内存部分及其位置。 (确保在Project-> Options-> Linker-> List下检查“生成链接器映射文件”。)映射文件是构建的输出,然而,它是确定位置的链接器命令文件。 / p>

因此内存中的空间存在,因为链接器命令文件指示它是那样的。我不确定这个空间是否必要,但肯定不是问题。您可以尝试使用链接器命令文件并移动第二部分。但是异常表(a.k.a.中断向量表)必须位于0x00000000。并且如果移动它,您将需要确保重置向量指向启动代码的新位置。

答案 2 :(得分:0)

物理(非虚拟)内存地址映射到物理电路。最低地址通常映射到寄存器,而不是RAM阵列。为了保持一致性,给定地址通常映射到同一系列的不同处理器上的相同功能,并且缺少的功能在地址映射中显示为小孔。

此外,在所有I / O寄存器和内务处理功能之后,RAM被分配到一个连续的地址范围。这会在所有寄存器和RAM之间产生一个大漏洞。

或者,正如@Martin建议的那样,它可能表示未初始化和只读的Flash存储器为--个字节。与真正未分配的地址不同,访问它不太可能产生异常,甚至可以使用适当的Flash控制器命令使它们“重新出现”。

在现代桌面级计算机上,虚拟内存会隐藏所有这些内容,甚至可以配置物理地址映射的某些部分。许多嵌入式处理器允许配置到指定中断向量表的位置。