PE文件详解(八)
来源:互联网 发布:趴在桌上睡觉知乎 编辑:程序博客网 时间:2024/06/09 20:23
本文转载自小甲鱼PE文件详解系列教程原文传送门
当应用程序需要调用DLL中的函数时,会由系统将DLL中的函数映射到程序的虚拟内存中,dll中本身没有自己的栈,它是借用的应用程序的栈,这样当dll中出现类似于mov eax, [1000000]这样直接寻址的代码时,由于事先并不知道它会被映射到应用程序中的哪个位置,并且可能这个内存地址已经被使用,所以当调用dll中的函数时,系统会进行一个基址重定位的操作。系统是根据dll中的基址重定位表中的信息决定如何进行基址重定位,哪些位置的指令需要进行基址重定位。
所以这次主要说明基址重定位表。
这个重定位表位于数据目录表的第六项。这个表的主要结构如下:
IMAGE_BASE_RELOCATION STRUC VirtualAddress DWORD ? ; 重定位数据开始的RVA 地址 SizeOfBlock DWORD ? ; 重定位块得长度 TypeOffset WORD ? ; 重定项位数组IMAGE_BASE_RELOCATION ENDS
VirtualAddress 是 Base Relocation Table 的位置它是一个 RVA 值
SizeOfBlock 是 Base Relocation Table 的大小;
这个结构的示意图如下:
TypeOffset 是一个数组,数组每项大小为两个字节(16位),它由高 4位和低 12位组成,高 4位代表重定位类型,低 12位是重定位地址。高4位一般是3,表示这个地址是一个32位的地址,它与 VirtualAddress 相加即是指向PE 映像中需要修改的那个地址的位置,注意这里不是定位到对应代码的位置
接下来进行手工的方式找到需要重定位的代码位置:
打开一个dll文件,发现它的基址重定位表所在RVA = 0x00004000
通过计算得到它是在.relo ,对应文件的偏移为0x800,查看这个位置的值为:
VirtualAddress = 0x1000,
SizeOfBlock = 0x18
通过它的大小,得知需要重定位的位置主要有(0x18 - 8) / 2 = 8,最后一个以0结尾,所以实际上总共有7处需要重定位
这8个位置分别为:0x028, 0x02e, 0x003e 0x04b, 0x051, 0x61, 0x6c
后面的以此类推,可以发现这些需要重定位的位置,存储的都是一些立即寻址的地址
- PE文件详解(八)
- PE格式详解(八)
- PE文件详解八:IMAGE_BASE_RELOCATION STRUC基址重定
- PE文件详解(三)
- PE文件详解(四)
- PE文件详解(五)
- PE文件详解(六)
- PE文件详解(七)
- PE文件详解(九)
- PE文件详解(一)
- PE文件结构详解(三)PE导出表
- PE文件结构详解(四)PE导入表
- PE文件结构详解(三)PE导出表
- PE文件结构详解(四)PE导入表
- PE文件结构详解(三)PE导出表
- PE文件结构详解(四)PE导入表
- PE文件结构详解(三)PE导出表
- PE文件结构详解(四)PE导入表
- django 模型 models详解
- python操作Excel读写--使用xlrd
- Java Socket 简单的Client/Server程序
- 内核 驱动 硬件直接的关系
- 给JSP页面添加验证码
- PE文件详解(八)
- Android中Volley的使用及部分源码分析
- 声明
- Android---启动模式
- PAT L1-019. 谁先倒
- jsp验证码代码
- Linux下的开源软件有哪些有趣的玩法
- jQuery选择器之基本筛选选择器
- Activity的四种启动模式