const数据存储在哪里?

时间:2016-04-22 21:18:55

标签: c++

例如:

在文件demo.c中,

#inlcude<stdio.h>
int a = 5;
int main(){
  int b=5;
  int c=a;
  printf("%d", b+c);
  return 0;
}

对于int a = 5,编译器是否将其转换为虚拟内存地址处的存储0x5,例如,const区域中的Ox0000000f,以便对于int c = a,它将被翻译类似于movl 0x0000000f %eax

然后对于int b = 5,数字5不会被放入const区域,而是直接转换为汇编指令中的立即数mov $0x5 %ebx

2 个答案:

答案 0 :(得分:1)

这取决于。你的程序有几个常量:

int a = 5;

这是一个静态的&#34;初始化(在运行之前加载程序文本和数据时发生)。该值存储在由a保留的存储器中,该存储器位于读写数据&#34;程序部分&#34;中。如果某些内容发生变化a,则值5将丢失。

int b=5;

这是一个范围有限的局部变量(仅限main())。存储可以是CPU寄存器或堆栈上的位置。为大多数体系结构生成的指令将值5作为&#34;立即数据&#34;放置在x86示例中:

mov   eax, 5

指令保持任意常量的能力是有限的。大多数CPU指令都支持小常量。 &#34;大&#34;通常不直接支持常量。在这种情况下,编译器会将常量存储在内存中并加载它。例如,

       .psect  rodata
k1     dd      3141592653
       .psect  code
       mov     eax  k1

ARM系列具有强大的设计,可以直接加载大多数常量:任何8位常数值都可以旋转任意偶数次。请参阅this第2-25页。

声明中有一个不那么明显但完全不同的项目:

printf("%d", b+c);

字符串%d通过现代C语义,是一个由三个char组成的常量数组。大多数现代实现都会将它存储在只读内存中,以便尝试更改它会导致SEGFAULT,这是一个低级CPU错误,通常会导致程序立即中止。

       .psect  rodata
s1     db      '%', 'd', 0
       .psect  code
       mov     eax  s1
       push    eax

答案 1 :(得分:1)

在OP的程序中,a是“初始化的”“全局”。我希望它放在数据段的初始化部分。请参阅https://en.wikipedia.org/wiki/File:Program_memory_layout.pdfhttp://www.cs.uleth.ca/~holzmann/C/system/memorylayout.gif(来自more info on Memory layout of an executable program (process))。 a的位置由编译器 - 链接器duo决定。

另一方面,作为自动(堆栈)变量,预计堆栈段中会出现bc

据说,只要未违反观察到的行为(What exactly is the "as-if" rule?),编译器/链接器就可以执行任何优化。例如,如果永远不会引用a,那么它可能会完全优化。