以下代碼基于Android8.0。
PackageManagerService簡稱為PMS,管理著所有跟package相關(guān)的工作,常見的比如安裝、卸載應(yīng)用。
1、啟動(dòng)入口
PMS屬于系統(tǒng)服務(wù),啟動(dòng)入口在SystemServer中的main方法
public static void main(String[] args) {
new SystemServer().run();
}
private void run() {
...
traceBeginAndSlog("StartServices");
//啟動(dòng)引導(dǎo)服務(wù),PMS的啟動(dòng)包含在此
startBootstrapServices();
//啟動(dòng)核心服務(wù)
startCoreServices();
//啟動(dòng)其他服務(wù)
startOtherServices();
...
}
private void startBootstrapServices() {
...
//啟動(dòng)安裝服務(wù)
traceBeginAndSlog("StartInstaller");
Installer installer = mSystemServiceManager.startService(Installer.class);
traceEnd();
...
//啟動(dòng)PMS
// Start the package manager.
if (!mRuntimeRestart) {
MetricsLogger.histogram(null, "boot_package_manager_init_start",
(int) SystemClock.elapsedRealtime());
}
traceBeginAndSlog("StartPackageManagerService");
mPackageManagerService = PackageManagerService.main(mSystemContext, installer,
mFactoryTestMode != FactoryTest.FACTORY_TEST_OFF, mOnlyCore);
mFirstBoot = mPackageManagerService.isFirstBoot();
mPackageManager = mSystemContext.getPackageManager();
traceEnd();
if (!mRuntimeRestart && !isFirstBootOrUpgrade()) {
MetricsLogger.histogram(null, "boot_package_manager_init_ready",
(int) SystemClock.elapsedRealtime());
}
...
}
概括來講,Android系統(tǒng)啟動(dòng)時(shí),會(huì)創(chuàng)建SystemServer進(jìn)程,進(jìn)程運(yùn)行會(huì)執(zhí)行SystemServer類中的run方法,在run方法中會(huì)啟動(dòng)三類服務(wù),包括引導(dǎo)服務(wù)、核心服務(wù)和其他服務(wù),PMS包含在引導(dǎo)服務(wù)中,在啟動(dòng)引導(dǎo)服務(wù)時(shí)啟動(dòng)PMS。
2、PMS構(gòu)造方法
在PMS啟動(dòng)時(shí),會(huì)調(diào)用PackageManagerService中的main方法,看下main方法做了些啥工作:
public static PackageManagerService main(Context context, Installer installer,
boolean factoryTest, boolean onlyCore) {
// Self-check for initial settings.
PackageManagerServiceCompilerMapping.checkProperties();
PackageManagerService m = new PackageManagerService(context, installer,
factoryTest, onlyCore);
m.enableSystemUserPackages();
ServiceManager.addService("package", m);
return m;
}
可以看出,這里其實(shí)就是初始化了PMS對(duì)象,然后添加到了ServiceManager中,ServerManager即為binder線程池,即PMS注冊到了Binder。接下來看下構(gòu)造方法。
PMS的構(gòu)造方法比較龐大,總體可以分為五個(gè)階段:
BOOT_PROGRESS_PMS_START
- 掃描并解析 ,XML 文件,將其中的信息保存到特定的數(shù)據(jù)結(jié)構(gòu)中。
- 保存installer對(duì)象到mInstaller
- 創(chuàng)建/system的子目錄,比如/system/framework、system/priv-app和/system/app等等
BOOT_PROGRESS_PMS_SYSTEM_SCAN_START
- 掃描系統(tǒng)文件,比如/vendor/overlay、/system/framework、/system/app等等目錄下的文件,對(duì)掃描到的系統(tǒng)文件做后續(xù)處理。
- /system/frameworks:該目錄中的文件都是系統(tǒng)庫,例如:framework.jar、services.jar、framework-res.apk。不過 scanDirLI 只掃描APK文件,所以 framework-res.apk 是該目錄中唯一“受寵”的文件。
該目錄下全是默認(rèn)的系統(tǒng)應(yīng)用,例如:Browser.apk、SettingsProvider.apk 等。
/vendor/app:該目錄中的文件由廠商提供,即廠商特定的 APK 文件,不過目前市面上的廠商都把自己的應(yīng)用放在 /system/app 目錄下。
BOOT_PROGRESS_PMS_DATA_SCAN_START
- 掃描/data/app和/data/app-private目錄下的文件
- 遍歷possiblyDeletedUpdatedSystemApps列表,如果這個(gè)系統(tǒng)App的包信息不在PMS的變量mPackages中,說明是殘留的App信息,后續(xù)會(huì)刪除它的數(shù)據(jù)。說明是存在于Data分區(qū),不屬于系統(tǒng)App,那么移除其系統(tǒng)權(quán)限。
- 遍歷mExpectingBetter列表,根據(jù)系統(tǒng)App所在的目錄設(shè)置掃描的解析參數(shù),內(nèi)部會(huì)將
packageName對(duì)應(yīng)的包設(shè)置數(shù)據(jù)(PackageSetting)添加到mSettings的mPackages中。掃描系統(tǒng)App的升級(jí)包,最后清除mExpectingBetter列表。
BOOT_PROGRESS_PMS_SCAN_END
- 如果當(dāng)前平臺(tái)SDK版本和上次啟動(dòng)時(shí)的SDK版本不同,重新更新APK的授權(quán)
- 如果是第一次啟動(dòng)或者是Android M升級(jí)后的第一次啟動(dòng),需要初始化所有用戶定義的默認(rèn)首選App。
- OTA升級(jí)后的第一次啟動(dòng),會(huì)清除代碼緩存目錄。
- 把Settings的內(nèi)容保存到packages.xml中,這樣此后PMS再次創(chuàng)建時(shí)會(huì)讀到此前保存的Settings的內(nèi)容。
BOOT_PROGRESS_PMS_READY
準(zhǔn)備階段
PMS啟動(dòng)流程圖

PMS啟動(dòng)流程.png
內(nèi)置APP安裝流程圖

內(nèi)置APP安裝流程.png