第16章:基址重定位

Posted rev-omi

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了第16章:基址重定位相关的知识,希望对你有一定的参考价值。

PE重定位

使得硬编码在程序中的内存地址随当前加载地址的变化而变化就是PE重定位.

若不添加重定位,而加载时内存地址被占用,则会出现"内存地址引用错误",使得程序异常终止.

PE重定位的操作原理:

技术图片

 

查找硬编码地址需要用到重定位表(Relocation Table),它是记录硬编码地址偏移列表.是PE文件构建过程中(编译/链接的时候提供的).

技术图片

 

 

重定位表在Image_optional_header/DataDirectory[5]中可找到地址,转化为FileOffset即可.

技术图片

 

查看各个节区头的信息,发现在reloc节区中,直接查该节区头的PointerToRawData字段中的地址.即红色框起来的四字节.

技术图片

技术图片

 

SizeOfBlock后面跟着的元素是很多两字节的TypeOffset.末端以0结尾.

第一个为例:3424. 高四位(此处是3)是重定位类型,低12位(此处是424)是偏移.

在网上搜索可知,在Windows中只采用的Image_Rel_Based_HighLow(3)这种类型.

硬编码地址的计算为:1000(Virtual Address)+3424(Offset) = 1324(FileOffset).

转到地址1424处,值大小为4字节,此处为010010c8:

技术图片

 

 在可选头中查找到ImageBase值,一般来说是1000000.

技术图片

 

偏移地址为010010c8-1000000 = 10c8.从系统获取程序实际加载的基地址,二者相加即可得到重定位地址.

技术图片

技术图片

 

 此处就是10c8+210000 = 2110c8即可看到导入的DLL的函数地址.

 

以上是关于第16章:基址重定位的主要内容,如果未能解决你的问题,请参考以下文章

《PE总结 》– 重定位表

Week of 2.28

专业名词汇总

学习笔记

使用 extern 时 gcc 的重定位错误

Golang内部构件,第3部分:链接器,目标文件和重定位