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 17 package com.android.server.devicepolicy; 18 19 import static org.mockito.Mockito.mock; 20 import static org.mockito.Mockito.when; 21 22 import android.annotation.Nullable; 23 import android.app.AppOpsManager; 24 import android.content.BroadcastReceiver; 25 import android.content.ContentResolver; 26 import android.content.Context; 27 import android.content.Intent; 28 import android.content.IntentFilter; 29 import android.content.pm.ApplicationInfo; 30 import android.content.pm.PackageManager; 31 import android.content.res.Resources; 32 import android.os.Bundle; 33 import android.os.Handler; 34 import android.os.UserHandle; 35 import android.test.mock.MockContext; 36 import android.util.ArrayMap; 37 import android.util.DisplayMetrics; 38 import android.util.ExceptionUtils; 39 40 import androidx.annotation.NonNull; 41 42 import com.android.internal.util.FunctionalUtils; 43 import com.android.server.pm.UserManagerInternal; 44 45 import org.junit.Assert; 46 47 import java.util.ArrayList; 48 import java.util.List; 49 import java.util.Map; 50 import java.util.concurrent.Executor; 51 52 /** 53 * Context used throughout DPMS tests. 54 */ 55 public class DpmMockContext extends MockContext { 56 /** 57 * User-id of a non-system user we use throughout unit tests. 58 */ 59 public static final int CALLER_USER_HANDLE = 20; 60 61 /** 62 * UID corresponding to {@link #CALLER_USER_HANDLE}. 63 */ 64 public static final int CALLER_UID = UserHandle.getUid(CALLER_USER_HANDLE, 20123); 65 66 /** 67 * UID corresponding to {@link #CALLER_USER_HANDLE}. 68 */ 69 public static final int CALLER_MANAGED_PROVISIONING_UID = UserHandle.getUid(CALLER_USER_HANDLE, 70 20125); 71 72 /** 73 * UID used when a caller is on the system user. 74 */ 75 public static final int CALLER_SYSTEM_USER_UID = 20321; 76 77 /** 78 * PID of the caller. 79 */ 80 public static final int CALLER_PID = 22222; 81 82 /** 83 * UID of the system server. 84 */ 85 public static final int SYSTEM_UID = android.os.Process.SYSTEM_UID; 86 87 /** 88 * PID of the system server. 89 */ 90 public static final int SYSTEM_PID = 11111; 91 92 public static final String ANOTHER_PACKAGE_NAME = "com.another.package.name"; 93 public static final int ANOTHER_UID = UserHandle.getUid(UserHandle.USER_SYSTEM, 18434); 94 95 public static final String DELEGATE_PACKAGE_NAME = "com.delegate.package.name"; 96 public static final int DELEGATE_CERT_INSTALLER_UID = UserHandle.getUid(UserHandle.USER_SYSTEM, 97 18437); 98 99 private final MockSystemServices mMockSystemServices; 100 101 public static class MockBinder { 102 public int callingUid = CALLER_UID; 103 public int callingPid = CALLER_PID; 104 public final Map<Integer, List<String>> callingPermissions = new ArrayMap<>(); 105 clearCallingIdentity()106 public long clearCallingIdentity() { 107 final long token = (((long) callingUid) << 32) | (callingPid); 108 callingUid = SYSTEM_UID; 109 callingPid = SYSTEM_PID; 110 return token; 111 } 112 restoreCallingIdentity(long token)113 public void restoreCallingIdentity(long token) { 114 callingUid = (int) (token >> 32); 115 callingPid = (int) token; 116 } 117 withCleanCallingIdentity(@onNull FunctionalUtils.ThrowingRunnable action)118 public void withCleanCallingIdentity(@NonNull FunctionalUtils.ThrowingRunnable action) { 119 final long callingIdentity = clearCallingIdentity(); 120 Throwable throwableToPropagate = null; 121 try { 122 action.runOrThrow(); 123 } catch (Throwable throwable) { 124 throwableToPropagate = throwable; 125 } finally { 126 restoreCallingIdentity(callingIdentity); 127 if (throwableToPropagate != null) { 128 throw ExceptionUtils.propagate(throwableToPropagate); 129 } 130 } 131 } 132 getCallingUid()133 public int getCallingUid() { 134 return callingUid; 135 } 136 getCallingPid()137 public int getCallingPid() { 138 return callingPid; 139 } 140 getCallingUserHandle()141 public UserHandle getCallingUserHandle() { 142 return new UserHandle(UserHandle.getUserId(getCallingUid())); 143 } 144 isCallerUidMyUid()145 public boolean isCallerUidMyUid() { 146 return callingUid == SYSTEM_UID; 147 } 148 } 149 150 private final Context realTestContext; 151 152 /** 153 * Use this instance to verify unimplemented methods such as {@link #sendBroadcast}. 154 * (Spying on {@code this} instance will confuse mockito somehow and I got weired "wrong number 155 * of arguments" exceptions.) 156 */ 157 public final Context spiedContext; 158 159 public final MockBinder binder; 160 public final Resources resources; 161 162 /** TODO: Migrate everything to use {@link #permissions} to avoid confusion. */ 163 @Deprecated 164 public final List<String> callerPermissions = new ArrayList<>(); 165 166 /** Less confusing alias for {@link #callerPermissions}. */ 167 public final List<String> permissions = callerPermissions; 168 169 public String packageName = null; 170 171 public ApplicationInfo applicationInfo = null; 172 DpmMockContext(MockSystemServices mockSystemServices, Context context)173 public DpmMockContext(MockSystemServices mockSystemServices, Context context) { 174 this(mockSystemServices, context, new MockBinder()); 175 } 176 DpmMockContext(MockSystemServices mockSystemServices, Context context, @NonNull MockBinder mockBinder)177 public DpmMockContext(MockSystemServices mockSystemServices, Context context, 178 @NonNull MockBinder mockBinder) { 179 mMockSystemServices = mockSystemServices; 180 realTestContext = context; 181 binder = mockBinder; 182 183 resources = mock(Resources.class); 184 spiedContext = mock(Context.class); 185 186 // Set up density for notification building 187 DisplayMetrics displayMetrics = mock(DisplayMetrics.class); 188 displayMetrics.density = 2.25f; 189 when(resources.getDisplayMetrics()).thenReturn(displayMetrics); 190 } 191 192 @Override getResources()193 public Resources getResources() { 194 return resources; 195 } 196 197 @Override getTheme()198 public Resources.Theme getTheme() { 199 return spiedContext.getTheme(); 200 } 201 202 @Override getPackageName()203 public String getPackageName() { 204 if (packageName != null) { 205 return packageName; 206 } 207 return super.getPackageName(); 208 } 209 210 @Override getOpPackageName()211 public String getOpPackageName() { 212 return getPackageName(); 213 } 214 215 @Override getApplicationInfo()216 public ApplicationInfo getApplicationInfo() { 217 if (applicationInfo != null) { 218 return applicationInfo; 219 } 220 return super.getApplicationInfo(); 221 } 222 223 @Override getSystemService(String name)224 public Object getSystemService(String name) { 225 switch (name) { 226 case Context.ALARM_SERVICE: 227 return mMockSystemServices.alarmManager; 228 case Context.USER_SERVICE: 229 return mMockSystemServices.userManager; 230 case Context.POWER_SERVICE: 231 return mMockSystemServices.powerManager; 232 case Context.WIFI_SERVICE: 233 return mMockSystemServices.wifiManager; 234 case Context.ACCOUNT_SERVICE: 235 return mMockSystemServices.accountManager; 236 case Context.TELEPHONY_SERVICE: 237 return mMockSystemServices.telephonyManager; 238 case Context.CONNECTIVITY_SERVICE: 239 return mMockSystemServices.connectivityManager; 240 case Context.APP_OPS_SERVICE: 241 return mMockSystemServices.appOpsManager; 242 case Context.CROSS_PROFILE_APPS_SERVICE: 243 return mMockSystemServices.crossProfileApps; 244 case Context.VPN_MANAGEMENT_SERVICE: 245 return mMockSystemServices.vpnManager; 246 case Context.DEVICE_POLICY_SERVICE: 247 return mMockSystemServices.devicePolicyManager; 248 case Context.LOCATION_SERVICE: 249 return mMockSystemServices.locationManager; 250 case Context.ROLE_SERVICE: 251 return mMockSystemServices.roleManager; 252 case Context.TELEPHONY_SUBSCRIPTION_SERVICE: 253 return mMockSystemServices.subscriptionManager; 254 case Context.USB_SERVICE: 255 return mMockSystemServices.usbManager; 256 } 257 throw new UnsupportedOperationException(); 258 } 259 260 @Override getSystemServiceName(Class<?> serviceClass)261 public String getSystemServiceName(Class<?> serviceClass) { 262 return realTestContext.getSystemServiceName(serviceClass); 263 } 264 265 @Override getPackageManager()266 public PackageManager getPackageManager() { 267 return mMockSystemServices.packageManager; 268 } 269 getUserManagerInternal()270 public UserManagerInternal getUserManagerInternal() { 271 return mMockSystemServices.userManagerInternal; 272 } 273 274 @Override enforceCallingOrSelfPermission(String permission, String message)275 public void enforceCallingOrSelfPermission(String permission, String message) { 276 if (UserHandle.isSameApp(binder.getCallingUid(), SYSTEM_UID)) { 277 return; // Assume system has all permissions. 278 } 279 List<String> permissions = binder.callingPermissions.get(binder.getCallingUid()); 280 if (permissions == null) { 281 // TODO: delete the following line. to do this without breaking any tests, first it's 282 // necessary to remove all tests that set it directly. 283 permissions = callerPermissions; 284 // throw new UnsupportedOperationException( 285 // "Caller UID " + binder.getCallingUid() + " doesn't exist"); 286 } 287 if (!permissions.contains(permission)) { 288 throw new SecurityException("Caller doesn't have " + permission + " : " + message); 289 } 290 } 291 292 @Override checkPermission(String permission, int pid, int uid)293 public int checkPermission(String permission, int pid, int uid) { 294 return checkPermission(permission); 295 } 296 297 @Override sendBroadcast(Intent intent)298 public void sendBroadcast(Intent intent) { 299 spiedContext.sendBroadcast(intent); 300 } 301 302 @Override sendBroadcast(Intent intent, String receiverPermission)303 public void sendBroadcast(Intent intent, String receiverPermission) { 304 spiedContext.sendBroadcast(intent, receiverPermission); 305 } 306 307 @Override sendBroadcastMultiplePermissions(Intent intent, String[] receiverPermissions)308 public void sendBroadcastMultiplePermissions(Intent intent, String[] receiverPermissions) { 309 spiedContext.sendBroadcastMultiplePermissions(intent, receiverPermissions); 310 } 311 312 @Override sendBroadcastMultiplePermissions(Intent intent, String[] receiverPermissions, Bundle options)313 public void sendBroadcastMultiplePermissions(Intent intent, String[] receiverPermissions, 314 Bundle options) { 315 spiedContext.sendBroadcastMultiplePermissions(intent, receiverPermissions, options); 316 } 317 318 @Override sendBroadcastAsUserMultiplePermissions(Intent intent, UserHandle user, String[] receiverPermissions)319 public void sendBroadcastAsUserMultiplePermissions(Intent intent, UserHandle user, 320 String[] receiverPermissions) { 321 spiedContext.sendBroadcastAsUserMultiplePermissions(intent, user, receiverPermissions); 322 } 323 324 @Override sendBroadcast(Intent intent, String receiverPermission, Bundle options)325 public void sendBroadcast(Intent intent, String receiverPermission, Bundle options) { 326 spiedContext.sendBroadcast(intent, receiverPermission, options); 327 } 328 329 @Override sendBroadcast(Intent intent, String receiverPermission, int appOp)330 public void sendBroadcast(Intent intent, String receiverPermission, int appOp) { 331 spiedContext.sendBroadcast(intent, receiverPermission, appOp); 332 } 333 334 @Override sendOrderedBroadcast(Intent intent, String receiverPermission)335 public void sendOrderedBroadcast(Intent intent, String receiverPermission) { 336 spiedContext.sendOrderedBroadcast(intent, receiverPermission); 337 } 338 339 @Override sendOrderedBroadcast(Intent intent, String receiverPermission, BroadcastReceiver resultReceiver, Handler scheduler, int initialCode, String initialData, Bundle initialExtras)340 public void sendOrderedBroadcast(Intent intent, String receiverPermission, 341 BroadcastReceiver resultReceiver, Handler scheduler, int initialCode, 342 String initialData, Bundle initialExtras) { 343 spiedContext.sendOrderedBroadcast(intent, receiverPermission, resultReceiver, scheduler, 344 initialCode, initialData, initialExtras); 345 } 346 347 @Override sendOrderedBroadcast(Intent intent, String receiverPermission, Bundle options, BroadcastReceiver resultReceiver, Handler scheduler, int initialCode, String initialData, Bundle initialExtras)348 public void sendOrderedBroadcast(Intent intent, String receiverPermission, Bundle options, 349 BroadcastReceiver resultReceiver, Handler scheduler, int initialCode, 350 String initialData, Bundle initialExtras) { 351 spiedContext.sendOrderedBroadcast(intent, receiverPermission, options, resultReceiver, 352 scheduler, 353 initialCode, initialData, initialExtras); 354 } 355 356 @Override sendOrderedBroadcast(Intent intent, String receiverPermission, int appOp, BroadcastReceiver resultReceiver, Handler scheduler, int initialCode, String initialData, Bundle initialExtras)357 public void sendOrderedBroadcast(Intent intent, String receiverPermission, int appOp, 358 BroadcastReceiver resultReceiver, Handler scheduler, int initialCode, 359 String initialData, Bundle initialExtras) { 360 spiedContext.sendOrderedBroadcast(intent, receiverPermission, appOp, resultReceiver, 361 scheduler, 362 initialCode, initialData, initialExtras); 363 } 364 365 @Override sendBroadcastAsUser(Intent intent, UserHandle user)366 public void sendBroadcastAsUser(Intent intent, UserHandle user) { 367 if (binder.callingPid != SYSTEM_PID) { 368 // Unless called as the system process, can only call if the target user is the 369 // calling user. 370 // (The actual check is more complex; we may need to change it later.) 371 Assert.assertEquals(UserHandle.getUserId(binder.getCallingUid()), user.getIdentifier()); 372 } 373 374 spiedContext.sendBroadcastAsUser(intent, user); 375 } 376 377 @Override sendBroadcastAsUser(Intent intent, UserHandle user, @Nullable String receiverPermission, @Nullable Bundle options)378 public void sendBroadcastAsUser(Intent intent, 379 UserHandle user, @Nullable String receiverPermission, @Nullable Bundle options) { 380 spiedContext.sendBroadcastAsUser(intent, user, receiverPermission, options); 381 } 382 383 @Override sendBroadcastAsUser(Intent intent, UserHandle user, String receiverPermission)384 public void sendBroadcastAsUser(Intent intent, UserHandle user, String receiverPermission) { 385 spiedContext.sendBroadcastAsUser(intent, user, receiverPermission); 386 } 387 388 @Override sendBroadcastAsUser(Intent intent, UserHandle user, String receiverPermission, int appOp)389 public void sendBroadcastAsUser(Intent intent, UserHandle user, String receiverPermission, 390 int appOp) { 391 spiedContext.sendBroadcastAsUser(intent, user, receiverPermission, appOp); 392 } 393 394 @Override sendOrderedBroadcastAsUser(Intent intent, UserHandle user, String receiverPermission, BroadcastReceiver resultReceiver, Handler scheduler, int initialCode, String initialData, Bundle initialExtras)395 public void sendOrderedBroadcastAsUser(Intent intent, UserHandle user, 396 String receiverPermission, BroadcastReceiver resultReceiver, Handler scheduler, 397 int initialCode, String initialData, Bundle initialExtras) { 398 sendOrderedBroadcastAsUser( 399 intent, user, receiverPermission, AppOpsManager.OP_NONE, resultReceiver, 400 scheduler, initialCode, initialData, initialExtras); 401 } 402 403 @Override sendOrderedBroadcastAsUser(Intent intent, UserHandle user, String receiverPermission, int appOp, BroadcastReceiver resultReceiver, Handler scheduler, int initialCode, String initialData, Bundle initialExtras)404 public void sendOrderedBroadcastAsUser(Intent intent, UserHandle user, 405 String receiverPermission, int appOp, BroadcastReceiver resultReceiver, 406 Handler scheduler, int initialCode, String initialData, Bundle initialExtras) { 407 sendOrderedBroadcastAsUser( 408 intent, user, receiverPermission, appOp, null, resultReceiver, 409 scheduler, initialCode, initialData, initialExtras); 410 } 411 412 @Override sendOrderedBroadcastAsUser(Intent intent, UserHandle user, String receiverPermission, int appOp, Bundle options, BroadcastReceiver resultReceiver, Handler scheduler, int initialCode, String initialData, Bundle initialExtras)413 public void sendOrderedBroadcastAsUser(Intent intent, UserHandle user, 414 String receiverPermission, int appOp, Bundle options, BroadcastReceiver resultReceiver, 415 Handler scheduler, int initialCode, String initialData, Bundle initialExtras) { 416 spiedContext.sendOrderedBroadcastAsUser(intent, user, receiverPermission, appOp, options, 417 resultReceiver, scheduler, initialCode, initialData, initialExtras); 418 resultReceiver.onReceive(spiedContext, intent); 419 } 420 421 @Override sendStickyBroadcast(Intent intent)422 public void sendStickyBroadcast(Intent intent) { 423 spiedContext.sendStickyBroadcast(intent); 424 } 425 426 @Override sendStickyOrderedBroadcast(Intent intent, BroadcastReceiver resultReceiver, Handler scheduler, int initialCode, String initialData, Bundle initialExtras)427 public void sendStickyOrderedBroadcast(Intent intent, BroadcastReceiver resultReceiver, 428 Handler scheduler, int initialCode, String initialData, Bundle initialExtras) { 429 spiedContext.sendStickyOrderedBroadcast(intent, resultReceiver, scheduler, initialCode, 430 initialData, initialExtras); 431 } 432 433 @Override removeStickyBroadcast(Intent intent)434 public void removeStickyBroadcast(Intent intent) { 435 spiedContext.removeStickyBroadcast(intent); 436 } 437 438 @Override sendStickyBroadcastAsUser(Intent intent, UserHandle user)439 public void sendStickyBroadcastAsUser(Intent intent, UserHandle user) { 440 spiedContext.sendStickyBroadcastAsUser(intent, user); 441 } 442 443 @Override sendStickyOrderedBroadcastAsUser(Intent intent, UserHandle user, BroadcastReceiver resultReceiver, Handler scheduler, int initialCode, String initialData, Bundle initialExtras)444 public void sendStickyOrderedBroadcastAsUser(Intent intent, UserHandle user, 445 BroadcastReceiver resultReceiver, Handler scheduler, int initialCode, 446 String initialData, Bundle initialExtras) { 447 spiedContext.sendStickyOrderedBroadcastAsUser(intent, user, resultReceiver, scheduler, initialCode, 448 initialData, initialExtras); 449 } 450 451 @Override removeStickyBroadcastAsUser(Intent intent, UserHandle user)452 public void removeStickyBroadcastAsUser(Intent intent, UserHandle user) { 453 spiedContext.removeStickyBroadcastAsUser(intent, user); 454 } 455 456 @Override registerReceiver(BroadcastReceiver receiver, IntentFilter filter)457 public Intent registerReceiver(BroadcastReceiver receiver, IntentFilter filter) { 458 mMockSystemServices.registerReceiver(receiver, filter, null); 459 return spiedContext.registerReceiver(receiver, filter, 460 Context.RECEIVER_EXPORTED_UNAUDITED); 461 } 462 463 @Override registerReceiver(BroadcastReceiver receiver, IntentFilter filter, int flags)464 public Intent registerReceiver(BroadcastReceiver receiver, IntentFilter filter, int flags) { 465 mMockSystemServices.registerReceiver(receiver, filter, null); 466 return spiedContext.registerReceiver(receiver, filter, flags); 467 } 468 469 @Override registerReceiver(BroadcastReceiver receiver, IntentFilter filter, String broadcastPermission, Handler scheduler)470 public Intent registerReceiver(BroadcastReceiver receiver, IntentFilter filter, 471 String broadcastPermission, Handler scheduler) { 472 mMockSystemServices.registerReceiver(receiver, filter, scheduler); 473 return spiedContext.registerReceiver(receiver, filter, broadcastPermission, scheduler); 474 } 475 476 @Override registerReceiverAsUser(BroadcastReceiver receiver, UserHandle user, IntentFilter filter, String broadcastPermission, Handler scheduler)477 public Intent registerReceiverAsUser(BroadcastReceiver receiver, UserHandle user, 478 IntentFilter filter, String broadcastPermission, Handler scheduler) { 479 mMockSystemServices.registerReceiver(receiver, filter, scheduler); 480 return spiedContext.registerReceiverAsUser(receiver, user, filter, broadcastPermission, 481 scheduler); 482 } 483 484 @Override unregisterReceiver(BroadcastReceiver receiver)485 public void unregisterReceiver(BroadcastReceiver receiver) { 486 mMockSystemServices.unregisterReceiver(receiver); 487 spiedContext.unregisterReceiver(receiver); 488 } 489 490 @Override createPackageContextAsUser(String packageName, int flags, UserHandle user)491 public Context createPackageContextAsUser(String packageName, int flags, UserHandle user) 492 throws PackageManager.NameNotFoundException { 493 return mMockSystemServices.createPackageContextAsUser(packageName, flags, user); 494 } 495 496 @Override createContextAsUser(UserHandle user, int flags)497 public Context createContextAsUser(UserHandle user, int flags) { 498 try { 499 return mMockSystemServices.createPackageContextAsUser(packageName, flags, user); 500 } catch (PackageManager.NameNotFoundException e) { 501 throw new IllegalStateException(e); 502 } 503 } 504 505 @Override getContentResolver()506 public ContentResolver getContentResolver() { 507 return mMockSystemServices.contentResolver; 508 } 509 510 @Override getUserId()511 public int getUserId() { 512 return UserHandle.getUserId(binder.getCallingUid()); 513 } 514 515 @Override getMainExecutor()516 public Executor getMainExecutor() { 517 return mMockSystemServices.executor; 518 } 519 520 @Override checkCallingPermission(String permission)521 public int checkCallingPermission(String permission) { 522 return checkPermission(permission); 523 } 524 525 @Override checkCallingOrSelfPermission(String permission)526 public int checkCallingOrSelfPermission(String permission) { 527 return checkPermission(permission); 528 } 529 530 @Override startActivityAsUser(Intent intent, UserHandle userHandle)531 public void startActivityAsUser(Intent intent, UserHandle userHandle) { 532 spiedContext.startActivityAsUser(intent, userHandle); 533 } 534 checkPermission(String permission)535 private int checkPermission(String permission) { 536 if (UserHandle.isSameApp(binder.getCallingUid(), SYSTEM_UID)) { 537 return PackageManager.PERMISSION_GRANTED; // Assume system has all permissions. 538 } 539 List<String> permissions = binder.callingPermissions.get(binder.getCallingUid()); 540 if (permissions == null) { 541 permissions = callerPermissions; 542 } 543 if (permissions.contains(permission)) { 544 return PackageManager.PERMISSION_GRANTED; 545 } else { 546 return PackageManager.PERMISSION_DENIED; 547 } 548 } 549 550 } 551