本项目旨在以反恶意软件受保护进程轻量级(PPL)方式运行“任意*”进程,用于研究目的。(* 详见限制章节了解更多细节)
关于本项目的更多细节和设计动机,请参阅我写的这篇博客。
系统受保护进程是 Windows 中的一种安全模型,旨在保护系统和反病毒进程免遭篡改或内省,即使是管理员/SYSTEM 也无法对其进行操作。
以反恶意软件“受保护进程轻量级”(PPL)方式启动的进程在功能上受到限制,只能加载已签名的代码,且无法被非受保护进程调试、检查或终止。此外,它们还可以访问特殊数据,例如 Microsoft-Windows-Threat-Intelligence ETW 提供程序。
本项目创建了一个早期启动反恶意软件(ELAM)驱动程序和用户态服务。该服务在启动时会启动一个可配置的子进程,该子进程同样会被标记为 PPL。
子进程二进制文件必须使用与服务相同的证书进行签名,并满足其他一些限制,但除此之外可以是任意二进制文件和你选择的命令行参数。
说实话,我在解释 ELAM 和 PPL 是什么方面做得并不好,因此我建议从以下资料开始:
你可以从 Releases 获取预构建并已签名的 PPLRunner 服务和内核模块。发布包中还包含自动生成的证书和私钥,位于 .pfx 文件中,该文件受密码保护,密码为 password。我说过这仅供研究目的使用,对吧?
要生成并构建你自己的项目:
确保已安装 Windows SDK。
打开 generate_cert.ps1 和 sign_file.ps1,将 $password 变量改为其他值(两者必须一致)。
运行 generate_cert.ps1。这将生成一个包含新私钥和公钥证书的 ppl_runner.pfx 文件。
该证书将用于对 PPLRunner 使用的所有二进制文件进行签名。
构建 ppl_runner.sln。这将生成 3 个二进制文件:
包含证书信息的 ELAM 内核驱动程序。 该驱动程序实际上不执行任何操作,也不会被实际加载,它仅作为签名证书的载体使用。
服务安装程序和二进制文件。作为 PPL 服务,启动时它会以 PPL 方式启动一个子进程,然后停止并退出。
一个示例可执行文件,在构建时由 Visual Studio 使用正确的证书进行签名。 PPLRunner 几乎可以运行任何二进制文件,这只是一个会被自动签名的示例。
注意 仅在测试机器上安装,不要在生产环境/你的家用电脑上安装。
构建完成后,将 elam_driver.sys 和 ppl_runner.exe 复制到目标机器上的某个文件夹中。
在提升权限的命令提示符中运行以下命令以启用测试签名,然后重启:
bcdedit /set testsigning on
ppl_runner.exe install
这将安装一个名为 ppl_runner 的服务。
要对一个二进制文件进行签名以便运行,请使用 ppl_runner.pfx 证书对其进行签名,可以使用 sign_file.ps1 脚本,
或者直接自行运行 signtool.exe。如果你没有 signtool.exe,它位于 Windows SDK 中。
创建注册表项 HKLM\SOFTWARE\PPL_RUNNER。
将默认/空键设置为 REG_SZ,其中包含要执行的二进制文件的完整路径,
以及任何命令行参数。例如,从命令行执行:
REG.exe ADD HKLM\SOFTWARE\PPL_RUNNER /ve /t REG_SZ /d "C:\path\to\binay --argument 1"
要让服务启动该可执行文件,只需在提升权限的命令提示符中运行:
net start ppl_runner
作为 PPL 服务,启动后 ppl_runner 会读取注册表键,启动子进程,子进程同样作为 PPL,然后停止并退出。成功启动后仍会显示 the service failed to run,但如果你用 sc query ppl_runner 检查返回码,它应该是 0,即 ERROR_SUCCESS。
子进程将不会可见,但你可以使用调试输出和 DBGView.exe 获取某种形式的输出(参见 child_example 代码)。
由于该服务同时也是反恶意软件 PPL,因此只能由同样高权限的进程停止和删除。不过,我们可以使用 PPLRunner 来移除自身,只需将注册表键中的命令设置为:
C:\path\to\ppl_runner.exe remove
并运行该服务。即运行:
REG.exe ADD HKLM\SOFTWARE\PPL_RUNNER /ve /t REG_SZ /d "C:\path\to\ppl_runner.exe remove"
net start ppl_runner
testsigning 模式下有效。ppl_runner.exe install运行 Sysinternals 的 DBGView 并记录 Win32 Global,过滤 *[PPL_RUNNER]*。
这将显示来自服务和安装程序的所有日志。
待定 - Sealighter 博客
James Forshaw 创建了一个很棒的项目,用于将代码注入现有的 PPL 进程。
关注 Alex Ionescu 可能是深入了解 ELAM 和 PPL 的最佳方式。 或许可以从这篇文章开始: https://www.crowdstrike.com/blog/protected-processes-part-3-windows-pki-internals-signing-levels-scenarios-signers-root-keys/
关注 Matt Graeber 和 James Forshaw 也是很好的途径。
非常感谢 Matt 提供的 powershell 脚本,用于从证书中获取“待签名”(To-Be-Signed)哈希。