27、安全运行 PowerShell

安全运行 PowerShell

1. 应用程序控制

应用程序控制解决方案可防止未经授权的应用程序运行。第三方应用程序如 Trellix 可实现此功能,而 Windows 10 及更高版本自带两个内置应用程序:Windows Defender 应用程序控制(WDAC)和 AppLocker。这些工具可用于创建策略,强制实施允许执行的应用程序白名单,并阻止其他任何程序运行。由于 AppLocker 已停止开发,因此推荐使用 WDAC。这些解决方案适用于企业环境,支持集中控制,但目前尚未发现适用于 Linux 或 macOS 上 PowerShell 的类似解决方案。当 PowerShell 在默认的 WDAC 策略下运行时,借助语言模式功能,受信任的模块和脚本比不受信任的脚本拥有更多访问权限。

2. 语言模式

语言模式用于控制在受应用程序控制策略约束的 PowerShell 环境中脚本的运行方式。需要注意的是,网上有很多文章介绍如何使用变量设置语言模式,但这仅用于测试代码在特定模式下的行为,并不安全。根据微软的说法,使用语言模式实施安全策略的唯一方法是通过如 WDAC 这样的应用程序。语言模式有以下三种:
- FullLanguage :在未运行应用程序控制策略时,这是默认模式。
- ConstrainedLanguage :此模式可防止创建和使用某些 .NET 类型,并限制从 PowerShell 访问 C# 代码,同时也限制对 ScheduledJob 等功能的访问。许多脚本在受限语言模式下无法运行,需要进行签名,并且发布机构需添加到白名单中。
- NoLanguage :此模式会完全禁用 PowerShell 脚本编写,仅允许运行本地命令和 cmdlet,同时禁用 New - Object。

我们可以通过调用 $ExecutionContext.SessionState.LanguageMode 变量来检查会话的语言模式,示例如下:

# 检查当前语言模式
$ExecutionContext.SessionState.LanguageMode
# 设置语言模式为 ConstrainedLanguage
$ExecutionContext.SessionState.LanguageMode = 'ConstrainedLanguage'
# 再次检查语言模式
$ExecutionContext.SessionState.LanguageMode

在上述代码中,若尝试将语言模式从 ConstrainedLanguage 改回 FullLanguage 可能会失败,因为在 ConstrainedLanguage 模式下对变量的访问受限。解决方法是关闭会话并重新打开,语言模式将恢复为 FullLanguage 。但需注意,设置此变量并不能使 PowerShell 更安全。

3. 安全服务标准

PowerShell 遵循微软针对 Windows 的安全服务标准,因此在检测到漏洞时,某些功能会获得安全更新。不过,这些功能仅适用于 Windows,例如执行策略和应用程序控制。

4. 软件物料清单(SBOM)

软件物料清单(SBOM)通过识别软件创建过程中使用的每个资源,为软件提供透明度、完整性和标识。它还提供代码签名和软件标识,可用于将软件与已知漏洞关联起来。由于 2020 年的 SolarWinds 供应链攻击事件,许多政府要求使用 SBOM,此要求适用于 Windows 和 Linux/Mac。

5. Windows 反恶意软件扫描接口支持

PowerShell 将脚本块和 .NET 调用传递给 Windows 反恶意软件扫描接口(AMSI)API,以便反恶意软件应用程序(如 Windows Defender)可以检查其中是否存在恶意代码。这是仅适用于 Windows 的功能。

6. Secure Shell(SSH)远程连接

SSH 协议是一种加密协议,可在不安全的网络上支持安全的网络服务。它具有跨平台特性,可在 Windows、Linux 和 Mac 系统上使用。SSH 依赖于公钥加密技术,使用步骤如下:
1. 生成密钥对。
2. 将公钥传递到要远程连接的系统。
3. 打开会话时,指定本地机器上私钥的路径,SSH 会验证远程机器上的公钥是否与本地私钥配对。在整个过程中,私钥不会通过网络传输。虽然设置过程较为复杂,但设置完成后使用 SSH 非常方便。

7. 最小权限管理(JEA)

最小权限管理(JEA)是另一个仅适用于 Windows 的安全功能,它允许我们委托对可以通过 PowerShell 管理的事项进行管理,如域名服务(DNS)、Active Directory 和 Exchange 等应用程序。例如,我们可以让某人监控机器上的进程,但不能启动新进程。具体操作步骤如下:
1. 根据最小权限原则,配置仅能访问特定任务所需命令(如 Get - Process )的 PowerShell 端点,排除其他命令的运行权限,这样用户将无法运行 Start - Process
2. 配置端点使用虚拟特权账户,使用户无需拥有管理员账户即可运行命令,从而大幅减少拥有管理员特权账户的用户数量。

8. PowerShell 日志记录

PowerShell 有多种方式记录我们的操作,下面介绍三种常见的日志记录方式:
- Over the shoulder logging :使用 Start - Transcript Stop - Transcript cmdlet 可以记录会话的转录内容,该功能会记录屏幕上显示的所有内容,方便记录操作和输出结果并与他人共享。操作步骤如下:
1. 使用 -Path 参数设置转录文件的保存路径。
2. 使用 -Append 参数将内容添加到现有转录文件中,需指定现有转录文件的名称和路径。
3. 使用 -InvocationHeader 参数记录每个命令的运行时间。
4. 若要停止记录,使用 Stop - Transcript cmdlet。

在较旧版本的 PowerShell 中,开启转录功能较为复杂,且仅能记录控制台中的交互式会话。现在,在 Windows 系统中,我们可以通过组策略或编辑 $pshome 位置(在 Windows 中为 C:\Program Files\PowerShell\7 )的 powershell.config.json 文件来开启自动转录功能。编辑配置文件的方法适用于 Windows 和 Linux/Mac,但可能需要先创建该文件。若要启用转录功能,需在文件中添加以下 JSON 内容:

{
    "Transcription": {
        "EnableTranscripting": true,
        "EnableInvocationHeader": true,
        "OutputDirectory": "c:\\Temp\\MyTranscriptPath"
    }
}

若要停止转录,删除上述 JSON 条目即可。转录文件包含有用的头部信息,如会话运行的账户、是否使用了管理员等 RunAs 凭据、所使用的 PowerShell 版本以及进程编号。

graph LR
    A[开始转录] --> B[设置路径和参数]
    B --> C[运行命令]
    C --> D[停止转录]
  • Deep script block logging :当调用函数或脚本时,普通转录只会记录调用信息,而不会记录函数或脚本的内容。此时就需要深度脚本块日志记录功能,它会将脚本内容和其他相关信息记录到日志系统中。在 Windows 中,日志记录在事件查看器的 Applications and Services Logs 下的 PowerShellCore 日志中;在 Linux 中,记录在 /var/log/journal 下的 systemd 日志中。

    • 在 Windows 中,可通过组策略启用深度脚本块日志记录;若机器不在 Active Directory 域中,也可通过配置文件启用。编辑 PowerShell.config.json 文件时,需确保 JSON 语法正确,VS Code 会标记语法错误,保存文件时需要管理员权限。
    • 开启配置后,打开新会话并调用脚本(如 HelloWorld.ps1 ),事件日志中会显示相应事件,可从中查看脚本内容、运行账户、运行时间和运行机器等信息。
  • Module logging :模块日志记录与脚本块日志记录类似,用于跟踪 PowerShell 中加载和调用的模块。由于该功能可能会快速生成大量信息,因此可以选择仅记录指定的模块。若要记录所有模块,可在添加到配置文件的 JSON 中使用通配符 * 代替模块名称数组。同样,若有组策略可用,也可通过组策略启用模块日志记录。

编写安全代码

1. 安全存储密码

在编写脚本时,常常需要使用特定的凭据来运行命令。我们可以将凭据存储在 XML 文件中,示例如下:

# 获取凭据
$cred = Get - Credential
# 将凭据导出到 XML 文件
$cred | Export - Clixml Credential.xml

上述代码将凭据存储在 XML 对象中,该对象包含一个加密的标准字符串,即输入的密码,此加密基于账户和机器,具有可逆性。若要将密码保存为安全字符串,可按以下步骤操作:

# 定义密码字符串
$pwd = "ILovePowershell"
# 将密码转换为安全字符串
$securepwd = $pwd | ConvertTo - SecureString - AsPlainText - Force
# 将安全字符串转换为加密字符串
$encryptedpwd = $securepwd | ConvertFrom - SecureString
# 输出加密字符串
write - host $encryptedpwd

加密字符串可以存储在文件或注册表中,并用于创建 PSCredential 对象,示例如下:

# 将加密字符串添加到文件
Add - Content - Path encryptedpwd.txt - Value $encryptedpwd
# 从文件读取内容并转换为安全字符串
$securepwd2 = Get - Content - Path encryptedpwd.txt | ConvertTo - SecureString
# 创建 PSCredential 对象
$credential = New - Object System.Management.Automation.PSCredential("username", $securepwd2)
# 检查密码属性
$credential.GetNetworkCredential().Password

需要注意的是,加密字符串是经过加密的普通文本字符串,而安全字符串是 System.Security.SecureString 类型的对象,许多 PowerShell cmdlet 只接受 System.Security.SecureString 类型的密码,因此了解所需类型很重要。

2. 脚本签名

执行策略依赖于脚本签名来确定其可信度。数字签名有两个作用:一是确保脚本由受信任的来源签名,二是验证脚本在签名后未被编辑。要对脚本进行签名,我们需要以下类型的代码签名证书:
- 来自受信任机构(如 VeriSign)的代码签名证书,大多数计算机都会信任此类证书。
- 来自 Active Directory 证书颁发机构的证书,该目录内的机器会信任此类证书。
- 自签名证书,仅在用于签名脚本的机器上受信任。

获得代码签名证书后,可使用 Set - AuthenticodeSignature cmdlet 对脚本进行签名,签名包含脚本的哈希值,签名后对脚本所做的任何更改都会使签名失效,导致脚本不被信任。此签名功能仅适用于 Windows 环境。

3. 参数安全

我们可以使用加速器强制参数仅接受特定类型的输入,也可以使用正则表达式确保输入格式正确,如日期字符串或 IP 地址。以下代码用于测试参数是否为 DD/MM/YYYY 格式的日期字符串:

function Test - Date {
    param(
        [string]$date
    )
    if ($date -match "^(3[01]|[12][0-9]|0?[1-9])(\/|-)(1[0-2]|0?[1-9])\2([0-9]{2})?[0-9]{2}$") {
        return $true
    } else {
        return $false
    }
}

使用示例:

# 测试有效日期
Test - Date - date "01/01/2024"
# 测试无效日期
Test - Date - date "21/13/2023"

未经验证的参数可能会被用于恶意代码注入,通过参数验证可以有效防止此类情况发生。

安全运行 PowerShell

4. 总结与练习

前面介绍了 PowerShell 的多种安全特性和编写安全代码的方法。这些特性大多仅适用于 Windows 环境,Linux 和 macOS 的安全特性相对较少。下面总结一下学到的内容,并通过一些练习加深理解。

总结
  • PowerShell 安全特性 :包括应用程序控制、语言模式、安全服务标准、软件物料清单、Windows 反恶意软件扫描接口支持、SSH 远程连接、最小权限管理和日志记录等。
  • 编写安全代码 :涵盖安全存储密码、脚本签名和参数验证等技术。
练习
  1. 创建远程管理会话 :使用哪个 cmdlet 创建新的 PowerShell 远程管理会话?
  2. Linux 上的安全远程连接 :如何在 Linux 上安全地使用 PowerShell 远程连接?
  3. 执行策略 :PowerShell 中哪种执行策略仅允许运行已签名的脚本?
  4. 绕过执行策略 -ExecutionPolicy Bypass 开关的作用是什么?
  5. 恶意脚本分析 :在 Windows 上,什么可以用于分析和阻止已知的恶意脚本和配置?
  6. 受限语言模式 :PowerShell 中受限语言模式的目的是什么?
  7. 限制 cmdlet 使用 :如何在 Windows 上的 PowerShell 中限制特定用户对特定 cmdlet 的使用?
  8. 脚本块日志记录 :什么是 PowerShell 中的脚本块日志记录,为什么它对安全很重要?
  9. 安全字符串与加密字符串 :安全字符串和加密字符串有什么区别?

通过这些练习,可以进一步巩固对 PowerShell 安全知识的掌握。

相关知识补充

为了更好地理解和应用 PowerShell 的安全特性,下面提供一些相关知识的补充说明。

1. 语言模式的详细比较
语言模式 描述 适用场景
FullLanguage 默认模式,无应用程序控制策略时使用,脚本可自由运行 开发和测试环境
ConstrainedLanguage 限制某些 .NET 类型的创建和使用,限制对 C# 代码和部分功能的访问,脚本需签名 生产环境,提高安全性
NoLanguage 完全禁用 PowerShell 脚本编写,仅允许本地命令和 cmdlet 运行 对安全性要求极高的环境
2. 日志记录的重要性

日志记录在 PowerShell 安全中起着至关重要的作用,不同类型的日志记录有不同的用途:
- Over the shoulder logging :记录会话的所有操作和输出,方便事后审查和共享。
- Deep script block logging :记录脚本的具体内容,有助于发现潜在的安全问题。
- Module logging :跟踪模块的加载和调用,可用于监控系统活动。

3. 安全存储密码的注意事项

虽然将密码存储为加密字符串可以提高安全性,但仍需注意以下几点:
- 加密基于当前账户和机器,不能在其他机器上解密。
- 有人可以通过远程连接到 PowerShell 解密密码,因此需要确保机器的物理和网络安全。

4. 脚本签名的最佳实践
  • 尽量使用受信任机构颁发的代码签名证书,提高脚本的可信度。
  • 定期更新证书,确保签名的有效性。
  • 对重要脚本进行签名,防止被篡改。

流程图回顾

下面再次回顾一下 Over the shoulder logging 的流程图,帮助理解其操作流程。

graph LR
    A[开始转录] --> B[设置路径和参数]
    B --> C[运行命令]
    C --> D[停止转录]

这个流程图清晰地展示了 Over the shoulder logging 的操作步骤,从开始转录到设置参数,再到运行命令,最后停止转录。

总结

通过本文的介绍,我们了解了 PowerShell 的多种安全特性和编写安全代码的方法。在实际使用中,应根据具体需求选择合适的安全措施,确保 PowerShell 环境的安全性。同时,通过练习和相关知识的补充,不断巩固和提高对 PowerShell 安全的理解和应用能力。希望这些内容对大家有所帮助,让我们能够更安全地使用 PowerShell。

基于数据驱动的 Koopman 算子的递归神经网络模型线性化,用于纳米定位系统的预测控制研究(Matlab代码实现)内容概要:本文围绕“基于数据驱动的Koopman算子的递归神经网络模型线性化”展开,旨在研究纳米定位系统的预测控制方法。通过结合数据驱动技术与Koopman算子理论,将非线性系统动态近似为高维线性系统,进而利用递归神经网络(RNN)建模并实现系统行为的精确预测。文中详细阐述了模型构建流程、线性化策略及在预测控制中的集成应用,并提供了完整的Matlab代码实现,便于科研人员复现实验、优化算法并拓展至其他精密控制系统。该方法有效提升了纳米级定位系统的控制精度与动态响应性能。; 适合人群:具备自动控制、机器学习或信号处理背景,熟悉Matlab编程,从事精密仪器控制、智能制造或先进控制算法研究的研究生、科研人员及工程技术人员。; 使用场景及目标:①实现非线性动态系统的数据驱动线性化建模;②提升纳米定位平台的轨迹跟踪与预测控制性能;③为高精度控制系统提供可复现的Koopman-RNN融合解决方案; 阅读建议:建议结合Matlab代码逐段理解算法实现细节,重点关注Koopman观测矩阵构造、RNN训练流程与模型预测控制器(MPC)的集成方式,鼓励在实际硬件平台上验证并调整参数以适应具体应用场景。
评论
成就一亿技术人!
拼手气红包6.0元
还能输入1000个字符  | 博主筛选后可见
 
红包 添加红包
表情包 插入表情
 条评论被折叠 查看
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值