c - 对于 'C' 程序,常量局部变量数组在内存中的位置

标签 c gcc memory

我正在使用 GCC 4.8.1,它似乎没有在 DATA 段中存储 main 本地的 const 变量。下面是 3 个这样的程序的代码和内存映射:

代码 1:

int main(void) 
{ //char a[10]="HELLO"; //1 //const char a[10] = "HELLO"; //2 
return 0; 
} 

MEMORY MAP FOR ABOVE: 
text     data    bss     dec     hex    filename 
7264     1688 1040   9992    2708   a.exe 

代码 2:

int main(void)
{
    char a[10]="HELLO";
    //const char a[10] = "HELLO";
    return 0;
}

MEMORY MAP FOR 2: 
text     data    bss     dec     hex    filename 
7280     1688    1040    10008   2718 a.exe 

代码 3:

int main(void)
{
    //char a[10]="HELLO";
    const char a[10] = "HELLO";
    return 0;
}

MEMORY MAP FOR 3 :
 text    data    bss     dec     hex    filename 
7280     1688    1040    10008   2718   a.exe

我没有看到 3 个代码之间的数据段有任何差异。谁能给我解释一下这个结果。

感谢期待!

最佳答案

如果您的数组未被您的程序使用,那么允许编译器简单地优化对象。

来自 C 标准:

(C99, 5.1.2.3p1) "The semantic descriptions in this International Standard describe the behavior of an abstract machine in which issues of optimization are irrelevant"

(C99, 5.1.2.3p3) "In the abstract machine, all expressions are evaluated as specified by the semantics. An actual implementation need not evaluate part of an expression if it can deduce that its value is not used and that no needed side effects are produced (including any caused by calling a function or accessing a volatile object)."

如果您在禁用优化 (-O0) 的情况下编译您的程序 #3,或者根据您的编译器,该对象仍然可以分配。在您的情况下,它不会出现在 datarodata 部分中,而是出现在 text 部分中,因此 text 部分增加.

例如,在您的第三个示例中,在我的编译器中,带有 -O0 的结果代码是(使用 objdump -d 转储):

00000000004004d0 <main>:
  4004d0:       55                      push   %rbp
  4004d1:       48 89 e5                mov    %rsp,%rbp
  4004d4:       48 b8 48 45 4c 4c 4f    mov    $0x4f4c4c4548,%rax
  4004db:       00 00 00
  4004de:       48 89 45 f0             mov    %rax,-0x10(%rbp)
  4004e2:       66 c7 45 f8 00 00       movw   $0x0,-0x8(%rbp)
  4004e8:       b8 00 00 00 00          mov    $0x0,%eax
  4004ed:       5d                      pop    %rbp
  4004ee:       c3                      retq
  4004ef:       90                      nop

0x4f4c4c4548 是将字符串的 ASCII 字符移入寄存器,然后压入堆栈。

如果我用-O3编译同一个程序,输出就是:

00000000004004d0 <main>:
  4004d0:       31 c0                   xor    %eax,%eax
  4004d2:       c3                      retq
  4004d3:       90                      nop

并且该字符串没有出现在datarodata中,它只是被优化掉了。

关于c - 对于 'C' 程序,常量局部变量数组在内存中的位置,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/24431015/

相关文章:

c - "peek"入eventfd内部计数器值不变

c - 如何为数组单元格中的反向位顺序创建宏

linux - 为什么 GNU 链接器找不到带有 -l<library> 的共享对象?

windows - Haskell Platform/Cabal - 由于 'haskell-gi',链接时安装包 'undefined references' 失败

c++ - 包含 .cpp 文件而不是 .h 文件以使 vanilla gcc 能够更多地优化我的代码是个好主意吗?

php - 允许的内存大小 134217728 字节已用尽

python - 当原始引用现在指向一个新值时,Python 如何知道在哪里找到创建的不可变值?

比较整数函数 SIGSEGV

java - 私有(private)静态 final 与私有(private) final

c - 对寻找循环列表算法的疑惑