对于Zygote的理解

Zygote是什么?

Zygote是Android系统中的进程,由用户空间的第一个进程——Init进程启动,是Android系统运行的第一个AndroidRuntime进程,同时也是打通Native和Java的桥梁。

Zygote的作用?

Zygote进程的作用主要有两个:

  • 创建SystemServer进程;
  • 孵化其他应用程序进程;

Zygote的启动流程?

  • Zygote进程是由Init进程解析init.zygote.rc文件启动的,zygote所对应的可执行程序app_process,所对应的源文件是App_main.cpp,进程名为zygote;
service zygote /system/bin/app_process -Xzygote /system/bin --zygote --start-system-server
class main
socket zygote stream 660 root system 

首先执行App_main.cpp的main()函数,在这里会执行以下步骤:

1.解析命令参数,也就是上面配置文件中的 --zygote 和 --start-system-server;
2.调用AppRuntime.start("com.android.internal.os.ZygoteInit",...);

  • startVm启动虚拟机;
  • startReg注册JNI函数;

3.通过JNI调用ZygoteInit.java的main()方法,从这里开始进入Java的世界;

运行Zygote的main方法,主要执行以下步骤:
1.预加载:

  • preloadClasses()
  • preloadResources()
  • preloadSharedLibraries()

2.forkSystemServer,最终会调用SystemServer.java的main()方法;
3.创建ZygoteService,进入runSelectLoop;

Zygote需要注意的

1.Zygote进行fork的时候要是单线程,为了避免造成死锁或者状态不一致等问题;
2.Zygote的跨进程通信没有采用Binder机制,而是采用本地socket。

关于Zygote的疑问?

1.孵化应用进程这种事为什么不交给SystemServer来做,而专门设计一个Zygote?

我们知道,应用在启动的时候需要做很多准备工作,包括启动虚拟机,加载各类系统资源等等,这些都是非常耗时的,如果能在zygote里就给这些必要的初始化工作做好,子进程在fork的时候就能直接共享,那么这样的话效率就会非常高。这个就是zygote存在的价值,这一点呢SystemServer是替代不了的,主要是因为SystemServer里跑了一堆系统服务,这些是不能继承到应用进程的。所以给SystemServer和应用进程里都要用到的资源抽出来单独放在一个进程里,也就是这的zygote进程,然后zygote进程再分别孵化出SystemServer进程和应用进程。

  1. Zygote的IPC通信机制为什么使用socket而不采用binder?

主要原因是因为Zygote进行fork的时候要是单线程,父进程binder线程有锁,然后子进程的主线程一直在等其子线程(从父进程拷贝过来的子进程)的资源,但是其实父进程的子进程并没有被拷贝过来,造成死锁,所以fork不允许存在多线程。而非常巧的是Binder通讯偏偏就是多线程,所以干脆父进程(Zygote)这个时候就不使用binder线程。

最后上一张gityuan博客中的Android系统启动流程图:
Android系统启动流程图

引用:http://gityuan.com/2016/02/13/android-zygote/

原文地址:https://www.cnblogs.com/monsterdev/p/12685091.html