/frameworks/base/cmds/app_process/App_main.cpp
/frameworks/base/core/jni/AndroidRuntime.cpp
/frameworks/base/core/java/com/android/internal/os/
- ZygoteInit.java
- Zygote.java
- ZygoteConnection.java
/frameworks/base/core/java/android/net/LocalServerSocket.java
/system/core/libutils/Threads.cpp
1 概况
Zygote是由init进程通过解析init.zygote64.rc文件而创建的,zygote所对应的可执行程序app_process,所对应的源文件是App_main.cpp,进程名为zygote。
service zygote /system/bin/app_process64 -Xzygote /system/bin --zygote --start-system-server
class main
socket zygote stream 660 root system
onrestart write /sys/android_power/request_state wake
onrestart write /sys/power/state on
onrestart restart media
onrestart restart netd
writepid /dev/cpuset/foreground/tasks
Zygote进程能够重启的地方:
- servicemanager进程被杀; (onresart)
- surfaceflinger进程被杀; (onresart)
- Zygote进程自己被杀; (oneshot=false)
- system_server进程被杀; (waitpid)
2 启动流程
app_main.cpp中main()方法的整体流程如下:
{
//传到的参数argv为“-Xzygote /system/bin --zygote --start-system-server”
AppRuntime runtime(argv[0], computeArgBlockSize(argc, argv));
argc--; argv++; //忽略第一个参数
//参数解析
bool zygote = false;
bool startSystemServer = false;
bool application = false;
String8 niceName;
String8 className;
++i;
while (i < argc) {
const char* arg = argv[i++];
if (strcmp(arg, "--zygote") == 0) {
zygote = true;
//对于64位系统nice_name为zygote64; 32位系统为zygote
niceName = ZYGOTE_NICE_NAME;
} else if (strcmp(arg, "--start-system-server") == 0) {
startSystemServer = true;
} else if (strcmp(arg, "--application") == 0) {
application = true;
} else if (strncmp(arg, "--nice-name=", 12) == 0) {
niceName.setTo(arg + 12);
} else if (strncmp(arg, "--", 2) != 0) {
className.setTo(arg);
break;
} else {
--i;
break;
}
}
if (zygote) {
// 启动AppRuntime
runtime.start("com.android.internal.os.ZygoteInit", args, zygote);
} else if (className) {
runtime.start("com.android.internal.os.RuntimeInit", args, zygote);
} else {
//没有指定类名或zygote,参数错误
return 10;
}
}
AndroidRuntime.start()
void AndroidRuntime::start(const char* className, const Vector<String8>& options, bool zygote)
{
static const String8 startSystemServer("start-system-server");
// 虚拟机创建【见小节2.3】
if (startVm(&mJavaVM, &env, zygote) != 0) {
return;
}
onVmCreated(env);
// JNI方法注册【见小节2.4】
if (startReg(env) < 0) {
return;
}
//等价 strArray[0] = "com.android.internal.os.ZygoteInit"
classNameStr = env->NewStringUTF(className);
env->SetObjectArrayElement(strArray, 0, classNameStr);
//等价 strArray[1] = "start-system-server";
// strArray[2] = "--abi-list=xxx";
//其中xxx为系统响应的cpu架构类型,比如arm64-v8a.
for (size_t i = 0; i < options.size(); ++i) {
jstring optionsStr = env->NewStringUTF(options.itemAt(i).string());
env->SetObjectArrayElement(strArray, i + 1, optionsStr);
}
//将"com.android.internal.os.ZygoteInit"转换为"com/android/internal/os/ZygoteInit"
char* slashClassName = toSlashClassName(className);
jclass startClass = env->FindClass(slashClassName);
if (startClass == NULL) {
...
} else {
jmethodID startMeth = env->GetStaticMethodID(startClass, "main",
"([Ljava/lang/String;)V");
// 调用ZygoteInit.main()方法
env->CallStaticVoidMethod(startClass, startMeth, strArray);
}
//释放相应对象的内存空间
free(slashClassName);
mJavaVM->DetachCurrentThread();
mJavaVM->DestroyJavaVM();
}
startVm() 创建java虚拟机
int AndroidRuntime::startVm(JavaVM** pJavaVM, JNIEnv** pEnv, bool zygote)
{
//虚拟机产生的trace文件,主要用于分析系统问题,路径默认为/data/anr/traces.txt
parseRuntimeOption("dalvik.vm.stack-trace-file", stackTraceFileBuf, "-Xstacktracefile:");
//对于不同的软硬件环境,这些参数往往需要调整、优化,从而使系统达到最佳性能
parseRuntimeOption("dalvik.vm.heapstartsize", heapstartsizeOptsBuf, "-Xms", "4m");
//preloaded-classes文件内容是由WritePreloadedClassFile.java生成的,
//在ZygoteInit类中会预加载工作将其中的classes提前加载到内存,以提高系统性能
if (!hasFile("/system/etc/preloaded-classes")) {
return -1;
}
//初始化虚拟机
if (JNI_CreateJavaVM(pJavaVM, pEnv, &initArgs) < 0) {
ALOGE("JNI_CreateJavaVM failed\n");
return -1;
}
}
startReg() JNI方法注册
int AndroidRuntime::startReg(JNIEnv* env)
{
//设置线程创建方法为javaCreateThreadEtc
androidSetCreateThreadFunc((android_create_thread_fn) javaCreateThreadEtc);
env->PushLocalFrame(200);
//进程JNI方法的注册
if (register_jni_procs(gRegJNI, NELEM(gRegJNI), env) < 0) {
env->PopLocalFrame(NULL);
return -1;
}
env->PopLocalFrame(NULL);
return 0;
}
ZygoteInit.main() 进入java层
前面AndroidRuntime.start()执行到最后通过反射调用到ZygoteInit.main()。
public static void main(String argv[]) {
try {
RuntimeInit.enableDdms(); //开启DDMS功能
SamplingProfilerIntegration.start();
boolean startSystemServer = false;
String socketName = "zygote";
String abiList = null;
for (int i = 1; i < argv.length; i++) {
if ("start-system-server".equals(argv[i])) {
startSystemServer = true;
} else if (argv[i].startsWith(ABI_LIST_ARG)) {
abiList = argv[i].substring(ABI_LIST_ARG.length());
} else if (argv[i].startsWith(SOCKET_NAME_ARG)) {
socketName = argv[i].substring(SOCKET_NAME_ARG.length());
} else {
throw new RuntimeException("Unknown command line argument: " + argv[i]);
}
}
...
registerZygoteSocket(socketName); //为Zygote注册socket
preload(); // 预加载类和资源
SamplingProfilerIntegration.writeZygoteSnapshot();
gcAndFinalize(); //GC操作
if (startSystemServer) {
startSystemServer(abiList, socketName);//启动system_server
}
runSelectLoop(abiList); //进入循环模式
closeServerSocket();
} catch (MethodAndArgsCaller caller) {
caller.run(); //启动system_server中会讲到。
} catch (RuntimeException ex) {
closeServerSocket();
throw ex;
}
}
registerZygoteSocket
创建socket的本地服务端
private static void registerZygoteSocket(String socketName) {
if (sServerSocket == null) {
int fileDesc;
final String fullSocketName = ANDROID_SOCKET_PREFIX + socketName;
try {
String env = System.getenv(fullSocketName);
fileDesc = Integer.parseInt(env);
} catch (RuntimeException ex) {
...
}
try {
FileDescriptor fd = new FileDescriptor();
fd.setInt$(fileDesc); //设置文件描述符
sServerSocket = new LocalServerSocket(fd); //创建Socket的本地服务端
} catch (IOException ex) {
...
}
}
}
preload
将其中的classes提前加载到内存,以提高系统性能
static void preload() {
//预加载位于/system/etc/preloaded-classes文件中的类
preloadClasses();
//预加载资源,包含drawable和color资源
preloadResources();
//预加载OpenGL
preloadOpenGL();
//通过System.loadLibrary()方法,
//预加载"android","compiler_rt","jnigraphics"这3个共享库
preloadSharedLibraries();
//预加载 文本连接符资源
preloadTextResources();
//仅用于zygote进程,用于内存共享的进程
WebViewFactory.prepareWebViewInZygote();
}
执行Zygote进程的初始化,对于类加载,采用反射机制Class.forName()方法来加载。对于资源加载,主要是 com.android.internal.R.array.preloaded_drawables和com.android.internal.R.array.preloaded_color_state_lists,在应用程序中以com.android.internal.R.xxx开头的资源,便是此时由Zygote加载到内存的。zygote进程内加载了preload()方法中的所有资源,当需要fork新进程时,采用copy on write技术。