TrustManagerService.java revision 50bfeec868157106e8b60abf8964cb24462af182
1/* 2 * Copyright (C) 2014 The Android Open Source Project 3 * 4 * Licensed under the Apache License, Version 2.0 (the "License"); 5 * you may not use this file except in compliance with the License. 6 * You may obtain a copy of the License at 7 * 8 * http://www.apache.org/licenses/LICENSE-2.0 9 * 10 * Unless required by applicable law or agreed to in writing, software 11 * distributed under the License is distributed on an "AS IS" BASIS, 12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 * See the License for the specific language governing permissions and 14 * limitations under the License 15 */ 16 17package com.android.server.trust; 18 19import com.android.internal.annotations.GuardedBy; 20import com.android.internal.content.PackageMonitor; 21import com.android.internal.widget.LockPatternUtils; 22import com.android.server.SystemService; 23 24import org.xmlpull.v1.XmlPullParser; 25import org.xmlpull.v1.XmlPullParserException; 26 27import android.Manifest; 28import android.app.ActivityManager; 29import android.app.ActivityManagerNative; 30import android.app.admin.DevicePolicyManager; 31import android.app.trust.ITrustListener; 32import android.app.trust.ITrustManager; 33import android.content.BroadcastReceiver; 34import android.content.ComponentName; 35import android.content.Context; 36import android.content.Intent; 37import android.content.IntentFilter; 38import android.content.pm.ApplicationInfo; 39import android.content.pm.PackageManager; 40import android.content.pm.ResolveInfo; 41import android.content.pm.UserInfo; 42import android.content.res.Resources; 43import android.content.res.TypedArray; 44import android.content.res.XmlResourceParser; 45import android.graphics.drawable.Drawable; 46import android.os.Binder; 47import android.os.DeadObjectException; 48import android.os.Handler; 49import android.os.IBinder; 50import android.os.Message; 51import android.os.PersistableBundle; 52import android.os.RemoteException; 53import android.os.SystemClock; 54import android.os.UserHandle; 55import android.os.UserManager; 56import android.provider.Settings; 57import android.service.trust.TrustAgentService; 58import android.util.ArraySet; 59import android.util.AttributeSet; 60import android.util.Log; 61import android.util.Slog; 62import android.util.SparseBooleanArray; 63import android.util.Xml; 64import android.view.WindowManagerGlobal; 65import android.view.WindowManagerInternal; 66 67import java.io.FileDescriptor; 68import java.io.IOException; 69import java.io.PrintWriter; 70import java.util.ArrayList; 71import java.util.List; 72 73/** 74 * Manages trust agents and trust listeners. 75 * 76 * It is responsible for binding to the enabled {@link android.service.trust.TrustAgentService}s 77 * of each user and notifies them about events that are relevant to them. 78 * It start and stops them based on the value of 79 * {@link com.android.internal.widget.LockPatternUtils#getEnabledTrustAgents(int)}. 80 * 81 * It also keeps a set of {@link android.app.trust.ITrustListener}s that are notified whenever the 82 * trust state changes for any user. 83 * 84 * Trust state and the setting of enabled agents is kept per user and each user has its own 85 * instance of a {@link android.service.trust.TrustAgentService}. 86 */ 87public class TrustManagerService extends SystemService { 88 89 private static final boolean DEBUG = false; 90 private static final String TAG = "TrustManagerService"; 91 92 private static final Intent TRUST_AGENT_INTENT = 93 new Intent(TrustAgentService.SERVICE_INTERFACE); 94 private static final String PERMISSION_PROVIDE_AGENT = Manifest.permission.PROVIDE_TRUST_AGENT; 95 96 private static final int MSG_REGISTER_LISTENER = 1; 97 private static final int MSG_UNREGISTER_LISTENER = 2; 98 private static final int MSG_DISPATCH_UNLOCK_ATTEMPT = 3; 99 private static final int MSG_ENABLED_AGENTS_CHANGED = 4; 100 private static final int MSG_REQUIRE_CREDENTIAL_ENTRY = 5; 101 102 private final ArraySet<AgentInfo> mActiveAgents = new ArraySet<AgentInfo>(); 103 private final ArrayList<ITrustListener> mTrustListeners = new ArrayList<ITrustListener>(); 104 private final Receiver mReceiver = new Receiver(); 105 private final SparseBooleanArray mUserHasAuthenticatedSinceBoot = new SparseBooleanArray(); 106 /* package */ final TrustArchive mArchive = new TrustArchive(); 107 private final Context mContext; 108 private final LockPatternUtils mLockPatternUtils; 109 private final UserManager mUserManager; 110 private final ActivityManager mActivityManager; 111 112 @GuardedBy("mUserIsTrusted") 113 private final SparseBooleanArray mUserIsTrusted = new SparseBooleanArray(); 114 115 private boolean mTrustAgentsCanRun = false; 116 117 public TrustManagerService(Context context) { 118 super(context); 119 mContext = context; 120 mUserManager = (UserManager) mContext.getSystemService(Context.USER_SERVICE); 121 mActivityManager = (ActivityManager) mContext.getSystemService(Context.ACTIVITY_SERVICE); 122 mLockPatternUtils = new LockPatternUtils(context); 123 } 124 125 @Override 126 public void onStart() { 127 publishBinderService(Context.TRUST_SERVICE, mService); 128 } 129 130 @Override 131 public void onBootPhase(int phase) { 132 if (isSafeMode()) { 133 // No trust agents in safe mode. 134 return; 135 } 136 if (phase == SystemService.PHASE_SYSTEM_SERVICES_READY) { 137 mPackageMonitor.register(mContext, mHandler.getLooper(), UserHandle.ALL, true); 138 mReceiver.register(mContext); 139 } else if (phase == SystemService.PHASE_THIRD_PARTY_APPS_CAN_START) { 140 mTrustAgentsCanRun = true; 141 refreshAgentList(UserHandle.USER_ALL); 142 } else if (phase == SystemService.PHASE_BOOT_COMPLETED) { 143 maybeEnableFactoryTrustAgents(mLockPatternUtils, UserHandle.USER_OWNER); 144 } 145 } 146 147 // Agent management 148 149 private static final class AgentInfo { 150 CharSequence label; 151 Drawable icon; 152 ComponentName component; // service that implements ITrustAgent 153 ComponentName settings; // setting to launch to modify agent. 154 TrustAgentWrapper agent; 155 int userId; 156 157 @Override 158 public boolean equals(Object other) { 159 if (!(other instanceof AgentInfo)) { 160 return false; 161 } 162 AgentInfo o = (AgentInfo) other; 163 return component.equals(o.component) && userId == o.userId; 164 } 165 166 @Override 167 public int hashCode() { 168 return component.hashCode() * 31 + userId; 169 } 170 } 171 172 private void updateTrustAll() { 173 List<UserInfo> userInfos = mUserManager.getUsers(true /* excludeDying */); 174 for (UserInfo userInfo : userInfos) { 175 updateTrust(userInfo.id, false); 176 } 177 } 178 179 public void updateTrust(int userId, boolean initiatedByUser) { 180 dispatchOnTrustManagedChanged(aggregateIsTrustManaged(userId), userId); 181 boolean trusted = aggregateIsTrusted(userId); 182 synchronized (mUserIsTrusted) { 183 mUserIsTrusted.put(userId, trusted); 184 } 185 dispatchOnTrustChanged(trusted, userId, initiatedByUser); 186 } 187 188 void refreshAgentList(int userId) { 189 if (DEBUG) Slog.d(TAG, "refreshAgentList()"); 190 if (!mTrustAgentsCanRun) { 191 return; 192 } 193 if (userId != UserHandle.USER_ALL && userId < UserHandle.USER_OWNER) { 194 Log.e(TAG, "refreshAgentList(userId=" + userId + "): Invalid user handle," 195 + " must be USER_ALL or a specific user.", new Throwable("here")); 196 userId = UserHandle.USER_ALL; 197 } 198 PackageManager pm = mContext.getPackageManager(); 199 200 List<UserInfo> userInfos; 201 if (userId == UserHandle.USER_ALL) { 202 userInfos = mUserManager.getUsers(true /* excludeDying */); 203 } else { 204 userInfos = new ArrayList<>(); 205 userInfos.add(mUserManager.getUserInfo(userId)); 206 } 207 LockPatternUtils lockPatternUtils = mLockPatternUtils; 208 209 ArraySet<AgentInfo> obsoleteAgents = new ArraySet<>(); 210 obsoleteAgents.addAll(mActiveAgents); 211 212 for (UserInfo userInfo : userInfos) { 213 if (userInfo == null || userInfo.partial || !userInfo.isEnabled() 214 || userInfo.guestToRemove) continue; 215 if (!userInfo.supportsSwitchTo()) continue; 216 if (!mActivityManager.isUserRunning(userInfo.id)) continue; 217 if (lockPatternUtils.getKeyguardStoredPasswordQuality(userInfo.id) 218 == DevicePolicyManager.PASSWORD_QUALITY_UNSPECIFIED) continue; 219 if (!mUserHasAuthenticatedSinceBoot.get(userInfo.id)) continue; 220 DevicePolicyManager dpm = lockPatternUtils.getDevicePolicyManager(); 221 int disabledFeatures = dpm.getKeyguardDisabledFeatures(null, userInfo.id); 222 final boolean disableTrustAgents = 223 (disabledFeatures & DevicePolicyManager.KEYGUARD_DISABLE_TRUST_AGENTS) != 0; 224 225 List<ComponentName> enabledAgents = lockPatternUtils.getEnabledTrustAgents(userInfo.id); 226 if (enabledAgents == null) { 227 continue; 228 } 229 List<ResolveInfo> resolveInfos = resolveAllowedTrustAgents(pm, userInfo.id); 230 for (ResolveInfo resolveInfo : resolveInfos) { 231 ComponentName name = getComponentName(resolveInfo); 232 233 if (!enabledAgents.contains(name)) continue; 234 if (disableTrustAgents) { 235 List<PersistableBundle> config = 236 dpm.getTrustAgentConfiguration(null /* admin */, name, userInfo.id); 237 // Disable agent if no features are enabled. 238 if (config == null || config.isEmpty()) continue; 239 } 240 241 AgentInfo agentInfo = new AgentInfo(); 242 agentInfo.component = name; 243 agentInfo.userId = userInfo.id; 244 if (!mActiveAgents.contains(agentInfo)) { 245 agentInfo.label = resolveInfo.loadLabel(pm); 246 agentInfo.icon = resolveInfo.loadIcon(pm); 247 agentInfo.settings = getSettingsComponentName(pm, resolveInfo); 248 agentInfo.agent = new TrustAgentWrapper(mContext, this, 249 new Intent().setComponent(name), userInfo.getUserHandle()); 250 mActiveAgents.add(agentInfo); 251 } else { 252 obsoleteAgents.remove(agentInfo); 253 } 254 } 255 } 256 257 boolean trustMayHaveChanged = false; 258 for (int i = 0; i < obsoleteAgents.size(); i++) { 259 AgentInfo info = obsoleteAgents.valueAt(i); 260 if (userId == UserHandle.USER_ALL || userId == info.userId) { 261 if (info.agent.isManagingTrust()) { 262 trustMayHaveChanged = true; 263 } 264 info.agent.destroy(); 265 mActiveAgents.remove(info); 266 } 267 } 268 269 if (trustMayHaveChanged) { 270 if (userId == UserHandle.USER_ALL) { 271 updateTrustAll(); 272 } else { 273 updateTrust(userId, false /* initiatedByUser */); 274 } 275 } 276 } 277 278 void updateDevicePolicyFeatures() { 279 for (int i = 0; i < mActiveAgents.size(); i++) { 280 AgentInfo info = mActiveAgents.valueAt(i); 281 if (info.agent.isConnected()) { 282 info.agent.updateDevicePolicyFeatures(); 283 } 284 } 285 } 286 287 private void removeAgentsOfPackage(String packageName) { 288 boolean trustMayHaveChanged = false; 289 for (int i = mActiveAgents.size() - 1; i >= 0; i--) { 290 AgentInfo info = mActiveAgents.valueAt(i); 291 if (packageName.equals(info.component.getPackageName())) { 292 Log.i(TAG, "Resetting agent " + info.component.flattenToShortString()); 293 if (info.agent.isManagingTrust()) { 294 trustMayHaveChanged = true; 295 } 296 info.agent.destroy(); 297 mActiveAgents.removeAt(i); 298 } 299 } 300 if (trustMayHaveChanged) { 301 updateTrustAll(); 302 } 303 } 304 305 public void resetAgent(ComponentName name, int userId) { 306 boolean trustMayHaveChanged = false; 307 for (int i = mActiveAgents.size() - 1; i >= 0; i--) { 308 AgentInfo info = mActiveAgents.valueAt(i); 309 if (name.equals(info.component) && userId == info.userId) { 310 Log.i(TAG, "Resetting agent " + info.component.flattenToShortString()); 311 if (info.agent.isManagingTrust()) { 312 trustMayHaveChanged = true; 313 } 314 info.agent.destroy(); 315 mActiveAgents.removeAt(i); 316 } 317 } 318 if (trustMayHaveChanged) { 319 updateTrust(userId, false); 320 } 321 refreshAgentList(userId); 322 } 323 324 private ComponentName getSettingsComponentName(PackageManager pm, ResolveInfo resolveInfo) { 325 if (resolveInfo == null || resolveInfo.serviceInfo == null 326 || resolveInfo.serviceInfo.metaData == null) return null; 327 String cn = null; 328 XmlResourceParser parser = null; 329 Exception caughtException = null; 330 try { 331 parser = resolveInfo.serviceInfo.loadXmlMetaData(pm, 332 TrustAgentService.TRUST_AGENT_META_DATA); 333 if (parser == null) { 334 Slog.w(TAG, "Can't find " + TrustAgentService.TRUST_AGENT_META_DATA + " meta-data"); 335 return null; 336 } 337 Resources res = pm.getResourcesForApplication(resolveInfo.serviceInfo.applicationInfo); 338 AttributeSet attrs = Xml.asAttributeSet(parser); 339 int type; 340 while ((type = parser.next()) != XmlPullParser.END_DOCUMENT 341 && type != XmlPullParser.START_TAG) { 342 // Drain preamble. 343 } 344 String nodeName = parser.getName(); 345 if (!"trust-agent".equals(nodeName)) { 346 Slog.w(TAG, "Meta-data does not start with trust-agent tag"); 347 return null; 348 } 349 TypedArray sa = res 350 .obtainAttributes(attrs, com.android.internal.R.styleable.TrustAgent); 351 cn = sa.getString(com.android.internal.R.styleable.TrustAgent_settingsActivity); 352 sa.recycle(); 353 } catch (PackageManager.NameNotFoundException e) { 354 caughtException = e; 355 } catch (IOException e) { 356 caughtException = e; 357 } catch (XmlPullParserException e) { 358 caughtException = e; 359 } finally { 360 if (parser != null) parser.close(); 361 } 362 if (caughtException != null) { 363 Slog.w(TAG, "Error parsing : " + resolveInfo.serviceInfo.packageName, caughtException); 364 return null; 365 } 366 if (cn == null) { 367 return null; 368 } 369 if (cn.indexOf('/') < 0) { 370 cn = resolveInfo.serviceInfo.packageName + "/" + cn; 371 } 372 return ComponentName.unflattenFromString(cn); 373 } 374 375 private ComponentName getComponentName(ResolveInfo resolveInfo) { 376 if (resolveInfo == null || resolveInfo.serviceInfo == null) return null; 377 return new ComponentName(resolveInfo.serviceInfo.packageName, resolveInfo.serviceInfo.name); 378 } 379 380 private void maybeEnableFactoryTrustAgents(LockPatternUtils utils, int userId) { 381 if (0 != Settings.Secure.getIntForUser(mContext.getContentResolver(), 382 Settings.Secure.TRUST_AGENTS_INITIALIZED, 0, userId)) { 383 return; 384 } 385 PackageManager pm = mContext.getPackageManager(); 386 List<ResolveInfo> resolveInfos = resolveAllowedTrustAgents(pm, userId); 387 ArraySet<ComponentName> discoveredAgents = new ArraySet<>(); 388 for (ResolveInfo resolveInfo : resolveInfos) { 389 ComponentName componentName = getComponentName(resolveInfo); 390 int applicationInfoFlags = resolveInfo.serviceInfo.applicationInfo.flags; 391 if ((applicationInfoFlags & ApplicationInfo.FLAG_SYSTEM) == 0) { 392 Log.i(TAG, "Leaving agent " + componentName + " disabled because package " 393 + "is not a system package."); 394 continue; 395 } 396 discoveredAgents.add(componentName); 397 } 398 399 List<ComponentName> previouslyEnabledAgents = utils.getEnabledTrustAgents(userId); 400 if (previouslyEnabledAgents != null) { 401 discoveredAgents.addAll(previouslyEnabledAgents); 402 } 403 utils.setEnabledTrustAgents(discoveredAgents, userId); 404 Settings.Secure.putIntForUser(mContext.getContentResolver(), 405 Settings.Secure.TRUST_AGENTS_INITIALIZED, 1, userId); 406 } 407 408 private List<ResolveInfo> resolveAllowedTrustAgents(PackageManager pm, int userId) { 409 List<ResolveInfo> resolveInfos = pm.queryIntentServicesAsUser(TRUST_AGENT_INTENT, 410 0 /* flags */, userId); 411 ArrayList<ResolveInfo> allowedAgents = new ArrayList<>(resolveInfos.size()); 412 for (ResolveInfo resolveInfo : resolveInfos) { 413 if (resolveInfo.serviceInfo == null) continue; 414 if (resolveInfo.serviceInfo.applicationInfo == null) continue; 415 String packageName = resolveInfo.serviceInfo.packageName; 416 if (pm.checkPermission(PERMISSION_PROVIDE_AGENT, packageName) 417 != PackageManager.PERMISSION_GRANTED) { 418 ComponentName name = getComponentName(resolveInfo); 419 Log.w(TAG, "Skipping agent " + name + " because package does not have" 420 + " permission " + PERMISSION_PROVIDE_AGENT + "."); 421 continue; 422 } 423 allowedAgents.add(resolveInfo); 424 } 425 return allowedAgents; 426 } 427 428 // Agent dispatch and aggregation 429 430 private boolean aggregateIsTrusted(int userId) { 431 if (!mUserHasAuthenticatedSinceBoot.get(userId)) { 432 return false; 433 } 434 for (int i = 0; i < mActiveAgents.size(); i++) { 435 AgentInfo info = mActiveAgents.valueAt(i); 436 if (info.userId == userId) { 437 if (info.agent.isTrusted()) { 438 return true; 439 } 440 } 441 } 442 return false; 443 } 444 445 private boolean aggregateIsTrustManaged(int userId) { 446 if (!mUserHasAuthenticatedSinceBoot.get(userId)) { 447 return false; 448 } 449 for (int i = 0; i < mActiveAgents.size(); i++) { 450 AgentInfo info = mActiveAgents.valueAt(i); 451 if (info.userId == userId) { 452 if (info.agent.isManagingTrust()) { 453 return true; 454 } 455 } 456 } 457 return false; 458 } 459 460 private void dispatchUnlockAttempt(boolean successful, int userId) { 461 for (int i = 0; i < mActiveAgents.size(); i++) { 462 AgentInfo info = mActiveAgents.valueAt(i); 463 if (info.userId == userId) { 464 info.agent.onUnlockAttempt(successful); 465 } 466 } 467 468 if (successful) { 469 updateUserHasAuthenticated(userId); 470 } 471 } 472 473 private void updateUserHasAuthenticated(int userId) { 474 if (!mUserHasAuthenticatedSinceBoot.get(userId)) { 475 mUserHasAuthenticatedSinceBoot.put(userId, true); 476 refreshAgentList(userId); 477 } 478 } 479 480 481 private void requireCredentialEntry(int userId) { 482 if (userId == UserHandle.USER_ALL) { 483 mUserHasAuthenticatedSinceBoot.clear(); 484 refreshAgentList(UserHandle.USER_ALL); 485 } else { 486 mUserHasAuthenticatedSinceBoot.put(userId, false); 487 refreshAgentList(userId); 488 } 489 } 490 491 // Listeners 492 493 private void addListener(ITrustListener listener) { 494 for (int i = 0; i < mTrustListeners.size(); i++) { 495 if (mTrustListeners.get(i).asBinder() == listener.asBinder()) { 496 return; 497 } 498 } 499 mTrustListeners.add(listener); 500 updateTrustAll(); 501 } 502 503 private void removeListener(ITrustListener listener) { 504 for (int i = 0; i < mTrustListeners.size(); i++) { 505 if (mTrustListeners.get(i).asBinder() == listener.asBinder()) { 506 mTrustListeners.remove(i); 507 return; 508 } 509 } 510 } 511 512 private void dispatchOnTrustChanged(boolean enabled, int userId, boolean initiatedByUser) { 513 if (!enabled) initiatedByUser = false; 514 for (int i = 0; i < mTrustListeners.size(); i++) { 515 try { 516 mTrustListeners.get(i).onTrustChanged(enabled, userId, initiatedByUser); 517 } catch (DeadObjectException e) { 518 Slog.d(TAG, "Removing dead TrustListener."); 519 mTrustListeners.remove(i); 520 i--; 521 } catch (RemoteException e) { 522 Slog.e(TAG, "Exception while notifying TrustListener.", e); 523 } 524 } 525 } 526 527 private void dispatchOnTrustManagedChanged(boolean managed, int userId) { 528 for (int i = 0; i < mTrustListeners.size(); i++) { 529 try { 530 mTrustListeners.get(i).onTrustManagedChanged(managed, userId); 531 } catch (DeadObjectException e) { 532 Slog.d(TAG, "Removing dead TrustListener."); 533 mTrustListeners.remove(i); 534 i--; 535 } catch (RemoteException e) { 536 Slog.e(TAG, "Exception while notifying TrustListener.", e); 537 } 538 } 539 } 540 541 // User lifecycle 542 543 @Override 544 public void onStartUser(int userId) { 545 refreshAgentList(userId); 546 } 547 548 @Override 549 public void onCleanupUser(int userId) { 550 refreshAgentList(userId); 551 } 552 553 // Plumbing 554 555 private final IBinder mService = new ITrustManager.Stub() { 556 @Override 557 public void reportUnlockAttempt(boolean authenticated, int userId) throws RemoteException { 558 enforceReportPermission(); 559 mHandler.obtainMessage(MSG_DISPATCH_UNLOCK_ATTEMPT, authenticated ? 1 : 0, userId) 560 .sendToTarget(); 561 } 562 563 @Override 564 public void reportEnabledTrustAgentsChanged(int userId) throws RemoteException { 565 enforceReportPermission(); 566 // coalesce refresh messages. 567 mHandler.removeMessages(MSG_ENABLED_AGENTS_CHANGED); 568 mHandler.sendEmptyMessage(MSG_ENABLED_AGENTS_CHANGED); 569 } 570 571 @Override 572 public void reportRequireCredentialEntry(int userId) throws RemoteException { 573 enforceReportPermission(); 574 if (userId == UserHandle.USER_ALL || userId >= UserHandle.USER_OWNER) { 575 mHandler.obtainMessage(MSG_REQUIRE_CREDENTIAL_ENTRY, userId, 0).sendToTarget(); 576 } else { 577 throw new IllegalArgumentException( 578 "userId must be an explicit user id or USER_ALL"); 579 } 580 } 581 582 @Override 583 public void registerTrustListener(ITrustListener trustListener) throws RemoteException { 584 enforceListenerPermission(); 585 mHandler.obtainMessage(MSG_REGISTER_LISTENER, trustListener).sendToTarget(); 586 } 587 588 @Override 589 public void unregisterTrustListener(ITrustListener trustListener) throws RemoteException { 590 enforceListenerPermission(); 591 mHandler.obtainMessage(MSG_UNREGISTER_LISTENER, trustListener).sendToTarget(); 592 } 593 594 @Override 595 public boolean isDeviceLocked(int userId) throws RemoteException { 596 userId = ActivityManager.handleIncomingUser(getCallingPid(), getCallingUid(), userId, 597 false /* allowAll */, true /* requireFull */, "isDeviceLocked", null); 598 userId = resolveProfileParent(userId); 599 600 boolean isSecure = mLockPatternUtils.isSecure(userId); 601 602 boolean isTrusted; 603 synchronized (mUserIsTrusted) { 604 isTrusted = mUserIsTrusted.get(userId); 605 } 606 607 boolean isLocked; 608 if (ActivityManager.getCurrentUser() != userId) { 609 isLocked = true; 610 } else { 611 isLocked = WindowManagerGlobal.getWindowManagerService().isKeyguardLocked(); 612 } 613 614 return isSecure && isLocked && !isTrusted; 615 } 616 617 private void enforceReportPermission() { 618 mContext.enforceCallingOrSelfPermission( 619 Manifest.permission.ACCESS_KEYGUARD_SECURE_STORAGE, "reporting trust events"); 620 } 621 622 private void enforceListenerPermission() { 623 mContext.enforceCallingPermission(Manifest.permission.TRUST_LISTENER, 624 "register trust listener"); 625 } 626 627 @Override 628 protected void dump(FileDescriptor fd, final PrintWriter fout, String[] args) { 629 mContext.enforceCallingPermission(Manifest.permission.DUMP, 630 "dumping TrustManagerService"); 631 if (isSafeMode()) { 632 fout.println("disabled because the system is in safe mode."); 633 return; 634 } 635 if (!mTrustAgentsCanRun) { 636 fout.println("disabled because the third-party apps can't run yet."); 637 return; 638 } 639 final UserInfo currentUser; 640 final List<UserInfo> userInfos = mUserManager.getUsers(true /* excludeDying */); 641 try { 642 currentUser = ActivityManagerNative.getDefault().getCurrentUser(); 643 } catch (RemoteException e) { 644 throw new RuntimeException(e); 645 } 646 mHandler.runWithScissors(new Runnable() { 647 @Override 648 public void run() { 649 fout.println("Trust manager state:"); 650 for (UserInfo user : userInfos) { 651 dumpUser(fout, user, user.id == currentUser.id); 652 } 653 } 654 }, 1500); 655 } 656 657 private void dumpUser(PrintWriter fout, UserInfo user, boolean isCurrent) { 658 fout.printf(" User \"%s\" (id=%d, flags=%#x)", 659 user.name, user.id, user.flags); 660 if (isCurrent) { 661 fout.print(" (current)"); 662 } 663 fout.print(": trusted=" + dumpBool(aggregateIsTrusted(user.id))); 664 fout.print(", trustManaged=" + dumpBool(aggregateIsTrustManaged(user.id))); 665 fout.println(); 666 fout.println(" Enabled agents:"); 667 boolean duplicateSimpleNames = false; 668 ArraySet<String> simpleNames = new ArraySet<String>(); 669 for (AgentInfo info : mActiveAgents) { 670 if (info.userId != user.id) { continue; } 671 boolean trusted = info.agent.isTrusted(); 672 fout.print(" "); fout.println(info.component.flattenToShortString()); 673 fout.print(" bound=" + dumpBool(info.agent.isBound())); 674 fout.print(", connected=" + dumpBool(info.agent.isConnected())); 675 fout.print(", managingTrust=" + dumpBool(info.agent.isManagingTrust())); 676 fout.print(", trusted=" + dumpBool(trusted)); 677 fout.println(); 678 if (trusted) { 679 fout.println(" message=\"" + info.agent.getMessage() + "\""); 680 } 681 if (!info.agent.isConnected()) { 682 String restartTime = TrustArchive.formatDuration( 683 info.agent.getScheduledRestartUptimeMillis() 684 - SystemClock.uptimeMillis()); 685 fout.println(" restartScheduledAt=" + restartTime); 686 } 687 if (!simpleNames.add(TrustArchive.getSimpleName(info.component))) { 688 duplicateSimpleNames = true; 689 } 690 } 691 fout.println(" Events:"); 692 mArchive.dump(fout, 50, user.id, " " /* linePrefix */, duplicateSimpleNames); 693 fout.println(); 694 } 695 696 private String dumpBool(boolean b) { 697 return b ? "1" : "0"; 698 } 699 }; 700 701 private int resolveProfileParent(int userId) { 702 long identity = Binder.clearCallingIdentity(); 703 try { 704 UserInfo parent = mUserManager.getProfileParent(userId); 705 if (parent != null) { 706 return parent.getUserHandle().getIdentifier(); 707 } 708 return userId; 709 } finally { 710 Binder.restoreCallingIdentity(identity); 711 } 712 } 713 714 private final Handler mHandler = new Handler() { 715 @Override 716 public void handleMessage(Message msg) { 717 switch (msg.what) { 718 case MSG_REGISTER_LISTENER: 719 addListener((ITrustListener) msg.obj); 720 break; 721 case MSG_UNREGISTER_LISTENER: 722 removeListener((ITrustListener) msg.obj); 723 break; 724 case MSG_DISPATCH_UNLOCK_ATTEMPT: 725 dispatchUnlockAttempt(msg.arg1 != 0, msg.arg2); 726 break; 727 case MSG_ENABLED_AGENTS_CHANGED: 728 refreshAgentList(UserHandle.USER_ALL); 729 break; 730 case MSG_REQUIRE_CREDENTIAL_ENTRY: 731 requireCredentialEntry(msg.arg1); 732 break; 733 } 734 } 735 }; 736 737 private final PackageMonitor mPackageMonitor = new PackageMonitor() { 738 @Override 739 public void onSomePackagesChanged() { 740 refreshAgentList(UserHandle.USER_ALL); 741 } 742 743 @Override 744 public boolean onPackageChanged(String packageName, int uid, String[] components) { 745 // We're interested in all changes, even if just some components get enabled / disabled. 746 return true; 747 } 748 749 @Override 750 public void onPackageDisappeared(String packageName, int reason) { 751 removeAgentsOfPackage(packageName); 752 } 753 }; 754 755 private class Receiver extends BroadcastReceiver { 756 757 @Override 758 public void onReceive(Context context, Intent intent) { 759 String action = intent.getAction(); 760 if (DevicePolicyManager.ACTION_DEVICE_POLICY_MANAGER_STATE_CHANGED.equals(action)) { 761 refreshAgentList(getSendingUserId()); 762 updateDevicePolicyFeatures(); 763 } else if (Intent.ACTION_USER_PRESENT.equals(action)) { 764 updateUserHasAuthenticated(getSendingUserId()); 765 } else if (Intent.ACTION_USER_ADDED.equals(action)) { 766 int userId = getUserId(intent); 767 if (userId > 0) { 768 maybeEnableFactoryTrustAgents(mLockPatternUtils, userId); 769 } 770 } else if (Intent.ACTION_USER_REMOVED.equals(action)) { 771 int userId = getUserId(intent); 772 if (userId > 0) { 773 mUserHasAuthenticatedSinceBoot.delete(userId); 774 mUserIsTrusted.delete(userId); 775 refreshAgentList(userId); 776 } 777 } 778 } 779 780 private int getUserId(Intent intent) { 781 int userId = intent.getIntExtra(Intent.EXTRA_USER_HANDLE, -100); 782 if (userId > 0) { 783 return userId; 784 } else { 785 Slog.wtf(TAG, "EXTRA_USER_HANDLE missing or invalid, value=" + userId); 786 return -100; 787 } 788 } 789 790 public void register(Context context) { 791 IntentFilter filter = new IntentFilter(); 792 filter.addAction(DevicePolicyManager.ACTION_DEVICE_POLICY_MANAGER_STATE_CHANGED); 793 filter.addAction(Intent.ACTION_USER_PRESENT); 794 filter.addAction(Intent.ACTION_USER_ADDED); 795 filter.addAction(Intent.ACTION_USER_REMOVED); 796 context.registerReceiverAsUser(this, 797 UserHandle.ALL, 798 filter, 799 null /* permission */, 800 null /* scheduler */); 801 } 802 } 803} 804