欢迎您访问程序员文章站本站旨在为大家提供分享程序员计算机编程知识!
您现在的位置是: 首页

(4.1.52)Android启动流程分析

程序员文章站 2022-05-19 19:17:04
...

高能预警:本文超长,代码超多,但都是核心代码摘录,请耐心阅读。
本文采用顺序方式描述整个流程

主要涉及进程:

  • init进程:linux的根进程,android系统是基于linux系统的,因此可以算作是整个android操作系统的第一个进程
    • Zygote(孵化)进程:android系统的根进程,主要作用:可以作用Zygote进程fork出SystemServer进程和各种应用进程
    • SystemServer进程
      主要是在这个进程中启动系统的各项服务,比如ActivityManagerService,PackageManagerService,WindowManagerService服务等等;
    • 各种应用进程
      启动自己编写的客户端应用时,一般都是重新启动一个应用进程,有自己的虚拟机与运行环境;

android系统中进程之间通讯的方式是Binder,但是有一个例外是SystemService进程与Zygote进程之间是通过Socket的方式进行通讯的

一、Zygote孵化进程启动流程

Zygote(孵化)进程是所有的android进程的父进程,包括SystemServer和各种应用进程都是通过Zygote进程fork出来的,而Zygote进程则是通过linux系统的init进程启动的。

init进程在启动Zygote进程时一般都会调用ZygoteInit类的main方法,因此我们这里看一下该方法的具体实现(基于android23源码)。

Zygote进程main方法主要执行逻辑:

  • 由init进程fork出来的,并且执行其main方法启动
  • 初始化DDMS;
  • 注册Zygote进程的socket通讯;
  • 初始化Zygote中的各种类,资源文件,OpenGL,类库,Text资源等等;
  • fork出SystemServer进程,并执行其main()方法启动
  • fork出SystemServer进程之后,关闭socket连接;
    public static void main(String argv[]) {
        try {
            //【第1步】调用enableDdms(),设置DDMS可用,可以发现DDMS启动的时机还是比较早的,在整个Zygote进程刚刚开始要启动额时候就设置可用了
            RuntimeInit.enableDdms();
            // Start profiling the zygote initialization.
            SamplingProfilerIntegration.start();

            //【第2.1步】循环主要是解析main方法的参数获取是否需要启动SystemService进程,获取abi列表,获取scoket连接名称
            // android系统中进程之间通讯的方式是Binder,但是有一个例外是SystemService进程与Zygote进程之间是通过Socket的方式进行通讯的   
            boolean startSystemServer = false;
            String socketName = "zygote";
            String abiList = null;
            for (int i = 1; i < argv.length; i++) {
                if ("start-system-server".equals(argv[i])) {
                    startSystemServer = true;
                } else if (argv[i].startsWith(ABI_LIST_ARG)) {
                    abiList = argv[i].substring(ABI_LIST_ARG.length());
                } else if (argv[i].startsWith(SOCKET_NAME_ARG)) {
                    socketName = argv[i].substring(SOCKET_NAME_ARG.length());
                } else {
                    throw new RuntimeException("Unknown command line argument: " + argv[i]);
                }
            }

            if (abiList == null) {
                throw new RuntimeException("No ABI list supplied.");
            }

            //【第2.2步】registerZygoteSocket(String socketName)为Zygote进程注册socket
            registerZygoteSocket(socketName);
            EventLog.writeEvent(LOG_BOOT_PROGRESS_PRELOAD_START,
                SystemClock.uptimeMillis());
            //【第3步】系统方法preLoad()。初始化Zygote中的各种类,资源文件,OpenGL,类库,Text资源等等;    
            preload();
            EventLog.writeEvent(LOG_BOOT_PROGRESS_PRELOAD_END,
                SystemClock.uptimeMillis());

            // Finish profiling the zygote initialization.
            SamplingProfilerIntegration.writeZygoteSnapshot();

            // Do an initial gc to clean up after startup
            gcAndFinalize();

            // Disable tracing so that forked processes do not inherit stale tracing tags from
            // Zygote.
            Trace.setTracingEnabled(false);

            //【第4步】初始化完成之后fork出SystemServer进程;
            if (startSystemServer) {
                startSystemServer(abiList, socketName);
            }

            Log.i(TAG, "Accepting command socket connections");
            runSelectLoop(abiList);

            //【第5步】
            closeServerSocket();
        } catch (MethodAndArgsCaller caller) {
            caller.run();
        } catch (RuntimeException ex) {
            Log.e(TAG, "Zygote died with exception", ex);
            closeServerSocket();
            throw ex;
        }
    }

frameworks/base/core/java/com.android.internal.os.ZygoteInit.java

  • 【第2.2步】registerZygoteSocket(String socketName)为Zygote进程注册socket
private static void registerZygoteSocket(String socketName) {
        if (sServerSocket == null) {
            int fileDesc;
            final String fullSocketName = ANDROID_SOCKET_PREFIX + socketName;
            try {
                String env = System.getenv(fullSocketName);
                fileDesc = Integer.parseInt(env);
            } catch (RuntimeException ex) {
                throw new RuntimeException(fullSocketName + " unset or invalid", ex);
            }

            try {
                FileDescriptor fd = new FileDescriptor();
                fd.setInt$(fileDesc);
                sServerSocket = new LocalServerSocket(fd);
            } catch (IOException ex) {
                throw new RuntimeException(
                        "Error binding to local socket '" + fileDesc + "'", ex);
            }
        }
    }
  • 【第3步】系统方法preLoad()。初始化Zygote中的各种类,资源文件,OpenGL,类库,Text资源等等,这其中:

preloadClasses()用于初始化Zygote中需要的class类;
preloadResources()用于初始化系统资源;
preloadOpenGL()用于初始化OpenGL;
preloadSharedLibraries()用于初始化系统libraries;
preloadTextResources()用于初始化文字资源;
prepareWebViewInZygote()用于初始化webview;

static void preload() {
        Log.d(TAG, "begin preload");
        preloadClasses();
        preloadResources();
        preloadOpenGL();
        preloadSharedLibraries();
        preloadTextResources();
        // Ask the WebViewFactory to do any initialization that must run in the zygote process,
        // for memory sharing purposes.
        WebViewFactory.prepareWebViewInZygote();
        Log.d(TAG, "end preload");
    }
  • 【第4步】初始化完成之后fork出SystemServer进程;
private static boolean startSystemServer(String abiList, String socketName)
            throws MethodAndArgsCaller, RuntimeException {
        long capabilities = posixCapabilitiesAsBits(
            OsConstants.CAP_BLOCK_SUSPEND,
            OsConstants.CAP_KILL,
            OsConstants.CAP_NET_ADMIN,
            OsConstants.CAP_NET_BIND_SERVICE,
            OsConstants.CAP_NET_BROADCAST,
            OsConstants.CAP_NET_RAW,
            OsConstants.CAP_SYS_MODULE,
            OsConstants.CAP_SYS_NICE,
            OsConstants.CAP_SYS_RESOURCE,
            OsConstants.CAP_SYS_TIME,
            OsConstants.CAP_SYS_TTY_CONFIG
        );
        /* Hardcoded command line to start the system server */
        String args[] = {
            "--setuid=1000",
            "--setgid=1000",
            "--setgroups=1001,1002,1003,1004,1005,1006,1007,1008,1009,1010,1018,1021,1032,3001,3002,3003,3006,3007",
            "--capabilities=" + capabilities + "," + capabilities,
            "--nice-name=system_server",
            "--runtime-args",
            "com.android.server.SystemServer",
        };
        ZygoteConnection.Arguments parsedArgs = null;

        int pid;

        try {
            parsedArgs = new ZygoteConnection.Arguments(args);
            ZygoteConnection.applyDebuggerSystemProperty(parsedArgs);
            ZygoteConnection.applyInvokeWithSystemProperty(parsedArgs);

            /* Request to fork the system server process */
            pid = Zygote.forkSystemServer(
                    parsedArgs.uid, parsedArgs.gid,
                    parsedArgs.gids,
                    parsedArgs.debugFlags,
                    null,
                    parsedArgs.permittedCapabilities,
                    parsedArgs.effectiveCapabilities);
        } catch (IllegalArgumentException ex) {
            throw new RuntimeException(ex);
        }

        /* For child process */
        if (pid == 0) {
            if (hasSecondZygote(abiList)) {
                waitForSecondaryZygote(socketName);
            }

            handleSystemServerProcess(parsedArgs);
        }

        return true;
    }

二、SystemServer进程启动流程

SystemServer进程主要的作用是启动各种系统服务,比如ActivityManagerService,PackageManagerService,WindowManagerService等服务,我们平时熟知的各种系统性的服务其实都是在SystemServer进程中启动的,而当我们的应用需要使用各种系统服务的时候其实也是通过与SystemServer进程通讯获取各种服务对象的句柄的进而执行相应的操作的

主要任务:

  1. 由Zygote进程fork出来的,并且执行其main方法启动
  2. 设置系统的语言环境等;
  3. 设置虚拟机运行内存,加载运行库,设置SystemServer的异步消息
  4. 创建上下文Context对象mSystemContext
  5. 使用上下文对象,创建一个新的SystemServiceManager对象,并保存在LocalServices数据结构中(系统各种service服务的实际管理者)
  6. SystemServer进程在尝试启动服务之前会首先尝试与Zygote建立socket通讯,只有通讯成功之后才会开始尝试启动服务;
  7. 使用SystemServiceManager实例注册相关SystemService,并执行其onStart()方法开启(每一个SystemService都有自己的异步消息对象,并运行在单独的线程中)
    • startBootstrapService()启动系统Boot级服务过程
      1. 利用反射,实例、注册并开启[安装服务Installer SystemService]
      2. 实例注册启动ActivityManagerService服务,并为其设置SysServiceManager和Installer
      3. 实例注册启动PowerManagerService服务,并与mActivityManagerService关联
      4. 实例注册启动DisplayManagerService服务,负责管理手机显示方面
      5. 实例注册启动PackageManagerService,负责管理多apk文件的安装,解析,删除,卸载等等操作
      6. 实例注册启动UserManagerService,负责创建和删除用户,以及查询用户信息
      7. 实例注册启动SensorServic,负责各种感应器的状态和数值
      8. 启动系统进程的Application
    • startCoreServices()启动系统核心服务
      1. 实例注册启动LightsService服务,负责管理手机中关于闪光灯,LED等相关的服务
      2. 实例注册启动BatteryService,负责电池相关服务
      3. 实例注册启动UsageStatsManagerInternal,负责收集用户使用每一个APP的频率、使用时常
      4. 实例注册启动WebViewUpdateService,用于WebView的更新
    • startOtherServices() 启动一些非紧要或者是非需要及时启动的服务,并启动Launcher app进程
    • 实例注册启动一些非紧要或者是非需要及时启动的服务
      1. 实例注册启动ContentService,负责数据更新通知的管理者,是数据同步服务的管理中枢
      2. 实例注册启动ContentService,负责手机震动
      3. 实例注册启动ContentService,负责数据库等提供解决方法的服务
      4. 实例注册启动AlarmManagerService,负责定时服务
    • 启动Launcher app进程
      1. vibrator.systemReady();
      2. lockSettings.systemReady();
      3. wm.systemReady();
      4. mPowerManagerService.systemReady
      5. mPackageManagerService.systemReady();
      6. mDisplayManagerService.systemReady
      7. mActivityManagerService.systemReady
        7.1. startSystemUi(context);
        7.2 执行各种SystemService的启动方法,各种SystemService的systemReady方法
      8. 开启主线程Looper

更多服务内容,请移步:Android 系统服务一览表

public static void main(String[] args) {
    new SystemServer().run();
}

只是new出一个SystemServer对象并执行其run方法,查看SystemServer类的定义我们知道其实final类型的,所以我们不能重写或者继承SystemServer。然后我们查看SystemServer.run方法的实现:

    private void run() {
        ...
        //【第1步】首先判断系统当前时间,若当前时间小于1970年1月1日,则一些初始化操作可能会处所,所以当系统的当前时间小于1970年1月1日的时候,设置系统当前时间为该时间点
        if (System.currentTimeMillis() < EARLIEST_SUPPORTED_TIME) {
            Slog.w(TAG, "System clock is before 1970; setting to 1970.");
            SystemClock.setCurrentTimeMillis(EARLIEST_SUPPORTED_TIME);
        }

        ...
        //【第2步】主要是设置系统的语言环境等; 
        if (!SystemProperties.get("persist.sys.language").isEmpty()) {
            final String languageTag = Locale.getDefault().toLanguageTag();

            SystemProperties.set("persist.sys.locale", languageTag);
            SystemProperties.set("persist.sys.language", "");
            SystemProperties.set("persist.sys.country", "");
            SystemProperties.set("persist.sys.localevar", "");
        }

        // Here we go!
        Slog.i(TAG, "Entered the Android system server!");
        EventLog.writeEvent(EventLogTags.BOOT_PROGRESS_SYSTEM_RUN, SystemClock.uptimeMillis());

        ...
        //【第3步】主要是设置虚拟机运行内存,加载运行库,设置SystemServer的异步消息
        SystemProperties.set("persist.sys.dalvik.vm.lib.2", VMRuntime.getRuntime().vmLibrary());

        // Enable the sampling profiler.
        if (SamplingProfilerIntegration.isEnabled()) {
            SamplingProfilerIntegration.start();
            mProfilerSnapshotTimer = new Timer();
            mProfilerSnapshotTimer.schedule(new TimerTask() {
                @Override
                public void run() {
                    SamplingProfilerIntegration.writeSnapshot("system_server", null);
                }
            }, SNAPSHOT_INTERVAL, SNAPSHOT_INTERVAL);
        }

        //[3.1]主要是优化设置systemserver的内存环境,进程优先级等
        // Mmmmmm... more memory!
        VMRuntime.getRuntime().clearGrowthLimit();

        // The system server has to run all of the time, so it needs to be
        // as efficient as possible with its memory usage.
        VMRuntime.getRuntime().setTargetHeapUtilization(0.8f);

        // Some devices rely on runtime fingerprint generation, so make sure
        // we've defined it before booting further.
        Build.ensureFingerprintProperty();

        // Within the system server, it is an error to access Environment paths without
        // explicitly specifying a user.
        Environment.setUserRequired(true);

        // Ensure binder calls into the system always run at foreground priority.
        BinderInternal.disableBackgroundScheduling(true);

        //[3.2]创建main looper thread 
        // Prepare the main looper thread (this thread).
        android.os.Process.setThreadPriority(
                android.os.Process.THREAD_PRIORITY_FOREGROUND);
        android.os.Process.setCanSelfBackground(false);
        Looper.prepareMainLooper();

        //[3.3]初始化native service
        // Initialize native services.
        System.loadLibrary("android_servers");

        // Check whether we failed to shut down last time we tried.
        // This call may not return.
        performPendingShutdown();

        //【第4步】创建上下文Context对象mSystemContext
        // Initialize the system context.
        createSystemContext();

        //【第5步】使用上下文对象,创建一个新的SystemServiceManager对象,并保存在LocalServices数据结构中(系统各种service服务的实际管理者)
        // Create the system service manager.
        mSystemServiceManager = new SystemServiceManager(mSystemContext);
        LocalServices.addService(SystemServiceManager.class, mSystemServiceManager);

        //【第6步】启动:系统Boot级服务,系统核心的服务,一些非紧要或者是非需要及时启动的服务
        // Start services.
        try {
            startBootstrapServices();
            startCoreServices();
            startOtherServices();
        } catch (Throwable ex) {
            Slog.e("System", "******************************************");
            Slog.e("System", "************ Failure starting system services", ex);
            throw ex;
        }

        // For debug builds, log event loop stalls to dropbox for analysis.
        if (StrictMode.conditionallyEnableDebugLogging()) {
            Slog.i(TAG, "Enabled StrictMode for system server main thread.");
        }

        //【第7步】开启主线程Looper
        // Loop forever.
        Looper.loop();
        throw new RuntimeException("Main thread loop unexpectedly exited");
    }

frameworks/base/services/java/com.android.server.SystemServer.java

  • 【第4步】创建上下文Context对象mSystemContext

在SystemServer进程中也存在着Context对象,并且是通过ActivityThread.systemMain方法创建context的,这一部分的逻辑以后会通过介绍Activity的启动流程来介绍,这里就不在扩展,这里我们只知道在SystemServer进程中也需要创建Context对象

private void createSystemContext() {
        ActivityThread activityThread = ActivityThread.systemMain();
        mSystemContext = activityThread.getSystemContext();
        mSystemContext.setTheme(android.R.style.Theme_DeviceDefault_Light_DarkActionBar);
    }

2.1 startBootstrapService启动系统Boot级服务过程

private void startBootstrapServices() {
        //【第1步】利用反射,示例、注册并开启[安装服务Installer SystemService]
        Installer installer = mSystemServiceManager.startService(Installer.class);

        //【第2步】!!!启动ActivityManagerService服务,并为其设置SysServiceManager和Installer
        // Activity manager runs the show.
        mActivityManagerService = mSystemServiceManager.startService(
                ActivityManagerService.Lifecycle.class).getService();
        mActivityManagerService.setSystemServiceManager(mSystemServiceManager);
        mActivityManagerService.setInstaller(installer);

        //【第3步】启动PowerManagerService服务,并与mActivityManagerService关联
        //PowerManagerService主要用于计算系统中和Power相关的计算,然后决策系统应该如何反应。同时协调Power如何与系统其它模块的交互,比如没有用户活动时,屏幕变暗等等。
        mPowerManagerService = mSystemServiceManager.startService(PowerManagerService.class);

        // Now that the power manager has been started, let the activity manager
        // initialize power management features.
        mActivityManagerService.initPowerManagement();

        //【第4步】启动DisplayManagerService服务,负责管理手机显示方面
        // Display manager is needed to provide display metrics before package manager
        // starts up.
        mDisplayManagerService = mSystemServiceManager.startService(DisplayManagerService.class);

        // We need the default display before we can initialize the package manager.
        mSystemServiceManager.startBootPhase(SystemService.PHASE_WAIT_FOR_DEFAULT_DISPLAY);

        // Only run "core" apps if we're encrypting the device.
        String cryptState = SystemProperties.get("vold.decrypt");
        if (ENCRYPTING_STATE.equals(cryptState)) {
            Slog.w(TAG, "Detected encryption in progress - only parsing core apps");
            mOnlyCore = true;
        } else if (ENCRYPTED_STATE.equals(cryptState)) {
            Slog.w(TAG, "Device encrypted - only parsing core apps");
            mOnlyCore = true;
        }

        //【第5步】!!!启动PackageManagerService,负责管理多apk文件的安装,解析,删除,卸载等等操作
        //PackageManagerService服务的启动方式与其他服务的启动方式有一些区别,直接调用了PackageManagerService的静态main方法
        // Start the package manager.
        Slog.i(TAG, "Package Manager");
        mPackageManagerService = PackageManagerService.main(mSystemContext, installer,
                mFactoryTestMode != FactoryTest.FACTORY_TEST_OFF, mOnlyCore);
        mFirstBoot = mPackageManagerService.isFirstBoot();
        mPackageManager = mSystemContext.getPackageManager();

        //【第6步】启动UserManagerService,负责创建和删除用户,以及查询用户信息
        Slog.i(TAG, "User Service");
        ServiceManager.addService(Context.USER_SERVICE, UserManagerService.getInstance());

        // Initialize attribute cache used to cache resources from packages.
        AttributeCache.init(mSystemContext);

        //【第7步】启动系统进程的Application
        // Set up the Application instance for the system process and get started.
        mActivityManagerService.setSystemProcess();

        //【第8步】启动SensorServic,负责各种感应器的状态和数值
        // The sensor service needs access to package manager service, app ops
        // service, and permissions service, therefore we start it after them.
        startSensorService();
    }

frameworks/base/services/java/com.android.server.SystemServer.java

2.1.1 Installer SystemService

系统安装apk时的一个服务类,我们需要在启动完成Installer服务之后才能启动其他的系统服务。 重点看下其onStart函数:

不断的通过ping命令连接Zygote进程(SystemServer和Zygote进程通过socket方式通讯,其他进程通过Binder方式通讯)

    @Override
    public void onStart() {
        Slog.i(TAG, "Waiting for installd to be ready.");
        mInstaller.waitForConnection();
    }

    public void waitForConnection() {
        for (;;) {
            if (execute("ping") >= 0) {
                return;
            }
            Slog.w(TAG, "installd not ready");
            SystemClock.sleep(1000);
        }
    }

2.1.2 ActivityManagerService.Lifecycle SystemService

public static final class Lifecycle extends SystemService {
        private final ActivityManagerService mService;

        public Lifecycle(Context context) {
            super(context);
            mService = new ActivityManagerService(context);
        }

        @Override
        public void onStart() {
            mService.start();
        }

        public ActivityManagerService getService() {
            return mService;
        }
    }

Lifecycle是ActivityManagerService的一个静态内部类,其onStart()函数其实是ActivityManagerService的start方法:

private void start() {
        Process.removeAllProcessGroups();
        mProcessCpuThread.start();

        mBatteryStatsService.publish(mContext);
        mAppOpsService.publish(mContext);
        Slog.d("AppOps", "AppOpsService published");
        LocalServices.addService(ActivityManagerInternal.class, new LocalService());
    }

ActivityManagerService的创建过程比较复杂这里不做过多的分析了,主要是在其构造方法中初始化了一些变量

2.1.3 PackageManagerService

直接使用new的方式创建了一个PackageManagerService对象,并在其构造方法中初始化相关变量,最后调用了ServiceManager.addService方法,主要是通过Binder机制与JNI层交互,这里不再扩展

public static PackageManagerService main(Context context, Installer installer,
            boolean factoryTest, boolean onlyCore) {
        PackageManagerService m = new PackageManagerService(context, installer,
                factoryTest, onlyCore);
        ServiceManager.addService("package", m);
        return m;
    }

2.2 startCoreServices()启动系统核心服务

private void startCoreServices() {

        //【第1步】启动LightsService服务,负责管理手机中关于闪光灯,LED等相关的服务
        // Manages LEDs and display backlight so we need it to bring up the display.
        mSystemServiceManager.startService(LightsService.class);

        //【第2步】启动BatteryService,负责电池相关服务
        // Tracks the battery level.  Requires LightService.
        mSystemServiceManager.startService(BatteryService.class);

        //【第3步】启动UsageStatsManagerInternal,负责收集用户使用每一个APP的频率、使用时常
        // Tracks application usage stats.
        mSystemServiceManager.startService(UsageStatsService.class);
        mActivityManagerService.setUsageStatsManager(
                LocalServices.getService(UsageStatsManagerInternal.class));
        // Update after UsageStatsService is available, needed before performBootDexOpt.
        mPackageManagerService.getUsageStatsIfNoPackageUsageInfo();

        //【第4步】启动WebViewUpdateService,用于WebView的更新
        // Tracks whether the updatable WebView is in a ready state and watches for update installs.
        mSystemServiceManager.startService(WebViewUpdateService.class);
    }

frameworks/base/services/java/com.android.server.SystemServer.java

2.3 startOtherServices() 启动一些非紧要或者是非需要及时启动的服务

private void startOtherServices() {  

             final Context context = mSystemContext;
/*********************************第一部分:启动服务过程*****************************************************************/
            AccountManagerService accountManager = null;
            ContentService contentService = null;
            VibratorService vibrator = null;
            IAlarmManager alarm = null;
            MountService mountService = null;
            NetworkManagementService networkManagement = null;
            NetworkStatsService networkStats = null;
            NetworkPolicyManagerService networkPolicy = null;
            ConnectivityService connectivity = null;
            NetworkScoreService networkScore = null;
            NsdService serviceDiscovery= null;
            WindowManagerService wm = null;
            BluetoothManagerService bluetooth = null;
            UsbService usb = null;
            SerialService serial = null;
            NetworkTimeUpdateService networkTimeUpdater = null;
            CommonTimeManagementService commonTimeMgmtService = null;
            InputManagerService inputManager = null;
            TelephonyRegistry telephonyRegistry = null;
            ConsumerIrService consumerIr = null;
            AudioService audioService = null;
            MmsServiceBroker mmsService = null;

            //【第1步】启动ContentService,负责数据更新通知的管理者,是数据同步服务的管理中枢
            Slog.i(TAG, "Content Manager");  
            contentService = ContentService.main(context,  
                    mFactoryTestMode == FactoryTest.FACTORY_TEST_LOW_LEVEL);  

            Slog.i(TAG, "System Content Providers");  
            mActivityManagerService.installSystemProviders();  

            //【第2步】启动ibratorService,负责手机震动
            Slog.i(TAG, "Vibrator Service");  
            vibrator = new VibratorService(context);  
            ServiceManager.addService("vibrator", vibrator);  

            //【第3步】启动ContentService,负责数据库等提供解决方法的服务
            Slog.i(TAG, "Consumer IR Service");  
            consumerIr = new ConsumerIrService(context);  
            ServiceManager.addService(Context.CONSUMER_IR_SERVICE, consumerIr);  

            //【第4步】启动AlarmManagerService,负责定时服务
            mAlarmManagerService = mSystemServiceManager.startService(AlarmManagerService.class);  
            alarm = IAlarmManager.Stub.asInterface(  
                    ServiceManager.getService(Context.ALARM_SERVICE));  

            //【第5步】
            Slog.i(TAG, "Init Watchdog");  
            final Watchdog watchdog = Watchdog.getInstance();  
            watchdog.init(context, mActivityManagerService);  

            //【第6步】
            Slog.i(TAG, "Input Manager");
            inputManager = new InputManagerService(context);

            //【第7步】实例化WindowManagerService,调用其main函数启动,并与mActivityManagerService关联
            log.i(TAG, "Window Manager");
            wm = WindowManagerService.main(context, inputManager,
                    mFactoryTestMode != FactoryTest.FACTORY_TEST_LOW_LEVEL,
                    !mFirstBoot, mOnlyCore);
            ServiceManager.addService(Context.WINDOW_SERVICE, wm);
            ServiceManager.addService(Context.INPUT_SERVICE, inputManager);

            mActivityManagerService.setWindowManager(wm);

            StatusBarManagerService statusBar = null;
            INotificationManager notification = null;
            InputMethodManagerService imm = null;
            WallpaperManagerService wallpaper = null;
            LocationManagerService location = null;
            CountryDetectorService countryDetector = null;
            TextServicesManagerService tsms = null;
            LockSettingsService lockSettings = null;
            AssetAtlasService atlas = null;
            MediaRouterService mediaRouter = null;

            //...【n步启动服务过程】
            mSystemServiceManager.startService(LauncherAppsService.class);

/*********************************第二部分:启动app过程*****************************************************************/            
            // It is now time to start up the app processes...
            try {
            vibrator.systemReady();
            } catch (Throwable e) {
                reportWtf("making Vibrator Service ready", e);
            }

            if (lockSettings != null) {
                try {
                    lockSettings.systemReady();
                } catch (Throwable e) {
                    reportWtf("making Lock Settings Service ready", e);
                }
            }

            // Needed by DevicePolicyManager for initialization
            mSystemServiceManager.startBootPhase(SystemService.PHASE_LOCK_SETTINGS_READY);

            mSystemServiceManager.startBootPhase(SystemService.PHASE_SYSTEM_SERVICES_READY);

            try {
                wm.systemReady();
            } catch (Throwable e) {
                reportWtf("making Window Manager Service ready", e);
            }

            if (safeMode) {
                mActivityManagerService.showSafeModeOverlay();
            }

             // Update the configuration for this context by hand, because we're going
            // to start using it before the config change done in wm.systemReady() will
            // propagate to it.
            Configuration config = wm.computeNewConfiguration();
            DisplayMetrics metrics = new DisplayMetrics();
            WindowManager w = (WindowManager)context.getSystemService(Context.WINDOW_SERVICE);
            w.getDefaultDisplay().getMetrics(metrics);
            context.getResources().updateConfiguration(config, metrics);

            try {
                // TODO: use boot phase
                mPowerManagerService.systemReady(mActivityManagerService.getAppOpsService());
            } catch (Throwable e) {
                reportWtf("making Power Manager Service ready", e);
            }

            try {
                mPackageManagerService.systemReady();
            } catch (Throwable e) {
                reportWtf("making Package Manager Service ready", e);
            }

            try {
                // TODO: use boot phase and communicate these flags some other way
                mDisplayManagerService.systemReady(safeMode, mOnlyCore);
            } catch (Throwable e) {
                reportWtf("making Display Manager Service ready", e);
            }

            // We now tell the activity manager it is okay to run third party
            // code.  It will call back into us once it has gotten to the state
            // where third party code can really run (but before it has actually
            // started launching the initial applications), for us to complete our
            // initialization.
            mActivityManagerService.systemReady(new Runnable() {
                @Override
                public void run() {
                    Slog.i(TAG, "Making services ready");
                    mSystemServiceManager.startBootPhase(
                            SystemService.PHASE_ACTIVITY_MANAGER_READY);

                    try {
                        mActivityManagerService.startObservingNativeCrashes();
                    } catch (Throwable e) {
                        reportWtf("observing native crashes", e);
                    }

                    Slog.i(TAG, "WebViewFactory preparation");
                    WebViewFactory.prepareWebViewInSystemServer();

                    try {
                        startSystemUi(context);
                    } catch (Throwable e) {
                        reportWtf("starting System UI", e);
                    }

                    //各种systemReady
                }
            });
...  
}  


static final void startSystemUi(Context context) {
        Intent intent = new Intent();
        intent.setComponent(new ComponentName("com.android.systemui",
                    "com.android.systemui.SystemUIService"));
        //Slog.d(TAG, "Starting service: " + intent);
        context.startServiceAsUser(intent, UserHandle.OWNER);
}

frameworks/base/services/java/com.android.server.SystemServer.java

SystemServiceManager.startService函数利用反射,示例、注册并开启一个SystemService对象

SystemService系统服务的一个抽象接口

  1. 通过反射器构造方法创建出服务类
  2. 添加到SystemServiceManager的服务列表数据
  3. 调用service.onStart()方法
public <T extends SystemService> T startService(Class<T> serviceClass) {
        final String name = serviceClass.getName();
        Slog.i(TAG, "Starting " + name);

        // Create the service.
        if (!SystemService.class.isAssignableFrom(serviceClass)) {
            throw new RuntimeException("Failed to create " + name
                    + ": service must extend " + SystemService.class.getName());
        }
        final T service;
        try {
            Constructor<T> constructor = serviceClass.getConstructor(Context.class);
            service = constructor.newInstance(mContext);
        } catch (InstantiationException ex) {
            throw new RuntimeException("Failed to create service " + name
                    + ": service could not be instantiated", ex);
        } catch (IllegalAccessException ex) {
            throw new RuntimeException("Failed to create service " + name
                    + ": service must have a public constructor with a Context argument", ex);
        } catch (NoSuchMethodException ex) {
            throw new RuntimeException("Failed to create service " + name
                    + ": service must have a public constructor with a Context argument", ex);
        } catch (InvocationTargetException ex) {
            throw new RuntimeException("Failed to create service " + name
                    + ": service constructor threw an exception", ex);
        }

        // Register it.
        mServices.add(service);

        // Start it.
        try {
            service.onStart();
        } catch (RuntimeException ex) {
            throw new RuntimeException("Failed to start service " + name
                    + ": onStart threw an exception", ex);
        }
        return service;
    }

三、Launcher启动流程

Launcher进程用于启动我们平时看到的桌面程序,它其实也是一个android应用程序,只不过这个应用程序是系统默认第一个启动的应用程序。

  • Zygote进程 –> SystemServer进程 –> startOtherService方法 –> ActivityManagerService的systemReady方法 –> startHomeActivityLocked方法 –> ActivityStackSupervisor的startHomeActivity方法 –> 执行Activity的启动逻辑,执行scheduleResumeTopActivities()方法
  • LauncherActivity中是以ListView来显示我们的应用图标列表的,并且为每个Item保存了应用的包名和启动Activity类名,这样点击某一项应用图标的时候就可以根据应用包名和启动Activity名称启动我们的App了

startHomeActivityLocked中涉及应用进程启动 和 Activity启动过程,具体内容见四、五环节

3.1 Launcher 进程启动过程分析

以下我们对启动过程进行源码分析。

SystemServer进程在《startOtherService()启动一些非紧要或者是非需要及时启动的服务,并启动Launcher app进程》的第一阶段【n步启动服务过程】中,会启动LauncherAppService,该服务负责启动Launcher。

而后,在《startOtherService()启动一些非紧要或者是非需要及时启动的服务,并启动Launcher app进程》的第二阶段中会调用:mActivityManagerService#systemReady

ActivityManagerService.java

public void ActivityManagerService#systemReady(final Runnable goingCallback) {
        ...
        // Start up initial activity.
        mBooting = true;
        startHomeActivityLocked(mCurrentUserId, "systemReady");
        ...
    }

重点是在这个方法体中调用了ActivityManagerService#startHomeActivityLocked方法,看其名字就是说开始执行启动homeActivity的操作:

boolean ActivityManagerService#startHomeActivityLocked(int userId, String reason) {

        if (mFactoryTest == FactoryTest.FACTORY_TEST_LOW_LEVEL
                && mTopAction == null) {
            // We are running in factory test mode, but unable to find
            // the factory test app, so just sit around displaying the
            // error message and don't try to start anything.
            return false;
        }

        //【第1步】获取homeActivity的intent
        Intent intent = getHomeIntent();

        ActivityInfo aInfo =
            resolveActivityInfo(intent, STOCK_PM_FLAGS, userId);
        if (aInfo != null) {
            intent.setComponent(new ComponentName(
                    aInfo.applicationInfo.packageName, aInfo.name));
            // Don't do this if the home app is currently being
            // instrumented.
            aInfo = new ActivityInfo(aInfo);
            aInfo.applicationInfo = getAppInfoForUser(aInfo.applicationInfo, userId);
            ProcessRecord app = getProcessRecordLocked(aInfo.processName,
                    aInfo.applicationInfo.uid, true);
            if (app == null || app.instrumentationClass == null) {
                //【第2步】启动launcer Activity
                intent.setFlags(intent.getFlags() | Intent.FLAG_ACTIVITY_NEW_TASK);
                mStackSupervisor.startHomeActivity(intent, aInfo, reason);
            }
        }

        return true;
    }

3.1.1 获取homeActivity的intent

Intent getHomeIntent() {
        Intent intent = new Intent(mTopAction, mTopData != null ? Uri.parse(mTopData) : null);
        intent.setComponent(mTopComponent);
        if (mFactoryTest != FactoryTest.FACTORY_TEST_LOW_LEVEL) {
            intent.addCategory(Intent.CATEGORY_HOME);
        }
        return intent;
    }

启动Launcher的Intent对象中添加了Intent.CATEGORY_HOME常量,这个其实是一个launcher的标志。

一般系统的启动页面Activity都会在androidmanifest一般系统的启动页面Activity都会在androidmanifest.xml中配置这个标志。比如我们在github中的android launcher源码中查看其androidmanifest.xml文件:

(4.1.52)Android启动流程分析
【图1】

可以发现其Activity的定义intentfilter中就是定义了这样的category。不同的手机厂商可能会修改Launcher的源码,但是这个category一般是不会更改的

3.1.2 mStackSupervisor.startHomeActivity启动launcer进程和启动Activity

void startHomeActivity(Intent intent, ActivityInfo aInfo, String reason) {
        moveHomeStackTaskToTop(HOME_ACTIVITY_TYPE, reason);
        //【1】启动launcer进程
        startActivityLocked(null /* caller */
                            , intent, null /* resolvedType */
                            , aInfo, null /* voiceSession */
                            , null /* voiceInteractor */, null /* resultTo */
                            , null /* resultWho */, 0 /* requestCode */
                            , 0 /* callingPid */, 0 /* callingUid */
                            , null /* callingPackage */, 0 /* realCallingPid */
                            , 0 /* realCallingUid */, 0 /* startFlags */
                            , null /* options */, false /* ignoreTargetSecurity */
                            , false /* componentSpecified */
                            , null /* outActivity */, null /* container */,  null /* inTask */);
        if (inResumeTopActivity) {
            // If we are in resume section already, home activity will be initialized, but not
            // resumed (to avoid recursive resume) and will stay that way until something pokes it
            // again. We need to schedule another resume.
            //【2】启动Activity
            scheduleResumeTopActivities();
        }
    }

发现其调用的是scheduleResumeTopActivities()方法,这个方法其实是关于Activity的启动流程的逻辑了,这里我们不在详细的说明,后续说明

3.2 LauncherActivity桌面

Launcher启动的Intent是一个隐式的Intent,所以我们会启动在androidmanifest.xml中配置了相同catogory的activity,android M中配置的这个catogory就是LauncherActivity。

LauncherActivity

  • LauncherActivity继承ListActivity:
<FrameLayout xmlns:android="http://schemas.android.com/apk/res/android"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    >

    <ListView
        android:id="@android:id/list"
        android:layout_width="match_parent"
        android:layout_height="match_parent"
        />

    <TextView
        android:id="@android:id/empty"
        android:layout_width="match_parent"
        android:layout_height="match_parent"
        android:gravity="center"
        android:text="@string/activity_list_empty"
        android:visibility="gone"
        android:textAppearance="?android:attr/textAppearanceMedium"
        />

</FrameLayout>
  • 可以看到我们现实的桌面其实就是一个ListView控件,然后看一下其onCreate方法:
    @Override
    protected void onCreate(Bundle icicle) {
        super.onCreate(icicle);

        mPackageManager = getPackageManager();

        if (!mPackageManager.hasSystemFeature(PackageManager.FEATURE_WATCH)) {
            requestWindowFeature(Window.FEATURE_INDETERMINATE_PROGRESS);
            setProgressBarIndeterminateVisibility(true);
        }
        onSetContentView();

        mIconResizer = new IconResizer();

        mIntent = new Intent(getTargetIntent());
        mIntent.setComponent(null);
        mAdapter = new ActivityAdapter(mIconResizer);

        setListAdapter(mAdapter);
        getListView().setTextFilterEnabled(true);

        updateAlertTitle();
        updateButtonText();

        if (!mPackageManager.hasSystemFeature(PackageManager.FEATURE_WATCH)) {
            setProgressBarIndeterminateVisibility(false);
        }
    }

在LauncherActivity的onCreate方法中初始化了一个PackageManager,其主要作用就是从中查询出系统所有已经安装的应用列表,应用包名,应用图标等信息。然后将这些信息注入到Adapter中,这样就可以将系统应用图标和名称显示出来了。

  • 点击事件
    @Override
    protected void onListItemClick(ListView l, View v, int position, long id) {
        Intent intent = intentForPosition(position);
        startActivity(intent);
    }

    protected Intent intentForPosition(int position) {
        ActivityAdapter adapter = (ActivityAdapter) mAdapter;
        return adapter.intentForPosition(position);
    }

    //adapter#intentForPosition
    public Intent intentForPosition(int position) {
            if (mActivitiesList == null) {
                return null;
            }

            Intent intent = new Intent(mIntent);
            ListItem item = mActivitiesList.get(position);
            intent.setClassName(item.packageName, item.className);
            if (item.extras != null) {
                intent.putExtras(item.extras);
            }
            return intent;
        }

adapter的每一项中都保存了应用的包名可启动Activity名称,所以这里在初始化Intent的时候,直接将这些信息注入到Intent中,然后调用startActivity,就将这些应用启动了

具体的启动过程下文再讲

我们在启动Activity的时候,执行的逻辑就是创建一个Intent对象,然后初始化Intent对象,使用隐式启动的方式启动该Acvitity,这里为什么不能使用显示启动的方式呢?
因为Launcher程序启动的Activity一般都是启动一个新的应用进程,该进程与Launcher进程不是在同一个进程中,所以也就无法引用到启动的Activity字节码,自然也就无法启动该Activity了

四、应用进程启动流程

  • 每一个android应用默认都是在他自己的linux进程中运行。
  • android操作系统会在这个android应用中的组件需要被执行的时候启动这个应用进程,并且会在这个应用进程没有任何组件执行或者是系统需要为其他应用申请更多内存的时候杀死这个应用进程。

所以当我们需要启动这个应用的四大组件之一的时候如果这个应用的进程还没有启动,那么就会先启动这个应用程序进程。

android中应用进程可以通过许多方式启动,比如启动一个Activity,启动一个Service,启动一个ContentProvider或者是一个BroadcastReceiver,也就是说我们可以通过启动四大组件的方式启动应用进程,在应用进程没有启动的时候,如果我们通过启动这些组件,这时候系统会判断当前这些组件所需要的应用进程是否已经启动,若没有的话,则会启动应用进程。

Launcher启动的过程也是先启动Launcher进程再启动其Activity组件

  • 【总入口】Activiyt#startActivity()
  • 【内部调用】Activiyt#startActivityForResult()
  • 【分支判断】判断是否有ParentActivity
  • 【分支2:有父】Activity#startActivityFromChild() 方法:有,则调用mParent.startActivityFromChild方法
  • 【分支1:无父】Instrumentation#execStartActivity() 方法:没有,则启动Binder通信机制,ActivityManagerNative.getDefault().startActivity,远程调用ActivitManagerService
  • 【分支1入口】ActivityManagerNative.getDefault().startActivity:Binder通信
  • 【步骤1】ActivityManagerService#startActivity():被跨进程调用
  • 【步骤1内部】ActvityiManagerService#startActivityAsUser()
  • 【步骤1内部】ActivityStackSupervisor#startActivityMayWait()
  • 【步骤2】ActivityStackSupervisor#startActivityLocked() 方法:相关初始化后,触发该步骤
  • 【步骤3】ActivityStackSupervisor#startActivityUncheckedLocked()方法
  • 【步骤4】ActivityStack#startActivityLocked()方法:主要执行初始化了windowManager服务,然后调用resumeTopActivitiesLocked方法
  • 【步骤5】ActivityStackSupervisor#resumeTopActivitiesLocked()方法:经过循环逻辑判断之后,最终调用了resumeTopActivityLocked方法
  • 【步骤6】ActivityStack#resumeTopActivitiesLocked() 方法
  • 【步骤6重载调用】ActivityStack.resumeTopActivitiesLocked()
  • 【步骤7 核心】* ActivityStack.resumeTopActivityInnerLocked() *:执行当前栈顶Activity的生命周期 或者 判断需要开启进程等
  • 【其他步骤】。。。。。
  • 【步骤8】调用了ActivityStackSupervisor#startSpecificActivityLocked()方法
  • 【分支判断】判断一下需要启动的Activity所需要的应用进程是否已经启动
  • 【分支2:进程已启动】ActivityStackSupervisor#realStartAtivityLocked()
  • 【分支1:进程未启动】ActivityManagerService#startProcessLocked():启动进程
  • 【步骤1】Process#start():传入启动的进程的名称“android.app.ActivityThread”
  • 【步骤2】Process#startViaZygote()
  • 【步骤3】ActivityThread#main():启动了AcitivtyThread进程并执行了方法
  • 【步骤4】 Process#startViaZygote()
  • 【步骤5】 Process#zygoteSendArgsAndGetResult():最终调用了Zygote并通过socket通信的方式让Zygote进程fork除了一个新的进程,并根据我们刚刚传递的”android.app.ActivityThread”字符串,反射出该对象并执行ActivityThread的main方法
  • 【步骤6】 ActivityThread#main():开启主线程Looper循环等其他操作
  • 【步骤7】 ActivityThread#attach():Binder跨进程通信ActivityManagerNative.getDefault().attachApplication()
  • 【步骤8】ActivityManagerService#attachApplication():跨进程通信被调用
  • 【步骤9】ActivityManagerService#attachApplicationLocked():该方法执行了一系列的初始化操作,这样我们整个应用进程已经启动起来了,以确保Activity可以启动
  • 【A.步骤10】thread.bindApplication:biner机制,跨进程通信
  • 【A.步骤11】ApplicationThread#bindApplication:biner机制,跨进程通信被调用
  • 【A.步骤12】ActivityThread.sendMessage()
  • 【A.步骤13】ActivityThread.handleMessage()
  • 【A.步骤14】ActivityThread.handleBindApplication():反射机制创建了Instrumentation对象,并执行了init方法,执行了Insrtumentation对象的初始化;调用了LockedApk.makeApplication方法反射创建了Application对象
  • 【A.步骤15】Instrumentation#callApplicationOnCreate
  • 【A.步骤16】Application#onCreate
  • 【B.步骤10】 ActivityStackSupervisor#attachApplicationLocked()
  • 【B.步骤11】 ActivityStackSupervisor#realStartActivityLocked():启动Acitivity

4.1 Binder通信机制

4.1.2 什么是Binder

Binder是Android跨进程通信方式,它实现了IBinder接口,是ServiceManager连接各种Manager(如WindowManager、ActivityManager等)的桥梁

Android团队想要实现进程之间的通信,需要解决以下几个问题:

  • 1.如何知道客户端需要调用哪个进程以及该进程中的函数?
    只要给每个需要远程通信的类唯一标识就可以通过包名+类名的字符串就可以做到,然后在类里面给每个函数编号即可对函数唯一编码
  • 2.客户端如何将函数形参发送给远程进程中的函数,以及如何将远程进程函数计算结果返回客户端?
    定义一个可打包的接口Parcelable,这个接口提供2个重要函数,分别是将对象中的属性写入到数组和从数组中的数据还原对象,每个可以发送到远程函数作为形参的对象只需实现Parcelable对象即可
  • 3.如何去屏蔽底层通信细节,让实现客户端调用远程函数就像调用本地函数一样?
    定义一个类,由这个类来实现这些细节:首先,这个类得帮用户发送远程请求并将拿到返回结果提交给用户,这是最重要的功能了;其次,如果我想实现服务端,什么时候客户端调用我了,这些细节不用用户操心
    这个类就是Binder,由服务端集成实现

以下就是一个跨进程调用的示例.

第2行代码中,相当于客户端得到了wm,它是WindowManager对象的引用
第6行,客户端调用WindowManager引用的addView函数,将触发远程调用,调用的是运行在systemServer进程中的WindowManager的addView函数

//【第1步】获取WindowManager服务引用
WindowManager wm = (WindowManager)getSystemService(getApplication().WINDOW_SERVICE);  
//布局参数layoutParams相关设置略...
View view=LayoutInflater.from(getApplication()).inflate(R.layout.float_layout, null);  
//【第2步】添加view
wm.addView(view, layoutParams);  
  • 我们先来了解下:【第2步】远程调用过程假设你已经创建好服务端类MyService、客户端类MyClient。在客户端持有MyService的引用,并且调用了MyService的func函数,那么Android内部调用过程如图所示

(4.1.52)Android启动流程分析
【图3】

这张图有一点很重要,就是客户端当前线程会被挂起!因此,如果远程进程是执行长时间的运算,请不要使用主线程去调用远程函数,以防止ANR。

我们对远程进程调用代码执行过程有个初步了解,在Android开发中,我们大量使用到了系统Service,比如媒体播放、各种传感器以及WindowManagerService等等等等(太多了~)。
那么Android是什么时候创建这些服务,并且如何实现随时随地可以获取到引用呢?

  • 【第1步】创建服务SystemService类和注册全局引用

如果还记得上文的《二、SystemServer进程启动流程》的“**使用SystemServiceManager实例注册相关SystemService,并执行其onStart()方法开启”过程,你会发现我对每个服务的描述都是 “实例、注册、启动”

也就是说,在Android开机启动过程中,Android会初始化系统的各种Service,并将这些Service向ServiceManager全局注册(即让ServiceManager管理),客户端想要得到具体的Service直接向ServiceManager要即可

由此,我们可以从逻辑上大概明白基本过程:

  1. Service在服务端实例化、全局注册、并启动,开始监听请求
  2. 客户端向ServiceManager查询得到具体的Service引用,并通过这个引用向具体的服务端发送请求以申请远程跨进程调用,同时挂起当前线程等待返回
  3. Binder驱动将客户端的相关参数转给服务端的service,并调用响应函数进行处理,并将结果返回给客户端
  4. 客户端线程被唤起,并响应

(4.1.52)Android启动流程分析
【图4】

!!!实际上,我们获取的Service对象并不是实际的对象类,而是其代理。运用了代理模式:在触发原对象的同时,还会触发Binder驱动的相关操作
* 代理的对象,是客户端持有的远程服务引用, 实际上甚至这个引用也并不是真正的远程Binder对象,下文讲到*

4.1.3 Binder驱动

服务端跨进程的类都要继承Binder类,我们所持有的Binder引用(即服务端的类引用)并不是实际真实的远程Binder对象,我们的引用在“Binder驱动”里还要做一次映射

在《4.1.2环节》中,我们得知“客户端持有远程进程的某个对象引用,然后调用引用类中的函数,远程进程的函数就执行了”。学过操作系统都知道,不同的进程之间是不共享资源的。也就是说,客户端持有的这个对象跟远程进程中的实际对象完全是两个不同的对象。客户端调用引用的对象跟远程进程半毛钱关系都没有,凭啥远程进程就调用了执行了?

其中核心部分就是“Binder驱动”,它承载了核心任务:

(4.1.52)Android启动流程分析
【图5】

  1. 客户端要调用远程对象函数时,只需把数据写入到Parcel,在调用所持有的Binder引用的transact()函数,transact函数执行过程中会把参数、标识符(标记远程对象及其函数)等数据放入到Client的共享内存
  2. Binder驱动从Client的共享内存中读取数据,根据这些数据找到对应的远程进程的共享内存,把数据拷贝到远程进程的共享内存中,并通知远程进程执行onTransact()函数,这个函数也是属于Binder类
  3. 远程进程Binder对象执行完成后,将得到的写入自己的共享内存中,Binder驱动再将远程进程的共享内存数据拷贝到客户端的共享内存,并唤醒客户端线程

以上也就是Binder类的真正功能,我们回顾下《4.1.2环节》的示例:

  1. getSystemService(getApplication().WINDOW_SERVICE);函数内部原理就是向ServiceManager查询标识符为getApplication().WINDOW_SERVICE的远程对象的引用,该对象继承Binder类
  2. 客户端持有远程服务的引用(并不是实际真实的远程Binder对象,这个引用实质上是WindowManager的某个代理
  3. 客户端调用引用的函数,代理把参数打包到Parcel对象中,然后调用transact函数(该函数继承自Binder)
  4. Binder驱动转发
  5. 远程进程服务处理
  6. Binder驱动转发
  7. 客户端响应

关于Binder驱动可能有些误解哦,Binder通过共享內存进行通信,只有一次copy。Process A向Process B传递数据時,这些数据会被driver从ProcessA copy 到 binder和ProcessB之间的共享內存中。ProcessB已经映射过地址,就可以直接读取内存里面的数据了,就不需要再做一次拷贝动作了。可以参考:http://www.cnblogs.com/zhangxinyan/p/3487909.html

4.1.4 Binder源码


ActivityManager am = (ActivityManager) context.getSystemService(Context.ACTIVITY_SERVICE);

//查看getSystemService方法;(Context的实现在ContextImpl里面):
public Object getSystemService(String name) {
    ServiceFetcher fetcher = SYSTEM_SERVICE_MAP.get(name);
    return fetcher == null ? null : fetcher.getService(this);
}

//所有的service对象都保存在一张map里面,我们再看这个map是怎么初始化的:
registerService(ACCOUNT_SERVICE, new ServiceFetcher() {
                public Object createService(ContextImpl ctx) {
                    //【核心】向ServiceManager拿到一个远程对象的 Binder驱动
                    IBinder b = ServiceManager.getService(ACCOUNT_SERVICE);
                    //【核心】将驱动封装为代理对象
                    IAccountManager service = IAccountManager.Stub.asInterface(b);
                    return new AccountManager(ctx, service);
                }});
public static IBinder getService(String name) {
    try {
        IBinder service = sCache.get(name);
        if (service != null) {
            return service;
        } else {
            return getIServiceManager().getService(name);
        }
    } catch (RemoteException e) {
        Log.e(TAG, "error in getService", e);
    }
    return null;
}
  • 我们举系统剪切版服务为例,源码位置为android.content.IClipboard,IClipboard.Stub.asInterface方法代码如下:
public static android.content.IClipboard asInterface(android.os.IBinder obj) {
    if ((obj == null)) {
        return null; 
    }
    android.os.IInterface iin = obj.queryLocalInterface(DESCRIPTOR); // Hook点
    if (((iin != null) && (iin instanceof android.content.IClipboard))) {
        return ((android.content.IClipboard) iin);
    }
    return new android.content.IClipboard.Stub.Proxy(obj);
}

4.2 源码分析

在LauncherActivity的onItemClick函数中,通过应用包名和启动activity类名构造完成Intent之后,我们调用了startActivity方法来启动这个activity。

很明显的,当前这个应用并没有启动,也就是说我们调用的startActivity方法不单单为我们启动了这个activity也同时在启动activity之前启动了这个应用进程,好了,那我们这里就以这个方法为入口分析一下应用进程的启动流程。

    @Override
    public void startActivity(Intent intent, @Nullable Bundle options) {
        if (options != null) {
            startActivityForResult(intent, -1, options);
        } else {
            // Note we want to go through this call for compatibility with
            // applications that may have overridden the method.
            startActivityForResult(intent, -1);
        }
    }

    public void startActivityForResult(Intent intent, int requestCode) {
        startActivityForResult(intent, requestCode, null);
    }

    public void startActivityForResult(Intent intent, int requestCode, @Nullable Bundle options) {
        //【分支判断】判断是否有ParentActivity 
        if (mParent == null) {
            //- 【分支1:无父】Instrumentation#execStartActivity 方法:没有,则启动Binder通信机制,ActivityManagerNative.getDefault().startActivity,远程调用ActivitManagerService
            Instrumentation.ActivityResult ar =
                mInstrumentation.execStartActivity(
                    this    //启动Activity的对象
                    , mMainThread.getApplicationThread() //Binder对象,是主进程的context对象
                    , mToken                            //也是一个Binder对象,指向了服务端一个ActivityRecord对象
                    , this              
                    , intent                            //启动的Intent对象
                    , requestCode                       //请求码
                    , options);                         //参数
            if (ar != null) {
                mMainThread.sendActivityResult(
                    mToken, mEmbeddedID, requestCode, ar.getResultCode(),
                    ar.getResultData());
            }
            //【注意】:调用startActivityForResult的时候只有requestCode的值大于等于0,onActivityResult才会被回调
            if (requestCode >= 0) {
                mStartedActivity = true;
            }

            cancelInputsAndStartExitTransition(options);
            // TODO Consider clearing/flushing other event sources and events for child windows.
        } else {
            //- 【分支2:有父】Activity#startActivityFromChild 方法:有,则调用mParent.startActivityFromChild方法
            if (options != null) {
                mParent.startActivityFromChild(this, intent, requestCode, options);
            } else {
                // Note we want to go through this method for compatibility with
                // existing applications that may have overridden it.
                mParent.startActivityFromChild(this, intent, requestCode);
            }
        }
    }

这里调用了mInstrumentation.execStartActivity方法,这里先简单介绍一下Instrumentation对象,他是Android系统中应用程序端操作Activity的具体操作类,这里的操作端是相对于ActivityManagerService服务端来说的

也就是说当我们在执行对Activity的具体操作时,比如回调生命周期的各个方法都是借助于Instrumentation类来实现的

注意:通过这里的代码我们可以发现,其实我们在Activity中调用startActivity的内部也是调用的startActivityForResult的。
那么为什么调用startActivityForResult可以在Activity中回调onActivityResult而调用startActivity则不可以呢?
可以发现其主要的区别是调用startActivity内部调用startActivityForResult传递的传输requestCode值为-1,也就是说我们在Activity调用startActivityForResult的时候传递的requestCode值为-1的话,那么onActivityResult是不起作用的。
实际上,经测试requestCode的值小于0的时候都是不起作用的,所以当我们调用startActivityForResult的时候需要注意这一点

4.2.1 【分支1】Instrumentation的execStartActivity方法启动Binder通信机制

Instrumentation

public ActivityResult execStartActivity(
            Context who, IBinder contextThread, IBinder token, Activity target,
            Intent intent, int requestCode, Bundle options) {
        ...
        try {
            intent.migrateExtraStreamToClipData();
            intent.prepareToLeaveProcess();
            //【分支1入口】ActivityManagerNative.getDefault().startActivity:Binder通信
            int result = ActivityManagerNative.getDefault()
                .startActivity(whoThread
                , who.getBasePackageName()
                , intent
                , intent.resolveTypeIfNeeded(who.getContentResolver())
                , token
                , target != null ? target.mEmbeddedID : null
                , requestCode
                , 0, null, options);
            checkStartActivityResult(result, intent);
        } catch (RemoteException e) {
            throw new RuntimeException("Failure from system", e);
        }
        return null;
    }

核心代码:ActivityManagerNative.getDefault().startActivity代码,实际上是进程间通讯

这里就用到了《4.1 Binder通信机制》的知识,ActivityManagerService就是这个Binder机制的服务器端对象,而ActivityManagerNative就是这个Binder机制的客户端引用,所以我们这里调用的startActivity实际上是讲参数传递给ActivityManagerService并执行ActivityManagerService的startActivity方法

我们下边分析下,ActivityManagerNative

public abstract class ActivityManagerNative extends Binder implements IActivityManager
{
    //【1】
    static publicIActivityManager  ActivityManagerNative#getDefault() {
            return gDefault.get();
        }

    //【2】gDefault是持有IActivityManager对象的单例器,IActivityManager由asInterface(IBinder)示例
    private static final Singleton<IActivityManager> gDefault = new Singleton<IActivityManager>() {
            protected IActivityManager create() {
                IBinder b = ServiceManager.getService("activity");
                if (false) {
                    Log.v("ActivityManager", "default service binder = " + b);
                }
                IActivityManager am = asInterface(b);
                if (false) {
                    Log.v("ActivityManager", "default service = " + am);
                }
                return am;
            }
        };

    //【3】   最后直接返回一个ActivityManagerProxy对象,该对象为内部类,且继承自IActivityManager
    static public IActivityManager ActivityManagerNative#asInterface(IBinder obj) {
            if (obj == null) {
                return null;
            }
            IActivityManager in =
                (IActivityManager)obj.queryLocalInterface(descriptor);
            if (in != null) {
                return in;
            }

            return new ActivityManagerProxy(obj);
        }

    //【4】
    class ActivityManagerProxy implements IActivityManager
    {
        public ActivityManagerProxy(IBinder remote)
        {
            mRemote = remote;
        }
    }   
}   
  • ActivityManagerProxy 和 ActivityManagerNative 都是继承于IActivityManager
    • ActivityManagerNative是远程服务的本地引用
      继承于Binder接口,ActivityManagerNative extends Binder implements IActivityManager
    • ActivityManagerProxy 是本地引用的代理类,以便于触发binder驱动
      是内部类, ActivityManagerProxy implements IActivityManager
  • 上一节我们介绍SystemServer进程的时候对ActivityManagerService有过了解, ActivityManagerService extends ActivityManagerNative

ActivityManagerNative#getDefault最终返回的是ActivityManagerProxy,这就是我们提到的:

  1. 客户端所持有的 “远程服务端对象Binder引用的代理”,其代理的对象是通过queryLocalInterface从全局查询到的继承自Binder的远程服务引用(和远端进程的服务对象不是同一个,需要binder驱动转化)
  2. 当调用客户端的引用的代理ActivityManagerProxy接口方法的时候,会将数据写入Parcl,并挂起等待
  3. 代理会触发Binder driver,将请求数据与请求传递给server端
  4. 在server端执行具体的接口逻辑,ActivityManagerService#startActivity
  5. 代理触发客户端响应

我们来看看,实际的代理的ActivityManagerProxy#startActivity(),就是承载了步骤2、步骤3和步骤5:

public int startActivity(IApplicationThread caller, String callingPackage, Intent intent,
            String resolvedType, IBinder resultTo, String resultWho, int requestCode,
            int startFlags, ProfilerInfo profilerInfo, Bundle options) throws RemoteException {
        //【步骤2】当调用客户端的引用的代理ActivityManagerProxy接口方法的时候,会将数据写入Parcl,并挂起等待    
        Parcel data = Parcel.obtain();
        Parcel reply = Parcel.obtain();
        data.writeInterfaceToken(IActivityManager.descriptor);
        data.writeStrongBinder(caller != null ? caller.asBinder() : null);
        data.writeString(callingPackage);
        intent.writeToParcel(data, 0);
        data.writeString(resolvedType);
        data.writeStrongBinder(resultTo);
        data.writeString(resultWho);
        data.writeInt(requestCode);
        data.writeInt(startFlags);
        if (profilerInfo != null) {
            data.writeInt(1);
            profilerInfo.writeToParcel(data, Parcelable.PARCELABLE_WRITE_RETURN_VALUE);
        } else {
            data.writeInt(0);
        }
        if (options != null) {
            data.writeInt(1);
            options.writeToParcel(data, 0);
        } else {
            data.writeInt(0);
        }
        //【步骤3】代理会触发Binder driver,将请求数据与请求传递给server端
        mRemote.transact(START_ACTIVITY_TRANSACTION, data, reply, 0);

        //远程服务响应 ActivityManagerService#startActivity

        //【步骤5】代理触发客户端响应
        reply.readException();
        int result = reply.readInt();
        reply.recycle();
        data.recycle();
        return result;
    }

4.2.2 【分支1】跨进程调用ActivityManagerService#startActivity方法

ActivityStack从名称来看是跟栈相关的类,其实它是一个管理类,用来管理系统所有Activity的各种状态。
它由ActivityStackSupervisor来进行管理的,而ActivityStackSupervisor在AMS中的构造方法中被创建

  • 【步骤1】ActivityManagerService#startActivity():被跨进程调用
  • 【步骤1内部】ActvityiManagerService#startActivityAsUser()
  • 【步骤1内部】ActivityStackSupervisor#startActivityMayWait()
  • 【步骤2】ActivityStackSupervisor#startActivityLocked() 方法:相关初始化后,触发该步骤
  • 【步骤3】ActivityStackSupervisor#startActivityUncheckedLocked()方法
  • 【步骤4】ActivityStack#startActivityLocked()方法:主要执行初始化了windowManager服务,然后调用resumeTopActivitiesLocked方法
  • 【步骤5】ActivityStackSupervisor#resumeTopActivitiesLocked()方法:经过循环逻辑判断之后,最终调用了resumeTopActivityLocked方法
  • 【步骤6】ActivityStack#resumeTopActivitiesLocked() 方法
  • 【步骤6重载调用】ActivityStack.resumeTopActivitiesLocked()
  • 【步骤7 核心】* ActivityStack.resumeTopActivityInnerLocked() *:执行当前栈顶Activity的生命周期 或者 判断需要开启进程等
  • 【其他步骤】。。。。。
  • 【步骤8】调用了ActivityStackSupervisor#startSpecificActivityLocked()方法
  • 【分支判断】判断一下需要启动的Activity所需要的应用进程是否已经启动
  • 【分支2:进程已启动】ActivityStackSupervisor#realStartAtivityLocked()
  • 【分支1:进程未启动】ActivityManagerService#startProcessLocked():启动进程
  • 【步骤1】Process#start():传入启动的进程的名称“android.app.ActivityThread”
  • 【步骤2】Process#startViaZygote()
  • 【步骤3】ActivityThread#main():启动了AcitivtyThread进程并执行了方法
  • 【步骤4】 Process#startViaZygote()
  • 【步骤5】 Process#zygoteSendArgsAndGetResult():最终调用了Zygote并通过socket通信的方式让Zygote进程fork除了一个新的进程,并根据我们刚刚传递的”android.app.ActivityThread”字符串,反射出该对象并执行ActivityThread的main方法
  • 【步骤6】 ActivityThread#main():开启主线程Looper循环等其他操作
  • 【步骤7】 ActivityThread#attach():Binder跨进程通信ActivityManagerNative.getDefault().attachApplication()
  • 【步骤8】ActivityManagerService#attachApplication():跨进程通信被调用
  • 【步骤9】ActivityManagerService#attachApplicationLocked():该方法执行了一系列的初始化操作,这样我们整个应用进程已经启动起来了,以确保Activity可以启动
  • 【步骤10】 ActivityStackSupervisor#attachApplicationLocked()
  • 【步骤11】 ActivityStackSupervisor#realStartActivityLocked():启动Acitivity

  • 【步骤1】ActivityManagerService#startActivity:被跨进程调用

    @Override
    public final int ActivityManagerService#startActivity(IApplicationThread caller, String callingPackage,
            Intent intent, String resolvedType, IBinder resultTo, String resultWho, int requestCode,
            int startFlags, ProfilerInfo profilerInfo, Bundle options) {
        return startActivityAsUser(caller, callingPackage, intent, resolvedType, resultTo,
            resultWho, requestCode, startFlags, profilerInfo, options,
            UserHandle.getCallingUserId());
    }

    //【步骤1内部】ActvityiManagerService#startActivityAsUser() 
    @Override
    public final int ActivityManagerService#startActivityAsUser(IApplicationThread caller, String callingPackage,
            Intent intent, String resolvedType, IBinder resultTo, String resultWho, int requestCode,
            int startFlags, ProfilerInfo profilerInfo, Bundle options, int userId) {
        enforceNotIsolatedCaller("startActivity");
        userId = handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(), userId,
                false, ALLOW_FULL_ONLY, "startActivity", null);
        // TODO: Switch to user app stacks here.
        return mStackSupervisor.startActivityMayWait(caller, -1, callingPackage, intent,
                resolvedType, null, null, resultTo, resultWho, requestCode, startFlags,
                profilerInfo, null, null, options, false, userId, null, null);
    }
    //【步骤1内部】ActivityStackSupervisor#startActivityMayWait() 
    final int ActivityStackSupervisor#startActivityMayWait(IApplicationThread caller, int callingUid,
            String callingPackage, Intent intent, String resolvedType,
            IVoiceInteractionSession voiceSession, IVoiceInteractor voiceInteractor,
            IBinder resultTo, String resultWho, int requestCode, int startFlags,
            ProfilerInfo profilerInfo, WaitResult outResult, Configuration config,
            Bundle options, boolean ignoreTargetSecurity, int userId,
            IActivityContainer iContainer, TaskRecord inTask) {
        ...

            int res = startActivityLocked(caller, intent, resolvedType, aInfo,
                    voiceSession, voiceInteractor, resultTo, resultWho,
                    requestCode, callingPid, callingUid, callingPackage,
                    realCallingPid, realCallingUid, startFlags, options, ignoreTargetSecurity,
                    componentSpecified, null, container, inTask);

            ...

            return res;
        }
    }
  • 【步骤2】ActivityStackSupervisor#startActivityLocked 方法:相关初始化后,触发该步骤
    如果有印象的话,在《3.1.2 启动launcer Activity》ActivityStackSupervisor#startHomeActivity中也调用了
int ActivityStackSupervisor#startActivityLocked(){
    err = startActivityUncheckedLocked(r, sourceRecord, voiceSession, voiceInteractor,
                startFlags, true, options, inTask);  
}
final int ActivityStackSupervisor#startActivityUncheckedLocked(final ActivityRecord r, ActivityRecord sourceRecord,
            IVoiceInteractionSession voiceSession, IVoiceInteractor voiceInteractor, int startFlags,
            boolean doResume, Bundle options, TaskRecord inTask) {
        ...
        ActivityStack.logStartActivity(EventLogTags.AM_CREATE_ACTIVITY, r, r.task);
        targetStack.mLastPausedActivity = null;
        targetStack.startActivityLocked(r, newTask, doResume, keepCurTransition, options);
        if (!launchTaskBehind) {
            // Don't set focus on an activity that's going to the back.
            mService.setFocusedActivityLocked(r, "startedActivity");
        }
        return ActivityManager.START_SUCCESS;
    }
  • 【步骤4】ActivityStack#startActivityLocked方法:主要执行初始化了windowManager服务,然后调用resumeTopActivitiesLocked方法
    • 主要执行初始化了windowManager服务,然后调用resumeTopActivitiesLocked方法
final void ActivityStack#startActivityLocked(ActivityRecord r, boolean newTask,
            boolean doResume, boolean keepCurTransition, Bundle options) {
        ...
        if (doResume) {
            mStackSupervisor.resumeTopActivitiesLocked(this, r, options);
        }
    }
boolean ActivityStackSupervisor#resumeTopActivitiesLocked(ActivityStack targetStack, ActivityRecord target,
            Bundle targetOptions) {
        if (targetStack == null) {
            targetStack = mFocusedStack;
        }
        // Do targetStack first.
        boolean result = false;
        if (isFrontStack(targetStack)) {
            result = targetStack.resumeTopActivityLocked(target, targetOptions);
        }

        for (int displayNdx = mActivityDisplays.size() - 1; displayNdx >= 0; --displayNdx) {
            final ArrayList<ActivityStack> stacks = mActivityDisplays.valueAt(displayNdx).mStacks;
            for (int stackNdx = stacks.size() - 1; stackNdx >= 0; --stackNdx) {
                final ActivityStack stack = stacks.get(stackNdx);
                if (stack == targetStack) {
                    // Already started above.
                    continue;
                }
                if (isFrontStack(stack)) {
                    stack.resumeTopActivityLocked(null);
                }
            }
        }
        return result;
    }
final boolean ActivityStack#resumeTopActivityLocked(ActivityRecord prev) {
        return resumeTopActivityLocked(prev, null);
    }

//【步骤6重载调用】ActivityStack.resumeTopActivitiesLocked()    
final boolean ActivityStack#resumeTopActivityLocked(ActivityRecord prev, Bundle options) {
        if (mStackSupervisor.inResumeTopActivity) {
            // Don't even start recursing.
            return false;
        }

        boolean result = false;
        try {
            // Protect against recursion.
            mStackSupervisor.inResumeTopActivity = true;
            if (mService.mLockScreenShown == ActivityManagerService.LOCK_SCREEN_LEAVING) {
                mService.mLockScreenShown = ActivityManagerService.LOCK_SCREEN_HIDDEN;
                mService.updateSleepIfNeededLocked();
            }
            result = resumeTopActivityInnerLocked(prev, options);
        } finally {
            mStackSupervisor.inResumeTopActivity = false;
        }
        return result;
    }   
  • 【步骤7 核心】 ActivityStack#resumeTopActivityInnerLocked:执行当前栈顶Activity的生命周期 或者 判断需要开启进程等
private boolean ActivityStack#resumeTopActivityInnerLocked(ActivityRecord prev, Bundle options) {
    ...
    mStackSupervisor.startSpecificActivityLocked(next, true, true);
}   
void startSpecificActivityLocked(ActivityRecord r,
            boolean andResume, boolean checkConfig) {
        // Is this activity's application already running?
        ProcessRecord app = mService.getProcessRecordLocked(r.processName,
                r.info.applicationInfo.uid, true);

        r.task.stack.setLaunchTime(r);
        //【分支判断】判断一下需要启动的Activity所需要的应用进程是否已经启动
        if (app != null && app.thread != null) {
            try {
                if ((r.info.flags&ActivityInfo.FLAG_MULTIPROCESS) == 0
                        || !"android".equals(r.info.packageName)) {
                    // Don't add this if it is a platform component that is marked
                    // to run in multiple processes, because this is actually
                    // part of the framework so doesn't make sense to track as a
                    // separate apk in the process.
                    app.addPackage(r.info.packageName, r.info.applicationInfo.versionCode,
                            mService.mProcessStats);
                }
                //【分支2:进程已启动】ActivityStackSupervisor # realStartAtivityLocked
                realStartActivityLocked(r, app, andResume, checkConfig);
                return;
            } catch (RemoteException e) {
                Slog.w(TAG, "Exception when starting activity "
                        + r.intent.getComponent().flattenToShortString(), e);
            }

            // If a dead object exception was thrown -- fall through to
            // restart the application.
        }

        //【分支1:进程未启动】ActivityManagerService # startProcessLocked()
        mService.startProcessLocked(r.processName, r.info.applicationInfo, true, 0,
                "activity", r.intent.getComponent(), false, false, true);
    }
  • 【步骤9】ActivityManagerService # startProcessLocked 方法:从名字可以看出来这个方法就是启动进程的
final ProcessRecord startProcessLocked(String processName,
            ApplicationInfo info, boolean knownToBeDead, int intentFlags,
            String hostingType, ComponentName hostingName, boolean allowWhileBooting,
            boolean isolated, boolean keepIfLarge) {
        return startProcessLocked(processName, info, knownToBeDead, intentFlags, hostingType,
                hostingName, allowWhileBooting, isolated, 0 /* isolatedUid */, keepIfLarge,
                null /* ABI override */, null /* entryPoint */, null /* entryPointArgs */,
                null /* crashHandler */);
    }

private final void startProcessLocked(ProcessRecord app, String hostingType,
            String hostingNameStr, String abiOverride, String entryPoint, String[] entryPointArgs) {
            ...
            boolean isActivityProcess = (entryPoint == null);
            if (entryPoint == null) entryPoint = "android.app.ActivityThread";
            Trace.traceBegin(Trace.TRACE_TAG_ACTIVITY_MANAGER, "Start proc: " +
                    app.processName);
            checkTime(startTime, "startProcess: asking zygote to start proc");
            Process.ProcessStartResult startResult = Process.start(entryPoint,
                    app.processName, uid, uid, gids, debugFlags, mountExternal,
                    app.info.targetSdkVersion, app.info.seinfo, requiredAbi, instructionSet,
                    app.info.dataDir, entryPointArgs);
            checkTime(startTime, "startProcess: returned from zygote!");
            ...
    }   
  • 【步骤10】 Process#start():传入启动的进程的名称“android.app.ActivityThread”
public static final ProcessStartResult start(final String processClass,
                                  final String niceName,
                                  int uid, int gid, int[] gids,
                                  int debugFlags, int mountExternal,
                                  int targetSdkVersion,
                                  String seInfo,
                                  String abi,
                                  String instructionSet,
                                  String appDataDir,
                                  String[] zygoteArgs) {
        try {
            //【步骤10内容】Process#startViaZygote()
            return startViaZygote(processClass, niceName, uid, gid, gids,
                    debugFlags, mountExternal, targetSdkVersion, seInfo,
                    abi, instructionSet, appDataDir, zygoteArgs);
        } catch (ZygoteStartFailedEx ex) {
            Log.e(LOG_TAG,
                    "Starting VM process through Zygote failed");
            throw new RuntimeException(
                    "Starting VM process through Zygote failed", ex);
        }
    }

这里的processClass就是要启动的进程的名称,这里传递的就是ActivityThread:”android.app.ActivityThread”

  • 【步骤11】 Process#startViaZygote
private static ProcessStartResult startViaZygote(final String processClass,
                                  final String niceName,
                                  final int uid, final int gid,
                                  final int[] gids,
                                  int debugFlags, int mountExternal,
                                  int targetSdkVersion,
                                  String seInfo,
                                  String abi,
                                  String instructionSet,
                                  String appDataDir,
                                  String[] extraArgs)
                                  throws ZygoteStartFailedEx {
        synchronized(Process.class) {
            ...

            return zygoteSendArgsAndGetResult(openZygoteSocketIfNeeded(abi), argsForZygote);
        }
    }
  • 【步骤12】 Process#zygoteSendArgsAndGetResult:最终调用了Zygote并通过socket通信的方式让Zygote进程fork除了一个新的进程,并根据我们刚刚传递的”android.app.ActivityThread”字符串,反射出该对象并执行ActivityThread的main方法
    这样我们所要启动的应用进程这时候其实已经启动了,但是还没有执行相应的初始化操作
private static ProcessStartResult zygoteSendArgsAndGetResult(
            ZygoteState zygoteState, ArrayList<String> args)
            throws ZygoteStartFailedEx {
        try {
            /**
             * See com.android.internal.os.ZygoteInit.readArgumentList()
             * Presently the wire format to the zygote process is:
             * a) a count of arguments (argc, in essence)
             * b) a number of newline-separated argument strings equal to count
             *
             * After the zygote process reads these it will write the pid of
             * the child or -1 on failure, followed by boolean to
             * indicate whether a wrapper process was used.
             */
            final BufferedWriter writer = zygoteState.writer;
            final DataInputStream inputStream = zygoteState.inputStream;

            writer.write(Integer.toString(args.size()));
            writer.newLine();

            int sz = args.size();
            for (int i = 0; i < sz; i++) {
                String arg = args.get(i);
                if (arg.indexOf('\n') >= 0) {
                    throw new ZygoteStartFailedEx(
                            "embedded newlines not allowed");
                }
                writer.write(arg);
                writer.newLine();
            }

            writer.flush();

            // Should there be a timeout on this?
            ProcessStartResult result = new ProcessStartResult();
            result.pid = inputStream.readInt();
            if (result.pid < 0) {
                throw new ZygoteStartFailedEx("fork() failed");
            }
            result.usingWrapper = inputStream.readBoolean();
            return result;
        } catch (IOException ex) {
            zygoteState.close();
            throw new ZygoteStartFailedEx(ex);
        }
    }
  • 【步骤13】 ActivityThread#main:开启主线程Looper循环等其他操作

为什么我们平时都将ActivityThread称之为ui线程或者是主线程,这里可以看出,应用进程被创建之后首先执行的是ActivityThread的main方法,所以我们将ActivityThread成为主线程

public static void main(String[] args) {
        ...
        Process.setArgV0("<pre-initialized>");

        Looper.prepareMainLooper();

        ActivityThread thread = new ActivityThread();
        thread.attach(false);

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

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

        // End of event ActivityThreadMain.
        Trace.traceEnd(Trace.TRACE_TAG_ACTIVITY_MANAGER);
        Looper.loop();

        throw new RuntimeException("Main thread loop unexpectedly exited");
    }
  • 【步骤14】 ActivityThread#attach:Binder跨进程通信ActivityManagerNative.getDefault().attachApplication()
private void attach(boolean system) {
    ...
    final IActivityManager mgr = ActivityManagerNative.getDefault();
            try {
                mgr.attachApplication(mAppThread);
            } catch (RemoteException ex) {
                // Ignore
            }
    ...
}
  • 【步骤15】ActivityManagerService#attachApplication:跨进程通信被调用
@Override
    public final void attachApplication(IApplicationThread thread) {
        synchronized (this) {
            int callingPid = Binder.getCallingPid();
            final long origId = Binder.clearCallingIdentity();
            attachApplicationLocked(thread, callingPid);
            Binder.restoreCallingIdentity(origId);
        }
    }
  • 【步骤16】ActivityManagerService#attachApplicationLocked:该方法执行了一系列的初始化操作,这样我们整个应用进程已经启动起来了,以确保Activity可以启动
private final boolean attachApplicationLocked(IApplicationThread thread,
            int pid) {

        ...
        // See if the top visible activity is waiting to run in this process...
        if (normalMode) {
            try {
                if (mStackSupervisor.attachApplicationLocked(app)) {
                    didSomething = true;
                }
            } catch (Exception e) {
                Slog.wtf(TAG, "Exception thrown launching activities in " + app, e);
                badApp = true;
            }
        }
        ...

        return true;
    }
  • 【步骤17】 ActivityStackSupervisor#attachApplicationLocked()
boolean attachApplicationLocked(ProcessRecord app) throws RemoteException {
        final String processName = app.processName;
        boolean didSomething = false;
        for (int displayNdx = mActivityDisplays.size() - 1; displayNdx >= 0; --displayNdx) {
            ArrayList<ActivityStack> stacks = mActivityDisplays.valueAt(displayNdx).mStacks;
            for (int stackNdx = stacks.size() - 1; stackNdx >= 0; --stackNdx) {
                final ActivityStack stack = stacks.get(stackNdx);
                if (!isFrontStack(stack)) {
                    continue;
                }
                ActivityRecord hr = stack.topRunningActivityLocked(null);
                if (hr != null) {
                    if (hr.app == null && app.uid == hr.info.applicationInfo.uid
                            && processName.equals(hr.processName)) {
                        try {
                            if (realStartActivityLocked(hr, app, true, true)) {
                                didSomething = true;
                            }
                        } catch (RemoteException e) {
                            Slog.w(TAG, "Exception in new application when starting activity "
                                  + hr.intent.getComponent().flattenToShortString(), e);
                            throw e;
                        }
                    }
                }
            }
        }
        if (!didSomething) {
            ensureActivitiesVisibleLocked(null, 0);
        }
        return didSomething;
    }
  • 【步骤18】ActivityManagerService#realStartActivityLocked:启动Activity

4.2.3 应用进程Context创建流程

  • 【步骤16】ActivityManagerService#attachApplicationLocked:该方法执行了一系列的初始化操作,这样我们整个应用进程已经启动起来了,以确保Activity可以启动
  • 【步骤17】thread.bindApplication:biner机制,跨进程通信
  • 【步骤18】ApplicationThread#bindApplication:biner机制,跨进程通信被调用
  • 【步骤19】ActivityThread.sendMessage()
  • 【步骤20】ActivityThread.handleMessage()
  • 【步骤21】ActivityThread.handleBindApplication():反射机制创建了Instrumentation对象,并执行了init方法,执行了Insrtumentation对象的初始化;调用了LockedApk.makeApplication方法反射创建了Application对象
  • 【步骤22】Instrumentation#callApplicationOnCreate
  • 【步骤23】Application#onCreate

在开发过程中经常会遇到对Context对象的使用,Application是Context,Activity是Context,Service也是Context,所以有一个经典的问题是一个App中一共有多少个Context?这个问题的答案是Application + N个Activity + N个Service

  • 【步骤16】ActivityManagerService#attachApplicationLocked:该方法执行了一系列的初始化操作,这样我们整个应用进程已经启动起来了,以确保Activity可以启动
private final boolean attachApplicationLocked(IApplicationThread      thread, int pid) {

        ...
        thread.bindApplication(processName, appInfo, providers, app.instrumentationClass, profilerInfo, app.instrumentationArguments, app.instrumentationWatcher,
app.instrumentationUiAutomationConnection, testMode, enableOpenGlTrace, isRestrictedBackupMode || !normalMode, app.persistent, new Configuration(mConfiguration), app.compat,
getCommonServicesLocked(app.isolated),
mCoreSettingsObserver.getCoreSettingsLocked());
        ...
}       
  • 【步骤17】thread.bindApplication:biner机制,跨进程通信

  • 【步骤18】ApplicationThread#bindApplication:biner机制,跨进程通信被调用

  • 【步骤19】ActivityThread.sendMessage()

  • 【步骤20】ActivityThread.handleMessage()
  • 【步骤21】ActivityThread.handleBindApplication():反射机制创建了Instrumentation对象,并执行了init方法,执行了Insrtumentation对象的初始化;调用了LockedApk.makeApplication方法反射创建了Application对象
private void handleBindApplication(AppBindData data) {
        ...
        // 创建Instrumentation
        if (data.instrumentationName != null) {
            InstrumentationInfo ii = null;
            try {
                ii = appContext.getPackageManager().
                    getInstrumentationInfo(data.instrumentationName, 0);
            } catch (PackageManager.NameNotFoundException e) {
            }
            if (ii == null) {
                throw new RuntimeException(
                    "Unable to find instrumentation info for: "
                    + data.instrumentationName);
            }

            mInstrumentationPackageName = ii.packageName;
            mInstrumentationAppDir = ii.sourceDir;
            mInstrumentationSplitAppDirs = ii.splitSourceDirs;
            mInstrumentationLibDir = ii.nativeLibraryDir;
            mInstrumentedAppDir = data.info.getAppDir();
            mInstrumentedSplitAppDirs = data.info.getSplitAppDirs();
            mInstrumentedLibDir = data.info.getLibDir();

            ApplicationInfo instrApp = new ApplicationInfo();
            instrApp.packageName = ii.packageName;
            instrApp.sourceDir = ii.sourceDir;
            instrApp.publicSourceDir = ii.publicSourceDir;
            instrApp.splitSourceDirs = ii.splitSourceDirs;
            instrApp.splitPublicSourceDirs = ii.splitPublicSourceDirs;
            instrApp.dataDir = ii.dataDir;
            instrApp.nativeLibraryDir = ii.nativeLibraryDir;
            LoadedApk pi = getPackageInfo(instrApp, data.compatInfo,
                    appContext.getClassLoader(), false, true, false);
            ContextImpl instrContext = ContextImpl.createAppContext(this, pi);

            try {
                java.lang.ClassLoader cl = instrContext.getClassLoader();
                mInstrumentation = (Instrumentation)
                    cl.loadClass(data.instrumentationName.getClassName()).newInstance();
            } catch (Exception e) {
                throw new RuntimeException(
                    "Unable to instantiate instrumentation "
                    + data.instrumentationName + ": " + e.toString(), e);
            }

            mInstrumentation.init(this, instrContext, appContext,
                   new ComponentName(ii.packageName, ii.name), data.instrumentationWatcher,
                   data.instrumentationUiAutomationConnection);

            if (mProfiler.profileFile != null && !ii.handleProfiling
                    && mProfiler.profileFd == null) {
                mProfiler.handlingProfiling = true;
                File file = new File(mProfiler.profileFile);
                file.getParentFile().mkdirs();
                Debug.startMethodTracing(file.toString(), 8 * 1024 * 1024);
            }

        } else {
            mInstrumentation = new Instrumentation();
        }

        ...
        //调用了LockedApk.makeApplication方法反射创建了Application对象
        / If the app is being launched for full backup or restore, bring it up in
            // a restricted environment with the base application class.
            Application app = data.info.makeApplication(data.restrictedBackupMode, null);
            mInitialApplication = app;
        ...
        try {
           mInstrumentation.onCreate(data.instrumentationArgs);
         }
         catch (Exception e) {
                throw new RuntimeException(
                    "Exception thrown in onCreate() of "
                    + data.instrumentationName + ": " + e.toString(), e);
            }

            try {
                mInstrumentation.callApplicationOnCreate(app);
            } catch (Exception e) {
                if (!mInstrumentation.onException(app, e)) {
                    throw new RuntimeException(
                        "Unable to create application " + app.getClass().getName()
                        + ": " + e.toString(), e);
                }
            }
        } finally {
            StrictMode.setThreadPolicy(savedPolicy);
        }
    }
  • 【步骤22】Instrumentation#callApplicationOnCreate
public void callApplicationOnCreate(Application app) {
        app.onCreate();
    }
  • 【步骤23】Application#onCreate

五、Activity启动流程

Activity的启动流程相对复杂一下,涉及到了Activity中的生命周期方法,涉及到了Android体系的CS模式,涉及到了Android中进程通讯Binder机制等等

activity在Android系统中代表的就是一个屏幕,一个App就是由许多个不同的Acitivty组成的,并且不同进程之间的Activity是可以相互调用的

5.1 基本知识

  • Activity的生命周期
protected void onCreate(Bundle savedInstanceState); 
protected void onRestart(); 
protected void onStart(); 
protected void onResume(); 
protected void onPause(); 
protected void onStop(); 
protected void onDestory(); 
以上为Activity生命周期中的各个时期的回调方法,在不同的方法中我们可以执行不同的逻辑。

关于Activity生命周期的详细介绍可以参考: (4.1.2)基础总结篇之一:Activity生命周期

  • Activity的启动模式
activity启动时可以设置不同的启动模式,主要是:standrand,singleTop,singleTask,instance等四种启动模式,不同的启动模式在启动Activity时会执行不同的逻辑,系统会按不同的启动模式将Activity存放到不同的activity栈中。 

关于Activity启动模式的详细介绍,可以参考: (4.1.2.2)基础总结篇之三:Activity的task相关

  • Activity的启动进程
在Manifest.xml中定义Activity的时候,Activity默认是属于进程名称为包名的进程的,当然这时候是可以指定Activity的启动进程,所以在Activity启动时首先会检测当前Activity所属的进程是否已经启动,若进程没有启动,则首先会启动该进程,并在该进程启动之后才会执行Activity的启动过程
  • Intent启动Activity的方式
Intent启动Activity分为两种,显示启动和隐士启动.
显示启动就是在初始化Intent对象的时候直接引用需要启动的Activity的字节码,显示引用的好处就是可以直接告诉Intent对象启动的Activity对象不需要执行intent filter索引需要启动哪一个Activity,但是显示引用不能启动其他进程的Activity对象,因为无法获取其他进程的Activity对象的字节码.
隐式启动则可以通过配置Intent Filter启动其他进程的Activity对象,因此在应用内,我们一般都是使用显示启动的方式启动Activity,而如果需要启动其他应用的Activity时,一般使用隐式启动的方式。
  • Android Framework层的CS模式
通过前几篇文章的介绍我们知道android系统在启动过程中会执行这样的逻辑: 
Zygote进程 –> SystemServer进程 –> 各种系统服务 
                               –> 应用进程 

在Actvity启动过程中,其实是应用进程与SystemServer进程相互配合启动Activity的过程,涉及到多个进程之间的通讯这里主要是ActivityThread与ActivityManagerService之间的通讯,其中:
1. 应用进程主要用于执行具体的Activity的启动过程,回调生命周期方法等操作
    ActivityThread响应ActivityManagerService的ActivityStack等的远程调用,并触发Instrumentation 进行Activity生命周期管理
    使用ActivityManagerNative向ActivityManagerService申请远端通信,并远程调用ActivityStack、ActivityStackSupervisor进行Activity进出栈等操作
2. SystemServer进程则主要是调用其中的各种服务,将Activity保存在栈中,协调各种系统资源等操作
    ActivityManagerService响应ActivityManagerNative的远程调用,并使用ActivityStack、ActivityStackSupervisor进行管理
    使用ActivityThread.IApplicationThread申请远端通信,并远程调用Instrumentation 进行Activity生命周期管理
  • Android系统进程间通讯Binder机制
Android系统存了Zygote进程和SystemServer进程以及各种应用进程等,为了能够实现各种进程之间的通讯,Android系统采用了自己的进程间通讯方式Binder机制。其中主要涉及到了四种角色:Binder Client,Binder Server,Binder Manager, Binder driver

各种角色之间的关系可以参考下面这张图的介绍:

(4.1.52)Android启动流程分析
【图2】

  • 相关信息点
    • ActivityManagerService接收到应用进程创建Activity的请求之后会执行初始化操作,解析启动模式,保存请求信息等一系列操作
    • 【原栈顶Activity.onPause】ActivityManagerService保存完请求信息之后会将当前系统栈顶的Activity执行onPause操作,并且IApplication进程间通讯告诉应用程序继承执行当前栈顶的Activity的onPause方法
    • 【原栈顶Activity.onPause】ActivityThread接收到SystemServer的消息之后会统一交个自身定义的Handler对象处理分发
    • 【原栈顶Activity.onPause】ActivityThread执行完栈顶的Activity的onPause方法之后会通过ActivityManagerNative执行进程间通讯告诉ActivityManagerService,栈顶Actiity已经执行完成onPause方法,继续执行后续操作
    • 【新进程】ActivityManagerService会继续执行启动Activity的逻辑,这时候会判断需要启动的Activity所属的应用进程是否已经启动,若没有启动则首先会启动这个Activity的应用程序进程;
    • 【新进程】ActivityManagerService会通过socket与Zygote继承通讯,并告知Zygote进程fork出一个新的应用程序进程,然后执行ActivityThread的mani方法;
    • 【新进程】在ActivityThead.main方法中执行初始化操作,初始化主线程异步消息,然后通知ActivityManagerService执行进程初始化操作;
    • 【新进程】ActivityManagerService会在执行初始化操作的同时检测当前进程是否有需要创建的Activity对象,若有的话,则执行创建操作;
    • 【新Activity生命周期】ActivityManagerService将执行创建Activity的通知告知ActivityThread,然后通过反射机制创建出Activity对象,并执行Activity的onCreate方法,onStart方法,onResume方法
    • 【原栈顶Activity.onPStop】ActivityThread执行完成onResume方法之后告知ActivityManagerService onResume执行完成,开始执行栈顶Activity的onStop方法
    • 【原栈顶Activity.onPStop】ActivityManagerService开始执行栈顶的onStop方法并告知ActivityThread,最终触发ActivityThread.onStop
      MainActivity跳转到SecondActivity 的整个生命周期调控就是下边开始的
11-06 14:59:09.821 16683-16683/sangfor.com.teststaticlife I/MainActivity: onPause()  
11-06 14:59:09.841 16683-16683/sangfor.com.teststaticlife I/SecondActivity: onCreate()  
11-06 14:59:09.851 16683-16683/sangfor.com.teststaticlife I/SecondActivity: onStart()  
11-06 14:59:09.851 16683-16683/sangfor.com.teststaticlife I/SecondActivity: onPostCreate()  
11-06 14:59:09.851 16683-16683/sangfor.com.teststaticlife I/SecondActivity: onResume()  
11-06 14:59:09.851 16683-16683/sangfor.com.teststaticlife I/SecondActivity: onPostResume()  
11-06 14:59:09.861 16683-16683/sangfor.com.teststaticlife I/SecondActivity: onAttachedToWindow()  
11-06 14:59:09.901 16683-16683/sangfor.com.teststaticlife I/SecondActivity: onWindowFocusChanged():true  
11-06 14:59:09.941 16683-16683/sangfor.com.teststaticlife I/MainActivity: onWindowFocusChanged():false  
11-06 14:59:10.311 16683-16683/sangfor.com.teststaticlife I/MainActivity: onStop() 

5.2 启动过程:开始请求执行启动Activity 与 ActivityManagerService接收启动Activity的请求

Instrumentation是android系统中启动Activity的一个实际操作类,也就是说Activity在应用进程端的启动实际上就是Instrumentation执行的,那么为什么说是在应用进程端的启动呢?
实际上acitivty的启动分为应用进程端的启动和SystemServer服务进程端的启动的,多个应用进程相互配合最终完成了Activity在系统中的启动的,而在应用进程端的启动实际的操作类就是Intrumentation来执行的

其中在《【步骤7 核心】* ActivityStack.resumeTopActivityInnerLocked() *:执行当前栈顶Activity的生命周期 或者 判断需要开启进程等》过程中,会有许多判断处理

5.3 执行栈顶Activity的onPause方法ActivityStack#startPausingLocked

在《【步骤8】调用了[ActivityStackSupervisor#startSpecificActivityLocked]》前触发

  • 【第1步】ActivityStack#startPausingLocked():pre.app.thread.schedulePauseActivity方法跨进程调用ActivityThread
  • 【第2步】ActivityThread#schedulePauseActivity():跨进程通信中被调用
  • 【第3步】ActivityThread#sendMessage():handler机制触发,发送PAUSE_ACTIVITY_FINISHING消息
  • 【第4步】ActivityThread#handleMessage():handler机制响应 响应PAUSE_ACTIVITY_FINISHING
  • 【第5步】ActivityThread#handlePauseActivity()
  • 【第6步】ActivityThread#performPauseActivity()实现对栈顶Activity的onPause生命周期方法的回调
  • 【第6.1步】Instrumentation#callActivityOnPuase()
  • 【第6.2步】Activity#performPause() :最终回调到了该方法
  • 【第6.3步】Activity#onPause()方法
  • 【第7步】ActivityManagerNative.getDefault().activityPaused(token):ActivityThread#handlePauseActivity中会执行,应用进程远程通信告诉服务进程,栈顶Activity已经执行完成onPause方法了
  • 【第8步】ActivityManagerService#activityPaused()
  • 【第9步】ActivityStack#activityPausedLocked()
  • 【第10步】ActivityStack#completePauseLocked()
  • 【第11步】ActivityStack#resumeTopActivitiesLocked():经过了一系列的逻辑之后,又调用了该方法
  • 【第12步】* ActivityStack.resumeTopActivityInnerLocked() *
  • 【第13步】ActivityStackSupervisor.startSpecificActivityLocked()
    判断一下需要启动的Activity所需要的应用进程是否已经启动
    • 已启动,realStartAtivityLocked()
    • 未启动,ActivityManagerService#startProcessLocked()
      Process.start()
      Process.startViaZygote()
      启动了AcitivtyThread进程并执行了ActivityThread的main方法

下面我们从源码进行分析:

ActivityStack 如果当前存在ResumedActivity栈顶元素,则执行startPausingLocked

private boolean ActivityStack#resumeTopActivityInnerLocked(ActivityRecord prev, Bundle options) {

        ...
        if (mResumedActivity != null) {
            if (DEBUG_STATES) Slog.d(TAG_STATES,
                    "resumeTopActivityLocked: Pausing " + mResumedActivity);
            pausing |= startPausingLocked(userLeaving, false, true, dontWaitForPause);
        }       
        ...

        return true;
    }
  • 【第1步】ActivityStack#startPausingLocked()

可以看到这里执行了pre.app.thread.schedulePauseActivity()方法,通过分析不难发现这里的thread是一个IApplicationThread类型的对象,而在ActivityThread中也定义了一个ApplicationThread的类,其继承了IApplicationThread,并且都是Binder对象。

不难看出这里的IAppcation是一个Binder的client端,而ActivityThread中的ApplicationThread是一个Binder对象的server端,所以通过这里的thread.schedulePauseActivity实际上调用的就是ApplicationThread的schedulePauseActivity方法

这里的ApplicationThread可以和ActivityManagerNative对于一下:
通过 ActivityManagerNative –> ActivityManagerService实现了应用进程与SystemServer进程的通讯
通过 ActivityThread.AppicationThread <– IApplicationThread实现了SystemServer进程与应用进程的通讯

final boolean startPausingLocked(boolean userLeaving, boolean uiSleeping, boolean resuming,
            boolean dontWait) {
        ...
         ActivityRecord prev = mResumedActivity;
        if (prev == null) {
            if (!resuming) {
                Slog.wtf(TAG, "Trying to pause when nothing is resumed");
                mStackSupervisor.resumeTopActivitiesLocked();
            }
            return false;
        }

        if (mActivityContainer.mParentActivity == null) {
            // Top level stack, not a child. Look for child stacks.
            mStackSupervisor.pauseChildStacks(prev, userLeaving, uiSleeping, resuming, dontWait);
        }

        mResumedActivity = null;
        mPausingActivity = prev;
        mLastPausedActivity = prev;
        ...
        if (prev.app != null && prev.app.thread != null) {
            if (DEBUG_PAUSE) Slog.v(TAG_PAUSE, "Enqueueing pending pause: " + prev);
            try {
                EventLog.writeEvent(EventLogTags.AM_PAUSE_ACTIVITY,
                        prev.userId, System.identityHashCode(prev),
                        prev.shortComponentName);
                mService.updateUsageStats(prev, false);
                prev.app.thread.schedulePauseActivity(prev.appToken, prev.finishing,
                        userLeaving, prev.configChangeFlags, dontWait);
            } catch (Exception e) {
                // Ignore exception, if process died other code will cleanup.
                Slog.w(TAG, "Exception thrown during pause", e);
                mPausingActivity = null;
                mLastPausedActivity = null;
                mLastNoHistoryActivity = null;
            }
        } else {
            mPausingActivity = null;
            mLastPausedActivity = null;
            mLastNoHistoryActivity = null;
        }
        ...
    }

调用了mH的sendMessage方法,发送了PAUSE_ACTIVITY_FINISHING消息(mH是在ActivityThread中定义的一个Handler对象,主要处理SystemServer进程的消息)

public final void ActivityThread#schedulePauseActivity(IBinder token, boolean finished,
                boolean userLeaving, int configChanges, boolean dontReport) {
            sendMessage(
                    finished ? H.PAUSE_ACTIVITY_FINISHING : H.PAUSE_ACTIVITY,
                    token,
                    (userLeaving ? 1 : 0) | (dontReport ? 2 : 0),
                    configChanges);
        }

- 【第3步】handler机制触发ActivityThread#sendMessage(),发送PAUSE_ACTIVITY_FINISHING消息

调用了mH的sendMessage方法,发送了PAUSE_ACTIVITY_FINISHING消息(mH是在ActivityThread中定义的一个Handler对象,主要处理SystemServer进程的消息)

private void ActivityThread#sendMessage(int what, Object obj, int arg1, int arg2) {
        sendMessage(what, obj, arg1, arg2, false);
    }

private void ActivityThread#sendMessage(int what, Object obj, int arg1, int arg2, boolean async) {
        if (DEBUG_MESSAGES) Slog.v(
            TAG, "SCHEDULE " + what + " " + mH.codeToString(what)
            + ": " + arg1 + " / " + obj);
        Message msg = Message.obtain();
        msg.what = what;
        msg.obj = obj;
        msg.arg1 = arg1;
        msg.arg2 = arg2;
        if (async) {
            msg.setAsynchronous(true);
        }
        mH.sendMessage(msg);
    }   

可以发现其调用了handlePauseActivity()方法

public void ActivityThread#handleMessage(Message msg) {
            if (DEBUG_MESSAGES) Slog.v(TAG, ">>> handling: " + codeToString(msg.what));
            switch (msg.what) {
                ...
                case PAUSE_ACTIVITY_FINISHING:
                    Trace.traceBegin(Trace.TRACE_TAG_ACTIVITY_MANAGER, "activityPause");
                    handlePauseActivity((IBinder)msg.obj, true, (msg.arg1&1) != 0, msg.arg2,
                            (msg.arg1&1) != 0);
                    Trace.traceEnd(Trace.TRACE_TAG_ACTIVITY_MANAGER);
                    break;
                ...
}

其中在方法体内部通过调用performPauseActivity()方法来实现对栈顶Activity的onPause生命周期方法的回调

private void ActivityThread#handlePauseActivity(IBinder token, boolean finished,
            boolean userLeaving, int configChanges, boolean dontReport) {
        ActivityClientRecord r = mActivities.get(token);
        if (r != null) {
            //Slog.v(TAG, "userLeaving=" + userLeaving + " handling pause of " + r);
            if (userLeaving) {
                performUserLeavingActivity(r);
            }

            r.activity.mConfigChangeFlags |= configChanges;
            performPauseActivity(token, finished, r.isPreHoneycomb());//【第5步】

            // Make sure any pending writes are now committed.
            if (r.isPreHoneycomb()) {
                QueuedWork.waitToFinish();
            }

            // Tell the activity manager we have paused.
            if (!dontReport) {
                try {
                    ActivityManagerNative.getDefault().activityPaused(token);//【第6步】
                } catch (RemoteException ex) {
                }
            }
            mSomeActivitiesChanged = true;
        }
    }

回到了mInstrumentation的callActivityOnPuase()方法

final Bundle performPauseActivity(IBinder token, boolean finished,
            boolean saveState) {
        ActivityClientRecord r = mActivities.get(token);
        return r != null ? performPauseActivity(r, finished, saveState) : null;
    }

final Bundle performPauseActivity(ActivityClientRecord r, boolean finished,
            boolean saveState) {
        ...
        mInstrumentation.callActivityOnPause(r.activity);
        ...

        return !r.activity.mFinished && saveState ? r.state : null;
    }   
  • 【第6.1步】Instrumentation#callActivityOnPuase()
public void callActivityOnPause(Activity activity) {
        activity.performPause();
    }
  • 【第6.2步】最终回调到了 Activity#performPause() 方法

回调到了Activity的onPause方法,Activity生命周期中的第一个生命周期方法终于被我们找到了,也就是说我们在启动一个Activity的时候最先被执行的是栈顶的Activity的onPause方法

final void performPause() {
        mDoReportFullyDrawn = false;
        mFragments.dispatchPause();
        mCalled = false;
        onPause();
        mResumed = false;
        if (!mCalled && getApplicationInfo().targetSdkVersion
                >= android.os.Build.VERSION_CODES.GINGERBREAD) {
            throw new SuperNotCalledException(
                    "Activity " + mComponent.toShortString() +
                    " did not call through to super.onPause()");
        }
        mResumed = false;
    }
  • 【第6.3步】Activity#onPause()方法

  • 【第7步】ActivityThread#handlePauseActivity()中会执行 ActivityManagerNative.getDefault().activityPaused(token)应用进程远程通信告诉服务进程,栈顶Activity已经执行完成onPause方法了

ActivityManagerNative是跨进程通信,最终调用 ActivityManagerService的activityPaused()

  • 【第8步】 ActivityManagerService#activityPaused()

该方法内部会调用ActivityStack的activityPausedLocked方法

@Override
    public final void activityPaused(IBinder token) {
        final long origId = Binder.clearCallingIdentity();
        synchronized(this) {
            ActivityStack stack = ActivityRecord.getStackLocked(token);
            if (stack != null) {
                stack.activityPausedLocked(token, false);
            }
        }
        Binder.restoreCallingIdentity(origId);
    }
  • 【第9步】ActivityStack#activityPausedLocked()
final void activityPausedLocked(IBinder token, boolean timeout) {
            ...
                if (DEBUG_STATES) Slog.v(TAG_STATES, "Moving to PAUSED: " + r
                        + (timeout ? " (due to timeout)" : " (pause complete)"));
                completePauseLocked(true);
            ...
    }
  • 【第10步】ActivityStack#completePauseLocked()
private void completePauseLocked(boolean resumeNext) {
        ...

        if (resumeNext) {
            final ActivityStack topStack = mStackSupervisor.getFocusedStack();
            if (!mService.isSleepingOrShuttingDown()) {
                mStackSupervisor.resumeTopActivitiesLocked(topStack, prev, null);
            } else {
                mStackSupervisor.checkReadyForSleepLocked();
                ActivityRecord top = topStack.topRunningActivityLocked(null);
                if (top == null || (prev != null && top != prev)) {
                    // If there are no more activities available to run,
                    // do resume anyway to start something.  Also if the top
                    // activity on the stack is not the just paused activity,
                    // we need to go ahead and resume it to ensure we complete
                    // an in-flight app switch.
                    mStackSupervisor.resumeTopActivitiesLocked(topStack, null, null);
                }
            }
        }
        ...
    }
  • 【第11步】经过了一系列的逻辑之后,又调用了ActivityStack#resumeTopActivitiesLocked()方法
  • 【步骤11重载调用】ActivityStack.resumeTopActivitiesLocked()
  • 【第12步 核心】* ActivityStack.resumeTopActivityInnerLocked() *
  • 【第13步】 ActivityStackSupervisor.startSpecificActivityLocked()
    判断一下需要启动的Activity所需要的应用进程是否已经启动
    • 已启动,ActivityStackSupervisor#realStartAtivityLocked()
    • 未启动,ActivityManagerService#startProcessLocked()

5.4 ActivityStackSupervisor#startSpecificActivityLocked()启动进程和启动Activity

  • 【步骤13】ActivityStackSupervisor#startSpecificActivityLocked()方法
  • 【分支判断】判断一下需要启动的Activity所需要的应用进程是否已经启动
  • 【分支2:进程已启动】 ActivityStackSupervisor#realStartAtivityLocked()
  • 【分支1:进程未启动】 ActivityManagerService#startProcessLocked():启动进程
  • 【步骤1】 Process#start():传入启动的进程的名称“android.app.ActivityThread”
  • 【步骤2】 Process#startViaZygote()
  • 【步骤3】 ActivityThread#main():启动了AcitivtyThread进程并执行了方法
  • 【步骤4】 Process#startViaZygote()
  • 【步骤5】 Process#zygoteSendArgsAndGetResult():最终调用了Zygote并通过socket通信的方式让Zygote进程fork除了一个新的进程,并根据我们刚刚传递的”android.app.ActivityThread”字符串,反射出该对象并执行ActivityThread的main方法
  • 【步骤6】 ActivityThread#main():开启主线程Looper循环等其他操作
  • 【步骤7】 ActivityThread#attach():Binder跨进程通信ActivityManagerNative.getDefault().attachApplication()
  • 【步骤8】 ActivityManagerService#attachApplication():跨进程通信被调用
  • 【步骤9】 ActivityManagerService#attachApplicationLocked():该方法执行了一系列的初始化操作,这样我们整个应用进程已经启动起来了,以确保Activity可以启动
  • 【步骤10】 ActivityStackSupervisor#attachApplicationLocked()
  • 【步骤11】 ActivityStackSupervisor#realStartActivityLocked():启动Acitivity

具体请看《四、应用进程启动》环节的源码分析

5.5 ActivityStackSupervisor#realStartActivityLocked() 执行

  • 【第1步】ActivityStackSupervisor#realStartActivityLocked() : Binder机制跨进程通信ActivityThread
  • 【第2步】IApplicationThread#scheduleLauncherActivity() :Binder机制跨进程调用响应,内部handler发送信息
  • 【第3步】ActivityThread#sendMessage() :内部handler发送信息,H.LAUNCH_ACTIVITY
  • 【第4步】ActivityThread#handleMessage()
  • 【第5步】ActivityThread#handleLauncherActivity()
  • 【第6步】ActivityThread#performLauncherActivity() :执行Activity的启动操作,需要的Activity对象以反射方式启动,并触发Create和Start
  • 【第6.1步】Instrumentation#callActivityOnCreate()
  • 【第6.1.1步】 Activity#performCreate()
  • 【第6.1.2步】 Activity#onCreate() :第二个生命周期方法出来了,onCreate方法
  • 【第6.2步】Activity#performStart():内部调用 Instrumentation
  • 【第6.2.1步】 Instrumentation#callActivityOnStart()
  • 【第6.2.2步】Activity#onStart() :第三个生命周期方法出来了,onStart方法
  • 【第7步】ActivityThread#handleResumeActivity() :触发Resume生命周期、界面绘制流程、原栈顶Activity的onStop
  • 【第8步】ActivityThread#performResumeActivity()
  • 【第8.1步】Activity#performResume()
  • 【第8.2步】Instrumentation#callActivityOnResume()
  • 【第8.3步】Activity#onResume() :第四个生命周期方法出现了,onResume方法
  • 【第9步】《深入理解setContentView过程和View绘制过程》View绘制前过程
  • 【第10步】Looper.myQueue().addIdleHandler(new Idler()):Handle机制,触发空闲消息,用于触发原栈顶Activity的stop
  • 【第11步】ActivityManagerNative.getDefault().activityResumed(token) :跨进程通信
  • 【第12步】ActivityManagerNative.getDefault().finishActivity() :跨进程通信

  • 【第1步】ActivityStackSupervisor#realStartActivityLocked() : Binder机制跨进程通信ActivityThread

可以发现与第三步执行栈顶Activity onPause时类似,这里也是通过调用IApplicationThread的方法实现的,这里调用的是scheduleLauncherActivity方法,所以真正执行的是ActivityThread中的scheduleLauncherActivity

final boolean realStartActivityLocked(ActivityRecord r,
            ProcessRecord app, boolean andResume, boolean checkConfig)
            throws RemoteException {

        ...
            app.forceProcessStateUpTo(mService.mTopProcessState);
            app.thread.scheduleLaunchActivity(new Intent(r.intent), r.appToken,
                    System.identityHashCode(r), r.info, new Configuration(mService.mConfiguration),
                    new Configuration(stack.mOverrideConfig), r.compat, r.launchedFromPackage,
                    task.voiceInteractor, app.repProcState, r.icicle, r.persistentState, results,
                    newIntents, !andResume, mService.isNextTransitionForward(), profilerInfo);
        ...
        return true;
    }
  • 【第2步】IApplicationThread#scheduleLauncherActivity() :Binder机制跨进程调用响应,内部handler发送信息

ActivityThread接收到SystemServer进程的消息之后会通过其内部的Handler对象分发消息


    @Override
        public final void scheduleLaunchActivity(Intent intent, IBinder token, int ident,
                ActivityInfo info, Configuration curConfig, Configuration overrideConfig,
                CompatibilityInfo compatInfo, String referrer, IVoiceInteractor voiceInteractor,
                int procState, Bundle state, PersistableBundle persistentState,
                List<ResultInfo> pendingResults, List<ReferrerIntent> pendingNewIntents,
                boolean notResumed, boolean isForward, ProfilerInfo profilerInfo) {

            updateProcessState(procState, false);

            ActivityClientRecord r = new ActivityClientRecord();

            r.token = token;
            r.ident = ident;
            r.intent = intent;
            r.referrer = referrer;
            r.voiceInteractor = voiceInteractor;
            r.activityInfo = info;
            r.compatInfo = compatInfo;
            r.state = state;
            r.persistentState = persistentState;

            r.pendingResults = pendingResults;
            r.pendingIntents = pendingNewIntents;

            r.startsNotResumed = notResumed;
            r.isForward = isForward;

            r.profilerInfo = profilerInfo;

            r.overrideConfig = overrideConfig;
            updatePendingConfiguration(curConfig);

            sendMessage(H.LAUNCH_ACTIVITY, r);
        }
  • 【第3步】ActivityThread#sendMessage() :内部handler发送信息,H.LAUNCH_ACTIVITY
  • 【第4步】ActivityThread#handleMessage()
  • 【第5步】ActivityThread#handleLauncherActivity()
private void handleLaunchActivity(ActivityClientRecord r, Intent customIntent) {

        Activity a = performLaunchActivity(r, customIntent);

        if (a != null) {
            r.createdConfig = new Configuration(mConfiguration);
            Bundle oldState = r.state;
            handleResumeActivity(r.token, false, r.isForward,
                    !r.activity.mFinished && !r.startsNotResumed);


        }
        ...
    }
  • 【第6步】ActivityThread#performLauncherActivity() :执行Activity的启动操作,需要的Activity对象以反射方式启动,并触发Create和Start
private Activity performLaunchActivity(ActivityClientRecord r, Intent customIntent) {
        ...

Activity activity = null;
        try {
            java.lang.ClassLoader cl = r.packageInfo.getClassLoader();
            activity = mInstrumentation.newActivity(
                    cl, component.getClassName(), r.intent);
            StrictMode.incrementExpectedActivityCount(activity.getClass());
            r.intent.setExtrasClassLoader(cl);
            r.intent.prepareToEnterProcess();
            if (r.state != null) {
                r.state.setClassLoader(cl);
            }
        } catch (Exception e) {
            if (!mInstrumentation.onException(activity, e)) {
                throw new RuntimeException(
                    "Unable to instantiate activity " + component
                    + ": " + e.toString(), e);
            }
        }
        ...

        activity.mCalled = false;
        //【第6.1步】Instrumentation#callActivityOnCreate() 
        if (r.isPersistable()) {
           mInstrumentation.callActivityOnCreate(activity, r.state, r.persistentState);
        } else {
           mInstrumentation.callActivityOnCreate(activity, r.state);
        }
        ...
        //【第6.2步】Activity#performStart():内部调用 Instrumentation
        if (!r.activity.mFinished) {
                    activity.performStart();
                    r.stopped = false;
                }
        ...
        return activity;
    }
  • 【第6.1步】Instrumentation#callActivityOnCreate()
public void callActivityOnCreate(Activity activity, Bundle icicle,
            PersistableBundle persistentState) {
        prePerformCreate(activity);
        activity.performCreate(icicle);
        postPerformCreate(activity);
    }
  • 【第6.1.1步】 Activity#performCreate()
final void performCreate(Bundle icicle) {
        onCreate(icicle);
        mActivityTransitionState.readState(icicle);
        performCreateCommon();
    }
  • 【第6.1.2步】 Activity#onCreate() :第二个生命周期方法出来了,onCreate方法

  • 【第6.2步】Activity#performStart():内部调用 Instrumentation

final void performStart() {
        mActivityTransitionState.setEnterActivityOptions(this, getActivityOptions());
        mFragments.noteStateNotSaved();
        mCalled = false;
        mFragments.execPendingActions();
        mInstrumentation.callActivityOnStart(this);
        if (!mCalled) {
            throw new SuperNotCalledException(
                "Activity " + mComponent.toShortString() +
                " did not call through to super.onStart()");
        }
        mFragments.dispatchStart();
        mFragments.reportLoaderStart();
        mActivityTransitionState.enterReady(this);
    }
  • 【第6.2.1步】 Instrumentation#callActivityOnStart()
public void callActivityOnStart(Activity activity) {
        activity.onStart();
    }
  • 【第6.2.2步】Activity#onStart() :第三个生命周期方法出来了,onStart方法

  • 【第7步】ActivityThread#handleResumeActivity() :触发Resume生命周期、界面绘制流程、原栈顶Activity的onStop

final void handleResumeActivity(IBinder token,
            boolean clearHide, boolean isForward, boolean reallyResume) {

     // If we are getting ready to gc after going to the background, well
        // we are back active so skip it.
        unscheduleGcIdler();
        mSomeActivitiesChanged = true;

        //【第8步】ActivityThread#performResumeActivity() 
        // TODO Push resumeArgs into the activity for consideration
        ActivityClientRecord r = performResumeActivity(token, clearHide);

        if (r != null) {
            final Activity a = r.activity;

            if (localLOGV) Slog.v(
                TAG, "Resume " + r + " started activity: " +
                a.mStartedActivity + ", hideForNow: " + r.hideForNow
                + ", finished: " + a.mFinished);

            final int forwardBit = isForward ?
                    WindowManager.LayoutParams.SOFT_INPUT_IS_FORWARD_NAVIGATION : 0;

            // If the window hasn't yet been added to the window manager,
            // and this guy didn't finish itself or start another activity,
            // then go ahead and add the window.
            boolean willBeVisible = !a.mStartedActivity;
            if (!willBeVisible) {
                try {
                    willBeVisible = ActivityManagerNative.getDefault().willActivityBeVisible(
                            a.getActivityToken());
                } catch (RemoteException e) {
                }
            }
            //【第9步】《深入理解setContentView过程和View绘制过程》View绘制前过程
            if (r.window == null && !a.mFinished && willBeVisible) {
                r.window = r.activity.getWindow();
                View decor = r.window.getDecorView();
                decor.setVisibility(View.INVISIBLE);
                ViewManager wm = a.getWindowManager();
                WindowManager.LayoutParams l = r.window.getAttributes();
                a.mDecor = decor;
                l.type = WindowManager.LayoutParams.TYPE_BASE_APPLICATION;
                l.softInputMode |= forwardBit;
                if (a.mVisibleFromClient) {
                    a.mWindowAdded = true;
                    wm.addView(decor, l);
                }

            // If the window has already been added, but during resume
            // we started another activity, then don't yet make the
            // window visible.
            } else if (!willBeVisible) {
                if (localLOGV) Slog.v(
                    TAG, "Launch " + r + " mStartedActivity set");
                r.hideForNow = true;
            }

            // Get rid of anything left hanging around.
            cleanUpPendingRemoveWindows(r);

            // The window is now visible if it has been added, we are not
            // simply finishing, and we are not starting another activity.
            if (!r.activity.mFinished && willBeVisible
                    && r.activity.mDecor != null && !r.hideForNow) {
                if (r.newConfig != null) {
                    r.tmpConfig.setTo(r.newConfig);
                    if (r.overrideConfig != null) {
                        r.tmpConfig.updateFrom(r.overrideConfig);
                    }
                    if (DEBUG_CONFIGURATION) Slog.v(TAG, "Resuming activity "
                            + r.activityInfo.name + " with newConfig " + r.tmpConfig);
                    performConfigurationChanged(r.activity, r.tmpConfig);
                    freeTextLayoutCachesIfNeeded(r.activity.mCurrentConfig.diff(r.tmpConfig));
                    r.newConfig = null;
                }
                if (localLOGV) Slog.v(TAG, "Resuming " + r + " with isForward="
                        + isForward);
                WindowManager.LayoutParams l = r.window.getAttributes();
                if ((l.softInputMode
                        & WindowManager.LayoutParams.SOFT_INPUT_IS_FORWARD_NAVIGATION)
                        != forwardBit) {
                    l.softInputMode = (l.softInputMode
                            & (~WindowManager.LayoutParams.SOFT_INPUT_IS_FORWARD_NAVIGATION))
                            | forwardBit;
                    if (r.activity.mVisibleFromClient) {
                        ViewManager wm = a.getWindowManager();
                        View decor = r.window.getDecorView();
                        wm.updateViewLayout(decor, l);
                    }
                }
                r.activity.mVisibleFromServer = true;
                mNumVisibleActivities++;
                if (r.activity.mVisibleFromClient) {
                    r.activity.makeVisible();
                }
            }

            //【第10步】Looper.myQueue().addIdleHandler(new Idler()):Handle机制,触发空闲消息,用于触发原栈顶Activity的stop
            if (!r.onlyLocalRequest) {
                r.nextIdle = mNewActivities;
                mNewActivities = r;
                if (localLOGV) Slog.v(
                    TAG, "Scheduling idle handler for " + r);
                Looper.myQueue().addIdleHandler(new Idler());
            }
            r.onlyLocalRequest = false;

            // Tell the activity manager we have resumed.
            if (reallyResume) {
                try {
                    //【第11步】ActivityManagerNative.getDefault().activityResumed(token) :跨进程通信
                    ActivityManagerNative.getDefault().activityResumed(token);
                } catch (RemoteException ex) {
                }
            }

        } else {
            // If an exception was thrown when trying to resume, then
            // just end this activity.
            try {
                //【第12步】ActivityManagerNative.getDefault().finishActivity() :跨进程通信
                ActivityManagerNative.getDefault()
                    .finishActivity(token, Activity.RESULT_CANCELED, null, false);
            } catch (RemoteException ex) {
            }
        }   
}           
  • 【第8步】ActivityThread#performResumeActivity()
public final ActivityClientRecord performResumeActivity(IBinder token,
            boolean clearHide) {
        ActivityClientRecord r = mActivities.get(token);
        if (localLOGV) Slog.v(TAG, "Performing resume of " + r
                + " finished=" + r.activity.mFinished);
        if (r != null && !r.activity.mFinished) {
            if (clearHide) {
                r.hideForNow = false;
                r.activity.mStartedActivity = false;
            }
            try {
                r.activity.onStateNotSaved();
                r.activity.mFragments.noteStateNotSaved();
                if (r.pendingIntents != null) {
                    deliverNewIntents(r, r.pendingIntents);
                    r.pendingIntents = null;
                }
                if (r.pendingResults != null) {
                    deliverResults(r, r.pendingResults);
                    r.pendingResults = null;
                }
                r.activity.performResume();

                EventLog.writeEvent(LOG_AM_ON_RESUME_CALLED,
                        UserHandle.myUserId(), r.activity.getComponentName().getClassName());

                r.paused = false;
                r.stopped = false;
                r.state = null;
                r.persistentState = null;
            } catch (Exception e) {
                if (!mInstrumentation.onException(r.activity, e)) {
                    throw new RuntimeException(
                        "Unable to resume activity "
                        + r.intent.getComponent().toShortString()
                        + ": " + e.toString(), e);
                }
            }
        }
        return r;
    }
  • 【第8.1步】Activity#performResume()
final void performResume() {
        ...
        mInstrumentation.callActivityOnResume(this);
        ...
    }
  • 【第8.2步】Instrumentation#callActivityOnResume()
public void callActivityOnResume(Activity activity) {
        activity.mResumed = true;
        activity.onResume();

        if (mActivityMonitors != null) {
            synchronized (mSync) {
                final int N = mActivityMonitors.size();
                for (int i=0; i<N; i++) {
                    final ActivityMonitor am = mActivityMonitors.get(i);
                    am.match(activity, activity, activity.getIntent());
                }
            }
        }
    }
  • 【第8.3步】Activity#onResume() :第四个生命周期方法出现了,onResume方法
  • 【第9步】《深入理解setContentView过程和View绘制过程》View绘制前过程
  • 【第10步】Looper.myQueue().addIdleHandler(new Idler()):Handle机制,触发空闲消息,用于触发原栈顶Activity的stop
  • 【第11步】ActivityManagerNative.getDefault().activityResumed(token) :跨进程通信
  • 【第12步】ActivityManagerNative.getDefault().finishActivity() :跨进程通信

5.6 栈顶Activity执行onStop方法

在《5.5 ActivityStackSupervisor#realStartActivityLocked() 执行》的《【第7步】ActivityThread#handleResumeActivity() :触发Resume生命周期、界面绘制流程、原栈顶Activity的onStop》,中有空闲任务

更多关于IdlerHandler的信息,请参见《android空闲任务MessageQueue.IdleHandler》

  • 【入口】【第7步】ActivityThread#handleResumeActivity() :触发Resume生命周期、界面绘制流程、原栈顶Activity的onStop
  • 【第1步】Looper.myQueue().addIdleHandler(new Idler()) :空闲任务,当Messagequeue执行add方法之后就会回调其queueIdle()方法
  • 【第2步】ActivityManagerNative.getDefault()#activityIdle() :binder机制,跨进程通信启动
  • 【第3步】ActivityManagerService#activityIdle() :binder机制,跨进程通信被调用
  • 【第4步】ActivityStackSupervisor#activityIdleInternalLocked()
  • 【第5步】ActivityStack#stopActivityLocked()
  • 【第6步】IApplicationThread#scheduleStopActivity() :Binder机制,跨进程通信
  • 【第7步】ActivityThread#scheduleStopActivity() :Binder机制,跨进程通信被调用
  • 【第8步】ActivityThread#sendMessage() :handle机制发送Message
  • 【第9步】ActivityThread#handleMessage() :handle机制,响应Message
  • 【第10步】ActivityThread#handleStopActivity()
  • 【第11步】ActivityThread#performStopActivityInner()
  • 【第12步】ActivityThread#callCallActivityOnSaveInstanceState()
  • 【第12.1步】 Instrumentation#callActivityOnSaveInstanceState()
  • 【第12.2步】 Activity#performSaveInstanceState()
  • 【第12.3步】 Activity#onSaveInstanceState()
  • 【第13步】Activity#performStop()
  • 【第13.1步】Instrumentation#callActivityOnStop()
  • 【第13.2步】Activity#onStop()

  • 【第1步】Looper.myQueue().addIdleHandler(new Idler()) :空闲任务,当Messagequeue执行add方法之后就会回调其queueIdle()方法

private class Idler implements MessageQueue.IdleHandler {
        @Override
        public final boolean queueIdle() {
            ActivityClientRecord a = mNewActivities;
            boolean stopProfiling = false;
            if (mBoundApplication != null && mProfiler.profileFd != null
                    && mProfiler.autoStopProfiler) {
                stopProfiling = true;
            }
            if (a != null) {
                mNewActivities = null;
                IActivityManager am = ActivityManagerNative.getDefault();
                ActivityClientRecord prev;
                do {
                    if (localLOGV) Slog.v(
                        TAG, "Reporting idle of " + a +
                        " finished=" +
                        (a.activity != null && a.activity.mFinished));
                    if (a.activity != null && !a.activity.mFinished) {
                        try {
                            am.activityIdle(a.token, a.createdConfig, stopProfiling);
                            a.createdConfig = null;
                        } catch (RemoteException ex) {
                            // Ignore
                        }
                    }
                    prev = a;
                    a = a.nextIdle;
                    prev.nextIdle = null;
                } while (a != null);
            }
            if (stopProfiling) {
                mProfiler.stopProfiling();
            }
            ensureJitEnabled();
            return false;
        }
    }
  • 【第2步】ActivityManagerNative.getDefault()#activityIdle() :binder机制,跨进程通信启动
  • 【第3步】ActivityManagerService#activityIdle() :binder机制,跨进程通信被调用
@Override
    public final void activityIdle(IBinder token, Configuration config, boolean stopProfiling) {
        final long origId = Binder.clearCallingIdentity();
        synchronized (this) {
            ActivityStack stack = ActivityRecord.getStackLocked(token);
            if (stack != null) {
                ActivityRecord r =
                        mStackSupervisor.activityIdleInternalLocked(token, false, config);
                if (stopProfiling) {
                    if ((mProfileProc == r.app) && (mProfileFd != null)) {
                        try {
                            mProfileFd.close();
                        } catch (IOException e) {
                        }
                        clearProfilerLocked();
                    }
                }
            }
        }
        Binder.restoreCallingIdentity(origId);
    }
  • 【第4步】ActivityStackSupervisor#activityIdleInternalLocked()
final ActivityRecord activityIdleInternalLocked(final IBinder token, boolean fromTimeout,
            Configuration config) {
        ...

        // Stop any activities that are scheduled to do so but have been
        // waiting for the next one to start.
        for (int i = 0; i < NS; i++) {
            r = stops.get(i);
            final ActivityStack stack = r.task.stack;
            if (stack != null) {
                if (r.finishing) {
                    stack.finishCurrentActivityLocked(r, ActivityStack.FINISH_IMMEDIATELY, false);
                } else {
                    stack.stopActivityLocked(r);
                }
            }
        }

        ...

        return r;
    }
  • 【第5步】ActivityStack#stopActivityLocked()
final void stopActivityLocked(ActivityRecord r) {
        if (DEBUG_SWITCH) Slog.d(TAG_SWITCH, "Stopping: " + r);
        if ((r.intent.getFlags()&Intent.FLAG_ACTIVITY_NO_HISTORY) != 0
                || (r.info.flags&ActivityInfo.FLAG_NO_HISTORY) != 0) {
            ...
                r.app.thread.scheduleStopActivity(r.appToken, r.visible, r.configChangeFlags);
             ...
        }
    }
  • 【第6步】IApplicationThread#scheduleStopActivity() :Binder机制,跨进程通信
  • 【第7步】ActivityThread#scheduleStopActivity() :Binder机制,跨进程通信被调用
public final void scheduleStopActivity(IBinder token, boolean showWindow,
                int configChanges) {
           sendMessage(
                showWindow ? H.STOP_ACTIVITY_SHOW : H.STOP_ACTIVITY_HIDE,
                token, 0, configChanges);
        }
  • 【第8步】ActivityThread#sendMessage() :handle机制发送Message
  • 【第9步】ActivityThread#handleMessage() :handle机制,响应Message
  • 【第10步】ActivityThread#handleStopActivity()
private void handleStopActivity(IBinder token, boolean show, int configChanges) {
        ...
        performStopActivityInner(r, info, show, true);
        ...
    }
  • 【第11步】ActivityThread#performStopActivityInner()
private void performStopActivityInner(ActivityClientRecord r,
            StopInfo info, boolean keepShown, boolean saveState) {
            ...
            // Next have the activity save its current state and managed dialogs...
            if (!r.activity.mFinished && saveState) {
                if (r.state == null) {
                //【第11.1步】ActivityThread#callCallActivityOnSaveInstanceState() 
                    callCallActivityOnSaveInstanceState(r);
                }
            }

            if (!keepShown) {
                try {
                    // Now we are idle.
                    r.activity.performStop();
                } catch (Exception e) {
                    if (!mInstrumentation.onException(r.activity, e)) {
                        throw new RuntimeException(
                                "Unable to stop activity "
                                + r.intent.getComponent().toShortString()
                                + ": " + e.toString(), e);
                    }
                }
                r.stopped = true;
            }
        }
    }
  • 【第12步】ActivityThread#callCallActivityOnSaveInstanceState()
private void callCallActivityOnSaveInstanceState(ActivityClientRecord r) {
        r.state = new Bundle();
        r.state.setAllowFds(false);
        if (r.isPersistable()) {
            r.persistentState = new PersistableBundle();
            mInstrumentation.callActivityOnSaveInstanceState(r.activity, r.state,
                    r.persistentState);
        } else {
            mInstrumentation.callActivityOnSaveInstanceState(r.activity, r.state);
        }
    }
  • 【第12.1步】 Instrumentation#callActivityOnSaveInstanceState()
public void callActivityOnSaveInstanceState(Activity activity, Bundle outState,
            PersistableBundle outPersistentState) {
        activity.performSaveInstanceState(outState, outPersistentState);
    }
  • 【第12.2步】 Activity#performSaveInstanceState()
final void performSaveInstanceState(Bundle outState) {
        onSaveInstanceState(outState);
        saveManagedDialogs(outState);
        mActivityTransitionState.saveState(outState);
        if (DEBUG_LIFECYCLE) Slog.v(TAG, "onSaveInstanceState " + this + ": " + outState);
    }
  • 【第12.3步】 Activity#onSaveInstanceState()

  • 【第13步】Activity#performStop()

final void performStop() {
        mDoReportFullyDrawn = false;
        mFragments.doLoaderStop(mChangingConfigurations /*retain*/);

        if (!mStopped) {
            if (mWindow != null) {
                mWindow.closeAllPanels();
            }

            if (mToken != null && mParent == null) {
                WindowManagerGlobal.getInstance().setStoppedState(mToken, true);
            }

            mFragments.dispatchStop();

            mCalled = false;
            mInstrumentation.callActivityOnStop(this);
            if (!mCalled) {
                throw new SuperNotCalledException(
                    "Activity " + mComponent.toShortString() +
                    " did not call through to super.onStop()");
            }

            synchronized (mManagedCursors) {
                final int N = mManagedCursors.size();
                for (int i=0; i<N; i++) {
                    ManagedCursor mc = mManagedCursors.get(i);
                    if (!mc.mReleased) {
                        mc.mCursor.deactivate();
                        mc.mReleased = true;
                    }
                }
            }

            mStopped = true;
        }
        mResumed = false;
    }
  • 【第13.1步】Instrumentation#callActivityOnStop()
public void callActivityOnStop(Activity activity) {
        activity.onStop();
    }
  • 【第13.2步】Activity#onStop()

六、Activity销毁流程

  • Activity的销毁流程是从finish方法开始的
  • Activity销毁过程是:onPause –> other.onRestart –> other.onStart –> other.onResume –> onStop –> onDestroy
  • Activity的销毁流程是ActivityThread与ActivityManagerService相互配合销毁的

6.1 请求销毁当前Activity

  • 【第1步】Activity#finish()
public void finish() {
    finish(false);
}
  • 【第1步重载】Activity#finish(boolean)
private void finish(boolean finishTask) {
        if (mParent == null) {
            int resultCode;
            Intent resultData;
            synchronized (this) {
                resultCode = mResultCode;
                resultData = mResultData;
            }
            if (false) Log.v(TAG, "Finishing self: token=" + mToken);
            try {
                if (resultData != null) {
                    resultData.prepareToLeaveProcess();
                }
                if (ActivityManagerNative.getDefault()
                        .finishActivity(mToken, resultCode, resultData, finishTask)) {
                    mFinished = true;
                }
            } catch (RemoteException e) {
                // Empty
            }
        } else {
            mParent.finishFromChild(this);
        }
    }
  • 【第2步】ActivityManagerNative.getDefault()#finishActivity() : Binder机制,跨进程通信
  • 【第3步】ActivityManagerService#finishActivity() :Binder机制,跨进程通信被调用
@Override
public final boolean finishActivity(IBinder token, int resultCode, Intent resultData, boolean finishTask) {
     ...
     res = tr.stack.requestFinishActivityLocked(token, resultCode,resultData, "app-request", true);
     ...
}
  • 【第4步】ActivityStack#requestFinishActivityLocked()
final boolean requestFinishActivityLocked(IBinder token, int resultCode,
            Intent resultData, String reason, boolean oomAdj) {
        ActivityRecord r = isInStackLocked(token);
        if (DEBUG_RESULTS || DEBUG_STATES) Slog.v(TAG_STATES,
                "Finishing activity token=" + token + " r="
                + ", result=" + resultCode + ", data=" + resultData
                + ", reason=" + reason);
        if (r == null) {
            return false;
        }

        finishActivityLocked(r, resultCode, resultData, reason, oomAdj);
        return true;
    }
  • 【第5步】ActivityStack#finishActivityLocked()
final boolean finishActivityLocked(ActivityRecord r, int resultCode, Intent resultData,
            String reason, boolean oomAdj) {
        ...
        startPausingLocked(false, false, false, false);
        ...
        return false;
    }
  • 【第6步】ActivityStack#startPausingLocked()
final boolean startPausingLocked(boolean userLeaving, boolean uiSleeping, boolean resuming, boolean dontWait) {
       ...
            try {
                EventLog.writeEvent(EventLogTags.AM_PAUSE_ACTIVITY,
                        prev.userId, System.identityHashCode(prev),
                        prev.shortComponentName);
                mService.updateUsageStats(prev, false);
                prev.app.thread.schedulePauseActivity(prev.appToken, prev.finishing,
                        userLeaving, prev.configChangeFlags, dontWait);
            } catch (Exception e) {
                // Ignore exception, if process died other code will cleanup.
                Slog.w(TAG, "Exception thrown during pause", e);
                mPausingActivity = null;
                mLastPausedActivity = null;
                mLastNoHistoryActivity = null;
            }
        ...
    }
  • 【第7步】prev.app.thread.schedulePauseActivity:binder机制,跨进程通信

6.2 执行当前Activity的onPause方法

  • 【第1步】IApplicationThread.schedulePauseActivity()
  • 【第2步】ActivityThread.schedulePauseActivity()
public final void schedulePauseActivity(IBinder token, boolean finished, boolean userLeaving, int configChanges, boolean dontReport) {
   sendMessage(
       finished ? H.PAUSE_ACTIVITY_FINISHING : H.PAUSE_ACTIVITY,
       token, (userLeaving ? 1 : 0) | (dontReport ? 2 : 0),
                    configChanges);
}
  • 【第3步】ActivityThread.sendMessage()
  • 【第4步】ActivityThread.handleMessage()
  • 【第5步】ActivityThread.handlePauseActivity()
private void handlePauseActivity(IBinder token, boolean finished,
            boolean userLeaving, int configChanges, boolean dontReport) {
        ActivityClientRecord r = mActivities.get(token);
        if (r != null) {
            //Slog.v(TAG, "userLeaving=" + userLeaving + " handling pause of " + r);
            if (userLeaving) {
                performUserLeavingActivity(r);
            }

            r.activity.mConfigChangeFlags |= configChanges;
            performPauseActivity(token, finished, r.isPreHoneycomb());

            // Make sure any pending writes are now committed.
            if (r.isPreHoneycomb()) {
                QueuedWork.waitToFinish();
            }

            // Tell the activity manager we have paused.
            if (!dontReport) {
                try {
                    ActivityManagerNative.getDefault().activityPaused(token);
                } catch (RemoteException ex) {
                }
            }
            mSomeActivitiesChanged = true;
        }
    }
  • 【第6步】ActivityThread#handlePauseActivity()
  • 【第7步】ActivityThread#performPauseActivity()实现对栈顶Activity的onPause生命周期方法的回调
  • 【第7.1步】Instrumentation#callActivityOnPuase()
  • 【第7.2步】Activity#performPause() :最终回调到了该方法
  • 【第7.3步】Activity#onPause()方法
  • 【第8步】ActivityManagerNative.getDefault().activityPaused(token):ActivityThread#handlePauseActivity中会执行,应用进程远程通信告诉服务进程,栈顶Activity已经执行完成onPause方法了
  • 【第9步】ActivityManagerService#activityPaused()
  • 【第10步】ActivityStack#activityPausedLocked()
  • 【第11步】ActivityStack#completePauseLocked()
  • 【第12步】ActivityStack#resumeTopActivitiesLocked():经过了一系列的逻辑之后,又调用了该方法
  • 【第12步】* ActivityStack.resumeTopActivityInnerLocked() *

6.3 执行上一个Activity的onRestart、onStart、onResume操作

通过《五》的介绍,我们知道这个方法实际上是执行Activity的初始化,我们看一下其具体的调用过程:

  • ActivityStack.resumeTopActivityLocked()
  • ActivityStack.resumeTopInnerLocked()
  • IApplicationThread.scheduleResumeActivity()
  • ActivityThread.scheduleResumeActivity()
  • ActivityThread.sendMessage()
  • ActivityTherad.H.sendMessage()
  • ActivityThread.H.handleMessage()
  • ActivityThread.H.handleResumeMessage()
  • Activity.performResume()
  • Activity.performRestart()
  • Instrumentation.callActivityOnRestart()
  • Activity.onRestart()
  • Activity.performStart()
  • Instrumentation.callActivityOnStart()
  • Activity.onStart()
  • Instrumentation.callActivityOnResume()
  • Activity.onResume()

6.4 执行Activity的销毁操作

  • Looper.myQueue().addIdleHandler(new Idler())
  • ActivityManagerNative.getDefault().activityIdle()
  • ActivityManagerService.activityIdle()
  • ActivityStackSupervisor.activityIdleInternalLocked()
  • ActivityStack.destroyActivityLocked()
  • IApplicationThread.scheduleDestoryActivity()
  • ActivityThread.scheduleDestoryActivity()
  • ActivityThread.sendMessage()
  • ActivityThread.H.sendMessage()
  • ActivityThread.H.handleMessage()
  • ActivityThread.handleDestoryActivity()
  • ActivityThread.performDestoryActivity()
  • Activity.performStop()
  • Instrumentation.callActivityOnStop()
  • Activity.onStop()
  • Instrumentation.callActivityOnDestory()
  • Activity.performDestory()
  • Acitivity.onDestory()
  • ActivityManagerNative.getDefault().activityDestoryed()
  • ActivityManagerService.activityDestoryed()
  • ActivityStack.activityDestoryedLocked()

参考文献