从源码角度看Android系统SystemServer进程启动过程

本文详细探讨了Android SystemServer进程的启动过程,从Zygote进程的startSystemServer方法开始,逐步解析了forkSystemServer、nativeForkSystemServer、ForkAndSpecializeCommon等关键步骤。在SystemServer进程启动后,执行了包括dex优化、Binder线程池启动、SystemServer的main方法等一系列初始化工作。文章最后概述了SystemServer启动后的重要任务,如启动引导服务、核心服务和其他服务,涵盖了如ActivityManagerService、PowerManagerService等多个关键服务。
摘要由CSDN通过智能技术生成

SystemServer进程是由Zygote进程fork生成,进程名为system_server,主要用于创建系统服务。

备注:本文将结合Android8.0的源码看SystemServer进程的启动过程以及SystemServer进程做了哪些重要工作。

1. SystemServer进程启动的起点

《从源码角度看Android系统Zygote进程启动过程》一文中可知:Zygote进程启动过程中会调用startSystemServer方法,而startSystemServer函数是system_server进程启动流程的起点。

代码路径:frameworks/base/core/java/com/android/internal/os/ZygoteInit.java

深入到startSystemServer函数中:

private static boolean startSystemServer(String abiList, String socketName, ZygoteServer zygoteServer)
        throws Zygote.MethodAndArgsCaller, RuntimeException {

    ...省略...

	//参数准备,args数组中保存启动SystemServer的启动参数
    String args[] = { //注释1
        "--setuid=1000",
        "--setgid=1000",
        "--setgroups=1001,1002,1003,1004,1005,1006,1007,1008,1009,1010,1018,1021,1023,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); //注释2
        ZygoteConnection.applyDebuggerSystemProperty(parsedArgs);
        ZygoteConnection.applyInvokeWithSystemProperty(parsedArgs);

        //fork子进程,也是创建SystemServer进程
        pid = Zygote.forkSystemServer( //注释3
                parsedArgs.uid, parsedArgs.gid,
                parsedArgs.gids,
                parsedArgs.debugFlags,
                null,
                parsedArgs.permittedCapabilities,
                parsedArgs.effectiveCapabilities);
    } catch (IllegalArgumentException ex) {
        throw new RuntimeException(ex);
    }

    //运行在子进程中
    if (pid == 0) {
        if (hasSecondZygote(abiList)) {
            waitForSecondaryZygote(socketName);
        }
		//关闭zygote原有的socket
        zygoteServer.closeServerSocket();
		//处理SystemServer进程
        handleSystemServerProcess(parsedArgs); //注释4
    }
    return true;
}

注释解析:

  • 注释1创建args数组,主要用来保存启动SystemServer的启动参数。

其中:

可以看出SystemServer进程的的用户id和用户组id都被设置为了1000,并且拥有用户组1001-1010、1018、1021、1032、3001-3010的权限。

进程名为:system_server

启动的类名为:com.android.server.SystemServer

  • 注释2处将args数组封装成Arguments对象,并给注释3处的forkSystemServer函数调用

  • 注释3处调用Zygote的forkSystemServer方法,其内部会调用nativeForkSystemServer这个Native方法,nativeForkSystemServer会通过fork函数在当前进程创建一个子进程,即SystemServer进程。

  • 注释4处理SystemServer进程

2. 创建SystemServer进程
2.1 forkSystemServer

通过上面的注释3可知:是调用Zygote的forkSystemServer方法去创建SystemServer进程。

代码路径:frameworks/base/core/java/com/android/internal/os/Zygote.java

深入到函数forkSystemServer中:

public static int forkSystemServer(int uid, int gid, int[] gids, int debugFlags,
        int[][] rlimits, long permittedCapabilities, long effectiveCapabilities) {
    VM_HOOKS.preFork();
    // Resets nice priority for zygote process.
    resetNicePriority();
	//调用natvie方法fork system_server进程
    int pid = nativeForkSystemServer(
            uid, gid, gids, debugFlags, rlimits, permittedCapabilities, effectiveCapabilities);
    if (pid == 0) {
        Trace.setTracingEnabled(true);
    }
    VM_HOOKS.postForkCommon();
    return pid;
}

备注:这里继续往下看,需要懂一点JNI原理,这里不做介绍,后续会单独写一篇《JNI学习总结》。

nativeForkSystemServer()方法是在AndroidRuntime.cpp中注册的,通过com_android_internal_os_Zygote.cpp中的register_com_android_internal_os_Zygote()方法建立native方法的映射关系的。

2.2 nativeForkSystemServer

进入到com_android_internal_os_Zygote.cpp中:

代码路径:frameworks/base/core/jni/com_android_internal_os_Zygote.cpp

nativeForkSystemServer方法在JNI层对应的方法是:com_android_internal_os_Zygote_nativeForkSystemServer

深入到函数com_android_internal_os_Zygote_nativeForkSystemServer中:

static jint com_android_internal_os_Zygote_nativeForkSystemServer(
        JNIEnv* env, jclass, uid_t uid, gid_t gid, jintArray gids,
        jint debug_flags, jobjectArray rlimits, jlong permittedCapabilities,
        jlong effectiveCapabilities) {
  //fork 子进程
  pid_t pid = ForkAndSpecializeCommon(env, uid, gid, gids,
                                      debug_flags, rlimits,
                                      permittedCapabilities, effectiveCapabilities,
                                      MOUNT_EXTERNAL_DEFAULT, NULL, NULL, true, NULL,
                                      NULL, NULL, NULL);
  if (pid > 0) {
      // zygote进程检测system_server进程是否创建
      gSystemServerPid = pid;
      int status;
      if (waitpid(pid, &status, WNOHANG) == pid) {
          ALOGE("System server process %d has died. Restarting Zygote!", pid);
		  // 当system_server进程死亡后,重启zygote进程
          RuntimeAbort(env, __LINE__, "System server process has died. Restarting Zygote!");
      }
  }
  return pid;
}

从上面可知:

1: 调用ForkAndSpecializeCommon()方法fork子进程

2: 当system_server进程死亡后,会重启zygote进程

扩展知识:

在Android5.0以上时,会有两个zygote进程,分别是zygote和zygote64。一般在64位系统中system_server的父进程是zygote64。

在64位系统中,kill system_server、zygote、zygote64三个进程是否重启的关系图如下:

继续深入到ForkAndSpecializeCommon()方法中。

2.3 ForkAndSpecializeCommon

代码路径:frameworks/base/core/jni/com_android_internal_os_Zygote.cpp

深入到ForkAndSpecializeCommon方法中:

static pid_t ForkAndSpecializeCommon(JNIEnv* env, uid_t uid, gid_t gid, jintArray javaGids,
                                     jint debug_flags, jobjectArray javaRlimits,
                                     jlong permittedCapabilities, jlong effectiveCapabilities,
                                     jint mount_external,
                                     jstring java_se_info, jstring java_se_name,
                                     bool is_system_server, jintArray fdsToClose,
                                     jintArray fdsToIgnore,
                                     jstring instructionSet, jstring dataDir) {

  //设置子进程的signal信号处理
  SetSigChldHandler();

  ...省略...
  //fork 子进程
  pid_t pid = fork();
  // 进入子进程
  if (pid == 0) {
    
	...省略...

    //关闭并清除文件描述符
    DetachDescriptors(env, fdsToClose);

    ...省略...

    if (!is_system_server) {//如果是非system_server子进程,则创建进程组
        int rc = createProcessGroup(uid, getpid());
        if (rc != 0) {
            if (rc == -EROFS) {
                ALOGW("createProcessGroup failed, kernel missing CONFIG_CGROUP_CPUACCT?");
            } else {
                ALOGE("createProcessGroup(%d, %d) failed: %s", uid, pid, strerror(-rc));
            }
        }
    }
	//设置group
    SetGids(env, javaGids);
	//设置资源limit
    SetRLimits(env, javaRlimits);

    ...省略...
    //selinux上下文
    rc = selinux_android_setcontext(uid, is_system_server, se_info_c_str, se_name_c_str);
    if (rc == -1) {
      ALOGE("selinux_android_setcontext(%d, %d, \"%s\", \"%s\") failed", uid,
    
  • 1
    点赞
  • 3
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值