Android 7.0系統啓動流程分析

隨着Android版本的升級,aosp項目中的代碼也有了些變化,本文基於Android 7.0分析Android系統啓動流程.當我們按下電源鍵後,整個Android設備大體經過了一下過程:
這裏寫圖片描述

今天我們只想來分析init進程及其後的過程,也就是下圖所示部分:
這裏寫圖片描述


init進程

init進程會解析init.rc文件(關於init.rc中的語法,可以參見之前寫的深入分析AIL語言及init.rc文件),加載相關分區,並啓動相關服務.

init進程在/system/core/init/init.cpp
init.rc文件在/system/core/rootdir下
init.rc文件由parser.cpp解析,在/system/core/init/init_parser.cpp

在init.rc中,Zygote進程被啓動.Zygote進程是其他所有進程的孵化器.init.rc通過include引入init.zygote.rc,這裏以init.zygote64.rc爲例:

service zygote /system/bin/app_process64 -Xzygote /system/bin --zygote --start-system-server
    class main
    priority -20
    user root
    group root readproc
    socket zygote stream 660 root system
    onrestart write /sys/android_power/request_state wake
    onrestart write /sys/power/state on
    onrestart restart audioserver
    onrestart restart cameraserver
    onrestart restart media
    onrestart restart netd
    writepid /dev/cpuset/foreground/tasks

對個腳本簡單分析:

  1. service zygote /system/bin/app_process64 :service命令告訴init進程要創建一個名字爲zygote的進程,這個zygote進程執行的程序是/system/bin/app_process64,後面是傳給app_process64程序的參數.
  2. socket zygote stream 660 root system:表示zygote進程需要一個名爲”zygote”的socket,該socket用來實現進程間的通信.當新啓動一個應用時,ActivityManagerService想向該Socket發起請求,請求zygote進程fork出一個新的進程.
  3. 後面的onrestart表示zygote重啓時需要執行的動作.

Zygote進程啓動

上面說到init進程會根據init.rc執行相關的操作,其中有一項就是創建Zygote進程.Zygote進程所對應的程序是/system/bin/app_process,
位於/frameworks/base/cmds/app_process/app_main.cpp,其入口函數是main():

int main(int argc, char* const argv[])
{
    if (prctl(PR_SET_NO_NEW_PRIVS, 1, 0, 0, 0) < 0) {
        LOG_ALWAYS_FATAL("PR_SET_NO_NEW_PRIVS failed: %s", strerror(errno));
    }

    if (!LOG_NDEBUG) {
      String8 argv_String;
      for (int i = 0; i < argc; ++i) {
        argv_String.append("\"");
        argv_String.append(argv[i]);
        argv_String.append("\" ");
      }
      ALOGV("app_process main with argv: %s", argv_String.string());
    }

    AppRuntime runtime(argv[0], computeArgBlockSize(argc, argv));
    // Process command line arguments
    // ignore argv[0]
    argc--;
    argv++;
    const char* spaced_commands[] = { "-cp", "-classpath" };

    bool known_command = false;

    int i;
    for (i = 0; i < argc; i++) {
        if (known_command == true) {
          runtime.addOption(strdup(argv[i]));
          ALOGV("app_process main add known option '%s'", argv[i]);
          known_command = false;
          continue;
        }

        for (int j = 0;
             j < static_cast<int>(sizeof(spaced_commands) / sizeof(spaced_commands[0]));
             ++j) {
          if (strcmp(argv[i], spaced_commands[j]) == 0) {
            known_command = true;
            ALOGV("app_process main found known command '%s'", argv[i]);
          }
        }

        if (argv[i][0] != '-') {
            break;
        }
        if (argv[i][1] == '-' && argv[i][2] == 0) {
            ++i; // Skip --.
            break;
        }

        runtime.addOption(strdup(argv[i]));
        ALOGV("app_process main add option '%s'", argv[i]);
    }

    // Parse runtime arguments.  Stop at first unrecognized option.
    bool zygote = false;
    bool startSystemServer = false;
    bool application = false;
    String8 niceName;
    String8 className;

    ++i;  // Skip unused "parent dir" argument.
    while (i < argc) {
        const char* arg = argv[i++];
        if (strcmp(arg, "--zygote") == 0) {
            zygote = true;
            niceName = ZYGOTE_NICE_NAME;
        } else if (strcmp(arg, "--start-system-server") == 0) {
            //init.zygote64.rc中接受的參數,表示啓動SystemServer組件
            startSystemServer = true;
        } else if (strcmp(arg, "--application") == 0) {
            application = true;
        } else if (strncmp(arg, "--nice-name=", 12) == 0) {
            niceName.setTo(arg + 12);
        } else if (strncmp(arg, "--", 2) != 0) {
            className.setTo(arg);
            break;
        } else {
            --i;
            break;
        }
    }

    Vector<String8> args;
    if (!className.isEmpty()) {

        args.add(application ? String8("application") : String8("tool"));
        runtime.setClassNameAndArgs(className, argc - i, argv + i);

        if (!LOG_NDEBUG) {
          String8 restOfArgs;
          char* const* argv_new = argv + i;
          int argc_new = argc - i;
          for (int k = 0; k < argc_new; ++k) {
            restOfArgs.append("\"");
            restOfArgs.append(argv_new[k]);
            restOfArgs.append("\" ");
          }
          ALOGV("Class name = %s, args = %s", className.string(), restOfArgs.string());
        }
    } else {
        // We're in zygote mode.
        maybeCreateDalvikCache();

        if (startSystemServer) {
            args.add(String8("start-system-server"));
        }

        char prop[PROP_VALUE_MAX];
        if (property_get(ABI_LIST_PROPERTY, prop, NULL) == 0) {
            LOG_ALWAYS_FATAL("app_process: Unable to determine ABI list from property %s.",
                ABI_LIST_PROPERTY);
            return 11;
        }

        String8 abiFlag("--abi-list=");
        abiFlag.append(prop);
        args.add(abiFlag);

        // In zygote mode, pass all remaining arguments to the zygote
        // main() method.
        for (; i < argc; ++i) {
            args.add(String8(argv[i]));
        }
    }

    if (!niceName.isEmpty()) {
        runtime.setArgv0(niceName.string(), true /* setProcName */);
    }

    if (zygote) {
        //此處見到了我們熟悉的ZygoteInit,但該方法的具體實現在//AndroidRuntime.start()
        runtime.start("com.android.internal.os.ZygoteInit", args, zygote);
    } else if (className) {
        runtime.start("com.android.internal.os.RuntimeInit", args, zygote);
    } else {
        fprintf(stderr, "Error: no class name or --zygote supplied.\n");
        app_usage();
        LOG_ALWAYS_FATAL("app_process: no class name or --zygote supplied.");
    }
}

上述代碼總體比較簡單,主要是處理相關參數,並創建AppRuntime,由於在init.rc文件中,app_process啓動參數被設置爲--zygote --start-system-server,因此會執行runtime.start("com.android.internal.os.ZygoteInit", args, zygote),現在我們來看看AppRuntime的具體實現,它同樣在
在/frameworks/base/cmds/app_process/app_main.cpp:

class AppRuntime : public AndroidRuntime
{
public:
    AppRuntime(char* argBlockStart, const size_t argBlockLength)
        : AndroidRuntime(argBlockStart, argBlockLength)
        , mClass(NULL)
    {
    }

    void setClassNameAndArgs(const String8& className, int argc, char * const *argv) {
        mClassName = className;
        for (int i = 0; i < argc; ++i) {
             mArgs.add(String8(argv[i]));
        }
    }

    virtual void onVmCreated(JNIEnv* env)
    {
        if (mClassName.isEmpty()) {
            return; // Zygote. Nothing to do here.
        }

        char* slashClassName = toSlashClassName(mClassName.string());
        mClass = env->FindClass(slashClassName);
        if (mClass == NULL) {
            ALOGE("ERROR: could not find class '%s'\n", mClassName.string());
        }
        free(slashClassName);

        mClass = reinterpret_cast<jclass>(env->NewGlobalRef(mClass));
    }

    virtual void onStarted()
    {
        sp<ProcessState> proc = ProcessState::self();
        ALOGV("App process: starting thread pool.\n");
        proc->startThreadPool();

        AndroidRuntime* ar = AndroidRuntime::getRuntime();
        ar->callMain(mClassName, mClass, mArgs);

        IPCThreadState::self()->stopProcess();
    }

    virtual void onZygoteInit()
    {
        sp<ProcessState> proc = ProcessState::self();
        ALOGV("App process: starting thread pool.\n");
        proc->startThreadPool();
    }

    virtual void onExit(int code)
    {
        if (mClassName.isEmpty()) {
            // if zygote
            IPCThreadState::self()->stopProcess();
        }

        AndroidRuntime::onExit(code);
    }


    String8 mClassName;
    Vector<String8> mArgs;
    jclass mClass;
};

AppRuntime繼承AndroidRuntime,而AndroidRuntime位於
/frameworks/base/core/jni/AndroidRuntime.cpp.
而start()方法便是定義在AndroidRuntime的虛方法:

//這裏的className的值就是com.android.intrnal.os.ZygoteInit
void AndroidRuntime::start(const char* className, const Vector<String8>& options, bool zygote)
{
   //...省略多行代碼

    static const String8 startSystemServer("start-system-server");

    for (size_t i = 0; i < options.size(); ++i) {
        if (options[i] == startSystemServer) {
           /* track our progress through the boot sequence */
           const int LOG_BOOT_PROGRESS_START = 3000;
           LOG_EVENT_LONG(LOG_BOOT_PROGRESS_START,  ns2ms(systemTime(SYSTEM_TIME_MONOTONIC)));
        }
    }

    const char* rootDir = getenv("ANDROID_ROOT");
    if (rootDir == NULL) {
        rootDir = "/system";
        if (!hasDir("/system")) {
            LOG_FATAL("No root directory specified, and /android does not exist.");
            return;
        }
        setenv("ANDROID_ROOT", rootDir, 1);
    }

    //1. 啓動虛擬機
    if (startVm(&mJavaVM, &env, zygote) != 0) {
        return;
    }
    onVmCreated(env);

    //2. 調用startReg()註冊JNI方法
    if (startReg(env) < 0) {
        ALOGE("Unable to register all android natives\n");
        return;
    }

    jclass stringClass;
    jobjectArray strArray;
    jstring classNameStr;

    stringClass = env->FindClass("java/lang/String");
    assert(stringClass != NULL);
    strArray = env->NewObjectArray(options.size() + 1, stringClass, NULL);
    assert(strArray != NULL);
    classNameStr = env->NewStringUTF(className);
    assert(classNameStr != NULL);
    env->SetObjectArrayElement(strArray, 0, classNameStr);

    for (size_t i = 0; i < options.size(); ++i) {
        jstring optionsStr = env->NewStringUTF(options.itemAt(i).string());
        assert(optionsStr != NULL);
        env->SetObjectArrayElement(strArray, i + 1, optionsStr);
    }

    char* slashClassName = toSlashClassName(className);
    jclass startClass = env->FindClass(slashClassName);
    if (startClass == NULL) {
        ALOGE("JavaVM unable to locate class '%s'\n", slashClassName);
    } else {
         //3. 本質就是調用com.android.intrnal.os.ZygoteInit類的main函數
        jmethodID startMeth = env->GetStaticMethodID(startClass, "main",
            "([Ljava/lang/String;)V");
        if (startMeth == NULL) {
            ALOGE("JavaVM unable to find main() in '%s'\n", className);
            /* keep going */
        } else {
            env->CallStaticVoidMethod(startClass, startMeth, strArray);

#if 0
            if (env->ExceptionCheck())
                threadExitUncaughtException(env);
#endif
        }
    }
    free(slashClassName);

   // 省略多行代碼
}

在start()方法中主要做三件事情:
1. 調用startVM()函數啓動虛擬機
2. 調用startReg()註冊JNI方法
3. 調用com.android.internal.os.ZygoteInit.java類的main函數.

走進ZygoteInit

關於前兩者就不細說了,重點來關注我們熟悉的ZygoteInit.java.它在
rameworks/base/core/Java/com/android/internal/os/ZygoteInit.java,我們直接來看他的main方法:

public static void main(String argv[]) {
        ZygoteServer zygoteServer = new ZygoteServer();
        ZygoteHooks.startZygoteNoThreadCreation();
        try {
            Os.setpgid(0, 0);
        } catch (ErrnoException ex) {
            throw new RuntimeException("Failed to setpgid(0,0)", ex);
        }

        try {
            Trace.traceBegin(Trace.TRACE_TAG_DALVIK, "ZygoteInit");
            RuntimeInit.enableDdms();
            // Start profiling the zygote initialization.
            SamplingProfilerIntegration.start();

            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.");
            }
            //創建名爲zygote的socket
            zygoteServer.registerServerSocket(socketName);
            Trace.traceBegin(Trace.TRACE_TAG_DALVIK, "ZygotePreload");
           //省略多行參數
            SamplingProfilerIntegration.writeZygoteSnapshot();

            // Do an initial gc to clean up after startup
            Trace.traceBegin(Trace.TRACE_TAG_DALVIK, "PostZygoteInitGC");
            gcAndFinalize();
            Trace.traceEnd(Trace.TRACE_TAG_DALVIK);
            Trace.setTracingEnabled(false);
            Zygote.nativeUnmountStorageOnInit();

            ZygoteHooks.stopZygoteNoThreadCreation();
            //由於在init.rc中設置了start-system-server參數,因此
            //這裏將啓動SystemServer,可見SystemServer由Zygote創        //建的第一個進程
            if (startSystemServer) {
                //啓動SystemServer組件
                startSystemServer(abiList, socketName, zygoteServer);
            }

            Log.i(TAG, "Accepting command socket connections");
            //等待ActivityManagerService請求
            zygoteServer.runSelectLoop(abiList);

            zygoteServer.closeServerSocket();
        } catch (Zygote.MethodAndArgsCaller caller) {
            caller.run();
        } catch (Throwable ex) {
            Log.e(TAG, "System zygote died with exception", ex);
            zygoteServer.closeServerSocket();
            throw ex;
        }
    }

這裏的main()方法中主要做了三件事情
1. 通過registerServerSocket()來創建Socket,它將作爲服務端用來和作爲客戶端的ActivityManagerService進行通信
2. 通過startSystemServer()方法來啓動SystemServer
3. 最後通過通過runSelectLoop方法使得剛纔創建的Socket進入無限循環,以等待來自ActivityManagerService請求

Zygote中Socket創建

首先來看resiterServerSocket()它在:

  void registerServerSocket(String socketName) {
        if (mServerSocket == null) {
            int fileDesc;
            final String fullSocketName = ANDROID_SOCKET_PREFIX + socketName;
            try {
                String env = System.getenv(fullSocketName);
                //從環境變量env中獲取文件描述符,
                fileDesc = Integer.parseInt(env);
            } catch (RuntimeException ex) {
                throw new RuntimeException(fullSocketName + " unset or invalid", ex);
            }

            try {
                //通過文件描述符創建socket,該描述符代表/dev/socket/zygote文件.
                FileDescriptor fd = new FileDescriptor();
                fd.setInt$(fileDesc);
                mServerSocket = new LocalServerSocket(fd);
            } catch (IOException ex) {
                throw new RuntimeException(
                        "Error binding to local socket '" + fileDesc + "'", ex);
            }
        }
    }

方法主要通過文件描述符創建socket,該文件描述代表/dev/socket/zygote文件,現在看看開頭init.rc中的配置:socket zygote stream 660 root system

Zygote啓動SystemServer

現在來看startSystemServer()方法:

    private static boolean startSystemServer(String abiList, String socketName, ZygoteServer zygoteServer)
            throws Zygote.MethodAndArgsCaller, RuntimeException {
        long capabilities = posixCapabilitiesAsBits(
            OsConstants.CAP_IPC_LOCK,
            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,
            OsConstants.CAP_WAKE_ALARM
        );

        if (!SystemProperties.getBoolean(PROPERTY_RUNNING_IN_CONTAINER, false)) {
            capabilities |= posixCapabilitiesAsBits(OsConstants.CAP_BLOCK_SUSPEND);
        }
        /* 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,3009,3010",
            "--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);

            //創建子進程
            pid = Zygote.forkSystemServer(
                    parsedArgs.uid, parsedArgs.gid,
                    parsedArgs.gids,
                    parsedArgs.debugFlags,
                    null,
                    parsedArgs.permittedCapabilities,
                    parsedArgs.effectiveCapabilities);
        } catch (IllegalArgumentException ex) {
            throw new RuntimeException(ex);
        }

        //pid=0表示子進程,此處就是SystemServer進程
        if (pid == 0) {
            //用於處理系統中有兩個Zygote進程的情況,由於通常我們不會配置兩個Zygote,因此暫時不關注
            if (hasSecondZygote(abiList)) {
                waitForSecondaryZygote(socketName);
            }
            //Zygote創建的子進程(此處就是SystemServer)不需要使用Zygote中創建的Socket文件描述符,因此通過closeServerSocket()關閉它.
            zygoteServer.closeServerSocket();
            handleSystemServerProcess(parsedArgs);
        }

        return true;
    }

這裏首先通過Zygote.forkSystemServer()創建一個系統服務進程.與該方法相似還有forkAndSpecialize(),用於創建一個普通應用進程.進程創建成功後返回pid爲0.由於此處生成的新進程和Zygote進程一模一樣,也就是說這個新進程中同樣包含了剛纔創建的Socket,但是該Socket在此處無效,因此要將其關閉.接下來調用handleSystemServerProcess()處理剛纔新建的進程即SystemServer進程,需要注意此時已經工作在SystemServer進程中了:

    private static void handleSystemServerProcess(
            ZygoteConnection.Arguments parsedArgs)
            throws Zygote.MethodAndArgsCaller {
        //省略多行代碼,此處invokeWith爲null
        if (parsedArgs.invokeWith != null) {
            String[] args = parsedArgs.remainingArgs;

            if (systemServerClasspath != null) {
                 //省略多行代碼  
             } else {

            ClassLoader cl = null;
            if (systemServerClasspath != null) {
            //爲SysteServer進程創建PathClassLoader類加載器
                cl = createSystemServerClassLoader(systemServerClasspath,
                                            parsedArgs.targetSdkVersion);

Thread.currentThread().setContextClassLoader(cl);
            }

            RuntimeInit.zygoteInit(parsedArgs.targetSdkVersion, parsedArgs.remainingArgs, cl);
        }

    }

該函數繼續調用RuntimeInit.zygoteInit()進一步執行啓動SystemServer組件的操作.繼續來看 RuntimeInit.zygoteInit()的具體實現,它在
/frameworks/base/core/java/com/android/internal/os/RuntimeInit.java文件中:

    public static final void zygoteInit(int targetSdkVersion, String[] argv, ClassLoader classLoader)
            throws Zygote.MethodAndArgsCaller {
        //...省略多行代碼

        commonInit();
        nativeZygoteInit();
        applicationInit(targetSdkVersion, argv, classLoader);
    }

在該方法中主要調用了三個方法:

  • commonInit():爲當前進程的VM設置未捕獲異常處理器
  • nativeZygoteInit():Binder驅動初始化,該方法完成後,就可以通過該Binder進行進程通信
  • applicationInit():主要用調用com.android.server.SystemServer類的main()方法

由於commonInit()方法比較簡單,在此就不做分析.
nativeZygoteInit()是一個本地方法,其對應實現在frameworks/base/core/jni/AndroidRuntime.cpp中:

static void com_android_internal_os_RuntimeInit_nativeZygoteInit(JNIEnv* env, jobject clazz)
{
    gCurRuntime->onZygoteInit();
}

這裏的gCurRuntime是AppRuntime的指針,在frameworks/base/core/jni/AndroidRuntime.cpp中定義,並在AndroidRuntime的夠贊函數中初始化:

//定義
static AndroidRuntime* gCurRuntime = NULL;

...

//在frameworks/base/cmds/app_process/app_main.cpp的main()方法中被調用
AndroidRuntime::AndroidRuntime(char* argBlockStart, const size_t argBlockLength) :
        mExitWithoutCleanup(false),
        mArgBlockStart(argBlockStart),
        mArgBlockLength(argBlockLength)
{
    SkGraphics::Init();
    mOptions.setCapacity(20);

    assert(gCurRuntime == NULL);
    gCurRuntime = this;
}

繼續來看onZygoteInit():

 virtual void onZygoteInit()
    {
        sp<ProcessState> proc = ProcessState::self();
        ALOGV("App process: starting thread pool.\n");
        proc->startThreadPool();
    }

這裏調用ProcessState::startThreadPool()方法啓動線程池,這個線程池就是用來和Binder驅動程序進程交互的.(Binder驅動本質就是一個文件,位於/dev/binder),關於線程池具體創建的過程暫不做說明.

現在來看applicationInit():

    private static void applicationInit(int targetSdkVersion, String[] argv, ClassLoader classLoader)
            throws ZygoteInit.MethodAndArgsCaller {
         //省略多行代碼
        invokeStaticMain(args.startClass, args.startArgs, classLoader);
    }

這裏繼續調用了invokeStaticMain()進行後續工作:

    private static void invokeStaticMain(String className, String[] argv, ClassLoader classLoader)
            throws ZygoteInit.MethodAndArgsCaller {
        Class<?> cl;

        try {
            cl = Class.forName(className, true, classLoader);
        } catch (ClassNotFoundException ex) {
            throw new RuntimeException(
                    "Missing class when invoking static main " + className,
                    ex);
        }

        Method m;
        try {
            m = cl.getMethod("main", new Class[] { String[].class });
        } catch (NoSuchMethodException ex) {
            //...
        } catch (SecurityException ex) {
            //...
        }

       // 省略多行代碼

        /*
         * This throw gets caught in ZygoteInit.main(), which responds
         * by invoking the exception's run() method. This arrangement
         * clears up all the stack frames that were required in setting
         * up the process.
         */
        throw new ZygoteInit.MethodAndArgsCaller(m, argv);
    }

此時要執行的是com.android.server.SystemServer的中mian()方法.此外真正執行的過程是在Zygote.MethodAndArgsCaller的run()方法中:

    public static class MethodAndArgsCaller extends Exception
            implements Runnable {
        /** method to call */
        private final Method mMethod;

        /** argument array */
        private final String[] mArgs;

        public MethodAndArgsCaller(Method method, String[] args) {
            mMethod = method;
            mArgs = args;
        }

        public void run() {
            try {
                mMethod.invoke(null, new Object[] { mArgs });
            } catch (IllegalAccessException ex) {
                throw new RuntimeException(ex);
            } catch (InvocationTargetException ex) {
               //省略多行代碼
            }
        }
    }

MethodAndArgsCaller繼承Exception並實現Runnable接口,作爲一個異常他被ZygoteInit.main()捕獲並處理:

   public static void main(String argv[]) {
        // ...
        try {
             //...省略多行代碼
             startSystemServer(abiList, socketName);
        } catch (MethodAndArgsCaller caller) {
            caller.run();
        } catch (Throwable ex) {
            //...
        }
    }

現在SystemServer的main()已經被調用,我們順着來看一下實現:

public class SystemServer{

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


    private void run() {
        try {
            //...省略一些初始化操作

            android.os.Process.setThreadPriority(
                android.os.Process.THREAD_PRIORITY_FOREGROUND);
            android.os.Process.setCanSelfBackground(false);
            //初始化主線程Looper
            Looper.prepareMainLooper();

            //創建SystemServiceManager對象
            mSystemServiceManager = new SystemServiceManager(mSystemContext);
            LocalServices.addService(SystemServiceManager.class, mSystemServiceManager);
        } finally {
            Trace.traceEnd(Trace.TRACE_TAG_SYSTEM_SERVER);
        }

            // 啓動關鍵服務
            startBootstrapServices();
            //啓動核心服務
            startCoreServices();
            //啓動其他服務
            startOtherServices();
            //...省略多行代碼

            //啓動消息循環
            Looper.loop();

    }

}

在main()方法中調用了run()方法繼續啓動操作.在run方法中這三個方法非常重要:

  1. startBootstrapServices():啓動引導服務,比如AMS,PMS等
  2. startCoreServices():啓動核心服務,比如BatteryService等
  3. startOtherServices():啓動其他服務,比如NetworkStatsService等.

關於SystemService的具體執行過程,在此不做細解.

Socket循環監聽

到目前爲止,關於ZygoteServer.registerServerSocket()startSystemServer()的大體流程我們已經弄清除,接下來就是ZygoteServer.runSelectLoop()方法:

void runSelectLoop(String abiList) throws Zygote.MethodAndArgsCaller {
        ArrayList<FileDescriptor> fds = new ArrayList<FileDescriptor>();
        ArrayList<ZygoteConnection> peers = new ArrayList<ZygoteConnection>();

        fds.add(mServerSocket.getFileDescriptor());
        peers.add(null);

        while (true) {
            StructPollfd[] pollFds = new StructPollfd[fds.size()];
            for (int i = 0; i < pollFds.length; ++i) {
                pollFds[i] = new StructPollfd();
                pollFds[i].fd = fds.get(i);
                pollFds[i].events = (short) POLLIN;
            }
            try {
                Os.poll(pollFds, -1);
            } catch (ErrnoException ex) {
                throw new RuntimeException("poll failed", ex);
            }
            for (int i = pollFds.length - 1; i >= 0; --i) {
                if ((pollFds[i].revents & POLLIN) == 0) {
                    continue;
                }
                if (i == 0) {
                   //監聽Socket鏈接,如果你做過Socket編程就發現此處充當了服務端Socket
                    ZygoteConnection newPeer = acceptCommandPeer(abiList);
                    peers.add(newPeer);
                    fds.add(newPeer.getFileDesciptor());
                } else {
                    //重點關注runOnce()方法
                    boolean done = peers.get(i).runOnce(this);
                    if (done) {
                        peers.remove(i);
                        fds.remove(i);
                    }
                }
            }
        }
    }

該方法非常簡單:不斷的處理來自客戶端AMS的請求,然後交給runOnce().此處可見Android 7.0應用啓動流程分析

到現在爲止,整個SystemServer進程的啓動流程已經明確看,用一張順序圖大體的表示上述的整個流程:
這裏寫圖片描述


總結

  1. 系統啓動時init進程會創建Zygote進程,Zygote進程負責後續Android應用框架層的其他進程的創建和啓動.
  2. Zygote進程會首先創建一個SystemSever進程,然後由SystemServer負責啓動系統關鍵服務,如ActivityManagerService或者PackageManagerService等.
發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章