研究内容:
- サービスを開始するさまざまな方法は何ですか?
- スタートアップキープロセス中のサービスは何?
- 参加者を必要とするサービスは次のように通信処理を開始しますか?
サービスは、原則を開始します
STARTSERVICEサービスを開始します。
@Override
public ComponentName startService(Intent service) {
return startServiceCommon(service, mUser);
}
ComponentName startServiceCommon(Intent service, ...){
ComponentName cn = ActivityManagerNative.getDefault()
.startService(mMainThread.getApplicationThread(), service, ...);
return cn;
}
AMSのプロセス:
ComponentName startService(IApplicationThread caller, Intent service, ...){
ComponentName res = mServices.startServiceLocked(caller, service, ...);
return res;
}
意図クエリサービスレコードオブジェクト:
ターゲットServiceRecoreにAMSサービス、端末対応の各アプリケーション
ComponentName startServiceLocked(Intent service, ...){
ServiceLookupResult res = retrieveServiceLocked(service, ...);
ServiceRecord r = res.record;
...
//查到ServiceRecord之后new了一个StartItem并加到pendingStart里面,
//为后面调用onStartCommand准备
r.pendingStart.add(new ServiceRecord.StartItem(r, ...));
...
return startServiceInnerLocked(smap, service, r, ...);
}
ComponentName startServiceInnerLocked(ServiceMap smap, Intent service, ...){
bringUpServiceLocked(r, service.getFlags(), callerFg, false);
}
final String bringUpServiceLocked(ServiceRecord r, ...){
if(r.app != null && r.app.thread != null) {
//如果Service已经启动了,就调用下面这个函数,
//它将触发应用端的onStartCommand
sendServiceArgsLocked(r, ...);
return null;
}
//Service还没启动的情况:
ProcessRecord app = mAm.getProcessRecordLocked(procName, ...);
if(app != null && app.thread != null){
//如果Service所在的进程已经启动了,真正启动Service
//r.app就是在下面这个函数中设置的
realStartServiceLocked(r, app, execInFg);
return null;
}
//Service所在进程没有启动或者虽然已经启动但还没就绪的情况:
if(app == null){
//app进程还没启动,启动进程
app = mAm.startProcessLocked(procName, ...);
}
if(!mPendingServices.contains(r)){
//把ServiceRecord加到pending列表里面,等待进程启动后再处理
mPendingServices.add(r);
}
...
}
プロセスのフローチャートが開始しました:
- AMSは、ソケットを介してプロセスを開始する要求を開始した受精卵
- 受精卵プロセスは、要求の受信後に開始されます
- バインダーアプリケーションプロセスは、AMSへの呼び出しのattachApplicationを開始し、彼自身のバインダーオブジェクトが(でも準備ができている場合、このアプリケーションのためのAMSのために登録した後)AMSに登録されています
- アプリケーション・プロセスapplicationThreadを通じてサインアップアプリケーション側へbindApplicationコールを開始し、メインアプリケーションの初期化アプリケーション(AMSコンポーネントを保留扱うことができる起こった後に、この手順)
AMS処理機能のattachApplicationの:
boolean attachApplicationLocked(IApplicationThread thread, ...) {
...
mServices.attachApplicationLocked(app, processName);
...
return true;
}
//处理pending的Service
boolean attachApplicationLocked(ProcessRecord proc, ...){
for(int i = 0; i < mPendingServices.size(); i++){
sr = mPendingServices.get(i);
...
mPendingServices.remove(i--);
//对每一个pending的service调用realStartServiceLocked函数真正启动service
realStartServiceLocked(sr, proc, ...);
}
...
}
void realStartServiceLocked(ServiceRecord r, ProcessRecord app, ...){
r.app = app;
...
//向应用端发起IPC调用,应用收到后就会创建Service,执行应用里的onCreate回调
//参数r其实是一个binder对象: final class ServiceRecord extends Binder{}
//这是要存在应用端的,应用端有一个用来保存service对象的map,这里的r就是key
app.thread.scheduleCreateService(r, r.serviceInfo, ...);
...
//触发应用端Service的onStartCommand
sendServiceArgsLocked(r, ...);
}
AMSアプリケーション側で対処する方法はCreateServicd要求で構成されています。
private void handleCreateService(CreateServiceData data){
//先拿到loadedApk
LoadedApk packageInfo = getPackageInfoNoCheck(...);
//加载Service类,并通过newInstance调用其构造函数,从而获得Service对象
Service service = (Service)cl.loadClass(data.info.name).newInstance();
//给这个Service创建一个Context对象
ContextImpl context = ContextImpl.createAppContext(this, ...);
//获取Application,这个application是在应用启动的时候创建的
Application app = packageInfo.makeApplication(flase, ...);
//给service赋予上下文
service.attach(context, this, ...);
//执行Service的生命周期
service.onCreate();
mServices.put(data.token, service);
...
}
mServices是一个map:
ArrayMap<IBinder, Service>
private final void sendServiceArgsLocked(ServiceRecord r, ){
while(r.pendingStarts.size() > 0){
//取出每一个pending的startItem
StartItem si = r.pendingStarts.remove(0);
...
//向应用端发起IPC调用
r.app.thread.scheduleServiceArgs(r, ...);
}
}
AMSは、サービスのアプリケーション側をonStartCommandトリガーされる方法
AMSは、(R、...)r.app.thread.scheduleServiceArgsを呼び出した後に、取引のアプリケーション側:
public final void scheduleServiceArgs(IBinder token, ...) {
//封装了一个ServiceArgsData对象
ServiceArgsData s = new ServiceArgsData();
...
//丢到应用的主线程去处理
sendMessage(H.SERVICE_ARGS, s);
}
//应用端主线程的处理:
private void handleServiceArgs(ServiceArgsData data) {
//首先从mServices中把Service对象取出来。mService是一个map,其中:
//key就是AMS中的ServiceRecord的对象
//value就是应用端的Service对象
//data.token就是AMS中的ServiceRecord对象
Service s = mServices.get(data.token);
if(s != null){
...
//调用Service的onStartCommand
s.onStartCommand(data.args, data.flags, data.startId);
...
}
}
概要サービスの起動プロセス:
AMSの終わり:
- サービスのルックには開始されません:あなたは直接コマンドを送信するために開始する場合は、アプリケーション側で実行onStartCommandので()
- サービスが開始されない場合は、起動しませんでした過程でそれを見るために:あなたはすでに開始している場合は、サービスの開始に行き、そして他のonStartCommandサービスがコマンドを送信するために後の再スタートを実行することを許可
- プロセスが起動しない場合、プロセスが起動するサービスを開始するなど、ブートプロセスに行ってきました
アプリケーション終了:
- サービスオブジェクトを作成します。
- そして、文脈を与えます
- 最後の呼び出しライフサイクルのonCreate()
サービスがbindServiceで始まります
サービス開始は、別の状況があります:bindService時間BIND_AUTO_CREATEマークを持参します
int bindServiceLocked(IApplicationThread caller, ...){
...
if((flags & Context.BIND_AUTO_CREATE) != 0){
//如果带上BIND_AUTO_CREATE标记
bringUpServiceLocked(s, ...);
}
...
}
binderServiceとSTARTSERVICE違い:
- binderService onStartCommand機能は、アプリケーション側をトリガしません。
- 無binderServiceのでキューServiceRecordはmPendingStartを追加しました
サービスの原則について話を開始します。リターン
- サービスを開始するには、いくつかの方法がありますか?
A)STARTSERVICE
BIND_AUTO_CREATE bindServiceとB) - メインサービスの起動プロセスは何?
a)はAMSの終わり:
1)サービスを見ては起動しない:アプリケーション側がonStartCommand行うので、あなたは直接コマンドを送信するために開始した場合は()
サービスが開始されない場合は、プロセスでそれを見るために、)2が起動しませんでした:あなたはすでに、あなたを開始している場合など、サービスの開始後、起動した後、送信コマンドがonStartCommand実行を許可するサービス
プロセスが起動するサービスを開始のようなプロセスは、プロセスを開始するために行くに起動しない場合)、次に3を
B)アプリケーション側:
1)サービスオブジェクトを作成
2)、次いでコンテキストを与える
3)最後に(ライフサイクルのonCreateコール)
- 以下のような参加者、通信プロセスサービスの起動プロセス?
a)は、次の図を参照して: