ABI进程选择
应用进程位数不是由“设备是 64 位”直接决定,也不是看到 zygote64 就固定走 primary socket。ProcessList 先从 ABI override 或 ApplicationInfo.primaryCpuAbi 得到 requiredAbi,缺失时回退 Build.SUPPORTED_ABIS[0];再由 VMRuntime 推导 instruction set。ZygoteProcess 连接 primary/secondary Zygote,使用握手返回的 ABI list 执行 matches(abi),最终选择能处理 requiredAbi 的 socket。
1. 设备ABI列表
源码文件:frameworks/base/core/java/android/os/Build.java
public static final String[] SUPPORTED_ABIS =
getStringList("ro.product.cpu.abilist", ",");
public static final String[] SUPPORTED_32_BIT_ABIS =
getStringList("ro.product.cpu.abilist32", ",");
public static final String[] SUPPORTED_64_BIT_ABIS =
getStringList("ro.product.cpu.abilist64", ",");数组有偏好顺序,第一个元素是对应列表的首选 ABI。它们描述设备能力,不是某个 APK 的最终 ABI;PMS 安装扫描会结合 APK native library 和 package 配置填充 primaryCpuAbi/secondaryCpuAbi。
2. requiredAbi决策
源码文件:frameworks/base/services/core/java/com/android/server/am/ProcessList.java
String requiredAbi = abiOverride != null
? abiOverride
: app.info.primaryCpuAbi;
if (requiredAbi == null) {
requiredAbi = Build.SUPPORTED_ABIS[0];
}
String instructionSet = null;
if (app.info.primaryCpuAbi != null) {
instructionSet = VMRuntime.getInstructionSet(
requiredAbi);
}
app.setRequiredAbi(requiredAbi);
app.setInstructionSet(instructionSet);ABI override 优先,常用于调试/特殊进程;否则使用 package 的 primaryCpuAbi。若包无 native ABI,使用设备首选 ABI启动 Java 进程。instructionSet 只有 package primaryCpuAbi 非空时才推导,因为纯 Java 包通常不需要 native bridge/ISA 特化。
3. ABI字段
primaryCpuAbi 是当前进程默认使用的 native ABI;secondaryCpuAbi 表示包可能还安装另一套 native 库,但 ProcessList 此处不会自动在两者间随机选择。多进程/ABI override、WebView Zygote 或 app zygote 可能改变最终 requiredAbi;普通应用默认沿 primaryCpuAbi。
4. Zygote握手匹配
源码文件:frameworks/base/core/java/android/os/ZygoteProcess.java
boolean matches(String abi) {
return mAbiList.contains(abi);
}
private ZygoteState openZygoteSocketIfNeeded(
String abi) throws ZygoteStartFailedEx {
attemptConnectionToPrimaryZygote();
if (primaryZygoteState.matches(abi)) {
return primaryZygoteState;
}
if (mZygoteSecondarySocketAddress != null) {
attemptConnectionToSecondaryZygote();
if (secondaryZygoteState.matches(abi)) {
return secondaryZygoteState;
}
}
throw new ZygoteStartFailedEx(
"Unsupported zygote ABI: " + abi);
}客户端先连 primary 并检查真实 ABI list;只有不匹配才连 secondary。primary/secondary 是连接优先级和 init 配置角色,不应等同于 64/32 固定别名。
5. ISA与桥接
源码文件:frameworks/base/core/jni/com_android_internal_os_Zygote.cpp
bool need_pre_initialize_native_bridge =
!is_system_server
&& instruction_set.has_value()
&& android::NativeBridgeAvailable()
&& !android::NativeBridgeInitialized()
&& android::NeedsNativeBridge(
instruction_set.value().c_str());
if (need_pre_initialize_native_bridge) {
android::PreInitializeNativeBridge(
app_data_dir.has_value()
? app_data_dir.value().c_str()
: nullptr,
instruction_set.value().c_str());
}instruction set 不等于 ABI 字符串,但由 ABI 映射得到。目标 ISA 与当前 runtime 不兼容且设备提供 NativeBridge 时,在 specialization 前预初始化;app zygote 已初始化时跳过。SystemServer 不走 NativeBridge 分支。
6. 专用Zygote
if (hostingRecord.usesWebviewZygote()) {
startWebView(..., requiredAbi, instructionSet, ...);
} else if (hostingRecord.usesAppZygote()) {
appZygote.startProcess(...,
requiredAbi, instructionSet, ...);
} else {
Process.start(...,
requiredAbi, instructionSet, ...);
}requiredAbi/instructionSet 会传给三种父进程路径,但每个父 Zygote 有自己的 accepted ABI list。WebView/app zygote 不支持该 ABI 时,启动失败,不会无条件回退 regular Zygote,因为父进程隔离语义已经由 HostingRecord 决定。
7. 失败与排查
primaryCpuAbi错误:检查 PMS native library 扫描和 package metadata;- ABI override 错误:ProcessList 会优先使用并导致 unsupported ABI;
- 两个 Zygote 都不匹配:
Unsupported zygote ABI; - instructionSet 为空:纯 Java 包通常正常,不应直接判错;
- NativeBridge 失败:查目标 ISA、bridge 配置和 app data dir;
- WebView/AppZygote 不匹配:查专用 Zygote accepted ABI,不应只看 regular Zygote。
8. 导航与后续
# ProcessList 的 requiredAbi、instructionSet 和三类 Zygote 分流。
rg -n "requiredAbi|primaryCpuAbi|abiOverride|getInstructionSet|usesWebviewZygote|usesAppZygote" \
frameworks/base/services/core/java/com/android/server/am/ProcessList.java
# 设备 ABI 列表和 32/64 判断。
rg -n "SUPPORTED_ABIS|SUPPORTED_32_BIT_ABIS|SUPPORTED_64_BIT_ABIS|is64BitAbi" \
frameworks/base/core/java/android/os/Build.java
# Zygote socket 匹配与 NativeBridge。
rg -n "matches\(|openZygoteSocketIfNeeded|Unsupported zygote ABI|NeedsNativeBridge|PreInitializeNativeBridge" \
frameworks/base/core/java/android/os/ZygoteProcess.java \
frameworks/base/core/jni/com_android_internal_os_Zygote.cpp下一篇将进入 Zygote LocalSocket 通信和环境 fd 的运行时连接模型;不会重复 ABI 决策。
