赞
踩
zygote进程可以理解为Android系统的根进程,有了Zygote进程后,在Zygote进程中会创建SystemServer进程,在SystemServer进程中会去初始化Android系统所需的各种系统服务,先看下整体流程:
电源键按下——>bootloader——>kernal——>init——>zygote——>SystemServer
bootloader:类似于电脑的BIOS引导程序
kernal:android内核层,主要是加载硬件驱动程序,最后会创建一个init进程(/kernal/init/main.c——>kernal_init()——>run_init_process())
init:init进程,linux下的第一个进程,最后会去创建一个Zygote进程(/system/core/rootdir/init.rc——>/system/core/rootdir/init.zygote*.rc——>/framework/base/cmds/app_process/app_main.cpp)
zygote:zygote进程可以理解为android系统的根进程,在init进程执行app_main.cpp这个类的main函数是,会先去创建虚拟机,然后会调用到framework层的com.android.internal.os.ZygoteInit的main函数去初始化一些逻辑
SystemServer:Zygote作为android系统的根进程,首先会去创建一个SystemServer进程,在SystemServer进程中会去初始化各种android系统所需的服务
zygote进程在/frameworks/base/cmds/app_process/app_main.cpp开始初始化,会先去创建虚拟机,最后通过ZygoteInit进入到java世界,我们就先从ZygoteInit(/frameworks/base/core/java/com/android/internal/os/ZygoteInit)的Main函数开始进入:
- public static void main(String argv[]) {
- // 1.创建ZygoteServer
- ZygoteServer zygoteServer = null;
- // 调用native函数,确保当前没有其它线程在运行
- ZygoteHooks.startZygoteNoThreadCreation();
- //设置pid为0,Zygote进入自己的进程组
- Os.setpgid(0, 0);
- ......
- Runnable caller;
- try {
- ......
- //得到systrace的监控TAG
- String bootTimeTag = Process.is64Bit() ? "Zygote64Timing" : "Zygote32Timing";
- TimingsTraceLog bootTimingsTraceLog = new TimingsTraceLog(bootTimeTag,Trace.TRACE_TAG_DALVIK);
- //通过systradce来追踪 函数ZygoteInit, 可以通过systrace工具来进行分析
- //traceBegin 和 traceEnd 要成对出现,而且需要使用同一个tag
- bootTimingsTraceLog.traceBegin("ZygoteInit");
- //开启DDMS(Dalvik Debug Monitor Service)功能
- //注册所有已知的Java VM的处理块的监听器。线程监听、内存监听、native 堆内存监听、debug模式监听等等
- RuntimeInit.enableDdms();
- boolean startSystemServer = false;
- String zygoteSocketName = "zygote";
- String abiList = null;
- boolean enableLazyPreload = false;
-
- //2. 解析app_main.cpp - start()传入的参数
- for (int i = 1; i < argv.length; i++) {
- if ("start-system-server".equals(argv[i])) {
- startSystemServer = true; //启动zygote时,才会传入参数:start-system-server
- } else if ("--enable-lazy-preload".equals(argv[i])) {
- enableLazyPreload = true; //启动zygote_secondary时,才会传入参数:enable-lazy-preload
- } else if (argv[i].startsWith(ABI_LIST_ARG)) { //通过属性ro.product.cpu.abilist64\ro.product.cpu.abilist32 从C空间传来的值
- abiList = argv[i].substring(ABI_LIST_ARG.length());
- } else if (argv[i].startsWith(SOCKET_NAME_ARG)) {
- zygoteSocketName = argv[i].substring(SOCKET_NAME_ARG.length()); //会有两种值:zygote和zygote_secondary
- } else {
- throw new RuntimeException("Unknown command line argument: " + argv[i]);
- }
- }
-
- // 根据传入socket name来决定是创建socket还是zygote_secondary
- final boolean isPrimaryZygote = zygoteSocketName.equals(Zygote.PRIMARY_SOCKET_NAME);
- // 在第一次zygote启动时,enableLazyPreload为false,执行preload
- if (!enableLazyPreload) {
- //systrace 追踪 ZygotePreload
- bootTimingsTraceLog.traceBegin("ZygotePreload");
- EventLog.writeEvent(LOG_BOOT_PROGRESS_PRELOAD_START,
- SystemClock.uptimeMillis());
-
- // 3.加载进程的资源和类
- preload(bootTimingsTraceLog);
- EventLog.writeEvent(LOG_BOOT_PROGRESS_PRELOAD_END,
- SystemClock.uptimeMillis());
- //systrae结束 ZygotePreload的追踪
- bootTimingsTraceLog.traceEnd(); // ZygotePreload
- } else {
- // 延迟预加载, 变更Zygote进程优先级为NORMAL级别,第一次fork时才会preload
- Zygote.resetNicePriority();
- }
-
- //结束ZygoteInit的systrace追踪
- bootTimingsTraceLog.traceEnd(); // ZygoteInit
- //禁用systrace追踪,以便fork的进程不会从zygote继承过时的跟踪标记
- Trace.setTracingEnabled(false, 0);
- // 4.调用ZygoteServer 构造函数,创建socket,会根据传入的参数,
- // 创建两个socket:/dev/socket/zygote 和 /dev/socket/zygote_secondary
- zygoteServer = new ZygoteServer(isPrimaryZygote);
- if (startSystemServer) {
- //5. fork出system server
- Runnable r = forkSystemServer(abiList, zygoteSocketName, zygoteServer);
- // 启动SystemServer
- if (r != null) {
- r.run();
- return;
- }
- }
-
- // 6. zygote进程进入无限循环,处理请求,在ActivityMangerService中请求创建进程时就会执行到这里,比如打开一个新的应用
- caller = zygoteServer.runSelectLoop(abiList);
- } catch (Throwable ex) {
- Log.e(TAG, "System zygote died with exception", ex);
- throw ex;
- } finally {
- if (zygoteServer != null) {
- zygoteServer.closeServerSocket();
- }
- }
-
- // 7.在子进程中已经退出了select循环。继续执行命令
- if (caller != null) {
- caller.run();
- }
- }
对于代码中标序号的,这里说明几点:
第3点预加载:
什么是预加载:
预加载是指在zygote进程启动的时候就加载,这样系统只在zygote执行一次加载操作,所有APP用到该资源不需要再重新加载,减少资源加载时间,加快了应用启动速度,一般情况下,系统中App共享的资源会被列为预加载资源。
zygote fork子进程时,根据fork的copy-on-write机制可知,有些类如果不做改变,甚至都不用复制,子进程可以和父进程共享这部分数据,从而省去不少内存的占用。
预加载的原理:
zygote进程启动后将资源读取出来,保存到Resources一个全局静态变量中,下次读取系统资源的时候优先从静态变量中查找。
第4点创建Socket:
通过ZygoteServer创建Socket是通过文件描述符来创建的,内部会保存描述符用于后续Socket的创建,主要作用是:1、用于创建SystemServer;2、通过调用ZygoteServer.runSelectLoop()用于等待后续请求进程的创建。
第5点SystemServer创建:
在forkSystemServer()方法中,会去执行handleSystemServerProcess()方法,最终会创建SystemServer进程,并执行SystemServer的main()方法,由此就进入到SystemServer并初始化各种系统服务
第6点执行runSelectLoop:
这是一个无限循环函数,里面开启了一个Socket来监听请求,它有什么作用呢?我们这里直接举一个列子:
假如有一个没有启动的A应用,现在我们点击A应用的启动图标,这个时候就会进入到ActivityManagerService中去检查A应用是否启动了,没有启动的话,就会通过Socket请求创建A应用的进程,最终就会执行到runSelectLoop这个函数中去创建进程,最终会执行到android.app.ActivityThread的main()函数,这也就是为什么我们有时会听到,一个应用进程是从ActivityThread开始的。
好了,Zygote进程就到这里,下一篇再来看看SystemServer进程。
Copyright © 2003-2013 www.wpsshop.cn 版权所有,并保留所有权利。