Google

星期三, 一月 23, 2008

PE Format(20)

不管怎样,符号“x”的地址都被存在“__imp_x”的存储单元。所有这样的存储单元一起形成所谓的“输入地址表”,此表是由被用到的各DLL文件中的输入库提供给链接器的。输入地址表就是由下面这种形式的一组地址组成的:
 __imp__symbol: 0xdeadbeef
  __imp__symbol2: 0x40100
  __imp__symbol3: 0x300100
  ...

  这个输入地址表是输入目录的一部分,并且被IMAGE_DIRECTORY_ENTRY_IAT(输入地址表目录项)目录指针所指向(尽管有些链接器不设置此目录项,程序也能运行;很明显地,这是因为加载器不使用IMAGE_DIRECTORY_ENTRY_IAT(输入地址表目录项)目录也能解决输入问题)。

  这些地址并不被链接器所知;链接器只插入一些伪地址(函数名称的RVA;参见后面的更多信息),这些伪地址会在载入时被加载器用输出DLL文件中的输出目录来修正。输入地址表,以及它是怎样被加载器找到的,将会在本章的后面被详细讲述。

  注意:这个介绍是针对C语言规范的;有些别的应用程序构建环境是不使用输入库的,尽管它们都需要建立一个输入地址表,用来让它们的程序访问输入对象和函数。C语言编译器往往使用输入库,因为无论如何讲,这都有利于它们----它们的链接器使用好库。别的环境使用的是例如:一个列出需要的DLL文件名称和函数名称的描述文件(比如“模块定义文件”),或者一个源文件中的声明形式的列表等。

  这就是程序的代码如何使用输入函数的;现在我们再来看看输入目录是如何建立以便加载器使用的。

  输入目录应该存在于是“已初始化数据”并且“可读”的节中。

  输入目录是一个多IMAGE_IMPORT_DESCRIPTOR(输入描述结构)的数组,每个被使用的DLL文件都有一个。(它们的)列表由一个全部用0填充的IMAGE_IMPORT_DESCRIPTOR(输入地址表目录项)结构作为结束。

  一个IMAGE_IMPORT_DESCRIPTOR(输入地址表目录项)是一个拥有下列成员的结构体:

  OriginalFirstThunk(原始第一个换长)(汉译的说明见注释)

  它是一个RVA(32位),指向一个以0结尾的、由IMAGE_THUNK_DATA(换长数据)的RVA构成的数组,其每个IMAGE_THUNK_DATA(换长数据)元素都描述一个函数。此数组永不改变。

  TimeDateStamp(时间日期戳)

  它是一个具有好几个目的的32位的时间戳。让我们先假设时间戳为0,一些高级的情况将在以后处理。

标签: , ,

0 条评论:

发表评论

<< 主页

辽ICP备05003652号
流风洄雪听天籁,轻云蔽日看落花

Powered by Blogger