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

Commit 5c7257f1 authored by Miriam Polzer's avatar Miriam Polzer
Browse files

Add tests for gobal and local policies in DPE

Test the following behaviours:
- Global policies are set correctly
- Setting a local policy twice calls the resolution
- Local policies override global policies
- Global policies do not override local policies
- Setting global or local policies with the wrong funciton fails

Test: atest FrameworksServicesTests_devicepolicy:com.android.server.devicepolicy.DevicePolicyEngineTest
Bug: 416180519
Flag: TEST_ONLY
parent 35d95843
Loading
Loading
Loading
Loading
+172 −11
Original line number Diff line number Diff line
@@ -18,9 +18,12 @@ package com.android.server.devicepolicy

import android.app.admin.DevicePolicyManager
import android.app.admin.IntegerPolicyValue
import android.app.admin.PackageSetPolicyValue
import android.app.admin.PolicyUpdateResult
import android.app.admin.PolicyValue
import android.app.usage.UsageStatsManagerInternal
import android.content.ComponentName
import android.content.pm.PackageManagerInternal
import android.os.UserHandle
import android.os.UserManager
import androidx.test.ext.junit.runners.AndroidJUnit4
@@ -29,8 +32,10 @@ import com.android.internal.util.test.BroadcastInterceptingContext
import com.android.role.RoleManagerLocal
import com.android.server.LocalManagerRegistry
import com.android.server.LocalServices
import com.android.server.pm.UserManagerInternal
import com.google.common.truth.Truth.assertThat
import org.junit.After
import org.junit.Assert.assertThrows
import org.junit.Before
import org.junit.BeforeClass
import org.junit.ClassRule
@@ -47,6 +52,9 @@ class DevicePolicyEngineTest {

    private val deviceAdminServiceController = mock<DeviceAdminServiceController>()
    private val userManager = mock<UserManager>()
    private val userManagerInternal = mock<UserManagerInternal>()
    private val packageManager = mock<PackageManagerInternal>()
    private val usageStatsManagerInternal = mock<UsageStatsManagerInternal>()
    private val policyPathProvider = mock<PolicyPathProvider>()

    private val lock = Any()
@@ -55,8 +63,19 @@ class DevicePolicyEngineTest {
    @Before
    fun setUp() {
        resetPolicyFolder()

        LocalServices.removeServiceForTest(UserManager::class.java)
        LocalServices.addService(UserManager::class.java, userManager)

        LocalServices.removeServiceForTest(UserManagerInternal::class.java)
        LocalServices.addService(UserManagerInternal::class.java, userManagerInternal)

        LocalServices.removeServiceForTest(PackageManagerInternal::class.java)
        LocalServices.addService(PackageManagerInternal::class.java, packageManager)

        LocalServices.removeServiceForTest(UsageStatsManagerInternal::class.java)
        LocalServices.addService(UsageStatsManagerInternal::class.java, usageStatsManagerInternal)

        resetDevicePolicyEngine()
    }

@@ -75,29 +94,39 @@ class DevicePolicyEngineTest {
        devicePolicyEngine.load()
    }

    // Helper functions for test setup. Only DO needed for now, but we will want to exptend this to
    // other admin types in the future.
    // Helper functions for test setup.

    private fun <T> ensurePolicyIsSetLocally(
        policyDefinition: PolicyDefinition<T>,
        value: PolicyValue<T>,
        userId: Int = SYSTEM_USER_ID,
        enforcingAdmin: EnforcingAdmin = DEVICE_OWNER_ADMIN,
    ) {
        val result =
            devicePolicyEngine.setLocalPolicy(
                policyDefinition,
                DEVICE_OWNER_ADMIN,
                enforcingAdmin,
                value,
                DEVICE_OWNER_USER_ID,
                SYSTEM_USER_ID,
            )
        assertThat(result.get()).isEqualTo(POLICY_SET)
    }

    private fun <T> ensurePolicyIsSetGlobally(
        policyDefinition: PolicyDefinition<T>,
        value: PolicyValue<T>,
        enforcingAdmin: EnforcingAdmin = DEVICE_OWNER_ADMIN,
    ) {
        val result = devicePolicyEngine.setGlobalPolicy(policyDefinition, enforcingAdmin, value)
        assertThat(result.get()).isEqualTo(POLICY_SET)
    }

    private fun <T> ensurePolicyIsRemovedLocally(policyDefinition: PolicyDefinition<T>) {
        val result =
            devicePolicyEngine.removeLocalPolicy(
                policyDefinition,
                DEVICE_OWNER_ADMIN,
                DEVICE_OWNER_USER_ID,
                SYSTEM_USER_ID,
            )
        assertThat(result.get()).isEqualTo(POLICY_CLEARED)
    }
@@ -107,29 +136,145 @@ class DevicePolicyEngineTest {
        ensurePolicyIsSetLocally(PASSWORD_COMPLEXITY_POLICY, HIGH_PASSWORD_COMPLEXITY)

        val resolvedPolicy =
            devicePolicyEngine.getResolvedPolicy(PASSWORD_COMPLEXITY_POLICY, DEVICE_OWNER_USER_ID)
            devicePolicyEngine.getResolvedPolicy(PASSWORD_COMPLEXITY_POLICY, SYSTEM_USER_ID)

        assertThat(resolvedPolicy).isEqualTo(HIGH_PASSWORD_COMPLEXITY.value)
    }

    @Test
    fun setAndGetGlobalPolicy_returnsCorrectPolicy() {
        ensurePolicyIsSetGlobally(AUTO_TIME_ZONE_POLICY, AUTO_TIME_ZONE_ENABLED)

        val resolvedPolicy =
            devicePolicyEngine.getResolvedPolicy(AUTO_TIME_ZONE_POLICY, SYSTEM_USER_ID)

        assertThat(resolvedPolicy).isEqualTo(AUTO_TIME_ZONE_ENABLED.value)
    }

    @Test
    fun removeLocalPolicy_removesPolicyAndResolvesToNull() {
        ensurePolicyIsSetLocally(PASSWORD_COMPLEXITY_POLICY, HIGH_PASSWORD_COMPLEXITY)
        ensurePolicyIsRemovedLocally(PASSWORD_COMPLEXITY_POLICY)

        val resolvedPolicy =
            devicePolicyEngine.getResolvedPolicy(PASSWORD_COMPLEXITY_POLICY, DEVICE_OWNER_USER_ID)
            devicePolicyEngine.getResolvedPolicy(PASSWORD_COMPLEXITY_POLICY, SYSTEM_USER_ID)

        assertThat(resolvedPolicy).isNull()
    }

    @Test
    fun setLocalPackageSetPolicy_multipleEnforcingAdmins_resolvesToSetUnion() {
        ensurePolicyIsSetLocally(
            USER_CONTROLLED_DISABLED_PACKAGES_POLICY,
            PACKAGE_SET_POLICY_VALUE_1,
            SYSTEM_USER_ID,
            DEVICE_OWNER_ADMIN,
        )
        ensurePolicyIsSetLocally(
            USER_CONTROLLED_DISABLED_PACKAGES_POLICY,
            PACKAGE_SET_POLICY_VALUE_2,
            SYSTEM_USER_ID,
            SYSTEM_ADMIN,
        )

        val resolvedPolicy =
            devicePolicyEngine.getResolvedPolicy(
                USER_CONTROLLED_DISABLED_PACKAGES_POLICY,
                SYSTEM_USER_ID,
            )

        assertThat(resolvedPolicy)
            .isEqualTo(PACKAGE_SET_POLICY_VALUE_1.value.union(PACKAGE_SET_POLICY_VALUE_2.value))
    }

    @Test
    fun setGlobalAndThenLocalPolicy_localOverridesGlobal() {
        ensurePolicyIsSetGlobally(
            USER_CONTROLLED_DISABLED_PACKAGES_POLICY,
            PACKAGE_SET_POLICY_VALUE_1,
        )
        ensurePolicyIsSetLocally(
            USER_CONTROLLED_DISABLED_PACKAGES_POLICY,
            PACKAGE_SET_POLICY_VALUE_2,
        )

        val resolvedPolicy =
            devicePolicyEngine.getResolvedPolicy(
                USER_CONTROLLED_DISABLED_PACKAGES_POLICY,
                SYSTEM_USER_ID,
            )

        assertThat(resolvedPolicy).isEqualTo(PACKAGE_SET_POLICY_VALUE_2.value)
    }

    @Test
    fun setPackageSetPolicyLocallyThenGlobally_noSubset_returnsError() {
        ensurePolicyIsSetLocally(
            USER_CONTROLLED_DISABLED_PACKAGES_POLICY,
            PACKAGE_SET_POLICY_VALUE_1,
        )

        val result =
            devicePolicyEngine.setGlobalPolicy(
                USER_CONTROLLED_DISABLED_PACKAGES_POLICY,
                DEVICE_OWNER_ADMIN,
                PACKAGE_SET_POLICY_VALUE_2,
            )
        // The local policy takes precedence over the global policy, and the global policy is not a
        // subset of the local one, so we get an error.
        assertThat(result.get()).isEqualTo(ERROR_CONFLICTING_ADMIN_POLICY)
    }

    @Test
    fun setPackageSetPolicyLocallyThenGlobally_subset_returnsSuccess() {
        ensurePolicyIsSetLocally(
            USER_CONTROLLED_DISABLED_PACKAGES_POLICY,
            PACKAGE_SET_POLICY_VALUE_1,
        )

        val result =
            devicePolicyEngine.setGlobalPolicy(
                USER_CONTROLLED_DISABLED_PACKAGES_POLICY,
                DEVICE_OWNER_ADMIN,
                PACKAGE_SET_POLICY_VALUE_1_SUBSET,
            )
        // The local policy takes precedence over the global policy, but the global policy is a
        // subset of the local one.
        assertThat(result.get()).isEqualTo(POLICY_SET)
    }

    @Test
    fun setGlobalPolicy_withLocalOnlyPolicy_throwsIllegalArgumentException() {
        assertThrows(IllegalArgumentException::class.java) {
            val result =
                devicePolicyEngine.setGlobalPolicy(
                    PASSWORD_COMPLEXITY_POLICY,
                    DEVICE_OWNER_ADMIN,
                    HIGH_PASSWORD_COMPLEXITY,
                )
        }
    }

    @Test
    fun setLocalPolicy_withGlobalOnlyPolicy_throwsIllegalArgumentException() {
        assertThrows(IllegalArgumentException::class.java) {
            val result =
                devicePolicyEngine.setLocalPolicy(
                    AUTO_TIME_ZONE_POLICY,
                    DEVICE_OWNER_ADMIN,
                    AUTO_TIME_ZONE_ENABLED,
                    SYSTEM_USER_ID,
                )
        }
    }

    @Test
    fun setLocalPolicy_restartDevicePolicyEngine_policyIsStillSet() {
        ensurePolicyIsSetLocally(PASSWORD_COMPLEXITY_POLICY, HIGH_PASSWORD_COMPLEXITY)
        resetDevicePolicyEngine()

        val resolvedPolicy =
            devicePolicyEngine.getResolvedPolicy(PASSWORD_COMPLEXITY_POLICY, DEVICE_OWNER_USER_ID)
            devicePolicyEngine.getResolvedPolicy(PASSWORD_COMPLEXITY_POLICY, SYSTEM_USER_ID)

        assertThat(resolvedPolicy).isEqualTo(HIGH_PASSWORD_COMPLEXITY.value)
    }
@@ -141,24 +286,40 @@ class DevicePolicyEngineTest {
        resetDevicePolicyEngine()

        val resolvedPolicy =
            devicePolicyEngine.getResolvedPolicy(PASSWORD_COMPLEXITY_POLICY, DEVICE_OWNER_USER_ID)
            devicePolicyEngine.getResolvedPolicy(PASSWORD_COMPLEXITY_POLICY, SYSTEM_USER_ID)

        assertThat(resolvedPolicy).isNull()
    }

    companion object {
        private const val POLICY_SET = PolicyUpdateResult.RESULT_POLICY_SET
        private const val FAILURE_UNKNOWN = PolicyUpdateResult.RESULT_FAILURE_UNKNOWN
        private const val POLICY_CLEARED = PolicyUpdateResult.RESULT_POLICY_CLEARED
        private const val ERROR_CONFLICTING_ADMIN_POLICY =
            PolicyUpdateResult.RESULT_FAILURE_CONFLICTING_ADMIN_POLICY

        private val PASSWORD_COMPLEXITY_POLICY = PolicyDefinition.PASSWORD_COMPLEXITY
        private val AUTO_TIME_ZONE_POLICY = PolicyDefinition.AUTO_TIME_ZONE
        private val USER_CONTROLLED_DISABLED_PACKAGES_POLICY =
            PolicyDefinition.USER_CONTROLLED_DISABLED_PACKAGES

        private val HIGH_PASSWORD_COMPLEXITY =
            IntegerPolicyValue(DevicePolicyManager.PASSWORD_COMPLEXITY_HIGH)
        private val AUTO_TIME_ZONE_ENABLED =
            IntegerPolicyValue(DevicePolicyManager.AUTO_TIME_ZONE_ENABLED)
        private val PACKAGE_SET_POLICY_VALUE_1 =
            PackageSetPolicyValue(setOf("com.example.package1", "com.example.package2"))
        private val PACKAGE_SET_POLICY_VALUE_1_SUBSET =
            PackageSetPolicyValue(setOf("com.example.package1"))
        private val PACKAGE_SET_POLICY_VALUE_2 =
            PackageSetPolicyValue(setOf("com.example.package2", "com.example.package3"))

        private const val DEVICE_OWNER_USER_ID = UserHandle.USER_SYSTEM
        private const val SYSTEM_USER_ID = UserHandle.USER_SYSTEM
        private val SYSTEM_ADMIN = EnforcingAdmin.createSystemEnforcingAdmin("system_entity")
        private val DEVICE_OWNER_ADMIN =
            EnforcingAdmin.createEnterpriseEnforcingAdmin(
                ComponentName("packagename", "classname"),
                DEVICE_OWNER_USER_ID,
                SYSTEM_USER_ID,
            )

        @ClassRule @JvmField val tmpDir = TemporaryFolder()