Donate to e Foundation | Murena handsets with /e/OS | Own a part of Murena! Learn more

Commit 77e25331 authored by Paul Crowley's avatar Paul Crowley Committed by Android (Google) Code Review
Browse files

Merge "Add flag for wiping factory reset protection data." into lmp-mr1-dev

parents 3749541a a7e87acb
Loading
Loading
Loading
Loading
+1 −0
Original line number Diff line number Diff line
@@ -5441,6 +5441,7 @@ package android.app.admin {
    field public static final int PASSWORD_QUALITY_UNSPECIFIED = 0; // 0x0
    field public static final int RESET_PASSWORD_REQUIRE_ENTRY = 1; // 0x1
    field public static final int WIPE_EXTERNAL_STORAGE = 1; // 0x1
    field public static final int WIPE_RESET_PROTECTION_DATA = 2; // 0x2
  }
}
+14 −6
Original line number Diff line number Diff line
@@ -1473,22 +1473,30 @@ public class DevicePolicyManager {

    /**
     * Flag for {@link #wipeData(int)}: also erase the device's external
     * storage.
     * storage (such as SD cards).
     */
    public static final int WIPE_EXTERNAL_STORAGE = 0x0001;

    /**
     * Flag for {@link #wipeData(int)}: also erase the factory reset protection
     * data.
     *
     * This flag may only be set by device owner admins; if it is set by other
     * admins a {@link SecurityException} will be thrown.
     */
    public static final int WIPE_RESET_PROTECTION_DATA = 0x0002;

    /**
     * Ask the user data be wiped.  This will cause the device to reboot,
     * erasing all user data while next booting up.  External storage such
     * as SD cards will be also erased if the flag {@link #WIPE_EXTERNAL_STORAGE}
     * is set.
     * erasing all user data while next booting up.
     *
     * <p>The calling device admin must have requested
     * {@link DeviceAdminInfo#USES_POLICY_WIPE_DATA} to be able to call
     * this method; if it has not, a security exception will be thrown.
     *
     * @param flags Bit mask of additional options: currently 0 and
     *              {@link #WIPE_EXTERNAL_STORAGE} are supported.
     * @param flags Bit mask of additional options: currently supported flags
     * are {@link #WIPE_EXTERNAL_STORAGE} and
     * {@link #WIPE_RESET_PROTECTION_DATA}.
     */
    public void wipeData(int flags) {
        if (mService != null) {
+25 −17
Original line number Diff line number Diff line
@@ -17,6 +17,8 @@
package com.android.server.devicepolicy;

import static android.Manifest.permission.MANAGE_CA_CERTIFICATES;
import static android.app.admin.DevicePolicyManager.WIPE_EXTERNAL_STORAGE;
import static android.app.admin.DevicePolicyManager.WIPE_RESET_PROTECTION_DATA;
import static android.content.pm.PackageManager.GET_UNINSTALLED_PACKAGES;

import android.accessibilityservice.AccessibilityServiceInfo;
@@ -78,6 +80,7 @@ import android.security.IKeyChainService;
import android.security.KeyChain;
import android.security.KeyChain.KeyChainConnection;
import android.text.TextUtils;
import android.service.persistentdata.PersistentDataBlockManager;
import android.util.Log;
import android.util.PrintWriterPrinter;
import android.util.Printer;
@@ -2929,10 +2932,9 @@ public class DevicePolicyManagerService extends IDevicePolicyManager.Stub {
        return false;
    }

    void wipeDataLocked(int flags, String reason) {
    private void wipeDataLocked(boolean wipeExtRequested, String reason) {
        // If the SD card is encrypted and non-removable, we have to force a wipe.
        boolean forceExtWipe = !Environment.isExternalStorageRemovable() && isExtStorageEncrypted();
        boolean wipeExtRequested = (flags&DevicePolicyManager.WIPE_EXTERNAL_STORAGE) != 0;

        // Note: we can only do the wipe via ExternalStorageFormatter if the volume is not emulated.
        if ((forceExtWipe || wipeExtRequested) && !Environment.isExternalStorageEmulated()) {
@@ -2945,9 +2947,7 @@ public class DevicePolicyManagerService extends IDevicePolicyManager.Stub {
        } else {
            try {
                RecoverySystem.rebootWipeUserData(mContext, reason);
            } catch (IOException e) {
                Slog.w(LOG_TAG, "Failed requesting data wipe", e);
            } catch (SecurityException e) {
            } catch (IOException | SecurityException e) {
                Slog.w(LOG_TAG, "Failed requesting data wipe", e);
            }
        }
@@ -2966,20 +2966,27 @@ public class DevicePolicyManagerService extends IDevicePolicyManager.Stub {
                    DeviceAdminInfo.USES_POLICY_WIPE_DATA);

            final String source;
            if (admin != null && admin.info != null) {
            final ComponentName cname = admin.info.getComponent();
            if (cname != null) {
                source = cname.flattenToShortString();
            } else {
                source = admin.info.getPackageName();
            }
            } else {
                source = "?";
            }

            long ident = Binder.clearCallingIdentity();
            try {
                wipeDeviceOrUserLocked(flags, userHandle,
                if ((flags & WIPE_RESET_PROTECTION_DATA) != 0) {
                    if (userHandle != UserHandle.USER_OWNER
                            || !isDeviceOwner(admin.info.getPackageName())) {
                        throw new SecurityException(
                               "Only device owner admins can set WIPE_RESET_PROTECTION_DATA");
                    }
                    PersistentDataBlockManager manager = (PersistentDataBlockManager)
                            mContext.getSystemService(Context.PERSISTENT_DATA_BLOCK_SERVICE);
                    manager.wipe();
                }
                boolean wipeExtRequested = (flags & WIPE_EXTERNAL_STORAGE) != 0;
                wipeDeviceOrUserLocked(wipeExtRequested, userHandle,
                        "DevicePolicyManager.wipeData() from " + source);
            } finally {
                Binder.restoreCallingIdentity(ident);
@@ -2987,9 +2994,9 @@ public class DevicePolicyManagerService extends IDevicePolicyManager.Stub {
        }
    }

    private void wipeDeviceOrUserLocked(int flags, final int userHandle, String reason) {
    private void wipeDeviceOrUserLocked(boolean wipeExtRequested, final int userHandle, String reason) {
        if (userHandle == UserHandle.USER_OWNER) {
            wipeDataLocked(flags, reason);
            wipeDataLocked(wipeExtRequested, reason);
        } else {
            mHandler.post(new Runnable() {
                public void run() {
@@ -3141,7 +3148,8 @@ public class DevicePolicyManagerService extends IDevicePolicyManager.Stub {
            }
            if (wipeData) {
                // Call without holding lock.
                wipeDeviceOrUserLocked(0, identifier, "reportFailedPasswordAttempt()");
                wipeDeviceOrUserLocked(false, identifier,
                        "reportFailedPasswordAttempt()");
            }
        } finally {
            Binder.restoreCallingIdentity(ident);