From 103f93a7e64510e895af5d05385f723a87580808 Mon Sep 17 00:00:00 2001 From: Alex Johnston Date: Wed, 25 Mar 2020 12:36:10 +0000 Subject: Make FRP APIs callable by Settings Background * If the device is an organization-owned managed profile device and a FRP policy is set, the factory reset protection data is no longer erased from factory reset in Settings. Changes * Added isNotEmpty method to FRP policy. * Allow Settings to call getFactoryResetProtectionPolicy by checking for the MASTER_CLEAR permission. Bug: 148847767 Test: manual testing atest com.android.server.devicepolicy.DevicePolicyManagerTest Change-Id: I04f178255dd215579087c33b675b40eed7a6eac7 --- core/java/android/app/admin/DevicePolicyManager.java | 8 +++++--- .../app/admin/FactoryResetProtectionPolicy.java | 18 ++++++++++++++++++ .../devicepolicy/DevicePolicyManagerService.java | 4 +++- 3 files changed, 26 insertions(+), 4 deletions(-) diff --git a/core/java/android/app/admin/DevicePolicyManager.java b/core/java/android/app/admin/DevicePolicyManager.java index 24af5aff67ea..767926fb9d06 100644 --- a/core/java/android/app/admin/DevicePolicyManager.java +++ b/core/java/android/app/admin/DevicePolicyManager.java @@ -4424,11 +4424,13 @@ public class DevicePolicyManager { * the current factory reset protection (FRP) policy set previously by * {@link #setFactoryResetProtectionPolicy}. *

- * This method can also be called by the FRP management agent on device, in which case, - * it can pass {@code null} as the ComponentName. + * This method can also be called by the FRP management agent on device or with the permission + * {@link android.Manifest.permission#MASTER_CLEAR}, in which case, it can pass {@code null} + * as the ComponentName. * * @param admin Which {@link DeviceAdminReceiver} this request is associated with or - * {@code null} if called by the FRP management agent on device. + * {@code null} if called by the FRP management agent on device or with the + * permission {@link android.Manifest.permission#MASTER_CLEAR}. * @return The current FRP policy object or {@code null} if no policy is set. * @throws SecurityException if {@code admin} is not a device owner, a profile owner of * an organization-owned device or the FRP management agent. diff --git a/core/java/android/app/admin/FactoryResetProtectionPolicy.java b/core/java/android/app/admin/FactoryResetProtectionPolicy.java index 954db0459f99..aa94e817c152 100644 --- a/core/java/android/app/admin/FactoryResetProtectionPolicy.java +++ b/core/java/android/app/admin/FactoryResetProtectionPolicy.java @@ -43,6 +43,12 @@ import java.util.List; * reset protection policy for the device by calling the {@code DevicePolicyManager} method * {@link DevicePolicyManager#setFactoryResetProtectionPolicy(ComponentName, * FactoryResetProtectionPolicy)}}. + *

+ * Normally factory reset protection does not kick in if the device is factory reset via Settings. + * This is also the case when a device owner sets factory reset protection policy. However, + * when a profile owner of an organization-owned device sets factory reset protection policy that + * locks the device to specific accounts, the policy will take effect even if factory reset is + * performed from Settings. * * @see DevicePolicyManager#setFactoryResetProtectionPolicy * @see DevicePolicyManager#getFactoryResetProtectionPolicy @@ -236,4 +242,16 @@ public final class FactoryResetProtectionPolicy implements Parcelable { } } + /** + * Returns if the policy will result in factory reset protection being locked to + * admin-specified accounts. + *

+ * When a device has a non-empty factory reset protection policy, trusted factory reset + * via Settings will no longer remove factory reset protection from the device. + * @hide + */ + public boolean isNotEmpty() { + return !mFactoryResetProtectionAccounts.isEmpty() && mFactoryResetProtectionEnabled; + } + } diff --git a/services/devicepolicy/java/com/android/server/devicepolicy/DevicePolicyManagerService.java b/services/devicepolicy/java/com/android/server/devicepolicy/DevicePolicyManagerService.java index 6ab5303b41e4..02efa1dcf7eb 100644 --- a/services/devicepolicy/java/com/android/server/devicepolicy/DevicePolicyManagerService.java +++ b/services/devicepolicy/java/com/android/server/devicepolicy/DevicePolicyManagerService.java @@ -7137,7 +7137,9 @@ public class DevicePolicyManagerService extends BaseIDevicePolicyManager { ActiveAdmin admin; synchronized (getLockObject()) { if (who == null) { - if ((frpManagementAgentUid != mInjector.binderGetCallingUid())) { + if ((frpManagementAgentUid != mInjector.binderGetCallingUid()) + && (mContext.checkCallingPermission(permission.MASTER_CLEAR) + != PackageManager.PERMISSION_GRANTED)) { throw new SecurityException( "Must be called by the FRP management agent on device"); } -- cgit v1.2.3-59-g8ed1b