ELF 全稱 “Executable and Linkable Format”,即可執行可連結檔案格式,目前常見的Linux、 Android可執行檔案、共享庫(.so)、目標檔案( .o)以及Core 檔案(吐核)均為此格式。

檔案佈局

常見的ELF檔案大致結構如下:

ELF 格式詳解(一)

常見的ELF格式如上圖所示,左邊為連結檢視,右邊為執行檢視。

連結檢視:

靜態連結器(即編譯後參與生成最終ELF過程的連結器,如ld )會以連結檢視解析ELF。編譯時生成的 。o(目標檔案)以及連結後的 。so (共享庫)均可透過連結檢視解析,連結檢視可以沒有段表(如目標檔案不會有段表)。

執行檢視:

動態連結器(即載入器,如x86架構 linux下的 /lib/ld-linux。so。2或者安卓系統下的 /system/linker均為動態連結器)會以執行檢視解析ELF並動態連結,執行檢視可以沒有節表。

檔案頭

ELF的結構宣告位於系統標頭檔案 elf。h 中,ELF格式分為32位與64位兩種,除了重定位型別稍有區別,其它大致相同,為了簡化描述,後續說明將省略32/64字樣。

ELF Header的宣告如下 :

#define EI_NIDENT (16)

typedef struct

{

unsigned char e_ident[EI_NIDENT]; /* Magic number and other info */

Elf_Half e_type; /* Object file type */

Elf_Half e_machine; /* Architecture */

Elf_Word e_version; /* Object file version */

Elf_Addr e_entry; /* Entry point virtual address */

Elf_Off e_phoff; /* Program header table file offset */

Elf_Off e_shoff; /* Section header table file offset */

Elf_Word e_flags; /* Processor-specific flags */

Elf_Half e_ehsize; /* ELF header size in bytes */

Elf_Half e_phentsize; /* Program header table entry size */

Elf_Half e_phnum; /* Program header table entry count */

Elf_Half e_shentsize; /* Section header table entry size */

Elf_Half e_shnum; /* Section header table entry count */

Elf_Half e_shstrndx; /* Section header string table index */

} Elf_Ehdr;

e_ident

包含了Maigc Number和其它資訊,共16位元組。

0~3:前4位元組為Magic Number,固定為ELFMAG。

4(EI_CLASS):ELFCLASS32代表是32位ELF,ELFCLASS64 代表64位ELF。

5(EI_DATA):ELFDATA2LSB代表小端,ELFDATA2MSB代表大端。

6(EI_VERSION):固定為EV_CURRENT(1)。

7(EI_OSABI):作業系統ABI標識(實際未使用)。

8(EI_ABIVERSION):ABI版本(實際 未使用)。

9~15:對齊填充,無實際意義。

e_type

ELF的檔案型別,定義如下:

ET_REL 可重定位文 件(如目標檔案)

ET_EXEC 可執行檔案(可直接執行的檔案)

DT_DYN 共享目標檔案(如SO庫)

DT_CORE Core檔案(吐核檔案)

注:GCC使用編譯選項 -pie 編譯的可執行檔案實際 也是DT_DYN型別。

e_machine

e_verison

檔案版本,目前常見的ELF 檔案版本均為EV_CURRENT(1)。

e_entry

入口虛擬地址。

e_phoff

段表文件偏移。

e_shoff

節表文件偏移。

e_flags

處理器特定的標誌,一般為0。

e_ehsize

Elf_Header的大小(位元組)

e_phentsize

段頭(Program Header)的大小(位元組)。

e_phnum

段的數量。

e_shentsize

節頭(Section Header)的大小(位元組)。

e_shnum

字的數量。

e_shstrndx

節字串表的節索引。

更多技術相關文章:Virbox技術部落格