这一次,让SystemServer, SystemServiceManager,SystemService不可能再记混

近期整理android runtime的时候,看到以前在印象笔记里记的SystemServer跟SystemServiceManager笔记,查看源码的时候都避不开SystemServer跟SystemServiceManager,笔记尘封已久,之前一直犹豫会不会做得不够全面详细,毕竟现在客户端研发也到了末法时代,改改笔记结构内容发出来让大佬们指正一下也好.

场景复现

"SystemServer是什么, look at my eyes!"

"是android系统里的一个进程"

"什么进程"

"由Zygote进程孵化的第一个进程,在ZygoteInit类在执行main方法的过程中体现,具体forkSystemService方法"

"不是第一个进程不是launcher进程吗?桌面呀"

"不是,那个是app进程"

"那SystemServiceManager呢"

"从来不是同个东西"

"管理SystemService吗,还是管理SystemServer"

"大哥你别捣乱了,本来不晕都被你绕晕了"

"......,要不你还是好好说下吧"

SystemServer

进程怎么被创建的

从ZygoteInit方法的main方法可知,当参数argv里,携带允许start-system-server参数时,会触发forkSystemServer方法,内部通过拼接SystemServer进程所需参数后,转化为ZygoteCommand,最终借助Zygote类的同名方法,完成SystemServer进程的创建,最终返回子进程pid给到Zygote进程,代码执行回到ZygoteInit.随后执行handleSystemServerProcess方法处让SystemServer进程处理其他内容.

来,这里Zygote怎么创建SystemServer的,我们点击forkSystemServer方法查看内容.好的,native方法,看不下去了.收!

创建进程时都干了什么

看main方法,创建了一个SystemServer对象并执行其run方法.

run方法,这是个Runable?还真不是,实现的是Dumpable接口

但是这个接口里也没有对run抽象方法的声明呀.为什么,为什么?为什么!!!


没错,人家压根不是什么抽象方法run,就是起名叫了run而已.


好好好,都这么玩是吧,谷歌工程师们.唔,按我们业内的说法,属于历史原因,咱们就不追究了.如果你知道的话也麻烦告诉我.

回到run方法的流程内容,大概包括如下内容:

  • Looper处理
  • 加载动态库lib
  • 系统级别上下文创建和主线模块初始化
  • ActivityThread调用每个进程主线模块初始化
  • 创建SystemServiceManager挂载到LocalServices
  • SystemServiceManager启动各种服务
  • Looper开启循环

Looper初始化

调用了Looper.prepareMainLooper();

从上述代码可以知道,创建的是一个不可退出的Looper.诶?Looper,不是得跟线程绑定的吗,你看,还得存ThreadLocal里面,那目前所在的线程是什么线程? 答:主线程!SystemServer进程的main方法所在线程.

当时我在这里也打了问号:主线程不是UI线程吗?这里还在系统创建阶段,UI线程可能还没创建对吧?

这里要看对主线程的定义,在系统进程中,主线程通常是指进程启动时的第一个线程。对于SystemServer进程,main方法所在的线程就是主线程.但我们在android 应用中的主线程一般说的都是UI线程,这里说法不冲突.

总的作用就是让SystemServer进程的主线程有了Looper,使得主线程能够处理消息和任务。 先讲到这里,下面介绍looper调用loop方法我们再展开介绍.

加载动态库lib

加载android_servers.so,这个暂时没深挖,以后再说.

基于创建AcitvityThread来完成系统级别上下文创建和主线模块初始化

在这里开始整大活了,ActivityThread对象的创建,就是在SystemServer进程里完成的 ,关于ActivityThread创建的细节,我再单独拎出来介绍.完成创建后获取系统级别的Context.后续所有用到系统服务创建的,基本上都依赖mSystemContext字段.

调用主线模块中的各种初始器API,什么系统里的大管理对象,都在系统初始化阶段都实例化一遍.

基于系统级别上下文创建SystemServiceManager并挂载到LocalServices

来了,SystemServer的main方法里用new的方式创建了SystemServiceManager,使用LocalServices保存起来,这句记住以后还能记乱的话,那,那,那......那你就回来再看一遍!!!这里先打住,下面介绍SystemServiceManager时再说说保存方式

基于SystemServiceManager启动各种服务

这里包括但不限于:

  • Bootstrap服务: 启动系统启动所需的一小部分关键服务,由于这些服务具有复杂的相互依赖关系,在这里将它们全部初始化。具体查看方法内mSystemServiceManager.startService所启动的服务。注意,ActivityManagerService,简称AMS,也是在这个方法内被实例化的

  • 核心服务

  • 其他服务

looper开启循环

调用loop方法后,SystemServer进程的主线程开始接收消息,消息都是Android标准的Message对象,它们被放入SystemServer主线程的MessageQueue中,由Looper.loop方法按顺序取出并分发给对应的Handler处理.

但是要接收什么消息?应用消息?系统消息?还是从哪来的Message?

接收消息

  • 系统服务内部消息:各种系统服务(如ActivityManagerService、PackageManagerService、WindowManagerService等),通过Handler发送到主线程的消息,这些服务大多在启动时就会创建Handler与主线程的MessageQueue关联,用于服务内部状态更新、跨服务协调等.
  • Binder通信消息:应用进程通过Binder机制向系统服务发起的请求,这些请求通常在Binder线程池中接收,然后通过Handler转发到主线程处理.例如:应用启动Activity、Service的请求都会通过这种方式传递
  • 延时任务消息:系统服务通过Handler.postDelayed()安排的定时任务,用于处理需要延迟执行的操作
  • 事件响应消息:对系统广播、Intent的响应,硬件相关事件(如电源状态变化)的处理
  • 内部状态转换消息:服务生命周期状态变化,系统配置变更通知

SystemServer类里使用Looper#looper跟ZygoteInit类里ZygoteServer#runSelectLoop有什么区别?为什么?

这里的消息循环与ZygoteServer中用于接收新应用启动请求的runSelectLoop方法是完全不同的机制。

  • ZygoteServer使用的是Socket select循环来监听应用启动请求
  • SystemServer使用的是标准Android Handler消息循环机制

因为Zygote进程的作用是等待并处理新应用启动请求,要求高效地接收来自AMS的应用启动请求,快速fork出新进程,也把限制只有特定系统进程可以请求创建应用.所以使用基于Socket I/O的阻塞式监听.简单说就是,需要处理跨进程Socket通信,要求fork要快,还要安全.

但是SystemServer进程作用是管理各种系统服务,响应应用请求和系统事件,尤其是灵活处理各类异步事件,内部服务需要通过Binder提供给应用程序.所以使用基于Handler/Looper的消息驱动模式.简单说就是,需要处理内部服务间的协作,因为内部服务都在同一进程中,消息驱动适合处理大量并发的、轻量级的系统服务请求.

SystemServiceManager

用来干嘛

概括就是管理SystemServer进程内系统服务的创建、启动和其他生命周期事件(在上面截图也能看到各种startService,用它开启了多少系统服务).

怎么被保存的:LocalServices#addService

前面提到在SystemServer的run方法里,会用LocalServices的addService方法完成保存

LocalServices只能在同一个进程中使用(但这里是SystemServer进程内),内部使用静态字段map位置存储添加的服务,在添加删除时候以该map为同步锁,确保线程安全.

SystemServiceManager怎么保存其他服务的:容器

点开源码,列举其内容方法的重载,能得到结论:

  • 不管是类名,类的字节码对象都将通过类加载器被转换成SystemService对象 执行重载方法

  • 调用SystemService的抽象方法onStart开启服务,并以SystemService对象的形式,记录在列表字段里,用于防止服务重复启动.这里区别于四大组件里Service的onStart方法

关于SystemSevice

在文章开头故意给大家打岔的内容,我们现在也明确知道,SystemServiceManager确实是管理系统服务,你要说管理一堆SystemSevice也行,因为还真有SystemSevice这个类来代表那些系统服务,附上源码和介绍

补充:

SystemServer类里使用Looper#looper,那处理UI吗?

不处理. SystemServer主要处理系统级别的服务消息,而不是UI相关的消息。

LocalServices#addService除了保存SystemServiceManager,还保存了什么呢?

至少还保存了PermissionMigrationHelperImpl跟AppOpMigrationHelperImpl对象.详见startBootstrapServices方法

相关推荐
千里马学框架3 天前
一起学 Android 14:ShellTransition 屏幕旋转过程深度剖析
android·智能手机·性能优化·framework·性能·屏幕旋转·rotation
美狐美颜SDK开放平台3 天前
开发直播APP时如何接入视频美颜SDK?开发流程与注意事项
android·人工智能·计算机视觉·音视频·直播美颜sdk
AFinalStone3 天前
Android7 SystemUI源码解析(七)Keyguard锁屏模块深度解析
android·systemui
致远ccc3 天前
Google Play 上架前如何测试 App?多国家 Android 环境测试
android·app测试·googleplay·多国家应用测试
ttyyttemo3 天前
Kotlin 协程中的 Job 结构化并发与取消
android
sun0077003 天前
tbox 4g/5g切换,导致wan ip 改变,导致车机旧网络不可用。需要重启车机才行
android
其实防守也摸鱼3 天前
内网穿透与反向代理:原理、工具与实战指南
android·大数据·运维·安全·网络安全·自动化·渗透
AFinalStone3 天前
Android7 SystemUI 源码解析(四)NavigationBar 导航栏与 SystemBars
android·systemui
JMchen3 天前
属性动画原理与高级动画实现
android·kotlin·canvas
AFinalStone3 天前
Android7 SystemUI 源码解析(二)启动流程深度解析
android·systemui