ELF文件结构是这样的:<?XML:NAMESPACE PREFIX = O />
+-------------------+
| ELF文件头 |
| |
+-------------------+
| 程序头 |
| (c0h字节) |
+-------------------+
| 程序节 #1 |
+-------------------+
| 程序节 #2 |
+-------------------+
. . . . . .
. . . . . .
. . . . . .
+-------------------+
| 程序节 #n |
+-------------------+
| 节表头 |
| (n*20h字节) |
+-------------------+
____________
_ _ __/ /__ _ _
_ _ __ ELF 文件头 __ _ _
/____________/
+==========================================================================+
| ELF 文件头 |
+=====+===========+=============+==========================================+
|偏移 | 长度 | 引用 | 描 述
+-----+-----------+-------------+-------------------------------------------
| 0 | 10h bytes | e_ident | ‘ELF’标识和其他值
| 10 | word | e_type | 文件类型
| 12 | word | e_machine | 运行这个文件的机器的类型
| 14 | dword | e_version | ELF文件头版本。通常为1
| 18 | dword | e_entry | 入口的虚拟地址
| <?XML:NAMESPACE PREFIX = ST1 /><chmetcnv w:st="on" tcsc="0" numbertype="1" negative="False" hasspace="False" sourcevalue="1" unitname="C">1c</chmetcnv> | dword | e_phoff | 程序头的偏移
| 20 | dword | e_shoff | 节表头的偏移
| 24 | dword | e_flags | 标识
| 28 | word | e_ehsize | ELF文件头长度
| <chmetcnv w:st="on" tcsc="0" numbertype="1" negative="False" hasspace="False" sourcevalue="2" unitname="a">2A</chmetcnv> | word | e_phentsize | 程序头重一个入口的长度
| <chmetcnv w:st="on" tcsc="0" numbertype="1" negative="False" hasspace="False" sourcevalue="2" unitname="C">2C</chmetcnv> | word | e_phnum | 程序头中入口的个数
| 2E | word | e_shentsize | 节表头中一个入口的长度
| 30 | word | e_shunum | 节表头中入口的个数
| 32 | word | e_shstrndx | 名称字符串节的入口个数
+-----+-----------+-------------+-------------------------------------------
elf_header给出了其他头的信息,包括如何执行程序文件以及其他信息(结构,...)
/ e_ident:‘ELF’标识(<chmetcnv w:st="on" tcsc="0" numbertype="1" negative="False" hasspace="False" sourcevalue="464" unitname="C"><span lang="EN-US" twffan="done">464c</span></chmetcnv><chmetcnv w:st="on" tcsc="0" numbertype="1" negative="False" hasspace="False" sourcevalue="457" unitname="F"><span lang="EN-US" twffan="done">457f</span></chmetcnv>)和其他一些值:
'-------
前10h字节的结构:
+-----+---------------+---------+------------------------------------------+
|偏移 | 名称 | 长度 | 描 述 |
+-----+---------------+---------+------------------------------------------+
| 0 | e_ident | dword | ELF标识 |
| 4 | EI_CLASS | byte | 文件类标识或者字长 |
| 5 | EI_DATA | byte | 数据编码 |
| 6 | EI_VERSION | byte | 文件版本 |
| 7 | EI_OSABI | byte | 操作系统/ABI表识 |
| 8 | EI_ABIVERSION | byte | ABI版本 |
| 9 | EI_PAD | 8 bytes | 未使用/保留 |
| <chmetcnv w:st="on" tcsc="0" numbertype="1" negative="False" hasspace="False" sourcevalue="0" unitname="F">0F</chmetcnv> | EI_NIDENT | byte | e_ident结构大小??? |
+-----+---------------+---------+------------------------------------------+
e_ident: ‘ELF’标识(<chmetcnv w:st="on" tcsc="0" numbertype="1" negative="False" hasspace="False" sourcevalue="464" unitname="C"><span lang="EN-US" twffan="done">464c</span></chmetcnv><chmetcnv w:st="on" tcsc="0" numbertype="1" negative="False" hasspace="False" sourcevalue="457" unitname="F"><span lang="EN-US" twffan="done">457f</span></chmetcnv>)
EI_CLASS: 文件类型,或字长定义了对象文件容器使用的数据结构所使用的基本
类型
ELFCLASSNONE 0 无效类型
ELFCLASS32 1 32位对象 <--- 32位结构
ELFCLASS64 2 64位对象 <--- 64位结构
EI_DATA: 指定对象文件容器使用的数据结构和对象文件节中包含的数据的编码
ELFDATANONE 0 无效数据编码
ELFDATA2LSB 1 制定了2的补数值,最小有意义的字节占最低地址
ELFDATA2MSB 2 制定了2的补数值,最大有意义的字节占最低地址
EI_VERSION: ELF文件头版本
EI_OSABI: 标识目标对象的操作系统和ABI
EI_ABIVERSION: 标识目标对象的ABI版本
EI_PAD: 未使用/保留
/ e_type: 决定文件的类型。
'------
值 含义
0 无此类型
1 可重定位文件
2 可执行文件
3 可共享目标文件
4 Core文件
fe00 操作系统指定
feff 操作系统指定
ff00 处理器指定
ffff 处理器指定
/ e_machine: 运行次文件的机器类型
'---------
值 含义
(十进制?)
0 No machine
1 AT&T WE 32100
2 SPARC
3 Intel 80386
4 Motorola 68000
5 Motorola 88000
7 Intel 80860
8 MIPS I Architecture
9 IBM System/370 Processor
10 MIPS RS3000 Little-endian
15 Hewlett-Packard PA-RISC
17 Fujitsu VPP500
18 Enhanced instruction set SPARC
19 Intel 80960
20 PowerPC
21 64-bit PowerPC
36 NEC V800
37 Fujitsu FR20
38 TRW RH-32
39 Motorola RCE
40 Advanced RISC Machines ARM
41 Digital Alpha
42 Hitachi SH
43 SPARC Version 9
44 Siemens Tricore embedded processor
45 Argonaut RISC Core, Argonaut Technologies Inc.
46 Hitachi H8/300
47 Hitachi H8/300H
48 Hitachi H8S
49 Hitachi H8/500
50 Itanium-based platform
51 Stanford MIPS-X
52 Motorola ColdFire
53 Motorola M68HC12
54 Fujitsu MMA Multimedia Accelerator
55 Siemens PCP
56 Sony nCPU embedded RISC processor
57 Denso NDR1 microprocessor
58 Motorola Star*Core processor
59 Toyota ME16 processor
60 STMicroelectronics ST100 processor
61 Advanced Logic Corp. TinyJ embedded processor family
66 Siemens FX66 microcontroller
67 STMicroelectronics ST9+ 8/16 bit microcontroller
68 STMicroelectronics ST7 8-bit microcontroller
69 Motorola MC68HC16 Microcontroller
70 Motorola MC68HC11 Microcontroller
71 Motorola MC68HC08 Microcontroller
72 Motorola MC68HC05 Microcontroller
73 Silicon Graphics SVx
74 STMicroelectronics ST19 8-bit microcontroller
75 Digital VAX
76 Axis Communications 32-bit embedded processor
77 Infineon Technologies 32-bit embedded processor
78 Element 14 64-bit DSP Processor
79 LSI Logic 16-bit DSP Processor
80 Donald Knuth's educational 64-bit processor
81 Harvard University machine-independent object files
82 SiTera Prism
(译注:我想上面这个表不需要翻译了吧 :P)
/ e_version: ELF文件头版本。
'-------
值 含义
0 无效版本
1 当前版本
/ e_entry: 入口的虚拟地址,是程序入口处(代码的开始)的偏移。
'-------
/ e_phoff: 程序头的偏移,如果程序没有程序头表,e_phoff为0。
'-------
/ e_shoff: 节表头的偏移。如果程序没有节表,e_shoff为0。
'-------
/ e_flags: 与文件相关的处理器标志。
'-------
/ e_ehsize: ELF文件头的字节数
'--------
/ e_phentsize: 程序头表中一个入口的大小,所有入口大小相同。
'-----------
/ e_phnum: 程序头表中入口的个数,如果程序没有程序头表,e_phnum为0。
'-------
/ e_shentsize: 节表中一个入口的大小,所有入口大小相同。
'-----------
/ e_shunum: 节表中入口的个数,如果程序没有节表,e_shnum为0。
'--------
/ e_shstrndx: 这个字段保存着跟节名字相关的节的入口索引, 如果这个文件没有节
'---------- 名表,这个字段的值为SHN_UNDEF。
________________
_ _ __/ /__ _ _
_ _ __ 程序头 __ _ _
/________________/
程序头是一个用来为系统描述如何为程序的执行做准备的结构。
文件通过ELF文件头中的‘e_phentsize’和‘e_phnum’字段指定自己程序头的大小。
注意ELF头中的EI_CLASS,它有32位和64位的模式:
+============================================================================+
| 程序头表(32位) |
+=======+=========+==========+===============================================+
| 偏移 | 长度 | 名称 | 含义 |
+-------+---------+----------+-----------------------------------------------+
| 00 | dword | p_type | 段类型 |
| 04 | dword | p_offset | 段开始处的物理偏移(译注:在磁盘文件上的偏移)|
| 08 | dword | p_vaddr | 内存中的虚拟地址 |
| <chmetcnv w:st="on" tcsc="0" numbertype="1" negative="False" hasspace="False" sourcevalue="0" unitname="C">0c</chmetcnv> | dword | p_paddr | 物理地址 |
| 10 | dword | p_filesz | 从偏移处读取的数据长度 |
| 14 | dword | p_memsz | 内存中段的长度 |
| 18 | dword | p_flags | 段标志(读、写、可执行标志) |
| <chmetcnv w:st="on" tcsc="0" numbertype="1" negative="False" hasspace="False" sourcevalue="1" unitname="C">1c</chmetcnv> | dword | p_align | 对齐粒度 |
+-------+---------+----------+-----------------------------------------------+
+====================================================================+
| 程序头表(64位) |
+=========+==========+===============================================+
| 长度 | 名称 | 含义 |
+=========+==========+===============================================+
| dword | p_type | 段类型 |
| dword | p_flags | 段标志(读、写、可执行标志) |
| 8 bytes | p_offset | 段开始处的物理偏移(译注:在磁盘文件上的偏移 |
| 8 bytes | p_vaddr | 内存中的虚拟地址 |
| 8 bytes | p_paddr | 物理地址 |
| 8 bytes | p_filesz | 从偏移处读取的数据长度 |
| 8 bytes | p_memsz | 内存中段的长度 |
| 8 bytes | p_align | 对齐粒度 |
+---------+----------+-----------------------------------------------+
/ p_type: 段类型
'------
PT_NULL 0 未使用
PT_LOAD 1 见下
PT_DYNAMIC 2 动态链接信息
PT_INTERP 3 见下
PT_NOTE 4 辅助信息的位置和长度
PT_SHLIB 5 保留
PT_PHDR 6 见下
PT_LOOS 60000000 操作系统保留
PT_HIOS 6fffffff 操作系统保留
PT_LOPROC 70000000 处理器保留
PT_HIPROC 7fffffff 处理器保留
PT_LOAD: 可加载段,由p_filesz和p_memsz描述。文件中的内容被映射到内存段
的起始处。如果段的内存长度(p_memsz)大于文件长度,那么‘其余’
的内容被置为0并跟在段的初始化区域之后。文件长度不可能大于内存
中文件长度。可加载段在程序的入口根据p_vadder的值按升序排列。
PT_INTERP: 以解释的方式被调用的null结尾的路径名的位置和长度。这个段只对
可执行文件有效。
PT_PHDR: 如果存在,则同时指定文件头表的在文件和内存中的位置和长度。只
有程序头表程序在内存中映像的一部分时发生。如果不存在,它必须
在任何一个可加载段之前。
/ p_offset: 文件中段内第一个字节的虚拟地址
'--------
/ p_vaddr: 内存中段内第一个字节的虚拟地址
'-------
/ p_addr: 物理地址(如果相关,否则等于p_vaddr)
'------
/ p_filesz: 段在文件中的字节数;可能为0
'--------
/ p_memsz: 段在内存中的字节数;可能为0
'-------
/ p_flags: 许可标志:
'-------
名称 值 含义
PF_X 1 可执行
PF_W 2 可写
PF_R 4 可读
PF_MASKOS 0ff00000 未指定
PF_MASKPROC f0000000 未指定
/ p_align: 对齐粒度
'------- 0和1表示不需要对齐, 否则,p_align应该是一个为2的幂的正整数,
并且p_vaddr应该等于p_offset,模p_align。
________________
_ _ __/ /__ _ _
_ _ __ 节头 __ _ _
/________________/
ELF文件中的所有节都可以通过节表找到。节头和程序头相似。每一个入口关联文件中的
一个节。也许我在这里的描述会有错误 --> 节头是可选的。
+---------------------------------------------------------------------------+
| 节头(32位模式) |
+-----+--------------+-------+----------------------------------------------+
|偏移 | 名称 | 长度 | 描 述 |
+-----+--------------+-------+----------------------------------------------+
| 00 | sh_name | dword | 指向节的ascii名称 |
| 04 | sh_type | dword | 节类型 |
| 08 | sh_flags | dword | 标志 |
| <chmetcnv w:st="on" tcsc="0" numbertype="1" negative="False" hasspace="False" sourcevalue="0" unitname="C">0c</chmetcnv> | sh_addr | dword | 虚拟地址 |
| 10 | sh_offset | dword | 物理偏移 |
| 14 | sh_size | dword | 尺寸 |
| 18 | sh_link | dword | 其值依赖于节类型 |
| <chmetcnv w:st="on" tcsc="0" numbertype="1" negative="False" hasspace="False" sourcevalue="1" unitname="C">1c</chmetcnv> | sh_info | dword | 其值依赖于节类型 |
| 20 | sh_addralign | dword | 对齐 |
| 24 | sh_entsize | dword | 当节中包含固定长度入口时使用 |
+-----+--------------+-------+----------------------------------------------+
+-----------------------------------------------------------------------------+
| 节头(32位模式) |
+-----+--------------+---------+----------------------------------------------+
|偏移 | 名称 | 长度 | 描 述 |
+-----+--------------+---------+----------------------------------------------+
| 00 | sh_name | dword | 指向节的ascii名称 |
| 04 | sh_type | dword | 节类型 |
| 08 | sh_flags | dword | 标志 |
| <chmetcnv w:st="on" tcsc="0" numbertype="1" negative="False" hasspace="False" sourcevalue="0" unitname="C">0c</chmetcnv> | sh_addr | 8 bytes | 虚拟地址 |
| 14 | sh_offset | 8 bytes | 物理偏移 |
| <chmetcnv w:st="on" tcsc="0" numbertype="1" negative="False" hasspace="False" sourcevalue="1" unitname="C">1c</chmetcnv> | sh_size | dword | 尺寸 |
| 20 | sh_link | dword | 其值依赖于节类型 |
| 24 | sh_info | dword | 其值依赖于节类型 |
| 28 | sh_addralign | dword | 对齐 |
| <chmetcnv w:st="on" tcsc="0" numbertype="1" negative="False" hasspace="False" sourcevalue="3" unitname="C">3c</chmetcnv> | sh_entsize | dword | 当节中包含固定长度入口时使用 |
+-----+--------------+---------+----------------------------------------------+
/ sh_name: 节的名称。它的值为一个在节名称表中的索引。
'-------
/ sh_type: 节的类型
'-------
名称 值 描述
SHT_NULL 0 标志节头为非活动的。
SHT_PROGBITS 1 这个节包含程序定义的信息
SHT_SYMTAB 2 这个节包含符号表,为链接提供
SHT_STRTAB 3 这个节包含字符串表
SHT_RELA 4 这个节包含字符串表(译注:应为:这个节包含具有明
确加数的重定位入口)
SHT_HASH 5 这个节包含符号哈希表
SHT_DYNAMIC 6 这个节包含动态链接信息
SHT_NOTE 7 这个节包含以某种方式标志这个文件的信息
SHT_NOBITS 8 这个节不占用空间
SHT_REL 9 这个节不包含具有明确加数的重定位入口
SHT_SHLIB a 保留
SHT_DYNSYM b 包含动态链接符号的最小集合
SHT_INIT_ARRAY e 包含指向初始化例程的指针数组
SHT_FINI_ARRAY f 包含指向结束例程的指针数组
SHT_PREINIT_ARRAY 10 包含指向在其他初始化例程前被调用的例程的指针数组
SHT_LOOS 60000000 操作系统保留
SHT_HIOS 6fffffff 操作系统保留
SHT_LOPROC 70000000 处理器保留
SHT_HIPROC 7fffffff 处理器保留
SHT_LOUSER 80000000 应用程序保留的索引下界
SHT_HIUSER ffffffff 应用程序保留的索引上界
/ sh_flags: 用来描述复合属性的1位标志
'--------
/ sh_addr: 如果这个节被映射到进程的内存空间中,这个字段指定了这个节的第
'------- 一个字节的地址。否则,这个字段为0。
/ sh_offset: 从文件开头到节的第一个字节的偏移
'---------
/ sh_size: 节的字节数
'-------
/ sh_link: 这个字段包含一个节头表索引链接,这个链接的含义依节类型而定。
'-------
/ sh_info: 这个字段包含了其他一些信息,它的解释依节类型而定。
'-------
/ sh_addralign:有些节强制地址对齐。比如,如果一个节包含一个双字, 系统必须保
'------------ 证整个节是按双字对齐的。这个值必须是与0适应的,模sh_addralign
的值。
/ sh_entsize: 一些节包含一个固定长度入口的表,比如符号表。 对于这样一个节,
'---------- 这个字段指定了每个入口的字节数。
就像我所说的,我不会列举一大堆的标志描述,那是在浪费你的硬盘空间。 你可以在一
份 -好的- ELF文档中找得到(4.3中的urlz)。
这些都是文档。这是在Linux的世界中。让我们来看一写代码吧!!!
_____________________________________________________________________________
___________________
_ _ __/ /__ _ _
_ _ __ 注释了的例子 __ _ _
/___________________/
我们来看一看这份教程的最后一部分,你可以从中找到:
‘注释了的例子’的代码
‘注释了的例子’的代码的十六进制表示
我将用这些来揭开ELF文件的神秘面纱。
让我们来看一下我们的hello程序的十六进制表示:
+----------+-------------------------------------------------+------------------+
| 偏移 | 00 01 02 03 04 05 06 07 08 09 <chmetcnv w:st="on" tcsc="0" numbertype="1" negative="False" hasspace="False" sourcevalue="0" unitname="a">0a</chmetcnv> 0b <chmetcnv w:st="on" tcsc="0" numbertype="1" negative="False" hasspace="False" sourcevalue="0" unitname="C">0c</chmetcnv> 0d 0e <chmetcnv w:st="on" tcsc="0" numbertype="1" negative="False" hasspace="False" sourcevalue="0" unitname="F">0f</chmetcnv> | ascci表示 |
+----------+-------------------------------------------------+------------------+
|0000:0000 | <chmetcnv w:st="on" tcsc="0" numbertype="1" negative="False" hasspace="False" sourcevalue="7" unitname="F">7f</chmetcnv> 45 <chmetcnv w:st="on" tcsc="0" numbertype="1" negative="False" hasspace="False" sourcevalue="4" unitname="C">4c</chmetcnv> 46 01 01 01 00 00 00 00 00 00 00 00 00 | .ELF............ |
|0000:0010 | 02 00 03 00 01 00 00 00 80 80 04 08 34 00 00 00 | ............4... |
|0000:0020 | 10 01 00 00 00 00 00 00 34 00 20 00 02 00 28 00 | ........4. ...(. |
|0000:0030 | 08 00 05 00 | ...... |
+----------+-------------------------------------------------+------------------+
这是ELF文件头,所有的ELF文件都从这样一个文件头开始:
at offset 00h : ‘ELF’标识 :<chmetcnv w:st="on" tcsc="0" numbertype="1" negative="False" hasspace="False" sourcevalue="464" unitname="C"><span lang="EN-US" twffan="done">464c</span></chmetcnv><chmetcnv w:st="on" tcsc="0" numbertype="1" negative="False" hasspace="False" sourcevalue="457" unitname="F"><span lang="EN-US" twffan="done">457f</span></chmetcnv>
at offset 04h : 数据结构类型 :01h ---> 32位结构
at offset 10h : 文件类型 :0002h ---> 可执行文件
at offset 12h : 机器标志, 0003h :Intel 80386
at offset 14h : ELF文件头版本 :00000001h
. . 18h : 入口虚拟地址 :08048080h
. . 1ch : 程序头偏移 :00000034h
. . 20h : 节头偏移 :00000110h
. . 28h : ELF文件头长度 :34h字节
. . 2ah : 程序头表中一个入口的长度 :0020h
. . 2ch : 程序头中入口的个数 :0002h
. . 2eh : 节表头中一个入口的长度 :0028h
. . 30h : 节表头中入口的个数 :0008h
. . 32h : 名称字符串节的入口个数 :0005h
注意:程序头表中的入口是对ELF文件一个节的描述(程序头结构)。
我们在ELF文件头中可以看到程序头的偏移:00000034h,所以我们从偏移34h出开
始!!!
(EI_CLASS指定了这是一个32位的结构!)
+----------+-------------------------------------------------+------------------+
| 偏移 | 00 01 02 03 04 05 06 07 08 09 <chmetcnv w:st="on" tcsc="0" numbertype="1" negative="False" hasspace="False" sourcevalue="0" unitname="a">0a</chmetcnv> 0b <chmetcnv w:st="on" tcsc="0" numbertype="1" negative="False" hasspace="False" sourcevalue="0" unitname="C">0c</chmetcnv> 0d 0e <chmetcnv w:st="on" tcsc="0" numbertype="1" negative="False" hasspace="False" sourcevalue="0" unitname="F">0f</chmetcnv> | ascci表示 |
+----------+-------------------------------------------------+------------------+
|0000:0030 | 01 00 00 00 00 00 00 00 00 80 04 08 | ............ |
|0000:0040 | 00 80 04 <chmetcnv w:st="on" tcsc="0" numbertype="1" negative="False" hasspace="True" sourcevalue="8" unitname="a">08 a</chmetcnv>2 00 00 <chmetcnv w:st="on" tcsc="0" numbertype="1" negative="False" hasspace="True" sourcevalue="0" unitname="a">00 a</chmetcnv>2 00 00 00 05 00 00 00 | ....?..?...... |
|0000:0050 | 00 10 00 00 01 00 00 <chmetcnv w:st="on" tcsc="0" numbertype="1" negative="False" hasspace="True" sourcevalue="0" unitname="a">00 a</chmetcnv>4 00 00 <chmetcnv w:st="on" tcsc="0" numbertype="1" negative="False" hasspace="True" sourcevalue="0" unitname="a">00 a</chmetcnv>4 90 04 08 | ........?...?... |
|0000:0060 | a4 90 04 08 18 00 00 00 18 00 00 00 06 00 00 00 | ?............... |
|0000:0070 | 00 10 00 00 | .... |
+----------+-------------------------------------------------+------------------+
ELF文件头中的e_phnum指定了程序头中入口(节)的个数:这里有2个节...
节 #1 :
at offset 34h : 段类型 : 00000001h ----> 可加载段
at offset 38h : 物理偏移 : 00000000h
. . 3ch : 虚拟地址 : 08048000h
. . 40h : 物理地址 : 08048000h
. . 44h : 物理长度 : <chmetcnv w:st="on" tcsc="0" numbertype="1" negative="False" hasspace="False" sourcevalue="0" unitname="a">000000a</chmetcnv>2h
. . 48h : 虚拟长度 : 00000002h
. . 4ch : 标志 : 00000005h (可读/可执行)
. . 50h : 对齐 : 00001000h
节 #2 :
at offset 54h : 段类型 : 00000001h ----> loadable segment
at offset 58h : 物理偏移 : <chmetcnv w:st="on" tcsc="0" numbertype="1" negative="False" hasspace="False" sourcevalue="0" unitname="a">000000a</chmetcnv>4h
. . 5ch : 虚拟地址 : <chmetcnv w:st="on" tcsc="0" numbertype="1" negative="False" hasspace="False" sourcevalue="80490" unitname="a"><span lang="EN-US" twffan="done">080490a</span></chmetcnv>4h
. . 60h : 物理地址 : <chmetcnv w:st="on" tcsc="0" numbertype="1" negative="False" hasspace="False" sourcevalue="80490" unitname="a">080490a</chmetcnv>4h
. . 64h : 物理长度 : 00000018h
. . 68h : 虚拟长度 : 00000018h
. . 6ch : 标志 : 00000006h (可读/可写/可执行)
. . 70h : 对齐 : 00001000h
这里是节表:有8个入口。这些‘节表’结构提供了关于‘程序头’中描述的节和文件中
的其他节的信息。
+----------+-------------------------------------------------+------------------+
| 偏移 | 00 01 02 03 04 05 06 07 08 09 <chmetcnv w:st="on" tcsc="0" numbertype="1" negative="False" hasspace="False" sourcevalue="0" unitname="a">0a</chmetcnv> 0b <chmetcnv w:st="on" tcsc="0" numbertype="1" negative="False" hasspace="False" sourcevalue="0" unitname="C">0c</chmetcnv> 0d 0e <chmetcnv w:st="on" tcsc="0" numbertype="1" negative="False" hasspace="False" sourcevalue="0" unitname="F">0f</chmetcnv> | ascci表示 |
+----------+-------------------------------------------------+------------------+
|0000:0110 | 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 | ................ |
|0000:0120 | 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 | ................ |
|0000:0130 | 00 00 00 00 00 00 00 00 1b 00 00 00 01 00 00 00 | ................ |
|0000:0140 | 06 00 00 00 80 80 04 08 80 00 00 00 22 00 00 00 | ............"... |
|0000:0150 | 00 00 00 00 00 00 00 00 10 00 00 00 00 00 00 00 | ................ |
|0000:0160 | 21 00 00 00 01 00 00 00 03 00 00 <chmetcnv w:st="on" tcsc="0" numbertype="1" negative="False" hasspace="True" sourcevalue="0" unitname="a">00 a</chmetcnv>4 90 04 08 | !...........?... |
|0000:0170 | a4 00 00 00 18 00 00 00 00 00 00 00 00 00 00 00 | ?............... |
|0000:0180 | 04 00 00 00 00 00 00 00 27 00 00 00 08 00 00 00 | ........'....... |
|0000:0190 | 03 00 00 00 bc 90 04 08 bc 00 00 00 00 00 00 00 | ....?...?....... |
|0000:<chmetcnv w:st="on" tcsc="0" numbertype="1" negative="False" hasspace="False" sourcevalue="1" unitname="a">01a</chmetcnv>0 | 00 00 00 00 00 00 00 00 04 00 00 00 00 00 00 00 | ................ |
|0000:01b0 | <chmetcnv w:st="on" tcsc="0" numbertype="1" negative="False" hasspace="False" sourcevalue="2" unitname="C">2c</chmetcnv> 00 00 00 01 00 00 00 00 00 00 00 00 00 00 00 | ,............... |
|0000:<chmetcnv w:st="on" tcsc="0" numbertype="1" negative="False" hasspace="False" sourcevalue="1" unitname="C">01c</chmetcnv>0 | bc 00 00 00 <chmetcnv w:st="on" tcsc="0" numbertype="1" negative="False" hasspace="False" sourcevalue="1" unitname="F">1f</chmetcnv> 00 00 00 00 00 00 00 00 00 00 00 | ?............... |
|0000:01d0 | 01 00 00 00 00 00 00 00 11 00 00 00 03 00 00 00 | ................ |
|0000:01e0 | 00 00 00 00 00 00 00 00 db 00 00 00 35 00 00 00 | ........?..5... |
|0000:<chmetcnv w:st="on" tcsc="0" numbertype="1" negative="False" hasspace="False" sourcevalue="1" unitname="F">01f</chmetcnv>0 | 00 00 00 00 00 00 00 00 01 00 00 00 00 00 00 00 | ................ |
|0000:0200 | 01 00 00 00 02 00 00 00 00 00 00 00 00 00 00 00 | ................ |
|0000:0210 | 50 02 00 <chmetcnv w:st="on" tcsc="0" numbertype="1" negative="False" hasspace="True" sourcevalue="0" unitname="F">00 f</chmetcnv>0 00 00 00 07 00 00 00 0b 00 00 00 | P...?.......... |
|0000:0220 | 04 00 00 00 10 00 00 00 09 00 00 00 03 00 00 00 | ................ |
|0000:0230 | 00 00 00 00 00 00 00 00 40 03 00 00 39 00 00 00 | ........@...9... |
|0000:0240 | 00 00 00 00 00 00 00 00 01 00 00 00 00 00 00 00 | ................ |
+----------+-------------------------------------------------+------------------+
从偏移 110h 到 137h : 节表中的入口 #1
从偏移 138h 到 15fh : 节表中的入口 #2
从偏移 160h 到 187h : 节表中的入口 #3
从偏移 188h 到 1afh : 节表中的入口 #4
从偏移 1b0h 到 1d7h : 节表中的入口 #5
从偏移 1d8h 到 1ffh : 节表中的入口 #6
从偏移 200h 到 227h : 节表中的入口 #7
从偏移 228h 到 24fh : 节表中的入口 #8
sh_name关联字符串表的起始,可以通过它找到节的ascii名称。字符串表在偏移340h处
(见入口 #8的描述)
入口 #1:
---------
sh_name : 00h : 指向节名称
sh_type : 00h :非活动节头
sh_addr : 00h :虚拟地址
sh_offset : 00h : 物理地址
sh_size : 00h :长度
入口 #2:
---------
sh_name : 1bh : 指向节名称
sh_type : 01h :包含程序定义的信息
sh_addr : 08048080h : 虚拟地址
sh_offset : 80h : 物理地址
sh_size : 22h :长度
入口 #3:
---------
sh_name : 21h : 指向节名称
sh_type : 01h :包含程序定义的信息
sh_addr : <chmetcnv w:st="on" tcsc="0" numbertype="1" negative="False" hasspace="False" sourcevalue="80490" unitname="a">080490a</chmetcnv>4h : 虚拟地址
sh_offset : a4h : 物理地址
sh_size : 18h :长度
入口 #4:
---------
sh_name : 27h : 指向节名称
sh_type : 08h :不占用空间
sh_addr : 080490bch : 虚拟地址
sh_offset : bch : 物理地址
sh_size : 00h :长度
入口 #5:
---------
sh_name : 2ch : 指向节名称
sh_type : 01h :包含程序定义的信息
sh_addr : 00h :虚拟地址
sh_offset : bch : 物理地址
sh_size : 1fh :长度
入口 #6:
---------
sh_name : 11h : 指向节名称
sh_type : 03h :包含程序定义的信息
sh_addr : 00h :虚拟地址
sh_offset : dbh : 物理地址
sh_size : 35h :长度
入口 #7:
---------
sh_name : 01h : 指向节名称
sh_type : 02h :这个节包含符号表,为链接提供
sh_addr : 00h :虚拟地址
sh_offset : 250h : 物理地址
sh_size : f0h :长度
入口 #8:
---------
sh_name : 09h : 指向节名称
sh_type : 03h :包含字符串表
sh_addr : 00h :虚拟地址
sh_offset : 340h : 物理地址
sh_size : 39h :长度
______________________________
_ _ __/ /__ _ _
_ _ __ ‘注释了的例子’的代码 __ _ _
/______________________________/
;----------------------------------------------------.
; 这样编译这个文件: ; ;
; ; ;
; nasm -f elf hello.asm ; ;
; ld -o hello hello.o ; ;
;- - - - - - - - - - - - - ;
;
BITS32 ;
section .text ; 代码节 ;
global _start ; <---. ;
_start: ; <----/__为nasm ;
mov eax,4 ; ‘写’系统调用 ;
mov ebx,1 ; 屏幕的文件描述符 ;
mov ecx,message ; 写缓冲的偏移 ;
mov edx,23 ; 要写的字节数 ;
int 80h ; 80h中断 ;
;
mov eax,1 ; ‘结束’系统调用 ;
mov ebx,0 ; 结束码 ;
int 80h ; 80h中断 ;
;
section .data ; 数据节 ;
;
message db "hello LINUX world !!!",13,10,0 ;
;----------------------------------------------------'
______________________________________________
_ _ __/ /__ _ _
_ _ __ ‘注释了的例子’的代码的十六进制表示 __ _ _
/______________________________________________/
+----------+-------------------------------------------------+------------------+
| 偏移 | 00 01 02 03 04 05 06 07 08 09 <chmetcnv w:st="on" tcsc="0" numbertype="1" negative="False" hasspace="False" sourcevalue="0" unitname="a">0a</chmetcnv> 0b <chmetcnv w:st="on" tcsc="0" numbertype="1" negative="False" hasspace="False" sourcevalue="0" unitname="C">0c</chmetcnv> 0d 0e <chmetcnv w:st="on" tcsc="0" numbertype="1" negative="False" hasspace="False" sourcevalue="0" unitname="F">0f</chmetcnv> | ascci表示 |
+----------+-------------------------------------------------+------------------+
|0000:0000 | <chmetcnv w:st="on" tcsc="0" numbertype="1" negative="False" hasspace="False" sourcevalue="7" unitname="F">7f</chmetcnv> 45 <chmetcnv w:st="on" tcsc="0" numbertype="1" negative="False" hasspace="False" sourcevalue="4" unitname="C">4c</chmetcnv> 46 01 01 01 00 00 00 00 00 00 00 00 00 | .ELF............ | <-. <--------+
|0000:0010 | 02 00 03 00 01 00 00 00 80 80 04 08 34 00 00 00 | ............4... | /_ ELF文件 |
|0000:0020 | 10 01 00 00 00 00 00 00 34 00 20 00 02 00 28 00 | ........4. ...(. | / 头 |
|0000:0030 | 08 00 05 00 01 00 00 00 00 00 00 00 00 80 04 08 | ................ | <-< (3ch) |
|0000:0040 | 00 80 04 <chmetcnv w:st="on" tcsc="0" numbertype="1" negative="False" hasspace="True" sourcevalue="8" unitname="a">08 a</chmetcnv>2 00 00 <chmetcnv w:st="on" tcsc="0" numbertype="1" negative="False" hasspace="True" sourcevalue="0" unitname="a">00 a</chmetcnv>2 00 00 00 05 00 00 00 | ....?..?...... | / |
|0000:0050 | 00 10 00 00 01 00 00 <chmetcnv w:st="on" tcsc="0" numbertype="1" negative="False" hasspace="True" sourcevalue="0" unitname="a">00 a</chmetcnv>4 00 00 <chmetcnv w:st="on" tcsc="0" numbertype="1" negative="False" hasspace="True" sourcevalue="0" unitname="a">00 a</chmetcnv>4 90 04 08 | ........?...?... | > 程序头 +- 节 #1
|0000:0060 | a4 90 04 08 18 00 00 00 18 00 00 00 06 00 00 00 | ?............... | / (73h)|
|0000:0070 | 00 10 00 00 00 00 00 00 00 00 00 00 00 00 00 00 | ................ | <-' |
|0000:0080 | b8 04 00 00 00 bb 01 00 00 00 b<chmetcnv w:st="on" tcsc="0" numbertype="1" negative="False" hasspace="True" sourcevalue="9" unitname="a">9 a</chmetcnv>4 90 04 08 ba | ?....?...?...?| |
|0000:0090 | 17 00 00 00 cd 80 b8 01 00 00 00 bb 00 00 00 00 | ....??....?... | |
|0000:<chmetcnv w:st="on" tcsc="0" numbertype="1" negative="False" hasspace="False" sourcevalue="0" unitname="a">00a</chmetcnv>0 | cd 80 00 00 68 65 <chmetcnv w:st="on" tcsc="0" numbertype="1" negative="False" hasspace="False" sourcevalue="6" unitname="C">6c</chmetcnv><chmetcnv w:st="on" tcsc="0" numbertype="1" negative="False" hasspace="False" sourcevalue="6" unitname="C">6c</chmetcnv><chmetcnv w:st="on" tcsc="0" numbertype="1" negative="False" hasspace="False" sourcevalue="6" unitname="F">6f</chmetcnv> 20 <chmetcnv w:st="on" tcsc="0" numbertype="1" negative="False" hasspace="False" sourcevalue="4" unitname="C">4c</chmetcnv> 49 4e 55 58 20 | ?..hello LINUX | <-------------+_ 节 # 2
|0000:00b0 | 77 <chmetcnv w:st="on" tcsc="0" numbertype="1" negative="False" hasspace="False" sourcevalue="6" unitname="F">6f</chmetcnv> 72 <chmetcnv w:st="on" tcsc="0" numbertype="1" negative="False" hasspace="False" sourcevalue="6" unitname="C">6c</chmetcnv> 64 20 21 21 21 0d <chmetcnv w:st="on" tcsc="0" numbertype="1" negative="False" hasspace="False" sourcevalue="0" unitname="a">0a</chmetcnv> 00 00 54 68 65 | world !!!....The | <-------------'
|0000:<chmetcnv w:st="on" tcsc="0" numbertype="1" negative="False" hasspace="False" sourcevalue="0" unitname="C">00c</chmetcnv>0 | 20 4e 65 74 77 69 64 65 20 41 73 73 65 6d 62 <chmetcnv w:st="on" tcsc="0" numbertype="1" negative="False" hasspace="False" sourcevalue="6" unitname="C">6c</chmetcnv> | Netwide Assembl |
|0000:00d0 | 65 72 20 30 2e 39 38 2e 32 32 00 00 2e 73 79 6d | er 0.98.22...sym |
|0000:00e0 | 74 61 62 00 2e 73 74 72 74 61 62 00 2e 73 68 73 | tab..strtab..shs |
|0000:<chmetcnv w:st="on" tcsc="0" numbertype="1" negative="False" hasspace="False" sourcevalue="0" unitname="F">00f</chmetcnv>0 | 74 72 74 61 62 00 2e 74 65 78 74 00 2e 64 61 74 | trtab..text..dat |
|0000:0100 | 61 00 2e 62 73 73 00 2e 63 <chmetcnv w:st="on" tcsc="0" numbertype="1" negative="False" hasspace="False" sourcevalue="6" unitname="F">6f</chmetcnv> 6d 6d 65 6e 74 00 | a..bss..comment. |
|0000:0110 | 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 | ................ | <--.
|0000:0120 | 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 | ................ | |
|0000:0130 | 00 00 00 00 00 00 00 00 1b 00 00 00 01 00 00 00 | ................ | |
|0000:0140 | 06 00 00 00 80 80 04 08 80 00 00 00 22 00 00 00 | ............"... | |
|0000:0150 | 00 00 00 00 00 00 00 00 10 00 00 00 00 00 00 00 | ................ | |
|0000:0160 | 21 00 00 00 01 00 00 00 03 00 00 <chmetcnv w:st="on" tcsc="0" numbertype="1" negative="False" hasspace="True" sourcevalue="0" unitname="a">00 a</chmetcnv>4 90 04 08 | !...........?... | |
|0000:0170 | a4 00 00 00 18 00 00 00 00 00 00 00 00 00 00 00 | ?............... | |
|0000:0180 | 04 00 00 00 00 00 00 00 27 00 00 00 08 00 00 00 | ........'....... | |
|0000:0190 | 03 00 00 00 bc 90 04 08 bc 00 00 00 00 00 00 00 | ....?...?....... | |
|0000:<chmetcnv w:st="on" tcsc="0" numbertype="1" negative="False" hasspace="False" sourcevalue="1" unitname="a">01a</chmetcnv>0 | 00 00 00 00 00 00 00 00 04 00 00 00 00 00 00 00 | ................ | | 节表
|0000:01b0 | <chmetcnv w:st="on" tcsc="0" numbertype="1" negative="False" hasspace="False" sourcevalue="2" unitname="C">2c</chmetcnv> 00 00 00 01 00 00 00 00 00 00 00 00 00 00 00 | ,............... | |
|0000:<chmetcnv w:st="on" tcsc="0" numbertype="1" negative="False" hasspace="False" sourcevalue="1" unitname="C">01c</chmetcnv>0 | bc 00 00 00 <chmetcnv w:st="on" tcsc="0" numbertype="1" negative="False" hasspace="False" sourcevalue="1" unitname="F">1f</chmetcnv> 00 00 00 00 00 00 00 00 00 00 00 | ?............... | |
|0000:01d0 | 01 00 00 00 00 00 00 00 11 00 00 00 03 00 00 00 | ................ | |
|0000:01e0 | 00 00 00 00 00 00 00 00 db 00 00 00 35 00 00 00 | ........?..5... | |
|0000:<chmetcnv w:st="on" tcsc="0" numbertype="1" negative="False" hasspace="False" sourcevalue="1" unitname="F">01f</chmetcnv>0 | 00 00 00 00 00 00 00 00 01 00 00 00 00 00 00 00 | ................ | |
|0000:0200 | 01 00 00 00 02 00 00 00 00 00 00 00 00 00 00 00 | ................ | |
|0000:0210 | 50 02 00 <chmetcnv w:st="on" tcsc="0" numbertype="1" negative="False" hasspace="True" sourcevalue="0" unitname="F">00 f</chmetcnv>0 00 00 00 07 00 00 00 0b 00 00 00 | P...?.......... | |
|0000:0220 | 04 00 00 00 10 00 00 00 09 00 00 00 03 00 00 00 | ................ | |
|0000:0230 | 00 00 00 00 00 00 00 00 40 03 00 00 39 00 00 00 | ........@...9... | |
|0000:0240 | 00 00 00 00 00 00 00 00 01 00 00 00 00 00 00 00 | ................ | <--'
|0000:0250 | 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 | ................ | <--.
|0000:0260 | 00 00 00 00 80 80 04 08 00 00 00 00 03 00 01 00 | ................ | |
|0000:0270 | 00 00 00 <chmetcnv w:st="on" tcsc="0" numbertype="1" negative="False" hasspace="True" sourcevalue="0" unitname="a">00 a</chmetcnv>4 90 04 08 00 00 00 00 03 00 02 00 | ....?........... | |
|0000:0280 | 00 00 00 00 bc 90 04 08 00 00 00 00 03 00 03 00 | ....?........... | |
|0000:0290 | 00 00 00 00 00 00 00 00 00 00 00 00 03 00 04 00 | ................ | |
|0000:<chmetcnv w:st="on" tcsc="0" numbertype="1" negative="False" hasspace="False" sourcevalue="2" unitname="a">02a</chmetcnv>0 | 00 00 00 00 00 00 00 00 00 00 00 00 03 00 05 00 | ................ | |
|0000:02b0 | 00 00 00 00 00 00 00 00 00 00 00 00 03 00 06 00 | ................ | |_ 符号表
|0000:<chmetcnv w:st="on" tcsc="0" numbertype="1" negative="False" hasspace="False" sourcevalue="2" unitname="C">02c</chmetcnv>0 | 00 00 00 00 00 00 00 00 00 00 00 00 03 00 07 00 | ................ | |
|0000:02d0 | 01 00 00 00 00 00 00 00 00 00 00 00 04 <chmetcnv w:st="on" tcsc="0" numbertype="1" negative="False" hasspace="True" sourcevalue="0" unitname="F">00 f</chmetcnv>1 ff | ..............