DpmMockContext.java revision 3577ed2556f20f7ab09e58b6b286217c7e1560c9
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 */ 16 17package com.android.server.devicepolicy; 18 19import com.android.internal.widget.LockPatternUtils; 20 21import android.app.IActivityManager; 22import android.app.NotificationManager; 23import android.app.backup.IBackupManager; 24import android.content.BroadcastReceiver; 25import android.content.ContentResolver; 26import android.content.Context; 27import android.content.Intent; 28import android.content.IntentFilter; 29import android.content.pm.IPackageManager; 30import android.content.pm.PackageManager; 31import android.content.pm.PackageManagerInternal; 32import android.content.pm.UserInfo; 33import android.media.IAudioService; 34import android.net.wifi.WifiManager; 35import android.os.Bundle; 36import android.os.Handler; 37import android.os.PowerManager.WakeLock; 38import android.os.PowerManagerInternal; 39import android.os.UserHandle; 40import android.os.UserManager; 41import android.os.UserManagerInternal; 42import android.telephony.TelephonyManager; 43import android.test.mock.MockContentResolver; 44import android.test.mock.MockContext; 45import android.view.IWindowManager; 46 47import org.junit.Assert; 48import org.mockito.invocation.InvocationOnMock; 49import org.mockito.stubbing.Answer; 50 51import java.io.File; 52import java.util.ArrayList; 53import java.util.List; 54 55import static org.mockito.Matchers.anyBoolean; 56import static org.mockito.Matchers.anyInt; 57import static org.mockito.Matchers.eq; 58import static org.mockito.Mockito.mock; 59import static org.mockito.Mockito.spy; 60import static org.mockito.Mockito.when; 61 62/** 63 * Context used throughout DPMS tests. 64 */ 65public class DpmMockContext extends MockContext { 66 /** 67 * User-id of a non-system user we use throughout unit tests. 68 */ 69 public static final int CALLER_USER_HANDLE = 20; 70 71 /** 72 * UID corresponding to {@link #CALLER_USER_HANDLE}. 73 */ 74 public static final int CALLER_UID = UserHandle.getUid(CALLER_USER_HANDLE, 20123); 75 76 /** 77 * UID used when a caller is on the system user. 78 */ 79 public static final int CALLER_SYSTEM_USER_UID = 20321; 80 81 /** 82 * PID of the caller. 83 */ 84 public static final int CALLER_PID = 22222; 85 86 /** 87 * UID of the system server. 88 */ 89 public static final int SYSTEM_UID = android.os.Process.SYSTEM_UID; 90 91 /** 92 * PID of the system server. 93 */ 94 public static final int SYSTEM_PID = 11111; 95 96 public static class MockBinder { 97 public int callingUid = CALLER_UID; 98 public int callingPid = CALLER_PID; 99 100 public long clearCallingIdentity() { 101 final long token = (((long) callingUid) << 32) | (callingPid); 102 callingUid = SYSTEM_UID; 103 callingPid = SYSTEM_PID; 104 return token; 105 } 106 107 public void restoreCallingIdentity(long token) { 108 callingUid = (int) (token >> 32); 109 callingPid = (int) token; 110 } 111 112 public int getCallingUid() { 113 return callingUid; 114 } 115 116 public int getCallingPid() { 117 return callingPid; 118 } 119 120 public UserHandle getCallingUserHandle() { 121 return new UserHandle(UserHandle.getUserId(getCallingUid())); 122 } 123 124 public boolean isCallerUidMyUid() { 125 return callingUid == SYSTEM_UID; 126 } 127 } 128 129 public static class EnvironmentForMock { 130 public File getUserSystemDirectory(int userId) { 131 return null; 132 } 133 } 134 135 public static class BuildMock { 136 public boolean isDebuggable = true; 137 } 138 139 public static class PowerManagerForMock { 140 public WakeLock newWakeLock(int levelAndFlags, String tag) { 141 return null; 142 } 143 144 public void goToSleep(long time, int reason, int flags) { 145 } 146 147 public void reboot(String reason) { 148 } 149 } 150 151 public static class SystemPropertiesForMock { 152 public boolean getBoolean(String key, boolean def) { 153 return false; 154 } 155 156 public long getLong(String key, long def) { 157 return 0; 158 } 159 160 public String get(String key, String def) { 161 return null; 162 } 163 164 public String get(String key) { 165 return null; 166 } 167 168 public void set(String key, String value) { 169 } 170 } 171 172 public static class UserManagerForMock { 173 public boolean isSplitSystemUser() { 174 return false; 175 } 176 } 177 178 public static class SettingsForMock { 179 public int settingsSecureGetIntForUser(String name, int def, int userHandle) { 180 return 0; 181 } 182 183 public void settingsSecurePutIntForUser(String name, int value, int userHandle) { 184 } 185 186 public void settingsSecurePutStringForUser(String name, String value, int userHandle) { 187 } 188 189 public void settingsGlobalPutStringForUser(String name, String value, int userHandle) { 190 } 191 192 public void settingsSecurePutInt(String name, int value) { 193 } 194 195 public void settingsGlobalPutInt(String name, int value) { 196 } 197 198 public void settingsSecurePutString(String name, String value) { 199 } 200 201 public void settingsGlobalPutString(String name, String value) { 202 } 203 204 public int settingsGlobalGetInt(String name, int value) { 205 return 0; 206 } 207 208 public void securityLogSetLoggingEnabledProperty(boolean enabled) { 209 } 210 211 public boolean securityLogGetLoggingEnabledProperty() { 212 return false; 213 } 214 215 public boolean securityLogIsLoggingEnabled() { 216 return false; 217 } 218 } 219 220 public static class StorageManagerForMock { 221 public boolean isFileBasedEncryptionEnabled() { 222 return false; 223 } 224 225 public boolean isNonDefaultBlockEncrypted() { 226 return false; 227 } 228 229 public boolean isEncrypted() { 230 return false; 231 } 232 233 public boolean isEncryptable() { 234 return false; 235 } 236 } 237 238 public final Context realTestContext; 239 240 /** 241 * Use this instance to verify unimplemented methods such as {@link #sendBroadcast}. 242 * (Spying on {@code this} instance will confuse mockito somehow and I got weired "wrong number 243 * of arguments" exceptions.) 244 */ 245 public final Context spiedContext; 246 247 public final File dataDir; 248 public final File systemUserDataDir; 249 250 public final MockBinder binder; 251 public final EnvironmentForMock environment; 252 public final SystemPropertiesForMock systemProperties; 253 public final UserManager userManager; 254 public final UserManagerInternal userManagerInternal; 255 public final PackageManagerInternal packageManagerInternal; 256 public final UserManagerForMock userManagerForMock; 257 public final PowerManagerForMock powerManager; 258 public final PowerManagerInternal powerManagerInternal; 259 public final NotificationManager notificationManager; 260 public final IWindowManager iwindowManager; 261 public final IActivityManager iactivityManager; 262 public final IPackageManager ipackageManager; 263 public final IBackupManager ibackupManager; 264 public final IAudioService iaudioService; 265 public final LockPatternUtils lockPatternUtils; 266 public final StorageManagerForMock storageManager; 267 public final WifiManager wifiManager; 268 public final SettingsForMock settings; 269 public final MockContentResolver contentResolver; 270 public final TelephonyManager telephonyManager; 271 272 /** Note this is a partial mock, not a real mock. */ 273 public final PackageManager packageManager; 274 275 public final List<String> callerPermissions = new ArrayList<>(); 276 277 private final ArrayList<UserInfo> mUserInfos = new ArrayList<>(); 278 279 public final BuildMock buildMock = new BuildMock(); 280 281 public DpmMockContext(Context context, File dataDir) { 282 realTestContext = context; 283 284 this.dataDir = dataDir; 285 DpmTestUtils.clearDir(dataDir); 286 287 binder = new MockBinder(); 288 environment = mock(EnvironmentForMock.class); 289 systemProperties= mock(SystemPropertiesForMock.class); 290 userManager = mock(UserManager.class); 291 userManagerInternal = mock(UserManagerInternal.class); 292 userManagerForMock = mock(UserManagerForMock.class); 293 packageManagerInternal = mock(PackageManagerInternal.class); 294 powerManager = mock(PowerManagerForMock.class); 295 powerManagerInternal = mock(PowerManagerInternal.class); 296 notificationManager = mock(NotificationManager.class); 297 iwindowManager = mock(IWindowManager.class); 298 iactivityManager = mock(IActivityManager.class); 299 ipackageManager = mock(IPackageManager.class); 300 ibackupManager = mock(IBackupManager.class); 301 iaudioService = mock(IAudioService.class); 302 lockPatternUtils = mock(LockPatternUtils.class); 303 storageManager = mock(StorageManagerForMock.class); 304 wifiManager = mock(WifiManager.class); 305 settings = mock(SettingsForMock.class); 306 telephonyManager = mock(TelephonyManager.class); 307 308 // Package manager is huge, so we use a partial mock instead. 309 packageManager = spy(context.getPackageManager()); 310 311 spiedContext = mock(Context.class); 312 313 contentResolver = new MockContentResolver(); 314 315 // Add the system user 316 systemUserDataDir = addUser(UserHandle.USER_SYSTEM, UserInfo.FLAG_PRIMARY); 317 318 // System user is always running. 319 setUserRunning(UserHandle.USER_SYSTEM, true); 320 } 321 322 public File addUser(int userId, int flags) { 323 324 // Set up (default) UserInfo for CALLER_USER_HANDLE. 325 final UserInfo uh = new UserInfo(userId, "user" + userId, flags); 326 when(userManager.getUserInfo(eq(userId))).thenReturn(uh); 327 328 mUserInfos.add(uh); 329 when(userManager.getUsers()).thenReturn(mUserInfos); 330 when(userManager.getUsers(anyBoolean())).thenReturn(mUserInfos); 331 when(userManager.isUserRunning(eq(new UserHandle(userId)))).thenReturn(true); 332 when(userManager.getUserInfo(anyInt())).thenAnswer( 333 new Answer<UserInfo>() { 334 @Override 335 public UserInfo answer(InvocationOnMock invocation) throws Throwable { 336 final int userId = (int) invocation.getArguments()[0]; 337 for (UserInfo ui : mUserInfos) { 338 if (ui.id == userId) { 339 return ui; 340 } 341 } 342 return null; 343 } 344 } 345 ); 346 when(userManager.getProfiles(anyInt())).thenAnswer( 347 new Answer<List<UserInfo>>() { 348 @Override 349 public List<UserInfo> answer(InvocationOnMock invocation) throws Throwable { 350 final int userId = (int) invocation.getArguments()[0]; 351 return getProfiles(userId); 352 } 353 } 354 ); 355 when(userManager.getProfileIdsWithDisabled(anyInt())).thenAnswer( 356 new Answer<int[]>() { 357 @Override 358 public int[] answer(InvocationOnMock invocation) throws Throwable { 359 final int userId = (int) invocation.getArguments()[0]; 360 List<UserInfo> profiles = getProfiles(userId); 361 int[] results = new int[profiles.size()]; 362 for (int i = 0; i < results.length; i++) { 363 results[i] = profiles.get(i).id; 364 } 365 return results; 366 } 367 } 368 ); 369 370 371 // Create a data directory. 372 final File dir = new File(dataDir, "user" + userId); 373 DpmTestUtils.clearDir(dir); 374 375 when(environment.getUserSystemDirectory(eq(userId))).thenReturn(dir); 376 return dir; 377 } 378 379 private List<UserInfo> getProfiles(int userId) { 380 final ArrayList<UserInfo> ret = new ArrayList<UserInfo>(); 381 UserInfo parent = null; 382 for (UserInfo ui : mUserInfos) { 383 if (ui.id == userId) { 384 parent = ui; 385 break; 386 } 387 } 388 if (parent == null) { 389 return ret; 390 } 391 ret.add(parent); 392 for (UserInfo ui : mUserInfos) { 393 if (ui.id == userId) { 394 continue; 395 } 396 if (ui.profileGroupId != UserInfo.NO_PROFILE_GROUP_ID 397 && ui.profileGroupId == parent.profileGroupId) { 398 ret.add(ui); 399 } 400 } 401 return ret; 402 } 403 404 /** 405 * Add multiple users at once. They'll all have flag 0. 406 */ 407 public void addUsers(int... userIds) { 408 for (int userId : userIds) { 409 addUser(userId, 0); 410 } 411 } 412 413 public void setUserRunning(int userId, boolean isRunning) { 414 when(userManager.isUserRunning(MockUtils.checkUserHandle(userId))) 415 .thenReturn(isRunning); 416 } 417 418 @Override 419 public Object getSystemService(String name) { 420 switch (name) { 421 case Context.USER_SERVICE: 422 return userManager; 423 case Context.POWER_SERVICE: 424 return powerManager; 425 case Context.WIFI_SERVICE: 426 return wifiManager; 427 } 428 throw new UnsupportedOperationException(); 429 } 430 431 @Override 432 public String getSystemServiceName(Class<?> serviceClass) { 433 return realTestContext.getSystemServiceName(serviceClass); 434 } 435 436 @Override 437 public PackageManager getPackageManager() { 438 return packageManager; 439 } 440 441 @Override 442 public void enforceCallingOrSelfPermission(String permission, String message) { 443 if (binder.getCallingUid() == SYSTEM_UID) { 444 return; // Assume system has all permissions. 445 } 446 if (!callerPermissions.contains(permission)) { 447 throw new SecurityException("Caller doesn't have " + permission + " : " + message); 448 } 449 } 450 451 @Override 452 public void sendBroadcast(Intent intent) { 453 spiedContext.sendBroadcast(intent); 454 } 455 456 @Override 457 public void sendBroadcast(Intent intent, String receiverPermission) { 458 spiedContext.sendBroadcast(intent, receiverPermission); 459 } 460 461 @Override 462 public void sendBroadcastMultiplePermissions(Intent intent, String[] receiverPermissions) { 463 spiedContext.sendBroadcastMultiplePermissions(intent, receiverPermissions); 464 } 465 466 @Override 467 public void sendBroadcast(Intent intent, String receiverPermission, Bundle options) { 468 spiedContext.sendBroadcast(intent, receiverPermission, options); 469 } 470 471 @Override 472 public void sendBroadcast(Intent intent, String receiverPermission, int appOp) { 473 spiedContext.sendBroadcast(intent, receiverPermission, appOp); 474 } 475 476 @Override 477 public void sendOrderedBroadcast(Intent intent, String receiverPermission) { 478 spiedContext.sendOrderedBroadcast(intent, receiverPermission); 479 } 480 481 @Override 482 public void sendOrderedBroadcast(Intent intent, String receiverPermission, 483 BroadcastReceiver resultReceiver, Handler scheduler, int initialCode, 484 String initialData, Bundle initialExtras) { 485 spiedContext.sendOrderedBroadcast(intent, receiverPermission, resultReceiver, scheduler, 486 initialCode, initialData, initialExtras); 487 } 488 489 @Override 490 public void sendOrderedBroadcast(Intent intent, String receiverPermission, Bundle options, 491 BroadcastReceiver resultReceiver, Handler scheduler, int initialCode, 492 String initialData, Bundle initialExtras) { 493 spiedContext.sendOrderedBroadcast(intent, receiverPermission, options, resultReceiver, 494 scheduler, 495 initialCode, initialData, initialExtras); 496 } 497 498 @Override 499 public void sendOrderedBroadcast(Intent intent, String receiverPermission, int appOp, 500 BroadcastReceiver resultReceiver, Handler scheduler, int initialCode, 501 String initialData, Bundle initialExtras) { 502 spiedContext.sendOrderedBroadcast(intent, receiverPermission, appOp, resultReceiver, 503 scheduler, 504 initialCode, initialData, initialExtras); 505 } 506 507 @Override 508 public void sendBroadcastAsUser(Intent intent, UserHandle user) { 509 if (binder.callingPid != SYSTEM_PID) { 510 // Unless called as the system process, can only call if the target user is the 511 // calling user. 512 // (The actual check is more complex; we may need to change it later.) 513 Assert.assertEquals(UserHandle.getUserId(binder.getCallingUid()), user.getIdentifier()); 514 } 515 516 spiedContext.sendBroadcastAsUser(intent, user); 517 } 518 519 @Override 520 public void sendBroadcastAsUser(Intent intent, UserHandle user, String receiverPermission) { 521 spiedContext.sendBroadcastAsUser(intent, user, receiverPermission); 522 } 523 524 @Override 525 public void sendBroadcastAsUser(Intent intent, UserHandle user, String receiverPermission, 526 int appOp) { 527 spiedContext.sendBroadcastAsUser(intent, user, receiverPermission, appOp); 528 } 529 530 @Override 531 public void sendOrderedBroadcastAsUser(Intent intent, UserHandle user, 532 String receiverPermission, BroadcastReceiver resultReceiver, Handler scheduler, 533 int initialCode, String initialData, Bundle initialExtras) { 534 spiedContext.sendOrderedBroadcastAsUser(intent, user, receiverPermission, resultReceiver, 535 scheduler, initialCode, initialData, initialExtras); 536 resultReceiver.onReceive(spiedContext, intent); 537 } 538 539 @Override 540 public void sendOrderedBroadcastAsUser(Intent intent, UserHandle user, 541 String receiverPermission, int appOp, BroadcastReceiver resultReceiver, 542 Handler scheduler, int initialCode, String initialData, Bundle initialExtras) { 543 spiedContext.sendOrderedBroadcastAsUser(intent, user, receiverPermission, appOp, 544 resultReceiver, 545 scheduler, initialCode, initialData, initialExtras); 546 } 547 548 @Override 549 public void sendOrderedBroadcastAsUser(Intent intent, UserHandle user, 550 String receiverPermission, int appOp, Bundle options, BroadcastReceiver resultReceiver, 551 Handler scheduler, int initialCode, String initialData, Bundle initialExtras) { 552 spiedContext.sendOrderedBroadcastAsUser(intent, user, receiverPermission, appOp, options, 553 resultReceiver, scheduler, initialCode, initialData, initialExtras); 554 } 555 556 @Override 557 public void sendStickyBroadcast(Intent intent) { 558 spiedContext.sendStickyBroadcast(intent); 559 } 560 561 @Override 562 public void sendStickyOrderedBroadcast(Intent intent, BroadcastReceiver resultReceiver, 563 Handler scheduler, int initialCode, String initialData, Bundle initialExtras) { 564 spiedContext.sendStickyOrderedBroadcast(intent, resultReceiver, scheduler, initialCode, 565 initialData, initialExtras); 566 } 567 568 @Override 569 public void removeStickyBroadcast(Intent intent) { 570 spiedContext.removeStickyBroadcast(intent); 571 } 572 573 @Override 574 public void sendStickyBroadcastAsUser(Intent intent, UserHandle user) { 575 spiedContext.sendStickyBroadcastAsUser(intent, user); 576 } 577 578 @Override 579 public void sendStickyOrderedBroadcastAsUser(Intent intent, UserHandle user, 580 BroadcastReceiver resultReceiver, Handler scheduler, int initialCode, 581 String initialData, Bundle initialExtras) { 582 spiedContext.sendStickyOrderedBroadcastAsUser(intent, user, resultReceiver, scheduler, initialCode, 583 initialData, initialExtras); 584 } 585 586 @Override 587 public void removeStickyBroadcastAsUser(Intent intent, UserHandle user) { 588 spiedContext.removeStickyBroadcastAsUser(intent, user); 589 } 590 591 @Override 592 public Intent registerReceiver(BroadcastReceiver receiver, IntentFilter filter) { 593 return spiedContext.registerReceiver(receiver, filter); 594 } 595 596 @Override 597 public Intent registerReceiver(BroadcastReceiver receiver, IntentFilter filter, 598 String broadcastPermission, Handler scheduler) { 599 return spiedContext.registerReceiver(receiver, filter, broadcastPermission, scheduler); 600 } 601 602 @Override 603 public Intent registerReceiverAsUser(BroadcastReceiver receiver, UserHandle user, 604 IntentFilter filter, String broadcastPermission, Handler scheduler) { 605 return spiedContext.registerReceiverAsUser(receiver, user, filter, broadcastPermission, 606 scheduler); 607 } 608 609 @Override 610 public void unregisterReceiver(BroadcastReceiver receiver) { 611 spiedContext.unregisterReceiver(receiver); 612 } 613 614 @Override 615 public ContentResolver getContentResolver() { 616 return contentResolver; 617 } 618} 619