如何使用应用控件保护 PowerShell

本文介绍如何设置 适用于企业的 应用控制策略。 可以将策略配置为强制执行策略规则或审核策略规则。 在审核模式下,PowerShell 行为不会发生变化,但它会将事件 ID 16387 消息记录到 PowerShellCore/Analytic 事件日志。 在强制模式下,PowerShell 会应用策略的限制条件。

本文假设你使用的是测试计算机,以便在环境中部署策略之前,可以在计算机范围的应用控制策略下测试 PowerShell 行为。

创建应用控制策略

XML 文件中介绍了应用控制策略,其中包含有关策略选项、允许的文件以及策略识别的签名证书的信息。 应用策略后,仅允许加载和运行已批准的文件。 PowerShell 会阻止未经批准的脚本文件运行或在 ConstrainedLanguage 模式下运行这些文件,具体取决于策略选项。

使用 ConfigCI 模块创建和操作应用控制策略,该模块适用于所有受支持的 Windows 版本。 此 Windows PowerShell 模块可在 Windows PowerShell 5.1 或 PowerShell 7 中通过 Windows 兼容性层使用。 在 Windows PowerShell 中使用此模块会更简单。 创建的策略可应用于任何版本的 PowerShell。

创建应用控制策略的步骤

若要进行测试,只需创建默认策略和自签名代码签名证书。

  1. 创建默认策略

    New-CIPolicy -Level PcaCertificate -FilePath .\SystemCIPolicy.xml -UserPEs
    

    此命令會创建一个名为 SystemCIPolicy.xml 的默认策略文件,允许运行所有 Microsoft 代码签名的文件。

    注意

    此命令会扫描整个测试计算机,因此运行此命令最多可能需要两个小时。

  2. 禁用默认策略中的审核模式

    始终在 Audit 模式下创建新策略。 若要测试策略的强制实施情况,需要在应用策略时禁用审核模式。 使用文本编辑器(如 notepad.exe 或 Visual Studio Code [VS Code])编辑 SystemCIPolicy.xml 文件。 注释禁止 Audit mode 选项。

    <!--
    <Rule>
      <Option>Enabled:Audit Mode</Option>
    </Rule>
    -->
    
  3. 创建自签名代码签名证书

    需要一个代码签名证书来对要在测试计算机上运行的测试二进制文件或脚本文件进行签名。 New-SelfSignedCertificatePKI 模块提供。 为了获得最佳效果,请在 Windows PowerShell 5.1 中运行此命令。

    $newSelfSignedCertificateSplat = @{
        DnsName = $env:COMPUTERNAME
        CertStoreLocation = "Cert:\CurrentUser\My\"
        Type = 'CodeSigningCert'
    }
    $cert = New-SelfSignedCertificate @newSelfSignedCertificateSplat
    Export-Certificate -Cert $cert -FilePath c:\certs\signing.cer
    Import-Certificate -FilePath C:\certs\signing.cer -CertStoreLocation "Cert:\CurrentUser\Root\"
    $cert = Get-ChildItem Cert:\CurrentUser\My\ -CodeSigningCert
    
    dir c:\bin\powershell\pwsh.exe | Set-AuthenticodeSignature -Certificate $cert
    
  4. 将代码签名证书添加至策略

    使用以下命令将新的代码签名证书添加至策略。

    Add-SignerRule -FilePath .\SystemCIPolicy.xml -CertificatePath c:\certs\signing.cer -User
    
  5. 将 XML 策略文件转换为策略强制实施二进制文件

    最后,需要将 XML 文件转换为应用策略时由应用控件使用的二进制文件。

    ConvertFrom-CIPolicy -XmlFilePath .\SystemCIPolicy.xml -BinaryFilePath .\SIPolicy.p7b
    
  6. 应用应用控制策略

    若要将策略应用到测试计算机,请将 SIPolicy.p7b 文件复制到所需的系统位置 C:\Windows\System32\CodeIntegrity

    注意

    部分策略定义必须复制到子文件夹,例如 C:\Windows\System32\CodeIntegrity\CiPolicies。 有关详细信息,请参阅 应用控制管理员提示和已知问题

  7. 禁用应用控制策略

    若要禁用策略,请重命名 SIPolicy.p7b 文件。 如果需要执行更多测试,可以更改回原名称以重新启用策略。

    Rename-Item -Path .\SIPolicy.p7b -NewName .\SIPolicy.p7b.off
    

使用应用控制策略审核进行测试

PowerShell 7.4 添加了一项新功能,用于在审核模式下支持应用控制策略。 在审核模式下,PowerShell 在 ConstrainedLanguage 模式下运行不受信任的脚本且没有任何错误,但会将消息记录到事件日志中。 日志消息描述了如果策略处于“强制”模式,将应用哪些限制。

查看审核事件

PowerShell 将审核事件记录到 PowerShellCore/分析事件日志中。 默认情况下未启用日志。 若要启用日志,请打开 Windows 事件查看器,右键单击 PowerShellCore/Analytic 日志并选择“启用日志”。

或者,可以从权限提升的 PowerShell 会话运行以下命令。

wevtutil.exe sl PowerShellCore/Analytic /enabled:true /quiet

可以在 Windows 事件查看器中查看事件,也可以使用 Get-WinEvent cmdlet 检索事件。

Get-WinEvent -LogName PowerShellCore/Analytic -Oldest |
    Where-Object Id -eq 16387 | Format-List
TimeCreated  : 4/19/2023 10:11:07 AM
ProviderName : PowerShellCore
Id           : 16387
Message      : App Control Audit.

    Title: Method or Property Invocation
    Message: Method or Property 'WriteLine' on type 'System.Console' invocation will not
        be allowed in ConstrainedLanguage mode.
        At C:\scripts\Test1.ps1:3 char:1
        + [System.Console]::WriteLine("pwnd!")
        + ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
    FullyQualifiedId: MethodOrPropertyInvocationNotAllowed

事件消息包括将应用限制的脚本位置。 此信息可帮助你了解需要更改脚本的位置,使其在应用控制策略下运行。

重要

查看审核事件后,应禁用分析日志。 分析日志增长迅速,占用大量磁盘空间。

在 PowerShell 调试器中查看审核事件

如果将交互式 PowerShell 会话的 $DebugPreference 变量设置为 Break,则 PowerShell 将中断至发生审核事件的脚本中当前位置的命令行脚本调试器。 使用断点可以调试代码并实时检查脚本的当前状态。