1 /*
2  * Copyright (C) 2010 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 android.app;
18 
19 import android.annotation.DrawableRes;
20 import android.annotation.NonNull;
21 import android.annotation.Nullable;
22 import android.annotation.StringRes;
23 import android.annotation.XmlRes;
24 import android.content.ComponentName;
25 import android.content.ContentResolver;
26 import android.content.Intent;
27 import android.content.IntentFilter;
28 import android.content.IntentSender;
29 import android.content.pm.ActivityInfo;
30 import android.content.pm.ApplicationInfo;
31 import android.content.pm.ComponentInfo;
32 import android.content.pm.ContainerEncryptionParams;
33 import android.content.pm.FeatureInfo;
34 import android.content.pm.IOnPermissionsChangeListener;
35 import android.content.pm.IPackageDataObserver;
36 import android.content.pm.IPackageDeleteObserver;
37 import android.content.pm.IPackageInstallObserver;
38 import android.content.pm.IPackageManager;
39 import android.content.pm.IPackageMoveObserver;
40 import android.content.pm.IPackageStatsObserver;
41 import android.content.pm.InstrumentationInfo;
42 import android.content.pm.IntentFilterVerificationInfo;
43 import android.content.pm.KeySet;
44 import android.content.pm.ManifestDigest;
45 import android.content.pm.PackageInfo;
46 import android.content.pm.PackageInstaller;
47 import android.content.pm.PackageItemInfo;
48 import android.content.pm.PackageManager;
49 import android.content.pm.ParceledListSlice;
50 import android.content.pm.PermissionGroupInfo;
51 import android.content.pm.PermissionInfo;
52 import android.content.pm.ProviderInfo;
53 import android.content.pm.ResolveInfo;
54 import android.content.pm.ServiceInfo;
55 import android.content.pm.UserInfo;
56 import android.content.pm.VerificationParams;
57 import android.content.pm.VerifierDeviceIdentity;
58 import android.content.res.Resources;
59 import android.content.res.XmlResourceParser;
60 import android.graphics.Bitmap;
61 import android.graphics.Canvas;
62 import android.graphics.Rect;
63 import android.graphics.drawable.BitmapDrawable;
64 import android.graphics.drawable.Drawable;
65 import android.net.Uri;
66 import android.os.Bundle;
67 import android.os.Handler;
68 import android.os.Looper;
69 import android.os.Message;
70 import android.os.Process;
71 import android.os.RemoteException;
72 import android.os.SystemProperties;
73 import android.os.UserHandle;
74 import android.os.UserManager;
75 import android.os.storage.StorageManager;
76 import android.os.storage.VolumeInfo;
77 import android.util.ArrayMap;
78 import android.util.Log;
79 import android.view.Display;
80 
81 import dalvik.system.VMRuntime;
82 
83 import com.android.internal.annotations.GuardedBy;
84 import com.android.internal.os.SomeArgs;
85 import com.android.internal.util.Preconditions;
86 import com.android.internal.util.UserIcons;
87 
88 import java.lang.ref.WeakReference;
89 import java.util.ArrayList;
90 import java.util.Iterator;
91 import java.util.List;
92 import java.util.Map;
93 import java.util.Objects;
94 
95 /*package*/
96 final class ApplicationPackageManager extends PackageManager {
97     private static final String TAG = "ApplicationPackageManager";
98     private final static boolean DEBUG_ICONS = false;
99 
100     // Default flags to use with PackageManager when no flags are given.
101     private final static int sDefaultFlags = PackageManager.GET_SHARED_LIBRARY_FILES;
102 
103     private final Object mLock = new Object();
104 
105     @GuardedBy("mLock")
106     private UserManager mUserManager;
107     @GuardedBy("mLock")
108     private PackageInstaller mInstaller;
109 
110     @GuardedBy("mDelegates")
111     private final ArrayList<MoveCallbackDelegate> mDelegates = new ArrayList<>();
112 
113     @GuardedBy("mLock")
114     private String mPermissionsControllerPackageName;
115 
getUserManager()116     UserManager getUserManager() {
117         synchronized (mLock) {
118             if (mUserManager == null) {
119                 mUserManager = UserManager.get(mContext);
120             }
121             return mUserManager;
122         }
123     }
124 
125     @Override
getPackageInfo(String packageName, int flags)126     public PackageInfo getPackageInfo(String packageName, int flags)
127             throws NameNotFoundException {
128         try {
129             PackageInfo pi = mPM.getPackageInfo(packageName, flags, mContext.getUserId());
130             if (pi != null) {
131                 return pi;
132             }
133         } catch (RemoteException e) {
134             throw new RuntimeException("Package manager has died", e);
135         }
136 
137         throw new NameNotFoundException(packageName);
138     }
139 
140     @Override
currentToCanonicalPackageNames(String[] names)141     public String[] currentToCanonicalPackageNames(String[] names) {
142         try {
143             return mPM.currentToCanonicalPackageNames(names);
144         } catch (RemoteException e) {
145             throw new RuntimeException("Package manager has died", e);
146         }
147     }
148 
149     @Override
canonicalToCurrentPackageNames(String[] names)150     public String[] canonicalToCurrentPackageNames(String[] names) {
151         try {
152             return mPM.canonicalToCurrentPackageNames(names);
153         } catch (RemoteException e) {
154             throw new RuntimeException("Package manager has died", e);
155         }
156     }
157 
158     @Override
getLaunchIntentForPackage(String packageName)159     public Intent getLaunchIntentForPackage(String packageName) {
160         // First see if the package has an INFO activity; the existence of
161         // such an activity is implied to be the desired front-door for the
162         // overall package (such as if it has multiple launcher entries).
163         Intent intentToResolve = new Intent(Intent.ACTION_MAIN);
164         intentToResolve.addCategory(Intent.CATEGORY_INFO);
165         intentToResolve.setPackage(packageName);
166         List<ResolveInfo> ris = queryIntentActivities(intentToResolve, 0);
167 
168         // Otherwise, try to find a main launcher activity.
169         if (ris == null || ris.size() <= 0) {
170             // reuse the intent instance
171             intentToResolve.removeCategory(Intent.CATEGORY_INFO);
172             intentToResolve.addCategory(Intent.CATEGORY_LAUNCHER);
173             intentToResolve.setPackage(packageName);
174             ris = queryIntentActivities(intentToResolve, 0);
175         }
176         if (ris == null || ris.size() <= 0) {
177             return null;
178         }
179         Intent intent = new Intent(intentToResolve);
180         intent.setFlags(Intent.FLAG_ACTIVITY_NEW_TASK);
181         intent.setClassName(ris.get(0).activityInfo.packageName,
182                 ris.get(0).activityInfo.name);
183         return intent;
184     }
185 
186     @Override
getLeanbackLaunchIntentForPackage(String packageName)187     public Intent getLeanbackLaunchIntentForPackage(String packageName) {
188         // Try to find a main leanback_launcher activity.
189         Intent intentToResolve = new Intent(Intent.ACTION_MAIN);
190         intentToResolve.addCategory(Intent.CATEGORY_LEANBACK_LAUNCHER);
191         intentToResolve.setPackage(packageName);
192         List<ResolveInfo> ris = queryIntentActivities(intentToResolve, 0);
193 
194         if (ris == null || ris.size() <= 0) {
195             return null;
196         }
197         Intent intent = new Intent(intentToResolve);
198         intent.setFlags(Intent.FLAG_ACTIVITY_NEW_TASK);
199         intent.setClassName(ris.get(0).activityInfo.packageName,
200                 ris.get(0).activityInfo.name);
201         return intent;
202     }
203 
204     @Override
getPackageGids(String packageName)205     public int[] getPackageGids(String packageName)
206             throws NameNotFoundException {
207         try {
208             int[] gids = mPM.getPackageGids(packageName, mContext.getUserId());
209             if (gids != null) {
210                 return gids;
211             }
212         } catch (RemoteException e) {
213             throw new RuntimeException("Package manager has died", e);
214         }
215 
216         throw new NameNotFoundException(packageName);
217     }
218 
219     @Override
getPackageUid(String packageName, int userHandle)220     public int getPackageUid(String packageName, int userHandle)
221             throws NameNotFoundException {
222         try {
223             int uid = mPM.getPackageUid(packageName, userHandle);
224             if (uid >= 0) {
225                 return uid;
226             }
227         } catch (RemoteException e) {
228             throw new RuntimeException("Package manager has died", e);
229         }
230 
231         throw new NameNotFoundException(packageName);
232     }
233 
234     @Override
getPermissionInfo(String name, int flags)235     public PermissionInfo getPermissionInfo(String name, int flags)
236             throws NameNotFoundException {
237         try {
238             PermissionInfo pi = mPM.getPermissionInfo(name, flags);
239             if (pi != null) {
240                 return pi;
241             }
242         } catch (RemoteException e) {
243             throw new RuntimeException("Package manager has died", e);
244         }
245 
246         throw new NameNotFoundException(name);
247     }
248 
249     @Override
queryPermissionsByGroup(String group, int flags)250     public List<PermissionInfo> queryPermissionsByGroup(String group, int flags)
251             throws NameNotFoundException {
252         try {
253             List<PermissionInfo> pi = mPM.queryPermissionsByGroup(group, flags);
254             if (pi != null) {
255                 return pi;
256             }
257         } catch (RemoteException e) {
258             throw new RuntimeException("Package manager has died", e);
259         }
260 
261         throw new NameNotFoundException(group);
262     }
263 
264     @Override
getPermissionGroupInfo(String name, int flags)265     public PermissionGroupInfo getPermissionGroupInfo(String name,
266                                                       int flags) throws NameNotFoundException {
267         try {
268             PermissionGroupInfo pgi = mPM.getPermissionGroupInfo(name, flags);
269             if (pgi != null) {
270                 return pgi;
271             }
272         } catch (RemoteException e) {
273             throw new RuntimeException("Package manager has died", e);
274         }
275 
276         throw new NameNotFoundException(name);
277     }
278 
279     @Override
getAllPermissionGroups(int flags)280     public List<PermissionGroupInfo> getAllPermissionGroups(int flags) {
281         try {
282             return mPM.getAllPermissionGroups(flags);
283         } catch (RemoteException e) {
284             throw new RuntimeException("Package manager has died", e);
285         }
286     }
287 
288     @Override
getApplicationInfo(String packageName, int flags)289     public ApplicationInfo getApplicationInfo(String packageName, int flags)
290             throws NameNotFoundException {
291         try {
292             ApplicationInfo ai = mPM.getApplicationInfo(packageName, flags, mContext.getUserId());
293             if (ai != null) {
294                 // This is a temporary hack. Callers must use
295                 // createPackageContext(packageName).getApplicationInfo() to
296                 // get the right paths.
297                 maybeAdjustApplicationInfo(ai);
298                 return ai;
299             }
300         } catch (RemoteException e) {
301             throw new RuntimeException("Package manager has died", e);
302         }
303 
304         throw new NameNotFoundException(packageName);
305     }
306 
maybeAdjustApplicationInfo(ApplicationInfo info)307     private static void maybeAdjustApplicationInfo(ApplicationInfo info) {
308         // If we're dealing with a multi-arch application that has both
309         // 32 and 64 bit shared libraries, we might need to choose the secondary
310         // depending on what the current runtime's instruction set is.
311         if (info.primaryCpuAbi != null && info.secondaryCpuAbi != null) {
312             final String runtimeIsa = VMRuntime.getRuntime().vmInstructionSet();
313 
314             // Get the instruction set that the libraries of secondary Abi is supported.
315             // In presence of a native bridge this might be different than the one secondary Abi used.
316             String secondaryIsa = VMRuntime.getInstructionSet(info.secondaryCpuAbi);
317             final String secondaryDexCodeIsa = SystemProperties.get("ro.dalvik.vm.isa." + secondaryIsa);
318             secondaryIsa = secondaryDexCodeIsa.isEmpty() ? secondaryIsa : secondaryDexCodeIsa;
319 
320             // If the runtimeIsa is the same as the primary isa, then we do nothing.
321             // Everything will be set up correctly because info.nativeLibraryDir will
322             // correspond to the right ISA.
323             if (runtimeIsa.equals(secondaryIsa)) {
324                 info.nativeLibraryDir = info.secondaryNativeLibraryDir;
325             }
326         }
327     }
328 
329 
330     @Override
getActivityInfo(ComponentName className, int flags)331     public ActivityInfo getActivityInfo(ComponentName className, int flags)
332             throws NameNotFoundException {
333         try {
334             ActivityInfo ai = mPM.getActivityInfo(className, flags, mContext.getUserId());
335             if (ai != null) {
336                 return ai;
337             }
338         } catch (RemoteException e) {
339             throw new RuntimeException("Package manager has died", e);
340         }
341 
342         throw new NameNotFoundException(className.toString());
343     }
344 
345     @Override
getReceiverInfo(ComponentName className, int flags)346     public ActivityInfo getReceiverInfo(ComponentName className, int flags)
347             throws NameNotFoundException {
348         try {
349             ActivityInfo ai = mPM.getReceiverInfo(className, flags, mContext.getUserId());
350             if (ai != null) {
351                 return ai;
352             }
353         } catch (RemoteException e) {
354             throw new RuntimeException("Package manager has died", e);
355         }
356 
357         throw new NameNotFoundException(className.toString());
358     }
359 
360     @Override
getServiceInfo(ComponentName className, int flags)361     public ServiceInfo getServiceInfo(ComponentName className, int flags)
362             throws NameNotFoundException {
363         try {
364             ServiceInfo si = mPM.getServiceInfo(className, flags, mContext.getUserId());
365             if (si != null) {
366                 return si;
367             }
368         } catch (RemoteException e) {
369             throw new RuntimeException("Package manager has died", e);
370         }
371 
372         throw new NameNotFoundException(className.toString());
373     }
374 
375     @Override
getProviderInfo(ComponentName className, int flags)376     public ProviderInfo getProviderInfo(ComponentName className, int flags)
377             throws NameNotFoundException {
378         try {
379             ProviderInfo pi = mPM.getProviderInfo(className, flags, mContext.getUserId());
380             if (pi != null) {
381                 return pi;
382             }
383         } catch (RemoteException e) {
384             throw new RuntimeException("Package manager has died", e);
385         }
386 
387         throw new NameNotFoundException(className.toString());
388     }
389 
390     @Override
getSystemSharedLibraryNames()391     public String[] getSystemSharedLibraryNames() {
392         try {
393             return mPM.getSystemSharedLibraryNames();
394         } catch (RemoteException e) {
395             throw new RuntimeException("Package manager has died", e);
396         }
397     }
398 
399     @Override
getSystemAvailableFeatures()400     public FeatureInfo[] getSystemAvailableFeatures() {
401         try {
402             return mPM.getSystemAvailableFeatures();
403         } catch (RemoteException e) {
404             throw new RuntimeException("Package manager has died", e);
405         }
406     }
407 
408     @Override
hasSystemFeature(String name)409     public boolean hasSystemFeature(String name) {
410         try {
411             return mPM.hasSystemFeature(name);
412         } catch (RemoteException e) {
413             throw new RuntimeException("Package manager has died", e);
414         }
415     }
416 
417     @Override
checkPermission(String permName, String pkgName)418     public int checkPermission(String permName, String pkgName) {
419         try {
420             return mPM.checkPermission(permName, pkgName, mContext.getUserId());
421         } catch (RemoteException e) {
422             throw new RuntimeException("Package manager has died", e);
423         }
424     }
425 
426     @Override
isPermissionRevokedByPolicy(String permName, String pkgName)427     public boolean isPermissionRevokedByPolicy(String permName, String pkgName) {
428         try {
429             return mPM.isPermissionRevokedByPolicy(permName, pkgName, mContext.getUserId());
430         } catch (RemoteException e) {
431             throw new RuntimeException("Package manager has died", e);
432         }
433     }
434 
435     /**
436      * @hide
437      */
438     @Override
getPermissionControllerPackageName()439     public String getPermissionControllerPackageName() {
440         synchronized (mLock) {
441             if (mPermissionsControllerPackageName == null) {
442                 try {
443                     mPermissionsControllerPackageName = mPM.getPermissionControllerPackageName();
444                 } catch (RemoteException e) {
445                     throw new RuntimeException("Package manager has died", e);
446                 }
447             }
448             return mPermissionsControllerPackageName;
449         }
450     }
451 
452     @Override
addPermission(PermissionInfo info)453     public boolean addPermission(PermissionInfo info) {
454         try {
455             return mPM.addPermission(info);
456         } catch (RemoteException e) {
457             throw new RuntimeException("Package manager has died", e);
458         }
459     }
460 
461     @Override
addPermissionAsync(PermissionInfo info)462     public boolean addPermissionAsync(PermissionInfo info) {
463         try {
464             return mPM.addPermissionAsync(info);
465         } catch (RemoteException e) {
466             throw new RuntimeException("Package manager has died", e);
467         }
468     }
469 
470     @Override
removePermission(String name)471     public void removePermission(String name) {
472         try {
473             mPM.removePermission(name);
474         } catch (RemoteException e) {
475             throw new RuntimeException("Package manager has died", e);
476         }
477     }
478 
479     @Override
grantRuntimePermission(String packageName, String permissionName, UserHandle user)480     public void grantRuntimePermission(String packageName, String permissionName,
481             UserHandle user) {
482         try {
483             mPM.grantRuntimePermission(packageName, permissionName, user.getIdentifier());
484         } catch (RemoteException e) {
485             throw new RuntimeException("Package manager has died", e);
486         }
487     }
488 
489     @Override
revokeRuntimePermission(String packageName, String permissionName, UserHandle user)490     public void revokeRuntimePermission(String packageName, String permissionName,
491             UserHandle user) {
492         try {
493             mPM.revokeRuntimePermission(packageName, permissionName, user.getIdentifier());
494         } catch (RemoteException e) {
495             throw new RuntimeException("Package manager has died", e);
496         }
497     }
498 
499     @Override
getPermissionFlags(String permissionName, String packageName, UserHandle user)500     public int getPermissionFlags(String permissionName, String packageName, UserHandle user) {
501         try {
502             return mPM.getPermissionFlags(permissionName, packageName, user.getIdentifier());
503         } catch (RemoteException e) {
504             throw new RuntimeException("Package manager has died", e);
505         }
506     }
507 
508     @Override
updatePermissionFlags(String permissionName, String packageName, int flagMask, int flagValues, UserHandle user)509     public void updatePermissionFlags(String permissionName, String packageName,
510             int flagMask, int flagValues, UserHandle user) {
511         try {
512             mPM.updatePermissionFlags(permissionName, packageName, flagMask,
513                     flagValues, user.getIdentifier());
514         } catch (RemoteException e) {
515             throw new RuntimeException("Package manager has died", e);
516         }
517     }
518 
519     @Override
shouldShowRequestPermissionRationale(String permission)520     public boolean shouldShowRequestPermissionRationale(String permission) {
521         try {
522             return mPM.shouldShowRequestPermissionRationale(permission,
523                     mContext.getPackageName(), mContext.getUserId());
524         } catch (RemoteException e) {
525             throw new RuntimeException("Package manager has died", e);
526         }
527     }
528 
529     @Override
checkSignatures(String pkg1, String pkg2)530     public int checkSignatures(String pkg1, String pkg2) {
531         try {
532             return mPM.checkSignatures(pkg1, pkg2);
533         } catch (RemoteException e) {
534             throw new RuntimeException("Package manager has died", e);
535         }
536     }
537 
538     @Override
checkSignatures(int uid1, int uid2)539     public int checkSignatures(int uid1, int uid2) {
540         try {
541             return mPM.checkUidSignatures(uid1, uid2);
542         } catch (RemoteException e) {
543             throw new RuntimeException("Package manager has died", e);
544         }
545     }
546 
547     @Override
getPackagesForUid(int uid)548     public String[] getPackagesForUid(int uid) {
549         try {
550             return mPM.getPackagesForUid(uid);
551         } catch (RemoteException e) {
552             throw new RuntimeException("Package manager has died", e);
553         }
554     }
555 
556     @Override
getNameForUid(int uid)557     public String getNameForUid(int uid) {
558         try {
559             return mPM.getNameForUid(uid);
560         } catch (RemoteException e) {
561             throw new RuntimeException("Package manager has died", e);
562         }
563     }
564 
565     @Override
getUidForSharedUser(String sharedUserName)566     public int getUidForSharedUser(String sharedUserName)
567             throws NameNotFoundException {
568         try {
569             int uid = mPM.getUidForSharedUser(sharedUserName);
570             if(uid != -1) {
571                 return uid;
572             }
573         } catch (RemoteException e) {
574             throw new RuntimeException("Package manager has died", e);
575         }
576         throw new NameNotFoundException("No shared userid for user:"+sharedUserName);
577     }
578 
579     @SuppressWarnings("unchecked")
580     @Override
getInstalledPackages(int flags)581     public List<PackageInfo> getInstalledPackages(int flags) {
582         return getInstalledPackages(flags, mContext.getUserId());
583     }
584 
585     /** @hide */
586     @Override
getInstalledPackages(int flags, int userId)587     public List<PackageInfo> getInstalledPackages(int flags, int userId) {
588         try {
589             ParceledListSlice<PackageInfo> slice = mPM.getInstalledPackages(flags, userId);
590             return slice.getList();
591         } catch (RemoteException e) {
592             throw new RuntimeException("Package manager has died", e);
593         }
594     }
595 
596     @SuppressWarnings("unchecked")
597     @Override
getPackagesHoldingPermissions( String[] permissions, int flags)598     public List<PackageInfo> getPackagesHoldingPermissions(
599             String[] permissions, int flags) {
600         final int userId = mContext.getUserId();
601         try {
602             ParceledListSlice<PackageInfo> slice = mPM.getPackagesHoldingPermissions(
603                     permissions, flags, userId);
604             return slice.getList();
605         } catch (RemoteException e) {
606             throw new RuntimeException("Package manager has died", e);
607         }
608     }
609 
610     @SuppressWarnings("unchecked")
611     @Override
getInstalledApplications(int flags)612     public List<ApplicationInfo> getInstalledApplications(int flags) {
613         final int userId = mContext.getUserId();
614         try {
615             ParceledListSlice<ApplicationInfo> slice = mPM.getInstalledApplications(flags, userId);
616             return slice.getList();
617         } catch (RemoteException e) {
618             throw new RuntimeException("Package manager has died", e);
619         }
620     }
621 
622     @Override
resolveActivity(Intent intent, int flags)623     public ResolveInfo resolveActivity(Intent intent, int flags) {
624         return resolveActivityAsUser(intent, flags, mContext.getUserId());
625     }
626 
627     @Override
resolveActivityAsUser(Intent intent, int flags, int userId)628     public ResolveInfo resolveActivityAsUser(Intent intent, int flags, int userId) {
629         try {
630             return mPM.resolveIntent(
631                 intent,
632                 intent.resolveTypeIfNeeded(mContext.getContentResolver()),
633                 flags,
634                 userId);
635         } catch (RemoteException e) {
636             throw new RuntimeException("Package manager has died", e);
637         }
638     }
639 
640     @Override
queryIntentActivities(Intent intent, int flags)641     public List<ResolveInfo> queryIntentActivities(Intent intent,
642                                                    int flags) {
643         return queryIntentActivitiesAsUser(intent, flags, mContext.getUserId());
644     }
645 
646     /** @hide Same as above but for a specific user */
647     @Override
queryIntentActivitiesAsUser(Intent intent, int flags, int userId)648     public List<ResolveInfo> queryIntentActivitiesAsUser(Intent intent,
649                                                    int flags, int userId) {
650         try {
651             return mPM.queryIntentActivities(
652                 intent,
653                 intent.resolveTypeIfNeeded(mContext.getContentResolver()),
654                 flags,
655                 userId);
656         } catch (RemoteException e) {
657             throw new RuntimeException("Package manager has died", e);
658         }
659     }
660 
661     @Override
queryIntentActivityOptions( ComponentName caller, Intent[] specifics, Intent intent, int flags)662     public List<ResolveInfo> queryIntentActivityOptions(
663         ComponentName caller, Intent[] specifics, Intent intent,
664         int flags) {
665         final ContentResolver resolver = mContext.getContentResolver();
666 
667         String[] specificTypes = null;
668         if (specifics != null) {
669             final int N = specifics.length;
670             for (int i=0; i<N; i++) {
671                 Intent sp = specifics[i];
672                 if (sp != null) {
673                     String t = sp.resolveTypeIfNeeded(resolver);
674                     if (t != null) {
675                         if (specificTypes == null) {
676                             specificTypes = new String[N];
677                         }
678                         specificTypes[i] = t;
679                     }
680                 }
681             }
682         }
683 
684         try {
685             return mPM.queryIntentActivityOptions(caller, specifics,
686                                                   specificTypes, intent, intent.resolveTypeIfNeeded(resolver),
687                                                   flags, mContext.getUserId());
688         } catch (RemoteException e) {
689             throw new RuntimeException("Package manager has died", e);
690         }
691     }
692 
693     /**
694      * @hide
695      */
696     @Override
queryBroadcastReceivers(Intent intent, int flags, int userId)697     public List<ResolveInfo> queryBroadcastReceivers(Intent intent, int flags, int userId) {
698         try {
699             return mPM.queryIntentReceivers(
700                 intent,
701                 intent.resolveTypeIfNeeded(mContext.getContentResolver()),
702                 flags,
703                 userId);
704         } catch (RemoteException e) {
705             throw new RuntimeException("Package manager has died", e);
706         }
707     }
708 
709     @Override
queryBroadcastReceivers(Intent intent, int flags)710     public List<ResolveInfo> queryBroadcastReceivers(Intent intent, int flags) {
711         return queryBroadcastReceivers(intent, flags, mContext.getUserId());
712     }
713 
714     @Override
resolveService(Intent intent, int flags)715     public ResolveInfo resolveService(Intent intent, int flags) {
716         try {
717             return mPM.resolveService(
718                 intent,
719                 intent.resolveTypeIfNeeded(mContext.getContentResolver()),
720                 flags,
721                 mContext.getUserId());
722         } catch (RemoteException e) {
723             throw new RuntimeException("Package manager has died", e);
724         }
725     }
726 
727     @Override
queryIntentServicesAsUser(Intent intent, int flags, int userId)728     public List<ResolveInfo> queryIntentServicesAsUser(Intent intent, int flags, int userId) {
729         try {
730             return mPM.queryIntentServices(
731                 intent,
732                 intent.resolveTypeIfNeeded(mContext.getContentResolver()),
733                 flags,
734                 userId);
735         } catch (RemoteException e) {
736             throw new RuntimeException("Package manager has died", e);
737         }
738     }
739 
740     @Override
queryIntentServices(Intent intent, int flags)741     public List<ResolveInfo> queryIntentServices(Intent intent, int flags) {
742         return queryIntentServicesAsUser(intent, flags, mContext.getUserId());
743     }
744 
745     @Override
queryIntentContentProvidersAsUser( Intent intent, int flags, int userId)746     public List<ResolveInfo> queryIntentContentProvidersAsUser(
747             Intent intent, int flags, int userId) {
748         try {
749             return mPM.queryIntentContentProviders(intent,
750                     intent.resolveTypeIfNeeded(mContext.getContentResolver()), flags, userId);
751         } catch (RemoteException e) {
752             throw new RuntimeException("Package manager has died", e);
753         }
754     }
755 
756     @Override
queryIntentContentProviders(Intent intent, int flags)757     public List<ResolveInfo> queryIntentContentProviders(Intent intent, int flags) {
758         return queryIntentContentProvidersAsUser(intent, flags, mContext.getUserId());
759     }
760 
761     @Override
resolveContentProvider(String name, int flags)762     public ProviderInfo resolveContentProvider(String name, int flags) {
763         return resolveContentProviderAsUser(name, flags, mContext.getUserId());
764     }
765 
766     /** @hide **/
767     @Override
resolveContentProviderAsUser(String name, int flags, int userId)768     public ProviderInfo resolveContentProviderAsUser(String name, int flags, int userId) {
769         try {
770             return mPM.resolveContentProvider(name, flags, userId);
771         } catch (RemoteException e) {
772             throw new RuntimeException("Package manager has died", e);
773         }
774     }
775 
776     @Override
queryContentProviders(String processName, int uid, int flags)777     public List<ProviderInfo> queryContentProviders(String processName,
778                                                     int uid, int flags) {
779         try {
780             ParceledListSlice<ProviderInfo> slice
781                     = mPM.queryContentProviders(processName, uid, flags);
782             return slice != null ? slice.getList() : null;
783         } catch (RemoteException e) {
784             throw new RuntimeException("Package manager has died", e);
785         }
786     }
787 
788     @Override
getInstrumentationInfo( ComponentName className, int flags)789     public InstrumentationInfo getInstrumentationInfo(
790         ComponentName className, int flags)
791             throws NameNotFoundException {
792         try {
793             InstrumentationInfo ii = mPM.getInstrumentationInfo(
794                 className, flags);
795             if (ii != null) {
796                 return ii;
797             }
798         } catch (RemoteException e) {
799             throw new RuntimeException("Package manager has died", e);
800         }
801 
802         throw new NameNotFoundException(className.toString());
803     }
804 
805     @Override
queryInstrumentation( String targetPackage, int flags)806     public List<InstrumentationInfo> queryInstrumentation(
807         String targetPackage, int flags) {
808         try {
809             return mPM.queryInstrumentation(targetPackage, flags);
810         } catch (RemoteException e) {
811             throw new RuntimeException("Package manager has died", e);
812         }
813     }
814 
815     @Nullable
816     @Override
getDrawable(String packageName, @DrawableRes int resId, @Nullable ApplicationInfo appInfo)817     public Drawable getDrawable(String packageName, @DrawableRes int resId,
818             @Nullable ApplicationInfo appInfo) {
819         final ResourceName name = new ResourceName(packageName, resId);
820         final Drawable cachedIcon = getCachedIcon(name);
821         if (cachedIcon != null) {
822             return cachedIcon;
823         }
824 
825         if (appInfo == null) {
826             try {
827                 appInfo = getApplicationInfo(packageName, sDefaultFlags);
828             } catch (NameNotFoundException e) {
829                 return null;
830             }
831         }
832 
833         if (resId != 0) {
834             try {
835                 final Resources r = getResourcesForApplication(appInfo);
836                 final Drawable dr = r.getDrawable(resId, null);
837                 if (dr != null) {
838                     putCachedIcon(name, dr);
839                 }
840 
841                 if (false) {
842                     RuntimeException e = new RuntimeException("here");
843                     e.fillInStackTrace();
844                     Log.w(TAG, "Getting drawable 0x" + Integer.toHexString(resId)
845                                     + " from package " + packageName
846                                     + ": app scale=" + r.getCompatibilityInfo().applicationScale
847                                     + ", caller scale=" + mContext.getResources()
848                                     .getCompatibilityInfo().applicationScale,
849                             e);
850                 }
851                 if (DEBUG_ICONS) {
852                     Log.v(TAG, "Getting drawable 0x"
853                             + Integer.toHexString(resId) + " from " + r
854                             + ": " + dr);
855                 }
856                 return dr;
857             } catch (NameNotFoundException e) {
858                 Log.w("PackageManager", "Failure retrieving resources for "
859                         + appInfo.packageName);
860             } catch (Resources.NotFoundException e) {
861                 Log.w("PackageManager", "Failure retrieving resources for "
862                         + appInfo.packageName + ": " + e.getMessage());
863             } catch (Exception e) {
864                 // If an exception was thrown, fall through to return
865                 // default icon.
866                 Log.w("PackageManager", "Failure retrieving icon 0x"
867                         + Integer.toHexString(resId) + " in package "
868                         + packageName, e);
869             }
870         }
871 
872         return null;
873     }
874 
getActivityIcon(ComponentName activityName)875     @Override public Drawable getActivityIcon(ComponentName activityName)
876             throws NameNotFoundException {
877         return getActivityInfo(activityName, sDefaultFlags).loadIcon(this);
878     }
879 
getActivityIcon(Intent intent)880     @Override public Drawable getActivityIcon(Intent intent)
881             throws NameNotFoundException {
882         if (intent.getComponent() != null) {
883             return getActivityIcon(intent.getComponent());
884         }
885 
886         ResolveInfo info = resolveActivity(
887             intent, PackageManager.MATCH_DEFAULT_ONLY);
888         if (info != null) {
889             return info.activityInfo.loadIcon(this);
890         }
891 
892         throw new NameNotFoundException(intent.toUri(0));
893     }
894 
getDefaultActivityIcon()895     @Override public Drawable getDefaultActivityIcon() {
896         return Resources.getSystem().getDrawable(
897             com.android.internal.R.drawable.sym_def_app_icon);
898     }
899 
getApplicationIcon(ApplicationInfo info)900     @Override public Drawable getApplicationIcon(ApplicationInfo info) {
901         return info.loadIcon(this);
902     }
903 
getApplicationIcon(String packageName)904     @Override public Drawable getApplicationIcon(String packageName)
905             throws NameNotFoundException {
906         return getApplicationIcon(getApplicationInfo(packageName, sDefaultFlags));
907     }
908 
909     @Override
getActivityBanner(ComponentName activityName)910     public Drawable getActivityBanner(ComponentName activityName)
911             throws NameNotFoundException {
912         return getActivityInfo(activityName, sDefaultFlags).loadBanner(this);
913     }
914 
915     @Override
getActivityBanner(Intent intent)916     public Drawable getActivityBanner(Intent intent)
917             throws NameNotFoundException {
918         if (intent.getComponent() != null) {
919             return getActivityBanner(intent.getComponent());
920         }
921 
922         ResolveInfo info = resolveActivity(
923                 intent, PackageManager.MATCH_DEFAULT_ONLY);
924         if (info != null) {
925             return info.activityInfo.loadBanner(this);
926         }
927 
928         throw new NameNotFoundException(intent.toUri(0));
929     }
930 
931     @Override
getApplicationBanner(ApplicationInfo info)932     public Drawable getApplicationBanner(ApplicationInfo info) {
933         return info.loadBanner(this);
934     }
935 
936     @Override
getApplicationBanner(String packageName)937     public Drawable getApplicationBanner(String packageName)
938             throws NameNotFoundException {
939         return getApplicationBanner(getApplicationInfo(packageName, sDefaultFlags));
940     }
941 
942     @Override
getActivityLogo(ComponentName activityName)943     public Drawable getActivityLogo(ComponentName activityName)
944             throws NameNotFoundException {
945         return getActivityInfo(activityName, sDefaultFlags).loadLogo(this);
946     }
947 
948     @Override
getActivityLogo(Intent intent)949     public Drawable getActivityLogo(Intent intent)
950             throws NameNotFoundException {
951         if (intent.getComponent() != null) {
952             return getActivityLogo(intent.getComponent());
953         }
954 
955         ResolveInfo info = resolveActivity(
956             intent, PackageManager.MATCH_DEFAULT_ONLY);
957         if (info != null) {
958             return info.activityInfo.loadLogo(this);
959         }
960 
961         throw new NameNotFoundException(intent.toUri(0));
962     }
963 
964     @Override
getApplicationLogo(ApplicationInfo info)965     public Drawable getApplicationLogo(ApplicationInfo info) {
966         return info.loadLogo(this);
967     }
968 
969     @Override
getApplicationLogo(String packageName)970     public Drawable getApplicationLogo(String packageName)
971             throws NameNotFoundException {
972         return getApplicationLogo(getApplicationInfo(packageName, sDefaultFlags));
973     }
974 
975     @Override
getUserBadgedIcon(Drawable icon, UserHandle user)976     public Drawable getUserBadgedIcon(Drawable icon, UserHandle user) {
977         final int badgeResId = getBadgeResIdForUser(user.getIdentifier());
978         if (badgeResId == 0) {
979             return icon;
980         }
981         Drawable badgeIcon = getDrawable("system", badgeResId, null);
982         return getBadgedDrawable(icon, badgeIcon, null, true);
983     }
984 
985     @Override
getUserBadgedDrawableForDensity(Drawable drawable, UserHandle user, Rect badgeLocation, int badgeDensity)986     public Drawable getUserBadgedDrawableForDensity(Drawable drawable, UserHandle user,
987             Rect badgeLocation, int badgeDensity) {
988         Drawable badgeDrawable = getUserBadgeForDensity(user, badgeDensity);
989         if (badgeDrawable == null) {
990             return drawable;
991         }
992         return getBadgedDrawable(drawable, badgeDrawable, badgeLocation, true);
993     }
994 
995     @Override
getUserBadgeForDensity(UserHandle user, int density)996     public Drawable getUserBadgeForDensity(UserHandle user, int density) {
997         UserInfo userInfo = getUserIfProfile(user.getIdentifier());
998         if (userInfo != null && userInfo.isManagedProfile()) {
999             if (density <= 0) {
1000                 density = mContext.getResources().getDisplayMetrics().densityDpi;
1001             }
1002             return Resources.getSystem().getDrawableForDensity(
1003                     com.android.internal.R.drawable.ic_corp_badge, density);
1004         }
1005         return null;
1006     }
1007 
1008     @Override
getUserBadgedLabel(CharSequence label, UserHandle user)1009     public CharSequence getUserBadgedLabel(CharSequence label, UserHandle user) {
1010         UserInfo userInfo = getUserIfProfile(user.getIdentifier());
1011         if (userInfo != null && userInfo.isManagedProfile()) {
1012             return Resources.getSystem().getString(
1013                     com.android.internal.R.string.managed_profile_label_badge, label);
1014         }
1015         return label;
1016     }
1017 
1018     @Override
getResourcesForActivity(ComponentName activityName)1019     public Resources getResourcesForActivity(ComponentName activityName)
1020             throws NameNotFoundException {
1021         return getResourcesForApplication(
1022             getActivityInfo(activityName, sDefaultFlags).applicationInfo);
1023     }
1024 
1025     @Override
getResourcesForApplication(@onNull ApplicationInfo app)1026     public Resources getResourcesForApplication(@NonNull ApplicationInfo app)
1027             throws NameNotFoundException {
1028         if (app.packageName.equals("system")) {
1029             return mContext.mMainThread.getSystemContext().getResources();
1030         }
1031         final boolean sameUid = (app.uid == Process.myUid());
1032         final Resources r = mContext.mMainThread.getTopLevelResources(
1033                 sameUid ? app.sourceDir : app.publicSourceDir,
1034                 sameUid ? app.splitSourceDirs : app.splitPublicSourceDirs,
1035                 app.resourceDirs, app.sharedLibraryFiles, Display.DEFAULT_DISPLAY,
1036                 null, mContext.mPackageInfo);
1037         if (r != null) {
1038             return r;
1039         }
1040         throw new NameNotFoundException("Unable to open " + app.publicSourceDir);
1041     }
1042 
1043     @Override
getResourcesForApplication(String appPackageName)1044     public Resources getResourcesForApplication(String appPackageName)
1045             throws NameNotFoundException {
1046         return getResourcesForApplication(
1047             getApplicationInfo(appPackageName, sDefaultFlags));
1048     }
1049 
1050     /** @hide */
1051     @Override
getResourcesForApplicationAsUser(String appPackageName, int userId)1052     public Resources getResourcesForApplicationAsUser(String appPackageName, int userId)
1053             throws NameNotFoundException {
1054         if (userId < 0) {
1055             throw new IllegalArgumentException(
1056                     "Call does not support special user #" + userId);
1057         }
1058         if ("system".equals(appPackageName)) {
1059             return mContext.mMainThread.getSystemContext().getResources();
1060         }
1061         try {
1062             ApplicationInfo ai = mPM.getApplicationInfo(appPackageName, sDefaultFlags, userId);
1063             if (ai != null) {
1064                 return getResourcesForApplication(ai);
1065             }
1066         } catch (RemoteException e) {
1067             throw new RuntimeException("Package manager has died", e);
1068         }
1069         throw new NameNotFoundException("Package " + appPackageName + " doesn't exist");
1070     }
1071 
1072     int mCachedSafeMode = -1;
isSafeMode()1073     @Override public boolean isSafeMode() {
1074         try {
1075             if (mCachedSafeMode < 0) {
1076                 mCachedSafeMode = mPM.isSafeMode() ? 1 : 0;
1077             }
1078             return mCachedSafeMode != 0;
1079         } catch (RemoteException e) {
1080             throw new RuntimeException("Package manager has died", e);
1081         }
1082     }
1083 
1084     @Override
addOnPermissionsChangeListener(OnPermissionsChangedListener listener)1085     public void addOnPermissionsChangeListener(OnPermissionsChangedListener listener) {
1086         synchronized (mPermissionListeners) {
1087             if (mPermissionListeners.get(listener) != null) {
1088                 return;
1089             }
1090             OnPermissionsChangeListenerDelegate delegate =
1091                     new OnPermissionsChangeListenerDelegate(listener, Looper.getMainLooper());
1092             try {
1093                 mPM.addOnPermissionsChangeListener(delegate);
1094                 mPermissionListeners.put(listener, delegate);
1095             } catch (RemoteException e) {
1096                 throw new RuntimeException("Package manager has died", e);
1097             }
1098         }
1099     }
1100 
1101     @Override
removeOnPermissionsChangeListener(OnPermissionsChangedListener listener)1102     public void removeOnPermissionsChangeListener(OnPermissionsChangedListener listener) {
1103         synchronized (mPermissionListeners) {
1104             IOnPermissionsChangeListener delegate = mPermissionListeners.get(listener);
1105             if (delegate != null) {
1106                 try {
1107                     mPM.removeOnPermissionsChangeListener(delegate);
1108                     mPermissionListeners.remove(listener);
1109                 } catch (RemoteException e) {
1110                     throw new RuntimeException("Package manager has died", e);
1111                 }
1112             }
1113         }
1114     }
1115 
configurationChanged()1116     static void configurationChanged() {
1117         synchronized (sSync) {
1118             sIconCache.clear();
1119             sStringCache.clear();
1120         }
1121     }
1122 
ApplicationPackageManager(ContextImpl context, IPackageManager pm)1123     ApplicationPackageManager(ContextImpl context,
1124                               IPackageManager pm) {
1125         mContext = context;
1126         mPM = pm;
1127     }
1128 
1129     @Nullable
getCachedIcon(@onNull ResourceName name)1130     private Drawable getCachedIcon(@NonNull ResourceName name) {
1131         synchronized (sSync) {
1132             final WeakReference<Drawable.ConstantState> wr = sIconCache.get(name);
1133             if (DEBUG_ICONS) Log.v(TAG, "Get cached weak drawable ref for "
1134                                    + name + ": " + wr);
1135             if (wr != null) {   // we have the activity
1136                 final Drawable.ConstantState state = wr.get();
1137                 if (state != null) {
1138                     if (DEBUG_ICONS) {
1139                         Log.v(TAG, "Get cached drawable state for " + name + ": " + state);
1140                     }
1141                     // Note: It's okay here to not use the newDrawable(Resources) variant
1142                     //       of the API. The ConstantState comes from a drawable that was
1143                     //       originally created by passing the proper app Resources instance
1144                     //       which means the state should already contain the proper
1145                     //       resources specific information (like density.) See
1146                     //       BitmapDrawable.BitmapState for instance.
1147                     return state.newDrawable();
1148                 }
1149                 // our entry has been purged
1150                 sIconCache.remove(name);
1151             }
1152         }
1153         return null;
1154     }
1155 
putCachedIcon(@onNull ResourceName name, @NonNull Drawable dr)1156     private void putCachedIcon(@NonNull ResourceName name, @NonNull Drawable dr) {
1157         synchronized (sSync) {
1158             sIconCache.put(name, new WeakReference<>(dr.getConstantState()));
1159             if (DEBUG_ICONS) Log.v(TAG, "Added cached drawable state for " + name + ": " + dr);
1160         }
1161     }
1162 
handlePackageBroadcast(int cmd, String[] pkgList, boolean hasPkgInfo)1163     static void handlePackageBroadcast(int cmd, String[] pkgList, boolean hasPkgInfo) {
1164         boolean immediateGc = false;
1165         if (cmd == IApplicationThread.EXTERNAL_STORAGE_UNAVAILABLE) {
1166             immediateGc = true;
1167         }
1168         if (pkgList != null && (pkgList.length > 0)) {
1169             boolean needCleanup = false;
1170             for (String ssp : pkgList) {
1171                 synchronized (sSync) {
1172                     for (int i=sIconCache.size()-1; i>=0; i--) {
1173                         ResourceName nm = sIconCache.keyAt(i);
1174                         if (nm.packageName.equals(ssp)) {
1175                             //Log.i(TAG, "Removing cached drawable for " + nm);
1176                             sIconCache.removeAt(i);
1177                             needCleanup = true;
1178                         }
1179                     }
1180                     for (int i=sStringCache.size()-1; i>=0; i--) {
1181                         ResourceName nm = sStringCache.keyAt(i);
1182                         if (nm.packageName.equals(ssp)) {
1183                             //Log.i(TAG, "Removing cached string for " + nm);
1184                             sStringCache.removeAt(i);
1185                             needCleanup = true;
1186                         }
1187                     }
1188                 }
1189             }
1190             if (needCleanup || hasPkgInfo) {
1191                 if (immediateGc) {
1192                     // Schedule an immediate gc.
1193                     Runtime.getRuntime().gc();
1194                 } else {
1195                     ActivityThread.currentActivityThread().scheduleGcIdler();
1196                 }
1197             }
1198         }
1199     }
1200 
1201     private static final class ResourceName {
1202         final String packageName;
1203         final int iconId;
1204 
ResourceName(String _packageName, int _iconId)1205         ResourceName(String _packageName, int _iconId) {
1206             packageName = _packageName;
1207             iconId = _iconId;
1208         }
1209 
ResourceName(ApplicationInfo aInfo, int _iconId)1210         ResourceName(ApplicationInfo aInfo, int _iconId) {
1211             this(aInfo.packageName, _iconId);
1212         }
1213 
ResourceName(ComponentInfo cInfo, int _iconId)1214         ResourceName(ComponentInfo cInfo, int _iconId) {
1215             this(cInfo.applicationInfo.packageName, _iconId);
1216         }
1217 
ResourceName(ResolveInfo rInfo, int _iconId)1218         ResourceName(ResolveInfo rInfo, int _iconId) {
1219             this(rInfo.activityInfo.applicationInfo.packageName, _iconId);
1220         }
1221 
1222         @Override
equals(Object o)1223         public boolean equals(Object o) {
1224             if (this == o) return true;
1225             if (o == null || getClass() != o.getClass()) return false;
1226 
1227             ResourceName that = (ResourceName) o;
1228 
1229             if (iconId != that.iconId) return false;
1230             return !(packageName != null ?
1231                      !packageName.equals(that.packageName) : that.packageName != null);
1232 
1233         }
1234 
1235         @Override
hashCode()1236         public int hashCode() {
1237             int result;
1238             result = packageName.hashCode();
1239             result = 31 * result + iconId;
1240             return result;
1241         }
1242 
1243         @Override
toString()1244         public String toString() {
1245             return "{ResourceName " + packageName + " / " + iconId + "}";
1246         }
1247     }
1248 
getCachedString(ResourceName name)1249     private CharSequence getCachedString(ResourceName name) {
1250         synchronized (sSync) {
1251             WeakReference<CharSequence> wr = sStringCache.get(name);
1252             if (wr != null) {   // we have the activity
1253                 CharSequence cs = wr.get();
1254                 if (cs != null) {
1255                     return cs;
1256                 }
1257                 // our entry has been purged
1258                 sStringCache.remove(name);
1259             }
1260         }
1261         return null;
1262     }
1263 
putCachedString(ResourceName name, CharSequence cs)1264     private void putCachedString(ResourceName name, CharSequence cs) {
1265         synchronized (sSync) {
1266             sStringCache.put(name, new WeakReference<CharSequence>(cs));
1267         }
1268     }
1269 
1270     @Override
getText(String packageName, @StringRes int resid, ApplicationInfo appInfo)1271     public CharSequence getText(String packageName, @StringRes int resid,
1272                                 ApplicationInfo appInfo) {
1273         ResourceName name = new ResourceName(packageName, resid);
1274         CharSequence text = getCachedString(name);
1275         if (text != null) {
1276             return text;
1277         }
1278         if (appInfo == null) {
1279             try {
1280                 appInfo = getApplicationInfo(packageName, sDefaultFlags);
1281             } catch (NameNotFoundException e) {
1282                 return null;
1283             }
1284         }
1285         try {
1286             Resources r = getResourcesForApplication(appInfo);
1287             text = r.getText(resid);
1288             putCachedString(name, text);
1289             return text;
1290         } catch (NameNotFoundException e) {
1291             Log.w("PackageManager", "Failure retrieving resources for "
1292                   + appInfo.packageName);
1293         } catch (RuntimeException e) {
1294             // If an exception was thrown, fall through to return
1295             // default icon.
1296             Log.w("PackageManager", "Failure retrieving text 0x"
1297                   + Integer.toHexString(resid) + " in package "
1298                   + packageName, e);
1299         }
1300         return null;
1301     }
1302 
1303     @Override
getXml(String packageName, @XmlRes int resid, ApplicationInfo appInfo)1304     public XmlResourceParser getXml(String packageName, @XmlRes int resid,
1305                                     ApplicationInfo appInfo) {
1306         if (appInfo == null) {
1307             try {
1308                 appInfo = getApplicationInfo(packageName, sDefaultFlags);
1309             } catch (NameNotFoundException e) {
1310                 return null;
1311             }
1312         }
1313         try {
1314             Resources r = getResourcesForApplication(appInfo);
1315             return r.getXml(resid);
1316         } catch (RuntimeException e) {
1317             // If an exception was thrown, fall through to return
1318             // default icon.
1319             Log.w("PackageManager", "Failure retrieving xml 0x"
1320                   + Integer.toHexString(resid) + " in package "
1321                   + packageName, e);
1322         } catch (NameNotFoundException e) {
1323             Log.w("PackageManager", "Failure retrieving resources for "
1324                   + appInfo.packageName);
1325         }
1326         return null;
1327     }
1328 
1329     @Override
getApplicationLabel(ApplicationInfo info)1330     public CharSequence getApplicationLabel(ApplicationInfo info) {
1331         return info.loadLabel(this);
1332     }
1333 
1334     @Override
installPackage(Uri packageURI, IPackageInstallObserver observer, int flags, String installerPackageName)1335     public void installPackage(Uri packageURI, IPackageInstallObserver observer, int flags,
1336                                String installerPackageName) {
1337         final VerificationParams verificationParams = new VerificationParams(null, null,
1338                 null, VerificationParams.NO_UID, null);
1339         installCommon(packageURI, new LegacyPackageInstallObserver(observer), flags,
1340                 installerPackageName, verificationParams, null);
1341     }
1342 
1343     @Override
installPackageWithVerification(Uri packageURI, IPackageInstallObserver observer, int flags, String installerPackageName, Uri verificationURI, ManifestDigest manifestDigest, ContainerEncryptionParams encryptionParams)1344     public void installPackageWithVerification(Uri packageURI, IPackageInstallObserver observer,
1345             int flags, String installerPackageName, Uri verificationURI,
1346             ManifestDigest manifestDigest, ContainerEncryptionParams encryptionParams) {
1347         final VerificationParams verificationParams = new VerificationParams(verificationURI, null,
1348                 null, VerificationParams.NO_UID, manifestDigest);
1349         installCommon(packageURI, new LegacyPackageInstallObserver(observer), flags,
1350                 installerPackageName, verificationParams, encryptionParams);
1351     }
1352 
1353     @Override
installPackageWithVerificationAndEncryption(Uri packageURI, IPackageInstallObserver observer, int flags, String installerPackageName, VerificationParams verificationParams, ContainerEncryptionParams encryptionParams)1354     public void installPackageWithVerificationAndEncryption(Uri packageURI,
1355             IPackageInstallObserver observer, int flags, String installerPackageName,
1356             VerificationParams verificationParams, ContainerEncryptionParams encryptionParams) {
1357         installCommon(packageURI, new LegacyPackageInstallObserver(observer), flags,
1358                 installerPackageName, verificationParams, encryptionParams);
1359     }
1360 
1361     @Override
installPackage(Uri packageURI, PackageInstallObserver observer, int flags, String installerPackageName)1362     public void installPackage(Uri packageURI, PackageInstallObserver observer,
1363             int flags, String installerPackageName) {
1364         final VerificationParams verificationParams = new VerificationParams(null, null,
1365                 null, VerificationParams.NO_UID, null);
1366         installCommon(packageURI, observer, flags, installerPackageName, verificationParams, null);
1367     }
1368 
1369     @Override
installPackageWithVerification(Uri packageURI, PackageInstallObserver observer, int flags, String installerPackageName, Uri verificationURI, ManifestDigest manifestDigest, ContainerEncryptionParams encryptionParams)1370     public void installPackageWithVerification(Uri packageURI,
1371             PackageInstallObserver observer, int flags, String installerPackageName,
1372             Uri verificationURI, ManifestDigest manifestDigest,
1373             ContainerEncryptionParams encryptionParams) {
1374         final VerificationParams verificationParams = new VerificationParams(verificationURI, null,
1375                 null, VerificationParams.NO_UID, manifestDigest);
1376         installCommon(packageURI, observer, flags, installerPackageName, verificationParams,
1377                 encryptionParams);
1378     }
1379 
1380     @Override
installPackageWithVerificationAndEncryption(Uri packageURI, PackageInstallObserver observer, int flags, String installerPackageName, VerificationParams verificationParams, ContainerEncryptionParams encryptionParams)1381     public void installPackageWithVerificationAndEncryption(Uri packageURI,
1382             PackageInstallObserver observer, int flags, String installerPackageName,
1383             VerificationParams verificationParams, ContainerEncryptionParams encryptionParams) {
1384         installCommon(packageURI, observer, flags, installerPackageName, verificationParams,
1385                 encryptionParams);
1386     }
1387 
installCommon(Uri packageURI, PackageInstallObserver observer, int flags, String installerPackageName, VerificationParams verificationParams, ContainerEncryptionParams encryptionParams)1388     private void installCommon(Uri packageURI,
1389             PackageInstallObserver observer, int flags, String installerPackageName,
1390             VerificationParams verificationParams, ContainerEncryptionParams encryptionParams) {
1391         if (!"file".equals(packageURI.getScheme())) {
1392             throw new UnsupportedOperationException("Only file:// URIs are supported");
1393         }
1394         if (encryptionParams != null) {
1395             throw new UnsupportedOperationException("ContainerEncryptionParams not supported");
1396         }
1397 
1398         final String originPath = packageURI.getPath();
1399         try {
1400             mPM.installPackage(originPath, observer.getBinder(), flags, installerPackageName,
1401                     verificationParams, null);
1402         } catch (RemoteException ignored) {
1403         }
1404     }
1405 
1406     @Override
installExistingPackage(String packageName)1407     public int installExistingPackage(String packageName)
1408             throws NameNotFoundException {
1409         try {
1410             int res = mPM.installExistingPackageAsUser(packageName, UserHandle.myUserId());
1411             if (res == INSTALL_FAILED_INVALID_URI) {
1412                 throw new NameNotFoundException("Package " + packageName + " doesn't exist");
1413             }
1414             return res;
1415         } catch (RemoteException e) {
1416             // Should never happen!
1417             throw new NameNotFoundException("Package " + packageName + " doesn't exist");
1418         }
1419     }
1420 
1421     @Override
verifyPendingInstall(int id, int response)1422     public void verifyPendingInstall(int id, int response) {
1423         try {
1424             mPM.verifyPendingInstall(id, response);
1425         } catch (RemoteException e) {
1426             // Should never happen!
1427         }
1428     }
1429 
1430     @Override
extendVerificationTimeout(int id, int verificationCodeAtTimeout, long millisecondsToDelay)1431     public void extendVerificationTimeout(int id, int verificationCodeAtTimeout,
1432             long millisecondsToDelay) {
1433         try {
1434             mPM.extendVerificationTimeout(id, verificationCodeAtTimeout, millisecondsToDelay);
1435         } catch (RemoteException e) {
1436             // Should never happen!
1437         }
1438     }
1439 
1440     @Override
verifyIntentFilter(int id, int verificationCode, List<String> outFailedDomains)1441     public void verifyIntentFilter(int id, int verificationCode, List<String> outFailedDomains) {
1442         try {
1443             mPM.verifyIntentFilter(id, verificationCode, outFailedDomains);
1444         } catch (RemoteException e) {
1445             // Should never happen!
1446         }
1447     }
1448 
1449     @Override
getIntentVerificationStatus(String packageName, int userId)1450     public int getIntentVerificationStatus(String packageName, int userId) {
1451         try {
1452             return mPM.getIntentVerificationStatus(packageName, userId);
1453         } catch (RemoteException e) {
1454             // Should never happen!
1455             return PackageManager.INTENT_FILTER_DOMAIN_VERIFICATION_STATUS_UNDEFINED;
1456         }
1457     }
1458 
1459     @Override
updateIntentVerificationStatus(String packageName, int status, int userId)1460     public boolean updateIntentVerificationStatus(String packageName, int status, int userId) {
1461         try {
1462             return mPM.updateIntentVerificationStatus(packageName, status, userId);
1463         } catch (RemoteException e) {
1464             // Should never happen!
1465             return false;
1466         }
1467     }
1468 
1469     @Override
getIntentFilterVerifications(String packageName)1470     public List<IntentFilterVerificationInfo> getIntentFilterVerifications(String packageName) {
1471         try {
1472             return mPM.getIntentFilterVerifications(packageName);
1473         } catch (RemoteException e) {
1474             // Should never happen!
1475             return null;
1476         }
1477     }
1478 
1479     @Override
getAllIntentFilters(String packageName)1480     public List<IntentFilter> getAllIntentFilters(String packageName) {
1481         try {
1482             return mPM.getAllIntentFilters(packageName);
1483         } catch (RemoteException e) {
1484             // Should never happen!
1485             return null;
1486         }
1487     }
1488 
1489     @Override
getDefaultBrowserPackageName(int userId)1490     public String getDefaultBrowserPackageName(int userId) {
1491         try {
1492             return mPM.getDefaultBrowserPackageName(userId);
1493         } catch (RemoteException e) {
1494             // Should never happen!
1495             return null;
1496         }
1497     }
1498 
1499     @Override
setDefaultBrowserPackageName(String packageName, int userId)1500     public boolean setDefaultBrowserPackageName(String packageName, int userId) {
1501         try {
1502             return mPM.setDefaultBrowserPackageName(packageName, userId);
1503         } catch (RemoteException e) {
1504             // Should never happen!
1505             return false;
1506         }
1507     }
1508 
1509     @Override
setInstallerPackageName(String targetPackage, String installerPackageName)1510     public void setInstallerPackageName(String targetPackage,
1511             String installerPackageName) {
1512         try {
1513             mPM.setInstallerPackageName(targetPackage, installerPackageName);
1514         } catch (RemoteException e) {
1515             // Should never happen!
1516         }
1517     }
1518 
1519     @Override
getInstallerPackageName(String packageName)1520     public String getInstallerPackageName(String packageName) {
1521         try {
1522             return mPM.getInstallerPackageName(packageName);
1523         } catch (RemoteException e) {
1524             // Should never happen!
1525         }
1526         return null;
1527     }
1528 
1529     @Override
getMoveStatus(int moveId)1530     public int getMoveStatus(int moveId) {
1531         try {
1532             return mPM.getMoveStatus(moveId);
1533         } catch (RemoteException e) {
1534             throw e.rethrowAsRuntimeException();
1535         }
1536     }
1537 
1538     @Override
registerMoveCallback(MoveCallback callback, Handler handler)1539     public void registerMoveCallback(MoveCallback callback, Handler handler) {
1540         synchronized (mDelegates) {
1541             final MoveCallbackDelegate delegate = new MoveCallbackDelegate(callback,
1542                     handler.getLooper());
1543             try {
1544                 mPM.registerMoveCallback(delegate);
1545             } catch (RemoteException e) {
1546                 throw e.rethrowAsRuntimeException();
1547             }
1548             mDelegates.add(delegate);
1549         }
1550     }
1551 
1552     @Override
unregisterMoveCallback(MoveCallback callback)1553     public void unregisterMoveCallback(MoveCallback callback) {
1554         synchronized (mDelegates) {
1555             for (Iterator<MoveCallbackDelegate> i = mDelegates.iterator(); i.hasNext();) {
1556                 final MoveCallbackDelegate delegate = i.next();
1557                 if (delegate.mCallback == callback) {
1558                     try {
1559                         mPM.unregisterMoveCallback(delegate);
1560                     } catch (RemoteException e) {
1561                         throw e.rethrowAsRuntimeException();
1562                     }
1563                     i.remove();
1564                 }
1565             }
1566         }
1567     }
1568 
1569     @Override
movePackage(String packageName, VolumeInfo vol)1570     public int movePackage(String packageName, VolumeInfo vol) {
1571         try {
1572             final String volumeUuid;
1573             if (VolumeInfo.ID_PRIVATE_INTERNAL.equals(vol.id)) {
1574                 volumeUuid = StorageManager.UUID_PRIVATE_INTERNAL;
1575             } else if (vol.isPrimaryPhysical()) {
1576                 volumeUuid = StorageManager.UUID_PRIMARY_PHYSICAL;
1577             } else {
1578                 volumeUuid = Preconditions.checkNotNull(vol.fsUuid);
1579             }
1580 
1581             return mPM.movePackage(packageName, volumeUuid);
1582         } catch (RemoteException e) {
1583             throw e.rethrowAsRuntimeException();
1584         }
1585     }
1586 
1587     @Override
getPackageCurrentVolume(ApplicationInfo app)1588     public @Nullable VolumeInfo getPackageCurrentVolume(ApplicationInfo app) {
1589         final StorageManager storage = mContext.getSystemService(StorageManager.class);
1590         if (app.isInternal()) {
1591             return storage.findVolumeById(VolumeInfo.ID_PRIVATE_INTERNAL);
1592         } else if (app.isExternalAsec()) {
1593             return storage.getPrimaryPhysicalVolume();
1594         } else {
1595             return storage.findVolumeByUuid(app.volumeUuid);
1596         }
1597     }
1598 
1599     @Override
getPackageCandidateVolumes(ApplicationInfo app)1600     public @NonNull List<VolumeInfo> getPackageCandidateVolumes(ApplicationInfo app) {
1601         final StorageManager storage = mContext.getSystemService(StorageManager.class);
1602         final VolumeInfo currentVol = getPackageCurrentVolume(app);
1603         final List<VolumeInfo> vols = storage.getVolumes();
1604         final List<VolumeInfo> candidates = new ArrayList<>();
1605         for (VolumeInfo vol : vols) {
1606             if (Objects.equals(vol, currentVol) || isPackageCandidateVolume(app, vol)) {
1607                 candidates.add(vol);
1608             }
1609         }
1610         return candidates;
1611     }
1612 
isPackageCandidateVolume(ApplicationInfo app, VolumeInfo vol)1613     private static boolean isPackageCandidateVolume(ApplicationInfo app, VolumeInfo vol) {
1614         // Private internal is always an option
1615         if (VolumeInfo.ID_PRIVATE_INTERNAL.equals(vol.getId())) {
1616             return true;
1617         }
1618 
1619         // System apps and apps demanding internal storage can't be moved
1620         // anywhere else
1621         if (app.isSystemApp()
1622                 || app.installLocation == PackageInfo.INSTALL_LOCATION_INTERNAL_ONLY) {
1623             return false;
1624         }
1625 
1626         // Gotta be able to write there
1627         if (!vol.isMountedWritable()) {
1628             return false;
1629         }
1630 
1631         // Moving into an ASEC on public primary is only option internal
1632         if (vol.isPrimaryPhysical()) {
1633             return app.isInternal();
1634         }
1635 
1636         // Otherwise we can move to any private volume
1637         return (vol.getType() == VolumeInfo.TYPE_PRIVATE);
1638     }
1639 
1640     @Override
movePrimaryStorage(VolumeInfo vol)1641     public int movePrimaryStorage(VolumeInfo vol) {
1642         try {
1643             final String volumeUuid;
1644             if (VolumeInfo.ID_PRIVATE_INTERNAL.equals(vol.id)) {
1645                 volumeUuid = StorageManager.UUID_PRIVATE_INTERNAL;
1646             } else if (vol.isPrimaryPhysical()) {
1647                 volumeUuid = StorageManager.UUID_PRIMARY_PHYSICAL;
1648             } else {
1649                 volumeUuid = Preconditions.checkNotNull(vol.fsUuid);
1650             }
1651 
1652             return mPM.movePrimaryStorage(volumeUuid);
1653         } catch (RemoteException e) {
1654             throw e.rethrowAsRuntimeException();
1655         }
1656     }
1657 
1658     @Override
getPrimaryStorageCurrentVolume()1659     public @Nullable VolumeInfo getPrimaryStorageCurrentVolume() {
1660         final StorageManager storage = mContext.getSystemService(StorageManager.class);
1661         final String volumeUuid = storage.getPrimaryStorageUuid();
1662         return storage.findVolumeByQualifiedUuid(volumeUuid);
1663     }
1664 
1665     @Override
getPrimaryStorageCandidateVolumes()1666     public @NonNull List<VolumeInfo> getPrimaryStorageCandidateVolumes() {
1667         final StorageManager storage = mContext.getSystemService(StorageManager.class);
1668         final VolumeInfo currentVol = getPrimaryStorageCurrentVolume();
1669         final List<VolumeInfo> vols = storage.getVolumes();
1670         final List<VolumeInfo> candidates = new ArrayList<>();
1671         if (Objects.equals(StorageManager.UUID_PRIMARY_PHYSICAL,
1672                 storage.getPrimaryStorageUuid()) && currentVol != null) {
1673             // TODO: support moving primary physical to emulated volume
1674             candidates.add(currentVol);
1675         } else {
1676             for (VolumeInfo vol : vols) {
1677                 if (Objects.equals(vol, currentVol) || isPrimaryStorageCandidateVolume(vol)) {
1678                     candidates.add(vol);
1679                 }
1680             }
1681         }
1682         return candidates;
1683     }
1684 
isPrimaryStorageCandidateVolume(VolumeInfo vol)1685     private static boolean isPrimaryStorageCandidateVolume(VolumeInfo vol) {
1686         // Private internal is always an option
1687         if (VolumeInfo.ID_PRIVATE_INTERNAL.equals(vol.getId())) {
1688             return true;
1689         }
1690 
1691         // Gotta be able to write there
1692         if (!vol.isMountedWritable()) {
1693             return false;
1694         }
1695 
1696         // We can move to any private volume
1697         return (vol.getType() == VolumeInfo.TYPE_PRIVATE);
1698     }
1699 
1700     @Override
deletePackage(String packageName, IPackageDeleteObserver observer, int flags)1701     public void deletePackage(String packageName, IPackageDeleteObserver observer, int flags) {
1702         try {
1703             mPM.deletePackageAsUser(packageName, observer, UserHandle.myUserId(), flags);
1704         } catch (RemoteException e) {
1705             // Should never happen!
1706         }
1707     }
1708 
1709     @Override
clearApplicationUserData(String packageName, IPackageDataObserver observer)1710     public void clearApplicationUserData(String packageName,
1711                                          IPackageDataObserver observer) {
1712         try {
1713             mPM.clearApplicationUserData(packageName, observer, mContext.getUserId());
1714         } catch (RemoteException e) {
1715             // Should never happen!
1716         }
1717     }
1718     @Override
deleteApplicationCacheFiles(String packageName, IPackageDataObserver observer)1719     public void deleteApplicationCacheFiles(String packageName,
1720                                             IPackageDataObserver observer) {
1721         try {
1722             mPM.deleteApplicationCacheFiles(packageName, observer);
1723         } catch (RemoteException e) {
1724             // Should never happen!
1725         }
1726     }
1727 
1728     @Override
freeStorageAndNotify(String volumeUuid, long idealStorageSize, IPackageDataObserver observer)1729     public void freeStorageAndNotify(String volumeUuid, long idealStorageSize,
1730             IPackageDataObserver observer) {
1731         try {
1732             mPM.freeStorageAndNotify(volumeUuid, idealStorageSize, observer);
1733         } catch (RemoteException e) {
1734             // Should never happen!
1735         }
1736     }
1737 
1738     @Override
freeStorage(String volumeUuid, long freeStorageSize, IntentSender pi)1739     public void freeStorage(String volumeUuid, long freeStorageSize, IntentSender pi) {
1740         try {
1741             mPM.freeStorage(volumeUuid, freeStorageSize, pi);
1742         } catch (RemoteException e) {
1743             // Should never happen!
1744         }
1745     }
1746 
1747     @Override
getPackageSizeInfo(String packageName, int userHandle, IPackageStatsObserver observer)1748     public void getPackageSizeInfo(String packageName, int userHandle,
1749             IPackageStatsObserver observer) {
1750         try {
1751             mPM.getPackageSizeInfo(packageName, userHandle, observer);
1752         } catch (RemoteException e) {
1753             // Should never happen!
1754         }
1755     }
1756     @Override
addPackageToPreferred(String packageName)1757     public void addPackageToPreferred(String packageName) {
1758         try {
1759             mPM.addPackageToPreferred(packageName);
1760         } catch (RemoteException e) {
1761             // Should never happen!
1762         }
1763     }
1764 
1765     @Override
removePackageFromPreferred(String packageName)1766     public void removePackageFromPreferred(String packageName) {
1767         try {
1768             mPM.removePackageFromPreferred(packageName);
1769         } catch (RemoteException e) {
1770             // Should never happen!
1771         }
1772     }
1773 
1774     @Override
getPreferredPackages(int flags)1775     public List<PackageInfo> getPreferredPackages(int flags) {
1776         try {
1777             return mPM.getPreferredPackages(flags);
1778         } catch (RemoteException e) {
1779             // Should never happen!
1780         }
1781         return new ArrayList<PackageInfo>();
1782     }
1783 
1784     @Override
addPreferredActivity(IntentFilter filter, int match, ComponentName[] set, ComponentName activity)1785     public void addPreferredActivity(IntentFilter filter,
1786                                      int match, ComponentName[] set, ComponentName activity) {
1787         try {
1788             mPM.addPreferredActivity(filter, match, set, activity, mContext.getUserId());
1789         } catch (RemoteException e) {
1790             // Should never happen!
1791         }
1792     }
1793 
1794     @Override
addPreferredActivity(IntentFilter filter, int match, ComponentName[] set, ComponentName activity, int userId)1795     public void addPreferredActivity(IntentFilter filter, int match,
1796             ComponentName[] set, ComponentName activity, int userId) {
1797         try {
1798             mPM.addPreferredActivity(filter, match, set, activity, userId);
1799         } catch (RemoteException e) {
1800             // Should never happen!
1801         }
1802     }
1803 
1804     @Override
replacePreferredActivity(IntentFilter filter, int match, ComponentName[] set, ComponentName activity)1805     public void replacePreferredActivity(IntentFilter filter,
1806                                          int match, ComponentName[] set, ComponentName activity) {
1807         try {
1808             mPM.replacePreferredActivity(filter, match, set, activity, UserHandle.myUserId());
1809         } catch (RemoteException e) {
1810             // Should never happen!
1811         }
1812     }
1813 
1814     @Override
replacePreferredActivityAsUser(IntentFilter filter, int match, ComponentName[] set, ComponentName activity, int userId)1815     public void replacePreferredActivityAsUser(IntentFilter filter,
1816                                          int match, ComponentName[] set, ComponentName activity,
1817                                          int userId) {
1818         try {
1819             mPM.replacePreferredActivity(filter, match, set, activity, userId);
1820         } catch (RemoteException e) {
1821             // Should never happen!
1822         }
1823     }
1824 
1825     @Override
clearPackagePreferredActivities(String packageName)1826     public void clearPackagePreferredActivities(String packageName) {
1827         try {
1828             mPM.clearPackagePreferredActivities(packageName);
1829         } catch (RemoteException e) {
1830             // Should never happen!
1831         }
1832     }
1833 
1834     @Override
getPreferredActivities(List<IntentFilter> outFilters, List<ComponentName> outActivities, String packageName)1835     public int getPreferredActivities(List<IntentFilter> outFilters,
1836                                       List<ComponentName> outActivities, String packageName) {
1837         try {
1838             return mPM.getPreferredActivities(outFilters, outActivities, packageName);
1839         } catch (RemoteException e) {
1840             // Should never happen!
1841         }
1842         return 0;
1843     }
1844 
1845     @Override
getHomeActivities(List<ResolveInfo> outActivities)1846     public ComponentName getHomeActivities(List<ResolveInfo> outActivities) {
1847         try {
1848             return mPM.getHomeActivities(outActivities);
1849         } catch (RemoteException e) {
1850             // Should never happen!
1851         }
1852         return null;
1853     }
1854 
1855     @Override
setComponentEnabledSetting(ComponentName componentName, int newState, int flags)1856     public void setComponentEnabledSetting(ComponentName componentName,
1857                                            int newState, int flags) {
1858         try {
1859             mPM.setComponentEnabledSetting(componentName, newState, flags, mContext.getUserId());
1860         } catch (RemoteException e) {
1861             // Should never happen!
1862         }
1863     }
1864 
1865     @Override
getComponentEnabledSetting(ComponentName componentName)1866     public int getComponentEnabledSetting(ComponentName componentName) {
1867         try {
1868             return mPM.getComponentEnabledSetting(componentName, mContext.getUserId());
1869         } catch (RemoteException e) {
1870             // Should never happen!
1871         }
1872         return PackageManager.COMPONENT_ENABLED_STATE_DEFAULT;
1873     }
1874 
1875     @Override
setApplicationEnabledSetting(String packageName, int newState, int flags)1876     public void setApplicationEnabledSetting(String packageName,
1877                                              int newState, int flags) {
1878         try {
1879             mPM.setApplicationEnabledSetting(packageName, newState, flags,
1880                     mContext.getUserId(), mContext.getOpPackageName());
1881         } catch (RemoteException e) {
1882             // Should never happen!
1883         }
1884     }
1885 
1886     @Override
getApplicationEnabledSetting(String packageName)1887     public int getApplicationEnabledSetting(String packageName) {
1888         try {
1889             return mPM.getApplicationEnabledSetting(packageName, mContext.getUserId());
1890         } catch (RemoteException e) {
1891             // Should never happen!
1892         }
1893         return PackageManager.COMPONENT_ENABLED_STATE_DEFAULT;
1894     }
1895 
1896     @Override
setApplicationHiddenSettingAsUser(String packageName, boolean hidden, UserHandle user)1897     public boolean setApplicationHiddenSettingAsUser(String packageName, boolean hidden,
1898             UserHandle user) {
1899         try {
1900             return mPM.setApplicationHiddenSettingAsUser(packageName, hidden,
1901                     user.getIdentifier());
1902         } catch (RemoteException re) {
1903             // Should never happen!
1904         }
1905         return false;
1906     }
1907 
1908     @Override
getApplicationHiddenSettingAsUser(String packageName, UserHandle user)1909     public boolean getApplicationHiddenSettingAsUser(String packageName, UserHandle user) {
1910         try {
1911             return mPM.getApplicationHiddenSettingAsUser(packageName, user.getIdentifier());
1912         } catch (RemoteException re) {
1913             // Should never happen!
1914         }
1915         return false;
1916     }
1917 
1918     /** @hide */
1919     @Override
getKeySetByAlias(String packageName, String alias)1920     public KeySet getKeySetByAlias(String packageName, String alias) {
1921         Preconditions.checkNotNull(packageName);
1922         Preconditions.checkNotNull(alias);
1923         KeySet ks;
1924         try {
1925             ks = mPM.getKeySetByAlias(packageName, alias);
1926         } catch (RemoteException e) {
1927             return null;
1928         }
1929         return ks;
1930     }
1931 
1932     /** @hide */
1933     @Override
getSigningKeySet(String packageName)1934     public KeySet getSigningKeySet(String packageName) {
1935         Preconditions.checkNotNull(packageName);
1936         KeySet ks;
1937         try {
1938             ks = mPM.getSigningKeySet(packageName);
1939         } catch (RemoteException e) {
1940             return null;
1941         }
1942         return ks;
1943     }
1944 
1945     /** @hide */
1946     @Override
isSignedBy(String packageName, KeySet ks)1947     public boolean isSignedBy(String packageName, KeySet ks) {
1948         Preconditions.checkNotNull(packageName);
1949         Preconditions.checkNotNull(ks);
1950         try {
1951             return mPM.isPackageSignedByKeySet(packageName, ks);
1952         } catch (RemoteException e) {
1953             return false;
1954         }
1955     }
1956 
1957     /** @hide */
1958     @Override
isSignedByExactly(String packageName, KeySet ks)1959     public boolean isSignedByExactly(String packageName, KeySet ks) {
1960         Preconditions.checkNotNull(packageName);
1961         Preconditions.checkNotNull(ks);
1962         try {
1963             return mPM.isPackageSignedByKeySetExactly(packageName, ks);
1964         } catch (RemoteException e) {
1965             return false;
1966         }
1967     }
1968 
1969     /**
1970      * @hide
1971      */
1972     @Override
getVerifierDeviceIdentity()1973     public VerifierDeviceIdentity getVerifierDeviceIdentity() {
1974         try {
1975             return mPM.getVerifierDeviceIdentity();
1976         } catch (RemoteException e) {
1977             // Should never happen!
1978         }
1979         return null;
1980     }
1981 
1982     /**
1983      * @hide
1984      */
1985     @Override
isUpgrade()1986     public boolean isUpgrade() {
1987         try {
1988             return mPM.isUpgrade();
1989         } catch (RemoteException e) {
1990             return false;
1991         }
1992     }
1993 
1994     @Override
getPackageInstaller()1995     public PackageInstaller getPackageInstaller() {
1996         synchronized (mLock) {
1997             if (mInstaller == null) {
1998                 try {
1999                     mInstaller = new PackageInstaller(mContext, this, mPM.getPackageInstaller(),
2000                             mContext.getPackageName(), mContext.getUserId());
2001                 } catch (RemoteException e) {
2002                     throw e.rethrowAsRuntimeException();
2003                 }
2004             }
2005             return mInstaller;
2006         }
2007     }
2008 
2009     @Override
isPackageAvailable(String packageName)2010     public boolean isPackageAvailable(String packageName) {
2011         try {
2012             return mPM.isPackageAvailable(packageName, mContext.getUserId());
2013         } catch (RemoteException e) {
2014             throw e.rethrowAsRuntimeException();
2015         }
2016     }
2017 
2018     /**
2019      * @hide
2020      */
2021     @Override
addCrossProfileIntentFilter(IntentFilter filter, int sourceUserId, int targetUserId, int flags)2022     public void addCrossProfileIntentFilter(IntentFilter filter, int sourceUserId, int targetUserId,
2023             int flags) {
2024         try {
2025             mPM.addCrossProfileIntentFilter(filter, mContext.getOpPackageName(),
2026                     sourceUserId, targetUserId, flags);
2027         } catch (RemoteException e) {
2028             // Should never happen!
2029         }
2030     }
2031 
2032     /**
2033      * @hide
2034      */
2035     @Override
clearCrossProfileIntentFilters(int sourceUserId)2036     public void clearCrossProfileIntentFilters(int sourceUserId) {
2037         try {
2038             mPM.clearCrossProfileIntentFilters(sourceUserId, mContext.getOpPackageName());
2039         } catch (RemoteException e) {
2040             // Should never happen!
2041         }
2042     }
2043 
2044     /**
2045      * @hide
2046      */
loadItemIcon(PackageItemInfo itemInfo, ApplicationInfo appInfo)2047     public Drawable loadItemIcon(PackageItemInfo itemInfo, ApplicationInfo appInfo) {
2048         Drawable dr = loadUnbadgedItemIcon(itemInfo, appInfo);
2049         if (itemInfo.showUserIcon != UserHandle.USER_NULL) {
2050             return dr;
2051         }
2052         return getUserBadgedIcon(dr, new UserHandle(mContext.getUserId()));
2053     }
2054 
2055     /**
2056      * @hide
2057      */
loadUnbadgedItemIcon(PackageItemInfo itemInfo, ApplicationInfo appInfo)2058     public Drawable loadUnbadgedItemIcon(PackageItemInfo itemInfo, ApplicationInfo appInfo) {
2059         if (itemInfo.showUserIcon != UserHandle.USER_NULL) {
2060             Bitmap bitmap = getUserManager().getUserIcon(itemInfo.showUserIcon);
2061             if (bitmap == null) {
2062                 return UserIcons.getDefaultUserIcon(itemInfo.showUserIcon, /* light= */ false);
2063             }
2064             return new BitmapDrawable(bitmap);
2065         }
2066         Drawable dr = null;
2067         if (itemInfo.packageName != null) {
2068             dr = getDrawable(itemInfo.packageName, itemInfo.icon, appInfo);
2069         }
2070         if (dr == null) {
2071             dr = itemInfo.loadDefaultIcon(this);
2072         }
2073         return dr;
2074     }
2075 
getBadgedDrawable(Drawable drawable, Drawable badgeDrawable, Rect badgeLocation, boolean tryBadgeInPlace)2076     private Drawable getBadgedDrawable(Drawable drawable, Drawable badgeDrawable,
2077             Rect badgeLocation, boolean tryBadgeInPlace) {
2078         final int badgedWidth = drawable.getIntrinsicWidth();
2079         final int badgedHeight = drawable.getIntrinsicHeight();
2080         final boolean canBadgeInPlace = tryBadgeInPlace
2081                 && (drawable instanceof BitmapDrawable)
2082                 && ((BitmapDrawable) drawable).getBitmap().isMutable();
2083 
2084         final Bitmap bitmap;
2085         if (canBadgeInPlace) {
2086             bitmap = ((BitmapDrawable) drawable).getBitmap();
2087         } else {
2088             bitmap = Bitmap.createBitmap(badgedWidth, badgedHeight, Bitmap.Config.ARGB_8888);
2089         }
2090         Canvas canvas = new Canvas(bitmap);
2091 
2092         if (!canBadgeInPlace) {
2093             drawable.setBounds(0, 0, badgedWidth, badgedHeight);
2094             drawable.draw(canvas);
2095         }
2096 
2097         if (badgeLocation != null) {
2098             if (badgeLocation.left < 0 || badgeLocation.top < 0
2099                     || badgeLocation.width() > badgedWidth || badgeLocation.height() > badgedHeight) {
2100                 throw new IllegalArgumentException("Badge location " + badgeLocation
2101                         + " not in badged drawable bounds "
2102                         + new Rect(0, 0, badgedWidth, badgedHeight));
2103             }
2104             badgeDrawable.setBounds(0, 0, badgeLocation.width(), badgeLocation.height());
2105 
2106             canvas.save();
2107             canvas.translate(badgeLocation.left, badgeLocation.top);
2108             badgeDrawable.draw(canvas);
2109             canvas.restore();
2110         } else {
2111             badgeDrawable.setBounds(0, 0, badgedWidth, badgedHeight);
2112             badgeDrawable.draw(canvas);
2113         }
2114 
2115         if (!canBadgeInPlace) {
2116             BitmapDrawable mergedDrawable = new BitmapDrawable(mContext.getResources(), bitmap);
2117 
2118             if (drawable instanceof BitmapDrawable) {
2119                 BitmapDrawable bitmapDrawable = (BitmapDrawable) drawable;
2120                 mergedDrawable.setTargetDensity(bitmapDrawable.getBitmap().getDensity());
2121             }
2122 
2123             return mergedDrawable;
2124         }
2125 
2126         return drawable;
2127     }
2128 
getBadgeResIdForUser(int userHandle)2129     private int getBadgeResIdForUser(int userHandle) {
2130         // Return the framework-provided badge.
2131         UserInfo userInfo = getUserIfProfile(userHandle);
2132         if (userInfo != null && userInfo.isManagedProfile()) {
2133             return com.android.internal.R.drawable.ic_corp_icon_badge;
2134         }
2135         return 0;
2136     }
2137 
getUserIfProfile(int userHandle)2138     private UserInfo getUserIfProfile(int userHandle) {
2139         List<UserInfo> userProfiles = getUserManager().getProfiles(UserHandle.myUserId());
2140         for (UserInfo user : userProfiles) {
2141             if (user.id == userHandle) {
2142                 return user;
2143             }
2144         }
2145         return null;
2146     }
2147 
2148     /** {@hide} */
2149     private static class MoveCallbackDelegate extends IPackageMoveObserver.Stub implements
2150             Handler.Callback {
2151         private static final int MSG_CREATED = 1;
2152         private static final int MSG_STATUS_CHANGED = 2;
2153 
2154         final MoveCallback mCallback;
2155         final Handler mHandler;
2156 
MoveCallbackDelegate(MoveCallback callback, Looper looper)2157         public MoveCallbackDelegate(MoveCallback callback, Looper looper) {
2158             mCallback = callback;
2159             mHandler = new Handler(looper, this);
2160         }
2161 
2162         @Override
handleMessage(Message msg)2163         public boolean handleMessage(Message msg) {
2164             switch (msg.what) {
2165                 case MSG_CREATED: {
2166                     final SomeArgs args = (SomeArgs) msg.obj;
2167                     mCallback.onCreated(args.argi1, (Bundle) args.arg2);
2168                     args.recycle();
2169                     return true;
2170                 }
2171                 case MSG_STATUS_CHANGED: {
2172                     final SomeArgs args = (SomeArgs) msg.obj;
2173                     mCallback.onStatusChanged(args.argi1, args.argi2, (long) args.arg3);
2174                     args.recycle();
2175                     return true;
2176                 }
2177             }
2178             return false;
2179         }
2180 
2181         @Override
onCreated(int moveId, Bundle extras)2182         public void onCreated(int moveId, Bundle extras) {
2183             final SomeArgs args = SomeArgs.obtain();
2184             args.argi1 = moveId;
2185             args.arg2 = extras;
2186             mHandler.obtainMessage(MSG_CREATED, args).sendToTarget();
2187         }
2188 
2189         @Override
onStatusChanged(int moveId, int status, long estMillis)2190         public void onStatusChanged(int moveId, int status, long estMillis) {
2191             final SomeArgs args = SomeArgs.obtain();
2192             args.argi1 = moveId;
2193             args.argi2 = status;
2194             args.arg3 = estMillis;
2195             mHandler.obtainMessage(MSG_STATUS_CHANGED, args).sendToTarget();
2196         }
2197     }
2198 
2199     private final ContextImpl mContext;
2200     private final IPackageManager mPM;
2201 
2202     private static final Object sSync = new Object();
2203     private static ArrayMap<ResourceName, WeakReference<Drawable.ConstantState>> sIconCache
2204             = new ArrayMap<ResourceName, WeakReference<Drawable.ConstantState>>();
2205     private static ArrayMap<ResourceName, WeakReference<CharSequence>> sStringCache
2206             = new ArrayMap<ResourceName, WeakReference<CharSequence>>();
2207 
2208     private final Map<OnPermissionsChangedListener, IOnPermissionsChangeListener>
2209             mPermissionListeners = new ArrayMap<>();
2210 
2211     public class OnPermissionsChangeListenerDelegate extends IOnPermissionsChangeListener.Stub
2212             implements Handler.Callback{
2213         private static final int MSG_PERMISSIONS_CHANGED = 1;
2214 
2215         private final OnPermissionsChangedListener mListener;
2216         private final Handler mHandler;
2217 
2218 
OnPermissionsChangeListenerDelegate(OnPermissionsChangedListener listener, Looper looper)2219         public OnPermissionsChangeListenerDelegate(OnPermissionsChangedListener listener,
2220                 Looper looper) {
2221             mListener = listener;
2222             mHandler = new Handler(looper, this);
2223         }
2224 
2225         @Override
onPermissionsChanged(int uid)2226         public void onPermissionsChanged(int uid) {
2227             mHandler.obtainMessage(MSG_PERMISSIONS_CHANGED, uid, 0).sendToTarget();
2228         }
2229 
2230         @Override
handleMessage(Message msg)2231         public boolean handleMessage(Message msg) {
2232             switch (msg.what) {
2233                 case MSG_PERMISSIONS_CHANGED: {
2234                     final int uid = msg.arg1;
2235                     mListener.onPermissionsChanged(uid);
2236                     return true;
2237                 }
2238             }
2239             return false;
2240         }
2241     }
2242 }
2243