天天看點

Android應用架構之PackageManagerService

系統在啟動的時候會啟動一個叫做<code>packagemanagerservice</code>的服務,顧名思義,這個服務主要管理安裝在裝置上的應用程式,其中最為重要的工作就是在在系統啟動之後,<code>packagemanagerservice</code>會掃描特定目錄下地以apk為字尾的檔案,然後将對應的應用安裝到系統中。注意,這裡的安裝并不是我們平時所說的安裝,它指的的是将存放在磁盤之上的靜态應用程式檔案進行解析,并将相關資訊注冊到系統中。而具體的解析工作實際就是讀取應用的配置檔案<code>manifest.xml</code>,并将檔案中配置的元件

(<code>activity</code>,<code>service</code>,<code>broadcastrecevier</code>,<code>contentprovider</code>),權限等資訊注冊到<code>packagemanagerservice</code>中。

本篇部落客要介紹<code>packagemanagerservice</code>的啟動過程,以及<code>packagemanagerservice</code>如何安裝各個應用程式。

和<code>activitymanagerservice</code>,<code>windowmanagerservice</code>一樣,<code>packagemanagerservice</code>是一個系統級的服務,運作在獨立的程序中,而所有的系統級服務都是由<code>systemserver</code>啟動的。是以首先來看看<code>systemserver</code>的啟動過程。

systemserver元件是由zygote程序負責啟動的,啟動的時候就會調用它的main函數,這個函數主要調用了jni方法init1來做一些系統初始化的工作。

經過一系列調用後轉到<code>system_init</code>方法,這是一個jni方法

在這個方法中,建立了surfaceflinger、sensorservice、audioflinger、mediaplayerservice、cameraservice和audiopolicyservice這幾個服務,然後就通過系統全局唯一的androidruntime執行個體變量runtime的callstatic來調用systemserver的init2函數了。init2函數很簡單,建立一個線程,而<code>packagemanagerservice</code>就是在這個線程中建立的。

在這個線程中建立了<code>packagemanagerservice</code>,并同時啟動了其main函數。另外在這個線程中還啟動了<code>activitymanagerservice</code>等其他service

接下來再來看看<code>packagemanagerservice</code>啟動之後如何進行應用程式的安裝。

1)<code>packagemanagerservice.main</code>

可以看到,建立完成後,就加載到<code>servicemanager</code>中。接下來看看<code>packagemanagerservice</code>的構造函數:

可以看到,在構造函數中,<code>packagemanagerservice</code>(pms)會掃描特定目錄下的apk檔案,然後進行相關的加載工作,這些目錄包括:

/system/framework /system/app /vendor/app /data/app /data/app-private

在每個路徑下,都調用了<code>scandirli</code>函數,接下來看看對應的函數做了些什麼。

<code>scandirli</code>中又經過多次調用,具體就是掃描對應目錄的檔案,如果是apk檔案,就找到apk檔案中的manifest檔案,最後再為每一個apk建立一個<code>packageparser</code>對象,并将manifest檔案傳遞給<code>packageparser.parsepackage</code>。

這裡就是對androidmanifest.xml檔案中的application标簽進行解析了,我們常用到的标簽就有activity、service、receiver和provider,這裡解析完成後,一層層傳回,調用另一個版本的scanpackageli函數把來解析後得到的應用程式資訊儲存下來。

到這裡整個應用的安裝過程就介紹完了。其實整個過程還是很明确,清晰的。

接下來再來總結一下整個啟動過程:

zygote—&gt;啟動systemserver—&gt;啟動serverthread—&gt;啟動packagemanagerservice—&gt;掃描特定目錄下的apk檔案,進行加載—&gt;解析apk的manifest檔案,将配置資訊加載到<code>packagemanagerservice</code>中

繼續閱讀