ELF文件格式

这篇具有很好参考价值的文章主要介绍了ELF文件格式。希望对大家有所帮助。如果存在错误或未考虑完全的地方,请大家不吝赐教,您也可以点击"举报违法"按钮提交疑问。

Executable and Linkable Format是Linux操作系统上默认的二进制格式

一个可以执行的文件就是存储了一些数据和代码,我们要明白ELF文件有哪些部分,每一部分记录了文件的什么信息

ELF文件格式

                                我偷偷把星星散布于自己个人的天空,在那里创造我的无限                                                                                                           ——费尔南多·佩索阿

目录

二进制分析

ELF文件包括了4种类型的组件

ELF头部

e_ident数组

幻数

EI_CLASS

EI_DATA

EI_VERSION

EI_OSABI和EI_ABIVERSION

EI_PAD

使用readelf命令查看e_ident

e_type字段

e_machine字段

e_version字段

e_entry字段

e_phoff和e_shoff字段

e_flags字段

e_ehsize字段

e_*entsize和e_*num字段

e_shstrndx字段

节头

sh_name字段

sh_type字段

sh_flags字段

sh_addr,sh_offset及sh_size字段

sh_link字段

sh_info字段

sh_addralign字段

显示节

.init节

.fini节

.text节

.bss,.data及.rodata节

延迟绑定和.plt,.got和.got.plt节

延迟绑定和.plt

使用PLT动态解析库函数

其他节

.rel.和.rela.*节

.dynamic节

.init_array和.fini_array节

.shstrtab、.symtab、.strtab、.dynsym及.dynstr节

程序头

p_type字段

p_flags字段

p_offset、p_vaddr、p_paddr、p_filesz和p_memsz字段

p_align字段


二进制分析

什么是漏洞

漏洞的英文是leak

ELF文件格式

leak在英语语境中是一种气体,液体或者信息的泄露

我们的程序就像水流一样向下运行,用条件判断进行分流 

在这个运行过程中一些设计问题会让攻击者有可乘之机,这就是漏洞

通过漏铜我们可以劫持进程,泄露信息

我们运行的程序是编译过后的机器语言程序,不是高级语言直接运行,所有这个运行过程的漏洞要从二进制层面来发掘,ELF文件格式就是必修的二进制知识

本文就来介绍ELF文件的知识

ELF文件格式

ELF文件包括了4种类型的组件

  • ELF头部
  • 程序头
  • 节头

每一块都存储了文件的一部分信息

ELF头部

每个ELF二进制文件都是从ELF头部开始的,该头部是一系列结构化的字节

本质是什么,就是这个文件的头部存储了一些有用的数据,可理解为一个数据结构,就是一个结构体

下使用高级语言的定义

#define EI_NIDENT (16)
 
typedef struct
{
  unsigned char e_ident[EI_NIDENT];     /* Magic number and other info */
  Elf32_Half    e_type;                 /* Object file type */
  Elf32_Half    e_machine;              /* Architecture */
  Elf32_Word    e_version;              /* Object file version */
  Elf32_Addr    e_entry;                /* Entry point virtual address */
  Elf32_Off     e_phoff;                /* Program header table file offset */
  Elf32_Off     e_shoff;                /* Section header table file offset */
  Elf32_Word    e_flags;                /* Processor-specific flags */
  Elf32_Half    e_ehsize;               /* ELF header size in bytes */
  Elf32_Half    e_phentsize;            /* Program header table entry size */
  Elf32_Half    e_phnum;                /* Program header table entry count */
  Elf32_Half    e_shentsize;            /* Section header table entry size */
  Elf32_Half    e_shnum;                /* Section header table entry count */
  Elf32_Half    e_shstrndx;             /* Section header string table index */
} Elf32_Ehdr;

我们来一部分一部分进行一下解读

e_ident数组

 010Editor

这里先介绍一款二进制编辑工具的使用

ELF文件格式

这是一款强大的二进制编辑工具和十六进制编辑工具

我们存储的文件都是二进制的形式,这款工具可以查看二进制,默认是十六进制表示

可以直接修改这些二进制

ELF文件格式

看上面的定义是一个16字节的数组

幻数

第一部分是一个4字节的幻数,由0x7F和ELF的ASCLL码组成

我们看一下010edior的开头

ELF文件格式

左侧是16进制表示的二进制数据,右侧是左侧数据对应的ASCLL表示,'.'表示不可见字符

紧跟在幻数后面的字节提供了有关ELF二进制文件类型规范,就是e_ident的4~15索引

下面介绍这些部分,参考上图,或者自己找一个ELF文件用010editor查看

EI_CLASS

表示ELF规范中二进制文件的类,这个字节表示用的是32位还是64位体系结构
32位是1,64位是2

EI_DATA

指示二进制文件中的字节序

等于1是小端法,等于2是大端法

EI_VERSION

指示的是ELF版本规范,当前唯一有效的有效值是1

EI_OSABI和EI_ABIVERSION

表示的是应用程序的二进制接口

EI_PAD

这个部分包含很多字节,是 e_ident的9~15字节

当前设置都是0,保留供将来用

使用readelf命令查看e_ident

除了010editor,我们还可以在Linux中使用readelf命令查看文件的e_ident

命令与显示如图

ELF文件格式

Magic所显示的就是 e_ident

而且下面对于e_ident表示的信息进行了解读

还有显示了接下来的字段的内容解读

e_type字段

这里经常遇到的值是ET_REL(可重定位的对象文件),ET_EXEC(可执行的二进制文件),ET_DNY(动态库)

e_machine字段

表示二进制文件计划在什么体系结构上运行

EM_X86_64   EM_386   EM_ARM

e_version字段

作用与 e_ident数组中的EI_VERSION相同

唯一可能的值是EV_CURRENT,指定版本规范是1

e_entry字段

表示二进制文件的入口点

开始执行的虚拟地址

e_phoff和e_shoff字段

程序头和节头不必位于ELF文件中的任意特定偏移

e_phoff和e_shoff字段指定了程序头表和节头表距离开始的偏移量

e_flags字段

保存了二进制文件在特定处理器的标志

对于x86二进制文件,通常设置为0,无须过多关注

e_ehsize字段

指定了ELF头部的大小

64位始终为64字节,32位始终为52字节

e_*entsize和e_*num字段

每个程序头或者表中各个节头的大小

e_shstrndx字段

包含一个名为.shstrtab的,与特殊字符串表结相关的头索引

节头

ELF二进制文件中的代码和数据在逻辑上被分为连续的非重叠块,称为节

没有预设的结构体,每个节的结构体取决于内容

ELF文件格式

sh_name字段

如果这个子段被设置,字符串表中包含索引

sh_type字段

每个节的类型

sh_flags字段

SHF_WRITE 该节在运行时可写

SHF_ALLOC 指示在执行二进制文件时将节的内容加载到虚拟内存

SHF_EXECINSTR 指示该节包含可执行指令

sh_addr,sh_offset及sh_size字段

分别描述该节的虚拟地址,文件偏移和大小

sh_link字段

有时链接器需要了解节与节之间的关系,例如与SHT_SYMAB,SHT_DYNSYM或者SHT_DYNAMIC类型的节有关联的字符串表节,其中包含相关符号的名称

sh_info字段

存放关于节的额外信息,这些额外信息依赖与解类型

sh_addralign字段

包含固定大小的条目

显示节

使用readelf命令显示节

ELF文件格式

显示了节的虚拟地址,文件偏移和大小

.init节

包含可执行代码,用于执行初始化工作,并且在二进制文件执行其他代码之前运行,类似面向对象编程的构造函数

.fini节

在主程序运行完后执行,类似析构函数

.text节

包含程序的主要代码,是逆向分析的重点

包含了很多执行初始化和终止任务的标准函数,如_start,register_tm_clones,frame_dummy

.bss,.data及.rodata节

.rodata 保存只读数据

.data 存储可写的数据

.bss 初始化为0,并且标记该节为可写

延迟绑定和.plt,.got和.got.plt节

加载二进制文件的时候很多重定位一般都不会立即完成,而是延迟到对未解析位置进行首次引用之前,这就是延迟绑定

ELF文件格式

延迟绑定和.plt

延迟绑定保证了动态链接器不会在重定位上浪费时间,只在运行有需要的时候执行

延迟绑定用.plt节和.got节

通常有一个.got.plt的GOT

.plt是包含可执行代码的代码节

.got.plt是数据节

查看plt

ELF文件格式

PLT的格式如下

首先有一个默认存根,然后是一系列函数存根,每个库函数有一个存根

ELF文件格式

然后是一系列函数存根

ELF文件格式

压入栈的值依次递增,观察上图的push

使用PLT动态解析库函数

假设调用puts函数

已知该函数是libc库的一部分

可以直接调用相应的PLT存根puts@plt,不是直接调用该函数

push指令把一个整数压入栈,该整数是PLT存根的标识符

下一条转到所有PLT函数的存根之间共享的通用默认存根

默认存根会push另一个标识符,以表示可执行文件自身

然后间接地,通过GOT跳转到动态链接器 

其他节

.rel.和.rela.*节

有几个名为.rela.*的节

类型为SHT_RELA

包含链接器用于执行重定位的信息

每个SHT_RELA类型是一个重定位条目

ELF文件格式

.dynamic节

.dynamic节将充当操作系统和动态链接器的“路线图”

ELF文件格式

包含了一个Elf64_Dyn的结构体数组

也称为标签,有各种类型,每个标签有个关联值

DT_NEEDED的标签会通知通知动态链接器关于可执行文件的依赖问题

.init_array和.fini_array节

.init_array包含一个指向构造函数的指针数组

.fini_array包含一个指向析构函数的指针

ELF文件格式

.shstrtab、.symtab、.strtab、.dynsym及.dynstr节

.shstrtab只是一个以NULL结尾的字符串数组,包含所有二进制文件中所有节的名称

程序头

ELF文件格式

提供了二进制文件的段视图

ELF包括零或多个节,实际上就是把这些节捆绑成单个块

段提供的可执行视图,只有二进制文件会用到

p_type字段

标识了段的类型

主要类型包括PT_LOAD,PT_DYNAMIC,PT_INFERP

PT_LOAD类型的段会在创建进程时加载到内存中

PT_INFERP类型的段包含了.interp节,该节提供了加载二进制文件的解释器的名称

PT_DYNAMIC包含了.dynamic节,该节告诉解释器如何解析二进制文件用于执行

p_flags字段

指示了段在运行时的访问权限

有三种重要的类型

PF_X(可执行),PF_W(可写),PF_R(可读)

p_offset、p_vaddr、p_paddr、p_filesz和p_memsz字段

改段的起始文件偏移量,加载的虚拟地址以及段大小

p_align字段

指定了段所需的内存对齐方式(字节为单位)

本文介绍了ELF文件的各部分

ELF文件格式文章来源地址https://www.toymoban.com/news/detail-407696.html

到了这里,关于ELF文件格式的文章就介绍完了。如果您还想了解更多内容,请在右上角搜索TOY模板网以前的文章或继续浏览下面的相关文章,希望大家以后多多支持TOY模板网!

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处: 如若内容造成侵权/违法违规/事实不符,请点击违法举报进行投诉反馈,一经查实,立即删除!

领支付宝红包 赞助服务器费用

相关文章

  • 【嵌入式】ELF格式文件分析工具汇总

    🧑 作者简介 :阿里巴巴嵌入式技术专家,深耕嵌入式+人工智能领域,具备多年的嵌入式硬件产品研发管理经验。 📒 博客介绍 :分享嵌入式开发领域的相关知识、经验、思考和感悟,欢迎关注。提供嵌入式方向的学习指导、简历面试辅导、技术架构设计优化、开发外包等

    2024年03月10日
    浏览(183)
  • linux(wsl)下,vscode配置json文件,以及.clang-format文件

    c_cpp_properties.json launch.json task.json .clang-format 通常可用下面命令来生成,style选项 LLVM 、 Google 、 Chromium 、 Mozilla 、 Microsoft 、 GNU clang-format -style=LLVM -dump-config .clang-format

    2024年02月10日
    浏览(46)
  • 编译工具链 之二 详解 ELF 格式及标准、UNIX 发展、ABI

      在计算机及嵌入式系统中,二进制文件也有一定的标准格式,通常会包含在各平台的应用程序二进制接口 (Application Binary Interface,ABI)规范中。它是编译工具链必须要遵守的规范(编译工具链产生符合 ABI 的二进制文件)。   在计算机系统中,应用程序二进制接口 (

    2024年02月07日
    浏览(65)
  • 【linux】解压.gz文件 报错 gzip:stdin:not in gzip format(已解决)

    目录 1、问题: 2、分析原因 3、解决办法 在解压一个以【.gz】(注意不是.tar.gz)结尾的压缩包时,遇到报错 【gzip:stdin:不是gzip格式】 翻译一下问题:【gzip:stdin:不是gzip格式】 解压命令:sudo tar -zxvf + 包名 分析:这个问题导致的原因有两个: 1) 原因一、 压缩包受损

    2024年02月13日
    浏览(53)
  • Python基础——format格式化

      在python中,我们在输出字符串常用format方法设置一些特定的格式,以美化结果,同时便于更改字符串中指定内容。本文总结了format的常用方法。   format通过字符串中的花括号{}来识别和替换字符串,由此达到格式化字符串的目的。填充内容位置的识别,有按顺序自动替

    2024年02月02日
    浏览(45)
  • python中format格式化函数(全)

    格式化字符串的函数 str.format() 它增强了字符串格式化的功能。 通过用{} 和: 来代替 编程语言输出中的% 1.默认输出代码方式 输出hello world \\\" { } “输出{}内的内容以及” \\\"内的内容,空格也会跟着输出 2.指定位置的输出 输出hello,world 3.指定多个位置输出 输出world hello world 4.字

    2023年04月08日
    浏览(115)
  • std::format 如何实现编译期格式检查

    C++ 20 的 std::format 是一个很神奇、很实用的工具,最神奇的地方在于它能在编译期检查字符串的格式是否正确,而且不需要什么特殊的使用方法,只需要像使用普通函数那样传参即可。 C++ 20 的 std::format 来自一个著名的开源库 {fmt}。在 C++ 20 之前,fmt 需要为每个字符串字面量

    2024年04月08日
    浏览(31)
  • clang-format格式化代码

    Clang-Format可用于格式化(排版)多种不同语言的代码。其自带的排版格式主要有:LLVM, Google, Chromium, Mozilla, WebKit等; 利用style参数配置风格。通过编写 .clang-format 文件,可以实现代码风格的配置。 [vscode-clang-format]https://github.com/xaverh/vscode-clang-format 在.vscode/setting.json中添加 Acc

    2024年02月13日
    浏览(61)
  • Clang-format格式化及配置参数

    Clang-format格式化C代码 Author:Once Day Date:2022年11月3日 漫漫长路有人对你微笑过嘛… 参考文档: Clang-Format Style Options — Clang 16.0.0git documentation (llvm.org) ClangFormat — Clang 16.0.0git documentation (llvm.org) clang-format的介绍和使用 - Tudou_Blog - 博客园 (cnblogs.com) 1.引言 Clang-format是一种代码

    2023年04月21日
    浏览(41)
  • Linux文件系统(操作系统的文件管理)

    参考Linux内核源码版本------ linux-2.4.3 操作系统之下,进程是计算机系统 执行计算任务的基本单位 ,进程访问文件执行数据读写之前,操作系统会从外设获取相应的文件信息,在内存中建立 struct file 结构体对象来 描述和管理文件 ,进程借助 struct file 结构体提供的文件信息执行文件

    2024年02月05日
    浏览(54)

觉得文章有用就打赏一下文章作者

支付宝扫一扫打赏

博客赞助

微信扫一扫打赏

请作者喝杯咖啡吧~博客赞助

支付宝扫一扫领取红包,优惠每天领

二维码1

领取红包

二维码2

领红包