简体   繁体   English

PE:在.txt部分末尾添加代码

[英]PE: Adding code at the end of .txt section

As I understand in PE file Virtual Size shows how much space it allocates for section during loading and Raw Size shows how big the section is on disk. 据我所知,在PE文件中,虚拟大小显示了在加载过程中为节分配了多少空间,而原始大小显示了该节在磁盘上的大小。

I came across to this executable which did the following: 我遇到了这个可执行文件,它执行了以下操作:

It subtracted the virtual size ( offset 0x8 ) from the raw data size ( offset 0x10 ) and made sure there was some space(for example 100 bytes). 它从原始数据大小( offset 0x10 )中减去虚拟大小( offset 0x8 ),并确保有一些空间(例如100个字节)。 At offset 0x14 from the text section header it found the offset in the file for the section itself. 在文本部分标题的偏移量0x14处,它在文件中找到了该部分本身的偏移量。 It added to this the virtual size, finding right where the section ends in the file. 它添加了虚拟大小,找到该部分在文件中结束的位置。 it copied some shellcode(which at the end eventually jumped to the original entry point of an executable to make sure original executable ran) to the end of the text section of the binary. 它复制了一些shellcode(它最终跳转到可执行文件的原始入口点以确保原始可执行文件运行)到二进制文本部分的末尾。

Now I'm little confused here, if the Virtual Size shows the exact space which will be allocated for executable, would not adding code at the end of .txt section overwrite some other data of executable and make it crash? 现在我对此感到困惑,如果虚拟大小显示将为可执行文件分配的确切空间,则不会在.txt部分末尾添加代码覆盖可执行文件的其他一些数据并使其崩溃? thanks. 谢谢。

Uhmmm, this hack code seems crafted to hide malicious code between sections. 嗯,这个黑客代码似乎精心设计隐藏各部分之间的恶意代码。

Going to your question, you are correct VirtualSize is the space really allocated in memory and RawSize is the the space used on disk to hold the section data. 回答你的问题,你是对的VirtualSize是在内存中真正分配的空间,RawSize是磁盘上用来保存段数据的空间。 What you missed is (from MS PECOFF spec): 您错过的是(来自MS PECOFF规范):

VirtualSize : The total size of the section when loaded into memory. VirtualSize :加载到内存中的部分的总大小。 If this value is greater than SizeOfRawData , the section is zero-padded. 如果此值大于SizeOfRawData ,则该部分为零填充。 This field is valid only for executable images and should be set to zero for object files. 此字段仅对可执行映像有效,对于目标文件应设置为零。

This means that if a the result of SizeOfRawData - VirtualSize is positive we have some space available on disk actually filled with 0's . 这意味着如果SizeOfRawData - VirtualSize的结果是肯定的,那么我们在磁盘上有一些空间实际上填充了0

If that space is enough to hold the malicious code then adding the start of text section on disk with the VirtualSize you can get the start of 0's padded area that can be used to copy the code. 如果该空间足以容纳恶意代码,然后使用VirtualSize在磁盘上添加文本开头部分,则可以获得可用于复制代码的0的填充区域的开头。

The rest is story... 剩下的就是故事......

This is a great question and illustrates a very important point (or you might say quirk) about how the Windows loader calculates memory sizes. 这是一个很好的问题,并说明了Windows加载程序如何计算内存大小的一个非常重要的一点(或者你可能会说是怪癖)。

The PE/COFF spec does indeed describe VirtualSize as "The total size of the section when loaded into memory". PE / COFF规范确实将VirtualSize描述为“加载到内存中时节的总大小”。 This is technically true if you consider total to be the total amount of REAL data that comprises the section, but it is not the total amount of memory Windows allocates for the section. 如果您认为总数是构成该部分的REAL数据的总量,则这在技术上是正确的,但它不是Windows为该部分分配的内存总量。 You'll find VirtualSize is often LESS than the amount Windows allocates for the section in memory because VirtualSize must be rounded UP to the nearest memory alignment value (set in the PE image). 您会发现VirtualSize通常比Windows为内存中的部分分配的数量少,因为VirtualSize必须四舍五入到最近的内存对齐值(在PE映像中设置)。

In other words, VirtualSize represents the unrounded size of the section while SizeOfRawData is the size of the data in the image file, but rounded up to the nearest file alignment padding value. 换句话说,VirtualSize表示节的未包围大小,而SizeOfRawData是图像文件中数据的大小,但向上舍入到最近的文件对齐填充值。 This is the reason VirtualSize is the better representation of the true "raw" size of the data, in memory or on disk. 这就是为什么VirtualSize更好地表示数据的真正“原始”大小,在内存或磁盘上。 The PE/COFF spec does not make this distinction. PE / COFF规范没有做出这种区分。 Why one is rounded in the image file and not the other probably has its ancient roots in backwards compatibility. 为什么一个在图像文件中被舍入而另一个可能在向后兼容性方面有其古老的根源。

This is precisely why your shellcode uses VirtualSize to find the "real" end of data even as it resides in the image file. 这正是您的shellcode使用VirtualSize查找数据的“真实”结束的原因,即使它位于图像文件中也是如此。 Not surprisingly, you can calculate SizeOfRawData by rounding VirtualSize up to the file alignment's value, at least in well formed PE files. 毫不奇怪,您可以通过将VirtualSize四舍五入到文件对齐的值来计算SizeOfRawData,至少在格式良好的PE文件中。

The shellcode simply used VirtualSize to find the end of the REAL code. shellcode只是使用VirtualSize来查找REAL代码的结尾。 Between there and SizeOfRawData bytes, are just unused padding zeroes, making it a prime spot to add new code without affecting the size of the file or breaking addressing offsets within the PE file. 在那里和SizeOfRawData字节之间,只是未使用的填充零,使其成为添加新代码的主要位置,而不会影响文件的大小或破坏PE文件中的寻址偏移。

In summary, the Windows loader essentially takes the VirtualSize value and rounds it up to the memory alignment value to get the real size of the memory allocation (and even this may be rounded up to the nearest 4k-minimum memory page). 总之,Windows加载器基本上采用VirtualSize值并将其四舍五入到内存对齐值以获得内存分配的实际大小(甚至可以将其四舍五入到最接近的4k最小内存页面)。 Then up to SizeOfRawData bytes are copied from the file to the beginning of the memory section. 然后将SizeOfRawData字节从文件复制到内存部分的开头。 If it is less than the size of the section in memory, the remainder is zero filled. 如果它小于内存中节的大小,则余数为零。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM