Warning: file_get_contents(/data/phpspider/zhask/data//catemap/2/linux/28.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
C ELF文件的哪一部分必须加载到内存中?_C_Linux_Memory_Elf - Fatal编程技术网

C ELF文件的哪一部分必须加载到内存中?

C ELF文件的哪一部分必须加载到内存中?,c,linux,memory,elf,C,Linux,Memory,Elf,可执行文件的ELF文件有一个程序(段)头和一个节头,可以通过readelf-a看到,下面是一个示例: 上面的两张图片分别是节头和节目(段)头。可以看出,段头由几个节头组成,用于将程序加载到内存中 是否只需要将.text、.rodata、.data、.bss节加载到内存中 段中的所有其他段(例如第三段中的.ctors、.dtors.jcr)是否用于对齐?段和段是两个完全不同的概念。部分涉及存储在其中的数据的语义(即它将用于什么),并且在程序或共享库链接后实际上是无关的,除非出于调试目的。您甚至

可执行文件的ELF文件有一个程序(段)头和一个节头,可以通过
readelf-a
看到,下面是一个示例:

上面的两张图片分别是节头和节目(段)头。可以看出,段头由几个节头组成,用于将程序加载到内存中

是否只需要将.text、.rodata、.data、.bss节加载到内存中


段中的所有其他段(例如第三段中的.ctors、.dtors.jcr)是否用于对齐?

段和段是两个完全不同的概念。部分涉及存储在其中的数据的语义(即它将用于什么),并且在程序或共享库链接后实际上是无关的,除非出于调试目的。您甚至可以完全删除节头(或者用随机垃圾覆盖它们),程序仍然可以工作

段(即程序头加载指令)是内核和/或动态链接器在加载程序时实际查看的内容。例如,在您的示例中,有两个load指令。第一个导致文件的第一个4k(1页)映射到地址0x08048000,并指示仅实际使用此映射的第一个0x4b8字节(其余为对齐)。第二个导致文件的前8k(2页)映射到地址0x08049000。其中绝大多数是对齐。前0xf14字节不是load指令的一部分(只是对齐),将被浪费。从0x08049f14开始,实际使用从文件映射的0x108字节,加载程序(内核或动态链接器)对另一个0x10字节(达到0x118的MemSize)进行零填充。这最多可跨越0x0804a02c(在第二个映射页面中)。第二个映射页的其余部分未使用/浪费(但是
malloc
可能能够将其恢复为堆的一部分)


最后,虽然部分标题根本不会被使用,但是程序运行时可能会使用许多不同部分的内容。请注意,代码的地址范围> Ctos//Code >和 DrOss/Code >位于第二个负载映射的开始,因此它们在运行时被程序映射和访问(运行时启动/退出代码将使用它们运行全局构造函数和析构函数,如果使用C++或“具有Cto/Dor属性的GNU C”代码)。还请注意,
.data
从第二个映射页面中的地址0x0804a00c开始。这允许第一页在应用重定位之后被保护为只读(程序头中的Relo指令)。< /P> @阿德里亚诺,是与页面大小对齐的,因此不同的保护可以用于程序的不同部分,例如,文本(RX),数据(RW)C是否有C++的构造函数或析构函数?这是“GNUC”。你可以做各种非标准的事情,比如异常和构造函数。@R..:,是
.data
段地址从
p_-vaddr
p_-filesiz
.bss
p_-addr+p_-filesiz
p_-memsiz
,然后第二次所有加载的大小是
p_-memsiz-p_-vaddr
?@Soumen:页面大小是特定于arch的ABI或运行时约束;对于x86_64,它是4k的倍数,实际上总是4k。由于段的长度超过了从起点(
0xf14
mod 4k)到下一个4k边界的距离,因此以4k页面大小需要2页。@Soumen:我想我可能说得不好。它更像是打包而不是对齐,它是一种折衷,可以节省少量(逻辑的,甚至可能不是真实的)磁盘空间,以换取在运行时浪费额外的页面。第一个0xf14字节是ELF头,第一个(只读)加载段的内容。如果链接器一直等到偏移量0x1000才开始第二个加载映射,那么它将全部装入一个页面。