diff options
| author | 2019-02-11 16:44:45 -0800 | |
|---|---|---|
| committer | 2019-02-12 14:33:28 -0800 | |
| commit | 8be463fe953aa3df73f2eda5cbee8ab85ba589ff (patch) | |
| tree | e9946fb5cb2b702f3b47b562c4f871d373cdfc38 | |
| parent | 2e71c58863a9c86d9b37da1b59abfb0c132f3e46 (diff) | |
Use role for default home.
This change makes package manager update the home role holder when
preferred activity for the home intent changes, in order to be
backward-compatible.
Bug: 124260975
Test: manual
Change-Id: I2f29e86f0db88d7e1edee74d0e911d33fef889c9
4 files changed, 181 insertions, 42 deletions
diff --git a/core/java/android/content/pm/PackageManagerInternal.java b/core/java/android/content/pm/PackageManagerInternal.java index cfe35b061151..270e3879a71f 100644 --- a/core/java/android/content/pm/PackageManagerInternal.java +++ b/core/java/android/content/pm/PackageManagerInternal.java @@ -163,6 +163,30 @@ public abstract class PackageManagerInternal { } /** + * Provider for default home + */ + public interface DefaultHomeProvider { + + /** + * Get the package name of the default home. + * + * @param userId the user id + * + * @return the package name of the default home, or {@code null} if none + */ + @Nullable + String getDefaultHome(@UserIdInt int userId); + + /** + * Set the package name of the default home. + * + * @param packageName package name of the default home, or {@code null} to remove + * @param userId the user id + */ + void setDefaultHomeAsync(@Nullable String packageName, @UserIdInt int userId); + } + + /** * Sets the location provider packages provider. * @param provider The packages provider. */ @@ -886,4 +910,11 @@ public abstract class PackageManagerInternal { * @param provider the provider */ public abstract void setDefaultBrowserProvider(@NonNull DefaultBrowserProvider provider); + + /** + * Sets the default home provider. + * + * @param provider the provider + */ + public abstract void setDefaultHomeProvider(@NonNull DefaultHomeProvider provider); } diff --git a/services/core/java/com/android/server/pm/PackageManagerService.java b/services/core/java/com/android/server/pm/PackageManagerService.java index 874d1a719ee6..aaf15d1c046c 100644 --- a/services/core/java/com/android/server/pm/PackageManagerService.java +++ b/services/core/java/com/android/server/pm/PackageManagerService.java @@ -986,6 +986,9 @@ public class PackageManagerService extends IPackageManager.Stub @GuardedBy("mPackages") private PackageManagerInternal.DefaultBrowserProvider mDefaultBrowserProvider; + @GuardedBy("mPackages") + private PackageManagerInternal.DefaultHomeProvider mDefaultHomeProvider; + private class IntentVerifierProxy implements IntentFilterVerifier<ActivityIntentInfo> { private Context mContext; private ComponentName mIntentFilterVerifierComponent; @@ -1345,7 +1348,7 @@ public class PackageManagerService extends IPackageManager.Stub final @Nullable String mRequiredVerifierPackage; final @NonNull String mRequiredInstallerPackage; final @NonNull String mRequiredUninstallerPackage; - final String mRequiredPermissionControllerPackage; + final @NonNull String mRequiredPermissionControllerPackage; final @Nullable String mSetupWizardPackage; final @Nullable String mStorageManagerPackage; final @Nullable String mSystemTextClassifierPackage; @@ -1936,6 +1939,10 @@ public class PackageManagerService extends IPackageManager.Stub // We may also need to apply pending (restored) runtime // permission grants within these users. mSettings.applyPendingPermissionGrantsLPw(packageName, userId); + + // Persistent preferred activity might have came into effect due to this + // install. + updateDefaultHomeLPw(userId); } } } @@ -19104,6 +19111,7 @@ public class PackageManagerService extends IPackageManager.Stub pir.addFilter(new PreferredActivity(filter, match, set, activity, always)); scheduleWritePackageRestrictionsLocked(userId); postPreferredActivityChangedBroadcast(userId); + updateDefaultHomeLPw(userId); } } @@ -19254,6 +19262,13 @@ public class PackageManagerService extends IPackageManager.Stub /** This method takes a specific user id as well as UserHandle.USER_ALL. */ @GuardedBy("mPackages") boolean clearPackagePreferredActivitiesLPw(String packageName, int userId) { + return clearPackagePreferredActivitiesLPw(packageName, false, userId); + } + + /** This method takes a specific user id as well as UserHandle.USER_ALL. */ + @GuardedBy("mPackages") + private boolean clearPackagePreferredActivitiesLPw(String packageName, + boolean skipUpdateDefaultHome, int userId) { ArrayList<PreferredActivity> removed = null; boolean changed = false; for (int i=0; i<mSettings.mPreferredActivities.size(); i++) { @@ -19282,6 +19297,9 @@ public class PackageManagerService extends IPackageManager.Stub pir.removeFilter(pa); } changed = true; + if (!skipUpdateDefaultHome) { + updateDefaultHomeLPw(thisUserId); + } } } if (changed) { @@ -19341,8 +19359,9 @@ public class PackageManagerService extends IPackageManager.Stub // writer try { synchronized (mPackages) { - clearPackagePreferredActivitiesLPw(null, userId); + clearPackagePreferredActivitiesLPw(null, true, userId); mSettings.applyDefaultPreferredAppsLPw(userId); + updateDefaultHomeLPw(userId); // TODO: We have to reset the default SMS and Phone. This requires // significant refactoring to keep all default apps in the package // manager (cleaner but more work) or have the services provide @@ -19411,6 +19430,7 @@ public class PackageManagerService extends IPackageManager.Stub new PersistentPreferredActivity(filter, activity)); scheduleWritePackageRestrictionsLocked(userId); postPreferredActivityChangedBroadcast(userId); + updateDefaultHomeLPw(userId); } } @@ -19454,6 +19474,7 @@ public class PackageManagerService extends IPackageManager.Stub if (changed) { scheduleWritePackageRestrictionsLocked(userId); postPreferredActivityChangedBroadcast(userId); + updateDefaultHomeLPw(userId); } } } @@ -19541,6 +19562,7 @@ public class PackageManagerService extends IPackageManager.Stub (readParser, readUserId) -> { synchronized (mPackages) { mSettings.readPreferredActivitiesLPw(readParser, readUserId); + updateDefaultHomeLPw(readUserId); } }); } catch (Exception e) { @@ -19955,19 +19977,59 @@ public class PackageManagerService extends IPackageManager.Stub ComponentName getHomeActivitiesAsUser(List<ResolveInfo> allHomeCandidates, int userId) { Intent intent = getHomeIntent(); - List<ResolveInfo> list = queryIntentActivitiesInternal(intent, null, + List<ResolveInfo> resolveInfos = queryIntentActivitiesInternal(intent, null, PackageManager.GET_META_DATA, userId); - ResolveInfo preferred = findPreferredActivity(intent, null, 0, list, 0, - true, false, false, userId); - allHomeCandidates.clear(); - if (list != null) { - allHomeCandidates.addAll(list); + if (resolveInfos == null) { + return null; } - return (preferred == null || preferred.activityInfo == null) - ? null - : new ComponentName(preferred.activityInfo.packageName, - preferred.activityInfo.name); + allHomeCandidates.addAll(resolveInfos); + + PackageManagerInternal.DefaultHomeProvider provider; + synchronized (mPackages) { + provider = mDefaultHomeProvider; + } + if (provider == null) { + Slog.e(TAG, "mDefaultHomeProvider is null"); + return null; + } + String packageName = provider.getDefaultHome(userId); + if (packageName == null) { + return null; + } + int resolveInfosSize = resolveInfos.size(); + for (int i = 0; i < resolveInfosSize; i++) { + ResolveInfo resolveInfo = resolveInfos.get(i); + + if (resolveInfo.activityInfo != null && TextUtils.equals( + resolveInfo.activityInfo.packageName, packageName)) { + return new ComponentName(resolveInfo.activityInfo.packageName, + resolveInfo.activityInfo.name); + } + } + return null; + } + + private void updateDefaultHomeLPw(int userId) { + Intent intent = getHomeIntent(); + List<ResolveInfo> resolveInfos = queryIntentActivitiesInternal(intent, null, + PackageManager.GET_META_DATA, userId); + ResolveInfo preferredResolveInfo = findPreferredActivity(intent, null, 0, resolveInfos, + 0, true, false, false, userId); + String packageName = preferredResolveInfo != null + && preferredResolveInfo.activityInfo != null + ? preferredResolveInfo.activityInfo.packageName : null; + String currentPackageName = mDefaultHomeProvider.getDefaultHome(userId); + if (TextUtils.equals(currentPackageName, packageName)) { + return; + } + String[] callingPackages = getPackagesForUid(Binder.getCallingUid()); + if (callingPackages != null && ArrayUtils.contains(callingPackages, + mRequiredPermissionControllerPackage)) { + // PermissionController manages default home directly. + return; + } + mDefaultHomeProvider.setDefaultHomeAsync(packageName, userId); } @Override @@ -23901,6 +23963,13 @@ public class PackageManagerService extends IPackageManager.Stub mDefaultBrowserProvider = provider; } } + + @Override + public void setDefaultHomeProvider(@NonNull DefaultHomeProvider provider) { + synchronized (mPackages) { + mDefaultHomeProvider = provider; + } + } } @GuardedBy("mPackages") diff --git a/services/core/java/com/android/server/policy/role/LegacyRoleResolutionPolicy.java b/services/core/java/com/android/server/policy/role/LegacyRoleResolutionPolicy.java index 3534cf30e2bf..888dd9992bdf 100644 --- a/services/core/java/com/android/server/policy/role/LegacyRoleResolutionPolicy.java +++ b/services/core/java/com/android/server/policy/role/LegacyRoleResolutionPolicy.java @@ -17,10 +17,13 @@ package com.android.server.policy.role; import android.annotation.NonNull; +import android.annotation.UserIdInt; import android.app.role.RoleManager; import android.content.ComponentName; import android.content.Context; +import android.content.pm.PackageManager; import android.content.pm.PackageManagerInternal; +import android.content.pm.ResolveInfo; import android.os.Debug; import android.provider.Settings; import android.telecom.TelecomManager; @@ -33,6 +36,7 @@ import com.android.internal.util.CollectionUtils; import com.android.server.LocalServices; import com.android.server.role.RoleManagerService; +import java.util.ArrayList; import java.util.Collection; import java.util.Collections; import java.util.List; @@ -54,19 +58,44 @@ public class LegacyRoleResolutionPolicy implements RoleManagerService.RoleHolder @NonNull private final Context mContext; - public LegacyRoleResolutionPolicy(Context context) { + public LegacyRoleResolutionPolicy(@NonNull Context context) { mContext = context; } + @NonNull @Override - public List<String> getRoleHolders(String roleName, int userId) { + public List<String> getRoleHolders(@NonNull String roleName, @UserIdInt int userId) { switch (roleName) { + case RoleManager.ROLE_ASSISTANT: { + String legacyAssistant = Settings.Secure.getStringForUser( + mContext.getContentResolver(), Settings.Secure.ASSISTANT, userId); + if (legacyAssistant == null || legacyAssistant.isEmpty()) { + return Collections.emptyList(); + } else { + return Collections.singletonList( + ComponentName.unflattenFromString(legacyAssistant).getPackageName()); + } + } + case RoleManager.ROLE_BROWSER: { + PackageManagerInternal packageManagerInternal = LocalServices.getService( + PackageManagerInternal.class); + String packageName = packageManagerInternal.removeLegacyDefaultBrowserPackageName( + userId); + return CollectionUtils.singletonOrEmpty(packageName); + } + case RoleManager.ROLE_DIALER: { + String setting = Settings.Secure.getStringForUser( + mContext.getContentResolver(), + Settings.Secure.DIALER_DEFAULT_APPLICATION, userId); + return CollectionUtils.singletonOrEmpty(!TextUtils.isEmpty(setting) + ? setting + : mContext.getSystemService(TelecomManager.class).getSystemDialerPackage()); + } case RoleManager.ROLE_SMS: { // Moved over from SmsApplication#getApplication String result = Settings.Secure.getStringForUser( mContext.getContentResolver(), Settings.Secure.SMS_DEFAULT_APPLICATION, userId); - // TODO: STOPSHIP: Remove the following code once we read the value of // config_defaultSms in RoleControllerService. if (result == null) { @@ -92,34 +121,13 @@ public class LegacyRoleResolutionPolicy implements RoleManagerService.RoleHolder SmsApplication.SmsApplicationData app = applicationData; result = app == null ? null : app.mPackageName; } - return CollectionUtils.singletonOrEmpty(result); } - case RoleManager.ROLE_ASSISTANT: { - String legacyAssistant = Settings.Secure.getStringForUser( - mContext.getContentResolver(), Settings.Secure.ASSISTANT, userId); - - if (legacyAssistant == null || legacyAssistant.isEmpty()) { - return Collections.emptyList(); - } else { - return Collections.singletonList( - ComponentName.unflattenFromString(legacyAssistant).getPackageName()); - } - } - case RoleManager.ROLE_DIALER: { - String setting = Settings.Secure.getStringForUser( - mContext.getContentResolver(), - Settings.Secure.DIALER_DEFAULT_APPLICATION, userId); - - return CollectionUtils.singletonOrEmpty(!TextUtils.isEmpty(setting) - ? setting - : mContext.getSystemService(TelecomManager.class).getSystemDialerPackage()); - } - case RoleManager.ROLE_BROWSER: { - PackageManagerInternal packageManagerInternal = LocalServices.getService( - PackageManagerInternal.class); - String packageName = packageManagerInternal.removeLegacyDefaultBrowserPackageName( - userId); + case RoleManager.ROLE_HOME: { + PackageManager packageManager = mContext.getPackageManager(); + List<ResolveInfo> resolveInfos = new ArrayList<>(); + ComponentName componentName = packageManager.getHomeActivities(resolveInfos); + String packageName = componentName != null ? componentName.getPackageName() : null; return CollectionUtils.singletonOrEmpty(packageName); } default: { diff --git a/services/core/java/com/android/server/role/RoleManagerService.java b/services/core/java/com/android/server/role/RoleManagerService.java index 21bf9de5c8b0..d8531210cad8 100644 --- a/services/core/java/com/android/server/role/RoleManagerService.java +++ b/services/core/java/com/android/server/role/RoleManagerService.java @@ -111,7 +111,8 @@ public class RoleManagerService extends SystemService implements RoleUserState.C /** @see #getRoleHolders(String, int) */ public interface RoleHoldersResolver { /** @return a list of packages that hold a given role for a given user */ - List<String> getRoleHolders(String roleName, int userId); + @NonNull + List<String> getRoleHolders(@NonNull String roleName, @UserIdInt int userId); } /** @@ -154,6 +155,7 @@ public class RoleManagerService extends SystemService implements RoleUserState.C PackageManagerInternal packageManagerInternal = LocalServices.getService( PackageManagerInternal.class); packageManagerInternal.setDefaultBrowserProvider(new DefaultBrowserProvider()); + packageManagerInternal.setDefaultHomeProvider(new DefaultHomeProvider()); registerUserRemovedReceiver(); } @@ -741,4 +743,33 @@ public class RoleManagerService extends SystemService implements RoleUserState.C } } } + + private class DefaultHomeProvider implements PackageManagerInternal.DefaultHomeProvider { + + @Nullable + @Override + public String getDefaultHome(@UserIdInt int userId) { + return CollectionUtils.firstOrNull(getOrCreateUserState(userId).getRoleHolders( + RoleManager.ROLE_HOME)); + } + + @Override + public void setDefaultHomeAsync(@Nullable String packageName, @UserIdInt int userId) { + IRoleManagerCallback callback = new IRoleManagerCallback.Stub() { + @Override + public void onSuccess() {} + @Override + public void onFailure() { + Slog.e(LOG_TAG, "Failed to set default home: " + packageName); + } + }; + if (packageName != null) { + getOrCreateControllerService(userId).onAddRoleHolder(RoleManager.ROLE_HOME, + packageName, 0, callback); + } else { + getOrCreateControllerService(userId).onClearRoleHolders(RoleManager.ROLE_HOME, 0, + callback); + } + } + } } |