AOS Capsule 安全设计详解:信任边界、边缘校验、Fail-Closed 语义、资源限制与对抗式评审
【免费下载链接】aos-ceAOS Community Edition: the open agent operating system.项目地址https://gitcode.com/gh_mirrors/ao/aos-ce点击查看免费下载本文以 AOS Community Edition 作者手册中的 security 章节capsules/capsule-forge/src/guides/security.md为主体系统讲解在 AOSUnicity AOS上开发 capsule 时的安全工程方法哪些输入必须视为不可信、如何在 capsule 边缘做防御性校验、策略链为何必须 fail-closed、如何在有限的运行时资源边界内设计、如何隔离 principal、如何管理供应链与安装信任以及按后果严重程度分层做评估和对抗式代码评审的完整问题清单。读完后你应当能够为自研 capsule 建立一套可验证的“边界 门控”设计并对照仓库中的真实实现capsule-forge、aos-mcp-broker逐条核对。这份指南在仓库中的位置与阅读方式security 章节是 capsule-forge 内置的“作者手册”author manual之一。从源码结构看capsules/capsule-forge/src/lib.rs 中定义了GUIDE_CHAPTERS静态章节表每个章节通过include_str!将 Markdown 文件编译进 capsule 二进制// capsules/capsule-forge/src/lib.rs GuideChapter { topic: security, summary: untrusted inputs, failure semantics, limits, reliability, evaluation, and review, content: include_str!(guides/security.md), },模型或开发者可以通过forge_guide工具以topic: security按需加载该章节而不是把整本手册一次性塞进上下文——这是一种渐进式信息披露progressive disclosure的设计。capsules/capsule-forge/src/lib.rs 中的测试author_manual_is_progressive_and_complete还强制要求每一章正文不少于 35 行即“不允许把安全章节写薄”。这一点值得借鉴安全指南本身也被当作需要被测试守护的产品资产。capsule-forge 自身的清单 capsules/capsule-forge/Capsule.toml 也是一个最小化的能力示例只声明fs_read [home://]加上工具总线必需的 publish/subscribe ACL 条目tool.v1.execute.*.result等体现了“能力即显式授权”的基本盘。信任边界先划定“什么是不可信的”指南的第一节给出了一份明确的不可信输入清单。除非内核或运维方operator另有证明以下对象一律按不可信处理LLM 的工具参数与提示文本tool arguments and prompt textcapsule 清单manifest与打包资产路径外部 API 的响应、文件与平台事件载荷中携带的身份字符串identity strings carried inside payloads生成的源码与被建议的能力suggested capabilities其他 capsule 的普通数据输出。而真正“可执行”enforceable的边界只有这几类内核盖戳的主体归属kernel-stamped principal attribution、经过验证的内容身份verified content identity、清单门控manifest gates、主题 ACL、principal 授权principal grants以及同意consent。仓库中的实现对这一定位有多处印证capsules/capsule-forge/src/guides/manifest.md 开篇即声明“The manifest is untrusted declarative input”清单是不可信的声明式输入运行时负责把它解释为最大权限上限crates/aos-mcp-broker/src/policy.rs 中策略判定结果Decision::Deny { reason }的注释强调reason“由构造保证净化Sanitized by construction: operator string, no reflected args”——即拒绝理由只引用规则自身的 id运维方写的字符串绝不回显reflect来自不可信参数的内容避免参数注入进入错误消息载荷里“自称是另一个 principal”的字段在任何位置都不构成授权这与“身份字符串不可信”的条目一一对应。实践要点不要把“我信任这个模型”“这个字段是内部生成的”写进安全论证。论证只能落在上面那六类可执行边界上其余一切默认敌对。在 Capsule 边缘做校验先于主机调用失败指南第二节要求在发起主机host调用之前先把空值、畸形值、超大值拒掉。具体规则包括当参数应当是“一个安全的路径分量one safe component”时拒绝/、\\、..、NUL、URL scheme 以及绝对路径解析 URL 后将归一化normalized的主机名与预期域名集合比对而不是做字符串前缀匹配进程参数一律以 argv 形式传递绝不把不可信文本插值进 shell 命令对循环、递归、集合规模、响应大小、重试次数全部设上限对敏感操作认证内核盖戳的调用方身份避免把密钥secret反射到错误信息、日志、工具输出或 trace 中。指南特别说明VFS 与主机门控依然会各自执行边界检查本地校验的价值在于让模型拿到清晰的失败信号并在主机调用之前就保护住领域不变量domain invariants。仓库里就有该原则的直接实现。capsule-forge 的validate_name函数capsules/capsule-forge/src/lib.rs/// Reject empty names and path-traversal characters in untrusted name args. fn validate_name(name: str) - Result(), SysError { if name.is_empty() { return Err(SysError::ApiError(Name cannot be empty.into())); } if name.contains(/) || name.contains(\\) || name.contains(..) { return Err(SysError::ApiError( Invalid name — path traversal rejected.into(), )); } Ok(()) }该函数被scaffold_capsule、explain_interface、capsule_doctor三个工具入口调用capsules/capsule-forge/src/lib.rs拒绝的正是“空、路径穿越字符”这类模型可能随手生成的参数。错误消息也是固定文案不回显任何用户输入——同时满足“拒绝危险模式”与“不把不可信文本反射进错误”两条规则。同文件中suggest_capabilities还有一个容易被忽略的安全细节capsules/capsule-forge/src/lib.rs当意图描述中出现“no identity operations”“without http”这类否定句式时mentions_positive/occurrence_is_negated会识别否定并避免凭空生成对应的能力请求行。测试capability_suggestions_ignore_plain_negationcapsules/capsule-forge/src/lib.rs专门断言对含否定的意图输出中不得出现identity 或net 。这对应了信任边界清单中“生成的源码与被建议的能力是不可信的”——建议只是候选能力必须由作者显式确认。Fail-Closed策略层的错误不是拒绝第三节是全文最容易被实现错误的部分。规则只有两句但后果严重主机能力检查与 ACL 检查天然 fail-closed当 capsule 逻辑本身是策略决策点时它也必须 fail-closed。关键在于有序拦截器链ordered interceptor chain中的错误语义返回普通错误Err问题被记录日志链继续执行意图阻断请求的策略 capsule必须返回InterceptResult::Deny { reason }。指南的原文警告“测试这个行为一个Err不是拒绝anErris not a denial。” 此外可选 import 与尽力而为best-effort的后台工作只有在降级行为被显式声明且安全时才合法。仓库的 capsules/capsule-forge/src/guides/ipc.mdIPC 章节给出了该语义的完整定义可作为安全章节的配套参考同等优先级的匹配处理器之间是独立并发扇出concurrent fan-out一旦任何匹配优先级不同整个匹配集合变成一个按优先级升序执行的有序中间件链在有序链中Continue(非空 payload)替换下一层的 payloadFinal(payload)终止链并返回最终结果Deny { reason }以“拒绝”终止链NotSupported继续到下一层普通 handler 错误只记日志链继续——“That last rule is fail-open for middleware errors. A security or policy layer must returnDeny, notErr, when it intends to block an action.”最后一条规则对中间件错误而言是 fail-open 的安全/策略层若要阻断动作必须返回Deny而非Err。也就是说优先级赋值本身是一个架构决策新增一个不同优先级可能把所有并发订阅者悄悄改造成中间件链。指南给出的参考分层capsules/capsule-forge/src/guides/ipc.md10 validate and normalize 20 enforce policy (return Deny on refusal) 50 enrich context 100 execute provider策略层应放在执行层之前并且它的评审清单明确包含“policy refusal returnsDenyrather than an ordinary error”。capsules/capsule-forge/src/lib.rs 中的测试ipc_manual_explains_priority_mode_switch_and_fail_open_errors甚至断言 IPC 章节必须保留“must returnDeny, notErr”这句话——文档语义同样被测试锁定。仓库中还有一处更底层的对照实现MCP broker 的策略决策点crates/aos-mcp-broker/src/policy.rs/// Evaluate rules against one tool call. First-match-wins over the /// ordered list; the default is [Decision::Allow] so the PDP only ever /// narrows the surface the capability PEP already guards. pub(crate) fn evaluate(rules: [Rule], tool_name: str, arguments: Value) - Decision { for rule in rules { // ... 按顺序匹配命中即返回 Allow / Deny { reason: rule.id } } Decision::Allow }这里的设计值得注意策略 PDP决策点默认Allow因为它是在能力 PEP执行点即内核能力强制层之上再收窄的过滤层——真正的兜底 fail-closed 行为由能力层保证。这与 security 章节“主机能力与 ACL 检查 fail-closedcapsule 策略逻辑也要对齐”的分层思想一致每一层知道自己是否是最终防线策略层若想做最终裁决就必须用显式的Deny而不能依赖异常。同时matcher_holdscrates/aos-mcp-broker/src/policy.rs保证“缺失的参数永远不会意外满足一条 deny 规则”即不可信输入无法通过缺省路径绕过策略。围绕现有资源边界做设计第四节列出了当前运行时的作者相关限制。指南提醒限制是随运行时版本演进的依赖某个精确数值前应先检查所固定的运行时源码inspect the pinned source。当前作者相关的默认限制包括有界bounded的文件系统调用大小与目录列举动态订阅数量上限有界的并发主机进程数WASM 执行时间/epoch 中断有界的工具描述收集bounded tool-description collection。然后给出七条“假设一切外部资源都有限”的设计规则大数据流式化或分页stream or page限制消息与 trace 的保留量请求/响应流程加超时重试使用 compare-and-swap 或幂等键idempotency keys对平台事件去重用背压backpressure显式表达容量而不是派生无界工作长生命周期工作在安全边界处做检查点checkpoint。指南还特别指出uplink与持久进程persistent processes会放宽常规的“生命周期随调用结束”假设因此需要更强的关停shutdown、所有权ownership与恢复recovery设计。这与 capsules/capsule-forge/src/lib.rs 中suggest_capabilities对这些能力的描述互相印证host_process需要逐个列出可执行文件白名单allow_persistent true是“叠加在可执行文件白名单之上的显式布尔子授权”uplink true则“仅在真实的协议边缘real protocol edge才应使用”。换言之放宽生命周期的能力在清单层面就要求作者做出更强的显式承诺。Principal 隔离状态、路径、环境与密钥按调用选择第五节的规则状态、home 路径、环境变量、密钥都按调用per invocation选择绝不把 principal 专属的值缓存在全局属于 principal 作用域 KV 的数据不要放进可变全局状态跨 principal 服务必须把共享/运维作用域shared/operator scope显式化并且把授权与查找lookup分开调用方在 JSON 字段里声称自己是另一个 principal不产生任何以该 principal 行事的权限。仓库中对“运行时按 capsule principal 序列化执行”的说明见 capsules/capsule-forge/src/guides/ipc.md“调用身份来自内核盖戳的信封kernel-stamped envelope运行时在必要时按 capsule 与 principal 序列化执行避免可变状态成为跨 principal 竞态。不要添加破坏这种隔离的全局缓存。动态接收超时返回Ok 空集合应判空而不是匹配错误字符串敏感动作前对每条消息校验来源与 principal。” 这与 security 章节“不要缓存 principal 专属值到全局”的告诫完全咬合静态缓存一旦混入 principal 专属数据就是隔离漏洞。供应链与安装第六节覆盖从构建到安装的完整信任链可安装的.capsule归档必须通过官方构建器构建拒绝不安全的归档路径、符号链接、重复的便携名、以及未声明的资产保持“源码 → 产物 → 校验和/出处证明checksum/provenance→ 已安装字节 → 运行身份”全程可追溯不重打标签retag或静默替换已发布的发布字节把主机进程与 MCP 服务器视为显式的沙箱出口explicit sandbox exits审查生命周期钩子lifecycle hooks因为它们运行在安装或升级期间。关于钩子的具体面从 capsules/capsule-forge/src/guides/capsule.md 的 SDK 注解一览可以看到#[astrid::install]安装生命周期钩子与#[astrid::upgrade]接收前一版本的升级钩子等入口。这些钩子在安装/升级窗口内执行属于指南所说的“运行时机特殊、必须被单独审查”的代码面。审查时至少应确认钩子逻辑与正文工具逻辑同等对待同样的输入校验、fail-closed 语义升级钩子能处理“升级进行到一半崩溃”后的残留状态——这正是下文对抗式评审清单中的问题之一。评估强度与后果成正比第七节的核心观点不同风险等级的 capsule 需要不同强度的证明——一个本地格式化 Skill、一个只读连接器、一个身份管理员、一个发消息的平台 worker其评估深度应当不同。至少应评估代表性用例上的功能成功非法、恶意与被拒绝denied的输入权限范围与“负能力”测试negative capability tests断言没有的东西确实不能做principal 隔离重启、重试、重复、超时行为从受支持的前一状态做升级对真实 harness 与留出任务held-out tasks的影响日志/trace 无密钥泄漏。对于 meta-harness元框架自动搜索式扩展场景指南要求保留基线、候选源码、任务分布、指标、成本与原始 trace并且明确禁止“在留出评估集上优化”或“凭单个任务的轶事宣称泛化改进”。这与仓库中 meta-harness 指南的评估纪律一致其边界声明能力仍是操作边界、生成代码不能自我提权可以在同目录的 capsules/capsule-forge/src/guides/meta-harness.md 与 capsules/capsule-forge/src/guides/authority.md 中继续核对——[capsules/capsule-forge/src/lib.rs](https://link.gitcode.com/i/f5331b3e50997d84c63f2e23040508df)的测试authority_manual_separates_construction_from_activation就断言 authority 章节必须包含“Generated code cannot self-promote”生成代码不能自我提权。对抗式评审问题清单最后一节是一组可直接照用的评审问题adversarial review questions建议作为 PR/发布前 checklist如果模型提供了穿越路径traversal path或开放代理 URLopen-proxy URL会发生什么载荷能否伪造spoof一个 principal 或 provider某个错误会不会“意外地让策略链继续执行”对应 fail-open 陷阱重试会不会复制外部副作用duplicate an external effect一个 principal 的配置会不会通过静态缓存泄漏给另一个宽泛的通配符能否被收窄主机进程能否逃逸出预期的可执行文件/参数边界升级进行到一半崩溃时什么状态会存活下来生成的 Skill 或插件是否指示了操作系统OS并未授予的动作每一条“完成声明”completion claim是否都被“实际被测试的那个工件”所支撑指南以一句结论收尾“安全是真实的门控real gates与良好设计的边缘well-designed edges的组合而不是提示词里的一句声明not a claim in a prompt。”小结把安全章节落成可验证的工程动作把本文各节压缩成一份落地检查表主题核心动作仓库佐证信任边界输入默认敌对论证只落在六类可执行边界上manifest.md 声明清单为不可信输入边缘校验拒绝空/畸形/超大/穿越值argv 不拼 shell错误不回显输入lib.rs#L186-L197validate_nameFail-closed策略层阻断必须显式DenyErr只记日志并继续ipc.md#L98-L127policy.rs#L142-L178资源边界流式化、幂等、超时、背压、检查点security.md“Current resource boundaries”一节Principal 隔离按调用选择状态/环境/密钥禁止 principal 专属全局缓存ipc.md#L129-L138供应链官方构建器、可追溯、钩子需审查Capsule.toml 最小能力示例评估与评审按后果分层评估逐项过对抗式清单security.md 最后两节最后强调适用前提以上限制数值与能力字段如uplink、allow_persistent、allow_prompt_injection均为当前仓库版本的描述指南本身也提醒“依赖精确数值前先检查所固定的运行时源码”。在把该清单用于自己的 capsule 时应以你所固定的运行时版本对应的 WIT 契约与内核实现为准。赞分享【免费下载链接】aos-ceAOS Community Edition: the open agent operating system.项目地址https://gitcode.com/gh_mirrors/ao/aos-ce点击查看免费下载相关推荐OpenMed 多语言摄入威胁模型字典、编码与区域设置的 Fail-Closed 安全边界设计OpenMed 多语言摄入威胁模型字典、编码与区域设置的 Fail Closed 安全边界设计 导读 本文基于 OpenMed 仓库的 threat mode人工智能NLP医疗健康数据脱敏本地部署大模型AI 应用MCP 服务联邦学习GetQzonehistory 教程QQ空间说说、转发、留言备份到 Excel 的完整指南GetQzonehistory 教程QQ空间说说、转发、留言备份到 Excel 的完整指南 GetQzonehistory 是一个用 Python 编写的 Q网页爬虫数据分析IronClaw 内核权威边界Authority Perimeter九阶段权限管线、密封见证与逐阶段 Fail-Closed 安全设计解析IronClaw 内核权威边界Authority Perimeter九阶段权限管线、密封见证与逐阶段 Fail Closed 安全设计解析 本文以 cra人工智能AI 应用交互助手AI Agent上一篇happy-cli 沙箱运行时Sandbox Runtime完全指南为 Claude Code 与 Codex 提供 OS 级文件系统与网络隔离下一篇BG3ModManager完整使用指南博德之门3模组管理终极教程创作声明:本文部分内容由AI辅助生成(AIGC),仅供参考