Home | History | Annotate | Download | only in pm
      1 /*
      2  * Copyright (C) 2011 The Android Open Source Project
      3  *
      4  * Licensed under the Apache License, Version 2.0 (the "License");
      5  * you may not use this file except in compliance with the License.
      6  * You may obtain a copy of the License at
      7  *
      8  *      http://www.apache.org/licenses/LICENSE-2.0
      9  *
     10  * Unless required by applicable law or agreed to in writing, software
     11  * distributed under the License is distributed on an "AS IS" BASIS,
     12  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
     13  * See the License for the specific language governing permissions and
     14  * limitations under the License.
     15  */
     16 
     17 package com.android.server.pm;
     18 
     19 import static android.Manifest.permission.READ_EXTERNAL_STORAGE;
     20 import static android.content.pm.PackageManager.COMPONENT_ENABLED_STATE_DEFAULT;
     21 import static android.content.pm.PackageManager.COMPONENT_ENABLED_STATE_DISABLED;
     22 import static android.content.pm.PackageManager.COMPONENT_ENABLED_STATE_ENABLED;
     23 import static android.content.pm.PackageManager.FLAG_PERMISSION_REVOKE_ON_UPGRADE;
     24 import static android.content.pm.PackageManager.FLAG_PERMISSION_USER_FIXED;
     25 import static android.content.pm.PackageManager.FLAG_PERMISSION_USER_SET;
     26 import static android.content.pm.PackageManager.INSTALL_FAILED_INSUFFICIENT_STORAGE;
     27 import static android.content.pm.PackageManager.INSTALL_FAILED_SHARED_USER_INCOMPATIBLE;
     28 import static android.content.pm.PackageManager.INTENT_FILTER_DOMAIN_VERIFICATION_STATUS_ALWAYS;
     29 import static android.content.pm.PackageManager.INTENT_FILTER_DOMAIN_VERIFICATION_STATUS_UNDEFINED;
     30 import static android.content.pm.PackageManager.MATCH_DEFAULT_ONLY;
     31 import static android.os.Process.PACKAGE_INFO_GID;
     32 import static android.os.Process.SYSTEM_UID;
     33 
     34 import static com.android.server.pm.PackageManagerService.DEBUG_DOMAIN_VERIFICATION;
     35 
     36 import android.annotation.NonNull;
     37 import android.annotation.Nullable;
     38 import android.content.ComponentName;
     39 import android.content.Intent;
     40 import android.content.IntentFilter;
     41 import android.content.pm.ActivityInfo;
     42 import android.content.pm.ApplicationInfo;
     43 import android.content.pm.ComponentInfo;
     44 import android.content.pm.IntentFilterVerificationInfo;
     45 import android.content.pm.PackageCleanItem;
     46 import android.content.pm.PackageManager;
     47 import android.content.pm.PackageParser;
     48 import android.content.pm.PackageUserState;
     49 import android.content.pm.PermissionInfo;
     50 import android.content.pm.ResolveInfo;
     51 import android.content.pm.Signature;
     52 import android.content.pm.UserInfo;
     53 import android.content.pm.VerifierDeviceIdentity;
     54 import android.net.Uri;
     55 import android.os.Binder;
     56 import android.os.Build;
     57 import android.os.Environment;
     58 import android.os.FileUtils;
     59 import android.os.Handler;
     60 import android.os.Message;
     61 import android.os.PatternMatcher;
     62 import android.os.Process;
     63 import android.os.SystemClock;
     64 import android.os.UserHandle;
     65 import android.os.UserManager;
     66 import android.os.storage.StorageManager;
     67 import android.os.storage.VolumeInfo;
     68 import android.service.pm.PackageServiceDumpProto;
     69 import android.text.TextUtils;
     70 import android.util.ArrayMap;
     71 import android.util.ArraySet;
     72 import android.util.AtomicFile;
     73 import android.util.Log;
     74 import android.util.LogPrinter;
     75 import android.util.Slog;
     76 import android.util.SparseArray;
     77 import android.util.SparseBooleanArray;
     78 import android.util.SparseIntArray;
     79 import android.util.SparseLongArray;
     80 import android.util.Xml;
     81 import android.util.proto.ProtoOutputStream;
     82 
     83 import com.android.internal.annotations.GuardedBy;
     84 import com.android.internal.os.BackgroundThread;
     85 import com.android.internal.util.ArrayUtils;
     86 import com.android.internal.util.FastXmlSerializer;
     87 import com.android.internal.util.IndentingPrintWriter;
     88 import com.android.internal.util.JournaledFile;
     89 import com.android.internal.util.XmlUtils;
     90 import com.android.server.backup.PreferredActivityBackupHelper;
     91 import com.android.server.pm.Installer.InstallerException;
     92 import com.android.server.pm.PackageManagerService.DumpState;
     93 import com.android.server.pm.PermissionsState.PermissionState;
     94 
     95 import libcore.io.IoUtils;
     96 
     97 import org.xmlpull.v1.XmlPullParser;
     98 import org.xmlpull.v1.XmlPullParserException;
     99 import org.xmlpull.v1.XmlSerializer;
    100 
    101 import java.io.BufferedInputStream;
    102 import java.io.BufferedOutputStream;
    103 import java.io.BufferedWriter;
    104 import java.io.File;
    105 import java.io.FileInputStream;
    106 import java.io.FileNotFoundException;
    107 import java.io.FileOutputStream;
    108 import java.io.IOException;
    109 import java.io.InputStream;
    110 import java.io.OutputStreamWriter;
    111 import java.io.PrintWriter;
    112 import java.nio.charset.Charset;
    113 import java.nio.charset.StandardCharsets;
    114 import java.text.SimpleDateFormat;
    115 import java.util.ArrayList;
    116 import java.util.Arrays;
    117 import java.util.Collection;
    118 import java.util.Collections;
    119 import java.util.Date;
    120 import java.util.Iterator;
    121 import java.util.List;
    122 import java.util.Map;
    123 import java.util.Map.Entry;
    124 import java.util.Objects;
    125 import java.util.Set;
    126 
    127 /**
    128  * Holds information about dynamic settings.
    129  */
    130 final class Settings {
    131     private static final String TAG = "PackageSettings";
    132 
    133     /**
    134      * Current version of the package database. Set it to the latest version in
    135      * the {@link DatabaseVersion} class below to ensure the database upgrade
    136      * doesn't happen repeatedly.
    137      * <p>
    138      * Note that care should be taken to make sure all database upgrades are
    139      * idempotent.
    140      */
    141     public static final int CURRENT_DATABASE_VERSION = DatabaseVersion.SIGNATURE_MALFORMED_RECOVER;
    142 
    143     /**
    144      * This class contains constants that can be referred to from upgrade code.
    145      * Insert constant values here that describe the upgrade reason. The version
    146      * code must be monotonically increasing.
    147      */
    148     public static class DatabaseVersion {
    149         /**
    150          * The initial version of the database.
    151          */
    152         public static final int FIRST_VERSION = 1;
    153 
    154         /**
    155          * Migrating the Signature array from the entire certificate chain to
    156          * just the signing certificate.
    157          */
    158         public static final int SIGNATURE_END_ENTITY = 2;
    159 
    160         /**
    161          * There was a window of time in
    162          * {@link android.os.Build.VERSION_CODES#LOLLIPOP} where we persisted
    163          * certificates after potentially mutating them. To switch back to the
    164          * original untouched certificates, we need to force a collection pass.
    165          */
    166         public static final int SIGNATURE_MALFORMED_RECOVER = 3;
    167     }
    168 
    169     private static final boolean DEBUG_STOPPED = false;
    170     private static final boolean DEBUG_MU = false;
    171     private static final boolean DEBUG_KERNEL = false;
    172     private static final boolean DEBUG_PARSER = false;
    173 
    174     private static final String RUNTIME_PERMISSIONS_FILE_NAME = "runtime-permissions.xml";
    175 
    176     private static final String TAG_READ_EXTERNAL_STORAGE = "read-external-storage";
    177     private static final String ATTR_ENFORCEMENT = "enforcement";
    178 
    179     private static final String TAG_ITEM = "item";
    180     private static final String TAG_DISABLED_COMPONENTS = "disabled-components";
    181     private static final String TAG_ENABLED_COMPONENTS = "enabled-components";
    182     private static final String TAG_PACKAGE_RESTRICTIONS = "package-restrictions";
    183     private static final String TAG_PACKAGE = "pkg";
    184     private static final String TAG_SHARED_USER = "shared-user";
    185     private static final String TAG_RUNTIME_PERMISSIONS = "runtime-permissions";
    186     private static final String TAG_PERMISSIONS = "perms";
    187     private static final String TAG_CHILD_PACKAGE = "child-package";
    188     private static final String TAG_USES_STATIC_LIB = "uses-static-lib";
    189     private static final String TAG_BLOCK_UNINSTALL_PACKAGES = "block-uninstall-packages";
    190     private static final String TAG_BLOCK_UNINSTALL = "block-uninstall";
    191 
    192     private static final String TAG_PERSISTENT_PREFERRED_ACTIVITIES =
    193             "persistent-preferred-activities";
    194     static final String TAG_CROSS_PROFILE_INTENT_FILTERS =
    195             "crossProfile-intent-filters";
    196     private static final String TAG_DOMAIN_VERIFICATION = "domain-verification";
    197     private static final String TAG_DEFAULT_APPS = "default-apps";
    198     private static final String TAG_ALL_INTENT_FILTER_VERIFICATION =
    199             "all-intent-filter-verifications";
    200     private static final String TAG_DEFAULT_BROWSER = "default-browser";
    201     private static final String TAG_DEFAULT_DIALER = "default-dialer";
    202     private static final String TAG_VERSION = "version";
    203 
    204     private static final String ATTR_NAME = "name";
    205     private static final String ATTR_USER = "user";
    206     private static final String ATTR_CODE = "code";
    207     private static final String ATTR_GRANTED = "granted";
    208     private static final String ATTR_FLAGS = "flags";
    209     private static final String ATTR_VERSION = "version";
    210 
    211     private static final String ATTR_CE_DATA_INODE = "ceDataInode";
    212     private static final String ATTR_INSTALLED = "inst";
    213     private static final String ATTR_STOPPED = "stopped";
    214     private static final String ATTR_NOT_LAUNCHED = "nl";
    215     // Legacy, here for reading older versions of the package-restrictions.
    216     private static final String ATTR_BLOCKED = "blocked";
    217     // New name for the above attribute.
    218     private static final String ATTR_HIDDEN = "hidden";
    219     private static final String ATTR_SUSPENDED = "suspended";
    220     // Legacy, uninstall blocks are stored separately.
    221     @Deprecated
    222     private static final String ATTR_BLOCK_UNINSTALL = "blockUninstall";
    223     private static final String ATTR_ENABLED = "enabled";
    224     private static final String ATTR_ENABLED_CALLER = "enabledCaller";
    225     private static final String ATTR_DOMAIN_VERIFICATON_STATE = "domainVerificationStatus";
    226     private static final String ATTR_APP_LINK_GENERATION = "app-link-generation";
    227     private static final String ATTR_INSTALL_REASON = "install-reason";
    228     private static final String ATTR_INSTANT_APP = "instant-app";
    229     private static final String ATTR_VIRTUAL_PRELOAD = "virtual-preload";
    230 
    231     private static final String ATTR_PACKAGE_NAME = "packageName";
    232     private static final String ATTR_FINGERPRINT = "fingerprint";
    233     private static final String ATTR_VOLUME_UUID = "volumeUuid";
    234     private static final String ATTR_SDK_VERSION = "sdkVersion";
    235     private static final String ATTR_DATABASE_VERSION = "databaseVersion";
    236     private static final String ATTR_DONE = "done";
    237 
    238     // Bookkeeping for restored permission grants
    239     private static final String TAG_RESTORED_RUNTIME_PERMISSIONS = "restored-perms";
    240     // package name: ATTR_PACKAGE_NAME
    241     private static final String TAG_PERMISSION_ENTRY = "perm";
    242     // permission name: ATTR_NAME
    243     // permission granted (boolean): ATTR_GRANTED
    244     private static final String ATTR_USER_SET = "set";
    245     private static final String ATTR_USER_FIXED = "fixed";
    246     private static final String ATTR_REVOKE_ON_UPGRADE = "rou";
    247 
    248     // Flag mask of restored permission grants that are applied at install time
    249     private static final int USER_RUNTIME_GRANT_MASK =
    250             FLAG_PERMISSION_USER_SET
    251             | FLAG_PERMISSION_USER_FIXED
    252             | FLAG_PERMISSION_REVOKE_ON_UPGRADE;
    253 
    254     private final Object mLock;
    255 
    256     private final RuntimePermissionPersistence mRuntimePermissionsPersistence;
    257 
    258     private final File mSettingsFilename;
    259     private final File mBackupSettingsFilename;
    260     private final File mPackageListFilename;
    261     private final File mStoppedPackagesFilename;
    262     private final File mBackupStoppedPackagesFilename;
    263     /** The top level directory in configfs for sdcardfs to push the package->uid,userId mappings */
    264     private final File mKernelMappingFilename;
    265 
    266     /** Map from package name to settings */
    267     final ArrayMap<String, PackageSetting> mPackages = new ArrayMap<>();
    268 
    269     /** List of packages that installed other packages */
    270     final ArraySet<String> mInstallerPackages = new ArraySet<>();
    271 
    272     /** Map from package name to appId and excluded userids */
    273     private final ArrayMap<String, KernelPackageState> mKernelMapping = new ArrayMap<>();
    274 
    275     // List of replaced system applications
    276     private final ArrayMap<String, PackageSetting> mDisabledSysPackages =
    277         new ArrayMap<String, PackageSetting>();
    278 
    279     /** List of packages that are blocked for uninstall for specific users */
    280     private final SparseArray<ArraySet<String>> mBlockUninstallPackages = new SparseArray<>();
    281 
    282     // Set of restored intent-filter verification states
    283     private final ArrayMap<String, IntentFilterVerificationInfo> mRestoredIntentFilterVerifications =
    284             new ArrayMap<String, IntentFilterVerificationInfo>();
    285 
    286     private static final class KernelPackageState {
    287         int appId;
    288         int[] excludedUserIds;
    289     }
    290 
    291     // Bookkeeping for restored user permission grants
    292     final class RestoredPermissionGrant {
    293         String permissionName;
    294         boolean granted;
    295         int grantBits;
    296 
    297         RestoredPermissionGrant(String name, boolean isGranted, int theGrantBits) {
    298             permissionName = name;
    299             granted = isGranted;
    300             grantBits = theGrantBits;
    301         }
    302     }
    303 
    304     // This would be more compact as a flat array of restored grants or something, but we
    305     // may have quite a few, especially during early device lifetime, and avoiding all those
    306     // linear lookups will be important.
    307     private final SparseArray<ArrayMap<String, ArraySet<RestoredPermissionGrant>>>
    308             mRestoredUserGrants =
    309                 new SparseArray<ArrayMap<String, ArraySet<RestoredPermissionGrant>>>();
    310 
    311     private static int mFirstAvailableUid = 0;
    312 
    313     /** Map from volume UUID to {@link VersionInfo} */
    314     private ArrayMap<String, VersionInfo> mVersion = new ArrayMap<>();
    315 
    316     /**
    317      * Version details for a storage volume that may hold apps.
    318      */
    319     public static class VersionInfo {
    320         /**
    321          * These are the last platform API version we were using for the apps
    322          * installed on internal and external storage. It is used to grant newer
    323          * permissions one time during a system upgrade.
    324          */
    325         int sdkVersion;
    326 
    327         /**
    328          * The current database version for apps on internal storage. This is
    329          * used to upgrade the format of the packages.xml database not
    330          * necessarily tied to an SDK version.
    331          */
    332         int databaseVersion;
    333 
    334         /**
    335          * Last known value of {@link Build#FINGERPRINT}. Used to determine when
    336          * an system update has occurred, meaning we need to clear code caches.
    337          */
    338         String fingerprint;
    339 
    340         /**
    341          * Force all version information to match current system values,
    342          * typically after resolving any required upgrade steps.
    343          */
    344         public void forceCurrent() {
    345             sdkVersion = Build.VERSION.SDK_INT;
    346             databaseVersion = CURRENT_DATABASE_VERSION;
    347             fingerprint = Build.FINGERPRINT;
    348         }
    349     }
    350 
    351     Boolean mReadExternalStorageEnforced;
    352 
    353     /** Device identity for the purpose of package verification. */
    354     private VerifierDeviceIdentity mVerifierDeviceIdentity;
    355 
    356     // The user's preferred activities associated with particular intent
    357     // filters.
    358     final SparseArray<PreferredIntentResolver> mPreferredActivities =
    359             new SparseArray<PreferredIntentResolver>();
    360 
    361     // The persistent preferred activities of the user's profile/device owner
    362     // associated with particular intent filters.
    363     final SparseArray<PersistentPreferredIntentResolver> mPersistentPreferredActivities =
    364             new SparseArray<PersistentPreferredIntentResolver>();
    365 
    366     // For every user, it is used to find to which other users the intent can be forwarded.
    367     final SparseArray<CrossProfileIntentResolver> mCrossProfileIntentResolvers =
    368             new SparseArray<CrossProfileIntentResolver>();
    369 
    370     final ArrayMap<String, SharedUserSetting> mSharedUsers =
    371             new ArrayMap<String, SharedUserSetting>();
    372     private final ArrayList<Object> mUserIds = new ArrayList<Object>();
    373     private final SparseArray<Object> mOtherUserIds =
    374             new SparseArray<Object>();
    375 
    376     // For reading/writing settings file.
    377     private final ArrayList<Signature> mPastSignatures =
    378             new ArrayList<Signature>();
    379     private final ArrayMap<Long, Integer> mKeySetRefs =
    380             new ArrayMap<Long, Integer>();
    381 
    382     // Mapping from permission names to info about them.
    383     final ArrayMap<String, BasePermission> mPermissions =
    384             new ArrayMap<String, BasePermission>();
    385 
    386     // Mapping from permission tree names to info about them.
    387     final ArrayMap<String, BasePermission> mPermissionTrees =
    388             new ArrayMap<String, BasePermission>();
    389 
    390     // Packages that have been uninstalled and still need their external
    391     // storage data deleted.
    392     final ArrayList<PackageCleanItem> mPackagesToBeCleaned = new ArrayList<PackageCleanItem>();
    393 
    394     // Packages that have been renamed since they were first installed.
    395     // Keys are the new names of the packages, values are the original
    396     // names.  The packages appear everywhere else under their original
    397     // names.
    398     private final ArrayMap<String, String> mRenamedPackages = new ArrayMap<String, String>();
    399 
    400     // For every user, it is used to find the package name of the default Browser App.
    401     final SparseArray<String> mDefaultBrowserApp = new SparseArray<String>();
    402 
    403     // For every user, a record of the package name of the default Dialer App.
    404     final SparseArray<String> mDefaultDialerApp = new SparseArray<String>();
    405 
    406     // App-link priority tracking, per-user
    407     final SparseIntArray mNextAppLinkGeneration = new SparseIntArray();
    408 
    409     final StringBuilder mReadMessages = new StringBuilder();
    410 
    411     /**
    412      * Used to track packages that have a shared user ID that hasn't been read
    413      * in yet.
    414      * <p>
    415      * TODO: make this just a local variable that is passed in during package
    416      * scanning to make it less confusing.
    417      */
    418     private final ArrayList<PackageSetting> mPendingPackages = new ArrayList<>();
    419 
    420     private final File mSystemDir;
    421 
    422     public final KeySetManagerService mKeySetManagerService = new KeySetManagerService(mPackages);
    423 
    424     Settings(Object lock) {
    425         this(Environment.getDataDirectory(), lock);
    426     }
    427 
    428     Settings(File dataDir, Object lock) {
    429         mLock = lock;
    430 
    431         mRuntimePermissionsPersistence = new RuntimePermissionPersistence(mLock);
    432 
    433         mSystemDir = new File(dataDir, "system");
    434         mSystemDir.mkdirs();
    435         FileUtils.setPermissions(mSystemDir.toString(),
    436                 FileUtils.S_IRWXU|FileUtils.S_IRWXG
    437                 |FileUtils.S_IROTH|FileUtils.S_IXOTH,
    438                 -1, -1);
    439         mSettingsFilename = new File(mSystemDir, "packages.xml");
    440         mBackupSettingsFilename = new File(mSystemDir, "packages-backup.xml");
    441         mPackageListFilename = new File(mSystemDir, "packages.list");
    442         FileUtils.setPermissions(mPackageListFilename, 0640, SYSTEM_UID, PACKAGE_INFO_GID);
    443 
    444         final File kernelDir = new File("/config/sdcardfs");
    445         mKernelMappingFilename = kernelDir.exists() ? kernelDir : null;
    446 
    447         // Deprecated: Needed for migration
    448         mStoppedPackagesFilename = new File(mSystemDir, "packages-stopped.xml");
    449         mBackupStoppedPackagesFilename = new File(mSystemDir, "packages-stopped-backup.xml");
    450     }
    451 
    452     PackageSetting getPackageLPr(String pkgName) {
    453         return mPackages.get(pkgName);
    454     }
    455 
    456     String getRenamedPackageLPr(String pkgName) {
    457         return mRenamedPackages.get(pkgName);
    458     }
    459 
    460     String addRenamedPackageLPw(String pkgName, String origPkgName) {
    461         return mRenamedPackages.put(pkgName, origPkgName);
    462     }
    463 
    464     void setInstallStatus(String pkgName, final int status) {
    465         PackageSetting p = mPackages.get(pkgName);
    466         if(p != null) {
    467             if(p.getInstallStatus() != status) {
    468                 p.setInstallStatus(status);
    469             }
    470         }
    471     }
    472 
    473     void applyPendingPermissionGrantsLPw(String packageName, int userId) {
    474         ArrayMap<String, ArraySet<RestoredPermissionGrant>> grantsByPackage =
    475                 mRestoredUserGrants.get(userId);
    476         if (grantsByPackage == null || grantsByPackage.size() == 0) {
    477             return;
    478         }
    479 
    480         ArraySet<RestoredPermissionGrant> grants = grantsByPackage.get(packageName);
    481         if (grants == null || grants.size() == 0) {
    482             return;
    483         }
    484 
    485         final PackageSetting ps = mPackages.get(packageName);
    486         if (ps == null) {
    487             Slog.e(TAG, "Can't find supposedly installed package " + packageName);
    488             return;
    489         }
    490         final PermissionsState perms = ps.getPermissionsState();
    491 
    492         for (RestoredPermissionGrant grant : grants) {
    493             BasePermission bp = mPermissions.get(grant.permissionName);
    494             if (bp != null) {
    495                 if (grant.granted) {
    496                     perms.grantRuntimePermission(bp, userId);
    497                 }
    498                 perms.updatePermissionFlags(bp, userId, USER_RUNTIME_GRANT_MASK, grant.grantBits);
    499             }
    500         }
    501 
    502         // And remove it from the pending-grant bookkeeping
    503         grantsByPackage.remove(packageName);
    504         if (grantsByPackage.size() < 1) {
    505             mRestoredUserGrants.remove(userId);
    506         }
    507         writeRuntimePermissionsForUserLPr(userId, false);
    508     }
    509 
    510     void setInstallerPackageName(String pkgName, String installerPkgName) {
    511         PackageSetting p = mPackages.get(pkgName);
    512         if (p != null) {
    513             p.setInstallerPackageName(installerPkgName);
    514             if (installerPkgName != null) {
    515                 mInstallerPackages.add(installerPkgName);
    516             }
    517         }
    518     }
    519 
    520     /** Gets and optionally creates a new shared user id. */
    521     SharedUserSetting getSharedUserLPw(String name, int pkgFlags, int pkgPrivateFlags,
    522             boolean create) throws PackageManagerException {
    523         SharedUserSetting s = mSharedUsers.get(name);
    524         if (s == null && create) {
    525             s = new SharedUserSetting(name, pkgFlags, pkgPrivateFlags);
    526             s.userId = newUserIdLPw(s);
    527             if (s.userId < 0) {
    528                 // < 0 means we couldn't assign a userid; throw exception
    529                 throw new PackageManagerException(INSTALL_FAILED_INSUFFICIENT_STORAGE,
    530                         "Creating shared user " + name + " failed");
    531             }
    532             Log.i(PackageManagerService.TAG, "New shared user " + name + ": id=" + s.userId);
    533             mSharedUsers.put(name, s);
    534         }
    535         return s;
    536     }
    537 
    538     Collection<SharedUserSetting> getAllSharedUsersLPw() {
    539         return mSharedUsers.values();
    540     }
    541 
    542     boolean disableSystemPackageLPw(String name, boolean replaced) {
    543         final PackageSetting p = mPackages.get(name);
    544         if(p == null) {
    545             Log.w(PackageManagerService.TAG, "Package " + name + " is not an installed package");
    546             return false;
    547         }
    548         final PackageSetting dp = mDisabledSysPackages.get(name);
    549         // always make sure the system package code and resource paths dont change
    550         if (dp == null && p.pkg != null && p.pkg.isSystemApp() && !p.pkg.isUpdatedSystemApp()) {
    551             if((p.pkg != null) && (p.pkg.applicationInfo != null)) {
    552                 p.pkg.applicationInfo.flags |= ApplicationInfo.FLAG_UPDATED_SYSTEM_APP;
    553             }
    554             mDisabledSysPackages.put(name, p);
    555 
    556             if (replaced) {
    557                 // a little trick...  when we install the new package, we don't
    558                 // want to modify the existing PackageSetting for the built-in
    559                 // version.  so at this point we need a new PackageSetting that
    560                 // is okay to muck with.
    561                 PackageSetting newp = new PackageSetting(p);
    562                 replacePackageLPw(name, newp);
    563             }
    564             return true;
    565         }
    566         return false;
    567     }
    568 
    569     PackageSetting enableSystemPackageLPw(String name) {
    570         PackageSetting p = mDisabledSysPackages.get(name);
    571         if(p == null) {
    572             Log.w(PackageManagerService.TAG, "Package " + name + " is not disabled");
    573             return null;
    574         }
    575         // Reset flag in ApplicationInfo object
    576         if((p.pkg != null) && (p.pkg.applicationInfo != null)) {
    577             p.pkg.applicationInfo.flags &= ~ApplicationInfo.FLAG_UPDATED_SYSTEM_APP;
    578         }
    579         PackageSetting ret = addPackageLPw(name, p.realName, p.codePath, p.resourcePath,
    580                 p.legacyNativeLibraryPathString, p.primaryCpuAbiString,
    581                 p.secondaryCpuAbiString, p.cpuAbiOverrideString,
    582                 p.appId, p.versionCode, p.pkgFlags, p.pkgPrivateFlags,
    583                 p.parentPackageName, p.childPackageNames, p.usesStaticLibraries,
    584                 p.usesStaticLibrariesVersions);
    585         mDisabledSysPackages.remove(name);
    586         return ret;
    587     }
    588 
    589     boolean isDisabledSystemPackageLPr(String name) {
    590         return mDisabledSysPackages.containsKey(name);
    591     }
    592 
    593     void removeDisabledSystemPackageLPw(String name) {
    594         mDisabledSysPackages.remove(name);
    595     }
    596 
    597     PackageSetting addPackageLPw(String name, String realName, File codePath, File resourcePath,
    598             String legacyNativeLibraryPathString, String primaryCpuAbiString,
    599             String secondaryCpuAbiString, String cpuAbiOverrideString, int uid, int vc, int
    600             pkgFlags, int pkgPrivateFlags, String parentPackageName,
    601             List<String> childPackageNames, String[] usesStaticLibraries,
    602             int[] usesStaticLibraryNames) {
    603         PackageSetting p = mPackages.get(name);
    604         if (p != null) {
    605             if (p.appId == uid) {
    606                 return p;
    607             }
    608             PackageManagerService.reportSettingsProblem(Log.ERROR,
    609                     "Adding duplicate package, keeping first: " + name);
    610             return null;
    611         }
    612         p = new PackageSetting(name, realName, codePath, resourcePath,
    613                 legacyNativeLibraryPathString, primaryCpuAbiString, secondaryCpuAbiString,
    614                 cpuAbiOverrideString, vc, pkgFlags, pkgPrivateFlags, parentPackageName,
    615                 childPackageNames, 0 /*userId*/, usesStaticLibraries, usesStaticLibraryNames);
    616         p.appId = uid;
    617         if (addUserIdLPw(uid, p, name)) {
    618             mPackages.put(name, p);
    619             return p;
    620         }
    621         return null;
    622     }
    623 
    624     SharedUserSetting addSharedUserLPw(String name, int uid, int pkgFlags, int pkgPrivateFlags) {
    625         SharedUserSetting s = mSharedUsers.get(name);
    626         if (s != null) {
    627             if (s.userId == uid) {
    628                 return s;
    629             }
    630             PackageManagerService.reportSettingsProblem(Log.ERROR,
    631                     "Adding duplicate shared user, keeping first: " + name);
    632             return null;
    633         }
    634         s = new SharedUserSetting(name, pkgFlags, pkgPrivateFlags);
    635         s.userId = uid;
    636         if (addUserIdLPw(uid, s, name)) {
    637             mSharedUsers.put(name, s);
    638             return s;
    639         }
    640         return null;
    641     }
    642 
    643     void pruneSharedUsersLPw() {
    644         ArrayList<String> removeStage = new ArrayList<String>();
    645         for (Map.Entry<String,SharedUserSetting> entry : mSharedUsers.entrySet()) {
    646             final SharedUserSetting sus = entry.getValue();
    647             if (sus == null) {
    648                 removeStage.add(entry.getKey());
    649                 continue;
    650             }
    651             // remove packages that are no longer installed
    652             for (Iterator<PackageSetting> iter = sus.packages.iterator(); iter.hasNext();) {
    653                 PackageSetting ps = iter.next();
    654                 if (mPackages.get(ps.name) == null) {
    655                     iter.remove();
    656                 }
    657             }
    658             if (sus.packages.size() == 0) {
    659                 removeStage.add(entry.getKey());
    660             }
    661         }
    662         for (int i = 0; i < removeStage.size(); i++) {
    663             mSharedUsers.remove(removeStage.get(i));
    664         }
    665     }
    666 
    667     // Transfer ownership of permissions from one package to another.
    668     void transferPermissionsLPw(String origPkg, String newPkg) {
    669         // Transfer ownership of permissions to the new package.
    670         for (int i=0; i<2; i++) {
    671             ArrayMap<String, BasePermission> permissions =
    672                     i == 0 ? mPermissionTrees : mPermissions;
    673             for (BasePermission bp : permissions.values()) {
    674                 if (origPkg.equals(bp.sourcePackage)) {
    675                     if (PackageManagerService.DEBUG_UPGRADE) Log.v(PackageManagerService.TAG,
    676                             "Moving permission " + bp.name
    677                             + " from pkg " + bp.sourcePackage
    678                             + " to " + newPkg);
    679                     bp.sourcePackage = newPkg;
    680                     bp.packageSetting = null;
    681                     bp.perm = null;
    682                     if (bp.pendingInfo != null) {
    683                         bp.pendingInfo.packageName = newPkg;
    684                     }
    685                     bp.uid = 0;
    686                     bp.setGids(null, false);
    687                 }
    688             }
    689         }
    690     }
    691 
    692     /**
    693      * Creates a new {@code PackageSetting} object.
    694      * Use this method instead of the constructor to ensure a settings object is created
    695      * with the correct base.
    696      */
    697     static @NonNull PackageSetting createNewSetting(String pkgName, PackageSetting originalPkg,
    698             PackageSetting disabledPkg, String realPkgName, SharedUserSetting sharedUser,
    699             File codePath, File resourcePath, String legacyNativeLibraryPath, String primaryCpuAbi,
    700             String secondaryCpuAbi, int versionCode, int pkgFlags, int pkgPrivateFlags,
    701             UserHandle installUser, boolean allowInstall, boolean instantApp,
    702             boolean virtualPreload, String parentPkgName, List<String> childPkgNames,
    703             UserManagerService userManager,
    704             String[] usesStaticLibraries, int[] usesStaticLibrariesVersions) {
    705         final PackageSetting pkgSetting;
    706         if (originalPkg != null) {
    707             if (PackageManagerService.DEBUG_UPGRADE) Log.v(PackageManagerService.TAG, "Package "
    708                     + pkgName + " is adopting original package " + originalPkg.name);
    709             pkgSetting = new PackageSetting(originalPkg, pkgName /*realPkgName*/);
    710             pkgSetting.childPackageNames =
    711                     (childPkgNames != null) ? new ArrayList<>(childPkgNames) : null;
    712             pkgSetting.codePath = codePath;
    713             pkgSetting.legacyNativeLibraryPathString = legacyNativeLibraryPath;
    714             pkgSetting.origPackage = originalPkg;
    715             pkgSetting.parentPackageName = parentPkgName;
    716             pkgSetting.pkgFlags = pkgFlags;
    717             pkgSetting.pkgPrivateFlags = pkgPrivateFlags;
    718             pkgSetting.primaryCpuAbiString = primaryCpuAbi;
    719             pkgSetting.resourcePath = resourcePath;
    720             pkgSetting.secondaryCpuAbiString = secondaryCpuAbi;
    721             // NOTE: Create a deeper copy of the package signatures so we don't
    722             // overwrite the signatures in the original package setting.
    723             pkgSetting.signatures = new PackageSignatures();
    724             pkgSetting.versionCode = versionCode;
    725             pkgSetting.usesStaticLibraries = usesStaticLibraries;
    726             pkgSetting.usesStaticLibrariesVersions = usesStaticLibrariesVersions;
    727             // Update new package state.
    728             pkgSetting.setTimeStamp(codePath.lastModified());
    729         } else {
    730             pkgSetting = new PackageSetting(pkgName, realPkgName, codePath, resourcePath,
    731                     legacyNativeLibraryPath, primaryCpuAbi, secondaryCpuAbi,
    732                     null /*cpuAbiOverrideString*/, versionCode, pkgFlags, pkgPrivateFlags,
    733                     parentPkgName, childPkgNames, 0 /*sharedUserId*/, usesStaticLibraries,
    734                     usesStaticLibrariesVersions);
    735             pkgSetting.setTimeStamp(codePath.lastModified());
    736             pkgSetting.sharedUser = sharedUser;
    737             // If this is not a system app, it starts out stopped.
    738             if ((pkgFlags&ApplicationInfo.FLAG_SYSTEM) == 0) {
    739                 if (DEBUG_STOPPED) {
    740                     RuntimeException e = new RuntimeException("here");
    741                     e.fillInStackTrace();
    742                     Slog.i(PackageManagerService.TAG, "Stopping package " + pkgName, e);
    743                 }
    744                 List<UserInfo> users = getAllUsers(userManager);
    745                 final int installUserId = installUser != null ? installUser.getIdentifier() : 0;
    746                 if (users != null && allowInstall) {
    747                     for (UserInfo user : users) {
    748                         // By default we consider this app to be installed
    749                         // for the user if no user has been specified (which
    750                         // means to leave it at its original value, and the
    751                         // original default value is true), or we are being
    752                         // asked to install for all users, or this is the
    753                         // user we are installing for.
    754                         final boolean installed = installUser == null
    755                                 || (installUserId == UserHandle.USER_ALL
    756                                     && !isAdbInstallDisallowed(userManager, user.id))
    757                                 || installUserId == user.id;
    758                         pkgSetting.setUserState(user.id, 0, COMPONENT_ENABLED_STATE_DEFAULT,
    759                                 installed,
    760                                 true /*stopped*/,
    761                                 true /*notLaunched*/,
    762                                 false /*hidden*/,
    763                                 false /*suspended*/,
    764                                 instantApp,
    765                                 virtualPreload,
    766                                 null /*lastDisableAppCaller*/,
    767                                 null /*enabledComponents*/,
    768                                 null /*disabledComponents*/,
    769                                 INTENT_FILTER_DOMAIN_VERIFICATION_STATUS_UNDEFINED,
    770                                 0, PackageManager.INSTALL_REASON_UNKNOWN);
    771                     }
    772                 }
    773             }
    774             if (sharedUser != null) {
    775                 pkgSetting.appId = sharedUser.userId;
    776             } else {
    777                 // Clone the setting here for disabled system packages
    778                 if (disabledPkg != null) {
    779                     // For disabled packages a new setting is created
    780                     // from the existing user id. This still has to be
    781                     // added to list of user id's
    782                     // Copy signatures from previous setting
    783                     pkgSetting.signatures = new PackageSignatures(disabledPkg.signatures);
    784                     pkgSetting.appId = disabledPkg.appId;
    785                     // Clone permissions
    786                     pkgSetting.getPermissionsState().copyFrom(disabledPkg.getPermissionsState());
    787                     // Clone component info
    788                     List<UserInfo> users = getAllUsers(userManager);
    789                     if (users != null) {
    790                         for (UserInfo user : users) {
    791                             final int userId = user.id;
    792                             pkgSetting.setDisabledComponentsCopy(
    793                                     disabledPkg.getDisabledComponents(userId), userId);
    794                             pkgSetting.setEnabledComponentsCopy(
    795                                     disabledPkg.getEnabledComponents(userId), userId);
    796                         }
    797                     }
    798                 }
    799             }
    800         }
    801         return pkgSetting;
    802     }
    803 
    804     /**
    805      * Updates the given package setting using the provided information.
    806      * <p>
    807      * WARNING: The provided PackageSetting object may be mutated.
    808      */
    809     static void updatePackageSetting(@NonNull PackageSetting pkgSetting,
    810             @Nullable PackageSetting disabledPkg, @Nullable SharedUserSetting sharedUser,
    811             @NonNull File codePath, @Nullable String legacyNativeLibraryPath,
    812             @Nullable String primaryCpuAbi, @Nullable String secondaryCpuAbi,
    813             int pkgFlags, int pkgPrivateFlags, @Nullable List<String> childPkgNames,
    814             @NonNull UserManagerService userManager, @Nullable String[] usesStaticLibraries,
    815             @Nullable int[] usesStaticLibrariesVersions) throws PackageManagerException {
    816         final String pkgName = pkgSetting.name;
    817         if (pkgSetting.sharedUser != sharedUser) {
    818             PackageManagerService.reportSettingsProblem(Log.WARN,
    819                     "Package " + pkgName + " shared user changed from "
    820                     + (pkgSetting.sharedUser != null ? pkgSetting.sharedUser.name : "<nothing>")
    821                     + " to " + (sharedUser != null ? sharedUser.name : "<nothing>"));
    822             throw new PackageManagerException(INSTALL_FAILED_SHARED_USER_INCOMPATIBLE,
    823                     "Updating application package " + pkgName + " failed");
    824         }
    825 
    826         if (!pkgSetting.codePath.equals(codePath)) {
    827             // Check to see if its a disabled system app
    828             if ((pkgSetting.pkgFlags & ApplicationInfo.FLAG_SYSTEM) != 0) {
    829                 // This is an updated system app with versions in both system
    830                 // and data partition. Just let the most recent version
    831                 // take precedence.
    832                 Slog.w(PackageManagerService.TAG,
    833                         "Trying to update system app code path from "
    834                         + pkgSetting.codePathString + " to " + codePath.toString());
    835             } else {
    836                 // Just a change in the code path is not an issue, but
    837                 // let's log a message about it.
    838                 Slog.i(PackageManagerService.TAG,
    839                         "Package " + pkgName + " codePath changed from "
    840                         + pkgSetting.codePath + " to " + codePath
    841                         + "; Retaining data and using new");
    842 
    843                 // The owner user's installed flag is set false
    844                 // when the application was installed by other user
    845                 // and the installed flag is not updated
    846                 // when the application is appended as system app later.
    847                 if ((pkgFlags & ApplicationInfo.FLAG_SYSTEM) != 0
    848                         && disabledPkg == null) {
    849                     List<UserInfo> allUserInfos = getAllUsers(userManager);
    850                     if (allUserInfos != null) {
    851                         for (UserInfo userInfo : allUserInfos) {
    852                             pkgSetting.setInstalled(true, userInfo.id);
    853                         }
    854                     }
    855                 }
    856 
    857                 /*
    858                  * Since we've changed paths, we need to prefer the new
    859                  * native library path over the one stored in the
    860                  * package settings since we might have moved from
    861                  * internal to external storage or vice versa.
    862                  */
    863                 pkgSetting.legacyNativeLibraryPathString = legacyNativeLibraryPath;
    864             }
    865         }
    866         // If what we are scanning is a system (and possibly privileged) package,
    867         // then make it so, regardless of whether it was previously installed only
    868         // in the data partition.
    869         pkgSetting.pkgFlags |= pkgFlags & ApplicationInfo.FLAG_SYSTEM;
    870         pkgSetting.pkgPrivateFlags |=
    871                 pkgPrivateFlags & ApplicationInfo.PRIVATE_FLAG_PRIVILEGED;
    872         pkgSetting.primaryCpuAbiString = primaryCpuAbi;
    873         pkgSetting.secondaryCpuAbiString = secondaryCpuAbi;
    874         if (childPkgNames != null) {
    875             pkgSetting.childPackageNames = new ArrayList<>(childPkgNames);
    876         }
    877         if (usesStaticLibraries != null) {
    878             pkgSetting.usesStaticLibraries = Arrays.copyOf(usesStaticLibraries,
    879                     usesStaticLibraries.length);
    880         }
    881         if (usesStaticLibrariesVersions != null) {
    882             pkgSetting.usesStaticLibrariesVersions = Arrays.copyOf(usesStaticLibrariesVersions,
    883                     usesStaticLibrariesVersions.length);
    884         }
    885     }
    886 
    887     /**
    888      * Registers a user ID with the system. Potentially allocates a new user ID.
    889      * @throws PackageManagerException If a user ID could not be allocated.
    890      */
    891     void addUserToSettingLPw(PackageSetting p) throws PackageManagerException {
    892         if (p.appId == 0) {
    893             // Assign new user ID
    894             p.appId = newUserIdLPw(p);
    895         } else {
    896             // Add new setting to list of user IDs
    897             addUserIdLPw(p.appId, p, p.name);
    898         }
    899         if (p.appId < 0) {
    900             PackageManagerService.reportSettingsProblem(Log.WARN,
    901                     "Package " + p.name + " could not be assigned a valid UID");
    902             throw new PackageManagerException(INSTALL_FAILED_INSUFFICIENT_STORAGE,
    903                     "Package " + p.name + " could not be assigned a valid UID");
    904         }
    905     }
    906 
    907     /**
    908      * Writes per-user package restrictions if the user state has changed. If the user
    909      * state has not changed, this does nothing.
    910      */
    911     void writeUserRestrictionsLPw(PackageSetting newPackage, PackageSetting oldPackage) {
    912         // package doesn't exist; do nothing
    913         if (getPackageLPr(newPackage.name) == null) {
    914             return;
    915         }
    916         // no users defined; do nothing
    917         final List<UserInfo> allUsers = getAllUsers(UserManagerService.getInstance());
    918         if (allUsers == null) {
    919             return;
    920         }
    921         for (UserInfo user : allUsers) {
    922             final PackageUserState oldUserState = oldPackage == null
    923                     ? PackageSettingBase.DEFAULT_USER_STATE
    924                     : oldPackage.readUserState(user.id);
    925             if (!oldUserState.equals(newPackage.readUserState(user.id))) {
    926                 writePackageRestrictionsLPr(user.id);
    927             }
    928         }
    929     }
    930 
    931     static boolean isAdbInstallDisallowed(UserManagerService userManager, int userId) {
    932         return userManager.hasUserRestriction(UserManager.DISALLOW_DEBUGGING_FEATURES,
    933                 userId);
    934     }
    935 
    936     void insertPackageSettingLPw(PackageSetting p, PackageParser.Package pkg) {
    937         p.pkg = pkg;
    938         // pkg.mSetEnabled = p.getEnabled(userId);
    939         // pkg.mSetStopped = p.getStopped(userId);
    940         final String volumeUuid = pkg.applicationInfo.volumeUuid;
    941         final String codePath = pkg.applicationInfo.getCodePath();
    942         final String resourcePath = pkg.applicationInfo.getResourcePath();
    943         final String legacyNativeLibraryPath = pkg.applicationInfo.nativeLibraryRootDir;
    944         // Update volume if needed
    945         if (!Objects.equals(volumeUuid, p.volumeUuid)) {
    946             Slog.w(PackageManagerService.TAG, "Volume for " + p.pkg.packageName +
    947                     " changing from " + p.volumeUuid + " to " + volumeUuid);
    948             p.volumeUuid = volumeUuid;
    949         }
    950         // Update code path if needed
    951         if (!Objects.equals(codePath, p.codePathString)) {
    952             Slog.w(PackageManagerService.TAG, "Code path for " + p.pkg.packageName +
    953                     " changing from " + p.codePathString + " to " + codePath);
    954             p.codePath = new File(codePath);
    955             p.codePathString = codePath;
    956         }
    957         //Update resource path if needed
    958         if (!Objects.equals(resourcePath, p.resourcePathString)) {
    959             Slog.w(PackageManagerService.TAG, "Resource path for " + p.pkg.packageName +
    960                     " changing from " + p.resourcePathString + " to " + resourcePath);
    961             p.resourcePath = new File(resourcePath);
    962             p.resourcePathString = resourcePath;
    963         }
    964         // Update the native library paths if needed
    965         if (!Objects.equals(legacyNativeLibraryPath, p.legacyNativeLibraryPathString)) {
    966             p.legacyNativeLibraryPathString = legacyNativeLibraryPath;
    967         }
    968 
    969         // Update the required Cpu Abi
    970         p.primaryCpuAbiString = pkg.applicationInfo.primaryCpuAbi;
    971         p.secondaryCpuAbiString = pkg.applicationInfo.secondaryCpuAbi;
    972         p.cpuAbiOverrideString = pkg.cpuAbiOverride;
    973         // Update version code if needed
    974         if (pkg.mVersionCode != p.versionCode) {
    975             p.versionCode = pkg.mVersionCode;
    976         }
    977         // Update signatures if needed.
    978         if (p.signatures.mSignatures == null) {
    979             p.signatures.assignSignatures(pkg.mSignatures);
    980         }
    981         // Update flags if needed.
    982         if (pkg.applicationInfo.flags != p.pkgFlags) {
    983             p.pkgFlags = pkg.applicationInfo.flags;
    984         }
    985         // If this app defines a shared user id initialize
    986         // the shared user signatures as well.
    987         if (p.sharedUser != null && p.sharedUser.signatures.mSignatures == null) {
    988             p.sharedUser.signatures.assignSignatures(pkg.mSignatures);
    989         }
    990         // Update static shared library dependencies if needed
    991         if (pkg.usesStaticLibraries != null && pkg.usesStaticLibrariesVersions != null
    992                 && pkg.usesStaticLibraries.size() == pkg.usesStaticLibrariesVersions.length) {
    993             p.usesStaticLibraries = new String[pkg.usesStaticLibraries.size()];
    994             pkg.usesStaticLibraries.toArray(p.usesStaticLibraries);
    995             p.usesStaticLibrariesVersions = pkg.usesStaticLibrariesVersions;
    996         } else {
    997             p.usesStaticLibraries = null;
    998             p.usesStaticLibrariesVersions = null;
    999         }
   1000         addPackageSettingLPw(p, p.sharedUser);
   1001     }
   1002 
   1003     // Utility method that adds a PackageSetting to mPackages and
   1004     // completes updating the shared user attributes and any restored
   1005     // app link verification state
   1006     private void addPackageSettingLPw(PackageSetting p, SharedUserSetting sharedUser) {
   1007         mPackages.put(p.name, p);
   1008         if (sharedUser != null) {
   1009             if (p.sharedUser != null && p.sharedUser != sharedUser) {
   1010                 PackageManagerService.reportSettingsProblem(Log.ERROR,
   1011                         "Package " + p.name + " was user "
   1012                         + p.sharedUser + " but is now " + sharedUser
   1013                         + "; I am not changing its files so it will probably fail!");
   1014                 p.sharedUser.removePackage(p);
   1015             } else if (p.appId != sharedUser.userId) {
   1016                 PackageManagerService.reportSettingsProblem(Log.ERROR,
   1017                     "Package " + p.name + " was user id " + p.appId
   1018                     + " but is now user " + sharedUser
   1019                     + " with id " + sharedUser.userId
   1020                     + "; I am not changing its files so it will probably fail!");
   1021             }
   1022 
   1023             sharedUser.addPackage(p);
   1024             p.sharedUser = sharedUser;
   1025             p.appId = sharedUser.userId;
   1026         }
   1027 
   1028         // If the we know about this user id, we have to update it as it
   1029         // has to point to the same PackageSetting instance as the package.
   1030         Object userIdPs = getUserIdLPr(p.appId);
   1031         if (sharedUser == null) {
   1032             if (userIdPs != null && userIdPs != p) {
   1033                 replaceUserIdLPw(p.appId, p);
   1034             }
   1035         } else {
   1036             if (userIdPs != null && userIdPs != sharedUser) {
   1037                 replaceUserIdLPw(p.appId, sharedUser);
   1038             }
   1039         }
   1040 
   1041         IntentFilterVerificationInfo ivi = mRestoredIntentFilterVerifications.get(p.name);
   1042         if (ivi != null) {
   1043             if (DEBUG_DOMAIN_VERIFICATION) {
   1044                 Slog.i(TAG, "Applying restored IVI for " + p.name + " : " + ivi.getStatusString());
   1045             }
   1046             mRestoredIntentFilterVerifications.remove(p.name);
   1047             p.setIntentFilterVerificationInfo(ivi);
   1048         }
   1049     }
   1050 
   1051     /*
   1052      * Update the shared user setting when a package using
   1053      * specifying the shared user id is removed. The gids
   1054      * associated with each permission of the deleted package
   1055      * are removed from the shared user's gid list only if its
   1056      * not in use by other permissions of packages in the
   1057      * shared user setting.
   1058      */
   1059     int updateSharedUserPermsLPw(PackageSetting deletedPs, int userId) {
   1060         if ((deletedPs == null) || (deletedPs.pkg == null)) {
   1061             Slog.i(PackageManagerService.TAG,
   1062                     "Trying to update info for null package. Just ignoring");
   1063             return UserHandle.USER_NULL;
   1064         }
   1065 
   1066         // No sharedUserId
   1067         if (deletedPs.sharedUser == null) {
   1068             return UserHandle.USER_NULL;
   1069         }
   1070 
   1071         SharedUserSetting sus = deletedPs.sharedUser;
   1072 
   1073         // Update permissions
   1074         for (String eachPerm : deletedPs.pkg.requestedPermissions) {
   1075             BasePermission bp = mPermissions.get(eachPerm);
   1076             if (bp == null) {
   1077                 continue;
   1078             }
   1079 
   1080             // Check if another package in the shared user needs the permission.
   1081             boolean used = false;
   1082             for (PackageSetting pkg : sus.packages) {
   1083                 if (pkg.pkg != null
   1084                         && !pkg.pkg.packageName.equals(deletedPs.pkg.packageName)
   1085                         && pkg.pkg.requestedPermissions.contains(eachPerm)) {
   1086                     used = true;
   1087                     break;
   1088                 }
   1089             }
   1090             if (used) {
   1091                 continue;
   1092             }
   1093 
   1094             PermissionsState permissionsState = sus.getPermissionsState();
   1095             PackageSetting disabledPs = getDisabledSystemPkgLPr(deletedPs.pkg.packageName);
   1096 
   1097             // If the package is shadowing is a disabled system package,
   1098             // do not drop permissions that the shadowed package requests.
   1099             if (disabledPs != null) {
   1100                 boolean reqByDisabledSysPkg = false;
   1101                 for (String permission : disabledPs.pkg.requestedPermissions) {
   1102                     if (permission.equals(eachPerm)) {
   1103                         reqByDisabledSysPkg = true;
   1104                         break;
   1105                     }
   1106                 }
   1107                 if (reqByDisabledSysPkg) {
   1108                     continue;
   1109                 }
   1110             }
   1111 
   1112             // Try to revoke as an install permission which is for all users.
   1113             // The package is gone - no need to keep flags for applying policy.
   1114             permissionsState.updatePermissionFlags(bp, userId,
   1115                     PackageManager.MASK_PERMISSION_FLAGS, 0);
   1116 
   1117             if (permissionsState.revokeInstallPermission(bp) ==
   1118                     PermissionsState.PERMISSION_OPERATION_SUCCESS_GIDS_CHANGED) {
   1119                 return UserHandle.USER_ALL;
   1120             }
   1121 
   1122             // Try to revoke as an install permission which is per user.
   1123             if (permissionsState.revokeRuntimePermission(bp, userId) ==
   1124                     PermissionsState.PERMISSION_OPERATION_SUCCESS_GIDS_CHANGED) {
   1125                 return userId;
   1126             }
   1127         }
   1128 
   1129         return UserHandle.USER_NULL;
   1130     }
   1131 
   1132     int removePackageLPw(String name) {
   1133         final PackageSetting p = mPackages.get(name);
   1134         if (p != null) {
   1135             mPackages.remove(name);
   1136             removeInstallerPackageStatus(name);
   1137             if (p.sharedUser != null) {
   1138                 p.sharedUser.removePackage(p);
   1139                 if (p.sharedUser.packages.size() == 0) {
   1140                     mSharedUsers.remove(p.sharedUser.name);
   1141                     removeUserIdLPw(p.sharedUser.userId);
   1142                     return p.sharedUser.userId;
   1143                 }
   1144             } else {
   1145                 removeUserIdLPw(p.appId);
   1146                 return p.appId;
   1147             }
   1148         }
   1149         return -1;
   1150     }
   1151 
   1152     /**
   1153      * Checks if {@param packageName} is an installer package and if so, clear the installer
   1154      * package name of the packages that are installed by this.
   1155      */
   1156     private void removeInstallerPackageStatus(String packageName) {
   1157         // Check if the package to be removed is an installer package.
   1158         if (!mInstallerPackages.contains(packageName)) {
   1159             return;
   1160         }
   1161         for (int i = 0; i < mPackages.size(); i++) {
   1162             final PackageSetting ps = mPackages.valueAt(i);
   1163             final String installerPackageName = ps.getInstallerPackageName();
   1164             if (installerPackageName != null
   1165                     && installerPackageName.equals(packageName)) {
   1166                 ps.setInstallerPackageName(null);
   1167                 ps.isOrphaned = true;
   1168             }
   1169         }
   1170         mInstallerPackages.remove(packageName);
   1171     }
   1172 
   1173     private void replacePackageLPw(String name, PackageSetting newp) {
   1174         final PackageSetting p = mPackages.get(name);
   1175         if (p != null) {
   1176             if (p.sharedUser != null) {
   1177                 p.sharedUser.removePackage(p);
   1178                 p.sharedUser.addPackage(newp);
   1179             } else {
   1180                 replaceUserIdLPw(p.appId, newp);
   1181             }
   1182         }
   1183         mPackages.put(name, newp);
   1184     }
   1185 
   1186     private boolean addUserIdLPw(int uid, Object obj, Object name) {
   1187         if (uid > Process.LAST_APPLICATION_UID) {
   1188             return false;
   1189         }
   1190 
   1191         if (uid >= Process.FIRST_APPLICATION_UID) {
   1192             int N = mUserIds.size();
   1193             final int index = uid - Process.FIRST_APPLICATION_UID;
   1194             while (index >= N) {
   1195                 mUserIds.add(null);
   1196                 N++;
   1197             }
   1198             if (mUserIds.get(index) != null) {
   1199                 PackageManagerService.reportSettingsProblem(Log.ERROR,
   1200                         "Adding duplicate user id: " + uid
   1201                         + " name=" + name);
   1202                 return false;
   1203             }
   1204             mUserIds.set(index, obj);
   1205         } else {
   1206             if (mOtherUserIds.get(uid) != null) {
   1207                 PackageManagerService.reportSettingsProblem(Log.ERROR,
   1208                         "Adding duplicate shared id: " + uid
   1209                                 + " name=" + name);
   1210                 return false;
   1211             }
   1212             mOtherUserIds.put(uid, obj);
   1213         }
   1214         return true;
   1215     }
   1216 
   1217     public Object getUserIdLPr(int uid) {
   1218         if (uid >= Process.FIRST_APPLICATION_UID) {
   1219             final int N = mUserIds.size();
   1220             final int index = uid - Process.FIRST_APPLICATION_UID;
   1221             return index < N ? mUserIds.get(index) : null;
   1222         } else {
   1223             return mOtherUserIds.get(uid);
   1224         }
   1225     }
   1226 
   1227     private void removeUserIdLPw(int uid) {
   1228         if (uid >= Process.FIRST_APPLICATION_UID) {
   1229             final int N = mUserIds.size();
   1230             final int index = uid - Process.FIRST_APPLICATION_UID;
   1231             if (index < N) mUserIds.set(index, null);
   1232         } else {
   1233             mOtherUserIds.remove(uid);
   1234         }
   1235         setFirstAvailableUid(uid+1);
   1236     }
   1237 
   1238     private void replaceUserIdLPw(int uid, Object obj) {
   1239         if (uid >= Process.FIRST_APPLICATION_UID) {
   1240             final int N = mUserIds.size();
   1241             final int index = uid - Process.FIRST_APPLICATION_UID;
   1242             if (index < N) mUserIds.set(index, obj);
   1243         } else {
   1244             mOtherUserIds.put(uid, obj);
   1245         }
   1246     }
   1247 
   1248     PreferredIntentResolver editPreferredActivitiesLPw(int userId) {
   1249         PreferredIntentResolver pir = mPreferredActivities.get(userId);
   1250         if (pir == null) {
   1251             pir = new PreferredIntentResolver();
   1252             mPreferredActivities.put(userId, pir);
   1253         }
   1254         return pir;
   1255     }
   1256 
   1257     PersistentPreferredIntentResolver editPersistentPreferredActivitiesLPw(int userId) {
   1258         PersistentPreferredIntentResolver ppir = mPersistentPreferredActivities.get(userId);
   1259         if (ppir == null) {
   1260             ppir = new PersistentPreferredIntentResolver();
   1261             mPersistentPreferredActivities.put(userId, ppir);
   1262         }
   1263         return ppir;
   1264     }
   1265 
   1266     CrossProfileIntentResolver editCrossProfileIntentResolverLPw(int userId) {
   1267         CrossProfileIntentResolver cpir = mCrossProfileIntentResolvers.get(userId);
   1268         if (cpir == null) {
   1269             cpir = new CrossProfileIntentResolver();
   1270             mCrossProfileIntentResolvers.put(userId, cpir);
   1271         }
   1272         return cpir;
   1273     }
   1274 
   1275     /**
   1276      * The following functions suppose that you have a lock for managing access to the
   1277      * mIntentFiltersVerifications map.
   1278      */
   1279 
   1280     /* package protected */
   1281     IntentFilterVerificationInfo getIntentFilterVerificationLPr(String packageName) {
   1282         PackageSetting ps = mPackages.get(packageName);
   1283         if (ps == null) {
   1284             if (DEBUG_DOMAIN_VERIFICATION) {
   1285                 Slog.w(PackageManagerService.TAG, "No package known: " + packageName);
   1286             }
   1287             return null;
   1288         }
   1289         return ps.getIntentFilterVerificationInfo();
   1290     }
   1291 
   1292     /* package protected */
   1293     IntentFilterVerificationInfo createIntentFilterVerificationIfNeededLPw(String packageName,
   1294             ArraySet<String> domains) {
   1295         PackageSetting ps = mPackages.get(packageName);
   1296         if (ps == null) {
   1297             if (DEBUG_DOMAIN_VERIFICATION) {
   1298                 Slog.w(PackageManagerService.TAG, "No package known: " + packageName);
   1299             }
   1300             return null;
   1301         }
   1302         IntentFilterVerificationInfo ivi = ps.getIntentFilterVerificationInfo();
   1303         if (ivi == null) {
   1304             ivi = new IntentFilterVerificationInfo(packageName, domains);
   1305             ps.setIntentFilterVerificationInfo(ivi);
   1306             if (DEBUG_DOMAIN_VERIFICATION) {
   1307                 Slog.d(PackageManagerService.TAG,
   1308                         "Creating new IntentFilterVerificationInfo for pkg: " + packageName);
   1309             }
   1310         } else {
   1311             ivi.setDomains(domains);
   1312             if (DEBUG_DOMAIN_VERIFICATION) {
   1313                 Slog.d(PackageManagerService.TAG,
   1314                         "Setting domains to existing IntentFilterVerificationInfo for pkg: " +
   1315                                 packageName + " and with domains: " + ivi.getDomainsString());
   1316             }
   1317         }
   1318         return ivi;
   1319     }
   1320 
   1321     int getIntentFilterVerificationStatusLPr(String packageName, int userId) {
   1322         PackageSetting ps = mPackages.get(packageName);
   1323         if (ps == null) {
   1324             if (DEBUG_DOMAIN_VERIFICATION) {
   1325                 Slog.w(PackageManagerService.TAG, "No package known: " + packageName);
   1326             }
   1327             return INTENT_FILTER_DOMAIN_VERIFICATION_STATUS_UNDEFINED;
   1328         }
   1329         return (int)(ps.getDomainVerificationStatusForUser(userId) >> 32);
   1330     }
   1331 
   1332     boolean updateIntentFilterVerificationStatusLPw(String packageName, final int status, int userId) {
   1333         // Update the status for the current package
   1334         PackageSetting current = mPackages.get(packageName);
   1335         if (current == null) {
   1336             if (DEBUG_DOMAIN_VERIFICATION) {
   1337                 Slog.w(PackageManagerService.TAG, "No package known: " + packageName);
   1338             }
   1339             return false;
   1340         }
   1341 
   1342         final int alwaysGeneration;
   1343         if (status == INTENT_FILTER_DOMAIN_VERIFICATION_STATUS_ALWAYS) {
   1344             alwaysGeneration = mNextAppLinkGeneration.get(userId) + 1;
   1345             mNextAppLinkGeneration.put(userId, alwaysGeneration);
   1346         } else {
   1347             alwaysGeneration = 0;
   1348         }
   1349 
   1350         current.setDomainVerificationStatusForUser(status, alwaysGeneration, userId);
   1351         return true;
   1352     }
   1353 
   1354     /**
   1355      * Used for Settings App and PackageManagerService dump. Should be read only.
   1356      */
   1357     List<IntentFilterVerificationInfo> getIntentFilterVerificationsLPr(
   1358             String packageName) {
   1359         if (packageName == null) {
   1360             return Collections.<IntentFilterVerificationInfo>emptyList();
   1361         }
   1362         ArrayList<IntentFilterVerificationInfo> result = new ArrayList<>();
   1363         for (PackageSetting ps : mPackages.values()) {
   1364             IntentFilterVerificationInfo ivi = ps.getIntentFilterVerificationInfo();
   1365             if (ivi == null || TextUtils.isEmpty(ivi.getPackageName()) ||
   1366                     !ivi.getPackageName().equalsIgnoreCase(packageName)) {
   1367                 continue;
   1368             }
   1369             result.add(ivi);
   1370         }
   1371         return result;
   1372     }
   1373 
   1374     boolean removeIntentFilterVerificationLPw(String packageName, int userId) {
   1375         PackageSetting ps = mPackages.get(packageName);
   1376         if (ps == null) {
   1377             if (DEBUG_DOMAIN_VERIFICATION) {
   1378                 Slog.w(PackageManagerService.TAG, "No package known: " + packageName);
   1379             }
   1380             return false;
   1381         }
   1382         ps.clearDomainVerificationStatusForUser(userId);
   1383         return true;
   1384     }
   1385 
   1386     boolean removeIntentFilterVerificationLPw(String packageName, int[] userIds) {
   1387         boolean result = false;
   1388         for (int userId : userIds) {
   1389             result |= removeIntentFilterVerificationLPw(packageName, userId);
   1390         }
   1391         return result;
   1392     }
   1393 
   1394     boolean setDefaultBrowserPackageNameLPw(String packageName, int userId) {
   1395         if (userId == UserHandle.USER_ALL) {
   1396             return false;
   1397         }
   1398         if (packageName != null) {
   1399             mDefaultBrowserApp.put(userId, packageName);
   1400         } else {
   1401             mDefaultBrowserApp.remove(userId);
   1402         }
   1403         writePackageRestrictionsLPr(userId);
   1404         return true;
   1405     }
   1406 
   1407     String getDefaultBrowserPackageNameLPw(int userId) {
   1408         return (userId == UserHandle.USER_ALL) ? null : mDefaultBrowserApp.get(userId);
   1409     }
   1410 
   1411     boolean setDefaultDialerPackageNameLPw(String packageName, int userId) {
   1412         if (userId == UserHandle.USER_ALL) {
   1413             return false;
   1414         }
   1415         mDefaultDialerApp.put(userId, packageName);
   1416         writePackageRestrictionsLPr(userId);
   1417         return true;
   1418     }
   1419 
   1420     String getDefaultDialerPackageNameLPw(int userId) {
   1421         return (userId == UserHandle.USER_ALL) ? null : mDefaultDialerApp.get(userId);
   1422     }
   1423 
   1424     private File getUserPackagesStateFile(int userId) {
   1425         // TODO: Implement a cleaner solution when adding tests.
   1426         // This instead of Environment.getUserSystemDirectory(userId) to support testing.
   1427         File userDir = new File(new File(mSystemDir, "users"), Integer.toString(userId));
   1428         return new File(userDir, "package-restrictions.xml");
   1429     }
   1430 
   1431     private File getUserRuntimePermissionsFile(int userId) {
   1432         // TODO: Implement a cleaner solution when adding tests.
   1433         // This instead of Environment.getUserSystemDirectory(userId) to support testing.
   1434         File userDir = new File(new File(mSystemDir, "users"), Integer.toString(userId));
   1435         return new File(userDir, RUNTIME_PERMISSIONS_FILE_NAME);
   1436     }
   1437 
   1438     private File getUserPackagesStateBackupFile(int userId) {
   1439         return new File(Environment.getUserSystemDirectory(userId),
   1440                 "package-restrictions-backup.xml");
   1441     }
   1442 
   1443     void writeAllUsersPackageRestrictionsLPr() {
   1444         List<UserInfo> users = getAllUsers(UserManagerService.getInstance());
   1445         if (users == null) return;
   1446 
   1447         for (UserInfo user : users) {
   1448             writePackageRestrictionsLPr(user.id);
   1449         }
   1450     }
   1451 
   1452     void writeAllRuntimePermissionsLPr() {
   1453         for (int userId : UserManagerService.getInstance().getUserIds()) {
   1454             mRuntimePermissionsPersistence.writePermissionsForUserAsyncLPr(userId);
   1455         }
   1456     }
   1457 
   1458     boolean areDefaultRuntimePermissionsGrantedLPr(int userId) {
   1459         return mRuntimePermissionsPersistence
   1460                 .areDefaultRuntimPermissionsGrantedLPr(userId);
   1461     }
   1462 
   1463     void onDefaultRuntimePermissionsGrantedLPr(int userId) {
   1464         mRuntimePermissionsPersistence
   1465                 .onDefaultRuntimePermissionsGrantedLPr(userId);
   1466     }
   1467 
   1468     public VersionInfo findOrCreateVersion(String volumeUuid) {
   1469         VersionInfo ver = mVersion.get(volumeUuid);
   1470         if (ver == null) {
   1471             ver = new VersionInfo();
   1472             mVersion.put(volumeUuid, ver);
   1473         }
   1474         return ver;
   1475     }
   1476 
   1477     public VersionInfo getInternalVersion() {
   1478         return mVersion.get(StorageManager.UUID_PRIVATE_INTERNAL);
   1479     }
   1480 
   1481     public VersionInfo getExternalVersion() {
   1482         return mVersion.get(StorageManager.UUID_PRIMARY_PHYSICAL);
   1483     }
   1484 
   1485     public void onVolumeForgotten(String fsUuid) {
   1486         mVersion.remove(fsUuid);
   1487     }
   1488 
   1489     /**
   1490      * Applies the preferred activity state described by the given XML.  This code
   1491      * also supports the restore-from-backup code path.
   1492      *
   1493      * @see PreferredActivityBackupHelper
   1494      */
   1495     void readPreferredActivitiesLPw(XmlPullParser parser, int userId)
   1496             throws XmlPullParserException, IOException {
   1497         int outerDepth = parser.getDepth();
   1498         int type;
   1499         while ((type = parser.next()) != XmlPullParser.END_DOCUMENT
   1500                 && (type != XmlPullParser.END_TAG || parser.getDepth() > outerDepth)) {
   1501             if (type == XmlPullParser.END_TAG || type == XmlPullParser.TEXT) {
   1502                 continue;
   1503             }
   1504 
   1505             String tagName = parser.getName();
   1506             if (tagName.equals(TAG_ITEM)) {
   1507                 PreferredActivity pa = new PreferredActivity(parser);
   1508                 if (pa.mPref.getParseError() == null) {
   1509                     editPreferredActivitiesLPw(userId).addFilter(pa);
   1510                 } else {
   1511                     PackageManagerService.reportSettingsProblem(Log.WARN,
   1512                             "Error in package manager settings: <preferred-activity> "
   1513                                     + pa.mPref.getParseError() + " at "
   1514                                     + parser.getPositionDescription());
   1515                 }
   1516             } else {
   1517                 PackageManagerService.reportSettingsProblem(Log.WARN,
   1518                         "Unknown element under <preferred-activities>: " + parser.getName());
   1519                 XmlUtils.skipCurrentTag(parser);
   1520             }
   1521         }
   1522     }
   1523 
   1524     private void readPersistentPreferredActivitiesLPw(XmlPullParser parser, int userId)
   1525             throws XmlPullParserException, IOException {
   1526         int outerDepth = parser.getDepth();
   1527         int type;
   1528         while ((type = parser.next()) != XmlPullParser.END_DOCUMENT
   1529                 && (type != XmlPullParser.END_TAG || parser.getDepth() > outerDepth)) {
   1530             if (type == XmlPullParser.END_TAG || type == XmlPullParser.TEXT) {
   1531                 continue;
   1532             }
   1533             String tagName = parser.getName();
   1534             if (tagName.equals(TAG_ITEM)) {
   1535                 PersistentPreferredActivity ppa = new PersistentPreferredActivity(parser);
   1536                 editPersistentPreferredActivitiesLPw(userId).addFilter(ppa);
   1537             } else {
   1538                 PackageManagerService.reportSettingsProblem(Log.WARN,
   1539                         "Unknown element under <" + TAG_PERSISTENT_PREFERRED_ACTIVITIES + ">: "
   1540                         + parser.getName());
   1541                 XmlUtils.skipCurrentTag(parser);
   1542             }
   1543         }
   1544     }
   1545 
   1546     private void readCrossProfileIntentFiltersLPw(XmlPullParser parser, int userId)
   1547             throws XmlPullParserException, IOException {
   1548         int outerDepth = parser.getDepth();
   1549         int type;
   1550         while ((type = parser.next()) != XmlPullParser.END_DOCUMENT
   1551                 && (type != XmlPullParser.END_TAG || parser.getDepth() > outerDepth)) {
   1552             if (type == XmlPullParser.END_TAG || type == XmlPullParser.TEXT) {
   1553                 continue;
   1554             }
   1555             final String tagName = parser.getName();
   1556             if (tagName.equals(TAG_ITEM)) {
   1557                 CrossProfileIntentFilter cpif = new CrossProfileIntentFilter(parser);
   1558                 editCrossProfileIntentResolverLPw(userId).addFilter(cpif);
   1559             } else {
   1560                 String msg = "Unknown element under " +  TAG_CROSS_PROFILE_INTENT_FILTERS + ": " +
   1561                         tagName;
   1562                 PackageManagerService.reportSettingsProblem(Log.WARN, msg);
   1563                 XmlUtils.skipCurrentTag(parser);
   1564             }
   1565         }
   1566     }
   1567 
   1568     private void readDomainVerificationLPw(XmlPullParser parser, PackageSettingBase packageSetting)
   1569             throws XmlPullParserException, IOException {
   1570         IntentFilterVerificationInfo ivi = new IntentFilterVerificationInfo(parser);
   1571         packageSetting.setIntentFilterVerificationInfo(ivi);
   1572         if (DEBUG_PARSER) {
   1573             Log.d(TAG, "Read domain verification for package: " + ivi.getPackageName());
   1574         }
   1575     }
   1576 
   1577     private void readRestoredIntentFilterVerifications(XmlPullParser parser)
   1578             throws XmlPullParserException, IOException {
   1579         int outerDepth = parser.getDepth();
   1580         int type;
   1581         while ((type = parser.next()) != XmlPullParser.END_DOCUMENT
   1582                 && (type != XmlPullParser.END_TAG || parser.getDepth() > outerDepth)) {
   1583             if (type == XmlPullParser.END_TAG || type == XmlPullParser.TEXT) {
   1584                 continue;
   1585             }
   1586             final String tagName = parser.getName();
   1587             if (tagName.equals(TAG_DOMAIN_VERIFICATION)) {
   1588                 IntentFilterVerificationInfo ivi = new IntentFilterVerificationInfo(parser);
   1589                 if (DEBUG_DOMAIN_VERIFICATION) {
   1590                     Slog.i(TAG, "Restored IVI for " + ivi.getPackageName()
   1591                             + " status=" + ivi.getStatusString());
   1592                 }
   1593                 mRestoredIntentFilterVerifications.put(ivi.getPackageName(), ivi);
   1594             } else {
   1595                 Slog.w(TAG, "Unknown element: " + tagName);
   1596                 XmlUtils.skipCurrentTag(parser);
   1597             }
   1598         }
   1599     }
   1600 
   1601     void readDefaultAppsLPw(XmlPullParser parser, int userId)
   1602             throws XmlPullParserException, IOException {
   1603         int outerDepth = parser.getDepth();
   1604         int type;
   1605         while ((type = parser.next()) != XmlPullParser.END_DOCUMENT
   1606                 && (type != XmlPullParser.END_TAG || parser.getDepth() > outerDepth)) {
   1607             if (type == XmlPullParser.END_TAG || type == XmlPullParser.TEXT) {
   1608                 continue;
   1609             }
   1610             String tagName = parser.getName();
   1611             if (tagName.equals(TAG_DEFAULT_BROWSER)) {
   1612                 String packageName = parser.getAttributeValue(null, ATTR_PACKAGE_NAME);
   1613                 mDefaultBrowserApp.put(userId, packageName);
   1614             } else if (tagName.equals(TAG_DEFAULT_DIALER)) {
   1615                 String packageName = parser.getAttributeValue(null, ATTR_PACKAGE_NAME);
   1616                 mDefaultDialerApp.put(userId, packageName);
   1617             } else {
   1618                 String msg = "Unknown element under " +  TAG_DEFAULT_APPS + ": " +
   1619                         parser.getName();
   1620                 PackageManagerService.reportSettingsProblem(Log.WARN, msg);
   1621                 XmlUtils.skipCurrentTag(parser);
   1622             }
   1623         }
   1624     }
   1625 
   1626     void readBlockUninstallPackagesLPw(XmlPullParser parser, int userId)
   1627             throws XmlPullParserException, IOException {
   1628         int outerDepth = parser.getDepth();
   1629         int type;
   1630         ArraySet<String> packages = new ArraySet<>();
   1631         while ((type = parser.next()) != XmlPullParser.END_DOCUMENT
   1632                 && (type != XmlPullParser.END_TAG || parser.getDepth() > outerDepth)) {
   1633             if (type == XmlPullParser.END_TAG || type == XmlPullParser.TEXT) {
   1634                 continue;
   1635             }
   1636             String tagName = parser.getName();
   1637             if (tagName.equals(TAG_BLOCK_UNINSTALL)) {
   1638                 String packageName = parser.getAttributeValue(null, ATTR_PACKAGE_NAME);
   1639                 packages.add(packageName);
   1640             } else {
   1641                 String msg = "Unknown element under " +  TAG_BLOCK_UNINSTALL_PACKAGES + ": " +
   1642                         parser.getName();
   1643                 PackageManagerService.reportSettingsProblem(Log.WARN, msg);
   1644                 XmlUtils.skipCurrentTag(parser);
   1645             }
   1646         }
   1647         if (packages.isEmpty()) {
   1648             mBlockUninstallPackages.remove(userId);
   1649         } else {
   1650             mBlockUninstallPackages.put(userId, packages);
   1651         }
   1652     }
   1653 
   1654     void readPackageRestrictionsLPr(int userId) {
   1655         if (DEBUG_MU) {
   1656             Log.i(TAG, "Reading package restrictions for user=" + userId);
   1657         }
   1658         FileInputStream str = null;
   1659         File userPackagesStateFile = getUserPackagesStateFile(userId);
   1660         File backupFile = getUserPackagesStateBackupFile(userId);
   1661         if (backupFile.exists()) {
   1662             try {
   1663                 str = new FileInputStream(backupFile);
   1664                 mReadMessages.append("Reading from backup stopped packages file\n");
   1665                 PackageManagerService.reportSettingsProblem(Log.INFO,
   1666                         "Need to read from backup stopped packages file");
   1667                 if (userPackagesStateFile.exists()) {
   1668                     // If both the backup and normal file exist, we
   1669                     // ignore the normal one since it might have been
   1670                     // corrupted.
   1671                     Slog.w(PackageManagerService.TAG, "Cleaning up stopped packages file "
   1672                             + userPackagesStateFile);
   1673                     userPackagesStateFile.delete();
   1674                 }
   1675             } catch (java.io.IOException e) {
   1676                 // We'll try for the normal settings file.
   1677             }
   1678         }
   1679 
   1680         try {
   1681             if (str == null) {
   1682                 if (!userPackagesStateFile.exists()) {
   1683                     mReadMessages.append("No stopped packages file found\n");
   1684                     PackageManagerService.reportSettingsProblem(Log.INFO,
   1685                             "No stopped packages file; "
   1686                             + "assuming all started");
   1687                     // At first boot, make sure no packages are stopped.
   1688                     // We usually want to have third party apps initialize
   1689                     // in the stopped state, but not at first boot.  Also
   1690                     // consider all applications to be installed.
   1691                     for (PackageSetting pkg : mPackages.values()) {
   1692                         pkg.setUserState(userId, 0, COMPONENT_ENABLED_STATE_DEFAULT,
   1693                                 true  /*installed*/,
   1694                                 false /*stopped*/,
   1695                                 false /*notLaunched*/,
   1696                                 false /*hidden*/,
   1697                                 false /*suspended*/,
   1698                                 false /*instantApp*/,
   1699                                 false /*virtualPreload*/,
   1700                                 null /*lastDisableAppCaller*/,
   1701                                 null /*enabledComponents*/,
   1702                                 null /*disabledComponents*/,
   1703                                 INTENT_FILTER_DOMAIN_VERIFICATION_STATUS_UNDEFINED,
   1704                                 0, PackageManager.INSTALL_REASON_UNKNOWN);
   1705                     }
   1706                     return;
   1707                 }
   1708                 str = new FileInputStream(userPackagesStateFile);
   1709             }
   1710             final XmlPullParser parser = Xml.newPullParser();
   1711             parser.setInput(str, StandardCharsets.UTF_8.name());
   1712 
   1713             int type;
   1714             while ((type=parser.next()) != XmlPullParser.START_TAG
   1715                        && type != XmlPullParser.END_DOCUMENT) {
   1716                 ;
   1717             }
   1718 
   1719             if (type != XmlPullParser.START_TAG) {
   1720                 mReadMessages.append("No start tag found in package restrictions file\n");
   1721                 PackageManagerService.reportSettingsProblem(Log.WARN,
   1722                         "No start tag found in package manager stopped packages");
   1723                 return;
   1724             }
   1725 
   1726             int maxAppLinkGeneration = 0;
   1727 
   1728             int outerDepth = parser.getDepth();
   1729             PackageSetting ps = null;
   1730             while ((type=parser.next()) != XmlPullParser.END_DOCUMENT
   1731                    && (type != XmlPullParser.END_TAG
   1732                            || parser.getDepth() > outerDepth)) {
   1733                 if (type == XmlPullParser.END_TAG
   1734                         || type == XmlPullParser.TEXT) {
   1735                     continue;
   1736                 }
   1737 
   1738                 String tagName = parser.getName();
   1739                 if (tagName.equals(TAG_PACKAGE)) {
   1740                     String name = parser.getAttributeValue(null, ATTR_NAME);
   1741                     ps = mPackages.get(name);
   1742                     if (ps == null) {
   1743                         Slog.w(PackageManagerService.TAG, "No package known for stopped package "
   1744                                 + name);
   1745                         XmlUtils.skipCurrentTag(parser);
   1746                         continue;
   1747                     }
   1748 
   1749                     final long ceDataInode = XmlUtils.readLongAttribute(parser, ATTR_CE_DATA_INODE,
   1750                             0);
   1751                     final boolean installed = XmlUtils.readBooleanAttribute(parser, ATTR_INSTALLED,
   1752                             true);
   1753                     final boolean stopped = XmlUtils.readBooleanAttribute(parser, ATTR_STOPPED,
   1754                             false);
   1755                     final boolean notLaunched = XmlUtils.readBooleanAttribute(parser,
   1756                             ATTR_NOT_LAUNCHED, false);
   1757 
   1758                     // For backwards compatibility with the previous name of "blocked", which
   1759                     // now means hidden, read the old attribute as well.
   1760                     final String blockedStr = parser.getAttributeValue(null, ATTR_BLOCKED);
   1761                     boolean hidden = blockedStr == null
   1762                             ? false : Boolean.parseBoolean(blockedStr);
   1763                     final String hiddenStr = parser.getAttributeValue(null, ATTR_HIDDEN);
   1764                     hidden = hiddenStr == null
   1765                             ? hidden : Boolean.parseBoolean(hiddenStr);
   1766 
   1767                     final boolean suspended = XmlUtils.readBooleanAttribute(parser, ATTR_SUSPENDED,
   1768                             false);
   1769                     final boolean blockUninstall = XmlUtils.readBooleanAttribute(parser,
   1770                             ATTR_BLOCK_UNINSTALL, false);
   1771                     final boolean instantApp = XmlUtils.readBooleanAttribute(parser,
   1772                             ATTR_INSTANT_APP, false);
   1773                     final boolean virtualPreload = XmlUtils.readBooleanAttribute(parser,
   1774                             ATTR_VIRTUAL_PRELOAD, false);
   1775                     final int enabled = XmlUtils.readIntAttribute(parser, ATTR_ENABLED,
   1776                             COMPONENT_ENABLED_STATE_DEFAULT);
   1777                     final String enabledCaller = parser.getAttributeValue(null,
   1778                             ATTR_ENABLED_CALLER);
   1779 
   1780                     final int verifState = XmlUtils.readIntAttribute(parser,
   1781                             ATTR_DOMAIN_VERIFICATON_STATE,
   1782                             PackageManager.INTENT_FILTER_DOMAIN_VERIFICATION_STATUS_UNDEFINED);
   1783                     final int linkGeneration = XmlUtils.readIntAttribute(parser,
   1784                             ATTR_APP_LINK_GENERATION, 0);
   1785                     if (linkGeneration > maxAppLinkGeneration) {
   1786                         maxAppLinkGeneration = linkGeneration;
   1787                     }
   1788                     final int installReason = XmlUtils.readIntAttribute(parser,
   1789                             ATTR_INSTALL_REASON, PackageManager.INSTALL_REASON_UNKNOWN);
   1790 
   1791                     ArraySet<String> enabledComponents = null;
   1792                     ArraySet<String> disabledComponents = null;
   1793 
   1794                     int packageDepth = parser.getDepth();
   1795                     while ((type=parser.next()) != XmlPullParser.END_DOCUMENT
   1796                             && (type != XmlPullParser.END_TAG
   1797                             || parser.getDepth() > packageDepth)) {
   1798                         if (type == XmlPullParser.END_TAG
   1799                                 || type == XmlPullParser.TEXT) {
   1800                             continue;
   1801                         }
   1802                         tagName = parser.getName();
   1803                         if (tagName.equals(TAG_ENABLED_COMPONENTS)) {
   1804                             enabledComponents = readComponentsLPr(parser);
   1805                         } else if (tagName.equals(TAG_DISABLED_COMPONENTS)) {
   1806                             disabledComponents = readComponentsLPr(parser);
   1807                         }
   1808                     }
   1809 
   1810                     if (blockUninstall) {
   1811                         setBlockUninstallLPw(userId, name, true);
   1812                     }
   1813                     ps.setUserState(userId, ceDataInode, enabled, installed, stopped, notLaunched,
   1814                             hidden, suspended, instantApp, virtualPreload, enabledCaller,
   1815                             enabledComponents, disabledComponents, verifState, linkGeneration,
   1816                             installReason);
   1817                 } else if (tagName.equals("preferred-activities")) {
   1818                     readPreferredActivitiesLPw(parser, userId);
   1819                 } else if (tagName.equals(TAG_PERSISTENT_PREFERRED_ACTIVITIES)) {
   1820                     readPersistentPreferredActivitiesLPw(parser, userId);
   1821                 } else if (tagName.equals(TAG_CROSS_PROFILE_INTENT_FILTERS)) {
   1822                     readCrossProfileIntentFiltersLPw(parser, userId);
   1823                 } else if (tagName.equals(TAG_DEFAULT_APPS)) {
   1824                     readDefaultAppsLPw(parser, userId);
   1825                 } else if (tagName.equals(TAG_BLOCK_UNINSTALL_PACKAGES)) {
   1826                     readBlockUninstallPackagesLPw(parser, userId);
   1827                 } else {
   1828                     Slog.w(PackageManagerService.TAG, "Unknown element under <stopped-packages>: "
   1829                           + parser.getName());
   1830                     XmlUtils.skipCurrentTag(parser);
   1831                 }
   1832             }
   1833 
   1834             str.close();
   1835 
   1836             mNextAppLinkGeneration.put(userId, maxAppLinkGeneration + 1);
   1837 
   1838         } catch (XmlPullParserException e) {
   1839             mReadMessages.append("Error reading: " + e.toString());
   1840             PackageManagerService.reportSettingsProblem(Log.ERROR,
   1841                     "Error reading stopped packages: " + e);
   1842             Slog.wtf(PackageManagerService.TAG, "Error reading package manager stopped packages",
   1843                     e);
   1844 
   1845         } catch (java.io.IOException e) {
   1846             mReadMessages.append("Error reading: " + e.toString());
   1847             PackageManagerService.reportSettingsProblem(Log.ERROR, "Error reading settings: " + e);
   1848             Slog.wtf(PackageManagerService.TAG, "Error reading package manager stopped packages",
   1849                     e);
   1850         }
   1851     }
   1852 
   1853     void setBlockUninstallLPw(int userId, String packageName, boolean blockUninstall) {
   1854         ArraySet<String> packages = mBlockUninstallPackages.get(userId);
   1855         if (blockUninstall) {
   1856             if (packages == null) {
   1857                 packages = new ArraySet<String>();
   1858                 mBlockUninstallPackages.put(userId, packages);
   1859             }
   1860             packages.add(packageName);
   1861         } else if (packages != null) {
   1862             packages.remove(packageName);
   1863             if (packages.isEmpty()) {
   1864                 mBlockUninstallPackages.remove(userId);
   1865             }
   1866         }
   1867     }
   1868 
   1869     boolean getBlockUninstallLPr(int userId, String packageName) {
   1870         ArraySet<String> packages = mBlockUninstallPackages.get(userId);
   1871         if (packages == null) {
   1872             return false;
   1873         }
   1874         return packages.contains(packageName);
   1875     }
   1876 
   1877     private ArraySet<String> readComponentsLPr(XmlPullParser parser)
   1878             throws IOException, XmlPullParserException {
   1879         ArraySet<String> components = null;
   1880         int type;
   1881         int outerDepth = parser.getDepth();
   1882         String tagName;
   1883         while ((type = parser.next()) != XmlPullParser.END_DOCUMENT
   1884                 && (type != XmlPullParser.END_TAG
   1885                 || parser.getDepth() > outerDepth)) {
   1886             if (type == XmlPullParser.END_TAG
   1887                     || type == XmlPullParser.TEXT) {
   1888                 continue;
   1889             }
   1890             tagName = parser.getName();
   1891             if (tagName.equals(TAG_ITEM)) {
   1892                 String componentName = parser.getAttributeValue(null, ATTR_NAME);
   1893                 if (componentName != null) {
   1894                     if (components == null) {
   1895                         components = new ArraySet<String>();
   1896                     }
   1897                     components.add(componentName);
   1898                 }
   1899             }
   1900         }
   1901         return components;
   1902     }
   1903 
   1904     /**
   1905      * Record the state of preferred activity configuration into XML.  This is used both
   1906      * for recording packages.xml internally and for supporting backup/restore of the
   1907      * preferred activity configuration.
   1908      */
   1909     void writePreferredActivitiesLPr(XmlSerializer serializer, int userId, boolean full)
   1910             throws IllegalArgumentException, IllegalStateException, IOException {
   1911         serializer.startTag(null, "preferred-activities");
   1912         PreferredIntentResolver pir = mPreferredActivities.get(userId);
   1913         if (pir != null) {
   1914             for (final PreferredActivity pa : pir.filterSet()) {
   1915                 serializer.startTag(null, TAG_ITEM);
   1916                 pa.writeToXml(serializer, full);
   1917                 serializer.endTag(null, TAG_ITEM);
   1918             }
   1919         }
   1920         serializer.endTag(null, "preferred-activities");
   1921     }
   1922 
   1923     void writePersistentPreferredActivitiesLPr(XmlSerializer serializer, int userId)
   1924             throws IllegalArgumentException, IllegalStateException, IOException {
   1925         serializer.startTag(null, TAG_PERSISTENT_PREFERRED_ACTIVITIES);
   1926         PersistentPreferredIntentResolver ppir = mPersistentPreferredActivities.get(userId);
   1927         if (ppir != null) {
   1928             for (final PersistentPreferredActivity ppa : ppir.filterSet()) {
   1929                 serializer.startTag(null, TAG_ITEM);
   1930                 ppa.writeToXml(serializer);
   1931                 serializer.endTag(null, TAG_ITEM);
   1932             }
   1933         }
   1934         serializer.endTag(null, TAG_PERSISTENT_PREFERRED_ACTIVITIES);
   1935     }
   1936 
   1937     void writeCrossProfileIntentFiltersLPr(XmlSerializer serializer, int userId)
   1938             throws IllegalArgumentException, IllegalStateException, IOException {
   1939         serializer.startTag(null, TAG_CROSS_PROFILE_INTENT_FILTERS);
   1940         CrossProfileIntentResolver cpir = mCrossProfileIntentResolvers.get(userId);
   1941         if (cpir != null) {
   1942             for (final CrossProfileIntentFilter cpif : cpir.filterSet()) {
   1943                 serializer.startTag(null, TAG_ITEM);
   1944                 cpif.writeToXml(serializer);
   1945                 serializer.endTag(null, TAG_ITEM);
   1946             }
   1947         }
   1948         serializer.endTag(null, TAG_CROSS_PROFILE_INTENT_FILTERS);
   1949     }
   1950 
   1951     void writeDomainVerificationsLPr(XmlSerializer serializer,
   1952                                      IntentFilterVerificationInfo verificationInfo)
   1953             throws IllegalArgumentException, IllegalStateException, IOException {
   1954         if (verificationInfo != null && verificationInfo.getPackageName() != null) {
   1955             serializer.startTag(null, TAG_DOMAIN_VERIFICATION);
   1956             verificationInfo.writeToXml(serializer);
   1957             if (DEBUG_DOMAIN_VERIFICATION) {
   1958                 Slog.d(TAG, "Wrote domain verification for package: "
   1959                         + verificationInfo.getPackageName());
   1960             }
   1961             serializer.endTag(null, TAG_DOMAIN_VERIFICATION);
   1962         }
   1963     }
   1964 
   1965     // Specifically for backup/restore
   1966     void writeAllDomainVerificationsLPr(XmlSerializer serializer, int userId)
   1967             throws IllegalArgumentException, IllegalStateException, IOException {
   1968         serializer.startTag(null, TAG_ALL_INTENT_FILTER_VERIFICATION);
   1969         final int N = mPackages.size();
   1970         for (int i = 0; i < N; i++) {
   1971             PackageSetting ps = mPackages.valueAt(i);
   1972             IntentFilterVerificationInfo ivi = ps.getIntentFilterVerificationInfo();
   1973             if (ivi != null) {
   1974                 writeDomainVerificationsLPr(serializer, ivi);
   1975             }
   1976         }
   1977         serializer.endTag(null, TAG_ALL_INTENT_FILTER_VERIFICATION);
   1978     }
   1979 
   1980     // Specifically for backup/restore
   1981     void readAllDomainVerificationsLPr(XmlPullParser parser, int userId)
   1982             throws XmlPullParserException, IOException {
   1983         mRestoredIntentFilterVerifications.clear();
   1984 
   1985         int outerDepth = parser.getDepth();
   1986         int type;
   1987         while ((type = parser.next()) != XmlPullParser.END_DOCUMENT
   1988                 && (type != XmlPullParser.END_TAG || parser.getDepth() > outerDepth)) {
   1989             if (type == XmlPullParser.END_TAG || type == XmlPullParser.TEXT) {
   1990                 continue;
   1991             }
   1992 
   1993             String tagName = parser.getName();
   1994             if (tagName.equals(TAG_DOMAIN_VERIFICATION)) {
   1995                 IntentFilterVerificationInfo ivi = new IntentFilterVerificationInfo(parser);
   1996                 final String pkgName = ivi.getPackageName();
   1997                 final PackageSetting ps = mPackages.get(pkgName);
   1998                 if (ps != null) {
   1999                     // known/existing package; update in place
   2000                     ps.setIntentFilterVerificationInfo(ivi);
   2001                     if (DEBUG_DOMAIN_VERIFICATION) {
   2002                         Slog.d(TAG, "Restored IVI for existing app " + pkgName
   2003                                 + " status=" + ivi.getStatusString());
   2004                     }
   2005                 } else {
   2006                     mRestoredIntentFilterVerifications.put(pkgName, ivi);
   2007                     if (DEBUG_DOMAIN_VERIFICATION) {
   2008                         Slog.d(TAG, "Restored IVI for pending app " + pkgName
   2009                                 + " status=" + ivi.getStatusString());
   2010                     }
   2011                 }
   2012             } else {
   2013                 PackageManagerService.reportSettingsProblem(Log.WARN,
   2014                         "Unknown element under <all-intent-filter-verification>: "
   2015                         + parser.getName());
   2016                 XmlUtils.skipCurrentTag(parser);
   2017             }
   2018         }
   2019     }
   2020 
   2021     // Specifically for backup/restore
   2022     public void processRestoredPermissionGrantLPr(String pkgName, String permission,
   2023             boolean isGranted, int restoredFlagSet, int userId)
   2024             throws IOException, XmlPullParserException {
   2025         mRuntimePermissionsPersistence.rememberRestoredUserGrantLPr(
   2026                 pkgName, permission, isGranted, restoredFlagSet, userId);
   2027     }
   2028 
   2029     void writeDefaultAppsLPr(XmlSerializer serializer, int userId)
   2030             throws IllegalArgumentException, IllegalStateException, IOException {
   2031         serializer.startTag(null, TAG_DEFAULT_APPS);
   2032         String defaultBrowser = mDefaultBrowserApp.get(userId);
   2033         if (!TextUtils.isEmpty(defaultBrowser)) {
   2034             serializer.startTag(null, TAG_DEFAULT_BROWSER);
   2035             serializer.attribute(null, ATTR_PACKAGE_NAME, defaultBrowser);
   2036             serializer.endTag(null, TAG_DEFAULT_BROWSER);
   2037         }
   2038         String defaultDialer = mDefaultDialerApp.get(userId);
   2039         if (!TextUtils.isEmpty(defaultDialer)) {
   2040             serializer.startTag(null, TAG_DEFAULT_DIALER);
   2041             serializer.attribute(null, ATTR_PACKAGE_NAME, defaultDialer);
   2042             serializer.endTag(null, TAG_DEFAULT_DIALER);
   2043         }
   2044         serializer.endTag(null, TAG_DEFAULT_APPS);
   2045     }
   2046 
   2047     void writeBlockUninstallPackagesLPr(XmlSerializer serializer, int userId)
   2048             throws IOException  {
   2049         ArraySet<String> packages = mBlockUninstallPackages.get(userId);
   2050         if (packages != null) {
   2051             serializer.startTag(null, TAG_BLOCK_UNINSTALL_PACKAGES);
   2052             for (int i = 0; i < packages.size(); i++) {
   2053                  serializer.startTag(null, TAG_BLOCK_UNINSTALL);
   2054                  serializer.attribute(null, ATTR_PACKAGE_NAME, packages.valueAt(i));
   2055                  serializer.endTag(null, TAG_BLOCK_UNINSTALL);
   2056             }
   2057             serializer.endTag(null, TAG_BLOCK_UNINSTALL_PACKAGES);
   2058         }
   2059     }
   2060 
   2061     void writePackageRestrictionsLPr(int userId) {
   2062         if (DEBUG_MU) {
   2063             Log.i(TAG, "Writing package restrictions for user=" + userId);
   2064         }
   2065         // Keep the old stopped packages around until we know the new ones have
   2066         // been successfully written.
   2067         File userPackagesStateFile = getUserPackagesStateFile(userId);
   2068         File backupFile = getUserPackagesStateBackupFile(userId);
   2069         new File(userPackagesStateFile.getParent()).mkdirs();
   2070         if (userPackagesStateFile.exists()) {
   2071             // Presence of backup settings file indicates that we failed
   2072             // to persist packages earlier. So preserve the older
   2073             // backup for future reference since the current packages
   2074             // might have been corrupted.
   2075             if (!backupFile.exists()) {
   2076                 if (!userPackagesStateFile.renameTo(backupFile)) {
   2077                     Slog.wtf(PackageManagerService.TAG,
   2078                             "Unable to backup user packages state file, "
   2079                             + "current changes will be lost at reboot");
   2080                     return;
   2081                 }
   2082             } else {
   2083                 userPackagesStateFile.delete();
   2084                 Slog.w(PackageManagerService.TAG, "Preserving older stopped packages backup");
   2085             }
   2086         }
   2087 
   2088         try {
   2089             final FileOutputStream fstr = new FileOutputStream(userPackagesStateFile);
   2090             final BufferedOutputStream str = new BufferedOutputStream(fstr);
   2091 
   2092             final XmlSerializer serializer = new FastXmlSerializer();
   2093             serializer.setOutput(str, StandardCharsets.UTF_8.name());
   2094             serializer.startDocument(null, true);
   2095             serializer.setFeature("http://xmlpull.org/v1/doc/features.html#indent-output", true);
   2096 
   2097             serializer.startTag(null, TAG_PACKAGE_RESTRICTIONS);
   2098 
   2099             for (final PackageSetting pkg : mPackages.values()) {
   2100                 final PackageUserState ustate = pkg.readUserState(userId);
   2101                 if (DEBUG_MU) Log.i(TAG, "  pkg=" + pkg.name + ", state=" + ustate.enabled);
   2102 
   2103                 serializer.startTag(null, TAG_PACKAGE);
   2104                 serializer.attribute(null, ATTR_NAME, pkg.name);
   2105                 if (ustate.ceDataInode != 0) {
   2106                     XmlUtils.writeLongAttribute(serializer, ATTR_CE_DATA_INODE, ustate.ceDataInode);
   2107                 }
   2108                 if (!ustate.installed) {
   2109                     serializer.attribute(null, ATTR_INSTALLED, "false");
   2110                 }
   2111                 if (ustate.stopped) {
   2112                     serializer.attribute(null, ATTR_STOPPED, "true");
   2113                 }
   2114                 if (ustate.notLaunched) {
   2115                     serializer.attribute(null, ATTR_NOT_LAUNCHED, "true");
   2116                 }
   2117                 if (ustate.hidden) {
   2118                     serializer.attribute(null, ATTR_HIDDEN, "true");
   2119                 }
   2120                 if (ustate.suspended) {
   2121                     serializer.attribute(null, ATTR_SUSPENDED, "true");
   2122                 }
   2123                 if (ustate.instantApp) {
   2124                     serializer.attribute(null, ATTR_INSTANT_APP, "true");
   2125                 }
   2126                 if (ustate.virtualPreload) {
   2127                     serializer.attribute(null, ATTR_VIRTUAL_PRELOAD, "true");
   2128                 }
   2129                 if (ustate.enabled != COMPONENT_ENABLED_STATE_DEFAULT) {
   2130                     serializer.attribute(null, ATTR_ENABLED,
   2131                             Integer.toString(ustate.enabled));
   2132                     if (ustate.lastDisableAppCaller != null) {
   2133                         serializer.attribute(null, ATTR_ENABLED_CALLER,
   2134                                 ustate.lastDisableAppCaller);
   2135                     }
   2136                 }
   2137                 if (ustate.domainVerificationStatus !=
   2138                         PackageManager.INTENT_FILTER_DOMAIN_VERIFICATION_STATUS_UNDEFINED) {
   2139                     XmlUtils.writeIntAttribute(serializer, ATTR_DOMAIN_VERIFICATON_STATE,
   2140                             ustate.domainVerificationStatus);
   2141                 }
   2142                 if (ustate.appLinkGeneration != 0) {
   2143                     XmlUtils.writeIntAttribute(serializer, ATTR_APP_LINK_GENERATION,
   2144                             ustate.appLinkGeneration);
   2145                 }
   2146                 if (ustate.installReason != PackageManager.INSTALL_REASON_UNKNOWN) {
   2147                     serializer.attribute(null, ATTR_INSTALL_REASON,
   2148                             Integer.toString(ustate.installReason));
   2149                 }
   2150                 if (!ArrayUtils.isEmpty(ustate.enabledComponents)) {
   2151                     serializer.startTag(null, TAG_ENABLED_COMPONENTS);
   2152                     for (final String name : ustate.enabledComponents) {
   2153                         serializer.startTag(null, TAG_ITEM);
   2154                         serializer.attribute(null, ATTR_NAME, name);
   2155                         serializer.endTag(null, TAG_ITEM);
   2156                     }
   2157                     serializer.endTag(null, TAG_ENABLED_COMPONENTS);
   2158                 }
   2159                 if (!ArrayUtils.isEmpty(ustate.disabledComponents)) {
   2160                     serializer.startTag(null, TAG_DISABLED_COMPONENTS);
   2161                     for (final String name : ustate.disabledComponents) {
   2162                         serializer.startTag(null, TAG_ITEM);
   2163                         serializer.attribute(null, ATTR_NAME, name);
   2164                         serializer.endTag(null, TAG_ITEM);
   2165                     }
   2166                     serializer.endTag(null, TAG_DISABLED_COMPONENTS);
   2167                 }
   2168 
   2169                 serializer.endTag(null, TAG_PACKAGE);
   2170             }
   2171 
   2172             writePreferredActivitiesLPr(serializer, userId, true);
   2173             writePersistentPreferredActivitiesLPr(serializer, userId);
   2174             writeCrossProfileIntentFiltersLPr(serializer, userId);
   2175             writeDefaultAppsLPr(serializer, userId);
   2176             writeBlockUninstallPackagesLPr(serializer, userId);
   2177 
   2178             serializer.endTag(null, TAG_PACKAGE_RESTRICTIONS);
   2179 
   2180             serializer.endDocument();
   2181 
   2182             str.flush();
   2183             FileUtils.sync(fstr);
   2184             str.close();
   2185 
   2186             // New settings successfully written, old ones are no longer
   2187             // needed.
   2188             backupFile.delete();
   2189             FileUtils.setPermissions(userPackagesStateFile.toString(),
   2190                     FileUtils.S_IRUSR|FileUtils.S_IWUSR
   2191                     |FileUtils.S_IRGRP|FileUtils.S_IWGRP,
   2192                     -1, -1);
   2193 
   2194             // Done, all is good!
   2195             return;
   2196         } catch(java.io.IOException e) {
   2197             Slog.wtf(PackageManagerService.TAG,
   2198                     "Unable to write package manager user packages state, "
   2199                     + " current changes will be lost at reboot", e);
   2200         }
   2201 
   2202         // Clean up partially written files
   2203         if (userPackagesStateFile.exists()) {
   2204             if (!userPackagesStateFile.delete()) {
   2205                 Log.i(PackageManagerService.TAG, "Failed to clean up mangled file: "
   2206                         + mStoppedPackagesFilename);
   2207             }
   2208         }
   2209     }
   2210 
   2211     void readInstallPermissionsLPr(XmlPullParser parser,
   2212             PermissionsState permissionsState) throws IOException, XmlPullParserException {
   2213         int outerDepth = parser.getDepth();
   2214         int type;
   2215         while ((type=parser.next()) != XmlPullParser.END_DOCUMENT
   2216                 && (type != XmlPullParser.END_TAG
   2217                 || parser.getDepth() > outerDepth)) {
   2218             if (type == XmlPullParser.END_TAG
   2219                     || type == XmlPullParser.TEXT) {
   2220                 continue;
   2221             }
   2222             String tagName = parser.getName();
   2223             if (tagName.equals(TAG_ITEM)) {
   2224                 String name = parser.getAttributeValue(null, ATTR_NAME);
   2225 
   2226                 BasePermission bp = mPermissions.get(name);
   2227                 if (bp == null) {
   2228                     Slog.w(PackageManagerService.TAG, "Unknown permission: " + name);
   2229                     XmlUtils.skipCurrentTag(parser);
   2230                     continue;
   2231                 }
   2232 
   2233                 String grantedStr = parser.getAttributeValue(null, ATTR_GRANTED);
   2234                 final boolean granted = grantedStr == null
   2235                         || Boolean.parseBoolean(grantedStr);
   2236 
   2237                 String flagsStr = parser.getAttributeValue(null, ATTR_FLAGS);
   2238                 final int flags = (flagsStr != null)
   2239                         ? Integer.parseInt(flagsStr, 16) : 0;
   2240 
   2241                 if (granted) {
   2242                     if (permissionsState.grantInstallPermission(bp) ==
   2243                             PermissionsState.PERMISSION_OPERATION_FAILURE) {
   2244                         Slog.w(PackageManagerService.TAG, "Permission already added: " + name);
   2245                         XmlUtils.skipCurrentTag(parser);
   2246                     } else {
   2247                         permissionsState.updatePermissionFlags(bp, UserHandle.USER_ALL,
   2248                                 PackageManager.MASK_PERMISSION_FLAGS, flags);
   2249                     }
   2250                 } else {
   2251                     if (permissionsState.revokeInstallPermission(bp) ==
   2252                             PermissionsState.PERMISSION_OPERATION_FAILURE) {
   2253                         Slog.w(PackageManagerService.TAG, "Permission already added: " + name);
   2254                         XmlUtils.skipCurrentTag(parser);
   2255                     } else {
   2256                         permissionsState.updatePermissionFlags(bp, UserHandle.USER_ALL,
   2257                                 PackageManager.MASK_PERMISSION_FLAGS, flags);
   2258                     }
   2259                 }
   2260             } else {
   2261                 Slog.w(PackageManagerService.TAG, "Unknown element under <permissions>: "
   2262                         + parser.getName());
   2263                 XmlUtils.skipCurrentTag(parser);
   2264             }
   2265         }
   2266     }
   2267 
   2268     void writePermissionsLPr(XmlSerializer serializer, List<PermissionState> permissionStates)
   2269             throws IOException {
   2270         if (permissionStates.isEmpty()) {
   2271             return;
   2272         }
   2273 
   2274         serializer.startTag(null, TAG_PERMISSIONS);
   2275 
   2276         for (PermissionState permissionState : permissionStates) {
   2277             serializer.startTag(null, TAG_ITEM);
   2278             serializer.attribute(null, ATTR_NAME, permissionState.getName());
   2279             serializer.attribute(null, ATTR_GRANTED, String.valueOf(permissionState.isGranted()));
   2280             serializer.attribute(null, ATTR_FLAGS, Integer.toHexString(permissionState.getFlags()));
   2281             serializer.endTag(null, TAG_ITEM);
   2282         }
   2283 
   2284         serializer.endTag(null, TAG_PERMISSIONS);
   2285     }
   2286 
   2287     void writeChildPackagesLPw(XmlSerializer serializer, List<String> childPackageNames)
   2288             throws IOException {
   2289         if (childPackageNames == null) {
   2290             return;
   2291         }
   2292         final int childCount = childPackageNames.size();
   2293         for (int i = 0; i < childCount; i++) {
   2294             String childPackageName = childPackageNames.get(i);
   2295             serializer.startTag(null, TAG_CHILD_PACKAGE);
   2296             serializer.attribute(null, ATTR_NAME, childPackageName);
   2297             serializer.endTag(null, TAG_CHILD_PACKAGE);
   2298         }
   2299     }
   2300 
   2301     void readUsesStaticLibLPw(XmlPullParser parser, PackageSetting outPs)
   2302             throws IOException, XmlPullParserException {
   2303         int outerDepth = parser.getDepth();
   2304         int type;
   2305         while ((type = parser.next()) != XmlPullParser.END_DOCUMENT
   2306                 && (type != XmlPullParser.END_TAG || parser.getDepth() > outerDepth)) {
   2307             if (type == XmlPullParser.END_TAG || type == XmlPullParser.TEXT) {
   2308                 continue;
   2309             }
   2310             String libName = parser.getAttributeValue(null, ATTR_NAME);
   2311             String libVersionStr = parser.getAttributeValue(null, ATTR_VERSION);
   2312 
   2313             int libVersion = -1;
   2314             try {
   2315                 libVersion = Integer.parseInt(libVersionStr);
   2316             } catch (NumberFormatException e) {
   2317                 // ignore
   2318             }
   2319 
   2320             if (libName != null && libVersion >= 0) {
   2321                 outPs.usesStaticLibraries = ArrayUtils.appendElement(String.class,
   2322                         outPs.usesStaticLibraries, libName);
   2323                 outPs.usesStaticLibrariesVersions = ArrayUtils.appendInt(
   2324                         outPs.usesStaticLibrariesVersions, libVersion);
   2325             }
   2326 
   2327             XmlUtils.skipCurrentTag(parser);
   2328         }
   2329     }
   2330 
   2331     void writeUsesStaticLibLPw(XmlSerializer serializer, String[] usesStaticLibraries,
   2332             int[] usesStaticLibraryVersions) throws IOException {
   2333         if (ArrayUtils.isEmpty(usesStaticLibraries) || ArrayUtils.isEmpty(usesStaticLibraryVersions)
   2334                 || usesStaticLibraries.length != usesStaticLibraryVersions.length) {
   2335             return;
   2336         }
   2337         final int libCount = usesStaticLibraries.length;
   2338         for (int i = 0; i < libCount; i++) {
   2339             final String libName = usesStaticLibraries[i];
   2340             final int libVersion = usesStaticLibraryVersions[i];
   2341             serializer.startTag(null, TAG_USES_STATIC_LIB);
   2342             serializer.attribute(null, ATTR_NAME, libName);
   2343             serializer.attribute(null, ATTR_VERSION, Integer.toString(libVersion));
   2344             serializer.endTag(null, TAG_USES_STATIC_LIB);
   2345         }
   2346     }
   2347 
   2348     // Note: assumed "stopped" field is already cleared in all packages.
   2349     // Legacy reader, used to read in the old file format after an upgrade. Not used after that.
   2350     void readStoppedLPw() {
   2351         FileInputStream str = null;
   2352         if (mBackupStoppedPackagesFilename.exists()) {
   2353             try {
   2354                 str = new FileInputStream(mBackupStoppedPackagesFilename);
   2355                 mReadMessages.append("Reading from backup stopped packages file\n");
   2356                 PackageManagerService.reportSettingsProblem(Log.INFO,
   2357                         "Need to read from backup stopped packages file");
   2358                 if (mSettingsFilename.exists()) {
   2359                     // If both the backup and normal file exist, we
   2360                     // ignore the normal one since it might have been
   2361                     // corrupted.
   2362                     Slog.w(PackageManagerService.TAG, "Cleaning up stopped packages file "
   2363                             + mStoppedPackagesFilename);
   2364                     mStoppedPackagesFilename.delete();
   2365                 }
   2366             } catch (java.io.IOException e) {
   2367                 // We'll try for the normal settings file.
   2368             }
   2369         }
   2370 
   2371         try {
   2372             if (str == null) {
   2373                 if (!mStoppedPackagesFilename.exists()) {
   2374                     mReadMessages.append("No stopped packages file found\n");
   2375                     PackageManagerService.reportSettingsProblem(Log.INFO,
   2376                             "No stopped packages file file; assuming all started");
   2377                     // At first boot, make sure no packages are stopped.
   2378                     // We usually want to have third party apps initialize
   2379                     // in the stopped state, but not at first boot.
   2380                     for (PackageSetting pkg : mPackages.values()) {
   2381                         pkg.setStopped(false, 0);
   2382                         pkg.setNotLaunched(false, 0);
   2383                     }
   2384                     return;
   2385                 }
   2386                 str = new FileInputStream(mStoppedPackagesFilename);
   2387             }
   2388             final XmlPullParser parser = Xml.newPullParser();
   2389             parser.setInput(str, null);
   2390 
   2391             int type;
   2392             while ((type=parser.next()) != XmlPullParser.START_TAG
   2393                        && type != XmlPullParser.END_DOCUMENT) {
   2394                 ;
   2395             }
   2396 
   2397             if (type != XmlPullParser.START_TAG) {
   2398                 mReadMessages.append("No start tag found in stopped packages file\n");
   2399                 PackageManagerService.reportSettingsProblem(Log.WARN,
   2400                         "No start tag found in package manager stopped packages");
   2401                 return;
   2402             }
   2403 
   2404             int outerDepth = parser.getDepth();
   2405             while ((type=parser.next()) != XmlPullParser.END_DOCUMENT
   2406                    && (type != XmlPullParser.END_TAG
   2407                            || parser.getDepth() > outerDepth)) {
   2408                 if (type == XmlPullParser.END_TAG
   2409                         || type == XmlPullParser.TEXT) {
   2410                     continue;
   2411                 }
   2412 
   2413                 String tagName = parser.getName();
   2414                 if (tagName.equals(TAG_PACKAGE)) {
   2415                     String name = parser.getAttributeValue(null, ATTR_NAME);
   2416                     PackageSetting ps = mPackages.get(name);
   2417                     if (ps != null) {
   2418                         ps.setStopped(true, 0);
   2419                         if ("1".equals(parser.getAttributeValue(null, ATTR_NOT_LAUNCHED))) {
   2420                             ps.setNotLaunched(true, 0);
   2421                         }
   2422                     } else {
   2423                         Slog.w(PackageManagerService.TAG,
   2424                                 "No package known for stopped package " + name);
   2425                     }
   2426                     XmlUtils.skipCurrentTag(parser);
   2427                 } else {
   2428                     Slog.w(PackageManagerService.TAG, "Unknown element under <stopped-packages>: "
   2429                           + parser.getName());
   2430                     XmlUtils.skipCurrentTag(parser);
   2431                 }
   2432             }
   2433 
   2434             str.close();
   2435 
   2436         } catch (XmlPullParserException e) {
   2437             mReadMessages.append("Error reading: " + e.toString());
   2438             PackageManagerService.reportSettingsProblem(Log.ERROR,
   2439                     "Error reading stopped packages: " + e);
   2440             Slog.wtf(PackageManagerService.TAG, "Error reading package manager stopped packages",
   2441                     e);
   2442 
   2443         } catch (java.io.IOException e) {
   2444             mReadMessages.append("Error reading: " + e.toString());
   2445             PackageManagerService.reportSettingsProblem(Log.ERROR, "Error reading settings: " + e);
   2446             Slog.wtf(PackageManagerService.TAG, "Error reading package manager stopped packages",
   2447                     e);
   2448 
   2449         }
   2450     }
   2451 
   2452     void writeLPr() {
   2453         //Debug.startMethodTracing("/data/system/packageprof", 8 * 1024 * 1024);
   2454 
   2455         // Keep the old settings around until we know the new ones have
   2456         // been successfully written.
   2457         if (mSettingsFilename.exists()) {
   2458             // Presence of backup settings file indicates that we failed
   2459             // to persist settings earlier. So preserve the older
   2460             // backup for future reference since the current settings
   2461             // might have been corrupted.
   2462             if (!mBackupSettingsFilename.exists()) {
   2463                 if (!mSettingsFilename.renameTo(mBackupSettingsFilename)) {
   2464                     Slog.wtf(PackageManagerService.TAG,
   2465                             "Unable to backup package manager settings, "
   2466                             + " current changes will be lost at reboot");
   2467                     return;
   2468                 }
   2469             } else {
   2470                 mSettingsFilename.delete();
   2471                 Slog.w(PackageManagerService.TAG, "Preserving older settings backup");
   2472             }
   2473         }
   2474 
   2475         mPastSignatures.clear();
   2476 
   2477         try {
   2478             FileOutputStream fstr = new FileOutputStream(mSettingsFilename);
   2479             BufferedOutputStream str = new BufferedOutputStream(fstr);
   2480 
   2481             //XmlSerializer serializer = XmlUtils.serializerInstance();
   2482             XmlSerializer serializer = new FastXmlSerializer();
   2483             serializer.setOutput(str, StandardCharsets.UTF_8.name());
   2484             serializer.startDocument(null, true);
   2485             serializer.setFeature("http://xmlpull.org/v1/doc/features.html#indent-output", true);
   2486 
   2487             serializer.startTag(null, "packages");
   2488 
   2489             for (int i = 0; i < mVersion.size(); i++) {
   2490                 final String volumeUuid = mVersion.keyAt(i);
   2491                 final VersionInfo ver = mVersion.valueAt(i);
   2492 
   2493                 serializer.startTag(null, TAG_VERSION);
   2494                 XmlUtils.writeStringAttribute(serializer, ATTR_VOLUME_UUID, volumeUuid);
   2495                 XmlUtils.writeIntAttribute(serializer, ATTR_SDK_VERSION, ver.sdkVersion);
   2496                 XmlUtils.writeIntAttribute(serializer, ATTR_DATABASE_VERSION, ver.databaseVersion);
   2497                 XmlUtils.writeStringAttribute(serializer, ATTR_FINGERPRINT, ver.fingerprint);
   2498                 serializer.endTag(null, TAG_VERSION);
   2499             }
   2500 
   2501             if (mVerifierDeviceIdentity != null) {
   2502                 serializer.startTag(null, "verifier");
   2503                 serializer.attribute(null, "device", mVerifierDeviceIdentity.toString());
   2504                 serializer.endTag(null, "verifier");
   2505             }
   2506 
   2507             if (mReadExternalStorageEnforced != null) {
   2508                 serializer.startTag(null, TAG_READ_EXTERNAL_STORAGE);
   2509                 serializer.attribute(
   2510                         null, ATTR_ENFORCEMENT, mReadExternalStorageEnforced ? "1" : "0");
   2511                 serializer.endTag(null, TAG_READ_EXTERNAL_STORAGE);
   2512             }
   2513 
   2514             serializer.startTag(null, "permission-trees");
   2515             for (BasePermission bp : mPermissionTrees.values()) {
   2516                 writePermissionLPr(serializer, bp);
   2517             }
   2518             serializer.endTag(null, "permission-trees");
   2519 
   2520             serializer.startTag(null, "permissions");
   2521             for (BasePermission bp : mPermissions.values()) {
   2522                 writePermissionLPr(serializer, bp);
   2523             }
   2524             serializer.endTag(null, "permissions");
   2525 
   2526             for (final PackageSetting pkg : mPackages.values()) {
   2527                 writePackageLPr(serializer, pkg);
   2528             }
   2529 
   2530             for (final PackageSetting pkg : mDisabledSysPackages.values()) {
   2531                 writeDisabledSysPackageLPr(serializer, pkg);
   2532             }
   2533 
   2534             for (final SharedUserSetting usr : mSharedUsers.values()) {
   2535                 serializer.startTag(null, "shared-user");
   2536                 serializer.attribute(null, ATTR_NAME, usr.name);
   2537                 serializer.attribute(null, "userId",
   2538                         Integer.toString(usr.userId));
   2539                 usr.signatures.writeXml(serializer, "sigs", mPastSignatures);
   2540                 writePermissionsLPr(serializer, usr.getPermissionsState()
   2541                         .getInstallPermissionStates());
   2542                 serializer.endTag(null, "shared-user");
   2543             }
   2544 
   2545             if (mPackagesToBeCleaned.size() > 0) {
   2546                 for (PackageCleanItem item : mPackagesToBeCleaned) {
   2547                     final String userStr = Integer.toString(item.userId);
   2548                     serializer.startTag(null, "cleaning-package");
   2549                     serializer.attribute(null, ATTR_NAME, item.packageName);
   2550                     serializer.attribute(null, ATTR_CODE, item.andCode ? "true" : "false");
   2551                     serializer.attribute(null, ATTR_USER, userStr);
   2552                     serializer.endTag(null, "cleaning-package");
   2553                 }
   2554             }
   2555 
   2556             if (mRenamedPackages.size() > 0) {
   2557                 for (Map.Entry<String, String> e : mRenamedPackages.entrySet()) {
   2558                     serializer.startTag(null, "renamed-package");
   2559                     serializer.attribute(null, "new", e.getKey());
   2560                     serializer.attribute(null, "old", e.getValue());
   2561                     serializer.endTag(null, "renamed-package");
   2562                 }
   2563             }
   2564 
   2565             final int numIVIs = mRestoredIntentFilterVerifications.size();
   2566             if (numIVIs > 0) {
   2567                 if (DEBUG_DOMAIN_VERIFICATION) {
   2568                     Slog.i(TAG, "Writing restored-ivi entries to packages.xml");
   2569                 }
   2570                 serializer.startTag(null, "restored-ivi");
   2571                 for (int i = 0; i < numIVIs; i++) {
   2572                     IntentFilterVerificationInfo ivi = mRestoredIntentFilterVerifications.valueAt(i);
   2573                     writeDomainVerificationsLPr(serializer, ivi);
   2574                 }
   2575                 serializer.endTag(null, "restored-ivi");
   2576             } else {
   2577                 if (DEBUG_DOMAIN_VERIFICATION) {
   2578                     Slog.i(TAG, "  no restored IVI entries to write");
   2579                 }
   2580             }
   2581 
   2582             mKeySetManagerService.writeKeySetManagerServiceLPr(serializer);
   2583 
   2584             serializer.endTag(null, "packages");
   2585 
   2586             serializer.endDocument();
   2587 
   2588             str.flush();
   2589             FileUtils.sync(fstr);
   2590             str.close();
   2591 
   2592             // New settings successfully written, old ones are no longer
   2593             // needed.
   2594             mBackupSettingsFilename.delete();
   2595             FileUtils.setPermissions(mSettingsFilename.toString(),
   2596                     FileUtils.S_IRUSR|FileUtils.S_IWUSR
   2597                     |FileUtils.S_IRGRP|FileUtils.S_IWGRP,
   2598                     -1, -1);
   2599 
   2600             writeKernelMappingLPr();
   2601             writePackageListLPr();
   2602             writeAllUsersPackageRestrictionsLPr();
   2603             writeAllRuntimePermissionsLPr();
   2604             return;
   2605 
   2606         } catch(XmlPullParserException e) {
   2607             Slog.wtf(PackageManagerService.TAG, "Unable to write package manager settings, "
   2608                     + "current changes will be lost at reboot", e);
   2609         } catch(java.io.IOException e) {
   2610             Slog.wtf(PackageManagerService.TAG, "Unable to write package manager settings, "
   2611                     + "current changes will be lost at reboot", e);
   2612         }
   2613         // Clean up partially written files
   2614         if (mSettingsFilename.exists()) {
   2615             if (!mSettingsFilename.delete()) {
   2616                 Slog.wtf(PackageManagerService.TAG, "Failed to clean up mangled file: "
   2617                         + mSettingsFilename);
   2618             }
   2619         }
   2620         //Debug.stopMethodTracing();
   2621     }
   2622 
   2623     private void writeKernelRemoveUserLPr(int userId) {
   2624         if (mKernelMappingFilename == null) return;
   2625 
   2626         File removeUserIdFile = new File(mKernelMappingFilename, "remove_userid");
   2627         if (DEBUG_KERNEL) Slog.d(TAG, "Writing " + userId + " to " + removeUserIdFile
   2628                 .getAbsolutePath());
   2629         writeIntToFile(removeUserIdFile, userId);
   2630     }
   2631 
   2632     void writeKernelMappingLPr() {
   2633         if (mKernelMappingFilename == null) return;
   2634 
   2635         final String[] known = mKernelMappingFilename.list();
   2636         final ArraySet<String> knownSet = new ArraySet<>(known.length);
   2637         for (String name : known) {
   2638             knownSet.add(name);
   2639         }
   2640 
   2641         for (final PackageSetting ps : mPackages.values()) {
   2642             // Package is actively claimed
   2643             knownSet.remove(ps.name);
   2644             writeKernelMappingLPr(ps);
   2645         }
   2646 
   2647         // Remove any unclaimed mappings
   2648         for (int i = 0; i < knownSet.size(); i++) {
   2649             final String name = knownSet.valueAt(i);
   2650             if (DEBUG_KERNEL) Slog.d(TAG, "Dropping mapping " + name);
   2651 
   2652             mKernelMapping.remove(name);
   2653             new File(mKernelMappingFilename, name).delete();
   2654         }
   2655     }
   2656 
   2657     void writeKernelMappingLPr(PackageSetting ps) {
   2658         if (mKernelMappingFilename == null || ps == null || ps.name == null) return;
   2659 
   2660         KernelPackageState cur = mKernelMapping.get(ps.name);
   2661         final boolean firstTime = cur == null;
   2662         int[] excludedUserIds = ps.getNotInstalledUserIds();
   2663         final boolean userIdsChanged = firstTime
   2664                 || !Arrays.equals(excludedUserIds, cur.excludedUserIds);
   2665 
   2666         // Package directory
   2667         final File dir = new File(mKernelMappingFilename, ps.name);
   2668 
   2669         if (firstTime) {
   2670             dir.mkdir();
   2671             // Create a new mapping state
   2672             cur = new KernelPackageState();
   2673             mKernelMapping.put(ps.name, cur);
   2674         }
   2675 
   2676         // If mapping is incorrect or non-existent, write the appid file
   2677         if (cur.appId != ps.appId) {
   2678             final File appIdFile = new File(dir, "appid");
   2679             writeIntToFile(appIdFile, ps.appId);
   2680             if (DEBUG_KERNEL) Slog.d(TAG, "Mapping " + ps.name + " to " + ps.appId);
   2681         }
   2682 
   2683         if (userIdsChanged) {
   2684             // Build the exclusion list -- the ids to add to the exclusion list
   2685             for (int i = 0; i < excludedUserIds.length; i++) {
   2686                 if (cur.excludedUserIds == null || !ArrayUtils.contains(cur.excludedUserIds,
   2687                         excludedUserIds[i])) {
   2688                     writeIntToFile(new File(dir, "excluded_userids"), excludedUserIds[i]);
   2689                     if (DEBUG_KERNEL) Slog.d(TAG, "Writing " + excludedUserIds[i] + " to "
   2690                             + ps.name + "/excluded_userids");
   2691                 }
   2692             }
   2693             // Build the inclusion list -- the ids to remove from the exclusion list
   2694             if (cur.excludedUserIds != null) {
   2695                 for (int i = 0; i < cur.excludedUserIds.length; i++) {
   2696                     if (!ArrayUtils.contains(excludedUserIds, cur.excludedUserIds[i])) {
   2697                         writeIntToFile(new File(dir, "clear_userid"),
   2698                                 cur.excludedUserIds[i]);
   2699                         if (DEBUG_KERNEL) Slog.d(TAG, "Writing " + cur.excludedUserIds[i] + " to "
   2700                                 + ps.name + "/clear_userid");
   2701 
   2702                     }
   2703                 }
   2704             }
   2705             cur.excludedUserIds = excludedUserIds;
   2706         }
   2707     }
   2708 
   2709     private void writeIntToFile(File file, int value) {
   2710         try {
   2711             FileUtils.bytesToFile(file.getAbsolutePath(),
   2712                     Integer.toString(value).getBytes(StandardCharsets.US_ASCII));
   2713         } catch (IOException ignored) {
   2714             Slog.w(TAG, "Couldn't write " + value + " to " + file.getAbsolutePath());
   2715         }
   2716     }
   2717 
   2718     void writePackageListLPr() {
   2719         writePackageListLPr(-1);
   2720     }
   2721 
   2722     void writePackageListLPr(int creatingUserId) {
   2723         // Only derive GIDs for active users (not dying)
   2724         final List<UserInfo> users = UserManagerService.getInstance().getUsers(true);
   2725         int[] userIds = new int[users.size()];
   2726         for (int i = 0; i < userIds.length; i++) {
   2727             userIds[i] = users.get(i).id;
   2728         }
   2729         if (creatingUserId != -1) {
   2730             userIds = ArrayUtils.appendInt(userIds, creatingUserId);
   2731         }
   2732 
   2733         // Write package list file now, use a JournaledFile.
   2734         File tempFile = new File(mPackageListFilename.getAbsolutePath() + ".tmp");
   2735         JournaledFile journal = new JournaledFile(mPackageListFilename, tempFile);
   2736 
   2737         final File writeTarget = journal.chooseForWrite();
   2738         FileOutputStream fstr;
   2739         BufferedWriter writer = null;
   2740         try {
   2741             fstr = new FileOutputStream(writeTarget);
   2742             writer = new BufferedWriter(new OutputStreamWriter(fstr, Charset.defaultCharset()));
   2743             FileUtils.setPermissions(fstr.getFD(), 0640, SYSTEM_UID, PACKAGE_INFO_GID);
   2744 
   2745             StringBuilder sb = new StringBuilder();
   2746             for (final PackageSetting pkg : mPackages.values()) {
   2747                 if (pkg.pkg == null || pkg.pkg.applicationInfo == null
   2748                         || pkg.pkg.applicationInfo.dataDir == null) {
   2749                     if (!"android".equals(pkg.name)) {
   2750                         Slog.w(TAG, "Skipping " + pkg + " due to missing metadata");
   2751                     }
   2752                     continue;
   2753                 }
   2754 
   2755                 final ApplicationInfo ai = pkg.pkg.applicationInfo;
   2756                 final String dataPath = ai.dataDir;
   2757                 final boolean isDebug = (ai.flags & ApplicationInfo.FLAG_DEBUGGABLE) != 0;
   2758                 final int[] gids = pkg.getPermissionsState().computeGids(userIds);
   2759 
   2760                 // Avoid any application that has a space in its path.
   2761                 if (dataPath.indexOf(' ') >= 0)
   2762                     continue;
   2763 
   2764                 // we store on each line the following information for now:
   2765                 //
   2766                 // pkgName    - package name
   2767                 // userId     - application-specific user id
   2768                 // debugFlag  - 0 or 1 if the package is debuggable.
   2769                 // dataPath   - path to package's data path
   2770                 // seinfo     - seinfo label for the app (assigned at install time)
   2771                 // gids       - supplementary gids this app launches with
   2772                 //
   2773                 // NOTE: We prefer not to expose all ApplicationInfo flags for now.
   2774                 //
   2775                 // DO NOT MODIFY THIS FORMAT UNLESS YOU CAN ALSO MODIFY ITS USERS
   2776                 // FROM NATIVE CODE. AT THE MOMENT, LOOK AT THE FOLLOWING SOURCES:
   2777                 //   frameworks/base/libs/packagelistparser
   2778                 //   system/core/run-as/run-as.c
   2779                 //
   2780                 sb.setLength(0);
   2781                 sb.append(ai.packageName);
   2782                 sb.append(" ");
   2783                 sb.append(ai.uid);
   2784                 sb.append(isDebug ? " 1 " : " 0 ");
   2785                 sb.append(dataPath);
   2786                 sb.append(" ");
   2787                 sb.append(ai.seInfo);
   2788                 sb.append(" ");
   2789                 if (gids != null && gids.length > 0) {
   2790                     sb.append(gids[0]);
   2791                     for (int i = 1; i < gids.length; i++) {
   2792                         sb.append(",");
   2793                         sb.append(gids[i]);
   2794                     }
   2795                 } else {
   2796                     sb.append("none");
   2797                 }
   2798                 sb.append("\n");
   2799                 writer.append(sb);
   2800             }
   2801             writer.flush();
   2802             FileUtils.sync(fstr);
   2803             writer.close();
   2804             journal.commit();
   2805         } catch (Exception e) {
   2806             Slog.wtf(TAG, "Failed to write packages.list", e);
   2807             IoUtils.closeQuietly(writer);
   2808             journal.rollback();
   2809         }
   2810     }
   2811 
   2812     void writeDisabledSysPackageLPr(XmlSerializer serializer, final PackageSetting pkg)
   2813             throws java.io.IOException {
   2814         serializer.startTag(null, "updated-package");
   2815         serializer.attribute(null, ATTR_NAME, pkg.name);
   2816         if (pkg.realName != null) {
   2817             serializer.attribute(null, "realName", pkg.realName);
   2818         }
   2819         serializer.attribute(null, "codePath", pkg.codePathString);
   2820         serializer.attribute(null, "ft", Long.toHexString(pkg.timeStamp));
   2821         serializer.attribute(null, "it", Long.toHexString(pkg.firstInstallTime));
   2822         serializer.attribute(null, "ut", Long.toHexString(pkg.lastUpdateTime));
   2823         serializer.attribute(null, "version", String.valueOf(pkg.versionCode));
   2824         if (!pkg.resourcePathString.equals(pkg.codePathString)) {
   2825             serializer.attribute(null, "resourcePath", pkg.resourcePathString);
   2826         }
   2827         if (pkg.legacyNativeLibraryPathString != null) {
   2828             serializer.attribute(null, "nativeLibraryPath", pkg.legacyNativeLibraryPathString);
   2829         }
   2830         if (pkg.primaryCpuAbiString != null) {
   2831            serializer.attribute(null, "primaryCpuAbi", pkg.primaryCpuAbiString);
   2832         }
   2833         if (pkg.secondaryCpuAbiString != null) {
   2834             serializer.attribute(null, "secondaryCpuAbi", pkg.secondaryCpuAbiString);
   2835         }
   2836         if (pkg.cpuAbiOverrideString != null) {
   2837             serializer.attribute(null, "cpuAbiOverride", pkg.cpuAbiOverrideString);
   2838         }
   2839 
   2840         if (pkg.sharedUser == null) {
   2841             serializer.attribute(null, "userId", Integer.toString(pkg.appId));
   2842         } else {
   2843             serializer.attribute(null, "sharedUserId", Integer.toString(pkg.appId));
   2844         }
   2845 
   2846         if (pkg.parentPackageName != null) {
   2847             serializer.attribute(null, "parentPackageName", pkg.parentPackageName);
   2848         }
   2849 
   2850         writeChildPackagesLPw(serializer, pkg.childPackageNames);
   2851 
   2852         writeUsesStaticLibLPw(serializer, pkg.usesStaticLibraries, pkg.usesStaticLibrariesVersions);
   2853 
   2854         // If this is a shared user, the permissions will be written there.
   2855         if (pkg.sharedUser == null) {
   2856             writePermissionsLPr(serializer, pkg.getPermissionsState()
   2857                     .getInstallPermissionStates());
   2858         }
   2859 
   2860         serializer.endTag(null, "updated-package");
   2861     }
   2862 
   2863     void writePackageLPr(XmlSerializer serializer, final PackageSetting pkg)
   2864             throws java.io.IOException {
   2865         serializer.startTag(null, "package");
   2866         serializer.attribute(null, ATTR_NAME, pkg.name);
   2867         if (pkg.realName != null) {
   2868             serializer.attribute(null, "realName", pkg.realName);
   2869         }
   2870         serializer.attribute(null, "codePath", pkg.codePathString);
   2871         if (!pkg.resourcePathString.equals(pkg.codePathString)) {
   2872             serializer.attribute(null, "resourcePath", pkg.resourcePathString);
   2873         }
   2874 
   2875         if (pkg.legacyNativeLibraryPathString != null) {
   2876             serializer.attribute(null, "nativeLibraryPath", pkg.legacyNativeLibraryPathString);
   2877         }
   2878         if (pkg.primaryCpuAbiString != null) {
   2879             serializer.attribute(null, "primaryCpuAbi", pkg.primaryCpuAbiString);
   2880         }
   2881         if (pkg.secondaryCpuAbiString != null) {
   2882             serializer.attribute(null, "secondaryCpuAbi", pkg.secondaryCpuAbiString);
   2883         }
   2884         if (pkg.cpuAbiOverrideString != null) {
   2885             serializer.attribute(null, "cpuAbiOverride", pkg.cpuAbiOverrideString);
   2886         }
   2887 
   2888         serializer.attribute(null, "publicFlags", Integer.toString(pkg.pkgFlags));
   2889         serializer.attribute(null, "privateFlags", Integer.toString(pkg.pkgPrivateFlags));
   2890         serializer.attribute(null, "ft", Long.toHexString(pkg.timeStamp));
   2891         serializer.attribute(null, "it", Long.toHexString(pkg.firstInstallTime));
   2892         serializer.attribute(null, "ut", Long.toHexString(pkg.lastUpdateTime));
   2893         serializer.attribute(null, "version", String.valueOf(pkg.versionCode));
   2894         if (pkg.sharedUser == null) {
   2895             serializer.attribute(null, "userId", Integer.toString(pkg.appId));
   2896         } else {
   2897             serializer.attribute(null, "sharedUserId", Integer.toString(pkg.appId));
   2898         }
   2899         if (pkg.uidError) {
   2900             serializer.attribute(null, "uidError", "true");
   2901         }
   2902         if (pkg.installStatus == PackageSettingBase.PKG_INSTALL_INCOMPLETE) {
   2903             serializer.attribute(null, "installStatus", "false");
   2904         }
   2905         if (pkg.installerPackageName != null) {
   2906             serializer.attribute(null, "installer", pkg.installerPackageName);
   2907         }
   2908         if (pkg.isOrphaned) {
   2909             serializer.attribute(null, "isOrphaned", "true");
   2910         }
   2911         if (pkg.volumeUuid != null) {
   2912             serializer.attribute(null, "volumeUuid", pkg.volumeUuid);
   2913         }
   2914         if (pkg.categoryHint != ApplicationInfo.CATEGORY_UNDEFINED) {
   2915             serializer.attribute(null, "categoryHint",
   2916                     Integer.toString(pkg.categoryHint));
   2917         }
   2918         if (pkg.parentPackageName != null) {
   2919             serializer.attribute(null, "parentPackageName", pkg.parentPackageName);
   2920         }
   2921         if (pkg.updateAvailable) {
   2922             serializer.attribute(null, "updateAvailable", "true");
   2923         }
   2924 
   2925         writeChildPackagesLPw(serializer, pkg.childPackageNames);
   2926 
   2927         writeUsesStaticLibLPw(serializer, pkg.usesStaticLibraries, pkg.usesStaticLibrariesVersions);
   2928 
   2929         pkg.signatures.writeXml(serializer, "sigs", mPastSignatures);
   2930 
   2931         writePermissionsLPr(serializer, pkg.getPermissionsState()
   2932                     .getInstallPermissionStates());
   2933 
   2934         writeSigningKeySetLPr(serializer, pkg.keySetData);
   2935         writeUpgradeKeySetsLPr(serializer, pkg.keySetData);
   2936         writeKeySetAliasesLPr(serializer, pkg.keySetData);
   2937         writeDomainVerificationsLPr(serializer, pkg.verificationInfo);
   2938 
   2939         serializer.endTag(null, "package");
   2940     }
   2941 
   2942     void writeSigningKeySetLPr(XmlSerializer serializer,
   2943             PackageKeySetData data) throws IOException {
   2944         serializer.startTag(null, "proper-signing-keyset");
   2945         serializer.attribute(null, "identifier",
   2946                 Long.toString(data.getProperSigningKeySet()));
   2947         serializer.endTag(null, "proper-signing-keyset");
   2948     }
   2949 
   2950     void writeUpgradeKeySetsLPr(XmlSerializer serializer,
   2951             PackageKeySetData data) throws IOException {
   2952         long properSigning = data.getProperSigningKeySet();
   2953         if (data.isUsingUpgradeKeySets()) {
   2954             for (long id : data.getUpgradeKeySets()) {
   2955                 serializer.startTag(null, "upgrade-keyset");
   2956                 serializer.attribute(null, "identifier", Long.toString(id));
   2957                 serializer.endTag(null, "upgrade-keyset");
   2958             }
   2959         }
   2960     }
   2961 
   2962     void writeKeySetAliasesLPr(XmlSerializer serializer,
   2963             PackageKeySetData data) throws IOException {
   2964         for (Map.Entry<String, Long> e: data.getAliases().entrySet()) {
   2965             serializer.startTag(null, "defined-keyset");
   2966             serializer.attribute(null, "alias", e.getKey());
   2967             serializer.attribute(null, "identifier", Long.toString(e.getValue()));
   2968             serializer.endTag(null, "defined-keyset");
   2969         }
   2970     }
   2971 
   2972     void writePermissionLPr(XmlSerializer serializer, BasePermission bp)
   2973             throws XmlPullParserException, java.io.IOException {
   2974         if (bp.sourcePackage != null) {
   2975             serializer.startTag(null, TAG_ITEM);
   2976             serializer.attribute(null, ATTR_NAME, bp.name);
   2977             serializer.attribute(null, "package", bp.sourcePackage);
   2978             if (bp.protectionLevel != PermissionInfo.PROTECTION_NORMAL) {
   2979                 serializer.attribute(null, "protection", Integer.toString(bp.protectionLevel));
   2980             }
   2981             if (PackageManagerService.DEBUG_SETTINGS)
   2982                 Log.v(PackageManagerService.TAG, "Writing perm: name=" + bp.name + " type="
   2983                         + bp.type);
   2984             if (bp.type == BasePermission.TYPE_DYNAMIC) {
   2985                 final PermissionInfo pi = bp.perm != null ? bp.perm.info : bp.pendingInfo;
   2986                 if (pi != null) {
   2987                     serializer.attribute(null, "type", "dynamic");
   2988                     if (pi.icon != 0) {
   2989                         serializer.attribute(null, "icon", Integer.toString(pi.icon));
   2990                     }
   2991                     if (pi.nonLocalizedLabel != null) {
   2992                         serializer.attribute(null, "label", pi.nonLocalizedLabel.toString());
   2993                     }
   2994                 }
   2995             }
   2996             serializer.endTag(null, TAG_ITEM);
   2997         }
   2998     }
   2999 
   3000     ArrayList<PackageSetting> getListOfIncompleteInstallPackagesLPr() {
   3001         final ArraySet<String> kList = new ArraySet<String>(mPackages.keySet());
   3002         final Iterator<String> its = kList.iterator();
   3003         final ArrayList<PackageSetting> ret = new ArrayList<PackageSetting>();
   3004         while (its.hasNext()) {
   3005             final String key = its.next();
   3006             final PackageSetting ps = mPackages.get(key);
   3007             if (ps.getInstallStatus() == PackageSettingBase.PKG_INSTALL_INCOMPLETE) {
   3008                 ret.add(ps);
   3009             }
   3010         }
   3011         return ret;
   3012     }
   3013 
   3014     void addPackageToCleanLPw(PackageCleanItem pkg) {
   3015         if (!mPackagesToBeCleaned.contains(pkg)) {
   3016             mPackagesToBeCleaned.add(pkg);
   3017         }
   3018     }
   3019 
   3020     boolean readLPw(@NonNull List<UserInfo> users) {
   3021         FileInputStream str = null;
   3022         if (mBackupSettingsFilename.exists()) {
   3023             try {
   3024                 str = new FileInputStream(mBackupSettingsFilename);
   3025                 mReadMessages.append("Reading from backup settings file\n");
   3026                 PackageManagerService.reportSettingsProblem(Log.INFO,
   3027                         "Need to read from backup settings file");
   3028                 if (mSettingsFilename.exists()) {
   3029                     // If both the backup and settings file exist, we
   3030                     // ignore the settings since it might have been
   3031                     // corrupted.
   3032                     Slog.w(PackageManagerService.TAG, "Cleaning up settings file "
   3033                             + mSettingsFilename);
   3034                     mSettingsFilename.delete();
   3035                 }
   3036             } catch (java.io.IOException e) {
   3037                 // We'll try for the normal settings file.
   3038             }
   3039         }
   3040 
   3041         mPendingPackages.clear();
   3042         mPastSignatures.clear();
   3043         mKeySetRefs.clear();
   3044         mInstallerPackages.clear();
   3045 
   3046         try {
   3047             if (str == null) {
   3048                 if (!mSettingsFilename.exists()) {
   3049                     mReadMessages.append("No settings file found\n");
   3050                     PackageManagerService.reportSettingsProblem(Log.INFO,
   3051                             "No settings file; creating initial state");
   3052                     // It's enough to just touch version details to create them
   3053                     // with default values
   3054                     findOrCreateVersion(StorageManager.UUID_PRIVATE_INTERNAL).forceCurrent();
   3055                     findOrCreateVersion(StorageManager.UUID_PRIMARY_PHYSICAL).forceCurrent();
   3056                     return false;
   3057                 }
   3058                 str = new FileInputStream(mSettingsFilename);
   3059             }
   3060             XmlPullParser parser = Xml.newPullParser();
   3061             parser.setInput(str, StandardCharsets.UTF_8.name());
   3062 
   3063             int type;
   3064             while ((type = parser.next()) != XmlPullParser.START_TAG
   3065                     && type != XmlPullParser.END_DOCUMENT) {
   3066                 ;
   3067             }
   3068 
   3069             if (type != XmlPullParser.START_TAG) {
   3070                 mReadMessages.append("No start tag found in settings file\n");
   3071                 PackageManagerService.reportSettingsProblem(Log.WARN,
   3072                         "No start tag found in package manager settings");
   3073                 Slog.wtf(PackageManagerService.TAG,
   3074                         "No start tag found in package manager settings");
   3075                 return false;
   3076             }
   3077 
   3078             int outerDepth = parser.getDepth();
   3079             while ((type = parser.next()) != XmlPullParser.END_DOCUMENT
   3080                     && (type != XmlPullParser.END_TAG || parser.getDepth() > outerDepth)) {
   3081                 if (type == XmlPullParser.END_TAG || type == XmlPullParser.TEXT) {
   3082                     continue;
   3083                 }
   3084 
   3085                 String tagName = parser.getName();
   3086                 if (tagName.equals("package")) {
   3087                     readPackageLPw(parser);
   3088                 } else if (tagName.equals("permissions")) {
   3089                     readPermissionsLPw(mPermissions, parser);
   3090                 } else if (tagName.equals("permission-trees")) {
   3091                     readPermissionsLPw(mPermissionTrees, parser);
   3092                 } else if (tagName.equals("shared-user")) {
   3093                     readSharedUserLPw(parser);
   3094                 } else if (tagName.equals("preferred-packages")) {
   3095                     // no longer used.
   3096                 } else if (tagName.equals("preferred-activities")) {
   3097                     // Upgrading from old single-user implementation;
   3098                     // these are the preferred activities for user 0.
   3099                     readPreferredActivitiesLPw(parser, 0);
   3100                 } else if (tagName.equals(TAG_PERSISTENT_PREFERRED_ACTIVITIES)) {
   3101                     // TODO: check whether this is okay! as it is very
   3102                     // similar to how preferred-activities are treated
   3103                     readPersistentPreferredActivitiesLPw(parser, 0);
   3104                 } else if (tagName.equals(TAG_CROSS_PROFILE_INTENT_FILTERS)) {
   3105                     // TODO: check whether this is okay! as it is very
   3106                     // similar to how preferred-activities are treated
   3107                     readCrossProfileIntentFiltersLPw(parser, 0);
   3108                 } else if (tagName.equals(TAG_DEFAULT_BROWSER)) {
   3109                     readDefaultAppsLPw(parser, 0);
   3110                 } else if (tagName.equals("updated-package")) {
   3111                     readDisabledSysPackageLPw(parser);
   3112                 } else if (tagName.equals("cleaning-package")) {
   3113                     String name = parser.getAttributeValue(null, ATTR_NAME);
   3114                     String userStr = parser.getAttributeValue(null, ATTR_USER);
   3115                     String codeStr = parser.getAttributeValue(null, ATTR_CODE);
   3116                     if (name != null) {
   3117                         int userId = UserHandle.USER_SYSTEM;
   3118                         boolean andCode = true;
   3119                         try {
   3120                             if (userStr != null) {
   3121                                 userId = Integer.parseInt(userStr);
   3122                             }
   3123                         } catch (NumberFormatException e) {
   3124                         }
   3125                         if (codeStr != null) {
   3126                             andCode = Boolean.parseBoolean(codeStr);
   3127                         }
   3128                         addPackageToCleanLPw(new PackageCleanItem(userId, name, andCode));
   3129                     }
   3130                 } else if (tagName.equals("renamed-package")) {
   3131                     String nname = parser.getAttributeValue(null, "new");
   3132                     String oname = parser.getAttributeValue(null, "old");
   3133                     if (nname != null && oname != null) {
   3134                         mRenamedPackages.put(nname, oname);
   3135                     }
   3136                 } else if (tagName.equals("restored-ivi")) {
   3137                     readRestoredIntentFilterVerifications(parser);
   3138                 } else if (tagName.equals("last-platform-version")) {
   3139                     // Upgrade from older XML schema
   3140                     final VersionInfo internal = findOrCreateVersion(
   3141                             StorageManager.UUID_PRIVATE_INTERNAL);
   3142                     final VersionInfo external = findOrCreateVersion(
   3143                             StorageManager.UUID_PRIMARY_PHYSICAL);
   3144 
   3145                     internal.sdkVersion = XmlUtils.readIntAttribute(parser, "internal", 0);
   3146                     external.sdkVersion = XmlUtils.readIntAttribute(parser, "external", 0);
   3147                     internal.fingerprint = external.fingerprint =
   3148                             XmlUtils.readStringAttribute(parser, "fingerprint");
   3149 
   3150                 } else if (tagName.equals("database-version")) {
   3151                     // Upgrade from older XML schema
   3152                     final VersionInfo internal = findOrCreateVersion(
   3153                             StorageManager.UUID_PRIVATE_INTERNAL);
   3154                     final VersionInfo external = findOrCreateVersion(
   3155                             StorageManager.UUID_PRIMARY_PHYSICAL);
   3156 
   3157                     internal.databaseVersion = XmlUtils.readIntAttribute(parser, "internal", 0);
   3158                     external.databaseVersion = XmlUtils.readIntAttribute(parser, "external", 0);
   3159 
   3160                 } else if (tagName.equals("verifier")) {
   3161                     final String deviceIdentity = parser.getAttributeValue(null, "device");
   3162                     try {
   3163                         mVerifierDeviceIdentity = VerifierDeviceIdentity.parse(deviceIdentity);
   3164                     } catch (IllegalArgumentException e) {
   3165                         Slog.w(PackageManagerService.TAG, "Discard invalid verifier device id: "
   3166                                 + e.getMessage());
   3167                     }
   3168                 } else if (TAG_READ_EXTERNAL_STORAGE.equals(tagName)) {
   3169                     final String enforcement = parser.getAttributeValue(null, ATTR_ENFORCEMENT);
   3170                     mReadExternalStorageEnforced = "1".equals(enforcement);
   3171                 } else if (tagName.equals("keyset-settings")) {
   3172                     mKeySetManagerService.readKeySetsLPw(parser, mKeySetRefs);
   3173                 } else if (TAG_VERSION.equals(tagName)) {
   3174                     final String volumeUuid = XmlUtils.readStringAttribute(parser,
   3175                             ATTR_VOLUME_UUID);
   3176                     final VersionInfo ver = findOrCreateVersion(volumeUuid);
   3177                     ver.sdkVersion = XmlUtils.readIntAttribute(parser, ATTR_SDK_VERSION);
   3178                     ver.databaseVersion = XmlUtils.readIntAttribute(parser, ATTR_SDK_VERSION);
   3179                     ver.fingerprint = XmlUtils.readStringAttribute(parser, ATTR_FINGERPRINT);
   3180                 } else {
   3181                     Slog.w(PackageManagerService.TAG, "Unknown element under <packages>: "
   3182                             + parser.getName());
   3183                     XmlUtils.skipCurrentTag(parser);
   3184                 }
   3185             }
   3186 
   3187             str.close();
   3188 
   3189         } catch (XmlPullParserException e) {
   3190             mReadMessages.append("Error reading: " + e.toString());
   3191             PackageManagerService.reportSettingsProblem(Log.ERROR, "Error reading settings: " + e);
   3192             Slog.wtf(PackageManagerService.TAG, "Error reading package manager settings", e);
   3193 
   3194         } catch (java.io.IOException e) {
   3195             mReadMessages.append("Error reading: " + e.toString());
   3196             PackageManagerService.reportSettingsProblem(Log.ERROR, "Error reading settings: " + e);
   3197             Slog.wtf(PackageManagerService.TAG, "Error reading package manager settings", e);
   3198         }
   3199 
   3200         // If the build is setup to drop runtime permissions
   3201         // on update drop the files before loading them.
   3202         if (PackageManagerService.CLEAR_RUNTIME_PERMISSIONS_ON_UPGRADE) {
   3203             final VersionInfo internal = getInternalVersion();
   3204             if (!Build.FINGERPRINT.equals(internal.fingerprint)) {
   3205                 for (UserInfo user : users) {
   3206                     mRuntimePermissionsPersistence.deleteUserRuntimePermissionsFile(user.id);
   3207                 }
   3208             }
   3209         }
   3210 
   3211         final int N = mPendingPackages.size();
   3212 
   3213         for (int i = 0; i < N; i++) {
   3214             final PackageSetting p = mPendingPackages.get(i);
   3215             final int sharedUserId = p.getSharedUserId();
   3216             final Object idObj = getUserIdLPr(sharedUserId);
   3217             if (idObj instanceof SharedUserSetting) {
   3218                 final SharedUserSetting sharedUser = (SharedUserSetting) idObj;
   3219                 p.sharedUser = sharedUser;
   3220                 p.appId = sharedUser.userId;
   3221                 addPackageSettingLPw(p, sharedUser);
   3222             } else if (idObj != null) {
   3223                 String msg = "Bad package setting: package " + p.name + " has shared uid "
   3224                         + sharedUserId + " that is not a shared uid\n";
   3225                 mReadMessages.append(msg);
   3226                 PackageManagerService.reportSettingsProblem(Log.ERROR, msg);
   3227             } else {
   3228                 String msg = "Bad package setting: package " + p.name + " has shared uid "
   3229                         + sharedUserId + " that is not defined\n";
   3230                 mReadMessages.append(msg);
   3231                 PackageManagerService.reportSettingsProblem(Log.ERROR, msg);
   3232             }
   3233         }
   3234         mPendingPackages.clear();
   3235 
   3236         if (mBackupStoppedPackagesFilename.exists()
   3237                 || mStoppedPackagesFilename.exists()) {
   3238             // Read old file
   3239             readStoppedLPw();
   3240             mBackupStoppedPackagesFilename.delete();
   3241             mStoppedPackagesFilename.delete();
   3242             // Migrate to new file format
   3243             writePackageRestrictionsLPr(UserHandle.USER_SYSTEM);
   3244         } else {
   3245             for (UserInfo user : users) {
   3246                 readPackageRestrictionsLPr(user.id);
   3247             }
   3248         }
   3249 
   3250         for (UserInfo user : users) {
   3251             mRuntimePermissionsPersistence.readStateForUserSyncLPr(user.id);
   3252         }
   3253 
   3254         /*
   3255          * Make sure all the updated system packages have their shared users
   3256          * associated with them.
   3257          */
   3258         final Iterator<PackageSetting> disabledIt = mDisabledSysPackages.values().iterator();
   3259         while (disabledIt.hasNext()) {
   3260             final PackageSetting disabledPs = disabledIt.next();
   3261             final Object id = getUserIdLPr(disabledPs.appId);
   3262             if (id != null && id instanceof SharedUserSetting) {
   3263                 disabledPs.sharedUser = (SharedUserSetting) id;
   3264             }
   3265         }
   3266 
   3267         mReadMessages.append("Read completed successfully: " + mPackages.size() + " packages, "
   3268                 + mSharedUsers.size() + " shared uids\n");
   3269 
   3270         writeKernelMappingLPr();
   3271 
   3272         return true;
   3273     }
   3274 
   3275     void applyDefaultPreferredAppsLPw(PackageManagerService service, int userId) {
   3276         // First pull data from any pre-installed apps.
   3277         for (PackageSetting ps : mPackages.values()) {
   3278             if ((ps.pkgFlags&ApplicationInfo.FLAG_SYSTEM) != 0 && ps.pkg != null
   3279                     && ps.pkg.preferredActivityFilters != null) {
   3280                 ArrayList<PackageParser.ActivityIntentInfo> intents
   3281                         = ps.pkg.preferredActivityFilters;
   3282                 for (int i=0; i<intents.size(); i++) {
   3283                     PackageParser.ActivityIntentInfo aii = intents.get(i);
   3284                     applyDefaultPreferredActivityLPw(service, aii, new ComponentName(
   3285                             ps.name, aii.activity.className), userId);
   3286                 }
   3287             }
   3288         }
   3289 
   3290         // Read preferred apps from .../etc/preferred-apps directory.
   3291         File preferredDir = new File(Environment.getRootDirectory(), "etc/preferred-apps");
   3292         if (!preferredDir.exists() || !preferredDir.isDirectory()) {
   3293             return;
   3294         }
   3295         if (!preferredDir.canRead()) {
   3296             Slog.w(TAG, "Directory " + preferredDir + " cannot be read");
   3297             return;
   3298         }
   3299 
   3300         // Iterate over the files in the directory and scan .xml files
   3301         for (File f : preferredDir.listFiles()) {
   3302             if (!f.getPath().endsWith(".xml")) {
   3303                 Slog.i(TAG, "Non-xml file " + f + " in " + preferredDir + " directory, ignoring");
   3304                 continue;
   3305             }
   3306             if (!f.canRead()) {
   3307                 Slog.w(TAG, "Preferred apps file " + f + " cannot be read");
   3308                 continue;
   3309             }
   3310 
   3311             if (PackageManagerService.DEBUG_PREFERRED) Log.d(TAG, "Reading default preferred " + f);
   3312             InputStream str = null;
   3313             try {
   3314                 str = new BufferedInputStream(new FileInputStream(f));
   3315                 XmlPullParser parser = Xml.newPullParser();
   3316                 parser.setInput(str, null);
   3317 
   3318                 int type;
   3319                 while ((type = parser.next()) != XmlPullParser.START_TAG
   3320                         && type != XmlPullParser.END_DOCUMENT) {
   3321                     ;
   3322                 }
   3323 
   3324                 if (type != XmlPullParser.START_TAG) {
   3325                     Slog.w(TAG, "Preferred apps file " + f + " does not have start tag");
   3326                     continue;
   3327                 }
   3328                 if (!"preferred-activities".equals(parser.getName())) {
   3329                     Slog.w(TAG, "Preferred apps file " + f
   3330                             + " does not start with 'preferred-activities'");
   3331                     continue;
   3332                 }
   3333                 readDefaultPreferredActivitiesLPw(service, parser, userId);
   3334             } catch (XmlPullParserException e) {
   3335                 Slog.w(TAG, "Error reading apps file " + f, e);
   3336             } catch (IOException e) {
   3337                 Slog.w(TAG, "Error reading apps file " + f, e);
   3338             } finally {
   3339                 if (str != null) {
   3340                     try {
   3341                         str.close();
   3342                     } catch (IOException e) {
   3343                     }
   3344                 }
   3345             }
   3346         }
   3347     }
   3348 
   3349     private void applyDefaultPreferredActivityLPw(PackageManagerService service,
   3350             IntentFilter tmpPa, ComponentName cn, int userId) {
   3351         // The initial preferences only specify the target activity
   3352         // component and intent-filter, not the set of matches.  So we
   3353         // now need to query for the matches to build the correct
   3354         // preferred activity entry.
   3355         if (PackageManagerService.DEBUG_PREFERRED) {
   3356             Log.d(TAG, "Processing preferred:");
   3357             tmpPa.dump(new LogPrinter(Log.DEBUG, TAG), "  ");
   3358         }
   3359         Intent intent = new Intent();
   3360         int flags = PackageManager.MATCH_DIRECT_BOOT_AWARE
   3361                 | PackageManager.MATCH_DIRECT_BOOT_UNAWARE;
   3362         intent.setAction(tmpPa.getAction(0));
   3363         for (int i=0; i<tmpPa.countCategories(); i++) {
   3364             String cat = tmpPa.getCategory(i);
   3365             if (cat.equals(Intent.CATEGORY_DEFAULT)) {
   3366                 flags |= MATCH_DEFAULT_ONLY;
   3367             } else {
   3368                 intent.addCategory(cat);
   3369             }
   3370         }
   3371 
   3372         boolean doNonData = true;
   3373         boolean hasSchemes = false;
   3374 
   3375         for (int ischeme=0; ischeme<tmpPa.countDataSchemes(); ischeme++) {
   3376             boolean doScheme = true;
   3377             String scheme = tmpPa.getDataScheme(ischeme);
   3378             if (scheme != null && !scheme.isEmpty()) {
   3379                 hasSchemes = true;
   3380             }
   3381             for (int issp=0; issp<tmpPa.countDataSchemeSpecificParts(); issp++) {
   3382                 Uri.Builder builder = new Uri.Builder();
   3383                 builder.scheme(scheme);
   3384                 PatternMatcher ssp = tmpPa.getDataSchemeSpecificPart(issp);
   3385                 builder.opaquePart(ssp.getPath());
   3386                 Intent finalIntent = new Intent(intent);
   3387                 finalIntent.setData(builder.build());
   3388                 applyDefaultPreferredActivityLPw(service, finalIntent, flags, cn,
   3389                         scheme, ssp, null, null, userId);
   3390                 doScheme = false;
   3391             }
   3392             for (int iauth=0; iauth<tmpPa.countDataAuthorities(); iauth++) {
   3393                 boolean doAuth = true;
   3394                 IntentFilter.AuthorityEntry auth = tmpPa.getDataAuthority(iauth);
   3395                 for (int ipath=0; ipath<tmpPa.countDataPaths(); ipath++) {
   3396                     Uri.Builder builder = new Uri.Builder();
   3397                     builder.scheme(scheme);
   3398                     if (auth.getHost() != null) {
   3399                         builder.authority(auth.getHost());
   3400                     }
   3401                     PatternMatcher path = tmpPa.getDataPath(ipath);
   3402                     builder.path(path.getPath());
   3403                     Intent finalIntent = new Intent(intent);
   3404                     finalIntent.setData(builder.build());
   3405                     applyDefaultPreferredActivityLPw(service, finalIntent, flags, cn,
   3406                             scheme, null, auth, path, userId);
   3407                     doAuth = doScheme = false;
   3408                 }
   3409                 if (doAuth) {
   3410                     Uri.Builder builder = new Uri.Builder();
   3411                     builder.scheme(scheme);
   3412                     if (auth.getHost() != null) {
   3413                         builder.authority(auth.getHost());
   3414                     }
   3415                     Intent finalIntent = new Intent(intent);
   3416                     finalIntent.setData(builder.build());
   3417                     applyDefaultPreferredActivityLPw(service, finalIntent, flags, cn,
   3418                             scheme, null, auth, null, userId);
   3419                     doScheme = false;
   3420                 }
   3421             }
   3422             if (doScheme) {
   3423                 Uri.Builder builder = new Uri.Builder();
   3424                 builder.scheme(scheme);
   3425                 Intent finalIntent = new Intent(intent);
   3426                 finalIntent.setData(builder.build());
   3427                 applyDefaultPreferredActivityLPw(service, finalIntent, flags, cn,
   3428                         scheme, null, null, null, userId);
   3429             }
   3430             doNonData = false;
   3431         }
   3432 
   3433         for (int idata=0; idata<tmpPa.countDataTypes(); idata++) {
   3434             String mimeType = tmpPa.getDataType(idata);
   3435             if (hasSchemes) {
   3436                 Uri.Builder builder = new Uri.Builder();
   3437                 for (int ischeme=0; ischeme<tmpPa.countDataSchemes(); ischeme++) {
   3438                     String scheme = tmpPa.getDataScheme(ischeme);
   3439                     if (scheme != null && !scheme.isEmpty()) {
   3440                         Intent finalIntent = new Intent(intent);
   3441                         builder.scheme(scheme);
   3442                         finalIntent.setDataAndType(builder.build(), mimeType);
   3443                         applyDefaultPreferredActivityLPw(service, finalIntent, flags, cn,
   3444                                 scheme, null, null, null, userId);
   3445                     }
   3446                 }
   3447             } else {
   3448                 Intent finalIntent = new Intent(intent);
   3449                 finalIntent.setType(mimeType);
   3450                 applyDefaultPreferredActivityLPw(service, finalIntent, flags, cn,
   3451                         null, null, null, null, userId);
   3452             }
   3453             doNonData = false;
   3454         }
   3455 
   3456         if (doNonData) {
   3457             applyDefaultPreferredActivityLPw(service, intent, flags, cn,
   3458                     null, null, null, null, userId);
   3459         }
   3460     }
   3461 
   3462     private void applyDefaultPreferredActivityLPw(PackageManagerService service,
   3463             Intent intent, int flags, ComponentName cn, String scheme, PatternMatcher ssp,
   3464             IntentFilter.AuthorityEntry auth, PatternMatcher path, int userId) {
   3465         flags = service.updateFlagsForResolve(flags, userId, intent, Binder.getCallingUid(), false);
   3466         List<ResolveInfo> ri = service.mActivities.queryIntent(intent,
   3467                 intent.getType(), flags, 0);
   3468         if (PackageManagerService.DEBUG_PREFERRED) Log.d(TAG, "Queried " + intent
   3469                 + " results: " + ri);
   3470         int systemMatch = 0;
   3471         int thirdPartyMatch = 0;
   3472         if (ri != null && ri.size() > 1) {
   3473             boolean haveAct = false;
   3474             ComponentName haveNonSys = null;
   3475             ComponentName[] set = new ComponentName[ri.size()];
   3476             for (int i=0; i<ri.size(); i++) {
   3477                 ActivityInfo ai = ri.get(i).activityInfo;
   3478                 set[i] = new ComponentName(ai.packageName, ai.name);
   3479                 if ((ai.applicationInfo.flags&ApplicationInfo.FLAG_SYSTEM) == 0) {
   3480                     if (ri.get(i).match >= thirdPartyMatch) {
   3481                         // Keep track of the best match we find of all third
   3482                         // party apps, for use later to determine if we actually
   3483                         // want to set a preferred app for this intent.
   3484                         if (PackageManagerService.DEBUG_PREFERRED) Log.d(TAG, "Result "
   3485                                 + ai.packageName + "/" + ai.name + ": non-system!");
   3486                         haveNonSys = set[i];
   3487                         break;
   3488                     }
   3489                 } else if (cn.getPackageName().equals(ai.packageName)
   3490                         && cn.getClassName().equals(ai.name)) {
   3491                     if (PackageManagerService.DEBUG_PREFERRED) Log.d(TAG, "Result "
   3492                             + ai.packageName + "/" + ai.name + ": default!");
   3493                     haveAct = true;
   3494                     systemMatch = ri.get(i).match;
   3495                 } else {
   3496                     if (PackageManagerService.DEBUG_PREFERRED) Log.d(TAG, "Result "
   3497                             + ai.packageName + "/" + ai.name + ": skipped");
   3498                 }
   3499             }
   3500             if (haveNonSys != null && thirdPartyMatch < systemMatch) {
   3501                 // If we have a matching third party app, but its match is not as
   3502                 // good as the built-in system app, then we don't want to actually
   3503                 // consider it a match because presumably the built-in app is still
   3504                 // the thing we want users to see by default.
   3505                 haveNonSys = null;
   3506             }
   3507             if (haveAct && haveNonSys == null) {
   3508                 IntentFilter filter = new IntentFilter();
   3509                 if (intent.getAction() != null) {
   3510                     filter.addAction(intent.getAction());
   3511                 }
   3512                 if (intent.getCategories() != null) {
   3513                     for (String cat : intent.getCategories()) {
   3514                         filter.addCategory(cat);
   3515                     }
   3516                 }
   3517                 if ((flags & MATCH_DEFAULT_ONLY) != 0) {
   3518                     filter.addCategory(Intent.CATEGORY_DEFAULT);
   3519                 }
   3520                 if (scheme != null) {
   3521                     filter.addDataScheme(scheme);
   3522                 }
   3523                 if (ssp != null) {
   3524                     filter.addDataSchemeSpecificPart(ssp.getPath(), ssp.getType());
   3525                 }
   3526                 if (auth != null) {
   3527                     filter.addDataAuthority(auth);
   3528                 }
   3529                 if (path != null) {
   3530                     filter.addDataPath(path);
   3531                 }
   3532                 if (intent.getType() != null) {
   3533                     try {
   3534                         filter.addDataType(intent.getType());
   3535                     } catch (IntentFilter.MalformedMimeTypeException ex) {
   3536                         Slog.w(TAG, "Malformed mimetype " + intent.getType() + " for " + cn);
   3537                     }
   3538                 }
   3539                 PreferredActivity pa = new PreferredActivity(filter, systemMatch, set, cn, true);
   3540                 editPreferredActivitiesLPw(userId).addFilter(pa);
   3541             } else if (haveNonSys == null) {
   3542                 StringBuilder sb = new StringBuilder();
   3543                 sb.append("No component ");
   3544                 sb.append(cn.flattenToShortString());
   3545                 sb.append(" found setting preferred ");
   3546                 sb.append(intent);
   3547                 sb.append("; possible matches are ");
   3548                 for (int i=0; i<set.length; i++) {
   3549                     if (i > 0) sb.append(", ");
   3550                     sb.append(set[i].flattenToShortString());
   3551                 }
   3552                 Slog.w(TAG, sb.toString());
   3553             } else {
   3554                 Slog.i(TAG, "Not setting preferred " + intent + "; found third party match "
   3555                         + haveNonSys.flattenToShortString());
   3556             }
   3557         } else {
   3558             Slog.w(TAG, "No potential matches found for " + intent + " while setting preferred "
   3559                     + cn.flattenToShortString());
   3560         }
   3561     }
   3562 
   3563     private void readDefaultPreferredActivitiesLPw(PackageManagerService service,
   3564             XmlPullParser parser, int userId)
   3565             throws XmlPullParserException, IOException {
   3566         int outerDepth = parser.getDepth();
   3567         int type;
   3568         while ((type = parser.next()) != XmlPullParser.END_DOCUMENT
   3569                 && (type != XmlPullParser.END_TAG || parser.getDepth() > outerDepth)) {
   3570             if (type == XmlPullParser.END_TAG || type == XmlPullParser.TEXT) {
   3571                 continue;
   3572             }
   3573 
   3574             String tagName = parser.getName();
   3575             if (tagName.equals(TAG_ITEM)) {
   3576                 PreferredActivity tmpPa = new PreferredActivity(parser);
   3577                 if (tmpPa.mPref.getParseError() == null) {
   3578                     applyDefaultPreferredActivityLPw(service, tmpPa, tmpPa.mPref.mComponent,
   3579                             userId);
   3580                 } else {
   3581                     PackageManagerService.reportSettingsProblem(Log.WARN,
   3582                             "Error in package manager settings: <preferred-activity> "
   3583                                     + tmpPa.mPref.getParseError() + " at "
   3584                                     + parser.getPositionDescription());
   3585                 }
   3586             } else {
   3587                 PackageManagerService.reportSettingsProblem(Log.WARN,
   3588                         "Unknown element under <preferred-activities>: " + parser.getName());
   3589                 XmlUtils.skipCurrentTag(parser);
   3590             }
   3591         }
   3592     }
   3593 
   3594     private int readInt(XmlPullParser parser, String ns, String name, int defValue) {
   3595         String v = parser.getAttributeValue(ns, name);
   3596         try {
   3597             if (v == null) {
   3598                 return defValue;
   3599             }
   3600             return Integer.parseInt(v);
   3601         } catch (NumberFormatException e) {
   3602             PackageManagerService.reportSettingsProblem(Log.WARN,
   3603                     "Error in package manager settings: attribute " + name
   3604                             + " has bad integer value " + v + " at "
   3605                             + parser.getPositionDescription());
   3606         }
   3607         return defValue;
   3608     }
   3609 
   3610     private void readPermissionsLPw(ArrayMap<String, BasePermission> out, XmlPullParser parser)
   3611             throws IOException, XmlPullParserException {
   3612         int outerDepth = parser.getDepth();
   3613         int type;
   3614         while ((type = parser.next()) != XmlPullParser.END_DOCUMENT
   3615                 && (type != XmlPullParser.END_TAG || parser.getDepth() > outerDepth)) {
   3616             if (type == XmlPullParser.END_TAG || type == XmlPullParser.TEXT) {
   3617                 continue;
   3618             }
   3619 
   3620             final String tagName = parser.getName();
   3621             if (tagName.equals(TAG_ITEM)) {
   3622                 final String name = parser.getAttributeValue(null, ATTR_NAME);
   3623                 final String sourcePackage = parser.getAttributeValue(null, "package");
   3624                 final String ptype = parser.getAttributeValue(null, "type");
   3625                 if (name != null && sourcePackage != null) {
   3626                     final boolean dynamic = "dynamic".equals(ptype);
   3627                     BasePermission bp = out.get(name);
   3628                     // If the permission is builtin, do not clobber it.
   3629                     if (bp == null || bp.type != BasePermission.TYPE_BUILTIN) {
   3630                         bp = new BasePermission(name.intern(), sourcePackage,
   3631                                 dynamic ? BasePermission.TYPE_DYNAMIC : BasePermission.TYPE_NORMAL);
   3632                     }
   3633                     bp.protectionLevel = readInt(parser, null, "protection",
   3634                             PermissionInfo.PROTECTION_NORMAL);
   3635                     bp.protectionLevel = PermissionInfo.fixProtectionLevel(bp.protectionLevel);
   3636                     if (dynamic) {
   3637                         PermissionInfo pi = new PermissionInfo();
   3638                         pi.packageName = sourcePackage.intern();
   3639                         pi.name = name.intern();
   3640                         pi.icon = readInt(parser, null, "icon", 0);
   3641                         pi.nonLocalizedLabel = parser.getAttributeValue(null, "label");
   3642                         pi.protectionLevel = bp.protectionLevel;
   3643                         bp.pendingInfo = pi;
   3644                     }
   3645                     out.put(bp.name, bp);
   3646                 } else {
   3647                     PackageManagerService.reportSettingsProblem(Log.WARN,
   3648                             "Error in package manager settings: permissions has" + " no name at "
   3649                                     + parser.getPositionDescription());
   3650                 }
   3651             } else {
   3652                 PackageManagerService.reportSettingsProblem(Log.WARN,
   3653                         "Unknown element reading permissions: " + parser.getName() + " at "
   3654                                 + parser.getPositionDescription());
   3655             }
   3656             XmlUtils.skipCurrentTag(parser);
   3657         }
   3658     }
   3659 
   3660     private void readDisabledSysPackageLPw(XmlPullParser parser) throws XmlPullParserException,
   3661             IOException {
   3662         String name = parser.getAttributeValue(null, ATTR_NAME);
   3663         String realName = parser.getAttributeValue(null, "realName");
   3664         String codePathStr = parser.getAttributeValue(null, "codePath");
   3665         String resourcePathStr = parser.getAttributeValue(null, "resourcePath");
   3666 
   3667         String legacyCpuAbiStr = parser.getAttributeValue(null, "requiredCpuAbi");
   3668         String legacyNativeLibraryPathStr = parser.getAttributeValue(null, "nativeLibraryPath");
   3669 
   3670         String parentPackageName = parser.getAttributeValue(null, "parentPackageName");
   3671 
   3672         String primaryCpuAbiStr = parser.getAttributeValue(null, "primaryCpuAbi");
   3673         String secondaryCpuAbiStr = parser.getAttributeValue(null, "secondaryCpuAbi");
   3674         String cpuAbiOverrideStr = parser.getAttributeValue(null, "cpuAbiOverride");
   3675 
   3676         if (primaryCpuAbiStr == null && legacyCpuAbiStr != null) {
   3677             primaryCpuAbiStr = legacyCpuAbiStr;
   3678         }
   3679 
   3680         if (resourcePathStr == null) {
   3681             resourcePathStr = codePathStr;
   3682         }
   3683         String version = parser.getAttributeValue(null, "version");
   3684         int versionCode = 0;
   3685         if (version != null) {
   3686             try {
   3687                 versionCode = Integer.parseInt(version);
   3688             } catch (NumberFormatException e) {
   3689             }
   3690         }
   3691 
   3692         int pkgFlags = 0;
   3693         int pkgPrivateFlags = 0;
   3694         pkgFlags |= ApplicationInfo.FLAG_SYSTEM;
   3695         final File codePathFile = new File(codePathStr);
   3696         if (PackageManagerService.locationIsPrivileged(codePathFile)) {
   3697             pkgPrivateFlags |= ApplicationInfo.PRIVATE_FLAG_PRIVILEGED;
   3698         }
   3699         PackageSetting ps = new PackageSetting(name, realName, codePathFile,
   3700                 new File(resourcePathStr), legacyNativeLibraryPathStr, primaryCpuAbiStr,
   3701                 secondaryCpuAbiStr, cpuAbiOverrideStr, versionCode, pkgFlags, pkgPrivateFlags,
   3702                 parentPackageName, null /*childPackageNames*/, 0 /*sharedUserId*/, null, null);
   3703         String timeStampStr = parser.getAttributeValue(null, "ft");
   3704         if (timeStampStr != null) {
   3705             try {
   3706                 long timeStamp = Long.parseLong(timeStampStr, 16);
   3707                 ps.setTimeStamp(timeStamp);
   3708             } catch (NumberFormatException e) {
   3709             }
   3710         } else {
   3711             timeStampStr = parser.getAttributeValue(null, "ts");
   3712             if (timeStampStr != null) {
   3713                 try {
   3714                     long timeStamp = Long.parseLong(timeStampStr);
   3715                     ps.setTimeStamp(timeStamp);
   3716                 } catch (NumberFormatException e) {
   3717                 }
   3718             }
   3719         }
   3720         timeStampStr = parser.getAttributeValue(null, "it");
   3721         if (timeStampStr != null) {
   3722             try {
   3723                 ps.firstInstallTime = Long.parseLong(timeStampStr, 16);
   3724             } catch (NumberFormatException e) {
   3725             }
   3726         }
   3727         timeStampStr = parser.getAttributeValue(null, "ut");
   3728         if (timeStampStr != null) {
   3729             try {
   3730                 ps.lastUpdateTime = Long.parseLong(timeStampStr, 16);
   3731             } catch (NumberFormatException e) {
   3732             }
   3733         }
   3734         String idStr = parser.getAttributeValue(null, "userId");
   3735         ps.appId = idStr != null ? Integer.parseInt(idStr) : 0;
   3736         if (ps.appId <= 0) {
   3737             String sharedIdStr = parser.getAttributeValue(null, "sharedUserId");
   3738             ps.appId = sharedIdStr != null ? Integer.parseInt(sharedIdStr) : 0;
   3739         }
   3740 
   3741         int outerDepth = parser.getDepth();
   3742         int type;
   3743         while ((type = parser.next()) != XmlPullParser.END_DOCUMENT
   3744                 && (type != XmlPullParser.END_TAG || parser.getDepth() > outerDepth)) {
   3745             if (type == XmlPullParser.END_TAG || type == XmlPullParser.TEXT) {
   3746                 continue;
   3747             }
   3748 
   3749             if (parser.getName().equals(TAG_PERMISSIONS)) {
   3750                 readInstallPermissionsLPr(parser, ps.getPermissionsState());
   3751             } else if (parser.getName().equals(TAG_CHILD_PACKAGE)) {
   3752                 String childPackageName = parser.getAttributeValue(null, ATTR_NAME);
   3753                 if (ps.childPackageNames == null) {
   3754                     ps.childPackageNames = new ArrayList<>();
   3755                 }
   3756                 ps.childPackageNames.add(childPackageName);
   3757             } else if (parser.getName().equals(TAG_USES_STATIC_LIB)) {
   3758                 readUsesStaticLibLPw(parser, ps);
   3759             } else {
   3760                 PackageManagerService.reportSettingsProblem(Log.WARN,
   3761                         "Unknown element under <updated-package>: " + parser.getName());
   3762                 XmlUtils.skipCurrentTag(parser);
   3763             }
   3764         }
   3765 
   3766         mDisabledSysPackages.put(name, ps);
   3767     }
   3768 
   3769     private static int PRE_M_APP_INFO_FLAG_HIDDEN = 1<<27;
   3770     private static int PRE_M_APP_INFO_FLAG_CANT_SAVE_STATE = 1<<28;
   3771     private static int PRE_M_APP_INFO_FLAG_FORWARD_LOCK = 1<<29;
   3772     private static int PRE_M_APP_INFO_FLAG_PRIVILEGED = 1<<30;
   3773 
   3774     private void readPackageLPw(XmlPullParser parser) throws XmlPullParserException, IOException {
   3775         String name = null;
   3776         String realName = null;
   3777         String idStr = null;
   3778         String sharedIdStr = null;
   3779         String codePathStr = null;
   3780         String resourcePathStr = null;
   3781         String legacyCpuAbiString = null;
   3782         String legacyNativeLibraryPathStr = null;
   3783         String primaryCpuAbiString = null;
   3784         String secondaryCpuAbiString = null;
   3785         String cpuAbiOverrideString = null;
   3786         String systemStr = null;
   3787         String installerPackageName = null;
   3788         String isOrphaned = null;
   3789         String volumeUuid = null;
   3790         String categoryHintString = null;
   3791         String updateAvailable = null;
   3792         int categoryHint = ApplicationInfo.CATEGORY_UNDEFINED;
   3793         String uidError = null;
   3794         int pkgFlags = 0;
   3795         int pkgPrivateFlags = 0;
   3796         long timeStamp = 0;
   3797         long firstInstallTime = 0;
   3798         long lastUpdateTime = 0;
   3799         PackageSetting packageSetting = null;
   3800         String version = null;
   3801         int versionCode = 0;
   3802         String parentPackageName;
   3803         try {
   3804             name = parser.getAttributeValue(null, ATTR_NAME);
   3805             realName = parser.getAttributeValue(null, "realName");
   3806             idStr = parser.getAttributeValue(null, "userId");
   3807             uidError = parser.getAttributeValue(null, "uidError");
   3808             sharedIdStr = parser.getAttributeValue(null, "sharedUserId");
   3809             codePathStr = parser.getAttributeValue(null, "codePath");
   3810             resourcePathStr = parser.getAttributeValue(null, "resourcePath");
   3811 
   3812             legacyCpuAbiString = parser.getAttributeValue(null, "requiredCpuAbi");
   3813 
   3814             parentPackageName = parser.getAttributeValue(null, "parentPackageName");
   3815 
   3816             legacyNativeLibraryPathStr = parser.getAttributeValue(null, "nativeLibraryPath");
   3817             primaryCpuAbiString = parser.getAttributeValue(null, "primaryCpuAbi");
   3818             secondaryCpuAbiString = parser.getAttributeValue(null, "secondaryCpuAbi");
   3819             cpuAbiOverrideString = parser.getAttributeValue(null, "cpuAbiOverride");
   3820             updateAvailable = parser.getAttributeValue(null, "updateAvailable");
   3821 
   3822             if (primaryCpuAbiString == null && legacyCpuAbiString != null) {
   3823                 primaryCpuAbiString = legacyCpuAbiString;
   3824             }
   3825 
   3826             version = parser.getAttributeValue(null, "version");
   3827             if (version != null) {
   3828                 try {
   3829                     versionCode = Integer.parseInt(version);
   3830                 } catch (NumberFormatException e) {
   3831                 }
   3832             }
   3833             installerPackageName = parser.getAttributeValue(null, "installer");
   3834             isOrphaned = parser.getAttributeValue(null, "isOrphaned");
   3835             volumeUuid = parser.getAttributeValue(null, "volumeUuid");
   3836             categoryHintString = parser.getAttributeValue(null, "categoryHint");
   3837             if (categoryHintString != null) {
   3838                 try {
   3839                     categoryHint = Integer.parseInt(categoryHintString);
   3840                 } catch (NumberFormatException e) {
   3841                 }
   3842             }
   3843 
   3844             systemStr = parser.getAttributeValue(null, "publicFlags");
   3845             if (systemStr != null) {
   3846                 try {
   3847                     pkgFlags = Integer.parseInt(systemStr);
   3848                 } catch (NumberFormatException e) {
   3849                 }
   3850                 systemStr = parser.getAttributeValue(null, "privateFlags");
   3851                 if (systemStr != null) {
   3852                     try {
   3853                         pkgPrivateFlags = Integer.parseInt(systemStr);
   3854                     } catch (NumberFormatException e) {
   3855                     }
   3856                 }
   3857             } else {
   3858                 // Pre-M -- both public and private flags were stored in one "flags" field.
   3859                 systemStr = parser.getAttributeValue(null, "flags");
   3860                 if (systemStr != null) {
   3861                     try {
   3862                         pkgFlags = Integer.parseInt(systemStr);
   3863                     } catch (NumberFormatException e) {
   3864                     }
   3865                     if ((pkgFlags & PRE_M_APP_INFO_FLAG_HIDDEN) != 0) {
   3866                         pkgPrivateFlags |= ApplicationInfo.PRIVATE_FLAG_HIDDEN;
   3867                     }
   3868                     if ((pkgFlags & PRE_M_APP_INFO_FLAG_CANT_SAVE_STATE) != 0) {
   3869                         pkgPrivateFlags |= ApplicationInfo.PRIVATE_FLAG_CANT_SAVE_STATE;
   3870                     }
   3871                     if ((pkgFlags & PRE_M_APP_INFO_FLAG_FORWARD_LOCK) != 0) {
   3872                         pkgPrivateFlags |= ApplicationInfo.PRIVATE_FLAG_FORWARD_LOCK;
   3873                     }
   3874                     if ((pkgFlags & PRE_M_APP_INFO_FLAG_PRIVILEGED) != 0) {
   3875                         pkgPrivateFlags |= ApplicationInfo.PRIVATE_FLAG_PRIVILEGED;
   3876                     }
   3877                     pkgFlags &= ~(PRE_M_APP_INFO_FLAG_HIDDEN
   3878                             | PRE_M_APP_INFO_FLAG_CANT_SAVE_STATE
   3879                             | PRE_M_APP_INFO_FLAG_FORWARD_LOCK
   3880                             | PRE_M_APP_INFO_FLAG_PRIVILEGED);
   3881                 } else {
   3882                     // For backward compatibility
   3883                     systemStr = parser.getAttributeValue(null, "system");
   3884                     if (systemStr != null) {
   3885                         pkgFlags |= ("true".equalsIgnoreCase(systemStr)) ? ApplicationInfo.FLAG_SYSTEM
   3886                                 : 0;
   3887                     } else {
   3888                         // Old settings that don't specify system... just treat
   3889                         // them as system, good enough.
   3890                         pkgFlags |= ApplicationInfo.FLAG_SYSTEM;
   3891                     }
   3892                 }
   3893             }
   3894             String timeStampStr = parser.getAttributeValue(null, "ft");
   3895             if (timeStampStr != null) {
   3896                 try {
   3897                     timeStamp = Long.parseLong(timeStampStr, 16);
   3898                 } catch (NumberFormatException e) {
   3899                 }
   3900             } else {
   3901                 timeStampStr = parser.getAttributeValue(null, "ts");
   3902                 if (timeStampStr != null) {
   3903                     try {
   3904                         timeStamp = Long.parseLong(timeStampStr);
   3905                     } catch (NumberFormatException e) {
   3906                     }
   3907                 }
   3908             }
   3909             timeStampStr = parser.getAttributeValue(null, "it");
   3910             if (timeStampStr != null) {
   3911                 try {
   3912                     firstInstallTime = Long.parseLong(timeStampStr, 16);
   3913                 } catch (NumberFormatException e) {
   3914                 }
   3915             }
   3916             timeStampStr = parser.getAttributeValue(null, "ut");
   3917             if (timeStampStr != null) {
   3918                 try {
   3919                     lastUpdateTime = Long.parseLong(timeStampStr, 16);
   3920                 } catch (NumberFormatException e) {
   3921                 }
   3922             }
   3923             if (PackageManagerService.DEBUG_SETTINGS)
   3924                 Log.v(PackageManagerService.TAG, "Reading package: " + name + " userId=" + idStr
   3925                         + " sharedUserId=" + sharedIdStr);
   3926             final int userId = idStr != null ? Integer.parseInt(idStr) : 0;
   3927             final int sharedUserId = sharedIdStr != null ? Integer.parseInt(sharedIdStr) : 0;
   3928             if (resourcePathStr == null) {
   3929                 resourcePathStr = codePathStr;
   3930             }
   3931             if (realName != null) {
   3932                 realName = realName.intern();
   3933             }
   3934             if (name == null) {
   3935                 PackageManagerService.reportSettingsProblem(Log.WARN,
   3936                         "Error in package manager settings: <package> has no name at "
   3937                                 + parser.getPositionDescription());
   3938             } else if (codePathStr == null) {
   3939                 PackageManagerService.reportSettingsProblem(Log.WARN,
   3940                         "Error in package manager settings: <package> has no codePath at "
   3941                                 + parser.getPositionDescription());
   3942             } else if (userId > 0) {
   3943                 packageSetting = addPackageLPw(name.intern(), realName, new File(codePathStr),
   3944                         new File(resourcePathStr), legacyNativeLibraryPathStr, primaryCpuAbiString,
   3945                         secondaryCpuAbiString, cpuAbiOverrideString, userId, versionCode, pkgFlags,
   3946                         pkgPrivateFlags, parentPackageName, null /*childPackageNames*/,
   3947                         null /*usesStaticLibraries*/, null /*usesStaticLibraryVersions*/);
   3948                 if (PackageManagerService.DEBUG_SETTINGS)
   3949                     Log.i(PackageManagerService.TAG, "Reading package " + name + ": userId="
   3950                             + userId + " pkg=" + packageSetting);
   3951                 if (packageSetting == null) {
   3952                     PackageManagerService.reportSettingsProblem(Log.ERROR, "Failure adding uid "
   3953                             + userId + " while parsing settings at "
   3954                             + parser.getPositionDescription());
   3955                 } else {
   3956                     packageSetting.setTimeStamp(timeStamp);
   3957                     packageSetting.firstInstallTime = firstInstallTime;
   3958                     packageSetting.lastUpdateTime = lastUpdateTime;
   3959                 }
   3960             } else if (sharedIdStr != null) {
   3961                 if (sharedUserId > 0) {
   3962                     packageSetting = new PackageSetting(name.intern(), realName, new File(
   3963                             codePathStr), new File(resourcePathStr), legacyNativeLibraryPathStr,
   3964                             primaryCpuAbiString, secondaryCpuAbiString, cpuAbiOverrideString,
   3965                             versionCode, pkgFlags, pkgPrivateFlags, parentPackageName,
   3966                             null /*childPackageNames*/, sharedUserId,
   3967                             null /*usesStaticLibraries*/, null /*usesStaticLibraryVersions*/);
   3968                     packageSetting.setTimeStamp(timeStamp);
   3969                     packageSetting.firstInstallTime = firstInstallTime;
   3970                     packageSetting.lastUpdateTime = lastUpdateTime;
   3971                     mPendingPackages.add(packageSetting);
   3972                     if (PackageManagerService.DEBUG_SETTINGS)
   3973                         Log.i(PackageManagerService.TAG, "Reading package " + name
   3974                                 + ": sharedUserId=" + sharedUserId + " pkg=" + packageSetting);
   3975                 } else {
   3976                     PackageManagerService.reportSettingsProblem(Log.WARN,
   3977                             "Error in package manager settings: package " + name
   3978                                     + " has bad sharedId " + sharedIdStr + " at "
   3979                                     + parser.getPositionDescription());
   3980                 }
   3981             } else {
   3982                 PackageManagerService.reportSettingsProblem(Log.WARN,
   3983                         "Error in package manager settings: package " + name + " has bad userId "
   3984                                 + idStr + " at " + parser.getPositionDescription());
   3985             }
   3986         } catch (NumberFormatException e) {
   3987             PackageManagerService.reportSettingsProblem(Log.WARN,
   3988                     "Error in package manager settings: package " + name + " has bad userId "
   3989                             + idStr + " at " + parser.getPositionDescription());
   3990         }
   3991         if (packageSetting != null) {
   3992             packageSetting.uidError = "true".equals(uidError);
   3993             packageSetting.installerPackageName = installerPackageName;
   3994             packageSetting.isOrphaned = "true".equals(isOrphaned);
   3995             packageSetting.volumeUuid = volumeUuid;
   3996             packageSetting.categoryHint = categoryHint;
   3997             packageSetting.legacyNativeLibraryPathString = legacyNativeLibraryPathStr;
   3998             packageSetting.primaryCpuAbiString = primaryCpuAbiString;
   3999             packageSetting.secondaryCpuAbiString = secondaryCpuAbiString;
   4000             packageSetting.updateAvailable = "true".equals(updateAvailable);
   4001             // Handle legacy string here for single-user mode
   4002             final String enabledStr = parser.getAttributeValue(null, ATTR_ENABLED);
   4003             if (enabledStr != null) {
   4004                 try {
   4005                     packageSetting.setEnabled(Integer.parseInt(enabledStr), 0 /* userId */, null);
   4006                 } catch (NumberFormatException e) {
   4007                     if (enabledStr.equalsIgnoreCase("true")) {
   4008                         packageSetting.setEnabled(COMPONENT_ENABLED_STATE_ENABLED, 0, null);
   4009                     } else if (enabledStr.equalsIgnoreCase("false")) {
   4010                         packageSetting.setEnabled(COMPONENT_ENABLED_STATE_DISABLED, 0, null);
   4011                     } else if (enabledStr.equalsIgnoreCase("default")) {
   4012                         packageSetting.setEnabled(COMPONENT_ENABLED_STATE_DEFAULT, 0, null);
   4013                     } else {
   4014                         PackageManagerService.reportSettingsProblem(Log.WARN,
   4015                                 "Error in package manager settings: package " + name
   4016                                         + " has bad enabled value: " + idStr + " at "
   4017                                         + parser.getPositionDescription());
   4018                     }
   4019                 }
   4020             } else {
   4021                 packageSetting.setEnabled(COMPONENT_ENABLED_STATE_DEFAULT, 0, null);
   4022             }
   4023 
   4024             if (installerPackageName != null) {
   4025                 mInstallerPackages.add(installerPackageName);
   4026             }
   4027 
   4028             final String installStatusStr = parser.getAttributeValue(null, "installStatus");
   4029             if (installStatusStr != null) {
   4030                 if (installStatusStr.equalsIgnoreCase("false")) {
   4031                     packageSetting.installStatus = PackageSettingBase.PKG_INSTALL_INCOMPLETE;
   4032                 } else {
   4033                     packageSetting.installStatus = PackageSettingBase.PKG_INSTALL_COMPLETE;
   4034                 }
   4035             }
   4036 
   4037             int outerDepth = parser.getDepth();
   4038             int type;
   4039             while ((type = parser.next()) != XmlPullParser.END_DOCUMENT
   4040                     && (type != XmlPullParser.END_TAG || parser.getDepth() > outerDepth)) {
   4041                 if (type == XmlPullParser.END_TAG || type == XmlPullParser.TEXT) {
   4042                     continue;
   4043                 }
   4044 
   4045                 String tagName = parser.getName();
   4046                 // Legacy
   4047                 if (tagName.equals(TAG_DISABLED_COMPONENTS)) {
   4048                     readDisabledComponentsLPw(packageSetting, parser, 0);
   4049                 } else if (tagName.equals(TAG_ENABLED_COMPONENTS)) {
   4050                     readEnabledComponentsLPw(packageSetting, parser, 0);
   4051                 } else if (tagName.equals("sigs")) {
   4052                     packageSetting.signatures.readXml(parser, mPastSignatures);
   4053                 } else if (tagName.equals(TAG_PERMISSIONS)) {
   4054                     readInstallPermissionsLPr(parser,
   4055                             packageSetting.getPermissionsState());
   4056                     packageSetting.installPermissionsFixed = true;
   4057                 } else if (tagName.equals("proper-signing-keyset")) {
   4058                     long id = Long.parseLong(parser.getAttributeValue(null, "identifier"));
   4059                     Integer refCt = mKeySetRefs.get(id);
   4060                     if (refCt != null) {
   4061                         mKeySetRefs.put(id, refCt + 1);
   4062                     } else {
   4063                         mKeySetRefs.put(id, 1);
   4064                     }
   4065                     packageSetting.keySetData.setProperSigningKeySet(id);
   4066                 } else if (tagName.equals("signing-keyset")) {
   4067                     // from v1 of keysetmanagerservice - no longer used
   4068                 } else if (tagName.equals("upgrade-keyset")) {
   4069                     long id = Long.parseLong(parser.getAttributeValue(null, "identifier"));
   4070                     packageSetting.keySetData.addUpgradeKeySetById(id);
   4071                 } else if (tagName.equals("defined-keyset")) {
   4072                     long id = Long.parseLong(parser.getAttributeValue(null, "identifier"));
   4073                     String alias = parser.getAttributeValue(null, "alias");
   4074                     Integer refCt = mKeySetRefs.get(id);
   4075                     if (refCt != null) {
   4076                         mKeySetRefs.put(id, refCt + 1);
   4077                     } else {
   4078                         mKeySetRefs.put(id, 1);
   4079                     }
   4080                     packageSetting.keySetData.addDefinedKeySet(id, alias);
   4081                 } else if (tagName.equals(TAG_DOMAIN_VERIFICATION)) {
   4082                     readDomainVerificationLPw(parser, packageSetting);
   4083                 } else if (tagName.equals(TAG_CHILD_PACKAGE)) {
   4084                     String childPackageName = parser.getAttributeValue(null, ATTR_NAME);
   4085                     if (packageSetting.childPackageNames == null) {
   4086                         packageSetting.childPackageNames = new ArrayList<>();
   4087                     }
   4088                     packageSetting.childPackageNames.add(childPackageName);
   4089                 } else {
   4090                     PackageManagerService.reportSettingsProblem(Log.WARN,
   4091                             "Unknown element under <package>: " + parser.getName());
   4092                     XmlUtils.skipCurrentTag(parser);
   4093                 }
   4094             }
   4095         } else {
   4096             XmlUtils.skipCurrentTag(parser);
   4097         }
   4098     }
   4099 
   4100     private void readDisabledComponentsLPw(PackageSettingBase packageSetting, XmlPullParser parser,
   4101             int userId) throws IOException, XmlPullParserException {
   4102         int outerDepth = parser.getDepth();
   4103         int type;
   4104         while ((type = parser.next()) != XmlPullParser.END_DOCUMENT
   4105                 && (type != XmlPullParser.END_TAG || parser.getDepth() > outerDepth)) {
   4106             if (type == XmlPullParser.END_TAG || type == XmlPullParser.TEXT) {
   4107                 continue;
   4108             }
   4109 
   4110             String tagName = parser.getName();
   4111             if (tagName.equals(TAG_ITEM)) {
   4112                 String name = parser.getAttributeValue(null, ATTR_NAME);
   4113                 if (name != null) {
   4114                     packageSetting.addDisabledComponent(name.intern(), userId);
   4115                 } else {
   4116                     PackageManagerService.reportSettingsProblem(Log.WARN,
   4117                             "Error in package manager settings: <disabled-components> has"
   4118                                     + " no name at " + parser.getPositionDescription());
   4119                 }
   4120             } else {
   4121                 PackageManagerService.reportSettingsProblem(Log.WARN,
   4122                         "Unknown element under <disabled-components>: " + parser.getName());
   4123             }
   4124             XmlUtils.skipCurrentTag(parser);
   4125         }
   4126     }
   4127 
   4128     private void readEnabledComponentsLPw(PackageSettingBase packageSetting, XmlPullParser parser,
   4129             int userId) throws IOException, XmlPullParserException {
   4130         int outerDepth = parser.getDepth();
   4131         int type;
   4132         while ((type = parser.next()) != XmlPullParser.END_DOCUMENT
   4133                 && (type != XmlPullParser.END_TAG || parser.getDepth() > outerDepth)) {
   4134             if (type == XmlPullParser.END_TAG || type == XmlPullParser.TEXT) {
   4135                 continue;
   4136             }
   4137 
   4138             String tagName = parser.getName();
   4139             if (tagName.equals(TAG_ITEM)) {
   4140                 String name = parser.getAttributeValue(null, ATTR_NAME);
   4141                 if (name != null) {
   4142                     packageSetting.addEnabledComponent(name.intern(), userId);
   4143                 } else {
   4144                     PackageManagerService.reportSettingsProblem(Log.WARN,
   4145                             "Error in package manager settings: <enabled-components> has"
   4146                                     + " no name at " + parser.getPositionDescription());
   4147                 }
   4148             } else {
   4149                 PackageManagerService.reportSettingsProblem(Log.WARN,
   4150                         "Unknown element under <enabled-components>: " + parser.getName());
   4151             }
   4152             XmlUtils.skipCurrentTag(parser);
   4153         }
   4154     }
   4155 
   4156     private void readSharedUserLPw(XmlPullParser parser) throws XmlPullParserException,IOException {
   4157         String name = null;
   4158         String idStr = null;
   4159         int pkgFlags = 0;
   4160         int pkgPrivateFlags = 0;
   4161         SharedUserSetting su = null;
   4162         try {
   4163             name = parser.getAttributeValue(null, ATTR_NAME);
   4164             idStr = parser.getAttributeValue(null, "userId");
   4165             int userId = idStr != null ? Integer.parseInt(idStr) : 0;
   4166             if ("true".equals(parser.getAttributeValue(null, "system"))) {
   4167                 pkgFlags |= ApplicationInfo.FLAG_SYSTEM;
   4168             }
   4169             if (name == null) {
   4170                 PackageManagerService.reportSettingsProblem(Log.WARN,
   4171                         "Error in package manager settings: <shared-user> has no name at "
   4172                                 + parser.getPositionDescription());
   4173             } else if (userId == 0) {
   4174                 PackageManagerService.reportSettingsProblem(Log.WARN,
   4175                         "Error in package manager settings: shared-user " + name
   4176                                 + " has bad userId " + idStr + " at "
   4177                                 + parser.getPositionDescription());
   4178             } else {
   4179                 if ((su = addSharedUserLPw(name.intern(), userId, pkgFlags, pkgPrivateFlags))
   4180                         == null) {
   4181                     PackageManagerService
   4182                             .reportSettingsProblem(Log.ERROR, "Occurred while parsing settings at "
   4183                                     + parser.getPositionDescription());
   4184                 }
   4185             }
   4186         } catch (NumberFormatException e) {
   4187             PackageManagerService.reportSettingsProblem(Log.WARN,
   4188                     "Error in package manager settings: package " + name + " has bad userId "
   4189                             + idStr + " at " + parser.getPositionDescription());
   4190         }
   4191 
   4192         if (su != null) {
   4193             int outerDepth = parser.getDepth();
   4194             int type;
   4195             while ((type = parser.next()) != XmlPullParser.END_DOCUMENT
   4196                     && (type != XmlPullParser.END_TAG || parser.getDepth() > outerDepth)) {
   4197                 if (type == XmlPullParser.END_TAG || type == XmlPullParser.TEXT) {
   4198                     continue;
   4199                 }
   4200 
   4201                 String tagName = parser.getName();
   4202                 if (tagName.equals("sigs")) {
   4203                     su.signatures.readXml(parser, mPastSignatures);
   4204                 } else if (tagName.equals("perms")) {
   4205                     readInstallPermissionsLPr(parser, su.getPermissionsState());
   4206                 } else {
   4207                     PackageManagerService.reportSettingsProblem(Log.WARN,
   4208                             "Unknown element under <shared-user>: " + parser.getName());
   4209                     XmlUtils.skipCurrentTag(parser);
   4210                 }
   4211             }
   4212         } else {
   4213             XmlUtils.skipCurrentTag(parser);
   4214         }
   4215     }
   4216 
   4217     void createNewUserLI(@NonNull PackageManagerService service, @NonNull Installer installer,
   4218             int userHandle, String[] disallowedPackages) {
   4219         String[] volumeUuids;
   4220         String[] names;
   4221         int[] appIds;
   4222         String[] seinfos;
   4223         int[] targetSdkVersions;
   4224         int packagesCount;
   4225         synchronized (mPackages) {
   4226             Collection<PackageSetting> packages = mPackages.values();
   4227             packagesCount = packages.size();
   4228             volumeUuids = new String[packagesCount];
   4229             names = new String[packagesCount];
   4230             appIds = new int[packagesCount];
   4231             seinfos = new String[packagesCount];
   4232             targetSdkVersions = new int[packagesCount];
   4233             Iterator<PackageSetting> packagesIterator = packages.iterator();
   4234             for (int i = 0; i < packagesCount; i++) {
   4235                 PackageSetting ps = packagesIterator.next();
   4236                 if (ps.pkg == null || ps.pkg.applicationInfo == null) {
   4237                     continue;
   4238                 }
   4239                 final boolean shouldInstall = ps.isSystem() &&
   4240                         !ArrayUtils.contains(disallowedPackages, ps.name);
   4241                 // Only system apps are initially installed.
   4242                 ps.setInstalled(shouldInstall, userHandle);
   4243                 if (!shouldInstall) {
   4244                     writeKernelMappingLPr(ps);
   4245                 }
   4246                 // Need to create a data directory for all apps under this user. Accumulate all
   4247                 // required args and call the installer after mPackages lock has been released
   4248                 volumeUuids[i] = ps.volumeUuid;
   4249                 names[i] = ps.name;
   4250                 appIds[i] = ps.appId;
   4251                 seinfos[i] = ps.pkg.applicationInfo.seInfo;
   4252                 targetSdkVersions[i] = ps.pkg.applicationInfo.targetSdkVersion;
   4253             }
   4254         }
   4255         for (int i = 0; i < packagesCount; i++) {
   4256             if (names[i] == null) {
   4257                 continue;
   4258             }
   4259             // TODO: triage flags!
   4260             final int flags = StorageManager.FLAG_STORAGE_CE | StorageManager.FLAG_STORAGE_DE;
   4261             try {
   4262                 installer.createAppData(volumeUuids[i], names[i], userHandle, flags, appIds[i],
   4263                         seinfos[i], targetSdkVersions[i]);
   4264             } catch (InstallerException e) {
   4265                 Slog.w(TAG, "Failed to prepare app data", e);
   4266             }
   4267         }
   4268         synchronized (mPackages) {
   4269             applyDefaultPreferredAppsLPw(service, userHandle);
   4270         }
   4271     }
   4272 
   4273     void removeUserLPw(int userId) {
   4274         Set<Entry<String, PackageSetting>> entries = mPackages.entrySet();
   4275         for (Entry<String, PackageSetting> entry : entries) {
   4276             entry.getValue().removeUser(userId);
   4277         }
   4278         mPreferredActivities.remove(userId);
   4279         File file = getUserPackagesStateFile(userId);
   4280         file.delete();
   4281         file = getUserPackagesStateBackupFile(userId);
   4282         file.delete();
   4283         removeCrossProfileIntentFiltersLPw(userId);
   4284 
   4285         mRuntimePermissionsPersistence.onUserRemovedLPw(userId);
   4286 
   4287         writePackageListLPr();
   4288 
   4289         // Inform kernel that the user was removed, so that packages are marked uninstalled
   4290         // for sdcardfs
   4291         writeKernelRemoveUserLPr(userId);
   4292     }
   4293 
   4294     void removeCrossProfileIntentFiltersLPw(int userId) {
   4295         synchronized (mCrossProfileIntentResolvers) {
   4296             // userId is the source user
   4297             if (mCrossProfileIntentResolvers.get(userId) != null) {
   4298                 mCrossProfileIntentResolvers.remove(userId);
   4299                 writePackageRestrictionsLPr(userId);
   4300             }
   4301             // userId is the target user
   4302             int count = mCrossProfileIntentResolvers.size();
   4303             for (int i = 0; i < count; i++) {
   4304                 int sourceUserId = mCrossProfileIntentResolvers.keyAt(i);
   4305                 CrossProfileIntentResolver cpir = mCrossProfileIntentResolvers.get(sourceUserId);
   4306                 boolean needsWriting = false;
   4307                 ArraySet<CrossProfileIntentFilter> cpifs =
   4308                         new ArraySet<CrossProfileIntentFilter>(cpir.filterSet());
   4309                 for (CrossProfileIntentFilter cpif : cpifs) {
   4310                     if (cpif.getTargetUserId() == userId) {
   4311                         needsWriting = true;
   4312                         cpir.removeFilter(cpif);
   4313                     }
   4314                 }
   4315                 if (needsWriting) {
   4316                     writePackageRestrictionsLPr(sourceUserId);
   4317                 }
   4318             }
   4319         }
   4320     }
   4321 
   4322     // This should be called (at least) whenever an application is removed
   4323     private void setFirstAvailableUid(int uid) {
   4324         if (uid > mFirstAvailableUid) {
   4325             mFirstAvailableUid = uid;
   4326         }
   4327     }
   4328 
   4329     // Returns -1 if we could not find an available UserId to assign
   4330     private int newUserIdLPw(Object obj) {
   4331         // Let's be stupidly inefficient for now...
   4332         final int N = mUserIds.size();
   4333         for (int i = mFirstAvailableUid; i < N; i++) {
   4334             if (mUserIds.get(i) == null) {
   4335                 mUserIds.set(i, obj);
   4336                 return Process.FIRST_APPLICATION_UID + i;
   4337             }
   4338         }
   4339 
   4340         // None left?
   4341         if (N > (Process.LAST_APPLICATION_UID-Process.FIRST_APPLICATION_UID)) {
   4342             return -1;
   4343         }
   4344 
   4345         mUserIds.add(obj);
   4346         return Process.FIRST_APPLICATION_UID + N;
   4347     }
   4348 
   4349     public VerifierDeviceIdentity getVerifierDeviceIdentityLPw() {
   4350         if (mVerifierDeviceIdentity == null) {
   4351             mVerifierDeviceIdentity = VerifierDeviceIdentity.generate();
   4352 
   4353             writeLPr();
   4354         }
   4355 
   4356         return mVerifierDeviceIdentity;
   4357     }
   4358 
   4359     boolean hasOtherDisabledSystemPkgWithChildLPr(String parentPackageName,
   4360             String childPackageName) {
   4361         final int packageCount = mDisabledSysPackages.size();
   4362         for (int i = 0; i < packageCount; i++) {
   4363             PackageSetting disabledPs = mDisabledSysPackages.valueAt(i);
   4364             if (disabledPs.childPackageNames == null || disabledPs.childPackageNames.isEmpty()) {
   4365                 continue;
   4366             }
   4367             if (disabledPs.name.equals(parentPackageName)) {
   4368                 continue;
   4369             }
   4370             final int childCount = disabledPs.childPackageNames.size();
   4371             for (int j = 0; j < childCount; j++) {
   4372                 String currChildPackageName = disabledPs.childPackageNames.get(j);
   4373                 if (currChildPackageName.equals(childPackageName)) {
   4374                     return true;
   4375                 }
   4376             }
   4377         }
   4378         return false;
   4379     }
   4380 
   4381     public PackageSetting getDisabledSystemPkgLPr(String name) {
   4382         PackageSetting ps = mDisabledSysPackages.get(name);
   4383         return ps;
   4384     }
   4385 
   4386     private String compToString(ArraySet<String> cmp) {
   4387         return cmp != null ? Arrays.toString(cmp.toArray()) : "[]";
   4388     }
   4389 
   4390     boolean isEnabledAndMatchLPr(ComponentInfo componentInfo, int flags, int userId) {
   4391         final PackageSetting ps = mPackages.get(componentInfo.packageName);
   4392         if (ps == null) return false;
   4393 
   4394         final PackageUserState userState = ps.readUserState(userId);
   4395         return userState.isMatch(componentInfo, flags);
   4396     }
   4397 
   4398     String getInstallerPackageNameLPr(String packageName) {
   4399         final PackageSetting pkg = mPackages.get(packageName);
   4400         if (pkg == null) {
   4401             throw new IllegalArgumentException("Unknown package: " + packageName);
   4402         }
   4403         return pkg.installerPackageName;
   4404     }
   4405 
   4406     boolean isOrphaned(String packageName) {
   4407         final PackageSetting pkg = mPackages.get(packageName);
   4408         if (pkg == null) {
   4409             throw new IllegalArgumentException("Unknown package: " + packageName);
   4410         }
   4411         return pkg.isOrphaned;
   4412     }
   4413 
   4414     int getApplicationEnabledSettingLPr(String packageName, int userId) {
   4415         final PackageSetting pkg = mPackages.get(packageName);
   4416         if (pkg == null) {
   4417             throw new IllegalArgumentException("Unknown package: " + packageName);
   4418         }
   4419         return pkg.getEnabled(userId);
   4420     }
   4421 
   4422     int getComponentEnabledSettingLPr(ComponentName componentName, int userId) {
   4423         final String packageName = componentName.getPackageName();
   4424         final PackageSetting pkg = mPackages.get(packageName);
   4425         if (pkg == null) {
   4426             throw new IllegalArgumentException("Unknown component: " + componentName);
   4427         }
   4428         final String classNameStr = componentName.getClassName();
   4429         return pkg.getCurrentEnabledStateLPr(classNameStr, userId);
   4430     }
   4431 
   4432     boolean wasPackageEverLaunchedLPr(String packageName, int userId) {
   4433         final PackageSetting pkgSetting = mPackages.get(packageName);
   4434         if (pkgSetting == null) {
   4435             throw new IllegalArgumentException("Unknown package: " + packageName);
   4436         }
   4437         return !pkgSetting.getNotLaunched(userId);
   4438     }
   4439 
   4440     boolean setPackageStoppedStateLPw(PackageManagerService pm, String packageName,
   4441             boolean stopped, boolean allowedByPermission, int uid, int userId) {
   4442         int appId = UserHandle.getAppId(uid);
   4443         final PackageSetting pkgSetting = mPackages.get(packageName);
   4444         if (pkgSetting == null) {
   4445             throw new IllegalArgumentException("Unknown package: " + packageName);
   4446         }
   4447         if (!allowedByPermission && (appId != pkgSetting.appId)) {
   4448             throw new SecurityException(
   4449                     "Permission Denial: attempt to change stopped state from pid="
   4450                     + Binder.getCallingPid()
   4451                     + ", uid=" + uid + ", package uid=" + pkgSetting.appId);
   4452         }
   4453         if (DEBUG_STOPPED) {
   4454             if (stopped) {
   4455                 RuntimeException e = new RuntimeException("here");
   4456                 e.fillInStackTrace();
   4457                 Slog.i(TAG, "Stopping package " + packageName, e);
   4458             }
   4459         }
   4460         if (pkgSetting.getStopped(userId) != stopped) {
   4461             pkgSetting.setStopped(stopped, userId);
   4462             // pkgSetting.pkg.mSetStopped = stopped;
   4463             if (pkgSetting.getNotLaunched(userId)) {
   4464                 if (pkgSetting.installerPackageName != null) {
   4465                     pm.notifyFirstLaunch(pkgSetting.name, pkgSetting.installerPackageName, userId);
   4466                 }
   4467                 pkgSetting.setNotLaunched(false, userId);
   4468             }
   4469             return true;
   4470         }
   4471         return false;
   4472     }
   4473 
   4474     private static List<UserInfo> getAllUsers(UserManagerService userManager) {
   4475         long id = Binder.clearCallingIdentity();
   4476         try {
   4477             return userManager.getUsers(false);
   4478         } catch (NullPointerException npe) {
   4479             // packagemanager not yet initialized
   4480         } finally {
   4481             Binder.restoreCallingIdentity(id);
   4482         }
   4483         return null;
   4484     }
   4485 
   4486     /**
   4487      * Return all {@link PackageSetting} that are actively installed on the
   4488      * given {@link VolumeInfo#fsUuid}.
   4489      */
   4490     List<PackageSetting> getVolumePackagesLPr(String volumeUuid) {
   4491         ArrayList<PackageSetting> res = new ArrayList<>();
   4492         for (int i = 0; i < mPackages.size(); i++) {
   4493             final PackageSetting setting = mPackages.valueAt(i);
   4494             if (Objects.equals(volumeUuid, setting.volumeUuid)) {
   4495                 res.add(setting);
   4496             }
   4497         }
   4498         return res;
   4499     }
   4500 
   4501     static void printFlags(PrintWriter pw, int val, Object[] spec) {
   4502         pw.print("[ ");
   4503         for (int i=0; i<spec.length; i+=2) {
   4504             int mask = (Integer)spec[i];
   4505             if ((val & mask) != 0) {
   4506                 pw.print(spec[i+1]);
   4507                 pw.print(" ");
   4508             }
   4509         }
   4510         pw.print("]");
   4511     }
   4512 
   4513     static final Object[] FLAG_DUMP_SPEC = new Object[] {
   4514         ApplicationInfo.FLAG_SYSTEM, "SYSTEM",
   4515         ApplicationInfo.FLAG_DEBUGGABLE, "DEBUGGABLE",
   4516         ApplicationInfo.FLAG_HAS_CODE, "HAS_CODE",
   4517         ApplicationInfo.FLAG_PERSISTENT, "PERSISTENT",
   4518         ApplicationInfo.FLAG_FACTORY_TEST, "FACTORY_TEST",
   4519         ApplicationInfo.FLAG_ALLOW_TASK_REPARENTING, "ALLOW_TASK_REPARENTING",
   4520         ApplicationInfo.FLAG_ALLOW_CLEAR_USER_DATA, "ALLOW_CLEAR_USER_DATA",
   4521         ApplicationInfo.FLAG_UPDATED_SYSTEM_APP, "UPDATED_SYSTEM_APP",
   4522         ApplicationInfo.FLAG_TEST_ONLY, "TEST_ONLY",
   4523         ApplicationInfo.FLAG_VM_SAFE_MODE, "VM_SAFE_MODE",
   4524         ApplicationInfo.FLAG_ALLOW_BACKUP, "ALLOW_BACKUP",
   4525         ApplicationInfo.FLAG_KILL_AFTER_RESTORE, "KILL_AFTER_RESTORE",
   4526         ApplicationInfo.FLAG_RESTORE_ANY_VERSION, "RESTORE_ANY_VERSION",
   4527         ApplicationInfo.FLAG_EXTERNAL_STORAGE, "EXTERNAL_STORAGE",
   4528         ApplicationInfo.FLAG_LARGE_HEAP, "LARGE_HEAP",
   4529     };
   4530 
   4531     private static final Object[] PRIVATE_FLAG_DUMP_SPEC = new Object[] {
   4532         ApplicationInfo.PRIVATE_FLAG_HIDDEN, "HIDDEN",
   4533         ApplicationInfo.PRIVATE_FLAG_CANT_SAVE_STATE, "CANT_SAVE_STATE",
   4534         ApplicationInfo.PRIVATE_FLAG_FORWARD_LOCK, "FORWARD_LOCK",
   4535         ApplicationInfo.PRIVATE_FLAG_PRIVILEGED, "PRIVILEGED",
   4536         ApplicationInfo.PRIVATE_FLAG_HAS_DOMAIN_URLS, "HAS_DOMAIN_URLS",
   4537         ApplicationInfo.PRIVATE_FLAG_DEFAULT_TO_DEVICE_PROTECTED_STORAGE, "DEFAULT_TO_DEVICE_PROTECTED_STORAGE",
   4538         ApplicationInfo.PRIVATE_FLAG_DIRECT_BOOT_AWARE, "DIRECT_BOOT_AWARE",
   4539         ApplicationInfo.PRIVATE_FLAG_PARTIALLY_DIRECT_BOOT_AWARE, "PARTIALLY_DIRECT_BOOT_AWARE",
   4540         ApplicationInfo.PRIVATE_FLAG_INSTANT, "EPHEMERAL",
   4541         ApplicationInfo.PRIVATE_FLAG_REQUIRED_FOR_SYSTEM_USER, "REQUIRED_FOR_SYSTEM_USER",
   4542         ApplicationInfo.PRIVATE_FLAG_ACTIVITIES_RESIZE_MODE_RESIZEABLE, "PRIVATE_FLAG_ACTIVITIES_RESIZE_MODE_RESIZEABLE",
   4543         ApplicationInfo.PRIVATE_FLAG_ACTIVITIES_RESIZE_MODE_UNRESIZEABLE, "PRIVATE_FLAG_ACTIVITIES_RESIZE_MODE_UNRESIZEABLE",
   4544         ApplicationInfo.PRIVATE_FLAG_ACTIVITIES_RESIZE_MODE_RESIZEABLE_VIA_SDK_VERSION, "PRIVATE_FLAG_ACTIVITIES_RESIZE_MODE_RESIZEABLE_VIA_SDK_VERSION",
   4545         ApplicationInfo.PRIVATE_FLAG_BACKUP_IN_FOREGROUND, "BACKUP_IN_FOREGROUND",
   4546         ApplicationInfo.PRIVATE_FLAG_STATIC_SHARED_LIBRARY, "STATIC_SHARED_LIBRARY",
   4547     };
   4548 
   4549     void dumpVersionLPr(IndentingPrintWriter pw) {
   4550         pw.increaseIndent();
   4551         for (int i= 0; i < mVersion.size(); i++) {
   4552             final String volumeUuid = mVersion.keyAt(i);
   4553             final VersionInfo ver = mVersion.valueAt(i);
   4554             if (Objects.equals(StorageManager.UUID_PRIVATE_INTERNAL, volumeUuid)) {
   4555                 pw.println("Internal:");
   4556             } else if (Objects.equals(StorageManager.UUID_PRIMARY_PHYSICAL, volumeUuid)) {
   4557                 pw.println("External:");
   4558             } else {
   4559                 pw.println("UUID " + volumeUuid + ":");
   4560             }
   4561             pw.increaseIndent();
   4562             pw.printPair("sdkVersion", ver.sdkVersion);
   4563             pw.printPair("databaseVersion", ver.databaseVersion);
   4564             pw.println();
   4565             pw.printPair("fingerprint", ver.fingerprint);
   4566             pw.println();
   4567             pw.decreaseIndent();
   4568         }
   4569         pw.decreaseIndent();
   4570     }
   4571 
   4572     void dumpPackageLPr(PrintWriter pw, String prefix, String checkinTag,
   4573             ArraySet<String> permissionNames, PackageSetting ps, SimpleDateFormat sdf,
   4574             Date date, List<UserInfo> users, boolean dumpAll) {
   4575         if (checkinTag != null) {
   4576             pw.print(checkinTag);
   4577             pw.print(",");
   4578             pw.print(ps.realName != null ? ps.realName : ps.name);
   4579             pw.print(",");
   4580             pw.print(ps.appId);
   4581             pw.print(",");
   4582             pw.print(ps.versionCode);
   4583             pw.print(",");
   4584             pw.print(ps.firstInstallTime);
   4585             pw.print(",");
   4586             pw.print(ps.lastUpdateTime);
   4587             pw.print(",");
   4588             pw.print(ps.installerPackageName != null ? ps.installerPackageName : "?");
   4589             pw.println();
   4590             if (ps.pkg != null) {
   4591                 pw.print(checkinTag); pw.print("-"); pw.print("splt,");
   4592                 pw.print("base,");
   4593                 pw.println(ps.pkg.baseRevisionCode);
   4594                 if (ps.pkg.splitNames != null) {
   4595                     for (int i = 0; i < ps.pkg.splitNames.length; i++) {
   4596                         pw.print(checkinTag); pw.print("-"); pw.print("splt,");
   4597                         pw.print(ps.pkg.splitNames[i]); pw.print(",");
   4598                         pw.println(ps.pkg.splitRevisionCodes[i]);
   4599                     }
   4600                 }
   4601             }
   4602             for (UserInfo user : users) {
   4603                 pw.print(checkinTag);
   4604                 pw.print("-");
   4605                 pw.print("usr");
   4606                 pw.print(",");
   4607                 pw.print(user.id);
   4608                 pw.print(",");
   4609                 pw.print(ps.getInstalled(user.id) ? "I" : "i");
   4610                 pw.print(ps.getHidden(user.id) ? "B" : "b");
   4611                 pw.print(ps.getSuspended(user.id) ? "SU" : "su");
   4612                 pw.print(ps.getStopped(user.id) ? "S" : "s");
   4613                 pw.print(ps.getNotLaunched(user.id) ? "l" : "L");
   4614                 pw.print(ps.getInstantApp(user.id) ? "IA" : "ia");
   4615                 pw.print(ps.getVirtulalPreload(user.id) ? "VPI" : "vpi");
   4616                 pw.print(",");
   4617                 pw.print(ps.getEnabled(user.id));
   4618                 String lastDisabledAppCaller = ps.getLastDisabledAppCaller(user.id);
   4619                 pw.print(",");
   4620                 pw.print(lastDisabledAppCaller != null ? lastDisabledAppCaller : "?");
   4621                 pw.println();
   4622             }
   4623             return;
   4624         }
   4625 
   4626         pw.print(prefix); pw.print("Package [");
   4627             pw.print(ps.realName != null ? ps.realName : ps.name);
   4628             pw.print("] (");
   4629             pw.print(Integer.toHexString(System.identityHashCode(ps)));
   4630             pw.println("):");
   4631 
   4632         if (ps.realName != null) {
   4633             pw.print(prefix); pw.print("  compat name=");
   4634             pw.println(ps.name);
   4635         }
   4636 
   4637         pw.print(prefix); pw.print("  userId="); pw.println(ps.appId);
   4638 
   4639         if (ps.sharedUser != null) {
   4640             pw.print(prefix); pw.print("  sharedUser="); pw.println(ps.sharedUser);
   4641         }
   4642         pw.print(prefix); pw.print("  pkg="); pw.println(ps.pkg);
   4643         pw.print(prefix); pw.print("  codePath="); pw.println(ps.codePathString);
   4644         if (permissionNames == null) {
   4645             pw.print(prefix); pw.print("  resourcePath="); pw.println(ps.resourcePathString);
   4646             pw.print(prefix); pw.print("  legacyNativeLibraryDir=");
   4647             pw.println(ps.legacyNativeLibraryPathString);
   4648             pw.print(prefix); pw.print("  primaryCpuAbi="); pw.println(ps.primaryCpuAbiString);
   4649             pw.print(prefix); pw.print("  secondaryCpuAbi="); pw.println(ps.secondaryCpuAbiString);
   4650         }
   4651         pw.print(prefix); pw.print("  versionCode="); pw.print(ps.versionCode);
   4652         if (ps.pkg != null) {
   4653             pw.print(" minSdk="); pw.print(ps.pkg.applicationInfo.minSdkVersion);
   4654             pw.print(" targetSdk="); pw.print(ps.pkg.applicationInfo.targetSdkVersion);
   4655         }
   4656         pw.println();
   4657         if (ps.pkg != null) {
   4658             if (ps.pkg.parentPackage != null) {
   4659                 PackageParser.Package parentPkg = ps.pkg.parentPackage;
   4660                 PackageSetting pps = mPackages.get(parentPkg.packageName);
   4661                 if (pps == null || !pps.codePathString.equals(parentPkg.codePath)) {
   4662                     pps = mDisabledSysPackages.get(parentPkg.packageName);
   4663                 }
   4664                 if (pps != null) {
   4665                     pw.print(prefix); pw.print("  parentPackage=");
   4666                     pw.println(pps.realName != null ? pps.realName : pps.name);
   4667                 }
   4668             } else if (ps.pkg.childPackages != null) {
   4669                 pw.print(prefix); pw.print("  childPackages=[");
   4670                 final int childCount = ps.pkg.childPackages.size();
   4671                 for (int i = 0; i < childCount; i++) {
   4672                     PackageParser.Package childPkg = ps.pkg.childPackages.get(i);
   4673                     PackageSetting cps = mPackages.get(childPkg.packageName);
   4674                     if (cps == null || !cps.codePathString.equals(childPkg.codePath)) {
   4675                         cps = mDisabledSysPackages.get(childPkg.packageName);
   4676                     }
   4677                     if (cps != null) {
   4678                         if (i > 0) {
   4679                             pw.print(", ");
   4680                         }
   4681                         pw.print(cps.realName != null ? cps.realName : cps.name);
   4682                     }
   4683                 }
   4684                 pw.println("]");
   4685             }
   4686             pw.print(prefix); pw.print("  versionName="); pw.println(ps.pkg.mVersionName);
   4687             pw.print(prefix); pw.print("  splits="); dumpSplitNames(pw, ps.pkg); pw.println();
   4688             final int apkSigningVersion = PackageParser.getApkSigningVersion(ps.pkg);
   4689             if (apkSigningVersion != PackageParser.APK_SIGNING_UNKNOWN) {
   4690                 pw.print(prefix); pw.print("  apkSigningVersion="); pw.println(apkSigningVersion);
   4691             }
   4692             pw.print(prefix); pw.print("  applicationInfo=");
   4693                 pw.println(ps.pkg.applicationInfo.toString());
   4694             pw.print(prefix); pw.print("  flags="); printFlags(pw, ps.pkg.applicationInfo.flags,
   4695                     FLAG_DUMP_SPEC); pw.println();
   4696             if (ps.pkg.applicationInfo.privateFlags != 0) {
   4697                 pw.print(prefix); pw.print("  privateFlags="); printFlags(pw,
   4698                         ps.pkg.applicationInfo.privateFlags, PRIVATE_FLAG_DUMP_SPEC); pw.println();
   4699             }
   4700             pw.print(prefix); pw.print("  dataDir="); pw.println(ps.pkg.applicationInfo.dataDir);
   4701             pw.print(prefix); pw.print("  supportsScreens=[");
   4702             boolean first = true;
   4703             if ((ps.pkg.applicationInfo.flags & ApplicationInfo.FLAG_SUPPORTS_SMALL_SCREENS) != 0) {
   4704                 if (!first)
   4705                     pw.print(", ");
   4706                 first = false;
   4707                 pw.print("small");
   4708             }
   4709             if ((ps.pkg.applicationInfo.flags & ApplicationInfo.FLAG_SUPPORTS_NORMAL_SCREENS) != 0) {
   4710                 if (!first)
   4711                     pw.print(", ");
   4712                 first = false;
   4713                 pw.print("medium");
   4714             }
   4715             if ((ps.pkg.applicationInfo.flags & ApplicationInfo.FLAG_SUPPORTS_LARGE_SCREENS) != 0) {
   4716                 if (!first)
   4717                     pw.print(", ");
   4718                 first = false;
   4719                 pw.print("large");
   4720             }
   4721             if ((ps.pkg.applicationInfo.flags & ApplicationInfo.FLAG_SUPPORTS_XLARGE_SCREENS) != 0) {
   4722                 if (!first)
   4723                     pw.print(", ");
   4724                 first = false;
   4725                 pw.print("xlarge");
   4726             }
   4727             if ((ps.pkg.applicationInfo.flags & ApplicationInfo.FLAG_RESIZEABLE_FOR_SCREENS) != 0) {
   4728                 if (!first)
   4729                     pw.print(", ");
   4730                 first = false;
   4731                 pw.print("resizeable");
   4732             }
   4733             if ((ps.pkg.applicationInfo.flags & ApplicationInfo.FLAG_SUPPORTS_SCREEN_DENSITIES) != 0) {
   4734                 if (!first)
   4735                     pw.print(", ");
   4736                 first = false;
   4737                 pw.print("anyDensity");
   4738             }
   4739             pw.println("]");
   4740             if (ps.pkg.libraryNames != null && ps.pkg.libraryNames.size() > 0) {
   4741                 pw.print(prefix); pw.println("  dynamic libraries:");
   4742                 for (int i = 0; i<ps.pkg.libraryNames.size(); i++) {
   4743                     pw.print(prefix); pw.print("    ");
   4744                             pw.println(ps.pkg.libraryNames.get(i));
   4745                 }
   4746             }
   4747             if (ps.pkg.staticSharedLibName != null) {
   4748                 pw.print(prefix); pw.println("  static library:");
   4749                 pw.print(prefix); pw.print("    ");
   4750                 pw.print("name:"); pw.print(ps.pkg.staticSharedLibName);
   4751                 pw.print(" version:"); pw.println(ps.pkg.staticSharedLibVersion);
   4752             }
   4753             if (ps.pkg.usesLibraries != null && ps.pkg.usesLibraries.size() > 0) {
   4754                 pw.print(prefix); pw.println("  usesLibraries:");
   4755                 for (int i=0; i<ps.pkg.usesLibraries.size(); i++) {
   4756                     pw.print(prefix); pw.print("    "); pw.println(ps.pkg.usesLibraries.get(i));
   4757                 }
   4758             }
   4759             if (ps.pkg.usesStaticLibraries != null
   4760                     && ps.pkg.usesStaticLibraries.size() > 0) {
   4761                 pw.print(prefix); pw.println("  usesStaticLibraries:");
   4762                 for (int i=0; i<ps.pkg.usesStaticLibraries.size(); i++) {
   4763                     pw.print(prefix); pw.print("    ");
   4764                     pw.print(ps.pkg.usesStaticLibraries.get(i)); pw.print(" version:");
   4765                             pw.println(ps.pkg.usesStaticLibrariesVersions[i]);
   4766                 }
   4767             }
   4768             if (ps.pkg.usesOptionalLibraries != null
   4769                     && ps.pkg.usesOptionalLibraries.size() > 0) {
   4770                 pw.print(prefix); pw.println("  usesOptionalLibraries:");
   4771                 for (int i=0; i<ps.pkg.usesOptionalLibraries.size(); i++) {
   4772                     pw.print(prefix); pw.print("    ");
   4773                     pw.println(ps.pkg.usesOptionalLibraries.get(i));
   4774                 }
   4775             }
   4776             if (ps.pkg.usesLibraryFiles != null
   4777                     && ps.pkg.usesLibraryFiles.length > 0) {
   4778                 pw.print(prefix); pw.println("  usesLibraryFiles:");
   4779                 for (int i=0; i<ps.pkg.usesLibraryFiles.length; i++) {
   4780                     pw.print(prefix); pw.print("    "); pw.println(ps.pkg.usesLibraryFiles[i]);
   4781                 }
   4782             }
   4783         }
   4784         pw.print(prefix); pw.print("  timeStamp=");
   4785             date.setTime(ps.timeStamp);
   4786             pw.println(sdf.format(date));
   4787         pw.print(prefix); pw.print("  firstInstallTime=");
   4788             date.setTime(ps.firstInstallTime);
   4789             pw.println(sdf.format(date));
   4790         pw.print(prefix); pw.print("  lastUpdateTime=");
   4791             date.setTime(ps.lastUpdateTime);
   4792             pw.println(sdf.format(date));
   4793         if (ps.installerPackageName != null) {
   4794             pw.print(prefix); pw.print("  installerPackageName=");
   4795                     pw.println(ps.installerPackageName);
   4796         }
   4797         if (ps.volumeUuid != null) {
   4798             pw.print(prefix); pw.print("  volumeUuid=");
   4799                     pw.println(ps.volumeUuid);
   4800         }
   4801         pw.print(prefix); pw.print("  signatures="); pw.println(ps.signatures);
   4802         pw.print(prefix); pw.print("  installPermissionsFixed=");
   4803                 pw.print(ps.installPermissionsFixed);
   4804                 pw.print(" installStatus="); pw.println(ps.installStatus);
   4805         pw.print(prefix); pw.print("  pkgFlags="); printFlags(pw, ps.pkgFlags, FLAG_DUMP_SPEC);
   4806                 pw.println();
   4807 
   4808         if (ps.pkg != null && ps.pkg.permissions != null && ps.pkg.permissions.size() > 0) {
   4809             final ArrayList<PackageParser.Permission> perms = ps.pkg.permissions;
   4810             pw.print(prefix); pw.println("  declared permissions:");
   4811             for (int i=0; i<perms.size(); i++) {
   4812                 PackageParser.Permission perm = perms.get(i);
   4813                 if (permissionNames != null
   4814                         && !permissionNames.contains(perm.info.name)) {
   4815                     continue;
   4816                 }
   4817                 pw.print(prefix); pw.print("    "); pw.print(perm.info.name);
   4818                 pw.print(": prot=");
   4819                 pw.print(PermissionInfo.protectionToString(perm.info.protectionLevel));
   4820                 if ((perm.info.flags&PermissionInfo.FLAG_COSTS_MONEY) != 0) {
   4821                     pw.print(", COSTS_MONEY");
   4822                 }
   4823                 if ((perm.info.flags&PermissionInfo.FLAG_REMOVED) != 0) {
   4824                     pw.print(", HIDDEN");
   4825                 }
   4826                 if ((perm.info.flags&PermissionInfo.FLAG_INSTALLED) != 0) {
   4827                     pw.print(", INSTALLED");
   4828                 }
   4829                 pw.println();
   4830             }
   4831         }
   4832 
   4833         if ((permissionNames != null || dumpAll) && ps.pkg != null
   4834                 && ps.pkg.requestedPermissions != null
   4835                 && ps.pkg.requestedPermissions.size() > 0) {
   4836             final ArrayList<String> perms = ps.pkg.requestedPermissions;
   4837             pw.print(prefix); pw.println("  requested permissions:");
   4838             for (int i=0; i<perms.size(); i++) {
   4839                 String perm = perms.get(i);
   4840                 if (permissionNames != null
   4841                         && !permissionNames.contains(perm)) {
   4842                     continue;
   4843                 }
   4844                 pw.print(prefix); pw.print("    "); pw.println(perm);
   4845             }
   4846         }
   4847 
   4848         if (ps.sharedUser == null || permissionNames != null || dumpAll) {
   4849             PermissionsState permissionsState = ps.getPermissionsState();
   4850             dumpInstallPermissionsLPr(pw, prefix + "  ", permissionNames, permissionsState);
   4851         }
   4852 
   4853         for (UserInfo user : users) {
   4854             pw.print(prefix); pw.print("  User "); pw.print(user.id); pw.print(": ");
   4855             pw.print("ceDataInode=");
   4856             pw.print(ps.getCeDataInode(user.id));
   4857             pw.print(" installed=");
   4858             pw.print(ps.getInstalled(user.id));
   4859             pw.print(" hidden=");
   4860             pw.print(ps.getHidden(user.id));
   4861             pw.print(" suspended=");
   4862             pw.print(ps.getSuspended(user.id));
   4863             pw.print(" stopped=");
   4864             pw.print(ps.getStopped(user.id));
   4865             pw.print(" notLaunched=");
   4866             pw.print(ps.getNotLaunched(user.id));
   4867             pw.print(" enabled=");
   4868             pw.print(ps.getEnabled(user.id));
   4869             pw.print(" instant=");
   4870             pw.print(ps.getInstantApp(user.id));
   4871             pw.print(" virtual=");
   4872             pw.println(ps.getVirtulalPreload(user.id));
   4873 
   4874             String[] overlayPaths = ps.getOverlayPaths(user.id);
   4875             if (overlayPaths != null && overlayPaths.length > 0) {
   4876                 pw.print(prefix); pw.println("  overlay paths:");
   4877                 for (String path : overlayPaths) {
   4878                     pw.print(prefix); pw.print("    "); pw.println(path);
   4879                 }
   4880             }
   4881 
   4882             String lastDisabledAppCaller = ps.getLastDisabledAppCaller(user.id);
   4883             if (lastDisabledAppCaller != null) {
   4884                 pw.print(prefix); pw.print("    lastDisabledCaller: ");
   4885                         pw.println(lastDisabledAppCaller);
   4886             }
   4887 
   4888             if (ps.sharedUser == null) {
   4889                 PermissionsState permissionsState = ps.getPermissionsState();
   4890                 dumpGidsLPr(pw, prefix + "    ", permissionsState.computeGids(user.id));
   4891                 dumpRuntimePermissionsLPr(pw, prefix + "    ", permissionNames, permissionsState
   4892                         .getRuntimePermissionStates(user.id), dumpAll);
   4893             }
   4894 
   4895             if (permissionNames == null) {
   4896                 ArraySet<String> cmp = ps.getDisabledComponents(user.id);
   4897                 if (cmp != null && cmp.size() > 0) {
   4898                     pw.print(prefix); pw.println("    disabledComponents:");
   4899                     for (String s : cmp) {
   4900                         pw.print(prefix); pw.print("      "); pw.println(s);
   4901                     }
   4902                 }
   4903                 cmp = ps.getEnabledComponents(user.id);
   4904                 if (cmp != null && cmp.size() > 0) {
   4905                     pw.print(prefix); pw.println("    enabledComponents:");
   4906                     for (String s : cmp) {
   4907                         pw.print(prefix); pw.print("      "); pw.println(s);
   4908                     }
   4909                 }
   4910             }
   4911         }
   4912     }
   4913 
   4914     void dumpPackagesLPr(PrintWriter pw, String packageName, ArraySet<String> permissionNames,
   4915             DumpState dumpState, boolean checkin) {
   4916         final SimpleDateFormat sdf = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss");
   4917         final Date date = new Date();
   4918         boolean printedSomething = false;
   4919         List<UserInfo> users = getAllUsers(UserManagerService.getInstance());
   4920         for (final PackageSetting ps : mPackages.values()) {
   4921             if (packageName != null && !packageName.equals(ps.realName)
   4922                     && !packageName.equals(ps.name)) {
   4923                 continue;
   4924             }
   4925             if (permissionNames != null
   4926                     && !ps.getPermissionsState().hasRequestedPermission(permissionNames)) {
   4927                 continue;
   4928             }
   4929 
   4930             if (!checkin && packageName != null) {
   4931                 dumpState.setSharedUser(ps.sharedUser);
   4932             }
   4933 
   4934             if (!checkin && !printedSomething) {
   4935                 if (dumpState.onTitlePrinted())
   4936                     pw.println();
   4937                 pw.println("Packages:");
   4938                 printedSomething = true;
   4939             }
   4940             dumpPackageLPr(pw, "  ", checkin ? "pkg" : null, permissionNames, ps, sdf, date, users,
   4941                     packageName != null);
   4942         }
   4943 
   4944         printedSomething = false;
   4945         if (mRenamedPackages.size() > 0 && permissionNames == null) {
   4946             for (final Map.Entry<String, String> e : mRenamedPackages.entrySet()) {
   4947                 if (packageName != null && !packageName.equals(e.getKey())
   4948                         && !packageName.equals(e.getValue())) {
   4949                     continue;
   4950                 }
   4951                 if (!checkin) {
   4952                     if (!printedSomething) {
   4953                         if (dumpState.onTitlePrinted())
   4954                             pw.println();
   4955                         pw.println("Renamed packages:");
   4956                         printedSomething = true;
   4957                     }
   4958                     pw.print("  ");
   4959                 } else {
   4960                     pw.print("ren,");
   4961                 }
   4962                 pw.print(e.getKey());
   4963                 pw.print(checkin ? " -> " : ",");
   4964                 pw.println(e.getValue());
   4965             }
   4966         }
   4967 
   4968         printedSomething = false;
   4969         if (mDisabledSysPackages.size() > 0 && permissionNames == null) {
   4970             for (final PackageSetting ps : mDisabledSysPackages.values()) {
   4971                 if (packageName != null && !packageName.equals(ps.realName)
   4972                         && !packageName.equals(ps.name)) {
   4973                     continue;
   4974                 }
   4975                 if (!checkin && !printedSomething) {
   4976                     if (dumpState.onTitlePrinted())
   4977                         pw.println();
   4978                     pw.println("Hidden system packages:");
   4979                     printedSomething = true;
   4980                 }
   4981                 dumpPackageLPr(pw, "  ", checkin ? "dis" : null, permissionNames, ps, sdf, date,
   4982                         users, packageName != null);
   4983             }
   4984         }
   4985     }
   4986 
   4987     void dumpPackagesProto(ProtoOutputStream proto) {
   4988         List<UserInfo> users = getAllUsers(UserManagerService.getInstance());
   4989 
   4990         final int count = mPackages.size();
   4991         for (int i = 0; i < count; i++) {
   4992             final PackageSetting ps = mPackages.valueAt(i);
   4993             ps.writeToProto(proto, PackageServiceDumpProto.PACKAGES, users);
   4994         }
   4995     }
   4996 
   4997     void dumpPermissionsLPr(PrintWriter pw, String packageName, ArraySet<String> permissionNames,
   4998             DumpState dumpState) {
   4999         boolean printedSomething = false;
   5000         for (BasePermission p : mPermissions.values()) {
   5001             if (packageName != null && !packageName.equals(p.sourcePackage)) {
   5002                 continue;
   5003             }
   5004             if (permissionNames != null && !permissionNames.contains(p.name)) {
   5005                 continue;
   5006             }
   5007             if (!printedSomething) {
   5008                 if (dumpState.onTitlePrinted())
   5009                     pw.println();
   5010                 pw.println("Permissions:");
   5011                 printedSomething = true;
   5012             }
   5013             pw.print("  Permission ["); pw.print(p.name); pw.print("] (");
   5014                     pw.print(Integer.toHexString(System.identityHashCode(p)));
   5015                     pw.println("):");
   5016             pw.print("    sourcePackage="); pw.println(p.sourcePackage);
   5017             pw.print("    uid="); pw.print(p.uid);
   5018                     pw.print(" gids="); pw.print(Arrays.toString(
   5019                             p.computeGids(UserHandle.USER_SYSTEM)));
   5020                     pw.print(" type="); pw.print(p.type);
   5021                     pw.print(" prot=");
   5022                     pw.println(PermissionInfo.protectionToString(p.protectionLevel));
   5023             if (p.perm != null) {
   5024                 pw.print("    perm="); pw.println(p.perm);
   5025                 if ((p.perm.info.flags & PermissionInfo.FLAG_INSTALLED) == 0
   5026                         || (p.perm.info.flags & PermissionInfo.FLAG_REMOVED) != 0) {
   5027                     pw.print("    flags=0x"); pw.println(Integer.toHexString(p.perm.info.flags));
   5028                 }
   5029             }
   5030             if (p.packageSetting != null) {
   5031                 pw.print("    packageSetting="); pw.println(p.packageSetting);
   5032             }
   5033             if (READ_EXTERNAL_STORAGE.equals(p.name)) {
   5034                 pw.print("    enforced=");
   5035                 pw.println(mReadExternalStorageEnforced);
   5036             }
   5037         }
   5038     }
   5039 
   5040     void dumpSharedUsersLPr(PrintWriter pw, String packageName, ArraySet<String> permissionNames,
   5041             DumpState dumpState, boolean checkin) {
   5042         boolean printedSomething = false;
   5043         for (SharedUserSetting su : mSharedUsers.values()) {
   5044             if (packageName != null && su != dumpState.getSharedUser()) {
   5045                 continue;
   5046             }
   5047             if (permissionNames != null
   5048                     && !su.getPermissionsState().hasRequestedPermission(permissionNames)) {
   5049                 continue;
   5050             }
   5051             if (!checkin) {
   5052                 if (!printedSomething) {
   5053                     if (dumpState.onTitlePrinted())
   5054                         pw.println();
   5055                     pw.println("Shared users:");
   5056                     printedSomething = true;
   5057                 }
   5058                 pw.print("  SharedUser [");
   5059                 pw.print(su.name);
   5060                 pw.print("] (");
   5061                 pw.print(Integer.toHexString(System.identityHashCode(su)));
   5062                         pw.println("):");
   5063 
   5064                 String prefix = "    ";
   5065                 pw.print(prefix); pw.print("userId="); pw.println(su.userId);
   5066 
   5067                 PermissionsState permissionsState = su.getPermissionsState();
   5068                 dumpInstallPermissionsLPr(pw, prefix, permissionNames, permissionsState);
   5069 
   5070                 for (int userId : UserManagerService.getInstance().getUserIds()) {
   5071                     final int[] gids = permissionsState.computeGids(userId);
   5072                     List<PermissionState> permissions = permissionsState
   5073                             .getRuntimePermissionStates(userId);
   5074                     if (!ArrayUtils.isEmpty(gids) || !permissions.isEmpty()) {
   5075                         pw.print(prefix); pw.print("User "); pw.print(userId); pw.println(": ");
   5076                         dumpGidsLPr(pw, prefix + "  ", gids);
   5077                         dumpRuntimePermissionsLPr(pw, prefix + "  ", permissionNames, permissions,
   5078                                 packageName != null);
   5079                     }
   5080                 }
   5081             } else {
   5082                 pw.print("suid,"); pw.print(su.userId); pw.print(","); pw.println(su.name);
   5083             }
   5084         }
   5085     }
   5086 
   5087     void dumpSharedUsersProto(ProtoOutputStream proto) {
   5088         final int count = mSharedUsers.size();
   5089         for (int i = 0; i < count; i++) {
   5090             final SharedUserSetting su = mSharedUsers.valueAt(i);
   5091             final long sharedUserToken = proto.start(PackageServiceDumpProto.SHARED_USERS);
   5092             proto.write(PackageServiceDumpProto.SharedUserProto.USER_ID, su.userId);
   5093             proto.write(PackageServiceDumpProto.SharedUserProto.NAME, su.name);
   5094             proto.end(sharedUserToken);
   5095         }
   5096     }
   5097 
   5098     void dumpReadMessagesLPr(PrintWriter pw, DumpState dumpState) {
   5099         pw.println("Settings parse messages:");
   5100         pw.print(mReadMessages.toString());
   5101     }
   5102 
   5103     void dumpRestoredPermissionGrantsLPr(PrintWriter pw, DumpState dumpState) {
   5104         if (mRestoredUserGrants.size() > 0) {
   5105             pw.println();
   5106             pw.println("Restored (pending) permission grants:");
   5107             for (int userIndex = 0; userIndex < mRestoredUserGrants.size(); userIndex++) {
   5108                 ArrayMap<String, ArraySet<RestoredPermissionGrant>> grantsByPackage =
   5109                         mRestoredUserGrants.valueAt(userIndex);
   5110                 if (grantsByPackage != null && grantsByPackage.size() > 0) {
   5111                     final int userId = mRestoredUserGrants.keyAt(userIndex);
   5112                     pw.print("  User "); pw.println(userId);
   5113 
   5114                     for (int pkgIndex = 0; pkgIndex < grantsByPackage.size(); pkgIndex++) {
   5115                         ArraySet<RestoredPermissionGrant> grants = grantsByPackage.valueAt(pkgIndex);
   5116                         if (grants != null && grants.size() > 0) {
   5117                             final String pkgName = grantsByPackage.keyAt(pkgIndex);
   5118                             pw.print("    "); pw.print(pkgName); pw.println(" :");
   5119 
   5120                             for (RestoredPermissionGrant g : grants) {
   5121                                 pw.print("      ");
   5122                                 pw.print(g.permissionName);
   5123                                 if (g.granted) {
   5124                                     pw.print(" GRANTED");
   5125                                 }
   5126                                 if ((g.grantBits&FLAG_PERMISSION_USER_SET) != 0) {
   5127                                     pw.print(" user_set");
   5128                                 }
   5129                                 if ((g.grantBits&FLAG_PERMISSION_USER_FIXED) != 0) {
   5130                                     pw.print(" user_fixed");
   5131                                 }
   5132                                 if ((g.grantBits&FLAG_PERMISSION_REVOKE_ON_UPGRADE) != 0) {
   5133                                     pw.print(" revoke_on_upgrade");
   5134                                 }
   5135                                 pw.println();
   5136                             }
   5137                         }
   5138                     }
   5139                 }
   5140             }
   5141             pw.println();
   5142         }
   5143     }
   5144 
   5145     private static void dumpSplitNames(PrintWriter pw, PackageParser.Package pkg) {
   5146         if (pkg == null) {
   5147             pw.print("unknown");
   5148         } else {
   5149             // [base:10, config.mdpi, config.xhdpi:12]
   5150             pw.print("[");
   5151             pw.print("base");
   5152             if (pkg.baseRevisionCode != 0) {
   5153                 pw.print(":"); pw.print(pkg.baseRevisionCode);
   5154             }
   5155             if (pkg.splitNames != null) {
   5156                 for (int i = 0; i < pkg.splitNames.length; i++) {
   5157                     pw.print(", ");
   5158                     pw.print(pkg.splitNames[i]);
   5159                     if (pkg.splitRevisionCodes[i] != 0) {
   5160                         pw.print(":"); pw.print(pkg.splitRevisionCodes[i]);
   5161                     }
   5162                 }
   5163             }
   5164             pw.print("]");
   5165         }
   5166     }
   5167 
   5168     void dumpGidsLPr(PrintWriter pw, String prefix, int[] gids) {
   5169         if (!ArrayUtils.isEmpty(gids)) {
   5170             pw.print(prefix);
   5171             pw.print("gids="); pw.println(
   5172                     PackageManagerService.arrayToString(gids));
   5173         }
   5174     }
   5175 
   5176     void dumpRuntimePermissionsLPr(PrintWriter pw, String prefix, ArraySet<String> permissionNames,
   5177             List<PermissionState> permissionStates, boolean dumpAll) {
   5178         if (!permissionStates.isEmpty() || dumpAll) {
   5179             pw.print(prefix); pw.println("runtime permissions:");
   5180             for (PermissionState permissionState : permissionStates) {
   5181                 if (permissionNames != null
   5182                         && !permissionNames.contains(permissionState.getName())) {
   5183                     continue;
   5184                 }
   5185                 pw.print(prefix); pw.print("  "); pw.print(permissionState.getName());
   5186                 pw.print(": granted="); pw.print(permissionState.isGranted());
   5187                     pw.println(permissionFlagsToString(", flags=",
   5188                             permissionState.getFlags()));
   5189             }
   5190         }
   5191     }
   5192 
   5193     private static String permissionFlagsToString(String prefix, int flags) {
   5194         StringBuilder flagsString = null;
   5195         while (flags != 0) {
   5196             if (flagsString == null) {
   5197                 flagsString = new StringBuilder();
   5198                 flagsString.append(prefix);
   5199                 flagsString.append("[ ");
   5200             }
   5201             final int flag = 1 << Integer.numberOfTrailingZeros(flags);
   5202             flags &= ~flag;
   5203             flagsString.append(PackageManager.permissionFlagToString(flag));
   5204             flagsString.append(' ');
   5205         }
   5206         if (flagsString != null) {
   5207             flagsString.append(']');
   5208             return flagsString.toString();
   5209         } else {
   5210             return "";
   5211         }
   5212     }
   5213 
   5214     void dumpInstallPermissionsLPr(PrintWriter pw, String prefix, ArraySet<String> permissionNames,
   5215             PermissionsState permissionsState) {
   5216         List<PermissionState> permissionStates = permissionsState.getInstallPermissionStates();
   5217         if (!permissionStates.isEmpty()) {
   5218             pw.print(prefix); pw.println("install permissions:");
   5219             for (PermissionState permissionState : permissionStates) {
   5220                 if (permissionNames != null
   5221                         && !permissionNames.contains(permissionState.getName())) {
   5222                     continue;
   5223                 }
   5224                 pw.print(prefix); pw.print("  "); pw.print(permissionState.getName());
   5225                     pw.print(": granted="); pw.print(permissionState.isGranted());
   5226                     pw.println(permissionFlagsToString(", flags=",
   5227                         permissionState.getFlags()));
   5228             }
   5229         }
   5230     }
   5231 
   5232     public void writeRuntimePermissionsForUserLPr(int userId, boolean sync) {
   5233         if (sync) {
   5234             mRuntimePermissionsPersistence.writePermissionsForUserSyncLPr(userId);
   5235         } else {
   5236             mRuntimePermissionsPersistence.writePermissionsForUserAsyncLPr(userId);
   5237         }
   5238     }
   5239 
   5240     private final class RuntimePermissionPersistence {
   5241         private static final long WRITE_PERMISSIONS_DELAY_MILLIS = 200;
   5242         private static final long MAX_WRITE_PERMISSIONS_DELAY_MILLIS = 2000;
   5243 
   5244         private final Handler mHandler = new MyHandler();
   5245 
   5246         private final Object mLock;
   5247 
   5248         @GuardedBy("mLock")
   5249         private final SparseBooleanArray mWriteScheduled = new SparseBooleanArray();
   5250 
   5251         @GuardedBy("mLock")
   5252         // The mapping keys are user ids.
   5253         private final SparseLongArray mLastNotWrittenMutationTimesMillis = new SparseLongArray();
   5254 
   5255         @GuardedBy("mLock")
   5256         // The mapping keys are user ids.
   5257         private final SparseArray<String> mFingerprints = new SparseArray<>();
   5258 
   5259         @GuardedBy("mLock")
   5260         // The mapping keys are user ids.
   5261         private final SparseBooleanArray mDefaultPermissionsGranted = new SparseBooleanArray();
   5262 
   5263         public RuntimePermissionPersistence(Object lock) {
   5264             mLock = lock;
   5265         }
   5266 
   5267         public boolean areDefaultRuntimPermissionsGrantedLPr(int userId) {
   5268             return mDefaultPermissionsGranted.get(userId);
   5269         }
   5270 
   5271         public void onDefaultRuntimePermissionsGrantedLPr(int userId) {
   5272             mFingerprints.put(userId, Build.FINGERPRINT);
   5273             writePermissionsForUserAsyncLPr(userId);
   5274         }
   5275 
   5276         public void writePermissionsForUserSyncLPr(int userId) {
   5277             mHandler.removeMessages(userId);
   5278             writePermissionsSync(userId);
   5279         }
   5280 
   5281         public void writePermissionsForUserAsyncLPr(int userId) {
   5282             final long currentTimeMillis = SystemClock.uptimeMillis();
   5283 
   5284             if (mWriteScheduled.get(userId)) {
   5285                 mHandler.removeMessages(userId);
   5286 
   5287                 // If enough time passed, write without holding off anymore.
   5288                 final long lastNotWrittenMutationTimeMillis = mLastNotWrittenMutationTimesMillis
   5289                         .get(userId);
   5290                 final long timeSinceLastNotWrittenMutationMillis = currentTimeMillis
   5291                         - lastNotWrittenMutationTimeMillis;
   5292                 if (timeSinceLastNotWrittenMutationMillis >= MAX_WRITE_PERMISSIONS_DELAY_MILLIS) {
   5293                     mHandler.obtainMessage(userId).sendToTarget();
   5294                     return;
   5295                 }
   5296 
   5297                 // Hold off a bit more as settings are frequently changing.
   5298                 final long maxDelayMillis = Math.max(lastNotWrittenMutationTimeMillis
   5299                         + MAX_WRITE_PERMISSIONS_DELAY_MILLIS - currentTimeMillis, 0);
   5300                 final long writeDelayMillis = Math.min(WRITE_PERMISSIONS_DELAY_MILLIS,
   5301                         maxDelayMillis);
   5302 
   5303                 Message message = mHandler.obtainMessage(userId);
   5304                 mHandler.sendMessageDelayed(message, writeDelayMillis);
   5305             } else {
   5306                 mLastNotWrittenMutationTimesMillis.put(userId, currentTimeMillis);
   5307                 Message message = mHandler.obtainMessage(userId);
   5308                 mHandler.sendMessageDelayed(message, WRITE_PERMISSIONS_DELAY_MILLIS);
   5309                 mWriteScheduled.put(userId, true);
   5310             }
   5311         }
   5312 
   5313         private void writePermissionsSync(int userId) {
   5314             AtomicFile destination = new AtomicFile(getUserRuntimePermissionsFile(userId));
   5315 
   5316             ArrayMap<String, List<PermissionState>> permissionsForPackage = new ArrayMap<>();
   5317             ArrayMap<String, List<PermissionState>> permissionsForSharedUser = new ArrayMap<>();
   5318 
   5319             synchronized (mLock) {
   5320                 mWriteScheduled.delete(userId);
   5321 
   5322                 final int packageCount = mPackages.size();
   5323                 for (int i = 0; i < packageCount; i++) {
   5324                     String packageName = mPackages.keyAt(i);
   5325                     PackageSetting packageSetting = mPackages.valueAt(i);
   5326                     if (packageSetting.sharedUser == null) {
   5327                         PermissionsState permissionsState = packageSetting.getPermissionsState();
   5328                         List<PermissionState> permissionsStates = permissionsState
   5329                                 .getRuntimePermissionStates(userId);
   5330                         if (!permissionsStates.isEmpty()) {
   5331                             permissionsForPackage.put(packageName, permissionsStates);
   5332                         }
   5333                     }
   5334                 }
   5335 
   5336                 final int sharedUserCount = mSharedUsers.size();
   5337                 for (int i = 0; i < sharedUserCount; i++) {
   5338                     String sharedUserName = mSharedUsers.keyAt(i);
   5339                     SharedUserSetting sharedUser = mSharedUsers.valueAt(i);
   5340                     PermissionsState permissionsState = sharedUser.getPermissionsState();
   5341                     List<PermissionState> permissionsStates = permissionsState
   5342                             .getRuntimePermissionStates(userId);
   5343                     if (!permissionsStates.isEmpty()) {
   5344                         permissionsForSharedUser.put(sharedUserName, permissionsStates);
   5345                     }
   5346                 }
   5347             }
   5348 
   5349             FileOutputStream out = null;
   5350             try {
   5351                 out = destination.startWrite();
   5352 
   5353                 XmlSerializer serializer = Xml.newSerializer();
   5354                 serializer.setOutput(out, StandardCharsets.UTF_8.name());
   5355                 serializer.setFeature(
   5356                         "http://xmlpull.org/v1/doc/features.html#indent-output", true);
   5357                 serializer.startDocument(null, true);
   5358 
   5359                 serializer.startTag(null, TAG_RUNTIME_PERMISSIONS);
   5360 
   5361                 String fingerprint = mFingerprints.get(userId);
   5362                 if (fingerprint != null) {
   5363                     serializer.attribute(null, ATTR_FINGERPRINT, fingerprint);
   5364                 }
   5365 
   5366                 final int packageCount = permissionsForPackage.size();
   5367                 for (int i = 0; i < packageCount; i++) {
   5368                     String packageName = permissionsForPackage.keyAt(i);
   5369                     List<PermissionState> permissionStates = permissionsForPackage.valueAt(i);
   5370                     serializer.startTag(null, TAG_PACKAGE);
   5371                     serializer.attribute(null, ATTR_NAME, packageName);
   5372                     writePermissions(serializer, permissionStates);
   5373                     serializer.endTag(null, TAG_PACKAGE);
   5374                 }
   5375 
   5376                 final int sharedUserCount = permissionsForSharedUser.size();
   5377                 for (int i = 0; i < sharedUserCount; i++) {
   5378                     String packageName = permissionsForSharedUser.keyAt(i);
   5379                     List<PermissionState> permissionStates = permissionsForSharedUser.valueAt(i);
   5380                     serializer.startTag(null, TAG_SHARED_USER);
   5381                     serializer.attribute(null, ATTR_NAME, packageName);
   5382                     writePermissions(serializer, permissionStates);
   5383                     serializer.endTag(null, TAG_SHARED_USER);
   5384                 }
   5385 
   5386                 serializer.endTag(null, TAG_RUNTIME_PERMISSIONS);
   5387 
   5388                 // Now any restored permission grants that are waiting for the apps
   5389                 // in question to be installed.  These are stored as per-package
   5390                 // TAG_RESTORED_RUNTIME_PERMISSIONS blocks, each containing some
   5391                 // number of individual permission grant entities.
   5392                 if (mRestoredUserGrants.get(userId) != null) {
   5393                     ArrayMap<String, ArraySet<RestoredPermissionGrant>> restoredGrants =
   5394                             mRestoredUserGrants.get(userId);
   5395                     if (restoredGrants != null) {
   5396                         final int pkgCount = restoredGrants.size();
   5397                         for (int i = 0; i < pkgCount; i++) {
   5398                             final ArraySet<RestoredPermissionGrant> pkgGrants =
   5399                                     restoredGrants.valueAt(i);
   5400                             if (pkgGrants != null && pkgGrants.size() > 0) {
   5401                                 final String pkgName = restoredGrants.keyAt(i);
   5402                                 serializer.startTag(null, TAG_RESTORED_RUNTIME_PERMISSIONS);
   5403                                 serializer.attribute(null, ATTR_PACKAGE_NAME, pkgName);
   5404 
   5405                                 final int N = pkgGrants.size();
   5406                                 for (int z = 0; z < N; z++) {
   5407                                     RestoredPermissionGrant g = pkgGrants.valueAt(z);
   5408                                     serializer.startTag(null, TAG_PERMISSION_ENTRY);
   5409                                     serializer.attribute(null, ATTR_NAME, g.permissionName);
   5410 
   5411                                     if (g.granted) {
   5412                                         serializer.attribute(null, ATTR_GRANTED, "true");
   5413                                     }
   5414 
   5415                                     if ((g.grantBits&FLAG_PERMISSION_USER_SET) != 0) {
   5416                                         serializer.attribute(null, ATTR_USER_SET, "true");
   5417                                     }
   5418                                     if ((g.grantBits&FLAG_PERMISSION_USER_FIXED) != 0) {
   5419                                         serializer.attribute(null, ATTR_USER_FIXED, "true");
   5420                                     }
   5421                                     if ((g.grantBits&FLAG_PERMISSION_REVOKE_ON_UPGRADE) != 0) {
   5422                                         serializer.attribute(null, ATTR_REVOKE_ON_UPGRADE, "true");
   5423                                     }
   5424                                     serializer.endTag(null, TAG_PERMISSION_ENTRY);
   5425                                 }
   5426                                 serializer.endTag(null, TAG_RESTORED_RUNTIME_PERMISSIONS);
   5427                             }
   5428                         }
   5429                     }
   5430                 }
   5431 
   5432                 serializer.endDocument();
   5433                 destination.finishWrite(out);
   5434 
   5435                 if (Build.FINGERPRINT.equals(fingerprint)) {
   5436                     mDefaultPermissionsGranted.put(userId, true);
   5437                 }
   5438             // Any error while writing is fatal.
   5439             } catch (Throwable t) {
   5440                 Slog.wtf(PackageManagerService.TAG,
   5441                         "Failed to write settings, restoring backup", t);
   5442                 destination.failWrite(out);
   5443             } finally {
   5444                 IoUtils.closeQuietly(out);
   5445             }
   5446         }
   5447 
   5448         private void onUserRemovedLPw(int userId) {
   5449             // Make sure we do not
   5450             mHandler.removeMessages(userId);
   5451 
   5452             for (SettingBase sb : mPackages.values()) {
   5453                 revokeRuntimePermissionsAndClearFlags(sb, userId);
   5454             }
   5455 
   5456             for (SettingBase sb : mSharedUsers.values()) {
   5457                 revokeRuntimePermissionsAndClearFlags(sb, userId);
   5458             }
   5459 
   5460             mDefaultPermissionsGranted.delete(userId);
   5461             mFingerprints.remove(userId);
   5462         }
   5463 
   5464         private void revokeRuntimePermissionsAndClearFlags(SettingBase sb, int userId) {
   5465             PermissionsState permissionsState = sb.getPermissionsState();
   5466             for (PermissionState permissionState
   5467                     : permissionsState.getRuntimePermissionStates(userId)) {
   5468                 BasePermission bp = mPermissions.get(permissionState.getName());
   5469                 if (bp != null) {
   5470                     permissionsState.revokeRuntimePermission(bp, userId);
   5471                     permissionsState.updatePermissionFlags(bp, userId,
   5472                             PackageManager.MASK_PERMISSION_FLAGS, 0);
   5473                 }
   5474             }
   5475         }
   5476 
   5477         public void deleteUserRuntimePermissionsFile(int userId) {
   5478             getUserRuntimePermissionsFile(userId).delete();
   5479         }
   5480 
   5481         public void readStateForUserSyncLPr(int userId) {
   5482             File permissionsFile = getUserRuntimePermissionsFile(userId);
   5483             if (!permissionsFile.exists()) {
   5484                 return;
   5485             }
   5486 
   5487             FileInputStream in;
   5488             try {
   5489                 in = new AtomicFile(permissionsFile).openRead();
   5490             } catch (FileNotFoundException fnfe) {
   5491                 Slog.i(PackageManagerService.TAG, "No permissions state");
   5492                 return;
   5493             }
   5494 
   5495             try {
   5496                 XmlPullParser parser = Xml.newPullParser();
   5497                 parser.setInput(in, null);
   5498                 parseRuntimePermissionsLPr(parser, userId);
   5499 
   5500             } catch (XmlPullParserException | IOException e) {
   5501                 throw new IllegalStateException("Failed parsing permissions file: "
   5502                         + permissionsFile , e);
   5503             } finally {
   5504                 IoUtils.closeQuietly(in);
   5505             }
   5506         }
   5507 
   5508         // Backup/restore support
   5509 
   5510         public void rememberRestoredUserGrantLPr(String pkgName, String permission,
   5511                 boolean isGranted, int restoredFlagSet, int userId) {
   5512             // This change will be remembered at write-settings time
   5513             ArrayMap<String, ArraySet<RestoredPermissionGrant>> grantsByPackage =
   5514                     mRestoredUserGrants.get(userId);
   5515             if (grantsByPackage == null) {
   5516                 grantsByPackage = new ArrayMap<String, ArraySet<RestoredPermissionGrant>>();
   5517                 mRestoredUserGrants.put(userId, grantsByPackage);
   5518             }
   5519 
   5520             ArraySet<RestoredPermissionGrant> grants = grantsByPackage.get(pkgName);
   5521             if (grants == null) {
   5522                 grants = new ArraySet<RestoredPermissionGrant>();
   5523                 grantsByPackage.put(pkgName, grants);
   5524             }
   5525 
   5526             RestoredPermissionGrant grant = new RestoredPermissionGrant(permission,
   5527                     isGranted, restoredFlagSet);
   5528             grants.add(grant);
   5529         }
   5530 
   5531         // Private internals
   5532 
   5533         private void parseRuntimePermissionsLPr(XmlPullParser parser, int userId)
   5534                 throws IOException, XmlPullParserException {
   5535             final int outerDepth = parser.getDepth();
   5536             int type;
   5537             while ((type = parser.next()) != XmlPullParser.END_DOCUMENT
   5538                     && (type != XmlPullParser.END_TAG || parser.getDepth() > outerDepth)) {
   5539                 if (type == XmlPullParser.END_TAG || type == XmlPullParser.TEXT) {
   5540                     continue;
   5541                 }
   5542 
   5543                 switch (parser.getName()) {
   5544                     case TAG_RUNTIME_PERMISSIONS: {
   5545                         String fingerprint = parser.getAttributeValue(null, ATTR_FINGERPRINT);
   5546                         mFingerprints.put(userId, fingerprint);
   5547                         final boolean defaultsGranted = Build.FINGERPRINT.equals(fingerprint);
   5548                         mDefaultPermissionsGranted.put(userId, defaultsGranted);
   5549                     } break;
   5550 
   5551                     case TAG_PACKAGE: {
   5552                         String name = parser.getAttributeValue(null, ATTR_NAME);
   5553                         PackageSetting ps = mPackages.get(name);
   5554                         if (ps == null) {
   5555                             Slog.w(PackageManagerService.TAG, "Unknown package:" + name);
   5556                             XmlUtils.skipCurrentTag(parser);
   5557                             continue;
   5558                         }
   5559                         parsePermissionsLPr(parser, ps.getPermissionsState(), userId);
   5560                     } break;
   5561 
   5562                     case TAG_SHARED_USER: {
   5563                         String name = parser.getAttributeValue(null, ATTR_NAME);
   5564                         SharedUserSetting sus = mSharedUsers.get(name);
   5565                         if (sus == null) {
   5566                             Slog.w(PackageManagerService.TAG, "Unknown shared user:" + name);
   5567                             XmlUtils.skipCurrentTag(parser);
   5568                             continue;
   5569                         }
   5570                         parsePermissionsLPr(parser, sus.getPermissionsState(), userId);
   5571                     } break;
   5572 
   5573                     case TAG_RESTORED_RUNTIME_PERMISSIONS: {
   5574                         final String pkgName = parser.getAttributeValue(null, ATTR_PACKAGE_NAME);
   5575                         parseRestoredRuntimePermissionsLPr(parser, pkgName, userId);
   5576                     } break;
   5577                 }
   5578             }
   5579         }
   5580 
   5581         private void parseRestoredRuntimePermissionsLPr(XmlPullParser parser,
   5582                 final String pkgName, final int userId) throws IOException, XmlPullParserException {
   5583             final int outerDepth = parser.getDepth();
   5584             int type;
   5585             while ((type = parser.next()) != XmlPullParser.END_DOCUMENT
   5586                     && (type != XmlPullParser.END_TAG || parser.getDepth() > outerDepth)) {
   5587                 if (type == XmlPullParser.END_TAG || type == XmlPullParser.TEXT) {
   5588                     continue;
   5589                 }
   5590 
   5591                 switch (parser.getName()) {
   5592                     case TAG_PERMISSION_ENTRY: {
   5593                         final String permName = parser.getAttributeValue(null, ATTR_NAME);
   5594                         final boolean isGranted = "true".equals(
   5595                                 parser.getAttributeValue(null, ATTR_GRANTED));
   5596 
   5597                         int permBits = 0;
   5598                         if ("true".equals(parser.getAttributeValue(null, ATTR_USER_SET))) {
   5599                             permBits |= FLAG_PERMISSION_USER_SET;
   5600                         }
   5601                         if ("true".equals(parser.getAttributeValue(null, ATTR_USER_FIXED))) {
   5602                             permBits |= FLAG_PERMISSION_USER_FIXED;
   5603                         }
   5604                         if ("true".equals(parser.getAttributeValue(null, ATTR_REVOKE_ON_UPGRADE))) {
   5605                             permBits |= FLAG_PERMISSION_REVOKE_ON_UPGRADE;
   5606                         }
   5607 
   5608                         if (isGranted || permBits != 0) {
   5609                             rememberRestoredUserGrantLPr(pkgName, permName, isGranted, permBits, userId);
   5610                         }
   5611                     } break;
   5612                 }
   5613             }
   5614         }
   5615 
   5616         private void parsePermissionsLPr(XmlPullParser parser, PermissionsState permissionsState,
   5617                 int userId) throws IOException, XmlPullParserException {
   5618             final int outerDepth = parser.getDepth();
   5619             int type;
   5620             while ((type = parser.next()) != XmlPullParser.END_DOCUMENT
   5621                     && (type != XmlPullParser.END_TAG || parser.getDepth() > outerDepth)) {
   5622                 if (type == XmlPullParser.END_TAG || type == XmlPullParser.TEXT) {
   5623                     continue;
   5624                 }
   5625 
   5626                 switch (parser.getName()) {
   5627                     case TAG_ITEM: {
   5628                         String name = parser.getAttributeValue(null, ATTR_NAME);
   5629                         BasePermission bp = mPermissions.get(name);
   5630                         if (bp == null) {
   5631                             Slog.w(PackageManagerService.TAG, "Unknown permission:" + name);
   5632                             XmlUtils.skipCurrentTag(parser);
   5633                             continue;
   5634                         }
   5635 
   5636                         String grantedStr = parser.getAttributeValue(null, ATTR_GRANTED);
   5637                         final boolean granted = grantedStr == null
   5638                                 || Boolean.parseBoolean(grantedStr);
   5639 
   5640                         String flagsStr = parser.getAttributeValue(null, ATTR_FLAGS);
   5641                         final int flags = (flagsStr != null)
   5642                                 ? Integer.parseInt(flagsStr, 16) : 0;
   5643 
   5644                         if (granted) {
   5645                             permissionsState.grantRuntimePermission(bp, userId);
   5646                             permissionsState.updatePermissionFlags(bp, userId,
   5647                                         PackageManager.MASK_PERMISSION_FLAGS, flags);
   5648                         } else {
   5649                             permissionsState.updatePermissionFlags(bp, userId,
   5650                                     PackageManager.MASK_PERMISSION_FLAGS, flags);
   5651                         }
   5652 
   5653                     } break;
   5654                 }
   5655             }
   5656         }
   5657 
   5658         private void writePermissions(XmlSerializer serializer,
   5659                 List<PermissionState> permissionStates) throws IOException {
   5660             for (PermissionState permissionState : permissionStates) {
   5661                 serializer.startTag(null, TAG_ITEM);
   5662                 serializer.attribute(null, ATTR_NAME,permissionState.getName());
   5663                 serializer.attribute(null, ATTR_GRANTED,
   5664                         String.valueOf(permissionState.isGranted()));
   5665                 serializer.attribute(null, ATTR_FLAGS,
   5666                         Integer.toHexString(permissionState.getFlags()));
   5667                 serializer.endTag(null, TAG_ITEM);
   5668             }
   5669         }
   5670 
   5671         private final class MyHandler extends Handler {
   5672             public MyHandler() {
   5673                 super(BackgroundThread.getHandler().getLooper());
   5674             }
   5675 
   5676             @Override
   5677             public void handleMessage(Message message) {
   5678                 final int userId = message.what;
   5679                 Runnable callback = (Runnable) message.obj;
   5680                 writePermissionsSync(userId);
   5681                 if (callback != null) {
   5682                     callback.run();
   5683                 }
   5684             }
   5685         }
   5686     }
   5687 }
   5688