a.out中的数据部分

时间:2012-09-27 07:50:58

标签: c unix operating-system systems-programming

这是我执行的简单代码

int a;
int main()
{
    return 0;
}

然后用gcc编译后我做了

size a.out

我在bss和数据部分得到了一些输出......然后我将我的代码改为

int a;
int main()
{
    char *p = "hello";
    return 0;
}

再次当我在编译后通过大小a.out看到输出时,数据部分的大小保持不变。但是我们知道字符串hello将在只读初始化部分中分配内存。那么为什么数据部分的大小保持不变?

5 个答案:

答案 0 :(得分:5)

#include <stdio.h>

int main()
{
return 0;
}

它给出了

   text    data     bss     dec     hex filename
    960     248       8    1216     4c0 a.out

当你做

int a;
int main()
{
    char *p = "hello";
    return 0;
}

它给出了

   text    data     bss     dec     hex filename
    982     248       8    1238     4d6 a.out

当时hello存储在.rodata中,并且该地址的位置存储在char指针p中,但此处p存储在堆栈中

和size不显示堆栈。我不确定但.rodata在这里以文本或十进制计算。


当你写

int a;
char *p = "hello";
int main()
{
    return 0;
} 

它给出了

   text    data     bss     dec     hex filename
    966     252       8    1226     4ca a.out

现在这里再次“hello”存储在.rodata中,但char指针占用4个字节并存储在数据中,因此数据增加4个

了解更多信息http://codingfreak.blogspot.in/2012/03/memory-layout-of-c-program-part-2.html

答案 1 :(得分:2)

实际上,这是一个实现细节。编译器按原样工作。这意味着只要程序的行为相同,就可以自由地排除它想要的任何代码。在这种情况下,它可以完全跳过char* p = "hello"

答案 2 :(得分:2)

字符串“hello”在.rodata

部分中分配

答案 3 :(得分:1)

即使总大小没有改变,也不代表代码没有改变。

我测试了你的例子。 字符串“hello”是一个常量数据,因此它存储在readonly .rodata部分中。 您可以使用objdump查看此特定部分,例如:
objdump -s -j .rodata <yourbinary>

使用gcc 4.6.1没有任何选项,我得到了你的第二个代码:

Contents of section .rodata:
 4005b8 01000200 68656c6c 6f00               ....hello.

答案 4 :(得分:0)

由于您未在代码中使用char *,因此编译器对其进行了优化。