☰
血统与恢复:Astrid 如何继承 Plan 9 与 Inferno 的能力安全设计
2026/9/28 3:27:42 网站建设 项目流程
  • 文档
  • 教程

【免费下载链接】book

The canonical reference for Astrid: kernel, capsules, host ABI, IPC, and the security model.

项目地址:https://gitcode.com/gh_mirrors/book269/book
点击查看免费下载

"Not only is UNIX dead, it's starting to smell really bad." — Rob Pike, 1991

Unicity Astrid OS 的形态不是凭空设计出来的,而是一次恢复(restoration):其核心机制曾在贝尔实验室被同一群建造 Unix 的人正确设计过两次——一次是 Plan 9,一次是 Inferno——两次都正确,两次都死掉。本篇从操作系统史出发,梳理这两条血统线,并说明 WebAssembly 与 AI 智能体这两个迟到三十年的前提,为何让第三次设计(也就是 Astrid 本身)终于有了落地的基底与租户。读完你将能对 Astrid 的命名空间隔离、能力令牌、零 WASI 系统调用面等机制,与 Plan 9、Inferno 之间建立起精确的对应关系,也能理解"内核保持哑、能力住在墙里"在这条谱系中的历史必然性。

为什么一本参考手册需要一章"谱系"

本篇文章对应参考手册中的 The Lineage 一章,属于可选章节:手册其余部分的机制讲解完全不依赖它。The Labyrinth 用两篇科幻作品论证了 Astrid 形态的必然性,这一章则用真实历史做同样的论证。

这一章的核心命题是:本书中的机制并不是新想法。文件树即接口、每个进程拥有私有世界观、驱动只是非特权服务器、没有环境性权威——这些设计都被贝尔实验室实现过,也都因为两个缺失的前提而死亡。如今这两个前提都已到来,于是 Astrid 做的事情不是发明,而是把正确但被世界拒绝的墙重新砌起来。

第二次 Unix:Plan 9

把 "everything is a file" 变成字面事实

到 1980 年代末,Unix 的缔造者们已经认为 Unix 完工了——而且不是褒义的"完工"。他们的答案是Plan 9:来自同一研究中心的第二个操作系统,Ken Thompson 亲自动手,Dennis Ritchie 主持部门。

Plan 9 把 Unix 最古老的口号everything is a file真正落实:

  • 网络协议栈是一个文件树;
  • 窗口系统是一个文件树;
  • 进程表是一个文件树;
  • 系统里每一种资源都通过同一个协议 9P对外服务。

因为"一个文件树并不关心是哪台机器在服务它",Plan 9 的分布式是构造性的(distributed by construction),而不是事后添加的补丁。在 Plan 9 里,驱动程序不是焊死在内核里的特权代码,而只是一个对外服务文件树的普通程序。今天人们说"驱动不需要存在",记忆的正是这句话。

私有命名空间:权威就是世界的形状

Plan 9 的激进之处在于:每个进程都有自己私有的命名空间(namespace)——它自己看世界的视图,通过把资源 bind、mount 进这个空间来组合而成。

由此推导出一个极深刻的安全性质:

  • 没有全局文件系统,只有"你的视图";
  • 权威不是某张表里的一个比特位,而是你被给予的世界的形状;
  • 一个进程无法打开它的命名空间里不存在的对象,因为它根本无法命名它。

一位 Astrid 读者在这里看到了全部

参考手册自己在 The Lineage 中指出,读过前文的读者会发现 Plan 9 的每一个核心概念都在 Astrid 中重演:

  • 私有视图 ↔ 逐主体隔离(per-principal isolation)。在 PrincipalId and Per-Invocation Isolation 中,PrincipalId是一个字母表被严格限定的 newtype:只允许[a-zA-Z0-9_-],显式排除/、.、@。这保证了一个主体标识用作文件系统路径组件时不可能逃逸目录(../escape在'.'处就被拒),用作 KV 命名空间前缀时不可能碰撞存储层保留的分隔符。每个主体的 KV 命名空间形如{principal}:capsule:{capsule_id},分隔符:恰好位于PrincipalId字母表之外——"无法命名即无法访问"在 Astrid 里是构造层面的性质,而不是运行时策略。
  • 用挂载的资源组合世界 ↔ 导入解析(import resolution)。Imports, Exports, and Dependency Resolution 描述了 capsule 通过[imports]/[exports]声明依赖,内核在启动时构建依赖图、用 Kahn 算法拓扑排序,再按序加载。"世界由哪些资源组成"是一个可声明、可解析、可循环检测的显式过程。
  • 驱动作为非特权服务器 ↔ capsule 经总线导出工具(tools as IPC)。Tools as an IPC Convention 明确写着:工具不是内核特性。内核不知道任何工具名、工具 schema 或"执行工具"意味着什么;它只按主题路由 IPC 事件并调用拦截器。一个处理my_tool的 capsule 不过是声明了tool.v1.execute.my_tool主题订阅的普通程序——这正是"驱动是不需要存在的东西"的现代版本。无状态的ToolRoutercapsule 只做纯变换:校验工具名、计算转发主题、重新发布。
  • 没有环境性权威 ↔ 整个能力系统。Capabilities, Tokens, and Delegation 规定:静态能力采用冒号分隔的窄语法(段内只能是字母数字、-、_或独立*),求值优先级固定为revokes 永远先赢;每类资源的缺省都是空列表,而空列表在 Astrid 里是"全拒"的 allowlist,不是"未配置"的放行——这就是 fail-closed 的落点。权威不是宿主进程内隐含存在的,而是显式授予的。

Astrid 的一个升级:从被信任的机器到被验证的签名

Plan 9 的命名空间由你所管理的内核强制,其权威声明植根于"信任这台机器"——当每台机器都属于同一个机构时,这没有问题。

Astrid 在这里做了一次关键升级:一个 Astrid 能力是一枚带签名的令牌(signed token)。声明自带证明(the claim carries its own proof),因此它能够跨越互不信任的各方进行委托;并且子代只能被授予比父代更少的权限。

源码层面的支撑(锚点见 Capabilities, Tokens, and Delegation):

  • 运行时令牌CapabilityToken(源码锚点token.rs:90)由守护进程的 ed25519 密钥签名,除signature外的每个字段——包括绑定的principal——都在签名载荷内。篡改任何字段,验签即失败。
  • principal字段在签名载荷中意味着:一枚为alice铸造的令牌,bob拿去用会因validate_by_id返回InvalidSignature而失败关闭(锚点validator.rs:149)——"孩子只能得到更少"正是通过把身份烤进签名来实现的。
  • 当前委托边界是诚实的:配置层的子代理限制(subagents.max_concurrent、max_depth、timeout_secs只能从工作区基线递减)已实现,delegate:self:*出现在内置agent组的静态能力里,但运行时能力的衰减与重新签名链尚未完整落地——文档明确区分了"已实现"与"架构已预留"。

一段仍在"遗产检验期"的继承:分布式

Plan 9 是按构造分布式的:任何资源、由任何机器服务、可挂载进任何命名空间。而 Astrid 今天仍是一个"单机之家"(one machine's house)。

签名能力被设计成能经受命名空间经受不住的那个网络跳(network hop),但**"跳"本身是这条血统里尚未书写的一章**——参考手册明确表示不假装它已存在。对应到代码现状:uplink capsule 是当前的事件总线监听器(通过 Unix socket 收外部消息),其加载顺序被内核特殊处理,但它还不是 Plan 9 意义上的任意机器挂载。

浏览器标签页里的操作系统:Inferno

1996 年,同一批人在面向网络世界的背景下再次蒸馏了这套设计,命名为Inferno:

  • 程序编译为面向虚拟机Dis的可移植字节码,在每台机器上运行结果一致;
  • 资源仍然是文件树,通过协议Styx服务;
  • 操作系统本身有两种模式:native(裸机上)与hosted(作为 Windows 或 Unix 上的普通应用运行);
  • 甚至存在一个构建:把完整的操作系统作为 Internet Explorer 插件运行——一个拥有自己的进程、命名空间、网络模型的完整 OS,跑在浏览器标签页里,时间是 1997 年。

如果你觉得耳熟,那是因为 Astrid 用更好的材料做了同一个把戏:

  • Capsules 编译为 WebAssembly,在每处运行一致。构建管线astrid build产出的 capsule 目标被硬约束为wasm32-unknown-unknown——这是唯一合法的 capsule 构建目标。该目标没有任何wasi:*导入,capsule 对宿主的一切调用都必须穿过astrid:*的 WIT 接口面(详见 The Host ABI: The Syscall Surface)。
  • 内核既可以作为你机器上的守护进程(daemon)运行,也可以 hosted 在某个把操作系统当组件用的进程里——包括一个网页。Inferno 正是"OS 是可以被嵌入的东西,而不只是装在一切底下的东西"这一主张的祖先。
  • Inferno 的语言Limbo,以其带类型通道(typed channels)的并发模型,是 Go 的直系祖先;其赌注是:软件的基本单元是一个小的可移植模块,安全由构造保证,在只共享一个协议的机器之间移动。这条赌注线直接通向今天的 WASM 组件模型。

为什么它们会死去

不是因为它们错了。

Plan 9比 Unix 更好,但它竞争的对手是一个已经免费、已经无处不在的 Unix;而 Plan 9 在一场关键竞争结束前一直处于限制性许可证之下,等到它终于免费可用时,Linux 已经"继承了地球"。

Inferno的赌注需要整个行业采纳同一种可移植执行格式——行业确实采纳了一种,但 Sun 花了数十亿美元确保它叫 Java,而 Inferno 的所有者几乎没出现在战场上。结果 Dis 和 Limbo 始终是一个"只有一栋楼"的生态系统:每一个程序都必须用只有那栋楼会说的语言重写。

于是,整合性的设计从未交付,器官被一个一个地移植出去:

  • Linux namespaces——今天每个 Linux 容器底下的隔离机制——是 Plan 9 命名空间的移植;
  • Limbo 的通道变成了Go 的通道;
  • 9P今天随 WSL 和 QEMU 一起分发;
  • UTF-8是为 Plan 9 设计的:Thompson 与 Pike 于 1992 年 9 月在新泽西一家餐馆的餐垫上完成。

行业拿走了每一个零件,却拒绝了整个架构。

三十年后的两个前提

第一个前提:基底(substrate)——WebAssembly 就是获胜的 Dis

WebAssembly 是那个获胜的 Dis:

  • 厂商中立,内置于每个浏览器;
  • 每一种严肃语言都能编译到它;
  • 由标准化 web 的同一机构标准化。

但可移植性只是它价值里较小的一半。更深一层的性质是:WASM 的 import 模型本身就是一个能力模型——一个模块只能调用在实例化时被显式递给它的东西,它甚至无法命名任何其他东西;不存在一个可以伸手去够的"环境性系统调用面"。

Inferno 必须用环绕在虚拟机外围的命名空间去约束 VM;而一个 WASM 模块生而无法(born unable)。它收到的那个系统调用面是逐能力门控(gated)的:

  • 内核的 linker 只注册astrid:*接口,一个携带任何wasi:*import 的 capsule 在实例化时直接以 "interface not found" 失败——这是刻意姿态,不是要掩盖的 bug;
  • 能力门控在每次调用时执行(而不是只在加载时),因此会话中途撤销的能力在下一调用即生效;
  • 缺省即空列表,空列表即全拒——失败关闭(fail-closed)在 Capability Gating 中贯穿每一个能力类别。

Styx 给了资源一个共同的线上形状;WIT 合约则给它们类型化、版本化、可检查的接口。两套 WIT 命名空间分工明确:astrid:*(host ABI,内核到 capsule,直连 wasmtime Component Model linker)与astrid-bus:*(capsule 到 capsule 的事件 schema,经astrid:ipc/host.publish走 JSON)。每个 WIT 文件以版本号烙进文件名(如host/fs@1.0.0.wit)并标注 "Frozen per the ABI evolution discipline",新行为就是新文件新版本,绝不改旧文件。

Astrid 因此不必建造 VM、不必建造语言、不必建造生态——这些都不缺了。它只需要建造操作系统。

第二个前提:租户(tenant)——AI 智能体

Unix 的租户是一个人写的程序:它行为不端时,有一个可以修补的 bug、一个可以追究责任的作者。

Plan 9 和 Inferno 也是为同一个租户建造的——而那个租户从来没有需要它们到愿意搬家的程度。

新租户是agent:一个可以被说服(argued into things)的心灵。它的行为不端不是一个你能打补丁修掉的缺陷,因为**"易受说服影响"是构成性的(constitutive)——这一点 The Labyrinth 论证过。历史上第一次出现一种完全无法在环境性权威(ambient authority)之上负责任地运行**的工作负载。

架构终于等到了它为之设计的租户。用参考手册里那句话结束这一节再贴切不过:

Plan 9 是一个等待问题的答案。那个问题以自然语言到来了。

恢复(The Restoration)

The Labyrinth 从小说出发论证:安全必须住在墙里,而不是住在心灵里。历史从相反的方向得出同一个结论:那堵墙被两次正确设计——由当时在世的最好的系统程序员——然后被世界拒绝,原因只有一个:既没有承载模块的公共基底,也没有离不开隔离的租户。

如今这两个前提在几年之内相继到来。而有一个力量彻底逆转了:

Unix 靠"免费且无处不在"击败了 Plan 9,而那个更好的设计被挡在许可证后面。这一次,免费的是继承物本身。

Astrid 不是一个新想法。它是一个被继承的想法、被恢复的想法——而且这一次,那些缺失的拼图终于垫在它下面了。若要继续追这条线,可以依次阅读 The Labyrinth(从小说论证)、Capabilities, Tokens, and Delegation(能力与令牌的完整实现)、The Host ABI: The Syscall Surface(零 WASI 的系统调用面)以及 WIT Contracts and the Three-Repo Flow(两份 WIT 合约的流转)。

  • 文档
  • 教程

【免费下载链接】book

The canonical reference for Astrid: kernel, capsules, host ABI, IPC, and the security model.

项目地址:https://gitcode.com/gh_mirrors/book269/book
点击查看免费下载
上一篇:网盘直链下载助手2025:智能解决八大网盘下载限速难题
下一篇:Windows环境下Apple Touch Bar显示驱动技术实现与架构解析

创作声明:本文部分内容由AI辅助生成(AIGC),仅供参考

需要专业的网站建设服务?

联系我们获取免费的网站建设咨询和方案报价,让我们帮助您实现业务目标

立即咨询