1 /* 2 * Copyright (C) 2010 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; 18 19 import static android.Manifest.permission.MANAGE_CA_CERTIFICATES; 20 21 import com.android.internal.R; 22 import com.android.internal.os.storage.ExternalStorageFormatter; 23 import com.android.internal.util.FastXmlSerializer; 24 import com.android.internal.util.JournaledFile; 25 import com.android.internal.util.XmlUtils; 26 import com.android.internal.widget.LockPatternUtils; 27 import com.android.org.conscrypt.TrustedCertificateStore; 28 29 import org.xmlpull.v1.XmlPullParser; 30 import org.xmlpull.v1.XmlPullParserException; 31 import org.xmlpull.v1.XmlSerializer; 32 33 import android.app.Activity; 34 import android.app.ActivityManagerNative; 35 import android.app.AlarmManager; 36 import android.app.AppGlobals; 37 import android.app.INotificationManager; 38 import android.app.Notification; 39 import android.app.NotificationManager; 40 import android.app.PendingIntent; 41 import android.app.admin.DeviceAdminInfo; 42 import android.app.admin.DeviceAdminReceiver; 43 import android.app.admin.DevicePolicyManager; 44 import android.app.admin.IDevicePolicyManager; 45 import android.content.BroadcastReceiver; 46 import android.content.ComponentName; 47 import android.content.ContentResolver; 48 import android.content.Context; 49 import android.content.Intent; 50 import android.content.IntentFilter; 51 import android.content.pm.ApplicationInfo; 52 import android.content.pm.IPackageManager; 53 import android.content.pm.PackageInfo; 54 import android.content.pm.PackageManager; 55 import android.content.pm.Signature; 56 import android.content.pm.PackageManager.NameNotFoundException; 57 import android.content.pm.ResolveInfo; 58 import android.content.pm.UserInfo; 59 import android.net.Uri; 60 import android.os.AsyncTask; 61 import android.os.Binder; 62 import android.os.Bundle; 63 import android.os.Environment; 64 import android.os.Handler; 65 import android.os.IBinder; 66 import android.os.IPowerManager; 67 import android.os.PowerManager; 68 import android.os.Process; 69 import android.os.RecoverySystem; 70 import android.os.RemoteCallback; 71 import android.os.RemoteException; 72 import android.os.ServiceManager; 73 import android.os.SystemClock; 74 import android.os.SystemProperties; 75 import android.os.UserHandle; 76 import android.os.UserManager; 77 import android.provider.Settings; 78 import android.security.Credentials; 79 import android.security.IKeyChainService; 80 import android.security.KeyChain; 81 import android.security.KeyChain.KeyChainConnection; 82 import android.util.AtomicFile; 83 import android.util.Log; 84 import android.util.PrintWriterPrinter; 85 import android.util.Printer; 86 import android.util.Slog; 87 import android.util.SparseArray; 88 import android.util.Xml; 89 import android.view.IWindowManager; 90 import android.view.WindowManagerPolicy; 91 92 import java.io.ByteArrayInputStream; 93 import java.io.File; 94 import java.io.FileDescriptor; 95 import java.io.FileInputStream; 96 import java.io.FileNotFoundException; 97 import java.io.FileOutputStream; 98 import java.io.IOException; 99 import java.io.PrintWriter; 100 import java.security.KeyStore.TrustedCertificateEntry; 101 import java.security.cert.CertificateException; 102 import java.security.cert.CertificateFactory; 103 import java.security.cert.X509Certificate; 104 import java.text.DateFormat; 105 import java.util.ArrayList; 106 import java.util.Arrays; 107 import java.util.Collection; 108 import java.util.Collections; 109 import java.util.Date; 110 import java.util.HashMap; 111 import java.util.List; 112 import java.util.Set; 113 114 /** 115 * Implementation of the device policy APIs. 116 */ 117 public class DevicePolicyManagerService extends IDevicePolicyManager.Stub { 118 119 private static final String TAG = "DevicePolicyManagerService"; 120 121 private static final String DEVICE_POLICIES_XML = "device_policies.xml"; 122 123 private static final int REQUEST_EXPIRE_PASSWORD = 5571; 124 125 private static final long MS_PER_DAY = 86400 * 1000; 126 127 private static final long EXPIRATION_GRACE_PERIOD_MS = 5 * MS_PER_DAY; // 5 days, in ms 128 129 protected static final String ACTION_EXPIRED_PASSWORD_NOTIFICATION 130 = "com.android.server.ACTION_EXPIRED_PASSWORD_NOTIFICATION"; 131 132 private static final int MONITORING_CERT_NOTIFICATION_ID = R.string.ssl_ca_cert_warning; 133 134 private static final boolean DBG = false; 135 136 final Context mContext; 137 final PowerManager.WakeLock mWakeLock; 138 139 IPowerManager mIPowerManager; 140 IWindowManager mIWindowManager; 141 NotificationManager mNotificationManager; 142 143 private DeviceOwner mDeviceOwner; 144 145 /** 146 * Whether or not device admin feature is supported. If it isn't return defaults for all 147 * public methods. 148 */ 149 private boolean mHasFeature; 150 151 public static class DevicePolicyData { 152 int mActivePasswordQuality = DevicePolicyManager.PASSWORD_QUALITY_UNSPECIFIED; 153 int mActivePasswordLength = 0; 154 int mActivePasswordUpperCase = 0; 155 int mActivePasswordLowerCase = 0; 156 int mActivePasswordLetters = 0; 157 int mActivePasswordNumeric = 0; 158 int mActivePasswordSymbols = 0; 159 int mActivePasswordNonLetter = 0; 160 int mFailedPasswordAttempts = 0; 161 162 int mUserHandle;; 163 int mPasswordOwner = -1; 164 long mLastMaximumTimeToLock = -1; 165 166 final HashMap<ComponentName, ActiveAdmin> mAdminMap 167 = new HashMap<ComponentName, ActiveAdmin>(); 168 final ArrayList<ActiveAdmin> mAdminList 169 = new ArrayList<ActiveAdmin>(); 170 171 public DevicePolicyData(int userHandle) { 172 mUserHandle = userHandle; 173 } 174 } 175 176 final SparseArray<DevicePolicyData> mUserData = new SparseArray<DevicePolicyData>(); 177 178 Handler mHandler = new Handler(); 179 180 BroadcastReceiver mReceiver = new BroadcastReceiver() { 181 @Override 182 public void onReceive(Context context, Intent intent) { 183 final String action = intent.getAction(); 184 final int userHandle = intent.getIntExtra(Intent.EXTRA_USER_HANDLE, 185 getSendingUserId()); 186 if (Intent.ACTION_BOOT_COMPLETED.equals(action) 187 || ACTION_EXPIRED_PASSWORD_NOTIFICATION.equals(action)) { 188 if (DBG) Slog.v(TAG, "Sending password expiration notifications for action " 189 + action + " for user " + userHandle); 190 mHandler.post(new Runnable() { 191 public void run() { 192 handlePasswordExpirationNotification(getUserData(userHandle)); 193 } 194 }); 195 } 196 if (Intent.ACTION_BOOT_COMPLETED.equals(action) 197 || KeyChain.ACTION_STORAGE_CHANGED.equals(action)) { 198 manageMonitoringCertificateNotification(intent); 199 } 200 if (Intent.ACTION_USER_REMOVED.equals(action)) { 201 removeUserData(userHandle); 202 } else if (Intent.ACTION_USER_STARTED.equals(action) 203 || Intent.ACTION_PACKAGE_CHANGED.equals(action) 204 || Intent.ACTION_PACKAGE_REMOVED.equals(action) 205 || Intent.ACTION_EXTERNAL_APPLICATIONS_UNAVAILABLE.equals(action)) { 206 207 if (Intent.ACTION_USER_STARTED.equals(action)) { 208 // Reset the policy data 209 synchronized (DevicePolicyManagerService.this) { 210 mUserData.remove(userHandle); 211 } 212 } 213 214 handlePackagesChanged(userHandle); 215 } 216 } 217 }; 218 219 static class ActiveAdmin { 220 final DeviceAdminInfo info; 221 222 int passwordQuality = DevicePolicyManager.PASSWORD_QUALITY_UNSPECIFIED; 223 224 static final int DEF_MINIMUM_PASSWORD_LENGTH = 0; 225 int minimumPasswordLength = DEF_MINIMUM_PASSWORD_LENGTH; 226 227 static final int DEF_PASSWORD_HISTORY_LENGTH = 0; 228 int passwordHistoryLength = DEF_PASSWORD_HISTORY_LENGTH; 229 230 static final int DEF_MINIMUM_PASSWORD_UPPER_CASE = 0; 231 int minimumPasswordUpperCase = DEF_MINIMUM_PASSWORD_UPPER_CASE; 232 233 static final int DEF_MINIMUM_PASSWORD_LOWER_CASE = 0; 234 int minimumPasswordLowerCase = DEF_MINIMUM_PASSWORD_LOWER_CASE; 235 236 static final int DEF_MINIMUM_PASSWORD_LETTERS = 1; 237 int minimumPasswordLetters = DEF_MINIMUM_PASSWORD_LETTERS; 238 239 static final int DEF_MINIMUM_PASSWORD_NUMERIC = 1; 240 int minimumPasswordNumeric = DEF_MINIMUM_PASSWORD_NUMERIC; 241 242 static final int DEF_MINIMUM_PASSWORD_SYMBOLS = 1; 243 int minimumPasswordSymbols = DEF_MINIMUM_PASSWORD_SYMBOLS; 244 245 static final int DEF_MINIMUM_PASSWORD_NON_LETTER = 0; 246 int minimumPasswordNonLetter = DEF_MINIMUM_PASSWORD_NON_LETTER; 247 248 static final long DEF_MAXIMUM_TIME_TO_UNLOCK = 0; 249 long maximumTimeToUnlock = DEF_MAXIMUM_TIME_TO_UNLOCK; 250 251 static final int DEF_MAXIMUM_FAILED_PASSWORDS_FOR_WIPE = 0; 252 int maximumFailedPasswordsForWipe = DEF_MAXIMUM_FAILED_PASSWORDS_FOR_WIPE; 253 254 static final long DEF_PASSWORD_EXPIRATION_TIMEOUT = 0; 255 long passwordExpirationTimeout = DEF_PASSWORD_EXPIRATION_TIMEOUT; 256 257 static final long DEF_PASSWORD_EXPIRATION_DATE = 0; 258 long passwordExpirationDate = DEF_PASSWORD_EXPIRATION_DATE; 259 260 static final int DEF_KEYGUARD_FEATURES_DISABLED = 0; // none 261 int disabledKeyguardFeatures = DEF_KEYGUARD_FEATURES_DISABLED; 262 263 boolean encryptionRequested = false; 264 boolean disableCamera = false; 265 266 // TODO: review implementation decisions with frameworks team 267 boolean specifiesGlobalProxy = false; 268 String globalProxySpec = null; 269 String globalProxyExclusionList = null; 270 271 ActiveAdmin(DeviceAdminInfo _info) { 272 info = _info; 273 } 274 275 int getUid() { return info.getActivityInfo().applicationInfo.uid; } 276 277 public UserHandle getUserHandle() { 278 return new UserHandle(UserHandle.getUserId(info.getActivityInfo().applicationInfo.uid)); 279 } 280 281 void writeToXml(XmlSerializer out) 282 throws IllegalArgumentException, IllegalStateException, IOException { 283 out.startTag(null, "policies"); 284 info.writePoliciesToXml(out); 285 out.endTag(null, "policies"); 286 if (passwordQuality != DevicePolicyManager.PASSWORD_QUALITY_UNSPECIFIED) { 287 out.startTag(null, "password-quality"); 288 out.attribute(null, "value", Integer.toString(passwordQuality)); 289 out.endTag(null, "password-quality"); 290 if (minimumPasswordLength != DEF_MINIMUM_PASSWORD_LENGTH) { 291 out.startTag(null, "min-password-length"); 292 out.attribute(null, "value", Integer.toString(minimumPasswordLength)); 293 out.endTag(null, "min-password-length"); 294 } 295 if(passwordHistoryLength != DEF_PASSWORD_HISTORY_LENGTH) { 296 out.startTag(null, "password-history-length"); 297 out.attribute(null, "value", Integer.toString(passwordHistoryLength)); 298 out.endTag(null, "password-history-length"); 299 } 300 if (minimumPasswordUpperCase != DEF_MINIMUM_PASSWORD_UPPER_CASE) { 301 out.startTag(null, "min-password-uppercase"); 302 out.attribute(null, "value", Integer.toString(minimumPasswordUpperCase)); 303 out.endTag(null, "min-password-uppercase"); 304 } 305 if (minimumPasswordLowerCase != DEF_MINIMUM_PASSWORD_LOWER_CASE) { 306 out.startTag(null, "min-password-lowercase"); 307 out.attribute(null, "value", Integer.toString(minimumPasswordLowerCase)); 308 out.endTag(null, "min-password-lowercase"); 309 } 310 if (minimumPasswordLetters != DEF_MINIMUM_PASSWORD_LETTERS) { 311 out.startTag(null, "min-password-letters"); 312 out.attribute(null, "value", Integer.toString(minimumPasswordLetters)); 313 out.endTag(null, "min-password-letters"); 314 } 315 if (minimumPasswordNumeric != DEF_MINIMUM_PASSWORD_NUMERIC) { 316 out.startTag(null, "min-password-numeric"); 317 out.attribute(null, "value", Integer.toString(minimumPasswordNumeric)); 318 out.endTag(null, "min-password-numeric"); 319 } 320 if (minimumPasswordSymbols != DEF_MINIMUM_PASSWORD_SYMBOLS) { 321 out.startTag(null, "min-password-symbols"); 322 out.attribute(null, "value", Integer.toString(minimumPasswordSymbols)); 323 out.endTag(null, "min-password-symbols"); 324 } 325 if (minimumPasswordNonLetter > DEF_MINIMUM_PASSWORD_NON_LETTER) { 326 out.startTag(null, "min-password-nonletter"); 327 out.attribute(null, "value", Integer.toString(minimumPasswordNonLetter)); 328 out.endTag(null, "min-password-nonletter"); 329 } 330 } 331 if (maximumTimeToUnlock != DEF_MAXIMUM_TIME_TO_UNLOCK) { 332 out.startTag(null, "max-time-to-unlock"); 333 out.attribute(null, "value", Long.toString(maximumTimeToUnlock)); 334 out.endTag(null, "max-time-to-unlock"); 335 } 336 if (maximumFailedPasswordsForWipe != DEF_MAXIMUM_FAILED_PASSWORDS_FOR_WIPE) { 337 out.startTag(null, "max-failed-password-wipe"); 338 out.attribute(null, "value", Integer.toString(maximumFailedPasswordsForWipe)); 339 out.endTag(null, "max-failed-password-wipe"); 340 } 341 if (specifiesGlobalProxy) { 342 out.startTag(null, "specifies-global-proxy"); 343 out.attribute(null, "value", Boolean.toString(specifiesGlobalProxy)); 344 out.endTag(null, "specifies_global_proxy"); 345 if (globalProxySpec != null) { 346 out.startTag(null, "global-proxy-spec"); 347 out.attribute(null, "value", globalProxySpec); 348 out.endTag(null, "global-proxy-spec"); 349 } 350 if (globalProxyExclusionList != null) { 351 out.startTag(null, "global-proxy-exclusion-list"); 352 out.attribute(null, "value", globalProxyExclusionList); 353 out.endTag(null, "global-proxy-exclusion-list"); 354 } 355 } 356 if (passwordExpirationTimeout != DEF_PASSWORD_EXPIRATION_TIMEOUT) { 357 out.startTag(null, "password-expiration-timeout"); 358 out.attribute(null, "value", Long.toString(passwordExpirationTimeout)); 359 out.endTag(null, "password-expiration-timeout"); 360 } 361 if (passwordExpirationDate != DEF_PASSWORD_EXPIRATION_DATE) { 362 out.startTag(null, "password-expiration-date"); 363 out.attribute(null, "value", Long.toString(passwordExpirationDate)); 364 out.endTag(null, "password-expiration-date"); 365 } 366 if (encryptionRequested) { 367 out.startTag(null, "encryption-requested"); 368 out.attribute(null, "value", Boolean.toString(encryptionRequested)); 369 out.endTag(null, "encryption-requested"); 370 } 371 if (disableCamera) { 372 out.startTag(null, "disable-camera"); 373 out.attribute(null, "value", Boolean.toString(disableCamera)); 374 out.endTag(null, "disable-camera"); 375 } 376 if (disabledKeyguardFeatures != DEF_KEYGUARD_FEATURES_DISABLED) { 377 out.startTag(null, "disable-keyguard-features"); 378 out.attribute(null, "value", Integer.toString(disabledKeyguardFeatures)); 379 out.endTag(null, "disable-keyguard-features"); 380 } 381 } 382 383 void readFromXml(XmlPullParser parser) 384 throws XmlPullParserException, IOException { 385 int outerDepth = parser.getDepth(); 386 int type; 387 while ((type=parser.next()) != XmlPullParser.END_DOCUMENT 388 && (type != XmlPullParser.END_TAG || parser.getDepth() > outerDepth)) { 389 if (type == XmlPullParser.END_TAG || type == XmlPullParser.TEXT) { 390 continue; 391 } 392 String tag = parser.getName(); 393 if ("policies".equals(tag)) { 394 info.readPoliciesFromXml(parser); 395 } else if ("password-quality".equals(tag)) { 396 passwordQuality = Integer.parseInt( 397 parser.getAttributeValue(null, "value")); 398 } else if ("min-password-length".equals(tag)) { 399 minimumPasswordLength = Integer.parseInt( 400 parser.getAttributeValue(null, "value")); 401 } else if ("password-history-length".equals(tag)) { 402 passwordHistoryLength = Integer.parseInt( 403 parser.getAttributeValue(null, "value")); 404 } else if ("min-password-uppercase".equals(tag)) { 405 minimumPasswordUpperCase = Integer.parseInt( 406 parser.getAttributeValue(null, "value")); 407 } else if ("min-password-lowercase".equals(tag)) { 408 minimumPasswordLowerCase = Integer.parseInt( 409 parser.getAttributeValue(null, "value")); 410 } else if ("min-password-letters".equals(tag)) { 411 minimumPasswordLetters = Integer.parseInt( 412 parser.getAttributeValue(null, "value")); 413 } else if ("min-password-numeric".equals(tag)) { 414 minimumPasswordNumeric = Integer.parseInt( 415 parser.getAttributeValue(null, "value")); 416 } else if ("min-password-symbols".equals(tag)) { 417 minimumPasswordSymbols = Integer.parseInt( 418 parser.getAttributeValue(null, "value")); 419 } else if ("min-password-nonletter".equals(tag)) { 420 minimumPasswordNonLetter = Integer.parseInt( 421 parser.getAttributeValue(null, "value")); 422 } else if ("max-time-to-unlock".equals(tag)) { 423 maximumTimeToUnlock = Long.parseLong( 424 parser.getAttributeValue(null, "value")); 425 } else if ("max-failed-password-wipe".equals(tag)) { 426 maximumFailedPasswordsForWipe = Integer.parseInt( 427 parser.getAttributeValue(null, "value")); 428 } else if ("specifies-global-proxy".equals(tag)) { 429 specifiesGlobalProxy = Boolean.parseBoolean( 430 parser.getAttributeValue(null, "value")); 431 } else if ("global-proxy-spec".equals(tag)) { 432 globalProxySpec = 433 parser.getAttributeValue(null, "value"); 434 } else if ("global-proxy-exclusion-list".equals(tag)) { 435 globalProxyExclusionList = 436 parser.getAttributeValue(null, "value"); 437 } else if ("password-expiration-timeout".equals(tag)) { 438 passwordExpirationTimeout = Long.parseLong( 439 parser.getAttributeValue(null, "value")); 440 } else if ("password-expiration-date".equals(tag)) { 441 passwordExpirationDate = Long.parseLong( 442 parser.getAttributeValue(null, "value")); 443 } else if ("encryption-requested".equals(tag)) { 444 encryptionRequested = Boolean.parseBoolean( 445 parser.getAttributeValue(null, "value")); 446 } else if ("disable-camera".equals(tag)) { 447 disableCamera = Boolean.parseBoolean( 448 parser.getAttributeValue(null, "value")); 449 } else if ("disable-keyguard-features".equals(tag)) { 450 disabledKeyguardFeatures = Integer.parseInt( 451 parser.getAttributeValue(null, "value")); 452 } else { 453 Slog.w(TAG, "Unknown admin tag: " + tag); 454 } 455 XmlUtils.skipCurrentTag(parser); 456 } 457 } 458 459 void dump(String prefix, PrintWriter pw) { 460 pw.print(prefix); pw.print("uid="); pw.println(getUid()); 461 pw.print(prefix); pw.println("policies:"); 462 ArrayList<DeviceAdminInfo.PolicyInfo> pols = info.getUsedPolicies(); 463 if (pols != null) { 464 for (int i=0; i<pols.size(); i++) { 465 pw.print(prefix); pw.print(" "); pw.println(pols.get(i).tag); 466 } 467 } 468 pw.print(prefix); pw.print("passwordQuality=0x"); 469 pw.println(Integer.toHexString(passwordQuality)); 470 pw.print(prefix); pw.print("minimumPasswordLength="); 471 pw.println(minimumPasswordLength); 472 pw.print(prefix); pw.print("passwordHistoryLength="); 473 pw.println(passwordHistoryLength); 474 pw.print(prefix); pw.print("minimumPasswordUpperCase="); 475 pw.println(minimumPasswordUpperCase); 476 pw.print(prefix); pw.print("minimumPasswordLowerCase="); 477 pw.println(minimumPasswordLowerCase); 478 pw.print(prefix); pw.print("minimumPasswordLetters="); 479 pw.println(minimumPasswordLetters); 480 pw.print(prefix); pw.print("minimumPasswordNumeric="); 481 pw.println(minimumPasswordNumeric); 482 pw.print(prefix); pw.print("minimumPasswordSymbols="); 483 pw.println(minimumPasswordSymbols); 484 pw.print(prefix); pw.print("minimumPasswordNonLetter="); 485 pw.println(minimumPasswordNonLetter); 486 pw.print(prefix); pw.print("maximumTimeToUnlock="); 487 pw.println(maximumTimeToUnlock); 488 pw.print(prefix); pw.print("maximumFailedPasswordsForWipe="); 489 pw.println(maximumFailedPasswordsForWipe); 490 pw.print(prefix); pw.print("specifiesGlobalProxy="); 491 pw.println(specifiesGlobalProxy); 492 pw.print(prefix); pw.print("passwordExpirationTimeout="); 493 pw.println(passwordExpirationTimeout); 494 pw.print(prefix); pw.print("passwordExpirationDate="); 495 pw.println(passwordExpirationDate); 496 if (globalProxySpec != null) { 497 pw.print(prefix); pw.print("globalProxySpec="); 498 pw.println(globalProxySpec); 499 } 500 if (globalProxyExclusionList != null) { 501 pw.print(prefix); pw.print("globalProxyEclusionList="); 502 pw.println(globalProxyExclusionList); 503 } 504 pw.print(prefix); pw.print("encryptionRequested="); 505 pw.println(encryptionRequested); 506 pw.print(prefix); pw.print("disableCamera="); 507 pw.println(disableCamera); 508 pw.print(prefix); pw.print("disabledKeyguardFeatures="); 509 pw.println(disabledKeyguardFeatures); 510 } 511 } 512 513 private void handlePackagesChanged(int userHandle) { 514 boolean removed = false; 515 if (DBG) Slog.d(TAG, "Handling package changes for user " + userHandle); 516 DevicePolicyData policy = getUserData(userHandle); 517 IPackageManager pm = AppGlobals.getPackageManager(); 518 for (int i = policy.mAdminList.size() - 1; i >= 0; i--) { 519 ActiveAdmin aa = policy.mAdminList.get(i); 520 try { 521 if (pm.getPackageInfo(aa.info.getPackageName(), 0, userHandle) == null 522 || pm.getReceiverInfo(aa.info.getComponent(), 0, userHandle) == null) { 523 removed = true; 524 policy.mAdminList.remove(i); 525 } 526 } catch (RemoteException re) { 527 // Shouldn't happen 528 } 529 } 530 if (removed) { 531 validatePasswordOwnerLocked(policy); 532 syncDeviceCapabilitiesLocked(policy); 533 saveSettingsLocked(policy.mUserHandle); 534 } 535 } 536 537 /** 538 * Instantiates the service. 539 */ 540 public DevicePolicyManagerService(Context context) { 541 mContext = context; 542 mHasFeature = context.getPackageManager().hasSystemFeature( 543 PackageManager.FEATURE_DEVICE_ADMIN); 544 mWakeLock = ((PowerManager)context.getSystemService(Context.POWER_SERVICE)) 545 .newWakeLock(PowerManager.PARTIAL_WAKE_LOCK, "DPM"); 546 if (!mHasFeature) { 547 // Skip the rest of the initialization 548 return; 549 } 550 IntentFilter filter = new IntentFilter(); 551 filter.addAction(Intent.ACTION_BOOT_COMPLETED); 552 filter.addAction(ACTION_EXPIRED_PASSWORD_NOTIFICATION); 553 filter.addAction(Intent.ACTION_USER_REMOVED); 554 filter.addAction(Intent.ACTION_USER_STARTED); 555 filter.addAction(KeyChain.ACTION_STORAGE_CHANGED); 556 context.registerReceiverAsUser(mReceiver, UserHandle.ALL, filter, null, mHandler); 557 filter = new IntentFilter(); 558 filter.addAction(Intent.ACTION_PACKAGE_CHANGED); 559 filter.addAction(Intent.ACTION_PACKAGE_REMOVED); 560 filter.addAction(Intent.ACTION_EXTERNAL_APPLICATIONS_UNAVAILABLE); 561 filter.addAction(Intent.ACTION_PACKAGE_ADDED); 562 filter.addDataScheme("package"); 563 context.registerReceiverAsUser(mReceiver, UserHandle.ALL, filter, null, mHandler); 564 } 565 566 /** 567 * Creates and loads the policy data from xml. 568 * @param userHandle the user for whom to load the policy data 569 * @return 570 */ 571 DevicePolicyData getUserData(int userHandle) { 572 synchronized (this) { 573 DevicePolicyData policy = mUserData.get(userHandle); 574 if (policy == null) { 575 policy = new DevicePolicyData(userHandle); 576 mUserData.append(userHandle, policy); 577 loadSettingsLocked(policy, userHandle); 578 } 579 return policy; 580 } 581 } 582 583 void removeUserData(int userHandle) { 584 synchronized (this) { 585 if (userHandle == UserHandle.USER_OWNER) { 586 Slog.w(TAG, "Tried to remove device policy file for user 0! Ignoring."); 587 return; 588 } 589 DevicePolicyData policy = mUserData.get(userHandle); 590 if (policy != null) { 591 mUserData.remove(userHandle); 592 } 593 File policyFile = new File(Environment.getUserSystemDirectory(userHandle), 594 DEVICE_POLICIES_XML); 595 policyFile.delete(); 596 Slog.i(TAG, "Removed device policy file " + policyFile.getAbsolutePath()); 597 } 598 } 599 600 void loadDeviceOwner() { 601 synchronized (this) { 602 if (DeviceOwner.isRegistered()) { 603 mDeviceOwner = new DeviceOwner(); 604 } 605 } 606 } 607 608 /** 609 * Set an alarm for an upcoming event - expiration warning, expiration, or post-expiration 610 * reminders. Clears alarm if no expirations are configured. 611 */ 612 protected void setExpirationAlarmCheckLocked(Context context, DevicePolicyData policy) { 613 final long expiration = getPasswordExpirationLocked(null, policy.mUserHandle); 614 final long now = System.currentTimeMillis(); 615 final long timeToExpire = expiration - now; 616 final long alarmTime; 617 if (expiration == 0) { 618 // No expirations are currently configured: Cancel alarm. 619 alarmTime = 0; 620 } else if (timeToExpire <= 0) { 621 // The password has already expired: Repeat every 24 hours. 622 alarmTime = now + MS_PER_DAY; 623 } else { 624 // Selecting the next alarm time: Roll forward to the next 24 hour multiple before 625 // the expiration time. 626 long alarmInterval = timeToExpire % MS_PER_DAY; 627 if (alarmInterval == 0) { 628 alarmInterval = MS_PER_DAY; 629 } 630 alarmTime = now + alarmInterval; 631 } 632 633 long token = Binder.clearCallingIdentity(); 634 try { 635 AlarmManager am = (AlarmManager) context.getSystemService(Context.ALARM_SERVICE); 636 PendingIntent pi = PendingIntent.getBroadcastAsUser(context, REQUEST_EXPIRE_PASSWORD, 637 new Intent(ACTION_EXPIRED_PASSWORD_NOTIFICATION), 638 PendingIntent.FLAG_ONE_SHOT | PendingIntent.FLAG_UPDATE_CURRENT, 639 new UserHandle(policy.mUserHandle)); 640 am.cancel(pi); 641 if (alarmTime != 0) { 642 am.set(AlarmManager.RTC, alarmTime, pi); 643 } 644 } finally { 645 Binder.restoreCallingIdentity(token); 646 } 647 } 648 649 private IPowerManager getIPowerManager() { 650 if (mIPowerManager == null) { 651 IBinder b = ServiceManager.getService(Context.POWER_SERVICE); 652 mIPowerManager = IPowerManager.Stub.asInterface(b); 653 } 654 return mIPowerManager; 655 } 656 657 private IWindowManager getWindowManager() { 658 if (mIWindowManager == null) { 659 IBinder b = ServiceManager.getService(Context.WINDOW_SERVICE); 660 mIWindowManager = IWindowManager.Stub.asInterface(b); 661 } 662 return mIWindowManager; 663 } 664 665 private NotificationManager getNotificationManager() { 666 if (mNotificationManager == null) { 667 mNotificationManager = 668 (NotificationManager) mContext.getSystemService(Context.NOTIFICATION_SERVICE); 669 } 670 return mNotificationManager; 671 } 672 673 ActiveAdmin getActiveAdminUncheckedLocked(ComponentName who, int userHandle) { 674 ActiveAdmin admin = getUserData(userHandle).mAdminMap.get(who); 675 if (admin != null 676 && who.getPackageName().equals(admin.info.getActivityInfo().packageName) 677 && who.getClassName().equals(admin.info.getActivityInfo().name)) { 678 return admin; 679 } 680 return null; 681 } 682 683 ActiveAdmin getActiveAdminForCallerLocked(ComponentName who, int reqPolicy) 684 throws SecurityException { 685 final int callingUid = Binder.getCallingUid(); 686 final int userHandle = UserHandle.getUserId(callingUid); 687 final DevicePolicyData policy = getUserData(userHandle); 688 if (who != null) { 689 ActiveAdmin admin = policy.mAdminMap.get(who); 690 if (admin == null) { 691 throw new SecurityException("No active admin " + who); 692 } 693 if (admin.getUid() != callingUid) { 694 throw new SecurityException("Admin " + who + " is not owned by uid " 695 + Binder.getCallingUid()); 696 } 697 if (!admin.info.usesPolicy(reqPolicy)) { 698 throw new SecurityException("Admin " + admin.info.getComponent() 699 + " did not specify uses-policy for: " 700 + admin.info.getTagForPolicy(reqPolicy)); 701 } 702 return admin; 703 } else { 704 final int N = policy.mAdminList.size(); 705 for (int i=0; i<N; i++) { 706 ActiveAdmin admin = policy.mAdminList.get(i); 707 if (admin.getUid() == callingUid && admin.info.usesPolicy(reqPolicy)) { 708 return admin; 709 } 710 } 711 throw new SecurityException("No active admin owned by uid " 712 + Binder.getCallingUid() + " for policy #" + reqPolicy); 713 } 714 } 715 716 void sendAdminCommandLocked(ActiveAdmin admin, String action) { 717 sendAdminCommandLocked(admin, action, null); 718 } 719 720 void sendAdminCommandLocked(ActiveAdmin admin, String action, BroadcastReceiver result) { 721 Intent intent = new Intent(action); 722 intent.setComponent(admin.info.getComponent()); 723 if (action.equals(DeviceAdminReceiver.ACTION_PASSWORD_EXPIRING)) { 724 intent.putExtra("expiration", admin.passwordExpirationDate); 725 } 726 if (result != null) { 727 mContext.sendOrderedBroadcastAsUser(intent, admin.getUserHandle(), 728 null, result, mHandler, Activity.RESULT_OK, null, null); 729 } else { 730 mContext.sendBroadcastAsUser(intent, UserHandle.OWNER); 731 } 732 } 733 734 void sendAdminCommandLocked(String action, int reqPolicy, int userHandle) { 735 final DevicePolicyData policy = getUserData(userHandle); 736 final int count = policy.mAdminList.size(); 737 if (count > 0) { 738 for (int i = 0; i < count; i++) { 739 ActiveAdmin admin = policy.mAdminList.get(i); 740 if (admin.info.usesPolicy(reqPolicy)) { 741 sendAdminCommandLocked(admin, action); 742 } 743 } 744 } 745 } 746 747 void removeActiveAdminLocked(final ComponentName adminReceiver, int userHandle) { 748 final ActiveAdmin admin = getActiveAdminUncheckedLocked(adminReceiver, userHandle); 749 if (admin != null) { 750 sendAdminCommandLocked(admin, 751 DeviceAdminReceiver.ACTION_DEVICE_ADMIN_DISABLED, 752 new BroadcastReceiver() { 753 @Override 754 public void onReceive(Context context, Intent intent) { 755 synchronized (DevicePolicyManagerService.this) { 756 int userHandle = admin.getUserHandle().getIdentifier(); 757 DevicePolicyData policy = getUserData(userHandle); 758 boolean doProxyCleanup = admin.info.usesPolicy( 759 DeviceAdminInfo.USES_POLICY_SETS_GLOBAL_PROXY); 760 policy.mAdminList.remove(admin); 761 policy.mAdminMap.remove(adminReceiver); 762 validatePasswordOwnerLocked(policy); 763 syncDeviceCapabilitiesLocked(policy); 764 if (doProxyCleanup) { 765 resetGlobalProxyLocked(getUserData(userHandle)); 766 } 767 saveSettingsLocked(userHandle); 768 updateMaximumTimeToLockLocked(policy); 769 } 770 } 771 }); 772 } 773 } 774 775 public DeviceAdminInfo findAdmin(ComponentName adminName, int userHandle) { 776 if (!mHasFeature) { 777 return null; 778 } 779 enforceCrossUserPermission(userHandle); 780 Intent resolveIntent = new Intent(); 781 resolveIntent.setComponent(adminName); 782 List<ResolveInfo> infos = mContext.getPackageManager().queryBroadcastReceivers( 783 resolveIntent, 784 PackageManager.GET_META_DATA | PackageManager.GET_DISABLED_UNTIL_USED_COMPONENTS, 785 userHandle); 786 if (infos == null || infos.size() <= 0) { 787 throw new IllegalArgumentException("Unknown admin: " + adminName); 788 } 789 790 try { 791 return new DeviceAdminInfo(mContext, infos.get(0)); 792 } catch (XmlPullParserException e) { 793 Slog.w(TAG, "Bad device admin requested for user=" + userHandle + ": " + adminName, e); 794 return null; 795 } catch (IOException e) { 796 Slog.w(TAG, "Bad device admin requested for user=" + userHandle + ": " + adminName, e); 797 return null; 798 } 799 } 800 801 private static JournaledFile makeJournaledFile(int userHandle) { 802 final String base = userHandle == 0 803 ? "/data/system/" + DEVICE_POLICIES_XML 804 : new File(Environment.getUserSystemDirectory(userHandle), DEVICE_POLICIES_XML) 805 .getAbsolutePath(); 806 return new JournaledFile(new File(base), new File(base + ".tmp")); 807 } 808 809 private void saveSettingsLocked(int userHandle) { 810 DevicePolicyData policy = getUserData(userHandle); 811 JournaledFile journal = makeJournaledFile(userHandle); 812 FileOutputStream stream = null; 813 try { 814 stream = new FileOutputStream(journal.chooseForWrite(), false); 815 XmlSerializer out = new FastXmlSerializer(); 816 out.setOutput(stream, "utf-8"); 817 out.startDocument(null, true); 818 819 out.startTag(null, "policies"); 820 821 final int N = policy.mAdminList.size(); 822 for (int i=0; i<N; i++) { 823 ActiveAdmin ap = policy.mAdminList.get(i); 824 if (ap != null) { 825 out.startTag(null, "admin"); 826 out.attribute(null, "name", ap.info.getComponent().flattenToString()); 827 ap.writeToXml(out); 828 out.endTag(null, "admin"); 829 } 830 } 831 832 if (policy.mPasswordOwner >= 0) { 833 out.startTag(null, "password-owner"); 834 out.attribute(null, "value", Integer.toString(policy.mPasswordOwner)); 835 out.endTag(null, "password-owner"); 836 } 837 838 if (policy.mFailedPasswordAttempts != 0) { 839 out.startTag(null, "failed-password-attempts"); 840 out.attribute(null, "value", Integer.toString(policy.mFailedPasswordAttempts)); 841 out.endTag(null, "failed-password-attempts"); 842 } 843 844 if (policy.mActivePasswordQuality != 0 || policy.mActivePasswordLength != 0 845 || policy.mActivePasswordUpperCase != 0 || policy.mActivePasswordLowerCase != 0 846 || policy.mActivePasswordLetters != 0 || policy.mActivePasswordNumeric != 0 847 || policy.mActivePasswordSymbols != 0 || policy.mActivePasswordNonLetter != 0) { 848 out.startTag(null, "active-password"); 849 out.attribute(null, "quality", Integer.toString(policy.mActivePasswordQuality)); 850 out.attribute(null, "length", Integer.toString(policy.mActivePasswordLength)); 851 out.attribute(null, "uppercase", Integer.toString(policy.mActivePasswordUpperCase)); 852 out.attribute(null, "lowercase", Integer.toString(policy.mActivePasswordLowerCase)); 853 out.attribute(null, "letters", Integer.toString(policy.mActivePasswordLetters)); 854 out.attribute(null, "numeric", Integer 855 .toString(policy.mActivePasswordNumeric)); 856 out.attribute(null, "symbols", Integer.toString(policy.mActivePasswordSymbols)); 857 out.attribute(null, "nonletter", Integer.toString(policy.mActivePasswordNonLetter)); 858 out.endTag(null, "active-password"); 859 } 860 861 out.endTag(null, "policies"); 862 863 out.endDocument(); 864 stream.close(); 865 journal.commit(); 866 sendChangedNotification(userHandle); 867 } catch (IOException e) { 868 try { 869 if (stream != null) { 870 stream.close(); 871 } 872 } catch (IOException ex) { 873 // Ignore 874 } 875 journal.rollback(); 876 } 877 } 878 879 private void sendChangedNotification(int userHandle) { 880 Intent intent = new Intent(DevicePolicyManager.ACTION_DEVICE_POLICY_MANAGER_STATE_CHANGED); 881 intent.setFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY); 882 long ident = Binder.clearCallingIdentity(); 883 try { 884 mContext.sendBroadcastAsUser(intent, new UserHandle(userHandle)); 885 } finally { 886 Binder.restoreCallingIdentity(ident); 887 } 888 } 889 890 private void loadSettingsLocked(DevicePolicyData policy, int userHandle) { 891 JournaledFile journal = makeJournaledFile(userHandle); 892 FileInputStream stream = null; 893 File file = journal.chooseForRead(); 894 try { 895 stream = new FileInputStream(file); 896 XmlPullParser parser = Xml.newPullParser(); 897 parser.setInput(stream, null); 898 899 int type; 900 while ((type=parser.next()) != XmlPullParser.END_DOCUMENT 901 && type != XmlPullParser.START_TAG) { 902 } 903 String tag = parser.getName(); 904 if (!"policies".equals(tag)) { 905 throw new XmlPullParserException( 906 "Settings do not start with policies tag: found " + tag); 907 } 908 type = parser.next(); 909 int outerDepth = parser.getDepth(); 910 while ((type=parser.next()) != XmlPullParser.END_DOCUMENT 911 && (type != XmlPullParser.END_TAG || parser.getDepth() > outerDepth)) { 912 if (type == XmlPullParser.END_TAG || type == XmlPullParser.TEXT) { 913 continue; 914 } 915 tag = parser.getName(); 916 if ("admin".equals(tag)) { 917 String name = parser.getAttributeValue(null, "name"); 918 try { 919 DeviceAdminInfo dai = findAdmin( 920 ComponentName.unflattenFromString(name), userHandle); 921 if (DBG && (UserHandle.getUserId(dai.getActivityInfo().applicationInfo.uid) 922 != userHandle)) { 923 Slog.w(TAG, "findAdmin returned an incorrect uid " 924 + dai.getActivityInfo().applicationInfo.uid + " for user " 925 + userHandle); 926 } 927 if (dai != null) { 928 ActiveAdmin ap = new ActiveAdmin(dai); 929 ap.readFromXml(parser); 930 policy.mAdminMap.put(ap.info.getComponent(), ap); 931 policy.mAdminList.add(ap); 932 } 933 } catch (RuntimeException e) { 934 Slog.w(TAG, "Failed loading admin " + name, e); 935 } 936 } else if ("failed-password-attempts".equals(tag)) { 937 policy.mFailedPasswordAttempts = Integer.parseInt( 938 parser.getAttributeValue(null, "value")); 939 XmlUtils.skipCurrentTag(parser); 940 } else if ("password-owner".equals(tag)) { 941 policy.mPasswordOwner = Integer.parseInt( 942 parser.getAttributeValue(null, "value")); 943 XmlUtils.skipCurrentTag(parser); 944 } else if ("active-password".equals(tag)) { 945 policy.mActivePasswordQuality = Integer.parseInt( 946 parser.getAttributeValue(null, "quality")); 947 policy.mActivePasswordLength = Integer.parseInt( 948 parser.getAttributeValue(null, "length")); 949 policy.mActivePasswordUpperCase = Integer.parseInt( 950 parser.getAttributeValue(null, "uppercase")); 951 policy.mActivePasswordLowerCase = Integer.parseInt( 952 parser.getAttributeValue(null, "lowercase")); 953 policy.mActivePasswordLetters = Integer.parseInt( 954 parser.getAttributeValue(null, "letters")); 955 policy.mActivePasswordNumeric = Integer.parseInt( 956 parser.getAttributeValue(null, "numeric")); 957 policy.mActivePasswordSymbols = Integer.parseInt( 958 parser.getAttributeValue(null, "symbols")); 959 policy.mActivePasswordNonLetter = Integer.parseInt( 960 parser.getAttributeValue(null, "nonletter")); 961 XmlUtils.skipCurrentTag(parser); 962 } else { 963 Slog.w(TAG, "Unknown tag: " + tag); 964 XmlUtils.skipCurrentTag(parser); 965 } 966 } 967 } catch (NullPointerException e) { 968 Slog.w(TAG, "failed parsing " + file + " " + e); 969 } catch (NumberFormatException e) { 970 Slog.w(TAG, "failed parsing " + file + " " + e); 971 } catch (XmlPullParserException e) { 972 Slog.w(TAG, "failed parsing " + file + " " + e); 973 } catch (FileNotFoundException e) { 974 // Don't be noisy, this is normal if we haven't defined any policies. 975 } catch (IOException e) { 976 Slog.w(TAG, "failed parsing " + file + " " + e); 977 } catch (IndexOutOfBoundsException e) { 978 Slog.w(TAG, "failed parsing " + file + " " + e); 979 } 980 try { 981 if (stream != null) { 982 stream.close(); 983 } 984 } catch (IOException e) { 985 // Ignore 986 } 987 988 // Validate that what we stored for the password quality matches 989 // sufficiently what is currently set. Note that this is only 990 // a sanity check in case the two get out of sync; this should 991 // never normally happen. 992 LockPatternUtils utils = new LockPatternUtils(mContext); 993 if (utils.getActivePasswordQuality() < policy.mActivePasswordQuality) { 994 Slog.w(TAG, "Active password quality 0x" 995 + Integer.toHexString(policy.mActivePasswordQuality) 996 + " does not match actual quality 0x" 997 + Integer.toHexString(utils.getActivePasswordQuality())); 998 policy.mActivePasswordQuality = DevicePolicyManager.PASSWORD_QUALITY_UNSPECIFIED; 999 policy.mActivePasswordLength = 0; 1000 policy.mActivePasswordUpperCase = 0; 1001 policy.mActivePasswordLowerCase = 0; 1002 policy.mActivePasswordLetters = 0; 1003 policy.mActivePasswordNumeric = 0; 1004 policy.mActivePasswordSymbols = 0; 1005 policy.mActivePasswordNonLetter = 0; 1006 } 1007 1008 validatePasswordOwnerLocked(policy); 1009 syncDeviceCapabilitiesLocked(policy); 1010 updateMaximumTimeToLockLocked(policy); 1011 } 1012 1013 static void validateQualityConstant(int quality) { 1014 switch (quality) { 1015 case DevicePolicyManager.PASSWORD_QUALITY_UNSPECIFIED: 1016 case DevicePolicyManager.PASSWORD_QUALITY_BIOMETRIC_WEAK: 1017 case DevicePolicyManager.PASSWORD_QUALITY_SOMETHING: 1018 case DevicePolicyManager.PASSWORD_QUALITY_NUMERIC: 1019 case DevicePolicyManager.PASSWORD_QUALITY_ALPHABETIC: 1020 case DevicePolicyManager.PASSWORD_QUALITY_ALPHANUMERIC: 1021 case DevicePolicyManager.PASSWORD_QUALITY_COMPLEX: 1022 return; 1023 } 1024 throw new IllegalArgumentException("Invalid quality constant: 0x" 1025 + Integer.toHexString(quality)); 1026 } 1027 1028 void validatePasswordOwnerLocked(DevicePolicyData policy) { 1029 if (policy.mPasswordOwner >= 0) { 1030 boolean haveOwner = false; 1031 for (int i = policy.mAdminList.size() - 1; i >= 0; i--) { 1032 if (policy.mAdminList.get(i).getUid() == policy.mPasswordOwner) { 1033 haveOwner = true; 1034 break; 1035 } 1036 } 1037 if (!haveOwner) { 1038 Slog.w(TAG, "Previous password owner " + policy.mPasswordOwner 1039 + " no longer active; disabling"); 1040 policy.mPasswordOwner = -1; 1041 } 1042 } 1043 } 1044 1045 /** 1046 * Pushes down policy information to the system for any policies related to general device 1047 * capabilities that need to be enforced by lower level services (e.g. Camera services). 1048 */ 1049 void syncDeviceCapabilitiesLocked(DevicePolicyData policy) { 1050 // Ensure the status of the camera is synced down to the system. Interested native services 1051 // should monitor this value and act accordingly. 1052 boolean systemState = SystemProperties.getBoolean(SYSTEM_PROP_DISABLE_CAMERA, false); 1053 boolean cameraDisabled = getCameraDisabled(null, policy.mUserHandle); 1054 if (cameraDisabled != systemState) { 1055 long token = Binder.clearCallingIdentity(); 1056 try { 1057 String value = cameraDisabled ? "1" : "0"; 1058 if (DBG) Slog.v(TAG, "Change in camera state [" 1059 + SYSTEM_PROP_DISABLE_CAMERA + "] = " + value); 1060 SystemProperties.set(SYSTEM_PROP_DISABLE_CAMERA, value); 1061 } finally { 1062 Binder.restoreCallingIdentity(token); 1063 } 1064 } 1065 } 1066 1067 public void systemReady() { 1068 if (!mHasFeature) { 1069 return; 1070 } 1071 synchronized (this) { 1072 loadSettingsLocked(getUserData(UserHandle.USER_OWNER), UserHandle.USER_OWNER); 1073 loadDeviceOwner(); 1074 } 1075 } 1076 1077 private void handlePasswordExpirationNotification(DevicePolicyData policy) { 1078 synchronized (this) { 1079 final long now = System.currentTimeMillis(); 1080 final int N = policy.mAdminList.size(); 1081 if (N <= 0) { 1082 return; 1083 } 1084 for (int i=0; i < N; i++) { 1085 ActiveAdmin admin = policy.mAdminList.get(i); 1086 if (admin.info.usesPolicy(DeviceAdminInfo.USES_POLICY_EXPIRE_PASSWORD) 1087 && admin.passwordExpirationTimeout > 0L 1088 && admin.passwordExpirationDate > 0L 1089 && now >= admin.passwordExpirationDate - EXPIRATION_GRACE_PERIOD_MS) { 1090 sendAdminCommandLocked(admin, DeviceAdminReceiver.ACTION_PASSWORD_EXPIRING); 1091 } 1092 } 1093 setExpirationAlarmCheckLocked(mContext, policy); 1094 } 1095 } 1096 1097 private void manageMonitoringCertificateNotification(Intent intent) { 1098 final NotificationManager notificationManager = getNotificationManager(); 1099 1100 final boolean hasCert = DevicePolicyManager.hasAnyCaCertsInstalled(); 1101 if (! hasCert) { 1102 if (intent.getAction().equals(KeyChain.ACTION_STORAGE_CHANGED)) { 1103 UserManager um = (UserManager) mContext.getSystemService(Context.USER_SERVICE); 1104 for (UserInfo user : um.getUsers()) { 1105 notificationManager.cancelAsUser( 1106 null, MONITORING_CERT_NOTIFICATION_ID, user.getUserHandle()); 1107 } 1108 } 1109 return; 1110 } 1111 final boolean isManaged = getDeviceOwner() != null; 1112 int smallIconId; 1113 String contentText; 1114 if (isManaged) { 1115 contentText = mContext.getString(R.string.ssl_ca_cert_noti_managed, 1116 getDeviceOwnerName()); 1117 smallIconId = R.drawable.stat_sys_certificate_info; 1118 } else { 1119 contentText = mContext.getString(R.string.ssl_ca_cert_noti_by_unknown); 1120 smallIconId = android.R.drawable.stat_sys_warning; 1121 } 1122 1123 Intent dialogIntent = new Intent(Settings.ACTION_MONITORING_CERT_INFO); 1124 dialogIntent.setFlags(Intent.FLAG_ACTIVITY_NEW_TASK | Intent.FLAG_ACTIVITY_CLEAR_TASK); 1125 dialogIntent.setPackage("com.android.settings"); 1126 // Notification will be sent individually to all users. The activity should start as 1127 // whichever user is current when it starts. 1128 PendingIntent notifyIntent = PendingIntent.getActivityAsUser(mContext, 0, dialogIntent, 1129 PendingIntent.FLAG_UPDATE_CURRENT, null, UserHandle.CURRENT); 1130 1131 Notification noti = new Notification.Builder(mContext) 1132 .setSmallIcon(smallIconId) 1133 .setContentTitle(mContext.getString(R.string.ssl_ca_cert_warning)) 1134 .setContentText(contentText) 1135 .setContentIntent(notifyIntent) 1136 .setPriority(Notification.PRIORITY_HIGH) 1137 .setShowWhen(false) 1138 .build(); 1139 1140 // If this is a boot intent, this will fire for each user. But if this is a storage changed 1141 // intent, it will fire once, so we need to notify all users. 1142 if (intent.getAction().equals(KeyChain.ACTION_STORAGE_CHANGED)) { 1143 UserManager um = (UserManager) mContext.getSystemService(Context.USER_SERVICE); 1144 for (UserInfo user : um.getUsers()) { 1145 notificationManager.notifyAsUser( 1146 null, MONITORING_CERT_NOTIFICATION_ID, noti, user.getUserHandle()); 1147 } 1148 } else { 1149 notificationManager.notifyAsUser( 1150 null, MONITORING_CERT_NOTIFICATION_ID, noti, UserHandle.CURRENT); 1151 } 1152 } 1153 1154 /** 1155 * @param adminReceiver The admin to add 1156 * @param refreshing true = update an active admin, no error 1157 */ 1158 public void setActiveAdmin(ComponentName adminReceiver, boolean refreshing, int userHandle) { 1159 if (!mHasFeature) { 1160 return; 1161 } 1162 mContext.enforceCallingOrSelfPermission( 1163 android.Manifest.permission.MANAGE_DEVICE_ADMINS, null); 1164 enforceCrossUserPermission(userHandle); 1165 1166 DevicePolicyData policy = getUserData(userHandle); 1167 DeviceAdminInfo info = findAdmin(adminReceiver, userHandle); 1168 if (info == null) { 1169 throw new IllegalArgumentException("Bad admin: " + adminReceiver); 1170 } 1171 synchronized (this) { 1172 long ident = Binder.clearCallingIdentity(); 1173 try { 1174 if (!refreshing && getActiveAdminUncheckedLocked(adminReceiver, userHandle) != null) { 1175 throw new IllegalArgumentException("Admin is already added"); 1176 } 1177 ActiveAdmin newAdmin = new ActiveAdmin(info); 1178 policy.mAdminMap.put(adminReceiver, newAdmin); 1179 int replaceIndex = -1; 1180 if (refreshing) { 1181 final int N = policy.mAdminList.size(); 1182 for (int i=0; i < N; i++) { 1183 ActiveAdmin oldAdmin = policy.mAdminList.get(i); 1184 if (oldAdmin.info.getComponent().equals(adminReceiver)) { 1185 replaceIndex = i; 1186 break; 1187 } 1188 } 1189 } 1190 if (replaceIndex == -1) { 1191 policy.mAdminList.add(newAdmin); 1192 enableIfNecessary(info.getPackageName(), userHandle); 1193 } else { 1194 policy.mAdminList.set(replaceIndex, newAdmin); 1195 } 1196 saveSettingsLocked(userHandle); 1197 sendAdminCommandLocked(newAdmin, DeviceAdminReceiver.ACTION_DEVICE_ADMIN_ENABLED); 1198 } finally { 1199 Binder.restoreCallingIdentity(ident); 1200 } 1201 } 1202 } 1203 1204 public boolean isAdminActive(ComponentName adminReceiver, int userHandle) { 1205 if (!mHasFeature) { 1206 return false; 1207 } 1208 enforceCrossUserPermission(userHandle); 1209 synchronized (this) { 1210 return getActiveAdminUncheckedLocked(adminReceiver, userHandle) != null; 1211 } 1212 } 1213 1214 public boolean hasGrantedPolicy(ComponentName adminReceiver, int policyId, int userHandle) { 1215 if (!mHasFeature) { 1216 return false; 1217 } 1218 enforceCrossUserPermission(userHandle); 1219 synchronized (this) { 1220 ActiveAdmin administrator = getActiveAdminUncheckedLocked(adminReceiver, userHandle); 1221 if (administrator == null) { 1222 throw new SecurityException("No active admin " + adminReceiver); 1223 } 1224 return administrator.info.usesPolicy(policyId); 1225 } 1226 } 1227 1228 @SuppressWarnings("unchecked") 1229 public List<ComponentName> getActiveAdmins(int userHandle) { 1230 if (!mHasFeature) { 1231 return Collections.EMPTY_LIST; 1232 } 1233 1234 enforceCrossUserPermission(userHandle); 1235 synchronized (this) { 1236 DevicePolicyData policy = getUserData(userHandle); 1237 final int N = policy.mAdminList.size(); 1238 if (N <= 0) { 1239 return null; 1240 } 1241 ArrayList<ComponentName> res = new ArrayList<ComponentName>(N); 1242 for (int i=0; i<N; i++) { 1243 res.add(policy.mAdminList.get(i).info.getComponent()); 1244 } 1245 return res; 1246 } 1247 } 1248 1249 public boolean packageHasActiveAdmins(String packageName, int userHandle) { 1250 if (!mHasFeature) { 1251 return false; 1252 } 1253 enforceCrossUserPermission(userHandle); 1254 synchronized (this) { 1255 DevicePolicyData policy = getUserData(userHandle); 1256 final int N = policy.mAdminList.size(); 1257 for (int i=0; i<N; i++) { 1258 if (policy.mAdminList.get(i).info.getPackageName().equals(packageName)) { 1259 return true; 1260 } 1261 } 1262 return false; 1263 } 1264 } 1265 1266 public void removeActiveAdmin(ComponentName adminReceiver, int userHandle) { 1267 if (!mHasFeature) { 1268 return; 1269 } 1270 enforceCrossUserPermission(userHandle); 1271 synchronized (this) { 1272 ActiveAdmin admin = getActiveAdminUncheckedLocked(adminReceiver, userHandle); 1273 if (admin == null) { 1274 return; 1275 } 1276 if (admin.getUid() != Binder.getCallingUid()) { 1277 // If trying to remove device owner, refuse when the caller is not the owner. 1278 if (mDeviceOwner != null 1279 && adminReceiver.getPackageName().equals(mDeviceOwner.getPackageName())) { 1280 return; 1281 } 1282 mContext.enforceCallingOrSelfPermission( 1283 android.Manifest.permission.MANAGE_DEVICE_ADMINS, null); 1284 } 1285 long ident = Binder.clearCallingIdentity(); 1286 try { 1287 removeActiveAdminLocked(adminReceiver, userHandle); 1288 } finally { 1289 Binder.restoreCallingIdentity(ident); 1290 } 1291 } 1292 } 1293 1294 public void setPasswordQuality(ComponentName who, int quality, int userHandle) { 1295 if (!mHasFeature) { 1296 return; 1297 } 1298 validateQualityConstant(quality); 1299 enforceCrossUserPermission(userHandle); 1300 1301 synchronized (this) { 1302 if (who == null) { 1303 throw new NullPointerException("ComponentName is null"); 1304 } 1305 ActiveAdmin ap = getActiveAdminForCallerLocked(who, 1306 DeviceAdminInfo.USES_POLICY_LIMIT_PASSWORD); 1307 if (ap.passwordQuality != quality) { 1308 ap.passwordQuality = quality; 1309 saveSettingsLocked(userHandle); 1310 } 1311 } 1312 } 1313 1314 public int getPasswordQuality(ComponentName who, int userHandle) { 1315 if (!mHasFeature) { 1316 return DevicePolicyManager.PASSWORD_QUALITY_UNSPECIFIED; 1317 } 1318 enforceCrossUserPermission(userHandle); 1319 synchronized (this) { 1320 int mode = DevicePolicyManager.PASSWORD_QUALITY_UNSPECIFIED; 1321 DevicePolicyData policy = getUserData(userHandle); 1322 1323 if (who != null) { 1324 ActiveAdmin admin = getActiveAdminUncheckedLocked(who, userHandle); 1325 return admin != null ? admin.passwordQuality : mode; 1326 } 1327 1328 final int N = policy.mAdminList.size(); 1329 for (int i=0; i<N; i++) { 1330 ActiveAdmin admin = policy.mAdminList.get(i); 1331 if (mode < admin.passwordQuality) { 1332 mode = admin.passwordQuality; 1333 } 1334 } 1335 return mode; 1336 } 1337 } 1338 1339 public void setPasswordMinimumLength(ComponentName who, int length, int userHandle) { 1340 if (!mHasFeature) { 1341 return; 1342 } 1343 enforceCrossUserPermission(userHandle); 1344 synchronized (this) { 1345 if (who == null) { 1346 throw new NullPointerException("ComponentName is null"); 1347 } 1348 ActiveAdmin ap = getActiveAdminForCallerLocked(who, 1349 DeviceAdminInfo.USES_POLICY_LIMIT_PASSWORD); 1350 if (ap.minimumPasswordLength != length) { 1351 ap.minimumPasswordLength = length; 1352 saveSettingsLocked(userHandle); 1353 } 1354 } 1355 } 1356 1357 public int getPasswordMinimumLength(ComponentName who, int userHandle) { 1358 if (!mHasFeature) { 1359 return 0; 1360 } 1361 enforceCrossUserPermission(userHandle); 1362 synchronized (this) { 1363 DevicePolicyData policy = getUserData(userHandle); 1364 int length = 0; 1365 1366 if (who != null) { 1367 ActiveAdmin admin = getActiveAdminUncheckedLocked(who, userHandle); 1368 return admin != null ? admin.minimumPasswordLength : length; 1369 } 1370 1371 final int N = policy.mAdminList.size(); 1372 for (int i=0; i<N; i++) { 1373 ActiveAdmin admin = policy.mAdminList.get(i); 1374 if (length < admin.minimumPasswordLength) { 1375 length = admin.minimumPasswordLength; 1376 } 1377 } 1378 return length; 1379 } 1380 } 1381 1382 public void setPasswordHistoryLength(ComponentName who, int length, int userHandle) { 1383 if (!mHasFeature) { 1384 return; 1385 } 1386 enforceCrossUserPermission(userHandle); 1387 synchronized (this) { 1388 if (who == null) { 1389 throw new NullPointerException("ComponentName is null"); 1390 } 1391 ActiveAdmin ap = getActiveAdminForCallerLocked(who, 1392 DeviceAdminInfo.USES_POLICY_LIMIT_PASSWORD); 1393 if (ap.passwordHistoryLength != length) { 1394 ap.passwordHistoryLength = length; 1395 saveSettingsLocked(userHandle); 1396 } 1397 } 1398 } 1399 1400 public int getPasswordHistoryLength(ComponentName who, int userHandle) { 1401 if (!mHasFeature) { 1402 return 0; 1403 } 1404 enforceCrossUserPermission(userHandle); 1405 synchronized (this) { 1406 DevicePolicyData policy = getUserData(userHandle); 1407 int length = 0; 1408 1409 if (who != null) { 1410 ActiveAdmin admin = getActiveAdminUncheckedLocked(who, userHandle); 1411 return admin != null ? admin.passwordHistoryLength : length; 1412 } 1413 1414 final int N = policy.mAdminList.size(); 1415 for (int i = 0; i < N; i++) { 1416 ActiveAdmin admin = policy.mAdminList.get(i); 1417 if (length < admin.passwordHistoryLength) { 1418 length = admin.passwordHistoryLength; 1419 } 1420 } 1421 return length; 1422 } 1423 } 1424 1425 public void setPasswordExpirationTimeout(ComponentName who, long timeout, int userHandle) { 1426 if (!mHasFeature) { 1427 return; 1428 } 1429 enforceCrossUserPermission(userHandle); 1430 synchronized (this) { 1431 if (who == null) { 1432 throw new NullPointerException("ComponentName is null"); 1433 } 1434 if (timeout < 0) { 1435 throw new IllegalArgumentException("Timeout must be >= 0 ms"); 1436 } 1437 ActiveAdmin ap = getActiveAdminForCallerLocked(who, 1438 DeviceAdminInfo.USES_POLICY_EXPIRE_PASSWORD); 1439 // Calling this API automatically bumps the expiration date 1440 final long expiration = timeout > 0L ? (timeout + System.currentTimeMillis()) : 0L; 1441 ap.passwordExpirationDate = expiration; 1442 ap.passwordExpirationTimeout = timeout; 1443 if (timeout > 0L) { 1444 Slog.w(TAG, "setPasswordExpiration(): password will expire on " 1445 + DateFormat.getDateTimeInstance(DateFormat.DEFAULT, DateFormat.DEFAULT) 1446 .format(new Date(expiration))); 1447 } 1448 saveSettingsLocked(userHandle); 1449 // in case this is the first one 1450 setExpirationAlarmCheckLocked(mContext, getUserData(userHandle)); 1451 } 1452 } 1453 1454 /** 1455 * Return a single admin's expiration cycle time, or the min of all cycle times. 1456 * Returns 0 if not configured. 1457 */ 1458 public long getPasswordExpirationTimeout(ComponentName who, int userHandle) { 1459 if (!mHasFeature) { 1460 return 0L; 1461 } 1462 enforceCrossUserPermission(userHandle); 1463 synchronized (this) { 1464 if (who != null) { 1465 ActiveAdmin admin = getActiveAdminUncheckedLocked(who, userHandle); 1466 return admin != null ? admin.passwordExpirationTimeout : 0L; 1467 } 1468 1469 long timeout = 0L; 1470 DevicePolicyData policy = getUserData(userHandle); 1471 final int N = policy.mAdminList.size(); 1472 for (int i = 0; i < N; i++) { 1473 ActiveAdmin admin = policy.mAdminList.get(i); 1474 if (timeout == 0L || (admin.passwordExpirationTimeout != 0L 1475 && timeout > admin.passwordExpirationTimeout)) { 1476 timeout = admin.passwordExpirationTimeout; 1477 } 1478 } 1479 return timeout; 1480 } 1481 } 1482 1483 /** 1484 * Return a single admin's expiration date/time, or the min (soonest) for all admins. 1485 * Returns 0 if not configured. 1486 */ 1487 private long getPasswordExpirationLocked(ComponentName who, int userHandle) { 1488 if (who != null) { 1489 ActiveAdmin admin = getActiveAdminUncheckedLocked(who, userHandle); 1490 return admin != null ? admin.passwordExpirationDate : 0L; 1491 } 1492 1493 long timeout = 0L; 1494 DevicePolicyData policy = getUserData(userHandle); 1495 final int N = policy.mAdminList.size(); 1496 for (int i = 0; i < N; i++) { 1497 ActiveAdmin admin = policy.mAdminList.get(i); 1498 if (timeout == 0L || (admin.passwordExpirationDate != 0 1499 && timeout > admin.passwordExpirationDate)) { 1500 timeout = admin.passwordExpirationDate; 1501 } 1502 } 1503 return timeout; 1504 } 1505 1506 public long getPasswordExpiration(ComponentName who, int userHandle) { 1507 if (!mHasFeature) { 1508 return 0L; 1509 } 1510 enforceCrossUserPermission(userHandle); 1511 synchronized (this) { 1512 return getPasswordExpirationLocked(who, userHandle); 1513 } 1514 } 1515 1516 public void setPasswordMinimumUpperCase(ComponentName who, int length, int userHandle) { 1517 if (!mHasFeature) { 1518 return; 1519 } 1520 enforceCrossUserPermission(userHandle); 1521 synchronized (this) { 1522 if (who == null) { 1523 throw new NullPointerException("ComponentName is null"); 1524 } 1525 ActiveAdmin ap = getActiveAdminForCallerLocked(who, 1526 DeviceAdminInfo.USES_POLICY_LIMIT_PASSWORD); 1527 if (ap.minimumPasswordUpperCase != length) { 1528 ap.minimumPasswordUpperCase = length; 1529 saveSettingsLocked(userHandle); 1530 } 1531 } 1532 } 1533 1534 public int getPasswordMinimumUpperCase(ComponentName who, int userHandle) { 1535 if (!mHasFeature) { 1536 return 0; 1537 } 1538 enforceCrossUserPermission(userHandle); 1539 synchronized (this) { 1540 int length = 0; 1541 1542 if (who != null) { 1543 ActiveAdmin admin = getActiveAdminUncheckedLocked(who, userHandle); 1544 return admin != null ? admin.minimumPasswordUpperCase : length; 1545 } 1546 1547 DevicePolicyData policy = getUserData(userHandle); 1548 final int N = policy.mAdminList.size(); 1549 for (int i=0; i<N; i++) { 1550 ActiveAdmin admin = policy.mAdminList.get(i); 1551 if (length < admin.minimumPasswordUpperCase) { 1552 length = admin.minimumPasswordUpperCase; 1553 } 1554 } 1555 return length; 1556 } 1557 } 1558 1559 public void setPasswordMinimumLowerCase(ComponentName who, int length, int userHandle) { 1560 enforceCrossUserPermission(userHandle); 1561 synchronized (this) { 1562 if (who == null) { 1563 throw new NullPointerException("ComponentName is null"); 1564 } 1565 ActiveAdmin ap = getActiveAdminForCallerLocked(who, 1566 DeviceAdminInfo.USES_POLICY_LIMIT_PASSWORD); 1567 if (ap.minimumPasswordLowerCase != length) { 1568 ap.minimumPasswordLowerCase = length; 1569 saveSettingsLocked(userHandle); 1570 } 1571 } 1572 } 1573 1574 public int getPasswordMinimumLowerCase(ComponentName who, int userHandle) { 1575 if (!mHasFeature) { 1576 return 0; 1577 } 1578 enforceCrossUserPermission(userHandle); 1579 synchronized (this) { 1580 int length = 0; 1581 1582 if (who != null) { 1583 ActiveAdmin admin = getActiveAdminUncheckedLocked(who, userHandle); 1584 return admin != null ? admin.minimumPasswordLowerCase : length; 1585 } 1586 1587 DevicePolicyData policy = getUserData(userHandle); 1588 final int N = policy.mAdminList.size(); 1589 for (int i=0; i<N; i++) { 1590 ActiveAdmin admin = policy.mAdminList.get(i); 1591 if (length < admin.minimumPasswordLowerCase) { 1592 length = admin.minimumPasswordLowerCase; 1593 } 1594 } 1595 return length; 1596 } 1597 } 1598 1599 public void setPasswordMinimumLetters(ComponentName who, int length, int userHandle) { 1600 if (!mHasFeature) { 1601 return; 1602 } 1603 enforceCrossUserPermission(userHandle); 1604 synchronized (this) { 1605 if (who == null) { 1606 throw new NullPointerException("ComponentName is null"); 1607 } 1608 ActiveAdmin ap = getActiveAdminForCallerLocked(who, 1609 DeviceAdminInfo.USES_POLICY_LIMIT_PASSWORD); 1610 if (ap.minimumPasswordLetters != length) { 1611 ap.minimumPasswordLetters = length; 1612 saveSettingsLocked(userHandle); 1613 } 1614 } 1615 } 1616 1617 public int getPasswordMinimumLetters(ComponentName who, int userHandle) { 1618 if (!mHasFeature) { 1619 return 0; 1620 } 1621 enforceCrossUserPermission(userHandle); 1622 synchronized (this) { 1623 int length = 0; 1624 1625 if (who != null) { 1626 ActiveAdmin admin = getActiveAdminUncheckedLocked(who, userHandle); 1627 return admin != null ? admin.minimumPasswordLetters : length; 1628 } 1629 1630 DevicePolicyData policy = getUserData(userHandle); 1631 final int N = policy.mAdminList.size(); 1632 for (int i=0; i<N; i++) { 1633 ActiveAdmin admin = policy.mAdminList.get(i); 1634 if (length < admin.minimumPasswordLetters) { 1635 length = admin.minimumPasswordLetters; 1636 } 1637 } 1638 return length; 1639 } 1640 } 1641 1642 public void setPasswordMinimumNumeric(ComponentName who, int length, int userHandle) { 1643 if (!mHasFeature) { 1644 return; 1645 } 1646 enforceCrossUserPermission(userHandle); 1647 synchronized (this) { 1648 if (who == null) { 1649 throw new NullPointerException("ComponentName is null"); 1650 } 1651 ActiveAdmin ap = getActiveAdminForCallerLocked(who, 1652 DeviceAdminInfo.USES_POLICY_LIMIT_PASSWORD); 1653 if (ap.minimumPasswordNumeric != length) { 1654 ap.minimumPasswordNumeric = length; 1655 saveSettingsLocked(userHandle); 1656 } 1657 } 1658 } 1659 1660 public int getPasswordMinimumNumeric(ComponentName who, int userHandle) { 1661 if (!mHasFeature) { 1662 return 0; 1663 } 1664 enforceCrossUserPermission(userHandle); 1665 synchronized (this) { 1666 int length = 0; 1667 1668 if (who != null) { 1669 ActiveAdmin admin = getActiveAdminUncheckedLocked(who, userHandle); 1670 return admin != null ? admin.minimumPasswordNumeric : length; 1671 } 1672 1673 DevicePolicyData policy = getUserData(userHandle); 1674 final int N = policy.mAdminList.size(); 1675 for (int i = 0; i < N; i++) { 1676 ActiveAdmin admin = policy.mAdminList.get(i); 1677 if (length < admin.minimumPasswordNumeric) { 1678 length = admin.minimumPasswordNumeric; 1679 } 1680 } 1681 return length; 1682 } 1683 } 1684 1685 public void setPasswordMinimumSymbols(ComponentName who, int length, int userHandle) { 1686 if (!mHasFeature) { 1687 return; 1688 } 1689 enforceCrossUserPermission(userHandle); 1690 synchronized (this) { 1691 if (who == null) { 1692 throw new NullPointerException("ComponentName is null"); 1693 } 1694 ActiveAdmin ap = getActiveAdminForCallerLocked(who, 1695 DeviceAdminInfo.USES_POLICY_LIMIT_PASSWORD); 1696 if (ap.minimumPasswordSymbols != length) { 1697 ap.minimumPasswordSymbols = length; 1698 saveSettingsLocked(userHandle); 1699 } 1700 } 1701 } 1702 1703 public int getPasswordMinimumSymbols(ComponentName who, int userHandle) { 1704 if (!mHasFeature) { 1705 return 0; 1706 } 1707 enforceCrossUserPermission(userHandle); 1708 synchronized (this) { 1709 int length = 0; 1710 1711 if (who != null) { 1712 ActiveAdmin admin = getActiveAdminUncheckedLocked(who, userHandle); 1713 return admin != null ? admin.minimumPasswordSymbols : length; 1714 } 1715 1716 DevicePolicyData policy = getUserData(userHandle); 1717 final int N = policy.mAdminList.size(); 1718 for (int i=0; i<N; i++) { 1719 ActiveAdmin admin = policy.mAdminList.get(i); 1720 if (length < admin.minimumPasswordSymbols) { 1721 length = admin.minimumPasswordSymbols; 1722 } 1723 } 1724 return length; 1725 } 1726 } 1727 1728 public void setPasswordMinimumNonLetter(ComponentName who, int length, int userHandle) { 1729 if (!mHasFeature) { 1730 return; 1731 } 1732 enforceCrossUserPermission(userHandle); 1733 synchronized (this) { 1734 if (who == null) { 1735 throw new NullPointerException("ComponentName is null"); 1736 } 1737 ActiveAdmin ap = getActiveAdminForCallerLocked(who, 1738 DeviceAdminInfo.USES_POLICY_LIMIT_PASSWORD); 1739 if (ap.minimumPasswordNonLetter != length) { 1740 ap.minimumPasswordNonLetter = length; 1741 saveSettingsLocked(userHandle); 1742 } 1743 } 1744 } 1745 1746 public int getPasswordMinimumNonLetter(ComponentName who, int userHandle) { 1747 if (!mHasFeature) { 1748 return 0; 1749 } 1750 enforceCrossUserPermission(userHandle); 1751 synchronized (this) { 1752 int length = 0; 1753 1754 if (who != null) { 1755 ActiveAdmin admin = getActiveAdminUncheckedLocked(who, userHandle); 1756 return admin != null ? admin.minimumPasswordNonLetter : length; 1757 } 1758 1759 DevicePolicyData policy = getUserData(userHandle); 1760 final int N = policy.mAdminList.size(); 1761 for (int i=0; i<N; i++) { 1762 ActiveAdmin admin = policy.mAdminList.get(i); 1763 if (length < admin.minimumPasswordNonLetter) { 1764 length = admin.minimumPasswordNonLetter; 1765 } 1766 } 1767 return length; 1768 } 1769 } 1770 1771 public boolean isActivePasswordSufficient(int userHandle) { 1772 if (!mHasFeature) { 1773 return true; 1774 } 1775 enforceCrossUserPermission(userHandle); 1776 synchronized (this) { 1777 DevicePolicyData policy = getUserData(userHandle); 1778 // This API can only be called by an active device admin, 1779 // so try to retrieve it to check that the caller is one. 1780 getActiveAdminForCallerLocked(null, 1781 DeviceAdminInfo.USES_POLICY_LIMIT_PASSWORD); 1782 if (policy.mActivePasswordQuality < getPasswordQuality(null, userHandle) 1783 || policy.mActivePasswordLength < getPasswordMinimumLength(null, userHandle)) { 1784 return false; 1785 } 1786 if (policy.mActivePasswordQuality != DevicePolicyManager.PASSWORD_QUALITY_COMPLEX) { 1787 return true; 1788 } 1789 return policy.mActivePasswordUpperCase >= getPasswordMinimumUpperCase(null, userHandle) 1790 && policy.mActivePasswordLowerCase >= getPasswordMinimumLowerCase(null, userHandle) 1791 && policy.mActivePasswordLetters >= getPasswordMinimumLetters(null, userHandle) 1792 && policy.mActivePasswordNumeric >= getPasswordMinimumNumeric(null, userHandle) 1793 && policy.mActivePasswordSymbols >= getPasswordMinimumSymbols(null, userHandle) 1794 && policy.mActivePasswordNonLetter >= getPasswordMinimumNonLetter(null, userHandle); 1795 } 1796 } 1797 1798 public int getCurrentFailedPasswordAttempts(int userHandle) { 1799 enforceCrossUserPermission(userHandle); 1800 synchronized (this) { 1801 // This API can only be called by an active device admin, 1802 // so try to retrieve it to check that the caller is one. 1803 getActiveAdminForCallerLocked(null, 1804 DeviceAdminInfo.USES_POLICY_WATCH_LOGIN); 1805 return getUserData(userHandle).mFailedPasswordAttempts; 1806 } 1807 } 1808 1809 public void setMaximumFailedPasswordsForWipe(ComponentName who, int num, int userHandle) { 1810 if (!mHasFeature) { 1811 return; 1812 } 1813 enforceCrossUserPermission(userHandle); 1814 synchronized (this) { 1815 // This API can only be called by an active device admin, 1816 // so try to retrieve it to check that the caller is one. 1817 getActiveAdminForCallerLocked(who, 1818 DeviceAdminInfo.USES_POLICY_WIPE_DATA); 1819 ActiveAdmin ap = getActiveAdminForCallerLocked(who, 1820 DeviceAdminInfo.USES_POLICY_WATCH_LOGIN); 1821 if (ap.maximumFailedPasswordsForWipe != num) { 1822 ap.maximumFailedPasswordsForWipe = num; 1823 saveSettingsLocked(userHandle); 1824 } 1825 } 1826 } 1827 1828 public int getMaximumFailedPasswordsForWipe(ComponentName who, int userHandle) { 1829 if (!mHasFeature) { 1830 return 0; 1831 } 1832 enforceCrossUserPermission(userHandle); 1833 synchronized (this) { 1834 DevicePolicyData policy = getUserData(userHandle); 1835 int count = 0; 1836 1837 if (who != null) { 1838 ActiveAdmin admin = getActiveAdminUncheckedLocked(who, userHandle); 1839 return admin != null ? admin.maximumFailedPasswordsForWipe : count; 1840 } 1841 1842 final int N = policy.mAdminList.size(); 1843 for (int i=0; i<N; i++) { 1844 ActiveAdmin admin = policy.mAdminList.get(i); 1845 if (count == 0) { 1846 count = admin.maximumFailedPasswordsForWipe; 1847 } else if (admin.maximumFailedPasswordsForWipe != 0 1848 && count > admin.maximumFailedPasswordsForWipe) { 1849 count = admin.maximumFailedPasswordsForWipe; 1850 } 1851 } 1852 return count; 1853 } 1854 } 1855 1856 public boolean resetPassword(String password, int flags, int userHandle) { 1857 if (!mHasFeature) { 1858 return false; 1859 } 1860 enforceCrossUserPermission(userHandle); 1861 int quality; 1862 synchronized (this) { 1863 // This API can only be called by an active device admin, 1864 // so try to retrieve it to check that the caller is one. 1865 getActiveAdminForCallerLocked(null, 1866 DeviceAdminInfo.USES_POLICY_RESET_PASSWORD); 1867 quality = getPasswordQuality(null, userHandle); 1868 if (quality != DevicePolicyManager.PASSWORD_QUALITY_UNSPECIFIED) { 1869 int realQuality = LockPatternUtils.computePasswordQuality(password); 1870 if (realQuality < quality 1871 && quality != DevicePolicyManager.PASSWORD_QUALITY_COMPLEX) { 1872 Slog.w(TAG, "resetPassword: password quality 0x" 1873 + Integer.toHexString(realQuality) 1874 + " does not meet required quality 0x" 1875 + Integer.toHexString(quality)); 1876 return false; 1877 } 1878 quality = Math.max(realQuality, quality); 1879 } 1880 int length = getPasswordMinimumLength(null, userHandle); 1881 if (password.length() < length) { 1882 Slog.w(TAG, "resetPassword: password length " + password.length() 1883 + " does not meet required length " + length); 1884 return false; 1885 } 1886 if (quality == DevicePolicyManager.PASSWORD_QUALITY_COMPLEX) { 1887 int letters = 0; 1888 int uppercase = 0; 1889 int lowercase = 0; 1890 int numbers = 0; 1891 int symbols = 0; 1892 int nonletter = 0; 1893 for (int i = 0; i < password.length(); i++) { 1894 char c = password.charAt(i); 1895 if (c >= 'A' && c <= 'Z') { 1896 letters++; 1897 uppercase++; 1898 } else if (c >= 'a' && c <= 'z') { 1899 letters++; 1900 lowercase++; 1901 } else if (c >= '0' && c <= '9') { 1902 numbers++; 1903 nonletter++; 1904 } else { 1905 symbols++; 1906 nonletter++; 1907 } 1908 } 1909 int neededLetters = getPasswordMinimumLetters(null, userHandle); 1910 if(letters < neededLetters) { 1911 Slog.w(TAG, "resetPassword: number of letters " + letters 1912 + " does not meet required number of letters " + neededLetters); 1913 return false; 1914 } 1915 int neededNumbers = getPasswordMinimumNumeric(null, userHandle); 1916 if (numbers < neededNumbers) { 1917 Slog.w(TAG, "resetPassword: number of numerical digits " + numbers 1918 + " does not meet required number of numerical digits " 1919 + neededNumbers); 1920 return false; 1921 } 1922 int neededLowerCase = getPasswordMinimumLowerCase(null, userHandle); 1923 if (lowercase < neededLowerCase) { 1924 Slog.w(TAG, "resetPassword: number of lowercase letters " + lowercase 1925 + " does not meet required number of lowercase letters " 1926 + neededLowerCase); 1927 return false; 1928 } 1929 int neededUpperCase = getPasswordMinimumUpperCase(null, userHandle); 1930 if (uppercase < neededUpperCase) { 1931 Slog.w(TAG, "resetPassword: number of uppercase letters " + uppercase 1932 + " does not meet required number of uppercase letters " 1933 + neededUpperCase); 1934 return false; 1935 } 1936 int neededSymbols = getPasswordMinimumSymbols(null, userHandle); 1937 if (symbols < neededSymbols) { 1938 Slog.w(TAG, "resetPassword: number of special symbols " + symbols 1939 + " does not meet required number of special symbols " + neededSymbols); 1940 return false; 1941 } 1942 int neededNonLetter = getPasswordMinimumNonLetter(null, userHandle); 1943 if (nonletter < neededNonLetter) { 1944 Slog.w(TAG, "resetPassword: number of non-letter characters " + nonletter 1945 + " does not meet required number of non-letter characters " 1946 + neededNonLetter); 1947 return false; 1948 } 1949 } 1950 } 1951 1952 int callingUid = Binder.getCallingUid(); 1953 DevicePolicyData policy = getUserData(userHandle); 1954 if (policy.mPasswordOwner >= 0 && policy.mPasswordOwner != callingUid) { 1955 Slog.w(TAG, "resetPassword: already set by another uid and not entered by user"); 1956 return false; 1957 } 1958 1959 // Don't do this with the lock held, because it is going to call 1960 // back in to the service. 1961 long ident = Binder.clearCallingIdentity(); 1962 try { 1963 LockPatternUtils utils = new LockPatternUtils(mContext); 1964 utils.saveLockPassword(password, quality, false, userHandle); 1965 synchronized (this) { 1966 int newOwner = (flags&DevicePolicyManager.RESET_PASSWORD_REQUIRE_ENTRY) 1967 != 0 ? callingUid : -1; 1968 if (policy.mPasswordOwner != newOwner) { 1969 policy.mPasswordOwner = newOwner; 1970 saveSettingsLocked(userHandle); 1971 } 1972 } 1973 } finally { 1974 Binder.restoreCallingIdentity(ident); 1975 } 1976 1977 return true; 1978 } 1979 1980 public void setMaximumTimeToLock(ComponentName who, long timeMs, int userHandle) { 1981 if (!mHasFeature) { 1982 return; 1983 } 1984 enforceCrossUserPermission(userHandle); 1985 synchronized (this) { 1986 if (who == null) { 1987 throw new NullPointerException("ComponentName is null"); 1988 } 1989 ActiveAdmin ap = getActiveAdminForCallerLocked(who, 1990 DeviceAdminInfo.USES_POLICY_FORCE_LOCK); 1991 if (ap.maximumTimeToUnlock != timeMs) { 1992 ap.maximumTimeToUnlock = timeMs; 1993 saveSettingsLocked(userHandle); 1994 updateMaximumTimeToLockLocked(getUserData(userHandle)); 1995 } 1996 } 1997 } 1998 1999 void updateMaximumTimeToLockLocked(DevicePolicyData policy) { 2000 long timeMs = getMaximumTimeToLock(null, policy.mUserHandle); 2001 if (policy.mLastMaximumTimeToLock == timeMs) { 2002 return; 2003 } 2004 2005 long ident = Binder.clearCallingIdentity(); 2006 try { 2007 if (timeMs <= 0) { 2008 timeMs = Integer.MAX_VALUE; 2009 } else { 2010 // Make sure KEEP_SCREEN_ON is disabled, since that 2011 // would allow bypassing of the maximum time to lock. 2012 Settings.Global.putInt(mContext.getContentResolver(), 2013 Settings.Global.STAY_ON_WHILE_PLUGGED_IN, 0); 2014 } 2015 2016 policy.mLastMaximumTimeToLock = timeMs; 2017 2018 try { 2019 getIPowerManager().setMaximumScreenOffTimeoutFromDeviceAdmin((int)timeMs); 2020 } catch (RemoteException e) { 2021 Slog.w(TAG, "Failure talking with power manager", e); 2022 } 2023 } finally { 2024 Binder.restoreCallingIdentity(ident); 2025 } 2026 } 2027 2028 public long getMaximumTimeToLock(ComponentName who, int userHandle) { 2029 if (!mHasFeature) { 2030 return 0; 2031 } 2032 enforceCrossUserPermission(userHandle); 2033 synchronized (this) { 2034 long time = 0; 2035 2036 if (who != null) { 2037 ActiveAdmin admin = getActiveAdminUncheckedLocked(who, userHandle); 2038 return admin != null ? admin.maximumTimeToUnlock : time; 2039 } 2040 2041 DevicePolicyData policy = getUserData(userHandle); 2042 final int N = policy.mAdminList.size(); 2043 for (int i=0; i<N; i++) { 2044 ActiveAdmin admin = policy.mAdminList.get(i); 2045 if (time == 0) { 2046 time = admin.maximumTimeToUnlock; 2047 } else if (admin.maximumTimeToUnlock != 0 2048 && time > admin.maximumTimeToUnlock) { 2049 time = admin.maximumTimeToUnlock; 2050 } 2051 } 2052 return time; 2053 } 2054 } 2055 2056 public void lockNow() { 2057 if (!mHasFeature) { 2058 return; 2059 } 2060 synchronized (this) { 2061 // This API can only be called by an active device admin, 2062 // so try to retrieve it to check that the caller is one. 2063 getActiveAdminForCallerLocked(null, 2064 DeviceAdminInfo.USES_POLICY_FORCE_LOCK); 2065 lockNowUnchecked(); 2066 } 2067 } 2068 2069 private void lockNowUnchecked() { 2070 long ident = Binder.clearCallingIdentity(); 2071 try { 2072 // Power off the display 2073 getIPowerManager().goToSleep(SystemClock.uptimeMillis(), 2074 PowerManager.GO_TO_SLEEP_REASON_DEVICE_ADMIN); 2075 // Ensure the device is locked 2076 getWindowManager().lockNow(null); 2077 } catch (RemoteException e) { 2078 } finally { 2079 Binder.restoreCallingIdentity(ident); 2080 } 2081 } 2082 2083 private boolean isExtStorageEncrypted() { 2084 String state = SystemProperties.get("vold.decrypt"); 2085 return !"".equals(state); 2086 } 2087 2088 public boolean installCaCert(byte[] certBuffer) throws RemoteException { 2089 mContext.enforceCallingOrSelfPermission(MANAGE_CA_CERTIFICATES, null); 2090 KeyChainConnection keyChainConnection = null; 2091 byte[] pemCert; 2092 try { 2093 X509Certificate cert = parseCert(certBuffer); 2094 pemCert = Credentials.convertToPem(cert); 2095 } catch (CertificateException ce) { 2096 Log.e(TAG, "Problem converting cert", ce); 2097 return false; 2098 } catch (IOException ioe) { 2099 Log.e(TAG, "Problem reading cert", ioe); 2100 return false; 2101 } 2102 try { 2103 keyChainConnection = KeyChain.bind(mContext); 2104 try { 2105 keyChainConnection.getService().installCaCertificate(pemCert); 2106 return true; 2107 } finally { 2108 if (keyChainConnection != null) { 2109 keyChainConnection.close(); 2110 keyChainConnection = null; 2111 } 2112 } 2113 } catch (InterruptedException e1) { 2114 Log.w(TAG, "installCaCertsToKeyChain(): ", e1); 2115 Thread.currentThread().interrupt(); 2116 } 2117 return false; 2118 } 2119 2120 private static X509Certificate parseCert(byte[] certBuffer) 2121 throws CertificateException, IOException { 2122 CertificateFactory certFactory = CertificateFactory.getInstance("X.509"); 2123 return (X509Certificate) certFactory.generateCertificate(new ByteArrayInputStream( 2124 certBuffer)); 2125 } 2126 2127 public void uninstallCaCert(final byte[] certBuffer) { 2128 mContext.enforceCallingOrSelfPermission(MANAGE_CA_CERTIFICATES, null); 2129 TrustedCertificateStore certStore = new TrustedCertificateStore(); 2130 String alias = null; 2131 try { 2132 X509Certificate cert = parseCert(certBuffer); 2133 alias = certStore.getCertificateAlias(cert); 2134 } catch (CertificateException ce) { 2135 Log.e(TAG, "Problem creating X509Certificate", ce); 2136 return; 2137 } catch (IOException ioe) { 2138 Log.e(TAG, "Problem reading certificate", ioe); 2139 return; 2140 } 2141 try { 2142 KeyChainConnection keyChainConnection = KeyChain.bind(mContext); 2143 IKeyChainService service = keyChainConnection.getService(); 2144 try { 2145 service.deleteCaCertificate(alias); 2146 } catch (RemoteException e) { 2147 Log.e(TAG, "from CaCertUninstaller: ", e); 2148 } finally { 2149 keyChainConnection.close(); 2150 keyChainConnection = null; 2151 } 2152 } catch (InterruptedException ie) { 2153 Log.w(TAG, "CaCertUninstaller: ", ie); 2154 Thread.currentThread().interrupt(); 2155 } 2156 } 2157 2158 void wipeDataLocked(int flags) { 2159 // If the SD card is encrypted and non-removable, we have to force a wipe. 2160 boolean forceExtWipe = !Environment.isExternalStorageRemovable() && isExtStorageEncrypted(); 2161 boolean wipeExtRequested = (flags&DevicePolicyManager.WIPE_EXTERNAL_STORAGE) != 0; 2162 2163 // Note: we can only do the wipe via ExternalStorageFormatter if the volume is not emulated. 2164 if ((forceExtWipe || wipeExtRequested) && !Environment.isExternalStorageEmulated()) { 2165 Intent intent = new Intent(ExternalStorageFormatter.FORMAT_AND_FACTORY_RESET); 2166 intent.putExtra(ExternalStorageFormatter.EXTRA_ALWAYS_RESET, true); 2167 intent.setComponent(ExternalStorageFormatter.COMPONENT_NAME); 2168 mWakeLock.acquire(10000); 2169 mContext.startService(intent); 2170 } else { 2171 try { 2172 RecoverySystem.rebootWipeUserData(mContext); 2173 } catch (IOException e) { 2174 Slog.w(TAG, "Failed requesting data wipe", e); 2175 } 2176 } 2177 } 2178 2179 public void wipeData(int flags, final int userHandle) { 2180 if (!mHasFeature) { 2181 return; 2182 } 2183 enforceCrossUserPermission(userHandle); 2184 synchronized (this) { 2185 // This API can only be called by an active device admin, 2186 // so try to retrieve it to check that the caller is one. 2187 getActiveAdminForCallerLocked(null, 2188 DeviceAdminInfo.USES_POLICY_WIPE_DATA); 2189 long ident = Binder.clearCallingIdentity(); 2190 try { 2191 wipeDeviceOrUserLocked(flags, userHandle); 2192 } finally { 2193 Binder.restoreCallingIdentity(ident); 2194 } 2195 } 2196 } 2197 2198 private void wipeDeviceOrUserLocked(int flags, final int userHandle) { 2199 if (userHandle == UserHandle.USER_OWNER) { 2200 wipeDataLocked(flags); 2201 } else { 2202 lockNowUnchecked(); 2203 mHandler.post(new Runnable() { 2204 public void run() { 2205 try { 2206 ActivityManagerNative.getDefault().switchUser(UserHandle.USER_OWNER); 2207 ((UserManager) mContext.getSystemService(Context.USER_SERVICE)) 2208 .removeUser(userHandle); 2209 } catch (RemoteException re) { 2210 // Shouldn't happen 2211 } 2212 } 2213 }); 2214 } 2215 } 2216 2217 public void getRemoveWarning(ComponentName comp, final RemoteCallback result, int userHandle) { 2218 if (!mHasFeature) { 2219 return; 2220 } 2221 enforceCrossUserPermission(userHandle); 2222 mContext.enforceCallingOrSelfPermission( 2223 android.Manifest.permission.BIND_DEVICE_ADMIN, null); 2224 2225 synchronized (this) { 2226 ActiveAdmin admin = getActiveAdminUncheckedLocked(comp, userHandle); 2227 if (admin == null) { 2228 try { 2229 result.sendResult(null); 2230 } catch (RemoteException e) { 2231 } 2232 return; 2233 } 2234 Intent intent = new Intent(DeviceAdminReceiver.ACTION_DEVICE_ADMIN_DISABLE_REQUESTED); 2235 intent.setComponent(admin.info.getComponent()); 2236 mContext.sendOrderedBroadcastAsUser(intent, new UserHandle(userHandle), 2237 null, new BroadcastReceiver() { 2238 @Override 2239 public void onReceive(Context context, Intent intent) { 2240 try { 2241 result.sendResult(getResultExtras(false)); 2242 } catch (RemoteException e) { 2243 } 2244 } 2245 }, null, Activity.RESULT_OK, null, null); 2246 } 2247 } 2248 2249 public void setActivePasswordState(int quality, int length, int letters, int uppercase, 2250 int lowercase, int numbers, int symbols, int nonletter, int userHandle) { 2251 if (!mHasFeature) { 2252 return; 2253 } 2254 enforceCrossUserPermission(userHandle); 2255 mContext.enforceCallingOrSelfPermission( 2256 android.Manifest.permission.BIND_DEVICE_ADMIN, null); 2257 DevicePolicyData p = getUserData(userHandle); 2258 2259 validateQualityConstant(quality); 2260 2261 synchronized (this) { 2262 if (p.mActivePasswordQuality != quality || p.mActivePasswordLength != length 2263 || p.mFailedPasswordAttempts != 0 || p.mActivePasswordLetters != letters 2264 || p.mActivePasswordUpperCase != uppercase 2265 || p.mActivePasswordLowerCase != lowercase || p.mActivePasswordNumeric != numbers 2266 || p.mActivePasswordSymbols != symbols || p.mActivePasswordNonLetter != nonletter) { 2267 long ident = Binder.clearCallingIdentity(); 2268 try { 2269 p.mActivePasswordQuality = quality; 2270 p.mActivePasswordLength = length; 2271 p.mActivePasswordLetters = letters; 2272 p.mActivePasswordLowerCase = lowercase; 2273 p.mActivePasswordUpperCase = uppercase; 2274 p.mActivePasswordNumeric = numbers; 2275 p.mActivePasswordSymbols = symbols; 2276 p.mActivePasswordNonLetter = nonletter; 2277 p.mFailedPasswordAttempts = 0; 2278 saveSettingsLocked(userHandle); 2279 updatePasswordExpirationsLocked(userHandle); 2280 setExpirationAlarmCheckLocked(mContext, p); 2281 sendAdminCommandLocked(DeviceAdminReceiver.ACTION_PASSWORD_CHANGED, 2282 DeviceAdminInfo.USES_POLICY_LIMIT_PASSWORD, userHandle); 2283 } finally { 2284 Binder.restoreCallingIdentity(ident); 2285 } 2286 } 2287 } 2288 } 2289 2290 /** 2291 * Called any time the device password is updated. Resets all password expiration clocks. 2292 */ 2293 private void updatePasswordExpirationsLocked(int userHandle) { 2294 DevicePolicyData policy = getUserData(userHandle); 2295 final int N = policy.mAdminList.size(); 2296 if (N > 0) { 2297 for (int i=0; i<N; i++) { 2298 ActiveAdmin admin = policy.mAdminList.get(i); 2299 if (admin.info.usesPolicy(DeviceAdminInfo.USES_POLICY_EXPIRE_PASSWORD)) { 2300 long timeout = admin.passwordExpirationTimeout; 2301 long expiration = timeout > 0L ? (timeout + System.currentTimeMillis()) : 0L; 2302 admin.passwordExpirationDate = expiration; 2303 } 2304 } 2305 saveSettingsLocked(userHandle); 2306 } 2307 } 2308 2309 public void reportFailedPasswordAttempt(int userHandle) { 2310 enforceCrossUserPermission(userHandle); 2311 mContext.enforceCallingOrSelfPermission( 2312 android.Manifest.permission.BIND_DEVICE_ADMIN, null); 2313 2314 synchronized (this) { 2315 DevicePolicyData policy = getUserData(userHandle); 2316 long ident = Binder.clearCallingIdentity(); 2317 try { 2318 policy.mFailedPasswordAttempts++; 2319 saveSettingsLocked(userHandle); 2320 if (mHasFeature) { 2321 int max = getMaximumFailedPasswordsForWipe(null, userHandle); 2322 if (max > 0 && policy.mFailedPasswordAttempts >= max) { 2323 wipeDeviceOrUserLocked(0, userHandle); 2324 } 2325 sendAdminCommandLocked(DeviceAdminReceiver.ACTION_PASSWORD_FAILED, 2326 DeviceAdminInfo.USES_POLICY_WATCH_LOGIN, userHandle); 2327 } 2328 } finally { 2329 Binder.restoreCallingIdentity(ident); 2330 } 2331 } 2332 } 2333 2334 public void reportSuccessfulPasswordAttempt(int userHandle) { 2335 enforceCrossUserPermission(userHandle); 2336 mContext.enforceCallingOrSelfPermission( 2337 android.Manifest.permission.BIND_DEVICE_ADMIN, null); 2338 2339 synchronized (this) { 2340 DevicePolicyData policy = getUserData(userHandle); 2341 if (policy.mFailedPasswordAttempts != 0 || policy.mPasswordOwner >= 0) { 2342 long ident = Binder.clearCallingIdentity(); 2343 try { 2344 policy.mFailedPasswordAttempts = 0; 2345 policy.mPasswordOwner = -1; 2346 saveSettingsLocked(userHandle); 2347 if (mHasFeature) { 2348 sendAdminCommandLocked(DeviceAdminReceiver.ACTION_PASSWORD_SUCCEEDED, 2349 DeviceAdminInfo.USES_POLICY_WATCH_LOGIN, userHandle); 2350 } 2351 } finally { 2352 Binder.restoreCallingIdentity(ident); 2353 } 2354 } 2355 } 2356 } 2357 2358 public ComponentName setGlobalProxy(ComponentName who, String proxySpec, 2359 String exclusionList, int userHandle) { 2360 if (!mHasFeature) { 2361 return null; 2362 } 2363 enforceCrossUserPermission(userHandle); 2364 synchronized(this) { 2365 if (who == null) { 2366 throw new NullPointerException("ComponentName is null"); 2367 } 2368 2369 // Only check if owner has set global proxy. We don't allow other users to set it. 2370 DevicePolicyData policy = getUserData(UserHandle.USER_OWNER); 2371 ActiveAdmin admin = getActiveAdminForCallerLocked(who, 2372 DeviceAdminInfo.USES_POLICY_SETS_GLOBAL_PROXY); 2373 2374 // Scan through active admins and find if anyone has already 2375 // set the global proxy. 2376 Set<ComponentName> compSet = policy.mAdminMap.keySet(); 2377 for (ComponentName component : compSet) { 2378 ActiveAdmin ap = policy.mAdminMap.get(component); 2379 if ((ap.specifiesGlobalProxy) && (!component.equals(who))) { 2380 // Another admin already sets the global proxy 2381 // Return it to the caller. 2382 return component; 2383 } 2384 } 2385 2386 // If the user is not the owner, don't set the global proxy. Fail silently. 2387 if (UserHandle.getCallingUserId() != UserHandle.USER_OWNER) { 2388 Slog.w(TAG, "Only the owner is allowed to set the global proxy. User " 2389 + userHandle + " is not permitted."); 2390 return null; 2391 } 2392 if (proxySpec == null) { 2393 admin.specifiesGlobalProxy = false; 2394 admin.globalProxySpec = null; 2395 admin.globalProxyExclusionList = null; 2396 } else { 2397 2398 admin.specifiesGlobalProxy = true; 2399 admin.globalProxySpec = proxySpec; 2400 admin.globalProxyExclusionList = exclusionList; 2401 } 2402 2403 // Reset the global proxy accordingly 2404 // Do this using system permissions, as apps cannot write to secure settings 2405 long origId = Binder.clearCallingIdentity(); 2406 resetGlobalProxyLocked(policy); 2407 Binder.restoreCallingIdentity(origId); 2408 return null; 2409 } 2410 } 2411 2412 public ComponentName getGlobalProxyAdmin(int userHandle) { 2413 if (!mHasFeature) { 2414 return null; 2415 } 2416 enforceCrossUserPermission(userHandle); 2417 synchronized(this) { 2418 DevicePolicyData policy = getUserData(UserHandle.USER_OWNER); 2419 // Scan through active admins and find if anyone has already 2420 // set the global proxy. 2421 final int N = policy.mAdminList.size(); 2422 for (int i = 0; i < N; i++) { 2423 ActiveAdmin ap = policy.mAdminList.get(i); 2424 if (ap.specifiesGlobalProxy) { 2425 // Device admin sets the global proxy 2426 // Return it to the caller. 2427 return ap.info.getComponent(); 2428 } 2429 } 2430 } 2431 // No device admin sets the global proxy. 2432 return null; 2433 } 2434 2435 private void resetGlobalProxyLocked(DevicePolicyData policy) { 2436 final int N = policy.mAdminList.size(); 2437 for (int i = 0; i < N; i++) { 2438 ActiveAdmin ap = policy.mAdminList.get(i); 2439 if (ap.specifiesGlobalProxy) { 2440 saveGlobalProxyLocked(ap.globalProxySpec, ap.globalProxyExclusionList); 2441 return; 2442 } 2443 } 2444 // No device admins defining global proxies - reset global proxy settings to none 2445 saveGlobalProxyLocked(null, null); 2446 } 2447 2448 private void saveGlobalProxyLocked(String proxySpec, String exclusionList) { 2449 if (exclusionList == null) { 2450 exclusionList = ""; 2451 } 2452 if (proxySpec == null) { 2453 proxySpec = ""; 2454 } 2455 // Remove white spaces 2456 proxySpec = proxySpec.trim(); 2457 String data[] = proxySpec.split(":"); 2458 int proxyPort = 8080; 2459 if (data.length > 1) { 2460 try { 2461 proxyPort = Integer.parseInt(data[1]); 2462 } catch (NumberFormatException e) {} 2463 } 2464 exclusionList = exclusionList.trim(); 2465 ContentResolver res = mContext.getContentResolver(); 2466 Settings.Global.putString(res, Settings.Global.GLOBAL_HTTP_PROXY_HOST, data[0]); 2467 Settings.Global.putInt(res, Settings.Global.GLOBAL_HTTP_PROXY_PORT, proxyPort); 2468 Settings.Global.putString(res, Settings.Global.GLOBAL_HTTP_PROXY_EXCLUSION_LIST, 2469 exclusionList); 2470 } 2471 2472 /** 2473 * Set the storage encryption request for a single admin. Returns the new total request 2474 * status (for all admins). 2475 */ 2476 public int setStorageEncryption(ComponentName who, boolean encrypt, int userHandle) { 2477 if (!mHasFeature) { 2478 return DevicePolicyManager.ENCRYPTION_STATUS_UNSUPPORTED; 2479 } 2480 enforceCrossUserPermission(userHandle); 2481 synchronized (this) { 2482 // Check for permissions 2483 if (who == null) { 2484 throw new NullPointerException("ComponentName is null"); 2485 } 2486 // Only owner can set storage encryption 2487 if (userHandle != UserHandle.USER_OWNER 2488 || UserHandle.getCallingUserId() != UserHandle.USER_OWNER) { 2489 Slog.w(TAG, "Only owner is allowed to set storage encryption. User " 2490 + UserHandle.getCallingUserId() + " is not permitted."); 2491 return 0; 2492 } 2493 2494 ActiveAdmin ap = getActiveAdminForCallerLocked(who, 2495 DeviceAdminInfo.USES_ENCRYPTED_STORAGE); 2496 2497 // Quick exit: If the filesystem does not support encryption, we can exit early. 2498 if (!isEncryptionSupported()) { 2499 return DevicePolicyManager.ENCRYPTION_STATUS_UNSUPPORTED; 2500 } 2501 2502 // (1) Record the value for the admin so it's sticky 2503 if (ap.encryptionRequested != encrypt) { 2504 ap.encryptionRequested = encrypt; 2505 saveSettingsLocked(userHandle); 2506 } 2507 2508 DevicePolicyData policy = getUserData(UserHandle.USER_OWNER); 2509 // (2) Compute "max" for all admins 2510 boolean newRequested = false; 2511 final int N = policy.mAdminList.size(); 2512 for (int i = 0; i < N; i++) { 2513 newRequested |= policy.mAdminList.get(i).encryptionRequested; 2514 } 2515 2516 // Notify OS of new request 2517 setEncryptionRequested(newRequested); 2518 2519 // Return the new global request status 2520 return newRequested 2521 ? DevicePolicyManager.ENCRYPTION_STATUS_ACTIVE 2522 : DevicePolicyManager.ENCRYPTION_STATUS_INACTIVE; 2523 } 2524 } 2525 2526 /** 2527 * Get the current storage encryption request status for a given admin, or aggregate of all 2528 * active admins. 2529 */ 2530 public boolean getStorageEncryption(ComponentName who, int userHandle) { 2531 if (!mHasFeature) { 2532 return false; 2533 } 2534 enforceCrossUserPermission(userHandle); 2535 synchronized (this) { 2536 // Check for permissions if a particular caller is specified 2537 if (who != null) { 2538 // When checking for a single caller, status is based on caller's request 2539 ActiveAdmin ap = getActiveAdminUncheckedLocked(who, userHandle); 2540 return ap != null ? ap.encryptionRequested : false; 2541 } 2542 2543 // If no particular caller is specified, return the aggregate set of requests. 2544 // This is short circuited by returning true on the first hit. 2545 DevicePolicyData policy = getUserData(userHandle); 2546 final int N = policy.mAdminList.size(); 2547 for (int i = 0; i < N; i++) { 2548 if (policy.mAdminList.get(i).encryptionRequested) { 2549 return true; 2550 } 2551 } 2552 return false; 2553 } 2554 } 2555 2556 /** 2557 * Get the current encryption status of the device. 2558 */ 2559 public int getStorageEncryptionStatus(int userHandle) { 2560 if (!mHasFeature) { 2561 // Ok to return current status. 2562 } 2563 enforceCrossUserPermission(userHandle); 2564 return getEncryptionStatus(); 2565 } 2566 2567 /** 2568 * Hook to low-levels: This should report if the filesystem supports encrypted storage. 2569 */ 2570 private boolean isEncryptionSupported() { 2571 // Note, this can be implemented as 2572 // return getEncryptionStatus() != DevicePolicyManager.ENCRYPTION_STATUS_UNSUPPORTED; 2573 // But is provided as a separate internal method if there's a faster way to do a 2574 // simple check for supported-or-not. 2575 return getEncryptionStatus() != DevicePolicyManager.ENCRYPTION_STATUS_UNSUPPORTED; 2576 } 2577 2578 /** 2579 * Hook to low-levels: Reporting the current status of encryption. 2580 * @return A value such as {@link DevicePolicyManager#ENCRYPTION_STATUS_UNSUPPORTED} or 2581 * {@link DevicePolicyManager#ENCRYPTION_STATUS_INACTIVE} or 2582 * {@link DevicePolicyManager#ENCRYPTION_STATUS_ACTIVE}. 2583 */ 2584 private int getEncryptionStatus() { 2585 String status = SystemProperties.get("ro.crypto.state", "unsupported"); 2586 if ("encrypted".equalsIgnoreCase(status)) { 2587 return DevicePolicyManager.ENCRYPTION_STATUS_ACTIVE; 2588 } else if ("unencrypted".equalsIgnoreCase(status)) { 2589 return DevicePolicyManager.ENCRYPTION_STATUS_INACTIVE; 2590 } else { 2591 return DevicePolicyManager.ENCRYPTION_STATUS_UNSUPPORTED; 2592 } 2593 } 2594 2595 /** 2596 * Hook to low-levels: If needed, record the new admin setting for encryption. 2597 */ 2598 private void setEncryptionRequested(boolean encrypt) { 2599 } 2600 2601 /** 2602 * The system property used to share the state of the camera. The native camera service 2603 * is expected to read this property and act accordingly. 2604 */ 2605 public static final String SYSTEM_PROP_DISABLE_CAMERA = "sys.secpolicy.camera.disabled"; 2606 2607 /** 2608 * Disables all device cameras according to the specified admin. 2609 */ 2610 public void setCameraDisabled(ComponentName who, boolean disabled, int userHandle) { 2611 if (!mHasFeature) { 2612 return; 2613 } 2614 enforceCrossUserPermission(userHandle); 2615 synchronized (this) { 2616 if (who == null) { 2617 throw new NullPointerException("ComponentName is null"); 2618 } 2619 ActiveAdmin ap = getActiveAdminForCallerLocked(who, 2620 DeviceAdminInfo.USES_POLICY_DISABLE_CAMERA); 2621 if (ap.disableCamera != disabled) { 2622 ap.disableCamera = disabled; 2623 saveSettingsLocked(userHandle); 2624 } 2625 syncDeviceCapabilitiesLocked(getUserData(userHandle)); 2626 } 2627 } 2628 2629 /** 2630 * Gets whether or not all device cameras are disabled for a given admin, or disabled for any 2631 * active admins. 2632 */ 2633 public boolean getCameraDisabled(ComponentName who, int userHandle) { 2634 if (!mHasFeature) { 2635 return false; 2636 } 2637 synchronized (this) { 2638 if (who != null) { 2639 ActiveAdmin admin = getActiveAdminUncheckedLocked(who, userHandle); 2640 return (admin != null) ? admin.disableCamera : false; 2641 } 2642 2643 DevicePolicyData policy = getUserData(userHandle); 2644 // Determine whether or not the device camera is disabled for any active admins. 2645 final int N = policy.mAdminList.size(); 2646 for (int i = 0; i < N; i++) { 2647 ActiveAdmin admin = policy.mAdminList.get(i); 2648 if (admin.disableCamera) { 2649 return true; 2650 } 2651 } 2652 return false; 2653 } 2654 } 2655 2656 /** 2657 * Selectively disable keyguard features. 2658 */ 2659 public void setKeyguardDisabledFeatures(ComponentName who, int which, int userHandle) { 2660 if (!mHasFeature) { 2661 return; 2662 } 2663 enforceCrossUserPermission(userHandle); 2664 synchronized (this) { 2665 if (who == null) { 2666 throw new NullPointerException("ComponentName is null"); 2667 } 2668 ActiveAdmin ap = getActiveAdminForCallerLocked(who, 2669 DeviceAdminInfo.USES_POLICY_DISABLE_KEYGUARD_FEATURES); 2670 if (ap.disabledKeyguardFeatures != which) { 2671 ap.disabledKeyguardFeatures = which; 2672 saveSettingsLocked(userHandle); 2673 } 2674 syncDeviceCapabilitiesLocked(getUserData(userHandle)); 2675 } 2676 } 2677 2678 /** 2679 * Gets the disabled state for features in keyguard for the given admin, 2680 * or the aggregate of all active admins if who is null. 2681 */ 2682 public int getKeyguardDisabledFeatures(ComponentName who, int userHandle) { 2683 if (!mHasFeature) { 2684 return 0; 2685 } 2686 enforceCrossUserPermission(userHandle); 2687 synchronized (this) { 2688 if (who != null) { 2689 ActiveAdmin admin = getActiveAdminUncheckedLocked(who, userHandle); 2690 return (admin != null) ? admin.disabledKeyguardFeatures : 0; 2691 } 2692 2693 // Determine which keyguard features are disabled for any active admins. 2694 DevicePolicyData policy = getUserData(userHandle); 2695 final int N = policy.mAdminList.size(); 2696 int which = 0; 2697 for (int i = 0; i < N; i++) { 2698 ActiveAdmin admin = policy.mAdminList.get(i); 2699 which |= admin.disabledKeyguardFeatures; 2700 } 2701 return which; 2702 } 2703 } 2704 2705 @Override 2706 public boolean setDeviceOwner(String packageName, String ownerName) { 2707 if (!mHasFeature) { 2708 return false; 2709 } 2710 if (packageName == null 2711 || !DeviceOwner.isInstalled(packageName, mContext.getPackageManager())) { 2712 throw new IllegalArgumentException("Invalid package name " + packageName 2713 + " for device owner"); 2714 } 2715 synchronized (this) { 2716 if (mDeviceOwner == null && !isDeviceProvisioned()) { 2717 mDeviceOwner = new DeviceOwner(packageName, ownerName); 2718 mDeviceOwner.writeOwnerFile(); 2719 return true; 2720 } else { 2721 throw new IllegalStateException("Trying to set device owner to " + packageName 2722 + ", owner=" + mDeviceOwner.getPackageName() 2723 + ", device_provisioned=" + isDeviceProvisioned()); 2724 } 2725 } 2726 } 2727 2728 @Override 2729 public boolean isDeviceOwner(String packageName) { 2730 if (!mHasFeature) { 2731 return false; 2732 } 2733 synchronized (this) { 2734 return mDeviceOwner != null 2735 && mDeviceOwner.getPackageName().equals(packageName); 2736 } 2737 } 2738 2739 @Override 2740 public String getDeviceOwner() { 2741 if (!mHasFeature) { 2742 return null; 2743 } 2744 synchronized (this) { 2745 if (mDeviceOwner != null) { 2746 return mDeviceOwner.getPackageName(); 2747 } 2748 } 2749 return null; 2750 } 2751 2752 @Override 2753 public String getDeviceOwnerName() { 2754 if (!mHasFeature) { 2755 return null; 2756 } 2757 mContext.enforceCallingOrSelfPermission(android.Manifest.permission.MANAGE_USERS, null); 2758 synchronized (this) { 2759 if (mDeviceOwner != null) { 2760 return mDeviceOwner.getName(); 2761 } 2762 } 2763 return null; 2764 } 2765 2766 private boolean isDeviceProvisioned() { 2767 return Settings.Global.getInt(mContext.getContentResolver(), 2768 Settings.Global.DEVICE_PROVISIONED, 0) > 0; 2769 } 2770 2771 private void enforceCrossUserPermission(int userHandle) { 2772 if (userHandle < 0) { 2773 throw new IllegalArgumentException("Invalid userId " + userHandle); 2774 } 2775 final int callingUid = Binder.getCallingUid(); 2776 if (userHandle == UserHandle.getUserId(callingUid)) return; 2777 if (callingUid != Process.SYSTEM_UID && callingUid != 0) { 2778 mContext.enforceCallingOrSelfPermission( 2779 android.Manifest.permission.INTERACT_ACROSS_USERS_FULL, "Must be system or have" 2780 + " INTERACT_ACROSS_USERS_FULL permission"); 2781 } 2782 } 2783 2784 private void enableIfNecessary(String packageName, int userId) { 2785 try { 2786 IPackageManager ipm = AppGlobals.getPackageManager(); 2787 ApplicationInfo ai = ipm.getApplicationInfo(packageName, 2788 PackageManager.GET_DISABLED_UNTIL_USED_COMPONENTS, 2789 userId); 2790 if (ai.enabledSetting 2791 == PackageManager.COMPONENT_ENABLED_STATE_DISABLED_UNTIL_USED) { 2792 ipm.setApplicationEnabledSetting(packageName, 2793 PackageManager.COMPONENT_ENABLED_STATE_DEFAULT, 2794 PackageManager.DONT_KILL_APP, userId, "DevicePolicyManager"); 2795 } 2796 } catch (RemoteException e) { 2797 } 2798 } 2799 2800 @Override 2801 protected void dump(FileDescriptor fd, PrintWriter pw, String[] args) { 2802 if (mContext.checkCallingOrSelfPermission(android.Manifest.permission.DUMP) 2803 != PackageManager.PERMISSION_GRANTED) { 2804 2805 pw.println("Permission Denial: can't dump DevicePolicyManagerService from from pid=" 2806 + Binder.getCallingPid() 2807 + ", uid=" + Binder.getCallingUid()); 2808 return; 2809 } 2810 2811 final Printer p = new PrintWriterPrinter(pw); 2812 2813 synchronized (this) { 2814 p.println("Current Device Policy Manager state:"); 2815 2816 int userCount = mUserData.size(); 2817 for (int u = 0; u < userCount; u++) { 2818 DevicePolicyData policy = getUserData(mUserData.keyAt(u)); 2819 p.println(" Enabled Device Admins (User " + policy.mUserHandle + "):"); 2820 final int N = policy.mAdminList.size(); 2821 for (int i=0; i<N; i++) { 2822 ActiveAdmin ap = policy.mAdminList.get(i); 2823 if (ap != null) { 2824 pw.print(" "); pw.print(ap.info.getComponent().flattenToShortString()); 2825 pw.println(":"); 2826 ap.dump(" ", pw); 2827 } 2828 } 2829 2830 pw.println(" "); 2831 pw.print(" mPasswordOwner="); pw.println(policy.mPasswordOwner); 2832 } 2833 } 2834 } 2835 2836 static class DeviceOwner { 2837 private static final String DEVICE_OWNER_XML = "device_owner.xml"; 2838 private static final String TAG_DEVICE_OWNER = "device-owner"; 2839 private static final String ATTR_NAME = "name"; 2840 private static final String ATTR_PACKAGE = "package"; 2841 private String mPackageName; 2842 private String mOwnerName; 2843 2844 DeviceOwner() { 2845 readOwnerFile(); 2846 } 2847 2848 DeviceOwner(String packageName, String ownerName) { 2849 this.mPackageName = packageName; 2850 this.mOwnerName = ownerName; 2851 } 2852 2853 static boolean isRegistered() { 2854 return new File(Environment.getSystemSecureDirectory(), 2855 DEVICE_OWNER_XML).exists(); 2856 } 2857 2858 String getPackageName() { 2859 return mPackageName; 2860 } 2861 2862 String getName() { 2863 return mOwnerName; 2864 } 2865 2866 static boolean isInstalled(String packageName, PackageManager pm) { 2867 try { 2868 PackageInfo pi; 2869 if ((pi = pm.getPackageInfo(packageName, 0)) != null) { 2870 if ((pi.applicationInfo.flags & ApplicationInfo.FLAG_SYSTEM) != 0) { 2871 return true; 2872 } 2873 } 2874 } catch (NameNotFoundException nnfe) { 2875 Slog.w(TAG, "Device Owner package " + packageName + " not installed."); 2876 } 2877 return false; 2878 } 2879 2880 void readOwnerFile() { 2881 AtomicFile file = new AtomicFile(new File(Environment.getSystemSecureDirectory(), 2882 DEVICE_OWNER_XML)); 2883 try { 2884 FileInputStream input = file.openRead(); 2885 XmlPullParser parser = Xml.newPullParser(); 2886 parser.setInput(input, null); 2887 int type; 2888 while ((type=parser.next()) != XmlPullParser.END_DOCUMENT 2889 && type != XmlPullParser.START_TAG) { 2890 } 2891 String tag = parser.getName(); 2892 if (!TAG_DEVICE_OWNER.equals(tag)) { 2893 throw new XmlPullParserException( 2894 "Device Owner file does not start with device-owner tag: found " + tag); 2895 } 2896 mPackageName = parser.getAttributeValue(null, ATTR_PACKAGE); 2897 mOwnerName = parser.getAttributeValue(null, ATTR_NAME); 2898 input.close(); 2899 } catch (XmlPullParserException xppe) { 2900 Slog.e(TAG, "Error parsing device-owner file\n" + xppe); 2901 } catch (IOException ioe) { 2902 Slog.e(TAG, "IO Exception when reading device-owner file\n" + ioe); 2903 } 2904 } 2905 2906 void writeOwnerFile() { 2907 synchronized (this) { 2908 writeOwnerFileLocked(); 2909 } 2910 } 2911 2912 private void writeOwnerFileLocked() { 2913 AtomicFile file = new AtomicFile(new File(Environment.getSystemSecureDirectory(), 2914 DEVICE_OWNER_XML)); 2915 try { 2916 FileOutputStream output = file.startWrite(); 2917 XmlSerializer out = new FastXmlSerializer(); 2918 out.setOutput(output, "utf-8"); 2919 out.startDocument(null, true); 2920 out.startTag(null, TAG_DEVICE_OWNER); 2921 out.attribute(null, ATTR_PACKAGE, mPackageName); 2922 if (mOwnerName != null) { 2923 out.attribute(null, ATTR_NAME, mOwnerName); 2924 } 2925 out.endTag(null, TAG_DEVICE_OWNER); 2926 out.endDocument(); 2927 out.flush(); 2928 file.finishWrite(output); 2929 } catch (IOException ioe) { 2930 Slog.e(TAG, "IO Exception when writing device-owner file\n" + ioe); 2931 } 2932 } 2933 } 2934 } 2935