DevicePolicyManagerTest.java revision b88f42b6b1414ae8107be13c0d2f3957549ecaaf
1/*
2 * Copyright (C) 2015 The Android Open Source Project
3 *
4 * Licensed under the Apache License, Version 2.0 (the "License");
5 * you may not use this file except in compliance with the License.
6 * You may obtain a copy of the License at
7 *
8 *      http://www.apache.org/licenses/LICENSE-2.0
9 *
10 * Unless required by applicable law or agreed to in writing, software
11 * distributed under the License is distributed on an "AS IS" BASIS,
12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 * See the License for the specific language governing permissions and
14 * limitations under the License.
15 */
16package com.android.server.devicepolicy;
17
18import static android.os.UserManagerInternal.CAMERA_DISABLED_GLOBALLY;
19import static android.os.UserManagerInternal.CAMERA_DISABLED_LOCALLY;
20import static android.os.UserManagerInternal.CAMERA_NOT_DISABLED;
21
22import android.Manifest.permission;
23import android.app.Activity;
24import android.app.admin.DeviceAdminReceiver;
25import android.app.admin.DevicePolicyManager;
26import android.app.admin.DevicePolicyManagerInternal;
27import android.content.BroadcastReceiver;
28import android.content.ComponentName;
29import android.content.Context;
30import android.content.Intent;
31import android.content.ServiceConnection;
32import android.content.pm.ApplicationInfo;
33import android.content.pm.PackageInfo;
34import android.content.pm.PackageManager;
35import android.content.res.Resources;
36import android.graphics.Color;
37import android.net.IIpConnectivityMetrics;
38import android.content.pm.UserInfo;
39import android.net.wifi.WifiInfo;
40import android.os.Build.VERSION_CODES;
41import android.os.Bundle;
42import android.os.IBinder;
43import android.os.Process;
44import android.os.UserHandle;
45import android.os.UserManager;
46import android.os.UserManagerInternal;
47import android.provider.Settings;
48import android.telephony.TelephonyManager;
49import android.test.MoreAsserts;
50import android.test.suitebuilder.annotation.SmallTest;
51import android.util.ArraySet;
52import android.util.Pair;
53
54import com.android.internal.R;
55import com.android.server.LocalServices;
56import com.android.server.SystemService;
57import com.android.server.pm.UserRestrictionsUtils;
58
59import org.mockito.invocation.InvocationOnMock;
60import org.mockito.stubbing.Answer;
61
62import java.util.ArrayList;
63import java.util.Arrays;
64import java.util.Collections;
65import java.util.HashMap;
66import java.util.List;
67import java.util.Map;
68import java.util.Set;
69import java.util.concurrent.TimeUnit;
70
71import static org.mockito.Matchers.any;
72import static org.mockito.Matchers.anyInt;
73import static org.mockito.Matchers.anyLong;
74import static org.mockito.Matchers.anyObject;
75import static org.mockito.Matchers.anyString;
76import static org.mockito.Matchers.eq;
77import static org.mockito.Matchers.isNull;
78import static org.mockito.Mockito.atLeast;
79import static org.mockito.Mockito.doAnswer;
80import static org.mockito.Mockito.doReturn;
81import static org.mockito.Mockito.never;
82import static org.mockito.Mockito.reset;
83import static org.mockito.Mockito.times;
84import static org.mockito.Mockito.verify;
85import static org.mockito.Mockito.verifyZeroInteractions;
86import static org.mockito.Mockito.when;
87
88/**
89 * Tests for DevicePolicyManager( and DevicePolicyManagerService).
90 * You can run them via:
91 m FrameworksServicesTests &&
92 adb install \
93   -r ${ANDROID_PRODUCT_OUT}/data/app/FrameworksServicesTests/FrameworksServicesTests.apk &&
94 adb shell am instrument -e class com.android.server.devicepolicy.DevicePolicyManagerTest \
95   -w com.android.frameworks.servicestests/android.support.test.runner.AndroidJUnitRunner
96
97 (mmma frameworks/base/services/tests/servicestests/ for non-ninja build)
98 *
99 * , or:
100 * runtest -c com.android.server.devicepolicy.DevicePolicyManagerTest frameworks-services
101 */
102@SmallTest
103public class DevicePolicyManagerTest extends DpmTestBase {
104    private static final List<String> OWNER_SETUP_PERMISSIONS = Arrays.asList(
105            permission.MANAGE_DEVICE_ADMINS, permission.MANAGE_PROFILE_AND_DEVICE_OWNERS,
106            permission.MANAGE_USERS, permission.INTERACT_ACROSS_USERS_FULL);
107
108    private DpmMockContext mContext;
109    public DevicePolicyManager dpm;
110    public DevicePolicyManagerServiceTestable dpms;
111
112    @Override
113    protected void setUp() throws Exception {
114        super.setUp();
115
116        mContext = getContext();
117
118        when(mContext.packageManager.hasSystemFeature(eq(PackageManager.FEATURE_DEVICE_ADMIN)))
119                .thenReturn(true);
120
121        // By default, pretend all users are running and unlocked.
122        when(mContext.userManager.isUserUnlocked(anyInt())).thenReturn(true);
123
124        initializeDpms();
125
126        setUpPackageManagerForAdmin(admin1, DpmMockContext.CALLER_UID);
127        setUpPackageManagerForAdmin(admin2, DpmMockContext.CALLER_UID);
128        setUpPackageManagerForAdmin(admin3, DpmMockContext.CALLER_UID);
129        setUpPackageManagerForAdmin(adminNoPerm, DpmMockContext.CALLER_UID);
130
131        setUpUserManager();
132    }
133
134    private void initializeDpms() {
135        // Need clearCallingIdentity() to pass permission checks.
136        final long ident = mContext.binder.clearCallingIdentity();
137        try {
138            LocalServices.removeServiceForTest(DevicePolicyManagerInternal.class);
139
140            dpms = new DevicePolicyManagerServiceTestable(mContext, dataDir);
141
142            dpms.systemReady(SystemService.PHASE_LOCK_SETTINGS_READY);
143            dpms.systemReady(SystemService.PHASE_BOOT_COMPLETED);
144
145            dpm = new DevicePolicyManagerTestable(mContext, dpms);
146        } finally {
147            mContext.binder.restoreCallingIdentity(ident);
148        }
149    }
150
151    private void setUpUserManager() {
152        // Emulate UserManager.set/getApplicationRestriction().
153        final Map<Pair<String, UserHandle>, Bundle> appRestrictions = new HashMap<>();
154
155        // UM.setApplicationRestrictions() will save to appRestrictions.
156        doAnswer(new Answer<Void>() {
157            @Override
158            public Void answer(InvocationOnMock invocation) throws Throwable {
159                String pkg = (String) invocation.getArguments()[0];
160                Bundle bundle = (Bundle) invocation.getArguments()[1];
161                UserHandle user = (UserHandle) invocation.getArguments()[2];
162
163                appRestrictions.put(Pair.create(pkg, user), bundle);
164
165                return null;
166            }
167        }).when(mContext.userManager).setApplicationRestrictions(
168                anyString(), any(Bundle.class), any(UserHandle.class));
169
170        // UM.getApplicationRestrictions() will read from appRestrictions.
171        doAnswer(new Answer<Bundle>() {
172            @Override
173            public Bundle answer(InvocationOnMock invocation) throws Throwable {
174                String pkg = (String) invocation.getArguments()[0];
175                UserHandle user = (UserHandle) invocation.getArguments()[1];
176
177                return appRestrictions.get(Pair.create(pkg, user));
178            }
179        }).when(mContext.userManager).getApplicationRestrictions(
180                anyString(), any(UserHandle.class));
181
182        // Add the first secondary user.
183        mContext.addUser(DpmMockContext.CALLER_USER_HANDLE, 0);
184    }
185
186    private void setAsProfileOwner(ComponentName admin) {
187        mContext.callerPermissions.add(permission.MANAGE_DEVICE_ADMINS);
188        mContext.callerPermissions.add(permission.MANAGE_PROFILE_AND_DEVICE_OWNERS);
189
190        // PO needs to be an DA.
191        dpm.setActiveAdmin(admin, /* replace =*/ false);
192
193        // Fire!
194        assertTrue(dpm.setProfileOwner(admin, "owner-name", DpmMockContext.CALLER_USER_HANDLE));
195
196        // Check
197        assertEquals(admin, dpm.getProfileOwnerAsUser(DpmMockContext.CALLER_USER_HANDLE));
198    }
199
200    public void testHasNoFeature() throws Exception {
201        when(mContext.packageManager.hasSystemFeature(eq(PackageManager.FEATURE_DEVICE_ADMIN)))
202                .thenReturn(false);
203
204        LocalServices.removeServiceForTest(DevicePolicyManagerInternal.class);
205        new DevicePolicyManagerServiceTestable(mContext, dataDir);
206
207        // If the device has no DPMS feature, it shouldn't register the local service.
208        assertNull(LocalServices.getService(DevicePolicyManagerInternal.class));
209    }
210
211    /**
212     * Caller doesn't have proper permissions.
213     */
214    public void testSetActiveAdmin_SecurityException() {
215        // 1. Failure cases.
216
217        // Caller doesn't have MANAGE_DEVICE_ADMINS.
218        try {
219            dpm.setActiveAdmin(admin1, false);
220            fail("Didn't throw SecurityException");
221        } catch (SecurityException expected) {
222        }
223
224        // Caller has MANAGE_DEVICE_ADMINS, but for different user.
225        mContext.callerPermissions.add(android.Manifest.permission.MANAGE_DEVICE_ADMINS);
226        try {
227            dpm.setActiveAdmin(admin1, false, DpmMockContext.CALLER_USER_HANDLE + 1);
228            fail("Didn't throw SecurityException");
229        } catch (SecurityException expected) {
230        }
231    }
232
233    /**
234     * Test for:
235     * {@link DevicePolicyManager#setActiveAdmin}
236     * with replace=false and replace=true
237     * {@link DevicePolicyManager#isAdminActive}
238     * {@link DevicePolicyManager#isAdminActiveAsUser}
239     * {@link DevicePolicyManager#getActiveAdmins}
240     * {@link DevicePolicyManager#getActiveAdminsAsUser}
241     */
242    public void testSetActiveAdmin() throws Exception {
243        // 1. Make sure the caller has proper permissions.
244        mContext.callerPermissions.add(android.Manifest.permission.MANAGE_DEVICE_ADMINS);
245
246        // 2. Call the API.
247        dpm.setActiveAdmin(admin1, /* replace =*/ false);
248
249        // 3. Verify internal calls.
250
251        // Check if the boradcast is sent.
252        verify(mContext.spiedContext).sendBroadcastAsUser(
253                MockUtils.checkIntentAction(
254                        DevicePolicyManager.ACTION_DEVICE_POLICY_MANAGER_STATE_CHANGED),
255                MockUtils.checkUserHandle(DpmMockContext.CALLER_USER_HANDLE));
256        verify(mContext.spiedContext).sendBroadcastAsUser(
257                MockUtils.checkIntentAction(
258                        DeviceAdminReceiver.ACTION_DEVICE_ADMIN_ENABLED),
259                MockUtils.checkUserHandle(DpmMockContext.CALLER_USER_HANDLE));
260
261        verify(mContext.ipackageManager, times(1)).setApplicationEnabledSetting(
262                eq(admin1.getPackageName()),
263                eq(PackageManager.COMPONENT_ENABLED_STATE_DEFAULT),
264                eq(PackageManager.DONT_KILL_APP),
265                eq(DpmMockContext.CALLER_USER_HANDLE),
266                anyString());
267
268        // TODO Verify other calls too.
269
270        // Make sure it's active admin1.
271        assertTrue(dpm.isAdminActive(admin1));
272        assertFalse(dpm.isAdminActive(admin2));
273        assertFalse(dpm.isAdminActive(admin3));
274
275        // But not admin1 for a different user.
276
277        // For this to work, caller needs android.permission.INTERACT_ACROSS_USERS_FULL.
278        // (Because we're checking a different user's status from CALLER_USER_HANDLE.)
279        mContext.callerPermissions.add("android.permission.INTERACT_ACROSS_USERS_FULL");
280
281        assertFalse(dpm.isAdminActiveAsUser(admin1, DpmMockContext.CALLER_USER_HANDLE + 1));
282        assertFalse(dpm.isAdminActiveAsUser(admin2, DpmMockContext.CALLER_USER_HANDLE + 1));
283
284        mContext.callerPermissions.remove("android.permission.INTERACT_ACROSS_USERS_FULL");
285
286        // Next, add one more admin.
287        // Before doing so, update the application info, now it's enabled.
288        setUpPackageManagerForAdmin(admin2, DpmMockContext.CALLER_UID,
289                PackageManager.COMPONENT_ENABLED_STATE_ENABLED);
290
291        dpm.setActiveAdmin(admin2, /* replace =*/ false);
292
293        // Now we have two admins.
294        assertTrue(dpm.isAdminActive(admin1));
295        assertTrue(dpm.isAdminActive(admin2));
296        assertFalse(dpm.isAdminActive(admin3));
297
298        // Admin2 was already enabled, so setApplicationEnabledSetting() shouldn't have called
299        // again.  (times(1) because it was previously called for admin1)
300        verify(mContext.ipackageManager, times(1)).setApplicationEnabledSetting(
301                eq(admin1.getPackageName()),
302                eq(PackageManager.COMPONENT_ENABLED_STATE_DEFAULT),
303                eq(PackageManager.DONT_KILL_APP),
304                eq(DpmMockContext.CALLER_USER_HANDLE),
305                anyString());
306
307        // 4. Add the same admin1 again without replace, which should throw.
308        try {
309            dpm.setActiveAdmin(admin1, /* replace =*/ false);
310            fail("Didn't throw");
311        } catch (IllegalArgumentException expected) {
312        }
313
314        // 5. Add the same admin1 again with replace, which should succeed.
315        dpm.setActiveAdmin(admin1, /* replace =*/ true);
316
317        // TODO make sure it's replaced.
318
319        // 6. Test getActiveAdmins()
320        List<ComponentName> admins = dpm.getActiveAdmins();
321        assertEquals(2, admins.size());
322        assertEquals(admin1, admins.get(0));
323        assertEquals(admin2, admins.get(1));
324
325        // Another user has no admins.
326        mContext.callerPermissions.add("android.permission.INTERACT_ACROSS_USERS_FULL");
327
328        assertEquals(0, DpmTestUtils.getListSizeAllowingNull(
329                dpm.getActiveAdminsAsUser(DpmMockContext.CALLER_USER_HANDLE + 1)));
330
331        mContext.callerPermissions.remove("android.permission.INTERACT_ACROSS_USERS_FULL");
332    }
333
334    public void testSetActiveAdmin_multiUsers() throws Exception {
335
336        final int ANOTHER_USER_ID = 100;
337        final int ANOTHER_ADMIN_UID = UserHandle.getUid(ANOTHER_USER_ID, 20456);
338
339        mMockContext.addUser(ANOTHER_USER_ID, 0); // Add one more user.
340
341        // Set up pacakge manager for the other user.
342        setUpPackageManagerForAdmin(admin2, ANOTHER_ADMIN_UID);
343
344        mContext.callerPermissions.add(android.Manifest.permission.MANAGE_DEVICE_ADMINS);
345
346        dpm.setActiveAdmin(admin1, /* replace =*/ false);
347
348        mMockContext.binder.callingUid = ANOTHER_ADMIN_UID;
349        dpm.setActiveAdmin(admin2, /* replace =*/ false);
350
351
352        mMockContext.binder.callingUid = DpmMockContext.CALLER_UID;
353        assertTrue(dpm.isAdminActive(admin1));
354        assertFalse(dpm.isAdminActive(admin2));
355
356        mMockContext.binder.callingUid = ANOTHER_ADMIN_UID;
357        assertFalse(dpm.isAdminActive(admin1));
358        assertTrue(dpm.isAdminActive(admin2));
359    }
360
361    /**
362     * Test for:
363     * {@link DevicePolicyManager#setActiveAdmin}
364     * with replace=false
365     */
366    public void testSetActiveAdmin_twiceWithoutReplace() throws Exception {
367        // 1. Make sure the caller has proper permissions.
368        mContext.callerPermissions.add(android.Manifest.permission.MANAGE_DEVICE_ADMINS);
369
370        dpm.setActiveAdmin(admin1, /* replace =*/ false);
371        assertTrue(dpm.isAdminActive(admin1));
372
373        // Add the same admin1 again without replace, which should throw.
374        try {
375            dpm.setActiveAdmin(admin1, /* replace =*/ false);
376            fail("Didn't throw");
377        } catch (IllegalArgumentException expected) {
378        }
379    }
380
381    /**
382     * Test for:
383     * {@link DevicePolicyManager#setActiveAdmin} when the admin isn't protected with
384     * BIND_DEVICE_ADMIN.
385     */
386    public void testSetActiveAdmin_permissionCheck() throws Exception {
387        // 1. Make sure the caller has proper permissions.
388        mContext.callerPermissions.add(android.Manifest.permission.MANAGE_DEVICE_ADMINS);
389
390        try {
391            dpm.setActiveAdmin(adminNoPerm, /* replace =*/ false);
392            fail();
393        } catch (IllegalArgumentException expected) {
394            assertTrue(expected.getMessage().contains(permission.BIND_DEVICE_ADMIN));
395        }
396        assertFalse(dpm.isAdminActive(adminNoPerm));
397
398        // Change the target API level to MNC.  Now it can be set as DA.
399        setUpPackageManagerForAdmin(adminNoPerm, DpmMockContext.CALLER_UID, null,
400                VERSION_CODES.M);
401        dpm.setActiveAdmin(adminNoPerm, /* replace =*/ false);
402        assertTrue(dpm.isAdminActive(adminNoPerm));
403
404        // TODO Test the "load from the file" case where DA will still be loaded even without
405        // BIND_DEVICE_ADMIN and target API is N.
406    }
407
408    /**
409     * Test for:
410     * {@link DevicePolicyManager#removeActiveAdmin}
411     */
412    public void testRemoveActiveAdmin_SecurityException() {
413        mContext.callerPermissions.add(android.Manifest.permission.MANAGE_DEVICE_ADMINS);
414
415        // Add admin.
416
417        dpm.setActiveAdmin(admin1, /* replace =*/ false);
418
419        assertTrue(dpm.isAdminActive(admin1));
420
421        assertFalse(dpm.isRemovingAdmin(admin1, DpmMockContext.CALLER_USER_HANDLE));
422
423        // Directly call the DPMS method with a different userid, which should fail.
424        try {
425            dpms.removeActiveAdmin(admin1, DpmMockContext.CALLER_USER_HANDLE + 1);
426            fail("Didn't throw SecurityException");
427        } catch (SecurityException expected) {
428        }
429
430        // Try to remove active admin with a different caller userid should fail too, without
431        // having MANAGE_DEVICE_ADMINS.
432        mContext.callerPermissions.clear();
433
434        // Change the caller, and call into DPMS directly with a different user-id.
435
436        mContext.binder.callingUid = 1234567;
437        try {
438            dpms.removeActiveAdmin(admin1, DpmMockContext.CALLER_USER_HANDLE);
439            fail("Didn't throw SecurityException");
440        } catch (SecurityException expected) {
441        }
442    }
443
444    /**
445     * {@link DevicePolicyManager#removeActiveAdmin} should fail with the user is not unlocked
446     * (because we can't send the remove broadcast).
447     */
448    public void testRemoveActiveAdmin_userNotRunningOrLocked() {
449        mContext.callerPermissions.add(android.Manifest.permission.MANAGE_DEVICE_ADMINS);
450
451        mContext.binder.callingUid = DpmMockContext.CALLER_UID;
452
453        // Add admin.
454
455        dpm.setActiveAdmin(admin1, /* replace =*/ false);
456
457        assertTrue(dpm.isAdminActive(admin1));
458
459        assertFalse(dpm.isRemovingAdmin(admin1, DpmMockContext.CALLER_USER_HANDLE));
460
461        // 1. User not unlocked.
462        when(mContext.userManager.isUserUnlocked(eq(DpmMockContext.CALLER_USER_HANDLE)))
463                .thenReturn(false);
464        try {
465            dpm.removeActiveAdmin(admin1);
466            fail("Didn't throw IllegalStateException");
467        } catch (IllegalStateException expected) {
468            MoreAsserts.assertContainsRegex(
469                    "User must be running and unlocked", expected.getMessage());
470        }
471
472        assertFalse(dpm.isRemovingAdmin(admin1, DpmMockContext.CALLER_USER_HANDLE));
473
474        // 2. User unlocked.
475        when(mContext.userManager.isUserUnlocked(eq(DpmMockContext.CALLER_USER_HANDLE)))
476                .thenReturn(true);
477
478        dpm.removeActiveAdmin(admin1);
479        assertFalse(dpm.isAdminActiveAsUser(admin1, DpmMockContext.CALLER_USER_HANDLE));
480    }
481
482    /**
483     * Test for:
484     * {@link DevicePolicyManager#removeActiveAdmin}
485     */
486    public void testRemoveActiveAdmin_fromDifferentUserWithINTERACT_ACROSS_USERS_FULL() {
487        mContext.callerPermissions.add(android.Manifest.permission.MANAGE_DEVICE_ADMINS);
488
489        // Add admin1.
490
491        dpm.setActiveAdmin(admin1, /* replace =*/ false);
492
493        assertTrue(dpm.isAdminActive(admin1));
494        assertFalse(dpm.isRemovingAdmin(admin1, DpmMockContext.CALLER_USER_HANDLE));
495
496        // Different user, but should work, because caller has proper permissions.
497        mContext.callerPermissions.add(permission.INTERACT_ACROSS_USERS_FULL);
498
499        // Change the caller, and call into DPMS directly with a different user-id.
500        mContext.binder.callingUid = 1234567;
501
502        dpms.removeActiveAdmin(admin1, DpmMockContext.CALLER_USER_HANDLE);
503        assertFalse(dpm.isAdminActiveAsUser(admin1, DpmMockContext.CALLER_USER_HANDLE));
504
505        // TODO DO Still can't be removed in this case.
506    }
507
508    /**
509     * Test for:
510     * {@link DevicePolicyManager#removeActiveAdmin}
511     */
512    public void testRemoveActiveAdmin_sameUserNoMANAGE_DEVICE_ADMINS() {
513        // Need MANAGE_DEVICE_ADMINS for setActiveAdmin.  We'll remove it later.
514        mContext.callerPermissions.add(android.Manifest.permission.MANAGE_DEVICE_ADMINS);
515
516        // Add admin1.
517
518        dpm.setActiveAdmin(admin1, /* replace =*/ false);
519
520        assertTrue(dpm.isAdminActive(admin1));
521        assertFalse(dpm.isRemovingAdmin(admin1, DpmMockContext.CALLER_USER_HANDLE));
522
523        // Broadcast from saveSettingsLocked().
524        verify(mContext.spiedContext, times(1)).sendBroadcastAsUser(
525                MockUtils.checkIntentAction(
526                        DevicePolicyManager.ACTION_DEVICE_POLICY_MANAGER_STATE_CHANGED),
527                MockUtils.checkUserHandle(DpmMockContext.CALLER_USER_HANDLE));
528
529        // Remove.  No permissions, but same user, so it'll work.
530        mContext.callerPermissions.clear();
531        dpm.removeActiveAdmin(admin1);
532
533        verify(mContext.spiedContext).sendOrderedBroadcastAsUser(
534                MockUtils.checkIntentAction(
535                        DeviceAdminReceiver.ACTION_DEVICE_ADMIN_DISABLED),
536                MockUtils.checkUserHandle(DpmMockContext.CALLER_USER_HANDLE),
537                isNull(String.class),
538                any(BroadcastReceiver.class),
539                eq(dpms.mHandler),
540                eq(Activity.RESULT_OK),
541                isNull(String.class),
542                isNull(Bundle.class));
543
544        assertFalse(dpm.isAdminActiveAsUser(admin1, DpmMockContext.CALLER_USER_HANDLE));
545
546        // Again broadcast from saveSettingsLocked().
547        verify(mContext.spiedContext, times(2)).sendBroadcastAsUser(
548                MockUtils.checkIntentAction(
549                        DevicePolicyManager.ACTION_DEVICE_POLICY_MANAGER_STATE_CHANGED),
550                MockUtils.checkUserHandle(DpmMockContext.CALLER_USER_HANDLE));
551
552        // TODO Check other internal calls.
553    }
554
555    /**
556     * Test for: @{link DevicePolicyManager#setActivePasswordState}
557     *
558     * Validates that when the password for a user changes, the notification broadcast intent
559     * {@link DeviceAdminReceiver#ACTION_PASSWORD_CHANGED} is sent to managed profile owners, in
560     * addition to ones in the original user.
561     */
562    public void testSetActivePasswordState_sendToProfiles() throws Exception {
563        mContext.callerPermissions.add(permission.BIND_DEVICE_ADMIN);
564
565        final int MANAGED_PROFILE_USER_ID = 78;
566        final int MANAGED_PROFILE_ADMIN_UID =
567                UserHandle.getUid(MANAGED_PROFILE_USER_ID, DpmMockContext.SYSTEM_UID);
568
569        // Setup device owner.
570        mContext.binder.callingUid = DpmMockContext.SYSTEM_UID;
571        mContext.packageName = admin1.getPackageName();
572        setupDeviceOwner();
573
574        // Add a managed profile belonging to the system user.
575        addManagedProfile(admin1, MANAGED_PROFILE_ADMIN_UID, admin1);
576
577        // Change the parent user's password.
578        dpm.reportPasswordChanged(UserHandle.USER_SYSTEM);
579
580        // Both the device owner and the managed profile owner should receive this broadcast.
581        final Intent intent = new Intent(DeviceAdminReceiver.ACTION_PASSWORD_CHANGED);
582        intent.setComponent(admin1);
583        intent.putExtra(Intent.EXTRA_USER, UserHandle.of(UserHandle.USER_SYSTEM));
584
585        verify(mContext.spiedContext, times(1)).sendBroadcastAsUser(
586                MockUtils.checkIntent(intent),
587                MockUtils.checkUserHandle(UserHandle.USER_SYSTEM));
588        verify(mContext.spiedContext, times(1)).sendBroadcastAsUser(
589                MockUtils.checkIntent(intent),
590                MockUtils.checkUserHandle(MANAGED_PROFILE_USER_ID));
591    }
592
593    /**
594     * Test for: @{link DevicePolicyManager#setActivePasswordState}
595     *
596     * Validates that when the password for a managed profile changes, the notification broadcast
597     * intent {@link DeviceAdminReceiver#ACTION_PASSWORD_CHANGED} is only sent to the profile, not
598     * its parent.
599     */
600    public void testSetActivePasswordState_notSentToParent() throws Exception {
601        mContext.callerPermissions.add(permission.BIND_DEVICE_ADMIN);
602
603        final int MANAGED_PROFILE_USER_ID = 78;
604        final int MANAGED_PROFILE_ADMIN_UID =
605                UserHandle.getUid(MANAGED_PROFILE_USER_ID, DpmMockContext.SYSTEM_UID);
606
607        // Setup device owner.
608        mContext.binder.callingUid = DpmMockContext.SYSTEM_UID;
609        mContext.packageName = admin1.getPackageName();
610        doReturn(true).when(mContext.lockPatternUtils)
611                .isSeparateProfileChallengeEnabled(MANAGED_PROFILE_USER_ID);
612        setupDeviceOwner();
613
614        // Add a managed profile belonging to the system user.
615        addManagedProfile(admin1, MANAGED_PROFILE_ADMIN_UID, admin1);
616
617        // Change the profile's password.
618        dpm.reportPasswordChanged(MANAGED_PROFILE_USER_ID);
619
620        // Both the device owner and the managed profile owner should receive this broadcast.
621        final Intent intent = new Intent(DeviceAdminReceiver.ACTION_PASSWORD_CHANGED);
622        intent.setComponent(admin1);
623        intent.putExtra(Intent.EXTRA_USER, UserHandle.of(MANAGED_PROFILE_USER_ID));
624
625        verify(mContext.spiedContext, never()).sendBroadcastAsUser(
626                MockUtils.checkIntent(intent),
627                MockUtils.checkUserHandle(UserHandle.USER_SYSTEM));
628        verify(mContext.spiedContext, times(1)).sendBroadcastAsUser(
629                MockUtils.checkIntent(intent),
630                MockUtils.checkUserHandle(MANAGED_PROFILE_USER_ID));
631    }
632    /**
633     * Test for: {@link DevicePolicyManager#setDeviceOwner} DO on system user installs successfully.
634     */
635    public void testSetDeviceOwner() throws Exception {
636        setDeviceOwner();
637
638        // Try to set a profile owner on the same user, which should fail.
639        setUpPackageManagerForAdmin(admin2, DpmMockContext.CALLER_SYSTEM_USER_UID);
640        dpm.setActiveAdmin(admin2, /* refreshing= */ true, UserHandle.USER_SYSTEM);
641        try {
642            dpm.setProfileOwner(admin2, "owner-name", UserHandle.USER_SYSTEM);
643            fail("IllegalStateException not thrown");
644        } catch (IllegalStateException expected) {
645            assertTrue("Message was: " + expected.getMessage(),
646                    expected.getMessage().contains("already has a device owner"));
647        }
648
649        // DO admin can't be deactivated.
650        dpm.removeActiveAdmin(admin1);
651        assertTrue(dpm.isAdminActive(admin1));
652
653        // TODO Test getDeviceOwnerName() too. To do so, we need to change
654        // DPMS.getApplicationLabel() because Context.createPackageContextAsUser() is not mockable.
655    }
656
657    private void setDeviceOwner() throws Exception {
658        mContext.callerPermissions.add(permission.MANAGE_DEVICE_ADMINS);
659        mContext.callerPermissions.add(permission.MANAGE_USERS);
660        mContext.callerPermissions.add(permission.MANAGE_PROFILE_AND_DEVICE_OWNERS);
661        mContext.callerPermissions.add(permission.INTERACT_ACROSS_USERS_FULL);
662
663        // In this test, change the caller user to "system".
664        mContext.binder.callingUid = DpmMockContext.CALLER_SYSTEM_USER_UID;
665
666        // Make sure admin1 is installed on system user.
667        setUpPackageManagerForAdmin(admin1, DpmMockContext.CALLER_SYSTEM_USER_UID);
668
669        // Check various get APIs.
670        checkGetDeviceOwnerInfoApi(dpm, /* hasDeviceOwner =*/ false);
671
672        // DO needs to be an DA.
673        dpm.setActiveAdmin(admin1, /* replace =*/ false);
674
675        // Fire!
676        assertTrue(dpm.setDeviceOwner(admin1, "owner-name"));
677
678        // getDeviceOwnerComponent should return the admin1 component.
679        assertEquals(admin1, dpm.getDeviceOwnerComponentOnCallingUser());
680        assertEquals(admin1, dpm.getDeviceOwnerComponentOnAnyUser());
681
682        // Check various get APIs.
683        checkGetDeviceOwnerInfoApi(dpm, /* hasDeviceOwner =*/ true);
684
685        // getDeviceOwnerComponent should *NOT* return the admin1 component for other users.
686        mContext.binder.callingUid = DpmMockContext.CALLER_UID;
687        assertEquals(null, dpm.getDeviceOwnerComponentOnCallingUser());
688        assertEquals(admin1, dpm.getDeviceOwnerComponentOnAnyUser());
689
690        mContext.binder.callingUid = DpmMockContext.CALLER_SYSTEM_USER_UID;
691
692        // Verify internal calls.
693        verify(mContext.iactivityManager, times(1)).updateDeviceOwner(
694                eq(admin1.getPackageName()));
695
696        // TODO We should check if the caller has called clearCallerIdentity().
697        verify(mContext.ibackupManager, times(1)).setBackupServiceActive(
698                eq(UserHandle.USER_SYSTEM), eq(false));
699
700        verify(mContext.spiedContext, times(1)).sendBroadcastAsUser(
701                MockUtils.checkIntentAction(DevicePolicyManager.ACTION_DEVICE_OWNER_CHANGED),
702                MockUtils.checkUserHandle(UserHandle.USER_SYSTEM));
703
704        assertEquals(admin1, dpm.getDeviceOwnerComponentOnAnyUser());
705    }
706
707    private void checkGetDeviceOwnerInfoApi(DevicePolicyManager dpm, boolean hasDeviceOwner) {
708        final int origCallingUser = mContext.binder.callingUid;
709        final List origPermissions = new ArrayList(mContext.callerPermissions);
710        mContext.callerPermissions.clear();
711
712        mContext.callerPermissions.add(permission.MANAGE_USERS);
713
714        mContext.binder.callingUid = Process.SYSTEM_UID;
715
716        // TODO Test getDeviceOwnerName() too.  To do so, we need to change
717        // DPMS.getApplicationLabel() because Context.createPackageContextAsUser() is not mockable.
718        if (hasDeviceOwner) {
719            assertTrue(dpm.isDeviceOwnerApp(admin1.getPackageName()));
720            assertTrue(dpm.isDeviceOwnerAppOnCallingUser(admin1.getPackageName()));
721            assertEquals(admin1, dpm.getDeviceOwnerComponentOnCallingUser());
722
723            assertTrue(dpm.isDeviceOwnerAppOnAnyUser(admin1.getPackageName()));
724            assertEquals(admin1, dpm.getDeviceOwnerComponentOnAnyUser());
725            assertEquals(UserHandle.USER_SYSTEM, dpm.getDeviceOwnerUserId());
726        } else {
727            assertFalse(dpm.isDeviceOwnerApp(admin1.getPackageName()));
728            assertFalse(dpm.isDeviceOwnerAppOnCallingUser(admin1.getPackageName()));
729            assertEquals(null, dpm.getDeviceOwnerComponentOnCallingUser());
730
731            assertFalse(dpm.isDeviceOwnerAppOnAnyUser(admin1.getPackageName()));
732            assertEquals(null, dpm.getDeviceOwnerComponentOnAnyUser());
733            assertEquals(UserHandle.USER_NULL, dpm.getDeviceOwnerUserId());
734        }
735
736        mContext.binder.callingUid = DpmMockContext.CALLER_SYSTEM_USER_UID;
737        if (hasDeviceOwner) {
738            assertTrue(dpm.isDeviceOwnerApp(admin1.getPackageName()));
739            assertTrue(dpm.isDeviceOwnerAppOnCallingUser(admin1.getPackageName()));
740            assertEquals(admin1, dpm.getDeviceOwnerComponentOnCallingUser());
741
742            assertTrue(dpm.isDeviceOwnerAppOnAnyUser(admin1.getPackageName()));
743            assertEquals(admin1, dpm.getDeviceOwnerComponentOnAnyUser());
744            assertEquals(UserHandle.USER_SYSTEM, dpm.getDeviceOwnerUserId());
745        } else {
746            assertFalse(dpm.isDeviceOwnerApp(admin1.getPackageName()));
747            assertFalse(dpm.isDeviceOwnerAppOnCallingUser(admin1.getPackageName()));
748            assertEquals(null, dpm.getDeviceOwnerComponentOnCallingUser());
749
750            assertFalse(dpm.isDeviceOwnerAppOnAnyUser(admin1.getPackageName()));
751            assertEquals(null, dpm.getDeviceOwnerComponentOnAnyUser());
752            assertEquals(UserHandle.USER_NULL, dpm.getDeviceOwnerUserId());
753        }
754
755        mContext.binder.callingUid = DpmMockContext.CALLER_UID;
756        // Still with MANAGE_USERS.
757        assertFalse(dpm.isDeviceOwnerApp(admin1.getPackageName()));
758        assertFalse(dpm.isDeviceOwnerAppOnCallingUser(admin1.getPackageName()));
759        assertEquals(null, dpm.getDeviceOwnerComponentOnCallingUser());
760
761        if (hasDeviceOwner) {
762            assertTrue(dpm.isDeviceOwnerAppOnAnyUser(admin1.getPackageName()));
763            assertEquals(admin1, dpm.getDeviceOwnerComponentOnAnyUser());
764            assertEquals(UserHandle.USER_SYSTEM, dpm.getDeviceOwnerUserId());
765        } else {
766            assertFalse(dpm.isDeviceOwnerAppOnAnyUser(admin1.getPackageName()));
767            assertEquals(null, dpm.getDeviceOwnerComponentOnAnyUser());
768            assertEquals(UserHandle.USER_NULL, dpm.getDeviceOwnerUserId());
769        }
770
771        mContext.binder.callingUid = Process.SYSTEM_UID;
772        mContext.callerPermissions.remove(permission.MANAGE_USERS);
773        // System can still call "OnAnyUser" without MANAGE_USERS.
774        if (hasDeviceOwner) {
775            assertTrue(dpm.isDeviceOwnerApp(admin1.getPackageName()));
776            assertTrue(dpm.isDeviceOwnerAppOnCallingUser(admin1.getPackageName()));
777            assertEquals(admin1, dpm.getDeviceOwnerComponentOnCallingUser());
778
779            assertTrue(dpm.isDeviceOwnerAppOnAnyUser(admin1.getPackageName()));
780            assertEquals(admin1, dpm.getDeviceOwnerComponentOnAnyUser());
781            assertEquals(UserHandle.USER_SYSTEM, dpm.getDeviceOwnerUserId());
782        } else {
783            assertFalse(dpm.isDeviceOwnerApp(admin1.getPackageName()));
784            assertFalse(dpm.isDeviceOwnerAppOnCallingUser(admin1.getPackageName()));
785            assertEquals(null, dpm.getDeviceOwnerComponentOnCallingUser());
786
787            assertFalse(dpm.isDeviceOwnerAppOnAnyUser(admin1.getPackageName()));
788            assertEquals(null, dpm.getDeviceOwnerComponentOnAnyUser());
789            assertEquals(UserHandle.USER_NULL, dpm.getDeviceOwnerUserId());
790        }
791
792        mContext.binder.callingUid = DpmMockContext.CALLER_SYSTEM_USER_UID;
793        // Still no MANAGE_USERS.
794        if (hasDeviceOwner) {
795            assertTrue(dpm.isDeviceOwnerApp(admin1.getPackageName()));
796            assertTrue(dpm.isDeviceOwnerAppOnCallingUser(admin1.getPackageName()));
797            assertEquals(admin1, dpm.getDeviceOwnerComponentOnCallingUser());
798        } else {
799            assertFalse(dpm.isDeviceOwnerApp(admin1.getPackageName()));
800            assertFalse(dpm.isDeviceOwnerAppOnCallingUser(admin1.getPackageName()));
801            assertEquals(null, dpm.getDeviceOwnerComponentOnCallingUser());
802        }
803
804        try {
805            dpm.isDeviceOwnerAppOnAnyUser(admin1.getPackageName());
806            fail();
807        } catch (SecurityException expected) {
808        }
809        try {
810            dpm.getDeviceOwnerComponentOnAnyUser();
811            fail();
812        } catch (SecurityException expected) {
813        }
814        try {
815            dpm.getDeviceOwnerUserId();
816            fail();
817        } catch (SecurityException expected) {
818        }
819        try {
820            dpm.getDeviceOwnerNameOnAnyUser();
821            fail();
822        } catch (SecurityException expected) {
823        }
824
825        mContext.binder.callingUid = DpmMockContext.CALLER_UID;
826        // Still no MANAGE_USERS.
827        assertFalse(dpm.isDeviceOwnerApp(admin1.getPackageName()));
828        assertFalse(dpm.isDeviceOwnerAppOnCallingUser(admin1.getPackageName()));
829        assertEquals(null, dpm.getDeviceOwnerComponentOnCallingUser());
830
831        try {
832            dpm.isDeviceOwnerAppOnAnyUser(admin1.getPackageName());
833            fail();
834        } catch (SecurityException expected) {
835        }
836        try {
837            dpm.getDeviceOwnerComponentOnAnyUser();
838            fail();
839        } catch (SecurityException expected) {
840        }
841        try {
842            dpm.getDeviceOwnerUserId();
843            fail();
844        } catch (SecurityException expected) {
845        }
846        try {
847            dpm.getDeviceOwnerNameOnAnyUser();
848            fail();
849        } catch (SecurityException expected) {
850        }
851
852        // Restore.
853        mContext.binder.callingUid = origCallingUser;
854        mContext.callerPermissions.addAll(origPermissions);
855    }
856
857
858    /**
859     * Test for: {@link DevicePolicyManager#setDeviceOwner} Package doesn't exist.
860     */
861    public void testSetDeviceOwner_noSuchPackage() {
862        mContext.callerPermissions.add(permission.MANAGE_DEVICE_ADMINS);
863        mContext.callerPermissions.add(permission.MANAGE_USERS);
864        mContext.callerPermissions.add(permission.MANAGE_PROFILE_AND_DEVICE_OWNERS);
865        mContext.callerPermissions.add(permission.INTERACT_ACROSS_USERS_FULL);
866
867        // Call from a process on the system user.
868        mContext.binder.callingUid = DpmMockContext.CALLER_SYSTEM_USER_UID;
869
870        try {
871            dpm.setDeviceOwner(new ComponentName("a.b.c", ".def"));
872            fail("Didn't throw IllegalArgumentException");
873        } catch (IllegalArgumentException expected) {
874            assertTrue("Message was: " + expected.getMessage(),
875                    expected.getMessage().contains("Invalid component"));
876        }
877    }
878
879    public void testSetDeviceOwner_failures() throws Exception {
880        // TODO Test more failure cases.  Basically test all chacks in enforceCanSetDeviceOwner().
881    }
882
883    public void testClearDeviceOwner() throws Exception {
884        mContext.callerPermissions.add(permission.MANAGE_DEVICE_ADMINS);
885        mContext.callerPermissions.add(permission.MANAGE_USERS);
886        mContext.callerPermissions.add(permission.MANAGE_PROFILE_AND_DEVICE_OWNERS);
887        mContext.callerPermissions.add(permission.INTERACT_ACROSS_USERS_FULL);
888
889        // Set admin1 as a DA to the secondary user.
890        setUpPackageManagerForAdmin(admin1, DpmMockContext.CALLER_UID);
891
892        dpm.setActiveAdmin(admin1, /* replace =*/ false);
893
894        // Set admin 1 as the DO to the system user.
895
896        mContext.binder.callingUid = DpmMockContext.CALLER_SYSTEM_USER_UID;
897        setUpPackageManagerForAdmin(admin1, DpmMockContext.CALLER_SYSTEM_USER_UID);
898        dpm.setActiveAdmin(admin1, /* replace =*/ false);
899        assertTrue(dpm.setDeviceOwner(admin1, "owner-name"));
900
901        // Verify internal calls.
902        verify(mContext.iactivityManager, times(1)).updateDeviceOwner(
903                eq(admin1.getPackageName()));
904
905        assertEquals(admin1, dpm.getDeviceOwnerComponentOnAnyUser());
906
907        dpm.addUserRestriction(admin1, UserManager.DISALLOW_ADD_USER);
908
909        assertTrue(dpm.isAdminActive(admin1));
910        assertFalse(dpm.isRemovingAdmin(admin1, UserHandle.USER_SYSTEM));
911
912        // Set up other mocks.
913        when(mContext.userManager.getUserRestrictions()).thenReturn(new Bundle());
914
915        // Now call clear.
916        doReturn(DpmMockContext.CALLER_SYSTEM_USER_UID).when(mContext.packageManager).getPackageUidAsUser(
917                eq(admin1.getPackageName()),
918                anyInt());
919
920        // But first pretend the user is locked.  Then it should fail.
921        when(mContext.userManager.isUserUnlocked(anyInt())).thenReturn(false);
922        try {
923            dpm.clearDeviceOwnerApp(admin1.getPackageName());
924            fail("Didn't throw IllegalStateException");
925        } catch (IllegalStateException expected) {
926            MoreAsserts.assertContainsRegex(
927                    "User must be running and unlocked", expected.getMessage());
928        }
929
930        when(mContext.userManager.isUserUnlocked(anyInt())).thenReturn(true);
931        reset(mContext.userManagerInternal);
932        dpm.clearDeviceOwnerApp(admin1.getPackageName());
933
934        // Now DO shouldn't be set.
935        assertNull(dpm.getDeviceOwnerComponentOnAnyUser());
936
937        verify(mContext.userManagerInternal).setDevicePolicyUserRestrictions(
938                eq(UserHandle.USER_SYSTEM),
939                eq(null),
940                eq(true), eq(CAMERA_NOT_DISABLED));
941
942        assertFalse(dpm.isAdminActiveAsUser(admin1, UserHandle.USER_SYSTEM));
943
944        // ACTION_DEVICE_OWNER_CHANGED should be sent twice, once for setting the device owner
945        // and once for clearing it.
946        verify(mContext.spiedContext, times(2)).sendBroadcastAsUser(
947                MockUtils.checkIntentAction(DevicePolicyManager.ACTION_DEVICE_OWNER_CHANGED),
948                MockUtils.checkUserHandle(UserHandle.USER_SYSTEM));
949        // TODO Check other calls.
950    }
951
952    public void testClearDeviceOwner_fromDifferentUser() throws Exception {
953        mContext.callerPermissions.add(permission.MANAGE_DEVICE_ADMINS);
954        mContext.callerPermissions.add(permission.MANAGE_USERS);
955        mContext.callerPermissions.add(permission.MANAGE_PROFILE_AND_DEVICE_OWNERS);
956        mContext.callerPermissions.add(permission.INTERACT_ACROSS_USERS_FULL);
957
958        // Set admin1 as a DA to the secondary user.
959        setUpPackageManagerForAdmin(admin1, DpmMockContext.CALLER_UID);
960
961        dpm.setActiveAdmin(admin1, /* replace =*/ false);
962
963        // Set admin 1 as the DO to the system user.
964
965        mContext.binder.callingUid = DpmMockContext.CALLER_SYSTEM_USER_UID;
966        setUpPackageManagerForAdmin(admin1, DpmMockContext.CALLER_SYSTEM_USER_UID);
967        dpm.setActiveAdmin(admin1, /* replace =*/ false);
968        assertTrue(dpm.setDeviceOwner(admin1, "owner-name"));
969
970        // Verify internal calls.
971        verify(mContext.iactivityManager, times(1)).updateDeviceOwner(
972                eq(admin1.getPackageName()));
973
974        assertEquals(admin1, dpm.getDeviceOwnerComponentOnAnyUser());
975
976        // Now call clear from the secondary user, which should throw.
977        mContext.binder.callingUid = DpmMockContext.CALLER_UID;
978
979        // Now call clear.
980        doReturn(DpmMockContext.CALLER_UID).when(mContext.packageManager).getPackageUidAsUser(
981                eq(admin1.getPackageName()),
982                anyInt());
983        try {
984            dpm.clearDeviceOwnerApp(admin1.getPackageName());
985            fail("Didn't throw");
986        } catch (SecurityException e) {
987            assertEquals("clearDeviceOwner can only be called by the device owner", e.getMessage());
988        }
989
990        // DO shouldn't be removed.
991        assertTrue(dpm.isDeviceManaged());
992    }
993
994    public void testSetProfileOwner() throws Exception {
995        setAsProfileOwner(admin1);
996
997        // PO admin can't be deactivated.
998        dpm.removeActiveAdmin(admin1);
999        assertTrue(dpm.isAdminActive(admin1));
1000
1001        // Try setting DO on the same user, which should fail.
1002        setUpPackageManagerForAdmin(admin2, DpmMockContext.CALLER_UID);
1003        dpm.setActiveAdmin(admin2, /* refreshing= */ true, DpmMockContext.CALLER_USER_HANDLE);
1004        try {
1005            dpm.setDeviceOwner(admin2, "owner-name", DpmMockContext.CALLER_USER_HANDLE);
1006            fail("IllegalStateException not thrown");
1007        } catch (IllegalStateException expected) {
1008            assertTrue("Message was: " + expected.getMessage(),
1009                    expected.getMessage().contains("already has a profile owner"));
1010        }
1011    }
1012
1013    public void testClearProfileOwner() throws Exception {
1014        setAsProfileOwner(admin1);
1015
1016        mContext.binder.callingUid = DpmMockContext.CALLER_UID;
1017
1018        assertTrue(dpm.isProfileOwnerApp(admin1.getPackageName()));
1019        assertFalse(dpm.isRemovingAdmin(admin1, DpmMockContext.CALLER_USER_HANDLE));
1020
1021        // First try when the user is locked, which should fail.
1022        when(mContext.userManager.isUserUnlocked(anyInt()))
1023                .thenReturn(false);
1024        try {
1025            dpm.clearProfileOwner(admin1);
1026            fail("Didn't throw IllegalStateException");
1027        } catch (IllegalStateException expected) {
1028            MoreAsserts.assertContainsRegex(
1029                    "User must be running and unlocked", expected.getMessage());
1030        }
1031        // Clear, really.
1032        when(mContext.userManager.isUserUnlocked(anyInt()))
1033                .thenReturn(true);
1034        dpm.clearProfileOwner(admin1);
1035
1036        // Check
1037        assertFalse(dpm.isProfileOwnerApp(admin1.getPackageName()));
1038        assertFalse(dpm.isAdminActiveAsUser(admin1, DpmMockContext.CALLER_USER_HANDLE));
1039    }
1040
1041    public void testSetProfileOwner_failures() throws Exception {
1042        // TODO Test more failure cases.  Basically test all chacks in enforceCanSetProfileOwner().
1043    }
1044
1045    public void testGetDeviceOwnerAdminLocked() throws Exception {
1046        checkDeviceOwnerWithMultipleDeviceAdmins();
1047    }
1048
1049    private void checkDeviceOwnerWithMultipleDeviceAdmins() throws Exception {
1050        // In ths test, we use 3 users (system + 2 secondary users), set some device admins to them,
1051        // set admin2 on CALLER_USER_HANDLE as DO, then call getDeviceOwnerAdminLocked() to
1052        // make sure it gets the right component from the right user.
1053
1054        final int ANOTHER_USER_ID = 100;
1055        final int ANOTHER_ADMIN_UID = UserHandle.getUid(ANOTHER_USER_ID, 456);
1056
1057        mMockContext.addUser(ANOTHER_USER_ID, 0); // Add one more user.
1058
1059        mContext.callerPermissions.add(permission.MANAGE_DEVICE_ADMINS);
1060        mContext.callerPermissions.add(permission.MANAGE_USERS);
1061        mContext.callerPermissions.add(permission.MANAGE_PROFILE_AND_DEVICE_OWNERS);
1062        mContext.callerPermissions.add(permission.INTERACT_ACROSS_USERS_FULL);
1063
1064        mContext.binder.callingUid = DpmMockContext.CALLER_SYSTEM_USER_UID;
1065
1066        when(mContext.userManagerForMock.isSplitSystemUser()).thenReturn(true);
1067
1068        // Make sure the admin packge is installed to each user.
1069        setUpPackageManagerForAdmin(admin1, DpmMockContext.CALLER_SYSTEM_USER_UID);
1070        setUpPackageManagerForAdmin(admin3, DpmMockContext.CALLER_SYSTEM_USER_UID);
1071
1072        setUpPackageManagerForAdmin(admin1, DpmMockContext.CALLER_UID);
1073        setUpPackageManagerForAdmin(admin2, DpmMockContext.CALLER_UID);
1074
1075        setUpPackageManagerForAdmin(admin2, ANOTHER_ADMIN_UID);
1076
1077
1078        // Set active admins to the users.
1079        dpm.setActiveAdmin(admin1, /* replace =*/ false);
1080        dpm.setActiveAdmin(admin3, /* replace =*/ false);
1081
1082        dpm.setActiveAdmin(admin1, /* replace =*/ false, DpmMockContext.CALLER_USER_HANDLE);
1083        dpm.setActiveAdmin(admin2, /* replace =*/ false, DpmMockContext.CALLER_USER_HANDLE);
1084
1085        dpm.setActiveAdmin(admin2, /* replace =*/ false, ANOTHER_USER_ID);
1086
1087        // Set DO on the first non-system user.
1088        mContext.setUserRunning(DpmMockContext.CALLER_USER_HANDLE, true);
1089        assertTrue(dpm.setDeviceOwner(admin2, "owner-name", DpmMockContext.CALLER_USER_HANDLE));
1090
1091        assertEquals(admin2, dpms.getDeviceOwnerComponent(/* callingUserOnly =*/ false));
1092
1093        // Then check getDeviceOwnerAdminLocked().
1094        assertEquals(admin2, dpms.getDeviceOwnerAdminLocked().info.getComponent());
1095        assertEquals(DpmMockContext.CALLER_UID, dpms.getDeviceOwnerAdminLocked().getUid());
1096    }
1097
1098    /**
1099     * This essentially tests
1100     * {@code DevicePolicyManagerService.findOwnerComponentIfNecessaryLocked()}. (which is
1101     * private.)
1102     *
1103     * We didn't use to persist the DO component class name, but now we do, and the above method
1104     * finds the right component from a package name upon migration.
1105     */
1106    public void testDeviceOwnerMigration() throws Exception {
1107        when(mContext.userManagerForMock.isSplitSystemUser()).thenReturn(true);
1108        checkDeviceOwnerWithMultipleDeviceAdmins();
1109
1110        // Overwrite the device owner setting and clears the clas name.
1111        dpms.mOwners.setDeviceOwner(
1112                new ComponentName(admin2.getPackageName(), ""),
1113                "owner-name", DpmMockContext.CALLER_USER_HANDLE);
1114        dpms.mOwners.writeDeviceOwner();
1115
1116        // Make sure the DO component name doesn't have a class name.
1117        assertEquals("", dpms.getDeviceOwnerComponent(/* callingUserOnly =*/ false).getClassName());
1118
1119        // Then create a new DPMS to have it load the settings from files.
1120        when(mContext.userManager.getUserRestrictions(any(UserHandle.class)))
1121                .thenReturn(new Bundle());
1122        initializeDpms();
1123
1124        // Now the DO component name is a full name.
1125        // *BUT* because both admin1 and admin2 belong to the same package, we think admin1 is the
1126        // DO.
1127        assertEquals(admin1, dpms.getDeviceOwnerComponent(/* callingUserOnly =*/ false));
1128    }
1129
1130    public void testSetGetApplicationRestriction() {
1131        setAsProfileOwner(admin1);
1132
1133        {
1134            Bundle rest = new Bundle();
1135            rest.putString("KEY_STRING", "Foo1");
1136            dpm.setApplicationRestrictions(admin1, "pkg1", rest);
1137        }
1138
1139        {
1140            Bundle rest = new Bundle();
1141            rest.putString("KEY_STRING", "Foo2");
1142            dpm.setApplicationRestrictions(admin1, "pkg2", rest);
1143        }
1144
1145        {
1146            Bundle returned = dpm.getApplicationRestrictions(admin1, "pkg1");
1147            assertNotNull(returned);
1148            assertEquals(returned.size(), 1);
1149            assertEquals(returned.get("KEY_STRING"), "Foo1");
1150        }
1151
1152        {
1153            Bundle returned = dpm.getApplicationRestrictions(admin1, "pkg2");
1154            assertNotNull(returned);
1155            assertEquals(returned.size(), 1);
1156            assertEquals(returned.get("KEY_STRING"), "Foo2");
1157        }
1158
1159        dpm.setApplicationRestrictions(admin1, "pkg2", new Bundle());
1160        assertEquals(0, dpm.getApplicationRestrictions(admin1, "pkg2").size());
1161    }
1162
1163    public void testApplicationRestrictionsManagingApp() throws Exception {
1164        setAsProfileOwner(admin1);
1165
1166        final String nonExistAppRestrictionsManagerPackage = "com.google.app.restrictions.manager2";
1167        final String appRestrictionsManagerPackage = "com.google.app.restrictions.manager";
1168        final int appRestrictionsManagerAppId = 20987;
1169        final int appRestrictionsManagerUid = UserHandle.getUid(
1170                DpmMockContext.CALLER_USER_HANDLE, appRestrictionsManagerAppId);
1171        doReturn(appRestrictionsManagerUid).when(mContext.packageManager).getPackageUidAsUser(
1172                eq(appRestrictionsManagerPackage),
1173                eq(DpmMockContext.CALLER_USER_HANDLE));
1174        mContext.binder.callingUid = appRestrictionsManagerUid;
1175
1176        final PackageInfo pi = new PackageInfo();
1177        pi.applicationInfo = new ApplicationInfo();
1178        pi.applicationInfo.flags = ApplicationInfo.FLAG_HAS_CODE;
1179        doReturn(pi).when(mContext.ipackageManager).getPackageInfo(
1180                eq(appRestrictionsManagerPackage),
1181                anyInt(),
1182                eq(DpmMockContext.CALLER_USER_HANDLE));
1183
1184        // appRestrictionsManager package shouldn't be able to manage restrictions as the PO hasn't
1185        // delegated that permission yet.
1186        assertFalse(dpm.isCallerApplicationRestrictionsManagingPackage());
1187        Bundle rest = new Bundle();
1188        rest.putString("KEY_STRING", "Foo1");
1189        try {
1190            dpm.setApplicationRestrictions(null, "pkg1", rest);
1191            fail("Didn't throw expected SecurityException");
1192        } catch (SecurityException expected) {
1193            MoreAsserts.assertContainsRegex(
1194                    "caller cannot manage application restrictions", expected.getMessage());
1195        }
1196        try {
1197            dpm.getApplicationRestrictions(null, "pkg1");
1198            fail("Didn't throw expected SecurityException");
1199        } catch (SecurityException expected) {
1200            MoreAsserts.assertContainsRegex(
1201                    "caller cannot manage application restrictions", expected.getMessage());
1202        }
1203
1204        // Check via the profile owner that no restrictions were set.
1205        mContext.binder.callingUid = DpmMockContext.CALLER_UID;
1206        assertEquals(0, dpm.getApplicationRestrictions(admin1, "pkg1").size());
1207
1208        // Check the API does not allow setting a non-existent package
1209        try {
1210            dpm.setApplicationRestrictionsManagingPackage(admin1,
1211                    nonExistAppRestrictionsManagerPackage);
1212            fail("Non-existent app set as app restriction manager.");
1213        } catch (PackageManager.NameNotFoundException expected) {
1214            MoreAsserts.assertContainsRegex(
1215                    nonExistAppRestrictionsManagerPackage, expected.getMessage());
1216        }
1217
1218        // Let appRestrictionsManagerPackage manage app restrictions
1219        dpm.setApplicationRestrictionsManagingPackage(admin1, appRestrictionsManagerPackage);
1220        assertEquals(appRestrictionsManagerPackage,
1221                dpm.getApplicationRestrictionsManagingPackage(admin1));
1222
1223        // Now that package should be able to set and retrieve app restrictions.
1224        mContext.binder.callingUid = appRestrictionsManagerUid;
1225        assertTrue(dpm.isCallerApplicationRestrictionsManagingPackage());
1226        dpm.setApplicationRestrictions(null, "pkg1", rest);
1227        Bundle returned = dpm.getApplicationRestrictions(null, "pkg1");
1228        assertEquals(1, returned.size(), 1);
1229        assertEquals("Foo1", returned.get("KEY_STRING"));
1230
1231        // The same app running on a separate user shouldn't be able to manage app restrictions.
1232        mContext.binder.callingUid = UserHandle.getUid(
1233                UserHandle.USER_SYSTEM, appRestrictionsManagerAppId);
1234        assertFalse(dpm.isCallerApplicationRestrictionsManagingPackage());
1235        try {
1236            dpm.setApplicationRestrictions(null, "pkg1", rest);
1237            fail("Didn't throw expected SecurityException");
1238        } catch (SecurityException expected) {
1239            MoreAsserts.assertContainsRegex(
1240                    "caller cannot manage application restrictions", expected.getMessage());
1241        }
1242
1243        // The DPM is still able to manage app restrictions, even if it allowed another app to do it
1244        // too.
1245        mContext.binder.callingUid = DpmMockContext.CALLER_UID;
1246        assertEquals(returned, dpm.getApplicationRestrictions(admin1, "pkg1"));
1247        dpm.setApplicationRestrictions(admin1, "pkg1", null);
1248        assertEquals(0, dpm.getApplicationRestrictions(admin1, "pkg1").size());
1249
1250        // Removing the ability for the package to manage app restrictions.
1251        dpm.setApplicationRestrictionsManagingPackage(admin1, null);
1252        assertNull(dpm.getApplicationRestrictionsManagingPackage(admin1));
1253        mContext.binder.callingUid = appRestrictionsManagerUid;
1254        assertFalse(dpm.isCallerApplicationRestrictionsManagingPackage());
1255        try {
1256            dpm.setApplicationRestrictions(null, "pkg1", null);
1257            fail("Didn't throw expected SecurityException");
1258        } catch (SecurityException expected) {
1259            MoreAsserts.assertContainsRegex(
1260                    "caller cannot manage application restrictions", expected.getMessage());
1261        }
1262    }
1263
1264    public void testSetUserRestriction_asDo() throws Exception {
1265        mContext.callerPermissions.add(permission.MANAGE_DEVICE_ADMINS);
1266        mContext.callerPermissions.add(permission.MANAGE_USERS);
1267        mContext.callerPermissions.add(permission.MANAGE_PROFILE_AND_DEVICE_OWNERS);
1268        mContext.callerPermissions.add(permission.INTERACT_ACROSS_USERS_FULL);
1269
1270        // First, set DO.
1271
1272        // Call from a process on the system user.
1273        mContext.binder.callingUid = DpmMockContext.CALLER_SYSTEM_USER_UID;
1274
1275        // Make sure admin1 is installed on system user.
1276        setUpPackageManagerForAdmin(admin1, DpmMockContext.CALLER_SYSTEM_USER_UID);
1277
1278        // Call.
1279        dpm.setActiveAdmin(admin1, /* replace =*/ false, UserHandle.USER_SYSTEM);
1280        assertTrue(dpm.setDeviceOwner(admin1, "owner-name",
1281                UserHandle.USER_SYSTEM));
1282
1283        // Check that the user restrictions that are enabled by default are set. Then unset them.
1284        String[] defaultRestrictions = UserRestrictionsUtils
1285                .getDefaultEnabledForDeviceOwner().toArray(new String[0]);
1286        DpmTestUtils.assertRestrictions(
1287                DpmTestUtils.newRestrictions(defaultRestrictions),
1288                dpms.getDeviceOwnerAdminLocked().ensureUserRestrictions()
1289        );
1290        DpmTestUtils.assertRestrictions(
1291                DpmTestUtils.newRestrictions(defaultRestrictions),
1292                dpm.getUserRestrictions(admin1)
1293        );
1294        verify(mContext.userManagerInternal).setDevicePolicyUserRestrictions(
1295                eq(UserHandle.USER_SYSTEM),
1296                MockUtils.checkUserRestrictions(defaultRestrictions),
1297                eq(true) /* isDeviceOwner */,
1298                eq(CAMERA_NOT_DISABLED)
1299        );
1300        reset(mContext.userManagerInternal);
1301
1302        for (String restriction : defaultRestrictions) {
1303            dpm.clearUserRestriction(admin1, restriction);
1304        }
1305
1306        assertNoDeviceOwnerRestrictions();
1307        reset(mContext.userManagerInternal);
1308
1309        dpm.addUserRestriction(admin1, UserManager.DISALLOW_ADD_USER);
1310        verify(mContext.userManagerInternal).setDevicePolicyUserRestrictions(
1311                eq(UserHandle.USER_SYSTEM),
1312                MockUtils.checkUserRestrictions(UserManager.DISALLOW_ADD_USER),
1313                eq(true), eq(CAMERA_NOT_DISABLED));
1314        reset(mContext.userManagerInternal);
1315
1316        dpm.addUserRestriction(admin1, UserManager.DISALLOW_OUTGOING_CALLS);
1317        verify(mContext.userManagerInternal).setDevicePolicyUserRestrictions(
1318                eq(UserHandle.USER_SYSTEM),
1319                MockUtils.checkUserRestrictions(UserManager.DISALLOW_OUTGOING_CALLS,
1320                        UserManager.DISALLOW_ADD_USER),
1321                eq(true), eq(CAMERA_NOT_DISABLED));
1322        reset(mContext.userManagerInternal);
1323
1324        DpmTestUtils.assertRestrictions(
1325                DpmTestUtils.newRestrictions(
1326                        UserManager.DISALLOW_ADD_USER, UserManager.DISALLOW_OUTGOING_CALLS),
1327                dpms.getDeviceOwnerAdminLocked().ensureUserRestrictions()
1328        );
1329        DpmTestUtils.assertRestrictions(
1330                DpmTestUtils.newRestrictions(
1331                        UserManager.DISALLOW_ADD_USER, UserManager.DISALLOW_OUTGOING_CALLS),
1332                dpm.getUserRestrictions(admin1)
1333        );
1334
1335        dpm.clearUserRestriction(admin1, UserManager.DISALLOW_ADD_USER);
1336        verify(mContext.userManagerInternal).setDevicePolicyUserRestrictions(
1337                eq(UserHandle.USER_SYSTEM),
1338                MockUtils.checkUserRestrictions(UserManager.DISALLOW_OUTGOING_CALLS),
1339                eq(true), eq(CAMERA_NOT_DISABLED));
1340        reset(mContext.userManagerInternal);
1341
1342        DpmTestUtils.assertRestrictions(
1343                DpmTestUtils.newRestrictions(UserManager.DISALLOW_OUTGOING_CALLS),
1344                dpms.getDeviceOwnerAdminLocked().ensureUserRestrictions()
1345        );
1346        DpmTestUtils.assertRestrictions(
1347                DpmTestUtils.newRestrictions(UserManager.DISALLOW_OUTGOING_CALLS),
1348                dpm.getUserRestrictions(admin1)
1349        );
1350
1351        dpm.clearUserRestriction(admin1, UserManager.DISALLOW_OUTGOING_CALLS);
1352        verify(mContext.userManagerInternal).setDevicePolicyUserRestrictions(
1353                eq(UserHandle.USER_SYSTEM),
1354                MockUtils.checkUserRestrictions(),
1355                eq(true), eq(CAMERA_NOT_DISABLED));
1356        reset(mContext.userManagerInternal);
1357
1358        assertNoDeviceOwnerRestrictions();
1359
1360        // DISALLOW_ADJUST_VOLUME and DISALLOW_UNMUTE_MICROPHONE are PO restrictions, but when
1361        // DO sets them, the scope is global.
1362        dpm.addUserRestriction(admin1, UserManager.DISALLOW_ADJUST_VOLUME);
1363        reset(mContext.userManagerInternal);
1364        dpm.addUserRestriction(admin1, UserManager.DISALLOW_UNMUTE_MICROPHONE);
1365        verify(mContext.userManagerInternal).setDevicePolicyUserRestrictions(
1366                eq(UserHandle.USER_SYSTEM),
1367                MockUtils.checkUserRestrictions(UserManager.DISALLOW_ADJUST_VOLUME,
1368                        UserManager.DISALLOW_UNMUTE_MICROPHONE),
1369                eq(true), eq(CAMERA_NOT_DISABLED));
1370        reset(mContext.userManagerInternal);
1371
1372        dpm.clearUserRestriction(admin1, UserManager.DISALLOW_ADJUST_VOLUME);
1373        dpm.clearUserRestriction(admin1, UserManager.DISALLOW_UNMUTE_MICROPHONE);
1374        reset(mContext.userManagerInternal);
1375
1376        // More tests.
1377        dpm.addUserRestriction(admin1, UserManager.DISALLOW_ADD_USER);
1378        verify(mContext.userManagerInternal).setDevicePolicyUserRestrictions(
1379                eq(UserHandle.USER_SYSTEM),
1380                MockUtils.checkUserRestrictions(UserManager.DISALLOW_ADD_USER),
1381                eq(true), eq(CAMERA_NOT_DISABLED));
1382        reset(mContext.userManagerInternal);
1383
1384        dpm.addUserRestriction(admin1, UserManager.DISALLOW_FUN);
1385        verify(mContext.userManagerInternal).setDevicePolicyUserRestrictions(
1386                eq(UserHandle.USER_SYSTEM),
1387                MockUtils.checkUserRestrictions(UserManager.DISALLOW_FUN,
1388                        UserManager.DISALLOW_ADD_USER),
1389                eq(true), eq(CAMERA_NOT_DISABLED));
1390        reset(mContext.userManagerInternal);
1391
1392        dpm.setCameraDisabled(admin1, true);
1393        verify(mContext.userManagerInternal).setDevicePolicyUserRestrictions(
1394                eq(UserHandle.USER_SYSTEM),
1395                // DISALLOW_CAMERA will be applied to both local and global.
1396                MockUtils.checkUserRestrictions(UserManager.DISALLOW_FUN,
1397                        UserManager.DISALLOW_ADD_USER),
1398                eq(true), eq(CAMERA_DISABLED_GLOBALLY));
1399        reset(mContext.userManagerInternal);
1400
1401        // Set up another DA and let it disable camera.  Now DISALLOW_CAMERA will only be applied
1402        // locally.
1403        dpm.setCameraDisabled(admin1, false);
1404        reset(mContext.userManagerInternal);
1405
1406        setUpPackageManagerForAdmin(admin2, DpmMockContext.CALLER_SYSTEM_USER_UID);
1407        dpm.setActiveAdmin(admin2, /* replace =*/ false, UserHandle.USER_SYSTEM);
1408        dpm.setCameraDisabled(admin2, true);
1409
1410        verify(mContext.userManagerInternal).setDevicePolicyUserRestrictions(
1411                eq(UserHandle.USER_SYSTEM),
1412                // DISALLOW_CAMERA will be applied to both local and global. <- TODO: fix this
1413                MockUtils.checkUserRestrictions(UserManager.DISALLOW_FUN,
1414                        UserManager.DISALLOW_ADD_USER),
1415                eq(true), eq(CAMERA_DISABLED_LOCALLY));
1416        reset(mContext.userManagerInternal);
1417        // TODO Make sure restrictions are written to the file.
1418    }
1419
1420    public void testSetUserRestriction_asPo() {
1421        setAsProfileOwner(admin1);
1422
1423        DpmTestUtils.assertRestrictions(
1424                DpmTestUtils.newRestrictions(),
1425                dpms.getProfileOwnerAdminLocked(DpmMockContext.CALLER_USER_HANDLE)
1426                        .ensureUserRestrictions()
1427        );
1428
1429        dpm.addUserRestriction(admin1, UserManager.DISALLOW_INSTALL_UNKNOWN_SOURCES);
1430        verify(mContext.userManagerInternal).setDevicePolicyUserRestrictions(
1431                eq(DpmMockContext.CALLER_USER_HANDLE),
1432                MockUtils.checkUserRestrictions(UserManager.DISALLOW_INSTALL_UNKNOWN_SOURCES),
1433                eq(false), eq(CAMERA_NOT_DISABLED));
1434        reset(mContext.userManagerInternal);
1435
1436        dpm.addUserRestriction(admin1, UserManager.DISALLOW_OUTGOING_CALLS);
1437        verify(mContext.userManagerInternal).setDevicePolicyUserRestrictions(
1438                eq(DpmMockContext.CALLER_USER_HANDLE),
1439                MockUtils.checkUserRestrictions(UserManager.DISALLOW_INSTALL_UNKNOWN_SOURCES,
1440                        UserManager.DISALLOW_OUTGOING_CALLS),
1441                eq(false), eq(CAMERA_NOT_DISABLED));
1442        reset(mContext.userManagerInternal);
1443
1444        DpmTestUtils.assertRestrictions(
1445                DpmTestUtils.newRestrictions(
1446                        UserManager.DISALLOW_INSTALL_UNKNOWN_SOURCES,
1447                        UserManager.DISALLOW_OUTGOING_CALLS
1448                ),
1449                dpms.getProfileOwnerAdminLocked(DpmMockContext.CALLER_USER_HANDLE)
1450                        .ensureUserRestrictions()
1451        );
1452        DpmTestUtils.assertRestrictions(
1453                DpmTestUtils.newRestrictions(
1454                        UserManager.DISALLOW_INSTALL_UNKNOWN_SOURCES,
1455                        UserManager.DISALLOW_OUTGOING_CALLS
1456                ),
1457                dpm.getUserRestrictions(admin1)
1458        );
1459
1460        dpm.clearUserRestriction(admin1, UserManager.DISALLOW_INSTALL_UNKNOWN_SOURCES);
1461        verify(mContext.userManagerInternal).setDevicePolicyUserRestrictions(
1462                eq(DpmMockContext.CALLER_USER_HANDLE),
1463                MockUtils.checkUserRestrictions(UserManager.DISALLOW_OUTGOING_CALLS),
1464                eq(false), eq(CAMERA_NOT_DISABLED));
1465        reset(mContext.userManagerInternal);
1466
1467        DpmTestUtils.assertRestrictions(
1468                DpmTestUtils.newRestrictions(
1469                        UserManager.DISALLOW_OUTGOING_CALLS
1470                ),
1471                dpms.getProfileOwnerAdminLocked(DpmMockContext.CALLER_USER_HANDLE)
1472                        .ensureUserRestrictions()
1473        );
1474        DpmTestUtils.assertRestrictions(
1475                DpmTestUtils.newRestrictions(
1476                        UserManager.DISALLOW_OUTGOING_CALLS
1477                ),
1478                dpm.getUserRestrictions(admin1)
1479        );
1480
1481        dpm.clearUserRestriction(admin1, UserManager.DISALLOW_OUTGOING_CALLS);
1482        verify(mContext.userManagerInternal).setDevicePolicyUserRestrictions(
1483                eq(DpmMockContext.CALLER_USER_HANDLE),
1484                MockUtils.checkUserRestrictions(),
1485                eq(false), eq(CAMERA_NOT_DISABLED));
1486        reset(mContext.userManagerInternal);
1487
1488        DpmTestUtils.assertRestrictions(
1489                DpmTestUtils.newRestrictions(),
1490                dpms.getProfileOwnerAdminLocked(DpmMockContext.CALLER_USER_HANDLE)
1491                        .ensureUserRestrictions()
1492        );
1493        DpmTestUtils.assertRestrictions(
1494                DpmTestUtils.newRestrictions(),
1495                dpm.getUserRestrictions(admin1)
1496        );
1497
1498        // DISALLOW_ADJUST_VOLUME and DISALLOW_UNMUTE_MICROPHONE can be set by PO too, even
1499        // though when DO sets them they'll be applied globally.
1500        dpm.addUserRestriction(admin1, UserManager.DISALLOW_ADJUST_VOLUME);
1501        reset(mContext.userManagerInternal);
1502        dpm.addUserRestriction(admin1, UserManager.DISALLOW_UNMUTE_MICROPHONE);
1503        verify(mContext.userManagerInternal).setDevicePolicyUserRestrictions(
1504                eq(DpmMockContext.CALLER_USER_HANDLE),
1505                MockUtils.checkUserRestrictions(UserManager.DISALLOW_ADJUST_VOLUME,
1506                        UserManager.DISALLOW_UNMUTE_MICROPHONE),
1507                eq(false), eq(CAMERA_NOT_DISABLED));
1508        reset(mContext.userManagerInternal);
1509
1510        dpm.setCameraDisabled(admin1, true);
1511        verify(mContext.userManagerInternal).setDevicePolicyUserRestrictions(
1512                eq(DpmMockContext.CALLER_USER_HANDLE),
1513                MockUtils.checkUserRestrictions(UserManager.DISALLOW_ADJUST_VOLUME,
1514                        UserManager.DISALLOW_UNMUTE_MICROPHONE),
1515                eq(false), eq(CAMERA_DISABLED_LOCALLY));
1516        reset(mContext.userManagerInternal);
1517
1518        // TODO Make sure restrictions are written to the file.
1519    }
1520
1521
1522    public void testDefaultEnabledUserRestrictions() throws Exception {
1523        mContext.callerPermissions.add(permission.MANAGE_DEVICE_ADMINS);
1524        mContext.callerPermissions.add(permission.MANAGE_USERS);
1525        mContext.callerPermissions.add(permission.MANAGE_PROFILE_AND_DEVICE_OWNERS);
1526        mContext.callerPermissions.add(permission.INTERACT_ACROSS_USERS_FULL);
1527
1528        // First, set DO.
1529
1530        // Call from a process on the system user.
1531        mContext.binder.callingUid = DpmMockContext.CALLER_SYSTEM_USER_UID;
1532
1533        // Make sure admin1 is installed on system user.
1534        setUpPackageManagerForAdmin(admin1, DpmMockContext.CALLER_SYSTEM_USER_UID);
1535
1536        dpm.setActiveAdmin(admin1, /* replace =*/ false, UserHandle.USER_SYSTEM);
1537        assertTrue(dpm.setDeviceOwner(admin1, "owner-name",
1538                UserHandle.USER_SYSTEM));
1539
1540        // Check that the user restrictions that are enabled by default are set. Then unset them.
1541        String[] defaultRestrictions = UserRestrictionsUtils
1542                .getDefaultEnabledForDeviceOwner().toArray(new String[0]);
1543        assertTrue(defaultRestrictions.length > 0);
1544        DpmTestUtils.assertRestrictions(
1545                DpmTestUtils.newRestrictions(defaultRestrictions),
1546                dpms.getDeviceOwnerAdminLocked().ensureUserRestrictions()
1547        );
1548        DpmTestUtils.assertRestrictions(
1549                DpmTestUtils.newRestrictions(defaultRestrictions),
1550                dpm.getUserRestrictions(admin1)
1551        );
1552        verify(mContext.userManagerInternal).setDevicePolicyUserRestrictions(
1553                eq(UserHandle.USER_SYSTEM),
1554                MockUtils.checkUserRestrictions(defaultRestrictions),
1555                eq(true) /* isDeviceOwner */,
1556                eq(CAMERA_NOT_DISABLED)
1557        );
1558        reset(mContext.userManagerInternal);
1559
1560        for (String restriction : defaultRestrictions) {
1561            dpm.clearUserRestriction(admin1, restriction);
1562        }
1563
1564        assertNoDeviceOwnerRestrictions();
1565
1566        // Initialize DPMS again and check that the user restriction wasn't enabled again.
1567        reset(mContext.userManagerInternal);
1568        initializeDpms();
1569        assertTrue(dpm.isDeviceOwnerApp(admin1.getPackageName()));
1570        assertNotNull(dpms.getDeviceOwnerAdminLocked());
1571
1572        assertNoDeviceOwnerRestrictions();
1573
1574        // Add a new restriction to the default set, initialize DPMS, and check that the restriction
1575        // is set as it wasn't enabled during setDeviceOwner.
1576        final String newDefaultEnabledRestriction = UserManager.DISALLOW_REMOVE_MANAGED_PROFILE;
1577        assertFalse(UserRestrictionsUtils
1578                .getDefaultEnabledForDeviceOwner().contains(newDefaultEnabledRestriction));
1579        UserRestrictionsUtils
1580                .getDefaultEnabledForDeviceOwner().add(newDefaultEnabledRestriction);
1581        try {
1582            reset(mContext.userManagerInternal);
1583            initializeDpms();
1584            assertTrue(dpm.isDeviceOwnerApp(admin1.getPackageName()));
1585            assertNotNull(dpms.getDeviceOwnerAdminLocked());
1586
1587            DpmTestUtils.assertRestrictions(
1588                DpmTestUtils.newRestrictions(newDefaultEnabledRestriction),
1589                dpms.getDeviceOwnerAdminLocked().ensureUserRestrictions()
1590            );
1591            DpmTestUtils.assertRestrictions(
1592                DpmTestUtils.newRestrictions(newDefaultEnabledRestriction),
1593                dpm.getUserRestrictions(admin1)
1594            );
1595            verify(mContext.userManagerInternal, atLeast(1)).setDevicePolicyUserRestrictions(
1596                eq(UserHandle.USER_SYSTEM),
1597                MockUtils.checkUserRestrictions(newDefaultEnabledRestriction),
1598                eq(true) /* isDeviceOwner */,
1599                eq(CAMERA_NOT_DISABLED)
1600            );
1601            reset(mContext.userManagerInternal);
1602
1603            // Remove the restriction.
1604            dpm.clearUserRestriction(admin1, newDefaultEnabledRestriction);
1605
1606            // Initialize DPMS again. The restriction shouldn't be enabled for a second time.
1607            initializeDpms();
1608            assertTrue(dpm.isDeviceOwnerApp(admin1.getPackageName()));
1609            assertNotNull(dpms.getDeviceOwnerAdminLocked());
1610            assertNoDeviceOwnerRestrictions();
1611        } finally {
1612            UserRestrictionsUtils
1613                .getDefaultEnabledForDeviceOwner().remove(newDefaultEnabledRestriction);
1614        }
1615    }
1616
1617    private void assertNoDeviceOwnerRestrictions() {
1618        DpmTestUtils.assertRestrictions(
1619                DpmTestUtils.newRestrictions(),
1620                dpms.getDeviceOwnerAdminLocked().ensureUserRestrictions()
1621        );
1622        DpmTestUtils.assertRestrictions(
1623                DpmTestUtils.newRestrictions(),
1624                dpm.getUserRestrictions(admin1)
1625        );
1626    }
1627
1628    public void testGetMacAddress() throws Exception {
1629        mContext.callerPermissions.add(permission.MANAGE_DEVICE_ADMINS);
1630        mContext.callerPermissions.add(permission.MANAGE_PROFILE_AND_DEVICE_OWNERS);
1631        mContext.callerPermissions.add(permission.INTERACT_ACROSS_USERS_FULL);
1632
1633        // In this test, change the caller user to "system".
1634        mContext.binder.callingUid = DpmMockContext.CALLER_SYSTEM_USER_UID;
1635
1636        // Make sure admin1 is installed on system user.
1637        setUpPackageManagerForAdmin(admin1, DpmMockContext.CALLER_SYSTEM_USER_UID);
1638
1639        // Test 1. Caller doesn't have DO or DA.
1640        try {
1641            dpm.getWifiMacAddress(admin1);
1642            fail();
1643        } catch (SecurityException e) {
1644            MoreAsserts.assertContainsRegex("No active admin", e.getMessage());
1645        }
1646
1647        // DO needs to be an DA.
1648        dpm.setActiveAdmin(admin1, /* replace =*/ false);
1649        assertTrue(dpm.isAdminActive(admin1));
1650
1651        // Test 2. Caller has DA, but not DO.
1652        try {
1653            dpm.getWifiMacAddress(admin1);
1654            fail();
1655        } catch (SecurityException e) {
1656            MoreAsserts.assertContainsRegex("does not own the device", e.getMessage());
1657        }
1658
1659        // Test 3. Caller has PO, but not DO.
1660        assertTrue(dpm.setProfileOwner(admin1, null, UserHandle.USER_SYSTEM));
1661        try {
1662            dpm.getWifiMacAddress(admin1);
1663            fail();
1664        } catch (SecurityException e) {
1665            MoreAsserts.assertContainsRegex("does not own the device", e.getMessage());
1666        }
1667
1668        // Remove PO.
1669        dpm.clearProfileOwner(admin1);
1670        dpm.setActiveAdmin(admin1, false);
1671        // Test 4, Caller is DO now.
1672        assertTrue(dpm.setDeviceOwner(admin1, null, UserHandle.USER_SYSTEM));
1673
1674        // 4-1.  But no WifiInfo.
1675        assertNull(dpm.getWifiMacAddress(admin1));
1676
1677        // 4-2.  Returns WifiInfo, but with the default MAC.
1678        when(mContext.wifiManager.getConnectionInfo()).thenReturn(new WifiInfo());
1679        assertNull(dpm.getWifiMacAddress(admin1));
1680
1681        // 4-3. With a real MAC address.
1682        final WifiInfo wi = new WifiInfo();
1683        wi.setMacAddress("11:22:33:44:55:66");
1684        when(mContext.wifiManager.getConnectionInfo()).thenReturn(wi);
1685        assertEquals("11:22:33:44:55:66", dpm.getWifiMacAddress(admin1));
1686    }
1687
1688    public void testReboot() throws Exception {
1689        mContext.callerPermissions.add(permission.MANAGE_DEVICE_ADMINS);
1690        mContext.callerPermissions.add(permission.MANAGE_PROFILE_AND_DEVICE_OWNERS);
1691
1692        // In this test, change the caller user to "system".
1693        mContext.binder.callingUid = DpmMockContext.CALLER_SYSTEM_USER_UID;
1694
1695        // Make sure admin1 is installed on system user.
1696        setUpPackageManagerForAdmin(admin1, DpmMockContext.CALLER_SYSTEM_USER_UID);
1697
1698        // Set admin1 as DA.
1699        dpm.setActiveAdmin(admin1, false);
1700        assertTrue(dpm.isAdminActive(admin1));
1701        try {
1702            dpm.reboot(admin1);
1703            fail("DA calls DPM.reboot(), did not throw expected SecurityException");
1704        } catch (SecurityException expected) {
1705            MoreAsserts.assertContainsRegex("does not own the device", expected.getMessage());
1706        }
1707
1708        // Set admin1 as PO.
1709        assertTrue(dpm.setProfileOwner(admin1, null, UserHandle.USER_SYSTEM));
1710        try {
1711            dpm.reboot(admin1);
1712            fail("PO calls DPM.reboot(), did not throw expected SecurityException");
1713        } catch (SecurityException expected) {
1714            MoreAsserts.assertContainsRegex("does not own the device", expected.getMessage());
1715        }
1716
1717        // Remove PO and add DO.
1718        dpm.clearProfileOwner(admin1);
1719        dpm.setActiveAdmin(admin1, false);
1720        assertTrue(dpm.setDeviceOwner(admin1, null, UserHandle.USER_SYSTEM));
1721
1722        // admin1 is DO.
1723        // Set current call state of device to ringing.
1724        when(mContext.telephonyManager.getCallState())
1725                .thenReturn(TelephonyManager.CALL_STATE_RINGING);
1726        try {
1727            dpm.reboot(admin1);
1728            fail("DPM.reboot() called when receiveing a call, should thrown IllegalStateException");
1729        } catch (IllegalStateException expected) {
1730            MoreAsserts.assertContainsRegex("ongoing call on the device", expected.getMessage());
1731        }
1732
1733        // Set current call state of device to dialing/active.
1734        when(mContext.telephonyManager.getCallState())
1735                .thenReturn(TelephonyManager.CALL_STATE_OFFHOOK);
1736        try {
1737            dpm.reboot(admin1);
1738            fail("DPM.reboot() called when dialing, should thrown IllegalStateException");
1739        } catch (IllegalStateException expected) {
1740            MoreAsserts.assertContainsRegex("ongoing call on the device", expected.getMessage());
1741        }
1742
1743        // Set current call state of device to idle.
1744        when(mContext.telephonyManager.getCallState()).thenReturn(TelephonyManager.CALL_STATE_IDLE);
1745        dpm.reboot(admin1);
1746    }
1747
1748    public void testSetGetSupportText() {
1749        mContext.callerPermissions.add(permission.MANAGE_DEVICE_ADMINS);
1750        dpm.setActiveAdmin(admin1, true);
1751        dpm.setActiveAdmin(admin2, true);
1752        mContext.callerPermissions.remove(permission.MANAGE_DEVICE_ADMINS);
1753
1754        // Null default support messages.
1755        {
1756            assertNull(dpm.getLongSupportMessage(admin1));
1757            assertNull(dpm.getShortSupportMessage(admin1));
1758            mContext.binder.callingUid = DpmMockContext.SYSTEM_UID;
1759            assertNull(dpm.getShortSupportMessageForUser(admin1,
1760                    DpmMockContext.CALLER_USER_HANDLE));
1761            assertNull(dpm.getLongSupportMessageForUser(admin1,
1762                    DpmMockContext.CALLER_USER_HANDLE));
1763            mMockContext.binder.callingUid = DpmMockContext.CALLER_UID;
1764        }
1765
1766        // Only system can call the per user versions.
1767        {
1768            try {
1769                dpm.getShortSupportMessageForUser(admin1,
1770                        DpmMockContext.CALLER_USER_HANDLE);
1771                fail("Only system should be able to call getXXXForUser versions");
1772            } catch (SecurityException expected) {
1773                MoreAsserts.assertContainsRegex("message for user", expected.getMessage());
1774            }
1775            try {
1776                dpm.getLongSupportMessageForUser(admin1,
1777                        DpmMockContext.CALLER_USER_HANDLE);
1778                fail("Only system should be able to call getXXXForUser versions");
1779            } catch (SecurityException expected) {
1780                MoreAsserts.assertContainsRegex("message for user", expected.getMessage());
1781            }
1782        }
1783
1784        // Can't set message for admin in another uid.
1785        {
1786            mContext.binder.callingUid = DpmMockContext.CALLER_UID + 1;
1787            try {
1788                dpm.setShortSupportMessage(admin1, "Some text");
1789                fail("Admins should only be able to change their own support text.");
1790            } catch (SecurityException expected) {
1791                MoreAsserts.assertContainsRegex("is not owned by uid", expected.getMessage());
1792            }
1793            mContext.binder.callingUid = DpmMockContext.CALLER_UID;
1794        }
1795
1796        // Set/Get short returns what it sets and other admins text isn't changed.
1797        {
1798            final String supportText = "Some text to test with.";
1799            dpm.setShortSupportMessage(admin1, supportText);
1800            assertEquals(supportText, dpm.getShortSupportMessage(admin1));
1801            assertNull(dpm.getLongSupportMessage(admin1));
1802            assertNull(dpm.getShortSupportMessage(admin2));
1803
1804            mContext.binder.callingUid = DpmMockContext.SYSTEM_UID;
1805            assertEquals(supportText, dpm.getShortSupportMessageForUser(admin1,
1806                    DpmMockContext.CALLER_USER_HANDLE));
1807            assertNull(dpm.getShortSupportMessageForUser(admin2,
1808                    DpmMockContext.CALLER_USER_HANDLE));
1809            assertNull(dpm.getLongSupportMessageForUser(admin1,
1810                    DpmMockContext.CALLER_USER_HANDLE));
1811            mMockContext.binder.callingUid = DpmMockContext.CALLER_UID;
1812
1813            dpm.setShortSupportMessage(admin1, null);
1814            assertNull(dpm.getShortSupportMessage(admin1));
1815        }
1816
1817        // Set/Get long returns what it sets and other admins text isn't changed.
1818        {
1819            final String supportText = "Some text to test with.\nWith more text.";
1820            dpm.setLongSupportMessage(admin1, supportText);
1821            assertEquals(supportText, dpm.getLongSupportMessage(admin1));
1822            assertNull(dpm.getShortSupportMessage(admin1));
1823            assertNull(dpm.getLongSupportMessage(admin2));
1824
1825            mContext.binder.callingUid = DpmMockContext.SYSTEM_UID;
1826            assertEquals(supportText, dpm.getLongSupportMessageForUser(admin1,
1827                    DpmMockContext.CALLER_USER_HANDLE));
1828            assertNull(dpm.getLongSupportMessageForUser(admin2,
1829                    DpmMockContext.CALLER_USER_HANDLE));
1830            assertNull(dpm.getShortSupportMessageForUser(admin1,
1831                    DpmMockContext.CALLER_USER_HANDLE));
1832            mMockContext.binder.callingUid = DpmMockContext.CALLER_UID;
1833
1834            dpm.setLongSupportMessage(admin1, null);
1835            assertNull(dpm.getLongSupportMessage(admin1));
1836        }
1837    }
1838
1839    /**
1840     * Test for:
1841     * {@link DevicePolicyManager#setAffiliationIds}
1842     * {@link DevicePolicyManager#getAffiliationIds}
1843     * {@link DevicePolicyManager#isAffiliatedUser}
1844     */
1845    public void testUserAffiliation() throws Exception {
1846        mContext.callerPermissions.add(permission.MANAGE_DEVICE_ADMINS);
1847        mContext.callerPermissions.add(permission.MANAGE_PROFILE_AND_DEVICE_OWNERS);
1848        mContext.callerPermissions.add(permission.INTERACT_ACROSS_USERS_FULL);
1849
1850        // Check that the system user is unaffiliated.
1851        mContext.binder.callingUid = DpmMockContext.CALLER_SYSTEM_USER_UID;
1852        assertFalse(dpm.isAffiliatedUser());
1853
1854        // Set a device owner on the system user. Check that the system user becomes affiliated.
1855        setUpPackageManagerForAdmin(admin1, DpmMockContext.CALLER_SYSTEM_USER_UID);
1856        dpm.setActiveAdmin(admin1, /* replace =*/ false);
1857        assertTrue(dpm.setDeviceOwner(admin1, "owner-name"));
1858        assertTrue(dpm.isAffiliatedUser());
1859        assertTrue(dpm.getAffiliationIds(admin1).isEmpty());
1860
1861        // Install a profile owner. Check that the test user is unaffiliated.
1862        mContext.binder.callingUid = DpmMockContext.CALLER_UID;
1863        setAsProfileOwner(admin2);
1864        assertFalse(dpm.isAffiliatedUser());
1865        assertTrue(dpm.getAffiliationIds(admin2).isEmpty());
1866
1867        // Have the profile owner specify a set of affiliation ids. Check that the test user remains
1868        // unaffiliated.
1869        final List<String> userAffiliationIds = new ArrayList<>();
1870        userAffiliationIds.add("red");
1871        userAffiliationIds.add("green");
1872        userAffiliationIds.add("blue");
1873        dpm.setAffiliationIds(admin2, userAffiliationIds);
1874        MoreAsserts.assertContentsInAnyOrder(dpm.getAffiliationIds(admin2), "red", "green", "blue");
1875        assertFalse(dpm.isAffiliatedUser());
1876
1877        // Have the device owner specify a set of affiliation ids that do not intersect with those
1878        // specified by the profile owner. Check that the test user remains unaffiliated.
1879        final List<String> deviceAffiliationIds = new ArrayList<>();
1880        deviceAffiliationIds.add("cyan");
1881        deviceAffiliationIds.add("yellow");
1882        deviceAffiliationIds.add("magenta");
1883        mContext.binder.callingUid = DpmMockContext.CALLER_SYSTEM_USER_UID;
1884        dpm.setAffiliationIds(admin1, deviceAffiliationIds);
1885        MoreAsserts.assertContentsInAnyOrder(
1886            dpm.getAffiliationIds(admin1), "cyan", "yellow", "magenta");
1887        mContext.binder.callingUid = DpmMockContext.CALLER_UID;
1888        assertFalse(dpm.isAffiliatedUser());
1889
1890        // Have the profile owner specify a set of affiliation ids that intersect with those
1891        // specified by the device owner. Check that the test user becomes affiliated.
1892        userAffiliationIds.add("yellow");
1893        dpm.setAffiliationIds(admin2, userAffiliationIds);
1894        MoreAsserts.assertContentsInAnyOrder(
1895            dpm.getAffiliationIds(admin2), "red", "green", "blue", "yellow");
1896        assertTrue(dpm.isAffiliatedUser());
1897
1898        // Clear affiliation ids for the profile owner. The user becomes unaffiliated.
1899        dpm.setAffiliationIds(admin2, Collections.emptyList());
1900        assertTrue(dpm.getAffiliationIds(admin2).isEmpty());
1901        assertFalse(dpm.isAffiliatedUser());
1902
1903        // Check that the system user remains affiliated.
1904        mContext.binder.callingUid = DpmMockContext.CALLER_SYSTEM_USER_UID;
1905        assertTrue(dpm.isAffiliatedUser());
1906    }
1907
1908    public void testGetUserProvisioningState_defaultResult() {
1909        assertEquals(DevicePolicyManager.STATE_USER_UNMANAGED, dpm.getUserProvisioningState());
1910    }
1911
1912    public void testSetUserProvisioningState_permission() throws Exception {
1913        setupProfileOwner();
1914        mContext.callerPermissions.add(permission.MANAGE_PROFILE_AND_DEVICE_OWNERS);
1915
1916        exerciseUserProvisioningTransitions(DpmMockContext.CALLER_USER_HANDLE,
1917                DevicePolicyManager.STATE_USER_SETUP_FINALIZED);
1918    }
1919
1920    public void testSetUserProvisioningState_unprivileged() throws Exception {
1921        setupProfileOwner();
1922        try {
1923            dpm.setUserProvisioningState(DevicePolicyManager.STATE_USER_SETUP_FINALIZED,
1924                    DpmMockContext.CALLER_USER_HANDLE);
1925            fail("Expected SecurityException");
1926        } catch (SecurityException expected) {
1927        }
1928    }
1929
1930    public void testSetUserProvisioningState_noManagement() {
1931        mContext.callerPermissions.add(permission.MANAGE_PROFILE_AND_DEVICE_OWNERS);
1932        try {
1933            dpm.setUserProvisioningState(DevicePolicyManager.STATE_USER_SETUP_FINALIZED,
1934                    DpmMockContext.CALLER_USER_HANDLE);
1935            fail("IllegalStateException expected");
1936        } catch (IllegalStateException e) {
1937            MoreAsserts.assertContainsRegex("change provisioning state unless a .* owner is set",
1938                    e.getMessage());
1939        }
1940        assertEquals(DevicePolicyManager.STATE_USER_UNMANAGED, dpm.getUserProvisioningState());
1941    }
1942
1943    public void testSetUserProvisioningState_deviceOwnerFromSetupWizard() throws Exception {
1944        mContext.binder.callingUid = DpmMockContext.CALLER_SYSTEM_USER_UID;
1945        setupDeviceOwner();
1946        mContext.callerPermissions.add(permission.MANAGE_PROFILE_AND_DEVICE_OWNERS);
1947
1948        exerciseUserProvisioningTransitions(UserHandle.USER_SYSTEM,
1949                DevicePolicyManager.STATE_USER_SETUP_COMPLETE,
1950                DevicePolicyManager.STATE_USER_SETUP_FINALIZED);
1951    }
1952
1953    public void testSetUserProvisioningState_deviceOwnerFromSetupWizardAlternative()
1954            throws Exception {
1955        mContext.binder.callingUid = DpmMockContext.CALLER_SYSTEM_USER_UID;
1956        setupDeviceOwner();
1957        mContext.callerPermissions.add(permission.MANAGE_PROFILE_AND_DEVICE_OWNERS);
1958
1959        exerciseUserProvisioningTransitions(UserHandle.USER_SYSTEM,
1960                DevicePolicyManager.STATE_USER_SETUP_INCOMPLETE,
1961                DevicePolicyManager.STATE_USER_SETUP_FINALIZED);
1962    }
1963
1964    public void testSetUserProvisioningState_deviceOwnerWithoutSetupWizard() throws Exception {
1965        mContext.binder.callingUid = DpmMockContext.CALLER_SYSTEM_USER_UID;
1966        setupDeviceOwner();
1967        mContext.callerPermissions.add(permission.MANAGE_PROFILE_AND_DEVICE_OWNERS);
1968
1969        exerciseUserProvisioningTransitions(UserHandle.USER_SYSTEM,
1970                DevicePolicyManager.STATE_USER_SETUP_FINALIZED);
1971    }
1972
1973    public void testSetUserProvisioningState_managedProfileFromSetupWizard_primaryUser()
1974            throws Exception {
1975        setupProfileOwner();
1976        mContext.callerPermissions.add(permission.MANAGE_PROFILE_AND_DEVICE_OWNERS);
1977
1978        exerciseUserProvisioningTransitions(DpmMockContext.CALLER_USER_HANDLE,
1979                DevicePolicyManager.STATE_USER_PROFILE_COMPLETE,
1980                DevicePolicyManager.STATE_USER_UNMANAGED);
1981    }
1982
1983    public void testSetUserProvisioningState_managedProfileFromSetupWizard_managedProfile()
1984            throws Exception {
1985        setupProfileOwner();
1986        mContext.callerPermissions.add(permission.MANAGE_PROFILE_AND_DEVICE_OWNERS);
1987
1988        exerciseUserProvisioningTransitions(DpmMockContext.CALLER_USER_HANDLE,
1989                DevicePolicyManager.STATE_USER_SETUP_COMPLETE,
1990                DevicePolicyManager.STATE_USER_SETUP_FINALIZED);
1991    }
1992
1993    public void testSetUserProvisioningState_managedProfileWithoutSetupWizard() throws Exception {
1994        setupProfileOwner();
1995        mContext.callerPermissions.add(permission.MANAGE_PROFILE_AND_DEVICE_OWNERS);
1996
1997        exerciseUserProvisioningTransitions(DpmMockContext.CALLER_USER_HANDLE,
1998                DevicePolicyManager.STATE_USER_SETUP_FINALIZED);
1999    }
2000
2001    public void testSetUserProvisioningState_illegalTransitionOutOfFinalized1() throws Exception {
2002        setupProfileOwner();
2003        mContext.callerPermissions.add(permission.MANAGE_PROFILE_AND_DEVICE_OWNERS);
2004
2005        try {
2006            exerciseUserProvisioningTransitions(DpmMockContext.CALLER_USER_HANDLE,
2007                    DevicePolicyManager.STATE_USER_SETUP_FINALIZED,
2008                    DevicePolicyManager.STATE_USER_UNMANAGED);
2009            fail("Expected IllegalStateException");
2010        } catch (IllegalStateException e) {
2011            MoreAsserts.assertContainsRegex("Cannot move to user provisioning state",
2012                    e.getMessage());
2013        }
2014    }
2015
2016    public void testSetUserProvisioningState_illegalTransitionToAnotherInProgressState()
2017            throws Exception {
2018        setupProfileOwner();
2019        mContext.callerPermissions.add(permission.MANAGE_PROFILE_AND_DEVICE_OWNERS);
2020
2021        try {
2022            exerciseUserProvisioningTransitions(DpmMockContext.CALLER_USER_HANDLE,
2023                    DevicePolicyManager.STATE_USER_SETUP_INCOMPLETE,
2024                    DevicePolicyManager.STATE_USER_SETUP_COMPLETE);
2025            fail("Expected IllegalStateException");
2026        } catch (IllegalStateException e) {
2027            MoreAsserts.assertContainsRegex("Cannot move to user provisioning state",
2028                    e.getMessage());
2029        }
2030    }
2031
2032    private void exerciseUserProvisioningTransitions(int userId, int... states) {
2033        assertEquals(DevicePolicyManager.STATE_USER_UNMANAGED, dpm.getUserProvisioningState());
2034        for (int state : states) {
2035            dpm.setUserProvisioningState(state, userId);
2036            assertEquals(state, dpm.getUserProvisioningState());
2037        }
2038    }
2039
2040    private void setupProfileOwner() throws Exception {
2041        mContext.callerPermissions.addAll(OWNER_SETUP_PERMISSIONS);
2042
2043        setUpPackageManagerForAdmin(admin1, DpmMockContext.CALLER_UID);
2044        dpm.setActiveAdmin(admin1, false);
2045        assertTrue(dpm.setProfileOwner(admin1, null, DpmMockContext.CALLER_USER_HANDLE));
2046
2047        mContext.callerPermissions.removeAll(OWNER_SETUP_PERMISSIONS);
2048    }
2049
2050    private void setupDeviceOwner() throws Exception {
2051        mContext.callerPermissions.addAll(OWNER_SETUP_PERMISSIONS);
2052
2053        setUpPackageManagerForAdmin(admin1, DpmMockContext.CALLER_SYSTEM_USER_UID);
2054        dpm.setActiveAdmin(admin1, false);
2055        assertTrue(dpm.setDeviceOwner(admin1, null, UserHandle.USER_SYSTEM));
2056
2057        mContext.callerPermissions.removeAll(OWNER_SETUP_PERMISSIONS);
2058    }
2059
2060    public void testSetMaximumTimeToLock() {
2061        mContext.callerPermissions.add(android.Manifest.permission.MANAGE_DEVICE_ADMINS);
2062
2063        dpm.setActiveAdmin(admin1, /* replace =*/ false);
2064        dpm.setActiveAdmin(admin2, /* replace =*/ false);
2065
2066        reset(mMockContext.powerManagerInternal);
2067        reset(mMockContext.settings);
2068
2069        dpm.setMaximumTimeToLock(admin1, 0);
2070        verifyScreenTimeoutCall(null, false);
2071        reset(mMockContext.powerManagerInternal);
2072        reset(mMockContext.settings);
2073
2074        dpm.setMaximumTimeToLock(admin1, 1);
2075        verifyScreenTimeoutCall(1, true);
2076        reset(mMockContext.powerManagerInternal);
2077        reset(mMockContext.settings);
2078
2079        dpm.setMaximumTimeToLock(admin2, 10);
2080        verifyScreenTimeoutCall(null, false);
2081        reset(mMockContext.powerManagerInternal);
2082        reset(mMockContext.settings);
2083
2084        dpm.setMaximumTimeToLock(admin1, 5);
2085        verifyScreenTimeoutCall(5, true);
2086        reset(mMockContext.powerManagerInternal);
2087        reset(mMockContext.settings);
2088
2089        dpm.setMaximumTimeToLock(admin2, 4);
2090        verifyScreenTimeoutCall(4, true);
2091        reset(mMockContext.powerManagerInternal);
2092        reset(mMockContext.settings);
2093
2094        dpm.setMaximumTimeToLock(admin1, 0);
2095        reset(mMockContext.powerManagerInternal);
2096        reset(mMockContext.settings);
2097
2098        dpm.setMaximumTimeToLock(admin2, Integer.MAX_VALUE);
2099        verifyScreenTimeoutCall(Integer.MAX_VALUE, true);
2100        reset(mMockContext.powerManagerInternal);
2101        reset(mMockContext.settings);
2102
2103        dpm.setMaximumTimeToLock(admin2, Integer.MAX_VALUE + 1);
2104        verifyScreenTimeoutCall(Integer.MAX_VALUE, true);
2105        reset(mMockContext.powerManagerInternal);
2106        reset(mMockContext.settings);
2107
2108        dpm.setMaximumTimeToLock(admin2, 10);
2109        verifyScreenTimeoutCall(10, true);
2110        reset(mMockContext.powerManagerInternal);
2111        reset(mMockContext.settings);
2112
2113        // There's no restriction; shold be set to MAX.
2114        dpm.setMaximumTimeToLock(admin2, 0);
2115        verifyScreenTimeoutCall(Integer.MAX_VALUE, false);
2116    }
2117
2118    public void testSetRequiredStrongAuthTimeout_DeviceOwner() throws Exception {
2119        mContext.binder.callingUid = DpmMockContext.CALLER_SYSTEM_USER_UID;
2120        setupDeviceOwner();
2121        mContext.callerPermissions.add(permission.MANAGE_PROFILE_AND_DEVICE_OWNERS);
2122
2123        final long MINIMUM_STRONG_AUTH_TIMEOUT_MS = TimeUnit.HOURS.toMillis(1);
2124        final long ONE_MINUTE = TimeUnit.MINUTES.toMillis(1);
2125        final long MIN_PLUS_ONE_MINUTE = MINIMUM_STRONG_AUTH_TIMEOUT_MS + ONE_MINUTE;
2126        final long MAX_MINUS_ONE_MINUTE = DevicePolicyManager.DEFAULT_STRONG_AUTH_TIMEOUT_MS
2127                - ONE_MINUTE;
2128
2129        // verify that the minimum timeout cannot be modified on user builds (system property is
2130        // not being read)
2131        mContext.buildMock.isDebuggable = false;
2132
2133        dpm.setRequiredStrongAuthTimeout(admin1, MAX_MINUS_ONE_MINUTE);
2134        assertEquals(dpm.getRequiredStrongAuthTimeout(admin1), MAX_MINUS_ONE_MINUTE);
2135        assertEquals(dpm.getRequiredStrongAuthTimeout(null), MAX_MINUS_ONE_MINUTE);
2136
2137        verify(mContext.systemProperties, never()).getLong(anyString(), anyLong());
2138
2139        // restore to the debuggable build state
2140        mContext.buildMock.isDebuggable = true;
2141
2142        // Always return the default (second arg) when getting system property for long type
2143        when(mContext.systemProperties.getLong(anyString(), anyLong())).thenAnswer(
2144                new Answer<Long>() {
2145                    @Override
2146                    public Long answer(InvocationOnMock invocation) throws Throwable {
2147                        return (Long) invocation.getArguments()[1];
2148                    }
2149                }
2150        );
2151
2152        // reset to default (0 means the admin is not participating, so default should be returned)
2153        dpm.setRequiredStrongAuthTimeout(admin1, 0);
2154
2155        // aggregation should be the default if unset by any admin
2156        assertEquals(dpm.getRequiredStrongAuthTimeout(null),
2157                DevicePolicyManager.DEFAULT_STRONG_AUTH_TIMEOUT_MS);
2158
2159        // admin not participating by default
2160        assertEquals(dpm.getRequiredStrongAuthTimeout(admin1), 0);
2161
2162        //clamping from the top
2163        dpm.setRequiredStrongAuthTimeout(admin1,
2164                DevicePolicyManager.DEFAULT_STRONG_AUTH_TIMEOUT_MS + ONE_MINUTE);
2165        assertEquals(dpm.getRequiredStrongAuthTimeout(admin1),
2166                DevicePolicyManager.DEFAULT_STRONG_AUTH_TIMEOUT_MS);
2167        assertEquals(dpm.getRequiredStrongAuthTimeout(null),
2168                DevicePolicyManager.DEFAULT_STRONG_AUTH_TIMEOUT_MS);
2169
2170        // 0 means the admin is not participating, so default should be returned
2171        dpm.setRequiredStrongAuthTimeout(admin1, 0);
2172        assertEquals(dpm.getRequiredStrongAuthTimeout(admin1), 0);
2173        assertEquals(dpm.getRequiredStrongAuthTimeout(null),
2174                DevicePolicyManager.DEFAULT_STRONG_AUTH_TIMEOUT_MS);
2175
2176        // clamping from the bottom
2177        dpm.setRequiredStrongAuthTimeout(admin1, MINIMUM_STRONG_AUTH_TIMEOUT_MS - ONE_MINUTE);
2178        assertEquals(dpm.getRequiredStrongAuthTimeout(admin1), MINIMUM_STRONG_AUTH_TIMEOUT_MS);
2179        assertEquals(dpm.getRequiredStrongAuthTimeout(null), MINIMUM_STRONG_AUTH_TIMEOUT_MS);
2180
2181        // values within range
2182        dpm.setRequiredStrongAuthTimeout(admin1, MIN_PLUS_ONE_MINUTE);
2183        assertEquals(dpm.getRequiredStrongAuthTimeout(admin1), MIN_PLUS_ONE_MINUTE);
2184        assertEquals(dpm.getRequiredStrongAuthTimeout(null), MIN_PLUS_ONE_MINUTE);
2185
2186        dpm.setRequiredStrongAuthTimeout(admin1, MAX_MINUS_ONE_MINUTE);
2187        assertEquals(dpm.getRequiredStrongAuthTimeout(admin1), MAX_MINUS_ONE_MINUTE);
2188        assertEquals(dpm.getRequiredStrongAuthTimeout(null), MAX_MINUS_ONE_MINUTE);
2189
2190        // reset to default
2191        dpm.setRequiredStrongAuthTimeout(admin1, 0);
2192        assertEquals(dpm.getRequiredStrongAuthTimeout(admin1), 0);
2193        assertEquals(dpm.getRequiredStrongAuthTimeout(null),
2194                DevicePolicyManager.DEFAULT_STRONG_AUTH_TIMEOUT_MS);
2195
2196        // negative value
2197        try {
2198            dpm.setRequiredStrongAuthTimeout(admin1, -ONE_MINUTE);
2199            fail("Didn't throw IllegalArgumentException");
2200        } catch (IllegalArgumentException iae) {
2201        }
2202    }
2203
2204    private void verifyScreenTimeoutCall(Integer expectedTimeout,
2205            boolean shouldStayOnWhilePluggedInBeCleared) {
2206        if (expectedTimeout == null) {
2207            verify(mMockContext.powerManagerInternal, times(0))
2208                    .setMaximumScreenOffTimeoutFromDeviceAdmin(anyInt());
2209        } else {
2210            verify(mMockContext.powerManagerInternal, times(1))
2211                    .setMaximumScreenOffTimeoutFromDeviceAdmin(eq(expectedTimeout));
2212        }
2213        // TODO Verify calls to settingsGlobalPutInt.  Tried but somehow mockito threw
2214        // UnfinishedVerificationException.
2215    }
2216
2217    private void setup_DeviceAdminFeatureOff() throws Exception {
2218        when(mContext.packageManager.hasSystemFeature(PackageManager.FEATURE_DEVICE_ADMIN))
2219                .thenReturn(false);
2220        when(mContext.ipackageManager.hasSystemFeature(PackageManager.FEATURE_MANAGED_USERS, 0))
2221                .thenReturn(false);
2222        initializeDpms();
2223        when(mContext.userManagerForMock.isSplitSystemUser()).thenReturn(false);
2224        when(mContext.userManager.canAddMoreManagedProfiles(UserHandle.USER_SYSTEM, true))
2225                .thenReturn(true);
2226        setUserSetupCompleteForUser(false, UserHandle.USER_SYSTEM);
2227
2228        mContext.binder.callingUid = DpmMockContext.CALLER_SYSTEM_USER_UID;
2229    }
2230
2231    public void testIsProvisioningAllowed_DeviceAdminFeatureOff() throws Exception {
2232        setup_DeviceAdminFeatureOff();
2233        mContext.packageName = admin1.getPackageName();
2234        setUpPackageManagerForAdmin(admin1, mContext.binder.callingUid);
2235        assertProvisioningAllowed(DevicePolicyManager.ACTION_PROVISION_MANAGED_DEVICE, false);
2236        assertProvisioningAllowed(DevicePolicyManager.ACTION_PROVISION_MANAGED_PROFILE, false);
2237        assertProvisioningAllowed(DevicePolicyManager.ACTION_PROVISION_MANAGED_SHAREABLE_DEVICE,
2238                false);
2239        assertProvisioningAllowed(DevicePolicyManager.ACTION_PROVISION_MANAGED_USER, false);
2240    }
2241
2242    public void testCheckProvisioningPreCondition_DeviceAdminFeatureOff() throws Exception {
2243        setup_DeviceAdminFeatureOff();
2244        mContext.callerPermissions.add(permission.MANAGE_PROFILE_AND_DEVICE_OWNERS);
2245        assertCheckProvisioningPreCondition(DevicePolicyManager.ACTION_PROVISION_MANAGED_DEVICE,
2246                DevicePolicyManager.CODE_DEVICE_ADMIN_NOT_SUPPORTED);
2247        assertCheckProvisioningPreCondition(DevicePolicyManager.ACTION_PROVISION_MANAGED_PROFILE,
2248                DevicePolicyManager.CODE_DEVICE_ADMIN_NOT_SUPPORTED);
2249        assertCheckProvisioningPreCondition(
2250                DevicePolicyManager.ACTION_PROVISION_MANAGED_SHAREABLE_DEVICE,
2251                DevicePolicyManager.CODE_DEVICE_ADMIN_NOT_SUPPORTED);
2252        assertCheckProvisioningPreCondition(DevicePolicyManager.ACTION_PROVISION_MANAGED_USER,
2253                DevicePolicyManager.CODE_DEVICE_ADMIN_NOT_SUPPORTED);
2254    }
2255
2256    private void setup_ManagedProfileFeatureOff() throws Exception {
2257        when(mContext.ipackageManager.hasSystemFeature(PackageManager.FEATURE_MANAGED_USERS, 0))
2258                .thenReturn(false);
2259        initializeDpms();
2260        when(mContext.userManagerForMock.isSplitSystemUser()).thenReturn(false);
2261        when(mContext.userManager.canAddMoreManagedProfiles(UserHandle.USER_SYSTEM, true))
2262                .thenReturn(true);
2263        setUserSetupCompleteForUser(false, UserHandle.USER_SYSTEM);
2264
2265        mContext.binder.callingUid = DpmMockContext.CALLER_SYSTEM_USER_UID;
2266    }
2267
2268    public void testIsProvisioningAllowed_ManagedProfileFeatureOff() throws Exception {
2269        setup_ManagedProfileFeatureOff();
2270        mContext.packageName = admin1.getPackageName();
2271        setUpPackageManagerForAdmin(admin1, mContext.binder.callingUid);
2272        assertProvisioningAllowed(DevicePolicyManager.ACTION_PROVISION_MANAGED_DEVICE, true);
2273        assertProvisioningAllowed(DevicePolicyManager.ACTION_PROVISION_MANAGED_PROFILE, false);
2274        assertProvisioningAllowed(DevicePolicyManager.ACTION_PROVISION_MANAGED_SHAREABLE_DEVICE,
2275                false);
2276        assertProvisioningAllowed(DevicePolicyManager.ACTION_PROVISION_MANAGED_USER, false);
2277
2278        // Test again when split user is on
2279        when(mContext.userManagerForMock.isSplitSystemUser()).thenReturn(true);
2280        assertProvisioningAllowed(DevicePolicyManager.ACTION_PROVISION_MANAGED_DEVICE, true);
2281        assertProvisioningAllowed(DevicePolicyManager.ACTION_PROVISION_MANAGED_PROFILE, false);
2282        assertProvisioningAllowed(DevicePolicyManager.ACTION_PROVISION_MANAGED_SHAREABLE_DEVICE,
2283                true);
2284        assertProvisioningAllowed(DevicePolicyManager.ACTION_PROVISION_MANAGED_USER, false);
2285    }
2286
2287    public void testCheckProvisioningPreCondition_ManagedProfileFeatureOff() throws Exception {
2288        setup_ManagedProfileFeatureOff();
2289        mContext.callerPermissions.add(permission.MANAGE_PROFILE_AND_DEVICE_OWNERS);
2290        assertCheckProvisioningPreCondition(DevicePolicyManager.ACTION_PROVISION_MANAGED_DEVICE,
2291                DevicePolicyManager.CODE_OK);
2292        assertCheckProvisioningPreCondition(DevicePolicyManager.ACTION_PROVISION_MANAGED_PROFILE,
2293                DevicePolicyManager.CODE_MANAGED_USERS_NOT_SUPPORTED);
2294        assertCheckProvisioningPreCondition(
2295                DevicePolicyManager.ACTION_PROVISION_MANAGED_SHAREABLE_DEVICE,
2296                DevicePolicyManager.CODE_NOT_SYSTEM_USER_SPLIT);
2297        assertCheckProvisioningPreCondition(DevicePolicyManager.ACTION_PROVISION_MANAGED_USER,
2298                DevicePolicyManager.CODE_MANAGED_USERS_NOT_SUPPORTED);
2299
2300        // Test again when split user is on
2301        when(mContext.userManagerForMock.isSplitSystemUser()).thenReturn(true);
2302        assertCheckProvisioningPreCondition(DevicePolicyManager.ACTION_PROVISION_MANAGED_DEVICE,
2303                DevicePolicyManager.CODE_OK);
2304        assertCheckProvisioningPreCondition(DevicePolicyManager.ACTION_PROVISION_MANAGED_PROFILE,
2305                DevicePolicyManager.CODE_MANAGED_USERS_NOT_SUPPORTED);
2306        assertCheckProvisioningPreCondition(
2307                DevicePolicyManager.ACTION_PROVISION_MANAGED_SHAREABLE_DEVICE,
2308                DevicePolicyManager.CODE_OK);
2309        assertCheckProvisioningPreCondition(DevicePolicyManager.ACTION_PROVISION_MANAGED_USER,
2310                DevicePolicyManager.CODE_MANAGED_USERS_NOT_SUPPORTED);
2311    }
2312
2313    private void setup_nonSplitUser_firstBoot_primaryUser() throws Exception {
2314        when(mContext.ipackageManager.hasSystemFeature(PackageManager.FEATURE_MANAGED_USERS, 0))
2315                .thenReturn(true);
2316        when(mContext.userManagerForMock.isSplitSystemUser()).thenReturn(false);
2317        when(mContext.userManager.canAddMoreManagedProfiles(UserHandle.USER_SYSTEM, true))
2318                .thenReturn(true);
2319        setUserSetupCompleteForUser(false, UserHandle.USER_SYSTEM);
2320
2321        mContext.binder.callingUid = DpmMockContext.CALLER_SYSTEM_USER_UID;
2322    }
2323
2324    public void testIsProvisioningAllowed_nonSplitUser_firstBoot_primaryUser() throws Exception {
2325        setup_nonSplitUser_firstBoot_primaryUser();
2326        mContext.packageName = admin1.getPackageName();
2327        setUpPackageManagerForAdmin(admin1, mContext.binder.callingUid);
2328        assertProvisioningAllowed(DevicePolicyManager.ACTION_PROVISION_MANAGED_DEVICE, true);
2329        assertProvisioningAllowed(DevicePolicyManager.ACTION_PROVISION_MANAGED_PROFILE, true);
2330        assertProvisioningAllowed(DevicePolicyManager.ACTION_PROVISION_MANAGED_SHAREABLE_DEVICE,
2331                false /* because of non-split user */);
2332        assertProvisioningAllowed(DevicePolicyManager.ACTION_PROVISION_MANAGED_USER,
2333                false /* because of non-split user */);
2334    }
2335
2336    public void testCheckProvisioningPreCondition_nonSplitUser_firstBoot_primaryUser()
2337            throws Exception {
2338        setup_nonSplitUser_firstBoot_primaryUser();
2339        mContext.callerPermissions.add(permission.MANAGE_PROFILE_AND_DEVICE_OWNERS);
2340        assertCheckProvisioningPreCondition(DevicePolicyManager.ACTION_PROVISION_MANAGED_DEVICE,
2341                DevicePolicyManager.CODE_OK);
2342        assertCheckProvisioningPreCondition(DevicePolicyManager.ACTION_PROVISION_MANAGED_PROFILE,
2343                DevicePolicyManager.CODE_OK);
2344        assertCheckProvisioningPreCondition(
2345                DevicePolicyManager.ACTION_PROVISION_MANAGED_SHAREABLE_DEVICE,
2346                DevicePolicyManager.CODE_NOT_SYSTEM_USER_SPLIT);
2347        assertCheckProvisioningPreCondition(DevicePolicyManager.ACTION_PROVISION_MANAGED_USER,
2348                DevicePolicyManager.CODE_NOT_SYSTEM_USER_SPLIT);
2349    }
2350
2351    private void setup_nonSplitUser_afterDeviceSetup_primaryUser() throws Exception {
2352        when(mContext.ipackageManager.hasSystemFeature(PackageManager.FEATURE_MANAGED_USERS, 0))
2353                .thenReturn(true);
2354        when(mContext.userManagerForMock.isSplitSystemUser()).thenReturn(false);
2355        when(mContext.userManager.canAddMoreManagedProfiles(UserHandle.USER_SYSTEM, true))
2356                .thenReturn(true);
2357        setUserSetupCompleteForUser(true, UserHandle.USER_SYSTEM);
2358
2359        mContext.binder.callingUid = DpmMockContext.CALLER_SYSTEM_USER_UID;
2360    }
2361
2362    public void testIsProvisioningAllowed_nonSplitUser_afterDeviceSetup_primaryUser()
2363            throws Exception {
2364        setup_nonSplitUser_afterDeviceSetup_primaryUser();
2365        mContext.packageName = admin1.getPackageName();
2366        setUpPackageManagerForAdmin(admin1, mContext.binder.callingUid);
2367        assertProvisioningAllowed(DevicePolicyManager.ACTION_PROVISION_MANAGED_DEVICE,
2368                false/* because of completed device setup */);
2369        assertProvisioningAllowed(DevicePolicyManager.ACTION_PROVISION_MANAGED_PROFILE, true);
2370        assertProvisioningAllowed(DevicePolicyManager.ACTION_PROVISION_MANAGED_SHAREABLE_DEVICE,
2371                false/* because of non-split user */);
2372        assertProvisioningAllowed(DevicePolicyManager.ACTION_PROVISION_MANAGED_USER,
2373                false/* because of non-split user */);
2374    }
2375
2376    public void testCheckProvisioningPreCondition_nonSplitUser_afterDeviceSetup_primaryUser()
2377            throws Exception {
2378        setup_nonSplitUser_afterDeviceSetup_primaryUser();
2379        mContext.callerPermissions.add(permission.MANAGE_PROFILE_AND_DEVICE_OWNERS);
2380        assertCheckProvisioningPreCondition(DevicePolicyManager.ACTION_PROVISION_MANAGED_DEVICE,
2381                DevicePolicyManager.CODE_USER_SETUP_COMPLETED);
2382        assertCheckProvisioningPreCondition(DevicePolicyManager.ACTION_PROVISION_MANAGED_PROFILE,
2383                DevicePolicyManager.CODE_OK);
2384        assertCheckProvisioningPreCondition(
2385                DevicePolicyManager.ACTION_PROVISION_MANAGED_SHAREABLE_DEVICE,
2386                DevicePolicyManager.CODE_NOT_SYSTEM_USER_SPLIT);
2387        assertCheckProvisioningPreCondition(DevicePolicyManager.ACTION_PROVISION_MANAGED_USER,
2388                DevicePolicyManager.CODE_NOT_SYSTEM_USER_SPLIT);
2389    }
2390
2391    public void testIsProvisioningAllowed_nonSplitUser_withDo_primaryUser() throws Exception {
2392        setDeviceOwner();
2393        setup_nonSplitUser_afterDeviceSetup_primaryUser();
2394        setUpPackageManagerForAdmin(admin1, mContext.binder.callingUid);
2395        mContext.packageName = admin1.getPackageName();
2396
2397        final ComponentName adminDifferentPackage =
2398                new ComponentName("another.package", "whatever.random.class");
2399        final int ANOTHER_UID = UserHandle.getUid(DpmMockContext.CALLER_USER_HANDLE, 948);
2400        setUpPackageManagerForFakeAdmin(adminDifferentPackage, ANOTHER_UID, admin2);
2401
2402        // COMP mode is allowed.
2403        assertProvisioningAllowed(DevicePolicyManager.ACTION_PROVISION_MANAGED_PROFILE, true);
2404
2405        when(mContext.userManager.hasUserRestriction(
2406                eq(UserManager.DISALLOW_ADD_MANAGED_PROFILE),
2407                eq(UserHandle.getUserHandleForUid(mContext.binder.callingUid))))
2408                .thenReturn(true);
2409
2410        // The DO should be allowed to initiate provisioning if it set the restriction itself.
2411        when(mContext.userManager.getUserRestrictionSource(
2412                eq(UserManager.DISALLOW_ADD_MANAGED_PROFILE),
2413                eq(UserHandle.getUserHandleForUid(mContext.binder.callingUid))))
2414                .thenReturn(UserManager.RESTRICTION_SOURCE_DEVICE_OWNER);
2415        assertProvisioningAllowed(DevicePolicyManager.ACTION_PROVISION_MANAGED_PROFILE, true);
2416
2417        // But another app should not
2418        mContext.binder.callingUid = ANOTHER_UID;
2419        mContext.packageName = adminDifferentPackage.getPackageName();
2420        assertProvisioningAllowed(DevicePolicyManager.ACTION_PROVISION_MANAGED_PROFILE, false);
2421
2422        // The DO should not be allowed to initiate provisioning if the restriction is set by
2423        // another entity.
2424        when(mContext.userManager.getUserRestrictionSource(
2425                eq(UserManager.DISALLOW_ADD_MANAGED_PROFILE),
2426                eq(UserHandle.getUserHandleForUid(mContext.binder.callingUid))))
2427                .thenReturn(UserManager.RESTRICTION_SOURCE_SYSTEM);
2428        mContext.binder.callingUid = DpmMockContext.CALLER_UID;
2429        mContext.packageName = admin1.getPackageName();
2430        assertProvisioningAllowed(DevicePolicyManager.ACTION_PROVISION_MANAGED_PROFILE, false);
2431
2432        mContext.binder.callingUid = ANOTHER_UID;
2433        mContext.packageName = adminDifferentPackage.getPackageName();
2434        assertProvisioningAllowed(DevicePolicyManager.ACTION_PROVISION_MANAGED_PROFILE, false);
2435    }
2436
2437    public void testIsProvisioningAllowed_nonSplitUser_comp() throws Exception {
2438        setDeviceOwner();
2439        setup_nonSplitUser_afterDeviceSetup_primaryUser();
2440        setUpPackageManagerForAdmin(admin1, DpmMockContext.CALLER_UID);
2441
2442        final ComponentName adminDifferentPackage =
2443                new ComponentName("another.package", "whatever.class");
2444        final int ANOTHER_UID = UserHandle.getUid(DpmMockContext.CALLER_USER_HANDLE, 948);
2445        setUpPackageManagerForFakeAdmin(adminDifferentPackage, ANOTHER_UID, admin2);
2446
2447        final int MANAGED_PROFILE_USER_ID = 18;
2448        final int MANAGED_PROFILE_ADMIN_UID = UserHandle.getUid(MANAGED_PROFILE_USER_ID, 1308);
2449        addManagedProfile(admin1, MANAGED_PROFILE_ADMIN_UID, admin1);
2450
2451        when(mContext.userManager.canAddMoreManagedProfiles(DpmMockContext.CALLER_USER_HANDLE,
2452                false /* we can't remove a managed profile */)).thenReturn(false);
2453        when(mContext.userManager.canAddMoreManagedProfiles(DpmMockContext.CALLER_USER_HANDLE,
2454                true)).thenReturn(true);
2455
2456        // We can delete the managed profile to create a new one, so provisioning is allowed.
2457        mContext.packageName = admin1.getPackageName();
2458        mContext.binder.callingUid = DpmMockContext.CALLER_UID;
2459        assertProvisioningAllowed(DevicePolicyManager.ACTION_PROVISION_MANAGED_PROFILE, true);
2460
2461        mContext.packageName = adminDifferentPackage.getPackageName();
2462        mContext.binder.callingUid = ANOTHER_UID;
2463        assertProvisioningAllowed(DevicePolicyManager.ACTION_PROVISION_MANAGED_PROFILE, true);
2464
2465        when(mContext.userManager.hasUserRestriction(
2466                eq(UserManager.DISALLOW_REMOVE_MANAGED_PROFILE),
2467                eq(UserHandle.of(DpmMockContext.CALLER_USER_HANDLE))))
2468                .thenReturn(true);
2469
2470        // Now, we can't remove the profile any more to create a new one.
2471        mContext.packageName = admin1.getPackageName();
2472        mContext.binder.callingUid = DpmMockContext.CALLER_UID;
2473        assertProvisioningAllowed(DevicePolicyManager.ACTION_PROVISION_MANAGED_PROFILE, false);
2474
2475        mContext.packageName = adminDifferentPackage.getPackageName();
2476        mContext.binder.callingUid = ANOTHER_UID;
2477        assertProvisioningAllowed(DevicePolicyManager.ACTION_PROVISION_MANAGED_PROFILE, false);
2478    }
2479
2480    public void
2481    testCheckProvisioningPreCondition_nonSplitUser_withDo_primaryUser() throws Exception {
2482        setDeviceOwner();
2483        setup_nonSplitUser_afterDeviceSetup_primaryUser();
2484        mContext.callerPermissions.add(permission.MANAGE_PROFILE_AND_DEVICE_OWNERS);
2485
2486        assertCheckProvisioningPreCondition(DevicePolicyManager.ACTION_PROVISION_MANAGED_DEVICE,
2487                DevicePolicyManager.CODE_HAS_DEVICE_OWNER);
2488
2489        // COMP mode is allowed.
2490        assertCheckProvisioningPreCondition(DevicePolicyManager.ACTION_PROVISION_MANAGED_PROFILE,
2491                DevicePolicyManager.CODE_OK);
2492
2493        // And other DPCs can also provisioning a managed profile (DO + BYOD case).
2494        assertCheckProvisioningPreCondition(
2495                DevicePolicyManager.ACTION_PROVISION_MANAGED_PROFILE,
2496                "some.other.dpc.package.name",
2497                DevicePolicyManager.CODE_OK);
2498
2499        when(mContext.userManager.hasUserRestriction(
2500                eq(UserManager.DISALLOW_ADD_MANAGED_PROFILE),
2501                eq(UserHandle.getUserHandleForUid(mContext.binder.callingUid))))
2502                .thenReturn(true);
2503
2504        // The DO should be allowed to initiate provisioning if it set the restriction itself, but
2505        // other packages should be forbidden.
2506        when(mContext.userManager.getUserRestrictionSource(
2507                eq(UserManager.DISALLOW_ADD_MANAGED_PROFILE),
2508                eq(UserHandle.getUserHandleForUid(mContext.binder.callingUid))))
2509                .thenReturn(UserManager.RESTRICTION_SOURCE_DEVICE_OWNER);
2510        assertCheckProvisioningPreCondition(DevicePolicyManager.ACTION_PROVISION_MANAGED_PROFILE,
2511                DevicePolicyManager.CODE_OK);
2512        assertCheckProvisioningPreCondition(
2513                DevicePolicyManager.ACTION_PROVISION_MANAGED_PROFILE,
2514                "some.other.dpc.package.name",
2515                DevicePolicyManager.CODE_ADD_MANAGED_PROFILE_DISALLOWED);
2516
2517        // The DO should not be allowed to initiate provisioning if the restriction is set by
2518        // another entity.
2519        when(mContext.userManager.getUserRestrictionSource(
2520                eq(UserManager.DISALLOW_ADD_MANAGED_PROFILE),
2521                eq(UserHandle.getUserHandleForUid(mContext.binder.callingUid))))
2522                .thenReturn(UserManager.RESTRICTION_SOURCE_SYSTEM);
2523        assertCheckProvisioningPreCondition(DevicePolicyManager.ACTION_PROVISION_MANAGED_PROFILE,
2524                DevicePolicyManager.CODE_ADD_MANAGED_PROFILE_DISALLOWED);
2525                assertCheckProvisioningPreCondition(
2526                DevicePolicyManager.ACTION_PROVISION_MANAGED_PROFILE,
2527                "some.other.dpc.package.name",
2528                DevicePolicyManager.CODE_ADD_MANAGED_PROFILE_DISALLOWED);
2529    }
2530
2531    private void setup_splitUser_firstBoot_systemUser() throws Exception {
2532        when(mContext.ipackageManager.hasSystemFeature(PackageManager.FEATURE_MANAGED_USERS, 0))
2533                .thenReturn(true);
2534        when(mContext.userManagerForMock.isSplitSystemUser()).thenReturn(true);
2535        when(mContext.userManager.canAddMoreManagedProfiles(UserHandle.USER_SYSTEM, true))
2536                .thenReturn(false);
2537        setUserSetupCompleteForUser(false, UserHandle.USER_SYSTEM);
2538
2539        mContext.binder.callingUid = DpmMockContext.CALLER_SYSTEM_USER_UID;
2540    }
2541
2542    public void testIsProvisioningAllowed_splitUser_firstBoot_systemUser() throws Exception {
2543        setup_splitUser_firstBoot_systemUser();
2544        mContext.packageName = admin1.getPackageName();
2545        setUpPackageManagerForAdmin(admin1, mContext.binder.callingUid);
2546        assertProvisioningAllowed(DevicePolicyManager.ACTION_PROVISION_MANAGED_DEVICE, true);
2547        assertProvisioningAllowed(DevicePolicyManager.ACTION_PROVISION_MANAGED_PROFILE,
2548                false /* because canAddMoreManagedProfiles returns false */);
2549        assertProvisioningAllowed(DevicePolicyManager.ACTION_PROVISION_MANAGED_SHAREABLE_DEVICE,
2550                true);
2551        assertProvisioningAllowed(DevicePolicyManager.ACTION_PROVISION_MANAGED_USER,
2552                false/* because calling uid is system user */);
2553    }
2554
2555    public void testCheckProvisioningPreCondition_splitUser_firstBoot_systemUser()
2556            throws Exception {
2557        setup_splitUser_firstBoot_systemUser();
2558        mContext.callerPermissions.add(permission.MANAGE_PROFILE_AND_DEVICE_OWNERS);
2559        assertCheckProvisioningPreCondition(DevicePolicyManager.ACTION_PROVISION_MANAGED_DEVICE,
2560                DevicePolicyManager.CODE_OK);
2561        assertCheckProvisioningPreCondition(DevicePolicyManager.ACTION_PROVISION_MANAGED_PROFILE,
2562                DevicePolicyManager.CODE_SPLIT_SYSTEM_USER_DEVICE_SYSTEM_USER);
2563        assertCheckProvisioningPreCondition(
2564                DevicePolicyManager.ACTION_PROVISION_MANAGED_SHAREABLE_DEVICE,
2565                DevicePolicyManager.CODE_OK);
2566        assertCheckProvisioningPreCondition(DevicePolicyManager.ACTION_PROVISION_MANAGED_USER,
2567                DevicePolicyManager.CODE_SYSTEM_USER);
2568    }
2569
2570    private void setup_splitUser_afterDeviceSetup_systemUser() throws Exception {
2571        when(mContext.ipackageManager.hasSystemFeature(PackageManager.FEATURE_MANAGED_USERS, 0))
2572                .thenReturn(true);
2573        when(mContext.userManagerForMock.isSplitSystemUser()).thenReturn(true);
2574        when(mContext.userManager.canAddMoreManagedProfiles(UserHandle.USER_SYSTEM, true))
2575                .thenReturn(false);
2576        setUserSetupCompleteForUser(true, UserHandle.USER_SYSTEM);
2577
2578        mContext.binder.callingUid = DpmMockContext.CALLER_SYSTEM_USER_UID;
2579    }
2580
2581    public void testIsProvisioningAllowed_splitUser_afterDeviceSetup_systemUser() throws Exception {
2582        setup_splitUser_afterDeviceSetup_systemUser();
2583        mContext.packageName = admin1.getPackageName();
2584        setUpPackageManagerForAdmin(admin1, mContext.binder.callingUid);
2585        assertProvisioningAllowed(DevicePolicyManager.ACTION_PROVISION_MANAGED_DEVICE,
2586                true/* it's undefined behavior. Can be changed into false in the future */);
2587        assertProvisioningAllowed(DevicePolicyManager.ACTION_PROVISION_MANAGED_PROFILE,
2588                false /* because canAddMoreManagedProfiles returns false */);
2589        assertProvisioningAllowed(DevicePolicyManager.ACTION_PROVISION_MANAGED_SHAREABLE_DEVICE,
2590                true/* it's undefined behavior. Can be changed into false in the future */);
2591        assertProvisioningAllowed(DevicePolicyManager.ACTION_PROVISION_MANAGED_USER,
2592                false/* because calling uid is system user */);
2593    }
2594
2595    public void testCheckProvisioningPreCondition_splitUser_afterDeviceSetup_systemUser()
2596            throws Exception {
2597        setup_splitUser_afterDeviceSetup_systemUser();
2598        mContext.callerPermissions.add(permission.MANAGE_PROFILE_AND_DEVICE_OWNERS);
2599        assertCheckProvisioningPreCondition(DevicePolicyManager.ACTION_PROVISION_MANAGED_DEVICE,
2600                DevicePolicyManager.CODE_OK);
2601        assertCheckProvisioningPreCondition(DevicePolicyManager.ACTION_PROVISION_MANAGED_PROFILE,
2602                DevicePolicyManager.CODE_SPLIT_SYSTEM_USER_DEVICE_SYSTEM_USER);
2603        assertCheckProvisioningPreCondition(
2604                DevicePolicyManager.ACTION_PROVISION_MANAGED_SHAREABLE_DEVICE,
2605                DevicePolicyManager.CODE_OK);
2606        assertCheckProvisioningPreCondition(DevicePolicyManager.ACTION_PROVISION_MANAGED_USER,
2607                DevicePolicyManager.CODE_SYSTEM_USER);
2608    }
2609
2610    private void setup_splitUser_firstBoot_primaryUser() throws Exception {
2611        when(mContext.ipackageManager.hasSystemFeature(PackageManager.FEATURE_MANAGED_USERS, 0))
2612                .thenReturn(true);
2613        when(mContext.userManagerForMock.isSplitSystemUser()).thenReturn(true);
2614        when(mContext.userManager.canAddMoreManagedProfiles(DpmMockContext.CALLER_USER_HANDLE,
2615                true)).thenReturn(true);
2616        setUserSetupCompleteForUser(false, DpmMockContext.CALLER_USER_HANDLE);
2617
2618        mContext.binder.callingUid = DpmMockContext.CALLER_UID;
2619    }
2620
2621    public void testIsProvisioningAllowed_splitUser_firstBoot_primaryUser() throws Exception {
2622        setup_splitUser_firstBoot_primaryUser();
2623        mContext.packageName = admin1.getPackageName();
2624        setUpPackageManagerForAdmin(admin1, mContext.binder.callingUid);
2625        assertProvisioningAllowed(DevicePolicyManager.ACTION_PROVISION_MANAGED_DEVICE, true);
2626        assertProvisioningAllowed(DevicePolicyManager.ACTION_PROVISION_MANAGED_PROFILE, true);
2627        assertProvisioningAllowed(DevicePolicyManager.ACTION_PROVISION_MANAGED_SHAREABLE_DEVICE,
2628                true);
2629        assertProvisioningAllowed(DevicePolicyManager.ACTION_PROVISION_MANAGED_USER, true);
2630    }
2631
2632    public void testCheckProvisioningPreCondition_splitUser_firstBoot_primaryUser()
2633            throws Exception {
2634        setup_splitUser_firstBoot_primaryUser();
2635        mContext.callerPermissions.add(permission.MANAGE_PROFILE_AND_DEVICE_OWNERS);
2636        assertCheckProvisioningPreCondition(DevicePolicyManager.ACTION_PROVISION_MANAGED_DEVICE,
2637                DevicePolicyManager.CODE_OK);
2638        assertCheckProvisioningPreCondition(DevicePolicyManager.ACTION_PROVISION_MANAGED_PROFILE,
2639                DevicePolicyManager.CODE_OK);
2640        assertCheckProvisioningPreCondition(
2641                DevicePolicyManager.ACTION_PROVISION_MANAGED_SHAREABLE_DEVICE,
2642                DevicePolicyManager.CODE_OK);
2643        assertCheckProvisioningPreCondition(DevicePolicyManager.ACTION_PROVISION_MANAGED_USER,
2644                DevicePolicyManager.CODE_OK);
2645    }
2646
2647    private void setup_splitUser_afterDeviceSetup_primaryUser() throws Exception {
2648        when(mContext.ipackageManager.hasSystemFeature(PackageManager.FEATURE_MANAGED_USERS, 0))
2649                .thenReturn(true);
2650        when(mContext.userManagerForMock.isSplitSystemUser()).thenReturn(true);
2651        when(mContext.userManager.canAddMoreManagedProfiles(DpmMockContext.CALLER_USER_HANDLE,
2652                true)).thenReturn(true);
2653        setUserSetupCompleteForUser(true, DpmMockContext.CALLER_USER_HANDLE);
2654
2655        mContext.binder.callingUid = DpmMockContext.CALLER_UID;
2656    }
2657
2658    public void testIsProvisioningAllowed_splitUser_afterDeviceSetup_primaryUser()
2659            throws Exception {
2660        setup_splitUser_afterDeviceSetup_primaryUser();
2661        mContext.packageName = admin1.getPackageName();
2662        setUpPackageManagerForAdmin(admin1, mContext.binder.callingUid);
2663        assertProvisioningAllowed(DevicePolicyManager.ACTION_PROVISION_MANAGED_DEVICE,
2664                true/* it's undefined behavior. Can be changed into false in the future */);
2665        assertProvisioningAllowed(DevicePolicyManager.ACTION_PROVISION_MANAGED_PROFILE, true);
2666        assertProvisioningAllowed(DevicePolicyManager.ACTION_PROVISION_MANAGED_SHAREABLE_DEVICE,
2667                true/* it's undefined behavior. Can be changed into false in the future */);
2668        assertProvisioningAllowed(DevicePolicyManager.ACTION_PROVISION_MANAGED_USER,
2669                false/* because user setup completed */);
2670    }
2671
2672    public void testCheckProvisioningPreCondition_splitUser_afterDeviceSetup_primaryUser()
2673            throws Exception {
2674        setup_splitUser_afterDeviceSetup_primaryUser();
2675        mContext.callerPermissions.add(permission.MANAGE_PROFILE_AND_DEVICE_OWNERS);
2676        assertCheckProvisioningPreCondition(DevicePolicyManager.ACTION_PROVISION_MANAGED_DEVICE,
2677                DevicePolicyManager.CODE_OK);
2678        assertCheckProvisioningPreCondition(DevicePolicyManager.ACTION_PROVISION_MANAGED_PROFILE,
2679                DevicePolicyManager.CODE_OK);
2680        assertCheckProvisioningPreCondition(
2681                DevicePolicyManager.ACTION_PROVISION_MANAGED_SHAREABLE_DEVICE,
2682                DevicePolicyManager.CODE_OK);
2683        assertCheckProvisioningPreCondition(DevicePolicyManager.ACTION_PROVISION_MANAGED_USER,
2684                DevicePolicyManager.CODE_USER_SETUP_COMPLETED);
2685    }
2686
2687    private void setup_provisionManagedProfileWithDeviceOwner_systemUser() throws Exception {
2688        setDeviceOwner();
2689
2690        when(mContext.ipackageManager.hasSystemFeature(PackageManager.FEATURE_MANAGED_USERS, 0))
2691                .thenReturn(true);
2692        when(mContext.userManagerForMock.isSplitSystemUser()).thenReturn(true);
2693        when(mContext.userManager.canAddMoreManagedProfiles(UserHandle.USER_SYSTEM, true))
2694                .thenReturn(false);
2695        setUserSetupCompleteForUser(true, UserHandle.USER_SYSTEM);
2696
2697        mContext.binder.callingUid = DpmMockContext.CALLER_SYSTEM_USER_UID;
2698    }
2699
2700    public void testIsProvisioningAllowed_provisionManagedProfileWithDeviceOwner_systemUser()
2701            throws Exception {
2702        setup_provisionManagedProfileWithDeviceOwner_systemUser();
2703        mContext.packageName = admin1.getPackageName();
2704        setUpPackageManagerForAdmin(admin1, mContext.binder.callingUid);
2705        assertProvisioningAllowed(DevicePolicyManager.ACTION_PROVISION_MANAGED_PROFILE,
2706                false /* can't provision managed profile on system user */);
2707    }
2708
2709    public void testCheckProvisioningPreCondition_provisionManagedProfileWithDeviceOwner_systemUser()
2710            throws Exception {
2711        setup_provisionManagedProfileWithDeviceOwner_systemUser();
2712        mContext.callerPermissions.add(permission.MANAGE_PROFILE_AND_DEVICE_OWNERS);
2713        assertCheckProvisioningPreCondition(DevicePolicyManager.ACTION_PROVISION_MANAGED_PROFILE,
2714                DevicePolicyManager.CODE_SPLIT_SYSTEM_USER_DEVICE_SYSTEM_USER);
2715    }
2716
2717    private void setup_provisionManagedProfileWithDeviceOwner_primaryUser() throws Exception {
2718        setDeviceOwner();
2719
2720        when(mContext.ipackageManager.hasSystemFeature(PackageManager.FEATURE_MANAGED_USERS, 0))
2721                .thenReturn(true);
2722        when(mContext.userManagerForMock.isSplitSystemUser()).thenReturn(true);
2723        when(mContext.userManager.canAddMoreManagedProfiles(DpmMockContext.CALLER_USER_HANDLE,
2724                true)).thenReturn(true);
2725        setUserSetupCompleteForUser(false, DpmMockContext.CALLER_USER_HANDLE);
2726
2727        mContext.binder.callingUid = DpmMockContext.CALLER_UID;
2728    }
2729
2730    public void testIsProvisioningAllowed_provisionManagedProfileWithDeviceOwner_primaryUser()
2731            throws Exception {
2732        setup_provisionManagedProfileWithDeviceOwner_primaryUser();
2733        setUpPackageManagerForAdmin(admin1, mContext.binder.callingUid);
2734        mContext.packageName = admin1.getPackageName();
2735        assertProvisioningAllowed(DevicePolicyManager.ACTION_PROVISION_MANAGED_PROFILE, true);
2736    }
2737
2738    public void testCheckProvisioningPreCondition_provisionManagedProfileWithDeviceOwner_primaryUser()
2739            throws Exception {
2740        setup_provisionManagedProfileWithDeviceOwner_primaryUser();
2741        mContext.callerPermissions.add(permission.MANAGE_PROFILE_AND_DEVICE_OWNERS);
2742
2743        // COMP mode is allowed.
2744        assertCheckProvisioningPreCondition(DevicePolicyManager.ACTION_PROVISION_MANAGED_PROFILE,
2745                DevicePolicyManager.CODE_OK);
2746    }
2747
2748    private void setup_provisionManagedProfileCantRemoveUser_primaryUser() throws Exception {
2749        setDeviceOwner();
2750
2751        when(mContext.ipackageManager.hasSystemFeature(PackageManager.FEATURE_MANAGED_USERS, 0))
2752                .thenReturn(true);
2753        when(mContext.userManagerForMock.isSplitSystemUser()).thenReturn(true);
2754        when(mContext.userManager.hasUserRestriction(
2755                eq(UserManager.DISALLOW_REMOVE_MANAGED_PROFILE),
2756                eq(UserHandle.of(DpmMockContext.CALLER_USER_HANDLE))))
2757                .thenReturn(true);
2758        when(mContext.userManager.canAddMoreManagedProfiles(DpmMockContext.CALLER_USER_HANDLE,
2759                false /* we can't remove a managed profile */)).thenReturn(false);
2760        when(mContext.userManager.canAddMoreManagedProfiles(DpmMockContext.CALLER_USER_HANDLE,
2761                true)).thenReturn(true);
2762        setUserSetupCompleteForUser(false, DpmMockContext.CALLER_USER_HANDLE);
2763
2764        mContext.binder.callingUid = DpmMockContext.CALLER_UID;
2765    }
2766
2767    public void testIsProvisioningAllowed_provisionManagedProfileCantRemoveUser_primaryUser()
2768            throws Exception {
2769        setup_provisionManagedProfileCantRemoveUser_primaryUser();
2770        mContext.packageName = admin1.getPackageName();
2771        setUpPackageManagerForAdmin(admin1, mContext.binder.callingUid);
2772        assertProvisioningAllowed(DevicePolicyManager.ACTION_PROVISION_MANAGED_PROFILE, false);
2773    }
2774
2775    public void testCheckProvisioningPreCondition_provisionManagedProfileCantRemoveUser_primaryUser()
2776            throws Exception {
2777        setup_provisionManagedProfileCantRemoveUser_primaryUser();
2778        mContext.callerPermissions.add(permission.MANAGE_PROFILE_AND_DEVICE_OWNERS);
2779        assertCheckProvisioningPreCondition(DevicePolicyManager.ACTION_PROVISION_MANAGED_PROFILE,
2780                DevicePolicyManager.CODE_CANNOT_ADD_MANAGED_PROFILE);
2781    }
2782
2783    public void testCheckProvisioningPreCondition_permission() {
2784        // GIVEN the permission MANAGE_PROFILE_AND_DEVICE_OWNERS is not granted
2785        try {
2786            dpm.checkProvisioningPreCondition(
2787                    DevicePolicyManager.ACTION_PROVISION_MANAGED_PROFILE, "some.package");
2788            fail("Didn't throw SecurityException");
2789        } catch (SecurityException expected) {
2790        }
2791    }
2792
2793    public void testForceUpdateUserSetupComplete_permission() {
2794        // GIVEN the permission MANAGE_PROFILE_AND_DEVICE_OWNERS is not granted
2795        try {
2796            dpm.forceUpdateUserSetupComplete();
2797            fail("Didn't throw SecurityException");
2798        } catch (SecurityException expected) {
2799        }
2800    }
2801
2802    public void testForceUpdateUserSetupComplete_systemUser() {
2803        mContext.callerPermissions.add(permission.MANAGE_PROFILE_AND_DEVICE_OWNERS);
2804        // GIVEN calling from user 20
2805        mContext.binder.callingUid = DpmMockContext.CALLER_UID;
2806        try {
2807            dpm.forceUpdateUserSetupComplete();
2808            fail("Didn't throw SecurityException");
2809        } catch (SecurityException expected) {
2810        }
2811    }
2812
2813    public void testForceUpdateUserSetupComplete_userbuild() {
2814        mContext.callerPermissions.add(permission.MANAGE_PROFILE_AND_DEVICE_OWNERS);
2815        mContext.binder.callingUid = DpmMockContext.CALLER_SYSTEM_USER_UID;
2816
2817        final int userId = UserHandle.USER_SYSTEM;
2818        // GIVEN userComplete is false in SettingsProvider
2819        setUserSetupCompleteForUser(false, userId);
2820
2821        // GIVEN userComplete is true in DPM
2822        DevicePolicyManagerService.DevicePolicyData userData =
2823                new DevicePolicyManagerService.DevicePolicyData(userId);
2824        userData.mUserSetupComplete = true;
2825        dpms.mUserData.put(UserHandle.USER_SYSTEM, userData);
2826
2827        // GIVEN it's user build
2828        mContext.buildMock.isDebuggable = false;
2829
2830        assertTrue(dpms.hasUserSetupCompleted());
2831
2832        dpm.forceUpdateUserSetupComplete();
2833
2834        // THEN the state in dpms is not changed
2835        assertTrue(dpms.hasUserSetupCompleted());
2836    }
2837
2838    public void testForceUpdateUserSetupComplete_userDebugbuild() {
2839        mContext.callerPermissions.add(permission.MANAGE_PROFILE_AND_DEVICE_OWNERS);
2840        mContext.binder.callingUid = DpmMockContext.CALLER_SYSTEM_USER_UID;
2841
2842        final int userId = UserHandle.USER_SYSTEM;
2843        // GIVEN userComplete is false in SettingsProvider
2844        setUserSetupCompleteForUser(false, userId);
2845
2846        // GIVEN userComplete is true in DPM
2847        DevicePolicyManagerService.DevicePolicyData userData =
2848                new DevicePolicyManagerService.DevicePolicyData(userId);
2849        userData.mUserSetupComplete = true;
2850        dpms.mUserData.put(UserHandle.USER_SYSTEM, userData);
2851
2852        // GIVEN it's userdebug build
2853        mContext.buildMock.isDebuggable = true;
2854
2855        assertTrue(dpms.hasUserSetupCompleted());
2856
2857        dpm.forceUpdateUserSetupComplete();
2858
2859        // THEN the state in dpms is not changed
2860        assertFalse(dpms.hasUserSetupCompleted());
2861    }
2862
2863    private void clearDeviceOwner() throws Exception {
2864        final long ident = mContext.binder.clearCallingIdentity();
2865        mContext.binder.callingUid = DpmMockContext.CALLER_SYSTEM_USER_UID;
2866        doReturn(DpmMockContext.CALLER_SYSTEM_USER_UID).when(mContext.packageManager)
2867                .getPackageUidAsUser(eq(admin1.getPackageName()), anyInt());
2868        dpm.clearDeviceOwnerApp(admin1.getPackageName());
2869        mContext.binder.restoreCallingIdentity(ident);
2870    }
2871
2872    public void testGetLastSecurityLogRetrievalTime() throws Exception {
2873        mContext.binder.callingUid = DpmMockContext.CALLER_SYSTEM_USER_UID;
2874        setupDeviceOwner();
2875
2876        // setUp() adds a secondary user for CALLER_USER_HANDLE. Remove it as otherwise the
2877        // feature is disabled because there are non-affiliated secondary users.
2878        mContext.removeUser(DpmMockContext.CALLER_USER_HANDLE);
2879        when(mContext.resources.getBoolean(R.bool.config_supportPreRebootSecurityLogs))
2880                .thenReturn(true);
2881
2882        // No logs were retrieved so far.
2883        assertEquals(-1, dpm.getLastSecurityLogRetrievalTime());
2884
2885        // Enabling logging should not change the timestamp.
2886        dpm.setSecurityLoggingEnabled(admin1, true);
2887        verify(mContext.settings)
2888                .securityLogSetLoggingEnabledProperty(true);
2889        when(mContext.settings.securityLogGetLoggingEnabledProperty())
2890                .thenReturn(true);
2891        assertEquals(-1, dpm.getLastSecurityLogRetrievalTime());
2892
2893        // Retrieving the logs should update the timestamp.
2894        final long beforeRetrieval = System.currentTimeMillis();
2895        dpm.retrieveSecurityLogs(admin1);
2896        final long firstSecurityLogRetrievalTime = dpm.getLastSecurityLogRetrievalTime();
2897        final long afterRetrieval = System.currentTimeMillis();
2898        assertTrue(firstSecurityLogRetrievalTime >= beforeRetrieval);
2899        assertTrue(firstSecurityLogRetrievalTime <= afterRetrieval);
2900
2901        // Retrieving the pre-boot logs should update the timestamp.
2902        Thread.sleep(2);
2903        dpm.retrievePreRebootSecurityLogs(admin1);
2904        final long secondSecurityLogRetrievalTime = dpm.getLastSecurityLogRetrievalTime();
2905        assertTrue(secondSecurityLogRetrievalTime > firstSecurityLogRetrievalTime);
2906
2907        // Checking the timestamp again should not change it.
2908        Thread.sleep(2);
2909        assertEquals(secondSecurityLogRetrievalTime, dpm.getLastSecurityLogRetrievalTime());
2910
2911        // Retrieving the logs again should update the timestamp.
2912        dpm.retrieveSecurityLogs(admin1);
2913        final long thirdSecurityLogRetrievalTime = dpm.getLastSecurityLogRetrievalTime();
2914        assertTrue(thirdSecurityLogRetrievalTime > secondSecurityLogRetrievalTime);
2915
2916        // Disabling logging should not change the timestamp.
2917        Thread.sleep(2);
2918        dpm.setSecurityLoggingEnabled(admin1, false);
2919        assertEquals(thirdSecurityLogRetrievalTime, dpm.getLastSecurityLogRetrievalTime());
2920
2921        // Restarting the DPMS should not lose the timestamp.
2922        initializeDpms();
2923        assertEquals(thirdSecurityLogRetrievalTime, dpm.getLastSecurityLogRetrievalTime());
2924
2925        // Any uid holding MANAGE_USERS permission can retrieve the timestamp.
2926        mContext.binder.callingUid = 1234567;
2927        mContext.callerPermissions.add(permission.MANAGE_USERS);
2928        assertEquals(thirdSecurityLogRetrievalTime, dpm.getLastSecurityLogRetrievalTime());
2929        mContext.callerPermissions.remove(permission.MANAGE_USERS);
2930
2931        // System can retrieve the timestamp.
2932        mContext.binder.clearCallingIdentity();
2933        assertEquals(thirdSecurityLogRetrievalTime, dpm.getLastSecurityLogRetrievalTime());
2934
2935        // Removing the device owner should clear the timestamp.
2936        clearDeviceOwner();
2937        assertEquals(-1, dpm.getLastSecurityLogRetrievalTime());
2938    }
2939
2940    public void testGetLastBugReportRequestTime() throws Exception {
2941        mContext.binder.callingUid = DpmMockContext.CALLER_SYSTEM_USER_UID;
2942        setupDeviceOwner();
2943
2944        mContext.packageName = admin1.getPackageName();
2945        mContext.applicationInfo = new ApplicationInfo();
2946        when(mContext.resources.getColor(eq(R.color.notification_action_list), anyObject()))
2947                .thenReturn(Color.WHITE);
2948        when(mContext.resources.getColor(eq(R.color.notification_material_background_color),
2949                anyObject())).thenReturn(Color.WHITE);
2950
2951        // setUp() adds a secondary user for CALLER_USER_HANDLE. Remove it as otherwise the
2952        // feature is disabled because there are non-affiliated secondary users.
2953        mContext.removeUser(DpmMockContext.CALLER_USER_HANDLE);
2954
2955        // No bug reports were requested so far.
2956        assertEquals(-1, dpm.getLastBugReportRequestTime());
2957
2958        // Requesting a bug report should update the timestamp.
2959        final long beforeRequest = System.currentTimeMillis();
2960        dpm.requestBugreport(admin1);
2961        final long bugReportRequestTime = dpm.getLastBugReportRequestTime();
2962        final long afterRequest = System.currentTimeMillis();
2963        assertTrue(bugReportRequestTime >= beforeRequest);
2964        assertTrue(bugReportRequestTime <= afterRequest);
2965
2966        // Checking the timestamp again should not change it.
2967        Thread.sleep(2);
2968        assertEquals(bugReportRequestTime, dpm.getLastBugReportRequestTime());
2969
2970        // Restarting the DPMS should not lose the timestamp.
2971        initializeDpms();
2972        assertEquals(bugReportRequestTime, dpm.getLastBugReportRequestTime());
2973
2974        // Any uid holding MANAGE_USERS permission can retrieve the timestamp.
2975        mContext.binder.callingUid = 1234567;
2976        mContext.callerPermissions.add(permission.MANAGE_USERS);
2977        assertEquals(bugReportRequestTime, dpm.getLastBugReportRequestTime());
2978        mContext.callerPermissions.remove(permission.MANAGE_USERS);
2979
2980        // System can retrieve the timestamp.
2981        mContext.binder.clearCallingIdentity();
2982        assertEquals(bugReportRequestTime, dpm.getLastBugReportRequestTime());
2983
2984        // Removing the device owner should clear the timestamp.
2985        clearDeviceOwner();
2986        assertEquals(-1, dpm.getLastBugReportRequestTime());
2987    }
2988
2989    public void testGetLastNetworkLogRetrievalTime() throws Exception {
2990        mContext.binder.callingUid = DpmMockContext.CALLER_SYSTEM_USER_UID;
2991        setupDeviceOwner();
2992        mContext.packageName = admin1.getPackageName();
2993        mContext.applicationInfo = new ApplicationInfo();
2994        when(mContext.resources.getColor(eq(R.color.notification_action_list), anyObject()))
2995                .thenReturn(Color.WHITE);
2996        when(mContext.resources.getColor(eq(R.color.notification_material_background_color),
2997                anyObject())).thenReturn(Color.WHITE);
2998
2999        // setUp() adds a secondary user for CALLER_USER_HANDLE. Remove it as otherwise the
3000        // feature is disabled because there are non-affiliated secondary users.
3001        mContext.removeUser(DpmMockContext.CALLER_USER_HANDLE);
3002        when(mContext.iipConnectivityMetrics.registerNetdEventCallback(anyObject()))
3003                .thenReturn(true);
3004
3005        // No logs were retrieved so far.
3006        assertEquals(-1, dpm.getLastNetworkLogRetrievalTime());
3007
3008        // Attempting to retrieve logs without enabling logging should not change the timestamp.
3009        dpm.retrieveNetworkLogs(admin1, 0 /* batchToken */);
3010        assertEquals(-1, dpm.getLastNetworkLogRetrievalTime());
3011
3012        // Enabling logging should not change the timestamp.
3013        dpm.setNetworkLoggingEnabled(admin1, true);
3014        assertEquals(-1, dpm.getLastNetworkLogRetrievalTime());
3015
3016        // Retrieving the logs should update the timestamp.
3017        final long beforeRetrieval = System.currentTimeMillis();
3018        dpm.retrieveNetworkLogs(admin1, 0 /* batchToken */);
3019        final long firstNetworkLogRetrievalTime = dpm.getLastNetworkLogRetrievalTime();
3020        final long afterRetrieval = System.currentTimeMillis();
3021        assertTrue(firstNetworkLogRetrievalTime >= beforeRetrieval);
3022        assertTrue(firstNetworkLogRetrievalTime <= afterRetrieval);
3023
3024        // Checking the timestamp again should not change it.
3025        Thread.sleep(2);
3026        assertEquals(firstNetworkLogRetrievalTime, dpm.getLastNetworkLogRetrievalTime());
3027
3028        // Retrieving the logs again should update the timestamp.
3029        dpm.retrieveNetworkLogs(admin1, 0 /* batchToken */);
3030        final long secondNetworkLogRetrievalTime = dpm.getLastNetworkLogRetrievalTime();
3031        assertTrue(secondNetworkLogRetrievalTime > firstNetworkLogRetrievalTime);
3032
3033        // Disabling logging should not change the timestamp.
3034        Thread.sleep(2);
3035        dpm.setNetworkLoggingEnabled(admin1, false);
3036        assertEquals(secondNetworkLogRetrievalTime, dpm.getLastNetworkLogRetrievalTime());
3037
3038        // Restarting the DPMS should not lose the timestamp.
3039        initializeDpms();
3040        assertEquals(secondNetworkLogRetrievalTime, dpm.getLastNetworkLogRetrievalTime());
3041
3042        // Any uid holding MANAGE_USERS permission can retrieve the timestamp.
3043        mContext.binder.callingUid = 1234567;
3044        mContext.callerPermissions.add(permission.MANAGE_USERS);
3045        assertEquals(secondNetworkLogRetrievalTime, dpm.getLastNetworkLogRetrievalTime());
3046        mContext.callerPermissions.remove(permission.MANAGE_USERS);
3047
3048        // System can retrieve the timestamp.
3049        mContext.binder.clearCallingIdentity();
3050        assertEquals(secondNetworkLogRetrievalTime, dpm.getLastNetworkLogRetrievalTime());
3051
3052        // Removing the device owner should clear the timestamp.
3053        clearDeviceOwner();
3054        assertEquals(-1, dpm.getLastNetworkLogRetrievalTime());
3055    }
3056
3057    public void testGetBindDeviceAdminTargetUsers() throws Exception {
3058        // Setup device owner.
3059        mContext.binder.callingUid = DpmMockContext.CALLER_SYSTEM_USER_UID;
3060        setupDeviceOwner();
3061
3062        // Only device owner is setup, the result list should be empty.
3063        List<UserHandle> targetUsers = dpm.getBindDeviceAdminTargetUsers(admin1);
3064        MoreAsserts.assertEmpty(targetUsers);
3065
3066        // Setup a managed profile managed by the same admin.
3067        final int MANAGED_PROFILE_USER_ID = 15;
3068        final int MANAGED_PROFILE_ADMIN_UID = UserHandle.getUid(MANAGED_PROFILE_USER_ID, 20456);
3069        addManagedProfile(admin1, MANAGED_PROFILE_ADMIN_UID, admin1);
3070
3071        // Add a secondary user, it should never talk with.
3072        final int ANOTHER_USER_ID = 36;
3073        mContext.addUser(ANOTHER_USER_ID, 0);
3074
3075        // Since the managed profile is not affiliated, they should not be allowed to talk to each
3076        // other.
3077        targetUsers = dpm.getBindDeviceAdminTargetUsers(admin1);
3078        MoreAsserts.assertEmpty(targetUsers);
3079
3080        mContext.binder.callingUid = MANAGED_PROFILE_ADMIN_UID;
3081        targetUsers = dpm.getBindDeviceAdminTargetUsers(admin1);
3082        MoreAsserts.assertEmpty(targetUsers);
3083
3084        // Setting affiliation ids
3085        final List<String> userAffiliationIds = Arrays.asList("some.affiliation-id");
3086        mContext.binder.callingUid = DpmMockContext.CALLER_SYSTEM_USER_UID;
3087        dpm.setAffiliationIds(admin1, userAffiliationIds);
3088
3089        mContext.binder.callingUid = MANAGED_PROFILE_ADMIN_UID;
3090        dpm.setAffiliationIds(admin1, userAffiliationIds);
3091
3092        // Calling from device owner admin, the result list should just contain the managed
3093        // profile user id.
3094        mContext.binder.callingUid = DpmMockContext.CALLER_SYSTEM_USER_UID;
3095        targetUsers = dpm.getBindDeviceAdminTargetUsers(admin1);
3096        MoreAsserts.assertContentsInAnyOrder(targetUsers, UserHandle.of(MANAGED_PROFILE_USER_ID));
3097
3098        // Calling from managed profile admin, the result list should just contain the system
3099        // user id.
3100        mContext.binder.callingUid = MANAGED_PROFILE_ADMIN_UID;
3101        targetUsers = dpm.getBindDeviceAdminTargetUsers(admin1);
3102        MoreAsserts.assertContentsInAnyOrder(targetUsers, UserHandle.SYSTEM);
3103
3104        // Changing affiliation ids in one
3105        dpm.setAffiliationIds(admin1, Arrays.asList("some-different-affiliation-id"));
3106
3107        // Since the managed profile is not affiliated any more, they should not be allowed to talk
3108        // to each other.
3109        targetUsers = dpm.getBindDeviceAdminTargetUsers(admin1);
3110        MoreAsserts.assertEmpty(targetUsers);
3111
3112        mContext.binder.callingUid = DpmMockContext.CALLER_SYSTEM_USER_UID;
3113        targetUsers = dpm.getBindDeviceAdminTargetUsers(admin1);
3114        MoreAsserts.assertEmpty(targetUsers);
3115    }
3116
3117    public void testGetBindDeviceAdminTargetUsers_differentPackage() throws Exception {
3118        // Setup a device owner.
3119        mContext.binder.callingUid = DpmMockContext.CALLER_SYSTEM_USER_UID;
3120        setupDeviceOwner();
3121
3122        // Set up a managed profile managed by different package.
3123        final int MANAGED_PROFILE_USER_ID = 15;
3124        final int MANAGED_PROFILE_ADMIN_UID = UserHandle.getUid(MANAGED_PROFILE_USER_ID, 20456);
3125        final ComponentName adminDifferentPackage =
3126                new ComponentName("another.package", "whatever.class");
3127        addManagedProfile(adminDifferentPackage, MANAGED_PROFILE_ADMIN_UID, admin2);
3128
3129        // Setting affiliation ids
3130        final List<String> userAffiliationIds = Arrays.asList("some-affiliation-id");
3131        dpm.setAffiliationIds(admin1, userAffiliationIds);
3132
3133        mContext.binder.callingUid = MANAGED_PROFILE_ADMIN_UID;
3134        dpm.setAffiliationIds(adminDifferentPackage, userAffiliationIds);
3135
3136        // Calling from device owner admin, we should get zero bind device admin target users as
3137        // their packages are different.
3138        mContext.binder.callingUid = DpmMockContext.CALLER_SYSTEM_USER_UID;
3139        List<UserHandle> targetUsers = dpm.getBindDeviceAdminTargetUsers(admin1);
3140        MoreAsserts.assertEmpty(targetUsers);
3141
3142        // Calling from managed profile admin, we should still get zero target users for the same
3143        // reason.
3144        mContext.binder.callingUid = MANAGED_PROFILE_ADMIN_UID;
3145        targetUsers = dpm.getBindDeviceAdminTargetUsers(adminDifferentPackage);
3146        MoreAsserts.assertEmpty(targetUsers);
3147    }
3148
3149    public void testIsDeviceManaged() throws Exception {
3150        mContext.binder.callingUid = DpmMockContext.CALLER_SYSTEM_USER_UID;
3151        setupDeviceOwner();
3152
3153        // The device owner itself, any uid holding MANAGE_USERS permission and the system can
3154        // find out that the device has a device owner.
3155        assertTrue(dpm.isDeviceManaged());
3156        mContext.binder.callingUid = 1234567;
3157        mContext.callerPermissions.add(permission.MANAGE_USERS);
3158        assertTrue(dpm.isDeviceManaged());
3159        mContext.callerPermissions.remove(permission.MANAGE_USERS);
3160        mContext.binder.clearCallingIdentity();
3161        assertTrue(dpm.isDeviceManaged());
3162
3163        clearDeviceOwner();
3164
3165        // Any uid holding MANAGE_USERS permission and the system can find out that the device does
3166        // not have a device owner.
3167        mContext.binder.callingUid = 1234567;
3168        mContext.callerPermissions.add(permission.MANAGE_USERS);
3169        assertFalse(dpm.isDeviceManaged());
3170        mContext.callerPermissions.remove(permission.MANAGE_USERS);
3171        mContext.binder.clearCallingIdentity();
3172        assertFalse(dpm.isDeviceManaged());
3173    }
3174
3175    public void testDeviceOwnerOrganizationName() throws Exception {
3176        mContext.binder.callingUid = DpmMockContext.CALLER_SYSTEM_USER_UID;
3177        setupDeviceOwner();
3178
3179        dpm.setOrganizationName(admin1, "organization");
3180
3181        // Device owner can retrieve organization managing the device.
3182        assertEquals("organization", dpm.getDeviceOwnerOrganizationName());
3183
3184        // Any uid holding MANAGE_USERS permission can retrieve organization managing the device.
3185        mContext.binder.callingUid = 1234567;
3186        mContext.callerPermissions.add(permission.MANAGE_USERS);
3187        assertEquals("organization", dpm.getDeviceOwnerOrganizationName());
3188        mContext.callerPermissions.remove(permission.MANAGE_USERS);
3189
3190        // System can retrieve organization managing the device.
3191        mContext.binder.clearCallingIdentity();
3192        assertEquals("organization", dpm.getDeviceOwnerOrganizationName());
3193
3194        // Removing the device owner clears the organization managing the device.
3195        clearDeviceOwner();
3196        assertNull(dpm.getDeviceOwnerOrganizationName());
3197    }
3198
3199    public void testWipeDataManagedProfile() throws Exception {
3200        final int MANAGED_PROFILE_USER_ID = 15;
3201        final int MANAGED_PROFILE_ADMIN_UID = UserHandle.getUid(MANAGED_PROFILE_USER_ID, 19436);
3202        addManagedProfile(admin1, MANAGED_PROFILE_ADMIN_UID, admin1);
3203        mContext.binder.callingUid = MANAGED_PROFILE_ADMIN_UID;
3204
3205        // Even if the caller is the managed profile, the current user is the user 0
3206        when(mContext.iactivityManager.getCurrentUser())
3207                .thenReturn(new UserInfo(UserHandle.USER_SYSTEM, "user system", 0));
3208
3209        dpm.wipeData(0);
3210        verify(mContext.userManagerInternal).removeUserEvenWhenDisallowed(
3211                MANAGED_PROFILE_USER_ID);
3212    }
3213
3214    public void testWipeDataManagedProfileDisallowed() throws Exception {
3215        final int MANAGED_PROFILE_USER_ID = 15;
3216        final int MANAGED_PROFILE_ADMIN_UID = UserHandle.getUid(MANAGED_PROFILE_USER_ID, 19436);
3217        addManagedProfile(admin1, MANAGED_PROFILE_ADMIN_UID, admin1);
3218
3219        // Even if the caller is the managed profile, the current user is the user 0
3220        when(mContext.iactivityManager.getCurrentUser())
3221                .thenReturn(new UserInfo(UserHandle.USER_SYSTEM, "user system", 0));
3222
3223        when(mContext.userManager.getUserRestrictionSource(
3224                UserManager.DISALLOW_REMOVE_MANAGED_PROFILE,
3225                UserHandle.of(MANAGED_PROFILE_USER_ID)))
3226                .thenReturn(UserManager.RESTRICTION_SOURCE_SYSTEM);
3227        mContext.binder.callingUid = MANAGED_PROFILE_ADMIN_UID;
3228        try {
3229            // The PO is not allowed to remove the profile if the user restriction was set on the
3230            // profile by the system
3231            dpm.wipeData(0);
3232            fail("SecurityException not thrown");
3233        } catch (SecurityException expected) {
3234        }
3235    }
3236
3237    public void testWipeDataDeviceOwner() throws Exception {
3238        setDeviceOwner();
3239        when(mContext.userManager.getUserRestrictionSource(
3240                UserManager.DISALLOW_FACTORY_RESET,
3241                UserHandle.SYSTEM))
3242                .thenReturn(UserManager.RESTRICTION_SOURCE_DEVICE_OWNER);
3243
3244        dpm.wipeData(0);
3245        verify(mContext.recoverySystem).rebootWipeUserData(
3246                /*shutdown=*/ eq(false), anyString(), /*force=*/ eq(true));
3247    }
3248
3249    public void testWipeDataDeviceOwnerDisallowed() throws Exception {
3250        setDeviceOwner();
3251        when(mContext.userManager.getUserRestrictionSource(
3252                UserManager.DISALLOW_FACTORY_RESET,
3253                UserHandle.SYSTEM))
3254                .thenReturn(UserManager.RESTRICTION_SOURCE_SYSTEM);
3255        try {
3256            // The DO is not allowed to wipe the device if the user restriction was set
3257            // by the system
3258            dpm.wipeData(0);
3259            fail("SecurityException not thrown");
3260        } catch (SecurityException expected) {
3261        }
3262    }
3263
3264    public void testMaximumFailedPasswordAttemptsReachedManagedProfile() throws Exception {
3265        final int MANAGED_PROFILE_USER_ID = 15;
3266        final int MANAGED_PROFILE_ADMIN_UID = UserHandle.getUid(MANAGED_PROFILE_USER_ID, 19436);
3267        addManagedProfile(admin1, MANAGED_PROFILE_ADMIN_UID, admin1);
3268
3269        // Even if the caller is the managed profile, the current user is the user 0
3270        when(mContext.iactivityManager.getCurrentUser())
3271                .thenReturn(new UserInfo(UserHandle.USER_SYSTEM, "user system", 0));
3272
3273        when(mContext.userManager.getUserRestrictionSource(
3274                UserManager.DISALLOW_REMOVE_MANAGED_PROFILE,
3275                UserHandle.of(MANAGED_PROFILE_USER_ID)))
3276                .thenReturn(UserManager.RESTRICTION_SOURCE_PROFILE_OWNER);
3277
3278        mContext.binder.callingUid = MANAGED_PROFILE_ADMIN_UID;
3279        dpm.setMaximumFailedPasswordsForWipe(admin1, 3);
3280
3281        mContext.binder.callingUid = DpmMockContext.SYSTEM_UID;
3282        mContext.callerPermissions.add(permission.BIND_DEVICE_ADMIN);
3283        // Failed password attempts on the parent user are taken into account, as there isn't a
3284        // separate work challenge.
3285        dpm.reportFailedPasswordAttempt(UserHandle.USER_SYSTEM);
3286        dpm.reportFailedPasswordAttempt(UserHandle.USER_SYSTEM);
3287        dpm.reportFailedPasswordAttempt(UserHandle.USER_SYSTEM);
3288
3289        // The profile should be wiped even if DISALLOW_REMOVE_MANAGED_PROFILE is enabled, because
3290        // both the user restriction and the policy were set by the PO.
3291        verify(mContext.userManagerInternal).removeUserEvenWhenDisallowed(
3292                MANAGED_PROFILE_USER_ID);
3293        verifyZeroInteractions(mContext.recoverySystem);
3294    }
3295
3296    public void testMaximumFailedPasswordAttemptsReachedManagedProfileDisallowed()
3297            throws Exception {
3298        final int MANAGED_PROFILE_USER_ID = 15;
3299        final int MANAGED_PROFILE_ADMIN_UID = UserHandle.getUid(MANAGED_PROFILE_USER_ID, 19436);
3300        addManagedProfile(admin1, MANAGED_PROFILE_ADMIN_UID, admin1);
3301
3302        // Even if the caller is the managed profile, the current user is the user 0
3303        when(mContext.iactivityManager.getCurrentUser())
3304                .thenReturn(new UserInfo(UserHandle.USER_SYSTEM, "user system", 0));
3305
3306        when(mContext.userManager.getUserRestrictionSource(
3307                UserManager.DISALLOW_REMOVE_MANAGED_PROFILE,
3308                UserHandle.of(MANAGED_PROFILE_USER_ID)))
3309                .thenReturn(UserManager.RESTRICTION_SOURCE_SYSTEM);
3310
3311        mContext.binder.callingUid = MANAGED_PROFILE_ADMIN_UID;
3312        dpm.setMaximumFailedPasswordsForWipe(admin1, 3);
3313
3314        mContext.binder.callingUid = DpmMockContext.SYSTEM_UID;
3315        mContext.callerPermissions.add(permission.BIND_DEVICE_ADMIN);
3316        // Failed password attempts on the parent user are taken into account, as there isn't a
3317        // separate work challenge.
3318        dpm.reportFailedPasswordAttempt(UserHandle.USER_SYSTEM);
3319        dpm.reportFailedPasswordAttempt(UserHandle.USER_SYSTEM);
3320        dpm.reportFailedPasswordAttempt(UserHandle.USER_SYSTEM);
3321
3322        // DISALLOW_REMOVE_MANAGED_PROFILE was set by the system, not the PO, so the profile is
3323        // not wiped.
3324        verify(mContext.userManagerInternal, never())
3325                .removeUserEvenWhenDisallowed(anyInt());
3326        verifyZeroInteractions(mContext.recoverySystem);
3327    }
3328
3329    public void testMaximumFailedPasswordAttemptsReachedDeviceOwner() throws Exception {
3330        setDeviceOwner();
3331        when(mContext.userManager.getUserRestrictionSource(
3332                UserManager.DISALLOW_FACTORY_RESET,
3333                UserHandle.SYSTEM))
3334                .thenReturn(UserManager.RESTRICTION_SOURCE_DEVICE_OWNER);
3335
3336        dpm.setMaximumFailedPasswordsForWipe(admin1, 3);
3337
3338        mContext.binder.callingUid = DpmMockContext.SYSTEM_UID;
3339        mContext.callerPermissions.add(permission.BIND_DEVICE_ADMIN);
3340        dpm.reportFailedPasswordAttempt(UserHandle.USER_SYSTEM);
3341        dpm.reportFailedPasswordAttempt(UserHandle.USER_SYSTEM);
3342        dpm.reportFailedPasswordAttempt(UserHandle.USER_SYSTEM);
3343
3344        // The device should be wiped even if DISALLOW_FACTORY_RESET is enabled, because both the
3345        // user restriction and the policy were set by the DO.
3346        verify(mContext.recoverySystem).rebootWipeUserData(
3347                /*shutdown=*/ eq(false), anyString(), /*force=*/ eq(true));
3348    }
3349
3350    public void testMaximumFailedPasswordAttemptsReachedDeviceOwnerDisallowed() throws Exception {
3351        setDeviceOwner();
3352        when(mContext.userManager.getUserRestrictionSource(
3353                UserManager.DISALLOW_FACTORY_RESET,
3354                UserHandle.SYSTEM))
3355                .thenReturn(UserManager.RESTRICTION_SOURCE_SYSTEM);
3356
3357        dpm.setMaximumFailedPasswordsForWipe(admin1, 3);
3358
3359        mContext.binder.callingUid = DpmMockContext.SYSTEM_UID;
3360        mContext.callerPermissions.add(permission.BIND_DEVICE_ADMIN);
3361        dpm.reportFailedPasswordAttempt(UserHandle.USER_SYSTEM);
3362        dpm.reportFailedPasswordAttempt(UserHandle.USER_SYSTEM);
3363        dpm.reportFailedPasswordAttempt(UserHandle.USER_SYSTEM);
3364
3365        // DISALLOW_FACTORY_RESET was set by the system, not the DO, so the device is not wiped.
3366        verifyZeroInteractions(mContext.recoverySystem);
3367        verify(mContext.userManagerInternal, never())
3368                .removeUserEvenWhenDisallowed(anyInt());
3369    }
3370
3371    public void testGetPermissionGrantState() throws Exception {
3372        final String permission = "some.permission";
3373        final String app1 = "com.example.app1";
3374        final String app2 = "com.example.app2";
3375
3376        when(mContext.ipackageManager.checkPermission(eq(permission), eq(app1), anyInt()))
3377                .thenReturn(PackageManager.PERMISSION_GRANTED);
3378        doReturn(PackageManager.FLAG_PERMISSION_POLICY_FIXED).when(mContext.packageManager)
3379                .getPermissionFlags(permission, app1, UserHandle.SYSTEM);
3380        when(mContext.packageManager.getPermissionFlags(permission, app1,
3381                UserHandle.of(DpmMockContext.CALLER_USER_HANDLE)))
3382                .thenReturn(PackageManager.FLAG_PERMISSION_POLICY_FIXED);
3383        when(mContext.ipackageManager.checkPermission(eq(permission), eq(app2), anyInt()))
3384                .thenReturn(PackageManager.PERMISSION_DENIED);
3385        doReturn(0).when(mContext.packageManager).getPermissionFlags(permission, app2,
3386                UserHandle.SYSTEM);
3387        when(mContext.packageManager.getPermissionFlags(permission, app2,
3388                UserHandle.of(DpmMockContext.CALLER_USER_HANDLE))).thenReturn(0);
3389
3390        // System can retrieve permission grant state.
3391        mContext.binder.callingUid = DpmMockContext.SYSTEM_UID;
3392        assertEquals(DevicePolicyManager.PERMISSION_GRANT_STATE_GRANTED,
3393                dpm.getPermissionGrantState(null, app1, permission));
3394        assertEquals(DevicePolicyManager.PERMISSION_GRANT_STATE_DEFAULT,
3395                dpm.getPermissionGrantState(null, app2, permission));
3396
3397        // A regular app cannot retrieve permission grant state.
3398        mMockContext.binder.callingUid = DpmMockContext.CALLER_UID;
3399        try {
3400            dpm.getPermissionGrantState(null, app1, permission);
3401            fail("Didn't throw IllegalStateException");
3402        } catch (IllegalStateException expected) {
3403        }
3404
3405        // Profile owner can retrieve permission grant state.
3406        setAsProfileOwner(admin1);
3407        assertEquals(DevicePolicyManager.PERMISSION_GRANT_STATE_GRANTED,
3408                dpm.getPermissionGrantState(admin1, app1, permission));
3409        assertEquals(DevicePolicyManager.PERMISSION_GRANT_STATE_DEFAULT,
3410                dpm.getPermissionGrantState(admin1, app2, permission));
3411    }
3412
3413    private void setUserSetupCompleteForUser(boolean isUserSetupComplete, int userhandle) {
3414        when(mContext.settings.settingsSecureGetIntForUser(Settings.Secure.USER_SETUP_COMPLETE, 0,
3415                userhandle)).thenReturn(isUserSetupComplete ? 1 : 0);
3416        dpms.notifyChangeToContentObserver(
3417                Settings.Secure.getUriFor(Settings.Secure.USER_SETUP_COMPLETE), userhandle);
3418    }
3419
3420    private void assertProvisioningAllowed(String action, boolean expected) {
3421        assertEquals("isProvisioningAllowed(" + action + ") returning unexpected result", expected,
3422                dpm.isProvisioningAllowed(action));
3423    }
3424
3425    private void assertCheckProvisioningPreCondition(String action, int provisioningCondition) {
3426        assertCheckProvisioningPreCondition(action, admin1.getPackageName(), provisioningCondition);
3427    }
3428
3429    private void assertCheckProvisioningPreCondition(
3430            String action, String packageName, int provisioningCondition) {
3431        assertEquals("checkProvisioningPreCondition("
3432                        + action + ", " + packageName + ") returning unexpected result",
3433                provisioningCondition, dpm.checkProvisioningPreCondition(action, packageName));
3434    }
3435
3436    /**
3437     * Setup a managed profile with the specified admin and its uid.
3438     * @param admin ComponentName that's visible to the test code, which doesn't have to exist.
3439     * @param adminUid uid of the admin package.
3440     * @param copyFromAdmin package information for {@code admin} will be built based on this
3441     *     component's information.
3442     */
3443    private void addManagedProfile(
3444            ComponentName admin, int adminUid, ComponentName copyFromAdmin) throws Exception {
3445        final int userId = UserHandle.getUserId(adminUid);
3446        mContext.addUser(userId, UserInfo.FLAG_MANAGED_PROFILE, UserHandle.USER_SYSTEM);
3447        mContext.callerPermissions.addAll(OWNER_SETUP_PERMISSIONS);
3448        setUpPackageManagerForFakeAdmin(admin, adminUid, copyFromAdmin);
3449        dpm.setActiveAdmin(admin, false, userId);
3450        assertTrue(dpm.setProfileOwner(admin, null, userId));
3451        mContext.callerPermissions.removeAll(OWNER_SETUP_PERMISSIONS);
3452    }
3453}
3454