Android源码分析--system_server进程分析

来源:互联网 发布:火箭nba 知乎 编辑:程序博客网 时间:2024/06/05 07:09

在上一篇博文中我们进行了有关Zygote进程的分析,我们知道Zygote进程创建了一个重要的进程–system_server进程后就进入了无限循环中,之后Android系统中的重要任务就交给了system_server进程,作为zygote的嫡长子进程,system_server进程的意义非凡,今天我们来分析一下system_server进程。

创建system_server进程

在ZygoteInit中main方法中,通过调用startSystemServer方法开启了system_server进程。该方法主要为创建system_server进程准备了一些参数,并调用本地方法forkSystemServer创建system_server进程。让我们来看一下startSystemServer方法的代码:

    private static boolean startSystemServer()            throws MethodAndArgsCaller, RuntimeException {        String args[] = {            "--setuid=1000",            "--setgid=1000",            "--setgroups=1001,1002,1003,1004,1005,1006,1007,1008,1009,1010,1018,1032,3001,3002,3003,3006,3007",            "--capabilities=130104352,130104352",            "--runtime-init",            "--nice-name=system_server",            "com.android.server.SystemServer",        };        ZygoteConnection.Arguments parsedArgs = null;        int pid;        try {            parsedArgs = new ZygoteConnection.Arguments(args);            ZygoteConnection.applyDebuggerSystemProperty(parsedArgs);            ZygoteConnection.applyInvokeWithSystemProperty(parsedArgs);            /* 创建system_server进程 */            pid = Zygote.forkSystemServer(                    parsedArgs.uid, parsedArgs.gid,                    parsedArgs.gids,                    parsedArgs.debugFlags,                    null,                    parsedArgs.permittedCapabilities,                    parsedArgs.effectiveCapabilities);        } catch (IllegalArgumentException ex) {            throw new RuntimeException(ex);        }        /* 子进程中执行 */        if (pid == 0) {            handleSystemServerProcess(parsedArgs);        }        return true;    }

这里的代码并不复杂,可以看到,他调用了forkSystemServer方法来创建一个新的进程,之后在子进程,即system_server进程中执行handleSystemServerProcess方法。下面我们来看一下forkSystemServer方法,它是一个native方法对应的源文件在dalvik\vm\native\dalvik_system_Zygote.cpp中。代码如下:

static void Dalvik_dalvik_system_Zygote_forkSystemServer(        const u4* args, JValue* pResult){    pid_t pid;    pid = forkAndSpecializeCommon(args, true);    /* zygote进程检查其子进程是否死掉 */    if (pid > 0) {        int status;        ALOGI("System server process %d has been created", pid);        gDvm.systemServerPid = pid;        /*  如果system_server进程退出,则zygote进程也会被杀掉 */        if (waitpid(pid, &status, WNOHANG) == pid) {            ALOGE("System server process %d has died. Restarting Zygote!", pid);            kill(getpid(), SIGKILL);        }    }    RETURN_INT(pid);}

从代码中可以看到在forkAndSpecializeCommon方法中,我们创建了子进程,并返回了子进程id,接下来我检查如果system_server进程是否退出,若是的话则zygote进程也将会被被干掉,由此可见其重要性。接下来我们来看forkAndSpecializeCommon的代码,这个system_server进程的创建真的是千峰百转啊。。。

static pid_t forkAndSpecializeCommon(const u4* args, bool isSystemServer){    pid_t pid;    uid_t uid = (uid_t) args[0];    gid_t gid = (gid_t) args[1];    ArrayObject* gids = (ArrayObject *)args[2];    u4 debugFlags = args[3];    ArrayObject *rlimits = (ArrayObject *)args[4];    u4 mountMode = MOUNT_EXTERNAL_NONE;    int64_t permittedCapabilities, effectiveCapabilities;    char *seInfo = NULL;    char *niceName = NULL;    //传入参数isSystemServer为true    if (isSystemServer) {        permittedCapabilities = args[5] | (int64_t) args[6] << 32;        effectiveCapabilities = args[7] | (int64_t) args[8] << 32;    } else {       ......    }    if (!gDvm.zygote) {        dvmThrowIllegalStateException(            "VM instance not started with -Xzygote");        return -1;    }    // 在第一次调用fork函数之前需要调用    if (!dvmGcPreZygoteFork()) {        ALOGE("pre-fork heap failed");        dvmAbort();    }    setSignalHandler();    //向log文件中写入一些数据    dvmDumpLoaderStats("zygote");    //子进程被fork出来    pid = fork();    if (pid == 0) {    //在这里根据传入的参数对子进程做出一些处理,例如设置进程名,设置各种id等    ......    }    return pid;}

至此system_server进程终于被创建出来,我们可以看到system_server进程也是通过Linux系统特有的Fork机制分裂克隆出来的。在fork之前,我们还有一个重要方法没有分析–setSignalHandler方法,该方法用来设置信号处理,下面让我来看一下吧。

static void setSignalHandler(){    int err;    struct sigaction sa;    memset(&sa, 0, sizeof(sa));    sa.sa_handler = sigchldHandler;    err = sigaction (SIGCHLD, &sa, NULL);//设置信号处理函数,该信号是子进程死亡的信号    if (err < 0) {        ALOGW("Error setting SIGCHLD handler: %s", strerror(errno));    }}static void sigchldHandler(int s){    pid_t pid;    int status;    while ((pid = waitpid(-1, &status, WNOHANG)) > 0) {        /* 打印出我们所关心的进程的死亡状态. */        ......        /*         * 如果刚刚销毁的进程是system_server, 同时杀死zygote进程         * 这样system_server进程和zygote进程将会被init进程重启         */        if (pid == gDvm.systemServerPid) {            ALOG(LOG_INFO, ZYGOTE_LOG_TAG,                "Exit zygote because system server (%d) has terminated",                (int) pid);            kill(getpid(), SIGKILL);        }    }    if (pid < 0) {        ALOG(LOG_WARN, ZYGOTE_LOG_TAG,            "Zygote SIGCHLD error in waitpid: %s",strerror(errno));    }}

这里我们发现我们之前已经看到在forkSystemServer方法中已经检查过system_server进程是否死亡,为什么这里还要再一次进行检查?这是为了防止在我们还没有得到fork子进程的pid时,system_server进程就已经死亡的情况。

总结一下:system_server进程的创建经历了漫长的历程:首先startSystemServer中调用了native方法forkSystemServer;之后在native方法forkSystemServer中调用了forkAndSpecializeCommon方法;在forkAndSpecializeCommon方法中fork之前还调用了setSignalHandler来设置信号处理项。这样,我们的system_server进程终于被创建起来,同时他还和zygote进程保持着同生共死的关系。

system_server进程的职责

在startSystemServer的方法中我们可以看到,在创建进程之后,在子进程即system_server进程中会执行handleSystemServerProcess方法,这便是system_server的职责所在,下面我们来看一下:

    private static void handleSystemServerProcess(            ZygoteConnection.Arguments parsedArgs)            throws ZygoteInit.MethodAndArgsCaller {        closeServerSocket();        // 设置权限.        Libcore.os.umask(S_IRWXG | S_IRWXO);        ......        if (parsedArgs.invokeWith != null) {        ......        } else {            /* 剩余的参数传递到SystemServer. */            RuntimeInit.zygoteInit(parsedArgs.targetSdkVersion, parsedArgs.remainingArgs);        }    }

可以看到最后system_server进程来到了RuntimeInit中,它的实现在frameworks\base\core\java\com\android\internal\os\RuntimeInit.java中

    public static final void zygoteInit(int targetSdkVersion, String[] argv)            throws ZygoteInit.MethodAndArgsCaller {        if (DEBUG) Slog.d(TAG, "RuntimeInit: Starting application from zygote");        //关闭System.out和System.err,使用Android log        redirectLogStreams();        //做一些常规初始化        commonInit();        //native层初始化,调用此方法之后system_server将与Binder通信系统建立联系,这样就可以使用Binder了        nativeZygoteInit();        applicationInit(targetSdkVersion, argv);    }    private static void applicationInit(int targetSdkVersion, String[] argv)            throws ZygoteInit.MethodAndArgsCaller {        ......        try {            args = new Arguments(argv);        } catch (IllegalArgumentException ex) {            Slog.e(TAG, ex.getMessage());            // let the process exit            return;        }        invokeStaticMain(args.startClass, args.startArgs);    }

可以看到,最终我们调用了invokeStaticMain方法,该方法的传入参数在startSystemServer方法中被设置,其传入参数的类名是”com.android.server.SystemServer”

    private static void invokeStaticMain(String className, String[] argv)            throws ZygoteInit.MethodAndArgsCaller {        Class<?> cl;        try {            cl = Class.forName(className);        } 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) {            throw new RuntimeException(                    "Missing static main on " + className, ex);        } catch (SecurityException ex) {            throw new RuntimeException(                    "Problem getting static main on " + className, ex);        }        int modifiers = m.getModifiers();        if (! (Modifier.isStatic(modifiers) && Modifier.isPublic(modifiers))) {            throw new RuntimeException(                    "Main method is not public and static on " + className);        }        /* 抛出的异常在ZygoteInit.main()中被截获 */        throw new ZygoteInit.MethodAndArgsCaller(m, argv);    }

让我们来看看被截获的语句:

 catch (MethodAndArgsCaller caller) {            caller.run();//调用了caller的run方法        } 

run方法代码:

public void run() {            try {                mMethod.invoke(null, new Object[] { mArgs });            } catch (IllegalAccessException ex) {                throw new RuntimeException(ex);            } catch (InvocationTargetException ex) {                Throwable cause = ex.getCause();                if (cause instanceof RuntimeException) {                    throw (RuntimeException) cause;                } else if (cause instanceof Error) {                    throw (Error) cause;                }                throw new RuntimeException(ex);            }        }

可以看到,在函数最后抛出异常,在ZygoteInit.main()中被截获,由于传递的参数类名是”com.android.server.SystemServer”,这样我们调用了MethodAndArgsCaller.run()方法去执行了SystemServer类的静态main方法。(关于ZygoteInit可以参考上一篇博文:Android源码分析–Zygote进程分析)

    public static void main(String[] args) {        ......        // Mmmmmm... more memory!        dalvik.system.VMRuntime.getRuntime().clearGrowthLimit();        // system server一直在运行, 所以他需要尽可能有效的利用内存        VMRuntime.getRuntime().setTargetHeapUtilization(0.8f);        Environment.setUserRequired(true);        System.loadLibrary("android_servers");        Slog.i(TAG, "Entered the Android system server!");        // native方法,进行一些传感器服务的初始化        nativeInit();        // 创建一个单独的线程,在这里启动系统的各项服务        ServerThread thr = new ServerThread();        thr.initAndLoop();    }

最终,system_server开启了一个新的线程,并执行了它的initAndLoop方法,其也被定义在SystemServer.java中,该方法的代码较多,其主要的工作就是开启了系统中的各项服务,如电池服务,蓝牙服务等等。并调用了Looper的prepareMainLooper方法进行消息循环,然后处理消息,这里不再赘述。

最后,我们来总结一下:

  • 首先system_server执行handleSystemServerProcess方法来完成自己的使命;
  • 之后调用RuntimeInit.zygoteInit方法,在这里我们进行了一些常规的初始化工作已经native层的初始化,从而与Binder通信建立联系;
  • 之后调用invokeStaticMain方法,利用抛出异常的方法在ZygoteInit的main方法中截获并去执行SystemServer的main方法;
  • 在SystemServer的main方法中,我调用nativeInit方法去初始化一些传感器服务,并开启了单独的线程去开启Android系统中的各项服务,并调用了Looper的prepareMainLooper方法进行消息循环,然后处理消息
1 0
原创粉丝点击