vmlinux是Linux 内核编译后生成的原始、未压缩的 ELF 可执行文件它是内核的完整二进制映像包含了所有内核代码、数据、符号表和调试信息。1. 基本概念文件性质格式ELFExecutable and Linkable Format可执行文件位置位于内核源码编译目录通常是arch/架构/boot/的上级目录大小通常很大几十到几百MB因为包含调试符号状态未压缩、未处理的原始内核映像与其它内核文件的关系vmlinux (原始ELF文件) ↓ 压缩 添加解压代码 arch/x86/boot/compressed/vmlinux.bin ↓ 转换为特定格式 arch/x86/boot/bzImage (最终引导文件)2. 主要特点包含完整信息所有内核代码段.text所有数据段.data, .bss完整的符号表函数名、变量名及其地址调试信息DWARF 格式如果编译时开启重定位信息节区头表、程序头表等 ELF 元数据不可直接引导需要经过处理才能被引导加载器使用处理步骤包括压缩可选添加解压引导代码转换为引导加载器可识别的格式3. 主要用途内核调试# 使用 gdb 调试内核gdb vmlinux# 连接到 QEMU 运行的内核(gdb)target remote :1234# 设置断点(gdb)b sys_open(gdb)c符号分析# 查看所有符号nm vmlinux# 查看特定符号nm vmlinux|grepsys_call_table# 查看符号详细信息readelf-svmlinux|less# 查看节区信息readelf-Svmlinux反汇编分析# 反汇编特定函数objdump-dvmlinux--disassemblesys_open# 查看整个代码段objdump-dvmlinux-j.text|less生成 System.map# System.map 通常从 vmlinux 生成nm-nvmlinux|grep-v\( [aNUw] \)\|\(__crc_\)\|\( \$[adt]\)System.map性能分析支持perf 等工具需要 vmlinux 中的调试信息进行符号解析火焰图生成需要符号信息4. 文件结构示例使用readelf -h vmlinux查看 ELF 头ELF Header: Magic: 7f 45 4c 46 02 01 01 00 00 00 00 00 00 00 00 00 Class: ELF64 Data: 2s complement, little endian Version: 1 (current) OS/ABI: UNIX - System V ABI Version: 0 Type: EXEC (Executable file) Machine: Advanced Micro Devices X86-64 Version: 0x1 Entry point address: 0x1000000 Start of program headers: 64 (bytes into file) Start of section headers: 145765632 (bytes into file) Flags: 0x0 Size of this header: 64 (bytes) Size of program headers: 56 (bytes) Number of program headers: 5 Size of section headers: 64 (bytes) Number of section headers: 45 Section header string table index: 445. 与相关文件的区别文件性质用途大小可引导vmlinux原始ELF文件调试、分析大否vmlinuz压缩内核实际引导较小是bzImage大内核映像x86引导较小是zImage小内核映像旧x86/嵌入式较小是System.map文本符号表地址解析小-/proc/kallsyms运行时符号表动态调试--6. 实际应用场景场景1内核崩溃分析# 使用 crash 工具分析 vmcorecrash vmlinux vmcore# 查看崩溃时的堆栈crashbt crashlog场景2函数地址验证# 编译时地址nm vmlinux|grepstart_kernel# 输出ffffffff81000000 T start_kernel# 运行时地址需rootgrepstart_kernel/proc/kallsyms# 输出ffffffff8b200000 T start_kernel (KASLR偏移)场景3内核模块开发# 查看内核导出符号nm vmlinux|grep __ksymtab|less# 验证模块使用的符号是否存在场景4安全研究# 分析内核漏洞利用objdump-dvmlinux --start-address0xffffffff81000000|less# 查找特定指令序列objdump-dvmlinux|grepret|grep-c7. 如何获取 vmlinux从源码编译# 1. 配置内核makedefconfig# 或 make menuconfig# 2. 编译make-j$(nproc)# 3. vmlinux 生成在源码根目录ls-lhvmlinux从发行版获取# Debian/Ubuntuaptinstalllinux-image-$(uname-r)-dbgsym# 文件通常位于/usr/lib/debug/boot/vmlinux-$(uname-r)# 或从内核包提取dpkg-xlinux-image-*.deb /tmp/从调试信息包# RHEL/CentOSdebuginfo-install kernel-$(uname-r)# 文件位于/usr/lib/debug/lib/modules/$(uname-r)/vmlinux8. 注意事项版本匹配vmlinux 必须与运行内核版本完全一致配置一致编译配置影响符号和地址KASLR 影响运行时地址 编译地址 KASLR 偏移存储空间vmlinux 文件很大通常不包含在发行版中安全考虑包含完整符号信息生产环境通常不提供9. 相关工具链# 完整分析流程示例1. 获取 vmlinux2. 提取符号nm vmlinuxsymbols.txt3. 反汇编关键函数objdump-dvmlinux--disassembledo_forkdo_fork.asm4. 调试分析gdb vmlinux5. 性能关联perf report--symfs/path/to/vmlinux/dirvmlinux是内核开发者、安全研究员和系统调试者的基础分析工具提供了对内核内部结构的完整访问能力。虽然普通用户很少直接使用它但几乎所有内核级分析工具都依赖于它或它衍生的信息。