在理解 Android 系统架构时,很多人都会产生一个看似简单、但其实非常关键的疑问:
Android 系统跑起来后,是不是只有一个 ART 一直在运行?
这个问题如果停留在表面,很容易得到一个模糊但不准确的答案。
本文将从 系统启动与进程模型 出发,把 zygote、system_server、App 与 ART Runtime 的关系 一次讲清楚。
一、先给结论(非常重要)
Android 并不是只有一个 ART 在运行。
系统中始终存在一个运行着 ART 的 zygote 模板进程,
system_server 和每一个 App,都是通过 fork zygote 得到的、各自独立的 ART Runtime 实例。
一句话概括:
zygote 是 ART 的"模板工厂",而不是唯一的 ART。
二、Android 启动后,ART 的真实存在形态
1️⃣ zygote:第一个运行 ART 的进程(常驻)
系统启动流程简化如下:
Linux Kernel
→ init
→ zygote
zygote 的本质是:
-
一个 用户态进程
-
内部已经完成:
-
libart.so加载 -
ART Runtime 初始化
-
核心 Java / Framework 类预加载
📌 只要 Android 系统在运行,zygote 就一直存在。
这也是很多人产生「是不是只有一个 ART 在跑」直觉的原因。
2️⃣ system_server:系统级 ART Runtime
系统启动过程中,zygote 会执行一次关键 fork:
zygote
└─ fork → system_server
system_server 的特点:
- 是一个 独立进程
- 内部运行着 一套完整的 ART Runtime
- 承载:
- AMS / WMS / PMS
- Power / Window / Input 等系统服务
📌 system_server 本身就是一个 ART 虚拟机实例。
3️⃣ 每个 App,都是一个独立的 ART Runtime
当用户启动 App 时:
zygote
└─ fork → App Process
结果是:
- 每个 App:
- 都有 自己独立的 ART Runtime
- 独立的 Java 堆、GC、线程模型
- App 退出:
- 该进程和 ART Runtime 一起销毁
📌 ART 是"随进程存在的",而不是全系统共享的单例。
三、一个常见但错误的理解
❌ 错误理解:
Android 系统里只有一个 ART,App 都共用它
✔ 正确认知:
Android 系统中存在一个常驻的 ART 模板进程(zygote),
system_server 和每个 App,都是从它 fork 出来的、各自独立的 ART Runtime。
四、为什么 Android 要用 zygote + fork?
这是 Android 运行模型中最核心的设计之一。
1️⃣ 启动速度快
- ART 初始化非常"重"
- zygote 预先完成初始化
- fork 后直接继承运行态
👉 App 启动不需要重新创建 ART
2️⃣ 内存占用低(COW)
- ART 代码段
- 预加载的 Class
- Native Libraries
通过 写时复制(COW) 在多个进程间共享。
👉 多个 ART 实例 ≠ 多倍内存占用
3️⃣ 稳定性与隔离性
- 每个进程一个 ART Runtime
- App 崩溃 ≠ 系统崩溃
- system_server 可被 watchdog 重启
👉 这是 Android 稳定性的基石。
五、一个容易混淆但必须分清的点
fork 的是"进程",不是"ART 对象"
- Linux fork 复制的是进程
- ART Runtime 是进程内的一部分
- fork 后:
- Runtime 结构被复制
- 内存页按需写时复制
📌 ART 不是 new 出来的,而是 fork 出来的。
六、用一个形象但准确的类比(帮助记忆)
如果把 Android 系统看成一个生命体:
Linux Kernel:心脏
Binder:大动脉
zygote(ART):干细胞工厂
system_server / App(ART):分化后的器官细胞
👉 干细胞一直在,但器官细胞是按需生成、按需消亡的。
七、一句话总结(可以直接背)
Android 系统不是"一个 ART 一直在跑",
而是"zygote 一直在跑,ART 随进程而生灭"。