---
title: 'SystemServer'
disqus: kyleAlien
---
SystemServer
===
## OverView of Content
[TOC]
## SystemServer
SystemServer 是由 init 進程 Fork 出來,而 **AMS、PKMS、PMS、WMS... 等等系統服務 也是由 SystemServer 啟動**
> 
### SystemServer Context
* SystemServer 啟動 Context 流程
```java=
// /services/java/com/android/server/SystemServer.java
private void run() {
try {
... 省略部分
// Initialize the system context.
createSystemContext();
... 省略部分
} /*省略 catch 部分*/
}
private void createSystemContext() {
// 創建一個 ActivityThread 對象
ActivityThread activityThread = ActivityThread.systemMain();
// 取得 系統 Context
mSystemContext = activityThread.getSystemContext();
// 設定系統主題
mSystemContext.setTheme(DEFAULT_SYSTEM_THEME);
final Context systemUiContext = activityThread.getSystemUiContext();
systemUiContext.setTheme(DEFAULT_SYSTEM_THEME);
}
```
1. 創建 System 級別的 [**ActivityThread**](https://android.googlesource.com/platform/frameworks/base/+/master/core/java/android/app/ActivityThread.java) 對象
```java=
// /core/java/android/app/ActivityThread.java
public static ActivityThread systemMain() {
ThreadedRenderer.initForSystemProcess();
// 創建一個 ActivityThread 對象
ActivityThread thread = new ActivityThread();
// 繼續分析 attach 方法 (注意傳入參數為 true)
thread.attach(true, 0);
return thread;
}
```
2. **ActivityThread `#attach` 函數會創建 Instrumentation 對象**,該對象可以管理 Acitivty
```java=
// ActivityThread.java
@UnsupportedAppUsage
private void attach(boolean system, long startSeq) {
... 省略部分
if (!system) { // 一般 APP
... 省略部分
} else { // 系統
try {
// 創建儀錶板 Instrumentation
mInstrumentation = new Instrumentation();
mInstrumentation.basicInit(this);
// 創 App Context,接著看 createAppContext、getSystemContext 方法
ContextImpl context = ContextImpl.createAppContext(
this, getSystemContext().mPackageInfo);
// 創建 Application 對象
// makeApplication 下個小節分析
mInitialApplication = context.mPackageInfo.makeApplication(true, null);
mInitialApplication.onCreate();
} /* 省略 catch */
}
}
```
3. [**ContextImpl#createAppContext**](https://android.googlesource.com/platform/frameworks/base/+/master/core/java/android/app/ContextImpl.java) 創建 **ContextImpl 對象** (APP 等級)
```java=
// ContextImpl.java
@UnsupportedAppUsage
static ContextImpl createAppContext(ActivityThread mainThread, LoadedApk packageInfo) {
return createAppContext(mainThread, packageInfo, null);
}
static ContextImpl createAppContext(ActivityThread mainThread, LoadedApk packageInfo,
String opPackageName) {
if (packageInfo == null) throw new IllegalArgumentException("packageInfo");
ContextImpl context = new ContextImpl(null, mainThread, packageInfo,
ContextParams.EMPTY, null, null, null, null, null, 0, null, opPackageName);
context.setResources(packageInfo.getResources());
context.mContextType = isSystemOrSystemUI(context) ? CONTEXT_TYPE_SYSTEM_OR_SYSTEM_UI
: CONTEXT_TYPE_NON_UI;
return context;
}
```
4. 取得 ActivityThread 的系統 Context 對象
```java=
// ActivityThread.java
@Override
@UnsupportedAppUsage
public ContextImpl getSystemContext() {
synchronized (this) {
if (mSystemContext == null) {
mSystemContext = ContextImpl.createSystemContext(this);
}
return mSystemContext;
}
}
// 取得 系統 UiContext
@Override
public ContextImpl getSystemUiContext() {
synchronized (this) {
if (mSystemUiContext == null) {
mSystemUiContext = ContextImpl.createSystemUiContext(getSystemContext());
}
return mSystemUiContext;
}
}
```
5. [**ContextImpl#createSystemContext**](https://android.googlesource.com/platform/frameworks/base/+/master/core/java/android/app/ContextImpl.java) 創建系統 **Context (系統等級)**、**LoadedApk** 對象
```java=
// ContextImpl.java
static ContextImpl createSystemContext(ActivityThread mainThread) {
// 創建 LoadedApk,用來加載 APK 文件
LoadedApk packageInfo = new LoadedApk(mainThread);
// 創建 ContextImpl
ContextImpl context = new ContextImpl(null, mainThread, packageInfo, null, null, null, 0,
null);
// 設定 Package Resoureces
context.setResources(packageInfo.getResources());
context.mResources.updateConfiguration(context.mResourcesManager.getConfiguration(),
context.mResourcesManager.getDisplayMetrics());
return context;
}
```
> 
### ServiceManager - Applicatoin 創建
* 複習前面在 `ActivityThread#attach`函數時,會呼叫 ContextImp 中的 LoadedApk 的 **makeApplication 函數**
```java=
// ActivityThread.java
@UnsupportedAppUsage
private void attach(boolean system, long startSeq) {
... 省略部分
if (!system) {
... 省略部分
} else {
try {
// 創建儀錶板 Instrumentation
mInstrumentation = new Instrumentation();
mInstrumentation.basicInit(this);
ContextImpl context = ContextImpl.createAppContext(
this, getSystemContext().mPackageInfo);
// 創建 Application 對象
mInitialApplication = context.mPackageInfo.makeApplication(true, null);
mInitialApplication.onCreate();
} /* 省略 catch */
}
}
```
* LoadedApk 又是透過 Instrumentation 來創建 Application 對象,並複寫 R 檔(ID 資源檔)
```java=
// ContextImpl.java
static ContextImpl createAppContext(ActivityThread mainThread, LoadedApk packageInfo) {
if (packageInfo == null) throw new IllegalArgumentException("packageInfo");
ContextImpl context = new ContextImpl(null, mainThread, packageInfo, null, null, null, 0,
null);
// 設定 Context 資源
context.setResources(packageInfo.getResources());
return context;
}
// ----------------------------------------------------------
// LoadedApk.java
public Application makeApplication(boolean forceDefaultAppClass,
Instrumentation instrumentation) {
// 一個 LoadedApk 對應一個 mApplication
if (mApplication != null) {
return mApplication;
}
Trace.traceBegin(Trace.TRACE_TAG_ACTIVITY_MANAGER, "makeApplication");
Application app = null;
// 若 AndroidManifest.xml 有設定 className 就會使用 User 指定的 Application
// 取得 String Name 就可以透過反射創建
String appClass = mApplicationInfo.className;
if (forceDefaultAppClass || (appClass == null)) {
// 預設使用 android.app.Application
appClass = "android.app.Application";
}
try {
java.lang.ClassLoader cl = getClassLoader();
if (!mPackageName.equals("android")) {
Trace.traceBegin(Trace.TRACE_TAG_ACTIVITY_MANAGER,
"initializeJavaContextClassLoader");
initializeJavaContextClassLoader();
Trace.traceEnd(Trace.TRACE_TAG_ACTIVITY_MANAGER);
}
ContextImpl appContext = ContextImpl.createAppContext(mActivityThread, this);
// 透過 Instrumentation 創建 Application 對象
app = mActivityThread.mInstrumentation.newApplication(
cl, appClass, appContext);
appContext.setOuterContext(app);
} /*省略 catch*/
mActivityThread.mAllApplications.add(app);
mApplication = app;
if (instrumentation != null) {
try {
// 呼叫 Application#onCreate 函數
instrumentation.callApplicationOnCreate(app);
} /*省略 catch*/
}
// Rewrite the R 'constants' for all library apks.
SparseArray<String> packageIdentifiers = getAssets().getAssignedPackageIdentifiers();
final int N = packageIdentifiers.size();
for (int i = 0; i < N; i++) {
final int id = packageIdentifiers.keyAt(i);
if (id == 0x01 || id == 0x7f) {
continue;
}
rewriteRValues(getClassLoader(), packageIdentifiers.valueAt(i), id);
}
Trace.traceEnd(Trace.TRACE_TAG_ACTIVITY_MANAGER);
return app;
}
```
* 最終透過反射創建 Application (取得 AndroidManifest.xml 設定的 name)
> 
```java=
// Instrumentation
public Application newApplication(ClassLoader cl, String className, Context context)
throws InstantiationException, IllegalAccessException,
ClassNotFoundException {
// 接著看 instantiateApplication
Application app = getFactory(context.getPackageName())
.instantiateApplication(cl, className);
app.attach(context);
return app;
}
// AppComponectFactory.java
public @NonNull Application instantiateApplication(@NonNull ClassLoader cl,
@NonNull String className)
throws InstantiationException, IllegalAccessException, ClassNotFoundException {
// 使用反射創建 Application
return (Application) cl.loadClass(className).newInstance();
}
```
> 
### [SystemServiceManager](https://android.googlesource.com/platform/frameworks/base/+/refs/heads/master/services/core/java/com/android/server/SystemServiceManager.java) 建構
* **SystemServiceManager 類是用來管理、啟動系統的服務**,SystemServiceManager 對象建構是在 `SysemServer`#`run` 函數,**在建構完該函數後就會使用它來啟動其他服務**,其中就包括 AMS、WMS、PMS... 等等
```java=
// /android/server/SystemServer.java
public final class SystemServer implements Dumpable {
public static void main(String[] args) {
new SystemServer().run();
}
private void run() {
... 省略部分
try {
t.traceBegin("StartServices");
// 創建 SystemServiceManager 對象
mSystemServiceManager = new SystemServiceManager(mSystemContext);
try {
t.traceBegin("StartServices");
startBootstrapServices(t); // 引導服務
startCoreServices(t); // 核心服務
startOtherServices(t); // 啟動各種類型的 Services
} /* 省略服務 */
... 省略部分
} /*省略 catch*/
... 省略部分
}
}
```
### 抽象 [SystemService](https://android.googlesource.com/platform/frameworks/base/+/refs/heads/master/services/core/java/com/android/server/SystemService.java) 類 - 服務生命週期
* 這邊所提的 SystemService 是個 **抽象類** (請不要跟上一個搞混~ 雖然他們名子一樣),會讓其他系統的啟動類繼承 (eg. AMS#Lifecycle 類),跟系統的 SystemService 不同。
* SystemService 內部有多個參數,可以用來表示 **==服務啟動的過程==,相當於 ++服務啟動的一種生命週期++**,啟動說明請看註解
```java=
// /services/core/java/com/android/server/SystemService.java
public abstract class SystemService {
// 系統在啟動時的最早階段
public static final int PHASE_WAIT_FOR_DEFAULT_DISPLAY = 100;
// 異步啟動,等待 Sensor 服務
public static final int PHASE_WAIT_FOR_SENSOR_SERVICE = 200;
// 可獲取鎖設置數據
public static final int PHASE_LOCK_SETTINGS_READY = 480;
// 系統服務已準備好,可以安心調用核心服務
// eg. PowerManager or PackageManager
public static final int PHASE_SYSTEM_SERVICES_READY = 500;
// 可安心調用特定服務
public static final int PHASE_DEVICE_SPECIFIC_SERVICES_READY = 520;
// 接收到這個啟動階段,服務可以廣播 Intent
public static final int PHASE_ACTIVITY_MANAGER_READY = 550;
// 可以綁定第三方應用
// 應用 APP 能將 Binder 調用到服務中
public static final int PHASE_THIRD_PARTY_APPS_CAN_START = 600;
// 啟動服務完成,可以跟用戶交互
public static final int PHASE_BOOT_COMPLETED = 1000;
private final Context mContext;
public SystemService(@NonNull Context context) {
mContext = context;
}
public abstract void onStart();
... 省略部分函數
}
```
### SystemServiceManager 啟動服務
* 首先先來了解 SystemServiceManager 是如何啟動一個服務的 (**以下舉例 AMS 如何被啟動**)
```java=
// /android/server/SystemServer.java
// 啟動 AMS 的函數
private void startBootstrapServices(@NonNull TimingsTraceAndSlog t) {
... 省略部分
// Activity manager runs the show.
// AMS 啟動,分析 startService 方法
ActivityTaskManagerService atm = mSystemServiceManager.startService(
ActivityTaskManagerService.Lifecycle.class).getService();
mActivityManagerService = ActivityManagerService.Lifecycle.startService(
mSystemServiceManager, atm);
mActivityManagerService.setSystemServiceManager(mSystemServiceManager);
mActivityManagerService.setInstaller(installer);
... 省略部分
mActivityManagerService.setSystemProcess();
... 省略部分
}
```
* Service 啟動流程,是透過 [**SystemServiceManager**](https://android.googlesource.com/platform/frameworks/base/+/master/services/core/java/com/android/server/SystemServiceManager.java)#startService 方法來啟動
1. **啟動 (服務) 類必須繼承抽象的 SystemService 類** (上面說的抽象類)
2. 呼叫 startService 時使用反射創建對象 (有 Context parameter 的建構函數)
:::success
* 呼叫 startService 再建構對象相當於一種延遲加載
:::
3. 呼叫實現類的 **onStart 方法** (繼承抽象 SystemService 類)
```java=
// SystemServiceManager.java
// 快取
private final ArrayList<SystemService> mServices = new ArrayList<SystemService>();
public <T extends SystemService> T startService(Class<T> serviceClass) {
try {
final String name = serviceClass.getName();
...
// Create the service.
// 1. 啟動類必須繼承 SystemService 類
if (!SystemService.class.isAssignableFrom(serviceClass)) {
throw new RuntimeException("Failed to create " + name
+ ": service must extend " + SystemService.class.getName());
}
final T service;
try {
// 2. 啟動有 Context parameter 的建構函數
Constructor<T> constructor = serviceClass.getConstructor(Context.class);
service = constructor.newInstance(mContext);
} /**
* 省略 catch
*/
// 接著分析 startService
startService(service);
return service;
} finally {
Trace.traceEnd(Trace.TRACE_TAG_SYSTEM_SERVER);
}
}
public void startService(@NonNull final SystemService service) {
// Register it.
mServices.add(service);
// Start it.
long time = SystemClock.elapsedRealtime();
try {
// 呼叫實現類的 onStart 方法
// 抽象方法
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");
}
```
* UML 關係圖
> 
## Appendix & FAQ
:::info
:::
###### tags: `Android Framework`