Service啟動(dòng)過(guò)程與Activity類(lèi)似,了解了Activity啟動(dòng)之后來(lái)看Service就容易了,那么還是來(lái)簡(jiǎn)單過(guò)一下流程,先看一張整體流程圖:

應(yīng)用層startService 最終通過(guò)Binder IPC 到AMS:

Context關(guān)系以后再講,這里其實(shí)我們都知道Context是個(gè)抽象類(lèi),真正干活的是ContextImpl. 由它執(zhí)行真正的startService操作:
@Override
public ComponentName startService(Intent service) {
warnIfCallingFromSystemProcess();
return startServiceCommon(service, false, mUser);
}
private ComponentName startServiceCommon(Intent service, boolean requireForeground,
UserHandle user) {
try {
...
ComponentName cn = ActivityManager.getService().startService(
mMainThread.getApplicationThread(), service, service.resolveTypeIfNeeded(
getContentResolver()), requireForeground,
getOpPackageName(), user.getIdentifier());
...
}
這是典型的binder ipc過(guò)程了,話不多說(shuō)。

frameworks/base/services/core/java/com/android/server/am/ActivityManagerService.java
@Override
public ComponentName startService(IApplicationThread caller, Intent service,
String resolvedType, boolean requireForeground, String callingPackage, int userId)
throws TransactionTooLargeException {
...
res = mServices.startServiceLocked(caller, service,
resolvedType, callingPid, callingUid,
requireForeground, callingPackage, userId);
...
return res;
}
}
執(zhí)行startServiceLocked:
frameworks/base/services/core/java/com/android/server/am/ActiveServices.java
ComponentName startServiceLocked(IApplicationThread caller, Intent service, String resolvedType,
int callingPid, int callingUid, String callingPackage, final int userId)
throws TransactionTooLargeException {
...
return startServiceInnerLocked(smap, service, r, callerFg, addToStarting);
}
ComponentName startServiceInnerLocked(ServiceMap smap, Intent service, ServiceRecord r,
boolean callerFg, boolean addToStarting) throws TransactionTooLargeException {
...
String error = bringUpServiceLocked(r, service.getFlags(), callerFg, false, false);
...
return r.name;
}
startServiceLocked 和startServiceInnerLocked 對(duì)應(yīng)于Activity中的startActivityMayWait和startActivity的過(guò)程,無(wú)非也就是一些檢驗(yàn)和初始化的工作。而startServiceInnerLocked方法中又調(diào)用了bringUpServiceLocked方法.
private String bringUpServiceLocked(ServiceRecord r, int intentFlags, boolean execInFg,
boolean whileRestarting, boolean permissionsReviewRequired)
throws TransactionTooLargeException {
...
final String procName = r.processName;
ProcessRecord app;
if (!isolated) {
app = mAm.getProcessRecordLocked(procName, r.appInfo.uid, false);
if (DEBUG_MU) Slog.v(TAG_MU, "bringUpServiceLocked: appInfo.uid=" + r.appInfo.uid
+ " app=" + app);
if (app != null && app.thread != null) {
try {
app.addPackage(r.appInfo.packageName, r.appInfo.versionCode,
mAm.mProcessStats);
realStartServiceLocked(r, app, execInFg);
return null;
}
...
if (app == null && !permissionsReviewRequired) {
if ((app=mAm.startProcessLocked(procName, r.appInfo, true, intentFlags,
"service", r.name, false, isolated, false)) == null) {
...
}
...
}
...
}
該方法可以對(duì)比于Activity啟動(dòng)的startSpecificActivityLocked,也是一個(gè)分叉路,如果進(jìn)程存在則調(diào)用realStartServiceLocked去schedule Service應(yīng)用層的啟動(dòng),如果不存在,則socket通知Zygote去fork進(jìn)程,然后再回來(lái)schedule Service。Zygote去fork進(jìn)程部分與Activity啟動(dòng)部分并無(wú)太大差別,那么直接來(lái)看startSpecificActivityLocked:
private final void realStartServiceLocked(ServiceRecord r,
ProcessRecord app, boolean execInFg) throws RemoteException {
...
try {
...
app.thread.scheduleCreateService(r, r.serviceInfo,
mAm.compatibilityInfoForPackageLocked(r.serviceInfo.applicationInfo),
app.repProcState);
r.postNotification();
created = true;
} catch (DeadObjectException e) {
...
}
...
}
app.thread是IApplicationThread類(lèi)型的,它的實(shí)現(xiàn)是ActivityThread的內(nèi)部類(lèi)ApplicationThread。

frameworks/base/core/java/android/app/ActivityThread.java
public final void scheduleCreateService(IBinder token,
ServiceInfo info, CompatibilityInfo compatInfo, int processState) {
updateProcessState(processState, false);
CreateServiceData s = new CreateServiceData();
s.token = token;
s.info = info;
s.compatInfo = compatInfo;
sendMessage(H.CREATE_SERVICE, s);
}
到了ActivityThread的地界,那就是靠消息驅(qū)動(dòng)運(yùn)轉(zhuǎn)的世界了,由H發(fā)送CREATE_SERVICE的消息,然后在handleMessage對(duì)應(yīng)的case中執(zhí)行的是handleCreateService
private void handleCreateService(CreateServiceData data) {
unscheduleGcIdler();
LoadedApk packageInfo = getPackageInfoNoCheck(
data.info.applicationInfo, data.compatInfo);
Service service = null;
try {
java.lang.ClassLoader cl = packageInfo.getClassLoader();
service = (Service) cl.loadClass(data.info.name).newInstance();
} catch (Exception e) {
...
}
}
try {
if (localLOGV) Slog.v(TAG, "Creating service " + data.info.name);
ContextImpl context = ContextImpl.createAppContext(this, packageInfo);//4
context.setOuterContext(service);
Application app = packageInfo.makeApplication(false, mInstrumentation);
service.attach(context, this, data.info.name, data.token, app,
ActivityManagerNative.getDefault());//5
service.onCreate();//6
mServices.put(data.token, service);//7
...
} catch (Exception e) {
...
}
}
這里主要干兩件事:
將service load到內(nèi)存
通過(guò)Service的attach方法來(lái)初始化Service,然后走Service的onCreate方法,這樣Service就啟動(dòng)了。
好了今天就簡(jiǎn)單地總結(jié)了下Service的啟動(dòng)過(guò)程,下篇接著看看Service的綁定過(guò)程。
參考:
http://gityuan.com/2016/03/06/start-service/
http://liuwangshu.cn/framework/component/2-service-start.html