Androidアプリケーションを起動する方法を理解しようとしています。質問は、Zygoteが新しいDalvik VMをどのように(そしてなぜ)フォークするのですか?同じDalvik VM。
いいえ。Dalvikはプロセスにまたがりません。
ただし、バインダーIPCメカニズムは、オブジェクトを別のプロセスとそのDalvikインスタンスに移行するように見せるための非常に説得力のある仕事を行うことができます。典型的なアプリをホストするDalvikプロセスは、すべての共通Androidライブラリが既にマップされているため、新しい一意のコピーを開く必要はありません。
ソース: 複数のプロセスを使用するアプリはDalvikインスタンスを共有しますか?
次のリンクも確認してください。
http://davidehringer.com/software/Android/The_Dalvik_Virtual_Machine.pdf
Q. zygoteはどのようにDalvik VMを正確にフォークしますか?
短い回答:Zygoteプロセスは、システムの起動時にJava VM他のプロセス(ActivityManagerServiceなど)は、アプリケーションに新しいプロセスが必要になるたびにこのソケットにコマンドを書き込みますこれらのコマンドは、必要に応じてfork()を呼び出すZygoteプロセスによって読み取られます。プロセスは事前に温められたVMを実行します。これがZygoteがDalvik VMをフォークする方法です。
ロングアンサー:カーネルがロードされた後、init.rc
が解析され、ネイティブサービスが開始されます。次に、 /system/bin/app_process
)が実行されます。これは最終的に AndroidRuntime.start()
を呼び出し、パラメータcom.Android.internal.os.ZygoteInit
およびstart-system-server
を渡します。
AndroidRuntime.start()
は、Java VMを開始してから ZygoteInit.main()
を開始し、パラメータstart-system-server
。
ZygoteInit.main()
はZygoteソケットを登録します(Zygoteプロセスは着信コマンドをリッスンし、新しいコマンドを受信すると、要求に応じて新しいプロセスを生成します)。その後、多くのクラス( frameworks/base/preloaded-classes にリストされているように、Android 8.0)の4500以上)とドロアブルなどのシステム全体のリソースをプリロードします。 、xmlsなどその後、 com.Android.server.SystemServer
の新しいプロセスをフォークするstartSystemServer()
を呼び出します。このフォークは特別であり、通常のフォークと同じ方法では実行されません。 Zygoteは、要求プロセスの代わりに実行します。
SystemServerがフォークされた後、runSelectLoopMode()
関数が呼び出されます。これは、ZygoteソケットとZygoteConnection
を確立し、そのコマンドを待機するwhile(true)
ループです。コマンドを受信すると、 ZygoteConnection.runOnce()
が呼び出されます。
ZygoteConnection.runOnce()
は、次に Zygote.forkAndSpecialize()
を呼び出します。これは、ネイティブ関数を呼び出して実際の分岐を行います。したがって、SystemServerの場合と同様に、事前に温められたDalvik VM自体を継承する子プロセスが作成されます。
Q.同じDalvik VMで複数のアプリケーションを実行できないのはなぜですか?
私の知る限り、これは設計上の決定です。 Android男たちは、サンドボックスによるセキュリティのために、プロセスごとに新しいVM.
Zygoteは、システムのドロアブルをすべてのアプリと共有するためにも使用されます。これにより、システムは、たとえばボタンのビットマップを一度だけロードできます。
Zygoteがcopy-on-write techniqueを使用してコマンドを受信するときにフォークを行う場合、上記の回答にもう1点追加するだけです。メモリは、新しいプロセスが変更しようとしたときにのみコピーされます。
また、起動時にzygoteがロードするコアライブラリは読み取り専用であり、変更できません。したがって、これらはコピーではなく共有の新しいフォークプロセスです。
これらはすべてクイックスタートアップおよびメモリフットプリントの削減につながりました。
Zygoteは、Dalvikと実際には結び付いていません。これは、単なる初期化プロセスです。 Zygoteは、アプリを起動するために使用するメソッドAndroidです。新しいプロセスを最初から開始するのではなく、システム全体と毎回Androidフレームワークアプリを起動するには、そのプロセスを1回実行し、Zygoteがアプリ固有の処理を行う前にその時点で停止します。その後、アプリを起動するとき、Zygoteプロセスは分岐し、子プロセスはどこで続行しますアプリ自体をVMに読み込み、中断しました。