Linux系统启动流程

Linux启动概述

  android系统内核实质是使用了Linux的内核,所以在谈到android app启动流程就必须先了解Linux启动流程;当们启动Linux系统时,bootloader回加载linux内核到内存运行,完成后会启动系统的第一个进程(init进程),其完成后会主动创建许多(Daemon)守护进程,保证一些服务能正常开启,如usb daemon进程,保证usb驱动服务正常运行。

android相关概述

  init进程会创建android底层的一个Zygote进程,Zygote进程会初始化第一个VM虚拟器,并且加载android相关的framework和app所需要的资源,然后Zygote会开启一个socket来监听外部请求,如果受到请求,会根据已有的VM孵化出一个新的VM和进程;
  随后,Zygote会创建一个System Server进程,此进程会启动android相关的所有核心服务,入AMS(Activity Manager Service)和其他服务进程等,至此,系统会启动第一个App–Home进程,Home进程就是手机的桌面进程。

启动桌面上的app

  

android app 启动分析 android app启动流程分析_android


  

  1. 点击桌面app icon -> home的onclick()方法 -> startActivity(Intent)

  

  2. 通过Binder通信进制,将此次启动信息通知给ActivityManagerService,在service内部会做如下操作:

     a. 收集此次启动的对象信息,并封装在intent对象里面去 — PackageManager的resolveIntent()方法

     b. 验证用户是否有足够的权限来启动这个activity — grantUriPermissionLocked()

     c. 如果有权限,AMS就会启动这个activity,如果这个activity的进程ProcessRecord为null的话,就会为其创建一个新进程;反之,则回去打开已经存在的activity

     接下来,就开始分析AMS如何具体的启动activity

     

  3. AMS创建进程启动app

    AMS调用startProcessLocked()方法创建新进程,并且通过socket通道传递请求给Zygote进程,Zygote进程会根据收到的请求孵化出一个自身,并调用ZygoteInit.main来实例化一个ActivityThead,ActivityThread的main方法就是作为app的起始入口。

    

android app 启动分析 android app启动流程分析_java_02


  4. ActivityThread的main入口是app的起始入口,它是app进程的主线程,管理Activity和Application的启动和生命周期的调用等等

ActivityThread启动细节

android app 启动分析 android app启动流程分析_android_03

两个重要内部类

ApplicationThread 和 H

1. main入口

public static void main(String[] args) {
    //创建Looper对象, 创建MessageQueue对象
        Looper.prepareMainLooper();

    //创建自己的ActivityThread对象
        ActivityThread thread = new ActivityThread();
        thread.attach(false);                 // --- 这个很重要

        if (sMainThreadHandler == null) {
            sMainThreadHandler = thread.getHandler();
        }

        AsyncTask.init();

        if (false) {
            Looper.myLooper().setMessageLogging(new
                    LogPrinter(Log.DEBUG, "ActivityThread"));
        }

    //进入消息循环
        Looper.loop();

        throw new RuntimeException("Main thread loop unexpectedly exited");
    }
}
//applicationThread实质是一个binder实例,将binder实例绑定到AMS
private void attach(boolean system) {
    ...
    //获得AMS(ActivityManagerService)实例, AMS的log tag: "ActivityManager"
    IActivityManager mgr = ActivityManagerNative.getDefault();
    //把ApplicationThread对象传给AMS
    mgr.attachApplication(mAppThread);
    ...
}

2. attachApplication绑定ApplicationThread,收集进程的信息,并通过ApplicationThread的bindApplication接口跨进程回传此次新进程信息给ActivityThread

public final class ActivityManagerService extends ActivityManagerNative {
    ...
    public final void attachApplication(IApplicationThread thread) {
        ...
        attachApplicationLocked(thread, callingPid);
        ...
    }
    ...
    private final boolean attachApplicationLocked(IApplicationThread thread, int pid) {
        ....
        //通过binder,跨进程调用ApplicationThread的bindApplication()方法, 下面代码逻辑重回ActivityThread.java
            thread.bindApplication(processName, appInfo, providers,
                    app.instrumentationClass, profileFile, profileFd, profileAutoStop,
                    app.instrumentationArguments, app.instrumentationWatcher,
                    app.instrumentationUiAutomationConnection, testMode, enableOpenGlTrace,
                    isRestrictedBackupMode || !normalMode, app.persistent,
                    new Configuration(mConfiguration), app.compat, getCommonServicesLocked(),
                    mCoreSettingsObserver.getCoreSettingsLocked());
        ....

    }
}

这个时候还在Binder进程中,利用Handler把消息传回给ActivityThread

//ActivityThread.java

private class ApplicationThread extends Binder implements IApplicationThread{

    ...
        public final void bindApplication(String processName,
                ApplicationInfo appInfo, List<ProviderInfo> providers,
                ComponentName instrumentationName, String profileFile,
                ParcelFileDescriptor profileFd, boolean autoStopProfiler,
                Bundle instrumentationArgs, IInstrumentationWatcher instrumentationWatcher,
                IUiAutomationConnection instrumentationUiConnection, int debugMode,
                boolean enableOpenGlTrace, boolean isRestrictedBackupMode, boolean persistent,
                Configuration config, CompatibilityInfo compatInfo, Map<String, IBinder> services,
                Bundle coreSettings) {

            AppBindData data = new AppBindData();
            data.processName = processName;
            data.appInfo = appInfo;
            data.providers = providers;
            data.instrumentationName = instrumentationName;
            data.instrumentationArgs = instrumentationArgs;
            data.instrumentationWatcher = instrumentationWatcher;
            data.instrumentationUiAutomationConnection = instrumentationUiConnection;
            data.debugMode = debugMode;
            data.enableOpenGlTrace = enableOpenGlTrace;
            data.restrictedBackupMode = isRestrictedBackupMode;
            data.persistent = persistent;
            data.config = config;
            data.compatInfo = compatInfo;
            data.initProfileFile = profileFile;
            data.initProfileFd = profileFd;
            data.initAutoStopProfiler = false;
         //发消息
            sendMessage(H.BIND_APPLICATION, data);
        }

    ...
        private void sendMessage(int what, Object obj, int arg1, int arg2, boolean async) {
        Message msg = Message.obtain();
        msg.what = what;
        msg.obj = obj;
        msg.arg1 = arg1;
        msg.arg2 = arg2;
        if (async) {
            msg.setAsynchronous(true);
        }
        //通过mH把BIND_APPLICATION消息发给H处理
        mH.sendMessage(msg);
        }
    ...

}

3. ActivityThread的H接收消息并开启逐步执行Application的oncreate

收到BIND_APPLICATION消息后,创建Application对象以及上下文

//ActivityThread.java
public final class ActivityThread {
    ...
    private void handleBindApplication(AppBindData data) {
        ...
        //创建Instrumentation 对象
                java.lang.ClassLoader cl = instrContext.getClassLoader();
                mInstrumentation = (Instrumentation)
                    cl.loadClass(data.instrumentationName.getClassName()).newInstance();

        data.info = getPackageInfoNoCheck(data.appInfo, data.compatInfo);
        //创建app运行时的上下文对象,并对其进行初始化.
        final ContextImpl appContext = new ContextImpl();
        appContext.init(data.info, null, this);
        //这里的data.info是LoadedApk类的对象
        //在这里创建了上层开发者的代码中所涉及的Applicaiton类的对象
        Application app = data.info.makeApplication(data.restrictedBackupMode, null);
        ...

        //如果有ContentProvider的话, 先加载ContentProvider,后调用Application的onCreate()方法
        List<ProviderInfo> providers = data.providers;
        if (providers != null) {
            installContentProviders(app, providers);
        }
        //调Application的生命周期函数 onCreate()
        mInstrumentation.callApplicationOnCreate(app);

    }
    ...

    private class H extends Handler {
        ...
        public static final int BIND_APPLICATION  = 110;
        ...
        public void handleMessage(Message msg) {
            switch (msg.what) {
                ...
                    case BIND_APPLICATION:
                        Trace.traceBegin(Trace.TRACE_TAG_ACTIVITY_MANAGER, "bindApplication");
                        AppBindData data = (AppBindData)msg.obj;
                        handleBindApplication(data);//调用ActivityThread的handleBindApplication()方法处理
                        Trace.traceEnd(Trace.TRACE_TAG_ACTIVITY_MANAGER);
                        break;
                ...
            }
        }
    }
}

执行application的oncreate方法

// LoadedApk.java
public final class LoadedApk {
    ...
    public Application makeApplication(boolean forceDefaultAppClass,
            Instrumentation instrumentation) {
        Application app = null;
            app = mActivityThread.mInstrumentation.newApplication(
                    cl, appClass, appContext);
        return app;
    }
    ...

}

// Instrumentation.java
public class Instrumentation {
    ...
    public void callApplicationOnCreate(Application app) {
        app.onCreate();
    }
    ...
}

至此,Application启动流程完了;同理,启动activity的流程大致相同;
activty启动开始点在AMS的attachApplicationLocked方法内部,即bindApplication发送Application后,就会开始准备启动Activity,依次调用mStackSupervisor.attachApplicationLocked(app), 在里面再调用realStartActivityLocked(), 里面再调用app.thread.scheduleLaunchActivity(), 也就是mAppThread的scheduleLaunchActivity(), 在ApplicationThread的scheduleLaunchActivity()内,发送一个”LAUNCH_ACTIVITY”消息, mH处理”LAUNCH_ACTIVITY”时调用handleLaunchActivity(), handleLaunchActivity()分两步, 第一步调performLaunchActivity(),
创建Activity的对象, 依次调用它的onCreate(), onStart(). 第二步调handleResumeActivity(), 调用Activity对象的onResume().

至此, 应用启动的完整流程就分析完整了