首页 文章

可执行部分 Headers - 含义和用法?

提问于
浏览
3

通过在Windows中使用7zip打开许多可执行文件( .exe..msi ),我注意到许多不同的文件类型是常见的 . 那些包括.text,.data,.bss,.rdata,.pdata等 . 我发现它们的意思 . 以下是其中一些:

  • .text :代码部分,包含程序的指令 - 只读 - .

  • .data :通常用于具有一些初始化非零内容的可写数据 . 因此,数据部分包含可在应用程序执行期间更改的信息,并且必须为每个实例复制此部分 .

  • .bss :用于初始化为零的可写静态数据 .

  • .rdata :此处存储任何类型的Const /只读数据 .

  • .edata :导出目录,描述符和句柄

  • .idata :导入句柄和描述符的目录 . 可执行文件(exe,dll等)使用它来指定导入和导出的函数 .

  • .rsrc :包含可执行文件所需的各种其他资源的信息的部分,例如在资源管理器中查看可执行文件时显示的图标

还有很多其他的,很常见,我找不到任何信息 . 主要是: .pdata.tls.reloc ,CERTIFICATE, .rsrc_1.aspack.adata.INITDATACODE.ctors .

大多数文件夹中都包含 rsrc 文件夹,其中包含BITMAP,CURSOR,ICON,GROUP_CURSOR,GROUP_ICON,MENU,VERSION等文件夹 .

一些可执行文件还包含更多的可执行文件, .html 文件, .txt 文件等 . 我还打开了一个根本没有任何内容(至少没有用7zip打开它显示)! [我用7zip打开了它们 . ]


问题

  • 我发布的那些部分/细分是做什么的?有网站我可以找到它们吗?

  • 我看到的所有人都是Windows的PE . 这些格式是否标准并以类似/相同的方式应用于LINUX,UNIX等?

  • 为什么有些可执行文件包含其他可执行文件,或.html,.txt和其他文件?启动可执行文件时如何处理这些问题?他们该怎么办? AFAIK可执行文件中的所有内容应该只包含那些类似汇编代码段的"segments" .

  • rsrc 文件夹有什么用?它拥有什么样的资源?

我将不胜感激,如果你可以发布更多的信息/链接,为什么所有这些都使用(尽可能低),一般来说可执行结构应该是什么样的,应该包含什么等等 .

这就是全部 .


EDIT

我找到了其他常见的节头名称 . 我会在这里发表他们的意思是为了完整 .

  • .reloc :包含重定位表 .

  • .pdata :包含用于异常处理的函数表条目数组,并由映像数据目录中的异常表条目指向

  • *data :自定义数据部分名称

  • .init :此部分包含有助于进程初始化代码的可执行指令 . 也就是说,当程序开始运行时,系统安排在主程序入口点(在C程序中称为main)之前执行本节中的代码 .

  • .fini :此部分包含有助于进程终止代码的可执行指令 . 也就是说,当程序正常退出时,系统会安排执行本节中的代码 .

  • .ctors :保留构造函数列表的部分

  • .dtors :包含析构函数列表的部分

2 回答

  • 2

    部分名称与文件格式无关,工具链(通常是链接器)可以选择它喜欢的任何东西 . 操作系统不使用名称来查找它关注的部分,它使用文件头中的data directory . 其中包含数字,而不是名称 . 该名称仅作为帮助识别部分的助记符 . 或者可能用于帮助语言运行时或调试器查找数据目录未涵盖的部分 .

    部分名称有一些一致性,主要是按惯例 . 像BSS这样的古怪部分名称一直追溯到50年代,用于Fortran,这是Block Started by Symbol的首字母缩写 . 今天对它的使用没有多大帮助:)你可以假设一个名为CODE的部分将包含可执行代码并且相当于.text,更常见的名字选择 . 像.tls和.reloc这样的名称可以毫无困难地映射到相应的数据目录条目 .

    与.rsrc相同的receipe,映射到数据目录中的第三个条目 . 对操作系统来说很重要,像LoadString这样的winapi函数需要它 .

    但是,只有详细了解工具链才能为您提供真实的提示 .

    操作系统加载程序通过使用可执行文件作为后备存储的内存映射文件将一个部分直接放入虚拟内存中 . 这是如何使用.text,.data和.bss这样的部分,请注意它们在数据目录中没有相应的条目 . 链接器负责生成适当的地址,就像25年前完成的那样,操作系统没有任何帮助 . 除了.reloc部分,如果文件无法映射到其首选的基址,那就太旧了 .

  • 3

    这里没有魔法,也没有关于构造可执行文件的通用规则 . 您必须遵循相关操作系统的规则,并仅提供它理解的可执行格式 . 但即使有这些部分,尽管在几十年的时间内在编译器中非常普遍使用,但在技术上是任意的 . 你基本上完成了你需要做的所有工作并回答了你自己的问题 .

    操作系统只需要了解一些事情 . 这个文件有多少是实际可加载的数据,我在哪里加载它 . 操作系统不知道/看到来自.data的.text,它看到了可加载的块 . 它将这些块从文件复制到内存中,然后它会看到一个定义的入口点,它会分支到该入口点 . 剩下的信息是...信息...对于调试器而言,它是软件或者有兴趣了解编译器放置在.data部分中的数量或内容的人 .

    直接或间接由程序员来正确使用这些部分,通常程序员不会直接参与 . 称为引导程序的软件根据需要执行处理这些部分的工作 . 例如,引导程序通常将.bss部分归零,这是编译器工具链中的系统设计解决方案,告诉引导程序.bss的大小和起始地址以及ram的引导零 .

    .data和.text通常只是由操作系统加载而不需要进一步关注,因为它被加载到ram中 . 但是,例如,如果这是一个微控制器,我们需要在非易失性存储(flash / rom)中使用非零全局.data,但是当我们启动并运行我们编译的代码时,我们需要它在ram中 . 因此,引导程序通常使用编译器系统设计解决方案来执行将.data从flash复制到ram的工作,以告知引导程序闪存中的起始地址和ram中的起始地址以及复制的数量 .

    我正在谈论的系统设计是一个变量,如果您将使用汇编语言(否则它是一个鸡和蛋问题)引导程序使用链接器完成其工作后填充的链接填充并计算出有多少一切以及它们放置在二进制或内存映像中的位置 .

    数据是数据,你可以将数据嵌入你的二进制文件中,无论是文本还是html或图像(jpg,bmp,png等)或其他,正确的hexdump工具可以显示,使用的工具链甚至可能有特殊的部分名称用于该数据 .

    几乎所有这些节名都部分用于调试编译器输出,部分用于信息 . 特定的工具链具有其使用的特定部分名称,或者甚至允许用户(程序员)创建他们自己的任意名称,因为它们就是这样 . 并且该特定工具链使用该信息作为其系统设计的一部分,编译器从数据中分类出程序,并且它不必在历史上从开始全局数据中假定为零的非零全局数据进行分类 . 并且可能比仅读取非零数据更深 . 它标记那些带有名称的对象blob,以便链接器可以收集所有命名的blob,并使用链接器脚本完成将这些blob组装成更大的blob并为其分配地址的工作 . 然后根据需要修补二进制文件以解析外部地址/变量 .

    问题1:没有没有可以找到它们的网站,很可能很难证明至少有一个工具链允许用户发明自己的部分名称,因此一个或多个网站是不可能的涵盖所有可能的部分名称和定义那些程序员可能想到的那些部分名称 .

    问题2:有一个通用集.text,.data,.bss已经被所有目标系统(windows,unix等)上的大多数(如果不是全部)工具链所采用和使用,这是工具链的功能而不是操作系统作为操作系统不知道或不关心 . 它只是将可加载的blob和分支加载到入口点 . 由于这些名称是任意的,只需要在工具链的系统设计中工作,因此询问操作系统是没有意义的

    问题3:所有部分,无论是否奇怪,都可以通过工具链间接管理,也可以在库中链接或由程序员直接管理 . 从.bss到.somethingimadeup .

    问题4:这听起来与操作系统有关 . 了解操作系统定义了支持的可执行格式是什么以及它们包含的内容 . 编译器必须符合这一点才能生成有效的二进制文件 . 例如,像windows这样的操作系统可能非常希望在“二进制”中有一个图标位图,这样它就可以在程序名称旁边的桌面上显示,这也是二进制文件中的信息 . 因此,除了二进制文件格式需要具有的显而易见的事物(在文件中的偏移量和内存中的大小和目标地址,用于可加载的数据块和执行入口点)之外,文件格式可以具有其他信息或其他项 . “Windows快捷方式”的文件格式可能是子集或特殊的“二进制”格式,其中信息是另一个文件的路径和文件名,而不是您实际加载和运行的代码 . 您可能有一个包含网址的“二进制”文件格式或快捷方式 . 但这将是非常多的操作系统定义和依赖 .

相关问题