到此为止,小甲鱼和大家已经学了许多关于 DOS header 和 PE header 的知识。接下来就该轮到SectionTable (区块表,也成节表)。(视频教程:http://fishc.com/a/shipin/jiemixilie/

越学越多的结构,大家可能觉得PE挺乱挺杂的哈,所以这里插播下一下必要知识的详细注释,大伙可以按需要看。

PE文件到内存的映射

在执行一个PE文件的时候,windows 并不在一开始就将整个文件读入内存的,二十采用与内存映射文件类似的机制。也就是说,windows 装载器在装载的时候仅仅建立好虚拟地址和PE文件之间的映射关系。
当且仅当真正执行到某个内存页中的指令或者访问某一页中的数据时,这个页面才会被从磁盘提交到物理内存,这种机制使文件装入的速度和文件大小没有太大的关系。

但是要注意的是,系统装载可执行文件的方法又不完全等同于内存映射文件。
当使用内存映射文件的时候,系统对“原著”相当忠实,如果将磁盘文件和内存映像比较的话,可以发现不管是数据本身还是数据之间的相对位置它丫丫的都是完全相同的。
而我们知道,在装载可执行文件的时候,有些数据在装入前会被预处理,如重定位等,正因此,装入以后,数据之间的相对位置可能发生微妙的变化。

Windows 装载器在装载DOS部分、PE文件头部分和节表(区块表)部分是不进行任何特殊处理的,而在装载节(区块)的时候则会自动按节(区块)的属性做不同的处理。
一般情况下,它会处理以下几个方面的内容:

  • 内存页的属性;
  • 节的偏移地址;
  • 节的尺寸;
  • 不进行映射的节。

内存页的属性:

对于磁盘映射文件来说,所有的页都是按照磁盘映射文件函数指定的属性设置的。但是在装载可执行文件时,与节对应的内存页属性要按照节的属性来设置。所以,在同属于一个模块的内存页中,从不同节映射过来的的内存页的属性是不同的。

节的偏移地址:

节的起始地址在磁盘文件中是按照 IMAGE_OPTIONAL_HEADER32 结构的 FileAlignment 字段的值进行对齐的,而当被加载到内存中时是按照同一结构中的 SectionAlignment 字段的值对其的,两者的值可能不同,所以一个节被装入内存后相对于文件头的偏移和在磁盘文件中的偏移可能是不同的。

注意,节事实上就是相同属性数据的组合!当节被装入到内存中的时候,相同一个节所对应的内存页都将被赋予相同的页属性, 事实上,Windows 系统对内存属性的设置是以页为单位进行的,所以节在内存中的对齐单位必须至少是一个页的大小。(小甲鱼温馨提示:对于32位操作系统来说,这个值一般是4KB==1000H; 对于64位操作系统这个值一般是8KB==2000H)

在磁盘中就没有这个**,因为在磁盘中排放是以什么为主?肯定是以空间为主导,在磁盘只是存放,不是使用,所以不用设置那么详细的属性。试想想看,如果在磁盘中都是以4KB为大小对齐的话,不够就用0来填充,那么一个只占20字节的数据就要消耗4KB的空间来存放,是不是浪费?有木有??

节的尺寸:

对节的尺寸的处理主要分为两个方面:

第一个方面,正如刚刚我们所讲的,由于磁盘映像和内存映像中节对齐存储单位的不同而导致了长度扩展不同(填充的0数量不同嘛~);

第二个方面,是对于包含未初始化数据的节的处理问题。既然是未初始化,那么没有必要为其在磁盘中浪费空间资源,但在内存中不同,因为程序一运行,之前未初始化的数据便有可能要被赋值初始化,那么就必须为他们留下空间。

不进行映射的节:

有些节并不需要被映射到内存中,例如.reloc节,重定位数据对于文件的执行代码来说是透明的,无作用的,它只是提供Windows 装载器使用,执行代码根本不会去访问到它们,所以没有必要将他们映射到物理内存中。

好了,上边的一些知识相信又是对我们之前学习的一点补充和扩展。大家可能对上边的知识觉得又是眼熟,但又觉得有几分陌生。那是当然哈,小甲鱼教学遵循的思路就是今天的知识今天学好它,明天的东西明天再学!一下子你肯定不能接受那么深的东西,像上边的东西如果放在第一讲来讲解,那么恐怕很多朋友不会继续往下看(一头雾水看下去只能两头雾水,哈~),所以咱学习要遵循循环渐进,有些重点分开来重复讲解,虽然重复,但每次都会往下加深一点来让大家容易接受哈。

我们可以继续了,接下来是节表,也称为区块表:

节表(区块表):

PE文件中所有节的属性都被定义在节表中,节表由一系列的IMAGE_SECTION_HEADER结构排列而成,每个结构用来描述一个节,结构的排列顺序和它们描述的节在文件中的排列顺序是一致的。全部有效结构的最后以一个空的IMAGE_SECTION_HEADER结构作为结束,所以节表中总的IMAGE_SECTION_HEADER结构数量等于节的数量加一。节表总是被存放在紧接在PE文件头的地方。

另外,节表中 IMAGE_SECTION_HEADER 结构的总数总是由PE文件头 IMAGE_NT_HEADERS 结构中的 FileHeader.NumberOfSections 字段来指定的。

typedef struct _IMAGE_SECTION_HEADER

{

BYTE Name[IMAGE_SIZEOF_SHORT_NAME];     // 节表名称,如“.text”

//IMAGE_SIZEOF_SHORT_NAME=8

union
         {

DWORD PhysicalAddress;       
// 物理地址

DWORD VirtualSize;               
// 真实长度,这两个值是一个联合结构,可以使用其中的任何一个,一

// 般是取后一个

} Misc;

DWORD VirtualAddress;             
// 节区的 RVA 地址

DWORD SizeOfRawData;           
// 在文件中对齐后的尺寸

DWORD PointerToRawData;     
  // 在文件中的偏移量

DWORD PointerToRelocations;    
// 在OBJ文件中使用,重定位的偏移

DWORD PointerToLinenumbers;  
// 行号表的偏移(供调试使用地)

WORD NumberOfRelocations;     
// 在OBJ文件中使用,重定位项数目

WORD NumberOfLinenumbers;   
// 行号表中行号的数目

DWORD Characteristics;             
// 节属性如可读,可写,可执行等} IMAGE_SECTION_HEADER, *PIMAGE_SECTION_HEADER;

小甲鱼PE详解之区块表(节表)和区块(节)(PE详解04)的更多相关文章

  1. 小甲鱼PE详解之区块表(节表)和区块(节)续(PE详解05)

    这一讲我们结合实例来谈谈区块表的定义以及各个属性的含义. 首先,我们先用之前学过的一点知识在二进制文件中手动翻找区块表,这样做的好处是可以使你很快的对PE结构牢记于心.学来的东西就是能用的东西,不能用 ...

  2. 小甲鱼PE详解之区块描述、对齐值以及RVA详解(PE详解06)

    各种区块的描述: 很多朋友喜欢听小甲鱼的PE详解,因为他们觉得课堂上老师讲解的都是略略带过,绕得大家云里雾里~刚好小甲鱼文采也没课堂上的教授讲的那么好,只能以比较通俗的话语来给大家描述~ 通常,区块中 ...

  3. 小甲鱼PE详解之输入表(导出表)详解(PE详解09)

    小甲鱼PE详解之输出表(导出表)详解(PE详解09) 当PE 文件被执行的时候,Windows 加载器将文件装入内存并将导入表(Export Table) 登记的动态链接库(一般是DLL 格式)文件一 ...

  4. 小甲鱼PE详解之输入表(导入表)详解(PE详解07)

    捷径并不是把弯路改直了,而是帮你把岔道堵上! 走得弯路跟成长的速度是成正比的!不要害怕走上弯路,弯路会让你懂得更多,最终还是会在终点交汇! 岔路会将你引入万劫不复的深渊,并越走越深…… 在开始讲解输入 ...

  5. 小甲鱼PE详解之输入表(导入表)详解2(PE详解08)

    在此之前,我们已经对这个输入表进行了一些实践和理解,这有助于大家对这个概念更进一步的加深认识.小甲鱼觉得,越是复杂的问题我们应该越是去动手操作它,认识它,这样才容易熟悉它! 在上一节课我们像小鹿一样的 ...

  6. 小甲鱼PE详解之资源(PE详解11)

    原文出自:www.fishc.com 最近一直在安排第一届鱼C 学习班的事情,忙活了好一阵子,真是对不住大家,还大家久等了,这里要跟大家说声不好意思 ^_^ 今天我们来谈谈资源部分,资源部分可以说是 ...

  7. 小甲鱼PE详解之基址重定位详解(PE详解10)

    今天有一个朋友发短消息问我说“老师,为什么PE的格式要讲的这么这么细,这可不是一般的系哦”.其实之所以将PE结构放在解密系列继基础篇之后讲并且尽可能细致的讲,不是因为小甲鱼没事找事做,主要原因是因为P ...

  8. 小甲鱼PE详解之IMAGE_OPTIONAL_HEADER32 结构定义即各个属性的作用(PE详解03)

    咱接着往下讲解IMAGE_OPTIONAL_HEADER32 结构定义即各个属性的作用! (视频教程:http://fishc.com/a/shipin/jiemixilie/) 接着我们来谈谈 IM ...

  9. 小甲鱼PE详解之IMAGE_NT_HEADERS结构定义即各个属性的作用(PE详解02)

    PE Header 是PE相关结构NT映像头(IMAGE_NT_HEADER)的简称,里边包含着许多PE装载器用到的重要字段.下边小甲鱼将为大家详细讲解哈~ (视频教程:http://fishc.co ...

随机推荐

  1. WPF 操作键盘

    #region 打开键盘的键 const uint KEYEVENTF_EXTENDEDKEY = 0x1; const uint KEYEVENTF_KEYUP = 0x2; [DllImport( ...

  2. [Redis]c# redis缓存辅助类

    public static class RedisCache { private static IRedisClient RCClient = null; /// <summary> // ...

  3. 使用stty修改终端设置 stty 用法!

    在linux/unix平台上的 sqlplus中,如果输错了字符,要想删除,习惯性的按下backspace键后,发现非但没有删除想要删掉的字符,还多出了两个字符^H.当然,我们 可以同时按下ctrl+ ...

  4. virsh常用命令

    必须启动libvirtd,才能用virsh查看kvm后台. # systemctl start libvirtd 查看网络 # virsh net-list 启动default网络 # virsh n ...

  5. Ubuntu删除history记录

    history -c就是清除本次登录到目前所执行的命令 转自: http://www.linuxdiyf.com/viewarticle.php?id=189355

  6. cURL的几个经典实例

    1.cURL请求的基本步骤: (1)初始化 (2)设置选项,包括URL (3)执行并获取HTML文档内容 (4)释放cURL句柄 <?php //1.初始化 $ch = curl_init(); ...

  7. JavaScript String 对象方法

    String 对象方法 方法 描述 anchor() 创建 HTML 锚. big() 用大号字体显示字符串. blink() 显示闪动字符串. bold() 使用粗体显示字符串. charAt() ...

  8. linux下创建库函数

    来源: 在Linux下如何使用自己的库函数-riverok-ChinaUnix博客 http://blog.chinaunix.net/uid-21393885-id-88128.html 构建Lin ...

  9. 12.从上往下遍历二元树[LevelOrderOfBinaryTree]

    [题目] 输入一颗二元树,从上往下按层打印树的每个结点,同一层中按照从左往右的顺序打印. 例如输入 8    /  \   6    10  /\     /\ 5  7   9  11 输出8    ...

  10. codeforces A. K-Periodic Array 解题报告

    题目链接:http://codeforces.com/problemset/problem/371/A 题目意思:给出n和k和一个只有1或者2组成的序列,需要求出最少的改变次数,使得 n/k 组里面的 ...