「Android 研習社」深刻研究源碼:Android10.0系統啓動流程(四):SystemServer

前言java

Android源碼啓動篇終於到了最後一個重要的內容--SystemServer(系統服務),接下來咱們就來看看SystemServer爲何這麼重要吧android

福利活動bash

Android研習社機械工業出版社聯合發起的贈書活動正在進行中,歡迎你們點擊連接參與app

正文

SystemServer是Android基本服務的提供者,是Android系統運行的最基本需求,全部service運行在一個叫system_server的進程中,system_server進程是Android中Java虛擬機中的第一個進程,能夠說,整個Android系統的業務都是圍繞system_server而展開的socket

前情提要

SystemServer是由Zygotefork出來的第一個進程,咱們在上篇文章中也提到了,這裏咱們再來回顧下,在ZygoteInit類的main函數中,經過調用forkSystemServer(),內部採用硬編碼的方式建立相關參數,啓動SystemServer,由此正式進入SystemServer的相關業務邏輯中函數

ZygoteInit.javaoop

private static Runnable forkSystemServer(String abiList, String socketName,
            ZygoteServer zygoteServer) {
		...
        /* Hardcoded command line to start the system server */
        // "經過硬編碼的方式提供相關的參數"
        String args[] = {
                "--setuid=1000", //用戶id
                "--setgid=1000",//用戶組id
                "--setgroups=1001,1002,1003,1004,1005,1006,1007,1008,1009,1010,1018,1021,1023,"
                        + "1024,1032,1065,3001,3002,3003,3006,3007,3009,3010",
                "--capabilities=" + capabilities + "," + capabilities, //進程權能
                "--nice-name=system_server", //進程niceName
                "--runtime-args", 
                "--target-sdk-version=" + VMRuntime.SDK_VERSION_CUR_DEVELOPMENT, 
                "com.android.server.SystemServer", //須要啓動的類
        };
        ZygoteArguments parsedArgs = null; 

        int pid; //processId,進程id

        try {
            parsedArgs = new ZygoteArguments(args); //"建立ZygoteArguments對象,把args解析爲須要的參數"
            Zygote.applyDebuggerSystemProperty(parsedArgs);
            Zygote.applyInvokeWithSystemProperty(parsedArgs);

            boolean profileSystemServer = SystemProperties.getBoolean(
                    "dalvik.vm.profilesystemserver", false);  
            if (profileSystemServer) { 
                parsedArgs.mRuntimeFlags |= Zygote.PROFILE_SYSTEM_SERVER;
            }

            /* Request to fork the system server process */
            pid = Zygote.forkSystemServer( // "fork建立SystemServer"
                    parsedArgs.mUid, parsedArgs.mGid,
                    parsedArgs.mGids,
                    parsedArgs.mRuntimeFlags,
                    null,
                    parsedArgs.mPermittedCapabilities,
                    parsedArgs.mEffectiveCapabilities);
        } catch (IllegalArgumentException ex) {
            throw new RuntimeException(ex);
        }
        ...
    }
複製代碼

SystemServer的主要流程

咱們先來看一下總體的梳理 源碼分析

從上面這張流程圖能夠看到,SystemServer的主要流程其實仍是比較簡單的:

  1. 設置相關係統屬性,並作一些準備工做post

  2. 對Vm進行相關設置ui

  3. 建立主線程Looper

  4. 建立SystemServiceManager

  5. 建立ActivityThread及系統上下文Context

  6. 開啓各類服務

    //使用ServiceManger開啓服務,並對這些服務進行管理
    startBootstrapServices(); //引導服務
    startCoreServices();//核心服務
    startOtherServices(); //其餘服務
    複製代碼
  7. 進入Looper.loop的無限循環中

咱們來看看SystemServer具體開啓了哪些服務

能夠看到這裏面開啓了不少的服務,因此,分紅了三個函數類分類進程開啓,

  1. 引導服務
  2. 核心服務
  3. 其餘服務

這些服務,是經過調用SystemServiceManger.startServeice(),獲取到參數傳遞的Class對象,使用反射的方式,獲取到該類的構造器,建立該類的實例對象,並把該service對象添加到一個ArrayList列表中進行維護,最終調用service.onstart(),完成服務的開啓任務

這裏還要說一下,全部的服務,都是SystemService的子類對象,SystemService是一個抽象類,內部的onstart()是一個抽象方法,最終真正執行的邏輯是其子類對象本身去定義的

那麼咱們這裏就能夠先思考下,若是咱們想添加一個自定義的系統服務,應該如何去作?這裏先不作深究

具體源碼

"ssm"中根據Class對象反射建立指定的Service對象

public <T extends SystemService> T startService(Class<T> serviceClass) {
        try {
            final String name = serviceClass.getName();
            Slog.i(TAG, "Starting " + name);
            Trace.traceBegin(Trace.TRACE_TAG_SYSTEM_SERVER, "StartService " + 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);
            }

            startService(service);
            return service;
        } finally {
            Trace.traceEnd(Trace.TRACE_TAG_SYSTEM_SERVER);
        }
    }
複製代碼

添加到mServices的列表中進行維護,並維護這些服務的生命中週期事件,執行該服務的onStart()函數

// Services that should receive lifecycle events.
private final ArrayList<SystemService> mServices = new ArrayList<SystemService>();

public void startService(@NonNull final SystemService service) {
        // Register it.
        mServices.add(service);
        // Start it.
        long time = SystemClock.elapsedRealtime();
        try {
            service.onStart();
        } catch (RuntimeException ex) {
            throw new RuntimeException("Failed to start service " + service.getClass().getName()
                    + ": onStart threw an exception", ex);
        }
        warnIfTooLong(SystemClock.elapsedRealtime() - time, service, "onStart");
    }
複製代碼

SystemServer相關的主要系統服務

ActivityManagerService是如何啓動的

ActivityManagerService是在startBootstrapServices函數中開啓的服務,咱們來具體看下,它是如何被建立和啓動的

這裏主要涉及到了三個類,ActivityTaskManagerServiceActivityManagerServiceSystemServiceManager

private void startBootstrapServices() {
        ...
        //此處是經過"ssm"反射建立"atm"的靜態內部類對象,並經過"Lifecycle"提供的"getService()"獲取到"atm"實例對象
        ActivityTaskManagerService atm = mSystemServiceManager.startService(
                ActivityTaskManagerService.Lifecycle.class).getService();
        //調用"ams"的靜態內部類的靜態方法"startService"函數,把"ssm""atm"傳遞過去
        mActivityManagerService = ActivityManagerService.Lifecycle.startService(
                mSystemServiceManager, atm);//內部仍是使用"ssm"來建立的"ams"
        ...
}
複製代碼

具體如何啓動的上面的代碼註釋已經解釋的很清楚了,其中ATM和AMS中有着類似的設計,都是經過靜態內部類Lifecycle來建立和獲取本類對象,即當前系統服務的,關於AMS和Lifecycle咱們後面有機會再作深究

WindowManagerServices是如何啓動的

WMS是經過調用startOtherServices在其餘服務中開啓的, 能夠看出來這裏的開啓方式跟AMS不太同樣了,這裏並非使用SSM的StartService()函數來開啓的,而是先經過WMS的靜態工廠函數main()先建立出WMS對象,再經過ServiceManageraddService()函數,經過Binder機制進行進程間通訊,把WMS註冊到系統的服務表中

建立WMS對象並添加到ServiceManger

private void startOtherServices() {
// WMS needs sensor service ready
            ConcurrentUtils.waitForFutureNoInterrupt(mSensorServiceStart, START_SENSOR_SERVICE);
            mSensorServiceStart = null;
            wm = WindowManagerService.main(context, inputManager, !mFirstBoot, mOnlyCore,
                    new PhoneWindowManager(), mActivityManagerService.mActivityTaskManager);
            ServiceManager.addService(Context.WINDOW_SERVICE, wm, /* allowIsolated= */ false,
                    DUMP_FLAG_PRIORITY_CRITICAL | DUMP_FLAG_PROTO);
            ServiceManager.addService(Context.INPUT_SERVICE, inputManager,
                    /* allowIsolated= */ false, DUMP_FLAG_PRIORITY_CRITICAL);
}
複製代碼

經過addServcie添加到ServiceManager

public static void addService(String name, IBinder service, boolean allowIsolated,
            int dumpPriority) {
        try {
            getIServiceManager().addService(name, service, allowIsolated, dumpPriority);//獲取到ServiceManger對象並把`WMS`添加進去
        } catch (RemoteException e) {
            Log.e(TAG, "error in addService", e);
        }
    
複製代碼

加餐

經過上面的源碼分析,咱們得知,有兩種開啓服務的方式,下面咱們就來具體分析下

SystemServiceManager詳解

SSM這個類,目的是對系統服務「com.android.server.SystemService」的生命週期事件(建立,開啓和其餘事件)進行管理

SystemService生命週期

既然是對其生命週期進行管理,那先來看看系統服務都有哪些生命週期的方法 跟Activty的生命週期同樣,SystemService的生命週期方法也是onxxx()的函數命名的

  • onStart()
  • onBootPhase()
  • onStartUser()
  • onUnlockUser()
  • onSwitchUser()
  • onStopUser()
  • onCleanupUser() 這些生命週期的做用咱們在這裏就不展開分析了,你們能夠去查看具體源碼,源碼註釋中也寫的很清楚了

經過SystemServiceManager管理SystemService的生命週期

AMS的系統服務是經過SystemServiceManagerstartService()函數,建立並開啓指定className的系統服務,咱們來看下具體的代碼

/**
	 * 經過Classname建立(或者說開啓)一個系統服務
     * Starts a service by class name.
     *
     * @return The service instance.
     */
    @SuppressWarnings("unchecked")
    public SystemService startService(String className) {
        //反射建立系統服務
        final Class<SystemService> serviceClass;
        try {
            serviceClass = (Class<SystemService>)Class.forName(className);
        } catch (ClassNotFoundException ex) {
            Slog.i(TAG, "Starting " + className);
            throw new RuntimeException("Failed to create service " + className
                    + ": service class not found, usually indicates that the caller should "
                    + "have called PackageManager.hasSystemFeature() to check whether the "
                    + "feature is available on this device before trying to start the "
                    + "services that implement it", ex);
        }
        return startService(serviceClass);  //啓動建立好的系統服務
    }
複製代碼

啓動服務,調用系統服務的onStart()生命週期方法

public void startService(@NonNull final SystemService service) {
        // Register it.
        mServices.add(service);
        // Start it.
        long time = SystemClock.elapsedRealtime();
        try {
            service.onStart(); //調用已建立好的系統服務的onStart方法,完成初始化工做
        } catch (RuntimeException ex) {
            throw new RuntimeException("Failed to start service " + service.getClass().getName()
                    + ": onStart threw an exception", ex);
        }
        warnIfTooLong(SystemClock.elapsedRealtime() - time, service, "onStart");
    }
複製代碼

其餘的生命週期方法調用也是在SystemServiceManager中進行調用的,這裏再也不具體分析

ServiceManger詳解

總體分析

ServiceManger中主要的函數有

  • addService() 添加系統服務
  • getServerce() 獲取系統服務
  • checkService() 從service manager中檢索指定name的系統服務是否存在
  • listServices() 返回正在運行的全部服務

經過這些函數能夠看到,ServiceManger是對全部的系統服務進行管理,而SystemServiceManager是對單個系統服務的建立和生命週期進行管理

思考

咱們其實還能夠進一步來思考下,爲何AMS經過SystemServiceManager來添加,而WMS是經過ServiceManger來添加呢?這裏先賣個關子,你們能夠在評論中提出本身的見解

寫在最後

啓動篇的源碼分析斷斷續續作了一個多月的時間,寫到這裏咱們就把Android源碼啓動篇徹底分析完了,能夠先告一段落了,接下來,會對AMS,WMS,以及Binder相關內容進行詳盡的源碼分析。因爲水平有限,寫的不對的還請各位多多指教

原創不易,堅持更難

若是你想繼續看到我接下來的分享,請經過點讚的方式告訴我,你的鼓勵是我繼續創做的最大動力!

鄭重聲明

本文版權歸Android研習社全部,侵權必究!

相關文章
相關標籤/搜索