使用学习模式创建和优化 MXC 策略

Microsoft 执行容器 (MXC) 沙盒是默认拒绝方法,使包含的工作负荷只能使用其策略授予的文件、功能和其他资源。

但是,很难预测工作负荷可能需要访问的所有资源。 MXC 学习模式通过记录工作负荷尝试访问的资源,帮助你在 Windows 上创建最小特权策略,使你能够依据证据而非反复试错来创建或优化策略。

Note

学习模式目前可用于在 Windows 上的 MXC ProcessContainer 中运行的工作负载。 使用 运行时检测 确认主机上的 ProcessContainer 支持。

选择学习模式行为

学习模式有两种工作方式。 它们的区别在于 MXC 是否在记录访问时继续强制执行策略,这决定了应当由谁在何时使用各自的模式。

特性 拒绝并记录 允许并记录
未授予访问权限 已阻止并记录 已允许并已记录
策略执行 强制执行,但捕获可以更改隔离层 已对本次运行放宽默认拒绝策略
典型用户 应用开发人员和策略作者 评估现有工作负荷的 IT 管理员和开发人员
何时使用它 开发应用及其策略时 在策略构建之前,了解受信任工作负荷可访问的内容
捕获 mode 值 block(默认值) allow

拒绝并记录:开发应用和策略

开发应用或代理及其 MXC 策略时使用拒绝和记录(learningModeLogging)。 MXC 在记录时会持续强制执行策略,因此未授予的访问会像面向你的用户时一样失败。 学习模式添加策略阻止的每个访问的记录。 在某些主机上,捕获会更改 MXC 选择的隔离层。 有关详细信息,请参阅规划捕获先决条件。

常见用途包括:

  • 诊断包含的工作负荷失败的原因,并将缺少的授权与不相关的错误区分开来。
  • 反复修改策略草案,直到支持的方案成功,负向测试仍然失败。
  • 标识工作负载请求的功能。
  • 让你的应用的用户配置自己的沙盒。 你的应用记录被阻止的内容,在自己的 UI 中呈现它,并且仅在用户批准更改后重新生成策略。

由于 MXC 不断强制实施策略,因此拒绝和记录是更安全的选择。 每当有需要测试的策略时都可以使用它,即使该策略尚不完整。

允许和记录:在创建策略之前评估现有工作负荷

在向其应用 MXC 策略之前,当您需要了解现有受信任的工作负载会访问哪些内容时,请使用“允许并记录”(permissiveLearningMode)。 例如,IT 管理员可以在测试设备上按典型任务流程运行业务线工具或脚本,然后在启用强制之前使用结果创建基线策略。 将现有工具引入 MXC 的开发人员可以使用相同的方法来起草第一个策略。

允许并记录对该运行放宽默认拒绝策略的强制执行,因此,将工作负荷视为以用户的完整权限运行。 MXC 记录策略本应拒绝的每次访问。 每当此模式处于活动状态时,MXC 也会连同运行结果一起返回安全警告。 主机应显示该警告,而不是将其丢弃。

在使用“允许并记录”之前:

  • 仅在受控测试设备或帐户上,使用具有代表性的非敏感数据运行受信任的代码。
  • 执行工作负荷的典型任务。 运行未执行的访问不会显示在结果中。
  • 将结果视为起始清单。 移除不必要的授权,然后在部署策略之前使用“拒绝并记录”验证策略草案。

重要

不要将“允许并记录”学习模式公开为智能体可调用的生产工具。 受信任的主机代码或人员必须批准其使用以及任何由此产生的权限扩展。

规划捕获先决条件

MXC 通过两个捕获路径之一收集学习模式结果。 它根据主机和请求的策略在运行时选择路径。 这适用于任一模式下的 captureDenials,并适用于 wxc-exec.exe --audit 工作流。

捕获路径 当 MXC 使用它时 隔离级别 海拔
原生捕获 Windows提供 MXC 所需的进程安全环境和学习模式 API,并且可以表示请求的策略 BaseContainer 无
受保护的捕获 本机捕获不可用或无法表示请求的策略 兼容的 AppContainer 层 MXC 以提升权限启动已签名的帮助程序 plm.exe,以记录 Windows 性能记录器(WPR)跟踪。 用户必须批准 UAC 提示符或提供管理员凭据。

本机捕获不能表示某些策略,例如 processContainer.leastPrivilege、某些网络代理配置,以及在本机不支持拒绝路径的主机上设置的拒绝路径。 这些请求即使在支持本机捕获的主机上也使用受保护的捕获。 如果两个路径都不能保留完整策略,MXC 将返回错误,而不是削弱策略或跳过捕获。

若要找出请求将使用的路径,请在启动请求之前在启用捕获的情况下探测该请求。 探针不会创建容器。

SDK Call 要检查的结果
.NET MxcContainer.Probe(request) Tier、Probes.NativeCaptureAvailable、Probes.GuardedCaptureAvailable
TypeScript probe(request) tier、probes.nativeCaptureAvailable、probes.guardedCaptureAvailable
Rust v1::probe(Some(&request)) tier、probes.native_capture_available、probes.guarded_capture_available

BaseContainer 层级表示本机捕获。 AppContainer 层表示受保护的捕获和提升提示。 本机捕获事实描述的是主机,而不是你的请求,因此也应检查该层级。

考虑这些差异:

  • 在应用中,在开始捕获之前进行探测,并在捕获需要管理员批准时告知用户。 不要假设捕获会在每个主机上静默运行。
  • 当 IT 管理员评估工作负荷时,请确认测试设备支持本机捕获,或者管理员可以批准受保护的捕获提示。 AppContainer 层还可能需要做好主机准备工作。
  • 将捕获结果视为策略编写的证据。 由于受保护的捕获可以在与生产层不同的层上运行工作负荷,因此请通过不使用捕获的运行来确认最终策略。

示例:通过 MXC SDK 启用捕获

当应用托管工作负荷时,请使用 SDK 捕获。 若要在不编写主机代码的情况下评估工作负荷,请参阅 从命令行使用学习模式。

从 SDK 快速入门开始,包括拒绝写入的情况。 以下片段扩展了该示例,并使用相同的工作负荷和资源授予。 在 SDK 启动工作负荷之前立即插入所选片段。

这些示例使用 MXC 1.0 V1 SDK API。 在每个 SDK 中,需要在显式 ProcessContainer 包含选择上配置捕获,这将取代快速入门中的抽象进程意图。

为捕获创建主机所有的输出目录。 它不需要由包含的工作负载写入。

对请求中的显式 ProcessContainer 包含设置捕获选项:

string captureDirectory = Path.GetFullPath("captures");
Directory.CreateDirectory(captureDirectory);

request.Containment = new Containment.ProcessContainer
{
    CaptureDenials = new CaptureDenialsPolicy
    {
        Mode = CaptureDenialsMode.Block,
        OutputPath = Path.Combine(captureDirectory, "denials.json"),
    },
};

在 block 模式下,拒绝写入的情况仍然失败。 捕获拒绝不会授予写入权限。 对于经批准的“允许并记录”运行,请仅在 C# 中将模式更改为 CaptureDenialsMode.Allow、在 TypeScript 中更改为 'allow',在 Rust 中更改为 CaptureDenialsMode::Allow。

调整现有集成时,保留其他包含设置。 使用专用捕获选项,而不是保留的内部 learningModeLogging 或 permissiveLearningMode 能力名称。

找到已完成的捕获

等待执行和捕获完成后,再读取结果。 MXC 将唯一运行标识符插入已配置的文件名中,因此 denials.json 会成为一个名称,例如 denials.<run-id>.json。 使用报告的路径,而不是猜测它或扫描以查找最新的文件。

在 result.Warnings 完成并且你报告了 MxcContainer.RunAsync(request) 后,检查结果元数据:

if (result.OutputMetadata?.CaptureDenialsError is { } captureError)
{
    Console.Error.WriteLine($"Denial capture failed: {captureError.Message}");
    return 1;
}

if (result.OutputMetadata?.CaptureDenials is not { } capture)
{
    Console.Error.WriteLine("The run did not produce denial capture metadata.");
    return 1;
}

Console.WriteLine($"Denial document: {capture.OutputPath}");
Console.WriteLine($"Unique denials: {capture.TotalDenials}");
if (capture.DeniedResourcesTruncated)
{
    Console.Error.WriteLine("The capture is incomplete; don't generate a policy from this run.");
    return 1;
}

保留快速入门中对退出状态、超时和 result.Warnings 的处理。 特别是,.NET SDK 会发出有关宽松学习模式的警告,而不是自动将这些警告输出到终端。

如果使用流式执行,请在终端中等待完成后再检查 MxcProcess.OutputMetadata。 在不等待的情况下处置该进程并不能替代捕获完成。

读取拒绝输出

可操作的 JSON 文档用于标识资源、尝试的访问和摘要。 对于快速入门的拒绝写入案例,代表性条目如下所示:

{
  "denials": [
    {
      "resource": "C:\\src\\MxcQuickstart\\workspace\\input\\blocked.txt",
      "resourceType": "file",
      "accessType": "write",
      "pid": 1234,
      "filetime": "132847890123456789"
    }
  ],
  "summary": {
    "exitCode": 1,
    "totalDenials": 1,
    "deniedResourcesTruncated": false
  }
}

该文档是策略编写的证据,而不是工作负载所做一切的详尽日志。 resourceType 值确定如何读取 resource。 例如,一个 file 条目包含绝对路径,一 capability 个条目包含一个功能名称,例如 internetClient。 某些发现无法表示为策略授权,单个输入也无法覆盖所有代码路径。

在允许模式下,文档目前不包括功能请求。 以 deny 和 record 模式运行工作负荷,以确定其所需的功能。

如果true是deniedResourcesTruncated,则不要从该运行生成策略。 空文档同样不能证明工作负荷是安全的,也不能证明每项预期的限制都已得到验证。

MXC 还会在可操作文档旁边写入详细日志文件。 示例:denials.<run-id>.json 生成 denials.<run-id>.verbose.json。 详细文件是一份有界的、已脱敏的诊断记录,其中包括 MXC 策略无法处理的观测项,例如注册表写入。 输出元数据不报告其路径,因此请从可操作文档的路径中派生出它的路径。 使用详细文件来调查可操作文档未能解释的故障,而不要将其用作授予项列表。

区分拒绝与其他失败

结果 怎么办
MXC 拒绝该配置 检查架构、字段组合和所选后端。 不要为了绕过无效请求而授予更多访问权限。
后端或捕获功能不可用 检查支持信息和捕获先决条件。 不要以无提示方式禁用所需的限制。
工作负荷在强制执行的情况下失败 查看其退出状态、错误输出和已完成的拒绝捕获。 工作负荷失败不一定是资源拒绝。
捕获失败或不完整 将证据视为不可用或不完整,即使工作负载已成功退出。

结构化捕获收集可操作文档。 较低级别的 ProcessContainer learningMode 设置支持记录“拒绝并记录”事件,但其本身不会收集此文档。 当主机需要使用证据时使用捕获。

审阅观察到的访问

在更改策略之前对每个结果进行分类。 例如:

Finding 潜在措施
所需的输入文件 添加覆盖它的最窄只读路径
所需的输出或缓存 添加特定于任务的读写路径
凭据或不相关的用户文件 根据需要将其保持拒绝状态并更改工作负荷
宽泛的父目录 标识所需的子路径,而不是授予父路径
意外的网络、UI 或功能请求 在授予访问权限之前,先验证该工作负载为何需要它
MXC 无法在策略中表达的资源 更改工作负荷或选择可以强制实施要求的后端

观察到的访问可能来自启动、发现、可选功能、错误处理或一次运行中使用的特定输入。 不要假设每个请求都是必需的。 在快速入门的负面测试中,被拒绝的写入是预期结果,而不是缺少权限。

示例:从命令行使用学习模式

若要在不编写主机代码的情况下评估工作负荷,请使用 wxc-exec.exe 命令行工具和 JSON 配置运行它。 有关配置格式,请参阅编写并验证 MXC 策略。

安装 MXC SDK 包不会将 wxc-exec.exe 添加到 PATH 中。 从与 SDK 版本匹配的 mxc-release-binaries.zip 下载 ,并通过其完整路径运行该工具。 以下示例假定已将存档解压缩到 C:\Tools\Mxc 并使用 x64 文件夹。 在 Arm64 设备上,使用 arm64 文件夹。

使用任一行为进行捕获

选择 ProcessContainer 容器,并将 captureDenials 添加到配置的 processContainer 部分。 例如,评估没有策略的工作负荷的 IT 管理员可以使用模式 allow:

{
  "$schema": "https://raw.githubusercontent.com/microsoft/mxc/main/schemas/stable/mxc-config.schema.1.0.0.json",
  "version": "1.0.0",
  "containment": "processcontainer",
  "process": {
    "commandLine": "C:\\Tools\\Contoso\\ReportTool.exe"
  },
  "processContainer": {
    "captureDenials": {
      "mode": "allow",
      "outputPath": "C:\\MxcAudit\\denials.json"
    }
  }
}

在运行之前创建输出目录,然后将配置文件传递给该工具:

C:\Tools\Mxc\x64\wxc-exec.exe audit-config.json

运行后,wxc-exec向标准错误写入一行 JSON,其中包含实际输出路径和摘要:

{"type":"captureDenials","outputPath":"C:\\MxcAudit\\denials.<run-id>.json","exitCode":0,"totalDenials":2,"deniedResourcesTruncated":false}

使用所报告的路径读取文档。 若要在强制执行的情况下验证策略草案,请将授予项添加到配置中,并将模式更改为 block。

提出一个调整后的配置

对于由开发人员驱动的策略编写,审核工作流执行“允许并记录”的捕获流程,并建议修改后的配置:

C:\Tools\Mxc\x64\wxc-exec.exe --audit --config <path-to-config>

审核工作流写入拒绝文档、跟踪文件、源配置的快照,以及一个 Adjusted_*.json 文件,用于将观察到的访问合并到该配置中。 调整后的配置是供审核的提议,而不是已批准的策略。 截断捕获时,MXC 不会生成它,SDK 捕获根本不生成它。

审核工作流仅支持 ProcessContainer。 不要将 processContainer.captureDenials 与显式的 --audit 设置结合使用。 有关完整的 CLI 和 SDK 协定,请参阅GitHub 上的学习模式功能。

完成学习循环

使用此工作流从发现阶段过渡到强制执行的策略:

  1. 选择包含模型,然后启用学习模式。
  2. 如果工作负荷尚没有策略,并且你无法直接编写存在限制的策略,请在受控环境中以“允许并记录”模式运行它。 执行其典型任务。
  3. 根据证据起草一项范围狭窄的政策,并移除广泛且无关的授权。
  4. 在策略草案下以“拒绝并记录”模式运行工作负荷,并解决剩余的拒绝项,包括所需的功能。
  5. 重复使用具有代表性的成功、失败和边缘用例输入。
  6. 移除所有学习、捕获和审核设置,并运行最终的强制执行测试。 捕获可以更改 MXC 选择的隔离层,因此此运行会确认策略在生产中的行为方式。

当支持的工作负荷成功且负测试仍按预期失败时停止扩展访问权限。

编码智能体有助于解释观察结果,但请确保审阅并批准对资源访问策略所做的任何更改。