ELF程序头

ELF程序头

介绍

ELF程序头是对ELF二进制文件的描述,是程序必备必须装载的一部分,段(segment) 是在内核装载时被解析的。主要作用就是描述磁盘上可执行文件的内存布局以及如何映射到内存中。可以通过引用原始的ELF头中名为: **e_phoff**(程序头表的偏移量)的偏移量来得到程序头表。比如上文引用的ElfN_Ehdr结构中所示

下面讨论5种常见的程序头类型。程序头描述了可执行文件(包括共享库)中的段及其类型(为哪种类型的数据或代码而保留的段)。首先,我们来看一下Elf32_Phdr与Elf64_Phdr的程序头结构,它构成了32位与64位ELF可执行文件程序头表的一个程序头条目。

结构体

Elf32_Phdr程序头结构体如下:

typedef struct {

Elf32_Word p_type; // segment type

Elf32_Off p_offset; // segment offset

Elf32_Addr p_vaddr; // virtual address of segment

Elf32_Addr p_paddr; // physical address - ignored

Elf32_Word p_filesz; // number of bytes in file for seg.

Elf32_Word p_memsz; // number of bytes in mem. for seg.

Elf32_Word p_flags; // flags

Elf32_Word p_align; // memory alignment

} Elf32_Phdr;

Elf64_Phdr程序头结构体如下:

typedef struct {

Elf64_Half p_type; // entry type

Elf64_Half p_flags; // flags

Elf64_Off p_offset; // offset

Elf64_Addr p_vaddr; // virtual address

Elf64_Addr p_paddr; // physical address

Elf64_Xword p_filesz; // file size

Elf64_Xword p_memsz; // memory size

Elf64_Xword p_align; // memory & file alignment

} Elf64_Phdr;

核心字段就是 p_type p_offset p_vaddr 以及p_flags

这俩个结构主要描述了elf在被加载的时候内存要如何映射

字段含义及取义

p_type取值

typedef enum <Elf32_Word> {

PT_NULL = 0x0,

PT_LOAD = 0x1, /*表示段是可以被加载到内存中执行的*/

PT_DYNAMIC = 0x2,

PT_INERP = 0x3,

PT_NOTE = 0x4,

PT_SHLIB = 0x5,

PT_PHDR = 0x6,

PT_TLS = 0x7,

PT_NUM = 0x8,

PT_LOOS = 0x60000000,

PT_GNU_EH_FRAME = 0x6474e550,

PT_GNU_STACK = 0x6474e551,

PT_GNU_RELRO = 0x6474e552,

PT_LOSUNW = 0x6ffffffa,

PT_SUNWBSS = 0x6ffffffa,

PT_SUNWSTACK = 0x6ffffffb,

PT_HISUNW = 0x6fffffff,

PT_HIOS = 0x6fffffff,

PT_LOPROC = 0x70000000,

PT_HIPROC = 0x7fffffff,

// ARM Sections

PT_SHT_ARM_EXIDX = 0x70000001,

PT_SHT_ARM_PREEMPTMAP = 0x70000002,

PT_SHT_ARM_ATTRIBUTES = 0x70000003,

PT_SHT_ARM_DEBUGOVERLAY = 0x70000004,

PT_SHT_ARM_OVERLAYSECTION = 0x70000005

} p_type32_e;

typedef p_type32_e p_type64_e;

p_align取值

typedef enum <Elf32_Word> {

PF_None = 0x0, //表示没有属性

PF_Exec = 0x1, // 段可执行

PF_Write = 0x2, //可写

PF_Write_Exec = 0x3, //可写可执行

PF_Read = 0x4, //只读

PF_Read_Exec = 0x5, //读和执行

PF_Read_Write = 0x6, //读写

PF_Read_Write_Exec = 0x7 //读写执行

} p_flags32_e;

posted @ 2023-08-28 09:51  N0t3  阅读(48)  评论(0编辑  收藏  举报