前言:

  熟悉elf文件结构是一件很不错的事,因为安卓中的so加固以及修复都是需要这些知识的,包括pwn里面的rop之类的,也都是

和got节,plt节息息相关的,个人建议是在搞懂elf文件结构后,自己实现一个解析器,把注释写好,方便忘了再进一步重温,写的不好

见谅。

一. elf文件概述

elf文件包括了可执行文件,共享文件,目标文件这三类,其中安卓中涉及到的就是so文件,这个其实就是一个共享文件,类似

windows上的dll文件,目标文件是汇编文件,后缀为.o的文件,与可执行文件不同的是,并没有段头表,因为段是由相同功能的

节组合成的,而目标文件只是一个模块,并没有和其他模块进行链接,也就是节也没有合并,所以不存在段这个概念,程序的入口点

地址也是为空的,可执行文件和共享文件的话,大体结构和目标文件相同,多了段的概念,然后提供了两种视图(链接视图和装载视图)

二.elf文件结构

看起来其实不复杂,文件头,程序头表,节头表,节,段(其实就是相同功能节的组合体),接下来单独说说各个部分

三.elf文件头

这里搬出来010editor来看,这里是我导入之前做的crackme的so文件

好像名字奇奇怪怪的,我直接搬上,elf结构体定义

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;

重点说说几个字段,没说的说明比较简单易懂

1. e_ident:魔数,标识是哪个文件

2. e_phoff:程序头表在文件中的偏移

3. e_shoff: 程序节表在文件中的编译

4.e_phentsize: elf头占多少字节,32位的so,一般为52个字节

5. e_phnum: 程序头表中有关程序头的结构体个数,类似一个int数组,中int的个数

6. e_shnum:  和e_phnum差不多,把主语换成节头表

7. e_shstrndx: .strtab节在节头表的下标,因为里面存着所有节的名字

四.节头表解析

typedef struct
{
Elf32_Word sh_name; /* Section name (string tbl index) */
Elf32_Word sh_type; /* Section type */
Elf32_Word sh_flags; /* Section flags */
Elf32_Addr sh_addr; /* Section virtual addr at execution */
Elf32_Off sh_offset; /* Section file offset */
Elf32_Word sh_size; /* Section size in bytes */
Elf32_Word sh_link; /* Link to another section */
Elf32_Word sh_info; /* Additional section information */
Elf32_Word sh_addralign; /* Section alignment */
Elf32_Word sh_entsize; /* Entry size if section holds table */
} Elf32_Shdr;

节头表的结构如上图,实际上节头表就是上图结构体的数组,里面的数量是上面elf文件头中的e_shnum决定的,但是注意这个结构体并不是我们所想的节

也只是一个中间过渡的东西,只是定义了每个节在文件的哪个位置,名字叫什么,大小,类型是什么,具体的内容,还要根据其中定义好的偏移和大小再

去查找,接下来说说每个字段的含义

1.sh_name  是字符串节的下表,通常是先根据文件头中的strndx字段找到字符串节,然后再根据这个sh_name,找到节的名字

2. sh_type  表明这个节的类型是什么,内容比较多,直接上图

3.sh_flag 表明这个节是否可读可写可执行,记忆性的东西,直接上图

4.sh_addr  将会映射到虚拟内存空间中的地址

5.sh_size 和sh_off: 前一个是节的大小,后一个是节在文件中的偏移

在linux上也可以通过readelf -S xxx(文件名)进行查看

五. 特殊的节

五.1  .symtab

符号表的节,一般的so文件都会被抹去,怕被反编译,直接还原出符号名,也是一个结构体数组

st_name: 在字符串表中的下标

st_value :真正的值

st_size: 大小

st_info: 符号类别

毕竟符号分为局部符号,全局符号,还得标记是不是动态链接的

st_stndx: 符号属于哪个段,那个段在节头表的下标

挑了个so文件,发现里面的符号表已经被抹去了,-s只能查看.dynsym这个动态链接的节了

2..dynsym和.dynstr

动态链接符号表,里面主要存放着动态链接的符号,.dynstr里面主要存放动态链接符号的字符串名,

3. .rel.节名

重定位的表,很重要,因为这个表需要告诉linker哪个符号需要重定位

4. .plt节和.got节

出现.plt节的原因是有延迟绑定机制,因为动态链接中,符号很多,而且有些符号还没用到

那么重定位的负担就很重,所以就出现了延迟绑定,只有用到了该符号再进行绑定(这里的绑定主要说的是got表中填入符号的地址)

所以汇编代码大概是这样的:

jmp 后面的地址,是got表中的内容,但是如果没用过这个符号,里面填写的是push n的地址,也就是跳转到下一条指令了,

然后在把got表的下标和模块的id入栈,调用符号绑定的函数,实现延迟绑定,所以.plt节实际上就是一个got表的跳板,

六.程序头表(segment)
elf可分为两种视图,一种是链接视图,还有一种是装载视图

实际上不需要想的很复杂,段实际上就是相同功能的节的集合,本质上还是节,不过装载过程中所需的信息只和段有关,这也是为什么so加固中,可以去动节的一些信息,为我们解壳提供便利

typedef struct

{
  Elf32_Word    p_type;            /* Segment type */
  Elf32_Off    p_offset;          /* Segment file offset */
  Elf32_Addr    p_vaddr;        /* Segment virtual address */
  Elf32_Addr    p_paddr;        /* Segment physical address */
  Elf32_Word    p_filesz;        /* Segment size in file */
  Elf32_Word    p_memsz;        /* Segment size in memory */
  Elf32_Word    p_flags;        /* Segment flags */
  Elf32_Word    p_align;        /* Segment alignment */
} Elf32_Phdr;

也是一个结构体数组,注释也写得很清楚了。略

总结: 重心还是在节那块,参考了程序员自我修养,和看雪的几篇文章,但是看雪文章明显不如书有精华了,建议还是看看书

elf文件结构解读以及plt节got节的理解的更多相关文章

  1. ELF文件结构

    ELF文件结构 ELF文件的全称是Executable and Linkable Format,直译为"可执行可链接格式",包括目标文件(.o).可执行文件(可以直接运行).静态链 ...

  2. PE文件格式---节和节表

    17.1.4  节表和节 从排列位置来看,PE文件在DOS部分和PE文件头部分以后就是节表和多个不同的节(如图17.1中的③和④所示).要理解什么是节表,什么是节以及它们之间的关系,那就首先要了解Wi ...

  3. ELF文件结构描述

    ELF目标文件格式最前部ELF文件头(ELF Header),它包含了描述了整个文件的基本属性,比如ELF文件版本.目标机器型号.程序入口地址等.其中ELF文件与段有关的重要结构就是段表(Sectio ...

  4. elf文件中的.plt .rel.dyn .rel.plt .got .got.plt的关系

    .plt的作用是一个跳板,保存了某个符号在重定位表中的偏移量(用来第一次查找某个符号)和对应的.got.plt的对应的地址 .rel.dyn重定向表,在程序启动时就需要重定位完成. .rel.plt保 ...

  5. 程序运行之ELF文件结构

    ELF目标文件格式的最前部是ELF文件头.包含了整个文件的基本属性.比如ELF文件版本,目标机器型号,程序入口地址等.然后是ELF的各个段,其中ELF文件中与段有关的重要结构就是段表.段表描述了ELF ...

  6. 第一百二十九节,JavaScript,理解JavaScript库

    JavaScript,理解JavaScript库 学习要点: 1.项目介绍 2.理解JavaScript库 3.创建基础库 从本章,我们来用之前的基础知识来写一个项目,用以巩固之前所学.那么,每个项目 ...

  7. Vue-cli2.0 第3节 解读Vue-cli模板

    Vue-cli2.0 第3节 解读Vue-cli模板 目录 Vue-cli2.0 第3节 解读Vue-cli模板 第3节 解读Vue-cli模板 1. npm run build命令 2. main. ...

  8. Android C语言_init函数和constructor属性及.init/.init_array节探索

    本篇文章主要介绍了"Android C语言_init函数和constructor属性及.init/.init_array节探索",主要涉及到Android C语言_init函数和c ...

  9. Android so库文件的区节section修复代码分析

    本文博客地址:http://blog.csdn.net/qq1084283172/article/details/78818917 一.Android so库文件的节表secion修复方案整理 1.简 ...

随机推荐

  1. GO汇编-函数

    GO汇编-函数 终于到函数了!因为Go汇编语言中,可以也建议通过Go语言来定义全局变量,那么剩下的也就是函数了.只有掌握了汇编函数的基本用法,才能真正算是Go汇编语言入门.本章将简单讨论Go汇编中函数 ...

  2. 浅析IOC 和 DI

    学习过spring框架的人一定都会听过Spring的IoC(控制反转) .DI(依赖注入)这两个概念,对于初学Spring的人来说,总觉得IoC .DI这两个概念是模糊不清的,是很难理解的,今天和大家 ...

  3. Python小白的数学建模课-A3.12 个新冠疫情数模竞赛赛题与点评

    新冠疫情深刻和全面地影响着社会和生活,已经成为数学建模竞赛的背景帝. 本文收集了与新冠疫情相关的的数学建模竞赛赛题,供大家参考,欢迎收藏关注. 『Python小白的数学建模课 @ Youcans』带你 ...

  4. 将视频插入视频:CVPR2019论文解析

    将视频插入视频:CVPR2019论文解析 Inserting Videos into Videos 论文链接: http://openaccess.thecvf.com/content_CVPR_20 ...

  5. Linux 2 的 Windows 子系统上发布 CUDA

    Linux 2 的 Windows 子系统上发布 CUDA 为响应大众需求,微软 宣布 在 2020 年 5 月的 建造 大会上推出了 建造 ( WSL 2 ) – GPU 加速功能.这一特性为许多计 ...

  6. AI芯片体系结构目标图形处理

    AI芯片体系结构目标图形处理 AI chip architecture targets graph processing 可编程图形流处理器(GSP)能够执行"直接图形处理.片上任务图管理和 ...

  7. Spring Security 快速上手

    Spring Security 框架简介 Spring Security 说明 Spring Security 基于 Spring 框架,提供了一套 Web 应用安全性的完整解决方案 关于安全方面的两 ...

  8. 【NX二次开发】Block UI 多行字符串

    属性说明 常规         类型 描述     BlockID     String 控件ID     Enable     Logical 是否可操作     Group     Logical ...

  9. 03:CSS(01)

    内容概要 分组与嵌套 伪类选择器 伪元素选择器 选择器优先级 css属性相关(操作标签样式) 浮动 定位 模态框 透明度 内容详细 分组与嵌套 div,p,span { /*逗号表示并列关系*/ co ...

  10. Java第二次博客作业

    Java第二次博客作业 时间过的很快啊,在不知不觉中这门课程的学习也就快要过去一半了,现在就来总结一下在这个第二个月的学习当中存在的问题以及得到的心得. 1.前言 第四次题目集和第五次题目集给我的感觉 ...