如何拆解ELF文件大小:分析段与符号尺寸及文件大小差异
ELF文件size输出总和与实际文件大小不符的原因分析
我想了解ELF可执行文件或动态库中每个符号的大小,且认为符号总大小与其他部分大小之和应等于文件总大小。但通过size命令查看的段大小总和,和实际文件大小并不匹配,下面具体分析缺失的部分:
文件基础信息
文件libfoo.so的实际磁盘大小:
-rwxr-x---. 1 root root 20080 Dec 2 11:32 libfoo.so
执行size -A -d libfoo.so的输出结果:
.note.gnu.build-id 36 728 .gnu.hash 36 768 .dynsym 192 808 .dynstr 233 1000 .gnu.version 16 1234 .gnu.version_r 32 1256 .rela.dyn 168 1288 .rela.plt 72 1456 .init 27 4096 .plt 64 4128 .text 232 4192 .fini 13 4424 .rodata 16 8192 .eh_frame_hdr 28 8208 .eh_frame 100 8240 .init_array 8 15784 .fini_array 8 15792 .data.rel.ro 8 15800 .dynamic 544 15808 .got 32 16352 .got.plt 48 16384 .bss 8 16432 .comment 46 0 .GCC.command.line 101 0 .gnu.build.attributes 288 24632 .debug_aranges 48 0 .debug_info 1744 0 .debug_abbrev 388 0 .debug_line 161 0 .debug_str 873 0 .debug_line_str 348 0 Total 5966
缺失部分的具体说明
- ELF文件头与程序头表:
size命令默认不会统计这两部分。ELF文件头包含文件的基本标识、目标架构、入口地址等核心信息,64位系统下通常占64字节,32位系统下为52字节;程序头表描述了文件加载到内存时的段布局,每个表项在64位系统中是56字节,32位系统中是32字节,具体数量由ELF头的e_phnum字段决定。 - 段对齐填充字节:ELF文件中的段在磁盘上会按指定对齐值(通常为页大小4096字节)进行填充。比如输出中
.init段的起始偏移是4096,而前一个段.rela.plt结束于1456,中间从1457到4095的所有字节都是填充内容,这部分不会被size统计,但会算入实际文件大小。 - .bss段的特殊性:
.bss段用于存放未初始化的全局/静态数据,它在磁盘文件中不占用空间(输出中.bss的偏移为16432,但实际文件里没有这部分内容),size统计的是它在内存中加载后的大小,这部分数值不会计入磁盘文件的总大小。 - 其他未统计区域:少数情况下可能存在一些辅助段或文件末尾的额外数据,但最常见的缺失部分就是上述三类。
后续分析步骤
理清完整的段信息后,可以使用nm工具分析.text、.data等主要段中的符号细节,比如执行nm -S libfoo.so可以显示每个符号的大小及其所属段。
内容的提问来源于stack exchange,提问作者Lewis Chan
相关产品推荐
相关产品推荐

