Profile owners on a user can communicate with device owners

Allow device owners and profile owners on a user
to communicate with each other, rather than restricting
it to device owners and managed profile owners as it is
at the moment

Bug: 34429083

Test:  runtest -c com.android.server.devicepolicy.DevicePolicyManagerTest    frameworks-services
Test: cts-tradefed run cts -a armeabi-v7a --module DevicePolicyManager --test com.android.cts.devicepolicy.DeviceOwnerPlusManagedProfileTest
Change-Id: I81561a9838c3ccb623354a1b718da2fc6a5af1fe
diff --git a/core/java/android/app/admin/DevicePolicyManager.java b/core/java/android/app/admin/DevicePolicyManager.java
index 0ff8550..5b78ce8 100644
--- a/core/java/android/app/admin/DevicePolicyManager.java
+++ b/core/java/android/app/admin/DevicePolicyManager.java
@@ -7587,8 +7587,8 @@
     }
 
     /**
-     * Called by a device owner to bind to a service from a profile owner of a managed profile or
-     * vice versa. See {@link #getBindDeviceAdminTargetUsers} for a definition of which
+     * Called by a device owner to bind to a service from a profile owner or vice versa.
+     * See {@link #getBindDeviceAdminTargetUsers} for a definition of which
      * device/profile owners are allowed to bind to services of another profile/device owner.
      * <p>
      * The service must be unexported. Note that the {@link Context} used to obtain this
@@ -7634,14 +7634,10 @@
      * Returns the list of target users that the calling device or profile owner can use when
      * calling {@link #bindDeviceAdminServiceAsUser}.
      * <p>
-     * A device owner can bind to a service from a profile owner of a managed profile and
-     * vice versa, provided that:
+     * A device owner can bind to a service from a profile owner and vice versa, provided that:
      * <ul>
      * <li>Both belong to the same package name.
-     * <li>The managed profile is a profile of the user where the device owner is set.
-     *     See {@link UserManager#getUserProfiles()}
-     * <li>Both users are affiliated.
-     *     See {@link #setAffiliationIds}.
+     * <li>Both users are affiliated. See {@link #setAffiliationIds}.
      * </ul>
      */
     public @NonNull List<UserHandle> getBindDeviceAdminTargetUsers(@NonNull ComponentName admin) {
diff --git a/services/devicepolicy/java/com/android/server/devicepolicy/DevicePolicyManagerService.java b/services/devicepolicy/java/com/android/server/devicepolicy/DevicePolicyManagerService.java
index af78154..d30a823 100644
--- a/services/devicepolicy/java/com/android/server/devicepolicy/DevicePolicyManagerService.java
+++ b/services/devicepolicy/java/com/android/server/devicepolicy/DevicePolicyManagerService.java
@@ -9906,7 +9906,7 @@
     private boolean areAllUsersAffiliatedWithDeviceLocked() {
         final long ident = mInjector.binderClearCallingIdentity();
         try {
-            final List<UserInfo> userInfos = mUserManager.getUsers();
+            final List<UserInfo> userInfos = mUserManager.getUsers(/*excludeDying=*/ true);
             for (int i = 0; i < userInfos.size(); i++) {
                 int userId = userInfos.get(i).id;
                 if (!isUserAffiliatedWithDeviceLocked(userId)) {
@@ -10314,47 +10314,51 @@
             return Collections.emptyList();
         }
         Preconditions.checkNotNull(admin);
-        ArrayList<UserHandle> targetUsers = new ArrayList<>();
 
         synchronized (this) {
-            ActiveAdmin callingOwner = getActiveAdminForCallerLocked(
-                    admin, DeviceAdminInfo.USES_POLICY_PROFILE_OWNER);
+            getActiveAdminForCallerLocked(admin, DeviceAdminInfo.USES_POLICY_PROFILE_OWNER);
 
             final int callingUserId = mInjector.userHandleGetCallingUserId();
-            final boolean isCallerDeviceOwner = isDeviceOwner(callingOwner);
-            final boolean isCallerManagedProfile = isManagedProfile(callingUserId);
-            if ((!isCallerDeviceOwner && !isCallerManagedProfile)
-                    || !isUserAffiliatedWithDeviceLocked(callingUserId)) {
-                return targetUsers;
-            }
-
             final long callingIdentity = mInjector.binderClearCallingIdentity();
             try {
-                String callingOwnerPackage = callingOwner.info.getComponent().getPackageName();
-                for (int userId : mUserManager.getProfileIdsWithDisabled(callingUserId)) {
-                    if (userId == callingUserId) {
-                        continue;
+                ArrayList<UserHandle> targetUsers = new ArrayList<>();
+                if (!isDeviceOwner(admin, callingUserId)) {
+                    // Profile owners can only bind to the device owner.
+                    if (canUserBindToDeviceOwnerLocked(callingUserId)) {
+                        targetUsers.add(UserHandle.of(mOwners.getDeviceOwnerUserId()));
                     }
-
-                    // We only allow the device owner and a managed profile owner to bind to each
-                    // other.
-                    if ((isCallerManagedProfile && userId == mOwners.getDeviceOwnerUserId())
-                            || (isCallerDeviceOwner && isManagedProfile(userId))) {
-                        String targetOwnerPackage = getOwnerPackageNameForUserLocked(userId);
-
-                        // Both must be the same package and be affiliated in order to bind.
-                        if (callingOwnerPackage.equals(targetOwnerPackage)
-                               && isUserAffiliatedWithDeviceLocked(userId)) {
+                } else {
+                    // Caller is the device owner: Look for profile owners that it can bind to.
+                    final List<UserInfo> userInfos = mUserManager.getUsers(/*excludeDying=*/ true);
+                    for (int i = 0; i < userInfos.size(); i++) {
+                        final int userId = userInfos.get(i).id;
+                        if (userId != callingUserId && canUserBindToDeviceOwnerLocked(userId)) {
                             targetUsers.add(UserHandle.of(userId));
                         }
                     }
                 }
+
+                return targetUsers;
             } finally {
                 mInjector.binderRestoreCallingIdentity(callingIdentity);
             }
         }
+    }
 
-        return targetUsers;
+    private boolean canUserBindToDeviceOwnerLocked(int userId) {
+        // There has to be a device owner, under another user id.
+        if (!mOwners.hasDeviceOwner() || userId == mOwners.getDeviceOwnerUserId()) {
+            return false;
+        }
+
+        // The user must have a profile owner that belongs to the same package as the device owner.
+        if (!mOwners.hasProfileOwner(userId) || !TextUtils.equals(
+                mOwners.getDeviceOwnerPackageName(), mOwners.getProfileOwnerPackage(userId))) {
+            return false;
+        }
+
+        // The user must be affiliated.
+        return isUserAffiliatedWithDeviceLocked(userId);
     }
 
     /**