TrustManagerService.java revision c662898a182ca8f13d73b71649feeeeceb574edd
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.IWindowManager; 65import android.view.WindowManagerGlobal; 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_KEYGUARD_SHOWING_CHANGED = 6; 101 private static final int MSG_START_USER = 7; 102 private static final int MSG_CLEANUP_USER = 8; 103 private static final int MSG_SWITCH_USER = 9; 104 private static final int MSG_SET_DEVICE_LOCKED = 10; 105 private static final int MSG_FLUSH_TRUST_USUALLY_MANAGED = 11; 106 107 private static final int TRUST_USUALLY_MANAGED_FLUSH_DELAY = 2 * 60 * 1000; 108 109 private final ArraySet<AgentInfo> mActiveAgents = new ArraySet<>(); 110 private final ArrayList<ITrustListener> mTrustListeners = new ArrayList<>(); 111 private final Receiver mReceiver = new Receiver(); 112 113 /* package */ final TrustArchive mArchive = new TrustArchive(); 114 private final Context mContext; 115 private final LockPatternUtils mLockPatternUtils; 116 private final UserManager mUserManager; 117 private final ActivityManager mActivityManager; 118 119 @GuardedBy("mUserIsTrusted") 120 private final SparseBooleanArray mUserIsTrusted = new SparseBooleanArray(); 121 122 @GuardedBy("mDeviceLockedForUser") 123 private final SparseBooleanArray mDeviceLockedForUser = new SparseBooleanArray(); 124 125 @GuardedBy("mDeviceLockedForUser") 126 private final SparseBooleanArray mTrustUsuallyManagedForUser = new SparseBooleanArray(); 127 128 private final StrongAuthTracker mStrongAuthTracker; 129 130 private boolean mTrustAgentsCanRun = false; 131 private int mCurrentUser = UserHandle.USER_SYSTEM; 132 133 public TrustManagerService(Context context) { 134 super(context); 135 mContext = context; 136 mUserManager = (UserManager) mContext.getSystemService(Context.USER_SERVICE); 137 mActivityManager = (ActivityManager) mContext.getSystemService(Context.ACTIVITY_SERVICE); 138 mLockPatternUtils = new LockPatternUtils(context); 139 mStrongAuthTracker = new StrongAuthTracker(context); 140 } 141 142 @Override 143 public void onStart() { 144 publishBinderService(Context.TRUST_SERVICE, mService); 145 } 146 147 @Override 148 public void onBootPhase(int phase) { 149 if (isSafeMode()) { 150 // No trust agents in safe mode. 151 return; 152 } 153 if (phase == SystemService.PHASE_SYSTEM_SERVICES_READY) { 154 mPackageMonitor.register(mContext, mHandler.getLooper(), UserHandle.ALL, true); 155 mReceiver.register(mContext); 156 mLockPatternUtils.registerStrongAuthTracker(mStrongAuthTracker); 157 } else if (phase == SystemService.PHASE_THIRD_PARTY_APPS_CAN_START) { 158 mTrustAgentsCanRun = true; 159 refreshAgentList(UserHandle.USER_ALL); 160 } else if (phase == SystemService.PHASE_BOOT_COMPLETED) { 161 maybeEnableFactoryTrustAgents(mLockPatternUtils, UserHandle.USER_SYSTEM); 162 } 163 } 164 165 // Agent management 166 167 private static final class AgentInfo { 168 CharSequence label; 169 Drawable icon; 170 ComponentName component; // service that implements ITrustAgent 171 ComponentName settings; // setting to launch to modify agent. 172 TrustAgentWrapper agent; 173 int userId; 174 175 @Override 176 public boolean equals(Object other) { 177 if (!(other instanceof AgentInfo)) { 178 return false; 179 } 180 AgentInfo o = (AgentInfo) other; 181 return component.equals(o.component) && userId == o.userId; 182 } 183 184 @Override 185 public int hashCode() { 186 return component.hashCode() * 31 + userId; 187 } 188 } 189 190 private void updateTrustAll() { 191 List<UserInfo> userInfos = mUserManager.getUsers(true /* excludeDying */); 192 for (UserInfo userInfo : userInfos) { 193 updateTrust(userInfo.id, 0); 194 } 195 } 196 197 public void updateTrust(int userId, int flags) { 198 boolean managed = aggregateIsTrustManaged(userId); 199 dispatchOnTrustManagedChanged(managed, userId); 200 if (mStrongAuthTracker.isTrustAllowedForUser(userId) 201 && isTrustUsuallyManagedInternal(userId) != managed) { 202 updateTrustUsuallyManaged(userId, managed); 203 } 204 boolean trusted = aggregateIsTrusted(userId); 205 boolean changed; 206 synchronized (mUserIsTrusted) { 207 changed = mUserIsTrusted.get(userId) != trusted; 208 mUserIsTrusted.put(userId, trusted); 209 } 210 dispatchOnTrustChanged(trusted, userId, flags); 211 if (changed) { 212 refreshDeviceLockedForUser(userId); 213 } 214 } 215 216 private void updateTrustUsuallyManaged(int userId, boolean managed) { 217 synchronized (mTrustUsuallyManagedForUser) { 218 mTrustUsuallyManagedForUser.put(userId, managed); 219 } 220 // Wait a few minutes before committing to flash, in case the trust agent is transiently not 221 // managing trust (crashed, needs to acknowledge DPM restrictions, etc). 222 mHandler.removeMessages(MSG_FLUSH_TRUST_USUALLY_MANAGED); 223 mHandler.sendMessageDelayed( 224 mHandler.obtainMessage(MSG_FLUSH_TRUST_USUALLY_MANAGED), 225 TRUST_USUALLY_MANAGED_FLUSH_DELAY); 226 } 227 228 void refreshAgentList(int userIdOrAll) { 229 if (DEBUG) Slog.d(TAG, "refreshAgentList(" + userIdOrAll + ")"); 230 if (!mTrustAgentsCanRun) { 231 return; 232 } 233 if (userIdOrAll != UserHandle.USER_ALL && userIdOrAll < UserHandle.USER_SYSTEM) { 234 Log.e(TAG, "refreshAgentList(userId=" + userIdOrAll + "): Invalid user handle," 235 + " must be USER_ALL or a specific user.", new Throwable("here")); 236 userIdOrAll = UserHandle.USER_ALL; 237 } 238 PackageManager pm = mContext.getPackageManager(); 239 240 List<UserInfo> userInfos; 241 if (userIdOrAll == UserHandle.USER_ALL) { 242 userInfos = mUserManager.getUsers(true /* excludeDying */); 243 } else { 244 userInfos = new ArrayList<>(); 245 userInfos.add(mUserManager.getUserInfo(userIdOrAll)); 246 } 247 LockPatternUtils lockPatternUtils = mLockPatternUtils; 248 249 ArraySet<AgentInfo> obsoleteAgents = new ArraySet<>(); 250 obsoleteAgents.addAll(mActiveAgents); 251 252 for (UserInfo userInfo : userInfos) { 253 if (userInfo == null || userInfo.partial || !userInfo.isEnabled() 254 || userInfo.guestToRemove) continue; 255 if (!userInfo.supportsSwitchToByUser()) continue; 256 if (!mActivityManager.isUserRunning(userInfo.id)) continue; 257 if (!lockPatternUtils.isSecure(userInfo.id)) continue; 258 if (!mStrongAuthTracker.canAgentsRunForUser(userInfo.id)) continue; 259 DevicePolicyManager dpm = lockPatternUtils.getDevicePolicyManager(); 260 int disabledFeatures = dpm.getKeyguardDisabledFeatures(null, userInfo.id); 261 final boolean disableTrustAgents = 262 (disabledFeatures & DevicePolicyManager.KEYGUARD_DISABLE_TRUST_AGENTS) != 0; 263 264 List<ComponentName> enabledAgents = lockPatternUtils.getEnabledTrustAgents(userInfo.id); 265 if (enabledAgents == null) { 266 continue; 267 } 268 List<ResolveInfo> resolveInfos = resolveAllowedTrustAgents(pm, userInfo.id); 269 for (ResolveInfo resolveInfo : resolveInfos) { 270 ComponentName name = getComponentName(resolveInfo); 271 272 if (!enabledAgents.contains(name)) continue; 273 if (disableTrustAgents) { 274 List<PersistableBundle> config = 275 dpm.getTrustAgentConfiguration(null /* admin */, name, userInfo.id); 276 // Disable agent if no features are enabled. 277 if (config == null || config.isEmpty()) continue; 278 } 279 280 AgentInfo agentInfo = new AgentInfo(); 281 agentInfo.component = name; 282 agentInfo.userId = userInfo.id; 283 if (!mActiveAgents.contains(agentInfo)) { 284 agentInfo.label = resolveInfo.loadLabel(pm); 285 agentInfo.icon = resolveInfo.loadIcon(pm); 286 agentInfo.settings = getSettingsComponentName(pm, resolveInfo); 287 agentInfo.agent = new TrustAgentWrapper(mContext, this, 288 new Intent().setComponent(name), userInfo.getUserHandle()); 289 mActiveAgents.add(agentInfo); 290 } else { 291 obsoleteAgents.remove(agentInfo); 292 } 293 } 294 } 295 296 boolean trustMayHaveChanged = false; 297 for (int i = 0; i < obsoleteAgents.size(); i++) { 298 AgentInfo info = obsoleteAgents.valueAt(i); 299 if (userIdOrAll == UserHandle.USER_ALL || userIdOrAll == info.userId) { 300 if (info.agent.isManagingTrust()) { 301 trustMayHaveChanged = true; 302 } 303 info.agent.destroy(); 304 mActiveAgents.remove(info); 305 } 306 } 307 308 if (trustMayHaveChanged) { 309 if (userIdOrAll == UserHandle.USER_ALL) { 310 updateTrustAll(); 311 } else { 312 updateTrust(userIdOrAll, 0); 313 } 314 } 315 } 316 317 public void setDeviceLockedForUser(int userId, boolean locked) { 318 if (mLockPatternUtils.isSeparateProfileChallengeEnabled(userId)) { 319 synchronized (mDeviceLockedForUser) { 320 mDeviceLockedForUser.put(userId, locked); 321 } 322 if (locked) { 323 try { 324 ActivityManagerNative.getDefault().notifyLockedProfile(userId); 325 } catch (RemoteException e) { 326 } 327 } 328 } 329 } 330 331 boolean isDeviceLockedInner(int userId) { 332 synchronized (mDeviceLockedForUser) { 333 return mDeviceLockedForUser.get(userId, true); 334 } 335 } 336 337 private void refreshDeviceLockedForUser(int userId) { 338 if (userId != UserHandle.USER_ALL && userId < UserHandle.USER_SYSTEM) { 339 Log.e(TAG, "refreshDeviceLockedForUser(userId=" + userId + "): Invalid user handle," 340 + " must be USER_ALL or a specific user.", new Throwable("here")); 341 userId = UserHandle.USER_ALL; 342 } 343 344 List<UserInfo> userInfos; 345 if (userId == UserHandle.USER_ALL) { 346 userInfos = mUserManager.getUsers(true /* excludeDying */); 347 } else { 348 userInfos = new ArrayList<>(); 349 userInfos.add(mUserManager.getUserInfo(userId)); 350 } 351 352 IWindowManager wm = WindowManagerGlobal.getWindowManagerService(); 353 354 for (int i = 0; i < userInfos.size(); i++) { 355 UserInfo info = userInfos.get(i); 356 357 if (info == null || info.partial || !info.isEnabled() || info.guestToRemove 358 || !info.supportsSwitchToByUser()) { 359 continue; 360 } 361 362 int id = info.id; 363 boolean secure = mLockPatternUtils.isSecure(id); 364 boolean trusted = aggregateIsTrusted(id); 365 boolean showingKeyguard = true; 366 if (mCurrentUser == id) { 367 try { 368 showingKeyguard = wm.isKeyguardLocked(); 369 } catch (RemoteException e) { 370 } 371 } 372 boolean deviceLocked = secure && showingKeyguard && !trusted; 373 374 boolean changed; 375 synchronized (mDeviceLockedForUser) { 376 changed = isDeviceLockedInner(id) != deviceLocked; 377 mDeviceLockedForUser.put(id, deviceLocked); 378 } 379 if (changed) { 380 dispatchDeviceLocked(id, deviceLocked); 381 } 382 } 383 } 384 385 private void dispatchDeviceLocked(int userId, boolean isLocked) { 386 for (int i = 0; i < mActiveAgents.size(); i++) { 387 AgentInfo agent = mActiveAgents.valueAt(i); 388 if (agent.userId == userId) { 389 if (isLocked) { 390 agent.agent.onDeviceLocked(); 391 } else{ 392 agent.agent.onDeviceUnlocked(); 393 } 394 } 395 } 396 } 397 398 void updateDevicePolicyFeatures() { 399 for (int i = 0; i < mActiveAgents.size(); i++) { 400 AgentInfo info = mActiveAgents.valueAt(i); 401 if (info.agent.isConnected()) { 402 info.agent.updateDevicePolicyFeatures(); 403 } 404 } 405 } 406 407 private void removeAgentsOfPackage(String packageName) { 408 boolean trustMayHaveChanged = false; 409 for (int i = mActiveAgents.size() - 1; i >= 0; i--) { 410 AgentInfo info = mActiveAgents.valueAt(i); 411 if (packageName.equals(info.component.getPackageName())) { 412 Log.i(TAG, "Resetting agent " + info.component.flattenToShortString()); 413 if (info.agent.isManagingTrust()) { 414 trustMayHaveChanged = true; 415 } 416 info.agent.destroy(); 417 mActiveAgents.removeAt(i); 418 } 419 } 420 if (trustMayHaveChanged) { 421 updateTrustAll(); 422 } 423 } 424 425 public void resetAgent(ComponentName name, int userId) { 426 boolean trustMayHaveChanged = false; 427 for (int i = mActiveAgents.size() - 1; i >= 0; i--) { 428 AgentInfo info = mActiveAgents.valueAt(i); 429 if (name.equals(info.component) && userId == info.userId) { 430 Log.i(TAG, "Resetting agent " + info.component.flattenToShortString()); 431 if (info.agent.isManagingTrust()) { 432 trustMayHaveChanged = true; 433 } 434 info.agent.destroy(); 435 mActiveAgents.removeAt(i); 436 } 437 } 438 if (trustMayHaveChanged) { 439 updateTrust(userId, 0); 440 } 441 refreshAgentList(userId); 442 } 443 444 private ComponentName getSettingsComponentName(PackageManager pm, ResolveInfo resolveInfo) { 445 if (resolveInfo == null || resolveInfo.serviceInfo == null 446 || resolveInfo.serviceInfo.metaData == null) return null; 447 String cn = null; 448 XmlResourceParser parser = null; 449 Exception caughtException = null; 450 try { 451 parser = resolveInfo.serviceInfo.loadXmlMetaData(pm, 452 TrustAgentService.TRUST_AGENT_META_DATA); 453 if (parser == null) { 454 Slog.w(TAG, "Can't find " + TrustAgentService.TRUST_AGENT_META_DATA + " meta-data"); 455 return null; 456 } 457 Resources res = pm.getResourcesForApplication(resolveInfo.serviceInfo.applicationInfo); 458 AttributeSet attrs = Xml.asAttributeSet(parser); 459 int type; 460 while ((type = parser.next()) != XmlPullParser.END_DOCUMENT 461 && type != XmlPullParser.START_TAG) { 462 // Drain preamble. 463 } 464 String nodeName = parser.getName(); 465 if (!"trust-agent".equals(nodeName)) { 466 Slog.w(TAG, "Meta-data does not start with trust-agent tag"); 467 return null; 468 } 469 TypedArray sa = res 470 .obtainAttributes(attrs, com.android.internal.R.styleable.TrustAgent); 471 cn = sa.getString(com.android.internal.R.styleable.TrustAgent_settingsActivity); 472 sa.recycle(); 473 } catch (PackageManager.NameNotFoundException e) { 474 caughtException = e; 475 } catch (IOException e) { 476 caughtException = e; 477 } catch (XmlPullParserException e) { 478 caughtException = e; 479 } finally { 480 if (parser != null) parser.close(); 481 } 482 if (caughtException != null) { 483 Slog.w(TAG, "Error parsing : " + resolveInfo.serviceInfo.packageName, caughtException); 484 return null; 485 } 486 if (cn == null) { 487 return null; 488 } 489 if (cn.indexOf('/') < 0) { 490 cn = resolveInfo.serviceInfo.packageName + "/" + cn; 491 } 492 return ComponentName.unflattenFromString(cn); 493 } 494 495 private ComponentName getComponentName(ResolveInfo resolveInfo) { 496 if (resolveInfo == null || resolveInfo.serviceInfo == null) return null; 497 return new ComponentName(resolveInfo.serviceInfo.packageName, resolveInfo.serviceInfo.name); 498 } 499 500 private void maybeEnableFactoryTrustAgents(LockPatternUtils utils, int userId) { 501 if (0 != Settings.Secure.getIntForUser(mContext.getContentResolver(), 502 Settings.Secure.TRUST_AGENTS_INITIALIZED, 0, userId)) { 503 return; 504 } 505 PackageManager pm = mContext.getPackageManager(); 506 List<ResolveInfo> resolveInfos = resolveAllowedTrustAgents(pm, userId); 507 ArraySet<ComponentName> discoveredAgents = new ArraySet<>(); 508 for (ResolveInfo resolveInfo : resolveInfos) { 509 ComponentName componentName = getComponentName(resolveInfo); 510 int applicationInfoFlags = resolveInfo.serviceInfo.applicationInfo.flags; 511 if ((applicationInfoFlags & ApplicationInfo.FLAG_SYSTEM) == 0) { 512 Log.i(TAG, "Leaving agent " + componentName + " disabled because package " 513 + "is not a system package."); 514 continue; 515 } 516 discoveredAgents.add(componentName); 517 } 518 519 List<ComponentName> previouslyEnabledAgents = utils.getEnabledTrustAgents(userId); 520 if (previouslyEnabledAgents != null) { 521 discoveredAgents.addAll(previouslyEnabledAgents); 522 } 523 utils.setEnabledTrustAgents(discoveredAgents, userId); 524 Settings.Secure.putIntForUser(mContext.getContentResolver(), 525 Settings.Secure.TRUST_AGENTS_INITIALIZED, 1, userId); 526 } 527 528 private List<ResolveInfo> resolveAllowedTrustAgents(PackageManager pm, int userId) { 529 List<ResolveInfo> resolveInfos = pm.queryIntentServicesAsUser(TRUST_AGENT_INTENT, 530 0 /* flags */, userId); 531 ArrayList<ResolveInfo> allowedAgents = new ArrayList<>(resolveInfos.size()); 532 for (ResolveInfo resolveInfo : resolveInfos) { 533 if (resolveInfo.serviceInfo == null) continue; 534 if (resolveInfo.serviceInfo.applicationInfo == null) continue; 535 String packageName = resolveInfo.serviceInfo.packageName; 536 if (pm.checkPermission(PERMISSION_PROVIDE_AGENT, packageName) 537 != PackageManager.PERMISSION_GRANTED) { 538 ComponentName name = getComponentName(resolveInfo); 539 Log.w(TAG, "Skipping agent " + name + " because package does not have" 540 + " permission " + PERMISSION_PROVIDE_AGENT + "."); 541 continue; 542 } 543 allowedAgents.add(resolveInfo); 544 } 545 return allowedAgents; 546 } 547 548 // Agent dispatch and aggregation 549 550 private boolean aggregateIsTrusted(int userId) { 551 if (!mStrongAuthTracker.isTrustAllowedForUser(userId)) { 552 return false; 553 } 554 for (int i = 0; i < mActiveAgents.size(); i++) { 555 AgentInfo info = mActiveAgents.valueAt(i); 556 if (info.userId == userId) { 557 if (info.agent.isTrusted()) { 558 return true; 559 } 560 } 561 } 562 return false; 563 } 564 565 private boolean aggregateIsTrustManaged(int userId) { 566 if (!mStrongAuthTracker.isTrustAllowedForUser(userId)) { 567 return false; 568 } 569 for (int i = 0; i < mActiveAgents.size(); i++) { 570 AgentInfo info = mActiveAgents.valueAt(i); 571 if (info.userId == userId) { 572 if (info.agent.isManagingTrust()) { 573 return true; 574 } 575 } 576 } 577 return false; 578 } 579 580 private void dispatchUnlockAttempt(boolean successful, int userId) { 581 if (successful) { 582 mStrongAuthTracker.allowTrustFromUnlock(userId); 583 } 584 585 for (int i = 0; i < mActiveAgents.size(); i++) { 586 AgentInfo info = mActiveAgents.valueAt(i); 587 if (info.userId == userId) { 588 info.agent.onUnlockAttempt(successful); 589 } 590 } 591 } 592 593 // Listeners 594 595 private void addListener(ITrustListener listener) { 596 for (int i = 0; i < mTrustListeners.size(); i++) { 597 if (mTrustListeners.get(i).asBinder() == listener.asBinder()) { 598 return; 599 } 600 } 601 mTrustListeners.add(listener); 602 updateTrustAll(); 603 } 604 605 private void removeListener(ITrustListener listener) { 606 for (int i = 0; i < mTrustListeners.size(); i++) { 607 if (mTrustListeners.get(i).asBinder() == listener.asBinder()) { 608 mTrustListeners.remove(i); 609 return; 610 } 611 } 612 } 613 614 private void dispatchOnTrustChanged(boolean enabled, int userId, int flags) { 615 if (DEBUG) { 616 Log.i(TAG, "onTrustChanged(" + enabled + ", " + userId + ", 0x" 617 + Integer.toHexString(flags) + ")"); 618 } 619 if (!enabled) flags = 0; 620 for (int i = 0; i < mTrustListeners.size(); i++) { 621 try { 622 mTrustListeners.get(i).onTrustChanged(enabled, userId, flags); 623 } catch (DeadObjectException e) { 624 Slog.d(TAG, "Removing dead TrustListener."); 625 mTrustListeners.remove(i); 626 i--; 627 } catch (RemoteException e) { 628 Slog.e(TAG, "Exception while notifying TrustListener.", e); 629 } 630 } 631 } 632 633 private void dispatchOnTrustManagedChanged(boolean managed, int userId) { 634 if (DEBUG) { 635 Log.i(TAG, "onTrustManagedChanged(" + managed + ", " + userId + ")"); 636 } 637 for (int i = 0; i < mTrustListeners.size(); i++) { 638 try { 639 mTrustListeners.get(i).onTrustManagedChanged(managed, userId); 640 } catch (DeadObjectException e) { 641 Slog.d(TAG, "Removing dead TrustListener."); 642 mTrustListeners.remove(i); 643 i--; 644 } catch (RemoteException e) { 645 Slog.e(TAG, "Exception while notifying TrustListener.", e); 646 } 647 } 648 } 649 650 // User lifecycle 651 652 @Override 653 public void onStartUser(int userId) { 654 mHandler.obtainMessage(MSG_START_USER, userId, 0, null).sendToTarget(); 655 } 656 657 @Override 658 public void onCleanupUser(int userId) { 659 mHandler.obtainMessage(MSG_CLEANUP_USER, userId, 0, null).sendToTarget(); 660 } 661 662 @Override 663 public void onSwitchUser(int userId) { 664 mHandler.obtainMessage(MSG_SWITCH_USER, userId, 0, null).sendToTarget(); 665 } 666 667 // Plumbing 668 669 private final IBinder mService = new ITrustManager.Stub() { 670 @Override 671 public void reportUnlockAttempt(boolean authenticated, int userId) throws RemoteException { 672 enforceReportPermission(); 673 mHandler.obtainMessage(MSG_DISPATCH_UNLOCK_ATTEMPT, authenticated ? 1 : 0, userId) 674 .sendToTarget(); 675 } 676 677 @Override 678 public void reportEnabledTrustAgentsChanged(int userId) throws RemoteException { 679 enforceReportPermission(); 680 // coalesce refresh messages. 681 mHandler.removeMessages(MSG_ENABLED_AGENTS_CHANGED); 682 mHandler.sendEmptyMessage(MSG_ENABLED_AGENTS_CHANGED); 683 } 684 685 @Override 686 public void reportKeyguardShowingChanged() throws RemoteException { 687 enforceReportPermission(); 688 // coalesce refresh messages. 689 mHandler.removeMessages(MSG_KEYGUARD_SHOWING_CHANGED); 690 mHandler.sendEmptyMessage(MSG_KEYGUARD_SHOWING_CHANGED); 691 } 692 693 @Override 694 public void registerTrustListener(ITrustListener trustListener) throws RemoteException { 695 enforceListenerPermission(); 696 mHandler.obtainMessage(MSG_REGISTER_LISTENER, trustListener).sendToTarget(); 697 } 698 699 @Override 700 public void unregisterTrustListener(ITrustListener trustListener) throws RemoteException { 701 enforceListenerPermission(); 702 mHandler.obtainMessage(MSG_UNREGISTER_LISTENER, trustListener).sendToTarget(); 703 } 704 705 @Override 706 public boolean isDeviceLocked(int userId) throws RemoteException { 707 userId = ActivityManager.handleIncomingUser(getCallingPid(), getCallingUid(), userId, 708 false /* allowAll */, true /* requireFull */, "isDeviceLocked", null); 709 710 long token = Binder.clearCallingIdentity(); 711 try { 712 if (!mLockPatternUtils.isSeparateProfileChallengeEnabled(userId)) { 713 userId = resolveProfileParent(userId); 714 } 715 return isDeviceLockedInner(userId); 716 } finally { 717 Binder.restoreCallingIdentity(token); 718 } 719 } 720 721 @Override 722 public boolean isDeviceSecure(int userId) throws RemoteException { 723 userId = ActivityManager.handleIncomingUser(getCallingPid(), getCallingUid(), userId, 724 false /* allowAll */, true /* requireFull */, "isDeviceSecure", null); 725 726 long token = Binder.clearCallingIdentity(); 727 try { 728 if (!mLockPatternUtils.isSeparateProfileChallengeEnabled(userId)) { 729 userId = resolveProfileParent(userId); 730 } 731 return mLockPatternUtils.isSecure(userId); 732 } finally { 733 Binder.restoreCallingIdentity(token); 734 } 735 } 736 737 private void enforceReportPermission() { 738 mContext.enforceCallingOrSelfPermission( 739 Manifest.permission.ACCESS_KEYGUARD_SECURE_STORAGE, "reporting trust events"); 740 } 741 742 private void enforceListenerPermission() { 743 mContext.enforceCallingPermission(Manifest.permission.TRUST_LISTENER, 744 "register trust listener"); 745 } 746 747 @Override 748 protected void dump(FileDescriptor fd, final PrintWriter fout, String[] args) { 749 mContext.enforceCallingPermission(Manifest.permission.DUMP, 750 "dumping TrustManagerService"); 751 if (isSafeMode()) { 752 fout.println("disabled because the system is in safe mode."); 753 return; 754 } 755 if (!mTrustAgentsCanRun) { 756 fout.println("disabled because the third-party apps can't run yet."); 757 return; 758 } 759 final List<UserInfo> userInfos = mUserManager.getUsers(true /* excludeDying */); 760 mHandler.runWithScissors(new Runnable() { 761 @Override 762 public void run() { 763 fout.println("Trust manager state:"); 764 for (UserInfo user : userInfos) { 765 dumpUser(fout, user, user.id == mCurrentUser); 766 } 767 } 768 }, 1500); 769 } 770 771 private void dumpUser(PrintWriter fout, UserInfo user, boolean isCurrent) { 772 fout.printf(" User \"%s\" (id=%d, flags=%#x)", 773 user.name, user.id, user.flags); 774 if (!user.supportsSwitchToByUser()) { 775 fout.println("(managed profile)"); 776 fout.println(" disabled because switching to this user is not possible."); 777 return; 778 } 779 if (isCurrent) { 780 fout.print(" (current)"); 781 } 782 fout.print(": trusted=" + dumpBool(aggregateIsTrusted(user.id))); 783 fout.print(", trustManaged=" + dumpBool(aggregateIsTrustManaged(user.id))); 784 fout.print(", deviceLocked=" + dumpBool(isDeviceLockedInner(user.id))); 785 fout.print(", strongAuthRequired=" + dumpHex( 786 mStrongAuthTracker.getStrongAuthForUser(user.id))); 787 fout.println(); 788 fout.println(" Enabled agents:"); 789 boolean duplicateSimpleNames = false; 790 ArraySet<String> simpleNames = new ArraySet<String>(); 791 for (AgentInfo info : mActiveAgents) { 792 if (info.userId != user.id) { continue; } 793 boolean trusted = info.agent.isTrusted(); 794 fout.print(" "); fout.println(info.component.flattenToShortString()); 795 fout.print(" bound=" + dumpBool(info.agent.isBound())); 796 fout.print(", connected=" + dumpBool(info.agent.isConnected())); 797 fout.print(", managingTrust=" + dumpBool(info.agent.isManagingTrust())); 798 fout.print(", trusted=" + dumpBool(trusted)); 799 fout.println(); 800 if (trusted) { 801 fout.println(" message=\"" + info.agent.getMessage() + "\""); 802 } 803 if (!info.agent.isConnected()) { 804 String restartTime = TrustArchive.formatDuration( 805 info.agent.getScheduledRestartUptimeMillis() 806 - SystemClock.uptimeMillis()); 807 fout.println(" restartScheduledAt=" + restartTime); 808 } 809 if (!simpleNames.add(TrustArchive.getSimpleName(info.component))) { 810 duplicateSimpleNames = true; 811 } 812 } 813 fout.println(" Events:"); 814 mArchive.dump(fout, 50, user.id, " " /* linePrefix */, duplicateSimpleNames); 815 fout.println(); 816 } 817 818 private String dumpBool(boolean b) { 819 return b ? "1" : "0"; 820 } 821 822 private String dumpHex(int i) { 823 return "0x" + Integer.toHexString(i); 824 } 825 826 @Override 827 public void setDeviceLockedForUser(int userId, boolean value) { 828 enforceReportPermission(); 829 mHandler.obtainMessage(MSG_SET_DEVICE_LOCKED, value ? 1 : 0, userId) 830 .sendToTarget(); 831 } 832 833 @Override 834 public boolean isTrustUsuallyManaged(int userId) { 835 mContext.enforceCallingPermission(Manifest.permission.TRUST_LISTENER, 836 "query trust state"); 837 return isTrustUsuallyManagedInternal(userId); 838 } 839 }; 840 841 private boolean isTrustUsuallyManagedInternal(int userId) { 842 synchronized (mTrustUsuallyManagedForUser) { 843 int i = mTrustUsuallyManagedForUser.indexOfKey(userId); 844 if (i >= 0) { 845 return mTrustUsuallyManagedForUser.valueAt(i); 846 } 847 } 848 // It's not in memory yet, get the value from persisted storage instead 849 boolean persistedValue = mLockPatternUtils.isTrustUsuallyManaged(userId); 850 synchronized (mTrustUsuallyManagedForUser) { 851 int i = mTrustUsuallyManagedForUser.indexOfKey(userId); 852 if (i >= 0) { 853 // Someone set the trust usually managed in the mean time. Better use that. 854 return mTrustUsuallyManagedForUser.valueAt(i); 855 } else { 856 // .. otherwise it's safe to cache the fetched value now. 857 mTrustUsuallyManagedForUser.put(userId, persistedValue); 858 return persistedValue; 859 } 860 } 861 } 862 863 private int resolveProfileParent(int userId) { 864 long identity = Binder.clearCallingIdentity(); 865 try { 866 UserInfo parent = mUserManager.getProfileParent(userId); 867 if (parent != null) { 868 return parent.getUserHandle().getIdentifier(); 869 } 870 return userId; 871 } finally { 872 Binder.restoreCallingIdentity(identity); 873 } 874 } 875 876 private final Handler mHandler = new Handler() { 877 @Override 878 public void handleMessage(Message msg) { 879 switch (msg.what) { 880 case MSG_REGISTER_LISTENER: 881 addListener((ITrustListener) msg.obj); 882 break; 883 case MSG_UNREGISTER_LISTENER: 884 removeListener((ITrustListener) msg.obj); 885 break; 886 case MSG_DISPATCH_UNLOCK_ATTEMPT: 887 dispatchUnlockAttempt(msg.arg1 != 0, msg.arg2); 888 break; 889 case MSG_ENABLED_AGENTS_CHANGED: 890 refreshAgentList(UserHandle.USER_ALL); 891 // This is also called when the security mode of a user changes. 892 refreshDeviceLockedForUser(UserHandle.USER_ALL); 893 break; 894 case MSG_KEYGUARD_SHOWING_CHANGED: 895 refreshDeviceLockedForUser(mCurrentUser); 896 break; 897 case MSG_START_USER: 898 case MSG_CLEANUP_USER: 899 refreshAgentList(msg.arg1); 900 break; 901 case MSG_SWITCH_USER: 902 mCurrentUser = msg.arg1; 903 refreshDeviceLockedForUser(UserHandle.USER_ALL); 904 break; 905 case MSG_SET_DEVICE_LOCKED: 906 setDeviceLockedForUser(msg.arg2, msg.arg1 != 0); 907 break; 908 case MSG_FLUSH_TRUST_USUALLY_MANAGED: 909 SparseBooleanArray usuallyManaged; 910 synchronized (mTrustUsuallyManagedForUser) { 911 usuallyManaged = mTrustUsuallyManagedForUser.clone(); 912 } 913 914 for (int i = 0; i < usuallyManaged.size(); i++) { 915 int userId = usuallyManaged.keyAt(i); 916 boolean value = usuallyManaged.valueAt(i); 917 if (value != mLockPatternUtils.isTrustUsuallyManaged(userId)) { 918 mLockPatternUtils.setTrustUsuallyManaged(value, userId); 919 } 920 } 921 } 922 } 923 }; 924 925 private final PackageMonitor mPackageMonitor = new PackageMonitor() { 926 @Override 927 public void onSomePackagesChanged() { 928 refreshAgentList(UserHandle.USER_ALL); 929 } 930 931 @Override 932 public boolean onPackageChanged(String packageName, int uid, String[] components) { 933 // We're interested in all changes, even if just some components get enabled / disabled. 934 return true; 935 } 936 937 @Override 938 public void onPackageDisappeared(String packageName, int reason) { 939 removeAgentsOfPackage(packageName); 940 } 941 }; 942 943 private class Receiver extends BroadcastReceiver { 944 945 @Override 946 public void onReceive(Context context, Intent intent) { 947 String action = intent.getAction(); 948 if (DevicePolicyManager.ACTION_DEVICE_POLICY_MANAGER_STATE_CHANGED.equals(action)) { 949 refreshAgentList(getSendingUserId()); 950 updateDevicePolicyFeatures(); 951 } else if (Intent.ACTION_USER_ADDED.equals(action)) { 952 int userId = getUserId(intent); 953 if (userId > 0) { 954 maybeEnableFactoryTrustAgents(mLockPatternUtils, userId); 955 } 956 } else if (Intent.ACTION_USER_REMOVED.equals(action)) { 957 int userId = getUserId(intent); 958 if (userId > 0) { 959 synchronized (mUserIsTrusted) { 960 mUserIsTrusted.delete(userId); 961 } 962 synchronized (mDeviceLockedForUser) { 963 mDeviceLockedForUser.delete(userId); 964 } 965 refreshAgentList(userId); 966 refreshDeviceLockedForUser(userId); 967 } 968 } 969 } 970 971 private int getUserId(Intent intent) { 972 int userId = intent.getIntExtra(Intent.EXTRA_USER_HANDLE, -100); 973 if (userId > 0) { 974 return userId; 975 } else { 976 Slog.wtf(TAG, "EXTRA_USER_HANDLE missing or invalid, value=" + userId); 977 return -100; 978 } 979 } 980 981 public void register(Context context) { 982 IntentFilter filter = new IntentFilter(); 983 filter.addAction(DevicePolicyManager.ACTION_DEVICE_POLICY_MANAGER_STATE_CHANGED); 984 filter.addAction(Intent.ACTION_USER_PRESENT); 985 filter.addAction(Intent.ACTION_USER_ADDED); 986 filter.addAction(Intent.ACTION_USER_REMOVED); 987 context.registerReceiverAsUser(this, 988 UserHandle.ALL, 989 filter, 990 null /* permission */, 991 null /* scheduler */); 992 } 993 } 994 995 private class StrongAuthTracker extends LockPatternUtils.StrongAuthTracker { 996 997 SparseBooleanArray mStartFromSuccessfulUnlock = new SparseBooleanArray(); 998 999 public StrongAuthTracker(Context context) { 1000 super(context); 1001 } 1002 1003 @Override 1004 public void onStrongAuthRequiredChanged(int userId) { 1005 mStartFromSuccessfulUnlock.delete(userId); 1006 1007 if (DEBUG) { 1008 Log.i(TAG, "onStrongAuthRequiredChanged(" + userId + ") ->" 1009 + " trustAllowed=" + isTrustAllowedForUser(userId) 1010 + " agentsCanRun=" + canAgentsRunForUser(userId)); 1011 } 1012 1013 refreshAgentList(userId); 1014 1015 // The list of active trust agents may not have changed, if there was a previous call 1016 // to allowTrustFromUnlock, so we update the trust here too. 1017 updateTrust(userId, 0 /* flags */); 1018 } 1019 1020 boolean canAgentsRunForUser(int userId) { 1021 return mStartFromSuccessfulUnlock.get(userId) 1022 || super.isTrustAllowedForUser(userId); 1023 } 1024 1025 /** 1026 * Temporarily suppress strong auth requirements for {@param userId} until strong auth 1027 * changes again. Must only be called when we know about a successful unlock already 1028 * before the underlying StrongAuthTracker. 1029 * 1030 * Note that this only changes whether trust agents can be started, not the actual trusted 1031 * value. 1032 */ 1033 void allowTrustFromUnlock(int userId) { 1034 if (userId < UserHandle.USER_SYSTEM) { 1035 throw new IllegalArgumentException("userId must be a valid user: " + userId); 1036 } 1037 boolean previous = canAgentsRunForUser(userId); 1038 mStartFromSuccessfulUnlock.put(userId, true); 1039 1040 if (DEBUG) { 1041 Log.i(TAG, "allowTrustFromUnlock(" + userId + ") ->" 1042 + " trustAllowed=" + isTrustAllowedForUser(userId) 1043 + " agentsCanRun=" + canAgentsRunForUser(userId)); 1044 } 1045 1046 if (canAgentsRunForUser(userId) != previous) { 1047 refreshAgentList(userId); 1048 } 1049 } 1050 } 1051} 1052