From 9c0907c3b59534be60920841471c0056c3f2a648 Mon Sep 17 00:00:00 2001 From: Hai Zhang Date: Tue, 1 Dec 2020 20:45:45 -0800 Subject: [PATCH] Move default app related methods to role manager. Default apps (browser, dialer and home) are by no means a concept of permission, so they should not be exposed as permission manager API. Instead, they should be accessed via role manager API. This change moves getDefaultBrowser() and setDefaultBrowser()'s AIDL interface and implementation into RoleManagerService. Package manager has a number of special behaviors regarding these default apps, so we can not pretend that package manager doesn't know about these roles. After all, we can say permission and role are at the same level in the system after recent refactoring that split permission and package. So package manager is reusing the public role API now. The new methods moved to RoleManagerService needs to be system APIs on RoleManager, because IRoleManager cannot be a system API and we need to delegate method calls to it from ApplicationPackageManager. The other methods directly calling into DefaultPermissionGrantPolicy should be moved/refactored as well, depending on whether we want to mainline it, in a later change. Bug: 158736025 Test: presubmit Change-Id: I84b9519a084e410875a3c3e88b33e9a612e7de98 --- .../app/ApplicationPackageManager.java | 15 +- core/java/android/app/role/IRoleManager.aidl | 6 +- core/java/android/app/role/RoleManager.java | 56 +++++- .../permission/IPermissionManager.aidl | 4 - .../android/server/pm/DefaultAppProvider.java | 187 ++++++++++++++++++ .../server/pm/PackageManagerService.java | 53 +++-- .../permission/PermissionManagerService.java | 137 +------------ .../PermissionManagerServiceInternal.java | 144 +------------- .../server/role/RoleManagerService.java | 181 +++++++---------- 9 files changed, 365 insertions(+), 418 deletions(-) create mode 100644 services/core/java/com/android/server/pm/DefaultAppProvider.java diff --git a/core/java/android/app/ApplicationPackageManager.java b/core/java/android/app/ApplicationPackageManager.java index 34437afb614ab..3642d318e8209 100644 --- a/core/java/android/app/ApplicationPackageManager.java +++ b/core/java/android/app/ApplicationPackageManager.java @@ -30,6 +30,7 @@ import android.annotation.Nullable; import android.annotation.StringRes; import android.annotation.UserIdInt; import android.annotation.XmlRes; +import android.app.role.RoleManager; import android.compat.annotation.UnsupportedAppUsage; import android.content.ComponentName; import android.content.ContentResolver; @@ -2306,20 +2307,14 @@ public class ApplicationPackageManager extends PackageManager { @Override public String getDefaultBrowserPackageNameAsUser(int userId) { - try { - return mPermissionManager.getDefaultBrowser(userId); - } catch (RemoteException e) { - throw e.rethrowFromSystemServer(); - } + RoleManager roleManager = mContext.getSystemService(RoleManager.class); + return roleManager.getBrowserRoleHolder(userId); } @Override public boolean setDefaultBrowserPackageNameAsUser(String packageName, int userId) { - try { - return mPermissionManager.setDefaultBrowser(packageName, userId); - } catch (RemoteException e) { - throw e.rethrowFromSystemServer(); - } + RoleManager roleManager = mContext.getSystemService(RoleManager.class); + return roleManager.setBrowserRoleHolder(packageName, userId); } @Override diff --git a/core/java/android/app/role/IRoleManager.aidl b/core/java/android/app/role/IRoleManager.aidl index 6d790b381ace8..5fc25f0422e2f 100644 --- a/core/java/android/app/role/IRoleManager.aidl +++ b/core/java/android/app/role/IRoleManager.aidl @@ -53,5 +53,9 @@ interface IRoleManager { List getHeldRolesFromController(in String packageName); - String getDefaultSmsPackage(int userId); + String getBrowserRoleHolder(int userId); + + boolean setBrowserRoleHolder(String packageName, int userId); + + String getSmsRoleHolder(int userId); } diff --git a/core/java/android/app/role/RoleManager.java b/core/java/android/app/role/RoleManager.java index 408ce0f2ab1aa..8b2e07b097019 100644 --- a/core/java/android/app/role/RoleManager.java +++ b/core/java/android/app/role/RoleManager.java @@ -613,12 +613,56 @@ public final class RoleManager { } /** - * Allows getting the role holder for {@link #ROLE_SMS} without - * {@link Manifest.permission#OBSERVE_ROLE_HOLDERS}, as required by - * {@link android.provider.Telephony.Sms#getDefaultSmsPackage(Context)} + * Get the role holder of {@link #ROLE_BROWSER} without requiring + * {@link Manifest.permission#OBSERVE_ROLE_HOLDERS}, as in + * {@link android.content.pm.PackageManager#getDefaultBrowserPackageNameAsUser(int)} + * + * @param userId the user ID + * @return the package name of the default browser, or {@code null} if none + * + * @hide + */ + @Nullable + //@SystemApi(client = SystemApi.Client.MODULE_LIBRARIES) + public String getBrowserRoleHolder(@UserIdInt int userId) { + try { + return mService.getBrowserRoleHolder(userId); + } catch (RemoteException e) { + throw e.rethrowFromSystemServer(); + } + } + + /** + * Set the role holder of {@link #ROLE_BROWSER} requiring + * {@link Manifest.permission.SET_PREFERRED_APPLICATIONS} instead of + * {@link Manifest.permission#MANAGE_ROLE_HOLDERS}, as in + * {@link android.content.pm.PackageManager#setDefaultBrowserPackageNameAsUser(String, int)} + * + * @param packageName the package name of the default browser, or {@code null} if none + * @param userId the user ID + * @return whether the default browser was set successfully + * + * @hide + */ + @Nullable + @RequiresPermission(Manifest.permission.SET_PREFERRED_APPLICATIONS) + //@SystemApi(client = SystemApi.Client.MODULE_LIBRARIES) + public boolean setBrowserRoleHolder(@Nullable String packageName, @UserIdInt int userId) { + try { + return mService.setBrowserRoleHolder(packageName, userId); + } catch (RemoteException e) { + throw e.rethrowFromSystemServer(); + } + } + + /** + * Allows getting the role holder for {@link #ROLE_SMS} without requiring + * {@link Manifest.permission#OBSERVE_ROLE_HOLDERS}, as in + * {@link android.provider.Telephony.Sms#getDefaultSmsPackage(Context)}. + * + * @param userId the user ID to get the default SMS package for + * @return the package name of the default SMS app, or {@code null} if none * - * @param userId The user ID to get the default SMS package for. - * @return the package name of the default SMS app, or {@code null} if not configured. * @hide */ @Nullable @@ -626,7 +670,7 @@ public final class RoleManager { @TestApi public String getSmsRoleHolder(@UserIdInt int userId) { try { - return mService.getDefaultSmsPackage(userId); + return mService.getSmsRoleHolder(userId); } catch (RemoteException e) { throw e.rethrowFromSystemServer(); } diff --git a/core/java/android/permission/IPermissionManager.aidl b/core/java/android/permission/IPermissionManager.aidl index 1001668149754..9855a9a98cfb7 100644 --- a/core/java/android/permission/IPermissionManager.aidl +++ b/core/java/android/permission/IPermissionManager.aidl @@ -73,10 +73,6 @@ interface IPermissionManager { void resetRuntimePermissions(); - boolean setDefaultBrowser(String packageName, int userId); - - String getDefaultBrowser(int userId); - void grantDefaultPermissionsToEnabledCarrierApps(in String[] packageNames, int userId); void grantDefaultPermissionsToEnabledImsServices(in String[] packageNames, int userId); diff --git a/services/core/java/com/android/server/pm/DefaultAppProvider.java b/services/core/java/com/android/server/pm/DefaultAppProvider.java new file mode 100644 index 0000000000000..cc11fb2c00bd9 --- /dev/null +++ b/services/core/java/com/android/server/pm/DefaultAppProvider.java @@ -0,0 +1,187 @@ +/* + * Copyright (C) 2020 The Android Open Source Project + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +package com.android.server.pm; + +import android.annotation.NonNull; +import android.annotation.Nullable; +import android.annotation.UserIdInt; +import android.app.role.RoleManager; +import android.os.Binder; +import android.os.UserHandle; +import android.util.Slog; + +import com.android.internal.infra.AndroidFuture; +import com.android.internal.util.CollectionUtils; +import com.android.server.FgThread; +import com.android.server.pm.permission.PermissionManagerServiceInternal; + +import java.util.concurrent.ExecutionException; +import java.util.concurrent.Executor; +import java.util.concurrent.TimeUnit; +import java.util.concurrent.TimeoutException; +import java.util.function.Consumer; +import java.util.function.Supplier; + +/** + * Interacts with {@link RoleManager} to provide and manage default apps. + */ +public class DefaultAppProvider { + @NonNull + private final Supplier mRoleManagerSupplier; + @NonNull + private final PermissionManagerServiceInternal mPermissionManager; + + /** + * Create a new instance of this class + * + * @param roleManagerSupplier the supplier for {@link RoleManager} + * @param permissionManager the {@link PermissionManagerServiceInternal} + */ + public DefaultAppProvider(@NonNull Supplier roleManagerSupplier, @NonNull + PermissionManagerServiceInternal permissionManager) { + mRoleManagerSupplier = roleManagerSupplier; + mPermissionManager = permissionManager; + } + + /** + * Get the package name of the default browser. + * + * @param userId the user ID + * @return the package name of the default browser, or {@code null} if none + */ + @Nullable + public String getDefaultBrowser(@UserIdInt int userId) { + return getRoleHolder(RoleManager.ROLE_BROWSER, userId); + } + + /** + * Set the package name of the default browser. + * + * @param packageName package name of the default browser, or {@code null} to unset + * @param async whether the operation should be asynchronous + * @param doGrant whether to grant default permissions + * @param userId the user ID + * @return whether the default browser was successfully set. + */ + public boolean setDefaultBrowser(@Nullable String packageName, boolean async, boolean doGrant, + @UserIdInt int userId) { + if (userId == UserHandle.USER_ALL) { + return false; + } + final RoleManager roleManager = mRoleManagerSupplier.get(); + if (roleManager == null) { + return false; + } + final UserHandle user = UserHandle.of(userId); + final Executor executor = FgThread.getExecutor(); + final AndroidFuture future = new AndroidFuture<>(); + final Consumer callback = successful -> { + if (successful) { + future.complete(null); + } else { + future.completeExceptionally(new RuntimeException()); + } + }; + final long identity = Binder.clearCallingIdentity(); + try { + if (packageName != null) { + roleManager.addRoleHolderAsUser(RoleManager.ROLE_BROWSER, packageName, 0, user, + executor, callback); + } else { + roleManager.clearRoleHoldersAsUser(RoleManager.ROLE_BROWSER, 0, user, executor, + callback); + } + if (!async) { + try { + future.get(5, TimeUnit.SECONDS); + } catch (InterruptedException | ExecutionException | TimeoutException e) { + Slog.e(PackageManagerService.TAG, "Exception while setting default browser: " + + packageName, e); + return false; + } + } + if (doGrant && packageName != null) { + mPermissionManager.grantDefaultPermissionsToDefaultBrowser(packageName, userId); + } + } finally { + Binder.restoreCallingIdentity(identity); + } + return true; + } + + /** + * Get the package name of the default dialer. + * + * @param userId the user ID + * @return the package name of the default dialer, or {@code null} if none + */ + @Nullable + public String getDefaultDialer(@NonNull int userId) { + return getRoleHolder(RoleManager.ROLE_DIALER, userId); + } + + /** + * 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 + public String getDefaultHome(@NonNull int userId) { + return getRoleHolder(RoleManager.ROLE_HOME, userId); + } + + /** + * Set the package name of the default home. + * + * @param packageName package name of the default home + * @param userId the user ID + * @param executor the {@link Executor} to execute callback on + * @param callback the callback made after the default home as been updated + * @return whether the default home was set + */ + public boolean setDefaultHome(@NonNull String packageName, @UserIdInt int userId, + @NonNull Executor executor, @NonNull Consumer callback) { + final RoleManager roleManager = mRoleManagerSupplier.get(); + if (roleManager == null) { + return false; + } + final long identity = Binder.clearCallingIdentity(); + try { + roleManager.addRoleHolderAsUser(RoleManager.ROLE_HOME, packageName, 0, + UserHandle.of(userId), executor, callback); + } finally { + Binder.restoreCallingIdentity(identity); + } + return true; + } + + @Nullable + private String getRoleHolder(@NonNull String roleName, @NonNull int userId) { + final RoleManager roleManager = mRoleManagerSupplier.get(); + if (roleManager == null) { + return null; + } + final long identity = Binder.clearCallingIdentity(); + try { + return CollectionUtils.firstOrNull(roleManager.getRoleHoldersAsUser(roleName, + UserHandle.of(userId))); + } finally { + Binder.restoreCallingIdentity(identity); + } + } +} diff --git a/services/core/java/com/android/server/pm/PackageManagerService.java b/services/core/java/com/android/server/pm/PackageManagerService.java index e35749704aafa..2f076b652d295 100644 --- a/services/core/java/com/android/server/pm/PackageManagerService.java +++ b/services/core/java/com/android/server/pm/PackageManagerService.java @@ -152,6 +152,7 @@ import android.app.ResourcesManager; import android.app.admin.IDevicePolicyManager; import android.app.admin.SecurityLog; import android.app.backup.IBackupManager; +import android.app.role.RoleManager; import android.compat.annotation.ChangeId; import android.compat.annotation.EnabledAfter; import android.content.BroadcastReceiver; @@ -941,6 +942,7 @@ public class PackageManagerService extends IPackageManager.Stub private final Singleton mViewCompilerProducer; private final Singleton mPermissionManagerProducer; private final Singleton mIncrementalManagerProducer; + private final Singleton mDefaultAppProviderProducer; private final SystemWrapper mSystemWrapper; private final ServiceProducer mGetLocalServiceProducer; private final ServiceProducer mGetSystemServiceProducer; @@ -962,6 +964,7 @@ public class PackageManagerService extends IPackageManager.Stub Producer permissionManagerProducer, Producer viewCompilerProducer, Producer incrementalManagerProducer, + Producer defaultAppProviderProducer, SystemWrapper systemWrapper, ServiceProducer getLocalServiceProducer, ServiceProducer getSystemServiceProducer) { @@ -986,6 +989,7 @@ public class PackageManagerService extends IPackageManager.Stub mPermissionManagerProducer = new Singleton<>(permissionManagerProducer); mViewCompilerProducer = new Singleton<>(viewCompilerProducer); mIncrementalManagerProducer = new Singleton<>(incrementalManagerProducer); + mDefaultAppProviderProducer = new Singleton<>(defaultAppProviderProducer); mSystemWrapper = systemWrapper; mGetLocalServiceProducer = getLocalServiceProducer; mGetSystemServiceProducer = getSystemServiceProducer; @@ -1098,6 +1102,10 @@ public class PackageManagerService extends IPackageManager.Stub public IncrementalManager getIncrementalManager() { return mIncrementalManagerProducer.get(this, mPackageManager); } + + public DefaultAppProvider getDefaultAppProvider() { + return mDefaultAppProviderProducer.get(this, mPackageManager); + } } /** Provides an abstraction to static access to system state. */ @@ -1155,6 +1163,7 @@ public class PackageManagerService extends IPackageManager.Stub public ArtManagerService artManagerService; public @Nullable String configuratorPackage; public int defParseFlags; + public DefaultAppProvider defaultAppProvider; public DexManager dexManager; public List dirsToScanAsSystem; public @Nullable String documenterPackage; @@ -1308,6 +1317,8 @@ public class PackageManagerService extends IPackageManager.Stub private final IncrementalManager mIncrementalManager; + private final DefaultAppProvider mDefaultAppProvider; + private final PackageProperty mPackageProperty = new PackageProperty(); private static class IFVerificationParams { @@ -2761,6 +2772,8 @@ public class PackageManagerService extends IPackageManager.Stub (i, pm) -> new ViewCompiler(i.getInstallLock(), i.getInstaller()), (i, pm) -> (IncrementalManager) pm.mContext.getSystemService(Context.INCREMENTAL_SERVICE), + (i, pm) -> new DefaultAppProvider(() -> context.getSystemService(RoleManager.class), + i.getPermissionManagerServiceInternal()), new DefaultSystemWrapper(), LocalServices::getService, context::getSystemService); @@ -2936,6 +2949,7 @@ public class PackageManagerService extends IPackageManager.Stub mArtManagerService = testParams.artManagerService; mAvailableFeatures = testParams.availableFeatures; mDefParseFlags = testParams.defParseFlags; + mDefaultAppProvider = testParams.defaultAppProvider; mDexManager = testParams.dexManager; mDirsToScanAsSystem = testParams.dirsToScanAsSystem; mFactoryTest = testParams.factoryTest; @@ -3043,6 +3057,7 @@ public class PackageManagerService extends IPackageManager.Stub mSettings = injector.getSettings(); mPermissionManagerService = injector.getPermissionManagerService(); mIncrementalManager = mInjector.getIncrementalManager(); + mDefaultAppProvider = mInjector.getDefaultAppProvider(); PlatformCompat platformCompat = mInjector.getCompatibility(); mPackageParserCallback = new PackageParser2.Callback() { @Override @@ -7959,8 +7974,8 @@ public class PackageManagerService extends IPackageManager.Stub } else { // Browser/generic handling case. If there's a default browser, go straight // to that (but only if there is no other higher-priority match). - final String defaultBrowserPackageName = - mPermissionManager.getDefaultBrowser(userId); + final String defaultBrowserPackageName = mDefaultAppProvider.getDefaultBrowser( + userId); int maxMatchPrio = 0; ResolveInfo defaultBrowserMatch = null; final int numCandidates = matchAllList.size(); @@ -14156,8 +14171,8 @@ public class PackageManagerService extends IPackageManager.Stub final boolean isCallerOwner = isCallerDeviceOrProfileOwner(userId); final long callingId = Binder.clearCallingIdentity(); try { - final String activeLauncherPackageName = mPermissionManager.getDefaultHome(userId); - final String dialerPackageName = mPermissionManager.getDefaultDialer(userId); + final String activeLauncherPackageName = mDefaultAppProvider.getDefaultHome(userId); + final String dialerPackageName = mDefaultAppProvider.getDefaultDialer(userId); for (int i = 0; i < packageNames.length; i++) { canSuspend[i] = false; final String packageName = packageNames[i]; @@ -20635,10 +20650,10 @@ public class PackageManagerService extends IPackageManager.Stub } private void clearDefaultBrowserIfNeededForUser(String packageName, int userId) { - final String defaultBrowserPackageName = mPermissionManager.getDefaultBrowser(userId); + final String defaultBrowserPackageName = mDefaultAppProvider.getDefaultBrowser(userId); if (!TextUtils.isEmpty(defaultBrowserPackageName)) { if (packageName.equals(defaultBrowserPackageName)) { - mPermissionManager.setDefaultBrowser(null, true, true, userId); + mDefaultAppProvider.setDefaultBrowser(null, true, true, userId); } } } @@ -20653,7 +20668,7 @@ public class PackageManagerService extends IPackageManager.Stub // If this browser is restored from user's backup, do not clear // default-browser state for this user if (installReason != PackageManager.INSTALL_REASON_DEVICE_RESTORE) { - mPermissionManager.setDefaultBrowser(null, true, true, userId); + mDefaultAppProvider.setDefaultBrowser(null, true, true, userId); } } @@ -20692,7 +20707,7 @@ public class PackageManagerService extends IPackageManager.Stub // significant refactoring to keep all default apps in the package // manager (cleaner but more work) or have the services provide // callbacks to the package manager to request a default app reset. - mPermissionManager.setDefaultBrowser(null, true, true, userId); + mDefaultAppProvider.setDefaultBrowser(null, true, true, userId); resetNetworkPolicies(userId); synchronized (mLock) { scheduleWritePackageRestrictionsLocked(userId); @@ -20952,8 +20967,8 @@ public class PackageManagerService extends IPackageManager.Stub defaultBrowser = mSettings.removeDefaultBrowserPackageNameLPw(userId1); } if (defaultBrowser != null) { - mPermissionManager - .setDefaultBrowser(defaultBrowser, false, false, userId1); + mDefaultAppProvider.setDefaultBrowser(defaultBrowser, false, false, + userId1); } }); } catch (Exception e) { @@ -21193,7 +21208,7 @@ public class PackageManagerService extends IPackageManager.Stub } allHomeCandidates.addAll(resolveInfos); - final String packageName = mPermissionManager.getDefaultHome(userId); + final String packageName = mDefaultAppProvider.getDefaultHome(userId); if (packageName == null) { return null; } @@ -21247,7 +21262,7 @@ public class PackageManagerService extends IPackageManager.Stub final String packageName = preferredResolveInfo != null && preferredResolveInfo.activityInfo != null ? preferredResolveInfo.activityInfo.packageName : null; - final String currentPackageName = mPermissionManager.getDefaultHome(userId); + final String currentPackageName = mDefaultAppProvider.getDefaultHome(userId); if (TextUtils.equals(currentPackageName, packageName)) { return false; } @@ -21262,12 +21277,12 @@ public class PackageManagerService extends IPackageManager.Stub // Keep the default home package in RoleManager. return false; } - mPermissionManager.setDefaultHome(packageName, userId, (successful) -> { - if (successful) { - postPreferredActivityChangedBroadcast(userId); - } - }); - return true; + return mDefaultAppProvider.setDefaultHome(packageName, userId, mContext.getMainExecutor(), + successful -> { + if (successful) { + postPreferredActivityChangedBroadcast(userId); + } + }); } @Override @@ -25059,7 +25074,7 @@ public class PackageManagerService extends IPackageManager.Stub private String[] getKnownPackageNamesInternal(int knownPackage, int userId) { switch (knownPackage) { case PackageManagerInternal.PACKAGE_BROWSER: - return new String[]{mPermissionManager.getDefaultBrowser(userId)}; + return new String[] { mDefaultAppProvider.getDefaultBrowser(userId) }; case PackageManagerInternal.PACKAGE_INSTALLER: return filterOnlySystemPackages(mRequiredInstallerPackage); case PackageManagerInternal.PACKAGE_SETUP_WIZARD: diff --git a/services/core/java/com/android/server/pm/permission/PermissionManagerService.java b/services/core/java/com/android/server/pm/permission/PermissionManagerService.java index 3f923c0b0c670..be956b8fd8bf8 100644 --- a/services/core/java/com/android/server/pm/permission/PermissionManagerService.java +++ b/services/core/java/com/android/server/pm/permission/PermissionManagerService.java @@ -151,9 +151,6 @@ import com.android.server.pm.UserManagerInternal; import com.android.server.pm.UserManagerService; import com.android.server.pm.parsing.PackageInfoUtils; import com.android.server.pm.parsing.pkg.AndroidPackage; -import com.android.server.pm.permission.PermissionManagerServiceInternal.DefaultBrowserProvider; -import com.android.server.pm.permission.PermissionManagerServiceInternal.DefaultDialerProvider; -import com.android.server.pm.permission.PermissionManagerServiceInternal.DefaultHomeProvider; import com.android.server.policy.PermissionPolicyInternal; import com.android.server.policy.SoftRestrictedPermissionPolicy; @@ -176,7 +173,6 @@ import java.util.concurrent.CompletableFuture; import java.util.concurrent.ExecutionException; import java.util.concurrent.TimeUnit; import java.util.concurrent.TimeoutException; -import java.util.function.Consumer; /** * Manages all permissions and handles permissions related tasks. @@ -298,15 +294,6 @@ public class PermissionManagerService extends IPermissionManager.Stub { @NonNull private final OnPermissionChangeListeners mOnPermissionChangeListeners; - @GuardedBy("mLock") - private DefaultBrowserProvider mDefaultBrowserProvider; - - @GuardedBy("mLock") - private DefaultDialerProvider mDefaultDialerProvider; - - @GuardedBy("mLock") - private DefaultHomeProvider mDefaultHomeProvider; - // TODO: Take a look at the methods defined in the callback. // The callback was initially created to support the split between permission // manager and the package manager. However, it's started to be used for other @@ -2011,60 +1998,6 @@ public class PermissionManagerService extends IPermissionManager.Stub { mPackageManagerInt.writePermissionSettings(asyncUpdatedUsers.toArray(), true); } - @Override - public String getDefaultBrowser(int userId) { - final int callingUid = Binder.getCallingUid(); - if (UserHandle.getUserId(callingUid) != userId) { - mContext.enforceCallingOrSelfPermission( - android.Manifest.permission.INTERACT_ACROSS_USERS_FULL, null); - } - if (mPackageManagerInt.getInstantAppPackageName(callingUid) != null) { - return null; - } - DefaultBrowserProvider provider; - synchronized (mLock) { - provider = mDefaultBrowserProvider; - } - return provider != null ? provider.getDefaultBrowser(userId) : null; - } - - @Override - public boolean setDefaultBrowser(String packageName, int userId) { - mContext.enforceCallingOrSelfPermission( - android.Manifest.permission.SET_PREFERRED_APPLICATIONS, null); - if (UserHandle.getCallingUserId() != userId) { - mContext.enforceCallingOrSelfPermission( - android.Manifest.permission.INTERACT_ACROSS_USERS_FULL, null); - } - return setDefaultBrowserInternal(packageName, false, true, userId); - } - - private boolean setDefaultBrowserInternal(String packageName, boolean async, - boolean doGrant, int userId) { - if (userId == UserHandle.USER_ALL) { - return false; - } - DefaultBrowserProvider provider; - synchronized (mLock) { - provider = mDefaultBrowserProvider; - } - if (provider == null) { - return false; - } - if (async) { - provider.setDefaultBrowserAsync(packageName, userId); - } else { - if (!provider.setDefaultBrowser(packageName, userId)) { - return false; - } - } - if (doGrant && packageName != null) { - mDefaultPermissionGrantPolicy.grantDefaultPermissionsToDefaultBrowser(packageName, - userId); - } - return true; - } - @Override public void grantDefaultPermissionsToEnabledCarrierApps(String[] packageNames, int userId) { final int callingUid = Binder.getCallingUid(); @@ -5200,48 +5133,6 @@ public class PermissionManagerService extends IPermissionManager.Stub { } } - @Override - public void setDefaultBrowserProvider(@NonNull DefaultBrowserProvider provider) { - synchronized (mLock) { - mDefaultBrowserProvider = provider; - } - } - - @Override - public void setDefaultBrowser(String packageName, boolean async, boolean doGrant, - int userId) { - setDefaultBrowserInternal(packageName, async, doGrant, userId); - } - - @Override - public void setDefaultDialerProvider(@NonNull DefaultDialerProvider provider) { - synchronized (mLock) { - mDefaultDialerProvider = provider; - } - } - - @Override - public void setDefaultHomeProvider(@NonNull DefaultHomeProvider provider) { - synchronized (mLock) { - mDefaultHomeProvider = provider; - } - } - - @Override - public void setDefaultHome(String packageName, int userId, Consumer callback) { - if (userId == UserHandle.USER_ALL) { - return; - } - DefaultHomeProvider provider; - synchronized (mLock) { - provider = mDefaultHomeProvider; - } - if (provider == null) { - return; - } - provider.setDefaultHomeAsync(packageName, userId, callback); - } - @Override public void setDialerAppPackagesProvider(PackagesProvider provider) { mDefaultPermissionGrantPolicy.setDialerAppPackagesProvider(provider); @@ -5283,30 +5174,10 @@ public class PermissionManagerService extends IPermissionManager.Stub { } @Override - public String getDefaultBrowser(int userId) { - DefaultBrowserProvider provider; - synchronized (mLock) { - provider = mDefaultBrowserProvider; - } - return provider != null ? provider.getDefaultBrowser(userId) : null; - } - - @Override - public String getDefaultDialer(int userId) { - DefaultDialerProvider provider; - synchronized (mLock) { - provider = mDefaultDialerProvider; - } - return provider != null ? provider.getDefaultDialer(userId) : null; - } - - @Override - public String getDefaultHome(int userId) { - DefaultHomeProvider provider; - synchronized (mLock) { - provider = mDefaultHomeProvider; - } - return provider != null ? provider.getDefaultHome(userId) : null; + public void grantDefaultPermissionsToDefaultBrowser(@NonNull String packageName, + @UserIdInt int userId) { + mDefaultPermissionGrantPolicy.grantDefaultPermissionsToDefaultBrowser(packageName, + userId); } @Override diff --git a/services/core/java/com/android/server/pm/permission/PermissionManagerServiceInternal.java b/services/core/java/com/android/server/pm/permission/PermissionManagerServiceInternal.java index f924651f10514..c1efb1d920e63 100644 --- a/services/core/java/com/android/server/pm/permission/PermissionManagerServiceInternal.java +++ b/services/core/java/com/android/server/pm/permission/PermissionManagerServiceInternal.java @@ -30,7 +30,6 @@ import java.util.Collections; import java.util.List; import java.util.Objects; import java.util.Set; -import java.util.function.Consumer; /** * Internal interfaces services. @@ -66,82 +65,6 @@ public abstract class PermissionManagerServiceInternal extends PermissionManager String[] getPackages(String authority, int userId); } - /** - * Provider for default browser - */ - public interface DefaultBrowserProvider { - - /** - * Get the package name of the default browser. - * - * @param userId the user id - * - * @return the package name of the default browser, or {@code null} if none - */ - @Nullable - String getDefaultBrowser(@UserIdInt int userId); - - /** - * Set the package name of the default browser. - * - * @param packageName package name of the default browser, or {@code null} to remove - * @param userId the user id - * - * @return whether the default browser was successfully set. - */ - boolean setDefaultBrowser(@Nullable String packageName, @UserIdInt int userId); - - /** - * Set the package name of the default browser asynchronously. - * - * @param packageName package name of the default browser, or {@code null} to remove - * @param userId the user id - */ - void setDefaultBrowserAsync(@Nullable String packageName, @UserIdInt int userId); - } - - /** - * Provider for default dialer - */ - public interface DefaultDialerProvider { - - /** - * Get the package name of the default dialer. - * - * @param userId the user id - * - * @return the package name of the default dialer, or {@code null} if none - */ - @Nullable - String getDefaultDialer(@UserIdInt int userId); - } - - /** - * 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 - * @param callback the callback made after the default home as been updated - */ - void setDefaultHomeAsync(@Nullable String packageName, @UserIdInt int userId, - @NonNull Consumer callback); - } - public abstract void systemReady(); /** @@ -319,69 +242,12 @@ public abstract class PermissionManagerServiceInternal extends PermissionManager public abstract void setVoiceInteractionPackagesProvider(PackagesProvider provider); /** - * Sets the default browser provider. - * - * @param provider the provider + * Requests granting of the default permissions to the current default browser. + * @param packageName The default browser package name. + * @param userId The user for which to grant the permissions. */ - public abstract void setDefaultBrowserProvider(@NonNull DefaultBrowserProvider provider); - - /** - * Sets the package name of the default browser provider for the given user. - * - * @param packageName The package name of the default browser or {@code null} - * to clear the default browser - * @param async If {@code true}, set the default browser asynchronously, - * otherwise set it synchronously - * @param doGrant If {@code true} and if {@code packageName} is not {@code null}, - * perform default permission grants on the browser, otherwise skip the - * default permission grants. - * @param userId The user to set the default browser for. - */ - public abstract void setDefaultBrowser(@Nullable String packageName, boolean async, - boolean doGrant, @UserIdInt int userId); - - /** - * Sets the default dialer provider. - * - * @param provider the provider - */ - public abstract void setDefaultDialerProvider(@NonNull DefaultDialerProvider provider); - - /** - * Sets the default home provider. - * - * @param provider the provider - */ - public abstract void setDefaultHomeProvider(@NonNull DefaultHomeProvider provider); - - /** - * Asynchronously sets the package name of the default home provider for the given user. - * - * @param packageName The package name of the default home or {@code null} - * to clear the default browser - * @param userId The user to set the default browser for - * @param callback Invoked after the default home has been set - */ - public abstract void setDefaultHome(@Nullable String packageName, @UserIdInt int userId, - @NonNull Consumer callback); - - /** - * Returns the default browser package name for the given user. - */ - @Nullable - public abstract String getDefaultBrowser(@UserIdInt int userId); - - /** - * Returns the default dialer package name for the given user. - */ - @Nullable - public abstract String getDefaultDialer(@UserIdInt int userId); - - /** - * Returns the default home package name for the given user. - */ - @Nullable - public abstract String getDefaultHome(@UserIdInt int userId); + public abstract void grantDefaultPermissionsToDefaultBrowser( + @NonNull String packageName, @UserIdInt int userId); /** * Requests granting of the default permissions to the current default Use Open Wifi app. diff --git a/services/core/java/com/android/server/role/RoleManagerService.java b/services/core/java/com/android/server/role/RoleManagerService.java index ab6ada2f85f7f..3d91a85020974 100644 --- a/services/core/java/com/android/server/role/RoleManagerService.java +++ b/services/core/java/com/android/server/role/RoleManagerService.java @@ -83,7 +83,6 @@ import java.util.Objects; import java.util.concurrent.ExecutionException; import java.util.concurrent.TimeUnit; import java.util.concurrent.TimeoutException; -import java.util.function.Consumer; /** * Service for role management. @@ -162,12 +161,6 @@ public class RoleManagerService extends SystemService implements RoleUserState.C LocalServices.addService(RoleManagerInternal.class, new Internal()); - PermissionManagerServiceInternal permissionManagerInternal = - LocalServices.getService(PermissionManagerServiceInternal.class); - permissionManagerInternal.setDefaultBrowserProvider(new DefaultBrowserProvider()); - permissionManagerInternal.setDefaultDialerProvider(new DefaultDialerProvider()); - permissionManagerInternal.setDefaultHomeProvider(new DefaultHomeProvider()); - registerUserRemovedReceiver(); } @@ -657,12 +650,84 @@ public class RoleManagerService extends SystemService implements RoleUserState.C resultReceiver); } + @Nullable @Override - public String getDefaultSmsPackage(int userId) { + public String getBrowserRoleHolder(@UserIdInt int userId) { + final int callingUid = Binder.getCallingUid(); + if (UserHandle.getUserId(callingUid) != userId) { + getContext().enforceCallingOrSelfPermission( + android.Manifest.permission.INTERACT_ACROSS_USERS_FULL, null); + } + final PackageManagerInternal packageManager = LocalServices.getService( + PackageManagerInternal.class); + if (packageManager.getInstantAppPackageName(callingUid) != null) { + return null; + } + final long identity = Binder.clearCallingIdentity(); try { - return CollectionUtils.firstOrNull( - getRoleHoldersAsUser(RoleManager.ROLE_SMS, userId)); + return CollectionUtils.firstOrNull(getRoleHoldersAsUser(RoleManager.ROLE_BROWSER, + userId)); + } finally { + Binder.restoreCallingIdentity(identity); + } + } + + @Override + public boolean setBrowserRoleHolder(@Nullable String packageName, @UserIdInt int userId) { + final Context context = getContext(); + context.enforceCallingOrSelfPermission( + android.Manifest.permission.SET_PREFERRED_APPLICATIONS, null); + if (UserHandle.getCallingUserId() != userId) { + context.enforceCallingOrSelfPermission( + android.Manifest.permission.INTERACT_ACROSS_USERS_FULL, null); + } + + if (!mUserManagerInternal.exists(userId)) { + return false; + } + + final AndroidFuture future = new AndroidFuture<>(); + final RemoteCallback callback = new RemoteCallback(result -> { + boolean successful = result != null; + if (successful) { + future.complete(null); + } else { + future.completeExceptionally(new RuntimeException()); + } + }); + final long identity = Binder.clearCallingIdentity(); + try { + if (packageName != null) { + addRoleHolderAsUser(RoleManager.ROLE_BROWSER, packageName, 0, userId, callback); + } else { + clearRoleHoldersAsUser(RoleManager.ROLE_BROWSER, 0, userId, callback); + } + try { + future.get(5, TimeUnit.SECONDS); + } catch (InterruptedException | ExecutionException | TimeoutException e) { + Slog.e(LOG_TAG, "Exception while setting default browser: " + packageName, e); + return false; + } + + if (packageName != null) { + final PermissionManagerServiceInternal permissionManager = + LocalServices.getService(PermissionManagerServiceInternal.class); + permissionManager.grantDefaultPermissionsToDefaultBrowser(packageName, userId); + } + } finally { + Binder.restoreCallingIdentity(identity); + } + + return true; + } + + @Override + public String getSmsRoleHolder(int userId) { + final long identity = Binder.clearCallingIdentity(); + try { + return CollectionUtils.firstOrNull(getRoleHoldersAsUser(RoleManager.ROLE_SMS, + userId)); } finally { Binder.restoreCallingIdentity(identity); } @@ -718,100 +783,4 @@ public class RoleManagerService extends SystemService implements RoleUserState.C return getOrCreateUserState(userId).getRolesAndHolders(); } } - - private class DefaultBrowserProvider implements - PermissionManagerServiceInternal.DefaultBrowserProvider { - - @Nullable - @Override - public String getDefaultBrowser(@UserIdInt int userId) { - return CollectionUtils.firstOrNull(getOrCreateUserState(userId).getRoleHolders( - RoleManager.ROLE_BROWSER)); - } - - @Override - public boolean setDefaultBrowser(@Nullable String packageName, @UserIdInt int userId) { - AndroidFuture future = new AndroidFuture<>(); - RemoteCallback callback = new RemoteCallback(result -> { - boolean successful = result != null; - if (successful) { - future.complete(null); - } else { - future.completeExceptionally(new RuntimeException()); - } - }); - if (packageName != null) { - getOrCreateController(userId).onAddRoleHolder(RoleManager.ROLE_BROWSER, - packageName, 0, callback); - } else { - getOrCreateController(userId).onClearRoleHolders(RoleManager.ROLE_BROWSER, 0, - callback); - } - try { - future.get(5, TimeUnit.SECONDS); - return true; - } catch (InterruptedException | ExecutionException | TimeoutException e) { - Slog.e(LOG_TAG, "Exception while setting default browser: " + packageName, e); - return false; - } - } - - @Override - public void setDefaultBrowserAsync(@Nullable String packageName, @UserIdInt int userId) { - RemoteCallback callback = new RemoteCallback(result -> { - boolean successful = result != null; - if (!successful) { - Slog.e(LOG_TAG, "Failed to set default browser: " + packageName); - } - }); - if (packageName != null) { - getOrCreateController(userId).onAddRoleHolder(RoleManager.ROLE_BROWSER, - packageName, 0, callback); - } else { - getOrCreateController(userId).onClearRoleHolders(RoleManager.ROLE_BROWSER, 0, - callback); - } - } - } - - private class DefaultDialerProvider implements - PermissionManagerServiceInternal.DefaultDialerProvider { - - @Nullable - @Override - public String getDefaultDialer(@UserIdInt int userId) { - return CollectionUtils.firstOrNull(getOrCreateUserState(userId).getRoleHolders( - RoleManager.ROLE_DIALER)); - } - } - - private class DefaultHomeProvider implements - PermissionManagerServiceInternal.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, - @NonNull Consumer callback) { - RemoteCallback remoteCallback = new RemoteCallback(result -> { - boolean successful = result != null; - if (!successful) { - Slog.e(LOG_TAG, "Failed to set default home: " + packageName); - } - callback.accept(successful); - }); - if (packageName != null) { - getOrCreateController(userId).onAddRoleHolder(RoleManager.ROLE_HOME, - packageName, 0, remoteCallback); - } else { - getOrCreateController(userId).onClearRoleHolders(RoleManager.ROLE_HOME, 0, - remoteCallback); - } - } - } }