Android Binderまとめ

5315 ワード

1.MediapplayerServiceの起動、サービスマネージャでの登録方法、詳細は説明しない
ServiceManagerはシステム全体のServices管理者であり、残りのシステム・サービスはdefaultServiceManagerのリモート・インタフェースからServiceManagerを呼び出します.サービスは、サービスマネージャのインタフェースを取得すると、サービスマネージャに自分を追加して起動し、Client側のリクエスト接続を待っています.
SystemManagerがどのように起動され、管理者とBinderになるかについては、次の情報を参照してください.
               http://blog.csdn.net/luoshengyang/article/details/6621566
まずMediaPlayerServiceのUMLを見て、全体的な理解があります.
1)まずMediaPlayerServiceはmain_からmediaservice.cpp mainではインスタンス化されているので、MediaPlayerServiceもsystem_サービスのプロセス中.
int main(int argc, char** argv)
{
    ProcessState> proc(ProcessState::self());
    ... ...
    MediaPlayerService::instantiate();
    ... ...
    ProcessState::self()->startThreadPool();
    IPCThreadState::self()->joinThreadPool();
}

2)MediaPlayerServices::instantiate()では主に2つのことを行いました.1つ目はProcessState::self()によってグローバル変数gProcessを初期化し、ProcessStateのmDriverFDにはBinderデバイスのポインタが保存されます.2つ目の主な仕事は、ServiceManagerを呼び出して自分のnewを呼び出し、ServiceMangerマネージャに追加することです.
sp ProcessState::self()
{
    if (gProcess != NULL) return gProcess;
    
    AutoMutex _l(gProcessMutex);
    if (gProcess == NULL) gProcess = new ProcessState;
    return gProcess;
}
addServiceのプロセスは複雑で、興味のある人は羅さんのこの文章を読むことができます.
          http://blog.csdn.net/luoshengyang/article/details/6629298
void MediaPlayerService::instantiate() {
    defaultServiceManager()->addService(
            String16("media.player"), new MediaPlayerService());
}

3)ServiceManagerに自分を組み込むと、talkWithDriver関数を呼び出してBinderドライバと対話するために常に使用される2つの関数が実行され、実際にはtalkWithDriverを呼び出してClientの要求を待ってからexecuteCommandを呼び出して要求を処理し、executeCommand関数では、最終的にはBBinder::transactを呼び出してClientのリクエストを本当に処理します.
    ProcessState::self()->startThreadPool();
    IPCThreadState::self()->joinThreadPool();

2.MediaPlayerServiceを呼び出し、サービスと通信する方法
MediaPlayerServiceはこの時点ですでにサービスであり、Client側が接続を確立するのを待っています.このClientはMediaPlayerで、frameworks/base/include/media/mediaplayerで宣言して実現します.hとframeworks/base/media/libmedia/media player.cppファイルにあります.MediaPlayerはIMediaDeathNotifierクラスに継承され、frameworks/base/include/media/I MediaDeathNotifierで宣言および実装される.hとframeworks/base/media/libmedia//I MediaDeathNotifier.cppファイルには、IServiceManagement::getServiceインタフェースを介してMediaPlayerServiceのリモートインタフェースを取得する静的メンバー関数getMeidaPlayerServiceがあります.
IMediaDeathNotifier::getMeidaPlayerService関数を紹介する前に、この関数の目標を理解しておきます.実際には、BpMediaPlayerServiceオブジェクトと呼ばれるIMediaPlayerServiceインタフェースを取得することです.
以前のクラス図から分かるように、BpMediaPlayerServiceはBpInterfaceクラス、すなわちBpMediaPlayerServiceがIMediaPlayerServiceクラスとBpRefBaseクラスを継承し、この2つのクラスはそれぞれRefBaseクラスを継続している.BpRefBaseクラスには、IBinderタイプのメンバー変数mRemoteがあり、実際にはBpBinderオブジェクトです.BpBinderクラスは、Binderドライバと対話するためにIPCThreadStateクラスを使用します.一方、IPCThreadStateクラスには、ProcessStateタイプのメンバー変数mProcessがあります.IPCThreadStateクラスは、ProcessStateクラスを使用してBinderデバイスファイル/dev/binderを開くため、Binderドライバと対話できます.
BpMediaPlayerServiceのコンストラクション関数にはconst sp&というパラメータimplがあり、上記の説明から、これは実際にはBpBinderオブジェクトである.これにより、BpMediaPlayerServiceオブジェクトを作成するには、まずBpBinderオブジェクトが必要です.BpBinderクラスの構造関数を見ると、int 32_のパラメータhandleがあります.t,このパラメータの意味はMediaPlayerServiceというリモートインタフェースを要求するプロセスがMediaPlayerServiceというBinderエンティティへの参照である.したがって、MediaPlayerServiceというリモートインタフェースを取得する本質的な問題は、サービスマネージャからMediaPlayerServiceを取得するハンドルになります.
createのプロセスを例に挙げます.
1) MediaPlayer.getMediaPlayerService()
MediaPlayerはIMediaDeathNotifierを継承するので、IMediaDeathNotifierを呼び出す.getMediaPlayerService()は、SystemManagerから「media.player」サービスのIBinder、すなわちBpMediaPlayerServiceを取得し、このIBinderを介してサービス側と通信するBpMediaPlayerService()を主な役割を果たす.
2) service->create(getpid(), this, mAudioSessionId)
このサービスは実際にはBpMediaPlayerServiceなので、BpMediaPlayerServiceのcreateを呼び出し、この関数でremote()->transactを呼び出します.
3) remote()->transact(CREATE, data, &reply)
このremote()はBpBinderを返しますが、実際にはBpBinderです.Transact、このtransact自身は何もしないで、主にIPCThreadState->transactを呼び出してデータ要求の仕事を完成します.
4) IPCThreadState::self()->transact
このtransactでは主にwaitForResponseとtalkWithDriverによってBinderデバイスとのioctl動作を完了する.talkWithDriverが呼び出されると、MediaPlayerServiceのIPCThreadStateはリクエストを傍受し、独自のexecuteCommandを呼び出す.
5) BnMediaPlayerService.onTransact()
EXecuteCommandではcommandのタイプに応じてコールバック関数が呼び出されます.ここではBBinderが呼び出されます.transact,BBinder.Transactは最終的にBnMediaPlayerを呼び出す.onTransactは具体的な処理を行い、createを呼び出してMediaplayerのIbinderのclientを返します. 
3.AMSを例に、Java層のService Binderを見てみましょう.AMSはどのようにClientを手に入れて、Clientはどのようにサービスと通信します
1) Instrumentation.execStartActivity()
ActivityにはStartActivity関数があります.Instrumentationを呼び出します.execStartActivity()は、execStartActivity()はActivity Management Nativeを通過します.getDefault()削除用startActivity
2) ActivityManagerProxy.transact()
A n t i vityManagerNative.getDefault()は、Activity Management Proxyを返します.Activity Management ProxyのstartActivityでmRemoteが呼び出されます.Transact、mRemoteはBinderProxyオブジェクトなので、BinderProxyのtrasact関数を直接呼び出すのと同じです.
3)Binder.exectransact()
BinderProxyのtrasactはJNIによってBinderの要求を完了し、最後にサービス側のBinderのexecTransactionによって関数応答を行う.
4) ActivityManagerService.onTransact
   Biner.execTransactionはActivity Management Servicesを使用します.onTransactは最もコールバック関数で実行され、結果をreplyに配置します.
UML図:
http://sdrv.ms/Q79iGk