1. 程式人生 > >PackageManagerService 原始碼分析 (3) ApplicationInfo 相關

PackageManagerService 原始碼分析 (3) ApplicationInfo 相關

PackageParser.Package.ApplicationInfo  類

Application 是PackageParser.Package 的一個成員
 

一   . 呼叫情況:

1.PackageParser.parseBaseApk() :

   1. 解析指定路徑apk的AndroidManifest.xml檔案,遇到tag為”application”時,會呼叫parseBaseApplication()方法來完成接下來的節點解析工作;

    2 .parseBaseApplication()最後的解析結果都會存放在傳入其函式的引數owner中,它是PackageParser.Package型別。也就是所有ApplicationInfo資訊的來源均是從這個傳出的Package得來;

 

2 . PackageManagerService.scanPackageLI():

  PKMS.scanPackageLI ()

---> PackageParser.parsePackage ()

--->PackageParser.parseBaseApk()

... ...

--->PKSM.scanPackageLI (PackageParser.Package…)

---> PKMS.scanPackageDirtyLI() {

       ...

      mPackages.put(pkg.applicationInfo.packageName, pkg);

      ... }

pkg資訊錄入PKMS.mPackages 中

 

  3 . PackageManagerService.installPackageLI()

  外部呼叫PackageManager的方法installPackage()時,走到PackageManagerService內部會走到的方法,最後還是走到PackageManagerService.scanPackageLI(),這樣新安裝的apk對應的Package也會被新增到PackageManagerService的mPackages中去。

PackageManagerService.installPackageLI()

---> PKMS.installNewPackageLI()

---> PKMS.scanPackageLI(PackageParser.Package…)

 

二 .傳出Application 的方法

所有應用的ApplicationInfo均是存放在PackageManagerService的mPackages成員中,所以要取得某個應用的ApplicationInfo必須通過mPackages.get(packageName);先取到該packageName的Package. 這樣就可以在PackageManagerService中查詢有哪些地方這樣呼叫了。

1.PKMS.getApplicationInfo()

public ApplicationInfo getApplicationInfo(String packageName, int flags, int userId) 
{ 
    synchronized (mPackages) { 
       PackageParser.Package p = mPackages.get(packageName); 
...... 
       return PackageParser.generateApplicationInfo(p, flags, ps.readUserState(userId), userId); 
...... 
       if ("android".equals(packageName) || "system".equals(packageName)) { 
           return mAndroidApplication; 
       } 
    } 
} 

       取mPackages中Key為傳入的包名對應的Value, 然後用PackageParser.generateApplicationInfo()方法來生成ApplicationInfo並返回。

      generateApplicationInfo()方法中主要有一句: ApplicationInfo ai = new ApplicationInfo(p.applicationInfo); 傳給外部的是一份拷貝,而不是直接傳遞給外部p.applicationInfo, 當然也有特殊情況.

2.PKMS.getInstalledApplications(int flags, int userId)

取出mPackages中所有的Package,然後通過PackageParser.generateApplicationInfo()傳出每個Package的applicationInfo成員;

3.PKMS.getPersistentApplications(int flags) 

返回具有常駐屬性的ApplicationInfo,如果p的applicationInfo.flags有ApplicationInfo.FLAG_PERSISTENT屬性,就把它加入到結果列表中,當然對於每一個符合條件的Package, 也是通過PackageParser.generateApplicationInfo()分別傳出其applicationInfo成員

三. new Application