Linux size 命令,为什么bss 和data 部分不为零?

Linux size command, why are bss and data sections not zero?

我遇到了 size 命令,它给出了 ELF 文件的部分大小。在玩弄它时,我为最简单的 C++ 程序创建了一个输出文件:

int main(){return 0;}

显然,我没有定义任何初始化或未初始化的数据,那么为什么我的 BSS 和 DATA 部分大小为 512 和 8 个字节?

我认为可能是因为 int main(),我尝试为以下 C 程序创建目标文件:

void main(){}

我仍然没有得到 BSS 和 DATA 部分的 0。

是否因为分配给这些部分的某个最小大小的内存?

编辑-我认为这可能是因为链接库,但我的对象是动态链接的,所以可能不应该是问题

int main(){return 0;} 仅将数据放入 .text

$ echo 'int main(){return 0;}' | gcc -xc - -c -o main.o && size main.o
   text    data     bss     dec     hex filename
     67       0       0      67      43 main.o

您可能size正在使用完全链接的可执行文件。

$ gcc main.o -o main && size main
   text    data     bss     dec     hex filename
   1415     544       8    1967     7af main

事实上,如果您使用附加到二进制文件的 libc 进行编译,则会在 main() 函数之前(和之后)添加一些函数。它们在这里主要是为了加载动态库(即使你不需要它)并在 main() 结束后正确卸载它。

这些函数有需要存储的全局变量; BSS 段中未初始化(零初始化)的全局变量和 DATA 段中已初始化的全局变量。

这就是为什么,在使用 libc 编译的所有二进制文件中,您总是会看到 BSS 和 DATA。如果你想摆脱这个,那么你应该编写自己的汇编程序,像这样 (asm.s):

.globl _start
 _start:
    mov %eax, %ebx

然后,在没有 libc 的情况下编译它:

$> gcc -nostdlib -o asm asm.s

您应该减少此 ELF 二进制文件上 BSS 和 DATA 段的足迹。