在init.rc中有如下一段:
service zygote /system/bin/app_process -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
(关于init进程我会重新写一遍文章介绍,这里只讲zygote的启动)
zygote的实际进程是/system/bin/app_process,通过提供适当的参数即可给你的java程序提供一个虚拟机环境以供运行。
这里我们先来看看另外一个使用app_process 的地方,这就是当你运行adb install 的时候,惊呆了吧?
看frameworks\base\cmds\pm\pm文件的内容便知,
base=/system
export CLASSPATH=$base/framework/pm.jar
exec app_process $base/bin com.android.commands.pm.Pm "$@"
该shell脚本实现了从c或者shell环境调用java的目的,很神奇吧?还有我们熟悉的adb shell am start -a "ACTION"中的am也是采用相同原理实现的。
那我们就来看看app_process是个神马东东。
入口在frameworks\base\cmds\app_process\app_main.cpp中的main函数。先来看个图
详细的代码流程就不介绍了,自个看代码去吧,再说就算你看了代码如果不从整体上来了解最终也是事倍工半的。
app_process中定义了一个类 class AppRuntime : public AndroidRuntime
显然继承自AndroidRuntime并实现了其中的几个接口,onStarted、onZygoteInit、onExit。记住这个内部类很重要,他是一切的开始和承接点!
上图显示的是init.rc中启动systemserver的过程,此外还有pm命令,应用程序的启动都是从此开始,服务先启动,然后再是应用。
1.systemserver的启动
通过init.rc中向app_process传入参数调用,app_process调用AppRuntime的start函数,即AndroidRuntime的start函数,它初始化了javavm,注册
了系统服务等需要用到的JNI方法,这是运行java程序的基础,然后调用ZygoteInit的main函数,在其中预加载类和资源,注册zygote socket,一方面
等待AMS的连接以创建应用进程,一方面运行startSystemServer产生systemserver 进程,并调用RuntimeInit的zygoteInit方法,后者调用nativeZygoteInit
方法,该方法是jni方法,实现在AndroidRuntime中,jni方法调用gCurRuntime->onZygoteInit(),gCurRuntime就是AppRuntime了,该方法用来开始binder
通信,然后通过applicationInit调用到了SystemServer的main方法,于是systemserver就启动了。
2.pm的启动
在app_process中有这么一段
if (zygote) {
runtime.start("com.android.internal.os.ZygoteInit",
startSystemServer ? "start-system-server" : "");
} else if (className) {
// Remainder of args get passed to startup class main()
runtime.mClassName = className;
runtime.mArgC = argc - i;
runtime.mArgV = argv + i;
runtime.start("com.android.internal.os.RuntimeInit",
application ? "application" : "tool");
}
pm是通过
runtime.start("com.android.internal.os.RuntimeInit",
application ? "application" : "tool");
来启动的,即相对SystemServer运行的是RuntimeInit中的main方法,然后调用jni方法nativeFinishInit,同样是实现在AndroidRuntime中,通过调用AppRuntime的onStarted方法来调用命令行参数class com.android.commands.pm.Pm 的main方法。
从上可知,systemserver启动调用流程是app_process->AndroidRuntime->ZygoteInit->RuntimeInit
pm的流程是app_process->AndroidRuntime->RuntimeInit,当然也得益于systemserver先运行来预加载类等在ZygoteInit中的操作。