大家好! 与“逆向工程”课程的启动有关,我们举办了有计划的公开课。 它在加载的不同阶段分解了bootkit操作算法 。
讲师-卡巴斯基实验室病毒分析师
Arthur Pakulov 。
以下文章是介绍性文章,并且是该课程的一部分的纯文本版本,专门用于bootkit安装程序。 有关bootkit本身的详细分析,请参见视频。 引导程序包是一个恶意程序,会修改主引导记录,即第一个物理磁盘或引导扇区VBR的第一个扇区。 这类程序基本上具有Trojan功能,可用于执行系统中的任何隐藏操作。 在我们的示例中,bootkit将特权提升至系统级别的进程,该进程的名称以字母序列“ inte”开头。 实际上,bootkit是在0保护环中开始工作的rootkit,该保护环甚至在操作系统开始加载之前就已启动。 因此,他对研究产生了极大的兴趣。
要开发这样的程序,通常的逆向工程技能还不够。 仅仅能够阅读清单是不够的,您还需要了解处理器架构,内存寻址等内容。我们在一个公开课程中研究了Bootkit的关键位置。
为了工作,准备了一个特殊的示例bootkit-xp.exe,可在Windows XP下运行。 因此,除了研究bootkit之外,我们还对该操作系统有些怀旧。 但是总的来说,选择OS XP是为了使其更容易反转,因为XP具有很好的可视化效果并且没有不必要的复杂性。 好吧,根据其代码判断,该示例是专门为此操作系统编写的。
这
是bootkit安装程序的样子 :

仅查看它,您就可以得出某些结论。 例如,很明显该文件的重量很小。 如果查看入口点,则可以看到该代码正在接收文件描述符,该文件描述符具有指向第一个物理磁盘的符号链接的名称-“ PhysicalDrive0”:

此外,为了便于识别代码,我们
切换到IDA 。 很明显,对于典型的木马而言,可用功能很小。 甚至导入表也很小:

这种图像通常在分析包装样品时出现。 但是,在我们的情况下,该文件看起来并不打包。 事实证明,该示例要么被某个保护器/加密器所覆盖,并且在其工作过程中以动态方式接收功能的地址,然后调用所需的功能,否则一切都很好,并且示例保持原样。
我们继续探索代码。

正如我们在HIEW中看到的那样,使用一个有趣的参数作为第一个参数调用了
CreateFileA函数。 在这里,应该回顾一下诸如
内核对象之类的东西。 它们不能直接从用户模式进行操作,它们是由操作系统的内核控制的。 在用户模式下,程序只能发出请求以接收/更改任何内核对象的状态。 为了向系统指示程序将使用哪个特定的内核对象,需要获取所需内核对象的句柄。 在收到请求后,如果所有检查都通过,则操作系统将把
所请求的OA的
句柄返回给我们。 并且已经使用了handle,我们可以使用关联的OA。
因此,在上图中,使用CreateFile,符号链接被访问到第一个连接的物理硬盘。 如果授予访问权限,则可以像处理其他任何简单文件一样使用“文件”。 即,整个硬盘将显示为单个大文件。
因此,让我们继续。 句柄又回来了,我们发现自己在这里:

接下来会发生什么? 然后,
ReadFile函数读取前0x200字节。 而且我们在第一个物理磁盘的第一个扇区。

您可能已经猜到了,这是
主引导记录 (MBR)。 MBR由3部分组成:代码部分,分区表和签名。 在正常情况下,BIOS将MBR读入内存中的地址0:0x7c00h,并将控制权传递给它。 因此,MBR的代码部分开始执行。 在执行期间,它解析分区表,找到启动扇区并加载它。 对于引导程序,如果MBR被覆盖,则其代码现在将获得控制。
好的,已读取MBR,
下一步是
什么 ? 然后,bootkit再次以写访问模式打开PhysicalDrive0。

接下来,将指针设置在第600个偏移处。 即,
原始扇区被读取并复制到第三扇区 。
为什么要备份一个扇区? 显然,这对于将来将需要它是必要的。
然后循环开始。 自然地,看着代码,人们只能注意var_1C,
1BEh等常量。 并且,与此同时,位于上方的MBR结构应在内存中刷新。 特别是,我们对“偏移”列感兴趣。

请参阅,第一个扇区的读取缓冲区在
lpBuffer中 。 然后将
1BEh添加到其中,实际上指针指向分区表的开头。 从表到扇区末尾的所有数据均从相同的偏移量-1BE开始插入_marked_bytes中。

也就是说,原始MBR的第二部分和第三部分被插入
_marked_bytes中 。
接下来会发生什么?
然后SetFilePointer将指针设置为“文件”的开头,即MBR。

然后是一个写入(WriteFile),形成了
_marked_bytes并释放了内存。 至此,bootkit安装程序的功能结束。
但是很高兴
看到 _marked_bytes的第一部分
到底是
什么 。 为此,请将其转储到磁盘并进行分析。 引起您注意的第一件事是地址0x413处的变量内容减少了2。

如果查看技术文档,您会发现0X413变量包含以千字节为单位安装的物理内存量。 因此,bootkit代码“切断”了两千字节的内存:

现在,为了不做进一步的工作,将考虑比以前少2 KB的内存。 为什么-尚不清楚。
接下来,使用6位按位左移
来计算物理地址到“位关闭”存储器中:

移位6一次执行两个操作-将千字节转换为字节(将变量的值乘以2 ^ 10),从而获得被咬掉的内存的物理地址,并从中提取段号,将结果除以0x10(2 ^ 4)。
之后,您的身体将被复制到这一块内存中,并且由于bootkit代码位于“ bit off”部分中,因此
没有人会进一步干扰它 。 此外,中断不会改变该存储区中写入的内容。 我们可以说该
代码对于系统几乎是不可见的 ,就像那里没有内存一样。
这仅仅是bootkit的开始。 然后将进行中断拦截,ntldr签名跟踪,操作系统内核模块的修改等。
因此,我们不会破坏它,最好
观看网络研讨会的结尾,以免错过任何内容。