虚拟化的三条线索

2026-05-26

当你思考 "虚拟化" 这个话题,你会被乱飞过来的层出不穷的技术名词击晕:docker、podman、VirtualBox、VMWare、KVM、...。而从第一性原理出发,进程是虚拟化,虚拟内存也是虚拟化。概览各种虚拟化技术,你会发现三条线索:资源共享、权限控制和模拟执行。

资源共享

我所看到的虚拟化最主要的线索是资源共享。

理解了 "完整独占" 和 "资源性质不变" 这两个特性,我们可以即刻分析一堆虚拟化技术了

虚拟机技术(Hypervisor)

虚拟机共享硬件资源(不妨简单理解为 CPU),供给多种多样、并非宿主(Host)的操作系统使用。调研了半天,还是按照 Robert P. Goldberg 在 Architectural Principles for Virtual Computer Systems 提出的分类法来梳理虚拟机技术最清晰明了。请看从 Wikipedia 搬来的图:

简言之,Type 1 Hypervisor 利用硬件(CPU 指令集)对虚拟化的原生支持,向下直接和 CPU 交互,而向上支持多种 OS。

Type 2 Hypervisor 向上与 Type 1 Hypervisor 提供相同的服务/资源,向下却不直接和硬件交互,它运行在一个宿主操作系统上。

这个二分并非全面的。KVM 作为一个 Kernel Module,某种程度上把 Host OS 变成了一个 Type-1 Hypervisor,两者都不完全是。

最后关于用语:Virtualization 通常指代 Hardware Virtualization,即像这里把 CPU 硬件资源共享给多个操作系统使用。virtual as in virtual memory。这个过程通常需要 CPU 指令集的支持;相应地,Guest OS 也能获得接近 native 的性能。

权限与用量控制

理解资源共享是理解虚拟化之根本。然而通常只有虚拟化机制是不够的。在其基础上,我们引入一条新机制,权限控制。资源共享+权限控制,事情变得复杂起来。

比如说

在这些意义上,进程就是操作系统内置的虚拟化技术,它将宿主操作系统作为资源共享(自然附带更下面的硬件),供给多样的应用使用。

然而 "进程" 并不属于那些飞过来将你装晕的虚拟化技术名词。后者是 docker、podman、LXC、... - 对于以这三个玩意儿为代表的虚拟化技术,我们暂且称之为 Container,容器化技术。

容器化技术(Container)

Acknowledgment:Jacky 在讨论中的发言对本节内容贡献良多,本节很多部分是对 Jacky 讨论中发言的转述

在进程之外之所以还要容器,是因为在一些操作系统中(具体而言,Linux),进程这一抽象的 “完整独占” 的幻觉还不够逼真,权限控制的工具还不够方便。

为了弥补,Linux 内核提供了诸多底层 API:

从 Linux 操作系统的演化历史来看,这些 API 是逐步加入 Linux 内核的,没有一个统一的抽象。这时人们希望有一个统一的工具来协调这些底层 API,提供一个名为 "容器" 的抽象。

既然 "Docker container" 是 Container,那让我们看看 Docker 发布 runC 的博文

Because “containers” are actually an array of complicated, sometimes arcane system features*, we have integrated them into a unified low-level component which we simply call runC**.

*: control groups, namespaces, etc
**: runC is the low-level container runtime behind Docker

如果你能够且愿意手操这些 Linux API,你也可以手动构造所谓的 Container。

模仿我们对虚拟机技术的举例,在此再举几例

在 Linux PC/server 之外

如果我们把视线转向移动端,以 iOS 和 iOS 应用为例,它某种程度上就是主机/服务器 Container 的对应物(尽管通常不被称为 Container)。它们在用户空间,拥有资源共享/隔离机制,受到访问控制(尤其是当你考虑 iOS 的权限系统),都是比 "进程" 更有用的更高层抽象。

如果我们进一步不局限于操作系统,一个 "平台" 应用也可以将自己的资源带有访问控制地共享给 "租户" 应用。如今很多 AI Agent Framework 作为 "平台",创造沙盒(Sandbox)供 AI Agent 在里面自主发挥。

最后关于用语:Container 和 Containerization 通常就指代这一类比 "进程" 更适用于应用场景的用户空间资源隔离和访问控制技术,尤其是 Linux World 中与宿主共享 Kernel 但受控的轻量级容器。

模拟执行

当用户需要系统内不即已存在的资源和接口,作为下策,可以让系统使用它既有的资源模仿另一个系统(用户需要的)的行为,这就是 Emulation。Emulation 技术就好比下面的转换头,把一个 USB-C 母口扩展到 USB-C, HDMI 和 USB-B 母口,后两个接口都不是既有的。

仿真器(Emulator)

我们暂且将 Emulation 翻译为仿真 - 它与 Simulation 不同,Simulation 是模仿和重建现实系统的实验方法,它重在提供实验结果而非提供资源。

QEMU(Quick Emulator)为例:

模拟执行+权限控制的例子

一个这样糅合了虚拟化两条线索的例子是 iOS 系统上的 iSH Shell 应用。根据项目网站的简介:

iSH is a project to get a Linux shell environment running locally on your iOS device, using a usermode x86 emulator.

根据 iSH wiki,iSH 自身在 ARM 指令集的 iOS 系统上运行,却需要支持被编译到 x86_32 指令集Linux 系统上运行的应用。这里似乎有两个层级上的模拟或者说转化要做:

实际上发现 iSH 内的 ssh 命令提供的 ssh client 功能是可用的,说明这个 Shell 还是实现了很多相关的 System Call 的,具体没有深究。如果我们试图运行更多命令,安装 iproute2 包,借此更改 kernel 的网络配置,就无法成功了:

localhost:~# apk add iproute2
localhost:~# ip a
Cannot open netlink socket: Invalid argument

根本原因很好推测,即 iSH 作为一个 App Store 上的第三方应用不具有更改 iOS kernel 网络配置的权限。