从挂起进程中提取干净Syscall:绕过EDR钩子的实用技巧

admin 2025-12-30 01:20:49 网络安全文章 来源:ZONE.CI 全球网 0 阅读模式

文章总结: 本文介绍利用挂起进程提取干净ntdll副本以绕过EDR用户态钩子的技术。因挂起时仅加载ntdll,攻击者可读取该干净副本覆盖当前进程被挂钩的.text段,恢复原始系统调用。文章详细阐述了查找基址、修改内存保护及复制代码的实现步骤,并结合加密Shellcode验证了实战效果,指出该法对部分EDR有效。 综合评分: 90 文章分类: 免杀,红队,恶意软件,实战经验


cover_image

从挂起进程中提取干净Syscall:绕过EDR钩子的实用技巧

Ots安全

2025年12月29日 12:08 广东

威胁简报

恶意软件

漏洞攻击

APT 组织和恶意软件开发者经常使用系统调用(简称 syscall)来绕过 EDR 等现代安全工具的钩子。基于系统调用分析的行为恶意软件检测技术已十分流行,但尽管系统调用提取技术众多,其中一些仍然难以被发现。

作为红队成员或安全研究人员,我们在开发攻击路径时经常使用系统调用。

例如,我们可以在开发的恶意程序中使用直接系统调用,但这存在问题。因为系统调用号在不同的 Windows 操作系统版本和服务版本之间有所不同,这迫使我们为每个版本编写不同的系统调用。虽然有一些工具可以自动完成这个过程,但 EDR 系统已经开始对这种技术发出警报。

我们还可以使用间接系统调用。对于这种调用方式,我们需要在运行时从磁盘获取 ntdll.dll 的句柄。为此,我们必须读取 ntdll 文件的字节,解析 .rdata 和 .text 段,并提取我们需要使用的系统调用函数。即使我们避免将系统调用硬编码到程序中,我们的行为仍然很可疑,因为我们获取了磁盘上 ntdll 的句柄并映射了其内容,而 EDR 已经开始对这种技术发出警告。

让我们尝试探索一种不同的技术,它可以帮助我们从挂起的进程中提取系统调用。我们将首先分析攻击路径,然后详细介绍如何实施攻击,最后——额外内容——看看如何更进一步。

攻击路径

我们需要想办法获取一份全新的 ntdll 副本,并将其复制到进程内存中,从而绕过 EDR 钩子。如下例所示,当 explorer.exe 处于活动进程状态时,可疑函数会被钩住。

jmp 指令会跳转到 EDR 的 DLL 文件进行检查。如果我们创建的线程是恶意线程,EDR 会将其标记出来。

但如果 explorer.exe 处于挂起状态会发生什么情况?

在下面的示例中,我们尝试了这种方法。我们以挂起状态打开了 explorer.exe,可以看到,加载到其中的唯一 DLL 文件是 ntdll。

为什么只有 ntdll 被加载?为什么其他 DLL 文件, 包括 EDR 文件,都没有被加载?根据StackOverflow 上的这个帖子, 最初只映射了 ntdll.dll,并且 APC 被排队等待线程恢复运行时执行。

这会调用 ntdll!LdrpInitializeProcess,该函数初始化执行环境(例如语言支持、堆、线程本地存储、KnownDlls 目录),加载 kernel32.dll,获取 BaseThreadInitThunk 的地址,并执行静态 DLL 导入。

让我们检查一下这次 NtCteateThreadEx 是否被钩住了。

不,并非如此!这仅仅是因为 EDR 的 DLL 在进程挂起时没有加载,从而生成了一个没有任何钩子的干净的 ntdll 副本。

因此,理论上,我们可以创建一个处于挂起状态的新进程,读取其内存,找到已加载的 ntdll,将其内存映射到我们已钩住的 ntdll,并获得一个没有任何钩子的全新副本。

发展攻击

现在我们有了理论,让我们看看它在实践中是如何运作的。

首先,我们创建一个处于挂起模式的新进程:

现在我们来查找 ntdll 基地址。这是必要的,因为我们创建的进程将是子进程。它将具有相同的 ntdll 基地址,这使我们能够使用相同的地址从挂起的进程中读取数据。

为了获取 ntdll 地址,我们使用一个简单的函数,该函数将遍历我们的 PEB,直到找到 ntdll 模块。

获取ntdll 的句柄 后,我们对其进行类型 转换并获取其基地址。

注意:某些 EDR 会挂载 PEB。发生这种情况时,存储在 PEB 中的基地址会发生变化。因此,尝试从 PEB 读取数据会将我们引入到由 EDR 控制的区域。

理论上,我们可以使用 EPROCESS 内核结构来找回原始的 ntdll 文件,因为它存储着可能有助于我们找到原始 ntdll 文件的重要信息。微软表示:“EPROCESS 结构是一个不透明的结构,它充当进程的进程对象。”

进一步研究表明,当使用 NtQuerySystemInformation 和以下类时:

SystemExtendedHandleInformation 和 SystemModuleInformation 可能会泄露 EPROCESS 内存地址。由于 EPROCESS 超出了本文的讨论范围,因此我不会深入探讨这个话题,尽管这方面有很多内容可以讨论。

获取 ntdll 基地址后,我们读取挂起进程中未被钩住的 ntdll 内存,并将其数据复制到缓冲区中。

但首先,我们需要声明 DOS 头文件、NT 头文件和可选头文件,以获取 NTDLL 的大小。

将内容复制到缓冲区后,我们将终止已暂停的进程,因为我们不再需要它了。

现在,剩下的唯一步骤就是遍历所有段,找到 .text 段的虚拟地址,将保护级别更改为PAGE_EXECUTE_READWRITE,并将新映射缓冲区 (newNtdllBuffer) 的 .text 段复制到原始的已钩入 ntdll 版本中。这将覆盖原有的钩子。攻击的这一部分最后一步是恢复原始保护级别。

将攻击进一步升级

这里的目标是将我们上面创建的内容结合起来,并成功地将其应用于 EDR。

我打算整合一个加密的 msfvenom calc shellcode。我会修改 GetModuleFromPEB 和 GetAPIFromPEBModule 函数,使其接受哈希值而不是 DLL 名称。然后它会遍历所有 DLL ,计算它们的哈希值,并将其与我们的哈希值进行比较。shellcode 会在运行时解密自身并加载到当前进程中。

结论

虽然这项技术并不新鲜,但研究这个主题让我发现了一些网上的POC(概念验证),我想分享一下我的看法。

在对某些 EDR 进行测试时,该技术有效地绕过了检测,解除了 ntdll 的钩子,并成功加载了 shellcode,但值得一提的是,某些 EDR 可能会标记此技术。

参考

  • https://blog.sektor7.net/#!res/2021/perunsfart.md
  • https://www.ired.team/offensive-security/defense-evasion/how-to-unhook-a-dll-using-c++

END

公众号内容都来自国外平台-所有文章可通过点击阅读原文到达原文地址或参考地址

排版 编辑 | Ots 小安

采集 翻译 | Ots Ai牛马

公众号 | AnQuan7 (Ots安全)


免责声明:

本文所载程序、技术方法仅面向合法合规的安全研究与教学场景,旨在提升网络安全防护能力,具有明确的技术研究属性。

任何单位或个人未经授权,将本文内容用于攻击、破坏等非法用途的,由此引发的全部法律责任、民事赔偿及连带责任,均由行为人独立承担,本站不承担任何连带责任。

本站内容均为技术交流与知识分享目的发布,若存在版权侵权或其他异议,请通过邮件联系处理,具体联系方式可点击页面上方的联系我

本文转载自:Ots安全 《从挂起进程中提取干净Syscall:绕过EDR钩子的实用技巧》

OWASP2025年十大漏洞 网络安全文章

OWASP2025年十大漏洞

文章总结: OWASP发布2025年十大Web应用安全风险,更新了排名以反映现代威胁。新增软件供应链风险和异常处理不当两个类别,访问控制失效、安全配置错误、加密
评论:0   参与:  0