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

Commit 9770d6fe authored by Jonathan Scott's avatar Jonathan Scott Committed by Automerger Merge Worker
Browse files

Merge "[base] Fix logic around overriding DO when there are accounts on...

Merge "[base] Fix logic around overriding DO when there are accounts on device." into udc-dev am: e144f35e

Original change: https://googleplex-android-review.googlesource.com/c/platform/frameworks/base/+/22576317



Change-Id: I2300bf176c2c1c5a47b18ae8367b44355a9122ec
Signed-off-by: default avatarAutomerger Merge Worker <android-build-automerger-merge-worker@system.gserviceaccount.com>
parents ca255553 e144f35e
Loading
Loading
Loading
Loading
+1 −0
Original line number Diff line number Diff line
@@ -538,6 +538,7 @@ package android.app.admin {

  public class DevicePolicyManager {
    method @RequiresPermission(anyOf={android.Manifest.permission.MANAGE_USERS, android.Manifest.permission.INTERACT_ACROSS_USERS}) public void acknowledgeNewUserDisclaimer();
    method @RequiresPermission(android.Manifest.permission.MANAGE_PROFILE_AND_DEVICE_OWNERS) public void calculateHasIncompatibleAccounts();
    method @RequiresPermission(android.Manifest.permission.MANAGE_PROFILE_AND_DEVICE_OWNERS) public void clearOrganizationId();
    method @RequiresPermission(android.Manifest.permission.CLEAR_FREEZE_PERIOD) public void clearSystemUpdatePolicyFreezePeriodRecord();
    method @RequiresPermission(android.Manifest.permission.FORCE_DEVICE_POLICY_MANAGER_LOGS) public long forceNetworkLogs();
+17 −0
Original line number Diff line number Diff line
@@ -16824,6 +16824,23 @@ public class DevicePolicyManager {
        }
    }
    /**
     * Recalculate the incompatible accounts cache.
     *
     * @hide
     */
    @TestApi
    @RequiresPermission(permission.MANAGE_PROFILE_AND_DEVICE_OWNERS)
    public void calculateHasIncompatibleAccounts() {
        if (mService != null) {
            try {
                mService.calculateHasIncompatibleAccounts();
            } catch (RemoteException e) {
                throw e.rethrowFromSystemServer();
            }
        }
    }
    /**
     * @return {@code true} if bypassing the device policy management role qualification is allowed
     * with the current state of the device.
+2 −0
Original line number Diff line number Diff line
@@ -608,4 +608,6 @@ interface IDevicePolicyManager {

    boolean isDeviceFinanced(String callerPackageName);
    String getFinancedDeviceKioskRoleHolder(String callerPackageName);

    void calculateHasIncompatibleAccounts();
}
+86 −45
Original line number Diff line number Diff line
@@ -85,6 +85,7 @@ import static android.Manifest.permission.REQUEST_PASSWORD_COMPLEXITY;
import static android.Manifest.permission.SET_TIME;
import static android.Manifest.permission.SET_TIME_ZONE;
import static android.accessibilityservice.AccessibilityServiceInfo.FEEDBACK_ALL_MASK;
import static android.accounts.AccountManager.LOGIN_ACCOUNTS_CHANGED_ACTION;
import static android.app.ActivityManager.LOCK_TASK_MODE_NONE;
import static android.app.AppOpsManager.MODE_ALLOWED;
import static android.app.AppOpsManager.MODE_DEFAULT;
@@ -532,6 +533,7 @@ import java.util.Map;
import java.util.Objects;
import java.util.Set;
import java.util.concurrent.CompletableFuture;
import java.util.concurrent.ConcurrentHashMap;
import java.util.concurrent.ExecutionException;
import java.util.concurrent.Executor;
import java.util.concurrent.TimeUnit;
@@ -1140,6 +1142,11 @@ public class DevicePolicyManagerService extends IDevicePolicyManager.Stub {
                    }
                }
            }
            if (Intent.ACTION_BOOT_COMPLETED.equals(action)) {
                calculateHasIncompatibleAccounts();
            }
            if (Intent.ACTION_BOOT_COMPLETED.equals(action)
                    && userHandle == mOwners.getDeviceOwnerUserId()) {
                mBugreportCollectionManager.checkForPendingBugreportAfterBoot();
@@ -1253,6 +1260,8 @@ public class DevicePolicyManagerService extends IDevicePolicyManager.Stub {
            } else if (ACTION_MANAGED_PROFILE_AVAILABLE.equals(action)) {
                notifyIfManagedSubscriptionsAreUnavailable(
                        UserHandle.of(userHandle), /* managedProfileAvailable= */ true);
            } else if (LOGIN_ACCOUNTS_CHANGED_ACTION.equals(action)) {
                calculateHasIncompatibleAccounts();
            }
        }
@@ -2105,6 +2114,7 @@ public class DevicePolicyManagerService extends IDevicePolicyManager.Stub {
        filter.addAction(Intent.ACTION_USER_STOPPED);
        filter.addAction(Intent.ACTION_USER_SWITCHED);
        filter.addAction(Intent.ACTION_USER_UNLOCKED);
        filter.addAction(LOGIN_ACCOUNTS_CHANGED_ACTION);
        filter.addAction(ACTION_MANAGED_PROFILE_UNAVAILABLE);
        filter.addAction(ACTION_MANAGED_PROFILE_AVAILABLE);
        filter.setPriority(IntentFilter.SYSTEM_HIGH_PRIORITY);
@@ -9560,6 +9570,7 @@ public class DevicePolicyManagerService extends IDevicePolicyManager.Stub {
        synchronized (getLockObject()) {
            enforceCanSetDeviceOwnerLocked(caller, admin, userId, hasIncompatibleAccountsOrNonAdb);
            Preconditions.checkArgument(isPackageInstalledForUser(admin.getPackageName(), userId),
                    "Invalid component " + admin + " for device owner");
            final ActiveAdmin activeAdmin = getActiveAdminUncheckedLocked(admin, userId);
@@ -18386,6 +18397,26 @@ public class DevicePolicyManagerService extends IDevicePolicyManager.Stub {
        return isUserAffiliatedWithDeviceLocked(userId);
    }
    private boolean hasIncompatibleAccountsOnAnyUser() {
        if (mHasIncompatibleAccounts == null) {
            // Hasn't loaded for the first time yet - assume the worst
            return true;
        }
        for (boolean hasIncompatible : mHasIncompatibleAccounts.values()) {
            if (hasIncompatible) {
                return true;
            }
        }
        return false;
    }
    private boolean hasIncompatibleAccounts(int userId) {
        return mHasIncompatibleAccounts == null ? true
                : mHasIncompatibleAccounts.getOrDefault(userId, /* default= */ false);
    }
    /**
     * Return true if a given user has any accounts that'll prevent installing a device or profile
     * owner {@code owner}.
@@ -18423,7 +18454,7 @@ public class DevicePolicyManagerService extends IDevicePolicyManager.Stub {
                }
            }
            boolean compatible = !hasIncompatibleAccounts(am, accounts);
            boolean compatible = !hasIncompatibleAccounts(userId);
            if (compatible) {
                Slogf.w(LOG_TAG, "All accounts are compatible");
            } else {
@@ -18433,20 +18464,43 @@ public class DevicePolicyManagerService extends IDevicePolicyManager.Stub {
        });
    }
    private boolean hasIncompatibleAccounts(AccountManager am, Account[] accounts) {
        // TODO(b/244284408): Add test
        final String[] feature_allow =
    @Override
    public void calculateHasIncompatibleAccounts() {
        new CalculateHasIncompatibleAccountsTask().executeOnExecutor(
                AsyncTask.THREAD_POOL_EXECUTOR, null);
    }
    @Nullable
    private volatile Map<Integer, Boolean> mHasIncompatibleAccounts;
    class CalculateHasIncompatibleAccountsTask extends AsyncTask<
            Void, Void, Map<Integer, Boolean>> {
        private static final String[] FEATURE_ALLOW =
                {DevicePolicyManager.ACCOUNT_FEATURE_DEVICE_OR_PROFILE_OWNER_ALLOWED};
        final String[] feature_disallow =
        private static final String[] FEATURE_DISALLOW =
                {DevicePolicyManager.ACCOUNT_FEATURE_DEVICE_OR_PROFILE_OWNER_DISALLOWED};
        @Override
        protected Map<Integer, Boolean> doInBackground(Void... args) {
            List<UserInfo> users = mUserManagerInternal.getUsers(/* excludeDying= */ true);
            Map<Integer, Boolean> results = new HashMap<>();
            for (UserInfo userInfo : users) {
                results.put(userInfo.id, userHasIncompatibleAccounts(userInfo.id));
            }
            return results;
        }
        private boolean userHasIncompatibleAccounts(int id) {
            AccountManager am = mContext.createContextAsUser(UserHandle.of(id), /* flags= */ 0)
                    .getSystemService(AccountManager.class);
            Account[] accounts = am.getAccounts();
            for (Account account : accounts) {
            if (hasAccountFeatures(am, account, feature_disallow)) {
                Slogf.e(LOG_TAG, "%s has %s", account, feature_disallow[0]);
                if (hasAccountFeatures(am, account, FEATURE_DISALLOW)) {
                    return true;
                }
            if (!hasAccountFeatures(am, account, feature_allow)) {
                Slogf.e(LOG_TAG, "%s doesn't have %s", account, feature_allow[0]);
                if (!hasAccountFeatures(am, account, FEATURE_ALLOW)) {
                    return true;
                }
            }
@@ -18454,16 +18508,23 @@ public class DevicePolicyManagerService extends IDevicePolicyManager.Stub {
            return false;
        }
    private boolean hasAccountFeatures(AccountManager am, Account account, String[] features) {
        @Override
        protected void onPostExecute(Map<Integer, Boolean> results) {
            mHasIncompatibleAccounts = Collections.unmodifiableMap(results);
            Slogf.i(LOG_TAG, "Finished calculating hasIncompatibleAccountsTask");
        }
        private static boolean hasAccountFeatures(AccountManager am, Account account,
                String[] features) {
            try {
            // TODO(267156507): Restore without blocking binder thread
            return false;
//            return am.hasFeatures(account, features, null, null).getResult();
                return am.hasFeatures(account, features, null, null).getResult();
            } catch (Exception e) {
                Slogf.w(LOG_TAG, "Failed to get account feature", e);
                return false;
            }
        }
    };
    private boolean isAdb(CallerIdentity caller) {
        return isShellUid(caller) || isRootUid(caller);
@@ -22295,26 +22356,6 @@ public class DevicePolicyManagerService extends IDevicePolicyManager.Stub {
        }
    }
    private boolean hasIncompatibleAccountsOnAnyUser() {
        long callingIdentity = Binder.clearCallingIdentity();
        try {
            for (UserInfo user : mUserManagerInternal.getUsers(/* excludeDying= */ true)) {
                AccountManager am = mContext.createContextAsUser(
                        UserHandle.of(user.id), /* flags= */ 0)
                        .getSystemService(AccountManager.class);
                Account[] accounts = am.getAccounts();
                if (hasIncompatibleAccounts(am, accounts)) {
                    return true;
                }
            }
            return false;
        } finally {
            Binder.restoreCallingIdentity(callingIdentity);
        }
    }
    private void setBypassDevicePolicyManagementRoleQualificationStateInternal(
            String currentRoleHolder, boolean allowBypass) {
        boolean stateChanged = false;