应用程序的启动,又可称为根Activity的启动。但是在讲应用程序启动之前,我们有必要对应用程序进程(AppProcess)启动有所了解,那是因为启动一个应用程序首先要保证该应用程序的进程已经被启动。AMS在启动应用程序时,会先检查应用程序进程是否存在,如果不存在就需要请求Zygote进程创建并启动应用程序进程。这里我不会贴上大段大段的代码,只是一些总结,并提供了相关源码的链接。


应用程序进程(AppProcess)启动

启动大纲


  1. AMS发送启动应用程序进程请求.
  2. Zygote接收请求并创建应用程序进程.

AMS发送启动应用程序进程请求

Android源码分析--应用程序启动_Android


  • AMS通过调用​​startProcessLocked​​方法向Zygote进程发送请求。
  • ​Process​​调用​​start​​方法,使用​​ZygoteProcess​​的​​start​​方法。
  • 在ZygoteProcess的​​start​​方法中,先后调用了​​startViaZygote​​、​​zygoteSendArgsAndGetResult​​和​​openZygoteSocketIfNeeded​​等方法,最后在​​openZygoteSocketIfNeeded​​方法中调用了​​ZygoteState​​的connect方法建立与Zygote进程的连接。


AMS发送启动应用程序进程请求

Android源码分析--应用程序启动_源码分析_02


  • ​ZygoteServer​​执行​​runSelectLoop​​方法,一直等待AMS的请求数据到来。
  • 当AMS请求到来,与Zygote进程建立连接后,由​​ZygoteConnection​​的​​processOneCommand​​方法处理请求的数据。对请求数据进行解析,获取程序进程的启动参数,并通过​​Zygote​​的​​forkAndSpecialize​​方法进行应用程序进程的创建。
  • 进程创建完成后,交由​​ZygoteInit​​的​​zygoteInit​​方法和​​RuntimeInit​​的​​applicationInit​​方法分别进行进程和应用的初始化。在​​zygoteInit​​方法中,为应用程序进程创建了Binder线程池,这样进程就可以跨进程进行通信了。而​​applicationInit​​方法通过反射最终会调用​​ActivityThread​​的​​main​​方法,从而完成应用程序进程的创建。


应用程序(App)启动


讲完了应用程序进程(AppProcess)启动的相关内容后,接下来我们就来看看应用程序是如何一步一步启动的。


启动大纲


  1. Launcher请求AMS。
  2. AMS请求ApplicationThread。
  3. ActivityThread启动Activity。

启动时序图

Android源码分析--应用程序启动_Android_03

Launcher请求AMS

Android源码分析--应用程序启动_进程创建_04


  • 当我们点击应用程序的图标时,就会自动调用​​Launcher​​的​​startActivitySafely​​方法, 最终会调用​​Activity​​的​​startActivity​​方法。
  • 在Activity的​​startActivity​​中又调用了​​startActivityForResult​​方法,而​​startActivityForResult​​方法内部又调用了​​Instrumentation​​的​​execStartActivity​​方法。
  • 在Instrumentation的​​execStartActivity​​方法中又通过​​ActivityManager​​的​​getService​​方法获取了IBinder类型的AMS引用​​IActivityManager​​,最后调用了​​AMS​​的​​startActivity​​方法。

AMS请求ApplicationThread

Android源码分析--应用程序启动_初始化_05


  • 在AMS的​​startActivity​​方法中,又调用了其本身的​​startActivityAsUser​​方法,进行权限的检查。
  • 权限检查完后,调用​​ActivityStarter​​的​​startActivityMayWait​​方法,并在该方法中解析处理应用程序需要的参数,并进行相关参数的初始化,最终会调用其​​startActivity​​方法。而在​​startActivity​​方法中又调用了​​startActivityUnchecked​​方法来处理与栈管理相关的逻辑。
  • 在处理完栈的关系后,紧接着会调用​​ActivityStackSupervisor​​的​​resumeFocusedStackTopActivityLocked​​方法获取需要启动的Activity所在栈的栈顶。
  • 当需要启动的Activity的状态不是RESUMED状态,就需要调用​​ActivityStack​​的​​resumeTopActivityUncheckedLocked​​方法,而它的内部又调用了​​resumeTopActivityInnerLocked​​方法进行一系列的栈状态的判断,最终又回调了ActivityStackSupervisor的​​startSpecificActivityLocked​​方法。
  • 在​​ActivityStackSupervisor​​的​​startSpecificActivityLocked​​方法中先是获取了即将启动的Activity所在的应用程序进程(就是在这个地方判断应用所在进程是否存在且已启动,如果没有启动,就需要启动应用程序进程),然后调用​​realStartActivityLocked​​方法。
  • 在​​ActivityStackSupervisor​​的​​realStartActivityLocked​​方法中,对启动的应用程序进程进行一系列的判断和处理,最终会调用IBinder类型的ApplicationThread引用​​IApplicationThread​​,通过传入​​IApplicationThread​​建立​​ClientTransaction​​,加入执行​​LaunchActivityItem​​任务,最终实现跨进程执行调用​​ActivityThread​​的​​handleLaunchActivity​​方法。

ActivityThread启动Activity

Android源码分析--应用程序启动_初始化_06


  • 在ActivityThread调用了它的​​handleLaunchActivity​​方法中,会先调用其​​performLaunchActivity​​方法,之后调用​​handleResumeActivity​​,将Activity的状态置为Resume。
  • 在ActivityThread的​​performLaunchActivity​​方法中做了很多事情。


  1. 首先,执行了​​createBaseContextForActivity​​方法,创建要启动Activity的上下文;
  2. 其次,调用执行了Instrumentation的​​newActivity​​方法来创建Activity实例;
  3. 接着,调用​​LoadedApk​​​的​​makeApplication​​方法,创建应用程序的Application;
  4. 之后,调用需要启动的Activity的​​attach​​方法初始化Activity,创建Window对象并与Activity自身进行关联。
  5. 最后,调用执行了​​Instrumentation​​​的​​callActivityOnCreate​​方法来启动Activity。

  • 在Instrumentation执行了​​callActivityOnCreate​​​方法中,会调用​​Activity​​​的​​performCreate​​​方法,最终会调用Activity的​​onCreate​​方法,这样应用程序也就启动了。

应用程序启动的进程关系图


应用程序启动的过程中,主要涉及了Launcher进程、SystemServer进程、Zygote进程和应用程序进程这四个进程,它们之间的关系如下。
Android源码分析--应用程序启动_应用程序_07


Android源码分析--应用程序启动_进程创建_08​ 微信公共号

Android源码分析--应用程序启动_应用程序_09