ActivityManagerService.java revision 9c76a7b3e85ce7056071ac8627c8d675cc5c1599
1/* 2 * Copyright (C) 2006-2008 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.am; 18 19import static android.Manifest.permission.INTERACT_ACROSS_USERS; 20import static android.Manifest.permission.INTERACT_ACROSS_USERS_FULL; 21import static android.Manifest.permission.START_TASKS_FROM_RECENTS; 22import static android.content.pm.PackageManager.PERMISSION_GRANTED; 23import static com.android.internal.util.XmlUtils.readBooleanAttribute; 24import static com.android.internal.util.XmlUtils.readIntAttribute; 25import static com.android.internal.util.XmlUtils.readLongAttribute; 26import static com.android.internal.util.XmlUtils.writeBooleanAttribute; 27import static com.android.internal.util.XmlUtils.writeIntAttribute; 28import static com.android.internal.util.XmlUtils.writeLongAttribute; 29import static com.android.server.Watchdog.NATIVE_STACKS_OF_INTEREST; 30import static org.xmlpull.v1.XmlPullParser.END_DOCUMENT; 31import static org.xmlpull.v1.XmlPullParser.START_TAG; 32import static com.android.server.am.ActivityStackSupervisor.HOME_STACK_ID; 33 34import android.Manifest; 35import android.app.AppOpsManager; 36import android.app.ApplicationThreadNative; 37import android.app.IActivityContainer; 38import android.app.IActivityContainerCallback; 39import android.app.IAppTask; 40import android.app.ProfilerInfo; 41import android.app.admin.DevicePolicyManager; 42import android.app.usage.UsageEvents; 43import android.app.usage.UsageStatsManagerInternal; 44import android.appwidget.AppWidgetManager; 45import android.content.res.Resources; 46import android.graphics.Bitmap; 47import android.graphics.Point; 48import android.graphics.Rect; 49import android.os.BatteryStats; 50import android.os.PersistableBundle; 51import android.os.storage.IMountService; 52import android.os.storage.StorageManager; 53import android.service.voice.IVoiceInteractionSession; 54import android.util.ArrayMap; 55import android.util.ArraySet; 56import android.util.SparseIntArray; 57 58import com.android.internal.R; 59import com.android.internal.annotations.GuardedBy; 60import com.android.internal.app.IAppOpsService; 61import com.android.internal.app.IVoiceInteractor; 62import com.android.internal.app.ProcessMap; 63import com.android.internal.app.ProcessStats; 64import com.android.internal.content.PackageMonitor; 65import com.android.internal.os.BackgroundThread; 66import com.android.internal.os.BatteryStatsImpl; 67import com.android.internal.os.ProcessCpuTracker; 68import com.android.internal.os.TransferPipe; 69import com.android.internal.os.Zygote; 70import com.android.internal.util.FastPrintWriter; 71import com.android.internal.util.FastXmlSerializer; 72import com.android.internal.util.MemInfoReader; 73import com.android.internal.util.Preconditions; 74import com.android.server.AppOpsService; 75import com.android.server.AttributeCache; 76import com.android.server.IntentResolver; 77import com.android.server.LocalServices; 78import com.android.server.ServiceThread; 79import com.android.server.SystemService; 80import com.android.server.SystemServiceManager; 81import com.android.server.Watchdog; 82import com.android.server.am.ActivityStack.ActivityState; 83import com.android.server.firewall.IntentFirewall; 84import com.android.server.pm.Installer; 85import com.android.server.pm.UserManagerService; 86import com.android.server.statusbar.StatusBarManagerInternal; 87import com.android.server.wm.AppTransition; 88import com.android.server.wm.WindowManagerService; 89import com.google.android.collect.Lists; 90import com.google.android.collect.Maps; 91 92import libcore.io.IoUtils; 93 94import org.xmlpull.v1.XmlPullParser; 95import org.xmlpull.v1.XmlPullParserException; 96import org.xmlpull.v1.XmlSerializer; 97 98import android.app.Activity; 99import android.app.ActivityManager; 100import android.app.ActivityManager.RunningTaskInfo; 101import android.app.ActivityManager.StackInfo; 102import android.app.ActivityManagerInternal; 103import android.app.ActivityManagerNative; 104import android.app.ActivityOptions; 105import android.app.ActivityThread; 106import android.app.AlertDialog; 107import android.app.AppGlobals; 108import android.app.ApplicationErrorReport; 109import android.app.Dialog; 110import android.app.IActivityController; 111import android.app.IApplicationThread; 112import android.app.IInstrumentationWatcher; 113import android.app.INotificationManager; 114import android.app.IProcessObserver; 115import android.app.IServiceConnection; 116import android.app.IStopUserCallback; 117import android.app.IUiAutomationConnection; 118import android.app.IUserSwitchObserver; 119import android.app.Instrumentation; 120import android.app.Notification; 121import android.app.NotificationManager; 122import android.app.PendingIntent; 123import android.app.backup.IBackupManager; 124import android.content.ActivityNotFoundException; 125import android.content.BroadcastReceiver; 126import android.content.ClipData; 127import android.content.ComponentCallbacks2; 128import android.content.ComponentName; 129import android.content.ContentProvider; 130import android.content.ContentResolver; 131import android.content.Context; 132import android.content.DialogInterface; 133import android.content.IContentProvider; 134import android.content.IIntentReceiver; 135import android.content.IIntentSender; 136import android.content.Intent; 137import android.content.IntentFilter; 138import android.content.IntentSender; 139import android.content.pm.ActivityInfo; 140import android.content.pm.ApplicationInfo; 141import android.content.pm.ConfigurationInfo; 142import android.content.pm.IPackageDataObserver; 143import android.content.pm.IPackageManager; 144import android.content.pm.InstrumentationInfo; 145import android.content.pm.PackageInfo; 146import android.content.pm.PackageManager; 147import android.content.pm.ParceledListSlice; 148import android.content.pm.UserInfo; 149import android.content.pm.PackageManager.NameNotFoundException; 150import android.content.pm.PathPermission; 151import android.content.pm.ProviderInfo; 152import android.content.pm.ResolveInfo; 153import android.content.pm.ServiceInfo; 154import android.content.res.CompatibilityInfo; 155import android.content.res.Configuration; 156import android.net.Proxy; 157import android.net.ProxyInfo; 158import android.net.Uri; 159import android.os.Binder; 160import android.os.Build; 161import android.os.Bundle; 162import android.os.Debug; 163import android.os.DropBoxManager; 164import android.os.Environment; 165import android.os.FactoryTest; 166import android.os.FileObserver; 167import android.os.FileUtils; 168import android.os.Handler; 169import android.os.IBinder; 170import android.os.IPermissionController; 171import android.os.IRemoteCallback; 172import android.os.IUserManager; 173import android.os.Looper; 174import android.os.Message; 175import android.os.Parcel; 176import android.os.ParcelFileDescriptor; 177import android.os.Process; 178import android.os.RemoteCallbackList; 179import android.os.RemoteException; 180import android.os.SELinux; 181import android.os.ServiceManager; 182import android.os.StrictMode; 183import android.os.SystemClock; 184import android.os.SystemProperties; 185import android.os.UpdateLock; 186import android.os.UserHandle; 187import android.os.UserManager; 188import android.provider.Settings; 189import android.text.format.DateUtils; 190import android.text.format.Time; 191import android.util.AtomicFile; 192import android.util.EventLog; 193import android.util.Log; 194import android.util.Pair; 195import android.util.PrintWriterPrinter; 196import android.util.Slog; 197import android.util.SparseArray; 198import android.util.TimeUtils; 199import android.util.Xml; 200import android.view.Gravity; 201import android.view.LayoutInflater; 202import android.view.View; 203import android.view.WindowManager; 204 205import dalvik.system.VMRuntime; 206 207import java.io.BufferedInputStream; 208import java.io.BufferedOutputStream; 209import java.io.DataInputStream; 210import java.io.DataOutputStream; 211import java.io.File; 212import java.io.FileDescriptor; 213import java.io.FileInputStream; 214import java.io.FileNotFoundException; 215import java.io.FileOutputStream; 216import java.io.IOException; 217import java.io.InputStreamReader; 218import java.io.PrintWriter; 219import java.io.StringWriter; 220import java.lang.ref.WeakReference; 221import java.util.ArrayList; 222import java.util.Arrays; 223import java.util.Collections; 224import java.util.Comparator; 225import java.util.HashMap; 226import java.util.HashSet; 227import java.util.Iterator; 228import java.util.List; 229import java.util.Locale; 230import java.util.Map; 231import java.util.Set; 232import java.util.concurrent.atomic.AtomicBoolean; 233import java.util.concurrent.atomic.AtomicLong; 234 235public final class ActivityManagerService extends ActivityManagerNative 236 implements Watchdog.Monitor, BatteryStatsImpl.BatteryCallback { 237 238 private static final String USER_DATA_DIR = "/data/user/"; 239 // File that stores last updated system version and called preboot receivers 240 static final String CALLED_PRE_BOOTS_FILENAME = "called_pre_boots.dat"; 241 242 static final String TAG = "ActivityManager"; 243 static final String TAG_MU = "ActivityManagerServiceMU"; 244 static final boolean DEBUG = false; 245 static final boolean localLOGV = DEBUG; 246 static final boolean DEBUG_BACKUP = localLOGV || false; 247 static final boolean DEBUG_BROADCAST = localLOGV || false; 248 static final boolean DEBUG_BROADCAST_LIGHT = DEBUG_BROADCAST || false; 249 static final boolean DEBUG_BACKGROUND_BROADCAST = DEBUG_BROADCAST || false; 250 static final boolean DEBUG_CLEANUP = localLOGV || false; 251 static final boolean DEBUG_CONFIGURATION = localLOGV || false; 252 static final boolean DEBUG_FOCUS = false; 253 static final boolean DEBUG_IMMERSIVE = localLOGV || false; 254 static final boolean DEBUG_MU = localLOGV || false; 255 static final boolean DEBUG_OOM_ADJ = localLOGV || false; 256 static final boolean DEBUG_LRU = localLOGV || false; 257 static final boolean DEBUG_PAUSE = localLOGV || false; 258 static final boolean DEBUG_POWER = localLOGV || false; 259 static final boolean DEBUG_POWER_QUICK = DEBUG_POWER || false; 260 static final boolean DEBUG_PROCESS_OBSERVERS = localLOGV || false; 261 static final boolean DEBUG_PROCESSES = localLOGV || false; 262 static final boolean DEBUG_PROVIDER = localLOGV || false; 263 static final boolean DEBUG_RESULTS = localLOGV || false; 264 static final boolean DEBUG_SERVICE = localLOGV || false; 265 static final boolean DEBUG_SERVICE_EXECUTING = localLOGV || false; 266 static final boolean DEBUG_STACK = localLOGV || false; 267 static final boolean DEBUG_SWITCH = localLOGV || false; 268 static final boolean DEBUG_TASKS = localLOGV || false; 269 static final boolean DEBUG_THUMBNAILS = localLOGV || false; 270 static final boolean DEBUG_TRANSITION = localLOGV || false; 271 static final boolean DEBUG_URI_PERMISSION = localLOGV || false; 272 static final boolean DEBUG_USER_LEAVING = localLOGV || false; 273 static final boolean DEBUG_VISBILITY = localLOGV || false; 274 static final boolean DEBUG_PSS = localLOGV || false; 275 static final boolean DEBUG_LOCKSCREEN = localLOGV || false; 276 static final boolean DEBUG_RECENTS = localLOGV || false; 277 static final boolean VALIDATE_TOKENS = false; 278 static final boolean SHOW_ACTIVITY_START_TIME = true; 279 280 // Control over CPU and battery monitoring. 281 static final long BATTERY_STATS_TIME = 30*60*1000; // write battery stats every 30 minutes. 282 static final boolean MONITOR_CPU_USAGE = true; 283 static final long MONITOR_CPU_MIN_TIME = 5*1000; // don't sample cpu less than every 5 seconds. 284 static final long MONITOR_CPU_MAX_TIME = 0x0fffffff; // wait possibly forever for next cpu sample. 285 static final boolean MONITOR_THREAD_CPU_USAGE = false; 286 287 // The flags that are set for all calls we make to the package manager. 288 static final int STOCK_PM_FLAGS = PackageManager.GET_SHARED_LIBRARY_FILES; 289 290 private static final String SYSTEM_DEBUGGABLE = "ro.debuggable"; 291 292 static final boolean IS_USER_BUILD = "user".equals(Build.TYPE); 293 294 // Maximum number recent bitmaps to keep in memory. 295 static final int MAX_RECENT_BITMAPS = 5; 296 297 // Amount of time after a call to stopAppSwitches() during which we will 298 // prevent further untrusted switches from happening. 299 static final long APP_SWITCH_DELAY_TIME = 5*1000; 300 301 // How long we wait for a launched process to attach to the activity manager 302 // before we decide it's never going to come up for real. 303 static final int PROC_START_TIMEOUT = 10*1000; 304 305 // How long we wait for a launched process to attach to the activity manager 306 // before we decide it's never going to come up for real, when the process was 307 // started with a wrapper for instrumentation (such as Valgrind) because it 308 // could take much longer than usual. 309 static final int PROC_START_TIMEOUT_WITH_WRAPPER = 1200*1000; 310 311 // How long to wait after going idle before forcing apps to GC. 312 static final int GC_TIMEOUT = 5*1000; 313 314 // The minimum amount of time between successive GC requests for a process. 315 static final int GC_MIN_INTERVAL = 60*1000; 316 317 // The minimum amount of time between successive PSS requests for a process. 318 static final int FULL_PSS_MIN_INTERVAL = 10*60*1000; 319 320 // The minimum amount of time between successive PSS requests for a process 321 // when the request is due to the memory state being lowered. 322 static final int FULL_PSS_LOWERED_INTERVAL = 2*60*1000; 323 324 // The rate at which we check for apps using excessive power -- 15 mins. 325 static final int POWER_CHECK_DELAY = (DEBUG_POWER_QUICK ? 2 : 15) * 60*1000; 326 327 // The minimum sample duration we will allow before deciding we have 328 // enough data on wake locks to start killing things. 329 static final int WAKE_LOCK_MIN_CHECK_DURATION = (DEBUG_POWER_QUICK ? 1 : 5) * 60*1000; 330 331 // The minimum sample duration we will allow before deciding we have 332 // enough data on CPU usage to start killing things. 333 static final int CPU_MIN_CHECK_DURATION = (DEBUG_POWER_QUICK ? 1 : 5) * 60*1000; 334 335 // How long we allow a receiver to run before giving up on it. 336 static final int BROADCAST_FG_TIMEOUT = 10*1000; 337 static final int BROADCAST_BG_TIMEOUT = 60*1000; 338 339 // How long we wait until we timeout on key dispatching. 340 static final int KEY_DISPATCHING_TIMEOUT = 5*1000; 341 342 // How long we wait until we timeout on key dispatching during instrumentation. 343 static final int INSTRUMENTATION_KEY_DISPATCHING_TIMEOUT = 60*1000; 344 345 // Amount of time we wait for observers to handle a user switch before 346 // giving up on them and unfreezing the screen. 347 static final int USER_SWITCH_TIMEOUT = 2*1000; 348 349 // Maximum number of users we allow to be running at a time. 350 static final int MAX_RUNNING_USERS = 3; 351 352 // How long to wait in getAssistContextExtras for the activity and foreground services 353 // to respond with the result. 354 static final int PENDING_ASSIST_EXTRAS_TIMEOUT = 500; 355 356 // Maximum number of persisted Uri grants a package is allowed 357 static final int MAX_PERSISTED_URI_GRANTS = 128; 358 359 static final int MY_PID = Process.myPid(); 360 361 static final String[] EMPTY_STRING_ARRAY = new String[0]; 362 363 // How many bytes to write into the dropbox log before truncating 364 static final int DROPBOX_MAX_SIZE = 256 * 1024; 365 366 // Access modes for handleIncomingUser. 367 static final int ALLOW_NON_FULL = 0; 368 static final int ALLOW_NON_FULL_IN_PROFILE = 1; 369 static final int ALLOW_FULL_ONLY = 2; 370 371 static final int LAST_PREBOOT_DELIVERED_FILE_VERSION = 10000; 372 373 /** All system services */ 374 SystemServiceManager mSystemServiceManager; 375 376 private Installer mInstaller; 377 378 /** Run all ActivityStacks through this */ 379 ActivityStackSupervisor mStackSupervisor; 380 381 public IntentFirewall mIntentFirewall; 382 383 // Whether we should show our dialogs (ANR, crash, etc) or just perform their 384 // default actuion automatically. Important for devices without direct input 385 // devices. 386 private boolean mShowDialogs = true; 387 388 BroadcastQueue mFgBroadcastQueue; 389 BroadcastQueue mBgBroadcastQueue; 390 // Convenient for easy iteration over the queues. Foreground is first 391 // so that dispatch of foreground broadcasts gets precedence. 392 final BroadcastQueue[] mBroadcastQueues = new BroadcastQueue[2]; 393 394 BroadcastQueue broadcastQueueForIntent(Intent intent) { 395 final boolean isFg = (intent.getFlags() & Intent.FLAG_RECEIVER_FOREGROUND) != 0; 396 if (DEBUG_BACKGROUND_BROADCAST) { 397 Slog.i(TAG, "Broadcast intent " + intent + " on " 398 + (isFg ? "foreground" : "background") 399 + " queue"); 400 } 401 return (isFg) ? mFgBroadcastQueue : mBgBroadcastQueue; 402 } 403 404 BroadcastRecord broadcastRecordForReceiverLocked(IBinder receiver) { 405 for (BroadcastQueue queue : mBroadcastQueues) { 406 BroadcastRecord r = queue.getMatchingOrderedReceiver(receiver); 407 if (r != null) { 408 return r; 409 } 410 } 411 return null; 412 } 413 414 /** 415 * Activity we have told the window manager to have key focus. 416 */ 417 ActivityRecord mFocusedActivity = null; 418 419 /** 420 * List of intents that were used to start the most recent tasks. 421 */ 422 ArrayList<TaskRecord> mRecentTasks; 423 ArrayList<TaskRecord> mTmpRecents = new ArrayList<TaskRecord>(); 424 425 /** 426 * For addAppTask: cached of the last activity component that was added. 427 */ 428 ComponentName mLastAddedTaskComponent; 429 430 /** 431 * For addAppTask: cached of the last activity uid that was added. 432 */ 433 int mLastAddedTaskUid; 434 435 /** 436 * For addAppTask: cached of the last ActivityInfo that was added. 437 */ 438 ActivityInfo mLastAddedTaskActivity; 439 440 public class PendingAssistExtras extends Binder implements Runnable { 441 public final ActivityRecord activity; 442 public final Bundle extras; 443 public final Intent intent; 444 public final String hint; 445 public final int userHandle; 446 public boolean haveResult = false; 447 public Bundle result = null; 448 public PendingAssistExtras(ActivityRecord _activity, Bundle _extras, Intent _intent, 449 String _hint, int _userHandle) { 450 activity = _activity; 451 extras = _extras; 452 intent = _intent; 453 hint = _hint; 454 userHandle = _userHandle; 455 } 456 @Override 457 public void run() { 458 Slog.w(TAG, "getAssistContextExtras failed: timeout retrieving from " + activity); 459 synchronized (this) { 460 haveResult = true; 461 notifyAll(); 462 } 463 } 464 } 465 466 final ArrayList<PendingAssistExtras> mPendingAssistExtras 467 = new ArrayList<PendingAssistExtras>(); 468 469 /** 470 * Process management. 471 */ 472 final ProcessList mProcessList = new ProcessList(); 473 474 /** 475 * All of the applications we currently have running organized by name. 476 * The keys are strings of the application package name (as 477 * returned by the package manager), and the keys are ApplicationRecord 478 * objects. 479 */ 480 final ProcessMap<ProcessRecord> mProcessNames = new ProcessMap<ProcessRecord>(); 481 482 /** 483 * Tracking long-term execution of processes to look for abuse and other 484 * bad app behavior. 485 */ 486 final ProcessStatsService mProcessStats; 487 488 /** 489 * The currently running isolated processes. 490 */ 491 final SparseArray<ProcessRecord> mIsolatedProcesses = new SparseArray<ProcessRecord>(); 492 493 /** 494 * Counter for assigning isolated process uids, to avoid frequently reusing the 495 * same ones. 496 */ 497 int mNextIsolatedProcessUid = 0; 498 499 /** 500 * The currently running heavy-weight process, if any. 501 */ 502 ProcessRecord mHeavyWeightProcess = null; 503 504 /** 505 * The last time that various processes have crashed. 506 */ 507 final ProcessMap<Long> mProcessCrashTimes = new ProcessMap<Long>(); 508 509 /** 510 * Information about a process that is currently marked as bad. 511 */ 512 static final class BadProcessInfo { 513 BadProcessInfo(long time, String shortMsg, String longMsg, String stack) { 514 this.time = time; 515 this.shortMsg = shortMsg; 516 this.longMsg = longMsg; 517 this.stack = stack; 518 } 519 520 final long time; 521 final String shortMsg; 522 final String longMsg; 523 final String stack; 524 } 525 526 /** 527 * Set of applications that we consider to be bad, and will reject 528 * incoming broadcasts from (which the user has no control over). 529 * Processes are added to this set when they have crashed twice within 530 * a minimum amount of time; they are removed from it when they are 531 * later restarted (hopefully due to some user action). The value is the 532 * time it was added to the list. 533 */ 534 final ProcessMap<BadProcessInfo> mBadProcesses = new ProcessMap<BadProcessInfo>(); 535 536 /** 537 * All of the processes we currently have running organized by pid. 538 * The keys are the pid running the application. 539 * 540 * <p>NOTE: This object is protected by its own lock, NOT the global 541 * activity manager lock! 542 */ 543 final SparseArray<ProcessRecord> mPidsSelfLocked = new SparseArray<ProcessRecord>(); 544 545 /** 546 * All of the processes that have been forced to be foreground. The key 547 * is the pid of the caller who requested it (we hold a death 548 * link on it). 549 */ 550 abstract class ForegroundToken implements IBinder.DeathRecipient { 551 int pid; 552 IBinder token; 553 } 554 final SparseArray<ForegroundToken> mForegroundProcesses = new SparseArray<ForegroundToken>(); 555 556 /** 557 * List of records for processes that someone had tried to start before the 558 * system was ready. We don't start them at that point, but ensure they 559 * are started by the time booting is complete. 560 */ 561 final ArrayList<ProcessRecord> mProcessesOnHold = new ArrayList<ProcessRecord>(); 562 563 /** 564 * List of persistent applications that are in the process 565 * of being started. 566 */ 567 final ArrayList<ProcessRecord> mPersistentStartingProcesses = new ArrayList<ProcessRecord>(); 568 569 /** 570 * Processes that are being forcibly torn down. 571 */ 572 final ArrayList<ProcessRecord> mRemovedProcesses = new ArrayList<ProcessRecord>(); 573 574 /** 575 * List of running applications, sorted by recent usage. 576 * The first entry in the list is the least recently used. 577 */ 578 final ArrayList<ProcessRecord> mLruProcesses = new ArrayList<ProcessRecord>(); 579 580 /** 581 * Where in mLruProcesses that the processes hosting activities start. 582 */ 583 int mLruProcessActivityStart = 0; 584 585 /** 586 * Where in mLruProcesses that the processes hosting services start. 587 * This is after (lower index) than mLruProcessesActivityStart. 588 */ 589 int mLruProcessServiceStart = 0; 590 591 /** 592 * List of processes that should gc as soon as things are idle. 593 */ 594 final ArrayList<ProcessRecord> mProcessesToGc = new ArrayList<ProcessRecord>(); 595 596 /** 597 * Processes we want to collect PSS data from. 598 */ 599 final ArrayList<ProcessRecord> mPendingPssProcesses = new ArrayList<ProcessRecord>(); 600 601 /** 602 * Last time we requested PSS data of all processes. 603 */ 604 long mLastFullPssTime = SystemClock.uptimeMillis(); 605 606 /** 607 * If set, the next time we collect PSS data we should do a full collection 608 * with data from native processes and the kernel. 609 */ 610 boolean mFullPssPending = false; 611 612 /** 613 * This is the process holding what we currently consider to be 614 * the "home" activity. 615 */ 616 ProcessRecord mHomeProcess; 617 618 /** 619 * This is the process holding the activity the user last visited that 620 * is in a different process from the one they are currently in. 621 */ 622 ProcessRecord mPreviousProcess; 623 624 /** 625 * The time at which the previous process was last visible. 626 */ 627 long mPreviousProcessVisibleTime; 628 629 /** 630 * Which uses have been started, so are allowed to run code. 631 */ 632 final SparseArray<UserStartedState> mStartedUsers = new SparseArray<UserStartedState>(); 633 634 /** 635 * LRU list of history of current users. Most recently current is at the end. 636 */ 637 final ArrayList<Integer> mUserLru = new ArrayList<Integer>(); 638 639 /** 640 * Constant array of the users that are currently started. 641 */ 642 int[] mStartedUserArray = new int[] { 0 }; 643 644 /** 645 * Registered observers of the user switching mechanics. 646 */ 647 final RemoteCallbackList<IUserSwitchObserver> mUserSwitchObservers 648 = new RemoteCallbackList<IUserSwitchObserver>(); 649 650 /** 651 * Currently active user switch. 652 */ 653 Object mCurUserSwitchCallback; 654 655 /** 656 * Packages that the user has asked to have run in screen size 657 * compatibility mode instead of filling the screen. 658 */ 659 final CompatModePackages mCompatModePackages; 660 661 /** 662 * Set of IntentSenderRecord objects that are currently active. 663 */ 664 final HashMap<PendingIntentRecord.Key, WeakReference<PendingIntentRecord>> mIntentSenderRecords 665 = new HashMap<PendingIntentRecord.Key, WeakReference<PendingIntentRecord>>(); 666 667 /** 668 * Fingerprints (hashCode()) of stack traces that we've 669 * already logged DropBox entries for. Guarded by itself. If 670 * something (rogue user app) forces this over 671 * MAX_DUP_SUPPRESSED_STACKS entries, the contents are cleared. 672 */ 673 private final HashSet<Integer> mAlreadyLoggedViolatedStacks = new HashSet<Integer>(); 674 private static final int MAX_DUP_SUPPRESSED_STACKS = 5000; 675 676 /** 677 * Strict Mode background batched logging state. 678 * 679 * The string buffer is guarded by itself, and its lock is also 680 * used to determine if another batched write is already 681 * in-flight. 682 */ 683 private final StringBuilder mStrictModeBuffer = new StringBuilder(); 684 685 /** 686 * Keeps track of all IIntentReceivers that have been registered for 687 * broadcasts. Hash keys are the receiver IBinder, hash value is 688 * a ReceiverList. 689 */ 690 final HashMap<IBinder, ReceiverList> mRegisteredReceivers = 691 new HashMap<IBinder, ReceiverList>(); 692 693 /** 694 * Resolver for broadcast intents to registered receivers. 695 * Holds BroadcastFilter (subclass of IntentFilter). 696 */ 697 final IntentResolver<BroadcastFilter, BroadcastFilter> mReceiverResolver 698 = new IntentResolver<BroadcastFilter, BroadcastFilter>() { 699 @Override 700 protected boolean allowFilterResult( 701 BroadcastFilter filter, List<BroadcastFilter> dest) { 702 IBinder target = filter.receiverList.receiver.asBinder(); 703 for (int i=dest.size()-1; i>=0; i--) { 704 if (dest.get(i).receiverList.receiver.asBinder() == target) { 705 return false; 706 } 707 } 708 return true; 709 } 710 711 @Override 712 protected BroadcastFilter newResult(BroadcastFilter filter, int match, int userId) { 713 if (userId == UserHandle.USER_ALL || filter.owningUserId == UserHandle.USER_ALL 714 || userId == filter.owningUserId) { 715 return super.newResult(filter, match, userId); 716 } 717 return null; 718 } 719 720 @Override 721 protected BroadcastFilter[] newArray(int size) { 722 return new BroadcastFilter[size]; 723 } 724 725 @Override 726 protected boolean isPackageForFilter(String packageName, BroadcastFilter filter) { 727 return packageName.equals(filter.packageName); 728 } 729 }; 730 731 /** 732 * State of all active sticky broadcasts per user. Keys are the action of the 733 * sticky Intent, values are an ArrayList of all broadcasted intents with 734 * that action (which should usually be one). The SparseArray is keyed 735 * by the user ID the sticky is for, and can include UserHandle.USER_ALL 736 * for stickies that are sent to all users. 737 */ 738 final SparseArray<ArrayMap<String, ArrayList<Intent>>> mStickyBroadcasts = 739 new SparseArray<ArrayMap<String, ArrayList<Intent>>>(); 740 741 final ActiveServices mServices; 742 743 /** 744 * Backup/restore process management 745 */ 746 String mBackupAppName = null; 747 BackupRecord mBackupTarget = null; 748 749 final ProviderMap mProviderMap; 750 751 /** 752 * List of content providers who have clients waiting for them. The 753 * application is currently being launched and the provider will be 754 * removed from this list once it is published. 755 */ 756 final ArrayList<ContentProviderRecord> mLaunchingProviders 757 = new ArrayList<ContentProviderRecord>(); 758 759 /** 760 * File storing persisted {@link #mGrantedUriPermissions}. 761 */ 762 private final AtomicFile mGrantFile; 763 764 /** XML constants used in {@link #mGrantFile} */ 765 private static final String TAG_URI_GRANTS = "uri-grants"; 766 private static final String TAG_URI_GRANT = "uri-grant"; 767 private static final String ATTR_USER_HANDLE = "userHandle"; 768 private static final String ATTR_SOURCE_USER_ID = "sourceUserId"; 769 private static final String ATTR_TARGET_USER_ID = "targetUserId"; 770 private static final String ATTR_SOURCE_PKG = "sourcePkg"; 771 private static final String ATTR_TARGET_PKG = "targetPkg"; 772 private static final String ATTR_URI = "uri"; 773 private static final String ATTR_MODE_FLAGS = "modeFlags"; 774 private static final String ATTR_CREATED_TIME = "createdTime"; 775 private static final String ATTR_PREFIX = "prefix"; 776 777 /** 778 * Global set of specific {@link Uri} permissions that have been granted. 779 * This optimized lookup structure maps from {@link UriPermission#targetUid} 780 * to {@link UriPermission#uri} to {@link UriPermission}. 781 */ 782 @GuardedBy("this") 783 private final SparseArray<ArrayMap<GrantUri, UriPermission>> 784 mGrantedUriPermissions = new SparseArray<ArrayMap<GrantUri, UriPermission>>(); 785 786 public static class GrantUri { 787 public final int sourceUserId; 788 public final Uri uri; 789 public boolean prefix; 790 791 public GrantUri(int sourceUserId, Uri uri, boolean prefix) { 792 this.sourceUserId = sourceUserId; 793 this.uri = uri; 794 this.prefix = prefix; 795 } 796 797 @Override 798 public int hashCode() { 799 return toString().hashCode(); 800 } 801 802 @Override 803 public boolean equals(Object o) { 804 if (o instanceof GrantUri) { 805 GrantUri other = (GrantUri) o; 806 return uri.equals(other.uri) && (sourceUserId == other.sourceUserId) 807 && prefix == other.prefix; 808 } 809 return false; 810 } 811 812 @Override 813 public String toString() { 814 String result = Integer.toString(sourceUserId) + " @ " + uri.toString(); 815 if (prefix) result += " [prefix]"; 816 return result; 817 } 818 819 public String toSafeString() { 820 String result = Integer.toString(sourceUserId) + " @ " + uri.toSafeString(); 821 if (prefix) result += " [prefix]"; 822 return result; 823 } 824 825 public static GrantUri resolve(int defaultSourceUserHandle, Uri uri) { 826 return new GrantUri(ContentProvider.getUserIdFromUri(uri, defaultSourceUserHandle), 827 ContentProvider.getUriWithoutUserId(uri), false); 828 } 829 } 830 831 CoreSettingsObserver mCoreSettingsObserver; 832 833 /** 834 * Thread-local storage used to carry caller permissions over through 835 * indirect content-provider access. 836 */ 837 private class Identity { 838 public int pid; 839 public int uid; 840 841 Identity(int _pid, int _uid) { 842 pid = _pid; 843 uid = _uid; 844 } 845 } 846 847 private static final ThreadLocal<Identity> sCallerIdentity = new ThreadLocal<Identity>(); 848 849 /** 850 * All information we have collected about the runtime performance of 851 * any user id that can impact battery performance. 852 */ 853 final BatteryStatsService mBatteryStatsService; 854 855 /** 856 * Information about component usage 857 */ 858 UsageStatsManagerInternal mUsageStatsService; 859 860 /** 861 * Information about and control over application operations 862 */ 863 final AppOpsService mAppOpsService; 864 865 /** 866 * Save recent tasks information across reboots. 867 */ 868 final TaskPersister mTaskPersister; 869 870 /** 871 * Current configuration information. HistoryRecord objects are given 872 * a reference to this object to indicate which configuration they are 873 * currently running in, so this object must be kept immutable. 874 */ 875 Configuration mConfiguration = new Configuration(); 876 877 /** 878 * Current sequencing integer of the configuration, for skipping old 879 * configurations. 880 */ 881 int mConfigurationSeq = 0; 882 883 /** 884 * Hardware-reported OpenGLES version. 885 */ 886 final int GL_ES_VERSION; 887 888 /** 889 * List of initialization arguments to pass to all processes when binding applications to them. 890 * For example, references to the commonly used services. 891 */ 892 HashMap<String, IBinder> mAppBindArgs; 893 894 /** 895 * Temporary to avoid allocations. Protected by main lock. 896 */ 897 final StringBuilder mStringBuilder = new StringBuilder(256); 898 899 /** 900 * Used to control how we initialize the service. 901 */ 902 ComponentName mTopComponent; 903 String mTopAction = Intent.ACTION_MAIN; 904 String mTopData; 905 boolean mProcessesReady = false; 906 boolean mSystemReady = false; 907 boolean mBooting = false; 908 boolean mCallFinishBooting = false; 909 boolean mBootAnimationComplete = false; 910 boolean mWaitingUpdate = false; 911 boolean mDidUpdate = false; 912 boolean mOnBattery = false; 913 boolean mLaunchWarningShown = false; 914 915 Context mContext; 916 917 int mFactoryTest; 918 919 boolean mCheckedForSetup; 920 921 /** 922 * The time at which we will allow normal application switches again, 923 * after a call to {@link #stopAppSwitches()}. 924 */ 925 long mAppSwitchesAllowedTime; 926 927 /** 928 * This is set to true after the first switch after mAppSwitchesAllowedTime 929 * is set; any switches after that will clear the time. 930 */ 931 boolean mDidAppSwitch; 932 933 /** 934 * Last time (in realtime) at which we checked for power usage. 935 */ 936 long mLastPowerCheckRealtime; 937 938 /** 939 * Last time (in uptime) at which we checked for power usage. 940 */ 941 long mLastPowerCheckUptime; 942 943 /** 944 * Set while we are wanting to sleep, to prevent any 945 * activities from being started/resumed. 946 */ 947 private boolean mSleeping = false; 948 949 /** 950 * Set while we are running a voice interaction. This overrides 951 * sleeping while it is active. 952 */ 953 private boolean mRunningVoice = false; 954 955 /** 956 * State of external calls telling us if the device is asleep. 957 */ 958 private boolean mWentToSleep = false; 959 960 static final int LOCK_SCREEN_HIDDEN = 0; 961 static final int LOCK_SCREEN_LEAVING = 1; 962 static final int LOCK_SCREEN_SHOWN = 2; 963 /** 964 * State of external call telling us if the lock screen is shown. 965 */ 966 int mLockScreenShown = LOCK_SCREEN_HIDDEN; 967 968 /** 969 * Set if we are shutting down the system, similar to sleeping. 970 */ 971 boolean mShuttingDown = false; 972 973 /** 974 * Current sequence id for oom_adj computation traversal. 975 */ 976 int mAdjSeq = 0; 977 978 /** 979 * Current sequence id for process LRU updating. 980 */ 981 int mLruSeq = 0; 982 983 /** 984 * Keep track of the non-cached/empty process we last found, to help 985 * determine how to distribute cached/empty processes next time. 986 */ 987 int mNumNonCachedProcs = 0; 988 989 /** 990 * Keep track of the number of cached hidden procs, to balance oom adj 991 * distribution between those and empty procs. 992 */ 993 int mNumCachedHiddenProcs = 0; 994 995 /** 996 * Keep track of the number of service processes we last found, to 997 * determine on the next iteration which should be B services. 998 */ 999 int mNumServiceProcs = 0; 1000 int mNewNumAServiceProcs = 0; 1001 int mNewNumServiceProcs = 0; 1002 1003 /** 1004 * Allow the current computed overall memory level of the system to go down? 1005 * This is set to false when we are killing processes for reasons other than 1006 * memory management, so that the now smaller process list will not be taken as 1007 * an indication that memory is tighter. 1008 */ 1009 boolean mAllowLowerMemLevel = false; 1010 1011 /** 1012 * The last computed memory level, for holding when we are in a state that 1013 * processes are going away for other reasons. 1014 */ 1015 int mLastMemoryLevel = ProcessStats.ADJ_MEM_FACTOR_NORMAL; 1016 1017 /** 1018 * The last total number of process we have, to determine if changes actually look 1019 * like a shrinking number of process due to lower RAM. 1020 */ 1021 int mLastNumProcesses; 1022 1023 /** 1024 * The uptime of the last time we performed idle maintenance. 1025 */ 1026 long mLastIdleTime = SystemClock.uptimeMillis(); 1027 1028 /** 1029 * Total time spent with RAM that has been added in the past since the last idle time. 1030 */ 1031 long mLowRamTimeSinceLastIdle = 0; 1032 1033 /** 1034 * If RAM is currently low, when that horrible situation started. 1035 */ 1036 long mLowRamStartTime = 0; 1037 1038 /** 1039 * For reporting to battery stats the current top application. 1040 */ 1041 private String mCurResumedPackage = null; 1042 private int mCurResumedUid = -1; 1043 1044 /** 1045 * For reporting to battery stats the apps currently running foreground 1046 * service. The ProcessMap is package/uid tuples; each of these contain 1047 * an array of the currently foreground processes. 1048 */ 1049 final ProcessMap<ArrayList<ProcessRecord>> mForegroundPackages 1050 = new ProcessMap<ArrayList<ProcessRecord>>(); 1051 1052 /** 1053 * This is set if we had to do a delayed dexopt of an app before launching 1054 * it, to increase the ANR timeouts in that case. 1055 */ 1056 boolean mDidDexOpt; 1057 1058 /** 1059 * Set if the systemServer made a call to enterSafeMode. 1060 */ 1061 boolean mSafeMode; 1062 1063 String mDebugApp = null; 1064 boolean mWaitForDebugger = false; 1065 boolean mDebugTransient = false; 1066 String mOrigDebugApp = null; 1067 boolean mOrigWaitForDebugger = false; 1068 boolean mAlwaysFinishActivities = false; 1069 IActivityController mController = null; 1070 String mProfileApp = null; 1071 ProcessRecord mProfileProc = null; 1072 String mProfileFile; 1073 ParcelFileDescriptor mProfileFd; 1074 int mSamplingInterval = 0; 1075 boolean mAutoStopProfiler = false; 1076 int mProfileType = 0; 1077 String mOpenGlTraceApp = null; 1078 1079 static class ProcessChangeItem { 1080 static final int CHANGE_ACTIVITIES = 1<<0; 1081 static final int CHANGE_PROCESS_STATE = 1<<1; 1082 int changes; 1083 int uid; 1084 int pid; 1085 int processState; 1086 boolean foregroundActivities; 1087 } 1088 1089 final RemoteCallbackList<IProcessObserver> mProcessObservers 1090 = new RemoteCallbackList<IProcessObserver>(); 1091 ProcessChangeItem[] mActiveProcessChanges = new ProcessChangeItem[5]; 1092 1093 final ArrayList<ProcessChangeItem> mPendingProcessChanges 1094 = new ArrayList<ProcessChangeItem>(); 1095 final ArrayList<ProcessChangeItem> mAvailProcessChanges 1096 = new ArrayList<ProcessChangeItem>(); 1097 1098 /** 1099 * Runtime CPU use collection thread. This object's lock is used to 1100 * perform synchronization with the thread (notifying it to run). 1101 */ 1102 final Thread mProcessCpuThread; 1103 1104 /** 1105 * Used to collect per-process CPU use for ANRs, battery stats, etc. 1106 * Must acquire this object's lock when accessing it. 1107 * NOTE: this lock will be held while doing long operations (trawling 1108 * through all processes in /proc), so it should never be acquired by 1109 * any critical paths such as when holding the main activity manager lock. 1110 */ 1111 final ProcessCpuTracker mProcessCpuTracker = new ProcessCpuTracker( 1112 MONITOR_THREAD_CPU_USAGE); 1113 final AtomicLong mLastCpuTime = new AtomicLong(0); 1114 final AtomicBoolean mProcessCpuMutexFree = new AtomicBoolean(true); 1115 1116 long mLastWriteTime = 0; 1117 1118 /** 1119 * Used to retain an update lock when the foreground activity is in 1120 * immersive mode. 1121 */ 1122 final UpdateLock mUpdateLock = new UpdateLock("immersive"); 1123 1124 /** 1125 * Set to true after the system has finished booting. 1126 */ 1127 boolean mBooted = false; 1128 1129 int mProcessLimit = ProcessList.MAX_CACHED_APPS; 1130 int mProcessLimitOverride = -1; 1131 1132 WindowManagerService mWindowManager; 1133 1134 final ActivityThread mSystemThread; 1135 1136 // Holds the current foreground user's id 1137 int mCurrentUserId = 0; 1138 // Holds the target user's id during a user switch 1139 int mTargetUserId = UserHandle.USER_NULL; 1140 // If there are multiple profiles for the current user, their ids are here 1141 // Currently only the primary user can have managed profiles 1142 int[] mCurrentProfileIds = new int[] {UserHandle.USER_OWNER}; // Accessed by ActivityStack 1143 1144 /** 1145 * Mapping from each known user ID to the profile group ID it is associated with. 1146 */ 1147 SparseIntArray mUserProfileGroupIdsSelfLocked = new SparseIntArray(); 1148 1149 private UserManagerService mUserManager; 1150 1151 private final class AppDeathRecipient implements IBinder.DeathRecipient { 1152 final ProcessRecord mApp; 1153 final int mPid; 1154 final IApplicationThread mAppThread; 1155 1156 AppDeathRecipient(ProcessRecord app, int pid, 1157 IApplicationThread thread) { 1158 if (localLOGV) Slog.v( 1159 TAG, "New death recipient " + this 1160 + " for thread " + thread.asBinder()); 1161 mApp = app; 1162 mPid = pid; 1163 mAppThread = thread; 1164 } 1165 1166 @Override 1167 public void binderDied() { 1168 if (localLOGV) Slog.v( 1169 TAG, "Death received in " + this 1170 + " for thread " + mAppThread.asBinder()); 1171 synchronized(ActivityManagerService.this) { 1172 appDiedLocked(mApp, mPid, mAppThread); 1173 } 1174 } 1175 } 1176 1177 static final int SHOW_ERROR_MSG = 1; 1178 static final int SHOW_NOT_RESPONDING_MSG = 2; 1179 static final int SHOW_FACTORY_ERROR_MSG = 3; 1180 static final int UPDATE_CONFIGURATION_MSG = 4; 1181 static final int GC_BACKGROUND_PROCESSES_MSG = 5; 1182 static final int WAIT_FOR_DEBUGGER_MSG = 6; 1183 static final int SERVICE_TIMEOUT_MSG = 12; 1184 static final int UPDATE_TIME_ZONE = 13; 1185 static final int SHOW_UID_ERROR_MSG = 14; 1186 static final int SHOW_FINGERPRINT_ERROR_MSG = 15; 1187 static final int PROC_START_TIMEOUT_MSG = 20; 1188 static final int DO_PENDING_ACTIVITY_LAUNCHES_MSG = 21; 1189 static final int KILL_APPLICATION_MSG = 22; 1190 static final int FINALIZE_PENDING_INTENT_MSG = 23; 1191 static final int POST_HEAVY_NOTIFICATION_MSG = 24; 1192 static final int CANCEL_HEAVY_NOTIFICATION_MSG = 25; 1193 static final int SHOW_STRICT_MODE_VIOLATION_MSG = 26; 1194 static final int CHECK_EXCESSIVE_WAKE_LOCKS_MSG = 27; 1195 static final int CLEAR_DNS_CACHE_MSG = 28; 1196 static final int UPDATE_HTTP_PROXY_MSG = 29; 1197 static final int SHOW_COMPAT_MODE_DIALOG_MSG = 30; 1198 static final int DISPATCH_PROCESSES_CHANGED = 31; 1199 static final int DISPATCH_PROCESS_DIED = 32; 1200 static final int REPORT_MEM_USAGE_MSG = 33; 1201 static final int REPORT_USER_SWITCH_MSG = 34; 1202 static final int CONTINUE_USER_SWITCH_MSG = 35; 1203 static final int USER_SWITCH_TIMEOUT_MSG = 36; 1204 static final int IMMERSIVE_MODE_LOCK_MSG = 37; 1205 static final int PERSIST_URI_GRANTS_MSG = 38; 1206 static final int REQUEST_ALL_PSS_MSG = 39; 1207 static final int START_PROFILES_MSG = 40; 1208 static final int UPDATE_TIME = 41; 1209 static final int SYSTEM_USER_START_MSG = 42; 1210 static final int SYSTEM_USER_CURRENT_MSG = 43; 1211 static final int ENTER_ANIMATION_COMPLETE_MSG = 44; 1212 static final int FINISH_BOOTING_MSG = 45; 1213 static final int START_USER_SWITCH_MSG = 46; 1214 static final int SEND_LOCALE_TO_MOUNT_DAEMON_MSG = 47; 1215 static final int DISMISS_DIALOG_MSG = 48; 1216 1217 static final int FIRST_ACTIVITY_STACK_MSG = 100; 1218 static final int FIRST_BROADCAST_QUEUE_MSG = 200; 1219 static final int FIRST_COMPAT_MODE_MSG = 300; 1220 static final int FIRST_SUPERVISOR_STACK_MSG = 100; 1221 1222 CompatModeDialog mCompatModeDialog; 1223 long mLastMemUsageReportTime = 0; 1224 1225 /** 1226 * Flag whether the current user is a "monkey", i.e. whether 1227 * the UI is driven by a UI automation tool. 1228 */ 1229 private boolean mUserIsMonkey; 1230 1231 /** Flag whether the device has a Recents UI */ 1232 boolean mHasRecents; 1233 1234 /** The dimensions of the thumbnails in the Recents UI. */ 1235 int mThumbnailWidth; 1236 int mThumbnailHeight; 1237 1238 final ServiceThread mHandlerThread; 1239 final MainHandler mHandler; 1240 1241 final class MainHandler extends Handler { 1242 public MainHandler(Looper looper) { 1243 super(looper, null, true); 1244 } 1245 1246 @Override 1247 public void handleMessage(Message msg) { 1248 switch (msg.what) { 1249 case SHOW_ERROR_MSG: { 1250 HashMap<String, Object> data = (HashMap<String, Object>) msg.obj; 1251 boolean showBackground = Settings.Secure.getInt(mContext.getContentResolver(), 1252 Settings.Secure.ANR_SHOW_BACKGROUND, 0) != 0; 1253 synchronized (ActivityManagerService.this) { 1254 ProcessRecord proc = (ProcessRecord)data.get("app"); 1255 AppErrorResult res = (AppErrorResult) data.get("result"); 1256 if (proc != null && proc.crashDialog != null) { 1257 Slog.e(TAG, "App already has crash dialog: " + proc); 1258 if (res != null) { 1259 res.set(0); 1260 } 1261 return; 1262 } 1263 boolean isBackground = (UserHandle.getAppId(proc.uid) 1264 >= Process.FIRST_APPLICATION_UID 1265 && proc.pid != MY_PID); 1266 for (int userId : mCurrentProfileIds) { 1267 isBackground &= (proc.userId != userId); 1268 } 1269 if (isBackground && !showBackground) { 1270 Slog.w(TAG, "Skipping crash dialog of " + proc + ": background"); 1271 if (res != null) { 1272 res.set(0); 1273 } 1274 return; 1275 } 1276 if (mShowDialogs && !mSleeping && !mShuttingDown) { 1277 Dialog d = new AppErrorDialog(mContext, 1278 ActivityManagerService.this, res, proc); 1279 d.show(); 1280 proc.crashDialog = d; 1281 } else { 1282 // The device is asleep, so just pretend that the user 1283 // saw a crash dialog and hit "force quit". 1284 if (res != null) { 1285 res.set(0); 1286 } 1287 } 1288 } 1289 1290 ensureBootCompleted(); 1291 } break; 1292 case SHOW_NOT_RESPONDING_MSG: { 1293 synchronized (ActivityManagerService.this) { 1294 HashMap<String, Object> data = (HashMap<String, Object>) msg.obj; 1295 ProcessRecord proc = (ProcessRecord)data.get("app"); 1296 if (proc != null && proc.anrDialog != null) { 1297 Slog.e(TAG, "App already has anr dialog: " + proc); 1298 return; 1299 } 1300 1301 Intent intent = new Intent("android.intent.action.ANR"); 1302 if (!mProcessesReady) { 1303 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY 1304 | Intent.FLAG_RECEIVER_FOREGROUND); 1305 } 1306 broadcastIntentLocked(null, null, intent, 1307 null, null, 0, null, null, null, AppOpsManager.OP_NONE, 1308 false, false, MY_PID, Process.SYSTEM_UID, 0 /* TODO: Verify */); 1309 1310 if (mShowDialogs) { 1311 Dialog d = new AppNotRespondingDialog(ActivityManagerService.this, 1312 mContext, proc, (ActivityRecord)data.get("activity"), 1313 msg.arg1 != 0); 1314 d.show(); 1315 proc.anrDialog = d; 1316 } else { 1317 // Just kill the app if there is no dialog to be shown. 1318 killAppAtUsersRequest(proc, null); 1319 } 1320 } 1321 1322 ensureBootCompleted(); 1323 } break; 1324 case SHOW_STRICT_MODE_VIOLATION_MSG: { 1325 HashMap<String, Object> data = (HashMap<String, Object>) msg.obj; 1326 synchronized (ActivityManagerService.this) { 1327 ProcessRecord proc = (ProcessRecord) data.get("app"); 1328 if (proc == null) { 1329 Slog.e(TAG, "App not found when showing strict mode dialog."); 1330 break; 1331 } 1332 if (proc.crashDialog != null) { 1333 Slog.e(TAG, "App already has strict mode dialog: " + proc); 1334 return; 1335 } 1336 AppErrorResult res = (AppErrorResult) data.get("result"); 1337 if (mShowDialogs && !mSleeping && !mShuttingDown) { 1338 Dialog d = new StrictModeViolationDialog(mContext, 1339 ActivityManagerService.this, res, proc); 1340 d.show(); 1341 proc.crashDialog = d; 1342 } else { 1343 // The device is asleep, so just pretend that the user 1344 // saw a crash dialog and hit "force quit". 1345 res.set(0); 1346 } 1347 } 1348 ensureBootCompleted(); 1349 } break; 1350 case SHOW_FACTORY_ERROR_MSG: { 1351 Dialog d = new FactoryErrorDialog( 1352 mContext, msg.getData().getCharSequence("msg")); 1353 d.show(); 1354 ensureBootCompleted(); 1355 } break; 1356 case UPDATE_CONFIGURATION_MSG: { 1357 final ContentResolver resolver = mContext.getContentResolver(); 1358 Settings.System.putConfiguration(resolver, (Configuration)msg.obj); 1359 } break; 1360 case GC_BACKGROUND_PROCESSES_MSG: { 1361 synchronized (ActivityManagerService.this) { 1362 performAppGcsIfAppropriateLocked(); 1363 } 1364 } break; 1365 case WAIT_FOR_DEBUGGER_MSG: { 1366 synchronized (ActivityManagerService.this) { 1367 ProcessRecord app = (ProcessRecord)msg.obj; 1368 if (msg.arg1 != 0) { 1369 if (!app.waitedForDebugger) { 1370 Dialog d = new AppWaitingForDebuggerDialog( 1371 ActivityManagerService.this, 1372 mContext, app); 1373 app.waitDialog = d; 1374 app.waitedForDebugger = true; 1375 d.show(); 1376 } 1377 } else { 1378 if (app.waitDialog != null) { 1379 app.waitDialog.dismiss(); 1380 app.waitDialog = null; 1381 } 1382 } 1383 } 1384 } break; 1385 case SERVICE_TIMEOUT_MSG: { 1386 if (mDidDexOpt) { 1387 mDidDexOpt = false; 1388 Message nmsg = mHandler.obtainMessage(SERVICE_TIMEOUT_MSG); 1389 nmsg.obj = msg.obj; 1390 mHandler.sendMessageDelayed(nmsg, ActiveServices.SERVICE_TIMEOUT); 1391 return; 1392 } 1393 mServices.serviceTimeout((ProcessRecord)msg.obj); 1394 } break; 1395 case UPDATE_TIME_ZONE: { 1396 synchronized (ActivityManagerService.this) { 1397 for (int i = mLruProcesses.size() - 1 ; i >= 0 ; i--) { 1398 ProcessRecord r = mLruProcesses.get(i); 1399 if (r.thread != null) { 1400 try { 1401 r.thread.updateTimeZone(); 1402 } catch (RemoteException ex) { 1403 Slog.w(TAG, "Failed to update time zone for: " + r.info.processName); 1404 } 1405 } 1406 } 1407 } 1408 } break; 1409 case CLEAR_DNS_CACHE_MSG: { 1410 synchronized (ActivityManagerService.this) { 1411 for (int i = mLruProcesses.size() - 1 ; i >= 0 ; i--) { 1412 ProcessRecord r = mLruProcesses.get(i); 1413 if (r.thread != null) { 1414 try { 1415 r.thread.clearDnsCache(); 1416 } catch (RemoteException ex) { 1417 Slog.w(TAG, "Failed to clear dns cache for: " + r.info.processName); 1418 } 1419 } 1420 } 1421 } 1422 } break; 1423 case UPDATE_HTTP_PROXY_MSG: { 1424 ProxyInfo proxy = (ProxyInfo)msg.obj; 1425 String host = ""; 1426 String port = ""; 1427 String exclList = ""; 1428 Uri pacFileUrl = Uri.EMPTY; 1429 if (proxy != null) { 1430 host = proxy.getHost(); 1431 port = Integer.toString(proxy.getPort()); 1432 exclList = proxy.getExclusionListAsString(); 1433 pacFileUrl = proxy.getPacFileUrl(); 1434 } 1435 synchronized (ActivityManagerService.this) { 1436 for (int i = mLruProcesses.size() - 1 ; i >= 0 ; i--) { 1437 ProcessRecord r = mLruProcesses.get(i); 1438 if (r.thread != null) { 1439 try { 1440 r.thread.setHttpProxy(host, port, exclList, pacFileUrl); 1441 } catch (RemoteException ex) { 1442 Slog.w(TAG, "Failed to update http proxy for: " + 1443 r.info.processName); 1444 } 1445 } 1446 } 1447 } 1448 } break; 1449 case SHOW_UID_ERROR_MSG: { 1450 if (mShowDialogs) { 1451 AlertDialog d = new BaseErrorDialog(mContext); 1452 d.getWindow().setType(WindowManager.LayoutParams.TYPE_SYSTEM_ERROR); 1453 d.setCancelable(false); 1454 d.setTitle(mContext.getText(R.string.android_system_label)); 1455 d.setMessage(mContext.getText(R.string.system_error_wipe_data)); 1456 d.setButton(DialogInterface.BUTTON_POSITIVE, mContext.getText(R.string.ok), 1457 mHandler.obtainMessage(DISMISS_DIALOG_MSG, d)); 1458 d.show(); 1459 } 1460 } break; 1461 case SHOW_FINGERPRINT_ERROR_MSG: { 1462 if (mShowDialogs) { 1463 AlertDialog d = new BaseErrorDialog(mContext); 1464 d.getWindow().setType(WindowManager.LayoutParams.TYPE_SYSTEM_ERROR); 1465 d.setCancelable(false); 1466 d.setTitle(mContext.getText(R.string.android_system_label)); 1467 d.setMessage(mContext.getText(R.string.system_error_manufacturer)); 1468 d.setButton(DialogInterface.BUTTON_POSITIVE, mContext.getText(R.string.ok), 1469 mHandler.obtainMessage(DISMISS_DIALOG_MSG, d)); 1470 d.show(); 1471 } 1472 } break; 1473 case PROC_START_TIMEOUT_MSG: { 1474 if (mDidDexOpt) { 1475 mDidDexOpt = false; 1476 Message nmsg = mHandler.obtainMessage(PROC_START_TIMEOUT_MSG); 1477 nmsg.obj = msg.obj; 1478 mHandler.sendMessageDelayed(nmsg, PROC_START_TIMEOUT); 1479 return; 1480 } 1481 ProcessRecord app = (ProcessRecord)msg.obj; 1482 synchronized (ActivityManagerService.this) { 1483 processStartTimedOutLocked(app); 1484 } 1485 } break; 1486 case DO_PENDING_ACTIVITY_LAUNCHES_MSG: { 1487 synchronized (ActivityManagerService.this) { 1488 mStackSupervisor.doPendingActivityLaunchesLocked(true); 1489 } 1490 } break; 1491 case KILL_APPLICATION_MSG: { 1492 synchronized (ActivityManagerService.this) { 1493 int appid = msg.arg1; 1494 boolean restart = (msg.arg2 == 1); 1495 Bundle bundle = (Bundle)msg.obj; 1496 String pkg = bundle.getString("pkg"); 1497 String reason = bundle.getString("reason"); 1498 forceStopPackageLocked(pkg, appid, restart, false, true, false, 1499 false, UserHandle.USER_ALL, reason); 1500 } 1501 } break; 1502 case FINALIZE_PENDING_INTENT_MSG: { 1503 ((PendingIntentRecord)msg.obj).completeFinalize(); 1504 } break; 1505 case POST_HEAVY_NOTIFICATION_MSG: { 1506 INotificationManager inm = NotificationManager.getService(); 1507 if (inm == null) { 1508 return; 1509 } 1510 1511 ActivityRecord root = (ActivityRecord)msg.obj; 1512 ProcessRecord process = root.app; 1513 if (process == null) { 1514 return; 1515 } 1516 1517 try { 1518 Context context = mContext.createPackageContext(process.info.packageName, 0); 1519 String text = mContext.getString(R.string.heavy_weight_notification, 1520 context.getApplicationInfo().loadLabel(context.getPackageManager())); 1521 Notification notification = new Notification(); 1522 notification.icon = com.android.internal.R.drawable.stat_sys_adb; //context.getApplicationInfo().icon; 1523 notification.when = 0; 1524 notification.flags = Notification.FLAG_ONGOING_EVENT; 1525 notification.tickerText = text; 1526 notification.defaults = 0; // please be quiet 1527 notification.sound = null; 1528 notification.vibrate = null; 1529 notification.color = mContext.getResources().getColor( 1530 com.android.internal.R.color.system_notification_accent_color); 1531 notification.setLatestEventInfo(context, text, 1532 mContext.getText(R.string.heavy_weight_notification_detail), 1533 PendingIntent.getActivityAsUser(mContext, 0, root.intent, 1534 PendingIntent.FLAG_CANCEL_CURRENT, null, 1535 new UserHandle(root.userId))); 1536 1537 try { 1538 int[] outId = new int[1]; 1539 inm.enqueueNotificationWithTag("android", "android", null, 1540 R.string.heavy_weight_notification, 1541 notification, outId, root.userId); 1542 } catch (RuntimeException e) { 1543 Slog.w(ActivityManagerService.TAG, 1544 "Error showing notification for heavy-weight app", e); 1545 } catch (RemoteException e) { 1546 } 1547 } catch (NameNotFoundException e) { 1548 Slog.w(TAG, "Unable to create context for heavy notification", e); 1549 } 1550 } break; 1551 case CANCEL_HEAVY_NOTIFICATION_MSG: { 1552 INotificationManager inm = NotificationManager.getService(); 1553 if (inm == null) { 1554 return; 1555 } 1556 try { 1557 inm.cancelNotificationWithTag("android", null, 1558 R.string.heavy_weight_notification, msg.arg1); 1559 } catch (RuntimeException e) { 1560 Slog.w(ActivityManagerService.TAG, 1561 "Error canceling notification for service", e); 1562 } catch (RemoteException e) { 1563 } 1564 } break; 1565 case CHECK_EXCESSIVE_WAKE_LOCKS_MSG: { 1566 synchronized (ActivityManagerService.this) { 1567 checkExcessivePowerUsageLocked(true); 1568 removeMessages(CHECK_EXCESSIVE_WAKE_LOCKS_MSG); 1569 Message nmsg = obtainMessage(CHECK_EXCESSIVE_WAKE_LOCKS_MSG); 1570 sendMessageDelayed(nmsg, POWER_CHECK_DELAY); 1571 } 1572 } break; 1573 case SHOW_COMPAT_MODE_DIALOG_MSG: { 1574 synchronized (ActivityManagerService.this) { 1575 ActivityRecord ar = (ActivityRecord)msg.obj; 1576 if (mCompatModeDialog != null) { 1577 if (mCompatModeDialog.mAppInfo.packageName.equals( 1578 ar.info.applicationInfo.packageName)) { 1579 return; 1580 } 1581 mCompatModeDialog.dismiss(); 1582 mCompatModeDialog = null; 1583 } 1584 if (ar != null && false) { 1585 if (mCompatModePackages.getPackageAskCompatModeLocked( 1586 ar.packageName)) { 1587 int mode = mCompatModePackages.computeCompatModeLocked( 1588 ar.info.applicationInfo); 1589 if (mode == ActivityManager.COMPAT_MODE_DISABLED 1590 || mode == ActivityManager.COMPAT_MODE_ENABLED) { 1591 mCompatModeDialog = new CompatModeDialog( 1592 ActivityManagerService.this, mContext, 1593 ar.info.applicationInfo); 1594 mCompatModeDialog.show(); 1595 } 1596 } 1597 } 1598 } 1599 break; 1600 } 1601 case DISPATCH_PROCESSES_CHANGED: { 1602 dispatchProcessesChanged(); 1603 break; 1604 } 1605 case DISPATCH_PROCESS_DIED: { 1606 final int pid = msg.arg1; 1607 final int uid = msg.arg2; 1608 dispatchProcessDied(pid, uid); 1609 break; 1610 } 1611 case REPORT_MEM_USAGE_MSG: { 1612 final ArrayList<ProcessMemInfo> memInfos = (ArrayList<ProcessMemInfo>)msg.obj; 1613 Thread thread = new Thread() { 1614 @Override public void run() { 1615 reportMemUsage(memInfos); 1616 } 1617 }; 1618 thread.start(); 1619 break; 1620 } 1621 case START_USER_SWITCH_MSG: { 1622 showUserSwitchDialog(msg.arg1, (String) msg.obj); 1623 break; 1624 } 1625 case REPORT_USER_SWITCH_MSG: { 1626 dispatchUserSwitch((UserStartedState) msg.obj, msg.arg1, msg.arg2); 1627 break; 1628 } 1629 case CONTINUE_USER_SWITCH_MSG: { 1630 continueUserSwitch((UserStartedState) msg.obj, msg.arg1, msg.arg2); 1631 break; 1632 } 1633 case USER_SWITCH_TIMEOUT_MSG: { 1634 timeoutUserSwitch((UserStartedState) msg.obj, msg.arg1, msg.arg2); 1635 break; 1636 } 1637 case IMMERSIVE_MODE_LOCK_MSG: { 1638 final boolean nextState = (msg.arg1 != 0); 1639 if (mUpdateLock.isHeld() != nextState) { 1640 if (DEBUG_IMMERSIVE) { 1641 final ActivityRecord r = (ActivityRecord) msg.obj; 1642 Slog.d(TAG, "Applying new update lock state '" + nextState + "' for " + r); 1643 } 1644 if (nextState) { 1645 mUpdateLock.acquire(); 1646 } else { 1647 mUpdateLock.release(); 1648 } 1649 } 1650 break; 1651 } 1652 case PERSIST_URI_GRANTS_MSG: { 1653 writeGrantedUriPermissions(); 1654 break; 1655 } 1656 case REQUEST_ALL_PSS_MSG: { 1657 requestPssAllProcsLocked(SystemClock.uptimeMillis(), true, false); 1658 break; 1659 } 1660 case START_PROFILES_MSG: { 1661 synchronized (ActivityManagerService.this) { 1662 startProfilesLocked(); 1663 } 1664 break; 1665 } 1666 case UPDATE_TIME: { 1667 synchronized (ActivityManagerService.this) { 1668 for (int i = mLruProcesses.size() - 1 ; i >= 0 ; i--) { 1669 ProcessRecord r = mLruProcesses.get(i); 1670 if (r.thread != null) { 1671 try { 1672 r.thread.updateTimePrefs(msg.arg1 == 0 ? false : true); 1673 } catch (RemoteException ex) { 1674 Slog.w(TAG, "Failed to update preferences for: " + r.info.processName); 1675 } 1676 } 1677 } 1678 } 1679 break; 1680 } 1681 case SYSTEM_USER_START_MSG: { 1682 mBatteryStatsService.noteEvent(BatteryStats.HistoryItem.EVENT_USER_RUNNING_START, 1683 Integer.toString(msg.arg1), msg.arg1); 1684 mSystemServiceManager.startUser(msg.arg1); 1685 break; 1686 } 1687 case SYSTEM_USER_CURRENT_MSG: { 1688 mBatteryStatsService.noteEvent( 1689 BatteryStats.HistoryItem.EVENT_USER_FOREGROUND_FINISH, 1690 Integer.toString(msg.arg2), msg.arg2); 1691 mBatteryStatsService.noteEvent( 1692 BatteryStats.HistoryItem.EVENT_USER_FOREGROUND_START, 1693 Integer.toString(msg.arg1), msg.arg1); 1694 mSystemServiceManager.switchUser(msg.arg1); 1695 break; 1696 } 1697 case ENTER_ANIMATION_COMPLETE_MSG: { 1698 synchronized (ActivityManagerService.this) { 1699 ActivityRecord r = ActivityRecord.forToken((IBinder) msg.obj); 1700 if (r != null && r.app != null && r.app.thread != null) { 1701 try { 1702 r.app.thread.scheduleEnterAnimationComplete(r.appToken); 1703 } catch (RemoteException e) { 1704 } 1705 } 1706 } 1707 break; 1708 } 1709 case FINISH_BOOTING_MSG: { 1710 if (msg.arg1 != 0) { 1711 finishBooting(); 1712 } 1713 if (msg.arg2 != 0) { 1714 enableScreenAfterBoot(); 1715 } 1716 break; 1717 } 1718 case SEND_LOCALE_TO_MOUNT_DAEMON_MSG: { 1719 try { 1720 Locale l = (Locale) msg.obj; 1721 IBinder service = ServiceManager.getService("mount"); 1722 IMountService mountService = IMountService.Stub.asInterface(service); 1723 Log.d(TAG, "Storing locale " + l.toLanguageTag() + " for decryption UI"); 1724 mountService.setField(StorageManager.SYSTEM_LOCALE_KEY, l.toLanguageTag()); 1725 } catch (RemoteException e) { 1726 Log.e(TAG, "Error storing locale for decryption UI", e); 1727 } 1728 break; 1729 } 1730 case DISMISS_DIALOG_MSG: { 1731 final Dialog d = (Dialog) msg.obj; 1732 d.dismiss(); 1733 break; 1734 } 1735 } 1736 } 1737 }; 1738 1739 static final int COLLECT_PSS_BG_MSG = 1; 1740 1741 final Handler mBgHandler = new Handler(BackgroundThread.getHandler().getLooper()) { 1742 @Override 1743 public void handleMessage(Message msg) { 1744 switch (msg.what) { 1745 case COLLECT_PSS_BG_MSG: { 1746 long start = SystemClock.uptimeMillis(); 1747 MemInfoReader memInfo = null; 1748 synchronized (ActivityManagerService.this) { 1749 if (mFullPssPending) { 1750 mFullPssPending = false; 1751 memInfo = new MemInfoReader(); 1752 } 1753 } 1754 if (memInfo != null) { 1755 updateCpuStatsNow(); 1756 long nativeTotalPss = 0; 1757 synchronized (mProcessCpuTracker) { 1758 final int N = mProcessCpuTracker.countStats(); 1759 for (int j=0; j<N; j++) { 1760 ProcessCpuTracker.Stats st = mProcessCpuTracker.getStats(j); 1761 if (st.vsize <= 0 || st.uid >= Process.FIRST_APPLICATION_UID) { 1762 // This is definitely an application process; skip it. 1763 continue; 1764 } 1765 synchronized (mPidsSelfLocked) { 1766 if (mPidsSelfLocked.indexOfKey(st.pid) >= 0) { 1767 // This is one of our own processes; skip it. 1768 continue; 1769 } 1770 } 1771 nativeTotalPss += Debug.getPss(st.pid, null); 1772 } 1773 } 1774 memInfo.readMemInfo(); 1775 synchronized (ActivityManagerService.this) { 1776 if (DEBUG_PSS) Slog.d(TAG, "Collected native and kernel memory in " 1777 + (SystemClock.uptimeMillis()-start) + "ms"); 1778 mProcessStats.addSysMemUsageLocked(memInfo.getCachedSizeKb(), 1779 memInfo.getFreeSizeKb(), memInfo.getZramTotalSizeKb(), 1780 memInfo.getKernelUsedSizeKb(), nativeTotalPss); 1781 } 1782 } 1783 1784 int i = 0; 1785 int num = 0; 1786 long[] tmp = new long[1]; 1787 do { 1788 ProcessRecord proc; 1789 int procState; 1790 int pid; 1791 synchronized (ActivityManagerService.this) { 1792 if (i >= mPendingPssProcesses.size()) { 1793 if (DEBUG_PSS) Slog.d(TAG, "Collected PSS of " + num + " of " + i 1794 + " processes in " + (SystemClock.uptimeMillis()-start) + "ms"); 1795 mPendingPssProcesses.clear(); 1796 return; 1797 } 1798 proc = mPendingPssProcesses.get(i); 1799 procState = proc.pssProcState; 1800 if (proc.thread != null && procState == proc.setProcState) { 1801 pid = proc.pid; 1802 } else { 1803 proc = null; 1804 pid = 0; 1805 } 1806 i++; 1807 } 1808 if (proc != null) { 1809 long pss = Debug.getPss(pid, tmp); 1810 synchronized (ActivityManagerService.this) { 1811 if (proc.thread != null && proc.setProcState == procState 1812 && proc.pid == pid) { 1813 num++; 1814 proc.lastPssTime = SystemClock.uptimeMillis(); 1815 proc.baseProcessTracker.addPss(pss, tmp[0], true, proc.pkgList); 1816 if (DEBUG_PSS) Slog.d(TAG, "PSS of " + proc.toShortString() 1817 + ": " + pss + " lastPss=" + proc.lastPss 1818 + " state=" + ProcessList.makeProcStateString(procState)); 1819 if (proc.initialIdlePss == 0) { 1820 proc.initialIdlePss = pss; 1821 } 1822 proc.lastPss = pss; 1823 if (procState >= ActivityManager.PROCESS_STATE_HOME) { 1824 proc.lastCachedPss = pss; 1825 } 1826 } 1827 } 1828 } 1829 } while (true); 1830 } 1831 } 1832 } 1833 }; 1834 1835 /** 1836 * Monitor for package changes and update our internal state. 1837 */ 1838 private final PackageMonitor mPackageMonitor = new PackageMonitor() { 1839 @Override 1840 public void onPackageRemoved(String packageName, int uid) { 1841 // Remove all tasks with activities in the specified package from the list of recent tasks 1842 final int eventUserId = getChangingUserId(); 1843 synchronized (ActivityManagerService.this) { 1844 for (int i = mRecentTasks.size() - 1; i >= 0; i--) { 1845 TaskRecord tr = mRecentTasks.get(i); 1846 if (tr.userId != eventUserId) continue; 1847 1848 ComponentName cn = tr.intent.getComponent(); 1849 if (cn != null && cn.getPackageName().equals(packageName)) { 1850 // If the package name matches, remove the task 1851 removeTaskByIdLocked(tr.taskId, true); 1852 } 1853 } 1854 } 1855 } 1856 1857 @Override 1858 public boolean onPackageChanged(String packageName, int uid, String[] components) { 1859 onPackageModified(packageName); 1860 return true; 1861 } 1862 1863 @Override 1864 public void onPackageModified(String packageName) { 1865 final int eventUserId = getChangingUserId(); 1866 final IPackageManager pm = AppGlobals.getPackageManager(); 1867 final ArrayList<Pair<Intent, Integer>> recentTaskIntents = 1868 new ArrayList<Pair<Intent, Integer>>(); 1869 final HashSet<ComponentName> componentsKnownToExist = new HashSet<ComponentName>(); 1870 final ArrayList<Integer> tasksToRemove = new ArrayList<Integer>(); 1871 // Copy the list of recent tasks so that we don't hold onto the lock on 1872 // ActivityManagerService for long periods while checking if components exist. 1873 synchronized (ActivityManagerService.this) { 1874 for (int i = mRecentTasks.size() - 1; i >= 0; i--) { 1875 TaskRecord tr = mRecentTasks.get(i); 1876 if (tr.userId != eventUserId) continue; 1877 1878 recentTaskIntents.add(new Pair<Intent, Integer>(tr.intent, tr.taskId)); 1879 } 1880 } 1881 // Check the recent tasks and filter out all tasks with components that no longer exist. 1882 for (int i = recentTaskIntents.size() - 1; i >= 0; i--) { 1883 Pair<Intent, Integer> p = recentTaskIntents.get(i); 1884 ComponentName cn = p.first.getComponent(); 1885 if (cn != null && cn.getPackageName().equals(packageName)) { 1886 if (componentsKnownToExist.contains(cn)) { 1887 // If we know that the component still exists in the package, then skip 1888 continue; 1889 } 1890 try { 1891 ActivityInfo info = pm.getActivityInfo(cn, 0, eventUserId); 1892 if (info != null) { 1893 componentsKnownToExist.add(cn); 1894 } else { 1895 tasksToRemove.add(p.second); 1896 } 1897 } catch (RemoteException e) { 1898 Log.e(TAG, "Failed to query activity info for component: " + cn, e); 1899 } 1900 } 1901 } 1902 // Prune all the tasks with removed components from the list of recent tasks 1903 synchronized (ActivityManagerService.this) { 1904 for (int i = tasksToRemove.size() - 1; i >= 0; i--) { 1905 removeTaskByIdLocked(tasksToRemove.get(i), false); 1906 } 1907 } 1908 } 1909 1910 @Override 1911 public boolean onHandleForceStop(Intent intent, String[] packages, int uid, boolean doit) { 1912 // Force stop the specified packages 1913 int userId = intent.getIntExtra(Intent.EXTRA_USER_HANDLE, 0); 1914 if (packages != null) { 1915 for (String pkg : packages) { 1916 synchronized (ActivityManagerService.this) { 1917 if (forceStopPackageLocked(pkg, -1, false, false, false, false, false, 1918 userId, "finished booting")) { 1919 return true; 1920 } 1921 } 1922 } 1923 } 1924 return false; 1925 } 1926 }; 1927 1928 public void setSystemProcess() { 1929 try { 1930 ServiceManager.addService(Context.ACTIVITY_SERVICE, this, true); 1931 ServiceManager.addService(ProcessStats.SERVICE_NAME, mProcessStats); 1932 ServiceManager.addService("meminfo", new MemBinder(this)); 1933 ServiceManager.addService("gfxinfo", new GraphicsBinder(this)); 1934 ServiceManager.addService("dbinfo", new DbBinder(this)); 1935 if (MONITOR_CPU_USAGE) { 1936 ServiceManager.addService("cpuinfo", new CpuBinder(this)); 1937 } 1938 ServiceManager.addService("permission", new PermissionController(this)); 1939 1940 ApplicationInfo info = mContext.getPackageManager().getApplicationInfo( 1941 "android", STOCK_PM_FLAGS); 1942 mSystemThread.installSystemApplicationInfo(info, getClass().getClassLoader()); 1943 1944 synchronized (this) { 1945 ProcessRecord app = newProcessRecordLocked(info, info.processName, false, 0); 1946 app.persistent = true; 1947 app.pid = MY_PID; 1948 app.maxAdj = ProcessList.SYSTEM_ADJ; 1949 app.makeActive(mSystemThread.getApplicationThread(), mProcessStats); 1950 mProcessNames.put(app.processName, app.uid, app); 1951 synchronized (mPidsSelfLocked) { 1952 mPidsSelfLocked.put(app.pid, app); 1953 } 1954 updateLruProcessLocked(app, false, null); 1955 updateOomAdjLocked(); 1956 } 1957 } catch (PackageManager.NameNotFoundException e) { 1958 throw new RuntimeException( 1959 "Unable to find android system package", e); 1960 } 1961 } 1962 1963 public void setWindowManager(WindowManagerService wm) { 1964 mWindowManager = wm; 1965 mStackSupervisor.setWindowManager(wm); 1966 } 1967 1968 public void setUsageStatsManager(UsageStatsManagerInternal usageStatsManager) { 1969 mUsageStatsService = usageStatsManager; 1970 } 1971 1972 public void startObservingNativeCrashes() { 1973 final NativeCrashListener ncl = new NativeCrashListener(this); 1974 ncl.start(); 1975 } 1976 1977 public IAppOpsService getAppOpsService() { 1978 return mAppOpsService; 1979 } 1980 1981 static class MemBinder extends Binder { 1982 ActivityManagerService mActivityManagerService; 1983 MemBinder(ActivityManagerService activityManagerService) { 1984 mActivityManagerService = activityManagerService; 1985 } 1986 1987 @Override 1988 protected void dump(FileDescriptor fd, PrintWriter pw, String[] args) { 1989 if (mActivityManagerService.checkCallingPermission(android.Manifest.permission.DUMP) 1990 != PackageManager.PERMISSION_GRANTED) { 1991 pw.println("Permission Denial: can't dump meminfo from from pid=" 1992 + Binder.getCallingPid() + ", uid=" + Binder.getCallingUid() 1993 + " without permission " + android.Manifest.permission.DUMP); 1994 return; 1995 } 1996 1997 mActivityManagerService.dumpApplicationMemoryUsage(fd, pw, " ", args, false, null); 1998 } 1999 } 2000 2001 static class GraphicsBinder extends Binder { 2002 ActivityManagerService mActivityManagerService; 2003 GraphicsBinder(ActivityManagerService activityManagerService) { 2004 mActivityManagerService = activityManagerService; 2005 } 2006 2007 @Override 2008 protected void dump(FileDescriptor fd, PrintWriter pw, String[] args) { 2009 if (mActivityManagerService.checkCallingPermission(android.Manifest.permission.DUMP) 2010 != PackageManager.PERMISSION_GRANTED) { 2011 pw.println("Permission Denial: can't dump gfxinfo from from pid=" 2012 + Binder.getCallingPid() + ", uid=" + Binder.getCallingUid() 2013 + " without permission " + android.Manifest.permission.DUMP); 2014 return; 2015 } 2016 2017 mActivityManagerService.dumpGraphicsHardwareUsage(fd, pw, args); 2018 } 2019 } 2020 2021 static class DbBinder extends Binder { 2022 ActivityManagerService mActivityManagerService; 2023 DbBinder(ActivityManagerService activityManagerService) { 2024 mActivityManagerService = activityManagerService; 2025 } 2026 2027 @Override 2028 protected void dump(FileDescriptor fd, PrintWriter pw, String[] args) { 2029 if (mActivityManagerService.checkCallingPermission(android.Manifest.permission.DUMP) 2030 != PackageManager.PERMISSION_GRANTED) { 2031 pw.println("Permission Denial: can't dump dbinfo from from pid=" 2032 + Binder.getCallingPid() + ", uid=" + Binder.getCallingUid() 2033 + " without permission " + android.Manifest.permission.DUMP); 2034 return; 2035 } 2036 2037 mActivityManagerService.dumpDbInfo(fd, pw, args); 2038 } 2039 } 2040 2041 static class CpuBinder extends Binder { 2042 ActivityManagerService mActivityManagerService; 2043 CpuBinder(ActivityManagerService activityManagerService) { 2044 mActivityManagerService = activityManagerService; 2045 } 2046 2047 @Override 2048 protected void dump(FileDescriptor fd, PrintWriter pw, String[] args) { 2049 if (mActivityManagerService.checkCallingPermission(android.Manifest.permission.DUMP) 2050 != PackageManager.PERMISSION_GRANTED) { 2051 pw.println("Permission Denial: can't dump cpuinfo from from pid=" 2052 + Binder.getCallingPid() + ", uid=" + Binder.getCallingUid() 2053 + " without permission " + android.Manifest.permission.DUMP); 2054 return; 2055 } 2056 2057 synchronized (mActivityManagerService.mProcessCpuTracker) { 2058 pw.print(mActivityManagerService.mProcessCpuTracker.printCurrentLoad()); 2059 pw.print(mActivityManagerService.mProcessCpuTracker.printCurrentState( 2060 SystemClock.uptimeMillis())); 2061 } 2062 } 2063 } 2064 2065 public static final class Lifecycle extends SystemService { 2066 private final ActivityManagerService mService; 2067 2068 public Lifecycle(Context context) { 2069 super(context); 2070 mService = new ActivityManagerService(context); 2071 } 2072 2073 @Override 2074 public void onStart() { 2075 mService.start(); 2076 } 2077 2078 public ActivityManagerService getService() { 2079 return mService; 2080 } 2081 } 2082 2083 // Note: This method is invoked on the main thread but may need to attach various 2084 // handlers to other threads. So take care to be explicit about the looper. 2085 public ActivityManagerService(Context systemContext) { 2086 mContext = systemContext; 2087 mFactoryTest = FactoryTest.getMode(); 2088 mSystemThread = ActivityThread.currentActivityThread(); 2089 2090 Slog.i(TAG, "Memory class: " + ActivityManager.staticGetMemoryClass()); 2091 2092 mHandlerThread = new ServiceThread(TAG, 2093 android.os.Process.THREAD_PRIORITY_FOREGROUND, false /*allowIo*/); 2094 mHandlerThread.start(); 2095 mHandler = new MainHandler(mHandlerThread.getLooper()); 2096 2097 mFgBroadcastQueue = new BroadcastQueue(this, mHandler, 2098 "foreground", BROADCAST_FG_TIMEOUT, false); 2099 mBgBroadcastQueue = new BroadcastQueue(this, mHandler, 2100 "background", BROADCAST_BG_TIMEOUT, true); 2101 mBroadcastQueues[0] = mFgBroadcastQueue; 2102 mBroadcastQueues[1] = mBgBroadcastQueue; 2103 2104 mServices = new ActiveServices(this); 2105 mProviderMap = new ProviderMap(this); 2106 2107 // TODO: Move creation of battery stats service outside of activity manager service. 2108 File dataDir = Environment.getDataDirectory(); 2109 File systemDir = new File(dataDir, "system"); 2110 systemDir.mkdirs(); 2111 mBatteryStatsService = new BatteryStatsService(systemDir, mHandler); 2112 mBatteryStatsService.getActiveStatistics().readLocked(); 2113 mBatteryStatsService.getActiveStatistics().writeAsyncLocked(); 2114 mOnBattery = DEBUG_POWER ? true 2115 : mBatteryStatsService.getActiveStatistics().getIsOnBattery(); 2116 mBatteryStatsService.getActiveStatistics().setCallback(this); 2117 2118 mProcessStats = new ProcessStatsService(this, new File(systemDir, "procstats")); 2119 2120 mAppOpsService = new AppOpsService(new File(systemDir, "appops.xml"), mHandler); 2121 2122 mGrantFile = new AtomicFile(new File(systemDir, "urigrants.xml")); 2123 2124 // User 0 is the first and only user that runs at boot. 2125 mStartedUsers.put(0, new UserStartedState(new UserHandle(0), true)); 2126 mUserLru.add(Integer.valueOf(0)); 2127 updateStartedUserArrayLocked(); 2128 2129 GL_ES_VERSION = SystemProperties.getInt("ro.opengles.version", 2130 ConfigurationInfo.GL_ES_VERSION_UNDEFINED); 2131 2132 mConfiguration.setToDefaults(); 2133 mConfiguration.setLocale(Locale.getDefault()); 2134 2135 mConfigurationSeq = mConfiguration.seq = 1; 2136 mProcessCpuTracker.init(); 2137 2138 mCompatModePackages = new CompatModePackages(this, systemDir, mHandler); 2139 mIntentFirewall = new IntentFirewall(new IntentFirewallInterface(), mHandler); 2140 mStackSupervisor = new ActivityStackSupervisor(this); 2141 mTaskPersister = new TaskPersister(systemDir, mStackSupervisor); 2142 2143 mProcessCpuThread = new Thread("CpuTracker") { 2144 @Override 2145 public void run() { 2146 while (true) { 2147 try { 2148 try { 2149 synchronized(this) { 2150 final long now = SystemClock.uptimeMillis(); 2151 long nextCpuDelay = (mLastCpuTime.get()+MONITOR_CPU_MAX_TIME)-now; 2152 long nextWriteDelay = (mLastWriteTime+BATTERY_STATS_TIME)-now; 2153 //Slog.i(TAG, "Cpu delay=" + nextCpuDelay 2154 // + ", write delay=" + nextWriteDelay); 2155 if (nextWriteDelay < nextCpuDelay) { 2156 nextCpuDelay = nextWriteDelay; 2157 } 2158 if (nextCpuDelay > 0) { 2159 mProcessCpuMutexFree.set(true); 2160 this.wait(nextCpuDelay); 2161 } 2162 } 2163 } catch (InterruptedException e) { 2164 } 2165 updateCpuStatsNow(); 2166 } catch (Exception e) { 2167 Slog.e(TAG, "Unexpected exception collecting process stats", e); 2168 } 2169 } 2170 } 2171 }; 2172 2173 Watchdog.getInstance().addMonitor(this); 2174 Watchdog.getInstance().addThread(mHandler); 2175 } 2176 2177 public void setSystemServiceManager(SystemServiceManager mgr) { 2178 mSystemServiceManager = mgr; 2179 } 2180 2181 public void setInstaller(Installer installer) { 2182 mInstaller = installer; 2183 } 2184 2185 private void start() { 2186 Process.removeAllProcessGroups(); 2187 mProcessCpuThread.start(); 2188 2189 mBatteryStatsService.publish(mContext); 2190 mAppOpsService.publish(mContext); 2191 Slog.d("AppOps", "AppOpsService published"); 2192 LocalServices.addService(ActivityManagerInternal.class, new LocalService()); 2193 } 2194 2195 public void initPowerManagement() { 2196 mStackSupervisor.initPowerManagement(); 2197 mBatteryStatsService.initPowerManagement(); 2198 } 2199 2200 @Override 2201 public boolean onTransact(int code, Parcel data, Parcel reply, int flags) 2202 throws RemoteException { 2203 if (code == SYSPROPS_TRANSACTION) { 2204 // We need to tell all apps about the system property change. 2205 ArrayList<IBinder> procs = new ArrayList<IBinder>(); 2206 synchronized(this) { 2207 final int NP = mProcessNames.getMap().size(); 2208 for (int ip=0; ip<NP; ip++) { 2209 SparseArray<ProcessRecord> apps = mProcessNames.getMap().valueAt(ip); 2210 final int NA = apps.size(); 2211 for (int ia=0; ia<NA; ia++) { 2212 ProcessRecord app = apps.valueAt(ia); 2213 if (app.thread != null) { 2214 procs.add(app.thread.asBinder()); 2215 } 2216 } 2217 } 2218 } 2219 2220 int N = procs.size(); 2221 for (int i=0; i<N; i++) { 2222 Parcel data2 = Parcel.obtain(); 2223 try { 2224 procs.get(i).transact(IBinder.SYSPROPS_TRANSACTION, data2, null, 0); 2225 } catch (RemoteException e) { 2226 } 2227 data2.recycle(); 2228 } 2229 } 2230 try { 2231 return super.onTransact(code, data, reply, flags); 2232 } catch (RuntimeException e) { 2233 // The activity manager only throws security exceptions, so let's 2234 // log all others. 2235 if (!(e instanceof SecurityException)) { 2236 Slog.wtf(TAG, "Activity Manager Crash", e); 2237 } 2238 throw e; 2239 } 2240 } 2241 2242 void updateCpuStats() { 2243 final long now = SystemClock.uptimeMillis(); 2244 if (mLastCpuTime.get() >= now - MONITOR_CPU_MIN_TIME) { 2245 return; 2246 } 2247 if (mProcessCpuMutexFree.compareAndSet(true, false)) { 2248 synchronized (mProcessCpuThread) { 2249 mProcessCpuThread.notify(); 2250 } 2251 } 2252 } 2253 2254 void updateCpuStatsNow() { 2255 synchronized (mProcessCpuTracker) { 2256 mProcessCpuMutexFree.set(false); 2257 final long now = SystemClock.uptimeMillis(); 2258 boolean haveNewCpuStats = false; 2259 2260 if (MONITOR_CPU_USAGE && 2261 mLastCpuTime.get() < (now-MONITOR_CPU_MIN_TIME)) { 2262 mLastCpuTime.set(now); 2263 haveNewCpuStats = true; 2264 mProcessCpuTracker.update(); 2265 //Slog.i(TAG, mProcessCpu.printCurrentState()); 2266 //Slog.i(TAG, "Total CPU usage: " 2267 // + mProcessCpu.getTotalCpuPercent() + "%"); 2268 2269 // Slog the cpu usage if the property is set. 2270 if ("true".equals(SystemProperties.get("events.cpu"))) { 2271 int user = mProcessCpuTracker.getLastUserTime(); 2272 int system = mProcessCpuTracker.getLastSystemTime(); 2273 int iowait = mProcessCpuTracker.getLastIoWaitTime(); 2274 int irq = mProcessCpuTracker.getLastIrqTime(); 2275 int softIrq = mProcessCpuTracker.getLastSoftIrqTime(); 2276 int idle = mProcessCpuTracker.getLastIdleTime(); 2277 2278 int total = user + system + iowait + irq + softIrq + idle; 2279 if (total == 0) total = 1; 2280 2281 EventLog.writeEvent(EventLogTags.CPU, 2282 ((user+system+iowait+irq+softIrq) * 100) / total, 2283 (user * 100) / total, 2284 (system * 100) / total, 2285 (iowait * 100) / total, 2286 (irq * 100) / total, 2287 (softIrq * 100) / total); 2288 } 2289 } 2290 2291 long[] cpuSpeedTimes = mProcessCpuTracker.getLastCpuSpeedTimes(); 2292 final BatteryStatsImpl bstats = mBatteryStatsService.getActiveStatistics(); 2293 synchronized(bstats) { 2294 synchronized(mPidsSelfLocked) { 2295 if (haveNewCpuStats) { 2296 if (mOnBattery) { 2297 int perc = bstats.startAddingCpuLocked(); 2298 int totalUTime = 0; 2299 int totalSTime = 0; 2300 final int N = mProcessCpuTracker.countStats(); 2301 for (int i=0; i<N; i++) { 2302 ProcessCpuTracker.Stats st = mProcessCpuTracker.getStats(i); 2303 if (!st.working) { 2304 continue; 2305 } 2306 ProcessRecord pr = mPidsSelfLocked.get(st.pid); 2307 int otherUTime = (st.rel_utime*perc)/100; 2308 int otherSTime = (st.rel_stime*perc)/100; 2309 totalUTime += otherUTime; 2310 totalSTime += otherSTime; 2311 if (pr != null) { 2312 BatteryStatsImpl.Uid.Proc ps = pr.curProcBatteryStats; 2313 if (ps == null || !ps.isActive()) { 2314 pr.curProcBatteryStats = ps = bstats.getProcessStatsLocked( 2315 pr.info.uid, pr.processName); 2316 } 2317 ps.addCpuTimeLocked(st.rel_utime-otherUTime, 2318 st.rel_stime-otherSTime); 2319 ps.addSpeedStepTimes(cpuSpeedTimes); 2320 pr.curCpuTime += (st.rel_utime+st.rel_stime) * 10; 2321 } else { 2322 BatteryStatsImpl.Uid.Proc ps = st.batteryStats; 2323 if (ps == null || !ps.isActive()) { 2324 st.batteryStats = ps = bstats.getProcessStatsLocked( 2325 bstats.mapUid(st.uid), st.name); 2326 } 2327 ps.addCpuTimeLocked(st.rel_utime-otherUTime, 2328 st.rel_stime-otherSTime); 2329 ps.addSpeedStepTimes(cpuSpeedTimes); 2330 } 2331 } 2332 bstats.finishAddingCpuLocked(perc, totalUTime, 2333 totalSTime, cpuSpeedTimes); 2334 } 2335 } 2336 } 2337 2338 if (mLastWriteTime < (now-BATTERY_STATS_TIME)) { 2339 mLastWriteTime = now; 2340 mBatteryStatsService.getActiveStatistics().writeAsyncLocked(); 2341 } 2342 } 2343 } 2344 } 2345 2346 @Override 2347 public void batteryNeedsCpuUpdate() { 2348 updateCpuStatsNow(); 2349 } 2350 2351 @Override 2352 public void batteryPowerChanged(boolean onBattery) { 2353 // When plugging in, update the CPU stats first before changing 2354 // the plug state. 2355 updateCpuStatsNow(); 2356 synchronized (this) { 2357 synchronized(mPidsSelfLocked) { 2358 mOnBattery = DEBUG_POWER ? true : onBattery; 2359 } 2360 } 2361 } 2362 2363 /** 2364 * Initialize the application bind args. These are passed to each 2365 * process when the bindApplication() IPC is sent to the process. They're 2366 * lazily setup to make sure the services are running when they're asked for. 2367 */ 2368 private HashMap<String, IBinder> getCommonServicesLocked() { 2369 if (mAppBindArgs == null) { 2370 mAppBindArgs = new HashMap<String, IBinder>(); 2371 2372 // Setup the application init args 2373 mAppBindArgs.put("package", ServiceManager.getService("package")); 2374 mAppBindArgs.put("window", ServiceManager.getService("window")); 2375 mAppBindArgs.put(Context.ALARM_SERVICE, 2376 ServiceManager.getService(Context.ALARM_SERVICE)); 2377 } 2378 return mAppBindArgs; 2379 } 2380 2381 final void setFocusedActivityLocked(ActivityRecord r) { 2382 if (mFocusedActivity != r) { 2383 if (DEBUG_FOCUS) Slog.d(TAG, "setFocusedActivityLocked: r=" + r); 2384 mFocusedActivity = r; 2385 if (r.task != null && r.task.voiceInteractor != null) { 2386 startRunningVoiceLocked(); 2387 } else { 2388 finishRunningVoiceLocked(); 2389 } 2390 mStackSupervisor.setFocusedStack(r); 2391 if (r != null) { 2392 mWindowManager.setFocusedApp(r.appToken, true); 2393 } 2394 applyUpdateLockStateLocked(r); 2395 } 2396 } 2397 2398 final void clearFocusedActivity(ActivityRecord r) { 2399 if (mFocusedActivity == r) { 2400 mFocusedActivity = null; 2401 } 2402 } 2403 2404 @Override 2405 public void setFocusedStack(int stackId) { 2406 if (DEBUG_FOCUS) Slog.d(TAG, "setFocusedStack: stackId=" + stackId); 2407 synchronized (ActivityManagerService.this) { 2408 ActivityStack stack = mStackSupervisor.getStack(stackId); 2409 if (stack != null) { 2410 ActivityRecord r = stack.topRunningActivityLocked(null); 2411 if (r != null) { 2412 setFocusedActivityLocked(r); 2413 } 2414 } 2415 } 2416 } 2417 2418 @Override 2419 public void notifyActivityDrawn(IBinder token) { 2420 if (DEBUG_VISBILITY) Slog.d(TAG, "notifyActivityDrawn: token=" + token); 2421 synchronized (this) { 2422 ActivityRecord r= mStackSupervisor.isInAnyStackLocked(token); 2423 if (r != null) { 2424 r.task.stack.notifyActivityDrawnLocked(r); 2425 } 2426 } 2427 } 2428 2429 final void applyUpdateLockStateLocked(ActivityRecord r) { 2430 // Modifications to the UpdateLock state are done on our handler, outside 2431 // the activity manager's locks. The new state is determined based on the 2432 // state *now* of the relevant activity record. The object is passed to 2433 // the handler solely for logging detail, not to be consulted/modified. 2434 final boolean nextState = r != null && r.immersive; 2435 mHandler.sendMessage( 2436 mHandler.obtainMessage(IMMERSIVE_MODE_LOCK_MSG, (nextState) ? 1 : 0, 0, r)); 2437 } 2438 2439 final void showAskCompatModeDialogLocked(ActivityRecord r) { 2440 Message msg = Message.obtain(); 2441 msg.what = SHOW_COMPAT_MODE_DIALOG_MSG; 2442 msg.obj = r.task.askedCompatMode ? null : r; 2443 mHandler.sendMessage(msg); 2444 } 2445 2446 private final int updateLruProcessInternalLocked(ProcessRecord app, long now, int index, 2447 String what, Object obj, ProcessRecord srcApp) { 2448 app.lastActivityTime = now; 2449 2450 if (app.activities.size() > 0) { 2451 // Don't want to touch dependent processes that are hosting activities. 2452 return index; 2453 } 2454 2455 int lrui = mLruProcesses.lastIndexOf(app); 2456 if (lrui < 0) { 2457 Slog.wtf(TAG, "Adding dependent process " + app + " not on LRU list: " 2458 + what + " " + obj + " from " + srcApp); 2459 return index; 2460 } 2461 2462 if (lrui >= index) { 2463 // Don't want to cause this to move dependent processes *back* in the 2464 // list as if they were less frequently used. 2465 return index; 2466 } 2467 2468 if (lrui >= mLruProcessActivityStart) { 2469 // Don't want to touch dependent processes that are hosting activities. 2470 return index; 2471 } 2472 2473 mLruProcesses.remove(lrui); 2474 if (index > 0) { 2475 index--; 2476 } 2477 if (DEBUG_LRU) Slog.d(TAG, "Moving dep from " + lrui + " to " + index 2478 + " in LRU list: " + app); 2479 mLruProcesses.add(index, app); 2480 return index; 2481 } 2482 2483 final void removeLruProcessLocked(ProcessRecord app) { 2484 int lrui = mLruProcesses.lastIndexOf(app); 2485 if (lrui >= 0) { 2486 if (!app.killed) { 2487 Slog.wtfStack(TAG, "Removing process that hasn't been killed: " + app); 2488 Process.killProcessQuiet(app.pid); 2489 Process.killProcessGroup(app.info.uid, app.pid); 2490 } 2491 if (lrui <= mLruProcessActivityStart) { 2492 mLruProcessActivityStart--; 2493 } 2494 if (lrui <= mLruProcessServiceStart) { 2495 mLruProcessServiceStart--; 2496 } 2497 mLruProcesses.remove(lrui); 2498 } 2499 } 2500 2501 final void updateLruProcessLocked(ProcessRecord app, boolean activityChange, 2502 ProcessRecord client) { 2503 final boolean hasActivity = app.activities.size() > 0 || app.hasClientActivities 2504 || app.treatLikeActivity; 2505 final boolean hasService = false; // not impl yet. app.services.size() > 0; 2506 if (!activityChange && hasActivity) { 2507 // The process has activities, so we are only allowing activity-based adjustments 2508 // to move it. It should be kept in the front of the list with other 2509 // processes that have activities, and we don't want those to change their 2510 // order except due to activity operations. 2511 return; 2512 } 2513 2514 mLruSeq++; 2515 final long now = SystemClock.uptimeMillis(); 2516 app.lastActivityTime = now; 2517 2518 // First a quick reject: if the app is already at the position we will 2519 // put it, then there is nothing to do. 2520 if (hasActivity) { 2521 final int N = mLruProcesses.size(); 2522 if (N > 0 && mLruProcesses.get(N-1) == app) { 2523 if (DEBUG_LRU) Slog.d(TAG, "Not moving, already top activity: " + app); 2524 return; 2525 } 2526 } else { 2527 if (mLruProcessServiceStart > 0 2528 && mLruProcesses.get(mLruProcessServiceStart-1) == app) { 2529 if (DEBUG_LRU) Slog.d(TAG, "Not moving, already top other: " + app); 2530 return; 2531 } 2532 } 2533 2534 int lrui = mLruProcesses.lastIndexOf(app); 2535 2536 if (app.persistent && lrui >= 0) { 2537 // We don't care about the position of persistent processes, as long as 2538 // they are in the list. 2539 if (DEBUG_LRU) Slog.d(TAG, "Not moving, persistent: " + app); 2540 return; 2541 } 2542 2543 /* In progress: compute new position first, so we can avoid doing work 2544 if the process is not actually going to move. Not yet working. 2545 int addIndex; 2546 int nextIndex; 2547 boolean inActivity = false, inService = false; 2548 if (hasActivity) { 2549 // Process has activities, put it at the very tipsy-top. 2550 addIndex = mLruProcesses.size(); 2551 nextIndex = mLruProcessServiceStart; 2552 inActivity = true; 2553 } else if (hasService) { 2554 // Process has services, put it at the top of the service list. 2555 addIndex = mLruProcessActivityStart; 2556 nextIndex = mLruProcessServiceStart; 2557 inActivity = true; 2558 inService = true; 2559 } else { 2560 // Process not otherwise of interest, it goes to the top of the non-service area. 2561 addIndex = mLruProcessServiceStart; 2562 if (client != null) { 2563 int clientIndex = mLruProcesses.lastIndexOf(client); 2564 if (clientIndex < 0) Slog.d(TAG, "Unknown client " + client + " when updating " 2565 + app); 2566 if (clientIndex >= 0 && addIndex > clientIndex) { 2567 addIndex = clientIndex; 2568 } 2569 } 2570 nextIndex = addIndex > 0 ? addIndex-1 : addIndex; 2571 } 2572 2573 Slog.d(TAG, "Update LRU at " + lrui + " to " + addIndex + " (act=" 2574 + mLruProcessActivityStart + "): " + app); 2575 */ 2576 2577 if (lrui >= 0) { 2578 if (lrui < mLruProcessActivityStart) { 2579 mLruProcessActivityStart--; 2580 } 2581 if (lrui < mLruProcessServiceStart) { 2582 mLruProcessServiceStart--; 2583 } 2584 /* 2585 if (addIndex > lrui) { 2586 addIndex--; 2587 } 2588 if (nextIndex > lrui) { 2589 nextIndex--; 2590 } 2591 */ 2592 mLruProcesses.remove(lrui); 2593 } 2594 2595 /* 2596 mLruProcesses.add(addIndex, app); 2597 if (inActivity) { 2598 mLruProcessActivityStart++; 2599 } 2600 if (inService) { 2601 mLruProcessActivityStart++; 2602 } 2603 */ 2604 2605 int nextIndex; 2606 if (hasActivity) { 2607 final int N = mLruProcesses.size(); 2608 if (app.activities.size() == 0 && mLruProcessActivityStart < (N-1)) { 2609 // Process doesn't have activities, but has clients with 2610 // activities... move it up, but one below the top (the top 2611 // should always have a real activity). 2612 if (DEBUG_LRU) Slog.d(TAG, "Adding to second-top of LRU activity list: " + app); 2613 mLruProcesses.add(N-1, app); 2614 // To keep it from spamming the LRU list (by making a bunch of clients), 2615 // we will push down any other entries owned by the app. 2616 final int uid = app.info.uid; 2617 for (int i=N-2; i>mLruProcessActivityStart; i--) { 2618 ProcessRecord subProc = mLruProcesses.get(i); 2619 if (subProc.info.uid == uid) { 2620 // We want to push this one down the list. If the process after 2621 // it is for the same uid, however, don't do so, because we don't 2622 // want them internally to be re-ordered. 2623 if (mLruProcesses.get(i-1).info.uid != uid) { 2624 if (DEBUG_LRU) Slog.d(TAG, "Pushing uid " + uid + " swapping at " + i 2625 + ": " + mLruProcesses.get(i) + " : " + mLruProcesses.get(i-1)); 2626 ProcessRecord tmp = mLruProcesses.get(i); 2627 mLruProcesses.set(i, mLruProcesses.get(i-1)); 2628 mLruProcesses.set(i-1, tmp); 2629 i--; 2630 } 2631 } else { 2632 // A gap, we can stop here. 2633 break; 2634 } 2635 } 2636 } else { 2637 // Process has activities, put it at the very tipsy-top. 2638 if (DEBUG_LRU) Slog.d(TAG, "Adding to top of LRU activity list: " + app); 2639 mLruProcesses.add(app); 2640 } 2641 nextIndex = mLruProcessServiceStart; 2642 } else if (hasService) { 2643 // Process has services, put it at the top of the service list. 2644 if (DEBUG_LRU) Slog.d(TAG, "Adding to top of LRU service list: " + app); 2645 mLruProcesses.add(mLruProcessActivityStart, app); 2646 nextIndex = mLruProcessServiceStart; 2647 mLruProcessActivityStart++; 2648 } else { 2649 // Process not otherwise of interest, it goes to the top of the non-service area. 2650 int index = mLruProcessServiceStart; 2651 if (client != null) { 2652 // If there is a client, don't allow the process to be moved up higher 2653 // in the list than that client. 2654 int clientIndex = mLruProcesses.lastIndexOf(client); 2655 if (DEBUG_LRU && clientIndex < 0) Slog.d(TAG, "Unknown client " + client 2656 + " when updating " + app); 2657 if (clientIndex <= lrui) { 2658 // Don't allow the client index restriction to push it down farther in the 2659 // list than it already is. 2660 clientIndex = lrui; 2661 } 2662 if (clientIndex >= 0 && index > clientIndex) { 2663 index = clientIndex; 2664 } 2665 } 2666 if (DEBUG_LRU) Slog.d(TAG, "Adding at " + index + " of LRU list: " + app); 2667 mLruProcesses.add(index, app); 2668 nextIndex = index-1; 2669 mLruProcessActivityStart++; 2670 mLruProcessServiceStart++; 2671 } 2672 2673 // If the app is currently using a content provider or service, 2674 // bump those processes as well. 2675 for (int j=app.connections.size()-1; j>=0; j--) { 2676 ConnectionRecord cr = app.connections.valueAt(j); 2677 if (cr.binding != null && !cr.serviceDead && cr.binding.service != null 2678 && cr.binding.service.app != null 2679 && cr.binding.service.app.lruSeq != mLruSeq 2680 && !cr.binding.service.app.persistent) { 2681 nextIndex = updateLruProcessInternalLocked(cr.binding.service.app, now, nextIndex, 2682 "service connection", cr, app); 2683 } 2684 } 2685 for (int j=app.conProviders.size()-1; j>=0; j--) { 2686 ContentProviderRecord cpr = app.conProviders.get(j).provider; 2687 if (cpr.proc != null && cpr.proc.lruSeq != mLruSeq && !cpr.proc.persistent) { 2688 nextIndex = updateLruProcessInternalLocked(cpr.proc, now, nextIndex, 2689 "provider reference", cpr, app); 2690 } 2691 } 2692 } 2693 2694 final ProcessRecord getProcessRecordLocked(String processName, int uid, boolean keepIfLarge) { 2695 if (uid == Process.SYSTEM_UID) { 2696 // The system gets to run in any process. If there are multiple 2697 // processes with the same uid, just pick the first (this 2698 // should never happen). 2699 SparseArray<ProcessRecord> procs = mProcessNames.getMap().get(processName); 2700 if (procs == null) return null; 2701 final int N = procs.size(); 2702 for (int i = 0; i < N; i++) { 2703 if (UserHandle.isSameUser(procs.keyAt(i), uid)) return procs.valueAt(i); 2704 } 2705 } 2706 ProcessRecord proc = mProcessNames.get(processName, uid); 2707 if (false && proc != null && !keepIfLarge 2708 && proc.setProcState >= ActivityManager.PROCESS_STATE_CACHED_EMPTY 2709 && proc.lastCachedPss >= 4000) { 2710 // Turn this condition on to cause killing to happen regularly, for testing. 2711 if (proc.baseProcessTracker != null) { 2712 proc.baseProcessTracker.reportCachedKill(proc.pkgList, proc.lastCachedPss); 2713 } 2714 proc.kill(Long.toString(proc.lastCachedPss) + "k from cached", true); 2715 } else if (proc != null && !keepIfLarge 2716 && mLastMemoryLevel > ProcessStats.ADJ_MEM_FACTOR_NORMAL 2717 && proc.setProcState >= ActivityManager.PROCESS_STATE_CACHED_EMPTY) { 2718 if (DEBUG_PSS) Slog.d(TAG, "May not keep " + proc + ": pss=" + proc.lastCachedPss); 2719 if (proc.lastCachedPss >= mProcessList.getCachedRestoreThresholdKb()) { 2720 if (proc.baseProcessTracker != null) { 2721 proc.baseProcessTracker.reportCachedKill(proc.pkgList, proc.lastCachedPss); 2722 } 2723 proc.kill(Long.toString(proc.lastCachedPss) + "k from cached", true); 2724 } 2725 } 2726 return proc; 2727 } 2728 2729 void ensurePackageDexOpt(String packageName) { 2730 IPackageManager pm = AppGlobals.getPackageManager(); 2731 try { 2732 if (pm.performDexOptIfNeeded(packageName, null /* instruction set */)) { 2733 mDidDexOpt = true; 2734 } 2735 } catch (RemoteException e) { 2736 } 2737 } 2738 2739 boolean isNextTransitionForward() { 2740 int transit = mWindowManager.getPendingAppTransition(); 2741 return transit == AppTransition.TRANSIT_ACTIVITY_OPEN 2742 || transit == AppTransition.TRANSIT_TASK_OPEN 2743 || transit == AppTransition.TRANSIT_TASK_TO_FRONT; 2744 } 2745 2746 int startIsolatedProcess(String entryPoint, String[] entryPointArgs, 2747 String processName, String abiOverride, int uid, Runnable crashHandler) { 2748 synchronized(this) { 2749 ApplicationInfo info = new ApplicationInfo(); 2750 // In general the ApplicationInfo.uid isn't neccesarily equal to ProcessRecord.uid. 2751 // For isolated processes, the former contains the parent's uid and the latter the 2752 // actual uid of the isolated process. 2753 // In the special case introduced by this method (which is, starting an isolated 2754 // process directly from the SystemServer without an actual parent app process) the 2755 // closest thing to a parent's uid is SYSTEM_UID. 2756 // The only important thing here is to keep AI.uid != PR.uid, in order to trigger 2757 // the |isolated| logic in the ProcessRecord constructor. 2758 info.uid = Process.SYSTEM_UID; 2759 info.processName = processName; 2760 info.className = entryPoint; 2761 info.packageName = "android"; 2762 ProcessRecord proc = startProcessLocked(processName, info /* info */, 2763 false /* knownToBeDead */, 0 /* intentFlags */, "" /* hostingType */, 2764 null /* hostingName */, true /* allowWhileBooting */, true /* isolated */, 2765 uid, true /* keepIfLarge */, abiOverride, entryPoint, entryPointArgs, 2766 crashHandler); 2767 return proc != null ? proc.pid : 0; 2768 } 2769 } 2770 2771 final ProcessRecord startProcessLocked(String processName, 2772 ApplicationInfo info, boolean knownToBeDead, int intentFlags, 2773 String hostingType, ComponentName hostingName, boolean allowWhileBooting, 2774 boolean isolated, boolean keepIfLarge) { 2775 return startProcessLocked(processName, info, knownToBeDead, intentFlags, hostingType, 2776 hostingName, allowWhileBooting, isolated, 0 /* isolatedUid */, keepIfLarge, 2777 null /* ABI override */, null /* entryPoint */, null /* entryPointArgs */, 2778 null /* crashHandler */); 2779 } 2780 2781 final ProcessRecord startProcessLocked(String processName, ApplicationInfo info, 2782 boolean knownToBeDead, int intentFlags, String hostingType, ComponentName hostingName, 2783 boolean allowWhileBooting, boolean isolated, int isolatedUid, boolean keepIfLarge, 2784 String abiOverride, String entryPoint, String[] entryPointArgs, Runnable crashHandler) { 2785 long startTime = SystemClock.elapsedRealtime(); 2786 ProcessRecord app; 2787 if (!isolated) { 2788 app = getProcessRecordLocked(processName, info.uid, keepIfLarge); 2789 checkTime(startTime, "startProcess: after getProcessRecord"); 2790 } else { 2791 // If this is an isolated process, it can't re-use an existing process. 2792 app = null; 2793 } 2794 // We don't have to do anything more if: 2795 // (1) There is an existing application record; and 2796 // (2) The caller doesn't think it is dead, OR there is no thread 2797 // object attached to it so we know it couldn't have crashed; and 2798 // (3) There is a pid assigned to it, so it is either starting or 2799 // already running. 2800 if (DEBUG_PROCESSES) Slog.v(TAG, "startProcess: name=" + processName 2801 + " app=" + app + " knownToBeDead=" + knownToBeDead 2802 + " thread=" + (app != null ? app.thread : null) 2803 + " pid=" + (app != null ? app.pid : -1)); 2804 if (app != null && app.pid > 0) { 2805 if (!knownToBeDead || app.thread == null) { 2806 // We already have the app running, or are waiting for it to 2807 // come up (we have a pid but not yet its thread), so keep it. 2808 if (DEBUG_PROCESSES) Slog.v(TAG, "App already running: " + app); 2809 // If this is a new package in the process, add the package to the list 2810 app.addPackage(info.packageName, info.versionCode, mProcessStats); 2811 checkTime(startTime, "startProcess: done, added package to proc"); 2812 return app; 2813 } 2814 2815 // An application record is attached to a previous process, 2816 // clean it up now. 2817 if (DEBUG_PROCESSES || DEBUG_CLEANUP) Slog.v(TAG, "App died: " + app); 2818 checkTime(startTime, "startProcess: bad proc running, killing"); 2819 Process.killProcessGroup(app.info.uid, app.pid); 2820 handleAppDiedLocked(app, true, true); 2821 checkTime(startTime, "startProcess: done killing old proc"); 2822 } 2823 2824 String hostingNameStr = hostingName != null 2825 ? hostingName.flattenToShortString() : null; 2826 2827 if (!isolated) { 2828 if ((intentFlags&Intent.FLAG_FROM_BACKGROUND) != 0) { 2829 // If we are in the background, then check to see if this process 2830 // is bad. If so, we will just silently fail. 2831 if (mBadProcesses.get(info.processName, info.uid) != null) { 2832 if (DEBUG_PROCESSES) Slog.v(TAG, "Bad process: " + info.uid 2833 + "/" + info.processName); 2834 return null; 2835 } 2836 } else { 2837 // When the user is explicitly starting a process, then clear its 2838 // crash count so that we won't make it bad until they see at 2839 // least one crash dialog again, and make the process good again 2840 // if it had been bad. 2841 if (DEBUG_PROCESSES) Slog.v(TAG, "Clearing bad process: " + info.uid 2842 + "/" + info.processName); 2843 mProcessCrashTimes.remove(info.processName, info.uid); 2844 if (mBadProcesses.get(info.processName, info.uid) != null) { 2845 EventLog.writeEvent(EventLogTags.AM_PROC_GOOD, 2846 UserHandle.getUserId(info.uid), info.uid, 2847 info.processName); 2848 mBadProcesses.remove(info.processName, info.uid); 2849 if (app != null) { 2850 app.bad = false; 2851 } 2852 } 2853 } 2854 } 2855 2856 if (app == null) { 2857 checkTime(startTime, "startProcess: creating new process record"); 2858 app = newProcessRecordLocked(info, processName, isolated, isolatedUid); 2859 app.crashHandler = crashHandler; 2860 if (app == null) { 2861 Slog.w(TAG, "Failed making new process record for " 2862 + processName + "/" + info.uid + " isolated=" + isolated); 2863 return null; 2864 } 2865 mProcessNames.put(processName, app.uid, app); 2866 if (isolated) { 2867 mIsolatedProcesses.put(app.uid, app); 2868 } 2869 checkTime(startTime, "startProcess: done creating new process record"); 2870 } else { 2871 // If this is a new package in the process, add the package to the list 2872 app.addPackage(info.packageName, info.versionCode, mProcessStats); 2873 checkTime(startTime, "startProcess: added package to existing proc"); 2874 } 2875 2876 // If the system is not ready yet, then hold off on starting this 2877 // process until it is. 2878 if (!mProcessesReady 2879 && !isAllowedWhileBooting(info) 2880 && !allowWhileBooting) { 2881 if (!mProcessesOnHold.contains(app)) { 2882 mProcessesOnHold.add(app); 2883 } 2884 if (DEBUG_PROCESSES) Slog.v(TAG, "System not ready, putting on hold: " + app); 2885 checkTime(startTime, "startProcess: returning with proc on hold"); 2886 return app; 2887 } 2888 2889 checkTime(startTime, "startProcess: stepping in to startProcess"); 2890 startProcessLocked( 2891 app, hostingType, hostingNameStr, abiOverride, entryPoint, entryPointArgs); 2892 checkTime(startTime, "startProcess: done starting proc!"); 2893 return (app.pid != 0) ? app : null; 2894 } 2895 2896 boolean isAllowedWhileBooting(ApplicationInfo ai) { 2897 return (ai.flags&ApplicationInfo.FLAG_PERSISTENT) != 0; 2898 } 2899 2900 private final void startProcessLocked(ProcessRecord app, 2901 String hostingType, String hostingNameStr) { 2902 startProcessLocked(app, hostingType, hostingNameStr, null /* abiOverride */, 2903 null /* entryPoint */, null /* entryPointArgs */); 2904 } 2905 2906 private final void startProcessLocked(ProcessRecord app, String hostingType, 2907 String hostingNameStr, String abiOverride, String entryPoint, String[] entryPointArgs) { 2908 long startTime = SystemClock.elapsedRealtime(); 2909 if (app.pid > 0 && app.pid != MY_PID) { 2910 checkTime(startTime, "startProcess: removing from pids map"); 2911 synchronized (mPidsSelfLocked) { 2912 mPidsSelfLocked.remove(app.pid); 2913 mHandler.removeMessages(PROC_START_TIMEOUT_MSG, app); 2914 } 2915 checkTime(startTime, "startProcess: done removing from pids map"); 2916 app.setPid(0); 2917 } 2918 2919 if (DEBUG_PROCESSES && mProcessesOnHold.contains(app)) Slog.v(TAG, 2920 "startProcessLocked removing on hold: " + app); 2921 mProcessesOnHold.remove(app); 2922 2923 checkTime(startTime, "startProcess: starting to update cpu stats"); 2924 updateCpuStats(); 2925 checkTime(startTime, "startProcess: done updating cpu stats"); 2926 2927 try { 2928 int uid = app.uid; 2929 2930 int[] gids = null; 2931 int mountExternal = Zygote.MOUNT_EXTERNAL_NONE; 2932 if (!app.isolated) { 2933 int[] permGids = null; 2934 try { 2935 checkTime(startTime, "startProcess: getting gids from package manager"); 2936 final PackageManager pm = mContext.getPackageManager(); 2937 permGids = pm.getPackageGids(app.info.packageName); 2938 2939 if (Environment.isExternalStorageEmulated()) { 2940 checkTime(startTime, "startProcess: checking external storage perm"); 2941 if (pm.checkPermission( 2942 android.Manifest.permission.ACCESS_ALL_EXTERNAL_STORAGE, 2943 app.info.packageName) == PERMISSION_GRANTED) { 2944 mountExternal = Zygote.MOUNT_EXTERNAL_MULTIUSER_ALL; 2945 } else { 2946 mountExternal = Zygote.MOUNT_EXTERNAL_MULTIUSER; 2947 } 2948 } 2949 } catch (PackageManager.NameNotFoundException e) { 2950 Slog.w(TAG, "Unable to retrieve gids", e); 2951 } 2952 2953 /* 2954 * Add shared application and profile GIDs so applications can share some 2955 * resources like shared libraries and access user-wide resources 2956 */ 2957 if (permGids == null) { 2958 gids = new int[2]; 2959 } else { 2960 gids = new int[permGids.length + 2]; 2961 System.arraycopy(permGids, 0, gids, 2, permGids.length); 2962 } 2963 gids[0] = UserHandle.getSharedAppGid(UserHandle.getAppId(uid)); 2964 gids[1] = UserHandle.getUserGid(UserHandle.getUserId(uid)); 2965 } 2966 checkTime(startTime, "startProcess: building args"); 2967 if (mFactoryTest != FactoryTest.FACTORY_TEST_OFF) { 2968 if (mFactoryTest == FactoryTest.FACTORY_TEST_LOW_LEVEL 2969 && mTopComponent != null 2970 && app.processName.equals(mTopComponent.getPackageName())) { 2971 uid = 0; 2972 } 2973 if (mFactoryTest == FactoryTest.FACTORY_TEST_HIGH_LEVEL 2974 && (app.info.flags&ApplicationInfo.FLAG_FACTORY_TEST) != 0) { 2975 uid = 0; 2976 } 2977 } 2978 int debugFlags = 0; 2979 if ((app.info.flags & ApplicationInfo.FLAG_DEBUGGABLE) != 0) { 2980 debugFlags |= Zygote.DEBUG_ENABLE_DEBUGGER; 2981 // Also turn on CheckJNI for debuggable apps. It's quite 2982 // awkward to turn on otherwise. 2983 debugFlags |= Zygote.DEBUG_ENABLE_CHECKJNI; 2984 } 2985 // Run the app in safe mode if its manifest requests so or the 2986 // system is booted in safe mode. 2987 if ((app.info.flags & ApplicationInfo.FLAG_VM_SAFE_MODE) != 0 || 2988 mSafeMode == true) { 2989 debugFlags |= Zygote.DEBUG_ENABLE_SAFEMODE; 2990 } 2991 if ("1".equals(SystemProperties.get("debug.checkjni"))) { 2992 debugFlags |= Zygote.DEBUG_ENABLE_CHECKJNI; 2993 } 2994 if ("1".equals(SystemProperties.get("debug.jni.logging"))) { 2995 debugFlags |= Zygote.DEBUG_ENABLE_JNI_LOGGING; 2996 } 2997 if ("1".equals(SystemProperties.get("debug.assert"))) { 2998 debugFlags |= Zygote.DEBUG_ENABLE_ASSERT; 2999 } 3000 3001 String requiredAbi = (abiOverride != null) ? abiOverride : app.info.primaryCpuAbi; 3002 if (requiredAbi == null) { 3003 requiredAbi = Build.SUPPORTED_ABIS[0]; 3004 } 3005 3006 String instructionSet = null; 3007 if (app.info.primaryCpuAbi != null) { 3008 instructionSet = VMRuntime.getInstructionSet(app.info.primaryCpuAbi); 3009 } 3010 3011 // Start the process. It will either succeed and return a result containing 3012 // the PID of the new process, or else throw a RuntimeException. 3013 boolean isActivityProcess = (entryPoint == null); 3014 if (entryPoint == null) entryPoint = "android.app.ActivityThread"; 3015 checkTime(startTime, "startProcess: asking zygote to start proc"); 3016 Process.ProcessStartResult startResult = Process.start(entryPoint, 3017 app.processName, uid, uid, gids, debugFlags, mountExternal, 3018 app.info.targetSdkVersion, app.info.seinfo, requiredAbi, instructionSet, 3019 app.info.dataDir, entryPointArgs); 3020 checkTime(startTime, "startProcess: returned from zygote!"); 3021 3022 if (app.isolated) { 3023 mBatteryStatsService.addIsolatedUid(app.uid, app.info.uid); 3024 } 3025 mBatteryStatsService.noteProcessStart(app.processName, app.info.uid); 3026 checkTime(startTime, "startProcess: done updating battery stats"); 3027 3028 EventLog.writeEvent(EventLogTags.AM_PROC_START, 3029 UserHandle.getUserId(uid), startResult.pid, uid, 3030 app.processName, hostingType, 3031 hostingNameStr != null ? hostingNameStr : ""); 3032 3033 if (app.persistent) { 3034 Watchdog.getInstance().processStarted(app.processName, startResult.pid); 3035 } 3036 3037 checkTime(startTime, "startProcess: building log message"); 3038 StringBuilder buf = mStringBuilder; 3039 buf.setLength(0); 3040 buf.append("Start proc "); 3041 buf.append(app.processName); 3042 if (!isActivityProcess) { 3043 buf.append(" ["); 3044 buf.append(entryPoint); 3045 buf.append("]"); 3046 } 3047 buf.append(" for "); 3048 buf.append(hostingType); 3049 if (hostingNameStr != null) { 3050 buf.append(" "); 3051 buf.append(hostingNameStr); 3052 } 3053 buf.append(": pid="); 3054 buf.append(startResult.pid); 3055 buf.append(" uid="); 3056 buf.append(uid); 3057 buf.append(" gids={"); 3058 if (gids != null) { 3059 for (int gi=0; gi<gids.length; gi++) { 3060 if (gi != 0) buf.append(", "); 3061 buf.append(gids[gi]); 3062 3063 } 3064 } 3065 buf.append("}"); 3066 if (requiredAbi != null) { 3067 buf.append(" abi="); 3068 buf.append(requiredAbi); 3069 } 3070 Slog.i(TAG, buf.toString()); 3071 app.setPid(startResult.pid); 3072 app.usingWrapper = startResult.usingWrapper; 3073 app.removed = false; 3074 app.killed = false; 3075 app.killedByAm = false; 3076 checkTime(startTime, "startProcess: starting to update pids map"); 3077 synchronized (mPidsSelfLocked) { 3078 this.mPidsSelfLocked.put(startResult.pid, app); 3079 if (isActivityProcess) { 3080 Message msg = mHandler.obtainMessage(PROC_START_TIMEOUT_MSG); 3081 msg.obj = app; 3082 mHandler.sendMessageDelayed(msg, startResult.usingWrapper 3083 ? PROC_START_TIMEOUT_WITH_WRAPPER : PROC_START_TIMEOUT); 3084 } 3085 } 3086 checkTime(startTime, "startProcess: done updating pids map"); 3087 } catch (RuntimeException e) { 3088 // XXX do better error recovery. 3089 app.setPid(0); 3090 mBatteryStatsService.noteProcessFinish(app.processName, app.info.uid); 3091 if (app.isolated) { 3092 mBatteryStatsService.removeIsolatedUid(app.uid, app.info.uid); 3093 } 3094 Slog.e(TAG, "Failure starting process " + app.processName, e); 3095 } 3096 } 3097 3098 void updateUsageStats(ActivityRecord component, boolean resumed) { 3099 if (DEBUG_SWITCH) Slog.d(TAG, "updateUsageStats: comp=" + component + "res=" + resumed); 3100 final BatteryStatsImpl stats = mBatteryStatsService.getActiveStatistics(); 3101 if (resumed) { 3102 if (mUsageStatsService != null) { 3103 mUsageStatsService.reportEvent(component.realActivity, component.userId, 3104 UsageEvents.Event.MOVE_TO_FOREGROUND); 3105 } 3106 synchronized (stats) { 3107 stats.noteActivityResumedLocked(component.app.uid); 3108 } 3109 } else { 3110 if (mUsageStatsService != null) { 3111 mUsageStatsService.reportEvent(component.realActivity, component.userId, 3112 UsageEvents.Event.MOVE_TO_BACKGROUND); 3113 } 3114 synchronized (stats) { 3115 stats.noteActivityPausedLocked(component.app.uid); 3116 } 3117 } 3118 } 3119 3120 Intent getHomeIntent() { 3121 Intent intent = new Intent(mTopAction, mTopData != null ? Uri.parse(mTopData) : null); 3122 intent.setComponent(mTopComponent); 3123 if (mFactoryTest != FactoryTest.FACTORY_TEST_LOW_LEVEL) { 3124 intent.addCategory(Intent.CATEGORY_HOME); 3125 } 3126 return intent; 3127 } 3128 3129 boolean startHomeActivityLocked(int userId) { 3130 if (mFactoryTest == FactoryTest.FACTORY_TEST_LOW_LEVEL 3131 && mTopAction == null) { 3132 // We are running in factory test mode, but unable to find 3133 // the factory test app, so just sit around displaying the 3134 // error message and don't try to start anything. 3135 return false; 3136 } 3137 Intent intent = getHomeIntent(); 3138 ActivityInfo aInfo = 3139 resolveActivityInfo(intent, STOCK_PM_FLAGS, userId); 3140 if (aInfo != null) { 3141 intent.setComponent(new ComponentName( 3142 aInfo.applicationInfo.packageName, aInfo.name)); 3143 // Don't do this if the home app is currently being 3144 // instrumented. 3145 aInfo = new ActivityInfo(aInfo); 3146 aInfo.applicationInfo = getAppInfoForUser(aInfo.applicationInfo, userId); 3147 ProcessRecord app = getProcessRecordLocked(aInfo.processName, 3148 aInfo.applicationInfo.uid, true); 3149 if (app == null || app.instrumentationClass == null) { 3150 intent.setFlags(intent.getFlags() | Intent.FLAG_ACTIVITY_NEW_TASK); 3151 mStackSupervisor.startHomeActivity(intent, aInfo); 3152 } 3153 } 3154 3155 return true; 3156 } 3157 3158 private ActivityInfo resolveActivityInfo(Intent intent, int flags, int userId) { 3159 ActivityInfo ai = null; 3160 ComponentName comp = intent.getComponent(); 3161 try { 3162 if (comp != null) { 3163 ai = AppGlobals.getPackageManager().getActivityInfo(comp, flags, userId); 3164 } else { 3165 ResolveInfo info = AppGlobals.getPackageManager().resolveIntent( 3166 intent, 3167 intent.resolveTypeIfNeeded(mContext.getContentResolver()), 3168 flags, userId); 3169 3170 if (info != null) { 3171 ai = info.activityInfo; 3172 } 3173 } 3174 } catch (RemoteException e) { 3175 // ignore 3176 } 3177 3178 return ai; 3179 } 3180 3181 /** 3182 * Starts the "new version setup screen" if appropriate. 3183 */ 3184 void startSetupActivityLocked() { 3185 // Only do this once per boot. 3186 if (mCheckedForSetup) { 3187 return; 3188 } 3189 3190 // We will show this screen if the current one is a different 3191 // version than the last one shown, and we are not running in 3192 // low-level factory test mode. 3193 final ContentResolver resolver = mContext.getContentResolver(); 3194 if (mFactoryTest != FactoryTest.FACTORY_TEST_LOW_LEVEL && 3195 Settings.Global.getInt(resolver, 3196 Settings.Global.DEVICE_PROVISIONED, 0) != 0) { 3197 mCheckedForSetup = true; 3198 3199 // See if we should be showing the platform update setup UI. 3200 Intent intent = new Intent(Intent.ACTION_UPGRADE_SETUP); 3201 List<ResolveInfo> ris = mContext.getPackageManager() 3202 .queryIntentActivities(intent, PackageManager.GET_META_DATA); 3203 3204 // We don't allow third party apps to replace this. 3205 ResolveInfo ri = null; 3206 for (int i=0; ris != null && i<ris.size(); i++) { 3207 if ((ris.get(i).activityInfo.applicationInfo.flags 3208 & ApplicationInfo.FLAG_SYSTEM) != 0) { 3209 ri = ris.get(i); 3210 break; 3211 } 3212 } 3213 3214 if (ri != null) { 3215 String vers = ri.activityInfo.metaData != null 3216 ? ri.activityInfo.metaData.getString(Intent.METADATA_SETUP_VERSION) 3217 : null; 3218 if (vers == null && ri.activityInfo.applicationInfo.metaData != null) { 3219 vers = ri.activityInfo.applicationInfo.metaData.getString( 3220 Intent.METADATA_SETUP_VERSION); 3221 } 3222 String lastVers = Settings.Secure.getString( 3223 resolver, Settings.Secure.LAST_SETUP_SHOWN); 3224 if (vers != null && !vers.equals(lastVers)) { 3225 intent.setFlags(Intent.FLAG_ACTIVITY_NEW_TASK); 3226 intent.setComponent(new ComponentName( 3227 ri.activityInfo.packageName, ri.activityInfo.name)); 3228 mStackSupervisor.startActivityLocked(null, intent, null, ri.activityInfo, 3229 null, null, null, null, 0, 0, 0, null, 0, 0, 0, null, false, null, null, 3230 null); 3231 } 3232 } 3233 } 3234 } 3235 3236 CompatibilityInfo compatibilityInfoForPackageLocked(ApplicationInfo ai) { 3237 return mCompatModePackages.compatibilityInfoForPackageLocked(ai); 3238 } 3239 3240 void enforceNotIsolatedCaller(String caller) { 3241 if (UserHandle.isIsolated(Binder.getCallingUid())) { 3242 throw new SecurityException("Isolated process not allowed to call " + caller); 3243 } 3244 } 3245 3246 void enforceShellRestriction(String restriction, int userHandle) { 3247 if (Binder.getCallingUid() == Process.SHELL_UID) { 3248 if (userHandle < 0 3249 || mUserManager.hasUserRestriction(restriction, userHandle)) { 3250 throw new SecurityException("Shell does not have permission to access user " 3251 + userHandle); 3252 } 3253 } 3254 } 3255 3256 @Override 3257 public int getFrontActivityScreenCompatMode() { 3258 enforceNotIsolatedCaller("getFrontActivityScreenCompatMode"); 3259 synchronized (this) { 3260 return mCompatModePackages.getFrontActivityScreenCompatModeLocked(); 3261 } 3262 } 3263 3264 @Override 3265 public void setFrontActivityScreenCompatMode(int mode) { 3266 enforceCallingPermission(android.Manifest.permission.SET_SCREEN_COMPATIBILITY, 3267 "setFrontActivityScreenCompatMode"); 3268 synchronized (this) { 3269 mCompatModePackages.setFrontActivityScreenCompatModeLocked(mode); 3270 } 3271 } 3272 3273 @Override 3274 public int getPackageScreenCompatMode(String packageName) { 3275 enforceNotIsolatedCaller("getPackageScreenCompatMode"); 3276 synchronized (this) { 3277 return mCompatModePackages.getPackageScreenCompatModeLocked(packageName); 3278 } 3279 } 3280 3281 @Override 3282 public void setPackageScreenCompatMode(String packageName, int mode) { 3283 enforceCallingPermission(android.Manifest.permission.SET_SCREEN_COMPATIBILITY, 3284 "setPackageScreenCompatMode"); 3285 synchronized (this) { 3286 mCompatModePackages.setPackageScreenCompatModeLocked(packageName, mode); 3287 } 3288 } 3289 3290 @Override 3291 public boolean getPackageAskScreenCompat(String packageName) { 3292 enforceNotIsolatedCaller("getPackageAskScreenCompat"); 3293 synchronized (this) { 3294 return mCompatModePackages.getPackageAskCompatModeLocked(packageName); 3295 } 3296 } 3297 3298 @Override 3299 public void setPackageAskScreenCompat(String packageName, boolean ask) { 3300 enforceCallingPermission(android.Manifest.permission.SET_SCREEN_COMPATIBILITY, 3301 "setPackageAskScreenCompat"); 3302 synchronized (this) { 3303 mCompatModePackages.setPackageAskCompatModeLocked(packageName, ask); 3304 } 3305 } 3306 3307 private void dispatchProcessesChanged() { 3308 int N; 3309 synchronized (this) { 3310 N = mPendingProcessChanges.size(); 3311 if (mActiveProcessChanges.length < N) { 3312 mActiveProcessChanges = new ProcessChangeItem[N]; 3313 } 3314 mPendingProcessChanges.toArray(mActiveProcessChanges); 3315 mAvailProcessChanges.addAll(mPendingProcessChanges); 3316 mPendingProcessChanges.clear(); 3317 if (DEBUG_PROCESS_OBSERVERS) Slog.i(TAG, "*** Delivering " + N + " process changes"); 3318 } 3319 3320 int i = mProcessObservers.beginBroadcast(); 3321 while (i > 0) { 3322 i--; 3323 final IProcessObserver observer = mProcessObservers.getBroadcastItem(i); 3324 if (observer != null) { 3325 try { 3326 for (int j=0; j<N; j++) { 3327 ProcessChangeItem item = mActiveProcessChanges[j]; 3328 if ((item.changes&ProcessChangeItem.CHANGE_ACTIVITIES) != 0) { 3329 if (DEBUG_PROCESS_OBSERVERS) Slog.i(TAG, "ACTIVITIES CHANGED pid=" 3330 + item.pid + " uid=" + item.uid + ": " 3331 + item.foregroundActivities); 3332 observer.onForegroundActivitiesChanged(item.pid, item.uid, 3333 item.foregroundActivities); 3334 } 3335 if ((item.changes&ProcessChangeItem.CHANGE_PROCESS_STATE) != 0) { 3336 if (DEBUG_PROCESS_OBSERVERS) Slog.i(TAG, "PROCSTATE CHANGED pid=" 3337 + item.pid + " uid=" + item.uid + ": " + item.processState); 3338 observer.onProcessStateChanged(item.pid, item.uid, item.processState); 3339 } 3340 } 3341 } catch (RemoteException e) { 3342 } 3343 } 3344 } 3345 mProcessObservers.finishBroadcast(); 3346 } 3347 3348 private void dispatchProcessDied(int pid, int uid) { 3349 int i = mProcessObservers.beginBroadcast(); 3350 while (i > 0) { 3351 i--; 3352 final IProcessObserver observer = mProcessObservers.getBroadcastItem(i); 3353 if (observer != null) { 3354 try { 3355 observer.onProcessDied(pid, uid); 3356 } catch (RemoteException e) { 3357 } 3358 } 3359 } 3360 mProcessObservers.finishBroadcast(); 3361 } 3362 3363 @Override 3364 public final int startActivity(IApplicationThread caller, String callingPackage, 3365 Intent intent, String resolvedType, IBinder resultTo, String resultWho, int requestCode, 3366 int startFlags, ProfilerInfo profilerInfo, Bundle options) { 3367 return startActivityAsUser(caller, callingPackage, intent, resolvedType, resultTo, 3368 resultWho, requestCode, startFlags, profilerInfo, options, 3369 UserHandle.getCallingUserId()); 3370 } 3371 3372 @Override 3373 public final int startActivityAsUser(IApplicationThread caller, String callingPackage, 3374 Intent intent, String resolvedType, IBinder resultTo, String resultWho, int requestCode, 3375 int startFlags, ProfilerInfo profilerInfo, Bundle options, int userId) { 3376 enforceNotIsolatedCaller("startActivity"); 3377 userId = handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(), userId, 3378 false, ALLOW_FULL_ONLY, "startActivity", null); 3379 // TODO: Switch to user app stacks here. 3380 return mStackSupervisor.startActivityMayWait(caller, -1, callingPackage, intent, 3381 resolvedType, null, null, resultTo, resultWho, requestCode, startFlags, 3382 profilerInfo, null, null, options, userId, null, null); 3383 } 3384 3385 @Override 3386 public final int startActivityAsCaller(IApplicationThread caller, String callingPackage, 3387 Intent intent, String resolvedType, IBinder resultTo, String resultWho, int requestCode, 3388 int startFlags, ProfilerInfo profilerInfo, Bundle options, int userId) { 3389 3390 // This is very dangerous -- it allows you to perform a start activity (including 3391 // permission grants) as any app that may launch one of your own activities. So 3392 // we will only allow this to be done from activities that are part of the core framework, 3393 // and then only when they are running as the system. 3394 final ActivityRecord sourceRecord; 3395 final int targetUid; 3396 final String targetPackage; 3397 synchronized (this) { 3398 if (resultTo == null) { 3399 throw new SecurityException("Must be called from an activity"); 3400 } 3401 sourceRecord = mStackSupervisor.isInAnyStackLocked(resultTo); 3402 if (sourceRecord == null) { 3403 throw new SecurityException("Called with bad activity token: " + resultTo); 3404 } 3405 if (!sourceRecord.info.packageName.equals("android")) { 3406 throw new SecurityException( 3407 "Must be called from an activity that is declared in the android package"); 3408 } 3409 if (sourceRecord.app == null) { 3410 throw new SecurityException("Called without a process attached to activity"); 3411 } 3412 if (UserHandle.getAppId(sourceRecord.app.uid) != Process.SYSTEM_UID) { 3413 // This is still okay, as long as this activity is running under the 3414 // uid of the original calling activity. 3415 if (sourceRecord.app.uid != sourceRecord.launchedFromUid) { 3416 throw new SecurityException( 3417 "Calling activity in uid " + sourceRecord.app.uid 3418 + " must be system uid or original calling uid " 3419 + sourceRecord.launchedFromUid); 3420 } 3421 } 3422 targetUid = sourceRecord.launchedFromUid; 3423 targetPackage = sourceRecord.launchedFromPackage; 3424 } 3425 3426 if (userId == UserHandle.USER_NULL) { 3427 userId = UserHandle.getUserId(sourceRecord.app.uid); 3428 } 3429 3430 // TODO: Switch to user app stacks here. 3431 try { 3432 int ret = mStackSupervisor.startActivityMayWait(null, targetUid, targetPackage, intent, 3433 resolvedType, null, null, resultTo, resultWho, requestCode, startFlags, null, 3434 null, null, options, userId, null, null); 3435 return ret; 3436 } catch (SecurityException e) { 3437 // XXX need to figure out how to propagate to original app. 3438 // A SecurityException here is generally actually a fault of the original 3439 // calling activity (such as a fairly granting permissions), so propagate it 3440 // back to them. 3441 /* 3442 StringBuilder msg = new StringBuilder(); 3443 msg.append("While launching"); 3444 msg.append(intent.toString()); 3445 msg.append(": "); 3446 msg.append(e.getMessage()); 3447 */ 3448 throw e; 3449 } 3450 } 3451 3452 @Override 3453 public final WaitResult startActivityAndWait(IApplicationThread caller, String callingPackage, 3454 Intent intent, String resolvedType, IBinder resultTo, String resultWho, int requestCode, 3455 int startFlags, ProfilerInfo profilerInfo, Bundle options, int userId) { 3456 enforceNotIsolatedCaller("startActivityAndWait"); 3457 userId = handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(), userId, 3458 false, ALLOW_FULL_ONLY, "startActivityAndWait", null); 3459 WaitResult res = new WaitResult(); 3460 // TODO: Switch to user app stacks here. 3461 mStackSupervisor.startActivityMayWait(caller, -1, callingPackage, intent, resolvedType, 3462 null, null, resultTo, resultWho, requestCode, startFlags, profilerInfo, res, null, 3463 options, userId, null, null); 3464 return res; 3465 } 3466 3467 @Override 3468 public final int startActivityWithConfig(IApplicationThread caller, String callingPackage, 3469 Intent intent, String resolvedType, IBinder resultTo, String resultWho, int requestCode, 3470 int startFlags, Configuration config, Bundle options, int userId) { 3471 enforceNotIsolatedCaller("startActivityWithConfig"); 3472 userId = handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(), userId, 3473 false, ALLOW_FULL_ONLY, "startActivityWithConfig", null); 3474 // TODO: Switch to user app stacks here. 3475 int ret = mStackSupervisor.startActivityMayWait(caller, -1, callingPackage, intent, 3476 resolvedType, null, null, resultTo, resultWho, requestCode, startFlags, 3477 null, null, config, options, userId, null, null); 3478 return ret; 3479 } 3480 3481 @Override 3482 public int startActivityIntentSender(IApplicationThread caller, 3483 IntentSender intent, Intent fillInIntent, String resolvedType, 3484 IBinder resultTo, String resultWho, int requestCode, 3485 int flagsMask, int flagsValues, Bundle options) { 3486 enforceNotIsolatedCaller("startActivityIntentSender"); 3487 // Refuse possible leaked file descriptors 3488 if (fillInIntent != null && fillInIntent.hasFileDescriptors()) { 3489 throw new IllegalArgumentException("File descriptors passed in Intent"); 3490 } 3491 3492 IIntentSender sender = intent.getTarget(); 3493 if (!(sender instanceof PendingIntentRecord)) { 3494 throw new IllegalArgumentException("Bad PendingIntent object"); 3495 } 3496 3497 PendingIntentRecord pir = (PendingIntentRecord)sender; 3498 3499 synchronized (this) { 3500 // If this is coming from the currently resumed activity, it is 3501 // effectively saying that app switches are allowed at this point. 3502 final ActivityStack stack = getFocusedStack(); 3503 if (stack.mResumedActivity != null && 3504 stack.mResumedActivity.info.applicationInfo.uid == Binder.getCallingUid()) { 3505 mAppSwitchesAllowedTime = 0; 3506 } 3507 } 3508 int ret = pir.sendInner(0, fillInIntent, resolvedType, null, null, 3509 resultTo, resultWho, requestCode, flagsMask, flagsValues, options, null); 3510 return ret; 3511 } 3512 3513 @Override 3514 public int startVoiceActivity(String callingPackage, int callingPid, int callingUid, 3515 Intent intent, String resolvedType, IVoiceInteractionSession session, 3516 IVoiceInteractor interactor, int startFlags, ProfilerInfo profilerInfo, 3517 Bundle options, int userId) { 3518 if (checkCallingPermission(Manifest.permission.BIND_VOICE_INTERACTION) 3519 != PackageManager.PERMISSION_GRANTED) { 3520 String msg = "Permission Denial: startVoiceActivity() from pid=" 3521 + Binder.getCallingPid() 3522 + ", uid=" + Binder.getCallingUid() 3523 + " requires " + android.Manifest.permission.BIND_VOICE_INTERACTION; 3524 Slog.w(TAG, msg); 3525 throw new SecurityException(msg); 3526 } 3527 if (session == null || interactor == null) { 3528 throw new NullPointerException("null session or interactor"); 3529 } 3530 userId = handleIncomingUser(callingPid, callingUid, userId, 3531 false, ALLOW_FULL_ONLY, "startVoiceActivity", null); 3532 // TODO: Switch to user app stacks here. 3533 return mStackSupervisor.startActivityMayWait(null, callingUid, callingPackage, intent, 3534 resolvedType, session, interactor, null, null, 0, startFlags, profilerInfo, null, 3535 null, options, userId, null, null); 3536 } 3537 3538 @Override 3539 public boolean startNextMatchingActivity(IBinder callingActivity, 3540 Intent intent, Bundle options) { 3541 // Refuse possible leaked file descriptors 3542 if (intent != null && intent.hasFileDescriptors() == true) { 3543 throw new IllegalArgumentException("File descriptors passed in Intent"); 3544 } 3545 3546 synchronized (this) { 3547 final ActivityRecord r = ActivityRecord.isInStackLocked(callingActivity); 3548 if (r == null) { 3549 ActivityOptions.abort(options); 3550 return false; 3551 } 3552 if (r.app == null || r.app.thread == null) { 3553 // The caller is not running... d'oh! 3554 ActivityOptions.abort(options); 3555 return false; 3556 } 3557 intent = new Intent(intent); 3558 // The caller is not allowed to change the data. 3559 intent.setDataAndType(r.intent.getData(), r.intent.getType()); 3560 // And we are resetting to find the next component... 3561 intent.setComponent(null); 3562 3563 final boolean debug = ((intent.getFlags() & Intent.FLAG_DEBUG_LOG_RESOLUTION) != 0); 3564 3565 ActivityInfo aInfo = null; 3566 try { 3567 List<ResolveInfo> resolves = 3568 AppGlobals.getPackageManager().queryIntentActivities( 3569 intent, r.resolvedType, 3570 PackageManager.MATCH_DEFAULT_ONLY | STOCK_PM_FLAGS, 3571 UserHandle.getCallingUserId()); 3572 3573 // Look for the original activity in the list... 3574 final int N = resolves != null ? resolves.size() : 0; 3575 for (int i=0; i<N; i++) { 3576 ResolveInfo rInfo = resolves.get(i); 3577 if (rInfo.activityInfo.packageName.equals(r.packageName) 3578 && rInfo.activityInfo.name.equals(r.info.name)) { 3579 // We found the current one... the next matching is 3580 // after it. 3581 i++; 3582 if (i<N) { 3583 aInfo = resolves.get(i).activityInfo; 3584 } 3585 if (debug) { 3586 Slog.v(TAG, "Next matching activity: found current " + r.packageName 3587 + "/" + r.info.name); 3588 Slog.v(TAG, "Next matching activity: next is " + aInfo.packageName 3589 + "/" + aInfo.name); 3590 } 3591 break; 3592 } 3593 } 3594 } catch (RemoteException e) { 3595 } 3596 3597 if (aInfo == null) { 3598 // Nobody who is next! 3599 ActivityOptions.abort(options); 3600 if (debug) Slog.d(TAG, "Next matching activity: nothing found"); 3601 return false; 3602 } 3603 3604 intent.setComponent(new ComponentName( 3605 aInfo.applicationInfo.packageName, aInfo.name)); 3606 intent.setFlags(intent.getFlags()&~( 3607 Intent.FLAG_ACTIVITY_FORWARD_RESULT| 3608 Intent.FLAG_ACTIVITY_CLEAR_TOP| 3609 Intent.FLAG_ACTIVITY_MULTIPLE_TASK| 3610 Intent.FLAG_ACTIVITY_NEW_TASK)); 3611 3612 // Okay now we need to start the new activity, replacing the 3613 // currently running activity. This is a little tricky because 3614 // we want to start the new one as if the current one is finished, 3615 // but not finish the current one first so that there is no flicker. 3616 // And thus... 3617 final boolean wasFinishing = r.finishing; 3618 r.finishing = true; 3619 3620 // Propagate reply information over to the new activity. 3621 final ActivityRecord resultTo = r.resultTo; 3622 final String resultWho = r.resultWho; 3623 final int requestCode = r.requestCode; 3624 r.resultTo = null; 3625 if (resultTo != null) { 3626 resultTo.removeResultsLocked(r, resultWho, requestCode); 3627 } 3628 3629 final long origId = Binder.clearCallingIdentity(); 3630 int res = mStackSupervisor.startActivityLocked(r.app.thread, intent, 3631 r.resolvedType, aInfo, null, null, resultTo != null ? resultTo.appToken : null, 3632 resultWho, requestCode, -1, r.launchedFromUid, r.launchedFromPackage, 3633 -1, r.launchedFromUid, 0, options, false, null, null, null); 3634 Binder.restoreCallingIdentity(origId); 3635 3636 r.finishing = wasFinishing; 3637 if (res != ActivityManager.START_SUCCESS) { 3638 return false; 3639 } 3640 return true; 3641 } 3642 } 3643 3644 @Override 3645 public final int startActivityFromRecents(int taskId, Bundle options) { 3646 if (checkCallingPermission(START_TASKS_FROM_RECENTS) != PackageManager.PERMISSION_GRANTED) { 3647 String msg = "Permission Denial: startActivityFromRecents called without " + 3648 START_TASKS_FROM_RECENTS; 3649 Slog.w(TAG, msg); 3650 throw new SecurityException(msg); 3651 } 3652 return startActivityFromRecentsInner(taskId, options); 3653 } 3654 3655 final int startActivityFromRecentsInner(int taskId, Bundle options) { 3656 final TaskRecord task; 3657 final int callingUid; 3658 final String callingPackage; 3659 final Intent intent; 3660 final int userId; 3661 synchronized (this) { 3662 task = recentTaskForIdLocked(taskId); 3663 if (task == null) { 3664 throw new IllegalArgumentException("Task " + taskId + " not found."); 3665 } 3666 callingUid = task.mCallingUid; 3667 callingPackage = task.mCallingPackage; 3668 intent = task.intent; 3669 intent.addFlags(Intent.FLAG_ACTIVITY_LAUNCHED_FROM_HISTORY); 3670 userId = task.userId; 3671 } 3672 return startActivityInPackage(callingUid, callingPackage, intent, null, null, null, 0, 0, 3673 options, userId, null, task); 3674 } 3675 3676 final int startActivityInPackage(int uid, String callingPackage, 3677 Intent intent, String resolvedType, IBinder resultTo, 3678 String resultWho, int requestCode, int startFlags, Bundle options, int userId, 3679 IActivityContainer container, TaskRecord inTask) { 3680 3681 userId = handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(), userId, 3682 false, ALLOW_FULL_ONLY, "startActivityInPackage", null); 3683 3684 // TODO: Switch to user app stacks here. 3685 int ret = mStackSupervisor.startActivityMayWait(null, uid, callingPackage, intent, 3686 resolvedType, null, null, resultTo, resultWho, requestCode, startFlags, 3687 null, null, null, options, userId, container, inTask); 3688 return ret; 3689 } 3690 3691 @Override 3692 public final int startActivities(IApplicationThread caller, String callingPackage, 3693 Intent[] intents, String[] resolvedTypes, IBinder resultTo, Bundle options, 3694 int userId) { 3695 enforceNotIsolatedCaller("startActivities"); 3696 userId = handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(), userId, 3697 false, ALLOW_FULL_ONLY, "startActivity", null); 3698 // TODO: Switch to user app stacks here. 3699 int ret = mStackSupervisor.startActivities(caller, -1, callingPackage, intents, 3700 resolvedTypes, resultTo, options, userId); 3701 return ret; 3702 } 3703 3704 final int startActivitiesInPackage(int uid, String callingPackage, 3705 Intent[] intents, String[] resolvedTypes, IBinder resultTo, 3706 Bundle options, int userId) { 3707 3708 userId = handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(), userId, 3709 false, ALLOW_FULL_ONLY, "startActivityInPackage", null); 3710 // TODO: Switch to user app stacks here. 3711 int ret = mStackSupervisor.startActivities(null, uid, callingPackage, intents, resolvedTypes, 3712 resultTo, options, userId); 3713 return ret; 3714 } 3715 3716 //explicitly remove thd old information in mRecentTasks when removing existing user. 3717 private void removeRecentTasksForUserLocked(int userId) { 3718 if(userId <= 0) { 3719 Slog.i(TAG, "Can't remove recent task on user " + userId); 3720 return; 3721 } 3722 3723 for (int i = mRecentTasks.size() - 1; i >= 0; --i) { 3724 TaskRecord tr = mRecentTasks.get(i); 3725 if (tr.userId == userId) { 3726 if(DEBUG_TASKS) Slog.i(TAG, "remove RecentTask " + tr 3727 + " when finishing user" + userId); 3728 mRecentTasks.remove(i); 3729 tr.removedFromRecents(mTaskPersister); 3730 } 3731 } 3732 3733 // Remove tasks from persistent storage. 3734 mTaskPersister.wakeup(null, true); 3735 } 3736 3737 // Sort by taskId 3738 private Comparator<TaskRecord> mTaskRecordComparator = new Comparator<TaskRecord>() { 3739 @Override 3740 public int compare(TaskRecord lhs, TaskRecord rhs) { 3741 return rhs.taskId - lhs.taskId; 3742 } 3743 }; 3744 3745 // Extract the affiliates of the chain containing mRecentTasks[start]. 3746 private int processNextAffiliateChain(int start) { 3747 final TaskRecord startTask = mRecentTasks.get(start); 3748 final int affiliateId = startTask.mAffiliatedTaskId; 3749 3750 // Quick identification of isolated tasks. I.e. those not launched behind. 3751 if (startTask.taskId == affiliateId && startTask.mPrevAffiliate == null && 3752 startTask.mNextAffiliate == null) { 3753 // There is still a slim chance that there are other tasks that point to this task 3754 // and that the chain is so messed up that this task no longer points to them but 3755 // the gain of this optimization outweighs the risk. 3756 startTask.inRecents = true; 3757 return start + 1; 3758 } 3759 3760 // Remove all tasks that are affiliated to affiliateId and put them in mTmpRecents. 3761 mTmpRecents.clear(); 3762 for (int i = mRecentTasks.size() - 1; i >= start; --i) { 3763 final TaskRecord task = mRecentTasks.get(i); 3764 if (task.mAffiliatedTaskId == affiliateId) { 3765 mRecentTasks.remove(i); 3766 mTmpRecents.add(task); 3767 } 3768 } 3769 3770 // Sort them all by taskId. That is the order they were create in and that order will 3771 // always be correct. 3772 Collections.sort(mTmpRecents, mTaskRecordComparator); 3773 3774 // Go through and fix up the linked list. 3775 // The first one is the end of the chain and has no next. 3776 final TaskRecord first = mTmpRecents.get(0); 3777 first.inRecents = true; 3778 if (first.mNextAffiliate != null) { 3779 Slog.w(TAG, "Link error 1 first.next=" + first.mNextAffiliate); 3780 first.setNextAffiliate(null); 3781 mTaskPersister.wakeup(first, false); 3782 } 3783 // Everything in the middle is doubly linked from next to prev. 3784 final int tmpSize = mTmpRecents.size(); 3785 for (int i = 0; i < tmpSize - 1; ++i) { 3786 final TaskRecord next = mTmpRecents.get(i); 3787 final TaskRecord prev = mTmpRecents.get(i + 1); 3788 if (next.mPrevAffiliate != prev) { 3789 Slog.w(TAG, "Link error 2 next=" + next + " prev=" + next.mPrevAffiliate + 3790 " setting prev=" + prev); 3791 next.setPrevAffiliate(prev); 3792 mTaskPersister.wakeup(next, false); 3793 } 3794 if (prev.mNextAffiliate != next) { 3795 Slog.w(TAG, "Link error 3 prev=" + prev + " next=" + prev.mNextAffiliate + 3796 " setting next=" + next); 3797 prev.setNextAffiliate(next); 3798 mTaskPersister.wakeup(prev, false); 3799 } 3800 prev.inRecents = true; 3801 } 3802 // The last one is the beginning of the list and has no prev. 3803 final TaskRecord last = mTmpRecents.get(tmpSize - 1); 3804 if (last.mPrevAffiliate != null) { 3805 Slog.w(TAG, "Link error 4 last.prev=" + last.mPrevAffiliate); 3806 last.setPrevAffiliate(null); 3807 mTaskPersister.wakeup(last, false); 3808 } 3809 3810 // Insert the group back into mRecentTasks at start. 3811 mRecentTasks.addAll(start, mTmpRecents); 3812 3813 // Let the caller know where we left off. 3814 return start + tmpSize; 3815 } 3816 3817 /** 3818 * Update the recent tasks lists: make sure tasks should still be here (their 3819 * applications / activities still exist), update their availability, fixup ordering 3820 * of affiliations. 3821 */ 3822 void cleanupRecentTasksLocked(int userId) { 3823 if (mRecentTasks == null) { 3824 // Happens when called from the packagemanager broadcast before boot. 3825 return; 3826 } 3827 3828 final HashMap<ComponentName, ActivityInfo> availActCache = new HashMap<>(); 3829 final HashMap<String, ApplicationInfo> availAppCache = new HashMap<>(); 3830 final IPackageManager pm = AppGlobals.getPackageManager(); 3831 final ActivityInfo dummyAct = new ActivityInfo(); 3832 final ApplicationInfo dummyApp = new ApplicationInfo(); 3833 3834 int N = mRecentTasks.size(); 3835 3836 int[] users = userId == UserHandle.USER_ALL 3837 ? getUsersLocked() : new int[] { userId }; 3838 for (int user : users) { 3839 for (int i = 0; i < N; i++) { 3840 TaskRecord task = mRecentTasks.get(i); 3841 if (task.userId != user) { 3842 // Only look at tasks for the user ID of interest. 3843 continue; 3844 } 3845 if (task.autoRemoveRecents && task.getTopActivity() == null) { 3846 // This situation is broken, and we should just get rid of it now. 3847 mRecentTasks.remove(i); 3848 task.removedFromRecents(mTaskPersister); 3849 i--; 3850 N--; 3851 Slog.w(TAG, "Removing auto-remove without activity: " + task); 3852 continue; 3853 } 3854 // Check whether this activity is currently available. 3855 if (task.realActivity != null) { 3856 ActivityInfo ai = availActCache.get(task.realActivity); 3857 if (ai == null) { 3858 try { 3859 ai = pm.getActivityInfo(task.realActivity, 3860 PackageManager.GET_UNINSTALLED_PACKAGES 3861 | PackageManager.GET_DISABLED_COMPONENTS, user); 3862 } catch (RemoteException e) { 3863 // Will never happen. 3864 continue; 3865 } 3866 if (ai == null) { 3867 ai = dummyAct; 3868 } 3869 availActCache.put(task.realActivity, ai); 3870 } 3871 if (ai == dummyAct) { 3872 // This could be either because the activity no longer exists, or the 3873 // app is temporarily gone. For the former we want to remove the recents 3874 // entry; for the latter we want to mark it as unavailable. 3875 ApplicationInfo app = availAppCache.get(task.realActivity.getPackageName()); 3876 if (app == null) { 3877 try { 3878 app = pm.getApplicationInfo(task.realActivity.getPackageName(), 3879 PackageManager.GET_UNINSTALLED_PACKAGES 3880 | PackageManager.GET_DISABLED_COMPONENTS, user); 3881 } catch (RemoteException e) { 3882 // Will never happen. 3883 continue; 3884 } 3885 if (app == null) { 3886 app = dummyApp; 3887 } 3888 availAppCache.put(task.realActivity.getPackageName(), app); 3889 } 3890 if (app == dummyApp || (app.flags&ApplicationInfo.FLAG_INSTALLED) == 0) { 3891 // Doesn't exist any more! Good-bye. 3892 mRecentTasks.remove(i); 3893 task.removedFromRecents(mTaskPersister); 3894 i--; 3895 N--; 3896 Slog.w(TAG, "Removing no longer valid recent: " + task); 3897 continue; 3898 } else { 3899 // Otherwise just not available for now. 3900 if (task.isAvailable) { 3901 if (DEBUG_RECENTS) Slog.d(TAG, "Making recent unavailable: " 3902 + task); 3903 } 3904 task.isAvailable = false; 3905 } 3906 } else { 3907 if (!ai.enabled || !ai.applicationInfo.enabled 3908 || (ai.applicationInfo.flags&ApplicationInfo.FLAG_INSTALLED) == 0) { 3909 if (task.isAvailable) { 3910 if (DEBUG_RECENTS) Slog.d(TAG, "Making recent unavailable: " 3911 + task + " (enabled=" + ai.enabled + "/" 3912 + ai.applicationInfo.enabled + " flags=" 3913 + Integer.toHexString(ai.applicationInfo.flags) + ")"); 3914 } 3915 task.isAvailable = false; 3916 } else { 3917 if (!task.isAvailable) { 3918 if (DEBUG_RECENTS) Slog.d(TAG, "Making recent available: " 3919 + task); 3920 } 3921 task.isAvailable = true; 3922 } 3923 } 3924 } 3925 } 3926 } 3927 3928 // Verify the affiliate chain for each task. 3929 for (int i = 0; i < N; i = processNextAffiliateChain(i)) { 3930 } 3931 3932 mTmpRecents.clear(); 3933 // mRecentTasks is now in sorted, affiliated order. 3934 } 3935 3936 private final boolean moveAffiliatedTasksToFront(TaskRecord task, int taskIndex) { 3937 int N = mRecentTasks.size(); 3938 TaskRecord top = task; 3939 int topIndex = taskIndex; 3940 while (top.mNextAffiliate != null && topIndex > 0) { 3941 top = top.mNextAffiliate; 3942 topIndex--; 3943 } 3944 if (DEBUG_RECENTS) Slog.d(TAG, "addRecent: adding affilliates starting at " 3945 + topIndex + " from intial " + taskIndex); 3946 // Find the end of the chain, doing a sanity check along the way. 3947 boolean sane = top.mAffiliatedTaskId == task.mAffiliatedTaskId; 3948 int endIndex = topIndex; 3949 TaskRecord prev = top; 3950 while (endIndex < N) { 3951 TaskRecord cur = mRecentTasks.get(endIndex); 3952 if (DEBUG_RECENTS) Slog.d(TAG, "addRecent: looking at next chain @" 3953 + endIndex + " " + cur); 3954 if (cur == top) { 3955 // Verify start of the chain. 3956 if (cur.mNextAffiliate != null || cur.mNextAffiliateTaskId != -1) { 3957 Slog.wtf(TAG, "Bad chain @" + endIndex 3958 + ": first task has next affiliate: " + prev); 3959 sane = false; 3960 break; 3961 } 3962 } else { 3963 // Verify middle of the chain's next points back to the one before. 3964 if (cur.mNextAffiliate != prev 3965 || cur.mNextAffiliateTaskId != prev.taskId) { 3966 Slog.wtf(TAG, "Bad chain @" + endIndex 3967 + ": middle task " + cur + " @" + endIndex 3968 + " has bad next affiliate " 3969 + cur.mNextAffiliate + " id " + cur.mNextAffiliateTaskId 3970 + ", expected " + prev); 3971 sane = false; 3972 break; 3973 } 3974 } 3975 if (cur.mPrevAffiliateTaskId == -1) { 3976 // Chain ends here. 3977 if (cur.mPrevAffiliate != null) { 3978 Slog.wtf(TAG, "Bad chain @" + endIndex 3979 + ": last task " + cur + " has previous affiliate " 3980 + cur.mPrevAffiliate); 3981 sane = false; 3982 } 3983 if (DEBUG_RECENTS) Slog.d(TAG, "addRecent: end of chain @" + endIndex); 3984 break; 3985 } else { 3986 // Verify middle of the chain's prev points to a valid item. 3987 if (cur.mPrevAffiliate == null) { 3988 Slog.wtf(TAG, "Bad chain @" + endIndex 3989 + ": task " + cur + " has previous affiliate " 3990 + cur.mPrevAffiliate + " but should be id " 3991 + cur.mPrevAffiliate); 3992 sane = false; 3993 break; 3994 } 3995 } 3996 if (cur.mAffiliatedTaskId != task.mAffiliatedTaskId) { 3997 Slog.wtf(TAG, "Bad chain @" + endIndex 3998 + ": task " + cur + " has affiliated id " 3999 + cur.mAffiliatedTaskId + " but should be " 4000 + task.mAffiliatedTaskId); 4001 sane = false; 4002 break; 4003 } 4004 prev = cur; 4005 endIndex++; 4006 if (endIndex >= N) { 4007 Slog.wtf(TAG, "Bad chain ran off index " + endIndex 4008 + ": last task " + prev); 4009 sane = false; 4010 break; 4011 } 4012 } 4013 if (sane) { 4014 if (endIndex < taskIndex) { 4015 Slog.wtf(TAG, "Bad chain @" + endIndex 4016 + ": did not extend to task " + task + " @" + taskIndex); 4017 sane = false; 4018 } 4019 } 4020 if (sane) { 4021 // All looks good, we can just move all of the affiliated tasks 4022 // to the top. 4023 for (int i=topIndex; i<=endIndex; i++) { 4024 if (DEBUG_RECENTS) Slog.d(TAG, "addRecent: moving affiliated " + task 4025 + " from " + i + " to " + (i-topIndex)); 4026 TaskRecord cur = mRecentTasks.remove(i); 4027 mRecentTasks.add(i-topIndex, cur); 4028 } 4029 if (DEBUG_RECENTS) Slog.d(TAG, "addRecent: done moving tasks " + topIndex 4030 + " to " + endIndex); 4031 return true; 4032 } 4033 4034 // Whoops, couldn't do it. 4035 return false; 4036 } 4037 4038 final void addRecentTaskLocked(TaskRecord task) { 4039 final boolean isAffiliated = task.mAffiliatedTaskId != task.taskId 4040 || task.mNextAffiliateTaskId != -1 || task.mPrevAffiliateTaskId != -1; 4041 4042 int N = mRecentTasks.size(); 4043 // Quick case: check if the top-most recent task is the same. 4044 if (!isAffiliated && N > 0 && mRecentTasks.get(0) == task) { 4045 if (DEBUG_RECENTS) Slog.d(TAG, "addRecent: already at top: " + task); 4046 return; 4047 } 4048 // Another quick case: check if this is part of a set of affiliated 4049 // tasks that are at the top. 4050 if (isAffiliated && N > 0 && task.inRecents 4051 && task.mAffiliatedTaskId == mRecentTasks.get(0).mAffiliatedTaskId) { 4052 if (DEBUG_RECENTS) Slog.d(TAG, "addRecent: affiliated " + mRecentTasks.get(0) 4053 + " at top when adding " + task); 4054 return; 4055 } 4056 // Another quick case: never add voice sessions. 4057 if (task.voiceSession != null) { 4058 if (DEBUG_RECENTS) Slog.d(TAG, "addRecent: not adding voice interaction " + task); 4059 return; 4060 } 4061 4062 boolean needAffiliationFix = false; 4063 4064 // Slightly less quick case: the task is already in recents, so all we need 4065 // to do is move it. 4066 if (task.inRecents) { 4067 int taskIndex = mRecentTasks.indexOf(task); 4068 if (taskIndex >= 0) { 4069 if (!isAffiliated) { 4070 // Simple case: this is not an affiliated task, so we just move it to the front. 4071 mRecentTasks.remove(taskIndex); 4072 mRecentTasks.add(0, task); 4073 notifyTaskPersisterLocked(task, false); 4074 if (DEBUG_RECENTS) Slog.d(TAG, "addRecent: moving to top " + task 4075 + " from " + taskIndex); 4076 return; 4077 } else { 4078 // More complicated: need to keep all affiliated tasks together. 4079 if (moveAffiliatedTasksToFront(task, taskIndex)) { 4080 // All went well. 4081 return; 4082 } 4083 4084 // Uh oh... something bad in the affiliation chain, try to rebuild 4085 // everything and then go through our general path of adding a new task. 4086 needAffiliationFix = true; 4087 } 4088 } else { 4089 Slog.wtf(TAG, "Task with inRecent not in recents: " + task); 4090 needAffiliationFix = true; 4091 } 4092 } 4093 4094 if (DEBUG_RECENTS) Slog.d(TAG, "addRecent: trimming tasks for " + task); 4095 trimRecentsForTask(task, true); 4096 4097 N = mRecentTasks.size(); 4098 while (N >= ActivityManager.getMaxRecentTasksStatic()) { 4099 final TaskRecord tr = mRecentTasks.remove(N - 1); 4100 tr.removedFromRecents(mTaskPersister); 4101 N--; 4102 } 4103 task.inRecents = true; 4104 if (!isAffiliated || needAffiliationFix) { 4105 // If this is a simple non-affiliated task, or we had some failure trying to 4106 // handle it as part of an affilated task, then just place it at the top. 4107 mRecentTasks.add(0, task); 4108 } else if (isAffiliated) { 4109 // If this is a new affiliated task, then move all of the affiliated tasks 4110 // to the front and insert this new one. 4111 TaskRecord other = task.mNextAffiliate; 4112 if (other == null) { 4113 other = task.mPrevAffiliate; 4114 } 4115 if (other != null) { 4116 int otherIndex = mRecentTasks.indexOf(other); 4117 if (otherIndex >= 0) { 4118 // Insert new task at appropriate location. 4119 int taskIndex; 4120 if (other == task.mNextAffiliate) { 4121 // We found the index of our next affiliation, which is who is 4122 // before us in the list, so add after that point. 4123 taskIndex = otherIndex+1; 4124 } else { 4125 // We found the index of our previous affiliation, which is who is 4126 // after us in the list, so add at their position. 4127 taskIndex = otherIndex; 4128 } 4129 if (DEBUG_RECENTS) Slog.d(TAG, "addRecent: new affiliated task added at " 4130 + taskIndex + ": " + task); 4131 mRecentTasks.add(taskIndex, task); 4132 4133 // Now move everything to the front. 4134 if (moveAffiliatedTasksToFront(task, taskIndex)) { 4135 // All went well. 4136 return; 4137 } 4138 4139 // Uh oh... something bad in the affiliation chain, try to rebuild 4140 // everything and then go through our general path of adding a new task. 4141 needAffiliationFix = true; 4142 } else { 4143 if (DEBUG_RECENTS) Slog.d(TAG, "addRecent: couldn't find other affiliation " 4144 + other); 4145 needAffiliationFix = true; 4146 } 4147 } else { 4148 if (DEBUG_RECENTS) Slog.d(TAG, 4149 "addRecent: adding affiliated task without next/prev:" + task); 4150 needAffiliationFix = true; 4151 } 4152 } 4153 if (DEBUG_RECENTS) Slog.d(TAG, "addRecent: adding " + task); 4154 4155 if (needAffiliationFix) { 4156 if (DEBUG_RECENTS) Slog.d(TAG, "addRecent: regrouping affiliations"); 4157 cleanupRecentTasksLocked(task.userId); 4158 } 4159 } 4160 4161 /** 4162 * If needed, remove oldest existing entries in recents that are for the same kind 4163 * of task as the given one. 4164 */ 4165 int trimRecentsForTask(TaskRecord task, boolean doTrim) { 4166 int N = mRecentTasks.size(); 4167 final Intent intent = task.intent; 4168 final boolean document = intent != null && intent.isDocument(); 4169 4170 int maxRecents = task.maxRecents - 1; 4171 for (int i=0; i<N; i++) { 4172 final TaskRecord tr = mRecentTasks.get(i); 4173 if (task != tr) { 4174 if (task.userId != tr.userId) { 4175 continue; 4176 } 4177 if (i > MAX_RECENT_BITMAPS) { 4178 tr.freeLastThumbnail(); 4179 } 4180 final Intent trIntent = tr.intent; 4181 if ((task.affinity == null || !task.affinity.equals(tr.affinity)) && 4182 (intent == null || !intent.filterEquals(trIntent))) { 4183 continue; 4184 } 4185 final boolean trIsDocument = trIntent != null && trIntent.isDocument(); 4186 if (document && trIsDocument) { 4187 // These are the same document activity (not necessarily the same doc). 4188 if (maxRecents > 0) { 4189 --maxRecents; 4190 continue; 4191 } 4192 // Hit the maximum number of documents for this task. Fall through 4193 // and remove this document from recents. 4194 } else if (document || trIsDocument) { 4195 // Only one of these is a document. Not the droid we're looking for. 4196 continue; 4197 } 4198 } 4199 4200 if (!doTrim) { 4201 // If the caller is not actually asking for a trim, just tell them we reached 4202 // a point where the trim would happen. 4203 return i; 4204 } 4205 4206 // Either task and tr are the same or, their affinities match or their intents match 4207 // and neither of them is a document, or they are documents using the same activity 4208 // and their maxRecents has been reached. 4209 tr.disposeThumbnail(); 4210 mRecentTasks.remove(i); 4211 if (task != tr) { 4212 tr.removedFromRecents(mTaskPersister); 4213 } 4214 i--; 4215 N--; 4216 if (task.intent == null) { 4217 // If the new recent task we are adding is not fully 4218 // specified, then replace it with the existing recent task. 4219 task = tr; 4220 } 4221 notifyTaskPersisterLocked(tr, false); 4222 } 4223 4224 return -1; 4225 } 4226 4227 @Override 4228 public void reportActivityFullyDrawn(IBinder token) { 4229 synchronized (this) { 4230 ActivityRecord r = ActivityRecord.isInStackLocked(token); 4231 if (r == null) { 4232 return; 4233 } 4234 r.reportFullyDrawnLocked(); 4235 } 4236 } 4237 4238 @Override 4239 public void setRequestedOrientation(IBinder token, int requestedOrientation) { 4240 synchronized (this) { 4241 ActivityRecord r = ActivityRecord.isInStackLocked(token); 4242 if (r == null) { 4243 return; 4244 } 4245 final long origId = Binder.clearCallingIdentity(); 4246 mWindowManager.setAppOrientation(r.appToken, requestedOrientation); 4247 Configuration config = mWindowManager.updateOrientationFromAppTokens( 4248 mConfiguration, r.mayFreezeScreenLocked(r.app) ? r.appToken : null); 4249 if (config != null) { 4250 r.frozenBeforeDestroy = true; 4251 if (!updateConfigurationLocked(config, r, false, false)) { 4252 mStackSupervisor.resumeTopActivitiesLocked(); 4253 } 4254 } 4255 Binder.restoreCallingIdentity(origId); 4256 } 4257 } 4258 4259 @Override 4260 public int getRequestedOrientation(IBinder token) { 4261 synchronized (this) { 4262 ActivityRecord r = ActivityRecord.isInStackLocked(token); 4263 if (r == null) { 4264 return ActivityInfo.SCREEN_ORIENTATION_UNSPECIFIED; 4265 } 4266 return mWindowManager.getAppOrientation(r.appToken); 4267 } 4268 } 4269 4270 /** 4271 * This is the internal entry point for handling Activity.finish(). 4272 * 4273 * @param token The Binder token referencing the Activity we want to finish. 4274 * @param resultCode Result code, if any, from this Activity. 4275 * @param resultData Result data (Intent), if any, from this Activity. 4276 * @param finishTask Whether to finish the task associated with this Activity. Only applies to 4277 * the root Activity in the task. 4278 * 4279 * @return Returns true if the activity successfully finished, or false if it is still running. 4280 */ 4281 @Override 4282 public final boolean finishActivity(IBinder token, int resultCode, Intent resultData, 4283 boolean finishTask) { 4284 // Refuse possible leaked file descriptors 4285 if (resultData != null && resultData.hasFileDescriptors() == true) { 4286 throw new IllegalArgumentException("File descriptors passed in Intent"); 4287 } 4288 4289 synchronized(this) { 4290 ActivityRecord r = ActivityRecord.isInStackLocked(token); 4291 if (r == null) { 4292 return true; 4293 } 4294 // Keep track of the root activity of the task before we finish it 4295 TaskRecord tr = r.task; 4296 ActivityRecord rootR = tr.getRootActivity(); 4297 if (rootR == null) { 4298 Slog.w(TAG, "Finishing task with all activities already finished"); 4299 } 4300 // Do not allow task to finish in Lock Task mode. 4301 if (tr == mStackSupervisor.mLockTaskModeTask) { 4302 if (rootR == r) { 4303 Slog.i(TAG, "Not finishing task in lock task mode"); 4304 mStackSupervisor.showLockTaskToast(); 4305 return false; 4306 } 4307 } 4308 if (mController != null) { 4309 // Find the first activity that is not finishing. 4310 ActivityRecord next = r.task.stack.topRunningActivityLocked(token, 0); 4311 if (next != null) { 4312 // ask watcher if this is allowed 4313 boolean resumeOK = true; 4314 try { 4315 resumeOK = mController.activityResuming(next.packageName); 4316 } catch (RemoteException e) { 4317 mController = null; 4318 Watchdog.getInstance().setActivityController(null); 4319 } 4320 4321 if (!resumeOK) { 4322 Slog.i(TAG, "Not finishing activity because controller resumed"); 4323 return false; 4324 } 4325 } 4326 } 4327 final long origId = Binder.clearCallingIdentity(); 4328 try { 4329 boolean res; 4330 if (finishTask && r == rootR) { 4331 // If requested, remove the task that is associated to this activity only if it 4332 // was the root activity in the task. The result code and data is ignored 4333 // because we don't support returning them across task boundaries. 4334 res = removeTaskByIdLocked(tr.taskId, false); 4335 if (!res) { 4336 Slog.i(TAG, "Removing task failed to finish activity"); 4337 } 4338 } else { 4339 res = tr.stack.requestFinishActivityLocked(token, resultCode, 4340 resultData, "app-request", true); 4341 if (!res) { 4342 Slog.i(TAG, "Failed to finish by app-request"); 4343 } 4344 } 4345 return res; 4346 } finally { 4347 Binder.restoreCallingIdentity(origId); 4348 } 4349 } 4350 } 4351 4352 @Override 4353 public final void finishHeavyWeightApp() { 4354 if (checkCallingPermission(android.Manifest.permission.FORCE_STOP_PACKAGES) 4355 != PackageManager.PERMISSION_GRANTED) { 4356 String msg = "Permission Denial: finishHeavyWeightApp() from pid=" 4357 + Binder.getCallingPid() 4358 + ", uid=" + Binder.getCallingUid() 4359 + " requires " + android.Manifest.permission.FORCE_STOP_PACKAGES; 4360 Slog.w(TAG, msg); 4361 throw new SecurityException(msg); 4362 } 4363 4364 synchronized(this) { 4365 if (mHeavyWeightProcess == null) { 4366 return; 4367 } 4368 4369 ArrayList<ActivityRecord> activities = new ArrayList<ActivityRecord>( 4370 mHeavyWeightProcess.activities); 4371 for (int i=0; i<activities.size(); i++) { 4372 ActivityRecord r = activities.get(i); 4373 if (!r.finishing) { 4374 r.task.stack.finishActivityLocked(r, Activity.RESULT_CANCELED, 4375 null, "finish-heavy", true); 4376 } 4377 } 4378 4379 mHandler.sendMessage(mHandler.obtainMessage(CANCEL_HEAVY_NOTIFICATION_MSG, 4380 mHeavyWeightProcess.userId, 0)); 4381 mHeavyWeightProcess = null; 4382 } 4383 } 4384 4385 @Override 4386 public void crashApplication(int uid, int initialPid, String packageName, 4387 String message) { 4388 if (checkCallingPermission(android.Manifest.permission.FORCE_STOP_PACKAGES) 4389 != PackageManager.PERMISSION_GRANTED) { 4390 String msg = "Permission Denial: crashApplication() from pid=" 4391 + Binder.getCallingPid() 4392 + ", uid=" + Binder.getCallingUid() 4393 + " requires " + android.Manifest.permission.FORCE_STOP_PACKAGES; 4394 Slog.w(TAG, msg); 4395 throw new SecurityException(msg); 4396 } 4397 4398 synchronized(this) { 4399 ProcessRecord proc = null; 4400 4401 // Figure out which process to kill. We don't trust that initialPid 4402 // still has any relation to current pids, so must scan through the 4403 // list. 4404 synchronized (mPidsSelfLocked) { 4405 for (int i=0; i<mPidsSelfLocked.size(); i++) { 4406 ProcessRecord p = mPidsSelfLocked.valueAt(i); 4407 if (p.uid != uid) { 4408 continue; 4409 } 4410 if (p.pid == initialPid) { 4411 proc = p; 4412 break; 4413 } 4414 if (p.pkgList.containsKey(packageName)) { 4415 proc = p; 4416 } 4417 } 4418 } 4419 4420 if (proc == null) { 4421 Slog.w(TAG, "crashApplication: nothing for uid=" + uid 4422 + " initialPid=" + initialPid 4423 + " packageName=" + packageName); 4424 return; 4425 } 4426 4427 if (proc.thread != null) { 4428 if (proc.pid == Process.myPid()) { 4429 Log.w(TAG, "crashApplication: trying to crash self!"); 4430 return; 4431 } 4432 long ident = Binder.clearCallingIdentity(); 4433 try { 4434 proc.thread.scheduleCrash(message); 4435 } catch (RemoteException e) { 4436 } 4437 Binder.restoreCallingIdentity(ident); 4438 } 4439 } 4440 } 4441 4442 @Override 4443 public final void finishSubActivity(IBinder token, String resultWho, 4444 int requestCode) { 4445 synchronized(this) { 4446 final long origId = Binder.clearCallingIdentity(); 4447 ActivityRecord r = ActivityRecord.isInStackLocked(token); 4448 if (r != null) { 4449 r.task.stack.finishSubActivityLocked(r, resultWho, requestCode); 4450 } 4451 Binder.restoreCallingIdentity(origId); 4452 } 4453 } 4454 4455 @Override 4456 public boolean finishActivityAffinity(IBinder token) { 4457 synchronized(this) { 4458 final long origId = Binder.clearCallingIdentity(); 4459 try { 4460 ActivityRecord r = ActivityRecord.isInStackLocked(token); 4461 4462 ActivityRecord rootR = r.task.getRootActivity(); 4463 // Do not allow task to finish in Lock Task mode. 4464 if (r.task == mStackSupervisor.mLockTaskModeTask) { 4465 if (rootR == r) { 4466 mStackSupervisor.showLockTaskToast(); 4467 return false; 4468 } 4469 } 4470 boolean res = false; 4471 if (r != null) { 4472 res = r.task.stack.finishActivityAffinityLocked(r); 4473 } 4474 return res; 4475 } finally { 4476 Binder.restoreCallingIdentity(origId); 4477 } 4478 } 4479 } 4480 4481 @Override 4482 public void finishVoiceTask(IVoiceInteractionSession session) { 4483 synchronized(this) { 4484 final long origId = Binder.clearCallingIdentity(); 4485 try { 4486 mStackSupervisor.finishVoiceTask(session); 4487 } finally { 4488 Binder.restoreCallingIdentity(origId); 4489 } 4490 } 4491 4492 } 4493 4494 @Override 4495 public boolean releaseActivityInstance(IBinder token) { 4496 synchronized(this) { 4497 final long origId = Binder.clearCallingIdentity(); 4498 try { 4499 ActivityRecord r = ActivityRecord.isInStackLocked(token); 4500 if (r.task == null || r.task.stack == null) { 4501 return false; 4502 } 4503 return r.task.stack.safelyDestroyActivityLocked(r, "app-req"); 4504 } finally { 4505 Binder.restoreCallingIdentity(origId); 4506 } 4507 } 4508 } 4509 4510 @Override 4511 public void releaseSomeActivities(IApplicationThread appInt) { 4512 synchronized(this) { 4513 final long origId = Binder.clearCallingIdentity(); 4514 try { 4515 ProcessRecord app = getRecordForAppLocked(appInt); 4516 mStackSupervisor.releaseSomeActivitiesLocked(app, "low-mem"); 4517 } finally { 4518 Binder.restoreCallingIdentity(origId); 4519 } 4520 } 4521 } 4522 4523 @Override 4524 public boolean willActivityBeVisible(IBinder token) { 4525 synchronized(this) { 4526 ActivityStack stack = ActivityRecord.getStackLocked(token); 4527 if (stack != null) { 4528 return stack.willActivityBeVisibleLocked(token); 4529 } 4530 return false; 4531 } 4532 } 4533 4534 @Override 4535 public void overridePendingTransition(IBinder token, String packageName, 4536 int enterAnim, int exitAnim) { 4537 synchronized(this) { 4538 ActivityRecord self = ActivityRecord.isInStackLocked(token); 4539 if (self == null) { 4540 return; 4541 } 4542 4543 final long origId = Binder.clearCallingIdentity(); 4544 4545 if (self.state == ActivityState.RESUMED 4546 || self.state == ActivityState.PAUSING) { 4547 mWindowManager.overridePendingAppTransition(packageName, 4548 enterAnim, exitAnim, null); 4549 } 4550 4551 Binder.restoreCallingIdentity(origId); 4552 } 4553 } 4554 4555 /** 4556 * Main function for removing an existing process from the activity manager 4557 * as a result of that process going away. Clears out all connections 4558 * to the process. 4559 */ 4560 private final void handleAppDiedLocked(ProcessRecord app, 4561 boolean restarting, boolean allowRestart) { 4562 int pid = app.pid; 4563 boolean kept = cleanUpApplicationRecordLocked(app, restarting, allowRestart, -1); 4564 if (!kept && !restarting) { 4565 removeLruProcessLocked(app); 4566 if (pid > 0) { 4567 ProcessList.remove(pid); 4568 } 4569 } 4570 4571 if (mProfileProc == app) { 4572 clearProfilerLocked(); 4573 } 4574 4575 // Remove this application's activities from active lists. 4576 boolean hasVisibleActivities = mStackSupervisor.handleAppDiedLocked(app); 4577 4578 app.activities.clear(); 4579 4580 if (app.instrumentationClass != null) { 4581 Slog.w(TAG, "Crash of app " + app.processName 4582 + " running instrumentation " + app.instrumentationClass); 4583 Bundle info = new Bundle(); 4584 info.putString("shortMsg", "Process crashed."); 4585 finishInstrumentationLocked(app, Activity.RESULT_CANCELED, info); 4586 } 4587 4588 if (!restarting) { 4589 if (!mStackSupervisor.resumeTopActivitiesLocked()) { 4590 // If there was nothing to resume, and we are not already 4591 // restarting this process, but there is a visible activity that 4592 // is hosted by the process... then make sure all visible 4593 // activities are running, taking care of restarting this 4594 // process. 4595 if (hasVisibleActivities) { 4596 mStackSupervisor.ensureActivitiesVisibleLocked(null, 0); 4597 } 4598 } 4599 } 4600 } 4601 4602 private final int getLRURecordIndexForAppLocked(IApplicationThread thread) { 4603 IBinder threadBinder = thread.asBinder(); 4604 // Find the application record. 4605 for (int i=mLruProcesses.size()-1; i>=0; i--) { 4606 ProcessRecord rec = mLruProcesses.get(i); 4607 if (rec.thread != null && rec.thread.asBinder() == threadBinder) { 4608 return i; 4609 } 4610 } 4611 return -1; 4612 } 4613 4614 final ProcessRecord getRecordForAppLocked( 4615 IApplicationThread thread) { 4616 if (thread == null) { 4617 return null; 4618 } 4619 4620 int appIndex = getLRURecordIndexForAppLocked(thread); 4621 return appIndex >= 0 ? mLruProcesses.get(appIndex) : null; 4622 } 4623 4624 final void doLowMemReportIfNeededLocked(ProcessRecord dyingProc) { 4625 // If there are no longer any background processes running, 4626 // and the app that died was not running instrumentation, 4627 // then tell everyone we are now low on memory. 4628 boolean haveBg = false; 4629 for (int i=mLruProcesses.size()-1; i>=0; i--) { 4630 ProcessRecord rec = mLruProcesses.get(i); 4631 if (rec.thread != null 4632 && rec.setProcState >= ActivityManager.PROCESS_STATE_CACHED_ACTIVITY) { 4633 haveBg = true; 4634 break; 4635 } 4636 } 4637 4638 if (!haveBg) { 4639 boolean doReport = "1".equals(SystemProperties.get(SYSTEM_DEBUGGABLE, "0")); 4640 if (doReport) { 4641 long now = SystemClock.uptimeMillis(); 4642 if (now < (mLastMemUsageReportTime+5*60*1000)) { 4643 doReport = false; 4644 } else { 4645 mLastMemUsageReportTime = now; 4646 } 4647 } 4648 final ArrayList<ProcessMemInfo> memInfos 4649 = doReport ? new ArrayList<ProcessMemInfo>(mLruProcesses.size()) : null; 4650 EventLog.writeEvent(EventLogTags.AM_LOW_MEMORY, mLruProcesses.size()); 4651 long now = SystemClock.uptimeMillis(); 4652 for (int i=mLruProcesses.size()-1; i>=0; i--) { 4653 ProcessRecord rec = mLruProcesses.get(i); 4654 if (rec == dyingProc || rec.thread == null) { 4655 continue; 4656 } 4657 if (doReport) { 4658 memInfos.add(new ProcessMemInfo(rec.processName, rec.pid, rec.setAdj, 4659 rec.setProcState, rec.adjType, rec.makeAdjReason())); 4660 } 4661 if ((rec.lastLowMemory+GC_MIN_INTERVAL) <= now) { 4662 // The low memory report is overriding any current 4663 // state for a GC request. Make sure to do 4664 // heavy/important/visible/foreground processes first. 4665 if (rec.setAdj <= ProcessList.HEAVY_WEIGHT_APP_ADJ) { 4666 rec.lastRequestedGc = 0; 4667 } else { 4668 rec.lastRequestedGc = rec.lastLowMemory; 4669 } 4670 rec.reportLowMemory = true; 4671 rec.lastLowMemory = now; 4672 mProcessesToGc.remove(rec); 4673 addProcessToGcListLocked(rec); 4674 } 4675 } 4676 if (doReport) { 4677 Message msg = mHandler.obtainMessage(REPORT_MEM_USAGE_MSG, memInfos); 4678 mHandler.sendMessage(msg); 4679 } 4680 scheduleAppGcsLocked(); 4681 } 4682 } 4683 4684 final void appDiedLocked(ProcessRecord app) { 4685 appDiedLocked(app, app.pid, app.thread); 4686 } 4687 4688 final void appDiedLocked(ProcessRecord app, int pid, IApplicationThread thread) { 4689 // First check if this ProcessRecord is actually active for the pid. 4690 synchronized (mPidsSelfLocked) { 4691 ProcessRecord curProc = mPidsSelfLocked.get(pid); 4692 if (curProc != app) { 4693 Slog.w(TAG, "Spurious death for " + app + ", curProc for " + pid + ": " + curProc); 4694 return; 4695 } 4696 } 4697 4698 BatteryStatsImpl stats = mBatteryStatsService.getActiveStatistics(); 4699 synchronized (stats) { 4700 stats.noteProcessDiedLocked(app.info.uid, pid); 4701 } 4702 4703 Process.killProcessQuiet(pid); 4704 Process.killProcessGroup(app.info.uid, pid); 4705 app.killed = true; 4706 4707 // Clean up already done if the process has been re-started. 4708 if (app.pid == pid && app.thread != null && 4709 app.thread.asBinder() == thread.asBinder()) { 4710 boolean doLowMem = app.instrumentationClass == null; 4711 boolean doOomAdj = doLowMem; 4712 if (!app.killedByAm) { 4713 Slog.i(TAG, "Process " + app.processName + " (pid " + pid 4714 + ") has died"); 4715 mAllowLowerMemLevel = true; 4716 } else { 4717 // Note that we always want to do oom adj to update our state with the 4718 // new number of procs. 4719 mAllowLowerMemLevel = false; 4720 doLowMem = false; 4721 } 4722 EventLog.writeEvent(EventLogTags.AM_PROC_DIED, app.userId, app.pid, app.processName); 4723 if (DEBUG_CLEANUP) Slog.v( 4724 TAG, "Dying app: " + app + ", pid: " + pid 4725 + ", thread: " + thread.asBinder()); 4726 handleAppDiedLocked(app, false, true); 4727 4728 if (doOomAdj) { 4729 updateOomAdjLocked(); 4730 } 4731 if (doLowMem) { 4732 doLowMemReportIfNeededLocked(app); 4733 } 4734 } else if (app.pid != pid) { 4735 // A new process has already been started. 4736 Slog.i(TAG, "Process " + app.processName + " (pid " + pid 4737 + ") has died and restarted (pid " + app.pid + ")."); 4738 EventLog.writeEvent(EventLogTags.AM_PROC_DIED, app.userId, app.pid, app.processName); 4739 } else if (DEBUG_PROCESSES) { 4740 Slog.d(TAG, "Received spurious death notification for thread " 4741 + thread.asBinder()); 4742 } 4743 } 4744 4745 /** 4746 * If a stack trace dump file is configured, dump process stack traces. 4747 * @param clearTraces causes the dump file to be erased prior to the new 4748 * traces being written, if true; when false, the new traces will be 4749 * appended to any existing file content. 4750 * @param firstPids of dalvik VM processes to dump stack traces for first 4751 * @param lastPids of dalvik VM processes to dump stack traces for last 4752 * @param nativeProcs optional list of native process names to dump stack crawls 4753 * @return file containing stack traces, or null if no dump file is configured 4754 */ 4755 public static File dumpStackTraces(boolean clearTraces, ArrayList<Integer> firstPids, 4756 ProcessCpuTracker processCpuTracker, SparseArray<Boolean> lastPids, String[] nativeProcs) { 4757 String tracesPath = SystemProperties.get("dalvik.vm.stack-trace-file", null); 4758 if (tracesPath == null || tracesPath.length() == 0) { 4759 return null; 4760 } 4761 4762 File tracesFile = new File(tracesPath); 4763 try { 4764 File tracesDir = tracesFile.getParentFile(); 4765 if (!tracesDir.exists()) { 4766 tracesDir.mkdirs(); 4767 if (!SELinux.restorecon(tracesDir)) { 4768 return null; 4769 } 4770 } 4771 FileUtils.setPermissions(tracesDir.getPath(), 0775, -1, -1); // drwxrwxr-x 4772 4773 if (clearTraces && tracesFile.exists()) tracesFile.delete(); 4774 tracesFile.createNewFile(); 4775 FileUtils.setPermissions(tracesFile.getPath(), 0666, -1, -1); // -rw-rw-rw- 4776 } catch (IOException e) { 4777 Slog.w(TAG, "Unable to prepare ANR traces file: " + tracesPath, e); 4778 return null; 4779 } 4780 4781 dumpStackTraces(tracesPath, firstPids, processCpuTracker, lastPids, nativeProcs); 4782 return tracesFile; 4783 } 4784 4785 private static void dumpStackTraces(String tracesPath, ArrayList<Integer> firstPids, 4786 ProcessCpuTracker processCpuTracker, SparseArray<Boolean> lastPids, String[] nativeProcs) { 4787 // Use a FileObserver to detect when traces finish writing. 4788 // The order of traces is considered important to maintain for legibility. 4789 FileObserver observer = new FileObserver(tracesPath, FileObserver.CLOSE_WRITE) { 4790 @Override 4791 public synchronized void onEvent(int event, String path) { notify(); } 4792 }; 4793 4794 try { 4795 observer.startWatching(); 4796 4797 // First collect all of the stacks of the most important pids. 4798 if (firstPids != null) { 4799 try { 4800 int num = firstPids.size(); 4801 for (int i = 0; i < num; i++) { 4802 synchronized (observer) { 4803 Process.sendSignal(firstPids.get(i), Process.SIGNAL_QUIT); 4804 observer.wait(200); // Wait for write-close, give up after 200msec 4805 } 4806 } 4807 } catch (InterruptedException e) { 4808 Slog.wtf(TAG, e); 4809 } 4810 } 4811 4812 // Next collect the stacks of the native pids 4813 if (nativeProcs != null) { 4814 int[] pids = Process.getPidsForCommands(nativeProcs); 4815 if (pids != null) { 4816 for (int pid : pids) { 4817 Debug.dumpNativeBacktraceToFile(pid, tracesPath); 4818 } 4819 } 4820 } 4821 4822 // Lastly, measure CPU usage. 4823 if (processCpuTracker != null) { 4824 processCpuTracker.init(); 4825 System.gc(); 4826 processCpuTracker.update(); 4827 try { 4828 synchronized (processCpuTracker) { 4829 processCpuTracker.wait(500); // measure over 1/2 second. 4830 } 4831 } catch (InterruptedException e) { 4832 } 4833 processCpuTracker.update(); 4834 4835 // We'll take the stack crawls of just the top apps using CPU. 4836 final int N = processCpuTracker.countWorkingStats(); 4837 int numProcs = 0; 4838 for (int i=0; i<N && numProcs<5; i++) { 4839 ProcessCpuTracker.Stats stats = processCpuTracker.getWorkingStats(i); 4840 if (lastPids.indexOfKey(stats.pid) >= 0) { 4841 numProcs++; 4842 try { 4843 synchronized (observer) { 4844 Process.sendSignal(stats.pid, Process.SIGNAL_QUIT); 4845 observer.wait(200); // Wait for write-close, give up after 200msec 4846 } 4847 } catch (InterruptedException e) { 4848 Slog.wtf(TAG, e); 4849 } 4850 4851 } 4852 } 4853 } 4854 } finally { 4855 observer.stopWatching(); 4856 } 4857 } 4858 4859 final void logAppTooSlow(ProcessRecord app, long startTime, String msg) { 4860 if (true || IS_USER_BUILD) { 4861 return; 4862 } 4863 String tracesPath = SystemProperties.get("dalvik.vm.stack-trace-file", null); 4864 if (tracesPath == null || tracesPath.length() == 0) { 4865 return; 4866 } 4867 4868 StrictMode.ThreadPolicy oldPolicy = StrictMode.allowThreadDiskReads(); 4869 StrictMode.allowThreadDiskWrites(); 4870 try { 4871 final File tracesFile = new File(tracesPath); 4872 final File tracesDir = tracesFile.getParentFile(); 4873 final File tracesTmp = new File(tracesDir, "__tmp__"); 4874 try { 4875 if (!tracesDir.exists()) { 4876 tracesDir.mkdirs(); 4877 if (!SELinux.restorecon(tracesDir.getPath())) { 4878 return; 4879 } 4880 } 4881 FileUtils.setPermissions(tracesDir.getPath(), 0775, -1, -1); // drwxrwxr-x 4882 4883 if (tracesFile.exists()) { 4884 tracesTmp.delete(); 4885 tracesFile.renameTo(tracesTmp); 4886 } 4887 StringBuilder sb = new StringBuilder(); 4888 Time tobj = new Time(); 4889 tobj.set(System.currentTimeMillis()); 4890 sb.append(tobj.format("%Y-%m-%d %H:%M:%S")); 4891 sb.append(": "); 4892 TimeUtils.formatDuration(SystemClock.uptimeMillis()-startTime, sb); 4893 sb.append(" since "); 4894 sb.append(msg); 4895 FileOutputStream fos = new FileOutputStream(tracesFile); 4896 fos.write(sb.toString().getBytes()); 4897 if (app == null) { 4898 fos.write("\n*** No application process!".getBytes()); 4899 } 4900 fos.close(); 4901 FileUtils.setPermissions(tracesFile.getPath(), 0666, -1, -1); // -rw-rw-rw- 4902 } catch (IOException e) { 4903 Slog.w(TAG, "Unable to prepare slow app traces file: " + tracesPath, e); 4904 return; 4905 } 4906 4907 if (app != null) { 4908 ArrayList<Integer> firstPids = new ArrayList<Integer>(); 4909 firstPids.add(app.pid); 4910 dumpStackTraces(tracesPath, firstPids, null, null, null); 4911 } 4912 4913 File lastTracesFile = null; 4914 File curTracesFile = null; 4915 for (int i=9; i>=0; i--) { 4916 String name = String.format(Locale.US, "slow%02d.txt", i); 4917 curTracesFile = new File(tracesDir, name); 4918 if (curTracesFile.exists()) { 4919 if (lastTracesFile != null) { 4920 curTracesFile.renameTo(lastTracesFile); 4921 } else { 4922 curTracesFile.delete(); 4923 } 4924 } 4925 lastTracesFile = curTracesFile; 4926 } 4927 tracesFile.renameTo(curTracesFile); 4928 if (tracesTmp.exists()) { 4929 tracesTmp.renameTo(tracesFile); 4930 } 4931 } finally { 4932 StrictMode.setThreadPolicy(oldPolicy); 4933 } 4934 } 4935 4936 final void appNotResponding(ProcessRecord app, ActivityRecord activity, 4937 ActivityRecord parent, boolean aboveSystem, final String annotation) { 4938 ArrayList<Integer> firstPids = new ArrayList<Integer>(5); 4939 SparseArray<Boolean> lastPids = new SparseArray<Boolean>(20); 4940 4941 if (mController != null) { 4942 try { 4943 // 0 == continue, -1 = kill process immediately 4944 int res = mController.appEarlyNotResponding(app.processName, app.pid, annotation); 4945 if (res < 0 && app.pid != MY_PID) { 4946 app.kill("anr", true); 4947 } 4948 } catch (RemoteException e) { 4949 mController = null; 4950 Watchdog.getInstance().setActivityController(null); 4951 } 4952 } 4953 4954 long anrTime = SystemClock.uptimeMillis(); 4955 if (MONITOR_CPU_USAGE) { 4956 updateCpuStatsNow(); 4957 } 4958 4959 synchronized (this) { 4960 // PowerManager.reboot() can block for a long time, so ignore ANRs while shutting down. 4961 if (mShuttingDown) { 4962 Slog.i(TAG, "During shutdown skipping ANR: " + app + " " + annotation); 4963 return; 4964 } else if (app.notResponding) { 4965 Slog.i(TAG, "Skipping duplicate ANR: " + app + " " + annotation); 4966 return; 4967 } else if (app.crashing) { 4968 Slog.i(TAG, "Crashing app skipping ANR: " + app + " " + annotation); 4969 return; 4970 } 4971 4972 // In case we come through here for the same app before completing 4973 // this one, mark as anring now so we will bail out. 4974 app.notResponding = true; 4975 4976 // Log the ANR to the event log. 4977 EventLog.writeEvent(EventLogTags.AM_ANR, app.userId, app.pid, 4978 app.processName, app.info.flags, annotation); 4979 4980 // Dump thread traces as quickly as we can, starting with "interesting" processes. 4981 firstPids.add(app.pid); 4982 4983 int parentPid = app.pid; 4984 if (parent != null && parent.app != null && parent.app.pid > 0) parentPid = parent.app.pid; 4985 if (parentPid != app.pid) firstPids.add(parentPid); 4986 4987 if (MY_PID != app.pid && MY_PID != parentPid) firstPids.add(MY_PID); 4988 4989 for (int i = mLruProcesses.size() - 1; i >= 0; i--) { 4990 ProcessRecord r = mLruProcesses.get(i); 4991 if (r != null && r.thread != null) { 4992 int pid = r.pid; 4993 if (pid > 0 && pid != app.pid && pid != parentPid && pid != MY_PID) { 4994 if (r.persistent) { 4995 firstPids.add(pid); 4996 } else { 4997 lastPids.put(pid, Boolean.TRUE); 4998 } 4999 } 5000 } 5001 } 5002 } 5003 5004 // Log the ANR to the main log. 5005 StringBuilder info = new StringBuilder(); 5006 info.setLength(0); 5007 info.append("ANR in ").append(app.processName); 5008 if (activity != null && activity.shortComponentName != null) { 5009 info.append(" (").append(activity.shortComponentName).append(")"); 5010 } 5011 info.append("\n"); 5012 info.append("PID: ").append(app.pid).append("\n"); 5013 if (annotation != null) { 5014 info.append("Reason: ").append(annotation).append("\n"); 5015 } 5016 if (parent != null && parent != activity) { 5017 info.append("Parent: ").append(parent.shortComponentName).append("\n"); 5018 } 5019 5020 final ProcessCpuTracker processCpuTracker = new ProcessCpuTracker(true); 5021 5022 File tracesFile = dumpStackTraces(true, firstPids, processCpuTracker, lastPids, 5023 NATIVE_STACKS_OF_INTEREST); 5024 5025 String cpuInfo = null; 5026 if (MONITOR_CPU_USAGE) { 5027 updateCpuStatsNow(); 5028 synchronized (mProcessCpuTracker) { 5029 cpuInfo = mProcessCpuTracker.printCurrentState(anrTime); 5030 } 5031 info.append(processCpuTracker.printCurrentLoad()); 5032 info.append(cpuInfo); 5033 } 5034 5035 info.append(processCpuTracker.printCurrentState(anrTime)); 5036 5037 Slog.e(TAG, info.toString()); 5038 if (tracesFile == null) { 5039 // There is no trace file, so dump (only) the alleged culprit's threads to the log 5040 Process.sendSignal(app.pid, Process.SIGNAL_QUIT); 5041 } 5042 5043 addErrorToDropBox("anr", app, app.processName, activity, parent, annotation, 5044 cpuInfo, tracesFile, null); 5045 5046 if (mController != null) { 5047 try { 5048 // 0 == show dialog, 1 = keep waiting, -1 = kill process immediately 5049 int res = mController.appNotResponding(app.processName, app.pid, info.toString()); 5050 if (res != 0) { 5051 if (res < 0 && app.pid != MY_PID) { 5052 app.kill("anr", true); 5053 } else { 5054 synchronized (this) { 5055 mServices.scheduleServiceTimeoutLocked(app); 5056 } 5057 } 5058 return; 5059 } 5060 } catch (RemoteException e) { 5061 mController = null; 5062 Watchdog.getInstance().setActivityController(null); 5063 } 5064 } 5065 5066 // Unless configured otherwise, swallow ANRs in background processes & kill the process. 5067 boolean showBackground = Settings.Secure.getInt(mContext.getContentResolver(), 5068 Settings.Secure.ANR_SHOW_BACKGROUND, 0) != 0; 5069 5070 synchronized (this) { 5071 if (!showBackground && !app.isInterestingToUserLocked() && app.pid != MY_PID) { 5072 app.kill("bg anr", true); 5073 return; 5074 } 5075 5076 // Set the app's notResponding state, and look up the errorReportReceiver 5077 makeAppNotRespondingLocked(app, 5078 activity != null ? activity.shortComponentName : null, 5079 annotation != null ? "ANR " + annotation : "ANR", 5080 info.toString()); 5081 5082 // Bring up the infamous App Not Responding dialog 5083 Message msg = Message.obtain(); 5084 HashMap<String, Object> map = new HashMap<String, Object>(); 5085 msg.what = SHOW_NOT_RESPONDING_MSG; 5086 msg.obj = map; 5087 msg.arg1 = aboveSystem ? 1 : 0; 5088 map.put("app", app); 5089 if (activity != null) { 5090 map.put("activity", activity); 5091 } 5092 5093 mHandler.sendMessage(msg); 5094 } 5095 } 5096 5097 final void showLaunchWarningLocked(final ActivityRecord cur, final ActivityRecord next) { 5098 if (!mLaunchWarningShown) { 5099 mLaunchWarningShown = true; 5100 mHandler.post(new Runnable() { 5101 @Override 5102 public void run() { 5103 synchronized (ActivityManagerService.this) { 5104 final Dialog d = new LaunchWarningWindow(mContext, cur, next); 5105 d.show(); 5106 mHandler.postDelayed(new Runnable() { 5107 @Override 5108 public void run() { 5109 synchronized (ActivityManagerService.this) { 5110 d.dismiss(); 5111 mLaunchWarningShown = false; 5112 } 5113 } 5114 }, 4000); 5115 } 5116 } 5117 }); 5118 } 5119 } 5120 5121 @Override 5122 public boolean clearApplicationUserData(final String packageName, 5123 final IPackageDataObserver observer, int userId) { 5124 enforceNotIsolatedCaller("clearApplicationUserData"); 5125 int uid = Binder.getCallingUid(); 5126 int pid = Binder.getCallingPid(); 5127 userId = handleIncomingUser(pid, uid, 5128 userId, false, ALLOW_FULL_ONLY, "clearApplicationUserData", null); 5129 long callingId = Binder.clearCallingIdentity(); 5130 try { 5131 IPackageManager pm = AppGlobals.getPackageManager(); 5132 int pkgUid = -1; 5133 synchronized(this) { 5134 try { 5135 pkgUid = pm.getPackageUid(packageName, userId); 5136 } catch (RemoteException e) { 5137 } 5138 if (pkgUid == -1) { 5139 Slog.w(TAG, "Invalid packageName: " + packageName); 5140 if (observer != null) { 5141 try { 5142 observer.onRemoveCompleted(packageName, false); 5143 } catch (RemoteException e) { 5144 Slog.i(TAG, "Observer no longer exists."); 5145 } 5146 } 5147 return false; 5148 } 5149 if (uid == pkgUid || checkComponentPermission( 5150 android.Manifest.permission.CLEAR_APP_USER_DATA, 5151 pid, uid, -1, true) 5152 == PackageManager.PERMISSION_GRANTED) { 5153 forceStopPackageLocked(packageName, pkgUid, "clear data"); 5154 } else { 5155 throw new SecurityException("PID " + pid + " does not have permission " 5156 + android.Manifest.permission.CLEAR_APP_USER_DATA + " to clear data" 5157 + " of package " + packageName); 5158 } 5159 5160 // Remove all tasks match the cleared application package and user 5161 for (int i = mRecentTasks.size() - 1; i >= 0; i--) { 5162 final TaskRecord tr = mRecentTasks.get(i); 5163 final String taskPackageName = 5164 tr.getBaseIntent().getComponent().getPackageName(); 5165 if (tr.userId != userId) continue; 5166 if (!taskPackageName.equals(packageName)) continue; 5167 removeTaskByIdLocked(tr.taskId, false); 5168 } 5169 } 5170 5171 try { 5172 // Clear application user data 5173 pm.clearApplicationUserData(packageName, observer, userId); 5174 5175 synchronized(this) { 5176 // Remove all permissions granted from/to this package 5177 removeUriPermissionsForPackageLocked(packageName, userId, true); 5178 } 5179 5180 Intent intent = new Intent(Intent.ACTION_PACKAGE_DATA_CLEARED, 5181 Uri.fromParts("package", packageName, null)); 5182 intent.putExtra(Intent.EXTRA_UID, pkgUid); 5183 broadcastIntentInPackage("android", Process.SYSTEM_UID, intent, 5184 null, null, 0, null, null, null, false, false, userId); 5185 } catch (RemoteException e) { 5186 } 5187 } finally { 5188 Binder.restoreCallingIdentity(callingId); 5189 } 5190 return true; 5191 } 5192 5193 @Override 5194 public void killBackgroundProcesses(final String packageName, int userId) { 5195 if (checkCallingPermission(android.Manifest.permission.KILL_BACKGROUND_PROCESSES) 5196 != PackageManager.PERMISSION_GRANTED && 5197 checkCallingPermission(android.Manifest.permission.RESTART_PACKAGES) 5198 != PackageManager.PERMISSION_GRANTED) { 5199 String msg = "Permission Denial: killBackgroundProcesses() from pid=" 5200 + Binder.getCallingPid() 5201 + ", uid=" + Binder.getCallingUid() 5202 + " requires " + android.Manifest.permission.KILL_BACKGROUND_PROCESSES; 5203 Slog.w(TAG, msg); 5204 throw new SecurityException(msg); 5205 } 5206 5207 userId = handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(), 5208 userId, true, ALLOW_FULL_ONLY, "killBackgroundProcesses", null); 5209 long callingId = Binder.clearCallingIdentity(); 5210 try { 5211 IPackageManager pm = AppGlobals.getPackageManager(); 5212 synchronized(this) { 5213 int appId = -1; 5214 try { 5215 appId = UserHandle.getAppId(pm.getPackageUid(packageName, 0)); 5216 } catch (RemoteException e) { 5217 } 5218 if (appId == -1) { 5219 Slog.w(TAG, "Invalid packageName: " + packageName); 5220 return; 5221 } 5222 killPackageProcessesLocked(packageName, appId, userId, 5223 ProcessList.SERVICE_ADJ, false, true, true, false, "kill background"); 5224 } 5225 } finally { 5226 Binder.restoreCallingIdentity(callingId); 5227 } 5228 } 5229 5230 @Override 5231 public void killAllBackgroundProcesses() { 5232 if (checkCallingPermission(android.Manifest.permission.KILL_BACKGROUND_PROCESSES) 5233 != PackageManager.PERMISSION_GRANTED) { 5234 String msg = "Permission Denial: killAllBackgroundProcesses() from pid=" 5235 + Binder.getCallingPid() 5236 + ", uid=" + Binder.getCallingUid() 5237 + " requires " + android.Manifest.permission.KILL_BACKGROUND_PROCESSES; 5238 Slog.w(TAG, msg); 5239 throw new SecurityException(msg); 5240 } 5241 5242 long callingId = Binder.clearCallingIdentity(); 5243 try { 5244 synchronized(this) { 5245 ArrayList<ProcessRecord> procs = new ArrayList<ProcessRecord>(); 5246 final int NP = mProcessNames.getMap().size(); 5247 for (int ip=0; ip<NP; ip++) { 5248 SparseArray<ProcessRecord> apps = mProcessNames.getMap().valueAt(ip); 5249 final int NA = apps.size(); 5250 for (int ia=0; ia<NA; ia++) { 5251 ProcessRecord app = apps.valueAt(ia); 5252 if (app.persistent) { 5253 // we don't kill persistent processes 5254 continue; 5255 } 5256 if (app.removed) { 5257 procs.add(app); 5258 } else if (app.setAdj >= ProcessList.CACHED_APP_MIN_ADJ) { 5259 app.removed = true; 5260 procs.add(app); 5261 } 5262 } 5263 } 5264 5265 int N = procs.size(); 5266 for (int i=0; i<N; i++) { 5267 removeProcessLocked(procs.get(i), false, true, "kill all background"); 5268 } 5269 mAllowLowerMemLevel = true; 5270 updateOomAdjLocked(); 5271 doLowMemReportIfNeededLocked(null); 5272 } 5273 } finally { 5274 Binder.restoreCallingIdentity(callingId); 5275 } 5276 } 5277 5278 @Override 5279 public void forceStopPackage(final String packageName, int userId) { 5280 if (checkCallingPermission(android.Manifest.permission.FORCE_STOP_PACKAGES) 5281 != PackageManager.PERMISSION_GRANTED) { 5282 String msg = "Permission Denial: forceStopPackage() from pid=" 5283 + Binder.getCallingPid() 5284 + ", uid=" + Binder.getCallingUid() 5285 + " requires " + android.Manifest.permission.FORCE_STOP_PACKAGES; 5286 Slog.w(TAG, msg); 5287 throw new SecurityException(msg); 5288 } 5289 final int callingPid = Binder.getCallingPid(); 5290 userId = handleIncomingUser(callingPid, Binder.getCallingUid(), 5291 userId, true, ALLOW_FULL_ONLY, "forceStopPackage", null); 5292 long callingId = Binder.clearCallingIdentity(); 5293 try { 5294 IPackageManager pm = AppGlobals.getPackageManager(); 5295 synchronized(this) { 5296 int[] users = userId == UserHandle.USER_ALL 5297 ? getUsersLocked() : new int[] { userId }; 5298 for (int user : users) { 5299 int pkgUid = -1; 5300 try { 5301 pkgUid = pm.getPackageUid(packageName, user); 5302 } catch (RemoteException e) { 5303 } 5304 if (pkgUid == -1) { 5305 Slog.w(TAG, "Invalid packageName: " + packageName); 5306 continue; 5307 } 5308 try { 5309 pm.setPackageStoppedState(packageName, true, user); 5310 } catch (RemoteException e) { 5311 } catch (IllegalArgumentException e) { 5312 Slog.w(TAG, "Failed trying to unstop package " 5313 + packageName + ": " + e); 5314 } 5315 if (isUserRunningLocked(user, false)) { 5316 forceStopPackageLocked(packageName, pkgUid, "from pid " + callingPid); 5317 } 5318 } 5319 } 5320 } finally { 5321 Binder.restoreCallingIdentity(callingId); 5322 } 5323 } 5324 5325 @Override 5326 public void addPackageDependency(String packageName) { 5327 synchronized (this) { 5328 int callingPid = Binder.getCallingPid(); 5329 if (callingPid == Process.myPid()) { 5330 // Yeah, um, no. 5331 Slog.w(TAG, "Can't addPackageDependency on system process"); 5332 return; 5333 } 5334 ProcessRecord proc; 5335 synchronized (mPidsSelfLocked) { 5336 proc = mPidsSelfLocked.get(Binder.getCallingPid()); 5337 } 5338 if (proc != null) { 5339 if (proc.pkgDeps == null) { 5340 proc.pkgDeps = new ArraySet<String>(1); 5341 } 5342 proc.pkgDeps.add(packageName); 5343 } 5344 } 5345 } 5346 5347 /* 5348 * The pkg name and app id have to be specified. 5349 */ 5350 @Override 5351 public void killApplicationWithAppId(String pkg, int appid, String reason) { 5352 if (pkg == null) { 5353 return; 5354 } 5355 // Make sure the uid is valid. 5356 if (appid < 0) { 5357 Slog.w(TAG, "Invalid appid specified for pkg : " + pkg); 5358 return; 5359 } 5360 int callerUid = Binder.getCallingUid(); 5361 // Only the system server can kill an application 5362 if (callerUid == Process.SYSTEM_UID) { 5363 // Post an aysnc message to kill the application 5364 Message msg = mHandler.obtainMessage(KILL_APPLICATION_MSG); 5365 msg.arg1 = appid; 5366 msg.arg2 = 0; 5367 Bundle bundle = new Bundle(); 5368 bundle.putString("pkg", pkg); 5369 bundle.putString("reason", reason); 5370 msg.obj = bundle; 5371 mHandler.sendMessage(msg); 5372 } else { 5373 throw new SecurityException(callerUid + " cannot kill pkg: " + 5374 pkg); 5375 } 5376 } 5377 5378 @Override 5379 public void closeSystemDialogs(String reason) { 5380 enforceNotIsolatedCaller("closeSystemDialogs"); 5381 5382 final int pid = Binder.getCallingPid(); 5383 final int uid = Binder.getCallingUid(); 5384 final long origId = Binder.clearCallingIdentity(); 5385 try { 5386 synchronized (this) { 5387 // Only allow this from foreground processes, so that background 5388 // applications can't abuse it to prevent system UI from being shown. 5389 if (uid >= Process.FIRST_APPLICATION_UID) { 5390 ProcessRecord proc; 5391 synchronized (mPidsSelfLocked) { 5392 proc = mPidsSelfLocked.get(pid); 5393 } 5394 if (proc.curRawAdj > ProcessList.PERCEPTIBLE_APP_ADJ) { 5395 Slog.w(TAG, "Ignoring closeSystemDialogs " + reason 5396 + " from background process " + proc); 5397 return; 5398 } 5399 } 5400 closeSystemDialogsLocked(reason); 5401 } 5402 } finally { 5403 Binder.restoreCallingIdentity(origId); 5404 } 5405 } 5406 5407 void closeSystemDialogsLocked(String reason) { 5408 Intent intent = new Intent(Intent.ACTION_CLOSE_SYSTEM_DIALOGS); 5409 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY 5410 | Intent.FLAG_RECEIVER_FOREGROUND); 5411 if (reason != null) { 5412 intent.putExtra("reason", reason); 5413 } 5414 mWindowManager.closeSystemDialogs(reason); 5415 5416 mStackSupervisor.closeSystemDialogsLocked(); 5417 5418 broadcastIntentLocked(null, null, intent, null, 5419 null, 0, null, null, null, AppOpsManager.OP_NONE, false, false, -1, 5420 Process.SYSTEM_UID, UserHandle.USER_ALL); 5421 } 5422 5423 @Override 5424 public Debug.MemoryInfo[] getProcessMemoryInfo(int[] pids) { 5425 enforceNotIsolatedCaller("getProcessMemoryInfo"); 5426 Debug.MemoryInfo[] infos = new Debug.MemoryInfo[pids.length]; 5427 for (int i=pids.length-1; i>=0; i--) { 5428 ProcessRecord proc; 5429 int oomAdj; 5430 synchronized (this) { 5431 synchronized (mPidsSelfLocked) { 5432 proc = mPidsSelfLocked.get(pids[i]); 5433 oomAdj = proc != null ? proc.setAdj : 0; 5434 } 5435 } 5436 infos[i] = new Debug.MemoryInfo(); 5437 Debug.getMemoryInfo(pids[i], infos[i]); 5438 if (proc != null) { 5439 synchronized (this) { 5440 if (proc.thread != null && proc.setAdj == oomAdj) { 5441 // Record this for posterity if the process has been stable. 5442 proc.baseProcessTracker.addPss(infos[i].getTotalPss(), 5443 infos[i].getTotalUss(), false, proc.pkgList); 5444 } 5445 } 5446 } 5447 } 5448 return infos; 5449 } 5450 5451 @Override 5452 public long[] getProcessPss(int[] pids) { 5453 enforceNotIsolatedCaller("getProcessPss"); 5454 long[] pss = new long[pids.length]; 5455 for (int i=pids.length-1; i>=0; i--) { 5456 ProcessRecord proc; 5457 int oomAdj; 5458 synchronized (this) { 5459 synchronized (mPidsSelfLocked) { 5460 proc = mPidsSelfLocked.get(pids[i]); 5461 oomAdj = proc != null ? proc.setAdj : 0; 5462 } 5463 } 5464 long[] tmpUss = new long[1]; 5465 pss[i] = Debug.getPss(pids[i], tmpUss); 5466 if (proc != null) { 5467 synchronized (this) { 5468 if (proc.thread != null && proc.setAdj == oomAdj) { 5469 // Record this for posterity if the process has been stable. 5470 proc.baseProcessTracker.addPss(pss[i], tmpUss[0], false, proc.pkgList); 5471 } 5472 } 5473 } 5474 } 5475 return pss; 5476 } 5477 5478 @Override 5479 public void killApplicationProcess(String processName, int uid) { 5480 if (processName == null) { 5481 return; 5482 } 5483 5484 int callerUid = Binder.getCallingUid(); 5485 // Only the system server can kill an application 5486 if (callerUid == Process.SYSTEM_UID) { 5487 synchronized (this) { 5488 ProcessRecord app = getProcessRecordLocked(processName, uid, true); 5489 if (app != null && app.thread != null) { 5490 try { 5491 app.thread.scheduleSuicide(); 5492 } catch (RemoteException e) { 5493 // If the other end already died, then our work here is done. 5494 } 5495 } else { 5496 Slog.w(TAG, "Process/uid not found attempting kill of " 5497 + processName + " / " + uid); 5498 } 5499 } 5500 } else { 5501 throw new SecurityException(callerUid + " cannot kill app process: " + 5502 processName); 5503 } 5504 } 5505 5506 private void forceStopPackageLocked(final String packageName, int uid, String reason) { 5507 forceStopPackageLocked(packageName, UserHandle.getAppId(uid), false, 5508 false, true, false, false, UserHandle.getUserId(uid), reason); 5509 Intent intent = new Intent(Intent.ACTION_PACKAGE_RESTARTED, 5510 Uri.fromParts("package", packageName, null)); 5511 if (!mProcessesReady) { 5512 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY 5513 | Intent.FLAG_RECEIVER_FOREGROUND); 5514 } 5515 intent.putExtra(Intent.EXTRA_UID, uid); 5516 intent.putExtra(Intent.EXTRA_USER_HANDLE, UserHandle.getUserId(uid)); 5517 broadcastIntentLocked(null, null, intent, 5518 null, null, 0, null, null, null, AppOpsManager.OP_NONE, 5519 false, false, 5520 MY_PID, Process.SYSTEM_UID, UserHandle.getUserId(uid)); 5521 } 5522 5523 private void forceStopUserLocked(int userId, String reason) { 5524 forceStopPackageLocked(null, -1, false, false, true, false, false, userId, reason); 5525 Intent intent = new Intent(Intent.ACTION_USER_STOPPED); 5526 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY 5527 | Intent.FLAG_RECEIVER_FOREGROUND); 5528 intent.putExtra(Intent.EXTRA_USER_HANDLE, userId); 5529 broadcastIntentLocked(null, null, intent, 5530 null, null, 0, null, null, null, AppOpsManager.OP_NONE, 5531 false, false, 5532 MY_PID, Process.SYSTEM_UID, UserHandle.USER_ALL); 5533 } 5534 5535 private final boolean killPackageProcessesLocked(String packageName, int appId, 5536 int userId, int minOomAdj, boolean callerWillRestart, boolean allowRestart, 5537 boolean doit, boolean evenPersistent, String reason) { 5538 ArrayList<ProcessRecord> procs = new ArrayList<ProcessRecord>(); 5539 5540 // Remove all processes this package may have touched: all with the 5541 // same UID (except for the system or root user), and all whose name 5542 // matches the package name. 5543 final int NP = mProcessNames.getMap().size(); 5544 for (int ip=0; ip<NP; ip++) { 5545 SparseArray<ProcessRecord> apps = mProcessNames.getMap().valueAt(ip); 5546 final int NA = apps.size(); 5547 for (int ia=0; ia<NA; ia++) { 5548 ProcessRecord app = apps.valueAt(ia); 5549 if (app.persistent && !evenPersistent) { 5550 // we don't kill persistent processes 5551 continue; 5552 } 5553 if (app.removed) { 5554 if (doit) { 5555 procs.add(app); 5556 } 5557 continue; 5558 } 5559 5560 // Skip process if it doesn't meet our oom adj requirement. 5561 if (app.setAdj < minOomAdj) { 5562 continue; 5563 } 5564 5565 // If no package is specified, we call all processes under the 5566 // give user id. 5567 if (packageName == null) { 5568 if (app.userId != userId) { 5569 continue; 5570 } 5571 if (appId >= 0 && UserHandle.getAppId(app.uid) != appId) { 5572 continue; 5573 } 5574 // Package has been specified, we want to hit all processes 5575 // that match it. We need to qualify this by the processes 5576 // that are running under the specified app and user ID. 5577 } else { 5578 final boolean isDep = app.pkgDeps != null 5579 && app.pkgDeps.contains(packageName); 5580 if (!isDep && UserHandle.getAppId(app.uid) != appId) { 5581 continue; 5582 } 5583 if (userId != UserHandle.USER_ALL && app.userId != userId) { 5584 continue; 5585 } 5586 if (!app.pkgList.containsKey(packageName) && !isDep) { 5587 continue; 5588 } 5589 } 5590 5591 // Process has passed all conditions, kill it! 5592 if (!doit) { 5593 return true; 5594 } 5595 app.removed = true; 5596 procs.add(app); 5597 } 5598 } 5599 5600 int N = procs.size(); 5601 for (int i=0; i<N; i++) { 5602 removeProcessLocked(procs.get(i), callerWillRestart, allowRestart, reason); 5603 } 5604 updateOomAdjLocked(); 5605 return N > 0; 5606 } 5607 5608 private final boolean forceStopPackageLocked(String name, int appId, 5609 boolean callerWillRestart, boolean purgeCache, boolean doit, 5610 boolean evenPersistent, boolean uninstalling, int userId, String reason) { 5611 int i; 5612 int N; 5613 5614 if (userId == UserHandle.USER_ALL && name == null) { 5615 Slog.w(TAG, "Can't force stop all processes of all users, that is insane!"); 5616 } 5617 5618 if (appId < 0 && name != null) { 5619 try { 5620 appId = UserHandle.getAppId( 5621 AppGlobals.getPackageManager().getPackageUid(name, 0)); 5622 } catch (RemoteException e) { 5623 } 5624 } 5625 5626 if (doit) { 5627 if (name != null) { 5628 Slog.i(TAG, "Force stopping " + name + " appid=" + appId 5629 + " user=" + userId + ": " + reason); 5630 } else { 5631 Slog.i(TAG, "Force stopping u" + userId + ": " + reason); 5632 } 5633 5634 final ArrayMap<String, SparseArray<Long>> pmap = mProcessCrashTimes.getMap(); 5635 for (int ip=pmap.size()-1; ip>=0; ip--) { 5636 SparseArray<Long> ba = pmap.valueAt(ip); 5637 for (i=ba.size()-1; i>=0; i--) { 5638 boolean remove = false; 5639 final int entUid = ba.keyAt(i); 5640 if (name != null) { 5641 if (userId == UserHandle.USER_ALL) { 5642 if (UserHandle.getAppId(entUid) == appId) { 5643 remove = true; 5644 } 5645 } else { 5646 if (entUid == UserHandle.getUid(userId, appId)) { 5647 remove = true; 5648 } 5649 } 5650 } else if (UserHandle.getUserId(entUid) == userId) { 5651 remove = true; 5652 } 5653 if (remove) { 5654 ba.removeAt(i); 5655 } 5656 } 5657 if (ba.size() == 0) { 5658 pmap.removeAt(ip); 5659 } 5660 } 5661 } 5662 5663 boolean didSomething = killPackageProcessesLocked(name, appId, userId, 5664 -100, callerWillRestart, true, doit, evenPersistent, 5665 name == null ? ("stop user " + userId) : ("stop " + name)); 5666 5667 if (mStackSupervisor.forceStopPackageLocked(name, doit, evenPersistent, userId)) { 5668 if (!doit) { 5669 return true; 5670 } 5671 didSomething = true; 5672 } 5673 5674 if (mServices.forceStopLocked(name, userId, evenPersistent, doit)) { 5675 if (!doit) { 5676 return true; 5677 } 5678 didSomething = true; 5679 } 5680 5681 if (name == null) { 5682 // Remove all sticky broadcasts from this user. 5683 mStickyBroadcasts.remove(userId); 5684 } 5685 5686 ArrayList<ContentProviderRecord> providers = new ArrayList<ContentProviderRecord>(); 5687 if (mProviderMap.collectForceStopProviders(name, appId, doit, evenPersistent, 5688 userId, providers)) { 5689 if (!doit) { 5690 return true; 5691 } 5692 didSomething = true; 5693 } 5694 N = providers.size(); 5695 for (i=0; i<N; i++) { 5696 removeDyingProviderLocked(null, providers.get(i), true); 5697 } 5698 5699 // Remove transient permissions granted from/to this package/user 5700 removeUriPermissionsForPackageLocked(name, userId, false); 5701 5702 if (name == null || uninstalling) { 5703 // Remove pending intents. For now we only do this when force 5704 // stopping users, because we have some problems when doing this 5705 // for packages -- app widgets are not currently cleaned up for 5706 // such packages, so they can be left with bad pending intents. 5707 if (mIntentSenderRecords.size() > 0) { 5708 Iterator<WeakReference<PendingIntentRecord>> it 5709 = mIntentSenderRecords.values().iterator(); 5710 while (it.hasNext()) { 5711 WeakReference<PendingIntentRecord> wpir = it.next(); 5712 if (wpir == null) { 5713 it.remove(); 5714 continue; 5715 } 5716 PendingIntentRecord pir = wpir.get(); 5717 if (pir == null) { 5718 it.remove(); 5719 continue; 5720 } 5721 if (name == null) { 5722 // Stopping user, remove all objects for the user. 5723 if (pir.key.userId != userId) { 5724 // Not the same user, skip it. 5725 continue; 5726 } 5727 } else { 5728 if (UserHandle.getAppId(pir.uid) != appId) { 5729 // Different app id, skip it. 5730 continue; 5731 } 5732 if (userId != UserHandle.USER_ALL && pir.key.userId != userId) { 5733 // Different user, skip it. 5734 continue; 5735 } 5736 if (!pir.key.packageName.equals(name)) { 5737 // Different package, skip it. 5738 continue; 5739 } 5740 } 5741 if (!doit) { 5742 return true; 5743 } 5744 didSomething = true; 5745 it.remove(); 5746 pir.canceled = true; 5747 if (pir.key.activity != null) { 5748 pir.key.activity.pendingResults.remove(pir.ref); 5749 } 5750 } 5751 } 5752 } 5753 5754 if (doit) { 5755 if (purgeCache && name != null) { 5756 AttributeCache ac = AttributeCache.instance(); 5757 if (ac != null) { 5758 ac.removePackage(name); 5759 } 5760 } 5761 if (mBooted) { 5762 mStackSupervisor.resumeTopActivitiesLocked(); 5763 mStackSupervisor.scheduleIdleLocked(); 5764 } 5765 } 5766 5767 return didSomething; 5768 } 5769 5770 private final boolean removeProcessLocked(ProcessRecord app, 5771 boolean callerWillRestart, boolean allowRestart, String reason) { 5772 final String name = app.processName; 5773 final int uid = app.uid; 5774 if (DEBUG_PROCESSES) Slog.d( 5775 TAG, "Force removing proc " + app.toShortString() + " (" + name 5776 + "/" + uid + ")"); 5777 5778 mProcessNames.remove(name, uid); 5779 mIsolatedProcesses.remove(app.uid); 5780 if (mHeavyWeightProcess == app) { 5781 mHandler.sendMessage(mHandler.obtainMessage(CANCEL_HEAVY_NOTIFICATION_MSG, 5782 mHeavyWeightProcess.userId, 0)); 5783 mHeavyWeightProcess = null; 5784 } 5785 boolean needRestart = false; 5786 if (app.pid > 0 && app.pid != MY_PID) { 5787 int pid = app.pid; 5788 synchronized (mPidsSelfLocked) { 5789 mPidsSelfLocked.remove(pid); 5790 mHandler.removeMessages(PROC_START_TIMEOUT_MSG, app); 5791 } 5792 mBatteryStatsService.noteProcessFinish(app.processName, app.info.uid); 5793 if (app.isolated) { 5794 mBatteryStatsService.removeIsolatedUid(app.uid, app.info.uid); 5795 } 5796 app.kill(reason, true); 5797 handleAppDiedLocked(app, true, allowRestart); 5798 removeLruProcessLocked(app); 5799 5800 if (app.persistent && !app.isolated) { 5801 if (!callerWillRestart) { 5802 addAppLocked(app.info, false, null /* ABI override */); 5803 } else { 5804 needRestart = true; 5805 } 5806 } 5807 } else { 5808 mRemovedProcesses.add(app); 5809 } 5810 5811 return needRestart; 5812 } 5813 5814 private final void processStartTimedOutLocked(ProcessRecord app) { 5815 final int pid = app.pid; 5816 boolean gone = false; 5817 synchronized (mPidsSelfLocked) { 5818 ProcessRecord knownApp = mPidsSelfLocked.get(pid); 5819 if (knownApp != null && knownApp.thread == null) { 5820 mPidsSelfLocked.remove(pid); 5821 gone = true; 5822 } 5823 } 5824 5825 if (gone) { 5826 Slog.w(TAG, "Process " + app + " failed to attach"); 5827 EventLog.writeEvent(EventLogTags.AM_PROCESS_START_TIMEOUT, app.userId, 5828 pid, app.uid, app.processName); 5829 mProcessNames.remove(app.processName, app.uid); 5830 mIsolatedProcesses.remove(app.uid); 5831 if (mHeavyWeightProcess == app) { 5832 mHandler.sendMessage(mHandler.obtainMessage(CANCEL_HEAVY_NOTIFICATION_MSG, 5833 mHeavyWeightProcess.userId, 0)); 5834 mHeavyWeightProcess = null; 5835 } 5836 mBatteryStatsService.noteProcessFinish(app.processName, app.info.uid); 5837 if (app.isolated) { 5838 mBatteryStatsService.removeIsolatedUid(app.uid, app.info.uid); 5839 } 5840 // Take care of any launching providers waiting for this process. 5841 checkAppInLaunchingProvidersLocked(app, true); 5842 // Take care of any services that are waiting for the process. 5843 mServices.processStartTimedOutLocked(app); 5844 app.kill("start timeout", true); 5845 if (mBackupTarget != null && mBackupTarget.app.pid == pid) { 5846 Slog.w(TAG, "Unattached app died before backup, skipping"); 5847 try { 5848 IBackupManager bm = IBackupManager.Stub.asInterface( 5849 ServiceManager.getService(Context.BACKUP_SERVICE)); 5850 bm.agentDisconnected(app.info.packageName); 5851 } catch (RemoteException e) { 5852 // Can't happen; the backup manager is local 5853 } 5854 } 5855 if (isPendingBroadcastProcessLocked(pid)) { 5856 Slog.w(TAG, "Unattached app died before broadcast acknowledged, skipping"); 5857 skipPendingBroadcastLocked(pid); 5858 } 5859 } else { 5860 Slog.w(TAG, "Spurious process start timeout - pid not known for " + app); 5861 } 5862 } 5863 5864 private final boolean attachApplicationLocked(IApplicationThread thread, 5865 int pid) { 5866 5867 // Find the application record that is being attached... either via 5868 // the pid if we are running in multiple processes, or just pull the 5869 // next app record if we are emulating process with anonymous threads. 5870 ProcessRecord app; 5871 if (pid != MY_PID && pid >= 0) { 5872 synchronized (mPidsSelfLocked) { 5873 app = mPidsSelfLocked.get(pid); 5874 } 5875 } else { 5876 app = null; 5877 } 5878 5879 if (app == null) { 5880 Slog.w(TAG, "No pending application record for pid " + pid 5881 + " (IApplicationThread " + thread + "); dropping process"); 5882 EventLog.writeEvent(EventLogTags.AM_DROP_PROCESS, pid); 5883 if (pid > 0 && pid != MY_PID) { 5884 Process.killProcessQuiet(pid); 5885 //TODO: Process.killProcessGroup(app.info.uid, pid); 5886 } else { 5887 try { 5888 thread.scheduleExit(); 5889 } catch (Exception e) { 5890 // Ignore exceptions. 5891 } 5892 } 5893 return false; 5894 } 5895 5896 // If this application record is still attached to a previous 5897 // process, clean it up now. 5898 if (app.thread != null) { 5899 handleAppDiedLocked(app, true, true); 5900 } 5901 5902 // Tell the process all about itself. 5903 5904 if (localLOGV) Slog.v( 5905 TAG, "Binding process pid " + pid + " to record " + app); 5906 5907 final String processName = app.processName; 5908 try { 5909 AppDeathRecipient adr = new AppDeathRecipient( 5910 app, pid, thread); 5911 thread.asBinder().linkToDeath(adr, 0); 5912 app.deathRecipient = adr; 5913 } catch (RemoteException e) { 5914 app.resetPackageList(mProcessStats); 5915 startProcessLocked(app, "link fail", processName); 5916 return false; 5917 } 5918 5919 EventLog.writeEvent(EventLogTags.AM_PROC_BOUND, app.userId, app.pid, app.processName); 5920 5921 app.makeActive(thread, mProcessStats); 5922 app.curAdj = app.setAdj = -100; 5923 app.curSchedGroup = app.setSchedGroup = Process.THREAD_GROUP_DEFAULT; 5924 app.forcingToForeground = null; 5925 updateProcessForegroundLocked(app, false, false); 5926 app.hasShownUi = false; 5927 app.debugging = false; 5928 app.cached = false; 5929 5930 mHandler.removeMessages(PROC_START_TIMEOUT_MSG, app); 5931 5932 boolean normalMode = mProcessesReady || isAllowedWhileBooting(app.info); 5933 List<ProviderInfo> providers = normalMode ? generateApplicationProvidersLocked(app) : null; 5934 5935 if (!normalMode) { 5936 Slog.i(TAG, "Launching preboot mode app: " + app); 5937 } 5938 5939 if (localLOGV) Slog.v( 5940 TAG, "New app record " + app 5941 + " thread=" + thread.asBinder() + " pid=" + pid); 5942 try { 5943 int testMode = IApplicationThread.DEBUG_OFF; 5944 if (mDebugApp != null && mDebugApp.equals(processName)) { 5945 testMode = mWaitForDebugger 5946 ? IApplicationThread.DEBUG_WAIT 5947 : IApplicationThread.DEBUG_ON; 5948 app.debugging = true; 5949 if (mDebugTransient) { 5950 mDebugApp = mOrigDebugApp; 5951 mWaitForDebugger = mOrigWaitForDebugger; 5952 } 5953 } 5954 String profileFile = app.instrumentationProfileFile; 5955 ParcelFileDescriptor profileFd = null; 5956 int samplingInterval = 0; 5957 boolean profileAutoStop = false; 5958 if (mProfileApp != null && mProfileApp.equals(processName)) { 5959 mProfileProc = app; 5960 profileFile = mProfileFile; 5961 profileFd = mProfileFd; 5962 samplingInterval = mSamplingInterval; 5963 profileAutoStop = mAutoStopProfiler; 5964 } 5965 boolean enableOpenGlTrace = false; 5966 if (mOpenGlTraceApp != null && mOpenGlTraceApp.equals(processName)) { 5967 enableOpenGlTrace = true; 5968 mOpenGlTraceApp = null; 5969 } 5970 5971 // If the app is being launched for restore or full backup, set it up specially 5972 boolean isRestrictedBackupMode = false; 5973 if (mBackupTarget != null && mBackupAppName.equals(processName)) { 5974 isRestrictedBackupMode = (mBackupTarget.backupMode == BackupRecord.RESTORE) 5975 || (mBackupTarget.backupMode == BackupRecord.RESTORE_FULL) 5976 || (mBackupTarget.backupMode == BackupRecord.BACKUP_FULL); 5977 } 5978 5979 ensurePackageDexOpt(app.instrumentationInfo != null 5980 ? app.instrumentationInfo.packageName 5981 : app.info.packageName); 5982 if (app.instrumentationClass != null) { 5983 ensurePackageDexOpt(app.instrumentationClass.getPackageName()); 5984 } 5985 if (DEBUG_CONFIGURATION) Slog.v(TAG, "Binding proc " 5986 + processName + " with config " + mConfiguration); 5987 ApplicationInfo appInfo = app.instrumentationInfo != null 5988 ? app.instrumentationInfo : app.info; 5989 app.compat = compatibilityInfoForPackageLocked(appInfo); 5990 if (profileFd != null) { 5991 profileFd = profileFd.dup(); 5992 } 5993 ProfilerInfo profilerInfo = profileFile == null ? null 5994 : new ProfilerInfo(profileFile, profileFd, samplingInterval, profileAutoStop); 5995 thread.bindApplication(processName, appInfo, providers, app.instrumentationClass, 5996 profilerInfo, app.instrumentationArguments, app.instrumentationWatcher, 5997 app.instrumentationUiAutomationConnection, testMode, enableOpenGlTrace, 5998 isRestrictedBackupMode || !normalMode, app.persistent, 5999 new Configuration(mConfiguration), app.compat, getCommonServicesLocked(), 6000 mCoreSettingsObserver.getCoreSettingsLocked()); 6001 updateLruProcessLocked(app, false, null); 6002 app.lastRequestedGc = app.lastLowMemory = SystemClock.uptimeMillis(); 6003 } catch (Exception e) { 6004 // todo: Yikes! What should we do? For now we will try to 6005 // start another process, but that could easily get us in 6006 // an infinite loop of restarting processes... 6007 Slog.wtf(TAG, "Exception thrown during bind of " + app, e); 6008 6009 app.resetPackageList(mProcessStats); 6010 app.unlinkDeathRecipient(); 6011 startProcessLocked(app, "bind fail", processName); 6012 return false; 6013 } 6014 6015 // Remove this record from the list of starting applications. 6016 mPersistentStartingProcesses.remove(app); 6017 if (DEBUG_PROCESSES && mProcessesOnHold.contains(app)) Slog.v(TAG, 6018 "Attach application locked removing on hold: " + app); 6019 mProcessesOnHold.remove(app); 6020 6021 boolean badApp = false; 6022 boolean didSomething = false; 6023 6024 // See if the top visible activity is waiting to run in this process... 6025 if (normalMode) { 6026 try { 6027 if (mStackSupervisor.attachApplicationLocked(app)) { 6028 didSomething = true; 6029 } 6030 } catch (Exception e) { 6031 Slog.wtf(TAG, "Exception thrown launching activities in " + app, e); 6032 badApp = true; 6033 } 6034 } 6035 6036 // Find any services that should be running in this process... 6037 if (!badApp) { 6038 try { 6039 didSomething |= mServices.attachApplicationLocked(app, processName); 6040 } catch (Exception e) { 6041 Slog.wtf(TAG, "Exception thrown starting services in " + app, e); 6042 badApp = true; 6043 } 6044 } 6045 6046 // Check if a next-broadcast receiver is in this process... 6047 if (!badApp && isPendingBroadcastProcessLocked(pid)) { 6048 try { 6049 didSomething |= sendPendingBroadcastsLocked(app); 6050 } catch (Exception e) { 6051 // If the app died trying to launch the receiver we declare it 'bad' 6052 Slog.wtf(TAG, "Exception thrown dispatching broadcasts in " + app, e); 6053 badApp = true; 6054 } 6055 } 6056 6057 // Check whether the next backup agent is in this process... 6058 if (!badApp && mBackupTarget != null && mBackupTarget.appInfo.uid == app.uid) { 6059 if (DEBUG_BACKUP) Slog.v(TAG, "New app is backup target, launching agent for " + app); 6060 ensurePackageDexOpt(mBackupTarget.appInfo.packageName); 6061 try { 6062 thread.scheduleCreateBackupAgent(mBackupTarget.appInfo, 6063 compatibilityInfoForPackageLocked(mBackupTarget.appInfo), 6064 mBackupTarget.backupMode); 6065 } catch (Exception e) { 6066 Slog.wtf(TAG, "Exception thrown creating backup agent in " + app, e); 6067 badApp = true; 6068 } 6069 } 6070 6071 if (badApp) { 6072 app.kill("error during init", true); 6073 handleAppDiedLocked(app, false, true); 6074 return false; 6075 } 6076 6077 if (!didSomething) { 6078 updateOomAdjLocked(); 6079 } 6080 6081 return true; 6082 } 6083 6084 @Override 6085 public final void attachApplication(IApplicationThread thread) { 6086 synchronized (this) { 6087 int callingPid = Binder.getCallingPid(); 6088 final long origId = Binder.clearCallingIdentity(); 6089 attachApplicationLocked(thread, callingPid); 6090 Binder.restoreCallingIdentity(origId); 6091 } 6092 } 6093 6094 @Override 6095 public final void activityIdle(IBinder token, Configuration config, boolean stopProfiling) { 6096 final long origId = Binder.clearCallingIdentity(); 6097 synchronized (this) { 6098 ActivityStack stack = ActivityRecord.getStackLocked(token); 6099 if (stack != null) { 6100 ActivityRecord r = 6101 mStackSupervisor.activityIdleInternalLocked(token, false, config); 6102 if (stopProfiling) { 6103 if ((mProfileProc == r.app) && (mProfileFd != null)) { 6104 try { 6105 mProfileFd.close(); 6106 } catch (IOException e) { 6107 } 6108 clearProfilerLocked(); 6109 } 6110 } 6111 } 6112 } 6113 Binder.restoreCallingIdentity(origId); 6114 } 6115 6116 void postFinishBooting(boolean finishBooting, boolean enableScreen) { 6117 mHandler.sendMessage(mHandler.obtainMessage(FINISH_BOOTING_MSG, 6118 finishBooting? 1 : 0, enableScreen ? 1 : 0)); 6119 } 6120 6121 void enableScreenAfterBoot() { 6122 EventLog.writeEvent(EventLogTags.BOOT_PROGRESS_ENABLE_SCREEN, 6123 SystemClock.uptimeMillis()); 6124 mWindowManager.enableScreenAfterBoot(); 6125 6126 synchronized (this) { 6127 updateEventDispatchingLocked(); 6128 } 6129 } 6130 6131 @Override 6132 public void showBootMessage(final CharSequence msg, final boolean always) { 6133 enforceNotIsolatedCaller("showBootMessage"); 6134 mWindowManager.showBootMessage(msg, always); 6135 } 6136 6137 @Override 6138 public void keyguardWaitingForActivityDrawn() { 6139 enforceNotIsolatedCaller("keyguardWaitingForActivityDrawn"); 6140 final long token = Binder.clearCallingIdentity(); 6141 try { 6142 synchronized (this) { 6143 if (DEBUG_LOCKSCREEN) logLockScreen(""); 6144 mWindowManager.keyguardWaitingForActivityDrawn(); 6145 if (mLockScreenShown == LOCK_SCREEN_SHOWN) { 6146 mLockScreenShown = LOCK_SCREEN_LEAVING; 6147 } 6148 } 6149 } finally { 6150 Binder.restoreCallingIdentity(token); 6151 } 6152 } 6153 6154 final void finishBooting() { 6155 synchronized (this) { 6156 if (!mBootAnimationComplete) { 6157 mCallFinishBooting = true; 6158 return; 6159 } 6160 mCallFinishBooting = false; 6161 } 6162 6163 ArraySet<String> completedIsas = new ArraySet<String>(); 6164 for (String abi : Build.SUPPORTED_ABIS) { 6165 Process.establishZygoteConnectionForAbi(abi); 6166 final String instructionSet = VMRuntime.getInstructionSet(abi); 6167 if (!completedIsas.contains(instructionSet)) { 6168 if (mInstaller.markBootComplete(VMRuntime.getInstructionSet(abi)) != 0) { 6169 Slog.e(TAG, "Unable to mark boot complete for abi: " + abi); 6170 } 6171 completedIsas.add(instructionSet); 6172 } 6173 } 6174 6175 // Register receivers to handle package update events 6176 mPackageMonitor.register(mContext, Looper.getMainLooper(), UserHandle.ALL, false); 6177 6178 // Let system services know. 6179 mSystemServiceManager.startBootPhase(SystemService.PHASE_BOOT_COMPLETED); 6180 6181 synchronized (this) { 6182 // Ensure that any processes we had put on hold are now started 6183 // up. 6184 final int NP = mProcessesOnHold.size(); 6185 if (NP > 0) { 6186 ArrayList<ProcessRecord> procs = 6187 new ArrayList<ProcessRecord>(mProcessesOnHold); 6188 for (int ip=0; ip<NP; ip++) { 6189 if (DEBUG_PROCESSES) Slog.v(TAG, "Starting process on hold: " 6190 + procs.get(ip)); 6191 startProcessLocked(procs.get(ip), "on-hold", null); 6192 } 6193 } 6194 6195 if (mFactoryTest != FactoryTest.FACTORY_TEST_LOW_LEVEL) { 6196 // Start looking for apps that are abusing wake locks. 6197 Message nmsg = mHandler.obtainMessage(CHECK_EXCESSIVE_WAKE_LOCKS_MSG); 6198 mHandler.sendMessageDelayed(nmsg, POWER_CHECK_DELAY); 6199 // Tell anyone interested that we are done booting! 6200 SystemProperties.set("sys.boot_completed", "1"); 6201 6202 // And trigger dev.bootcomplete if we are not showing encryption progress 6203 if (!"trigger_restart_min_framework".equals(SystemProperties.get("vold.decrypt")) 6204 || "".equals(SystemProperties.get("vold.encrypt_progress"))) { 6205 SystemProperties.set("dev.bootcomplete", "1"); 6206 } 6207 for (int i=0; i<mStartedUsers.size(); i++) { 6208 UserStartedState uss = mStartedUsers.valueAt(i); 6209 if (uss.mState == UserStartedState.STATE_BOOTING) { 6210 uss.mState = UserStartedState.STATE_RUNNING; 6211 final int userId = mStartedUsers.keyAt(i); 6212 Intent intent = new Intent(Intent.ACTION_BOOT_COMPLETED, null); 6213 intent.putExtra(Intent.EXTRA_USER_HANDLE, userId); 6214 intent.addFlags(Intent.FLAG_RECEIVER_NO_ABORT); 6215 broadcastIntentLocked(null, null, intent, null, 6216 new IIntentReceiver.Stub() { 6217 @Override 6218 public void performReceive(Intent intent, int resultCode, 6219 String data, Bundle extras, boolean ordered, 6220 boolean sticky, int sendingUser) { 6221 synchronized (ActivityManagerService.this) { 6222 requestPssAllProcsLocked(SystemClock.uptimeMillis(), 6223 true, false); 6224 } 6225 } 6226 }, 6227 0, null, null, 6228 android.Manifest.permission.RECEIVE_BOOT_COMPLETED, 6229 AppOpsManager.OP_NONE, true, false, MY_PID, Process.SYSTEM_UID, 6230 userId); 6231 } 6232 } 6233 scheduleStartProfilesLocked(); 6234 } 6235 } 6236 } 6237 6238 @Override 6239 public void bootAnimationComplete() { 6240 final boolean callFinishBooting; 6241 synchronized (this) { 6242 callFinishBooting = mCallFinishBooting; 6243 mBootAnimationComplete = true; 6244 } 6245 if (callFinishBooting) { 6246 finishBooting(); 6247 } 6248 } 6249 6250 final void ensureBootCompleted() { 6251 boolean booting; 6252 boolean enableScreen; 6253 synchronized (this) { 6254 booting = mBooting; 6255 mBooting = false; 6256 enableScreen = !mBooted; 6257 mBooted = true; 6258 } 6259 6260 if (booting) { 6261 finishBooting(); 6262 } 6263 6264 if (enableScreen) { 6265 enableScreenAfterBoot(); 6266 } 6267 } 6268 6269 @Override 6270 public final void activityResumed(IBinder token) { 6271 final long origId = Binder.clearCallingIdentity(); 6272 synchronized(this) { 6273 ActivityStack stack = ActivityRecord.getStackLocked(token); 6274 if (stack != null) { 6275 ActivityRecord.activityResumedLocked(token); 6276 } 6277 } 6278 Binder.restoreCallingIdentity(origId); 6279 } 6280 6281 @Override 6282 public final void activityPaused(IBinder token) { 6283 final long origId = Binder.clearCallingIdentity(); 6284 synchronized(this) { 6285 ActivityStack stack = ActivityRecord.getStackLocked(token); 6286 if (stack != null) { 6287 stack.activityPausedLocked(token, false); 6288 } 6289 } 6290 Binder.restoreCallingIdentity(origId); 6291 } 6292 6293 @Override 6294 public final void activityStopped(IBinder token, Bundle icicle, 6295 PersistableBundle persistentState, CharSequence description) { 6296 if (localLOGV) Slog.v(TAG, "Activity stopped: token=" + token); 6297 6298 // Refuse possible leaked file descriptors 6299 if (icicle != null && icicle.hasFileDescriptors()) { 6300 throw new IllegalArgumentException("File descriptors passed in Bundle"); 6301 } 6302 6303 final long origId = Binder.clearCallingIdentity(); 6304 6305 synchronized (this) { 6306 ActivityRecord r = ActivityRecord.isInStackLocked(token); 6307 if (r != null) { 6308 r.task.stack.activityStoppedLocked(r, icicle, persistentState, description); 6309 } 6310 } 6311 6312 trimApplications(); 6313 6314 Binder.restoreCallingIdentity(origId); 6315 } 6316 6317 @Override 6318 public final void activityDestroyed(IBinder token) { 6319 if (DEBUG_SWITCH) Slog.v(TAG, "ACTIVITY DESTROYED: " + token); 6320 synchronized (this) { 6321 ActivityStack stack = ActivityRecord.getStackLocked(token); 6322 if (stack != null) { 6323 stack.activityDestroyedLocked(token); 6324 } 6325 } 6326 } 6327 6328 @Override 6329 public final void backgroundResourcesReleased(IBinder token) { 6330 final long origId = Binder.clearCallingIdentity(); 6331 try { 6332 synchronized (this) { 6333 ActivityStack stack = ActivityRecord.getStackLocked(token); 6334 if (stack != null) { 6335 stack.backgroundResourcesReleased(token); 6336 } 6337 } 6338 } finally { 6339 Binder.restoreCallingIdentity(origId); 6340 } 6341 } 6342 6343 @Override 6344 public final void notifyLaunchTaskBehindComplete(IBinder token) { 6345 mStackSupervisor.scheduleLaunchTaskBehindComplete(token); 6346 } 6347 6348 @Override 6349 public final void notifyEnterAnimationComplete(IBinder token) { 6350 mHandler.sendMessage(mHandler.obtainMessage(ENTER_ANIMATION_COMPLETE_MSG, token)); 6351 } 6352 6353 @Override 6354 public String getCallingPackage(IBinder token) { 6355 synchronized (this) { 6356 ActivityRecord r = getCallingRecordLocked(token); 6357 return r != null ? r.info.packageName : null; 6358 } 6359 } 6360 6361 @Override 6362 public ComponentName getCallingActivity(IBinder token) { 6363 synchronized (this) { 6364 ActivityRecord r = getCallingRecordLocked(token); 6365 return r != null ? r.intent.getComponent() : null; 6366 } 6367 } 6368 6369 private ActivityRecord getCallingRecordLocked(IBinder token) { 6370 ActivityRecord r = ActivityRecord.isInStackLocked(token); 6371 if (r == null) { 6372 return null; 6373 } 6374 return r.resultTo; 6375 } 6376 6377 @Override 6378 public ComponentName getActivityClassForToken(IBinder token) { 6379 synchronized(this) { 6380 ActivityRecord r = ActivityRecord.isInStackLocked(token); 6381 if (r == null) { 6382 return null; 6383 } 6384 return r.intent.getComponent(); 6385 } 6386 } 6387 6388 @Override 6389 public String getPackageForToken(IBinder token) { 6390 synchronized(this) { 6391 ActivityRecord r = ActivityRecord.isInStackLocked(token); 6392 if (r == null) { 6393 return null; 6394 } 6395 return r.packageName; 6396 } 6397 } 6398 6399 @Override 6400 public IIntentSender getIntentSender(int type, 6401 String packageName, IBinder token, String resultWho, 6402 int requestCode, Intent[] intents, String[] resolvedTypes, 6403 int flags, Bundle options, int userId) { 6404 enforceNotIsolatedCaller("getIntentSender"); 6405 // Refuse possible leaked file descriptors 6406 if (intents != null) { 6407 if (intents.length < 1) { 6408 throw new IllegalArgumentException("Intents array length must be >= 1"); 6409 } 6410 for (int i=0; i<intents.length; i++) { 6411 Intent intent = intents[i]; 6412 if (intent != null) { 6413 if (intent.hasFileDescriptors()) { 6414 throw new IllegalArgumentException("File descriptors passed in Intent"); 6415 } 6416 if (type == ActivityManager.INTENT_SENDER_BROADCAST && 6417 (intent.getFlags()&Intent.FLAG_RECEIVER_BOOT_UPGRADE) != 0) { 6418 throw new IllegalArgumentException( 6419 "Can't use FLAG_RECEIVER_BOOT_UPGRADE here"); 6420 } 6421 intents[i] = new Intent(intent); 6422 } 6423 } 6424 if (resolvedTypes != null && resolvedTypes.length != intents.length) { 6425 throw new IllegalArgumentException( 6426 "Intent array length does not match resolvedTypes length"); 6427 } 6428 } 6429 if (options != null) { 6430 if (options.hasFileDescriptors()) { 6431 throw new IllegalArgumentException("File descriptors passed in options"); 6432 } 6433 } 6434 6435 synchronized(this) { 6436 int callingUid = Binder.getCallingUid(); 6437 int origUserId = userId; 6438 userId = handleIncomingUser(Binder.getCallingPid(), callingUid, userId, 6439 type == ActivityManager.INTENT_SENDER_BROADCAST, 6440 ALLOW_NON_FULL, "getIntentSender", null); 6441 if (origUserId == UserHandle.USER_CURRENT) { 6442 // We don't want to evaluate this until the pending intent is 6443 // actually executed. However, we do want to always do the 6444 // security checking for it above. 6445 userId = UserHandle.USER_CURRENT; 6446 } 6447 try { 6448 if (callingUid != 0 && callingUid != Process.SYSTEM_UID) { 6449 int uid = AppGlobals.getPackageManager() 6450 .getPackageUid(packageName, UserHandle.getUserId(callingUid)); 6451 if (!UserHandle.isSameApp(callingUid, uid)) { 6452 String msg = "Permission Denial: getIntentSender() from pid=" 6453 + Binder.getCallingPid() 6454 + ", uid=" + Binder.getCallingUid() 6455 + ", (need uid=" + uid + ")" 6456 + " is not allowed to send as package " + packageName; 6457 Slog.w(TAG, msg); 6458 throw new SecurityException(msg); 6459 } 6460 } 6461 6462 return getIntentSenderLocked(type, packageName, callingUid, userId, 6463 token, resultWho, requestCode, intents, resolvedTypes, flags, options); 6464 6465 } catch (RemoteException e) { 6466 throw new SecurityException(e); 6467 } 6468 } 6469 } 6470 6471 IIntentSender getIntentSenderLocked(int type, String packageName, 6472 int callingUid, int userId, IBinder token, String resultWho, 6473 int requestCode, Intent[] intents, String[] resolvedTypes, int flags, 6474 Bundle options) { 6475 if (DEBUG_MU) 6476 Slog.v(TAG_MU, "getIntentSenderLocked(): uid=" + callingUid); 6477 ActivityRecord activity = null; 6478 if (type == ActivityManager.INTENT_SENDER_ACTIVITY_RESULT) { 6479 activity = ActivityRecord.isInStackLocked(token); 6480 if (activity == null) { 6481 return null; 6482 } 6483 if (activity.finishing) { 6484 return null; 6485 } 6486 } 6487 6488 final boolean noCreate = (flags&PendingIntent.FLAG_NO_CREATE) != 0; 6489 final boolean cancelCurrent = (flags&PendingIntent.FLAG_CANCEL_CURRENT) != 0; 6490 final boolean updateCurrent = (flags&PendingIntent.FLAG_UPDATE_CURRENT) != 0; 6491 flags &= ~(PendingIntent.FLAG_NO_CREATE|PendingIntent.FLAG_CANCEL_CURRENT 6492 |PendingIntent.FLAG_UPDATE_CURRENT); 6493 6494 PendingIntentRecord.Key key = new PendingIntentRecord.Key( 6495 type, packageName, activity, resultWho, 6496 requestCode, intents, resolvedTypes, flags, options, userId); 6497 WeakReference<PendingIntentRecord> ref; 6498 ref = mIntentSenderRecords.get(key); 6499 PendingIntentRecord rec = ref != null ? ref.get() : null; 6500 if (rec != null) { 6501 if (!cancelCurrent) { 6502 if (updateCurrent) { 6503 if (rec.key.requestIntent != null) { 6504 rec.key.requestIntent.replaceExtras(intents != null ? 6505 intents[intents.length - 1] : null); 6506 } 6507 if (intents != null) { 6508 intents[intents.length-1] = rec.key.requestIntent; 6509 rec.key.allIntents = intents; 6510 rec.key.allResolvedTypes = resolvedTypes; 6511 } else { 6512 rec.key.allIntents = null; 6513 rec.key.allResolvedTypes = null; 6514 } 6515 } 6516 return rec; 6517 } 6518 rec.canceled = true; 6519 mIntentSenderRecords.remove(key); 6520 } 6521 if (noCreate) { 6522 return rec; 6523 } 6524 rec = new PendingIntentRecord(this, key, callingUid); 6525 mIntentSenderRecords.put(key, rec.ref); 6526 if (type == ActivityManager.INTENT_SENDER_ACTIVITY_RESULT) { 6527 if (activity.pendingResults == null) { 6528 activity.pendingResults 6529 = new HashSet<WeakReference<PendingIntentRecord>>(); 6530 } 6531 activity.pendingResults.add(rec.ref); 6532 } 6533 return rec; 6534 } 6535 6536 @Override 6537 public void cancelIntentSender(IIntentSender sender) { 6538 if (!(sender instanceof PendingIntentRecord)) { 6539 return; 6540 } 6541 synchronized(this) { 6542 PendingIntentRecord rec = (PendingIntentRecord)sender; 6543 try { 6544 int uid = AppGlobals.getPackageManager() 6545 .getPackageUid(rec.key.packageName, UserHandle.getCallingUserId()); 6546 if (!UserHandle.isSameApp(uid, Binder.getCallingUid())) { 6547 String msg = "Permission Denial: cancelIntentSender() from pid=" 6548 + Binder.getCallingPid() 6549 + ", uid=" + Binder.getCallingUid() 6550 + " is not allowed to cancel packges " 6551 + rec.key.packageName; 6552 Slog.w(TAG, msg); 6553 throw new SecurityException(msg); 6554 } 6555 } catch (RemoteException e) { 6556 throw new SecurityException(e); 6557 } 6558 cancelIntentSenderLocked(rec, true); 6559 } 6560 } 6561 6562 void cancelIntentSenderLocked(PendingIntentRecord rec, boolean cleanActivity) { 6563 rec.canceled = true; 6564 mIntentSenderRecords.remove(rec.key); 6565 if (cleanActivity && rec.key.activity != null) { 6566 rec.key.activity.pendingResults.remove(rec.ref); 6567 } 6568 } 6569 6570 @Override 6571 public String getPackageForIntentSender(IIntentSender pendingResult) { 6572 if (!(pendingResult instanceof PendingIntentRecord)) { 6573 return null; 6574 } 6575 try { 6576 PendingIntentRecord res = (PendingIntentRecord)pendingResult; 6577 return res.key.packageName; 6578 } catch (ClassCastException e) { 6579 } 6580 return null; 6581 } 6582 6583 @Override 6584 public int getUidForIntentSender(IIntentSender sender) { 6585 if (sender instanceof PendingIntentRecord) { 6586 try { 6587 PendingIntentRecord res = (PendingIntentRecord)sender; 6588 return res.uid; 6589 } catch (ClassCastException e) { 6590 } 6591 } 6592 return -1; 6593 } 6594 6595 @Override 6596 public boolean isIntentSenderTargetedToPackage(IIntentSender pendingResult) { 6597 if (!(pendingResult instanceof PendingIntentRecord)) { 6598 return false; 6599 } 6600 try { 6601 PendingIntentRecord res = (PendingIntentRecord)pendingResult; 6602 if (res.key.allIntents == null) { 6603 return false; 6604 } 6605 for (int i=0; i<res.key.allIntents.length; i++) { 6606 Intent intent = res.key.allIntents[i]; 6607 if (intent.getPackage() != null && intent.getComponent() != null) { 6608 return false; 6609 } 6610 } 6611 return true; 6612 } catch (ClassCastException e) { 6613 } 6614 return false; 6615 } 6616 6617 @Override 6618 public boolean isIntentSenderAnActivity(IIntentSender pendingResult) { 6619 if (!(pendingResult instanceof PendingIntentRecord)) { 6620 return false; 6621 } 6622 try { 6623 PendingIntentRecord res = (PendingIntentRecord)pendingResult; 6624 if (res.key.type == ActivityManager.INTENT_SENDER_ACTIVITY) { 6625 return true; 6626 } 6627 return false; 6628 } catch (ClassCastException e) { 6629 } 6630 return false; 6631 } 6632 6633 @Override 6634 public Intent getIntentForIntentSender(IIntentSender pendingResult) { 6635 if (!(pendingResult instanceof PendingIntentRecord)) { 6636 return null; 6637 } 6638 try { 6639 PendingIntentRecord res = (PendingIntentRecord)pendingResult; 6640 return res.key.requestIntent != null ? new Intent(res.key.requestIntent) : null; 6641 } catch (ClassCastException e) { 6642 } 6643 return null; 6644 } 6645 6646 @Override 6647 public String getTagForIntentSender(IIntentSender pendingResult, String prefix) { 6648 if (!(pendingResult instanceof PendingIntentRecord)) { 6649 return null; 6650 } 6651 try { 6652 PendingIntentRecord res = (PendingIntentRecord)pendingResult; 6653 Intent intent = res.key.requestIntent; 6654 if (intent != null) { 6655 if (res.lastTag != null && res.lastTagPrefix == prefix && (res.lastTagPrefix == null 6656 || res.lastTagPrefix.equals(prefix))) { 6657 return res.lastTag; 6658 } 6659 res.lastTagPrefix = prefix; 6660 StringBuilder sb = new StringBuilder(128); 6661 if (prefix != null) { 6662 sb.append(prefix); 6663 } 6664 if (intent.getAction() != null) { 6665 sb.append(intent.getAction()); 6666 } else if (intent.getComponent() != null) { 6667 intent.getComponent().appendShortString(sb); 6668 } else { 6669 sb.append("?"); 6670 } 6671 return res.lastTag = sb.toString(); 6672 } 6673 } catch (ClassCastException e) { 6674 } 6675 return null; 6676 } 6677 6678 @Override 6679 public void setProcessLimit(int max) { 6680 enforceCallingPermission(android.Manifest.permission.SET_PROCESS_LIMIT, 6681 "setProcessLimit()"); 6682 synchronized (this) { 6683 mProcessLimit = max < 0 ? ProcessList.MAX_CACHED_APPS : max; 6684 mProcessLimitOverride = max; 6685 } 6686 trimApplications(); 6687 } 6688 6689 @Override 6690 public int getProcessLimit() { 6691 synchronized (this) { 6692 return mProcessLimitOverride; 6693 } 6694 } 6695 6696 void foregroundTokenDied(ForegroundToken token) { 6697 synchronized (ActivityManagerService.this) { 6698 synchronized (mPidsSelfLocked) { 6699 ForegroundToken cur 6700 = mForegroundProcesses.get(token.pid); 6701 if (cur != token) { 6702 return; 6703 } 6704 mForegroundProcesses.remove(token.pid); 6705 ProcessRecord pr = mPidsSelfLocked.get(token.pid); 6706 if (pr == null) { 6707 return; 6708 } 6709 pr.forcingToForeground = null; 6710 updateProcessForegroundLocked(pr, false, false); 6711 } 6712 updateOomAdjLocked(); 6713 } 6714 } 6715 6716 @Override 6717 public void setProcessForeground(IBinder token, int pid, boolean isForeground) { 6718 enforceCallingPermission(android.Manifest.permission.SET_PROCESS_LIMIT, 6719 "setProcessForeground()"); 6720 synchronized(this) { 6721 boolean changed = false; 6722 6723 synchronized (mPidsSelfLocked) { 6724 ProcessRecord pr = mPidsSelfLocked.get(pid); 6725 if (pr == null && isForeground) { 6726 Slog.w(TAG, "setProcessForeground called on unknown pid: " + pid); 6727 return; 6728 } 6729 ForegroundToken oldToken = mForegroundProcesses.get(pid); 6730 if (oldToken != null) { 6731 oldToken.token.unlinkToDeath(oldToken, 0); 6732 mForegroundProcesses.remove(pid); 6733 if (pr != null) { 6734 pr.forcingToForeground = null; 6735 } 6736 changed = true; 6737 } 6738 if (isForeground && token != null) { 6739 ForegroundToken newToken = new ForegroundToken() { 6740 @Override 6741 public void binderDied() { 6742 foregroundTokenDied(this); 6743 } 6744 }; 6745 newToken.pid = pid; 6746 newToken.token = token; 6747 try { 6748 token.linkToDeath(newToken, 0); 6749 mForegroundProcesses.put(pid, newToken); 6750 pr.forcingToForeground = token; 6751 changed = true; 6752 } catch (RemoteException e) { 6753 // If the process died while doing this, we will later 6754 // do the cleanup with the process death link. 6755 } 6756 } 6757 } 6758 6759 if (changed) { 6760 updateOomAdjLocked(); 6761 } 6762 } 6763 } 6764 6765 // ========================================================= 6766 // PERMISSIONS 6767 // ========================================================= 6768 6769 static class PermissionController extends IPermissionController.Stub { 6770 ActivityManagerService mActivityManagerService; 6771 PermissionController(ActivityManagerService activityManagerService) { 6772 mActivityManagerService = activityManagerService; 6773 } 6774 6775 @Override 6776 public boolean checkPermission(String permission, int pid, int uid) { 6777 return mActivityManagerService.checkPermission(permission, pid, 6778 uid) == PackageManager.PERMISSION_GRANTED; 6779 } 6780 } 6781 6782 class IntentFirewallInterface implements IntentFirewall.AMSInterface { 6783 @Override 6784 public int checkComponentPermission(String permission, int pid, int uid, 6785 int owningUid, boolean exported) { 6786 return ActivityManagerService.this.checkComponentPermission(permission, pid, uid, 6787 owningUid, exported); 6788 } 6789 6790 @Override 6791 public Object getAMSLock() { 6792 return ActivityManagerService.this; 6793 } 6794 } 6795 6796 /** 6797 * This can be called with or without the global lock held. 6798 */ 6799 int checkComponentPermission(String permission, int pid, int uid, 6800 int owningUid, boolean exported) { 6801 // We might be performing an operation on behalf of an indirect binder 6802 // invocation, e.g. via {@link #openContentUri}. Check and adjust the 6803 // client identity accordingly before proceeding. 6804 Identity tlsIdentity = sCallerIdentity.get(); 6805 if (tlsIdentity != null) { 6806 Slog.d(TAG, "checkComponentPermission() adjusting {pid,uid} to {" 6807 + tlsIdentity.pid + "," + tlsIdentity.uid + "}"); 6808 uid = tlsIdentity.uid; 6809 pid = tlsIdentity.pid; 6810 } 6811 6812 if (pid == MY_PID) { 6813 return PackageManager.PERMISSION_GRANTED; 6814 } 6815 6816 return ActivityManager.checkComponentPermission(permission, uid, 6817 owningUid, exported); 6818 } 6819 6820 /** 6821 * As the only public entry point for permissions checking, this method 6822 * can enforce the semantic that requesting a check on a null global 6823 * permission is automatically denied. (Internally a null permission 6824 * string is used when calling {@link #checkComponentPermission} in cases 6825 * when only uid-based security is needed.) 6826 * 6827 * This can be called with or without the global lock held. 6828 */ 6829 @Override 6830 public int checkPermission(String permission, int pid, int uid) { 6831 if (permission == null) { 6832 return PackageManager.PERMISSION_DENIED; 6833 } 6834 return checkComponentPermission(permission, pid, UserHandle.getAppId(uid), -1, true); 6835 } 6836 6837 /** 6838 * Binder IPC calls go through the public entry point. 6839 * This can be called with or without the global lock held. 6840 */ 6841 int checkCallingPermission(String permission) { 6842 return checkPermission(permission, 6843 Binder.getCallingPid(), 6844 UserHandle.getAppId(Binder.getCallingUid())); 6845 } 6846 6847 /** 6848 * This can be called with or without the global lock held. 6849 */ 6850 void enforceCallingPermission(String permission, String func) { 6851 if (checkCallingPermission(permission) 6852 == PackageManager.PERMISSION_GRANTED) { 6853 return; 6854 } 6855 6856 String msg = "Permission Denial: " + func + " from pid=" 6857 + Binder.getCallingPid() 6858 + ", uid=" + Binder.getCallingUid() 6859 + " requires " + permission; 6860 Slog.w(TAG, msg); 6861 throw new SecurityException(msg); 6862 } 6863 6864 /** 6865 * Determine if UID is holding permissions required to access {@link Uri} in 6866 * the given {@link ProviderInfo}. Final permission checking is always done 6867 * in {@link ContentProvider}. 6868 */ 6869 private final boolean checkHoldingPermissionsLocked( 6870 IPackageManager pm, ProviderInfo pi, GrantUri grantUri, int uid, final int modeFlags) { 6871 if (DEBUG_URI_PERMISSION) Slog.v(TAG, 6872 "checkHoldingPermissionsLocked: uri=" + grantUri + " uid=" + uid); 6873 if (UserHandle.getUserId(uid) != grantUri.sourceUserId) { 6874 if (ActivityManager.checkComponentPermission(INTERACT_ACROSS_USERS, uid, -1, true) 6875 != PERMISSION_GRANTED) { 6876 return false; 6877 } 6878 } 6879 return checkHoldingPermissionsInternalLocked(pm, pi, grantUri, uid, modeFlags, true); 6880 } 6881 6882 private final boolean checkHoldingPermissionsInternalLocked(IPackageManager pm, ProviderInfo pi, 6883 GrantUri grantUri, int uid, final int modeFlags, boolean considerUidPermissions) { 6884 if (pi.applicationInfo.uid == uid) { 6885 return true; 6886 } else if (!pi.exported) { 6887 return false; 6888 } 6889 6890 boolean readMet = (modeFlags & Intent.FLAG_GRANT_READ_URI_PERMISSION) == 0; 6891 boolean writeMet = (modeFlags & Intent.FLAG_GRANT_WRITE_URI_PERMISSION) == 0; 6892 try { 6893 // check if target holds top-level <provider> permissions 6894 if (!readMet && pi.readPermission != null && considerUidPermissions 6895 && (pm.checkUidPermission(pi.readPermission, uid) == PERMISSION_GRANTED)) { 6896 readMet = true; 6897 } 6898 if (!writeMet && pi.writePermission != null && considerUidPermissions 6899 && (pm.checkUidPermission(pi.writePermission, uid) == PERMISSION_GRANTED)) { 6900 writeMet = true; 6901 } 6902 6903 // track if unprotected read/write is allowed; any denied 6904 // <path-permission> below removes this ability 6905 boolean allowDefaultRead = pi.readPermission == null; 6906 boolean allowDefaultWrite = pi.writePermission == null; 6907 6908 // check if target holds any <path-permission> that match uri 6909 final PathPermission[] pps = pi.pathPermissions; 6910 if (pps != null) { 6911 final String path = grantUri.uri.getPath(); 6912 int i = pps.length; 6913 while (i > 0 && (!readMet || !writeMet)) { 6914 i--; 6915 PathPermission pp = pps[i]; 6916 if (pp.match(path)) { 6917 if (!readMet) { 6918 final String pprperm = pp.getReadPermission(); 6919 if (DEBUG_URI_PERMISSION) Slog.v(TAG, "Checking read perm for " 6920 + pprperm + " for " + pp.getPath() 6921 + ": match=" + pp.match(path) 6922 + " check=" + pm.checkUidPermission(pprperm, uid)); 6923 if (pprperm != null) { 6924 if (considerUidPermissions && pm.checkUidPermission(pprperm, uid) 6925 == PERMISSION_GRANTED) { 6926 readMet = true; 6927 } else { 6928 allowDefaultRead = false; 6929 } 6930 } 6931 } 6932 if (!writeMet) { 6933 final String ppwperm = pp.getWritePermission(); 6934 if (DEBUG_URI_PERMISSION) Slog.v(TAG, "Checking write perm " 6935 + ppwperm + " for " + pp.getPath() 6936 + ": match=" + pp.match(path) 6937 + " check=" + pm.checkUidPermission(ppwperm, uid)); 6938 if (ppwperm != null) { 6939 if (considerUidPermissions && pm.checkUidPermission(ppwperm, uid) 6940 == PERMISSION_GRANTED) { 6941 writeMet = true; 6942 } else { 6943 allowDefaultWrite = false; 6944 } 6945 } 6946 } 6947 } 6948 } 6949 } 6950 6951 // grant unprotected <provider> read/write, if not blocked by 6952 // <path-permission> above 6953 if (allowDefaultRead) readMet = true; 6954 if (allowDefaultWrite) writeMet = true; 6955 6956 } catch (RemoteException e) { 6957 return false; 6958 } 6959 6960 return readMet && writeMet; 6961 } 6962 6963 private ProviderInfo getProviderInfoLocked(String authority, int userHandle) { 6964 ProviderInfo pi = null; 6965 ContentProviderRecord cpr = mProviderMap.getProviderByName(authority, userHandle); 6966 if (cpr != null) { 6967 pi = cpr.info; 6968 } else { 6969 try { 6970 pi = AppGlobals.getPackageManager().resolveContentProvider( 6971 authority, PackageManager.GET_URI_PERMISSION_PATTERNS, userHandle); 6972 } catch (RemoteException ex) { 6973 } 6974 } 6975 return pi; 6976 } 6977 6978 private UriPermission findUriPermissionLocked(int targetUid, GrantUri grantUri) { 6979 final ArrayMap<GrantUri, UriPermission> targetUris = mGrantedUriPermissions.get(targetUid); 6980 if (targetUris != null) { 6981 return targetUris.get(grantUri); 6982 } 6983 return null; 6984 } 6985 6986 private UriPermission findOrCreateUriPermissionLocked(String sourcePkg, 6987 String targetPkg, int targetUid, GrantUri grantUri) { 6988 ArrayMap<GrantUri, UriPermission> targetUris = mGrantedUriPermissions.get(targetUid); 6989 if (targetUris == null) { 6990 targetUris = Maps.newArrayMap(); 6991 mGrantedUriPermissions.put(targetUid, targetUris); 6992 } 6993 6994 UriPermission perm = targetUris.get(grantUri); 6995 if (perm == null) { 6996 perm = new UriPermission(sourcePkg, targetPkg, targetUid, grantUri); 6997 targetUris.put(grantUri, perm); 6998 } 6999 7000 return perm; 7001 } 7002 7003 private final boolean checkUriPermissionLocked(GrantUri grantUri, int uid, 7004 final int modeFlags) { 7005 final boolean persistable = (modeFlags & Intent.FLAG_GRANT_PERSISTABLE_URI_PERMISSION) != 0; 7006 final int minStrength = persistable ? UriPermission.STRENGTH_PERSISTABLE 7007 : UriPermission.STRENGTH_OWNED; 7008 7009 // Root gets to do everything. 7010 if (uid == 0) { 7011 return true; 7012 } 7013 7014 final ArrayMap<GrantUri, UriPermission> perms = mGrantedUriPermissions.get(uid); 7015 if (perms == null) return false; 7016 7017 // First look for exact match 7018 final UriPermission exactPerm = perms.get(grantUri); 7019 if (exactPerm != null && exactPerm.getStrength(modeFlags) >= minStrength) { 7020 return true; 7021 } 7022 7023 // No exact match, look for prefixes 7024 final int N = perms.size(); 7025 for (int i = 0; i < N; i++) { 7026 final UriPermission perm = perms.valueAt(i); 7027 if (perm.uri.prefix && grantUri.uri.isPathPrefixMatch(perm.uri.uri) 7028 && perm.getStrength(modeFlags) >= minStrength) { 7029 return true; 7030 } 7031 } 7032 7033 return false; 7034 } 7035 7036 /** 7037 * @param uri This uri must NOT contain an embedded userId. 7038 * @param userId The userId in which the uri is to be resolved. 7039 */ 7040 @Override 7041 public int checkUriPermission(Uri uri, int pid, int uid, 7042 final int modeFlags, int userId) { 7043 enforceNotIsolatedCaller("checkUriPermission"); 7044 7045 // Another redirected-binder-call permissions check as in 7046 // {@link checkComponentPermission}. 7047 Identity tlsIdentity = sCallerIdentity.get(); 7048 if (tlsIdentity != null) { 7049 uid = tlsIdentity.uid; 7050 pid = tlsIdentity.pid; 7051 } 7052 7053 // Our own process gets to do everything. 7054 if (pid == MY_PID) { 7055 return PackageManager.PERMISSION_GRANTED; 7056 } 7057 synchronized (this) { 7058 return checkUriPermissionLocked(new GrantUri(userId, uri, false), uid, modeFlags) 7059 ? PackageManager.PERMISSION_GRANTED 7060 : PackageManager.PERMISSION_DENIED; 7061 } 7062 } 7063 7064 /** 7065 * Check if the targetPkg can be granted permission to access uri by 7066 * the callingUid using the given modeFlags. Throws a security exception 7067 * if callingUid is not allowed to do this. Returns the uid of the target 7068 * if the URI permission grant should be performed; returns -1 if it is not 7069 * needed (for example targetPkg already has permission to access the URI). 7070 * If you already know the uid of the target, you can supply it in 7071 * lastTargetUid else set that to -1. 7072 */ 7073 int checkGrantUriPermissionLocked(int callingUid, String targetPkg, GrantUri grantUri, 7074 final int modeFlags, int lastTargetUid) { 7075 if (!Intent.isAccessUriMode(modeFlags)) { 7076 return -1; 7077 } 7078 7079 if (targetPkg != null) { 7080 if (DEBUG_URI_PERMISSION) Slog.v(TAG, 7081 "Checking grant " + targetPkg + " permission to " + grantUri); 7082 } 7083 7084 final IPackageManager pm = AppGlobals.getPackageManager(); 7085 7086 // If this is not a content: uri, we can't do anything with it. 7087 if (!ContentResolver.SCHEME_CONTENT.equals(grantUri.uri.getScheme())) { 7088 if (DEBUG_URI_PERMISSION) Slog.v(TAG, 7089 "Can't grant URI permission for non-content URI: " + grantUri); 7090 return -1; 7091 } 7092 7093 final String authority = grantUri.uri.getAuthority(); 7094 final ProviderInfo pi = getProviderInfoLocked(authority, grantUri.sourceUserId); 7095 if (pi == null) { 7096 Slog.w(TAG, "No content provider found for permission check: " + 7097 grantUri.uri.toSafeString()); 7098 return -1; 7099 } 7100 7101 int targetUid = lastTargetUid; 7102 if (targetUid < 0 && targetPkg != null) { 7103 try { 7104 targetUid = pm.getPackageUid(targetPkg, UserHandle.getUserId(callingUid)); 7105 if (targetUid < 0) { 7106 if (DEBUG_URI_PERMISSION) Slog.v(TAG, 7107 "Can't grant URI permission no uid for: " + targetPkg); 7108 return -1; 7109 } 7110 } catch (RemoteException ex) { 7111 return -1; 7112 } 7113 } 7114 7115 if (targetUid >= 0) { 7116 // First... does the target actually need this permission? 7117 if (checkHoldingPermissionsLocked(pm, pi, grantUri, targetUid, modeFlags)) { 7118 // No need to grant the target this permission. 7119 if (DEBUG_URI_PERMISSION) Slog.v(TAG, 7120 "Target " + targetPkg + " already has full permission to " + grantUri); 7121 return -1; 7122 } 7123 } else { 7124 // First... there is no target package, so can anyone access it? 7125 boolean allowed = pi.exported; 7126 if ((modeFlags&Intent.FLAG_GRANT_READ_URI_PERMISSION) != 0) { 7127 if (pi.readPermission != null) { 7128 allowed = false; 7129 } 7130 } 7131 if ((modeFlags&Intent.FLAG_GRANT_WRITE_URI_PERMISSION) != 0) { 7132 if (pi.writePermission != null) { 7133 allowed = false; 7134 } 7135 } 7136 if (allowed) { 7137 return -1; 7138 } 7139 } 7140 7141 /* There is a special cross user grant if: 7142 * - The target is on another user. 7143 * - Apps on the current user can access the uri without any uid permissions. 7144 * In this case, we grant a uri permission, even if the ContentProvider does not normally 7145 * grant uri permissions. 7146 */ 7147 boolean specialCrossUserGrant = UserHandle.getUserId(targetUid) != grantUri.sourceUserId 7148 && checkHoldingPermissionsInternalLocked(pm, pi, grantUri, callingUid, 7149 modeFlags, false /*without considering the uid permissions*/); 7150 7151 // Second... is the provider allowing granting of URI permissions? 7152 if (!specialCrossUserGrant) { 7153 if (!pi.grantUriPermissions) { 7154 throw new SecurityException("Provider " + pi.packageName 7155 + "/" + pi.name 7156 + " does not allow granting of Uri permissions (uri " 7157 + grantUri + ")"); 7158 } 7159 if (pi.uriPermissionPatterns != null) { 7160 final int N = pi.uriPermissionPatterns.length; 7161 boolean allowed = false; 7162 for (int i=0; i<N; i++) { 7163 if (pi.uriPermissionPatterns[i] != null 7164 && pi.uriPermissionPatterns[i].match(grantUri.uri.getPath())) { 7165 allowed = true; 7166 break; 7167 } 7168 } 7169 if (!allowed) { 7170 throw new SecurityException("Provider " + pi.packageName 7171 + "/" + pi.name 7172 + " does not allow granting of permission to path of Uri " 7173 + grantUri); 7174 } 7175 } 7176 } 7177 7178 // Third... does the caller itself have permission to access 7179 // this uri? 7180 if (UserHandle.getAppId(callingUid) != Process.SYSTEM_UID) { 7181 if (!checkHoldingPermissionsLocked(pm, pi, grantUri, callingUid, modeFlags)) { 7182 // Require they hold a strong enough Uri permission 7183 if (!checkUriPermissionLocked(grantUri, callingUid, modeFlags)) { 7184 throw new SecurityException("Uid " + callingUid 7185 + " does not have permission to uri " + grantUri); 7186 } 7187 } 7188 } 7189 return targetUid; 7190 } 7191 7192 /** 7193 * @param uri This uri must NOT contain an embedded userId. 7194 * @param userId The userId in which the uri is to be resolved. 7195 */ 7196 @Override 7197 public int checkGrantUriPermission(int callingUid, String targetPkg, Uri uri, 7198 final int modeFlags, int userId) { 7199 enforceNotIsolatedCaller("checkGrantUriPermission"); 7200 synchronized(this) { 7201 return checkGrantUriPermissionLocked(callingUid, targetPkg, 7202 new GrantUri(userId, uri, false), modeFlags, -1); 7203 } 7204 } 7205 7206 void grantUriPermissionUncheckedLocked(int targetUid, String targetPkg, GrantUri grantUri, 7207 final int modeFlags, UriPermissionOwner owner) { 7208 if (!Intent.isAccessUriMode(modeFlags)) { 7209 return; 7210 } 7211 7212 // So here we are: the caller has the assumed permission 7213 // to the uri, and the target doesn't. Let's now give this to 7214 // the target. 7215 7216 if (DEBUG_URI_PERMISSION) Slog.v(TAG, 7217 "Granting " + targetPkg + "/" + targetUid + " permission to " + grantUri); 7218 7219 final String authority = grantUri.uri.getAuthority(); 7220 final ProviderInfo pi = getProviderInfoLocked(authority, grantUri.sourceUserId); 7221 if (pi == null) { 7222 Slog.w(TAG, "No content provider found for grant: " + grantUri.toSafeString()); 7223 return; 7224 } 7225 7226 if ((modeFlags & Intent.FLAG_GRANT_PREFIX_URI_PERMISSION) != 0) { 7227 grantUri.prefix = true; 7228 } 7229 final UriPermission perm = findOrCreateUriPermissionLocked( 7230 pi.packageName, targetPkg, targetUid, grantUri); 7231 perm.grantModes(modeFlags, owner); 7232 } 7233 7234 void grantUriPermissionLocked(int callingUid, String targetPkg, GrantUri grantUri, 7235 final int modeFlags, UriPermissionOwner owner, int targetUserId) { 7236 if (targetPkg == null) { 7237 throw new NullPointerException("targetPkg"); 7238 } 7239 int targetUid; 7240 final IPackageManager pm = AppGlobals.getPackageManager(); 7241 try { 7242 targetUid = pm.getPackageUid(targetPkg, targetUserId); 7243 } catch (RemoteException ex) { 7244 return; 7245 } 7246 7247 targetUid = checkGrantUriPermissionLocked(callingUid, targetPkg, grantUri, modeFlags, 7248 targetUid); 7249 if (targetUid < 0) { 7250 return; 7251 } 7252 7253 grantUriPermissionUncheckedLocked(targetUid, targetPkg, grantUri, modeFlags, 7254 owner); 7255 } 7256 7257 static class NeededUriGrants extends ArrayList<GrantUri> { 7258 final String targetPkg; 7259 final int targetUid; 7260 final int flags; 7261 7262 NeededUriGrants(String targetPkg, int targetUid, int flags) { 7263 this.targetPkg = targetPkg; 7264 this.targetUid = targetUid; 7265 this.flags = flags; 7266 } 7267 } 7268 7269 /** 7270 * Like checkGrantUriPermissionLocked, but takes an Intent. 7271 */ 7272 NeededUriGrants checkGrantUriPermissionFromIntentLocked(int callingUid, 7273 String targetPkg, Intent intent, int mode, NeededUriGrants needed, int targetUserId) { 7274 if (DEBUG_URI_PERMISSION) Slog.v(TAG, 7275 "Checking URI perm to data=" + (intent != null ? intent.getData() : null) 7276 + " clip=" + (intent != null ? intent.getClipData() : null) 7277 + " from " + intent + "; flags=0x" 7278 + Integer.toHexString(intent != null ? intent.getFlags() : 0)); 7279 7280 if (targetPkg == null) { 7281 throw new NullPointerException("targetPkg"); 7282 } 7283 7284 if (intent == null) { 7285 return null; 7286 } 7287 Uri data = intent.getData(); 7288 ClipData clip = intent.getClipData(); 7289 if (data == null && clip == null) { 7290 return null; 7291 } 7292 // Default userId for uris in the intent (if they don't specify it themselves) 7293 int contentUserHint = intent.getContentUserHint(); 7294 if (contentUserHint == UserHandle.USER_CURRENT) { 7295 contentUserHint = UserHandle.getUserId(callingUid); 7296 } 7297 final IPackageManager pm = AppGlobals.getPackageManager(); 7298 int targetUid; 7299 if (needed != null) { 7300 targetUid = needed.targetUid; 7301 } else { 7302 try { 7303 targetUid = pm.getPackageUid(targetPkg, targetUserId); 7304 } catch (RemoteException ex) { 7305 return null; 7306 } 7307 if (targetUid < 0) { 7308 if (DEBUG_URI_PERMISSION) { 7309 Slog.v(TAG, "Can't grant URI permission no uid for: " + targetPkg 7310 + " on user " + targetUserId); 7311 } 7312 return null; 7313 } 7314 } 7315 if (data != null) { 7316 GrantUri grantUri = GrantUri.resolve(contentUserHint, data); 7317 targetUid = checkGrantUriPermissionLocked(callingUid, targetPkg, grantUri, mode, 7318 targetUid); 7319 if (targetUid > 0) { 7320 if (needed == null) { 7321 needed = new NeededUriGrants(targetPkg, targetUid, mode); 7322 } 7323 needed.add(grantUri); 7324 } 7325 } 7326 if (clip != null) { 7327 for (int i=0; i<clip.getItemCount(); i++) { 7328 Uri uri = clip.getItemAt(i).getUri(); 7329 if (uri != null) { 7330 GrantUri grantUri = GrantUri.resolve(contentUserHint, uri); 7331 targetUid = checkGrantUriPermissionLocked(callingUid, targetPkg, grantUri, mode, 7332 targetUid); 7333 if (targetUid > 0) { 7334 if (needed == null) { 7335 needed = new NeededUriGrants(targetPkg, targetUid, mode); 7336 } 7337 needed.add(grantUri); 7338 } 7339 } else { 7340 Intent clipIntent = clip.getItemAt(i).getIntent(); 7341 if (clipIntent != null) { 7342 NeededUriGrants newNeeded = checkGrantUriPermissionFromIntentLocked( 7343 callingUid, targetPkg, clipIntent, mode, needed, targetUserId); 7344 if (newNeeded != null) { 7345 needed = newNeeded; 7346 } 7347 } 7348 } 7349 } 7350 } 7351 7352 return needed; 7353 } 7354 7355 /** 7356 * Like grantUriPermissionUncheckedLocked, but takes an Intent. 7357 */ 7358 void grantUriPermissionUncheckedFromIntentLocked(NeededUriGrants needed, 7359 UriPermissionOwner owner) { 7360 if (needed != null) { 7361 for (int i=0; i<needed.size(); i++) { 7362 GrantUri grantUri = needed.get(i); 7363 grantUriPermissionUncheckedLocked(needed.targetUid, needed.targetPkg, 7364 grantUri, needed.flags, owner); 7365 } 7366 } 7367 } 7368 7369 void grantUriPermissionFromIntentLocked(int callingUid, 7370 String targetPkg, Intent intent, UriPermissionOwner owner, int targetUserId) { 7371 NeededUriGrants needed = checkGrantUriPermissionFromIntentLocked(callingUid, targetPkg, 7372 intent, intent != null ? intent.getFlags() : 0, null, targetUserId); 7373 if (needed == null) { 7374 return; 7375 } 7376 7377 grantUriPermissionUncheckedFromIntentLocked(needed, owner); 7378 } 7379 7380 /** 7381 * @param uri This uri must NOT contain an embedded userId. 7382 * @param userId The userId in which the uri is to be resolved. 7383 */ 7384 @Override 7385 public void grantUriPermission(IApplicationThread caller, String targetPkg, Uri uri, 7386 final int modeFlags, int userId) { 7387 enforceNotIsolatedCaller("grantUriPermission"); 7388 GrantUri grantUri = new GrantUri(userId, uri, false); 7389 synchronized(this) { 7390 final ProcessRecord r = getRecordForAppLocked(caller); 7391 if (r == null) { 7392 throw new SecurityException("Unable to find app for caller " 7393 + caller 7394 + " when granting permission to uri " + grantUri); 7395 } 7396 if (targetPkg == null) { 7397 throw new IllegalArgumentException("null target"); 7398 } 7399 if (grantUri == null) { 7400 throw new IllegalArgumentException("null uri"); 7401 } 7402 7403 Preconditions.checkFlagsArgument(modeFlags, Intent.FLAG_GRANT_READ_URI_PERMISSION 7404 | Intent.FLAG_GRANT_WRITE_URI_PERMISSION 7405 | Intent.FLAG_GRANT_PERSISTABLE_URI_PERMISSION 7406 | Intent.FLAG_GRANT_PREFIX_URI_PERMISSION); 7407 7408 grantUriPermissionLocked(r.uid, targetPkg, grantUri, modeFlags, null, 7409 UserHandle.getUserId(r.uid)); 7410 } 7411 } 7412 7413 void removeUriPermissionIfNeededLocked(UriPermission perm) { 7414 if (perm.modeFlags == 0) { 7415 final ArrayMap<GrantUri, UriPermission> perms = mGrantedUriPermissions.get( 7416 perm.targetUid); 7417 if (perms != null) { 7418 if (DEBUG_URI_PERMISSION) Slog.v(TAG, 7419 "Removing " + perm.targetUid + " permission to " + perm.uri); 7420 7421 perms.remove(perm.uri); 7422 if (perms.isEmpty()) { 7423 mGrantedUriPermissions.remove(perm.targetUid); 7424 } 7425 } 7426 } 7427 } 7428 7429 private void revokeUriPermissionLocked(int callingUid, GrantUri grantUri, final int modeFlags) { 7430 if (DEBUG_URI_PERMISSION) Slog.v(TAG, "Revoking all granted permissions to " + grantUri); 7431 7432 final IPackageManager pm = AppGlobals.getPackageManager(); 7433 final String authority = grantUri.uri.getAuthority(); 7434 final ProviderInfo pi = getProviderInfoLocked(authority, grantUri.sourceUserId); 7435 if (pi == null) { 7436 Slog.w(TAG, "No content provider found for permission revoke: " 7437 + grantUri.toSafeString()); 7438 return; 7439 } 7440 7441 // Does the caller have this permission on the URI? 7442 if (!checkHoldingPermissionsLocked(pm, pi, grantUri, callingUid, modeFlags)) { 7443 // If they don't have direct access to the URI, then revoke any 7444 // ownerless URI permissions that have been granted to them. 7445 final ArrayMap<GrantUri, UriPermission> perms = mGrantedUriPermissions.get(callingUid); 7446 if (perms != null) { 7447 boolean persistChanged = false; 7448 for (Iterator<UriPermission> it = perms.values().iterator(); it.hasNext();) { 7449 final UriPermission perm = it.next(); 7450 if (perm.uri.sourceUserId == grantUri.sourceUserId 7451 && perm.uri.uri.isPathPrefixMatch(grantUri.uri)) { 7452 if (DEBUG_URI_PERMISSION) 7453 Slog.v(TAG, "Revoking non-owned " + perm.targetUid + 7454 " permission to " + perm.uri); 7455 persistChanged |= perm.revokeModes( 7456 modeFlags | Intent.FLAG_GRANT_PERSISTABLE_URI_PERMISSION, false); 7457 if (perm.modeFlags == 0) { 7458 it.remove(); 7459 } 7460 } 7461 } 7462 if (perms.isEmpty()) { 7463 mGrantedUriPermissions.remove(callingUid); 7464 } 7465 if (persistChanged) { 7466 schedulePersistUriGrants(); 7467 } 7468 } 7469 return; 7470 } 7471 7472 boolean persistChanged = false; 7473 7474 // Go through all of the permissions and remove any that match. 7475 int N = mGrantedUriPermissions.size(); 7476 for (int i = 0; i < N; i++) { 7477 final int targetUid = mGrantedUriPermissions.keyAt(i); 7478 final ArrayMap<GrantUri, UriPermission> perms = mGrantedUriPermissions.valueAt(i); 7479 7480 for (Iterator<UriPermission> it = perms.values().iterator(); it.hasNext();) { 7481 final UriPermission perm = it.next(); 7482 if (perm.uri.sourceUserId == grantUri.sourceUserId 7483 && perm.uri.uri.isPathPrefixMatch(grantUri.uri)) { 7484 if (DEBUG_URI_PERMISSION) 7485 Slog.v(TAG, 7486 "Revoking " + perm.targetUid + " permission to " + perm.uri); 7487 persistChanged |= perm.revokeModes( 7488 modeFlags | Intent.FLAG_GRANT_PERSISTABLE_URI_PERMISSION, true); 7489 if (perm.modeFlags == 0) { 7490 it.remove(); 7491 } 7492 } 7493 } 7494 7495 if (perms.isEmpty()) { 7496 mGrantedUriPermissions.remove(targetUid); 7497 N--; 7498 i--; 7499 } 7500 } 7501 7502 if (persistChanged) { 7503 schedulePersistUriGrants(); 7504 } 7505 } 7506 7507 /** 7508 * @param uri This uri must NOT contain an embedded userId. 7509 * @param userId The userId in which the uri is to be resolved. 7510 */ 7511 @Override 7512 public void revokeUriPermission(IApplicationThread caller, Uri uri, final int modeFlags, 7513 int userId) { 7514 enforceNotIsolatedCaller("revokeUriPermission"); 7515 synchronized(this) { 7516 final ProcessRecord r = getRecordForAppLocked(caller); 7517 if (r == null) { 7518 throw new SecurityException("Unable to find app for caller " 7519 + caller 7520 + " when revoking permission to uri " + uri); 7521 } 7522 if (uri == null) { 7523 Slog.w(TAG, "revokeUriPermission: null uri"); 7524 return; 7525 } 7526 7527 if (!Intent.isAccessUriMode(modeFlags)) { 7528 return; 7529 } 7530 7531 final IPackageManager pm = AppGlobals.getPackageManager(); 7532 final String authority = uri.getAuthority(); 7533 final ProviderInfo pi = getProviderInfoLocked(authority, userId); 7534 if (pi == null) { 7535 Slog.w(TAG, "No content provider found for permission revoke: " 7536 + uri.toSafeString()); 7537 return; 7538 } 7539 7540 revokeUriPermissionLocked(r.uid, new GrantUri(userId, uri, false), modeFlags); 7541 } 7542 } 7543 7544 /** 7545 * Remove any {@link UriPermission} granted <em>from</em> or <em>to</em> the 7546 * given package. 7547 * 7548 * @param packageName Package name to match, or {@code null} to apply to all 7549 * packages. 7550 * @param userHandle User to match, or {@link UserHandle#USER_ALL} to apply 7551 * to all users. 7552 * @param persistable If persistable grants should be removed. 7553 */ 7554 private void removeUriPermissionsForPackageLocked( 7555 String packageName, int userHandle, boolean persistable) { 7556 if (userHandle == UserHandle.USER_ALL && packageName == null) { 7557 throw new IllegalArgumentException("Must narrow by either package or user"); 7558 } 7559 7560 boolean persistChanged = false; 7561 7562 int N = mGrantedUriPermissions.size(); 7563 for (int i = 0; i < N; i++) { 7564 final int targetUid = mGrantedUriPermissions.keyAt(i); 7565 final ArrayMap<GrantUri, UriPermission> perms = mGrantedUriPermissions.valueAt(i); 7566 7567 // Only inspect grants matching user 7568 if (userHandle == UserHandle.USER_ALL 7569 || userHandle == UserHandle.getUserId(targetUid)) { 7570 for (Iterator<UriPermission> it = perms.values().iterator(); it.hasNext();) { 7571 final UriPermission perm = it.next(); 7572 7573 // Only inspect grants matching package 7574 if (packageName == null || perm.sourcePkg.equals(packageName) 7575 || perm.targetPkg.equals(packageName)) { 7576 persistChanged |= perm.revokeModes(persistable 7577 ? ~0 : ~Intent.FLAG_GRANT_PERSISTABLE_URI_PERMISSION, true); 7578 7579 // Only remove when no modes remain; any persisted grants 7580 // will keep this alive. 7581 if (perm.modeFlags == 0) { 7582 it.remove(); 7583 } 7584 } 7585 } 7586 7587 if (perms.isEmpty()) { 7588 mGrantedUriPermissions.remove(targetUid); 7589 N--; 7590 i--; 7591 } 7592 } 7593 } 7594 7595 if (persistChanged) { 7596 schedulePersistUriGrants(); 7597 } 7598 } 7599 7600 @Override 7601 public IBinder newUriPermissionOwner(String name) { 7602 enforceNotIsolatedCaller("newUriPermissionOwner"); 7603 synchronized(this) { 7604 UriPermissionOwner owner = new UriPermissionOwner(this, name); 7605 return owner.getExternalTokenLocked(); 7606 } 7607 } 7608 7609 /** 7610 * @param uri This uri must NOT contain an embedded userId. 7611 * @param sourceUserId The userId in which the uri is to be resolved. 7612 * @param targetUserId The userId of the app that receives the grant. 7613 */ 7614 @Override 7615 public void grantUriPermissionFromOwner(IBinder token, int fromUid, String targetPkg, Uri uri, 7616 final int modeFlags, int sourceUserId, int targetUserId) { 7617 targetUserId = handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(), 7618 targetUserId, false, ALLOW_FULL_ONLY, "grantUriPermissionFromOwner", null); 7619 synchronized(this) { 7620 UriPermissionOwner owner = UriPermissionOwner.fromExternalToken(token); 7621 if (owner == null) { 7622 throw new IllegalArgumentException("Unknown owner: " + token); 7623 } 7624 if (fromUid != Binder.getCallingUid()) { 7625 if (Binder.getCallingUid() != Process.myUid()) { 7626 // Only system code can grant URI permissions on behalf 7627 // of other users. 7628 throw new SecurityException("nice try"); 7629 } 7630 } 7631 if (targetPkg == null) { 7632 throw new IllegalArgumentException("null target"); 7633 } 7634 if (uri == null) { 7635 throw new IllegalArgumentException("null uri"); 7636 } 7637 7638 grantUriPermissionLocked(fromUid, targetPkg, new GrantUri(sourceUserId, uri, false), 7639 modeFlags, owner, targetUserId); 7640 } 7641 } 7642 7643 /** 7644 * @param uri This uri must NOT contain an embedded userId. 7645 * @param userId The userId in which the uri is to be resolved. 7646 */ 7647 @Override 7648 public void revokeUriPermissionFromOwner(IBinder token, Uri uri, int mode, int userId) { 7649 synchronized(this) { 7650 UriPermissionOwner owner = UriPermissionOwner.fromExternalToken(token); 7651 if (owner == null) { 7652 throw new IllegalArgumentException("Unknown owner: " + token); 7653 } 7654 7655 if (uri == null) { 7656 owner.removeUriPermissionsLocked(mode); 7657 } else { 7658 owner.removeUriPermissionLocked(new GrantUri(userId, uri, false), mode); 7659 } 7660 } 7661 } 7662 7663 private void schedulePersistUriGrants() { 7664 if (!mHandler.hasMessages(PERSIST_URI_GRANTS_MSG)) { 7665 mHandler.sendMessageDelayed(mHandler.obtainMessage(PERSIST_URI_GRANTS_MSG), 7666 10 * DateUtils.SECOND_IN_MILLIS); 7667 } 7668 } 7669 7670 private void writeGrantedUriPermissions() { 7671 if (DEBUG_URI_PERMISSION) Slog.v(TAG, "writeGrantedUriPermissions()"); 7672 7673 // Snapshot permissions so we can persist without lock 7674 ArrayList<UriPermission.Snapshot> persist = Lists.newArrayList(); 7675 synchronized (this) { 7676 final int size = mGrantedUriPermissions.size(); 7677 for (int i = 0; i < size; i++) { 7678 final ArrayMap<GrantUri, UriPermission> perms = mGrantedUriPermissions.valueAt(i); 7679 for (UriPermission perm : perms.values()) { 7680 if (perm.persistedModeFlags != 0) { 7681 persist.add(perm.snapshot()); 7682 } 7683 } 7684 } 7685 } 7686 7687 FileOutputStream fos = null; 7688 try { 7689 fos = mGrantFile.startWrite(); 7690 7691 XmlSerializer out = new FastXmlSerializer(); 7692 out.setOutput(fos, "utf-8"); 7693 out.startDocument(null, true); 7694 out.startTag(null, TAG_URI_GRANTS); 7695 for (UriPermission.Snapshot perm : persist) { 7696 out.startTag(null, TAG_URI_GRANT); 7697 writeIntAttribute(out, ATTR_SOURCE_USER_ID, perm.uri.sourceUserId); 7698 writeIntAttribute(out, ATTR_TARGET_USER_ID, perm.targetUserId); 7699 out.attribute(null, ATTR_SOURCE_PKG, perm.sourcePkg); 7700 out.attribute(null, ATTR_TARGET_PKG, perm.targetPkg); 7701 out.attribute(null, ATTR_URI, String.valueOf(perm.uri.uri)); 7702 writeBooleanAttribute(out, ATTR_PREFIX, perm.uri.prefix); 7703 writeIntAttribute(out, ATTR_MODE_FLAGS, perm.persistedModeFlags); 7704 writeLongAttribute(out, ATTR_CREATED_TIME, perm.persistedCreateTime); 7705 out.endTag(null, TAG_URI_GRANT); 7706 } 7707 out.endTag(null, TAG_URI_GRANTS); 7708 out.endDocument(); 7709 7710 mGrantFile.finishWrite(fos); 7711 } catch (IOException e) { 7712 if (fos != null) { 7713 mGrantFile.failWrite(fos); 7714 } 7715 } 7716 } 7717 7718 private void readGrantedUriPermissionsLocked() { 7719 if (DEBUG_URI_PERMISSION) Slog.v(TAG, "readGrantedUriPermissions()"); 7720 7721 final long now = System.currentTimeMillis(); 7722 7723 FileInputStream fis = null; 7724 try { 7725 fis = mGrantFile.openRead(); 7726 final XmlPullParser in = Xml.newPullParser(); 7727 in.setInput(fis, null); 7728 7729 int type; 7730 while ((type = in.next()) != END_DOCUMENT) { 7731 final String tag = in.getName(); 7732 if (type == START_TAG) { 7733 if (TAG_URI_GRANT.equals(tag)) { 7734 final int sourceUserId; 7735 final int targetUserId; 7736 final int userHandle = readIntAttribute(in, 7737 ATTR_USER_HANDLE, UserHandle.USER_NULL); 7738 if (userHandle != UserHandle.USER_NULL) { 7739 // For backwards compatibility. 7740 sourceUserId = userHandle; 7741 targetUserId = userHandle; 7742 } else { 7743 sourceUserId = readIntAttribute(in, ATTR_SOURCE_USER_ID); 7744 targetUserId = readIntAttribute(in, ATTR_TARGET_USER_ID); 7745 } 7746 final String sourcePkg = in.getAttributeValue(null, ATTR_SOURCE_PKG); 7747 final String targetPkg = in.getAttributeValue(null, ATTR_TARGET_PKG); 7748 final Uri uri = Uri.parse(in.getAttributeValue(null, ATTR_URI)); 7749 final boolean prefix = readBooleanAttribute(in, ATTR_PREFIX); 7750 final int modeFlags = readIntAttribute(in, ATTR_MODE_FLAGS); 7751 final long createdTime = readLongAttribute(in, ATTR_CREATED_TIME, now); 7752 7753 // Sanity check that provider still belongs to source package 7754 final ProviderInfo pi = getProviderInfoLocked( 7755 uri.getAuthority(), sourceUserId); 7756 if (pi != null && sourcePkg.equals(pi.packageName)) { 7757 int targetUid = -1; 7758 try { 7759 targetUid = AppGlobals.getPackageManager() 7760 .getPackageUid(targetPkg, targetUserId); 7761 } catch (RemoteException e) { 7762 } 7763 if (targetUid != -1) { 7764 final UriPermission perm = findOrCreateUriPermissionLocked( 7765 sourcePkg, targetPkg, targetUid, 7766 new GrantUri(sourceUserId, uri, prefix)); 7767 perm.initPersistedModes(modeFlags, createdTime); 7768 } 7769 } else { 7770 Slog.w(TAG, "Persisted grant for " + uri + " had source " + sourcePkg 7771 + " but instead found " + pi); 7772 } 7773 } 7774 } 7775 } 7776 } catch (FileNotFoundException e) { 7777 // Missing grants is okay 7778 } catch (IOException e) { 7779 Slog.wtf(TAG, "Failed reading Uri grants", e); 7780 } catch (XmlPullParserException e) { 7781 Slog.wtf(TAG, "Failed reading Uri grants", e); 7782 } finally { 7783 IoUtils.closeQuietly(fis); 7784 } 7785 } 7786 7787 /** 7788 * @param uri This uri must NOT contain an embedded userId. 7789 * @param userId The userId in which the uri is to be resolved. 7790 */ 7791 @Override 7792 public void takePersistableUriPermission(Uri uri, final int modeFlags, int userId) { 7793 enforceNotIsolatedCaller("takePersistableUriPermission"); 7794 7795 Preconditions.checkFlagsArgument(modeFlags, 7796 Intent.FLAG_GRANT_READ_URI_PERMISSION | Intent.FLAG_GRANT_WRITE_URI_PERMISSION); 7797 7798 synchronized (this) { 7799 final int callingUid = Binder.getCallingUid(); 7800 boolean persistChanged = false; 7801 GrantUri grantUri = new GrantUri(userId, uri, false); 7802 7803 UriPermission exactPerm = findUriPermissionLocked(callingUid, 7804 new GrantUri(userId, uri, false)); 7805 UriPermission prefixPerm = findUriPermissionLocked(callingUid, 7806 new GrantUri(userId, uri, true)); 7807 7808 final boolean exactValid = (exactPerm != null) 7809 && ((modeFlags & exactPerm.persistableModeFlags) == modeFlags); 7810 final boolean prefixValid = (prefixPerm != null) 7811 && ((modeFlags & prefixPerm.persistableModeFlags) == modeFlags); 7812 7813 if (!(exactValid || prefixValid)) { 7814 throw new SecurityException("No persistable permission grants found for UID " 7815 + callingUid + " and Uri " + grantUri.toSafeString()); 7816 } 7817 7818 if (exactValid) { 7819 persistChanged |= exactPerm.takePersistableModes(modeFlags); 7820 } 7821 if (prefixValid) { 7822 persistChanged |= prefixPerm.takePersistableModes(modeFlags); 7823 } 7824 7825 persistChanged |= maybePrunePersistedUriGrantsLocked(callingUid); 7826 7827 if (persistChanged) { 7828 schedulePersistUriGrants(); 7829 } 7830 } 7831 } 7832 7833 /** 7834 * @param uri This uri must NOT contain an embedded userId. 7835 * @param userId The userId in which the uri is to be resolved. 7836 */ 7837 @Override 7838 public void releasePersistableUriPermission(Uri uri, final int modeFlags, int userId) { 7839 enforceNotIsolatedCaller("releasePersistableUriPermission"); 7840 7841 Preconditions.checkFlagsArgument(modeFlags, 7842 Intent.FLAG_GRANT_READ_URI_PERMISSION | Intent.FLAG_GRANT_WRITE_URI_PERMISSION); 7843 7844 synchronized (this) { 7845 final int callingUid = Binder.getCallingUid(); 7846 boolean persistChanged = false; 7847 7848 UriPermission exactPerm = findUriPermissionLocked(callingUid, 7849 new GrantUri(userId, uri, false)); 7850 UriPermission prefixPerm = findUriPermissionLocked(callingUid, 7851 new GrantUri(userId, uri, true)); 7852 if (exactPerm == null && prefixPerm == null) { 7853 throw new SecurityException("No permission grants found for UID " + callingUid 7854 + " and Uri " + uri.toSafeString()); 7855 } 7856 7857 if (exactPerm != null) { 7858 persistChanged |= exactPerm.releasePersistableModes(modeFlags); 7859 removeUriPermissionIfNeededLocked(exactPerm); 7860 } 7861 if (prefixPerm != null) { 7862 persistChanged |= prefixPerm.releasePersistableModes(modeFlags); 7863 removeUriPermissionIfNeededLocked(prefixPerm); 7864 } 7865 7866 if (persistChanged) { 7867 schedulePersistUriGrants(); 7868 } 7869 } 7870 } 7871 7872 /** 7873 * Prune any older {@link UriPermission} for the given UID until outstanding 7874 * persisted grants are below {@link #MAX_PERSISTED_URI_GRANTS}. 7875 * 7876 * @return if any mutations occured that require persisting. 7877 */ 7878 private boolean maybePrunePersistedUriGrantsLocked(int uid) { 7879 final ArrayMap<GrantUri, UriPermission> perms = mGrantedUriPermissions.get(uid); 7880 if (perms == null) return false; 7881 if (perms.size() < MAX_PERSISTED_URI_GRANTS) return false; 7882 7883 final ArrayList<UriPermission> persisted = Lists.newArrayList(); 7884 for (UriPermission perm : perms.values()) { 7885 if (perm.persistedModeFlags != 0) { 7886 persisted.add(perm); 7887 } 7888 } 7889 7890 final int trimCount = persisted.size() - MAX_PERSISTED_URI_GRANTS; 7891 if (trimCount <= 0) return false; 7892 7893 Collections.sort(persisted, new UriPermission.PersistedTimeComparator()); 7894 for (int i = 0; i < trimCount; i++) { 7895 final UriPermission perm = persisted.get(i); 7896 7897 if (DEBUG_URI_PERMISSION) { 7898 Slog.v(TAG, "Trimming grant created at " + perm.persistedCreateTime); 7899 } 7900 7901 perm.releasePersistableModes(~0); 7902 removeUriPermissionIfNeededLocked(perm); 7903 } 7904 7905 return true; 7906 } 7907 7908 @Override 7909 public ParceledListSlice<android.content.UriPermission> getPersistedUriPermissions( 7910 String packageName, boolean incoming) { 7911 enforceNotIsolatedCaller("getPersistedUriPermissions"); 7912 Preconditions.checkNotNull(packageName, "packageName"); 7913 7914 final int callingUid = Binder.getCallingUid(); 7915 final IPackageManager pm = AppGlobals.getPackageManager(); 7916 try { 7917 final int packageUid = pm.getPackageUid(packageName, UserHandle.getUserId(callingUid)); 7918 if (packageUid != callingUid) { 7919 throw new SecurityException( 7920 "Package " + packageName + " does not belong to calling UID " + callingUid); 7921 } 7922 } catch (RemoteException e) { 7923 throw new SecurityException("Failed to verify package name ownership"); 7924 } 7925 7926 final ArrayList<android.content.UriPermission> result = Lists.newArrayList(); 7927 synchronized (this) { 7928 if (incoming) { 7929 final ArrayMap<GrantUri, UriPermission> perms = mGrantedUriPermissions.get( 7930 callingUid); 7931 if (perms == null) { 7932 Slog.w(TAG, "No permission grants found for " + packageName); 7933 } else { 7934 for (UriPermission perm : perms.values()) { 7935 if (packageName.equals(perm.targetPkg) && perm.persistedModeFlags != 0) { 7936 result.add(perm.buildPersistedPublicApiObject()); 7937 } 7938 } 7939 } 7940 } else { 7941 final int size = mGrantedUriPermissions.size(); 7942 for (int i = 0; i < size; i++) { 7943 final ArrayMap<GrantUri, UriPermission> perms = 7944 mGrantedUriPermissions.valueAt(i); 7945 for (UriPermission perm : perms.values()) { 7946 if (packageName.equals(perm.sourcePkg) && perm.persistedModeFlags != 0) { 7947 result.add(perm.buildPersistedPublicApiObject()); 7948 } 7949 } 7950 } 7951 } 7952 } 7953 return new ParceledListSlice<android.content.UriPermission>(result); 7954 } 7955 7956 @Override 7957 public void showWaitingForDebugger(IApplicationThread who, boolean waiting) { 7958 synchronized (this) { 7959 ProcessRecord app = 7960 who != null ? getRecordForAppLocked(who) : null; 7961 if (app == null) return; 7962 7963 Message msg = Message.obtain(); 7964 msg.what = WAIT_FOR_DEBUGGER_MSG; 7965 msg.obj = app; 7966 msg.arg1 = waiting ? 1 : 0; 7967 mHandler.sendMessage(msg); 7968 } 7969 } 7970 7971 @Override 7972 public void getMemoryInfo(ActivityManager.MemoryInfo outInfo) { 7973 final long homeAppMem = mProcessList.getMemLevel(ProcessList.HOME_APP_ADJ); 7974 final long cachedAppMem = mProcessList.getMemLevel(ProcessList.CACHED_APP_MIN_ADJ); 7975 outInfo.availMem = Process.getFreeMemory(); 7976 outInfo.totalMem = Process.getTotalMemory(); 7977 outInfo.threshold = homeAppMem; 7978 outInfo.lowMemory = outInfo.availMem < (homeAppMem + ((cachedAppMem-homeAppMem)/2)); 7979 outInfo.hiddenAppThreshold = cachedAppMem; 7980 outInfo.secondaryServerThreshold = mProcessList.getMemLevel( 7981 ProcessList.SERVICE_ADJ); 7982 outInfo.visibleAppThreshold = mProcessList.getMemLevel( 7983 ProcessList.VISIBLE_APP_ADJ); 7984 outInfo.foregroundAppThreshold = mProcessList.getMemLevel( 7985 ProcessList.FOREGROUND_APP_ADJ); 7986 } 7987 7988 // ========================================================= 7989 // TASK MANAGEMENT 7990 // ========================================================= 7991 7992 @Override 7993 public List<IAppTask> getAppTasks(String callingPackage) { 7994 int callingUid = Binder.getCallingUid(); 7995 long ident = Binder.clearCallingIdentity(); 7996 7997 synchronized(this) { 7998 ArrayList<IAppTask> list = new ArrayList<IAppTask>(); 7999 try { 8000 if (localLOGV) Slog.v(TAG, "getAppTasks"); 8001 8002 final int N = mRecentTasks.size(); 8003 for (int i = 0; i < N; i++) { 8004 TaskRecord tr = mRecentTasks.get(i); 8005 // Skip tasks that do not match the caller. We don't need to verify 8006 // callingPackage, because we are also limiting to callingUid and know 8007 // that will limit to the correct security sandbox. 8008 if (tr.effectiveUid != callingUid) { 8009 continue; 8010 } 8011 Intent intent = tr.getBaseIntent(); 8012 if (intent == null || 8013 !callingPackage.equals(intent.getComponent().getPackageName())) { 8014 continue; 8015 } 8016 ActivityManager.RecentTaskInfo taskInfo = 8017 createRecentTaskInfoFromTaskRecord(tr); 8018 AppTaskImpl taskImpl = new AppTaskImpl(taskInfo.persistentId, callingUid); 8019 list.add(taskImpl); 8020 } 8021 } finally { 8022 Binder.restoreCallingIdentity(ident); 8023 } 8024 return list; 8025 } 8026 } 8027 8028 @Override 8029 public List<RunningTaskInfo> getTasks(int maxNum, int flags) { 8030 final int callingUid = Binder.getCallingUid(); 8031 ArrayList<RunningTaskInfo> list = new ArrayList<RunningTaskInfo>(); 8032 8033 synchronized(this) { 8034 if (localLOGV) Slog.v( 8035 TAG, "getTasks: max=" + maxNum + ", flags=" + flags); 8036 8037 final boolean allowed = isGetTasksAllowed("getTasks", Binder.getCallingPid(), 8038 callingUid); 8039 8040 // TODO: Improve with MRU list from all ActivityStacks. 8041 mStackSupervisor.getTasksLocked(maxNum, list, callingUid, allowed); 8042 } 8043 8044 return list; 8045 } 8046 8047 TaskRecord getMostRecentTask() { 8048 return mRecentTasks.get(0); 8049 } 8050 8051 /** 8052 * Creates a new RecentTaskInfo from a TaskRecord. 8053 */ 8054 private ActivityManager.RecentTaskInfo createRecentTaskInfoFromTaskRecord(TaskRecord tr) { 8055 // Update the task description to reflect any changes in the task stack 8056 tr.updateTaskDescription(); 8057 8058 // Compose the recent task info 8059 ActivityManager.RecentTaskInfo rti = new ActivityManager.RecentTaskInfo(); 8060 rti.id = tr.getTopActivity() == null ? -1 : tr.taskId; 8061 rti.persistentId = tr.taskId; 8062 rti.baseIntent = new Intent(tr.getBaseIntent()); 8063 rti.origActivity = tr.origActivity; 8064 rti.description = tr.lastDescription; 8065 rti.stackId = tr.stack != null ? tr.stack.mStackId : -1; 8066 rti.userId = tr.userId; 8067 rti.taskDescription = new ActivityManager.TaskDescription(tr.lastTaskDescription); 8068 rti.firstActiveTime = tr.firstActiveTime; 8069 rti.lastActiveTime = tr.lastActiveTime; 8070 rti.affiliatedTaskId = tr.mAffiliatedTaskId; 8071 rti.affiliatedTaskColor = tr.mAffiliatedTaskColor; 8072 return rti; 8073 } 8074 8075 private boolean isGetTasksAllowed(String caller, int callingPid, int callingUid) { 8076 boolean allowed = checkPermission(android.Manifest.permission.REAL_GET_TASKS, 8077 callingPid, callingUid) == PackageManager.PERMISSION_GRANTED; 8078 if (!allowed) { 8079 if (checkPermission(android.Manifest.permission.GET_TASKS, 8080 callingPid, callingUid) == PackageManager.PERMISSION_GRANTED) { 8081 // Temporary compatibility: some existing apps on the system image may 8082 // still be requesting the old permission and not switched to the new 8083 // one; if so, we'll still allow them full access. This means we need 8084 // to see if they are holding the old permission and are a system app. 8085 try { 8086 if (AppGlobals.getPackageManager().isUidPrivileged(callingUid)) { 8087 allowed = true; 8088 Slog.w(TAG, caller + ": caller " + callingUid 8089 + " is using old GET_TASKS but privileged; allowing"); 8090 } 8091 } catch (RemoteException e) { 8092 } 8093 } 8094 } 8095 if (!allowed) { 8096 Slog.w(TAG, caller + ": caller " + callingUid 8097 + " does not hold GET_TASKS; limiting output"); 8098 } 8099 return allowed; 8100 } 8101 8102 @Override 8103 public List<ActivityManager.RecentTaskInfo> getRecentTasks(int maxNum, int flags, int userId) { 8104 final int callingUid = Binder.getCallingUid(); 8105 userId = handleIncomingUser(Binder.getCallingPid(), callingUid, userId, 8106 false, ALLOW_FULL_ONLY, "getRecentTasks", null); 8107 8108 final boolean includeProfiles = (flags & ActivityManager.RECENT_INCLUDE_PROFILES) != 0; 8109 final boolean withExcluded = (flags&ActivityManager.RECENT_WITH_EXCLUDED) != 0; 8110 synchronized (this) { 8111 final boolean allowed = isGetTasksAllowed("getRecentTasks", Binder.getCallingPid(), 8112 callingUid); 8113 final boolean detailed = checkCallingPermission( 8114 android.Manifest.permission.GET_DETAILED_TASKS) 8115 == PackageManager.PERMISSION_GRANTED; 8116 8117 final int N = mRecentTasks.size(); 8118 ArrayList<ActivityManager.RecentTaskInfo> res 8119 = new ArrayList<ActivityManager.RecentTaskInfo>( 8120 maxNum < N ? maxNum : N); 8121 8122 final Set<Integer> includedUsers; 8123 if (includeProfiles) { 8124 includedUsers = getProfileIdsLocked(userId); 8125 } else { 8126 includedUsers = new HashSet<Integer>(); 8127 } 8128 includedUsers.add(Integer.valueOf(userId)); 8129 8130 for (int i=0; i<N && maxNum > 0; i++) { 8131 TaskRecord tr = mRecentTasks.get(i); 8132 // Only add calling user or related users recent tasks 8133 if (!includedUsers.contains(Integer.valueOf(tr.userId))) { 8134 if (DEBUG_RECENTS) Slog.d(TAG, "Skipping, not user: " + tr); 8135 continue; 8136 } 8137 8138 // Return the entry if desired by the caller. We always return 8139 // the first entry, because callers always expect this to be the 8140 // foreground app. We may filter others if the caller has 8141 // not supplied RECENT_WITH_EXCLUDED and there is some reason 8142 // we should exclude the entry. 8143 8144 if (i == 0 8145 || withExcluded 8146 || (tr.intent == null) 8147 || ((tr.intent.getFlags() & Intent.FLAG_ACTIVITY_EXCLUDE_FROM_RECENTS) 8148 == 0)) { 8149 if (!allowed) { 8150 // If the caller doesn't have the GET_TASKS permission, then only 8151 // allow them to see a small subset of tasks -- their own and home. 8152 if (!tr.isHomeTask() && tr.effectiveUid != callingUid) { 8153 if (DEBUG_RECENTS) Slog.d(TAG, "Skipping, not allowed: " + tr); 8154 continue; 8155 } 8156 } 8157 if ((flags & ActivityManager.RECENT_IGNORE_HOME_STACK_TASKS) != 0) { 8158 if (tr.stack != null && tr.stack.isHomeStack()) { 8159 if (DEBUG_RECENTS) Slog.d(TAG, "Skipping, home stack task: " + tr); 8160 continue; 8161 } 8162 } 8163 if (tr.autoRemoveRecents && tr.getTopActivity() == null) { 8164 // Don't include auto remove tasks that are finished or finishing. 8165 if (DEBUG_RECENTS) Slog.d(TAG, "Skipping, auto-remove without activity: " 8166 + tr); 8167 continue; 8168 } 8169 if ((flags&ActivityManager.RECENT_IGNORE_UNAVAILABLE) != 0 8170 && !tr.isAvailable) { 8171 if (DEBUG_RECENTS) Slog.d(TAG, "Skipping, unavail real act: " + tr); 8172 continue; 8173 } 8174 8175 ActivityManager.RecentTaskInfo rti = createRecentTaskInfoFromTaskRecord(tr); 8176 if (!detailed) { 8177 rti.baseIntent.replaceExtras((Bundle)null); 8178 } 8179 8180 res.add(rti); 8181 maxNum--; 8182 } 8183 } 8184 return res; 8185 } 8186 } 8187 8188 private TaskRecord taskForIdLocked(int id) { 8189 final TaskRecord task = recentTaskForIdLocked(id); 8190 if (task != null) { 8191 return task; 8192 } 8193 8194 // Don't give up. Sometimes it just hasn't made it to recents yet. 8195 return mStackSupervisor.anyTaskForIdLocked(id); 8196 } 8197 8198 private TaskRecord recentTaskForIdLocked(int id) { 8199 final int N = mRecentTasks.size(); 8200 for (int i=0; i<N; i++) { 8201 TaskRecord tr = mRecentTasks.get(i); 8202 if (tr.taskId == id) { 8203 return tr; 8204 } 8205 } 8206 return null; 8207 } 8208 8209 @Override 8210 public ActivityManager.TaskThumbnail getTaskThumbnail(int id) { 8211 synchronized (this) { 8212 enforceCallingPermission(android.Manifest.permission.READ_FRAME_BUFFER, 8213 "getTaskThumbnail()"); 8214 TaskRecord tr = recentTaskForIdLocked(id); 8215 if (tr != null) { 8216 return tr.getTaskThumbnailLocked(); 8217 } 8218 } 8219 return null; 8220 } 8221 8222 @Override 8223 public int addAppTask(IBinder activityToken, Intent intent, 8224 ActivityManager.TaskDescription description, Bitmap thumbnail) throws RemoteException { 8225 final int callingUid = Binder.getCallingUid(); 8226 final long callingIdent = Binder.clearCallingIdentity(); 8227 8228 try { 8229 synchronized (this) { 8230 ActivityRecord r = ActivityRecord.isInStackLocked(activityToken); 8231 if (r == null) { 8232 throw new IllegalArgumentException("Activity does not exist; token=" 8233 + activityToken); 8234 } 8235 ComponentName comp = intent.getComponent(); 8236 if (comp == null) { 8237 throw new IllegalArgumentException("Intent " + intent 8238 + " must specify explicit component"); 8239 } 8240 if (thumbnail.getWidth() != mThumbnailWidth 8241 || thumbnail.getHeight() != mThumbnailHeight) { 8242 throw new IllegalArgumentException("Bad thumbnail size: got " 8243 + thumbnail.getWidth() + "x" + thumbnail.getHeight() + ", require " 8244 + mThumbnailWidth + "x" + mThumbnailHeight); 8245 } 8246 if (intent.getSelector() != null) { 8247 intent.setSelector(null); 8248 } 8249 if (intent.getSourceBounds() != null) { 8250 intent.setSourceBounds(null); 8251 } 8252 if ((intent.getFlags()&Intent.FLAG_ACTIVITY_NEW_DOCUMENT) != 0) { 8253 if ((intent.getFlags()&Intent.FLAG_ACTIVITY_RETAIN_IN_RECENTS) == 0) { 8254 // The caller has added this as an auto-remove task... that makes no 8255 // sense, so turn off auto-remove. 8256 intent.addFlags(Intent.FLAG_ACTIVITY_RETAIN_IN_RECENTS); 8257 } 8258 } else if ((intent.getFlags()&Intent.FLAG_ACTIVITY_NEW_TASK) != 0) { 8259 // Must be a new task. 8260 intent.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK); 8261 } 8262 if (!comp.equals(mLastAddedTaskComponent) || callingUid != mLastAddedTaskUid) { 8263 mLastAddedTaskActivity = null; 8264 } 8265 ActivityInfo ainfo = mLastAddedTaskActivity; 8266 if (ainfo == null) { 8267 ainfo = mLastAddedTaskActivity = AppGlobals.getPackageManager().getActivityInfo( 8268 comp, 0, UserHandle.getUserId(callingUid)); 8269 if (ainfo.applicationInfo.uid != callingUid) { 8270 throw new SecurityException( 8271 "Can't add task for another application: target uid=" 8272 + ainfo.applicationInfo.uid + ", calling uid=" + callingUid); 8273 } 8274 } 8275 8276 TaskRecord task = new TaskRecord(this, mStackSupervisor.getNextTaskId(), ainfo, 8277 intent, description); 8278 8279 int trimIdx = trimRecentsForTask(task, false); 8280 if (trimIdx >= 0) { 8281 // If this would have caused a trim, then we'll abort because that 8282 // means it would be added at the end of the list but then just removed. 8283 return -1; 8284 } 8285 8286 final int N = mRecentTasks.size(); 8287 if (N >= (ActivityManager.getMaxRecentTasksStatic()-1)) { 8288 final TaskRecord tr = mRecentTasks.remove(N - 1); 8289 tr.removedFromRecents(mTaskPersister); 8290 } 8291 8292 task.inRecents = true; 8293 mRecentTasks.add(task); 8294 r.task.stack.addTask(task, false, false); 8295 8296 task.setLastThumbnail(thumbnail); 8297 task.freeLastThumbnail(); 8298 8299 return task.taskId; 8300 } 8301 } finally { 8302 Binder.restoreCallingIdentity(callingIdent); 8303 } 8304 } 8305 8306 @Override 8307 public Point getAppTaskThumbnailSize() { 8308 synchronized (this) { 8309 return new Point(mThumbnailWidth, mThumbnailHeight); 8310 } 8311 } 8312 8313 @Override 8314 public void setTaskDescription(IBinder token, ActivityManager.TaskDescription td) { 8315 synchronized (this) { 8316 ActivityRecord r = ActivityRecord.isInStackLocked(token); 8317 if (r != null) { 8318 r.setTaskDescription(td); 8319 r.task.updateTaskDescription(); 8320 } 8321 } 8322 } 8323 8324 @Override 8325 public Bitmap getTaskDescriptionIcon(String filename) { 8326 if (!FileUtils.isValidExtFilename(filename) 8327 || !filename.contains(ActivityRecord.ACTIVITY_ICON_SUFFIX)) { 8328 throw new IllegalArgumentException("Bad filename: " + filename); 8329 } 8330 return mTaskPersister.getTaskDescriptionIcon(filename); 8331 } 8332 8333 @Override 8334 public void startInPlaceAnimationOnFrontMostApplication(ActivityOptions opts) 8335 throws RemoteException { 8336 if (opts.getAnimationType() != ActivityOptions.ANIM_CUSTOM_IN_PLACE || 8337 opts.getCustomInPlaceResId() == 0) { 8338 throw new IllegalArgumentException("Expected in-place ActivityOption " + 8339 "with valid animation"); 8340 } 8341 mWindowManager.prepareAppTransition(AppTransition.TRANSIT_TASK_IN_PLACE, false); 8342 mWindowManager.overridePendingAppTransitionInPlace(opts.getPackageName(), 8343 opts.getCustomInPlaceResId()); 8344 mWindowManager.executeAppTransition(); 8345 } 8346 8347 private void cleanUpRemovedTaskLocked(TaskRecord tr, boolean killProcess) { 8348 mRecentTasks.remove(tr); 8349 tr.removedFromRecents(mTaskPersister); 8350 ComponentName component = tr.getBaseIntent().getComponent(); 8351 if (component == null) { 8352 Slog.w(TAG, "No component for base intent of task: " + tr); 8353 return; 8354 } 8355 8356 if (!killProcess) { 8357 return; 8358 } 8359 8360 // Determine if the process(es) for this task should be killed. 8361 final String pkg = component.getPackageName(); 8362 ArrayList<ProcessRecord> procsToKill = new ArrayList<ProcessRecord>(); 8363 ArrayMap<String, SparseArray<ProcessRecord>> pmap = mProcessNames.getMap(); 8364 for (int i = 0; i < pmap.size(); i++) { 8365 8366 SparseArray<ProcessRecord> uids = pmap.valueAt(i); 8367 for (int j = 0; j < uids.size(); j++) { 8368 ProcessRecord proc = uids.valueAt(j); 8369 if (proc.userId != tr.userId) { 8370 // Don't kill process for a different user. 8371 continue; 8372 } 8373 if (proc == mHomeProcess) { 8374 // Don't kill the home process along with tasks from the same package. 8375 continue; 8376 } 8377 if (!proc.pkgList.containsKey(pkg)) { 8378 // Don't kill process that is not associated with this task. 8379 continue; 8380 } 8381 8382 for (int k = 0; k < proc.activities.size(); k++) { 8383 TaskRecord otherTask = proc.activities.get(k).task; 8384 if (tr.taskId != otherTask.taskId && otherTask.inRecents) { 8385 // Don't kill process(es) that has an activity in a different task that is 8386 // also in recents. 8387 return; 8388 } 8389 } 8390 8391 // Add process to kill list. 8392 procsToKill.add(proc); 8393 } 8394 } 8395 8396 // Find any running services associated with this app and stop if needed. 8397 mServices.cleanUpRemovedTaskLocked(tr, component, new Intent(tr.getBaseIntent())); 8398 8399 // Kill the running processes. 8400 for (int i = 0; i < procsToKill.size(); i++) { 8401 ProcessRecord pr = procsToKill.get(i); 8402 if (pr.setSchedGroup == Process.THREAD_GROUP_BG_NONINTERACTIVE) { 8403 pr.kill("remove task", true); 8404 } else { 8405 pr.waitingToKill = "remove task"; 8406 } 8407 } 8408 } 8409 8410 /** 8411 * Removes the task with the specified task id. 8412 * 8413 * @param taskId Identifier of the task to be removed. 8414 * @param killProcess Kill any process associated with the task if possible. 8415 * @return Returns true if the given task was found and removed. 8416 */ 8417 private boolean removeTaskByIdLocked(int taskId, boolean killProcess) { 8418 TaskRecord tr = taskForIdLocked(taskId); 8419 if (tr != null) { 8420 tr.removeTaskActivitiesLocked(); 8421 cleanUpRemovedTaskLocked(tr, killProcess); 8422 if (tr.isPersistable) { 8423 notifyTaskPersisterLocked(null, true); 8424 } 8425 return true; 8426 } 8427 Slog.w(TAG, "Request to remove task ignored for non-existent task " + taskId); 8428 return false; 8429 } 8430 8431 @Override 8432 public boolean removeTask(int taskId) { 8433 synchronized (this) { 8434 enforceCallingPermission(android.Manifest.permission.REMOVE_TASKS, 8435 "removeTask()"); 8436 long ident = Binder.clearCallingIdentity(); 8437 try { 8438 return removeTaskByIdLocked(taskId, true); 8439 } finally { 8440 Binder.restoreCallingIdentity(ident); 8441 } 8442 } 8443 } 8444 8445 /** 8446 * TODO: Add mController hook 8447 */ 8448 @Override 8449 public void moveTaskToFront(int taskId, int flags, Bundle options) { 8450 enforceCallingPermission(android.Manifest.permission.REORDER_TASKS, 8451 "moveTaskToFront()"); 8452 8453 if (DEBUG_STACK) Slog.d(TAG, "moveTaskToFront: moving taskId=" + taskId); 8454 synchronized(this) { 8455 moveTaskToFrontLocked(taskId, flags, options); 8456 } 8457 } 8458 8459 void moveTaskToFrontLocked(int taskId, int flags, Bundle options) { 8460 if (!checkAppSwitchAllowedLocked(Binder.getCallingPid(), 8461 Binder.getCallingUid(), -1, -1, "Task to front")) { 8462 ActivityOptions.abort(options); 8463 return; 8464 } 8465 final long origId = Binder.clearCallingIdentity(); 8466 try { 8467 final TaskRecord task = mStackSupervisor.anyTaskForIdLocked(taskId); 8468 if (task == null) { 8469 Slog.d(TAG, "Could not find task for id: "+ taskId); 8470 return; 8471 } 8472 if (mStackSupervisor.isLockTaskModeViolation(task)) { 8473 mStackSupervisor.showLockTaskToast(); 8474 Slog.e(TAG, "moveTaskToFront: Attempt to violate Lock Task Mode"); 8475 return; 8476 } 8477 final ActivityRecord prev = mStackSupervisor.topRunningActivityLocked(); 8478 if (prev != null && prev.isRecentsActivity()) { 8479 task.setTaskToReturnTo(ActivityRecord.RECENTS_ACTIVITY_TYPE); 8480 } 8481 mStackSupervisor.findTaskToMoveToFrontLocked(task, flags, options); 8482 } finally { 8483 Binder.restoreCallingIdentity(origId); 8484 } 8485 ActivityOptions.abort(options); 8486 } 8487 8488 @Override 8489 public void moveTaskToBack(int taskId) { 8490 enforceCallingPermission(android.Manifest.permission.REORDER_TASKS, 8491 "moveTaskToBack()"); 8492 8493 synchronized(this) { 8494 TaskRecord tr = taskForIdLocked(taskId); 8495 if (tr != null) { 8496 if (tr == mStackSupervisor.mLockTaskModeTask) { 8497 mStackSupervisor.showLockTaskToast(); 8498 return; 8499 } 8500 if (DEBUG_STACK) Slog.d(TAG, "moveTaskToBack: moving task=" + tr); 8501 ActivityStack stack = tr.stack; 8502 if (stack.mResumedActivity != null && stack.mResumedActivity.task == tr) { 8503 if (!checkAppSwitchAllowedLocked(Binder.getCallingPid(), 8504 Binder.getCallingUid(), -1, -1, "Task to back")) { 8505 return; 8506 } 8507 } 8508 final long origId = Binder.clearCallingIdentity(); 8509 try { 8510 stack.moveTaskToBackLocked(taskId, null); 8511 } finally { 8512 Binder.restoreCallingIdentity(origId); 8513 } 8514 } 8515 } 8516 } 8517 8518 /** 8519 * Moves an activity, and all of the other activities within the same task, to the bottom 8520 * of the history stack. The activity's order within the task is unchanged. 8521 * 8522 * @param token A reference to the activity we wish to move 8523 * @param nonRoot If false then this only works if the activity is the root 8524 * of a task; if true it will work for any activity in a task. 8525 * @return Returns true if the move completed, false if not. 8526 */ 8527 @Override 8528 public boolean moveActivityTaskToBack(IBinder token, boolean nonRoot) { 8529 enforceNotIsolatedCaller("moveActivityTaskToBack"); 8530 synchronized(this) { 8531 final long origId = Binder.clearCallingIdentity(); 8532 try { 8533 int taskId = ActivityRecord.getTaskForActivityLocked(token, !nonRoot); 8534 if (taskId >= 0) { 8535 if ((mStackSupervisor.mLockTaskModeTask != null) 8536 && (mStackSupervisor.mLockTaskModeTask.taskId == taskId)) { 8537 mStackSupervisor.showLockTaskToast(); 8538 return false; 8539 } 8540 return ActivityRecord.getStackLocked(token).moveTaskToBackLocked(taskId, null); 8541 } 8542 } finally { 8543 Binder.restoreCallingIdentity(origId); 8544 } 8545 } 8546 return false; 8547 } 8548 8549 @Override 8550 public void moveTaskBackwards(int task) { 8551 enforceCallingPermission(android.Manifest.permission.REORDER_TASKS, 8552 "moveTaskBackwards()"); 8553 8554 synchronized(this) { 8555 if (!checkAppSwitchAllowedLocked(Binder.getCallingPid(), 8556 Binder.getCallingUid(), -1, -1, "Task backwards")) { 8557 return; 8558 } 8559 final long origId = Binder.clearCallingIdentity(); 8560 moveTaskBackwardsLocked(task); 8561 Binder.restoreCallingIdentity(origId); 8562 } 8563 } 8564 8565 private final void moveTaskBackwardsLocked(int task) { 8566 Slog.e(TAG, "moveTaskBackwards not yet implemented!"); 8567 } 8568 8569 @Override 8570 public IBinder getHomeActivityToken() throws RemoteException { 8571 enforceCallingPermission(android.Manifest.permission.MANAGE_ACTIVITY_STACKS, 8572 "getHomeActivityToken()"); 8573 synchronized (this) { 8574 return mStackSupervisor.getHomeActivityToken(); 8575 } 8576 } 8577 8578 @Override 8579 public IActivityContainer createActivityContainer(IBinder parentActivityToken, 8580 IActivityContainerCallback callback) throws RemoteException { 8581 enforceCallingPermission(android.Manifest.permission.MANAGE_ACTIVITY_STACKS, 8582 "createActivityContainer()"); 8583 synchronized (this) { 8584 if (parentActivityToken == null) { 8585 throw new IllegalArgumentException("parent token must not be null"); 8586 } 8587 ActivityRecord r = ActivityRecord.forToken(parentActivityToken); 8588 if (r == null) { 8589 return null; 8590 } 8591 if (callback == null) { 8592 throw new IllegalArgumentException("callback must not be null"); 8593 } 8594 return mStackSupervisor.createActivityContainer(r, callback); 8595 } 8596 } 8597 8598 @Override 8599 public void deleteActivityContainer(IActivityContainer container) throws RemoteException { 8600 enforceCallingPermission(android.Manifest.permission.MANAGE_ACTIVITY_STACKS, 8601 "deleteActivityContainer()"); 8602 synchronized (this) { 8603 mStackSupervisor.deleteActivityContainer(container); 8604 } 8605 } 8606 8607 @Override 8608 public IActivityContainer getEnclosingActivityContainer(IBinder activityToken) 8609 throws RemoteException { 8610 synchronized (this) { 8611 ActivityStack stack = ActivityRecord.getStackLocked(activityToken); 8612 if (stack != null) { 8613 return stack.mActivityContainer; 8614 } 8615 return null; 8616 } 8617 } 8618 8619 @Override 8620 public void moveTaskToStack(int taskId, int stackId, boolean toTop) { 8621 enforceCallingPermission(android.Manifest.permission.MANAGE_ACTIVITY_STACKS, 8622 "moveTaskToStack()"); 8623 if (stackId == HOME_STACK_ID) { 8624 Slog.e(TAG, "moveTaskToStack: Attempt to move task " + taskId + " to home stack", 8625 new RuntimeException("here").fillInStackTrace()); 8626 } 8627 synchronized (this) { 8628 long ident = Binder.clearCallingIdentity(); 8629 try { 8630 if (DEBUG_STACK) Slog.d(TAG, "moveTaskToStack: moving task=" + taskId + " to stackId=" 8631 + stackId + " toTop=" + toTop); 8632 mStackSupervisor.moveTaskToStack(taskId, stackId, toTop); 8633 } finally { 8634 Binder.restoreCallingIdentity(ident); 8635 } 8636 } 8637 } 8638 8639 @Override 8640 public void resizeStack(int stackBoxId, Rect bounds) { 8641 enforceCallingPermission(android.Manifest.permission.MANAGE_ACTIVITY_STACKS, 8642 "resizeStackBox()"); 8643 long ident = Binder.clearCallingIdentity(); 8644 try { 8645 mWindowManager.resizeStack(stackBoxId, bounds); 8646 } finally { 8647 Binder.restoreCallingIdentity(ident); 8648 } 8649 } 8650 8651 @Override 8652 public List<StackInfo> getAllStackInfos() { 8653 enforceCallingPermission(android.Manifest.permission.MANAGE_ACTIVITY_STACKS, 8654 "getAllStackInfos()"); 8655 long ident = Binder.clearCallingIdentity(); 8656 try { 8657 synchronized (this) { 8658 return mStackSupervisor.getAllStackInfosLocked(); 8659 } 8660 } finally { 8661 Binder.restoreCallingIdentity(ident); 8662 } 8663 } 8664 8665 @Override 8666 public StackInfo getStackInfo(int stackId) { 8667 enforceCallingPermission(android.Manifest.permission.MANAGE_ACTIVITY_STACKS, 8668 "getStackInfo()"); 8669 long ident = Binder.clearCallingIdentity(); 8670 try { 8671 synchronized (this) { 8672 return mStackSupervisor.getStackInfoLocked(stackId); 8673 } 8674 } finally { 8675 Binder.restoreCallingIdentity(ident); 8676 } 8677 } 8678 8679 @Override 8680 public boolean isInHomeStack(int taskId) { 8681 enforceCallingPermission(android.Manifest.permission.MANAGE_ACTIVITY_STACKS, 8682 "getStackInfo()"); 8683 long ident = Binder.clearCallingIdentity(); 8684 try { 8685 synchronized (this) { 8686 TaskRecord tr = taskForIdLocked(taskId); 8687 return tr != null && tr.stack != null && tr.stack.isHomeStack(); 8688 } 8689 } finally { 8690 Binder.restoreCallingIdentity(ident); 8691 } 8692 } 8693 8694 @Override 8695 public int getTaskForActivity(IBinder token, boolean onlyRoot) { 8696 synchronized(this) { 8697 return ActivityRecord.getTaskForActivityLocked(token, onlyRoot); 8698 } 8699 } 8700 8701 private boolean isLockTaskAuthorized(String pkg) { 8702 final DevicePolicyManager dpm = (DevicePolicyManager) 8703 mContext.getSystemService(Context.DEVICE_POLICY_SERVICE); 8704 try { 8705 int uid = mContext.getPackageManager().getPackageUid(pkg, 8706 Binder.getCallingUserHandle().getIdentifier()); 8707 return (uid == Binder.getCallingUid()) && dpm != null && dpm.isLockTaskPermitted(pkg); 8708 } catch (NameNotFoundException e) { 8709 return false; 8710 } 8711 } 8712 8713 void startLockTaskMode(TaskRecord task) { 8714 final String pkg; 8715 synchronized (this) { 8716 pkg = task.intent.getComponent().getPackageName(); 8717 } 8718 boolean isSystemInitiated = Binder.getCallingUid() == Process.SYSTEM_UID; 8719 if (!isSystemInitiated && !isLockTaskAuthorized(pkg)) { 8720 StatusBarManagerInternal statusBarManager = LocalServices.getService( 8721 StatusBarManagerInternal.class); 8722 if (statusBarManager != null) { 8723 statusBarManager.showScreenPinningRequest(); 8724 } 8725 return; 8726 } 8727 long ident = Binder.clearCallingIdentity(); 8728 try { 8729 synchronized (this) { 8730 // Since we lost lock on task, make sure it is still there. 8731 task = mStackSupervisor.anyTaskForIdLocked(task.taskId); 8732 if (task != null) { 8733 if (!isSystemInitiated 8734 && ((mStackSupervisor.getFocusedStack() == null) 8735 || (task != mStackSupervisor.getFocusedStack().topTask()))) { 8736 throw new IllegalArgumentException("Invalid task, not in foreground"); 8737 } 8738 mStackSupervisor.setLockTaskModeLocked(task, !isSystemInitiated); 8739 } 8740 } 8741 } finally { 8742 Binder.restoreCallingIdentity(ident); 8743 } 8744 } 8745 8746 @Override 8747 public void startLockTaskMode(int taskId) { 8748 final TaskRecord task; 8749 long ident = Binder.clearCallingIdentity(); 8750 try { 8751 synchronized (this) { 8752 task = mStackSupervisor.anyTaskForIdLocked(taskId); 8753 } 8754 } finally { 8755 Binder.restoreCallingIdentity(ident); 8756 } 8757 if (task != null) { 8758 startLockTaskMode(task); 8759 } 8760 } 8761 8762 @Override 8763 public void startLockTaskMode(IBinder token) { 8764 final TaskRecord task; 8765 long ident = Binder.clearCallingIdentity(); 8766 try { 8767 synchronized (this) { 8768 final ActivityRecord r = ActivityRecord.forToken(token); 8769 if (r == null) { 8770 return; 8771 } 8772 task = r.task; 8773 } 8774 } finally { 8775 Binder.restoreCallingIdentity(ident); 8776 } 8777 if (task != null) { 8778 startLockTaskMode(task); 8779 } 8780 } 8781 8782 @Override 8783 public void startLockTaskModeOnCurrent() throws RemoteException { 8784 enforceCallingPermission(android.Manifest.permission.MANAGE_ACTIVITY_STACKS, 8785 "startLockTaskModeOnCurrent"); 8786 long ident = Binder.clearCallingIdentity(); 8787 try { 8788 ActivityRecord r = null; 8789 synchronized (this) { 8790 r = mStackSupervisor.topRunningActivityLocked(); 8791 } 8792 startLockTaskMode(r.task); 8793 } finally { 8794 Binder.restoreCallingIdentity(ident); 8795 } 8796 } 8797 8798 @Override 8799 public void stopLockTaskMode() { 8800 // Verify that the user matches the package of the intent for the TaskRecord 8801 // we are locked to or systtem. This will ensure the same caller for startLockTaskMode 8802 // and stopLockTaskMode. 8803 final int callingUid = Binder.getCallingUid(); 8804 if (callingUid != Process.SYSTEM_UID) { 8805 try { 8806 String pkg = 8807 mStackSupervisor.mLockTaskModeTask.intent.getComponent().getPackageName(); 8808 int uid = mContext.getPackageManager().getPackageUid(pkg, 8809 Binder.getCallingUserHandle().getIdentifier()); 8810 if (uid != callingUid) { 8811 throw new SecurityException("Invalid uid, expected " + uid); 8812 } 8813 } catch (NameNotFoundException e) { 8814 Log.d(TAG, "stopLockTaskMode " + e); 8815 return; 8816 } 8817 } 8818 long ident = Binder.clearCallingIdentity(); 8819 try { 8820 Log.d(TAG, "stopLockTaskMode"); 8821 // Stop lock task 8822 synchronized (this) { 8823 mStackSupervisor.setLockTaskModeLocked(null, false); 8824 } 8825 } finally { 8826 Binder.restoreCallingIdentity(ident); 8827 } 8828 } 8829 8830 @Override 8831 public void stopLockTaskModeOnCurrent() throws RemoteException { 8832 enforceCallingPermission(android.Manifest.permission.MANAGE_ACTIVITY_STACKS, 8833 "stopLockTaskModeOnCurrent"); 8834 long ident = Binder.clearCallingIdentity(); 8835 try { 8836 stopLockTaskMode(); 8837 } finally { 8838 Binder.restoreCallingIdentity(ident); 8839 } 8840 } 8841 8842 @Override 8843 public boolean isInLockTaskMode() { 8844 synchronized (this) { 8845 return mStackSupervisor.isInLockTaskMode(); 8846 } 8847 } 8848 8849 // ========================================================= 8850 // CONTENT PROVIDERS 8851 // ========================================================= 8852 8853 private final List<ProviderInfo> generateApplicationProvidersLocked(ProcessRecord app) { 8854 List<ProviderInfo> providers = null; 8855 try { 8856 providers = AppGlobals.getPackageManager(). 8857 queryContentProviders(app.processName, app.uid, 8858 STOCK_PM_FLAGS | PackageManager.GET_URI_PERMISSION_PATTERNS); 8859 } catch (RemoteException ex) { 8860 } 8861 if (DEBUG_MU) 8862 Slog.v(TAG_MU, "generateApplicationProvidersLocked, app.info.uid = " + app.uid); 8863 int userId = app.userId; 8864 if (providers != null) { 8865 int N = providers.size(); 8866 app.pubProviders.ensureCapacity(N + app.pubProviders.size()); 8867 for (int i=0; i<N; i++) { 8868 ProviderInfo cpi = 8869 (ProviderInfo)providers.get(i); 8870 boolean singleton = isSingleton(cpi.processName, cpi.applicationInfo, 8871 cpi.name, cpi.flags); 8872 if (singleton && UserHandle.getUserId(app.uid) != 0) { 8873 // This is a singleton provider, but a user besides the 8874 // default user is asking to initialize a process it runs 8875 // in... well, no, it doesn't actually run in this process, 8876 // it runs in the process of the default user. Get rid of it. 8877 providers.remove(i); 8878 N--; 8879 i--; 8880 continue; 8881 } 8882 8883 ComponentName comp = new ComponentName(cpi.packageName, cpi.name); 8884 ContentProviderRecord cpr = mProviderMap.getProviderByClass(comp, userId); 8885 if (cpr == null) { 8886 cpr = new ContentProviderRecord(this, cpi, app.info, comp, singleton); 8887 mProviderMap.putProviderByClass(comp, cpr); 8888 } 8889 if (DEBUG_MU) 8890 Slog.v(TAG_MU, "generateApplicationProvidersLocked, cpi.uid = " + cpr.uid); 8891 app.pubProviders.put(cpi.name, cpr); 8892 if (!cpi.multiprocess || !"android".equals(cpi.packageName)) { 8893 // Don't add this if it is a platform component that is marked 8894 // to run in multiple processes, because this is actually 8895 // part of the framework so doesn't make sense to track as a 8896 // separate apk in the process. 8897 app.addPackage(cpi.applicationInfo.packageName, cpi.applicationInfo.versionCode, 8898 mProcessStats); 8899 } 8900 ensurePackageDexOpt(cpi.applicationInfo.packageName); 8901 } 8902 } 8903 return providers; 8904 } 8905 8906 /** 8907 * Check if {@link ProcessRecord} has a possible chance at accessing the 8908 * given {@link ProviderInfo}. Final permission checking is always done 8909 * in {@link ContentProvider}. 8910 */ 8911 private final String checkContentProviderPermissionLocked( 8912 ProviderInfo cpi, ProcessRecord r, int userId, boolean checkUser) { 8913 final int callingPid = (r != null) ? r.pid : Binder.getCallingPid(); 8914 final int callingUid = (r != null) ? r.uid : Binder.getCallingUid(); 8915 boolean checkedGrants = false; 8916 if (checkUser) { 8917 // Looking for cross-user grants before enforcing the typical cross-users permissions 8918 int tmpTargetUserId = unsafeConvertIncomingUser(userId); 8919 if (tmpTargetUserId != UserHandle.getUserId(callingUid)) { 8920 if (checkAuthorityGrants(callingUid, cpi, tmpTargetUserId, checkUser)) { 8921 return null; 8922 } 8923 checkedGrants = true; 8924 } 8925 userId = handleIncomingUser(callingPid, callingUid, userId, 8926 false, ALLOW_NON_FULL, 8927 "checkContentProviderPermissionLocked " + cpi.authority, null); 8928 if (userId != tmpTargetUserId) { 8929 // When we actually went to determine the final targer user ID, this ended 8930 // up different than our initial check for the authority. This is because 8931 // they had asked for USER_CURRENT_OR_SELF and we ended up switching to 8932 // SELF. So we need to re-check the grants again. 8933 checkedGrants = false; 8934 } 8935 } 8936 if (checkComponentPermission(cpi.readPermission, callingPid, callingUid, 8937 cpi.applicationInfo.uid, cpi.exported) 8938 == PackageManager.PERMISSION_GRANTED) { 8939 return null; 8940 } 8941 if (checkComponentPermission(cpi.writePermission, callingPid, callingUid, 8942 cpi.applicationInfo.uid, cpi.exported) 8943 == PackageManager.PERMISSION_GRANTED) { 8944 return null; 8945 } 8946 8947 PathPermission[] pps = cpi.pathPermissions; 8948 if (pps != null) { 8949 int i = pps.length; 8950 while (i > 0) { 8951 i--; 8952 PathPermission pp = pps[i]; 8953 String pprperm = pp.getReadPermission(); 8954 if (pprperm != null && checkComponentPermission(pprperm, callingPid, callingUid, 8955 cpi.applicationInfo.uid, cpi.exported) 8956 == PackageManager.PERMISSION_GRANTED) { 8957 return null; 8958 } 8959 String ppwperm = pp.getWritePermission(); 8960 if (ppwperm != null && checkComponentPermission(ppwperm, callingPid, callingUid, 8961 cpi.applicationInfo.uid, cpi.exported) 8962 == PackageManager.PERMISSION_GRANTED) { 8963 return null; 8964 } 8965 } 8966 } 8967 if (!checkedGrants && checkAuthorityGrants(callingUid, cpi, userId, checkUser)) { 8968 return null; 8969 } 8970 8971 String msg; 8972 if (!cpi.exported) { 8973 msg = "Permission Denial: opening provider " + cpi.name 8974 + " from " + (r != null ? r : "(null)") + " (pid=" + callingPid 8975 + ", uid=" + callingUid + ") that is not exported from uid " 8976 + cpi.applicationInfo.uid; 8977 } else { 8978 msg = "Permission Denial: opening provider " + cpi.name 8979 + " from " + (r != null ? r : "(null)") + " (pid=" + callingPid 8980 + ", uid=" + callingUid + ") requires " 8981 + cpi.readPermission + " or " + cpi.writePermission; 8982 } 8983 Slog.w(TAG, msg); 8984 return msg; 8985 } 8986 8987 /** 8988 * Returns if the ContentProvider has granted a uri to callingUid 8989 */ 8990 boolean checkAuthorityGrants(int callingUid, ProviderInfo cpi, int userId, boolean checkUser) { 8991 final ArrayMap<GrantUri, UriPermission> perms = mGrantedUriPermissions.get(callingUid); 8992 if (perms != null) { 8993 for (int i=perms.size()-1; i>=0; i--) { 8994 GrantUri grantUri = perms.keyAt(i); 8995 if (grantUri.sourceUserId == userId || !checkUser) { 8996 if (matchesProvider(grantUri.uri, cpi)) { 8997 return true; 8998 } 8999 } 9000 } 9001 } 9002 return false; 9003 } 9004 9005 /** 9006 * Returns true if the uri authority is one of the authorities specified in the provider. 9007 */ 9008 boolean matchesProvider(Uri uri, ProviderInfo cpi) { 9009 String uriAuth = uri.getAuthority(); 9010 String cpiAuth = cpi.authority; 9011 if (cpiAuth.indexOf(';') == -1) { 9012 return cpiAuth.equals(uriAuth); 9013 } 9014 String[] cpiAuths = cpiAuth.split(";"); 9015 int length = cpiAuths.length; 9016 for (int i = 0; i < length; i++) { 9017 if (cpiAuths[i].equals(uriAuth)) return true; 9018 } 9019 return false; 9020 } 9021 9022 ContentProviderConnection incProviderCountLocked(ProcessRecord r, 9023 final ContentProviderRecord cpr, IBinder externalProcessToken, boolean stable) { 9024 if (r != null) { 9025 for (int i=0; i<r.conProviders.size(); i++) { 9026 ContentProviderConnection conn = r.conProviders.get(i); 9027 if (conn.provider == cpr) { 9028 if (DEBUG_PROVIDER) Slog.v(TAG, 9029 "Adding provider requested by " 9030 + r.processName + " from process " 9031 + cpr.info.processName + ": " + cpr.name.flattenToShortString() 9032 + " scnt=" + conn.stableCount + " uscnt=" + conn.unstableCount); 9033 if (stable) { 9034 conn.stableCount++; 9035 conn.numStableIncs++; 9036 } else { 9037 conn.unstableCount++; 9038 conn.numUnstableIncs++; 9039 } 9040 return conn; 9041 } 9042 } 9043 ContentProviderConnection conn = new ContentProviderConnection(cpr, r); 9044 if (stable) { 9045 conn.stableCount = 1; 9046 conn.numStableIncs = 1; 9047 } else { 9048 conn.unstableCount = 1; 9049 conn.numUnstableIncs = 1; 9050 } 9051 cpr.connections.add(conn); 9052 r.conProviders.add(conn); 9053 return conn; 9054 } 9055 cpr.addExternalProcessHandleLocked(externalProcessToken); 9056 return null; 9057 } 9058 9059 boolean decProviderCountLocked(ContentProviderConnection conn, 9060 ContentProviderRecord cpr, IBinder externalProcessToken, boolean stable) { 9061 if (conn != null) { 9062 cpr = conn.provider; 9063 if (DEBUG_PROVIDER) Slog.v(TAG, 9064 "Removing provider requested by " 9065 + conn.client.processName + " from process " 9066 + cpr.info.processName + ": " + cpr.name.flattenToShortString() 9067 + " scnt=" + conn.stableCount + " uscnt=" + conn.unstableCount); 9068 if (stable) { 9069 conn.stableCount--; 9070 } else { 9071 conn.unstableCount--; 9072 } 9073 if (conn.stableCount == 0 && conn.unstableCount == 0) { 9074 cpr.connections.remove(conn); 9075 conn.client.conProviders.remove(conn); 9076 return true; 9077 } 9078 return false; 9079 } 9080 cpr.removeExternalProcessHandleLocked(externalProcessToken); 9081 return false; 9082 } 9083 9084 private void checkTime(long startTime, String where) { 9085 long now = SystemClock.elapsedRealtime(); 9086 if ((now-startTime) > 1000) { 9087 // If we are taking more than a second, log about it. 9088 Slog.w(TAG, "Slow operation: " + (now-startTime) + "ms so far, now at " + where); 9089 } 9090 } 9091 9092 private final ContentProviderHolder getContentProviderImpl(IApplicationThread caller, 9093 String name, IBinder token, boolean stable, int userId) { 9094 ContentProviderRecord cpr; 9095 ContentProviderConnection conn = null; 9096 ProviderInfo cpi = null; 9097 9098 synchronized(this) { 9099 long startTime = SystemClock.elapsedRealtime(); 9100 9101 ProcessRecord r = null; 9102 if (caller != null) { 9103 r = getRecordForAppLocked(caller); 9104 if (r == null) { 9105 throw new SecurityException( 9106 "Unable to find app for caller " + caller 9107 + " (pid=" + Binder.getCallingPid() 9108 + ") when getting content provider " + name); 9109 } 9110 } 9111 9112 boolean checkCrossUser = true; 9113 9114 checkTime(startTime, "getContentProviderImpl: getProviderByName"); 9115 9116 // First check if this content provider has been published... 9117 cpr = mProviderMap.getProviderByName(name, userId); 9118 // If that didn't work, check if it exists for user 0 and then 9119 // verify that it's a singleton provider before using it. 9120 if (cpr == null && userId != UserHandle.USER_OWNER) { 9121 cpr = mProviderMap.getProviderByName(name, UserHandle.USER_OWNER); 9122 if (cpr != null) { 9123 cpi = cpr.info; 9124 if (isSingleton(cpi.processName, cpi.applicationInfo, 9125 cpi.name, cpi.flags) 9126 && isValidSingletonCall(r.uid, cpi.applicationInfo.uid)) { 9127 userId = UserHandle.USER_OWNER; 9128 checkCrossUser = false; 9129 } else { 9130 cpr = null; 9131 cpi = null; 9132 } 9133 } 9134 } 9135 9136 boolean providerRunning = cpr != null; 9137 if (providerRunning) { 9138 cpi = cpr.info; 9139 String msg; 9140 checkTime(startTime, "getContentProviderImpl: before checkContentProviderPermission"); 9141 if ((msg = checkContentProviderPermissionLocked(cpi, r, userId, checkCrossUser)) 9142 != null) { 9143 throw new SecurityException(msg); 9144 } 9145 checkTime(startTime, "getContentProviderImpl: after checkContentProviderPermission"); 9146 9147 if (r != null && cpr.canRunHere(r)) { 9148 // This provider has been published or is in the process 9149 // of being published... but it is also allowed to run 9150 // in the caller's process, so don't make a connection 9151 // and just let the caller instantiate its own instance. 9152 ContentProviderHolder holder = cpr.newHolder(null); 9153 // don't give caller the provider object, it needs 9154 // to make its own. 9155 holder.provider = null; 9156 return holder; 9157 } 9158 9159 final long origId = Binder.clearCallingIdentity(); 9160 9161 checkTime(startTime, "getContentProviderImpl: incProviderCountLocked"); 9162 9163 // In this case the provider instance already exists, so we can 9164 // return it right away. 9165 conn = incProviderCountLocked(r, cpr, token, stable); 9166 if (conn != null && (conn.stableCount+conn.unstableCount) == 1) { 9167 if (cpr.proc != null && r.setAdj <= ProcessList.PERCEPTIBLE_APP_ADJ) { 9168 // If this is a perceptible app accessing the provider, 9169 // make sure to count it as being accessed and thus 9170 // back up on the LRU list. This is good because 9171 // content providers are often expensive to start. 9172 checkTime(startTime, "getContentProviderImpl: before updateLruProcess"); 9173 updateLruProcessLocked(cpr.proc, false, null); 9174 checkTime(startTime, "getContentProviderImpl: after updateLruProcess"); 9175 } 9176 } 9177 9178 if (cpr.proc != null) { 9179 if (false) { 9180 if (cpr.name.flattenToShortString().equals( 9181 "com.android.providers.calendar/.CalendarProvider2")) { 9182 Slog.v(TAG, "****************** KILLING " 9183 + cpr.name.flattenToShortString()); 9184 Process.killProcess(cpr.proc.pid); 9185 } 9186 } 9187 checkTime(startTime, "getContentProviderImpl: before updateOomAdj"); 9188 boolean success = updateOomAdjLocked(cpr.proc); 9189 checkTime(startTime, "getContentProviderImpl: after updateOomAdj"); 9190 if (DEBUG_PROVIDER) Slog.i(TAG, "Adjust success: " + success); 9191 // NOTE: there is still a race here where a signal could be 9192 // pending on the process even though we managed to update its 9193 // adj level. Not sure what to do about this, but at least 9194 // the race is now smaller. 9195 if (!success) { 9196 // Uh oh... it looks like the provider's process 9197 // has been killed on us. We need to wait for a new 9198 // process to be started, and make sure its death 9199 // doesn't kill our process. 9200 Slog.i(TAG, 9201 "Existing provider " + cpr.name.flattenToShortString() 9202 + " is crashing; detaching " + r); 9203 boolean lastRef = decProviderCountLocked(conn, cpr, token, stable); 9204 checkTime(startTime, "getContentProviderImpl: before appDied"); 9205 appDiedLocked(cpr.proc); 9206 checkTime(startTime, "getContentProviderImpl: after appDied"); 9207 if (!lastRef) { 9208 // This wasn't the last ref our process had on 9209 // the provider... we have now been killed, bail. 9210 return null; 9211 } 9212 providerRunning = false; 9213 conn = null; 9214 } 9215 } 9216 9217 Binder.restoreCallingIdentity(origId); 9218 } 9219 9220 boolean singleton; 9221 if (!providerRunning) { 9222 try { 9223 checkTime(startTime, "getContentProviderImpl: before resolveContentProvider"); 9224 cpi = AppGlobals.getPackageManager(). 9225 resolveContentProvider(name, 9226 STOCK_PM_FLAGS | PackageManager.GET_URI_PERMISSION_PATTERNS, userId); 9227 checkTime(startTime, "getContentProviderImpl: after resolveContentProvider"); 9228 } catch (RemoteException ex) { 9229 } 9230 if (cpi == null) { 9231 return null; 9232 } 9233 // If the provider is a singleton AND 9234 // (it's a call within the same user || the provider is a 9235 // privileged app) 9236 // Then allow connecting to the singleton provider 9237 singleton = isSingleton(cpi.processName, cpi.applicationInfo, 9238 cpi.name, cpi.flags) 9239 && isValidSingletonCall(r.uid, cpi.applicationInfo.uid); 9240 if (singleton) { 9241 userId = UserHandle.USER_OWNER; 9242 } 9243 cpi.applicationInfo = getAppInfoForUser(cpi.applicationInfo, userId); 9244 checkTime(startTime, "getContentProviderImpl: got app info for user"); 9245 9246 String msg; 9247 checkTime(startTime, "getContentProviderImpl: before checkContentProviderPermission"); 9248 if ((msg = checkContentProviderPermissionLocked(cpi, r, userId, !singleton)) 9249 != null) { 9250 throw new SecurityException(msg); 9251 } 9252 checkTime(startTime, "getContentProviderImpl: after checkContentProviderPermission"); 9253 9254 if (!mProcessesReady && !mDidUpdate && !mWaitingUpdate 9255 && !cpi.processName.equals("system")) { 9256 // If this content provider does not run in the system 9257 // process, and the system is not yet ready to run other 9258 // processes, then fail fast instead of hanging. 9259 throw new IllegalArgumentException( 9260 "Attempt to launch content provider before system ready"); 9261 } 9262 9263 // Make sure that the user who owns this provider is started. If not, 9264 // we don't want to allow it to run. 9265 if (mStartedUsers.get(userId) == null) { 9266 Slog.w(TAG, "Unable to launch app " 9267 + cpi.applicationInfo.packageName + "/" 9268 + cpi.applicationInfo.uid + " for provider " 9269 + name + ": user " + userId + " is stopped"); 9270 return null; 9271 } 9272 9273 ComponentName comp = new ComponentName(cpi.packageName, cpi.name); 9274 checkTime(startTime, "getContentProviderImpl: before getProviderByClass"); 9275 cpr = mProviderMap.getProviderByClass(comp, userId); 9276 checkTime(startTime, "getContentProviderImpl: after getProviderByClass"); 9277 final boolean firstClass = cpr == null; 9278 if (firstClass) { 9279 final long ident = Binder.clearCallingIdentity(); 9280 try { 9281 checkTime(startTime, "getContentProviderImpl: before getApplicationInfo"); 9282 ApplicationInfo ai = 9283 AppGlobals.getPackageManager(). 9284 getApplicationInfo( 9285 cpi.applicationInfo.packageName, 9286 STOCK_PM_FLAGS, userId); 9287 checkTime(startTime, "getContentProviderImpl: after getApplicationInfo"); 9288 if (ai == null) { 9289 Slog.w(TAG, "No package info for content provider " 9290 + cpi.name); 9291 return null; 9292 } 9293 ai = getAppInfoForUser(ai, userId); 9294 cpr = new ContentProviderRecord(this, cpi, ai, comp, singleton); 9295 } catch (RemoteException ex) { 9296 // pm is in same process, this will never happen. 9297 } finally { 9298 Binder.restoreCallingIdentity(ident); 9299 } 9300 } 9301 9302 checkTime(startTime, "getContentProviderImpl: now have ContentProviderRecord"); 9303 9304 if (r != null && cpr.canRunHere(r)) { 9305 // If this is a multiprocess provider, then just return its 9306 // info and allow the caller to instantiate it. Only do 9307 // this if the provider is the same user as the caller's 9308 // process, or can run as root (so can be in any process). 9309 return cpr.newHolder(null); 9310 } 9311 9312 if (DEBUG_PROVIDER) { 9313 RuntimeException e = new RuntimeException("here"); 9314 Slog.w(TAG, "LAUNCHING REMOTE PROVIDER (myuid " + (r != null ? r.uid : null) 9315 + " pruid " + cpr.appInfo.uid + "): " + cpr.info.name, e); 9316 } 9317 9318 // This is single process, and our app is now connecting to it. 9319 // See if we are already in the process of launching this 9320 // provider. 9321 final int N = mLaunchingProviders.size(); 9322 int i; 9323 for (i=0; i<N; i++) { 9324 if (mLaunchingProviders.get(i) == cpr) { 9325 break; 9326 } 9327 } 9328 9329 // If the provider is not already being launched, then get it 9330 // started. 9331 if (i >= N) { 9332 final long origId = Binder.clearCallingIdentity(); 9333 9334 try { 9335 // Content provider is now in use, its package can't be stopped. 9336 try { 9337 checkTime(startTime, "getContentProviderImpl: before set stopped state"); 9338 AppGlobals.getPackageManager().setPackageStoppedState( 9339 cpr.appInfo.packageName, false, userId); 9340 checkTime(startTime, "getContentProviderImpl: after set stopped state"); 9341 } catch (RemoteException e) { 9342 } catch (IllegalArgumentException e) { 9343 Slog.w(TAG, "Failed trying to unstop package " 9344 + cpr.appInfo.packageName + ": " + e); 9345 } 9346 9347 // Use existing process if already started 9348 checkTime(startTime, "getContentProviderImpl: looking for process record"); 9349 ProcessRecord proc = getProcessRecordLocked( 9350 cpi.processName, cpr.appInfo.uid, false); 9351 if (proc != null && proc.thread != null) { 9352 if (DEBUG_PROVIDER) { 9353 Slog.d(TAG, "Installing in existing process " + proc); 9354 } 9355 checkTime(startTime, "getContentProviderImpl: scheduling install"); 9356 proc.pubProviders.put(cpi.name, cpr); 9357 try { 9358 proc.thread.scheduleInstallProvider(cpi); 9359 } catch (RemoteException e) { 9360 } 9361 } else { 9362 checkTime(startTime, "getContentProviderImpl: before start process"); 9363 proc = startProcessLocked(cpi.processName, 9364 cpr.appInfo, false, 0, "content provider", 9365 new ComponentName(cpi.applicationInfo.packageName, 9366 cpi.name), false, false, false); 9367 checkTime(startTime, "getContentProviderImpl: after start process"); 9368 if (proc == null) { 9369 Slog.w(TAG, "Unable to launch app " 9370 + cpi.applicationInfo.packageName + "/" 9371 + cpi.applicationInfo.uid + " for provider " 9372 + name + ": process is bad"); 9373 return null; 9374 } 9375 } 9376 cpr.launchingApp = proc; 9377 mLaunchingProviders.add(cpr); 9378 } finally { 9379 Binder.restoreCallingIdentity(origId); 9380 } 9381 } 9382 9383 checkTime(startTime, "getContentProviderImpl: updating data structures"); 9384 9385 // Make sure the provider is published (the same provider class 9386 // may be published under multiple names). 9387 if (firstClass) { 9388 mProviderMap.putProviderByClass(comp, cpr); 9389 } 9390 9391 mProviderMap.putProviderByName(name, cpr); 9392 conn = incProviderCountLocked(r, cpr, token, stable); 9393 if (conn != null) { 9394 conn.waiting = true; 9395 } 9396 } 9397 checkTime(startTime, "getContentProviderImpl: done!"); 9398 } 9399 9400 // Wait for the provider to be published... 9401 synchronized (cpr) { 9402 while (cpr.provider == null) { 9403 if (cpr.launchingApp == null) { 9404 Slog.w(TAG, "Unable to launch app " 9405 + cpi.applicationInfo.packageName + "/" 9406 + cpi.applicationInfo.uid + " for provider " 9407 + name + ": launching app became null"); 9408 EventLog.writeEvent(EventLogTags.AM_PROVIDER_LOST_PROCESS, 9409 UserHandle.getUserId(cpi.applicationInfo.uid), 9410 cpi.applicationInfo.packageName, 9411 cpi.applicationInfo.uid, name); 9412 return null; 9413 } 9414 try { 9415 if (DEBUG_MU) { 9416 Slog.v(TAG_MU, "Waiting to start provider " + cpr + " launchingApp=" 9417 + cpr.launchingApp); 9418 } 9419 if (conn != null) { 9420 conn.waiting = true; 9421 } 9422 cpr.wait(); 9423 } catch (InterruptedException ex) { 9424 } finally { 9425 if (conn != null) { 9426 conn.waiting = false; 9427 } 9428 } 9429 } 9430 } 9431 return cpr != null ? cpr.newHolder(conn) : null; 9432 } 9433 9434 @Override 9435 public final ContentProviderHolder getContentProvider( 9436 IApplicationThread caller, String name, int userId, boolean stable) { 9437 enforceNotIsolatedCaller("getContentProvider"); 9438 if (caller == null) { 9439 String msg = "null IApplicationThread when getting content provider " 9440 + name; 9441 Slog.w(TAG, msg); 9442 throw new SecurityException(msg); 9443 } 9444 // The incoming user check is now handled in checkContentProviderPermissionLocked() to deal 9445 // with cross-user grant. 9446 return getContentProviderImpl(caller, name, null, stable, userId); 9447 } 9448 9449 public ContentProviderHolder getContentProviderExternal( 9450 String name, int userId, IBinder token) { 9451 enforceCallingPermission(android.Manifest.permission.ACCESS_CONTENT_PROVIDERS_EXTERNALLY, 9452 "Do not have permission in call getContentProviderExternal()"); 9453 userId = handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(), userId, 9454 false, ALLOW_FULL_ONLY, "getContentProvider", null); 9455 return getContentProviderExternalUnchecked(name, token, userId); 9456 } 9457 9458 private ContentProviderHolder getContentProviderExternalUnchecked(String name, 9459 IBinder token, int userId) { 9460 return getContentProviderImpl(null, name, token, true, userId); 9461 } 9462 9463 /** 9464 * Drop a content provider from a ProcessRecord's bookkeeping 9465 */ 9466 public void removeContentProvider(IBinder connection, boolean stable) { 9467 enforceNotIsolatedCaller("removeContentProvider"); 9468 long ident = Binder.clearCallingIdentity(); 9469 try { 9470 synchronized (this) { 9471 ContentProviderConnection conn; 9472 try { 9473 conn = (ContentProviderConnection)connection; 9474 } catch (ClassCastException e) { 9475 String msg ="removeContentProvider: " + connection 9476 + " not a ContentProviderConnection"; 9477 Slog.w(TAG, msg); 9478 throw new IllegalArgumentException(msg); 9479 } 9480 if (conn == null) { 9481 throw new NullPointerException("connection is null"); 9482 } 9483 if (decProviderCountLocked(conn, null, null, stable)) { 9484 updateOomAdjLocked(); 9485 } 9486 } 9487 } finally { 9488 Binder.restoreCallingIdentity(ident); 9489 } 9490 } 9491 9492 public void removeContentProviderExternal(String name, IBinder token) { 9493 enforceCallingPermission(android.Manifest.permission.ACCESS_CONTENT_PROVIDERS_EXTERNALLY, 9494 "Do not have permission in call removeContentProviderExternal()"); 9495 int userId = UserHandle.getCallingUserId(); 9496 long ident = Binder.clearCallingIdentity(); 9497 try { 9498 removeContentProviderExternalUnchecked(name, token, userId); 9499 } finally { 9500 Binder.restoreCallingIdentity(ident); 9501 } 9502 } 9503 9504 private void removeContentProviderExternalUnchecked(String name, IBinder token, int userId) { 9505 synchronized (this) { 9506 ContentProviderRecord cpr = mProviderMap.getProviderByName(name, userId); 9507 if(cpr == null) { 9508 //remove from mProvidersByClass 9509 if(localLOGV) Slog.v(TAG, name+" content provider not found in providers list"); 9510 return; 9511 } 9512 9513 //update content provider record entry info 9514 ComponentName comp = new ComponentName(cpr.info.packageName, cpr.info.name); 9515 ContentProviderRecord localCpr = mProviderMap.getProviderByClass(comp, userId); 9516 if (localCpr.hasExternalProcessHandles()) { 9517 if (localCpr.removeExternalProcessHandleLocked(token)) { 9518 updateOomAdjLocked(); 9519 } else { 9520 Slog.e(TAG, "Attmpt to remove content provider " + localCpr 9521 + " with no external reference for token: " 9522 + token + "."); 9523 } 9524 } else { 9525 Slog.e(TAG, "Attmpt to remove content provider: " + localCpr 9526 + " with no external references."); 9527 } 9528 } 9529 } 9530 9531 public final void publishContentProviders(IApplicationThread caller, 9532 List<ContentProviderHolder> providers) { 9533 if (providers == null) { 9534 return; 9535 } 9536 9537 enforceNotIsolatedCaller("publishContentProviders"); 9538 synchronized (this) { 9539 final ProcessRecord r = getRecordForAppLocked(caller); 9540 if (DEBUG_MU) 9541 Slog.v(TAG_MU, "ProcessRecord uid = " + r.uid); 9542 if (r == null) { 9543 throw new SecurityException( 9544 "Unable to find app for caller " + caller 9545 + " (pid=" + Binder.getCallingPid() 9546 + ") when publishing content providers"); 9547 } 9548 9549 final long origId = Binder.clearCallingIdentity(); 9550 9551 final int N = providers.size(); 9552 for (int i=0; i<N; i++) { 9553 ContentProviderHolder src = providers.get(i); 9554 if (src == null || src.info == null || src.provider == null) { 9555 continue; 9556 } 9557 ContentProviderRecord dst = r.pubProviders.get(src.info.name); 9558 if (DEBUG_MU) 9559 Slog.v(TAG_MU, "ContentProviderRecord uid = " + dst.uid); 9560 if (dst != null) { 9561 ComponentName comp = new ComponentName(dst.info.packageName, dst.info.name); 9562 mProviderMap.putProviderByClass(comp, dst); 9563 String names[] = dst.info.authority.split(";"); 9564 for (int j = 0; j < names.length; j++) { 9565 mProviderMap.putProviderByName(names[j], dst); 9566 } 9567 9568 int NL = mLaunchingProviders.size(); 9569 int j; 9570 for (j=0; j<NL; j++) { 9571 if (mLaunchingProviders.get(j) == dst) { 9572 mLaunchingProviders.remove(j); 9573 j--; 9574 NL--; 9575 } 9576 } 9577 synchronized (dst) { 9578 dst.provider = src.provider; 9579 dst.proc = r; 9580 dst.notifyAll(); 9581 } 9582 updateOomAdjLocked(r); 9583 } 9584 } 9585 9586 Binder.restoreCallingIdentity(origId); 9587 } 9588 } 9589 9590 public boolean refContentProvider(IBinder connection, int stable, int unstable) { 9591 ContentProviderConnection conn; 9592 try { 9593 conn = (ContentProviderConnection)connection; 9594 } catch (ClassCastException e) { 9595 String msg ="refContentProvider: " + connection 9596 + " not a ContentProviderConnection"; 9597 Slog.w(TAG, msg); 9598 throw new IllegalArgumentException(msg); 9599 } 9600 if (conn == null) { 9601 throw new NullPointerException("connection is null"); 9602 } 9603 9604 synchronized (this) { 9605 if (stable > 0) { 9606 conn.numStableIncs += stable; 9607 } 9608 stable = conn.stableCount + stable; 9609 if (stable < 0) { 9610 throw new IllegalStateException("stableCount < 0: " + stable); 9611 } 9612 9613 if (unstable > 0) { 9614 conn.numUnstableIncs += unstable; 9615 } 9616 unstable = conn.unstableCount + unstable; 9617 if (unstable < 0) { 9618 throw new IllegalStateException("unstableCount < 0: " + unstable); 9619 } 9620 9621 if ((stable+unstable) <= 0) { 9622 throw new IllegalStateException("ref counts can't go to zero here: stable=" 9623 + stable + " unstable=" + unstable); 9624 } 9625 conn.stableCount = stable; 9626 conn.unstableCount = unstable; 9627 return !conn.dead; 9628 } 9629 } 9630 9631 public void unstableProviderDied(IBinder connection) { 9632 ContentProviderConnection conn; 9633 try { 9634 conn = (ContentProviderConnection)connection; 9635 } catch (ClassCastException e) { 9636 String msg ="refContentProvider: " + connection 9637 + " not a ContentProviderConnection"; 9638 Slog.w(TAG, msg); 9639 throw new IllegalArgumentException(msg); 9640 } 9641 if (conn == null) { 9642 throw new NullPointerException("connection is null"); 9643 } 9644 9645 // Safely retrieve the content provider associated with the connection. 9646 IContentProvider provider; 9647 synchronized (this) { 9648 provider = conn.provider.provider; 9649 } 9650 9651 if (provider == null) { 9652 // Um, yeah, we're way ahead of you. 9653 return; 9654 } 9655 9656 // Make sure the caller is being honest with us. 9657 if (provider.asBinder().pingBinder()) { 9658 // Er, no, still looks good to us. 9659 synchronized (this) { 9660 Slog.w(TAG, "unstableProviderDied: caller " + Binder.getCallingUid() 9661 + " says " + conn + " died, but we don't agree"); 9662 return; 9663 } 9664 } 9665 9666 // Well look at that! It's dead! 9667 synchronized (this) { 9668 if (conn.provider.provider != provider) { 9669 // But something changed... good enough. 9670 return; 9671 } 9672 9673 ProcessRecord proc = conn.provider.proc; 9674 if (proc == null || proc.thread == null) { 9675 // Seems like the process is already cleaned up. 9676 return; 9677 } 9678 9679 // As far as we're concerned, this is just like receiving a 9680 // death notification... just a bit prematurely. 9681 Slog.i(TAG, "Process " + proc.processName + " (pid " + proc.pid 9682 + ") early provider death"); 9683 final long ident = Binder.clearCallingIdentity(); 9684 try { 9685 appDiedLocked(proc); 9686 } finally { 9687 Binder.restoreCallingIdentity(ident); 9688 } 9689 } 9690 } 9691 9692 @Override 9693 public void appNotRespondingViaProvider(IBinder connection) { 9694 enforceCallingPermission( 9695 android.Manifest.permission.REMOVE_TASKS, "appNotRespondingViaProvider()"); 9696 9697 final ContentProviderConnection conn = (ContentProviderConnection) connection; 9698 if (conn == null) { 9699 Slog.w(TAG, "ContentProviderConnection is null"); 9700 return; 9701 } 9702 9703 final ProcessRecord host = conn.provider.proc; 9704 if (host == null) { 9705 Slog.w(TAG, "Failed to find hosting ProcessRecord"); 9706 return; 9707 } 9708 9709 final long token = Binder.clearCallingIdentity(); 9710 try { 9711 appNotResponding(host, null, null, false, "ContentProvider not responding"); 9712 } finally { 9713 Binder.restoreCallingIdentity(token); 9714 } 9715 } 9716 9717 public final void installSystemProviders() { 9718 List<ProviderInfo> providers; 9719 synchronized (this) { 9720 ProcessRecord app = mProcessNames.get("system", Process.SYSTEM_UID); 9721 providers = generateApplicationProvidersLocked(app); 9722 if (providers != null) { 9723 for (int i=providers.size()-1; i>=0; i--) { 9724 ProviderInfo pi = (ProviderInfo)providers.get(i); 9725 if ((pi.applicationInfo.flags&ApplicationInfo.FLAG_SYSTEM) == 0) { 9726 Slog.w(TAG, "Not installing system proc provider " + pi.name 9727 + ": not system .apk"); 9728 providers.remove(i); 9729 } 9730 } 9731 } 9732 } 9733 if (providers != null) { 9734 mSystemThread.installSystemProviders(providers); 9735 } 9736 9737 mCoreSettingsObserver = new CoreSettingsObserver(this); 9738 9739 //mUsageStatsService.monitorPackages(); 9740 } 9741 9742 /** 9743 * Allows apps to retrieve the MIME type of a URI. 9744 * If an app is in the same user as the ContentProvider, or if it is allowed to interact across 9745 * users, then it does not need permission to access the ContentProvider. 9746 * Either, it needs cross-user uri grants. 9747 * 9748 * CTS tests for this functionality can be run with "runtest cts-appsecurity". 9749 * 9750 * Test cases are at cts/tests/appsecurity-tests/test-apps/UsePermissionDiffCert/ 9751 * src/com/android/cts/usespermissiondiffcertapp/AccessPermissionWithDiffSigTest.java 9752 */ 9753 public String getProviderMimeType(Uri uri, int userId) { 9754 enforceNotIsolatedCaller("getProviderMimeType"); 9755 final String name = uri.getAuthority(); 9756 int callingUid = Binder.getCallingUid(); 9757 int callingPid = Binder.getCallingPid(); 9758 long ident = 0; 9759 boolean clearedIdentity = false; 9760 userId = unsafeConvertIncomingUser(userId); 9761 if (canClearIdentity(callingPid, callingUid, userId)) { 9762 clearedIdentity = true; 9763 ident = Binder.clearCallingIdentity(); 9764 } 9765 ContentProviderHolder holder = null; 9766 try { 9767 holder = getContentProviderExternalUnchecked(name, null, userId); 9768 if (holder != null) { 9769 return holder.provider.getType(uri); 9770 } 9771 } catch (RemoteException e) { 9772 Log.w(TAG, "Content provider dead retrieving " + uri, e); 9773 return null; 9774 } finally { 9775 // We need to clear the identity to call removeContentProviderExternalUnchecked 9776 if (!clearedIdentity) { 9777 ident = Binder.clearCallingIdentity(); 9778 } 9779 try { 9780 if (holder != null) { 9781 removeContentProviderExternalUnchecked(name, null, userId); 9782 } 9783 } finally { 9784 Binder.restoreCallingIdentity(ident); 9785 } 9786 } 9787 9788 return null; 9789 } 9790 9791 private boolean canClearIdentity(int callingPid, int callingUid, int userId) { 9792 if (UserHandle.getUserId(callingUid) == userId) { 9793 return true; 9794 } 9795 if (checkComponentPermission(INTERACT_ACROSS_USERS, callingPid, 9796 callingUid, -1, true) == PackageManager.PERMISSION_GRANTED 9797 || checkComponentPermission(INTERACT_ACROSS_USERS_FULL, callingPid, 9798 callingUid, -1, true) == PackageManager.PERMISSION_GRANTED) { 9799 return true; 9800 } 9801 return false; 9802 } 9803 9804 // ========================================================= 9805 // GLOBAL MANAGEMENT 9806 // ========================================================= 9807 9808 final ProcessRecord newProcessRecordLocked(ApplicationInfo info, String customProcess, 9809 boolean isolated, int isolatedUid) { 9810 String proc = customProcess != null ? customProcess : info.processName; 9811 BatteryStatsImpl.Uid.Proc ps = null; 9812 BatteryStatsImpl stats = mBatteryStatsService.getActiveStatistics(); 9813 int uid = info.uid; 9814 if (isolated) { 9815 if (isolatedUid == 0) { 9816 int userId = UserHandle.getUserId(uid); 9817 int stepsLeft = Process.LAST_ISOLATED_UID - Process.FIRST_ISOLATED_UID + 1; 9818 while (true) { 9819 if (mNextIsolatedProcessUid < Process.FIRST_ISOLATED_UID 9820 || mNextIsolatedProcessUid > Process.LAST_ISOLATED_UID) { 9821 mNextIsolatedProcessUid = Process.FIRST_ISOLATED_UID; 9822 } 9823 uid = UserHandle.getUid(userId, mNextIsolatedProcessUid); 9824 mNextIsolatedProcessUid++; 9825 if (mIsolatedProcesses.indexOfKey(uid) < 0) { 9826 // No process for this uid, use it. 9827 break; 9828 } 9829 stepsLeft--; 9830 if (stepsLeft <= 0) { 9831 return null; 9832 } 9833 } 9834 } else { 9835 // Special case for startIsolatedProcess (internal only), where 9836 // the uid of the isolated process is specified by the caller. 9837 uid = isolatedUid; 9838 } 9839 } 9840 return new ProcessRecord(stats, info, proc, uid); 9841 } 9842 9843 final ProcessRecord addAppLocked(ApplicationInfo info, boolean isolated, 9844 String abiOverride) { 9845 ProcessRecord app; 9846 if (!isolated) { 9847 app = getProcessRecordLocked(info.processName, info.uid, true); 9848 } else { 9849 app = null; 9850 } 9851 9852 if (app == null) { 9853 app = newProcessRecordLocked(info, null, isolated, 0); 9854 mProcessNames.put(info.processName, app.uid, app); 9855 if (isolated) { 9856 mIsolatedProcesses.put(app.uid, app); 9857 } 9858 updateLruProcessLocked(app, false, null); 9859 updateOomAdjLocked(); 9860 } 9861 9862 // This package really, really can not be stopped. 9863 try { 9864 AppGlobals.getPackageManager().setPackageStoppedState( 9865 info.packageName, false, UserHandle.getUserId(app.uid)); 9866 } catch (RemoteException e) { 9867 } catch (IllegalArgumentException e) { 9868 Slog.w(TAG, "Failed trying to unstop package " 9869 + info.packageName + ": " + e); 9870 } 9871 9872 if ((info.flags&(ApplicationInfo.FLAG_SYSTEM|ApplicationInfo.FLAG_PERSISTENT)) 9873 == (ApplicationInfo.FLAG_SYSTEM|ApplicationInfo.FLAG_PERSISTENT)) { 9874 app.persistent = true; 9875 app.maxAdj = ProcessList.PERSISTENT_PROC_ADJ; 9876 } 9877 if (app.thread == null && mPersistentStartingProcesses.indexOf(app) < 0) { 9878 mPersistentStartingProcesses.add(app); 9879 startProcessLocked(app, "added application", app.processName, abiOverride, 9880 null /* entryPoint */, null /* entryPointArgs */); 9881 } 9882 9883 return app; 9884 } 9885 9886 public void unhandledBack() { 9887 enforceCallingPermission(android.Manifest.permission.FORCE_BACK, 9888 "unhandledBack()"); 9889 9890 synchronized(this) { 9891 final long origId = Binder.clearCallingIdentity(); 9892 try { 9893 getFocusedStack().unhandledBackLocked(); 9894 } finally { 9895 Binder.restoreCallingIdentity(origId); 9896 } 9897 } 9898 } 9899 9900 public ParcelFileDescriptor openContentUri(Uri uri) throws RemoteException { 9901 enforceNotIsolatedCaller("openContentUri"); 9902 final int userId = UserHandle.getCallingUserId(); 9903 String name = uri.getAuthority(); 9904 ContentProviderHolder cph = getContentProviderExternalUnchecked(name, null, userId); 9905 ParcelFileDescriptor pfd = null; 9906 if (cph != null) { 9907 // We record the binder invoker's uid in thread-local storage before 9908 // going to the content provider to open the file. Later, in the code 9909 // that handles all permissions checks, we look for this uid and use 9910 // that rather than the Activity Manager's own uid. The effect is that 9911 // we do the check against the caller's permissions even though it looks 9912 // to the content provider like the Activity Manager itself is making 9913 // the request. 9914 sCallerIdentity.set(new Identity( 9915 Binder.getCallingPid(), Binder.getCallingUid())); 9916 try { 9917 pfd = cph.provider.openFile(null, uri, "r", null); 9918 } catch (FileNotFoundException e) { 9919 // do nothing; pfd will be returned null 9920 } finally { 9921 // Ensure that whatever happens, we clean up the identity state 9922 sCallerIdentity.remove(); 9923 } 9924 9925 // We've got the fd now, so we're done with the provider. 9926 removeContentProviderExternalUnchecked(name, null, userId); 9927 } else { 9928 Slog.d(TAG, "Failed to get provider for authority '" + name + "'"); 9929 } 9930 return pfd; 9931 } 9932 9933 // Actually is sleeping or shutting down or whatever else in the future 9934 // is an inactive state. 9935 public boolean isSleepingOrShuttingDown() { 9936 return isSleeping() || mShuttingDown; 9937 } 9938 9939 public boolean isSleeping() { 9940 return mSleeping; 9941 } 9942 9943 void goingToSleep() { 9944 synchronized(this) { 9945 mWentToSleep = true; 9946 goToSleepIfNeededLocked(); 9947 } 9948 } 9949 9950 void finishRunningVoiceLocked() { 9951 if (mRunningVoice) { 9952 mRunningVoice = false; 9953 goToSleepIfNeededLocked(); 9954 } 9955 } 9956 9957 void goToSleepIfNeededLocked() { 9958 if (mWentToSleep && !mRunningVoice) { 9959 if (!mSleeping) { 9960 mSleeping = true; 9961 mStackSupervisor.goingToSleepLocked(); 9962 9963 // Initialize the wake times of all processes. 9964 checkExcessivePowerUsageLocked(false); 9965 mHandler.removeMessages(CHECK_EXCESSIVE_WAKE_LOCKS_MSG); 9966 Message nmsg = mHandler.obtainMessage(CHECK_EXCESSIVE_WAKE_LOCKS_MSG); 9967 mHandler.sendMessageDelayed(nmsg, POWER_CHECK_DELAY); 9968 } 9969 } 9970 } 9971 9972 void notifyTaskPersisterLocked(TaskRecord task, boolean flush) { 9973 if (task != null && task.stack != null && task.stack.isHomeStack()) { 9974 // Never persist the home stack. 9975 return; 9976 } 9977 mTaskPersister.wakeup(task, flush); 9978 } 9979 9980 @Override 9981 public boolean shutdown(int timeout) { 9982 if (checkCallingPermission(android.Manifest.permission.SHUTDOWN) 9983 != PackageManager.PERMISSION_GRANTED) { 9984 throw new SecurityException("Requires permission " 9985 + android.Manifest.permission.SHUTDOWN); 9986 } 9987 9988 boolean timedout = false; 9989 9990 synchronized(this) { 9991 mShuttingDown = true; 9992 updateEventDispatchingLocked(); 9993 timedout = mStackSupervisor.shutdownLocked(timeout); 9994 } 9995 9996 mAppOpsService.shutdown(); 9997 if (mUsageStatsService != null) { 9998 mUsageStatsService.prepareShutdown(); 9999 } 10000 mBatteryStatsService.shutdown(); 10001 synchronized (this) { 10002 mProcessStats.shutdownLocked(); 10003 } 10004 notifyTaskPersisterLocked(null, true); 10005 10006 return timedout; 10007 } 10008 10009 public final void activitySlept(IBinder token) { 10010 if (localLOGV) Slog.v(TAG, "Activity slept: token=" + token); 10011 10012 final long origId = Binder.clearCallingIdentity(); 10013 10014 synchronized (this) { 10015 final ActivityRecord r = ActivityRecord.isInStackLocked(token); 10016 if (r != null) { 10017 mStackSupervisor.activitySleptLocked(r); 10018 } 10019 } 10020 10021 Binder.restoreCallingIdentity(origId); 10022 } 10023 10024 private String lockScreenShownToString() { 10025 switch (mLockScreenShown) { 10026 case LOCK_SCREEN_HIDDEN: return "LOCK_SCREEN_HIDDEN"; 10027 case LOCK_SCREEN_LEAVING: return "LOCK_SCREEN_LEAVING"; 10028 case LOCK_SCREEN_SHOWN: return "LOCK_SCREEN_SHOWN"; 10029 default: return "Unknown=" + mLockScreenShown; 10030 } 10031 } 10032 10033 void logLockScreen(String msg) { 10034 if (DEBUG_LOCKSCREEN) Slog.d(TAG, Debug.getCallers(2) + ":" + msg + 10035 " mLockScreenShown=" + lockScreenShownToString() + " mWentToSleep=" + 10036 mWentToSleep + " mSleeping=" + mSleeping); 10037 } 10038 10039 void comeOutOfSleepIfNeededLocked() { 10040 if ((!mWentToSleep && mLockScreenShown == LOCK_SCREEN_HIDDEN) || mRunningVoice) { 10041 if (mSleeping) { 10042 mSleeping = false; 10043 mStackSupervisor.comeOutOfSleepIfNeededLocked(); 10044 } 10045 } 10046 } 10047 10048 void wakingUp() { 10049 synchronized(this) { 10050 mWentToSleep = false; 10051 comeOutOfSleepIfNeededLocked(); 10052 } 10053 } 10054 10055 void startRunningVoiceLocked() { 10056 if (!mRunningVoice) { 10057 mRunningVoice = true; 10058 comeOutOfSleepIfNeededLocked(); 10059 } 10060 } 10061 10062 private void updateEventDispatchingLocked() { 10063 mWindowManager.setEventDispatching(mBooted && !mShuttingDown); 10064 } 10065 10066 public void setLockScreenShown(boolean shown) { 10067 if (checkCallingPermission(android.Manifest.permission.DEVICE_POWER) 10068 != PackageManager.PERMISSION_GRANTED) { 10069 throw new SecurityException("Requires permission " 10070 + android.Manifest.permission.DEVICE_POWER); 10071 } 10072 10073 synchronized(this) { 10074 long ident = Binder.clearCallingIdentity(); 10075 try { 10076 if (DEBUG_LOCKSCREEN) logLockScreen(" shown=" + shown); 10077 mLockScreenShown = shown ? LOCK_SCREEN_SHOWN : LOCK_SCREEN_HIDDEN; 10078 comeOutOfSleepIfNeededLocked(); 10079 } finally { 10080 Binder.restoreCallingIdentity(ident); 10081 } 10082 } 10083 } 10084 10085 @Override 10086 public void stopAppSwitches() { 10087 if (checkCallingPermission(android.Manifest.permission.STOP_APP_SWITCHES) 10088 != PackageManager.PERMISSION_GRANTED) { 10089 throw new SecurityException("Requires permission " 10090 + android.Manifest.permission.STOP_APP_SWITCHES); 10091 } 10092 10093 synchronized(this) { 10094 mAppSwitchesAllowedTime = SystemClock.uptimeMillis() 10095 + APP_SWITCH_DELAY_TIME; 10096 mDidAppSwitch = false; 10097 mHandler.removeMessages(DO_PENDING_ACTIVITY_LAUNCHES_MSG); 10098 Message msg = mHandler.obtainMessage(DO_PENDING_ACTIVITY_LAUNCHES_MSG); 10099 mHandler.sendMessageDelayed(msg, APP_SWITCH_DELAY_TIME); 10100 } 10101 } 10102 10103 public void resumeAppSwitches() { 10104 if (checkCallingPermission(android.Manifest.permission.STOP_APP_SWITCHES) 10105 != PackageManager.PERMISSION_GRANTED) { 10106 throw new SecurityException("Requires permission " 10107 + android.Manifest.permission.STOP_APP_SWITCHES); 10108 } 10109 10110 synchronized(this) { 10111 // Note that we don't execute any pending app switches... we will 10112 // let those wait until either the timeout, or the next start 10113 // activity request. 10114 mAppSwitchesAllowedTime = 0; 10115 } 10116 } 10117 10118 boolean checkAppSwitchAllowedLocked(int sourcePid, int sourceUid, 10119 int callingPid, int callingUid, String name) { 10120 if (mAppSwitchesAllowedTime < SystemClock.uptimeMillis()) { 10121 return true; 10122 } 10123 10124 int perm = checkComponentPermission( 10125 android.Manifest.permission.STOP_APP_SWITCHES, sourcePid, 10126 sourceUid, -1, true); 10127 if (perm == PackageManager.PERMISSION_GRANTED) { 10128 return true; 10129 } 10130 10131 // If the actual IPC caller is different from the logical source, then 10132 // also see if they are allowed to control app switches. 10133 if (callingUid != -1 && callingUid != sourceUid) { 10134 perm = checkComponentPermission( 10135 android.Manifest.permission.STOP_APP_SWITCHES, callingPid, 10136 callingUid, -1, true); 10137 if (perm == PackageManager.PERMISSION_GRANTED) { 10138 return true; 10139 } 10140 } 10141 10142 Slog.w(TAG, name + " request from " + sourceUid + " stopped"); 10143 return false; 10144 } 10145 10146 public void setDebugApp(String packageName, boolean waitForDebugger, 10147 boolean persistent) { 10148 enforceCallingPermission(android.Manifest.permission.SET_DEBUG_APP, 10149 "setDebugApp()"); 10150 10151 long ident = Binder.clearCallingIdentity(); 10152 try { 10153 // Note that this is not really thread safe if there are multiple 10154 // callers into it at the same time, but that's not a situation we 10155 // care about. 10156 if (persistent) { 10157 final ContentResolver resolver = mContext.getContentResolver(); 10158 Settings.Global.putString( 10159 resolver, Settings.Global.DEBUG_APP, 10160 packageName); 10161 Settings.Global.putInt( 10162 resolver, Settings.Global.WAIT_FOR_DEBUGGER, 10163 waitForDebugger ? 1 : 0); 10164 } 10165 10166 synchronized (this) { 10167 if (!persistent) { 10168 mOrigDebugApp = mDebugApp; 10169 mOrigWaitForDebugger = mWaitForDebugger; 10170 } 10171 mDebugApp = packageName; 10172 mWaitForDebugger = waitForDebugger; 10173 mDebugTransient = !persistent; 10174 if (packageName != null) { 10175 forceStopPackageLocked(packageName, -1, false, false, true, true, 10176 false, UserHandle.USER_ALL, "set debug app"); 10177 } 10178 } 10179 } finally { 10180 Binder.restoreCallingIdentity(ident); 10181 } 10182 } 10183 10184 void setOpenGlTraceApp(ApplicationInfo app, String processName) { 10185 synchronized (this) { 10186 boolean isDebuggable = "1".equals(SystemProperties.get(SYSTEM_DEBUGGABLE, "0")); 10187 if (!isDebuggable) { 10188 if ((app.flags&ApplicationInfo.FLAG_DEBUGGABLE) == 0) { 10189 throw new SecurityException("Process not debuggable: " + app.packageName); 10190 } 10191 } 10192 10193 mOpenGlTraceApp = processName; 10194 } 10195 } 10196 10197 void setProfileApp(ApplicationInfo app, String processName, ProfilerInfo profilerInfo) { 10198 synchronized (this) { 10199 boolean isDebuggable = "1".equals(SystemProperties.get(SYSTEM_DEBUGGABLE, "0")); 10200 if (!isDebuggable) { 10201 if ((app.flags&ApplicationInfo.FLAG_DEBUGGABLE) == 0) { 10202 throw new SecurityException("Process not debuggable: " + app.packageName); 10203 } 10204 } 10205 mProfileApp = processName; 10206 mProfileFile = profilerInfo.profileFile; 10207 if (mProfileFd != null) { 10208 try { 10209 mProfileFd.close(); 10210 } catch (IOException e) { 10211 } 10212 mProfileFd = null; 10213 } 10214 mProfileFd = profilerInfo.profileFd; 10215 mSamplingInterval = profilerInfo.samplingInterval; 10216 mAutoStopProfiler = profilerInfo.autoStopProfiler; 10217 mProfileType = 0; 10218 } 10219 } 10220 10221 @Override 10222 public void setAlwaysFinish(boolean enabled) { 10223 enforceCallingPermission(android.Manifest.permission.SET_ALWAYS_FINISH, 10224 "setAlwaysFinish()"); 10225 10226 Settings.Global.putInt( 10227 mContext.getContentResolver(), 10228 Settings.Global.ALWAYS_FINISH_ACTIVITIES, enabled ? 1 : 0); 10229 10230 synchronized (this) { 10231 mAlwaysFinishActivities = enabled; 10232 } 10233 } 10234 10235 @Override 10236 public void setActivityController(IActivityController controller) { 10237 enforceCallingPermission(android.Manifest.permission.SET_ACTIVITY_WATCHER, 10238 "setActivityController()"); 10239 synchronized (this) { 10240 mController = controller; 10241 Watchdog.getInstance().setActivityController(controller); 10242 } 10243 } 10244 10245 @Override 10246 public void setUserIsMonkey(boolean userIsMonkey) { 10247 synchronized (this) { 10248 synchronized (mPidsSelfLocked) { 10249 final int callingPid = Binder.getCallingPid(); 10250 ProcessRecord precessRecord = mPidsSelfLocked.get(callingPid); 10251 if (precessRecord == null) { 10252 throw new SecurityException("Unknown process: " + callingPid); 10253 } 10254 if (precessRecord.instrumentationUiAutomationConnection == null) { 10255 throw new SecurityException("Only an instrumentation process " 10256 + "with a UiAutomation can call setUserIsMonkey"); 10257 } 10258 } 10259 mUserIsMonkey = userIsMonkey; 10260 } 10261 } 10262 10263 @Override 10264 public boolean isUserAMonkey() { 10265 synchronized (this) { 10266 // If there is a controller also implies the user is a monkey. 10267 return (mUserIsMonkey || mController != null); 10268 } 10269 } 10270 10271 public void requestBugReport() { 10272 enforceCallingPermission(android.Manifest.permission.DUMP, "requestBugReport"); 10273 SystemProperties.set("ctl.start", "bugreport"); 10274 } 10275 10276 public static long getInputDispatchingTimeoutLocked(ActivityRecord r) { 10277 return r != null ? getInputDispatchingTimeoutLocked(r.app) : KEY_DISPATCHING_TIMEOUT; 10278 } 10279 10280 public static long getInputDispatchingTimeoutLocked(ProcessRecord r) { 10281 if (r != null && (r.instrumentationClass != null || r.usingWrapper)) { 10282 return INSTRUMENTATION_KEY_DISPATCHING_TIMEOUT; 10283 } 10284 return KEY_DISPATCHING_TIMEOUT; 10285 } 10286 10287 @Override 10288 public long inputDispatchingTimedOut(int pid, final boolean aboveSystem, String reason) { 10289 if (checkCallingPermission(android.Manifest.permission.FILTER_EVENTS) 10290 != PackageManager.PERMISSION_GRANTED) { 10291 throw new SecurityException("Requires permission " 10292 + android.Manifest.permission.FILTER_EVENTS); 10293 } 10294 ProcessRecord proc; 10295 long timeout; 10296 synchronized (this) { 10297 synchronized (mPidsSelfLocked) { 10298 proc = mPidsSelfLocked.get(pid); 10299 } 10300 timeout = getInputDispatchingTimeoutLocked(proc); 10301 } 10302 10303 if (!inputDispatchingTimedOut(proc, null, null, aboveSystem, reason)) { 10304 return -1; 10305 } 10306 10307 return timeout; 10308 } 10309 10310 /** 10311 * Handle input dispatching timeouts. 10312 * Returns whether input dispatching should be aborted or not. 10313 */ 10314 public boolean inputDispatchingTimedOut(final ProcessRecord proc, 10315 final ActivityRecord activity, final ActivityRecord parent, 10316 final boolean aboveSystem, String reason) { 10317 if (checkCallingPermission(android.Manifest.permission.FILTER_EVENTS) 10318 != PackageManager.PERMISSION_GRANTED) { 10319 throw new SecurityException("Requires permission " 10320 + android.Manifest.permission.FILTER_EVENTS); 10321 } 10322 10323 final String annotation; 10324 if (reason == null) { 10325 annotation = "Input dispatching timed out"; 10326 } else { 10327 annotation = "Input dispatching timed out (" + reason + ")"; 10328 } 10329 10330 if (proc != null) { 10331 synchronized (this) { 10332 if (proc.debugging) { 10333 return false; 10334 } 10335 10336 if (mDidDexOpt) { 10337 // Give more time since we were dexopting. 10338 mDidDexOpt = false; 10339 return false; 10340 } 10341 10342 if (proc.instrumentationClass != null) { 10343 Bundle info = new Bundle(); 10344 info.putString("shortMsg", "keyDispatchingTimedOut"); 10345 info.putString("longMsg", annotation); 10346 finishInstrumentationLocked(proc, Activity.RESULT_CANCELED, info); 10347 return true; 10348 } 10349 } 10350 mHandler.post(new Runnable() { 10351 @Override 10352 public void run() { 10353 appNotResponding(proc, activity, parent, aboveSystem, annotation); 10354 } 10355 }); 10356 } 10357 10358 return true; 10359 } 10360 10361 public Bundle getAssistContextExtras(int requestType) { 10362 PendingAssistExtras pae = enqueueAssistContext(requestType, null, null, 10363 UserHandle.getCallingUserId()); 10364 if (pae == null) { 10365 return null; 10366 } 10367 synchronized (pae) { 10368 while (!pae.haveResult) { 10369 try { 10370 pae.wait(); 10371 } catch (InterruptedException e) { 10372 } 10373 } 10374 if (pae.result != null) { 10375 pae.extras.putBundle(Intent.EXTRA_ASSIST_CONTEXT, pae.result); 10376 } 10377 } 10378 synchronized (this) { 10379 mPendingAssistExtras.remove(pae); 10380 mHandler.removeCallbacks(pae); 10381 } 10382 return pae.extras; 10383 } 10384 10385 private PendingAssistExtras enqueueAssistContext(int requestType, Intent intent, String hint, 10386 int userHandle) { 10387 enforceCallingPermission(android.Manifest.permission.GET_TOP_ACTIVITY_INFO, 10388 "getAssistContextExtras()"); 10389 PendingAssistExtras pae; 10390 Bundle extras = new Bundle(); 10391 synchronized (this) { 10392 ActivityRecord activity = getFocusedStack().mResumedActivity; 10393 if (activity == null) { 10394 Slog.w(TAG, "getAssistContextExtras failed: no resumed activity"); 10395 return null; 10396 } 10397 extras.putString(Intent.EXTRA_ASSIST_PACKAGE, activity.packageName); 10398 if (activity.app == null || activity.app.thread == null) { 10399 Slog.w(TAG, "getAssistContextExtras failed: no process for " + activity); 10400 return null; 10401 } 10402 if (activity.app.pid == Binder.getCallingPid()) { 10403 Slog.w(TAG, "getAssistContextExtras failed: request process same as " + activity); 10404 return null; 10405 } 10406 pae = new PendingAssistExtras(activity, extras, intent, hint, userHandle); 10407 try { 10408 activity.app.thread.requestAssistContextExtras(activity.appToken, pae, 10409 requestType); 10410 mPendingAssistExtras.add(pae); 10411 mHandler.postDelayed(pae, PENDING_ASSIST_EXTRAS_TIMEOUT); 10412 } catch (RemoteException e) { 10413 Slog.w(TAG, "getAssistContextExtras failed: crash calling " + activity); 10414 return null; 10415 } 10416 return pae; 10417 } 10418 } 10419 10420 public void reportAssistContextExtras(IBinder token, Bundle extras) { 10421 PendingAssistExtras pae = (PendingAssistExtras)token; 10422 synchronized (pae) { 10423 pae.result = extras; 10424 pae.haveResult = true; 10425 pae.notifyAll(); 10426 if (pae.intent == null) { 10427 // Caller is just waiting for the result. 10428 return; 10429 } 10430 } 10431 10432 // We are now ready to launch the assist activity. 10433 synchronized (this) { 10434 boolean exists = mPendingAssistExtras.remove(pae); 10435 mHandler.removeCallbacks(pae); 10436 if (!exists) { 10437 // Timed out. 10438 return; 10439 } 10440 } 10441 pae.intent.replaceExtras(extras); 10442 if (pae.hint != null) { 10443 pae.intent.putExtra(pae.hint, true); 10444 } 10445 pae.intent.setFlags(Intent.FLAG_ACTIVITY_NEW_TASK 10446 | Intent.FLAG_ACTIVITY_SINGLE_TOP 10447 | Intent.FLAG_ACTIVITY_CLEAR_TOP); 10448 closeSystemDialogs("assist"); 10449 try { 10450 mContext.startActivityAsUser(pae.intent, new UserHandle(pae.userHandle)); 10451 } catch (ActivityNotFoundException e) { 10452 Slog.w(TAG, "No activity to handle assist action.", e); 10453 } 10454 } 10455 10456 public boolean launchAssistIntent(Intent intent, int requestType, String hint, int userHandle) { 10457 return enqueueAssistContext(requestType, intent, hint, userHandle) != null; 10458 } 10459 10460 public void registerProcessObserver(IProcessObserver observer) { 10461 enforceCallingPermission(android.Manifest.permission.SET_ACTIVITY_WATCHER, 10462 "registerProcessObserver()"); 10463 synchronized (this) { 10464 mProcessObservers.register(observer); 10465 } 10466 } 10467 10468 @Override 10469 public void unregisterProcessObserver(IProcessObserver observer) { 10470 synchronized (this) { 10471 mProcessObservers.unregister(observer); 10472 } 10473 } 10474 10475 @Override 10476 public boolean convertFromTranslucent(IBinder token) { 10477 final long origId = Binder.clearCallingIdentity(); 10478 try { 10479 synchronized (this) { 10480 final ActivityRecord r = ActivityRecord.isInStackLocked(token); 10481 if (r == null) { 10482 return false; 10483 } 10484 final boolean translucentChanged = r.changeWindowTranslucency(true); 10485 if (translucentChanged) { 10486 r.task.stack.releaseBackgroundResources(); 10487 mStackSupervisor.ensureActivitiesVisibleLocked(null, 0); 10488 } 10489 mWindowManager.setAppFullscreen(token, true); 10490 return translucentChanged; 10491 } 10492 } finally { 10493 Binder.restoreCallingIdentity(origId); 10494 } 10495 } 10496 10497 @Override 10498 public boolean convertToTranslucent(IBinder token, ActivityOptions options) { 10499 final long origId = Binder.clearCallingIdentity(); 10500 try { 10501 synchronized (this) { 10502 final ActivityRecord r = ActivityRecord.isInStackLocked(token); 10503 if (r == null) { 10504 return false; 10505 } 10506 int index = r.task.mActivities.lastIndexOf(r); 10507 if (index > 0) { 10508 ActivityRecord under = r.task.mActivities.get(index - 1); 10509 under.returningOptions = options; 10510 } 10511 final boolean translucentChanged = r.changeWindowTranslucency(false); 10512 if (translucentChanged) { 10513 r.task.stack.convertToTranslucent(r); 10514 } 10515 mStackSupervisor.ensureActivitiesVisibleLocked(null, 0); 10516 mWindowManager.setAppFullscreen(token, false); 10517 return translucentChanged; 10518 } 10519 } finally { 10520 Binder.restoreCallingIdentity(origId); 10521 } 10522 } 10523 10524 @Override 10525 public boolean requestVisibleBehind(IBinder token, boolean visible) { 10526 final long origId = Binder.clearCallingIdentity(); 10527 try { 10528 synchronized (this) { 10529 final ActivityRecord r = ActivityRecord.isInStackLocked(token); 10530 if (r != null) { 10531 return mStackSupervisor.requestVisibleBehindLocked(r, visible); 10532 } 10533 } 10534 return false; 10535 } finally { 10536 Binder.restoreCallingIdentity(origId); 10537 } 10538 } 10539 10540 @Override 10541 public boolean isBackgroundVisibleBehind(IBinder token) { 10542 final long origId = Binder.clearCallingIdentity(); 10543 try { 10544 synchronized (this) { 10545 final ActivityStack stack = ActivityRecord.getStackLocked(token); 10546 final boolean visible = stack == null ? false : stack.hasVisibleBehindActivity(); 10547 if (ActivityStackSupervisor.DEBUG_VISIBLE_BEHIND) Slog.d(TAG, 10548 "isBackgroundVisibleBehind: stack=" + stack + " visible=" + visible); 10549 return visible; 10550 } 10551 } finally { 10552 Binder.restoreCallingIdentity(origId); 10553 } 10554 } 10555 10556 @Override 10557 public ActivityOptions getActivityOptions(IBinder token) { 10558 final long origId = Binder.clearCallingIdentity(); 10559 try { 10560 synchronized (this) { 10561 final ActivityRecord r = ActivityRecord.isInStackLocked(token); 10562 if (r != null) { 10563 final ActivityOptions activityOptions = r.pendingOptions; 10564 r.pendingOptions = null; 10565 return activityOptions; 10566 } 10567 return null; 10568 } 10569 } finally { 10570 Binder.restoreCallingIdentity(origId); 10571 } 10572 } 10573 10574 @Override 10575 public void setImmersive(IBinder token, boolean immersive) { 10576 synchronized(this) { 10577 final ActivityRecord r = ActivityRecord.isInStackLocked(token); 10578 if (r == null) { 10579 throw new IllegalArgumentException(); 10580 } 10581 r.immersive = immersive; 10582 10583 // update associated state if we're frontmost 10584 if (r == mFocusedActivity) { 10585 if (DEBUG_IMMERSIVE) { 10586 Slog.d(TAG, "Frontmost changed immersion: "+ r); 10587 } 10588 applyUpdateLockStateLocked(r); 10589 } 10590 } 10591 } 10592 10593 @Override 10594 public boolean isImmersive(IBinder token) { 10595 synchronized (this) { 10596 ActivityRecord r = ActivityRecord.isInStackLocked(token); 10597 if (r == null) { 10598 throw new IllegalArgumentException(); 10599 } 10600 return r.immersive; 10601 } 10602 } 10603 10604 public boolean isTopActivityImmersive() { 10605 enforceNotIsolatedCaller("startActivity"); 10606 synchronized (this) { 10607 ActivityRecord r = getFocusedStack().topRunningActivityLocked(null); 10608 return (r != null) ? r.immersive : false; 10609 } 10610 } 10611 10612 @Override 10613 public boolean isTopOfTask(IBinder token) { 10614 synchronized (this) { 10615 ActivityRecord r = ActivityRecord.isInStackLocked(token); 10616 if (r == null) { 10617 throw new IllegalArgumentException(); 10618 } 10619 return r.task.getTopActivity() == r; 10620 } 10621 } 10622 10623 public final void enterSafeMode() { 10624 synchronized(this) { 10625 // It only makes sense to do this before the system is ready 10626 // and started launching other packages. 10627 if (!mSystemReady) { 10628 try { 10629 AppGlobals.getPackageManager().enterSafeMode(); 10630 } catch (RemoteException e) { 10631 } 10632 } 10633 10634 mSafeMode = true; 10635 } 10636 } 10637 10638 public final void showSafeModeOverlay() { 10639 View v = LayoutInflater.from(mContext).inflate( 10640 com.android.internal.R.layout.safe_mode, null); 10641 WindowManager.LayoutParams lp = new WindowManager.LayoutParams(); 10642 lp.type = WindowManager.LayoutParams.TYPE_SECURE_SYSTEM_OVERLAY; 10643 lp.width = WindowManager.LayoutParams.WRAP_CONTENT; 10644 lp.height = WindowManager.LayoutParams.WRAP_CONTENT; 10645 lp.gravity = Gravity.BOTTOM | Gravity.START; 10646 lp.format = v.getBackground().getOpacity(); 10647 lp.flags = WindowManager.LayoutParams.FLAG_NOT_FOCUSABLE 10648 | WindowManager.LayoutParams.FLAG_NOT_TOUCHABLE; 10649 lp.privateFlags |= WindowManager.LayoutParams.PRIVATE_FLAG_SHOW_FOR_ALL_USERS; 10650 ((WindowManager)mContext.getSystemService( 10651 Context.WINDOW_SERVICE)).addView(v, lp); 10652 } 10653 10654 public void noteWakeupAlarm(IIntentSender sender, int sourceUid, String sourcePkg) { 10655 if (!(sender instanceof PendingIntentRecord)) { 10656 return; 10657 } 10658 BatteryStatsImpl stats = mBatteryStatsService.getActiveStatistics(); 10659 synchronized (stats) { 10660 if (mBatteryStatsService.isOnBattery()) { 10661 mBatteryStatsService.enforceCallingPermission(); 10662 PendingIntentRecord rec = (PendingIntentRecord)sender; 10663 int MY_UID = Binder.getCallingUid(); 10664 int uid = rec.uid == MY_UID ? Process.SYSTEM_UID : rec.uid; 10665 BatteryStatsImpl.Uid.Pkg pkg = 10666 stats.getPackageStatsLocked(sourceUid >= 0 ? sourceUid : uid, 10667 sourcePkg != null ? sourcePkg : rec.key.packageName); 10668 pkg.incWakeupsLocked(); 10669 } 10670 } 10671 } 10672 10673 public boolean killPids(int[] pids, String pReason, boolean secure) { 10674 if (Binder.getCallingUid() != Process.SYSTEM_UID) { 10675 throw new SecurityException("killPids only available to the system"); 10676 } 10677 String reason = (pReason == null) ? "Unknown" : pReason; 10678 // XXX Note: don't acquire main activity lock here, because the window 10679 // manager calls in with its locks held. 10680 10681 boolean killed = false; 10682 synchronized (mPidsSelfLocked) { 10683 int[] types = new int[pids.length]; 10684 int worstType = 0; 10685 for (int i=0; i<pids.length; i++) { 10686 ProcessRecord proc = mPidsSelfLocked.get(pids[i]); 10687 if (proc != null) { 10688 int type = proc.setAdj; 10689 types[i] = type; 10690 if (type > worstType) { 10691 worstType = type; 10692 } 10693 } 10694 } 10695 10696 // If the worst oom_adj is somewhere in the cached proc LRU range, 10697 // then constrain it so we will kill all cached procs. 10698 if (worstType < ProcessList.CACHED_APP_MAX_ADJ 10699 && worstType > ProcessList.CACHED_APP_MIN_ADJ) { 10700 worstType = ProcessList.CACHED_APP_MIN_ADJ; 10701 } 10702 10703 // If this is not a secure call, don't let it kill processes that 10704 // are important. 10705 if (!secure && worstType < ProcessList.SERVICE_ADJ) { 10706 worstType = ProcessList.SERVICE_ADJ; 10707 } 10708 10709 Slog.w(TAG, "Killing processes " + reason + " at adjustment " + worstType); 10710 for (int i=0; i<pids.length; i++) { 10711 ProcessRecord proc = mPidsSelfLocked.get(pids[i]); 10712 if (proc == null) { 10713 continue; 10714 } 10715 int adj = proc.setAdj; 10716 if (adj >= worstType && !proc.killedByAm) { 10717 proc.kill(reason, true); 10718 killed = true; 10719 } 10720 } 10721 } 10722 return killed; 10723 } 10724 10725 @Override 10726 public void killUid(int uid, String reason) { 10727 if (Binder.getCallingUid() != Process.SYSTEM_UID) { 10728 throw new SecurityException("killUid only available to the system"); 10729 } 10730 synchronized (this) { 10731 killPackageProcessesLocked(null, UserHandle.getAppId(uid), UserHandle.getUserId(uid), 10732 ProcessList.FOREGROUND_APP_ADJ-1, false, true, true, false, 10733 reason != null ? reason : "kill uid"); 10734 } 10735 } 10736 10737 @Override 10738 public boolean killProcessesBelowForeground(String reason) { 10739 if (Binder.getCallingUid() != Process.SYSTEM_UID) { 10740 throw new SecurityException("killProcessesBelowForeground() only available to system"); 10741 } 10742 10743 return killProcessesBelowAdj(ProcessList.FOREGROUND_APP_ADJ, reason); 10744 } 10745 10746 private boolean killProcessesBelowAdj(int belowAdj, String reason) { 10747 if (Binder.getCallingUid() != Process.SYSTEM_UID) { 10748 throw new SecurityException("killProcessesBelowAdj() only available to system"); 10749 } 10750 10751 boolean killed = false; 10752 synchronized (mPidsSelfLocked) { 10753 final int size = mPidsSelfLocked.size(); 10754 for (int i = 0; i < size; i++) { 10755 final int pid = mPidsSelfLocked.keyAt(i); 10756 final ProcessRecord proc = mPidsSelfLocked.valueAt(i); 10757 if (proc == null) continue; 10758 10759 final int adj = proc.setAdj; 10760 if (adj > belowAdj && !proc.killedByAm) { 10761 proc.kill(reason, true); 10762 killed = true; 10763 } 10764 } 10765 } 10766 return killed; 10767 } 10768 10769 @Override 10770 public void hang(final IBinder who, boolean allowRestart) { 10771 if (checkCallingPermission(android.Manifest.permission.SET_ACTIVITY_WATCHER) 10772 != PackageManager.PERMISSION_GRANTED) { 10773 throw new SecurityException("Requires permission " 10774 + android.Manifest.permission.SET_ACTIVITY_WATCHER); 10775 } 10776 10777 final IBinder.DeathRecipient death = new DeathRecipient() { 10778 @Override 10779 public void binderDied() { 10780 synchronized (this) { 10781 notifyAll(); 10782 } 10783 } 10784 }; 10785 10786 try { 10787 who.linkToDeath(death, 0); 10788 } catch (RemoteException e) { 10789 Slog.w(TAG, "hang: given caller IBinder is already dead."); 10790 return; 10791 } 10792 10793 synchronized (this) { 10794 Watchdog.getInstance().setAllowRestart(allowRestart); 10795 Slog.i(TAG, "Hanging system process at request of pid " + Binder.getCallingPid()); 10796 synchronized (death) { 10797 while (who.isBinderAlive()) { 10798 try { 10799 death.wait(); 10800 } catch (InterruptedException e) { 10801 } 10802 } 10803 } 10804 Watchdog.getInstance().setAllowRestart(true); 10805 } 10806 } 10807 10808 @Override 10809 public void restart() { 10810 if (checkCallingPermission(android.Manifest.permission.SET_ACTIVITY_WATCHER) 10811 != PackageManager.PERMISSION_GRANTED) { 10812 throw new SecurityException("Requires permission " 10813 + android.Manifest.permission.SET_ACTIVITY_WATCHER); 10814 } 10815 10816 Log.i(TAG, "Sending shutdown broadcast..."); 10817 10818 BroadcastReceiver br = new BroadcastReceiver() { 10819 @Override public void onReceive(Context context, Intent intent) { 10820 // Now the broadcast is done, finish up the low-level shutdown. 10821 Log.i(TAG, "Shutting down activity manager..."); 10822 shutdown(10000); 10823 Log.i(TAG, "Shutdown complete, restarting!"); 10824 Process.killProcess(Process.myPid()); 10825 System.exit(10); 10826 } 10827 }; 10828 10829 // First send the high-level shut down broadcast. 10830 Intent intent = new Intent(Intent.ACTION_SHUTDOWN); 10831 intent.addFlags(Intent.FLAG_RECEIVER_FOREGROUND); 10832 intent.putExtra(Intent.EXTRA_SHUTDOWN_USERSPACE_ONLY, true); 10833 /* For now we are not doing a clean shutdown, because things seem to get unhappy. 10834 mContext.sendOrderedBroadcastAsUser(intent, 10835 UserHandle.ALL, null, br, mHandler, 0, null, null); 10836 */ 10837 br.onReceive(mContext, intent); 10838 } 10839 10840 private long getLowRamTimeSinceIdle(long now) { 10841 return mLowRamTimeSinceLastIdle + (mLowRamStartTime > 0 ? (now-mLowRamStartTime) : 0); 10842 } 10843 10844 @Override 10845 public void performIdleMaintenance() { 10846 if (checkCallingPermission(android.Manifest.permission.SET_ACTIVITY_WATCHER) 10847 != PackageManager.PERMISSION_GRANTED) { 10848 throw new SecurityException("Requires permission " 10849 + android.Manifest.permission.SET_ACTIVITY_WATCHER); 10850 } 10851 10852 synchronized (this) { 10853 final long now = SystemClock.uptimeMillis(); 10854 final long timeSinceLastIdle = now - mLastIdleTime; 10855 final long lowRamSinceLastIdle = getLowRamTimeSinceIdle(now); 10856 mLastIdleTime = now; 10857 mLowRamTimeSinceLastIdle = 0; 10858 if (mLowRamStartTime != 0) { 10859 mLowRamStartTime = now; 10860 } 10861 10862 StringBuilder sb = new StringBuilder(128); 10863 sb.append("Idle maintenance over "); 10864 TimeUtils.formatDuration(timeSinceLastIdle, sb); 10865 sb.append(" low RAM for "); 10866 TimeUtils.formatDuration(lowRamSinceLastIdle, sb); 10867 Slog.i(TAG, sb.toString()); 10868 10869 // If at least 1/3 of our time since the last idle period has been spent 10870 // with RAM low, then we want to kill processes. 10871 boolean doKilling = lowRamSinceLastIdle > (timeSinceLastIdle/3); 10872 10873 for (int i = mLruProcesses.size() - 1 ; i >= 0 ; i--) { 10874 ProcessRecord proc = mLruProcesses.get(i); 10875 if (proc.notCachedSinceIdle) { 10876 if (proc.setProcState > ActivityManager.PROCESS_STATE_TOP 10877 && proc.setProcState <= ActivityManager.PROCESS_STATE_SERVICE) { 10878 if (doKilling && proc.initialIdlePss != 0 10879 && proc.lastPss > ((proc.initialIdlePss*3)/2)) { 10880 proc.kill("idle maint (pss " + proc.lastPss 10881 + " from " + proc.initialIdlePss + ")", true); 10882 } 10883 } 10884 } else if (proc.setProcState < ActivityManager.PROCESS_STATE_HOME) { 10885 proc.notCachedSinceIdle = true; 10886 proc.initialIdlePss = 0; 10887 proc.nextPssTime = ProcessList.computeNextPssTime(proc.curProcState, true, 10888 isSleeping(), now); 10889 } 10890 } 10891 10892 mHandler.removeMessages(REQUEST_ALL_PSS_MSG); 10893 mHandler.sendEmptyMessageDelayed(REQUEST_ALL_PSS_MSG, 2*60*1000); 10894 } 10895 } 10896 10897 private void retrieveSettings() { 10898 final ContentResolver resolver = mContext.getContentResolver(); 10899 String debugApp = Settings.Global.getString( 10900 resolver, Settings.Global.DEBUG_APP); 10901 boolean waitForDebugger = Settings.Global.getInt( 10902 resolver, Settings.Global.WAIT_FOR_DEBUGGER, 0) != 0; 10903 boolean alwaysFinishActivities = Settings.Global.getInt( 10904 resolver, Settings.Global.ALWAYS_FINISH_ACTIVITIES, 0) != 0; 10905 boolean forceRtl = Settings.Global.getInt( 10906 resolver, Settings.Global.DEVELOPMENT_FORCE_RTL, 0) != 0; 10907 // Transfer any global setting for forcing RTL layout, into a System Property 10908 SystemProperties.set(Settings.Global.DEVELOPMENT_FORCE_RTL, forceRtl ? "1":"0"); 10909 10910 Configuration configuration = new Configuration(); 10911 Settings.System.getConfiguration(resolver, configuration); 10912 if (forceRtl) { 10913 // This will take care of setting the correct layout direction flags 10914 configuration.setLayoutDirection(configuration.locale); 10915 } 10916 10917 synchronized (this) { 10918 mDebugApp = mOrigDebugApp = debugApp; 10919 mWaitForDebugger = mOrigWaitForDebugger = waitForDebugger; 10920 mAlwaysFinishActivities = alwaysFinishActivities; 10921 // This happens before any activities are started, so we can 10922 // change mConfiguration in-place. 10923 updateConfigurationLocked(configuration, null, false, true); 10924 if (DEBUG_CONFIGURATION) Slog.v(TAG, "Initial config: " + mConfiguration); 10925 } 10926 } 10927 10928 /** Loads resources after the current configuration has been set. */ 10929 private void loadResourcesOnSystemReady() { 10930 final Resources res = mContext.getResources(); 10931 mHasRecents = res.getBoolean(com.android.internal.R.bool.config_hasRecents); 10932 mThumbnailWidth = res.getDimensionPixelSize(com.android.internal.R.dimen.thumbnail_width); 10933 mThumbnailHeight = res.getDimensionPixelSize(com.android.internal.R.dimen.thumbnail_height); 10934 } 10935 10936 public boolean testIsSystemReady() { 10937 // no need to synchronize(this) just to read & return the value 10938 return mSystemReady; 10939 } 10940 10941 private static File getCalledPreBootReceiversFile() { 10942 File dataDir = Environment.getDataDirectory(); 10943 File systemDir = new File(dataDir, "system"); 10944 File fname = new File(systemDir, CALLED_PRE_BOOTS_FILENAME); 10945 return fname; 10946 } 10947 10948 private static ArrayList<ComponentName> readLastDonePreBootReceivers() { 10949 ArrayList<ComponentName> lastDoneReceivers = new ArrayList<ComponentName>(); 10950 File file = getCalledPreBootReceiversFile(); 10951 FileInputStream fis = null; 10952 try { 10953 fis = new FileInputStream(file); 10954 DataInputStream dis = new DataInputStream(new BufferedInputStream(fis, 2048)); 10955 int fvers = dis.readInt(); 10956 if (fvers == LAST_PREBOOT_DELIVERED_FILE_VERSION) { 10957 String vers = dis.readUTF(); 10958 String codename = dis.readUTF(); 10959 String build = dis.readUTF(); 10960 if (android.os.Build.VERSION.RELEASE.equals(vers) 10961 && android.os.Build.VERSION.CODENAME.equals(codename) 10962 && android.os.Build.VERSION.INCREMENTAL.equals(build)) { 10963 int num = dis.readInt(); 10964 while (num > 0) { 10965 num--; 10966 String pkg = dis.readUTF(); 10967 String cls = dis.readUTF(); 10968 lastDoneReceivers.add(new ComponentName(pkg, cls)); 10969 } 10970 } 10971 } 10972 } catch (FileNotFoundException e) { 10973 } catch (IOException e) { 10974 Slog.w(TAG, "Failure reading last done pre-boot receivers", e); 10975 } finally { 10976 if (fis != null) { 10977 try { 10978 fis.close(); 10979 } catch (IOException e) { 10980 } 10981 } 10982 } 10983 return lastDoneReceivers; 10984 } 10985 10986 private static void writeLastDonePreBootReceivers(ArrayList<ComponentName> list) { 10987 File file = getCalledPreBootReceiversFile(); 10988 FileOutputStream fos = null; 10989 DataOutputStream dos = null; 10990 try { 10991 fos = new FileOutputStream(file); 10992 dos = new DataOutputStream(new BufferedOutputStream(fos, 2048)); 10993 dos.writeInt(LAST_PREBOOT_DELIVERED_FILE_VERSION); 10994 dos.writeUTF(android.os.Build.VERSION.RELEASE); 10995 dos.writeUTF(android.os.Build.VERSION.CODENAME); 10996 dos.writeUTF(android.os.Build.VERSION.INCREMENTAL); 10997 dos.writeInt(list.size()); 10998 for (int i=0; i<list.size(); i++) { 10999 dos.writeUTF(list.get(i).getPackageName()); 11000 dos.writeUTF(list.get(i).getClassName()); 11001 } 11002 } catch (IOException e) { 11003 Slog.w(TAG, "Failure writing last done pre-boot receivers", e); 11004 file.delete(); 11005 } finally { 11006 FileUtils.sync(fos); 11007 if (dos != null) { 11008 try { 11009 dos.close(); 11010 } catch (IOException e) { 11011 // TODO Auto-generated catch block 11012 e.printStackTrace(); 11013 } 11014 } 11015 } 11016 } 11017 11018 private boolean deliverPreBootCompleted(final Runnable onFinishCallback, 11019 ArrayList<ComponentName> doneReceivers, int userId) { 11020 boolean waitingUpdate = false; 11021 Intent intent = new Intent(Intent.ACTION_PRE_BOOT_COMPLETED); 11022 List<ResolveInfo> ris = null; 11023 try { 11024 ris = AppGlobals.getPackageManager().queryIntentReceivers( 11025 intent, null, 0, userId); 11026 } catch (RemoteException e) { 11027 } 11028 if (ris != null) { 11029 for (int i=ris.size()-1; i>=0; i--) { 11030 if ((ris.get(i).activityInfo.applicationInfo.flags 11031 &ApplicationInfo.FLAG_SYSTEM) == 0) { 11032 ris.remove(i); 11033 } 11034 } 11035 intent.addFlags(Intent.FLAG_RECEIVER_BOOT_UPGRADE); 11036 11037 // For User 0, load the version number. When delivering to a new user, deliver 11038 // to all receivers. 11039 if (userId == UserHandle.USER_OWNER) { 11040 ArrayList<ComponentName> lastDoneReceivers = readLastDonePreBootReceivers(); 11041 for (int i=0; i<ris.size(); i++) { 11042 ActivityInfo ai = ris.get(i).activityInfo; 11043 ComponentName comp = new ComponentName(ai.packageName, ai.name); 11044 if (lastDoneReceivers.contains(comp)) { 11045 // We already did the pre boot receiver for this app with the current 11046 // platform version, so don't do it again... 11047 ris.remove(i); 11048 i--; 11049 // ...however, do keep it as one that has been done, so we don't 11050 // forget about it when rewriting the file of last done receivers. 11051 doneReceivers.add(comp); 11052 } 11053 } 11054 } 11055 11056 // If primary user, send broadcast to all available users, else just to userId 11057 final int[] users = userId == UserHandle.USER_OWNER ? getUsersLocked() 11058 : new int[] { userId }; 11059 for (int i = 0; i < ris.size(); i++) { 11060 ActivityInfo ai = ris.get(i).activityInfo; 11061 ComponentName comp = new ComponentName(ai.packageName, ai.name); 11062 doneReceivers.add(comp); 11063 intent.setComponent(comp); 11064 for (int j=0; j<users.length; j++) { 11065 IIntentReceiver finisher = null; 11066 // On last receiver and user, set up a completion callback 11067 if (i == ris.size() - 1 && j == users.length - 1 && onFinishCallback != null) { 11068 finisher = new IIntentReceiver.Stub() { 11069 public void performReceive(Intent intent, int resultCode, 11070 String data, Bundle extras, boolean ordered, 11071 boolean sticky, int sendingUser) { 11072 // The raw IIntentReceiver interface is called 11073 // with the AM lock held, so redispatch to 11074 // execute our code without the lock. 11075 mHandler.post(onFinishCallback); 11076 } 11077 }; 11078 } 11079 Slog.i(TAG, "Sending system update to " + intent.getComponent() 11080 + " for user " + users[j]); 11081 broadcastIntentLocked(null, null, intent, null, finisher, 11082 0, null, null, null, AppOpsManager.OP_NONE, 11083 true, false, MY_PID, Process.SYSTEM_UID, 11084 users[j]); 11085 if (finisher != null) { 11086 waitingUpdate = true; 11087 } 11088 } 11089 } 11090 } 11091 11092 return waitingUpdate; 11093 } 11094 11095 public void systemReady(final Runnable goingCallback) { 11096 synchronized(this) { 11097 if (mSystemReady) { 11098 // If we're done calling all the receivers, run the next "boot phase" passed in 11099 // by the SystemServer 11100 if (goingCallback != null) { 11101 goingCallback.run(); 11102 } 11103 return; 11104 } 11105 11106 // Make sure we have the current profile info, since it is needed for 11107 // security checks. 11108 updateCurrentProfileIdsLocked(); 11109 11110 if (mRecentTasks == null) { 11111 mRecentTasks = mTaskPersister.restoreTasksLocked(); 11112 if (!mRecentTasks.isEmpty()) { 11113 mStackSupervisor.createStackForRestoredTaskHistory(mRecentTasks); 11114 } 11115 cleanupRecentTasksLocked(UserHandle.USER_ALL); 11116 mTaskPersister.startPersisting(); 11117 } 11118 11119 // Check to see if there are any update receivers to run. 11120 if (!mDidUpdate) { 11121 if (mWaitingUpdate) { 11122 return; 11123 } 11124 final ArrayList<ComponentName> doneReceivers = new ArrayList<ComponentName>(); 11125 mWaitingUpdate = deliverPreBootCompleted(new Runnable() { 11126 public void run() { 11127 synchronized (ActivityManagerService.this) { 11128 mDidUpdate = true; 11129 } 11130 writeLastDonePreBootReceivers(doneReceivers); 11131 showBootMessage(mContext.getText( 11132 R.string.android_upgrading_complete), 11133 false); 11134 systemReady(goingCallback); 11135 } 11136 }, doneReceivers, UserHandle.USER_OWNER); 11137 11138 if (mWaitingUpdate) { 11139 return; 11140 } 11141 mDidUpdate = true; 11142 } 11143 11144 mAppOpsService.systemReady(); 11145 mSystemReady = true; 11146 } 11147 11148 ArrayList<ProcessRecord> procsToKill = null; 11149 synchronized(mPidsSelfLocked) { 11150 for (int i=mPidsSelfLocked.size()-1; i>=0; i--) { 11151 ProcessRecord proc = mPidsSelfLocked.valueAt(i); 11152 if (!isAllowedWhileBooting(proc.info)){ 11153 if (procsToKill == null) { 11154 procsToKill = new ArrayList<ProcessRecord>(); 11155 } 11156 procsToKill.add(proc); 11157 } 11158 } 11159 } 11160 11161 synchronized(this) { 11162 if (procsToKill != null) { 11163 for (int i=procsToKill.size()-1; i>=0; i--) { 11164 ProcessRecord proc = procsToKill.get(i); 11165 Slog.i(TAG, "Removing system update proc: " + proc); 11166 removeProcessLocked(proc, true, false, "system update done"); 11167 } 11168 } 11169 11170 // Now that we have cleaned up any update processes, we 11171 // are ready to start launching real processes and know that 11172 // we won't trample on them any more. 11173 mProcessesReady = true; 11174 } 11175 11176 Slog.i(TAG, "System now ready"); 11177 EventLog.writeEvent(EventLogTags.BOOT_PROGRESS_AMS_READY, 11178 SystemClock.uptimeMillis()); 11179 11180 synchronized(this) { 11181 // Make sure we have no pre-ready processes sitting around. 11182 11183 if (mFactoryTest == FactoryTest.FACTORY_TEST_LOW_LEVEL) { 11184 ResolveInfo ri = mContext.getPackageManager() 11185 .resolveActivity(new Intent(Intent.ACTION_FACTORY_TEST), 11186 STOCK_PM_FLAGS); 11187 CharSequence errorMsg = null; 11188 if (ri != null) { 11189 ActivityInfo ai = ri.activityInfo; 11190 ApplicationInfo app = ai.applicationInfo; 11191 if ((app.flags&ApplicationInfo.FLAG_SYSTEM) != 0) { 11192 mTopAction = Intent.ACTION_FACTORY_TEST; 11193 mTopData = null; 11194 mTopComponent = new ComponentName(app.packageName, 11195 ai.name); 11196 } else { 11197 errorMsg = mContext.getResources().getText( 11198 com.android.internal.R.string.factorytest_not_system); 11199 } 11200 } else { 11201 errorMsg = mContext.getResources().getText( 11202 com.android.internal.R.string.factorytest_no_action); 11203 } 11204 if (errorMsg != null) { 11205 mTopAction = null; 11206 mTopData = null; 11207 mTopComponent = null; 11208 Message msg = Message.obtain(); 11209 msg.what = SHOW_FACTORY_ERROR_MSG; 11210 msg.getData().putCharSequence("msg", errorMsg); 11211 mHandler.sendMessage(msg); 11212 } 11213 } 11214 } 11215 11216 retrieveSettings(); 11217 loadResourcesOnSystemReady(); 11218 11219 synchronized (this) { 11220 readGrantedUriPermissionsLocked(); 11221 } 11222 11223 if (goingCallback != null) goingCallback.run(); 11224 11225 mBatteryStatsService.noteEvent(BatteryStats.HistoryItem.EVENT_USER_RUNNING_START, 11226 Integer.toString(mCurrentUserId), mCurrentUserId); 11227 mBatteryStatsService.noteEvent(BatteryStats.HistoryItem.EVENT_USER_FOREGROUND_START, 11228 Integer.toString(mCurrentUserId), mCurrentUserId); 11229 mSystemServiceManager.startUser(mCurrentUserId); 11230 11231 synchronized (this) { 11232 if (mFactoryTest != FactoryTest.FACTORY_TEST_LOW_LEVEL) { 11233 try { 11234 List apps = AppGlobals.getPackageManager(). 11235 getPersistentApplications(STOCK_PM_FLAGS); 11236 if (apps != null) { 11237 int N = apps.size(); 11238 int i; 11239 for (i=0; i<N; i++) { 11240 ApplicationInfo info 11241 = (ApplicationInfo)apps.get(i); 11242 if (info != null && 11243 !info.packageName.equals("android")) { 11244 addAppLocked(info, false, null /* ABI override */); 11245 } 11246 } 11247 } 11248 } catch (RemoteException ex) { 11249 // pm is in same process, this will never happen. 11250 } 11251 } 11252 11253 // Start up initial activity. 11254 mBooting = true; 11255 startHomeActivityLocked(mCurrentUserId); 11256 11257 try { 11258 if (AppGlobals.getPackageManager().hasSystemUidErrors()) { 11259 Slog.e(TAG, "UIDs on the system are inconsistent, you need to wipe your" 11260 + " data partition or your device will be unstable."); 11261 mHandler.obtainMessage(SHOW_UID_ERROR_MSG).sendToTarget(); 11262 } 11263 } catch (RemoteException e) { 11264 } 11265 11266 if (!Build.isFingerprintConsistent()) { 11267 Slog.e(TAG, "Build fingerprint is not consistent, warning user"); 11268 mHandler.obtainMessage(SHOW_FINGERPRINT_ERROR_MSG).sendToTarget(); 11269 } 11270 11271 long ident = Binder.clearCallingIdentity(); 11272 try { 11273 Intent intent = new Intent(Intent.ACTION_USER_STARTED); 11274 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY 11275 | Intent.FLAG_RECEIVER_FOREGROUND); 11276 intent.putExtra(Intent.EXTRA_USER_HANDLE, mCurrentUserId); 11277 broadcastIntentLocked(null, null, intent, 11278 null, null, 0, null, null, null, AppOpsManager.OP_NONE, 11279 false, false, MY_PID, Process.SYSTEM_UID, mCurrentUserId); 11280 intent = new Intent(Intent.ACTION_USER_STARTING); 11281 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY); 11282 intent.putExtra(Intent.EXTRA_USER_HANDLE, mCurrentUserId); 11283 broadcastIntentLocked(null, null, intent, 11284 null, new IIntentReceiver.Stub() { 11285 @Override 11286 public void performReceive(Intent intent, int resultCode, String data, 11287 Bundle extras, boolean ordered, boolean sticky, int sendingUser) 11288 throws RemoteException { 11289 } 11290 }, 0, null, null, 11291 INTERACT_ACROSS_USERS, AppOpsManager.OP_NONE, 11292 true, false, MY_PID, Process.SYSTEM_UID, UserHandle.USER_ALL); 11293 } catch (Throwable t) { 11294 Slog.wtf(TAG, "Failed sending first user broadcasts", t); 11295 } finally { 11296 Binder.restoreCallingIdentity(ident); 11297 } 11298 mStackSupervisor.resumeTopActivitiesLocked(); 11299 sendUserSwitchBroadcastsLocked(-1, mCurrentUserId); 11300 } 11301 } 11302 11303 private boolean makeAppCrashingLocked(ProcessRecord app, 11304 String shortMsg, String longMsg, String stackTrace) { 11305 app.crashing = true; 11306 app.crashingReport = generateProcessError(app, 11307 ActivityManager.ProcessErrorStateInfo.CRASHED, null, shortMsg, longMsg, stackTrace); 11308 startAppProblemLocked(app); 11309 app.stopFreezingAllLocked(); 11310 return handleAppCrashLocked(app, shortMsg, longMsg, stackTrace); 11311 } 11312 11313 private void makeAppNotRespondingLocked(ProcessRecord app, 11314 String activity, String shortMsg, String longMsg) { 11315 app.notResponding = true; 11316 app.notRespondingReport = generateProcessError(app, 11317 ActivityManager.ProcessErrorStateInfo.NOT_RESPONDING, 11318 activity, shortMsg, longMsg, null); 11319 startAppProblemLocked(app); 11320 app.stopFreezingAllLocked(); 11321 } 11322 11323 /** 11324 * Generate a process error record, suitable for attachment to a ProcessRecord. 11325 * 11326 * @param app The ProcessRecord in which the error occurred. 11327 * @param condition Crashing, Application Not Responding, etc. Values are defined in 11328 * ActivityManager.AppErrorStateInfo 11329 * @param activity The activity associated with the crash, if known. 11330 * @param shortMsg Short message describing the crash. 11331 * @param longMsg Long message describing the crash. 11332 * @param stackTrace Full crash stack trace, may be null. 11333 * 11334 * @return Returns a fully-formed AppErrorStateInfo record. 11335 */ 11336 private ActivityManager.ProcessErrorStateInfo generateProcessError(ProcessRecord app, 11337 int condition, String activity, String shortMsg, String longMsg, String stackTrace) { 11338 ActivityManager.ProcessErrorStateInfo report = new ActivityManager.ProcessErrorStateInfo(); 11339 11340 report.condition = condition; 11341 report.processName = app.processName; 11342 report.pid = app.pid; 11343 report.uid = app.info.uid; 11344 report.tag = activity; 11345 report.shortMsg = shortMsg; 11346 report.longMsg = longMsg; 11347 report.stackTrace = stackTrace; 11348 11349 return report; 11350 } 11351 11352 void killAppAtUsersRequest(ProcessRecord app, Dialog fromDialog) { 11353 synchronized (this) { 11354 app.crashing = false; 11355 app.crashingReport = null; 11356 app.notResponding = false; 11357 app.notRespondingReport = null; 11358 if (app.anrDialog == fromDialog) { 11359 app.anrDialog = null; 11360 } 11361 if (app.waitDialog == fromDialog) { 11362 app.waitDialog = null; 11363 } 11364 if (app.pid > 0 && app.pid != MY_PID) { 11365 handleAppCrashLocked(app, null, null, null); 11366 app.kill("user request after error", true); 11367 } 11368 } 11369 } 11370 11371 private boolean handleAppCrashLocked(ProcessRecord app, String shortMsg, String longMsg, 11372 String stackTrace) { 11373 long now = SystemClock.uptimeMillis(); 11374 11375 Long crashTime; 11376 if (!app.isolated) { 11377 crashTime = mProcessCrashTimes.get(app.info.processName, app.uid); 11378 } else { 11379 crashTime = null; 11380 } 11381 if (crashTime != null && now < crashTime+ProcessList.MIN_CRASH_INTERVAL) { 11382 // This process loses! 11383 Slog.w(TAG, "Process " + app.info.processName 11384 + " has crashed too many times: killing!"); 11385 EventLog.writeEvent(EventLogTags.AM_PROCESS_CRASHED_TOO_MUCH, 11386 app.userId, app.info.processName, app.uid); 11387 mStackSupervisor.handleAppCrashLocked(app); 11388 if (!app.persistent) { 11389 // We don't want to start this process again until the user 11390 // explicitly does so... but for persistent process, we really 11391 // need to keep it running. If a persistent process is actually 11392 // repeatedly crashing, then badness for everyone. 11393 EventLog.writeEvent(EventLogTags.AM_PROC_BAD, app.userId, app.uid, 11394 app.info.processName); 11395 if (!app.isolated) { 11396 // XXX We don't have a way to mark isolated processes 11397 // as bad, since they don't have a peristent identity. 11398 mBadProcesses.put(app.info.processName, app.uid, 11399 new BadProcessInfo(now, shortMsg, longMsg, stackTrace)); 11400 mProcessCrashTimes.remove(app.info.processName, app.uid); 11401 } 11402 app.bad = true; 11403 app.removed = true; 11404 // Don't let services in this process be restarted and potentially 11405 // annoy the user repeatedly. Unless it is persistent, since those 11406 // processes run critical code. 11407 removeProcessLocked(app, false, false, "crash"); 11408 mStackSupervisor.resumeTopActivitiesLocked(); 11409 return false; 11410 } 11411 mStackSupervisor.resumeTopActivitiesLocked(); 11412 } else { 11413 mStackSupervisor.finishTopRunningActivityLocked(app); 11414 } 11415 11416 // Bump up the crash count of any services currently running in the proc. 11417 for (int i=app.services.size()-1; i>=0; i--) { 11418 // Any services running in the application need to be placed 11419 // back in the pending list. 11420 ServiceRecord sr = app.services.valueAt(i); 11421 sr.crashCount++; 11422 } 11423 11424 // If the crashing process is what we consider to be the "home process" and it has been 11425 // replaced by a third-party app, clear the package preferred activities from packages 11426 // with a home activity running in the process to prevent a repeatedly crashing app 11427 // from blocking the user to manually clear the list. 11428 final ArrayList<ActivityRecord> activities = app.activities; 11429 if (app == mHomeProcess && activities.size() > 0 11430 && (mHomeProcess.info.flags & ApplicationInfo.FLAG_SYSTEM) == 0) { 11431 for (int activityNdx = activities.size() - 1; activityNdx >= 0; --activityNdx) { 11432 final ActivityRecord r = activities.get(activityNdx); 11433 if (r.isHomeActivity()) { 11434 Log.i(TAG, "Clearing package preferred activities from " + r.packageName); 11435 try { 11436 ActivityThread.getPackageManager() 11437 .clearPackagePreferredActivities(r.packageName); 11438 } catch (RemoteException c) { 11439 // pm is in same process, this will never happen. 11440 } 11441 } 11442 } 11443 } 11444 11445 if (!app.isolated) { 11446 // XXX Can't keep track of crash times for isolated processes, 11447 // because they don't have a perisistent identity. 11448 mProcessCrashTimes.put(app.info.processName, app.uid, now); 11449 } 11450 11451 if (app.crashHandler != null) mHandler.post(app.crashHandler); 11452 return true; 11453 } 11454 11455 void startAppProblemLocked(ProcessRecord app) { 11456 // If this app is not running under the current user, then we 11457 // can't give it a report button because that would require 11458 // launching the report UI under a different user. 11459 app.errorReportReceiver = null; 11460 11461 for (int userId : mCurrentProfileIds) { 11462 if (app.userId == userId) { 11463 app.errorReportReceiver = ApplicationErrorReport.getErrorReportReceiver( 11464 mContext, app.info.packageName, app.info.flags); 11465 } 11466 } 11467 skipCurrentReceiverLocked(app); 11468 } 11469 11470 void skipCurrentReceiverLocked(ProcessRecord app) { 11471 for (BroadcastQueue queue : mBroadcastQueues) { 11472 queue.skipCurrentReceiverLocked(app); 11473 } 11474 } 11475 11476 /** 11477 * Used by {@link com.android.internal.os.RuntimeInit} to report when an application crashes. 11478 * The application process will exit immediately after this call returns. 11479 * @param app object of the crashing app, null for the system server 11480 * @param crashInfo describing the exception 11481 */ 11482 public void handleApplicationCrash(IBinder app, ApplicationErrorReport.CrashInfo crashInfo) { 11483 ProcessRecord r = findAppProcess(app, "Crash"); 11484 final String processName = app == null ? "system_server" 11485 : (r == null ? "unknown" : r.processName); 11486 11487 handleApplicationCrashInner("crash", r, processName, crashInfo); 11488 } 11489 11490 /* Native crash reporting uses this inner version because it needs to be somewhat 11491 * decoupled from the AM-managed cleanup lifecycle 11492 */ 11493 void handleApplicationCrashInner(String eventType, ProcessRecord r, String processName, 11494 ApplicationErrorReport.CrashInfo crashInfo) { 11495 EventLog.writeEvent(EventLogTags.AM_CRASH, Binder.getCallingPid(), 11496 UserHandle.getUserId(Binder.getCallingUid()), processName, 11497 r == null ? -1 : r.info.flags, 11498 crashInfo.exceptionClassName, 11499 crashInfo.exceptionMessage, 11500 crashInfo.throwFileName, 11501 crashInfo.throwLineNumber); 11502 11503 addErrorToDropBox(eventType, r, processName, null, null, null, null, null, crashInfo); 11504 11505 crashApplication(r, crashInfo); 11506 } 11507 11508 public void handleApplicationStrictModeViolation( 11509 IBinder app, 11510 int violationMask, 11511 StrictMode.ViolationInfo info) { 11512 ProcessRecord r = findAppProcess(app, "StrictMode"); 11513 if (r == null) { 11514 return; 11515 } 11516 11517 if ((violationMask & StrictMode.PENALTY_DROPBOX) != 0) { 11518 Integer stackFingerprint = info.hashCode(); 11519 boolean logIt = true; 11520 synchronized (mAlreadyLoggedViolatedStacks) { 11521 if (mAlreadyLoggedViolatedStacks.contains(stackFingerprint)) { 11522 logIt = false; 11523 // TODO: sub-sample into EventLog for these, with 11524 // the info.durationMillis? Then we'd get 11525 // the relative pain numbers, without logging all 11526 // the stack traces repeatedly. We'd want to do 11527 // likewise in the client code, which also does 11528 // dup suppression, before the Binder call. 11529 } else { 11530 if (mAlreadyLoggedViolatedStacks.size() >= MAX_DUP_SUPPRESSED_STACKS) { 11531 mAlreadyLoggedViolatedStacks.clear(); 11532 } 11533 mAlreadyLoggedViolatedStacks.add(stackFingerprint); 11534 } 11535 } 11536 if (logIt) { 11537 logStrictModeViolationToDropBox(r, info); 11538 } 11539 } 11540 11541 if ((violationMask & StrictMode.PENALTY_DIALOG) != 0) { 11542 AppErrorResult result = new AppErrorResult(); 11543 synchronized (this) { 11544 final long origId = Binder.clearCallingIdentity(); 11545 11546 Message msg = Message.obtain(); 11547 msg.what = SHOW_STRICT_MODE_VIOLATION_MSG; 11548 HashMap<String, Object> data = new HashMap<String, Object>(); 11549 data.put("result", result); 11550 data.put("app", r); 11551 data.put("violationMask", violationMask); 11552 data.put("info", info); 11553 msg.obj = data; 11554 mHandler.sendMessage(msg); 11555 11556 Binder.restoreCallingIdentity(origId); 11557 } 11558 int res = result.get(); 11559 Slog.w(TAG, "handleApplicationStrictModeViolation; res=" + res); 11560 } 11561 } 11562 11563 // Depending on the policy in effect, there could be a bunch of 11564 // these in quick succession so we try to batch these together to 11565 // minimize disk writes, number of dropbox entries, and maximize 11566 // compression, by having more fewer, larger records. 11567 private void logStrictModeViolationToDropBox( 11568 ProcessRecord process, 11569 StrictMode.ViolationInfo info) { 11570 if (info == null) { 11571 return; 11572 } 11573 final boolean isSystemApp = process == null || 11574 (process.info.flags & (ApplicationInfo.FLAG_SYSTEM | 11575 ApplicationInfo.FLAG_UPDATED_SYSTEM_APP)) != 0; 11576 final String processName = process == null ? "unknown" : process.processName; 11577 final String dropboxTag = isSystemApp ? "system_app_strictmode" : "data_app_strictmode"; 11578 final DropBoxManager dbox = (DropBoxManager) 11579 mContext.getSystemService(Context.DROPBOX_SERVICE); 11580 11581 // Exit early if the dropbox isn't configured to accept this report type. 11582 if (dbox == null || !dbox.isTagEnabled(dropboxTag)) return; 11583 11584 boolean bufferWasEmpty; 11585 boolean needsFlush; 11586 final StringBuilder sb = isSystemApp ? mStrictModeBuffer : new StringBuilder(1024); 11587 synchronized (sb) { 11588 bufferWasEmpty = sb.length() == 0; 11589 appendDropBoxProcessHeaders(process, processName, sb); 11590 sb.append("Build: ").append(Build.FINGERPRINT).append("\n"); 11591 sb.append("System-App: ").append(isSystemApp).append("\n"); 11592 sb.append("Uptime-Millis: ").append(info.violationUptimeMillis).append("\n"); 11593 if (info.violationNumThisLoop != 0) { 11594 sb.append("Loop-Violation-Number: ").append(info.violationNumThisLoop).append("\n"); 11595 } 11596 if (info.numAnimationsRunning != 0) { 11597 sb.append("Animations-Running: ").append(info.numAnimationsRunning).append("\n"); 11598 } 11599 if (info.broadcastIntentAction != null) { 11600 sb.append("Broadcast-Intent-Action: ").append(info.broadcastIntentAction).append("\n"); 11601 } 11602 if (info.durationMillis != -1) { 11603 sb.append("Duration-Millis: ").append(info.durationMillis).append("\n"); 11604 } 11605 if (info.numInstances != -1) { 11606 sb.append("Instance-Count: ").append(info.numInstances).append("\n"); 11607 } 11608 if (info.tags != null) { 11609 for (String tag : info.tags) { 11610 sb.append("Span-Tag: ").append(tag).append("\n"); 11611 } 11612 } 11613 sb.append("\n"); 11614 if (info.crashInfo != null && info.crashInfo.stackTrace != null) { 11615 sb.append(info.crashInfo.stackTrace); 11616 } 11617 sb.append("\n"); 11618 11619 // Only buffer up to ~64k. Various logging bits truncate 11620 // things at 128k. 11621 needsFlush = (sb.length() > 64 * 1024); 11622 } 11623 11624 // Flush immediately if the buffer's grown too large, or this 11625 // is a non-system app. Non-system apps are isolated with a 11626 // different tag & policy and not batched. 11627 // 11628 // Batching is useful during internal testing with 11629 // StrictMode settings turned up high. Without batching, 11630 // thousands of separate files could be created on boot. 11631 if (!isSystemApp || needsFlush) { 11632 new Thread("Error dump: " + dropboxTag) { 11633 @Override 11634 public void run() { 11635 String report; 11636 synchronized (sb) { 11637 report = sb.toString(); 11638 sb.delete(0, sb.length()); 11639 sb.trimToSize(); 11640 } 11641 if (report.length() != 0) { 11642 dbox.addText(dropboxTag, report); 11643 } 11644 } 11645 }.start(); 11646 return; 11647 } 11648 11649 // System app batching: 11650 if (!bufferWasEmpty) { 11651 // An existing dropbox-writing thread is outstanding, so 11652 // we don't need to start it up. The existing thread will 11653 // catch the buffer appends we just did. 11654 return; 11655 } 11656 11657 // Worker thread to both batch writes and to avoid blocking the caller on I/O. 11658 // (After this point, we shouldn't access AMS internal data structures.) 11659 new Thread("Error dump: " + dropboxTag) { 11660 @Override 11661 public void run() { 11662 // 5 second sleep to let stacks arrive and be batched together 11663 try { 11664 Thread.sleep(5000); // 5 seconds 11665 } catch (InterruptedException e) {} 11666 11667 String errorReport; 11668 synchronized (mStrictModeBuffer) { 11669 errorReport = mStrictModeBuffer.toString(); 11670 if (errorReport.length() == 0) { 11671 return; 11672 } 11673 mStrictModeBuffer.delete(0, mStrictModeBuffer.length()); 11674 mStrictModeBuffer.trimToSize(); 11675 } 11676 dbox.addText(dropboxTag, errorReport); 11677 } 11678 }.start(); 11679 } 11680 11681 /** 11682 * Used by {@link Log} via {@link com.android.internal.os.RuntimeInit} to report serious errors. 11683 * @param app object of the crashing app, null for the system server 11684 * @param tag reported by the caller 11685 * @param system whether this wtf is coming from the system 11686 * @param crashInfo describing the context of the error 11687 * @return true if the process should exit immediately (WTF is fatal) 11688 */ 11689 public boolean handleApplicationWtf(final IBinder app, final String tag, boolean system, 11690 final ApplicationErrorReport.CrashInfo crashInfo) { 11691 final int callingUid = Binder.getCallingUid(); 11692 final int callingPid = Binder.getCallingPid(); 11693 11694 if (system) { 11695 // If this is coming from the system, we could very well have low-level 11696 // system locks held, so we want to do this all asynchronously. And we 11697 // never want this to become fatal, so there is that too. 11698 mHandler.post(new Runnable() { 11699 @Override public void run() { 11700 handleApplicationWtfInner(callingUid, callingPid, app, tag, crashInfo); 11701 } 11702 }); 11703 return false; 11704 } 11705 11706 final ProcessRecord r = handleApplicationWtfInner(callingUid, callingPid, app, tag, 11707 crashInfo); 11708 11709 if (r != null && r.pid != Process.myPid() && 11710 Settings.Global.getInt(mContext.getContentResolver(), 11711 Settings.Global.WTF_IS_FATAL, 0) != 0) { 11712 crashApplication(r, crashInfo); 11713 return true; 11714 } else { 11715 return false; 11716 } 11717 } 11718 11719 ProcessRecord handleApplicationWtfInner(int callingUid, int callingPid, IBinder app, String tag, 11720 final ApplicationErrorReport.CrashInfo crashInfo) { 11721 final ProcessRecord r = findAppProcess(app, "WTF"); 11722 final String processName = app == null ? "system_server" 11723 : (r == null ? "unknown" : r.processName); 11724 11725 EventLog.writeEvent(EventLogTags.AM_WTF, UserHandle.getUserId(callingUid), callingPid, 11726 processName, r == null ? -1 : r.info.flags, tag, crashInfo.exceptionMessage); 11727 11728 addErrorToDropBox("wtf", r, processName, null, null, tag, null, null, crashInfo); 11729 11730 return r; 11731 } 11732 11733 /** 11734 * @param app object of some object (as stored in {@link com.android.internal.os.RuntimeInit}) 11735 * @return the corresponding {@link ProcessRecord} object, or null if none could be found 11736 */ 11737 private ProcessRecord findAppProcess(IBinder app, String reason) { 11738 if (app == null) { 11739 return null; 11740 } 11741 11742 synchronized (this) { 11743 final int NP = mProcessNames.getMap().size(); 11744 for (int ip=0; ip<NP; ip++) { 11745 SparseArray<ProcessRecord> apps = mProcessNames.getMap().valueAt(ip); 11746 final int NA = apps.size(); 11747 for (int ia=0; ia<NA; ia++) { 11748 ProcessRecord p = apps.valueAt(ia); 11749 if (p.thread != null && p.thread.asBinder() == app) { 11750 return p; 11751 } 11752 } 11753 } 11754 11755 Slog.w(TAG, "Can't find mystery application for " + reason 11756 + " from pid=" + Binder.getCallingPid() 11757 + " uid=" + Binder.getCallingUid() + ": " + app); 11758 return null; 11759 } 11760 } 11761 11762 /** 11763 * Utility function for addErrorToDropBox and handleStrictModeViolation's logging 11764 * to append various headers to the dropbox log text. 11765 */ 11766 private void appendDropBoxProcessHeaders(ProcessRecord process, String processName, 11767 StringBuilder sb) { 11768 // Watchdog thread ends up invoking this function (with 11769 // a null ProcessRecord) to add the stack file to dropbox. 11770 // Do not acquire a lock on this (am) in such cases, as it 11771 // could cause a potential deadlock, if and when watchdog 11772 // is invoked due to unavailability of lock on am and it 11773 // would prevent watchdog from killing system_server. 11774 if (process == null) { 11775 sb.append("Process: ").append(processName).append("\n"); 11776 return; 11777 } 11778 // Note: ProcessRecord 'process' is guarded by the service 11779 // instance. (notably process.pkgList, which could otherwise change 11780 // concurrently during execution of this method) 11781 synchronized (this) { 11782 sb.append("Process: ").append(processName).append("\n"); 11783 int flags = process.info.flags; 11784 IPackageManager pm = AppGlobals.getPackageManager(); 11785 sb.append("Flags: 0x").append(Integer.toString(flags, 16)).append("\n"); 11786 for (int ip=0; ip<process.pkgList.size(); ip++) { 11787 String pkg = process.pkgList.keyAt(ip); 11788 sb.append("Package: ").append(pkg); 11789 try { 11790 PackageInfo pi = pm.getPackageInfo(pkg, 0, UserHandle.getCallingUserId()); 11791 if (pi != null) { 11792 sb.append(" v").append(pi.versionCode); 11793 if (pi.versionName != null) { 11794 sb.append(" (").append(pi.versionName).append(")"); 11795 } 11796 } 11797 } catch (RemoteException e) { 11798 Slog.e(TAG, "Error getting package info: " + pkg, e); 11799 } 11800 sb.append("\n"); 11801 } 11802 } 11803 } 11804 11805 private static String processClass(ProcessRecord process) { 11806 if (process == null || process.pid == MY_PID) { 11807 return "system_server"; 11808 } else if ((process.info.flags & ApplicationInfo.FLAG_SYSTEM) != 0) { 11809 return "system_app"; 11810 } else { 11811 return "data_app"; 11812 } 11813 } 11814 11815 /** 11816 * Write a description of an error (crash, WTF, ANR) to the drop box. 11817 * @param eventType to include in the drop box tag ("crash", "wtf", etc.) 11818 * @param process which caused the error, null means the system server 11819 * @param activity which triggered the error, null if unknown 11820 * @param parent activity related to the error, null if unknown 11821 * @param subject line related to the error, null if absent 11822 * @param report in long form describing the error, null if absent 11823 * @param logFile to include in the report, null if none 11824 * @param crashInfo giving an application stack trace, null if absent 11825 */ 11826 public void addErrorToDropBox(String eventType, 11827 ProcessRecord process, String processName, ActivityRecord activity, 11828 ActivityRecord parent, String subject, 11829 final String report, final File logFile, 11830 final ApplicationErrorReport.CrashInfo crashInfo) { 11831 // NOTE -- this must never acquire the ActivityManagerService lock, 11832 // otherwise the watchdog may be prevented from resetting the system. 11833 11834 final String dropboxTag = processClass(process) + "_" + eventType; 11835 final DropBoxManager dbox = (DropBoxManager) 11836 mContext.getSystemService(Context.DROPBOX_SERVICE); 11837 11838 // Exit early if the dropbox isn't configured to accept this report type. 11839 if (dbox == null || !dbox.isTagEnabled(dropboxTag)) return; 11840 11841 final StringBuilder sb = new StringBuilder(1024); 11842 appendDropBoxProcessHeaders(process, processName, sb); 11843 if (activity != null) { 11844 sb.append("Activity: ").append(activity.shortComponentName).append("\n"); 11845 } 11846 if (parent != null && parent.app != null && parent.app.pid != process.pid) { 11847 sb.append("Parent-Process: ").append(parent.app.processName).append("\n"); 11848 } 11849 if (parent != null && parent != activity) { 11850 sb.append("Parent-Activity: ").append(parent.shortComponentName).append("\n"); 11851 } 11852 if (subject != null) { 11853 sb.append("Subject: ").append(subject).append("\n"); 11854 } 11855 sb.append("Build: ").append(Build.FINGERPRINT).append("\n"); 11856 if (Debug.isDebuggerConnected()) { 11857 sb.append("Debugger: Connected\n"); 11858 } 11859 sb.append("\n"); 11860 11861 // Do the rest in a worker thread to avoid blocking the caller on I/O 11862 // (After this point, we shouldn't access AMS internal data structures.) 11863 Thread worker = new Thread("Error dump: " + dropboxTag) { 11864 @Override 11865 public void run() { 11866 if (report != null) { 11867 sb.append(report); 11868 } 11869 if (logFile != null) { 11870 try { 11871 sb.append(FileUtils.readTextFile(logFile, DROPBOX_MAX_SIZE, 11872 "\n\n[[TRUNCATED]]")); 11873 } catch (IOException e) { 11874 Slog.e(TAG, "Error reading " + logFile, e); 11875 } 11876 } 11877 if (crashInfo != null && crashInfo.stackTrace != null) { 11878 sb.append(crashInfo.stackTrace); 11879 } 11880 11881 String setting = Settings.Global.ERROR_LOGCAT_PREFIX + dropboxTag; 11882 int lines = Settings.Global.getInt(mContext.getContentResolver(), setting, 0); 11883 if (lines > 0) { 11884 sb.append("\n"); 11885 11886 // Merge several logcat streams, and take the last N lines 11887 InputStreamReader input = null; 11888 try { 11889 java.lang.Process logcat = new ProcessBuilder("/system/bin/logcat", 11890 "-v", "time", "-b", "events", "-b", "system", "-b", "main", 11891 "-b", "crash", 11892 "-t", String.valueOf(lines)).redirectErrorStream(true).start(); 11893 11894 try { logcat.getOutputStream().close(); } catch (IOException e) {} 11895 try { logcat.getErrorStream().close(); } catch (IOException e) {} 11896 input = new InputStreamReader(logcat.getInputStream()); 11897 11898 int num; 11899 char[] buf = new char[8192]; 11900 while ((num = input.read(buf)) > 0) sb.append(buf, 0, num); 11901 } catch (IOException e) { 11902 Slog.e(TAG, "Error running logcat", e); 11903 } finally { 11904 if (input != null) try { input.close(); } catch (IOException e) {} 11905 } 11906 } 11907 11908 dbox.addText(dropboxTag, sb.toString()); 11909 } 11910 }; 11911 11912 if (process == null) { 11913 // If process is null, we are being called from some internal code 11914 // and may be about to die -- run this synchronously. 11915 worker.run(); 11916 } else { 11917 worker.start(); 11918 } 11919 } 11920 11921 /** 11922 * Bring up the "unexpected error" dialog box for a crashing app. 11923 * Deal with edge cases (intercepts from instrumented applications, 11924 * ActivityController, error intent receivers, that sort of thing). 11925 * @param r the application crashing 11926 * @param crashInfo describing the failure 11927 */ 11928 private void crashApplication(ProcessRecord r, ApplicationErrorReport.CrashInfo crashInfo) { 11929 long timeMillis = System.currentTimeMillis(); 11930 String shortMsg = crashInfo.exceptionClassName; 11931 String longMsg = crashInfo.exceptionMessage; 11932 String stackTrace = crashInfo.stackTrace; 11933 if (shortMsg != null && longMsg != null) { 11934 longMsg = shortMsg + ": " + longMsg; 11935 } else if (shortMsg != null) { 11936 longMsg = shortMsg; 11937 } 11938 11939 AppErrorResult result = new AppErrorResult(); 11940 synchronized (this) { 11941 if (mController != null) { 11942 try { 11943 String name = r != null ? r.processName : null; 11944 int pid = r != null ? r.pid : Binder.getCallingPid(); 11945 int uid = r != null ? r.info.uid : Binder.getCallingUid(); 11946 if (!mController.appCrashed(name, pid, 11947 shortMsg, longMsg, timeMillis, crashInfo.stackTrace)) { 11948 if ("1".equals(SystemProperties.get(SYSTEM_DEBUGGABLE, "0")) 11949 && "Native crash".equals(crashInfo.exceptionClassName)) { 11950 Slog.w(TAG, "Skip killing native crashed app " + name 11951 + "(" + pid + ") during testing"); 11952 } else { 11953 Slog.w(TAG, "Force-killing crashed app " + name 11954 + " at watcher's request"); 11955 if (r != null) { 11956 r.kill("crash", true); 11957 } else { 11958 // Huh. 11959 Process.killProcess(pid); 11960 Process.killProcessGroup(uid, pid); 11961 } 11962 } 11963 return; 11964 } 11965 } catch (RemoteException e) { 11966 mController = null; 11967 Watchdog.getInstance().setActivityController(null); 11968 } 11969 } 11970 11971 final long origId = Binder.clearCallingIdentity(); 11972 11973 // If this process is running instrumentation, finish it. 11974 if (r != null && r.instrumentationClass != null) { 11975 Slog.w(TAG, "Error in app " + r.processName 11976 + " running instrumentation " + r.instrumentationClass + ":"); 11977 if (shortMsg != null) Slog.w(TAG, " " + shortMsg); 11978 if (longMsg != null) Slog.w(TAG, " " + longMsg); 11979 Bundle info = new Bundle(); 11980 info.putString("shortMsg", shortMsg); 11981 info.putString("longMsg", longMsg); 11982 finishInstrumentationLocked(r, Activity.RESULT_CANCELED, info); 11983 Binder.restoreCallingIdentity(origId); 11984 return; 11985 } 11986 11987 // If we can't identify the process or it's already exceeded its crash quota, 11988 // quit right away without showing a crash dialog. 11989 if (r == null || !makeAppCrashingLocked(r, shortMsg, longMsg, stackTrace)) { 11990 Binder.restoreCallingIdentity(origId); 11991 return; 11992 } 11993 11994 Message msg = Message.obtain(); 11995 msg.what = SHOW_ERROR_MSG; 11996 HashMap data = new HashMap(); 11997 data.put("result", result); 11998 data.put("app", r); 11999 msg.obj = data; 12000 mHandler.sendMessage(msg); 12001 12002 Binder.restoreCallingIdentity(origId); 12003 } 12004 12005 int res = result.get(); 12006 12007 Intent appErrorIntent = null; 12008 synchronized (this) { 12009 if (r != null && !r.isolated) { 12010 // XXX Can't keep track of crash time for isolated processes, 12011 // since they don't have a persistent identity. 12012 mProcessCrashTimes.put(r.info.processName, r.uid, 12013 SystemClock.uptimeMillis()); 12014 } 12015 if (res == AppErrorDialog.FORCE_QUIT_AND_REPORT) { 12016 appErrorIntent = createAppErrorIntentLocked(r, timeMillis, crashInfo); 12017 } 12018 } 12019 12020 if (appErrorIntent != null) { 12021 try { 12022 mContext.startActivityAsUser(appErrorIntent, new UserHandle(r.userId)); 12023 } catch (ActivityNotFoundException e) { 12024 Slog.w(TAG, "bug report receiver dissappeared", e); 12025 } 12026 } 12027 } 12028 12029 Intent createAppErrorIntentLocked(ProcessRecord r, 12030 long timeMillis, ApplicationErrorReport.CrashInfo crashInfo) { 12031 ApplicationErrorReport report = createAppErrorReportLocked(r, timeMillis, crashInfo); 12032 if (report == null) { 12033 return null; 12034 } 12035 Intent result = new Intent(Intent.ACTION_APP_ERROR); 12036 result.setComponent(r.errorReportReceiver); 12037 result.putExtra(Intent.EXTRA_BUG_REPORT, report); 12038 result.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK); 12039 return result; 12040 } 12041 12042 private ApplicationErrorReport createAppErrorReportLocked(ProcessRecord r, 12043 long timeMillis, ApplicationErrorReport.CrashInfo crashInfo) { 12044 if (r.errorReportReceiver == null) { 12045 return null; 12046 } 12047 12048 if (!r.crashing && !r.notResponding && !r.forceCrashReport) { 12049 return null; 12050 } 12051 12052 ApplicationErrorReport report = new ApplicationErrorReport(); 12053 report.packageName = r.info.packageName; 12054 report.installerPackageName = r.errorReportReceiver.getPackageName(); 12055 report.processName = r.processName; 12056 report.time = timeMillis; 12057 report.systemApp = (r.info.flags & ApplicationInfo.FLAG_SYSTEM) != 0; 12058 12059 if (r.crashing || r.forceCrashReport) { 12060 report.type = ApplicationErrorReport.TYPE_CRASH; 12061 report.crashInfo = crashInfo; 12062 } else if (r.notResponding) { 12063 report.type = ApplicationErrorReport.TYPE_ANR; 12064 report.anrInfo = new ApplicationErrorReport.AnrInfo(); 12065 12066 report.anrInfo.activity = r.notRespondingReport.tag; 12067 report.anrInfo.cause = r.notRespondingReport.shortMsg; 12068 report.anrInfo.info = r.notRespondingReport.longMsg; 12069 } 12070 12071 return report; 12072 } 12073 12074 public List<ActivityManager.ProcessErrorStateInfo> getProcessesInErrorState() { 12075 enforceNotIsolatedCaller("getProcessesInErrorState"); 12076 // assume our apps are happy - lazy create the list 12077 List<ActivityManager.ProcessErrorStateInfo> errList = null; 12078 12079 final boolean allUsers = ActivityManager.checkUidPermission(INTERACT_ACROSS_USERS_FULL, 12080 Binder.getCallingUid()) == PackageManager.PERMISSION_GRANTED; 12081 int userId = UserHandle.getUserId(Binder.getCallingUid()); 12082 12083 synchronized (this) { 12084 12085 // iterate across all processes 12086 for (int i=mLruProcesses.size()-1; i>=0; i--) { 12087 ProcessRecord app = mLruProcesses.get(i); 12088 if (!allUsers && app.userId != userId) { 12089 continue; 12090 } 12091 if ((app.thread != null) && (app.crashing || app.notResponding)) { 12092 // This one's in trouble, so we'll generate a report for it 12093 // crashes are higher priority (in case there's a crash *and* an anr) 12094 ActivityManager.ProcessErrorStateInfo report = null; 12095 if (app.crashing) { 12096 report = app.crashingReport; 12097 } else if (app.notResponding) { 12098 report = app.notRespondingReport; 12099 } 12100 12101 if (report != null) { 12102 if (errList == null) { 12103 errList = new ArrayList<ActivityManager.ProcessErrorStateInfo>(1); 12104 } 12105 errList.add(report); 12106 } else { 12107 Slog.w(TAG, "Missing app error report, app = " + app.processName + 12108 " crashing = " + app.crashing + 12109 " notResponding = " + app.notResponding); 12110 } 12111 } 12112 } 12113 } 12114 12115 return errList; 12116 } 12117 12118 static int procStateToImportance(int procState, int memAdj, 12119 ActivityManager.RunningAppProcessInfo currApp) { 12120 int imp = ActivityManager.RunningAppProcessInfo.procStateToImportance(procState); 12121 if (imp == ActivityManager.RunningAppProcessInfo.IMPORTANCE_BACKGROUND) { 12122 currApp.lru = memAdj; 12123 } else { 12124 currApp.lru = 0; 12125 } 12126 return imp; 12127 } 12128 12129 private void fillInProcMemInfo(ProcessRecord app, 12130 ActivityManager.RunningAppProcessInfo outInfo) { 12131 outInfo.pid = app.pid; 12132 outInfo.uid = app.info.uid; 12133 if (mHeavyWeightProcess == app) { 12134 outInfo.flags |= ActivityManager.RunningAppProcessInfo.FLAG_CANT_SAVE_STATE; 12135 } 12136 if (app.persistent) { 12137 outInfo.flags |= ActivityManager.RunningAppProcessInfo.FLAG_PERSISTENT; 12138 } 12139 if (app.activities.size() > 0) { 12140 outInfo.flags |= ActivityManager.RunningAppProcessInfo.FLAG_HAS_ACTIVITIES; 12141 } 12142 outInfo.lastTrimLevel = app.trimMemoryLevel; 12143 int adj = app.curAdj; 12144 int procState = app.curProcState; 12145 outInfo.importance = procStateToImportance(procState, adj, outInfo); 12146 outInfo.importanceReasonCode = app.adjTypeCode; 12147 outInfo.processState = app.curProcState; 12148 } 12149 12150 public List<ActivityManager.RunningAppProcessInfo> getRunningAppProcesses() { 12151 enforceNotIsolatedCaller("getRunningAppProcesses"); 12152 // Lazy instantiation of list 12153 List<ActivityManager.RunningAppProcessInfo> runList = null; 12154 final boolean allUsers = ActivityManager.checkUidPermission(INTERACT_ACROSS_USERS_FULL, 12155 Binder.getCallingUid()) == PackageManager.PERMISSION_GRANTED; 12156 int userId = UserHandle.getUserId(Binder.getCallingUid()); 12157 synchronized (this) { 12158 // Iterate across all processes 12159 for (int i=mLruProcesses.size()-1; i>=0; i--) { 12160 ProcessRecord app = mLruProcesses.get(i); 12161 if (!allUsers && app.userId != userId) { 12162 continue; 12163 } 12164 if ((app.thread != null) && (!app.crashing && !app.notResponding)) { 12165 // Generate process state info for running application 12166 ActivityManager.RunningAppProcessInfo currApp = 12167 new ActivityManager.RunningAppProcessInfo(app.processName, 12168 app.pid, app.getPackageList()); 12169 fillInProcMemInfo(app, currApp); 12170 if (app.adjSource instanceof ProcessRecord) { 12171 currApp.importanceReasonPid = ((ProcessRecord)app.adjSource).pid; 12172 currApp.importanceReasonImportance = 12173 ActivityManager.RunningAppProcessInfo.procStateToImportance( 12174 app.adjSourceProcState); 12175 } else if (app.adjSource instanceof ActivityRecord) { 12176 ActivityRecord r = (ActivityRecord)app.adjSource; 12177 if (r.app != null) currApp.importanceReasonPid = r.app.pid; 12178 } 12179 if (app.adjTarget instanceof ComponentName) { 12180 currApp.importanceReasonComponent = (ComponentName)app.adjTarget; 12181 } 12182 //Slog.v(TAG, "Proc " + app.processName + ": imp=" + currApp.importance 12183 // + " lru=" + currApp.lru); 12184 if (runList == null) { 12185 runList = new ArrayList<ActivityManager.RunningAppProcessInfo>(); 12186 } 12187 runList.add(currApp); 12188 } 12189 } 12190 } 12191 return runList; 12192 } 12193 12194 public List<ApplicationInfo> getRunningExternalApplications() { 12195 enforceNotIsolatedCaller("getRunningExternalApplications"); 12196 List<ActivityManager.RunningAppProcessInfo> runningApps = getRunningAppProcesses(); 12197 List<ApplicationInfo> retList = new ArrayList<ApplicationInfo>(); 12198 if (runningApps != null && runningApps.size() > 0) { 12199 Set<String> extList = new HashSet<String>(); 12200 for (ActivityManager.RunningAppProcessInfo app : runningApps) { 12201 if (app.pkgList != null) { 12202 for (String pkg : app.pkgList) { 12203 extList.add(pkg); 12204 } 12205 } 12206 } 12207 IPackageManager pm = AppGlobals.getPackageManager(); 12208 for (String pkg : extList) { 12209 try { 12210 ApplicationInfo info = pm.getApplicationInfo(pkg, 0, UserHandle.getCallingUserId()); 12211 if ((info.flags & ApplicationInfo.FLAG_EXTERNAL_STORAGE) != 0) { 12212 retList.add(info); 12213 } 12214 } catch (RemoteException e) { 12215 } 12216 } 12217 } 12218 return retList; 12219 } 12220 12221 @Override 12222 public void getMyMemoryState(ActivityManager.RunningAppProcessInfo outInfo) { 12223 enforceNotIsolatedCaller("getMyMemoryState"); 12224 synchronized (this) { 12225 ProcessRecord proc; 12226 synchronized (mPidsSelfLocked) { 12227 proc = mPidsSelfLocked.get(Binder.getCallingPid()); 12228 } 12229 fillInProcMemInfo(proc, outInfo); 12230 } 12231 } 12232 12233 @Override 12234 protected void dump(FileDescriptor fd, PrintWriter pw, String[] args) { 12235 if (checkCallingPermission(android.Manifest.permission.DUMP) 12236 != PackageManager.PERMISSION_GRANTED) { 12237 pw.println("Permission Denial: can't dump ActivityManager from from pid=" 12238 + Binder.getCallingPid() 12239 + ", uid=" + Binder.getCallingUid() 12240 + " without permission " 12241 + android.Manifest.permission.DUMP); 12242 return; 12243 } 12244 12245 boolean dumpAll = false; 12246 boolean dumpClient = false; 12247 String dumpPackage = null; 12248 12249 int opti = 0; 12250 while (opti < args.length) { 12251 String opt = args[opti]; 12252 if (opt == null || opt.length() <= 0 || opt.charAt(0) != '-') { 12253 break; 12254 } 12255 opti++; 12256 if ("-a".equals(opt)) { 12257 dumpAll = true; 12258 } else if ("-c".equals(opt)) { 12259 dumpClient = true; 12260 } else if ("-h".equals(opt)) { 12261 pw.println("Activity manager dump options:"); 12262 pw.println(" [-a] [-c] [-h] [cmd] ..."); 12263 pw.println(" cmd may be one of:"); 12264 pw.println(" a[ctivities]: activity stack state"); 12265 pw.println(" r[recents]: recent activities state"); 12266 pw.println(" b[roadcasts] [PACKAGE_NAME] [history [-s]]: broadcast state"); 12267 pw.println(" i[ntents] [PACKAGE_NAME]: pending intent state"); 12268 pw.println(" p[rocesses] [PACKAGE_NAME]: process state"); 12269 pw.println(" o[om]: out of memory management"); 12270 pw.println(" prov[iders] [COMP_SPEC ...]: content provider state"); 12271 pw.println(" provider [COMP_SPEC]: provider client-side state"); 12272 pw.println(" s[ervices] [COMP_SPEC ...]: service state"); 12273 pw.println(" service [COMP_SPEC]: service client-side state"); 12274 pw.println(" package [PACKAGE_NAME]: all state related to given package"); 12275 pw.println(" all: dump all activities"); 12276 pw.println(" top: dump the top activity"); 12277 pw.println(" write: write all pending state to storage"); 12278 pw.println(" cmd may also be a COMP_SPEC to dump activities."); 12279 pw.println(" COMP_SPEC may be a component name (com.foo/.myApp),"); 12280 pw.println(" a partial substring in a component name, a"); 12281 pw.println(" hex object identifier."); 12282 pw.println(" -a: include all available server state."); 12283 pw.println(" -c: include client state."); 12284 return; 12285 } else { 12286 pw.println("Unknown argument: " + opt + "; use -h for help"); 12287 } 12288 } 12289 12290 long origId = Binder.clearCallingIdentity(); 12291 boolean more = false; 12292 // Is the caller requesting to dump a particular piece of data? 12293 if (opti < args.length) { 12294 String cmd = args[opti]; 12295 opti++; 12296 if ("activities".equals(cmd) || "a".equals(cmd)) { 12297 synchronized (this) { 12298 dumpActivitiesLocked(fd, pw, args, opti, true, dumpClient, null); 12299 } 12300 } else if ("recents".equals(cmd) || "r".equals(cmd)) { 12301 synchronized (this) { 12302 dumpRecentsLocked(fd, pw, args, opti, true, null); 12303 } 12304 } else if ("broadcasts".equals(cmd) || "b".equals(cmd)) { 12305 String[] newArgs; 12306 String name; 12307 if (opti >= args.length) { 12308 name = null; 12309 newArgs = EMPTY_STRING_ARRAY; 12310 } else { 12311 name = args[opti]; 12312 opti++; 12313 newArgs = new String[args.length - opti]; 12314 if (args.length > 2) System.arraycopy(args, opti, newArgs, 0, 12315 args.length - opti); 12316 } 12317 synchronized (this) { 12318 dumpBroadcastsLocked(fd, pw, args, opti, true, name); 12319 } 12320 } else if ("intents".equals(cmd) || "i".equals(cmd)) { 12321 String[] newArgs; 12322 String name; 12323 if (opti >= args.length) { 12324 name = null; 12325 newArgs = EMPTY_STRING_ARRAY; 12326 } else { 12327 name = args[opti]; 12328 opti++; 12329 newArgs = new String[args.length - opti]; 12330 if (args.length > 2) System.arraycopy(args, opti, newArgs, 0, 12331 args.length - opti); 12332 } 12333 synchronized (this) { 12334 dumpPendingIntentsLocked(fd, pw, args, opti, true, name); 12335 } 12336 } else if ("processes".equals(cmd) || "p".equals(cmd)) { 12337 String[] newArgs; 12338 String name; 12339 if (opti >= args.length) { 12340 name = null; 12341 newArgs = EMPTY_STRING_ARRAY; 12342 } else { 12343 name = args[opti]; 12344 opti++; 12345 newArgs = new String[args.length - opti]; 12346 if (args.length > 2) System.arraycopy(args, opti, newArgs, 0, 12347 args.length - opti); 12348 } 12349 synchronized (this) { 12350 dumpProcessesLocked(fd, pw, args, opti, true, name); 12351 } 12352 } else if ("oom".equals(cmd) || "o".equals(cmd)) { 12353 synchronized (this) { 12354 dumpOomLocked(fd, pw, args, opti, true); 12355 } 12356 } else if ("provider".equals(cmd)) { 12357 String[] newArgs; 12358 String name; 12359 if (opti >= args.length) { 12360 name = null; 12361 newArgs = EMPTY_STRING_ARRAY; 12362 } else { 12363 name = args[opti]; 12364 opti++; 12365 newArgs = new String[args.length - opti]; 12366 if (args.length > 2) System.arraycopy(args, opti, newArgs, 0, args.length - opti); 12367 } 12368 if (!dumpProvider(fd, pw, name, newArgs, 0, dumpAll)) { 12369 pw.println("No providers match: " + name); 12370 pw.println("Use -h for help."); 12371 } 12372 } else if ("providers".equals(cmd) || "prov".equals(cmd)) { 12373 synchronized (this) { 12374 dumpProvidersLocked(fd, pw, args, opti, true, null); 12375 } 12376 } else if ("service".equals(cmd)) { 12377 String[] newArgs; 12378 String name; 12379 if (opti >= args.length) { 12380 name = null; 12381 newArgs = EMPTY_STRING_ARRAY; 12382 } else { 12383 name = args[opti]; 12384 opti++; 12385 newArgs = new String[args.length - opti]; 12386 if (args.length > 2) System.arraycopy(args, opti, newArgs, 0, 12387 args.length - opti); 12388 } 12389 if (!mServices.dumpService(fd, pw, name, newArgs, 0, dumpAll)) { 12390 pw.println("No services match: " + name); 12391 pw.println("Use -h for help."); 12392 } 12393 } else if ("package".equals(cmd)) { 12394 String[] newArgs; 12395 if (opti >= args.length) { 12396 pw.println("package: no package name specified"); 12397 pw.println("Use -h for help."); 12398 } else { 12399 dumpPackage = args[opti]; 12400 opti++; 12401 newArgs = new String[args.length - opti]; 12402 if (args.length > 2) System.arraycopy(args, opti, newArgs, 0, 12403 args.length - opti); 12404 args = newArgs; 12405 opti = 0; 12406 more = true; 12407 } 12408 } else if ("services".equals(cmd) || "s".equals(cmd)) { 12409 synchronized (this) { 12410 mServices.dumpServicesLocked(fd, pw, args, opti, true, dumpClient, null); 12411 } 12412 } else if ("write".equals(cmd)) { 12413 mTaskPersister.flush(); 12414 pw.println("All tasks persisted."); 12415 return; 12416 } else { 12417 // Dumping a single activity? 12418 if (!dumpActivity(fd, pw, cmd, args, opti, dumpAll)) { 12419 pw.println("Bad activity command, or no activities match: " + cmd); 12420 pw.println("Use -h for help."); 12421 } 12422 } 12423 if (!more) { 12424 Binder.restoreCallingIdentity(origId); 12425 return; 12426 } 12427 } 12428 12429 // No piece of data specified, dump everything. 12430 synchronized (this) { 12431 dumpPendingIntentsLocked(fd, pw, args, opti, dumpAll, dumpPackage); 12432 pw.println(); 12433 if (dumpAll) { 12434 pw.println("-------------------------------------------------------------------------------"); 12435 } 12436 dumpBroadcastsLocked(fd, pw, args, opti, dumpAll, dumpPackage); 12437 pw.println(); 12438 if (dumpAll) { 12439 pw.println("-------------------------------------------------------------------------------"); 12440 } 12441 dumpProvidersLocked(fd, pw, args, opti, dumpAll, dumpPackage); 12442 pw.println(); 12443 if (dumpAll) { 12444 pw.println("-------------------------------------------------------------------------------"); 12445 } 12446 mServices.dumpServicesLocked(fd, pw, args, opti, dumpAll, dumpClient, dumpPackage); 12447 pw.println(); 12448 if (dumpAll) { 12449 pw.println("-------------------------------------------------------------------------------"); 12450 } 12451 dumpRecentsLocked(fd, pw, args, opti, dumpAll, dumpPackage); 12452 pw.println(); 12453 if (dumpAll) { 12454 pw.println("-------------------------------------------------------------------------------"); 12455 } 12456 dumpActivitiesLocked(fd, pw, args, opti, dumpAll, dumpClient, dumpPackage); 12457 pw.println(); 12458 if (dumpAll) { 12459 pw.println("-------------------------------------------------------------------------------"); 12460 } 12461 dumpProcessesLocked(fd, pw, args, opti, dumpAll, dumpPackage); 12462 } 12463 Binder.restoreCallingIdentity(origId); 12464 } 12465 12466 void dumpActivitiesLocked(FileDescriptor fd, PrintWriter pw, String[] args, 12467 int opti, boolean dumpAll, boolean dumpClient, String dumpPackage) { 12468 pw.println("ACTIVITY MANAGER ACTIVITIES (dumpsys activity activities)"); 12469 12470 boolean printedAnything = mStackSupervisor.dumpActivitiesLocked(fd, pw, dumpAll, dumpClient, 12471 dumpPackage); 12472 boolean needSep = printedAnything; 12473 12474 boolean printed = ActivityStackSupervisor.printThisActivity(pw, mFocusedActivity, 12475 dumpPackage, needSep, " mFocusedActivity: "); 12476 if (printed) { 12477 printedAnything = true; 12478 needSep = false; 12479 } 12480 12481 if (dumpPackage == null) { 12482 if (needSep) { 12483 pw.println(); 12484 } 12485 needSep = true; 12486 printedAnything = true; 12487 mStackSupervisor.dump(pw, " "); 12488 } 12489 12490 if (!printedAnything) { 12491 pw.println(" (nothing)"); 12492 } 12493 } 12494 12495 void dumpRecentsLocked(FileDescriptor fd, PrintWriter pw, String[] args, 12496 int opti, boolean dumpAll, String dumpPackage) { 12497 pw.println("ACTIVITY MANAGER RECENT TASKS (dumpsys activity recents)"); 12498 12499 boolean printedAnything = false; 12500 12501 if (mRecentTasks != null && mRecentTasks.size() > 0) { 12502 boolean printedHeader = false; 12503 12504 final int N = mRecentTasks.size(); 12505 for (int i=0; i<N; i++) { 12506 TaskRecord tr = mRecentTasks.get(i); 12507 if (dumpPackage != null) { 12508 if (tr.realActivity == null || 12509 !dumpPackage.equals(tr.realActivity)) { 12510 continue; 12511 } 12512 } 12513 if (!printedHeader) { 12514 pw.println(" Recent tasks:"); 12515 printedHeader = true; 12516 printedAnything = true; 12517 } 12518 pw.print(" * Recent #"); pw.print(i); pw.print(": "); 12519 pw.println(tr); 12520 if (dumpAll) { 12521 mRecentTasks.get(i).dump(pw, " "); 12522 } 12523 } 12524 } 12525 12526 if (!printedAnything) { 12527 pw.println(" (nothing)"); 12528 } 12529 } 12530 12531 void dumpProcessesLocked(FileDescriptor fd, PrintWriter pw, String[] args, 12532 int opti, boolean dumpAll, String dumpPackage) { 12533 boolean needSep = false; 12534 boolean printedAnything = false; 12535 int numPers = 0; 12536 12537 pw.println("ACTIVITY MANAGER RUNNING PROCESSES (dumpsys activity processes)"); 12538 12539 if (dumpAll) { 12540 final int NP = mProcessNames.getMap().size(); 12541 for (int ip=0; ip<NP; ip++) { 12542 SparseArray<ProcessRecord> procs = mProcessNames.getMap().valueAt(ip); 12543 final int NA = procs.size(); 12544 for (int ia=0; ia<NA; ia++) { 12545 ProcessRecord r = procs.valueAt(ia); 12546 if (dumpPackage != null && !r.pkgList.containsKey(dumpPackage)) { 12547 continue; 12548 } 12549 if (!needSep) { 12550 pw.println(" All known processes:"); 12551 needSep = true; 12552 printedAnything = true; 12553 } 12554 pw.print(r.persistent ? " *PERS*" : " *APP*"); 12555 pw.print(" UID "); pw.print(procs.keyAt(ia)); 12556 pw.print(" "); pw.println(r); 12557 r.dump(pw, " "); 12558 if (r.persistent) { 12559 numPers++; 12560 } 12561 } 12562 } 12563 } 12564 12565 if (mIsolatedProcesses.size() > 0) { 12566 boolean printed = false; 12567 for (int i=0; i<mIsolatedProcesses.size(); i++) { 12568 ProcessRecord r = mIsolatedProcesses.valueAt(i); 12569 if (dumpPackage != null && !r.pkgList.containsKey(dumpPackage)) { 12570 continue; 12571 } 12572 if (!printed) { 12573 if (needSep) { 12574 pw.println(); 12575 } 12576 pw.println(" Isolated process list (sorted by uid):"); 12577 printedAnything = true; 12578 printed = true; 12579 needSep = true; 12580 } 12581 pw.println(String.format("%sIsolated #%2d: %s", 12582 " ", i, r.toString())); 12583 } 12584 } 12585 12586 if (mLruProcesses.size() > 0) { 12587 if (needSep) { 12588 pw.println(); 12589 } 12590 pw.print(" Process LRU list (sorted by oom_adj, "); pw.print(mLruProcesses.size()); 12591 pw.print(" total, non-act at "); 12592 pw.print(mLruProcesses.size()-mLruProcessActivityStart); 12593 pw.print(", non-svc at "); 12594 pw.print(mLruProcesses.size()-mLruProcessServiceStart); 12595 pw.println("):"); 12596 dumpProcessOomList(pw, this, mLruProcesses, " ", "Proc", "PERS", false, dumpPackage); 12597 needSep = true; 12598 printedAnything = true; 12599 } 12600 12601 if (dumpAll || dumpPackage != null) { 12602 synchronized (mPidsSelfLocked) { 12603 boolean printed = false; 12604 for (int i=0; i<mPidsSelfLocked.size(); i++) { 12605 ProcessRecord r = mPidsSelfLocked.valueAt(i); 12606 if (dumpPackage != null && !r.pkgList.containsKey(dumpPackage)) { 12607 continue; 12608 } 12609 if (!printed) { 12610 if (needSep) pw.println(); 12611 needSep = true; 12612 pw.println(" PID mappings:"); 12613 printed = true; 12614 printedAnything = true; 12615 } 12616 pw.print(" PID #"); pw.print(mPidsSelfLocked.keyAt(i)); 12617 pw.print(": "); pw.println(mPidsSelfLocked.valueAt(i)); 12618 } 12619 } 12620 } 12621 12622 if (mForegroundProcesses.size() > 0) { 12623 synchronized (mPidsSelfLocked) { 12624 boolean printed = false; 12625 for (int i=0; i<mForegroundProcesses.size(); i++) { 12626 ProcessRecord r = mPidsSelfLocked.get( 12627 mForegroundProcesses.valueAt(i).pid); 12628 if (dumpPackage != null && (r == null 12629 || !r.pkgList.containsKey(dumpPackage))) { 12630 continue; 12631 } 12632 if (!printed) { 12633 if (needSep) pw.println(); 12634 needSep = true; 12635 pw.println(" Foreground Processes:"); 12636 printed = true; 12637 printedAnything = true; 12638 } 12639 pw.print(" PID #"); pw.print(mForegroundProcesses.keyAt(i)); 12640 pw.print(": "); pw.println(mForegroundProcesses.valueAt(i)); 12641 } 12642 } 12643 } 12644 12645 if (mPersistentStartingProcesses.size() > 0) { 12646 if (needSep) pw.println(); 12647 needSep = true; 12648 printedAnything = true; 12649 pw.println(" Persisent processes that are starting:"); 12650 dumpProcessList(pw, this, mPersistentStartingProcesses, " ", 12651 "Starting Norm", "Restarting PERS", dumpPackage); 12652 } 12653 12654 if (mRemovedProcesses.size() > 0) { 12655 if (needSep) pw.println(); 12656 needSep = true; 12657 printedAnything = true; 12658 pw.println(" Processes that are being removed:"); 12659 dumpProcessList(pw, this, mRemovedProcesses, " ", 12660 "Removed Norm", "Removed PERS", dumpPackage); 12661 } 12662 12663 if (mProcessesOnHold.size() > 0) { 12664 if (needSep) pw.println(); 12665 needSep = true; 12666 printedAnything = true; 12667 pw.println(" Processes that are on old until the system is ready:"); 12668 dumpProcessList(pw, this, mProcessesOnHold, " ", 12669 "OnHold Norm", "OnHold PERS", dumpPackage); 12670 } 12671 12672 needSep = dumpProcessesToGc(fd, pw, args, opti, needSep, dumpAll, dumpPackage); 12673 12674 if (mProcessCrashTimes.getMap().size() > 0) { 12675 boolean printed = false; 12676 long now = SystemClock.uptimeMillis(); 12677 final ArrayMap<String, SparseArray<Long>> pmap = mProcessCrashTimes.getMap(); 12678 final int NP = pmap.size(); 12679 for (int ip=0; ip<NP; ip++) { 12680 String pname = pmap.keyAt(ip); 12681 SparseArray<Long> uids = pmap.valueAt(ip); 12682 final int N = uids.size(); 12683 for (int i=0; i<N; i++) { 12684 int puid = uids.keyAt(i); 12685 ProcessRecord r = mProcessNames.get(pname, puid); 12686 if (dumpPackage != null && (r == null 12687 || !r.pkgList.containsKey(dumpPackage))) { 12688 continue; 12689 } 12690 if (!printed) { 12691 if (needSep) pw.println(); 12692 needSep = true; 12693 pw.println(" Time since processes crashed:"); 12694 printed = true; 12695 printedAnything = true; 12696 } 12697 pw.print(" Process "); pw.print(pname); 12698 pw.print(" uid "); pw.print(puid); 12699 pw.print(": last crashed "); 12700 TimeUtils.formatDuration(now-uids.valueAt(i), pw); 12701 pw.println(" ago"); 12702 } 12703 } 12704 } 12705 12706 if (mBadProcesses.getMap().size() > 0) { 12707 boolean printed = false; 12708 final ArrayMap<String, SparseArray<BadProcessInfo>> pmap = mBadProcesses.getMap(); 12709 final int NP = pmap.size(); 12710 for (int ip=0; ip<NP; ip++) { 12711 String pname = pmap.keyAt(ip); 12712 SparseArray<BadProcessInfo> uids = pmap.valueAt(ip); 12713 final int N = uids.size(); 12714 for (int i=0; i<N; i++) { 12715 int puid = uids.keyAt(i); 12716 ProcessRecord r = mProcessNames.get(pname, puid); 12717 if (dumpPackage != null && (r == null 12718 || !r.pkgList.containsKey(dumpPackage))) { 12719 continue; 12720 } 12721 if (!printed) { 12722 if (needSep) pw.println(); 12723 needSep = true; 12724 pw.println(" Bad processes:"); 12725 printedAnything = true; 12726 } 12727 BadProcessInfo info = uids.valueAt(i); 12728 pw.print(" Bad process "); pw.print(pname); 12729 pw.print(" uid "); pw.print(puid); 12730 pw.print(": crashed at time "); pw.println(info.time); 12731 if (info.shortMsg != null) { 12732 pw.print(" Short msg: "); pw.println(info.shortMsg); 12733 } 12734 if (info.longMsg != null) { 12735 pw.print(" Long msg: "); pw.println(info.longMsg); 12736 } 12737 if (info.stack != null) { 12738 pw.println(" Stack:"); 12739 int lastPos = 0; 12740 for (int pos=0; pos<info.stack.length(); pos++) { 12741 if (info.stack.charAt(pos) == '\n') { 12742 pw.print(" "); 12743 pw.write(info.stack, lastPos, pos-lastPos); 12744 pw.println(); 12745 lastPos = pos+1; 12746 } 12747 } 12748 if (lastPos < info.stack.length()) { 12749 pw.print(" "); 12750 pw.write(info.stack, lastPos, info.stack.length()-lastPos); 12751 pw.println(); 12752 } 12753 } 12754 } 12755 } 12756 } 12757 12758 if (dumpPackage == null) { 12759 pw.println(); 12760 needSep = false; 12761 pw.println(" mStartedUsers:"); 12762 for (int i=0; i<mStartedUsers.size(); i++) { 12763 UserStartedState uss = mStartedUsers.valueAt(i); 12764 pw.print(" User #"); pw.print(uss.mHandle.getIdentifier()); 12765 pw.print(": "); uss.dump("", pw); 12766 } 12767 pw.print(" mStartedUserArray: ["); 12768 for (int i=0; i<mStartedUserArray.length; i++) { 12769 if (i > 0) pw.print(", "); 12770 pw.print(mStartedUserArray[i]); 12771 } 12772 pw.println("]"); 12773 pw.print(" mUserLru: ["); 12774 for (int i=0; i<mUserLru.size(); i++) { 12775 if (i > 0) pw.print(", "); 12776 pw.print(mUserLru.get(i)); 12777 } 12778 pw.println("]"); 12779 if (dumpAll) { 12780 pw.print(" mStartedUserArray: "); pw.println(Arrays.toString(mStartedUserArray)); 12781 } 12782 synchronized (mUserProfileGroupIdsSelfLocked) { 12783 if (mUserProfileGroupIdsSelfLocked.size() > 0) { 12784 pw.println(" mUserProfileGroupIds:"); 12785 for (int i=0; i<mUserProfileGroupIdsSelfLocked.size(); i++) { 12786 pw.print(" User #"); 12787 pw.print(mUserProfileGroupIdsSelfLocked.keyAt(i)); 12788 pw.print(" -> profile #"); 12789 pw.println(mUserProfileGroupIdsSelfLocked.valueAt(i)); 12790 } 12791 } 12792 } 12793 } 12794 if (mHomeProcess != null && (dumpPackage == null 12795 || mHomeProcess.pkgList.containsKey(dumpPackage))) { 12796 if (needSep) { 12797 pw.println(); 12798 needSep = false; 12799 } 12800 pw.println(" mHomeProcess: " + mHomeProcess); 12801 } 12802 if (mPreviousProcess != null && (dumpPackage == null 12803 || mPreviousProcess.pkgList.containsKey(dumpPackage))) { 12804 if (needSep) { 12805 pw.println(); 12806 needSep = false; 12807 } 12808 pw.println(" mPreviousProcess: " + mPreviousProcess); 12809 } 12810 if (dumpAll) { 12811 StringBuilder sb = new StringBuilder(128); 12812 sb.append(" mPreviousProcessVisibleTime: "); 12813 TimeUtils.formatDuration(mPreviousProcessVisibleTime, sb); 12814 pw.println(sb); 12815 } 12816 if (mHeavyWeightProcess != null && (dumpPackage == null 12817 || mHeavyWeightProcess.pkgList.containsKey(dumpPackage))) { 12818 if (needSep) { 12819 pw.println(); 12820 needSep = false; 12821 } 12822 pw.println(" mHeavyWeightProcess: " + mHeavyWeightProcess); 12823 } 12824 if (dumpPackage == null) { 12825 pw.println(" mConfiguration: " + mConfiguration); 12826 } 12827 if (dumpAll) { 12828 pw.println(" mConfigWillChange: " + getFocusedStack().mConfigWillChange); 12829 if (mCompatModePackages.getPackages().size() > 0) { 12830 boolean printed = false; 12831 for (Map.Entry<String, Integer> entry 12832 : mCompatModePackages.getPackages().entrySet()) { 12833 String pkg = entry.getKey(); 12834 int mode = entry.getValue(); 12835 if (dumpPackage != null && !dumpPackage.equals(pkg)) { 12836 continue; 12837 } 12838 if (!printed) { 12839 pw.println(" mScreenCompatPackages:"); 12840 printed = true; 12841 } 12842 pw.print(" "); pw.print(pkg); pw.print(": "); 12843 pw.print(mode); pw.println(); 12844 } 12845 } 12846 } 12847 if (dumpPackage == null) { 12848 if (mSleeping || mWentToSleep || mLockScreenShown != LOCK_SCREEN_HIDDEN) { 12849 pw.println(" mSleeping=" + mSleeping + " mWentToSleep=" + mWentToSleep 12850 + " mLockScreenShown " + lockScreenShownToString()); 12851 } 12852 if (mShuttingDown || mRunningVoice) { 12853 pw.print(" mShuttingDown=" + mShuttingDown + " mRunningVoice=" + mRunningVoice); 12854 } 12855 } 12856 if (mDebugApp != null || mOrigDebugApp != null || mDebugTransient 12857 || mOrigWaitForDebugger) { 12858 if (dumpPackage == null || dumpPackage.equals(mDebugApp) 12859 || dumpPackage.equals(mOrigDebugApp)) { 12860 if (needSep) { 12861 pw.println(); 12862 needSep = false; 12863 } 12864 pw.println(" mDebugApp=" + mDebugApp + "/orig=" + mOrigDebugApp 12865 + " mDebugTransient=" + mDebugTransient 12866 + " mOrigWaitForDebugger=" + mOrigWaitForDebugger); 12867 } 12868 } 12869 if (mOpenGlTraceApp != null) { 12870 if (dumpPackage == null || dumpPackage.equals(mOpenGlTraceApp)) { 12871 if (needSep) { 12872 pw.println(); 12873 needSep = false; 12874 } 12875 pw.println(" mOpenGlTraceApp=" + mOpenGlTraceApp); 12876 } 12877 } 12878 if (mProfileApp != null || mProfileProc != null || mProfileFile != null 12879 || mProfileFd != null) { 12880 if (dumpPackage == null || dumpPackage.equals(mProfileApp)) { 12881 if (needSep) { 12882 pw.println(); 12883 needSep = false; 12884 } 12885 pw.println(" mProfileApp=" + mProfileApp + " mProfileProc=" + mProfileProc); 12886 pw.println(" mProfileFile=" + mProfileFile + " mProfileFd=" + mProfileFd); 12887 pw.println(" mSamplingInterval=" + mSamplingInterval + " mAutoStopProfiler=" 12888 + mAutoStopProfiler); 12889 pw.println(" mProfileType=" + mProfileType); 12890 } 12891 } 12892 if (dumpPackage == null) { 12893 if (mAlwaysFinishActivities || mController != null) { 12894 pw.println(" mAlwaysFinishActivities=" + mAlwaysFinishActivities 12895 + " mController=" + mController); 12896 } 12897 if (dumpAll) { 12898 pw.println(" Total persistent processes: " + numPers); 12899 pw.println(" mProcessesReady=" + mProcessesReady 12900 + " mSystemReady=" + mSystemReady 12901 + " mBooted=" + mBooted 12902 + " mFactoryTest=" + mFactoryTest); 12903 pw.println(" mBooting=" + mBooting 12904 + " mCallFinishBooting=" + mCallFinishBooting 12905 + " mBootAnimationComplete=" + mBootAnimationComplete); 12906 pw.print(" mLastPowerCheckRealtime="); 12907 TimeUtils.formatDuration(mLastPowerCheckRealtime, pw); 12908 pw.println(""); 12909 pw.print(" mLastPowerCheckUptime="); 12910 TimeUtils.formatDuration(mLastPowerCheckUptime, pw); 12911 pw.println(""); 12912 pw.println(" mGoingToSleep=" + mStackSupervisor.mGoingToSleep); 12913 pw.println(" mLaunchingActivity=" + mStackSupervisor.mLaunchingActivity); 12914 pw.println(" mAdjSeq=" + mAdjSeq + " mLruSeq=" + mLruSeq); 12915 pw.println(" mNumNonCachedProcs=" + mNumNonCachedProcs 12916 + " (" + mLruProcesses.size() + " total)" 12917 + " mNumCachedHiddenProcs=" + mNumCachedHiddenProcs 12918 + " mNumServiceProcs=" + mNumServiceProcs 12919 + " mNewNumServiceProcs=" + mNewNumServiceProcs); 12920 pw.println(" mAllowLowerMemLevel=" + mAllowLowerMemLevel 12921 + " mLastMemoryLevel" + mLastMemoryLevel 12922 + " mLastNumProcesses" + mLastNumProcesses); 12923 long now = SystemClock.uptimeMillis(); 12924 pw.print(" mLastIdleTime="); 12925 TimeUtils.formatDuration(now, mLastIdleTime, pw); 12926 pw.print(" mLowRamSinceLastIdle="); 12927 TimeUtils.formatDuration(getLowRamTimeSinceIdle(now), pw); 12928 pw.println(); 12929 } 12930 } 12931 12932 if (!printedAnything) { 12933 pw.println(" (nothing)"); 12934 } 12935 } 12936 12937 boolean dumpProcessesToGc(FileDescriptor fd, PrintWriter pw, String[] args, 12938 int opti, boolean needSep, boolean dumpAll, String dumpPackage) { 12939 if (mProcessesToGc.size() > 0) { 12940 boolean printed = false; 12941 long now = SystemClock.uptimeMillis(); 12942 for (int i=0; i<mProcessesToGc.size(); i++) { 12943 ProcessRecord proc = mProcessesToGc.get(i); 12944 if (dumpPackage != null && !dumpPackage.equals(proc.info.packageName)) { 12945 continue; 12946 } 12947 if (!printed) { 12948 if (needSep) pw.println(); 12949 needSep = true; 12950 pw.println(" Processes that are waiting to GC:"); 12951 printed = true; 12952 } 12953 pw.print(" Process "); pw.println(proc); 12954 pw.print(" lowMem="); pw.print(proc.reportLowMemory); 12955 pw.print(", last gced="); 12956 pw.print(now-proc.lastRequestedGc); 12957 pw.print(" ms ago, last lowMem="); 12958 pw.print(now-proc.lastLowMemory); 12959 pw.println(" ms ago"); 12960 12961 } 12962 } 12963 return needSep; 12964 } 12965 12966 void printOomLevel(PrintWriter pw, String name, int adj) { 12967 pw.print(" "); 12968 if (adj >= 0) { 12969 pw.print(' '); 12970 if (adj < 10) pw.print(' '); 12971 } else { 12972 if (adj > -10) pw.print(' '); 12973 } 12974 pw.print(adj); 12975 pw.print(": "); 12976 pw.print(name); 12977 pw.print(" ("); 12978 pw.print(mProcessList.getMemLevel(adj)/1024); 12979 pw.println(" kB)"); 12980 } 12981 12982 boolean dumpOomLocked(FileDescriptor fd, PrintWriter pw, String[] args, 12983 int opti, boolean dumpAll) { 12984 boolean needSep = false; 12985 12986 if (mLruProcesses.size() > 0) { 12987 if (needSep) pw.println(); 12988 needSep = true; 12989 pw.println(" OOM levels:"); 12990 printOomLevel(pw, "SYSTEM_ADJ", ProcessList.SYSTEM_ADJ); 12991 printOomLevel(pw, "PERSISTENT_PROC_ADJ", ProcessList.PERSISTENT_PROC_ADJ); 12992 printOomLevel(pw, "PERSISTENT_SERVICE_ADJ", ProcessList.PERSISTENT_SERVICE_ADJ); 12993 printOomLevel(pw, "FOREGROUND_APP_ADJ", ProcessList.FOREGROUND_APP_ADJ); 12994 printOomLevel(pw, "VISIBLE_APP_ADJ", ProcessList.VISIBLE_APP_ADJ); 12995 printOomLevel(pw, "PERCEPTIBLE_APP_ADJ", ProcessList.PERCEPTIBLE_APP_ADJ); 12996 printOomLevel(pw, "BACKUP_APP_ADJ", ProcessList.BACKUP_APP_ADJ); 12997 printOomLevel(pw, "HEAVY_WEIGHT_APP_ADJ", ProcessList.HEAVY_WEIGHT_APP_ADJ); 12998 printOomLevel(pw, "SERVICE_ADJ", ProcessList.SERVICE_ADJ); 12999 printOomLevel(pw, "HOME_APP_ADJ", ProcessList.HOME_APP_ADJ); 13000 printOomLevel(pw, "PREVIOUS_APP_ADJ", ProcessList.PREVIOUS_APP_ADJ); 13001 printOomLevel(pw, "SERVICE_B_ADJ", ProcessList.SERVICE_B_ADJ); 13002 printOomLevel(pw, "CACHED_APP_MIN_ADJ", ProcessList.CACHED_APP_MIN_ADJ); 13003 printOomLevel(pw, "CACHED_APP_MAX_ADJ", ProcessList.CACHED_APP_MAX_ADJ); 13004 13005 if (needSep) pw.println(); 13006 pw.print(" Process OOM control ("); pw.print(mLruProcesses.size()); 13007 pw.print(" total, non-act at "); 13008 pw.print(mLruProcesses.size()-mLruProcessActivityStart); 13009 pw.print(", non-svc at "); 13010 pw.print(mLruProcesses.size()-mLruProcessServiceStart); 13011 pw.println("):"); 13012 dumpProcessOomList(pw, this, mLruProcesses, " ", "Proc", "PERS", true, null); 13013 needSep = true; 13014 } 13015 13016 dumpProcessesToGc(fd, pw, args, opti, needSep, dumpAll, null); 13017 13018 pw.println(); 13019 pw.println(" mHomeProcess: " + mHomeProcess); 13020 pw.println(" mPreviousProcess: " + mPreviousProcess); 13021 if (mHeavyWeightProcess != null) { 13022 pw.println(" mHeavyWeightProcess: " + mHeavyWeightProcess); 13023 } 13024 13025 return true; 13026 } 13027 13028 /** 13029 * There are three ways to call this: 13030 * - no provider specified: dump all the providers 13031 * - a flattened component name that matched an existing provider was specified as the 13032 * first arg: dump that one provider 13033 * - the first arg isn't the flattened component name of an existing provider: 13034 * dump all providers whose component contains the first arg as a substring 13035 */ 13036 protected boolean dumpProvider(FileDescriptor fd, PrintWriter pw, String name, String[] args, 13037 int opti, boolean dumpAll) { 13038 return mProviderMap.dumpProvider(fd, pw, name, args, opti, dumpAll); 13039 } 13040 13041 static class ItemMatcher { 13042 ArrayList<ComponentName> components; 13043 ArrayList<String> strings; 13044 ArrayList<Integer> objects; 13045 boolean all; 13046 13047 ItemMatcher() { 13048 all = true; 13049 } 13050 13051 void build(String name) { 13052 ComponentName componentName = ComponentName.unflattenFromString(name); 13053 if (componentName != null) { 13054 if (components == null) { 13055 components = new ArrayList<ComponentName>(); 13056 } 13057 components.add(componentName); 13058 all = false; 13059 } else { 13060 int objectId = 0; 13061 // Not a '/' separated full component name; maybe an object ID? 13062 try { 13063 objectId = Integer.parseInt(name, 16); 13064 if (objects == null) { 13065 objects = new ArrayList<Integer>(); 13066 } 13067 objects.add(objectId); 13068 all = false; 13069 } catch (RuntimeException e) { 13070 // Not an integer; just do string match. 13071 if (strings == null) { 13072 strings = new ArrayList<String>(); 13073 } 13074 strings.add(name); 13075 all = false; 13076 } 13077 } 13078 } 13079 13080 int build(String[] args, int opti) { 13081 for (; opti<args.length; opti++) { 13082 String name = args[opti]; 13083 if ("--".equals(name)) { 13084 return opti+1; 13085 } 13086 build(name); 13087 } 13088 return opti; 13089 } 13090 13091 boolean match(Object object, ComponentName comp) { 13092 if (all) { 13093 return true; 13094 } 13095 if (components != null) { 13096 for (int i=0; i<components.size(); i++) { 13097 if (components.get(i).equals(comp)) { 13098 return true; 13099 } 13100 } 13101 } 13102 if (objects != null) { 13103 for (int i=0; i<objects.size(); i++) { 13104 if (System.identityHashCode(object) == objects.get(i)) { 13105 return true; 13106 } 13107 } 13108 } 13109 if (strings != null) { 13110 String flat = comp.flattenToString(); 13111 for (int i=0; i<strings.size(); i++) { 13112 if (flat.contains(strings.get(i))) { 13113 return true; 13114 } 13115 } 13116 } 13117 return false; 13118 } 13119 } 13120 13121 /** 13122 * There are three things that cmd can be: 13123 * - a flattened component name that matches an existing activity 13124 * - the cmd arg isn't the flattened component name of an existing activity: 13125 * dump all activity whose component contains the cmd as a substring 13126 * - A hex number of the ActivityRecord object instance. 13127 */ 13128 protected boolean dumpActivity(FileDescriptor fd, PrintWriter pw, String name, String[] args, 13129 int opti, boolean dumpAll) { 13130 ArrayList<ActivityRecord> activities; 13131 13132 synchronized (this) { 13133 activities = mStackSupervisor.getDumpActivitiesLocked(name); 13134 } 13135 13136 if (activities.size() <= 0) { 13137 return false; 13138 } 13139 13140 String[] newArgs = new String[args.length - opti]; 13141 System.arraycopy(args, opti, newArgs, 0, args.length - opti); 13142 13143 TaskRecord lastTask = null; 13144 boolean needSep = false; 13145 for (int i=activities.size()-1; i>=0; i--) { 13146 ActivityRecord r = activities.get(i); 13147 if (needSep) { 13148 pw.println(); 13149 } 13150 needSep = true; 13151 synchronized (this) { 13152 if (lastTask != r.task) { 13153 lastTask = r.task; 13154 pw.print("TASK "); pw.print(lastTask.affinity); 13155 pw.print(" id="); pw.println(lastTask.taskId); 13156 if (dumpAll) { 13157 lastTask.dump(pw, " "); 13158 } 13159 } 13160 } 13161 dumpActivity(" ", fd, pw, activities.get(i), newArgs, dumpAll); 13162 } 13163 return true; 13164 } 13165 13166 /** 13167 * Invokes IApplicationThread.dumpActivity() on the thread of the specified activity if 13168 * there is a thread associated with the activity. 13169 */ 13170 private void dumpActivity(String prefix, FileDescriptor fd, PrintWriter pw, 13171 final ActivityRecord r, String[] args, boolean dumpAll) { 13172 String innerPrefix = prefix + " "; 13173 synchronized (this) { 13174 pw.print(prefix); pw.print("ACTIVITY "); pw.print(r.shortComponentName); 13175 pw.print(" "); pw.print(Integer.toHexString(System.identityHashCode(r))); 13176 pw.print(" pid="); 13177 if (r.app != null) pw.println(r.app.pid); 13178 else pw.println("(not running)"); 13179 if (dumpAll) { 13180 r.dump(pw, innerPrefix); 13181 } 13182 } 13183 if (r.app != null && r.app.thread != null) { 13184 // flush anything that is already in the PrintWriter since the thread is going 13185 // to write to the file descriptor directly 13186 pw.flush(); 13187 try { 13188 TransferPipe tp = new TransferPipe(); 13189 try { 13190 r.app.thread.dumpActivity(tp.getWriteFd().getFileDescriptor(), 13191 r.appToken, innerPrefix, args); 13192 tp.go(fd); 13193 } finally { 13194 tp.kill(); 13195 } 13196 } catch (IOException e) { 13197 pw.println(innerPrefix + "Failure while dumping the activity: " + e); 13198 } catch (RemoteException e) { 13199 pw.println(innerPrefix + "Got a RemoteException while dumping the activity"); 13200 } 13201 } 13202 } 13203 13204 void dumpBroadcastsLocked(FileDescriptor fd, PrintWriter pw, String[] args, 13205 int opti, boolean dumpAll, String dumpPackage) { 13206 boolean needSep = false; 13207 boolean onlyHistory = false; 13208 boolean printedAnything = false; 13209 13210 if ("history".equals(dumpPackage)) { 13211 if (opti < args.length && "-s".equals(args[opti])) { 13212 dumpAll = false; 13213 } 13214 onlyHistory = true; 13215 dumpPackage = null; 13216 } 13217 13218 pw.println("ACTIVITY MANAGER BROADCAST STATE (dumpsys activity broadcasts)"); 13219 if (!onlyHistory && dumpAll) { 13220 if (mRegisteredReceivers.size() > 0) { 13221 boolean printed = false; 13222 Iterator it = mRegisteredReceivers.values().iterator(); 13223 while (it.hasNext()) { 13224 ReceiverList r = (ReceiverList)it.next(); 13225 if (dumpPackage != null && (r.app == null || 13226 !dumpPackage.equals(r.app.info.packageName))) { 13227 continue; 13228 } 13229 if (!printed) { 13230 pw.println(" Registered Receivers:"); 13231 needSep = true; 13232 printed = true; 13233 printedAnything = true; 13234 } 13235 pw.print(" * "); pw.println(r); 13236 r.dump(pw, " "); 13237 } 13238 } 13239 13240 if (mReceiverResolver.dump(pw, needSep ? 13241 "\n Receiver Resolver Table:" : " Receiver Resolver Table:", 13242 " ", dumpPackage, false)) { 13243 needSep = true; 13244 printedAnything = true; 13245 } 13246 } 13247 13248 for (BroadcastQueue q : mBroadcastQueues) { 13249 needSep = q.dumpLocked(fd, pw, args, opti, dumpAll, dumpPackage, needSep); 13250 printedAnything |= needSep; 13251 } 13252 13253 needSep = true; 13254 13255 if (!onlyHistory && mStickyBroadcasts != null && dumpPackage == null) { 13256 for (int user=0; user<mStickyBroadcasts.size(); user++) { 13257 if (needSep) { 13258 pw.println(); 13259 } 13260 needSep = true; 13261 printedAnything = true; 13262 pw.print(" Sticky broadcasts for user "); 13263 pw.print(mStickyBroadcasts.keyAt(user)); pw.println(":"); 13264 StringBuilder sb = new StringBuilder(128); 13265 for (Map.Entry<String, ArrayList<Intent>> ent 13266 : mStickyBroadcasts.valueAt(user).entrySet()) { 13267 pw.print(" * Sticky action "); pw.print(ent.getKey()); 13268 if (dumpAll) { 13269 pw.println(":"); 13270 ArrayList<Intent> intents = ent.getValue(); 13271 final int N = intents.size(); 13272 for (int i=0; i<N; i++) { 13273 sb.setLength(0); 13274 sb.append(" Intent: "); 13275 intents.get(i).toShortString(sb, false, true, false, false); 13276 pw.println(sb.toString()); 13277 Bundle bundle = intents.get(i).getExtras(); 13278 if (bundle != null) { 13279 pw.print(" "); 13280 pw.println(bundle.toString()); 13281 } 13282 } 13283 } else { 13284 pw.println(""); 13285 } 13286 } 13287 } 13288 } 13289 13290 if (!onlyHistory && dumpAll) { 13291 pw.println(); 13292 for (BroadcastQueue queue : mBroadcastQueues) { 13293 pw.println(" mBroadcastsScheduled [" + queue.mQueueName + "]=" 13294 + queue.mBroadcastsScheduled); 13295 } 13296 pw.println(" mHandler:"); 13297 mHandler.dump(new PrintWriterPrinter(pw), " "); 13298 needSep = true; 13299 printedAnything = true; 13300 } 13301 13302 if (!printedAnything) { 13303 pw.println(" (nothing)"); 13304 } 13305 } 13306 13307 void dumpProvidersLocked(FileDescriptor fd, PrintWriter pw, String[] args, 13308 int opti, boolean dumpAll, String dumpPackage) { 13309 boolean needSep; 13310 boolean printedAnything = false; 13311 13312 ItemMatcher matcher = new ItemMatcher(); 13313 matcher.build(args, opti); 13314 13315 pw.println("ACTIVITY MANAGER CONTENT PROVIDERS (dumpsys activity providers)"); 13316 13317 needSep = mProviderMap.dumpProvidersLocked(pw, dumpAll, dumpPackage); 13318 printedAnything |= needSep; 13319 13320 if (mLaunchingProviders.size() > 0) { 13321 boolean printed = false; 13322 for (int i=mLaunchingProviders.size()-1; i>=0; i--) { 13323 ContentProviderRecord r = mLaunchingProviders.get(i); 13324 if (dumpPackage != null && !dumpPackage.equals(r.name.getPackageName())) { 13325 continue; 13326 } 13327 if (!printed) { 13328 if (needSep) pw.println(); 13329 needSep = true; 13330 pw.println(" Launching content providers:"); 13331 printed = true; 13332 printedAnything = true; 13333 } 13334 pw.print(" Launching #"); pw.print(i); pw.print(": "); 13335 pw.println(r); 13336 } 13337 } 13338 13339 if (mGrantedUriPermissions.size() > 0) { 13340 boolean printed = false; 13341 int dumpUid = -2; 13342 if (dumpPackage != null) { 13343 try { 13344 dumpUid = mContext.getPackageManager().getPackageUid(dumpPackage, 0); 13345 } catch (NameNotFoundException e) { 13346 dumpUid = -1; 13347 } 13348 } 13349 for (int i=0; i<mGrantedUriPermissions.size(); i++) { 13350 int uid = mGrantedUriPermissions.keyAt(i); 13351 if (dumpUid >= -1 && UserHandle.getAppId(uid) != dumpUid) { 13352 continue; 13353 } 13354 final ArrayMap<GrantUri, UriPermission> perms = mGrantedUriPermissions.valueAt(i); 13355 if (!printed) { 13356 if (needSep) pw.println(); 13357 needSep = true; 13358 pw.println(" Granted Uri Permissions:"); 13359 printed = true; 13360 printedAnything = true; 13361 } 13362 pw.print(" * UID "); pw.print(uid); pw.println(" holds:"); 13363 for (UriPermission perm : perms.values()) { 13364 pw.print(" "); pw.println(perm); 13365 if (dumpAll) { 13366 perm.dump(pw, " "); 13367 } 13368 } 13369 } 13370 } 13371 13372 if (!printedAnything) { 13373 pw.println(" (nothing)"); 13374 } 13375 } 13376 13377 void dumpPendingIntentsLocked(FileDescriptor fd, PrintWriter pw, String[] args, 13378 int opti, boolean dumpAll, String dumpPackage) { 13379 boolean printed = false; 13380 13381 pw.println("ACTIVITY MANAGER PENDING INTENTS (dumpsys activity intents)"); 13382 13383 if (mIntentSenderRecords.size() > 0) { 13384 Iterator<WeakReference<PendingIntentRecord>> it 13385 = mIntentSenderRecords.values().iterator(); 13386 while (it.hasNext()) { 13387 WeakReference<PendingIntentRecord> ref = it.next(); 13388 PendingIntentRecord rec = ref != null ? ref.get(): null; 13389 if (dumpPackage != null && (rec == null 13390 || !dumpPackage.equals(rec.key.packageName))) { 13391 continue; 13392 } 13393 printed = true; 13394 if (rec != null) { 13395 pw.print(" * "); pw.println(rec); 13396 if (dumpAll) { 13397 rec.dump(pw, " "); 13398 } 13399 } else { 13400 pw.print(" * "); pw.println(ref); 13401 } 13402 } 13403 } 13404 13405 if (!printed) { 13406 pw.println(" (nothing)"); 13407 } 13408 } 13409 13410 private static final int dumpProcessList(PrintWriter pw, 13411 ActivityManagerService service, List list, 13412 String prefix, String normalLabel, String persistentLabel, 13413 String dumpPackage) { 13414 int numPers = 0; 13415 final int N = list.size()-1; 13416 for (int i=N; i>=0; i--) { 13417 ProcessRecord r = (ProcessRecord)list.get(i); 13418 if (dumpPackage != null && !dumpPackage.equals(r.info.packageName)) { 13419 continue; 13420 } 13421 pw.println(String.format("%s%s #%2d: %s", 13422 prefix, (r.persistent ? persistentLabel : normalLabel), 13423 i, r.toString())); 13424 if (r.persistent) { 13425 numPers++; 13426 } 13427 } 13428 return numPers; 13429 } 13430 13431 private static final boolean dumpProcessOomList(PrintWriter pw, 13432 ActivityManagerService service, List<ProcessRecord> origList, 13433 String prefix, String normalLabel, String persistentLabel, 13434 boolean inclDetails, String dumpPackage) { 13435 13436 ArrayList<Pair<ProcessRecord, Integer>> list 13437 = new ArrayList<Pair<ProcessRecord, Integer>>(origList.size()); 13438 for (int i=0; i<origList.size(); i++) { 13439 ProcessRecord r = origList.get(i); 13440 if (dumpPackage != null && !r.pkgList.containsKey(dumpPackage)) { 13441 continue; 13442 } 13443 list.add(new Pair<ProcessRecord, Integer>(origList.get(i), i)); 13444 } 13445 13446 if (list.size() <= 0) { 13447 return false; 13448 } 13449 13450 Comparator<Pair<ProcessRecord, Integer>> comparator 13451 = new Comparator<Pair<ProcessRecord, Integer>>() { 13452 @Override 13453 public int compare(Pair<ProcessRecord, Integer> object1, 13454 Pair<ProcessRecord, Integer> object2) { 13455 if (object1.first.setAdj != object2.first.setAdj) { 13456 return object1.first.setAdj > object2.first.setAdj ? -1 : 1; 13457 } 13458 if (object1.second.intValue() != object2.second.intValue()) { 13459 return object1.second.intValue() > object2.second.intValue() ? -1 : 1; 13460 } 13461 return 0; 13462 } 13463 }; 13464 13465 Collections.sort(list, comparator); 13466 13467 final long curRealtime = SystemClock.elapsedRealtime(); 13468 final long realtimeSince = curRealtime - service.mLastPowerCheckRealtime; 13469 final long curUptime = SystemClock.uptimeMillis(); 13470 final long uptimeSince = curUptime - service.mLastPowerCheckUptime; 13471 13472 for (int i=list.size()-1; i>=0; i--) { 13473 ProcessRecord r = list.get(i).first; 13474 String oomAdj = ProcessList.makeOomAdjString(r.setAdj); 13475 char schedGroup; 13476 switch (r.setSchedGroup) { 13477 case Process.THREAD_GROUP_BG_NONINTERACTIVE: 13478 schedGroup = 'B'; 13479 break; 13480 case Process.THREAD_GROUP_DEFAULT: 13481 schedGroup = 'F'; 13482 break; 13483 default: 13484 schedGroup = '?'; 13485 break; 13486 } 13487 char foreground; 13488 if (r.foregroundActivities) { 13489 foreground = 'A'; 13490 } else if (r.foregroundServices) { 13491 foreground = 'S'; 13492 } else { 13493 foreground = ' '; 13494 } 13495 String procState = ProcessList.makeProcStateString(r.curProcState); 13496 pw.print(prefix); 13497 pw.print(r.persistent ? persistentLabel : normalLabel); 13498 pw.print(" #"); 13499 int num = (origList.size()-1)-list.get(i).second; 13500 if (num < 10) pw.print(' '); 13501 pw.print(num); 13502 pw.print(": "); 13503 pw.print(oomAdj); 13504 pw.print(' '); 13505 pw.print(schedGroup); 13506 pw.print('/'); 13507 pw.print(foreground); 13508 pw.print('/'); 13509 pw.print(procState); 13510 pw.print(" trm:"); 13511 if (r.trimMemoryLevel < 10) pw.print(' '); 13512 pw.print(r.trimMemoryLevel); 13513 pw.print(' '); 13514 pw.print(r.toShortString()); 13515 pw.print(" ("); 13516 pw.print(r.adjType); 13517 pw.println(')'); 13518 if (r.adjSource != null || r.adjTarget != null) { 13519 pw.print(prefix); 13520 pw.print(" "); 13521 if (r.adjTarget instanceof ComponentName) { 13522 pw.print(((ComponentName)r.adjTarget).flattenToShortString()); 13523 } else if (r.adjTarget != null) { 13524 pw.print(r.adjTarget.toString()); 13525 } else { 13526 pw.print("{null}"); 13527 } 13528 pw.print("<="); 13529 if (r.adjSource instanceof ProcessRecord) { 13530 pw.print("Proc{"); 13531 pw.print(((ProcessRecord)r.adjSource).toShortString()); 13532 pw.println("}"); 13533 } else if (r.adjSource != null) { 13534 pw.println(r.adjSource.toString()); 13535 } else { 13536 pw.println("{null}"); 13537 } 13538 } 13539 if (inclDetails) { 13540 pw.print(prefix); 13541 pw.print(" "); 13542 pw.print("oom: max="); pw.print(r.maxAdj); 13543 pw.print(" curRaw="); pw.print(r.curRawAdj); 13544 pw.print(" setRaw="); pw.print(r.setRawAdj); 13545 pw.print(" cur="); pw.print(r.curAdj); 13546 pw.print(" set="); pw.println(r.setAdj); 13547 pw.print(prefix); 13548 pw.print(" "); 13549 pw.print("state: cur="); pw.print(ProcessList.makeProcStateString(r.curProcState)); 13550 pw.print(" set="); pw.print(ProcessList.makeProcStateString(r.setProcState)); 13551 pw.print(" lastPss="); pw.print(r.lastPss); 13552 pw.print(" lastCachedPss="); pw.println(r.lastCachedPss); 13553 pw.print(prefix); 13554 pw.print(" "); 13555 pw.print("cached="); pw.print(r.cached); 13556 pw.print(" empty="); pw.print(r.empty); 13557 pw.print(" hasAboveClient="); pw.println(r.hasAboveClient); 13558 13559 if (r.setProcState >= ActivityManager.PROCESS_STATE_SERVICE) { 13560 if (r.lastWakeTime != 0) { 13561 long wtime; 13562 BatteryStatsImpl stats = service.mBatteryStatsService.getActiveStatistics(); 13563 synchronized (stats) { 13564 wtime = stats.getProcessWakeTime(r.info.uid, 13565 r.pid, curRealtime); 13566 } 13567 long timeUsed = wtime - r.lastWakeTime; 13568 pw.print(prefix); 13569 pw.print(" "); 13570 pw.print("keep awake over "); 13571 TimeUtils.formatDuration(realtimeSince, pw); 13572 pw.print(" used "); 13573 TimeUtils.formatDuration(timeUsed, pw); 13574 pw.print(" ("); 13575 pw.print((timeUsed*100)/realtimeSince); 13576 pw.println("%)"); 13577 } 13578 if (r.lastCpuTime != 0) { 13579 long timeUsed = r.curCpuTime - r.lastCpuTime; 13580 pw.print(prefix); 13581 pw.print(" "); 13582 pw.print("run cpu over "); 13583 TimeUtils.formatDuration(uptimeSince, pw); 13584 pw.print(" used "); 13585 TimeUtils.formatDuration(timeUsed, pw); 13586 pw.print(" ("); 13587 pw.print((timeUsed*100)/uptimeSince); 13588 pw.println("%)"); 13589 } 13590 } 13591 } 13592 } 13593 return true; 13594 } 13595 13596 ArrayList<ProcessRecord> collectProcesses(PrintWriter pw, int start, boolean allPkgs, 13597 String[] args) { 13598 ArrayList<ProcessRecord> procs; 13599 synchronized (this) { 13600 if (args != null && args.length > start 13601 && args[start].charAt(0) != '-') { 13602 procs = new ArrayList<ProcessRecord>(); 13603 int pid = -1; 13604 try { 13605 pid = Integer.parseInt(args[start]); 13606 } catch (NumberFormatException e) { 13607 } 13608 for (int i=mLruProcesses.size()-1; i>=0; i--) { 13609 ProcessRecord proc = mLruProcesses.get(i); 13610 if (proc.pid == pid) { 13611 procs.add(proc); 13612 } else if (allPkgs && proc.pkgList != null 13613 && proc.pkgList.containsKey(args[start])) { 13614 procs.add(proc); 13615 } else if (proc.processName.equals(args[start])) { 13616 procs.add(proc); 13617 } 13618 } 13619 if (procs.size() <= 0) { 13620 return null; 13621 } 13622 } else { 13623 procs = new ArrayList<ProcessRecord>(mLruProcesses); 13624 } 13625 } 13626 return procs; 13627 } 13628 13629 final void dumpGraphicsHardwareUsage(FileDescriptor fd, 13630 PrintWriter pw, String[] args) { 13631 ArrayList<ProcessRecord> procs = collectProcesses(pw, 0, false, args); 13632 if (procs == null) { 13633 pw.println("No process found for: " + args[0]); 13634 return; 13635 } 13636 13637 long uptime = SystemClock.uptimeMillis(); 13638 long realtime = SystemClock.elapsedRealtime(); 13639 pw.println("Applications Graphics Acceleration Info:"); 13640 pw.println("Uptime: " + uptime + " Realtime: " + realtime); 13641 13642 for (int i = procs.size() - 1 ; i >= 0 ; i--) { 13643 ProcessRecord r = procs.get(i); 13644 if (r.thread != null) { 13645 pw.println("\n** Graphics info for pid " + r.pid + " [" + r.processName + "] **"); 13646 pw.flush(); 13647 try { 13648 TransferPipe tp = new TransferPipe(); 13649 try { 13650 r.thread.dumpGfxInfo(tp.getWriteFd().getFileDescriptor(), args); 13651 tp.go(fd); 13652 } finally { 13653 tp.kill(); 13654 } 13655 } catch (IOException e) { 13656 pw.println("Failure while dumping the app: " + r); 13657 pw.flush(); 13658 } catch (RemoteException e) { 13659 pw.println("Got a RemoteException while dumping the app " + r); 13660 pw.flush(); 13661 } 13662 } 13663 } 13664 } 13665 13666 final void dumpDbInfo(FileDescriptor fd, PrintWriter pw, String[] args) { 13667 ArrayList<ProcessRecord> procs = collectProcesses(pw, 0, false, args); 13668 if (procs == null) { 13669 pw.println("No process found for: " + args[0]); 13670 return; 13671 } 13672 13673 pw.println("Applications Database Info:"); 13674 13675 for (int i = procs.size() - 1 ; i >= 0 ; i--) { 13676 ProcessRecord r = procs.get(i); 13677 if (r.thread != null) { 13678 pw.println("\n** Database info for pid " + r.pid + " [" + r.processName + "] **"); 13679 pw.flush(); 13680 try { 13681 TransferPipe tp = new TransferPipe(); 13682 try { 13683 r.thread.dumpDbInfo(tp.getWriteFd().getFileDescriptor(), args); 13684 tp.go(fd); 13685 } finally { 13686 tp.kill(); 13687 } 13688 } catch (IOException e) { 13689 pw.println("Failure while dumping the app: " + r); 13690 pw.flush(); 13691 } catch (RemoteException e) { 13692 pw.println("Got a RemoteException while dumping the app " + r); 13693 pw.flush(); 13694 } 13695 } 13696 } 13697 } 13698 13699 final static class MemItem { 13700 final boolean isProc; 13701 final String label; 13702 final String shortLabel; 13703 final long pss; 13704 final int id; 13705 final boolean hasActivities; 13706 ArrayList<MemItem> subitems; 13707 13708 public MemItem(String _label, String _shortLabel, long _pss, int _id, 13709 boolean _hasActivities) { 13710 isProc = true; 13711 label = _label; 13712 shortLabel = _shortLabel; 13713 pss = _pss; 13714 id = _id; 13715 hasActivities = _hasActivities; 13716 } 13717 13718 public MemItem(String _label, String _shortLabel, long _pss, int _id) { 13719 isProc = false; 13720 label = _label; 13721 shortLabel = _shortLabel; 13722 pss = _pss; 13723 id = _id; 13724 hasActivities = false; 13725 } 13726 } 13727 13728 static final void dumpMemItems(PrintWriter pw, String prefix, String tag, 13729 ArrayList<MemItem> items, boolean sort, boolean isCompact) { 13730 if (sort && !isCompact) { 13731 Collections.sort(items, new Comparator<MemItem>() { 13732 @Override 13733 public int compare(MemItem lhs, MemItem rhs) { 13734 if (lhs.pss < rhs.pss) { 13735 return 1; 13736 } else if (lhs.pss > rhs.pss) { 13737 return -1; 13738 } 13739 return 0; 13740 } 13741 }); 13742 } 13743 13744 for (int i=0; i<items.size(); i++) { 13745 MemItem mi = items.get(i); 13746 if (!isCompact) { 13747 pw.print(prefix); pw.printf("%7d kB: ", mi.pss); pw.println(mi.label); 13748 } else if (mi.isProc) { 13749 pw.print("proc,"); pw.print(tag); pw.print(","); pw.print(mi.shortLabel); 13750 pw.print(","); pw.print(mi.id); pw.print(","); pw.print(mi.pss); 13751 pw.println(mi.hasActivities ? ",a" : ",e"); 13752 } else { 13753 pw.print(tag); pw.print(","); pw.print(mi.shortLabel); pw.print(","); 13754 pw.println(mi.pss); 13755 } 13756 if (mi.subitems != null) { 13757 dumpMemItems(pw, prefix + " ", mi.shortLabel, mi.subitems, 13758 true, isCompact); 13759 } 13760 } 13761 } 13762 13763 // These are in KB. 13764 static final long[] DUMP_MEM_BUCKETS = new long[] { 13765 5*1024, 7*1024, 10*1024, 15*1024, 20*1024, 30*1024, 40*1024, 80*1024, 13766 120*1024, 160*1024, 200*1024, 13767 250*1024, 300*1024, 350*1024, 400*1024, 500*1024, 600*1024, 800*1024, 13768 1*1024*1024, 2*1024*1024, 5*1024*1024, 10*1024*1024, 20*1024*1024 13769 }; 13770 13771 static final void appendMemBucket(StringBuilder out, long memKB, String label, 13772 boolean stackLike) { 13773 int start = label.lastIndexOf('.'); 13774 if (start >= 0) start++; 13775 else start = 0; 13776 int end = label.length(); 13777 for (int i=0; i<DUMP_MEM_BUCKETS.length; i++) { 13778 if (DUMP_MEM_BUCKETS[i] >= memKB) { 13779 long bucket = DUMP_MEM_BUCKETS[i]/1024; 13780 out.append(bucket); 13781 out.append(stackLike ? "MB." : "MB "); 13782 out.append(label, start, end); 13783 return; 13784 } 13785 } 13786 out.append(memKB/1024); 13787 out.append(stackLike ? "MB." : "MB "); 13788 out.append(label, start, end); 13789 } 13790 13791 static final int[] DUMP_MEM_OOM_ADJ = new int[] { 13792 ProcessList.NATIVE_ADJ, 13793 ProcessList.SYSTEM_ADJ, ProcessList.PERSISTENT_PROC_ADJ, 13794 ProcessList.PERSISTENT_SERVICE_ADJ, ProcessList.FOREGROUND_APP_ADJ, 13795 ProcessList.VISIBLE_APP_ADJ, ProcessList.PERCEPTIBLE_APP_ADJ, 13796 ProcessList.BACKUP_APP_ADJ, ProcessList.HEAVY_WEIGHT_APP_ADJ, 13797 ProcessList.SERVICE_ADJ, ProcessList.HOME_APP_ADJ, 13798 ProcessList.PREVIOUS_APP_ADJ, ProcessList.SERVICE_B_ADJ, ProcessList.CACHED_APP_MAX_ADJ 13799 }; 13800 static final String[] DUMP_MEM_OOM_LABEL = new String[] { 13801 "Native", 13802 "System", "Persistent", "Persistent Service", "Foreground", 13803 "Visible", "Perceptible", 13804 "Heavy Weight", "Backup", 13805 "A Services", "Home", 13806 "Previous", "B Services", "Cached" 13807 }; 13808 static final String[] DUMP_MEM_OOM_COMPACT_LABEL = new String[] { 13809 "native", 13810 "sys", "pers", "persvc", "fore", 13811 "vis", "percept", 13812 "heavy", "backup", 13813 "servicea", "home", 13814 "prev", "serviceb", "cached" 13815 }; 13816 13817 private final void dumpApplicationMemoryUsageHeader(PrintWriter pw, long uptime, 13818 long realtime, boolean isCheckinRequest, boolean isCompact) { 13819 if (isCheckinRequest || isCompact) { 13820 // short checkin version 13821 pw.print("time,"); pw.print(uptime); pw.print(","); pw.println(realtime); 13822 } else { 13823 pw.println("Applications Memory Usage (kB):"); 13824 pw.println("Uptime: " + uptime + " Realtime: " + realtime); 13825 } 13826 } 13827 13828 private static final int KSM_SHARED = 0; 13829 private static final int KSM_SHARING = 1; 13830 private static final int KSM_UNSHARED = 2; 13831 private static final int KSM_VOLATILE = 3; 13832 13833 private final long[] getKsmInfo() { 13834 long[] longOut = new long[4]; 13835 final int[] SINGLE_LONG_FORMAT = new int[] { 13836 Process.PROC_SPACE_TERM|Process.PROC_OUT_LONG 13837 }; 13838 long[] longTmp = new long[1]; 13839 Process.readProcFile("/sys/kernel/mm/ksm/pages_shared", 13840 SINGLE_LONG_FORMAT, null, longTmp, null); 13841 longOut[KSM_SHARED] = longTmp[0] * ProcessList.PAGE_SIZE / 1024; 13842 longTmp[0] = 0; 13843 Process.readProcFile("/sys/kernel/mm/ksm/pages_sharing", 13844 SINGLE_LONG_FORMAT, null, longTmp, null); 13845 longOut[KSM_SHARING] = longTmp[0] * ProcessList.PAGE_SIZE / 1024; 13846 longTmp[0] = 0; 13847 Process.readProcFile("/sys/kernel/mm/ksm/pages_unshared", 13848 SINGLE_LONG_FORMAT, null, longTmp, null); 13849 longOut[KSM_UNSHARED] = longTmp[0] * ProcessList.PAGE_SIZE / 1024; 13850 longTmp[0] = 0; 13851 Process.readProcFile("/sys/kernel/mm/ksm/pages_volatile", 13852 SINGLE_LONG_FORMAT, null, longTmp, null); 13853 longOut[KSM_VOLATILE] = longTmp[0] * ProcessList.PAGE_SIZE / 1024; 13854 return longOut; 13855 } 13856 13857 final void dumpApplicationMemoryUsage(FileDescriptor fd, 13858 PrintWriter pw, String prefix, String[] args, boolean brief, PrintWriter categoryPw) { 13859 boolean dumpDetails = false; 13860 boolean dumpFullDetails = false; 13861 boolean dumpDalvik = false; 13862 boolean oomOnly = false; 13863 boolean isCompact = false; 13864 boolean localOnly = false; 13865 boolean packages = false; 13866 13867 int opti = 0; 13868 while (opti < args.length) { 13869 String opt = args[opti]; 13870 if (opt == null || opt.length() <= 0 || opt.charAt(0) != '-') { 13871 break; 13872 } 13873 opti++; 13874 if ("-a".equals(opt)) { 13875 dumpDetails = true; 13876 dumpFullDetails = true; 13877 dumpDalvik = true; 13878 } else if ("-d".equals(opt)) { 13879 dumpDalvik = true; 13880 } else if ("-c".equals(opt)) { 13881 isCompact = true; 13882 } else if ("--oom".equals(opt)) { 13883 oomOnly = true; 13884 } else if ("--local".equals(opt)) { 13885 localOnly = true; 13886 } else if ("--package".equals(opt)) { 13887 packages = true; 13888 } else if ("-h".equals(opt)) { 13889 pw.println("meminfo dump options: [-a] [-d] [-c] [--oom] [process]"); 13890 pw.println(" -a: include all available information for each process."); 13891 pw.println(" -d: include dalvik details when dumping process details."); 13892 pw.println(" -c: dump in a compact machine-parseable representation."); 13893 pw.println(" --oom: only show processes organized by oom adj."); 13894 pw.println(" --local: only collect details locally, don't call process."); 13895 pw.println(" --package: interpret process arg as package, dumping all"); 13896 pw.println(" processes that have loaded that package."); 13897 pw.println("If [process] is specified it can be the name or "); 13898 pw.println("pid of a specific process to dump."); 13899 return; 13900 } else { 13901 pw.println("Unknown argument: " + opt + "; use -h for help"); 13902 } 13903 } 13904 13905 final boolean isCheckinRequest = scanArgs(args, "--checkin"); 13906 long uptime = SystemClock.uptimeMillis(); 13907 long realtime = SystemClock.elapsedRealtime(); 13908 final long[] tmpLong = new long[1]; 13909 13910 ArrayList<ProcessRecord> procs = collectProcesses(pw, opti, packages, args); 13911 if (procs == null) { 13912 // No Java processes. Maybe they want to print a native process. 13913 if (args != null && args.length > opti 13914 && args[opti].charAt(0) != '-') { 13915 ArrayList<ProcessCpuTracker.Stats> nativeProcs 13916 = new ArrayList<ProcessCpuTracker.Stats>(); 13917 updateCpuStatsNow(); 13918 int findPid = -1; 13919 try { 13920 findPid = Integer.parseInt(args[opti]); 13921 } catch (NumberFormatException e) { 13922 } 13923 synchronized (mProcessCpuTracker) { 13924 final int N = mProcessCpuTracker.countStats(); 13925 for (int i=0; i<N; i++) { 13926 ProcessCpuTracker.Stats st = mProcessCpuTracker.getStats(i); 13927 if (st.pid == findPid || (st.baseName != null 13928 && st.baseName.equals(args[opti]))) { 13929 nativeProcs.add(st); 13930 } 13931 } 13932 } 13933 if (nativeProcs.size() > 0) { 13934 dumpApplicationMemoryUsageHeader(pw, uptime, realtime, isCheckinRequest, 13935 isCompact); 13936 Debug.MemoryInfo mi = null; 13937 for (int i = nativeProcs.size() - 1 ; i >= 0 ; i--) { 13938 final ProcessCpuTracker.Stats r = nativeProcs.get(i); 13939 final int pid = r.pid; 13940 if (!isCheckinRequest && dumpDetails) { 13941 pw.println("\n** MEMINFO in pid " + pid + " [" + r.baseName + "] **"); 13942 } 13943 if (mi == null) { 13944 mi = new Debug.MemoryInfo(); 13945 } 13946 if (dumpDetails || (!brief && !oomOnly)) { 13947 Debug.getMemoryInfo(pid, mi); 13948 } else { 13949 mi.dalvikPss = (int)Debug.getPss(pid, tmpLong); 13950 mi.dalvikPrivateDirty = (int)tmpLong[0]; 13951 } 13952 ActivityThread.dumpMemInfoTable(pw, mi, isCheckinRequest, dumpFullDetails, 13953 dumpDalvik, pid, r.baseName, 0, 0, 0, 0, 0, 0); 13954 if (isCheckinRequest) { 13955 pw.println(); 13956 } 13957 } 13958 return; 13959 } 13960 } 13961 pw.println("No process found for: " + args[opti]); 13962 return; 13963 } 13964 13965 if (!brief && !oomOnly && (procs.size() == 1 || isCheckinRequest || packages)) { 13966 dumpDetails = true; 13967 } 13968 13969 dumpApplicationMemoryUsageHeader(pw, uptime, realtime, isCheckinRequest, isCompact); 13970 13971 String[] innerArgs = new String[args.length-opti]; 13972 System.arraycopy(args, opti, innerArgs, 0, args.length-opti); 13973 13974 ArrayList<MemItem> procMems = new ArrayList<MemItem>(); 13975 final SparseArray<MemItem> procMemsMap = new SparseArray<MemItem>(); 13976 long nativePss = 0; 13977 long dalvikPss = 0; 13978 long otherPss = 0; 13979 long[] miscPss = new long[Debug.MemoryInfo.NUM_OTHER_STATS]; 13980 13981 long oomPss[] = new long[DUMP_MEM_OOM_LABEL.length]; 13982 ArrayList<MemItem>[] oomProcs = (ArrayList<MemItem>[]) 13983 new ArrayList[DUMP_MEM_OOM_LABEL.length]; 13984 13985 long totalPss = 0; 13986 long cachedPss = 0; 13987 13988 Debug.MemoryInfo mi = null; 13989 for (int i = procs.size() - 1 ; i >= 0 ; i--) { 13990 final ProcessRecord r = procs.get(i); 13991 final IApplicationThread thread; 13992 final int pid; 13993 final int oomAdj; 13994 final boolean hasActivities; 13995 synchronized (this) { 13996 thread = r.thread; 13997 pid = r.pid; 13998 oomAdj = r.getSetAdjWithServices(); 13999 hasActivities = r.activities.size() > 0; 14000 } 14001 if (thread != null) { 14002 if (!isCheckinRequest && dumpDetails) { 14003 pw.println("\n** MEMINFO in pid " + pid + " [" + r.processName + "] **"); 14004 } 14005 if (mi == null) { 14006 mi = new Debug.MemoryInfo(); 14007 } 14008 if (dumpDetails || (!brief && !oomOnly)) { 14009 Debug.getMemoryInfo(pid, mi); 14010 } else { 14011 mi.dalvikPss = (int)Debug.getPss(pid, tmpLong); 14012 mi.dalvikPrivateDirty = (int)tmpLong[0]; 14013 } 14014 if (dumpDetails) { 14015 if (localOnly) { 14016 ActivityThread.dumpMemInfoTable(pw, mi, isCheckinRequest, dumpFullDetails, 14017 dumpDalvik, pid, r.processName, 0, 0, 0, 0, 0, 0); 14018 if (isCheckinRequest) { 14019 pw.println(); 14020 } 14021 } else { 14022 try { 14023 pw.flush(); 14024 thread.dumpMemInfo(fd, mi, isCheckinRequest, dumpFullDetails, 14025 dumpDalvik, innerArgs); 14026 } catch (RemoteException e) { 14027 if (!isCheckinRequest) { 14028 pw.println("Got RemoteException!"); 14029 pw.flush(); 14030 } 14031 } 14032 } 14033 } 14034 14035 final long myTotalPss = mi.getTotalPss(); 14036 final long myTotalUss = mi.getTotalUss(); 14037 14038 synchronized (this) { 14039 if (r.thread != null && oomAdj == r.getSetAdjWithServices()) { 14040 // Record this for posterity if the process has been stable. 14041 r.baseProcessTracker.addPss(myTotalPss, myTotalUss, true, r.pkgList); 14042 } 14043 } 14044 14045 if (!isCheckinRequest && mi != null) { 14046 totalPss += myTotalPss; 14047 MemItem pssItem = new MemItem(r.processName + " (pid " + pid + 14048 (hasActivities ? " / activities)" : ")"), 14049 r.processName, myTotalPss, pid, hasActivities); 14050 procMems.add(pssItem); 14051 procMemsMap.put(pid, pssItem); 14052 14053 nativePss += mi.nativePss; 14054 dalvikPss += mi.dalvikPss; 14055 otherPss += mi.otherPss; 14056 for (int j=0; j<Debug.MemoryInfo.NUM_OTHER_STATS; j++) { 14057 long mem = mi.getOtherPss(j); 14058 miscPss[j] += mem; 14059 otherPss -= mem; 14060 } 14061 14062 if (oomAdj >= ProcessList.CACHED_APP_MIN_ADJ) { 14063 cachedPss += myTotalPss; 14064 } 14065 14066 for (int oomIndex=0; oomIndex<oomPss.length; oomIndex++) { 14067 if (oomAdj <= DUMP_MEM_OOM_ADJ[oomIndex] 14068 || oomIndex == (oomPss.length-1)) { 14069 oomPss[oomIndex] += myTotalPss; 14070 if (oomProcs[oomIndex] == null) { 14071 oomProcs[oomIndex] = new ArrayList<MemItem>(); 14072 } 14073 oomProcs[oomIndex].add(pssItem); 14074 break; 14075 } 14076 } 14077 } 14078 } 14079 } 14080 14081 long nativeProcTotalPss = 0; 14082 14083 if (!isCheckinRequest && procs.size() > 1 && !packages) { 14084 // If we are showing aggregations, also look for native processes to 14085 // include so that our aggregations are more accurate. 14086 updateCpuStatsNow(); 14087 synchronized (mProcessCpuTracker) { 14088 final int N = mProcessCpuTracker.countStats(); 14089 for (int i=0; i<N; i++) { 14090 ProcessCpuTracker.Stats st = mProcessCpuTracker.getStats(i); 14091 if (st.vsize > 0 && procMemsMap.indexOfKey(st.pid) < 0) { 14092 if (mi == null) { 14093 mi = new Debug.MemoryInfo(); 14094 } 14095 if (!brief && !oomOnly) { 14096 Debug.getMemoryInfo(st.pid, mi); 14097 } else { 14098 mi.nativePss = (int)Debug.getPss(st.pid, tmpLong); 14099 mi.nativePrivateDirty = (int)tmpLong[0]; 14100 } 14101 14102 final long myTotalPss = mi.getTotalPss(); 14103 totalPss += myTotalPss; 14104 nativeProcTotalPss += myTotalPss; 14105 14106 MemItem pssItem = new MemItem(st.name + " (pid " + st.pid + ")", 14107 st.name, myTotalPss, st.pid, false); 14108 procMems.add(pssItem); 14109 14110 nativePss += mi.nativePss; 14111 dalvikPss += mi.dalvikPss; 14112 otherPss += mi.otherPss; 14113 for (int j=0; j<Debug.MemoryInfo.NUM_OTHER_STATS; j++) { 14114 long mem = mi.getOtherPss(j); 14115 miscPss[j] += mem; 14116 otherPss -= mem; 14117 } 14118 oomPss[0] += myTotalPss; 14119 if (oomProcs[0] == null) { 14120 oomProcs[0] = new ArrayList<MemItem>(); 14121 } 14122 oomProcs[0].add(pssItem); 14123 } 14124 } 14125 } 14126 14127 ArrayList<MemItem> catMems = new ArrayList<MemItem>(); 14128 14129 catMems.add(new MemItem("Native", "Native", nativePss, -1)); 14130 catMems.add(new MemItem("Dalvik", "Dalvik", dalvikPss, -2)); 14131 catMems.add(new MemItem("Unknown", "Unknown", otherPss, -3)); 14132 for (int j=0; j<Debug.MemoryInfo.NUM_OTHER_STATS; j++) { 14133 String label = Debug.MemoryInfo.getOtherLabel(j); 14134 catMems.add(new MemItem(label, label, miscPss[j], j)); 14135 } 14136 14137 ArrayList<MemItem> oomMems = new ArrayList<MemItem>(); 14138 for (int j=0; j<oomPss.length; j++) { 14139 if (oomPss[j] != 0) { 14140 String label = isCompact ? DUMP_MEM_OOM_COMPACT_LABEL[j] 14141 : DUMP_MEM_OOM_LABEL[j]; 14142 MemItem item = new MemItem(label, label, oomPss[j], 14143 DUMP_MEM_OOM_ADJ[j]); 14144 item.subitems = oomProcs[j]; 14145 oomMems.add(item); 14146 } 14147 } 14148 14149 if (!brief && !oomOnly && !isCompact) { 14150 pw.println(); 14151 pw.println("Total PSS by process:"); 14152 dumpMemItems(pw, " ", "proc", procMems, true, isCompact); 14153 pw.println(); 14154 } 14155 if (!isCompact) { 14156 pw.println("Total PSS by OOM adjustment:"); 14157 } 14158 dumpMemItems(pw, " ", "oom", oomMems, false, isCompact); 14159 if (!brief && !oomOnly) { 14160 PrintWriter out = categoryPw != null ? categoryPw : pw; 14161 if (!isCompact) { 14162 out.println(); 14163 out.println("Total PSS by category:"); 14164 } 14165 dumpMemItems(out, " ", "cat", catMems, true, isCompact); 14166 } 14167 if (!isCompact) { 14168 pw.println(); 14169 } 14170 MemInfoReader memInfo = new MemInfoReader(); 14171 memInfo.readMemInfo(); 14172 if (nativeProcTotalPss > 0) { 14173 synchronized (this) { 14174 mProcessStats.addSysMemUsageLocked(memInfo.getCachedSizeKb(), 14175 memInfo.getFreeSizeKb(), memInfo.getZramTotalSizeKb(), 14176 memInfo.getKernelUsedSizeKb(), nativeProcTotalPss); 14177 } 14178 } 14179 if (!brief) { 14180 if (!isCompact) { 14181 pw.print("Total RAM: "); pw.print(memInfo.getTotalSizeKb()); 14182 pw.print(" kB (status "); 14183 switch (mLastMemoryLevel) { 14184 case ProcessStats.ADJ_MEM_FACTOR_NORMAL: 14185 pw.println("normal)"); 14186 break; 14187 case ProcessStats.ADJ_MEM_FACTOR_MODERATE: 14188 pw.println("moderate)"); 14189 break; 14190 case ProcessStats.ADJ_MEM_FACTOR_LOW: 14191 pw.println("low)"); 14192 break; 14193 case ProcessStats.ADJ_MEM_FACTOR_CRITICAL: 14194 pw.println("critical)"); 14195 break; 14196 default: 14197 pw.print(mLastMemoryLevel); 14198 pw.println(")"); 14199 break; 14200 } 14201 pw.print(" Free RAM: "); pw.print(cachedPss + memInfo.getCachedSizeKb() 14202 + memInfo.getFreeSizeKb()); pw.print(" kB ("); 14203 pw.print(cachedPss); pw.print(" cached pss + "); 14204 pw.print(memInfo.getCachedSizeKb()); pw.print(" cached kernel + "); 14205 pw.print(memInfo.getFreeSizeKb()); pw.println(" free)"); 14206 } else { 14207 pw.print("ram,"); pw.print(memInfo.getTotalSizeKb()); pw.print(","); 14208 pw.print(cachedPss + memInfo.getCachedSizeKb() 14209 + memInfo.getFreeSizeKb()); pw.print(","); 14210 pw.println(totalPss - cachedPss); 14211 } 14212 } 14213 if (!isCompact) { 14214 pw.print(" Used RAM: "); pw.print(totalPss - cachedPss 14215 + memInfo.getKernelUsedSizeKb()); pw.print(" kB ("); 14216 pw.print(totalPss - cachedPss); pw.print(" used pss + "); 14217 pw.print(memInfo.getKernelUsedSizeKb()); pw.print(" kernel)\n"); 14218 pw.print(" Lost RAM: "); pw.print(memInfo.getTotalSizeKb() 14219 - totalPss - memInfo.getFreeSizeKb() - memInfo.getCachedSizeKb() 14220 - memInfo.getKernelUsedSizeKb()); pw.println(" kB"); 14221 } 14222 if (!brief) { 14223 if (memInfo.getZramTotalSizeKb() != 0) { 14224 if (!isCompact) { 14225 pw.print(" ZRAM: "); pw.print(memInfo.getZramTotalSizeKb()); 14226 pw.print(" kB physical used for "); 14227 pw.print(memInfo.getSwapTotalSizeKb() 14228 - memInfo.getSwapFreeSizeKb()); 14229 pw.print(" kB in swap ("); 14230 pw.print(memInfo.getSwapTotalSizeKb()); 14231 pw.println(" kB total swap)"); 14232 } else { 14233 pw.print("zram,"); pw.print(memInfo.getZramTotalSizeKb()); pw.print(","); 14234 pw.print(memInfo.getSwapTotalSizeKb()); pw.print(","); 14235 pw.println(memInfo.getSwapFreeSizeKb()); 14236 } 14237 } 14238 final long[] ksm = getKsmInfo(); 14239 if (!isCompact) { 14240 if (ksm[KSM_SHARING] != 0 || ksm[KSM_SHARED] != 0 || ksm[KSM_UNSHARED] != 0 14241 || ksm[KSM_VOLATILE] != 0) { 14242 pw.print(" KSM: "); pw.print(ksm[KSM_SHARING]); 14243 pw.print(" kB saved from shared "); 14244 pw.print(ksm[KSM_SHARED]); pw.println(" kB"); 14245 pw.print(" "); pw.print(ksm[KSM_UNSHARED]); 14246 pw.print(" kB unshared; "); 14247 pw.print(ksm[KSM_VOLATILE]); pw.println(" kB volatile"); 14248 } 14249 pw.print(" Tuning: "); 14250 pw.print(ActivityManager.staticGetMemoryClass()); 14251 pw.print(" (large "); 14252 pw.print(ActivityManager.staticGetLargeMemoryClass()); 14253 pw.print("), oom "); 14254 pw.print(mProcessList.getMemLevel(ProcessList.CACHED_APP_MAX_ADJ)/1024); 14255 pw.print(" kB"); 14256 pw.print(", restore limit "); 14257 pw.print(mProcessList.getCachedRestoreThresholdKb()); 14258 pw.print(" kB"); 14259 if (ActivityManager.isLowRamDeviceStatic()) { 14260 pw.print(" (low-ram)"); 14261 } 14262 if (ActivityManager.isHighEndGfx()) { 14263 pw.print(" (high-end-gfx)"); 14264 } 14265 pw.println(); 14266 } else { 14267 pw.print("ksm,"); pw.print(ksm[KSM_SHARING]); pw.print(","); 14268 pw.print(ksm[KSM_SHARED]); pw.print(","); pw.print(ksm[KSM_UNSHARED]); 14269 pw.print(","); pw.println(ksm[KSM_VOLATILE]); 14270 pw.print("tuning,"); 14271 pw.print(ActivityManager.staticGetMemoryClass()); 14272 pw.print(','); 14273 pw.print(ActivityManager.staticGetLargeMemoryClass()); 14274 pw.print(','); 14275 pw.print(mProcessList.getMemLevel(ProcessList.CACHED_APP_MAX_ADJ)/1024); 14276 if (ActivityManager.isLowRamDeviceStatic()) { 14277 pw.print(",low-ram"); 14278 } 14279 if (ActivityManager.isHighEndGfx()) { 14280 pw.print(",high-end-gfx"); 14281 } 14282 pw.println(); 14283 } 14284 } 14285 } 14286 } 14287 14288 private void appendBasicMemEntry(StringBuilder sb, int oomAdj, int procState, long pss, 14289 String name) { 14290 sb.append(" "); 14291 sb.append(ProcessList.makeOomAdjString(oomAdj)); 14292 sb.append(' '); 14293 sb.append(ProcessList.makeProcStateString(procState)); 14294 sb.append(' '); 14295 ProcessList.appendRamKb(sb, pss); 14296 sb.append(" kB: "); 14297 sb.append(name); 14298 } 14299 14300 private void appendMemInfo(StringBuilder sb, ProcessMemInfo mi) { 14301 appendBasicMemEntry(sb, mi.oomAdj, mi.procState, mi.pss, mi.name); 14302 sb.append(" ("); 14303 sb.append(mi.pid); 14304 sb.append(") "); 14305 sb.append(mi.adjType); 14306 sb.append('\n'); 14307 if (mi.adjReason != null) { 14308 sb.append(" "); 14309 sb.append(mi.adjReason); 14310 sb.append('\n'); 14311 } 14312 } 14313 14314 void reportMemUsage(ArrayList<ProcessMemInfo> memInfos) { 14315 final SparseArray<ProcessMemInfo> infoMap = new SparseArray<>(memInfos.size()); 14316 for (int i=0, N=memInfos.size(); i<N; i++) { 14317 ProcessMemInfo mi = memInfos.get(i); 14318 infoMap.put(mi.pid, mi); 14319 } 14320 updateCpuStatsNow(); 14321 synchronized (mProcessCpuTracker) { 14322 final int N = mProcessCpuTracker.countStats(); 14323 for (int i=0; i<N; i++) { 14324 ProcessCpuTracker.Stats st = mProcessCpuTracker.getStats(i); 14325 if (st.vsize > 0) { 14326 long pss = Debug.getPss(st.pid, null); 14327 if (pss > 0) { 14328 if (infoMap.indexOfKey(st.pid) < 0) { 14329 ProcessMemInfo mi = new ProcessMemInfo(st.name, st.pid, 14330 ProcessList.NATIVE_ADJ, -1, "native", null); 14331 mi.pss = pss; 14332 memInfos.add(mi); 14333 } 14334 } 14335 } 14336 } 14337 } 14338 14339 long totalPss = 0; 14340 for (int i=0, N=memInfos.size(); i<N; i++) { 14341 ProcessMemInfo mi = memInfos.get(i); 14342 if (mi.pss == 0) { 14343 mi.pss = Debug.getPss(mi.pid, null); 14344 } 14345 totalPss += mi.pss; 14346 } 14347 Collections.sort(memInfos, new Comparator<ProcessMemInfo>() { 14348 @Override public int compare(ProcessMemInfo lhs, ProcessMemInfo rhs) { 14349 if (lhs.oomAdj != rhs.oomAdj) { 14350 return lhs.oomAdj < rhs.oomAdj ? -1 : 1; 14351 } 14352 if (lhs.pss != rhs.pss) { 14353 return lhs.pss < rhs.pss ? 1 : -1; 14354 } 14355 return 0; 14356 } 14357 }); 14358 14359 StringBuilder tag = new StringBuilder(128); 14360 StringBuilder stack = new StringBuilder(128); 14361 tag.append("Low on memory -- "); 14362 appendMemBucket(tag, totalPss, "total", false); 14363 appendMemBucket(stack, totalPss, "total", true); 14364 14365 StringBuilder fullNativeBuilder = new StringBuilder(1024); 14366 StringBuilder shortNativeBuilder = new StringBuilder(1024); 14367 StringBuilder fullJavaBuilder = new StringBuilder(1024); 14368 14369 boolean firstLine = true; 14370 int lastOomAdj = Integer.MIN_VALUE; 14371 long extraNativeRam = 0; 14372 long cachedPss = 0; 14373 for (int i=0, N=memInfos.size(); i<N; i++) { 14374 ProcessMemInfo mi = memInfos.get(i); 14375 14376 if (mi.oomAdj >= ProcessList.CACHED_APP_MIN_ADJ) { 14377 cachedPss += mi.pss; 14378 } 14379 14380 if (mi.oomAdj != ProcessList.NATIVE_ADJ 14381 && (mi.oomAdj < ProcessList.SERVICE_ADJ 14382 || mi.oomAdj == ProcessList.HOME_APP_ADJ 14383 || mi.oomAdj == ProcessList.PREVIOUS_APP_ADJ)) { 14384 if (lastOomAdj != mi.oomAdj) { 14385 lastOomAdj = mi.oomAdj; 14386 if (mi.oomAdj <= ProcessList.FOREGROUND_APP_ADJ) { 14387 tag.append(" / "); 14388 } 14389 if (mi.oomAdj >= ProcessList.FOREGROUND_APP_ADJ) { 14390 if (firstLine) { 14391 stack.append(":"); 14392 firstLine = false; 14393 } 14394 stack.append("\n\t at "); 14395 } else { 14396 stack.append("$"); 14397 } 14398 } else { 14399 tag.append(" "); 14400 stack.append("$"); 14401 } 14402 if (mi.oomAdj <= ProcessList.FOREGROUND_APP_ADJ) { 14403 appendMemBucket(tag, mi.pss, mi.name, false); 14404 } 14405 appendMemBucket(stack, mi.pss, mi.name, true); 14406 if (mi.oomAdj >= ProcessList.FOREGROUND_APP_ADJ 14407 && ((i+1) >= N || memInfos.get(i+1).oomAdj != lastOomAdj)) { 14408 stack.append("("); 14409 for (int k=0; k<DUMP_MEM_OOM_ADJ.length; k++) { 14410 if (DUMP_MEM_OOM_ADJ[k] == mi.oomAdj) { 14411 stack.append(DUMP_MEM_OOM_LABEL[k]); 14412 stack.append(":"); 14413 stack.append(DUMP_MEM_OOM_ADJ[k]); 14414 } 14415 } 14416 stack.append(")"); 14417 } 14418 } 14419 14420 appendMemInfo(fullNativeBuilder, mi); 14421 if (mi.oomAdj == ProcessList.NATIVE_ADJ) { 14422 // The short form only has native processes that are >= 1MB. 14423 if (mi.pss >= 1000) { 14424 appendMemInfo(shortNativeBuilder, mi); 14425 } else { 14426 extraNativeRam += mi.pss; 14427 } 14428 } else { 14429 // Short form has all other details, but if we have collected RAM 14430 // from smaller native processes let's dump a summary of that. 14431 if (extraNativeRam > 0) { 14432 appendBasicMemEntry(shortNativeBuilder, ProcessList.NATIVE_ADJ, 14433 -1, extraNativeRam, "(Other native)"); 14434 shortNativeBuilder.append('\n'); 14435 extraNativeRam = 0; 14436 } 14437 appendMemInfo(fullJavaBuilder, mi); 14438 } 14439 } 14440 14441 fullJavaBuilder.append(" "); 14442 ProcessList.appendRamKb(fullJavaBuilder, totalPss); 14443 fullJavaBuilder.append(" kB: TOTAL\n"); 14444 14445 MemInfoReader memInfo = new MemInfoReader(); 14446 memInfo.readMemInfo(); 14447 final long[] infos = memInfo.getRawInfo(); 14448 14449 StringBuilder memInfoBuilder = new StringBuilder(1024); 14450 Debug.getMemInfo(infos); 14451 memInfoBuilder.append(" MemInfo: "); 14452 memInfoBuilder.append(infos[Debug.MEMINFO_SLAB]).append(" kB slab, "); 14453 memInfoBuilder.append(infos[Debug.MEMINFO_SHMEM]).append(" kB shmem, "); 14454 memInfoBuilder.append(infos[Debug.MEMINFO_VM_ALLOC_USED]).append(" kB vm alloc, "); 14455 memInfoBuilder.append(infos[Debug.MEMINFO_PAGE_TABLES]).append(" kB page tables "); 14456 memInfoBuilder.append(infos[Debug.MEMINFO_KERNEL_STACK]).append(" kB kernel stack\n"); 14457 memInfoBuilder.append(" "); 14458 memInfoBuilder.append(infos[Debug.MEMINFO_BUFFERS]).append(" kB buffers, "); 14459 memInfoBuilder.append(infos[Debug.MEMINFO_CACHED]).append(" kB cached, "); 14460 memInfoBuilder.append(infos[Debug.MEMINFO_MAPPED]).append(" kB mapped, "); 14461 memInfoBuilder.append(infos[Debug.MEMINFO_FREE]).append(" kB free\n"); 14462 if (infos[Debug.MEMINFO_ZRAM_TOTAL] != 0) { 14463 memInfoBuilder.append(" ZRAM: "); 14464 memInfoBuilder.append(infos[Debug.MEMINFO_ZRAM_TOTAL]); 14465 memInfoBuilder.append(" kB RAM, "); 14466 memInfoBuilder.append(infos[Debug.MEMINFO_SWAP_TOTAL]); 14467 memInfoBuilder.append(" kB swap total, "); 14468 memInfoBuilder.append(infos[Debug.MEMINFO_SWAP_FREE]); 14469 memInfoBuilder.append(" kB swap free\n"); 14470 } 14471 final long[] ksm = getKsmInfo(); 14472 if (ksm[KSM_SHARING] != 0 || ksm[KSM_SHARED] != 0 || ksm[KSM_UNSHARED] != 0 14473 || ksm[KSM_VOLATILE] != 0) { 14474 memInfoBuilder.append(" KSM: "); memInfoBuilder.append(ksm[KSM_SHARING]); 14475 memInfoBuilder.append(" kB saved from shared "); 14476 memInfoBuilder.append(ksm[KSM_SHARED]); memInfoBuilder.append(" kB\n"); 14477 memInfoBuilder.append(" "); memInfoBuilder.append(ksm[KSM_UNSHARED]); 14478 memInfoBuilder.append(" kB unshared; "); 14479 memInfoBuilder.append(ksm[KSM_VOLATILE]); memInfoBuilder.append(" kB volatile\n"); 14480 } 14481 memInfoBuilder.append(" Free RAM: "); 14482 memInfoBuilder.append(cachedPss + memInfo.getCachedSizeKb() 14483 + memInfo.getFreeSizeKb()); 14484 memInfoBuilder.append(" kB\n"); 14485 memInfoBuilder.append(" Used RAM: "); 14486 memInfoBuilder.append(totalPss - cachedPss + memInfo.getKernelUsedSizeKb()); 14487 memInfoBuilder.append(" kB\n"); 14488 memInfoBuilder.append(" Lost RAM: "); 14489 memInfoBuilder.append(memInfo.getTotalSizeKb() 14490 - totalPss - memInfo.getFreeSizeKb() - memInfo.getCachedSizeKb() 14491 - memInfo.getKernelUsedSizeKb()); 14492 memInfoBuilder.append(" kB\n"); 14493 Slog.i(TAG, "Low on memory:"); 14494 Slog.i(TAG, shortNativeBuilder.toString()); 14495 Slog.i(TAG, fullJavaBuilder.toString()); 14496 Slog.i(TAG, memInfoBuilder.toString()); 14497 14498 StringBuilder dropBuilder = new StringBuilder(1024); 14499 /* 14500 StringWriter oomSw = new StringWriter(); 14501 PrintWriter oomPw = new FastPrintWriter(oomSw, false, 256); 14502 StringWriter catSw = new StringWriter(); 14503 PrintWriter catPw = new FastPrintWriter(catSw, false, 256); 14504 String[] emptyArgs = new String[] { }; 14505 dumpApplicationMemoryUsage(null, oomPw, " ", emptyArgs, true, catPw); 14506 oomPw.flush(); 14507 String oomString = oomSw.toString(); 14508 */ 14509 dropBuilder.append("Low on memory:"); 14510 dropBuilder.append(stack); 14511 dropBuilder.append('\n'); 14512 dropBuilder.append(fullNativeBuilder); 14513 dropBuilder.append(fullJavaBuilder); 14514 dropBuilder.append('\n'); 14515 dropBuilder.append(memInfoBuilder); 14516 dropBuilder.append('\n'); 14517 /* 14518 dropBuilder.append(oomString); 14519 dropBuilder.append('\n'); 14520 */ 14521 StringWriter catSw = new StringWriter(); 14522 synchronized (ActivityManagerService.this) { 14523 PrintWriter catPw = new FastPrintWriter(catSw, false, 256); 14524 String[] emptyArgs = new String[] { }; 14525 catPw.println(); 14526 dumpProcessesLocked(null, catPw, emptyArgs, 0, false, null); 14527 catPw.println(); 14528 mServices.dumpServicesLocked(null, catPw, emptyArgs, 0, 14529 false, false, null); 14530 catPw.println(); 14531 dumpActivitiesLocked(null, catPw, emptyArgs, 0, false, false, null); 14532 catPw.flush(); 14533 } 14534 dropBuilder.append(catSw.toString()); 14535 addErrorToDropBox("lowmem", null, "system_server", null, 14536 null, tag.toString(), dropBuilder.toString(), null, null); 14537 //Slog.i(TAG, "Sent to dropbox:"); 14538 //Slog.i(TAG, dropBuilder.toString()); 14539 synchronized (ActivityManagerService.this) { 14540 long now = SystemClock.uptimeMillis(); 14541 if (mLastMemUsageReportTime < now) { 14542 mLastMemUsageReportTime = now; 14543 } 14544 } 14545 } 14546 14547 /** 14548 * Searches array of arguments for the specified string 14549 * @param args array of argument strings 14550 * @param value value to search for 14551 * @return true if the value is contained in the array 14552 */ 14553 private static boolean scanArgs(String[] args, String value) { 14554 if (args != null) { 14555 for (String arg : args) { 14556 if (value.equals(arg)) { 14557 return true; 14558 } 14559 } 14560 } 14561 return false; 14562 } 14563 14564 private final boolean removeDyingProviderLocked(ProcessRecord proc, 14565 ContentProviderRecord cpr, boolean always) { 14566 final boolean inLaunching = mLaunchingProviders.contains(cpr); 14567 14568 if (!inLaunching || always) { 14569 synchronized (cpr) { 14570 cpr.launchingApp = null; 14571 cpr.notifyAll(); 14572 } 14573 mProviderMap.removeProviderByClass(cpr.name, UserHandle.getUserId(cpr.uid)); 14574 String names[] = cpr.info.authority.split(";"); 14575 for (int j = 0; j < names.length; j++) { 14576 mProviderMap.removeProviderByName(names[j], UserHandle.getUserId(cpr.uid)); 14577 } 14578 } 14579 14580 for (int i=0; i<cpr.connections.size(); i++) { 14581 ContentProviderConnection conn = cpr.connections.get(i); 14582 if (conn.waiting) { 14583 // If this connection is waiting for the provider, then we don't 14584 // need to mess with its process unless we are always removing 14585 // or for some reason the provider is not currently launching. 14586 if (inLaunching && !always) { 14587 continue; 14588 } 14589 } 14590 ProcessRecord capp = conn.client; 14591 conn.dead = true; 14592 if (conn.stableCount > 0) { 14593 if (!capp.persistent && capp.thread != null 14594 && capp.pid != 0 14595 && capp.pid != MY_PID) { 14596 capp.kill("depends on provider " 14597 + cpr.name.flattenToShortString() 14598 + " in dying proc " + (proc != null ? proc.processName : "??"), true); 14599 } 14600 } else if (capp.thread != null && conn.provider.provider != null) { 14601 try { 14602 capp.thread.unstableProviderDied(conn.provider.provider.asBinder()); 14603 } catch (RemoteException e) { 14604 } 14605 // In the protocol here, we don't expect the client to correctly 14606 // clean up this connection, we'll just remove it. 14607 cpr.connections.remove(i); 14608 conn.client.conProviders.remove(conn); 14609 } 14610 } 14611 14612 if (inLaunching && always) { 14613 mLaunchingProviders.remove(cpr); 14614 } 14615 return inLaunching; 14616 } 14617 14618 /** 14619 * Main code for cleaning up a process when it has gone away. This is 14620 * called both as a result of the process dying, or directly when stopping 14621 * a process when running in single process mode. 14622 * 14623 * @return Returns true if the given process has been restarted, so the 14624 * app that was passed in must remain on the process lists. 14625 */ 14626 private final boolean cleanUpApplicationRecordLocked(ProcessRecord app, 14627 boolean restarting, boolean allowRestart, int index) { 14628 if (index >= 0) { 14629 removeLruProcessLocked(app); 14630 ProcessList.remove(app.pid); 14631 } 14632 14633 mProcessesToGc.remove(app); 14634 mPendingPssProcesses.remove(app); 14635 14636 // Dismiss any open dialogs. 14637 if (app.crashDialog != null && !app.forceCrashReport) { 14638 app.crashDialog.dismiss(); 14639 app.crashDialog = null; 14640 } 14641 if (app.anrDialog != null) { 14642 app.anrDialog.dismiss(); 14643 app.anrDialog = null; 14644 } 14645 if (app.waitDialog != null) { 14646 app.waitDialog.dismiss(); 14647 app.waitDialog = null; 14648 } 14649 14650 app.crashing = false; 14651 app.notResponding = false; 14652 14653 app.resetPackageList(mProcessStats); 14654 app.unlinkDeathRecipient(); 14655 app.makeInactive(mProcessStats); 14656 app.waitingToKill = null; 14657 app.forcingToForeground = null; 14658 updateProcessForegroundLocked(app, false, false); 14659 app.foregroundActivities = false; 14660 app.hasShownUi = false; 14661 app.treatLikeActivity = false; 14662 app.hasAboveClient = false; 14663 app.hasClientActivities = false; 14664 14665 mServices.killServicesLocked(app, allowRestart); 14666 14667 boolean restart = false; 14668 14669 // Remove published content providers. 14670 for (int i=app.pubProviders.size()-1; i>=0; i--) { 14671 ContentProviderRecord cpr = app.pubProviders.valueAt(i); 14672 final boolean always = app.bad || !allowRestart; 14673 if (removeDyingProviderLocked(app, cpr, always) || always) { 14674 // We left the provider in the launching list, need to 14675 // restart it. 14676 restart = true; 14677 } 14678 14679 cpr.provider = null; 14680 cpr.proc = null; 14681 } 14682 app.pubProviders.clear(); 14683 14684 // Take care of any launching providers waiting for this process. 14685 if (checkAppInLaunchingProvidersLocked(app, false)) { 14686 restart = true; 14687 } 14688 14689 // Unregister from connected content providers. 14690 if (!app.conProviders.isEmpty()) { 14691 for (int i=0; i<app.conProviders.size(); i++) { 14692 ContentProviderConnection conn = app.conProviders.get(i); 14693 conn.provider.connections.remove(conn); 14694 } 14695 app.conProviders.clear(); 14696 } 14697 14698 // At this point there may be remaining entries in mLaunchingProviders 14699 // where we were the only one waiting, so they are no longer of use. 14700 // Look for these and clean up if found. 14701 // XXX Commented out for now. Trying to figure out a way to reproduce 14702 // the actual situation to identify what is actually going on. 14703 if (false) { 14704 for (int i=0; i<mLaunchingProviders.size(); i++) { 14705 ContentProviderRecord cpr = (ContentProviderRecord) 14706 mLaunchingProviders.get(i); 14707 if (cpr.connections.size() <= 0 && !cpr.hasExternalProcessHandles()) { 14708 synchronized (cpr) { 14709 cpr.launchingApp = null; 14710 cpr.notifyAll(); 14711 } 14712 } 14713 } 14714 } 14715 14716 skipCurrentReceiverLocked(app); 14717 14718 // Unregister any receivers. 14719 for (int i=app.receivers.size()-1; i>=0; i--) { 14720 removeReceiverLocked(app.receivers.valueAt(i)); 14721 } 14722 app.receivers.clear(); 14723 14724 // If the app is undergoing backup, tell the backup manager about it 14725 if (mBackupTarget != null && app.pid == mBackupTarget.app.pid) { 14726 if (DEBUG_BACKUP || DEBUG_CLEANUP) Slog.d(TAG, "App " 14727 + mBackupTarget.appInfo + " died during backup"); 14728 try { 14729 IBackupManager bm = IBackupManager.Stub.asInterface( 14730 ServiceManager.getService(Context.BACKUP_SERVICE)); 14731 bm.agentDisconnected(app.info.packageName); 14732 } catch (RemoteException e) { 14733 // can't happen; backup manager is local 14734 } 14735 } 14736 14737 for (int i = mPendingProcessChanges.size()-1; i>=0; i--) { 14738 ProcessChangeItem item = mPendingProcessChanges.get(i); 14739 if (item.pid == app.pid) { 14740 mPendingProcessChanges.remove(i); 14741 mAvailProcessChanges.add(item); 14742 } 14743 } 14744 mHandler.obtainMessage(DISPATCH_PROCESS_DIED, app.pid, app.info.uid, null).sendToTarget(); 14745 14746 // If the caller is restarting this app, then leave it in its 14747 // current lists and let the caller take care of it. 14748 if (restarting) { 14749 return false; 14750 } 14751 14752 if (!app.persistent || app.isolated) { 14753 if (DEBUG_PROCESSES || DEBUG_CLEANUP) Slog.v(TAG, 14754 "Removing non-persistent process during cleanup: " + app); 14755 mProcessNames.remove(app.processName, app.uid); 14756 mIsolatedProcesses.remove(app.uid); 14757 if (mHeavyWeightProcess == app) { 14758 mHandler.sendMessage(mHandler.obtainMessage(CANCEL_HEAVY_NOTIFICATION_MSG, 14759 mHeavyWeightProcess.userId, 0)); 14760 mHeavyWeightProcess = null; 14761 } 14762 } else if (!app.removed) { 14763 // This app is persistent, so we need to keep its record around. 14764 // If it is not already on the pending app list, add it there 14765 // and start a new process for it. 14766 if (mPersistentStartingProcesses.indexOf(app) < 0) { 14767 mPersistentStartingProcesses.add(app); 14768 restart = true; 14769 } 14770 } 14771 if ((DEBUG_PROCESSES || DEBUG_CLEANUP) && mProcessesOnHold.contains(app)) Slog.v(TAG, 14772 "Clean-up removing on hold: " + app); 14773 mProcessesOnHold.remove(app); 14774 14775 if (app == mHomeProcess) { 14776 mHomeProcess = null; 14777 } 14778 if (app == mPreviousProcess) { 14779 mPreviousProcess = null; 14780 } 14781 14782 if (restart && !app.isolated) { 14783 // We have components that still need to be running in the 14784 // process, so re-launch it. 14785 if (index < 0) { 14786 ProcessList.remove(app.pid); 14787 } 14788 mProcessNames.put(app.processName, app.uid, app); 14789 startProcessLocked(app, "restart", app.processName); 14790 return true; 14791 } else if (app.pid > 0 && app.pid != MY_PID) { 14792 // Goodbye! 14793 boolean removed; 14794 synchronized (mPidsSelfLocked) { 14795 mPidsSelfLocked.remove(app.pid); 14796 mHandler.removeMessages(PROC_START_TIMEOUT_MSG, app); 14797 } 14798 mBatteryStatsService.noteProcessFinish(app.processName, app.info.uid); 14799 if (app.isolated) { 14800 mBatteryStatsService.removeIsolatedUid(app.uid, app.info.uid); 14801 } 14802 app.setPid(0); 14803 } 14804 return false; 14805 } 14806 14807 boolean checkAppInLaunchingProvidersLocked(ProcessRecord app, boolean alwaysBad) { 14808 // Look through the content providers we are waiting to have launched, 14809 // and if any run in this process then either schedule a restart of 14810 // the process or kill the client waiting for it if this process has 14811 // gone bad. 14812 int NL = mLaunchingProviders.size(); 14813 boolean restart = false; 14814 for (int i=0; i<NL; i++) { 14815 ContentProviderRecord cpr = mLaunchingProviders.get(i); 14816 if (cpr.launchingApp == app) { 14817 if (!alwaysBad && !app.bad) { 14818 restart = true; 14819 } else { 14820 removeDyingProviderLocked(app, cpr, true); 14821 // cpr should have been removed from mLaunchingProviders 14822 NL = mLaunchingProviders.size(); 14823 i--; 14824 } 14825 } 14826 } 14827 return restart; 14828 } 14829 14830 // ========================================================= 14831 // SERVICES 14832 // ========================================================= 14833 14834 @Override 14835 public List<ActivityManager.RunningServiceInfo> getServices(int maxNum, 14836 int flags) { 14837 enforceNotIsolatedCaller("getServices"); 14838 synchronized (this) { 14839 return mServices.getRunningServiceInfoLocked(maxNum, flags); 14840 } 14841 } 14842 14843 @Override 14844 public PendingIntent getRunningServiceControlPanel(ComponentName name) { 14845 enforceNotIsolatedCaller("getRunningServiceControlPanel"); 14846 synchronized (this) { 14847 return mServices.getRunningServiceControlPanelLocked(name); 14848 } 14849 } 14850 14851 @Override 14852 public ComponentName startService(IApplicationThread caller, Intent service, 14853 String resolvedType, int userId) { 14854 enforceNotIsolatedCaller("startService"); 14855 // Refuse possible leaked file descriptors 14856 if (service != null && service.hasFileDescriptors() == true) { 14857 throw new IllegalArgumentException("File descriptors passed in Intent"); 14858 } 14859 14860 if (DEBUG_SERVICE) 14861 Slog.v(TAG, "startService: " + service + " type=" + resolvedType); 14862 synchronized(this) { 14863 final int callingPid = Binder.getCallingPid(); 14864 final int callingUid = Binder.getCallingUid(); 14865 final long origId = Binder.clearCallingIdentity(); 14866 ComponentName res = mServices.startServiceLocked(caller, service, 14867 resolvedType, callingPid, callingUid, userId); 14868 Binder.restoreCallingIdentity(origId); 14869 return res; 14870 } 14871 } 14872 14873 ComponentName startServiceInPackage(int uid, 14874 Intent service, String resolvedType, int userId) { 14875 synchronized(this) { 14876 if (DEBUG_SERVICE) 14877 Slog.v(TAG, "startServiceInPackage: " + service + " type=" + resolvedType); 14878 final long origId = Binder.clearCallingIdentity(); 14879 ComponentName res = mServices.startServiceLocked(null, service, 14880 resolvedType, -1, uid, userId); 14881 Binder.restoreCallingIdentity(origId); 14882 return res; 14883 } 14884 } 14885 14886 @Override 14887 public int stopService(IApplicationThread caller, Intent service, 14888 String resolvedType, int userId) { 14889 enforceNotIsolatedCaller("stopService"); 14890 // Refuse possible leaked file descriptors 14891 if (service != null && service.hasFileDescriptors() == true) { 14892 throw new IllegalArgumentException("File descriptors passed in Intent"); 14893 } 14894 14895 synchronized(this) { 14896 return mServices.stopServiceLocked(caller, service, resolvedType, userId); 14897 } 14898 } 14899 14900 @Override 14901 public IBinder peekService(Intent service, String resolvedType) { 14902 enforceNotIsolatedCaller("peekService"); 14903 // Refuse possible leaked file descriptors 14904 if (service != null && service.hasFileDescriptors() == true) { 14905 throw new IllegalArgumentException("File descriptors passed in Intent"); 14906 } 14907 synchronized(this) { 14908 return mServices.peekServiceLocked(service, resolvedType); 14909 } 14910 } 14911 14912 @Override 14913 public boolean stopServiceToken(ComponentName className, IBinder token, 14914 int startId) { 14915 synchronized(this) { 14916 return mServices.stopServiceTokenLocked(className, token, startId); 14917 } 14918 } 14919 14920 @Override 14921 public void setServiceForeground(ComponentName className, IBinder token, 14922 int id, Notification notification, boolean removeNotification) { 14923 synchronized(this) { 14924 mServices.setServiceForegroundLocked(className, token, id, notification, 14925 removeNotification); 14926 } 14927 } 14928 14929 @Override 14930 public int handleIncomingUser(int callingPid, int callingUid, int userId, boolean allowAll, 14931 boolean requireFull, String name, String callerPackage) { 14932 return handleIncomingUser(callingPid, callingUid, userId, allowAll, 14933 requireFull ? ALLOW_FULL_ONLY : ALLOW_NON_FULL, name, callerPackage); 14934 } 14935 14936 int unsafeConvertIncomingUser(int userId) { 14937 return (userId == UserHandle.USER_CURRENT || userId == UserHandle.USER_CURRENT_OR_SELF) 14938 ? mCurrentUserId : userId; 14939 } 14940 14941 int handleIncomingUser(int callingPid, int callingUid, int userId, boolean allowAll, 14942 int allowMode, String name, String callerPackage) { 14943 final int callingUserId = UserHandle.getUserId(callingUid); 14944 if (callingUserId == userId) { 14945 return userId; 14946 } 14947 14948 // Note that we may be accessing mCurrentUserId outside of a lock... 14949 // shouldn't be a big deal, if this is being called outside 14950 // of a locked context there is intrinsically a race with 14951 // the value the caller will receive and someone else changing it. 14952 // We assume that USER_CURRENT_OR_SELF will use the current user; later 14953 // we will switch to the calling user if access to the current user fails. 14954 int targetUserId = unsafeConvertIncomingUser(userId); 14955 14956 if (callingUid != 0 && callingUid != Process.SYSTEM_UID) { 14957 final boolean allow; 14958 if (checkComponentPermission(INTERACT_ACROSS_USERS_FULL, callingPid, 14959 callingUid, -1, true) == PackageManager.PERMISSION_GRANTED) { 14960 // If the caller has this permission, they always pass go. And collect $200. 14961 allow = true; 14962 } else if (allowMode == ALLOW_FULL_ONLY) { 14963 // We require full access, sucks to be you. 14964 allow = false; 14965 } else if (checkComponentPermission(INTERACT_ACROSS_USERS, callingPid, 14966 callingUid, -1, true) != PackageManager.PERMISSION_GRANTED) { 14967 // If the caller does not have either permission, they are always doomed. 14968 allow = false; 14969 } else if (allowMode == ALLOW_NON_FULL) { 14970 // We are blanket allowing non-full access, you lucky caller! 14971 allow = true; 14972 } else if (allowMode == ALLOW_NON_FULL_IN_PROFILE) { 14973 // We may or may not allow this depending on whether the two users are 14974 // in the same profile. 14975 synchronized (mUserProfileGroupIdsSelfLocked) { 14976 int callingProfile = mUserProfileGroupIdsSelfLocked.get(callingUserId, 14977 UserInfo.NO_PROFILE_GROUP_ID); 14978 int targetProfile = mUserProfileGroupIdsSelfLocked.get(targetUserId, 14979 UserInfo.NO_PROFILE_GROUP_ID); 14980 allow = callingProfile != UserInfo.NO_PROFILE_GROUP_ID 14981 && callingProfile == targetProfile; 14982 } 14983 } else { 14984 throw new IllegalArgumentException("Unknown mode: " + allowMode); 14985 } 14986 if (!allow) { 14987 if (userId == UserHandle.USER_CURRENT_OR_SELF) { 14988 // In this case, they would like to just execute as their 14989 // owner user instead of failing. 14990 targetUserId = callingUserId; 14991 } else { 14992 StringBuilder builder = new StringBuilder(128); 14993 builder.append("Permission Denial: "); 14994 builder.append(name); 14995 if (callerPackage != null) { 14996 builder.append(" from "); 14997 builder.append(callerPackage); 14998 } 14999 builder.append(" asks to run as user "); 15000 builder.append(userId); 15001 builder.append(" but is calling from user "); 15002 builder.append(UserHandle.getUserId(callingUid)); 15003 builder.append("; this requires "); 15004 builder.append(INTERACT_ACROSS_USERS_FULL); 15005 if (allowMode != ALLOW_FULL_ONLY) { 15006 builder.append(" or "); 15007 builder.append(INTERACT_ACROSS_USERS); 15008 } 15009 String msg = builder.toString(); 15010 Slog.w(TAG, msg); 15011 throw new SecurityException(msg); 15012 } 15013 } 15014 } 15015 if (!allowAll && targetUserId < 0) { 15016 throw new IllegalArgumentException( 15017 "Call does not support special user #" + targetUserId); 15018 } 15019 // Check shell permission 15020 if (callingUid == Process.SHELL_UID && targetUserId >= UserHandle.USER_OWNER) { 15021 if (mUserManager.hasUserRestriction(UserManager.DISALLOW_DEBUGGING_FEATURES, 15022 targetUserId)) { 15023 throw new SecurityException("Shell does not have permission to access user " 15024 + targetUserId + "\n " + Debug.getCallers(3)); 15025 } 15026 } 15027 return targetUserId; 15028 } 15029 15030 boolean isSingleton(String componentProcessName, ApplicationInfo aInfo, 15031 String className, int flags) { 15032 boolean result = false; 15033 // For apps that don't have pre-defined UIDs, check for permission 15034 if (UserHandle.getAppId(aInfo.uid) >= Process.FIRST_APPLICATION_UID) { 15035 if ((flags & ServiceInfo.FLAG_SINGLE_USER) != 0) { 15036 if (ActivityManager.checkUidPermission( 15037 INTERACT_ACROSS_USERS, 15038 aInfo.uid) != PackageManager.PERMISSION_GRANTED) { 15039 ComponentName comp = new ComponentName(aInfo.packageName, className); 15040 String msg = "Permission Denial: Component " + comp.flattenToShortString() 15041 + " requests FLAG_SINGLE_USER, but app does not hold " 15042 + INTERACT_ACROSS_USERS; 15043 Slog.w(TAG, msg); 15044 throw new SecurityException(msg); 15045 } 15046 // Permission passed 15047 result = true; 15048 } 15049 } else if ("system".equals(componentProcessName)) { 15050 result = true; 15051 } else if ((flags & ServiceInfo.FLAG_SINGLE_USER) != 0) { 15052 // Phone app and persistent apps are allowed to export singleuser providers. 15053 result = UserHandle.isSameApp(aInfo.uid, Process.PHONE_UID) 15054 || (aInfo.flags & ApplicationInfo.FLAG_PERSISTENT) != 0; 15055 } 15056 if (DEBUG_MU) { 15057 Slog.v(TAG, "isSingleton(" + componentProcessName + ", " + aInfo 15058 + ", " + className + ", 0x" + Integer.toHexString(flags) + ") = " + result); 15059 } 15060 return result; 15061 } 15062 15063 /** 15064 * Checks to see if the caller is in the same app as the singleton 15065 * component, or the component is in a special app. It allows special apps 15066 * to export singleton components but prevents exporting singleton 15067 * components for regular apps. 15068 */ 15069 boolean isValidSingletonCall(int callingUid, int componentUid) { 15070 int componentAppId = UserHandle.getAppId(componentUid); 15071 return UserHandle.isSameApp(callingUid, componentUid) 15072 || componentAppId == Process.SYSTEM_UID 15073 || componentAppId == Process.PHONE_UID 15074 || ActivityManager.checkUidPermission(INTERACT_ACROSS_USERS_FULL, componentUid) 15075 == PackageManager.PERMISSION_GRANTED; 15076 } 15077 15078 public int bindService(IApplicationThread caller, IBinder token, 15079 Intent service, String resolvedType, 15080 IServiceConnection connection, int flags, int userId) { 15081 enforceNotIsolatedCaller("bindService"); 15082 15083 // Refuse possible leaked file descriptors 15084 if (service != null && service.hasFileDescriptors() == true) { 15085 throw new IllegalArgumentException("File descriptors passed in Intent"); 15086 } 15087 15088 synchronized(this) { 15089 return mServices.bindServiceLocked(caller, token, service, resolvedType, 15090 connection, flags, userId); 15091 } 15092 } 15093 15094 public boolean unbindService(IServiceConnection connection) { 15095 synchronized (this) { 15096 return mServices.unbindServiceLocked(connection); 15097 } 15098 } 15099 15100 public void publishService(IBinder token, Intent intent, IBinder service) { 15101 // Refuse possible leaked file descriptors 15102 if (intent != null && intent.hasFileDescriptors() == true) { 15103 throw new IllegalArgumentException("File descriptors passed in Intent"); 15104 } 15105 15106 synchronized(this) { 15107 if (!(token instanceof ServiceRecord)) { 15108 throw new IllegalArgumentException("Invalid service token"); 15109 } 15110 mServices.publishServiceLocked((ServiceRecord)token, intent, service); 15111 } 15112 } 15113 15114 public void unbindFinished(IBinder token, Intent intent, boolean doRebind) { 15115 // Refuse possible leaked file descriptors 15116 if (intent != null && intent.hasFileDescriptors() == true) { 15117 throw new IllegalArgumentException("File descriptors passed in Intent"); 15118 } 15119 15120 synchronized(this) { 15121 mServices.unbindFinishedLocked((ServiceRecord)token, intent, doRebind); 15122 } 15123 } 15124 15125 public void serviceDoneExecuting(IBinder token, int type, int startId, int res) { 15126 synchronized(this) { 15127 if (!(token instanceof ServiceRecord)) { 15128 throw new IllegalArgumentException("Invalid service token"); 15129 } 15130 mServices.serviceDoneExecutingLocked((ServiceRecord)token, type, startId, res); 15131 } 15132 } 15133 15134 // ========================================================= 15135 // BACKUP AND RESTORE 15136 // ========================================================= 15137 15138 // Cause the target app to be launched if necessary and its backup agent 15139 // instantiated. The backup agent will invoke backupAgentCreated() on the 15140 // activity manager to announce its creation. 15141 public boolean bindBackupAgent(ApplicationInfo app, int backupMode) { 15142 if (DEBUG_BACKUP) Slog.v(TAG, "bindBackupAgent: app=" + app + " mode=" + backupMode); 15143 enforceCallingPermission("android.permission.CONFIRM_FULL_BACKUP", "bindBackupAgent"); 15144 15145 synchronized(this) { 15146 // !!! TODO: currently no check here that we're already bound 15147 BatteryStatsImpl.Uid.Pkg.Serv ss = null; 15148 BatteryStatsImpl stats = mBatteryStatsService.getActiveStatistics(); 15149 synchronized (stats) { 15150 ss = stats.getServiceStatsLocked(app.uid, app.packageName, app.name); 15151 } 15152 15153 // Backup agent is now in use, its package can't be stopped. 15154 try { 15155 AppGlobals.getPackageManager().setPackageStoppedState( 15156 app.packageName, false, UserHandle.getUserId(app.uid)); 15157 } catch (RemoteException e) { 15158 } catch (IllegalArgumentException e) { 15159 Slog.w(TAG, "Failed trying to unstop package " 15160 + app.packageName + ": " + e); 15161 } 15162 15163 BackupRecord r = new BackupRecord(ss, app, backupMode); 15164 ComponentName hostingName = (backupMode == IApplicationThread.BACKUP_MODE_INCREMENTAL) 15165 ? new ComponentName(app.packageName, app.backupAgentName) 15166 : new ComponentName("android", "FullBackupAgent"); 15167 // startProcessLocked() returns existing proc's record if it's already running 15168 ProcessRecord proc = startProcessLocked(app.processName, app, 15169 false, 0, "backup", hostingName, false, false, false); 15170 if (proc == null) { 15171 Slog.e(TAG, "Unable to start backup agent process " + r); 15172 return false; 15173 } 15174 15175 r.app = proc; 15176 mBackupTarget = r; 15177 mBackupAppName = app.packageName; 15178 15179 // Try not to kill the process during backup 15180 updateOomAdjLocked(proc); 15181 15182 // If the process is already attached, schedule the creation of the backup agent now. 15183 // If it is not yet live, this will be done when it attaches to the framework. 15184 if (proc.thread != null) { 15185 if (DEBUG_BACKUP) Slog.v(TAG, "Agent proc already running: " + proc); 15186 try { 15187 proc.thread.scheduleCreateBackupAgent(app, 15188 compatibilityInfoForPackageLocked(app), backupMode); 15189 } catch (RemoteException e) { 15190 // Will time out on the backup manager side 15191 } 15192 } else { 15193 if (DEBUG_BACKUP) Slog.v(TAG, "Agent proc not running, waiting for attach"); 15194 } 15195 // Invariants: at this point, the target app process exists and the application 15196 // is either already running or in the process of coming up. mBackupTarget and 15197 // mBackupAppName describe the app, so that when it binds back to the AM we 15198 // know that it's scheduled for a backup-agent operation. 15199 } 15200 15201 return true; 15202 } 15203 15204 @Override 15205 public void clearPendingBackup() { 15206 if (DEBUG_BACKUP) Slog.v(TAG, "clearPendingBackup"); 15207 enforceCallingPermission("android.permission.BACKUP", "clearPendingBackup"); 15208 15209 synchronized (this) { 15210 mBackupTarget = null; 15211 mBackupAppName = null; 15212 } 15213 } 15214 15215 // A backup agent has just come up 15216 public void backupAgentCreated(String agentPackageName, IBinder agent) { 15217 if (DEBUG_BACKUP) Slog.v(TAG, "backupAgentCreated: " + agentPackageName 15218 + " = " + agent); 15219 15220 synchronized(this) { 15221 if (!agentPackageName.equals(mBackupAppName)) { 15222 Slog.e(TAG, "Backup agent created for " + agentPackageName + " but not requested!"); 15223 return; 15224 } 15225 } 15226 15227 long oldIdent = Binder.clearCallingIdentity(); 15228 try { 15229 IBackupManager bm = IBackupManager.Stub.asInterface( 15230 ServiceManager.getService(Context.BACKUP_SERVICE)); 15231 bm.agentConnected(agentPackageName, agent); 15232 } catch (RemoteException e) { 15233 // can't happen; the backup manager service is local 15234 } catch (Exception e) { 15235 Slog.w(TAG, "Exception trying to deliver BackupAgent binding: "); 15236 e.printStackTrace(); 15237 } finally { 15238 Binder.restoreCallingIdentity(oldIdent); 15239 } 15240 } 15241 15242 // done with this agent 15243 public void unbindBackupAgent(ApplicationInfo appInfo) { 15244 if (DEBUG_BACKUP) Slog.v(TAG, "unbindBackupAgent: " + appInfo); 15245 if (appInfo == null) { 15246 Slog.w(TAG, "unbind backup agent for null app"); 15247 return; 15248 } 15249 15250 synchronized(this) { 15251 try { 15252 if (mBackupAppName == null) { 15253 Slog.w(TAG, "Unbinding backup agent with no active backup"); 15254 return; 15255 } 15256 15257 if (!mBackupAppName.equals(appInfo.packageName)) { 15258 Slog.e(TAG, "Unbind of " + appInfo + " but is not the current backup target"); 15259 return; 15260 } 15261 15262 // Not backing this app up any more; reset its OOM adjustment 15263 final ProcessRecord proc = mBackupTarget.app; 15264 updateOomAdjLocked(proc); 15265 15266 // If the app crashed during backup, 'thread' will be null here 15267 if (proc.thread != null) { 15268 try { 15269 proc.thread.scheduleDestroyBackupAgent(appInfo, 15270 compatibilityInfoForPackageLocked(appInfo)); 15271 } catch (Exception e) { 15272 Slog.e(TAG, "Exception when unbinding backup agent:"); 15273 e.printStackTrace(); 15274 } 15275 } 15276 } finally { 15277 mBackupTarget = null; 15278 mBackupAppName = null; 15279 } 15280 } 15281 } 15282 // ========================================================= 15283 // BROADCASTS 15284 // ========================================================= 15285 15286 private final List getStickiesLocked(String action, IntentFilter filter, 15287 List cur, int userId) { 15288 final ContentResolver resolver = mContext.getContentResolver(); 15289 ArrayMap<String, ArrayList<Intent>> stickies = mStickyBroadcasts.get(userId); 15290 if (stickies == null) { 15291 return cur; 15292 } 15293 final ArrayList<Intent> list = stickies.get(action); 15294 if (list == null) { 15295 return cur; 15296 } 15297 int N = list.size(); 15298 for (int i=0; i<N; i++) { 15299 Intent intent = list.get(i); 15300 if (filter.match(resolver, intent, true, TAG) >= 0) { 15301 if (cur == null) { 15302 cur = new ArrayList<Intent>(); 15303 } 15304 cur.add(intent); 15305 } 15306 } 15307 return cur; 15308 } 15309 15310 boolean isPendingBroadcastProcessLocked(int pid) { 15311 return mFgBroadcastQueue.isPendingBroadcastProcessLocked(pid) 15312 || mBgBroadcastQueue.isPendingBroadcastProcessLocked(pid); 15313 } 15314 15315 void skipPendingBroadcastLocked(int pid) { 15316 Slog.w(TAG, "Unattached app died before broadcast acknowledged, skipping"); 15317 for (BroadcastQueue queue : mBroadcastQueues) { 15318 queue.skipPendingBroadcastLocked(pid); 15319 } 15320 } 15321 15322 // The app just attached; send any pending broadcasts that it should receive 15323 boolean sendPendingBroadcastsLocked(ProcessRecord app) { 15324 boolean didSomething = false; 15325 for (BroadcastQueue queue : mBroadcastQueues) { 15326 didSomething |= queue.sendPendingBroadcastsLocked(app); 15327 } 15328 return didSomething; 15329 } 15330 15331 public Intent registerReceiver(IApplicationThread caller, String callerPackage, 15332 IIntentReceiver receiver, IntentFilter filter, String permission, int userId) { 15333 enforceNotIsolatedCaller("registerReceiver"); 15334 int callingUid; 15335 int callingPid; 15336 synchronized(this) { 15337 ProcessRecord callerApp = null; 15338 if (caller != null) { 15339 callerApp = getRecordForAppLocked(caller); 15340 if (callerApp == null) { 15341 throw new SecurityException( 15342 "Unable to find app for caller " + caller 15343 + " (pid=" + Binder.getCallingPid() 15344 + ") when registering receiver " + receiver); 15345 } 15346 if (callerApp.info.uid != Process.SYSTEM_UID && 15347 !callerApp.pkgList.containsKey(callerPackage) && 15348 !"android".equals(callerPackage)) { 15349 throw new SecurityException("Given caller package " + callerPackage 15350 + " is not running in process " + callerApp); 15351 } 15352 callingUid = callerApp.info.uid; 15353 callingPid = callerApp.pid; 15354 } else { 15355 callerPackage = null; 15356 callingUid = Binder.getCallingUid(); 15357 callingPid = Binder.getCallingPid(); 15358 } 15359 15360 userId = this.handleIncomingUser(callingPid, callingUid, userId, 15361 true, ALLOW_FULL_ONLY, "registerReceiver", callerPackage); 15362 15363 List allSticky = null; 15364 15365 // Look for any matching sticky broadcasts... 15366 Iterator actions = filter.actionsIterator(); 15367 if (actions != null) { 15368 while (actions.hasNext()) { 15369 String action = (String)actions.next(); 15370 allSticky = getStickiesLocked(action, filter, allSticky, 15371 UserHandle.USER_ALL); 15372 allSticky = getStickiesLocked(action, filter, allSticky, 15373 UserHandle.getUserId(callingUid)); 15374 } 15375 } else { 15376 allSticky = getStickiesLocked(null, filter, allSticky, 15377 UserHandle.USER_ALL); 15378 allSticky = getStickiesLocked(null, filter, allSticky, 15379 UserHandle.getUserId(callingUid)); 15380 } 15381 15382 // The first sticky in the list is returned directly back to 15383 // the client. 15384 Intent sticky = allSticky != null ? (Intent)allSticky.get(0) : null; 15385 15386 if (DEBUG_BROADCAST) Slog.v(TAG, "Register receiver " + filter 15387 + ": " + sticky); 15388 15389 if (receiver == null) { 15390 return sticky; 15391 } 15392 15393 ReceiverList rl 15394 = (ReceiverList)mRegisteredReceivers.get(receiver.asBinder()); 15395 if (rl == null) { 15396 rl = new ReceiverList(this, callerApp, callingPid, callingUid, 15397 userId, receiver); 15398 if (rl.app != null) { 15399 rl.app.receivers.add(rl); 15400 } else { 15401 try { 15402 receiver.asBinder().linkToDeath(rl, 0); 15403 } catch (RemoteException e) { 15404 return sticky; 15405 } 15406 rl.linkedToDeath = true; 15407 } 15408 mRegisteredReceivers.put(receiver.asBinder(), rl); 15409 } else if (rl.uid != callingUid) { 15410 throw new IllegalArgumentException( 15411 "Receiver requested to register for uid " + callingUid 15412 + " was previously registered for uid " + rl.uid); 15413 } else if (rl.pid != callingPid) { 15414 throw new IllegalArgumentException( 15415 "Receiver requested to register for pid " + callingPid 15416 + " was previously registered for pid " + rl.pid); 15417 } else if (rl.userId != userId) { 15418 throw new IllegalArgumentException( 15419 "Receiver requested to register for user " + userId 15420 + " was previously registered for user " + rl.userId); 15421 } 15422 BroadcastFilter bf = new BroadcastFilter(filter, rl, callerPackage, 15423 permission, callingUid, userId); 15424 rl.add(bf); 15425 if (!bf.debugCheck()) { 15426 Slog.w(TAG, "==> For Dynamic broadast"); 15427 } 15428 mReceiverResolver.addFilter(bf); 15429 15430 // Enqueue broadcasts for all existing stickies that match 15431 // this filter. 15432 if (allSticky != null) { 15433 ArrayList receivers = new ArrayList(); 15434 receivers.add(bf); 15435 15436 int N = allSticky.size(); 15437 for (int i=0; i<N; i++) { 15438 Intent intent = (Intent)allSticky.get(i); 15439 BroadcastQueue queue = broadcastQueueForIntent(intent); 15440 BroadcastRecord r = new BroadcastRecord(queue, intent, null, 15441 null, -1, -1, null, null, AppOpsManager.OP_NONE, receivers, null, 0, 15442 null, null, false, true, true, -1); 15443 queue.enqueueParallelBroadcastLocked(r); 15444 queue.scheduleBroadcastsLocked(); 15445 } 15446 } 15447 15448 return sticky; 15449 } 15450 } 15451 15452 public void unregisterReceiver(IIntentReceiver receiver) { 15453 if (DEBUG_BROADCAST) Slog.v(TAG, "Unregister receiver: " + receiver); 15454 15455 final long origId = Binder.clearCallingIdentity(); 15456 try { 15457 boolean doTrim = false; 15458 15459 synchronized(this) { 15460 ReceiverList rl = mRegisteredReceivers.get(receiver.asBinder()); 15461 if (rl != null) { 15462 if (rl.curBroadcast != null) { 15463 BroadcastRecord r = rl.curBroadcast; 15464 final boolean doNext = finishReceiverLocked( 15465 receiver.asBinder(), r.resultCode, r.resultData, 15466 r.resultExtras, r.resultAbort); 15467 if (doNext) { 15468 doTrim = true; 15469 r.queue.processNextBroadcast(false); 15470 } 15471 } 15472 15473 if (rl.app != null) { 15474 rl.app.receivers.remove(rl); 15475 } 15476 removeReceiverLocked(rl); 15477 if (rl.linkedToDeath) { 15478 rl.linkedToDeath = false; 15479 rl.receiver.asBinder().unlinkToDeath(rl, 0); 15480 } 15481 } 15482 } 15483 15484 // If we actually concluded any broadcasts, we might now be able 15485 // to trim the recipients' apps from our working set 15486 if (doTrim) { 15487 trimApplications(); 15488 return; 15489 } 15490 15491 } finally { 15492 Binder.restoreCallingIdentity(origId); 15493 } 15494 } 15495 15496 void removeReceiverLocked(ReceiverList rl) { 15497 mRegisteredReceivers.remove(rl.receiver.asBinder()); 15498 int N = rl.size(); 15499 for (int i=0; i<N; i++) { 15500 mReceiverResolver.removeFilter(rl.get(i)); 15501 } 15502 } 15503 15504 private final void sendPackageBroadcastLocked(int cmd, String[] packages, int userId) { 15505 for (int i = mLruProcesses.size() - 1 ; i >= 0 ; i--) { 15506 ProcessRecord r = mLruProcesses.get(i); 15507 if (r.thread != null && (userId == UserHandle.USER_ALL || r.userId == userId)) { 15508 try { 15509 r.thread.dispatchPackageBroadcast(cmd, packages); 15510 } catch (RemoteException ex) { 15511 } 15512 } 15513 } 15514 } 15515 15516 private List<ResolveInfo> collectReceiverComponents(Intent intent, String resolvedType, 15517 int callingUid, int[] users) { 15518 List<ResolveInfo> receivers = null; 15519 try { 15520 HashSet<ComponentName> singleUserReceivers = null; 15521 boolean scannedFirstReceivers = false; 15522 for (int user : users) { 15523 // Skip users that have Shell restrictions 15524 if (callingUid == Process.SHELL_UID 15525 && getUserManagerLocked().hasUserRestriction( 15526 UserManager.DISALLOW_DEBUGGING_FEATURES, user)) { 15527 continue; 15528 } 15529 List<ResolveInfo> newReceivers = AppGlobals.getPackageManager() 15530 .queryIntentReceivers(intent, resolvedType, STOCK_PM_FLAGS, user); 15531 if (user != 0 && newReceivers != null) { 15532 // If this is not the primary user, we need to check for 15533 // any receivers that should be filtered out. 15534 for (int i=0; i<newReceivers.size(); i++) { 15535 ResolveInfo ri = newReceivers.get(i); 15536 if ((ri.activityInfo.flags&ActivityInfo.FLAG_PRIMARY_USER_ONLY) != 0) { 15537 newReceivers.remove(i); 15538 i--; 15539 } 15540 } 15541 } 15542 if (newReceivers != null && newReceivers.size() == 0) { 15543 newReceivers = null; 15544 } 15545 if (receivers == null) { 15546 receivers = newReceivers; 15547 } else if (newReceivers != null) { 15548 // We need to concatenate the additional receivers 15549 // found with what we have do far. This would be easy, 15550 // but we also need to de-dup any receivers that are 15551 // singleUser. 15552 if (!scannedFirstReceivers) { 15553 // Collect any single user receivers we had already retrieved. 15554 scannedFirstReceivers = true; 15555 for (int i=0; i<receivers.size(); i++) { 15556 ResolveInfo ri = receivers.get(i); 15557 if ((ri.activityInfo.flags&ActivityInfo.FLAG_SINGLE_USER) != 0) { 15558 ComponentName cn = new ComponentName( 15559 ri.activityInfo.packageName, ri.activityInfo.name); 15560 if (singleUserReceivers == null) { 15561 singleUserReceivers = new HashSet<ComponentName>(); 15562 } 15563 singleUserReceivers.add(cn); 15564 } 15565 } 15566 } 15567 // Add the new results to the existing results, tracking 15568 // and de-dupping single user receivers. 15569 for (int i=0; i<newReceivers.size(); i++) { 15570 ResolveInfo ri = newReceivers.get(i); 15571 if ((ri.activityInfo.flags&ActivityInfo.FLAG_SINGLE_USER) != 0) { 15572 ComponentName cn = new ComponentName( 15573 ri.activityInfo.packageName, ri.activityInfo.name); 15574 if (singleUserReceivers == null) { 15575 singleUserReceivers = new HashSet<ComponentName>(); 15576 } 15577 if (!singleUserReceivers.contains(cn)) { 15578 singleUserReceivers.add(cn); 15579 receivers.add(ri); 15580 } 15581 } else { 15582 receivers.add(ri); 15583 } 15584 } 15585 } 15586 } 15587 } catch (RemoteException ex) { 15588 // pm is in same process, this will never happen. 15589 } 15590 return receivers; 15591 } 15592 15593 private final int broadcastIntentLocked(ProcessRecord callerApp, 15594 String callerPackage, Intent intent, String resolvedType, 15595 IIntentReceiver resultTo, int resultCode, String resultData, 15596 Bundle map, String requiredPermission, int appOp, 15597 boolean ordered, boolean sticky, int callingPid, int callingUid, 15598 int userId) { 15599 intent = new Intent(intent); 15600 15601 // By default broadcasts do not go to stopped apps. 15602 intent.addFlags(Intent.FLAG_EXCLUDE_STOPPED_PACKAGES); 15603 15604 if (DEBUG_BROADCAST_LIGHT) Slog.v( 15605 TAG, (sticky ? "Broadcast sticky: ": "Broadcast: ") + intent 15606 + " ordered=" + ordered + " userid=" + userId); 15607 if ((resultTo != null) && !ordered) { 15608 Slog.w(TAG, "Broadcast " + intent + " not ordered but result callback requested!"); 15609 } 15610 15611 userId = handleIncomingUser(callingPid, callingUid, userId, 15612 true, ALLOW_NON_FULL, "broadcast", callerPackage); 15613 15614 // Make sure that the user who is receiving this broadcast is started. 15615 // If not, we will just skip it. 15616 15617 if (userId != UserHandle.USER_ALL && mStartedUsers.get(userId) == null) { 15618 if (callingUid != Process.SYSTEM_UID || (intent.getFlags() 15619 & Intent.FLAG_RECEIVER_BOOT_UPGRADE) == 0) { 15620 Slog.w(TAG, "Skipping broadcast of " + intent 15621 + ": user " + userId + " is stopped"); 15622 return ActivityManager.BROADCAST_FAILED_USER_STOPPED; 15623 } 15624 } 15625 15626 /* 15627 * Prevent non-system code (defined here to be non-persistent 15628 * processes) from sending protected broadcasts. 15629 */ 15630 int callingAppId = UserHandle.getAppId(callingUid); 15631 if (callingAppId == Process.SYSTEM_UID || callingAppId == Process.PHONE_UID 15632 || callingAppId == Process.SHELL_UID || callingAppId == Process.BLUETOOTH_UID 15633 || callingAppId == Process.NFC_UID || callingUid == 0) { 15634 // Always okay. 15635 } else if (callerApp == null || !callerApp.persistent) { 15636 try { 15637 if (AppGlobals.getPackageManager().isProtectedBroadcast( 15638 intent.getAction())) { 15639 String msg = "Permission Denial: not allowed to send broadcast " 15640 + intent.getAction() + " from pid=" 15641 + callingPid + ", uid=" + callingUid; 15642 Slog.w(TAG, msg); 15643 throw new SecurityException(msg); 15644 } else if (AppWidgetManager.ACTION_APPWIDGET_CONFIGURE.equals(intent.getAction())) { 15645 // Special case for compatibility: we don't want apps to send this, 15646 // but historically it has not been protected and apps may be using it 15647 // to poke their own app widget. So, instead of making it protected, 15648 // just limit it to the caller. 15649 if (callerApp == null) { 15650 String msg = "Permission Denial: not allowed to send broadcast " 15651 + intent.getAction() + " from unknown caller."; 15652 Slog.w(TAG, msg); 15653 throw new SecurityException(msg); 15654 } else if (intent.getComponent() != null) { 15655 // They are good enough to send to an explicit component... verify 15656 // it is being sent to the calling app. 15657 if (!intent.getComponent().getPackageName().equals( 15658 callerApp.info.packageName)) { 15659 String msg = "Permission Denial: not allowed to send broadcast " 15660 + intent.getAction() + " to " 15661 + intent.getComponent().getPackageName() + " from " 15662 + callerApp.info.packageName; 15663 Slog.w(TAG, msg); 15664 throw new SecurityException(msg); 15665 } 15666 } else { 15667 // Limit broadcast to their own package. 15668 intent.setPackage(callerApp.info.packageName); 15669 } 15670 } 15671 } catch (RemoteException e) { 15672 Slog.w(TAG, "Remote exception", e); 15673 return ActivityManager.BROADCAST_SUCCESS; 15674 } 15675 } 15676 15677 // Handle special intents: if this broadcast is from the package 15678 // manager about a package being removed, we need to remove all of 15679 // its activities from the history stack. 15680 final boolean uidRemoved = Intent.ACTION_UID_REMOVED.equals( 15681 intent.getAction()); 15682 if (Intent.ACTION_PACKAGE_REMOVED.equals(intent.getAction()) 15683 || Intent.ACTION_PACKAGE_CHANGED.equals(intent.getAction()) 15684 || Intent.ACTION_EXTERNAL_APPLICATIONS_UNAVAILABLE.equals(intent.getAction()) 15685 || Intent.ACTION_EXTERNAL_APPLICATIONS_AVAILABLE.equals(intent.getAction()) 15686 || uidRemoved) { 15687 if (checkComponentPermission( 15688 android.Manifest.permission.BROADCAST_PACKAGE_REMOVED, 15689 callingPid, callingUid, -1, true) 15690 == PackageManager.PERMISSION_GRANTED) { 15691 if (uidRemoved) { 15692 final Bundle intentExtras = intent.getExtras(); 15693 final int uid = intentExtras != null 15694 ? intentExtras.getInt(Intent.EXTRA_UID) : -1; 15695 if (uid >= 0) { 15696 BatteryStatsImpl bs = mBatteryStatsService.getActiveStatistics(); 15697 synchronized (bs) { 15698 bs.removeUidStatsLocked(uid); 15699 } 15700 mAppOpsService.uidRemoved(uid); 15701 } 15702 } else { 15703 // If resources are unavailable just force stop all 15704 // those packages and flush the attribute cache as well. 15705 if (Intent.ACTION_EXTERNAL_APPLICATIONS_UNAVAILABLE.equals(intent.getAction())) { 15706 String list[] = intent.getStringArrayExtra(Intent.EXTRA_CHANGED_PACKAGE_LIST); 15707 if (list != null && (list.length > 0)) { 15708 for (String pkg : list) { 15709 forceStopPackageLocked(pkg, -1, false, true, true, false, false, userId, 15710 "storage unmount"); 15711 } 15712 cleanupRecentTasksLocked(UserHandle.USER_ALL); 15713 sendPackageBroadcastLocked( 15714 IApplicationThread.EXTERNAL_STORAGE_UNAVAILABLE, list, userId); 15715 } 15716 } else if (Intent.ACTION_EXTERNAL_APPLICATIONS_AVAILABLE.equals( 15717 intent.getAction())) { 15718 cleanupRecentTasksLocked(UserHandle.USER_ALL); 15719 } else { 15720 Uri data = intent.getData(); 15721 String ssp; 15722 if (data != null && (ssp=data.getSchemeSpecificPart()) != null) { 15723 boolean removed = Intent.ACTION_PACKAGE_REMOVED.equals( 15724 intent.getAction()); 15725 boolean fullUninstall = removed && 15726 !intent.getBooleanExtra(Intent.EXTRA_REPLACING, false); 15727 if (!intent.getBooleanExtra(Intent.EXTRA_DONT_KILL_APP, false)) { 15728 forceStopPackageLocked(ssp, UserHandle.getAppId( 15729 intent.getIntExtra(Intent.EXTRA_UID, -1)), false, true, true, 15730 false, fullUninstall, userId, 15731 removed ? "pkg removed" : "pkg changed"); 15732 } 15733 if (removed) { 15734 sendPackageBroadcastLocked(IApplicationThread.PACKAGE_REMOVED, 15735 new String[] {ssp}, userId); 15736 if (!intent.getBooleanExtra(Intent.EXTRA_REPLACING, false)) { 15737 mAppOpsService.packageRemoved( 15738 intent.getIntExtra(Intent.EXTRA_UID, -1), ssp); 15739 15740 // Remove all permissions granted from/to this package 15741 removeUriPermissionsForPackageLocked(ssp, userId, true); 15742 } 15743 } 15744 } 15745 } 15746 } 15747 } else { 15748 String msg = "Permission Denial: " + intent.getAction() 15749 + " broadcast from " + callerPackage + " (pid=" + callingPid 15750 + ", uid=" + callingUid + ")" 15751 + " requires " 15752 + android.Manifest.permission.BROADCAST_PACKAGE_REMOVED; 15753 Slog.w(TAG, msg); 15754 throw new SecurityException(msg); 15755 } 15756 15757 // Special case for adding a package: by default turn on compatibility 15758 // mode. 15759 } else if (Intent.ACTION_PACKAGE_ADDED.equals(intent.getAction())) { 15760 Uri data = intent.getData(); 15761 String ssp; 15762 if (data != null && (ssp=data.getSchemeSpecificPart()) != null) { 15763 mCompatModePackages.handlePackageAddedLocked(ssp, 15764 intent.getBooleanExtra(Intent.EXTRA_REPLACING, false)); 15765 } 15766 } 15767 15768 /* 15769 * If this is the time zone changed action, queue up a message that will reset the timezone 15770 * of all currently running processes. This message will get queued up before the broadcast 15771 * happens. 15772 */ 15773 if (Intent.ACTION_TIMEZONE_CHANGED.equals(intent.getAction())) { 15774 mHandler.sendEmptyMessage(UPDATE_TIME_ZONE); 15775 } 15776 15777 /* 15778 * If the user set the time, let all running processes know. 15779 */ 15780 if (Intent.ACTION_TIME_CHANGED.equals(intent.getAction())) { 15781 final int is24Hour = intent.getBooleanExtra( 15782 Intent.EXTRA_TIME_PREF_24_HOUR_FORMAT, false) ? 1 : 0; 15783 mHandler.sendMessage(mHandler.obtainMessage(UPDATE_TIME, is24Hour, 0)); 15784 BatteryStatsImpl stats = mBatteryStatsService.getActiveStatistics(); 15785 synchronized (stats) { 15786 stats.noteCurrentTimeChangedLocked(); 15787 } 15788 } 15789 15790 if (Intent.ACTION_CLEAR_DNS_CACHE.equals(intent.getAction())) { 15791 mHandler.sendEmptyMessage(CLEAR_DNS_CACHE_MSG); 15792 } 15793 15794 if (Proxy.PROXY_CHANGE_ACTION.equals(intent.getAction())) { 15795 ProxyInfo proxy = intent.getParcelableExtra(Proxy.EXTRA_PROXY_INFO); 15796 mHandler.sendMessage(mHandler.obtainMessage(UPDATE_HTTP_PROXY_MSG, proxy)); 15797 } 15798 15799 // Add to the sticky list if requested. 15800 if (sticky) { 15801 if (checkPermission(android.Manifest.permission.BROADCAST_STICKY, 15802 callingPid, callingUid) 15803 != PackageManager.PERMISSION_GRANTED) { 15804 String msg = "Permission Denial: broadcastIntent() requesting a sticky broadcast from pid=" 15805 + callingPid + ", uid=" + callingUid 15806 + " requires " + android.Manifest.permission.BROADCAST_STICKY; 15807 Slog.w(TAG, msg); 15808 throw new SecurityException(msg); 15809 } 15810 if (requiredPermission != null) { 15811 Slog.w(TAG, "Can't broadcast sticky intent " + intent 15812 + " and enforce permission " + requiredPermission); 15813 return ActivityManager.BROADCAST_STICKY_CANT_HAVE_PERMISSION; 15814 } 15815 if (intent.getComponent() != null) { 15816 throw new SecurityException( 15817 "Sticky broadcasts can't target a specific component"); 15818 } 15819 // We use userId directly here, since the "all" target is maintained 15820 // as a separate set of sticky broadcasts. 15821 if (userId != UserHandle.USER_ALL) { 15822 // But first, if this is not a broadcast to all users, then 15823 // make sure it doesn't conflict with an existing broadcast to 15824 // all users. 15825 ArrayMap<String, ArrayList<Intent>> stickies = mStickyBroadcasts.get( 15826 UserHandle.USER_ALL); 15827 if (stickies != null) { 15828 ArrayList<Intent> list = stickies.get(intent.getAction()); 15829 if (list != null) { 15830 int N = list.size(); 15831 int i; 15832 for (i=0; i<N; i++) { 15833 if (intent.filterEquals(list.get(i))) { 15834 throw new IllegalArgumentException( 15835 "Sticky broadcast " + intent + " for user " 15836 + userId + " conflicts with existing global broadcast"); 15837 } 15838 } 15839 } 15840 } 15841 } 15842 ArrayMap<String, ArrayList<Intent>> stickies = mStickyBroadcasts.get(userId); 15843 if (stickies == null) { 15844 stickies = new ArrayMap<String, ArrayList<Intent>>(); 15845 mStickyBroadcasts.put(userId, stickies); 15846 } 15847 ArrayList<Intent> list = stickies.get(intent.getAction()); 15848 if (list == null) { 15849 list = new ArrayList<Intent>(); 15850 stickies.put(intent.getAction(), list); 15851 } 15852 int N = list.size(); 15853 int i; 15854 for (i=0; i<N; i++) { 15855 if (intent.filterEquals(list.get(i))) { 15856 // This sticky already exists, replace it. 15857 list.set(i, new Intent(intent)); 15858 break; 15859 } 15860 } 15861 if (i >= N) { 15862 list.add(new Intent(intent)); 15863 } 15864 } 15865 15866 int[] users; 15867 if (userId == UserHandle.USER_ALL) { 15868 // Caller wants broadcast to go to all started users. 15869 users = mStartedUserArray; 15870 } else { 15871 // Caller wants broadcast to go to one specific user. 15872 users = new int[] {userId}; 15873 } 15874 15875 // Figure out who all will receive this broadcast. 15876 List receivers = null; 15877 List<BroadcastFilter> registeredReceivers = null; 15878 // Need to resolve the intent to interested receivers... 15879 if ((intent.getFlags()&Intent.FLAG_RECEIVER_REGISTERED_ONLY) 15880 == 0) { 15881 receivers = collectReceiverComponents(intent, resolvedType, callingUid, users); 15882 } 15883 if (intent.getComponent() == null) { 15884 if (userId == UserHandle.USER_ALL && callingUid == Process.SHELL_UID) { 15885 // Query one target user at a time, excluding shell-restricted users 15886 UserManagerService ums = getUserManagerLocked(); 15887 for (int i = 0; i < users.length; i++) { 15888 if (ums.hasUserRestriction( 15889 UserManager.DISALLOW_DEBUGGING_FEATURES, users[i])) { 15890 continue; 15891 } 15892 List<BroadcastFilter> registeredReceiversForUser = 15893 mReceiverResolver.queryIntent(intent, 15894 resolvedType, false, users[i]); 15895 if (registeredReceivers == null) { 15896 registeredReceivers = registeredReceiversForUser; 15897 } else if (registeredReceiversForUser != null) { 15898 registeredReceivers.addAll(registeredReceiversForUser); 15899 } 15900 } 15901 } else { 15902 registeredReceivers = mReceiverResolver.queryIntent(intent, 15903 resolvedType, false, userId); 15904 } 15905 } 15906 15907 final boolean replacePending = 15908 (intent.getFlags()&Intent.FLAG_RECEIVER_REPLACE_PENDING) != 0; 15909 15910 if (DEBUG_BROADCAST) Slog.v(TAG, "Enqueing broadcast: " + intent.getAction() 15911 + " replacePending=" + replacePending); 15912 15913 int NR = registeredReceivers != null ? registeredReceivers.size() : 0; 15914 if (!ordered && NR > 0) { 15915 // If we are not serializing this broadcast, then send the 15916 // registered receivers separately so they don't wait for the 15917 // components to be launched. 15918 final BroadcastQueue queue = broadcastQueueForIntent(intent); 15919 BroadcastRecord r = new BroadcastRecord(queue, intent, callerApp, 15920 callerPackage, callingPid, callingUid, resolvedType, requiredPermission, 15921 appOp, registeredReceivers, resultTo, resultCode, resultData, map, 15922 ordered, sticky, false, userId); 15923 if (DEBUG_BROADCAST) Slog.v( 15924 TAG, "Enqueueing parallel broadcast " + r); 15925 final boolean replaced = replacePending && queue.replaceParallelBroadcastLocked(r); 15926 if (!replaced) { 15927 queue.enqueueParallelBroadcastLocked(r); 15928 queue.scheduleBroadcastsLocked(); 15929 } 15930 registeredReceivers = null; 15931 NR = 0; 15932 } 15933 15934 // Merge into one list. 15935 int ir = 0; 15936 if (receivers != null) { 15937 // A special case for PACKAGE_ADDED: do not allow the package 15938 // being added to see this broadcast. This prevents them from 15939 // using this as a back door to get run as soon as they are 15940 // installed. Maybe in the future we want to have a special install 15941 // broadcast or such for apps, but we'd like to deliberately make 15942 // this decision. 15943 String skipPackages[] = null; 15944 if (Intent.ACTION_PACKAGE_ADDED.equals(intent.getAction()) 15945 || Intent.ACTION_PACKAGE_RESTARTED.equals(intent.getAction()) 15946 || Intent.ACTION_PACKAGE_DATA_CLEARED.equals(intent.getAction())) { 15947 Uri data = intent.getData(); 15948 if (data != null) { 15949 String pkgName = data.getSchemeSpecificPart(); 15950 if (pkgName != null) { 15951 skipPackages = new String[] { pkgName }; 15952 } 15953 } 15954 } else if (Intent.ACTION_EXTERNAL_APPLICATIONS_AVAILABLE.equals(intent.getAction())) { 15955 skipPackages = intent.getStringArrayExtra(Intent.EXTRA_CHANGED_PACKAGE_LIST); 15956 } 15957 if (skipPackages != null && (skipPackages.length > 0)) { 15958 for (String skipPackage : skipPackages) { 15959 if (skipPackage != null) { 15960 int NT = receivers.size(); 15961 for (int it=0; it<NT; it++) { 15962 ResolveInfo curt = (ResolveInfo)receivers.get(it); 15963 if (curt.activityInfo.packageName.equals(skipPackage)) { 15964 receivers.remove(it); 15965 it--; 15966 NT--; 15967 } 15968 } 15969 } 15970 } 15971 } 15972 15973 int NT = receivers != null ? receivers.size() : 0; 15974 int it = 0; 15975 ResolveInfo curt = null; 15976 BroadcastFilter curr = null; 15977 while (it < NT && ir < NR) { 15978 if (curt == null) { 15979 curt = (ResolveInfo)receivers.get(it); 15980 } 15981 if (curr == null) { 15982 curr = registeredReceivers.get(ir); 15983 } 15984 if (curr.getPriority() >= curt.priority) { 15985 // Insert this broadcast record into the final list. 15986 receivers.add(it, curr); 15987 ir++; 15988 curr = null; 15989 it++; 15990 NT++; 15991 } else { 15992 // Skip to the next ResolveInfo in the final list. 15993 it++; 15994 curt = null; 15995 } 15996 } 15997 } 15998 while (ir < NR) { 15999 if (receivers == null) { 16000 receivers = new ArrayList(); 16001 } 16002 receivers.add(registeredReceivers.get(ir)); 16003 ir++; 16004 } 16005 16006 if ((receivers != null && receivers.size() > 0) 16007 || resultTo != null) { 16008 BroadcastQueue queue = broadcastQueueForIntent(intent); 16009 BroadcastRecord r = new BroadcastRecord(queue, intent, callerApp, 16010 callerPackage, callingPid, callingUid, resolvedType, 16011 requiredPermission, appOp, receivers, resultTo, resultCode, 16012 resultData, map, ordered, sticky, false, userId); 16013 if (DEBUG_BROADCAST) Slog.v( 16014 TAG, "Enqueueing ordered broadcast " + r 16015 + ": prev had " + queue.mOrderedBroadcasts.size()); 16016 if (DEBUG_BROADCAST) { 16017 int seq = r.intent.getIntExtra("seq", -1); 16018 Slog.i(TAG, "Enqueueing broadcast " + r.intent.getAction() + " seq=" + seq); 16019 } 16020 boolean replaced = replacePending && queue.replaceOrderedBroadcastLocked(r); 16021 if (!replaced) { 16022 queue.enqueueOrderedBroadcastLocked(r); 16023 queue.scheduleBroadcastsLocked(); 16024 } 16025 } 16026 16027 return ActivityManager.BROADCAST_SUCCESS; 16028 } 16029 16030 final Intent verifyBroadcastLocked(Intent intent) { 16031 // Refuse possible leaked file descriptors 16032 if (intent != null && intent.hasFileDescriptors() == true) { 16033 throw new IllegalArgumentException("File descriptors passed in Intent"); 16034 } 16035 16036 int flags = intent.getFlags(); 16037 16038 if (!mProcessesReady) { 16039 // if the caller really truly claims to know what they're doing, go 16040 // ahead and allow the broadcast without launching any receivers 16041 if ((flags&Intent.FLAG_RECEIVER_REGISTERED_ONLY_BEFORE_BOOT) != 0) { 16042 intent = new Intent(intent); 16043 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY); 16044 } else if ((flags&Intent.FLAG_RECEIVER_REGISTERED_ONLY) == 0) { 16045 Slog.e(TAG, "Attempt to launch receivers of broadcast intent " + intent 16046 + " before boot completion"); 16047 throw new IllegalStateException("Cannot broadcast before boot completed"); 16048 } 16049 } 16050 16051 if ((flags&Intent.FLAG_RECEIVER_BOOT_UPGRADE) != 0) { 16052 throw new IllegalArgumentException( 16053 "Can't use FLAG_RECEIVER_BOOT_UPGRADE here"); 16054 } 16055 16056 return intent; 16057 } 16058 16059 public final int broadcastIntent(IApplicationThread caller, 16060 Intent intent, String resolvedType, IIntentReceiver resultTo, 16061 int resultCode, String resultData, Bundle map, 16062 String requiredPermission, int appOp, boolean serialized, boolean sticky, int userId) { 16063 enforceNotIsolatedCaller("broadcastIntent"); 16064 synchronized(this) { 16065 intent = verifyBroadcastLocked(intent); 16066 16067 final ProcessRecord callerApp = getRecordForAppLocked(caller); 16068 final int callingPid = Binder.getCallingPid(); 16069 final int callingUid = Binder.getCallingUid(); 16070 final long origId = Binder.clearCallingIdentity(); 16071 int res = broadcastIntentLocked(callerApp, 16072 callerApp != null ? callerApp.info.packageName : null, 16073 intent, resolvedType, resultTo, 16074 resultCode, resultData, map, requiredPermission, appOp, serialized, sticky, 16075 callingPid, callingUid, userId); 16076 Binder.restoreCallingIdentity(origId); 16077 return res; 16078 } 16079 } 16080 16081 int broadcastIntentInPackage(String packageName, int uid, 16082 Intent intent, String resolvedType, IIntentReceiver resultTo, 16083 int resultCode, String resultData, Bundle map, 16084 String requiredPermission, boolean serialized, boolean sticky, int userId) { 16085 synchronized(this) { 16086 intent = verifyBroadcastLocked(intent); 16087 16088 final long origId = Binder.clearCallingIdentity(); 16089 int res = broadcastIntentLocked(null, packageName, intent, resolvedType, 16090 resultTo, resultCode, resultData, map, requiredPermission, 16091 AppOpsManager.OP_NONE, serialized, sticky, -1, uid, userId); 16092 Binder.restoreCallingIdentity(origId); 16093 return res; 16094 } 16095 } 16096 16097 public final void unbroadcastIntent(IApplicationThread caller, Intent intent, int userId) { 16098 // Refuse possible leaked file descriptors 16099 if (intent != null && intent.hasFileDescriptors() == true) { 16100 throw new IllegalArgumentException("File descriptors passed in Intent"); 16101 } 16102 16103 userId = handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(), 16104 userId, true, ALLOW_NON_FULL, "removeStickyBroadcast", null); 16105 16106 synchronized(this) { 16107 if (checkCallingPermission(android.Manifest.permission.BROADCAST_STICKY) 16108 != PackageManager.PERMISSION_GRANTED) { 16109 String msg = "Permission Denial: unbroadcastIntent() from pid=" 16110 + Binder.getCallingPid() 16111 + ", uid=" + Binder.getCallingUid() 16112 + " requires " + android.Manifest.permission.BROADCAST_STICKY; 16113 Slog.w(TAG, msg); 16114 throw new SecurityException(msg); 16115 } 16116 ArrayMap<String, ArrayList<Intent>> stickies = mStickyBroadcasts.get(userId); 16117 if (stickies != null) { 16118 ArrayList<Intent> list = stickies.get(intent.getAction()); 16119 if (list != null) { 16120 int N = list.size(); 16121 int i; 16122 for (i=0; i<N; i++) { 16123 if (intent.filterEquals(list.get(i))) { 16124 list.remove(i); 16125 break; 16126 } 16127 } 16128 if (list.size() <= 0) { 16129 stickies.remove(intent.getAction()); 16130 } 16131 } 16132 if (stickies.size() <= 0) { 16133 mStickyBroadcasts.remove(userId); 16134 } 16135 } 16136 } 16137 } 16138 16139 private final boolean finishReceiverLocked(IBinder receiver, int resultCode, 16140 String resultData, Bundle resultExtras, boolean resultAbort) { 16141 final BroadcastRecord r = broadcastRecordForReceiverLocked(receiver); 16142 if (r == null) { 16143 Slog.w(TAG, "finishReceiver called but not found on queue"); 16144 return false; 16145 } 16146 16147 return r.queue.finishReceiverLocked(r, resultCode, resultData, resultExtras, resultAbort, false); 16148 } 16149 16150 void backgroundServicesFinishedLocked(int userId) { 16151 for (BroadcastQueue queue : mBroadcastQueues) { 16152 queue.backgroundServicesFinishedLocked(userId); 16153 } 16154 } 16155 16156 public void finishReceiver(IBinder who, int resultCode, String resultData, 16157 Bundle resultExtras, boolean resultAbort) { 16158 if (DEBUG_BROADCAST) Slog.v(TAG, "Finish receiver: " + who); 16159 16160 // Refuse possible leaked file descriptors 16161 if (resultExtras != null && resultExtras.hasFileDescriptors()) { 16162 throw new IllegalArgumentException("File descriptors passed in Bundle"); 16163 } 16164 16165 final long origId = Binder.clearCallingIdentity(); 16166 try { 16167 boolean doNext = false; 16168 BroadcastRecord r; 16169 16170 synchronized(this) { 16171 r = broadcastRecordForReceiverLocked(who); 16172 if (r != null) { 16173 doNext = r.queue.finishReceiverLocked(r, resultCode, 16174 resultData, resultExtras, resultAbort, true); 16175 } 16176 } 16177 16178 if (doNext) { 16179 r.queue.processNextBroadcast(false); 16180 } 16181 trimApplications(); 16182 } finally { 16183 Binder.restoreCallingIdentity(origId); 16184 } 16185 } 16186 16187 // ========================================================= 16188 // INSTRUMENTATION 16189 // ========================================================= 16190 16191 public boolean startInstrumentation(ComponentName className, 16192 String profileFile, int flags, Bundle arguments, 16193 IInstrumentationWatcher watcher, IUiAutomationConnection uiAutomationConnection, 16194 int userId, String abiOverride) { 16195 enforceNotIsolatedCaller("startInstrumentation"); 16196 userId = handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(), 16197 userId, false, ALLOW_FULL_ONLY, "startInstrumentation", null); 16198 // Refuse possible leaked file descriptors 16199 if (arguments != null && arguments.hasFileDescriptors()) { 16200 throw new IllegalArgumentException("File descriptors passed in Bundle"); 16201 } 16202 16203 synchronized(this) { 16204 InstrumentationInfo ii = null; 16205 ApplicationInfo ai = null; 16206 try { 16207 ii = mContext.getPackageManager().getInstrumentationInfo( 16208 className, STOCK_PM_FLAGS); 16209 ai = AppGlobals.getPackageManager().getApplicationInfo( 16210 ii.targetPackage, STOCK_PM_FLAGS, userId); 16211 } catch (PackageManager.NameNotFoundException e) { 16212 } catch (RemoteException e) { 16213 } 16214 if (ii == null) { 16215 reportStartInstrumentationFailure(watcher, className, 16216 "Unable to find instrumentation info for: " + className); 16217 return false; 16218 } 16219 if (ai == null) { 16220 reportStartInstrumentationFailure(watcher, className, 16221 "Unable to find instrumentation target package: " + ii.targetPackage); 16222 return false; 16223 } 16224 16225 int match = mContext.getPackageManager().checkSignatures( 16226 ii.targetPackage, ii.packageName); 16227 if (match < 0 && match != PackageManager.SIGNATURE_FIRST_NOT_SIGNED) { 16228 String msg = "Permission Denial: starting instrumentation " 16229 + className + " from pid=" 16230 + Binder.getCallingPid() 16231 + ", uid=" + Binder.getCallingPid() 16232 + " not allowed because package " + ii.packageName 16233 + " does not have a signature matching the target " 16234 + ii.targetPackage; 16235 reportStartInstrumentationFailure(watcher, className, msg); 16236 throw new SecurityException(msg); 16237 } 16238 16239 final long origId = Binder.clearCallingIdentity(); 16240 // Instrumentation can kill and relaunch even persistent processes 16241 forceStopPackageLocked(ii.targetPackage, -1, true, false, true, true, false, userId, 16242 "start instr"); 16243 ProcessRecord app = addAppLocked(ai, false, abiOverride); 16244 app.instrumentationClass = className; 16245 app.instrumentationInfo = ai; 16246 app.instrumentationProfileFile = profileFile; 16247 app.instrumentationArguments = arguments; 16248 app.instrumentationWatcher = watcher; 16249 app.instrumentationUiAutomationConnection = uiAutomationConnection; 16250 app.instrumentationResultClass = className; 16251 Binder.restoreCallingIdentity(origId); 16252 } 16253 16254 return true; 16255 } 16256 16257 /** 16258 * Report errors that occur while attempting to start Instrumentation. Always writes the 16259 * error to the logs, but if somebody is watching, send the report there too. This enables 16260 * the "am" command to report errors with more information. 16261 * 16262 * @param watcher The IInstrumentationWatcher. Null if there isn't one. 16263 * @param cn The component name of the instrumentation. 16264 * @param report The error report. 16265 */ 16266 private void reportStartInstrumentationFailure(IInstrumentationWatcher watcher, 16267 ComponentName cn, String report) { 16268 Slog.w(TAG, report); 16269 try { 16270 if (watcher != null) { 16271 Bundle results = new Bundle(); 16272 results.putString(Instrumentation.REPORT_KEY_IDENTIFIER, "ActivityManagerService"); 16273 results.putString("Error", report); 16274 watcher.instrumentationStatus(cn, -1, results); 16275 } 16276 } catch (RemoteException e) { 16277 Slog.w(TAG, e); 16278 } 16279 } 16280 16281 void finishInstrumentationLocked(ProcessRecord app, int resultCode, Bundle results) { 16282 if (app.instrumentationWatcher != null) { 16283 try { 16284 // NOTE: IInstrumentationWatcher *must* be oneway here 16285 app.instrumentationWatcher.instrumentationFinished( 16286 app.instrumentationClass, 16287 resultCode, 16288 results); 16289 } catch (RemoteException e) { 16290 } 16291 } 16292 if (app.instrumentationUiAutomationConnection != null) { 16293 try { 16294 app.instrumentationUiAutomationConnection.shutdown(); 16295 } catch (RemoteException re) { 16296 /* ignore */ 16297 } 16298 // Only a UiAutomation can set this flag and now that 16299 // it is finished we make sure it is reset to its default. 16300 mUserIsMonkey = false; 16301 } 16302 app.instrumentationWatcher = null; 16303 app.instrumentationUiAutomationConnection = null; 16304 app.instrumentationClass = null; 16305 app.instrumentationInfo = null; 16306 app.instrumentationProfileFile = null; 16307 app.instrumentationArguments = null; 16308 16309 forceStopPackageLocked(app.info.packageName, -1, false, false, true, true, false, app.userId, 16310 "finished inst"); 16311 } 16312 16313 public void finishInstrumentation(IApplicationThread target, 16314 int resultCode, Bundle results) { 16315 int userId = UserHandle.getCallingUserId(); 16316 // Refuse possible leaked file descriptors 16317 if (results != null && results.hasFileDescriptors()) { 16318 throw new IllegalArgumentException("File descriptors passed in Intent"); 16319 } 16320 16321 synchronized(this) { 16322 ProcessRecord app = getRecordForAppLocked(target); 16323 if (app == null) { 16324 Slog.w(TAG, "finishInstrumentation: no app for " + target); 16325 return; 16326 } 16327 final long origId = Binder.clearCallingIdentity(); 16328 finishInstrumentationLocked(app, resultCode, results); 16329 Binder.restoreCallingIdentity(origId); 16330 } 16331 } 16332 16333 // ========================================================= 16334 // CONFIGURATION 16335 // ========================================================= 16336 16337 public ConfigurationInfo getDeviceConfigurationInfo() { 16338 ConfigurationInfo config = new ConfigurationInfo(); 16339 synchronized (this) { 16340 config.reqTouchScreen = mConfiguration.touchscreen; 16341 config.reqKeyboardType = mConfiguration.keyboard; 16342 config.reqNavigation = mConfiguration.navigation; 16343 if (mConfiguration.navigation == Configuration.NAVIGATION_DPAD 16344 || mConfiguration.navigation == Configuration.NAVIGATION_TRACKBALL) { 16345 config.reqInputFeatures |= ConfigurationInfo.INPUT_FEATURE_FIVE_WAY_NAV; 16346 } 16347 if (mConfiguration.keyboard != Configuration.KEYBOARD_UNDEFINED 16348 && mConfiguration.keyboard != Configuration.KEYBOARD_NOKEYS) { 16349 config.reqInputFeatures |= ConfigurationInfo.INPUT_FEATURE_HARD_KEYBOARD; 16350 } 16351 config.reqGlEsVersion = GL_ES_VERSION; 16352 } 16353 return config; 16354 } 16355 16356 ActivityStack getFocusedStack() { 16357 return mStackSupervisor.getFocusedStack(); 16358 } 16359 16360 public Configuration getConfiguration() { 16361 Configuration ci; 16362 synchronized(this) { 16363 ci = new Configuration(mConfiguration); 16364 } 16365 return ci; 16366 } 16367 16368 public void updatePersistentConfiguration(Configuration values) { 16369 enforceCallingPermission(android.Manifest.permission.CHANGE_CONFIGURATION, 16370 "updateConfiguration()"); 16371 enforceCallingPermission(android.Manifest.permission.WRITE_SETTINGS, 16372 "updateConfiguration()"); 16373 if (values == null) { 16374 throw new NullPointerException("Configuration must not be null"); 16375 } 16376 16377 synchronized(this) { 16378 final long origId = Binder.clearCallingIdentity(); 16379 updateConfigurationLocked(values, null, true, false); 16380 Binder.restoreCallingIdentity(origId); 16381 } 16382 } 16383 16384 public void updateConfiguration(Configuration values) { 16385 enforceCallingPermission(android.Manifest.permission.CHANGE_CONFIGURATION, 16386 "updateConfiguration()"); 16387 16388 synchronized(this) { 16389 if (values == null && mWindowManager != null) { 16390 // sentinel: fetch the current configuration from the window manager 16391 values = mWindowManager.computeNewConfiguration(); 16392 } 16393 16394 if (mWindowManager != null) { 16395 mProcessList.applyDisplaySize(mWindowManager); 16396 } 16397 16398 final long origId = Binder.clearCallingIdentity(); 16399 if (values != null) { 16400 Settings.System.clearConfiguration(values); 16401 } 16402 updateConfigurationLocked(values, null, false, false); 16403 Binder.restoreCallingIdentity(origId); 16404 } 16405 } 16406 16407 /** 16408 * Do either or both things: (1) change the current configuration, and (2) 16409 * make sure the given activity is running with the (now) current 16410 * configuration. Returns true if the activity has been left running, or 16411 * false if <var>starting</var> is being destroyed to match the new 16412 * configuration. 16413 * @param persistent TODO 16414 */ 16415 boolean updateConfigurationLocked(Configuration values, 16416 ActivityRecord starting, boolean persistent, boolean initLocale) { 16417 int changes = 0; 16418 16419 if (values != null) { 16420 Configuration newConfig = new Configuration(mConfiguration); 16421 changes = newConfig.updateFrom(values); 16422 if (changes != 0) { 16423 if (DEBUG_SWITCH || DEBUG_CONFIGURATION) { 16424 Slog.i(TAG, "Updating configuration to: " + values); 16425 } 16426 16427 EventLog.writeEvent(EventLogTags.CONFIGURATION_CHANGED, changes); 16428 16429 if (values.locale != null && !initLocale) { 16430 saveLocaleLocked(values.locale, 16431 !values.locale.equals(mConfiguration.locale), 16432 values.userSetLocale); 16433 } 16434 16435 mConfigurationSeq++; 16436 if (mConfigurationSeq <= 0) { 16437 mConfigurationSeq = 1; 16438 } 16439 newConfig.seq = mConfigurationSeq; 16440 mConfiguration = newConfig; 16441 Slog.i(TAG, "Config changes=" + Integer.toHexString(changes) + " " + newConfig); 16442 mUsageStatsService.reportConfigurationChange(newConfig, mCurrentUserId); 16443 //mUsageStatsService.noteStartConfig(newConfig); 16444 16445 final Configuration configCopy = new Configuration(mConfiguration); 16446 16447 // TODO: If our config changes, should we auto dismiss any currently 16448 // showing dialogs? 16449 mShowDialogs = shouldShowDialogs(newConfig); 16450 16451 AttributeCache ac = AttributeCache.instance(); 16452 if (ac != null) { 16453 ac.updateConfiguration(configCopy); 16454 } 16455 16456 // Make sure all resources in our process are updated 16457 // right now, so that anyone who is going to retrieve 16458 // resource values after we return will be sure to get 16459 // the new ones. This is especially important during 16460 // boot, where the first config change needs to guarantee 16461 // all resources have that config before following boot 16462 // code is executed. 16463 mSystemThread.applyConfigurationToResources(configCopy); 16464 16465 if (persistent && Settings.System.hasInterestingConfigurationChanges(changes)) { 16466 Message msg = mHandler.obtainMessage(UPDATE_CONFIGURATION_MSG); 16467 msg.obj = new Configuration(configCopy); 16468 mHandler.sendMessage(msg); 16469 } 16470 16471 for (int i=mLruProcesses.size()-1; i>=0; i--) { 16472 ProcessRecord app = mLruProcesses.get(i); 16473 try { 16474 if (app.thread != null) { 16475 if (DEBUG_CONFIGURATION) Slog.v(TAG, "Sending to proc " 16476 + app.processName + " new config " + mConfiguration); 16477 app.thread.scheduleConfigurationChanged(configCopy); 16478 } 16479 } catch (Exception e) { 16480 } 16481 } 16482 Intent intent = new Intent(Intent.ACTION_CONFIGURATION_CHANGED); 16483 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY 16484 | Intent.FLAG_RECEIVER_REPLACE_PENDING 16485 | Intent.FLAG_RECEIVER_FOREGROUND); 16486 broadcastIntentLocked(null, null, intent, null, null, 0, null, null, 16487 null, AppOpsManager.OP_NONE, false, false, MY_PID, 16488 Process.SYSTEM_UID, UserHandle.USER_ALL); 16489 if ((changes&ActivityInfo.CONFIG_LOCALE) != 0) { 16490 intent = new Intent(Intent.ACTION_LOCALE_CHANGED); 16491 intent.addFlags(Intent.FLAG_RECEIVER_FOREGROUND); 16492 broadcastIntentLocked(null, null, intent, 16493 null, null, 0, null, null, null, AppOpsManager.OP_NONE, 16494 false, false, MY_PID, Process.SYSTEM_UID, UserHandle.USER_ALL); 16495 } 16496 } 16497 } 16498 16499 boolean kept = true; 16500 final ActivityStack mainStack = mStackSupervisor.getFocusedStack(); 16501 // mainStack is null during startup. 16502 if (mainStack != null) { 16503 if (changes != 0 && starting == null) { 16504 // If the configuration changed, and the caller is not already 16505 // in the process of starting an activity, then find the top 16506 // activity to check if its configuration needs to change. 16507 starting = mainStack.topRunningActivityLocked(null); 16508 } 16509 16510 if (starting != null) { 16511 kept = mainStack.ensureActivityConfigurationLocked(starting, changes); 16512 // And we need to make sure at this point that all other activities 16513 // are made visible with the correct configuration. 16514 mStackSupervisor.ensureActivitiesVisibleLocked(starting, changes); 16515 } 16516 } 16517 16518 if (values != null && mWindowManager != null) { 16519 mWindowManager.setNewConfiguration(mConfiguration); 16520 } 16521 16522 return kept; 16523 } 16524 16525 /** 16526 * Decide based on the configuration whether we should shouw the ANR, 16527 * crash, etc dialogs. The idea is that if there is no affordnace to 16528 * press the on-screen buttons, we shouldn't show the dialog. 16529 * 16530 * A thought: SystemUI might also want to get told about this, the Power 16531 * dialog / global actions also might want different behaviors. 16532 */ 16533 private static final boolean shouldShowDialogs(Configuration config) { 16534 return !(config.keyboard == Configuration.KEYBOARD_NOKEYS 16535 && config.touchscreen == Configuration.TOUCHSCREEN_NOTOUCH); 16536 } 16537 16538 /** 16539 * Save the locale. You must be inside a synchronized (this) block. 16540 */ 16541 private void saveLocaleLocked(Locale l, boolean isDiff, boolean isPersist) { 16542 if(isDiff) { 16543 SystemProperties.set("user.language", l.getLanguage()); 16544 SystemProperties.set("user.region", l.getCountry()); 16545 } 16546 16547 if(isPersist) { 16548 SystemProperties.set("persist.sys.language", l.getLanguage()); 16549 SystemProperties.set("persist.sys.country", l.getCountry()); 16550 SystemProperties.set("persist.sys.localevar", l.getVariant()); 16551 16552 mHandler.sendMessage(mHandler.obtainMessage(SEND_LOCALE_TO_MOUNT_DAEMON_MSG, l)); 16553 } 16554 } 16555 16556 @Override 16557 public boolean shouldUpRecreateTask(IBinder token, String destAffinity) { 16558 synchronized (this) { 16559 ActivityRecord srec = ActivityRecord.forToken(token); 16560 if (srec.task != null && srec.task.stack != null) { 16561 return srec.task.stack.shouldUpRecreateTaskLocked(srec, destAffinity); 16562 } 16563 } 16564 return false; 16565 } 16566 16567 public boolean navigateUpTo(IBinder token, Intent destIntent, int resultCode, 16568 Intent resultData) { 16569 16570 synchronized (this) { 16571 final ActivityStack stack = ActivityRecord.getStackLocked(token); 16572 if (stack != null) { 16573 return stack.navigateUpToLocked(token, destIntent, resultCode, resultData); 16574 } 16575 return false; 16576 } 16577 } 16578 16579 public int getLaunchedFromUid(IBinder activityToken) { 16580 ActivityRecord srec = ActivityRecord.forToken(activityToken); 16581 if (srec == null) { 16582 return -1; 16583 } 16584 return srec.launchedFromUid; 16585 } 16586 16587 public String getLaunchedFromPackage(IBinder activityToken) { 16588 ActivityRecord srec = ActivityRecord.forToken(activityToken); 16589 if (srec == null) { 16590 return null; 16591 } 16592 return srec.launchedFromPackage; 16593 } 16594 16595 // ========================================================= 16596 // LIFETIME MANAGEMENT 16597 // ========================================================= 16598 16599 // Returns which broadcast queue the app is the current [or imminent] receiver 16600 // on, or 'null' if the app is not an active broadcast recipient. 16601 private BroadcastQueue isReceivingBroadcast(ProcessRecord app) { 16602 BroadcastRecord r = app.curReceiver; 16603 if (r != null) { 16604 return r.queue; 16605 } 16606 16607 // It's not the current receiver, but it might be starting up to become one 16608 synchronized (this) { 16609 for (BroadcastQueue queue : mBroadcastQueues) { 16610 r = queue.mPendingBroadcast; 16611 if (r != null && r.curApp == app) { 16612 // found it; report which queue it's in 16613 return queue; 16614 } 16615 } 16616 } 16617 16618 return null; 16619 } 16620 16621 private final int computeOomAdjLocked(ProcessRecord app, int cachedAdj, ProcessRecord TOP_APP, 16622 boolean doingAll, long now) { 16623 if (mAdjSeq == app.adjSeq) { 16624 // This adjustment has already been computed. 16625 return app.curRawAdj; 16626 } 16627 16628 if (app.thread == null) { 16629 app.adjSeq = mAdjSeq; 16630 app.curSchedGroup = Process.THREAD_GROUP_BG_NONINTERACTIVE; 16631 app.curProcState = ActivityManager.PROCESS_STATE_CACHED_EMPTY; 16632 return (app.curAdj=app.curRawAdj=ProcessList.CACHED_APP_MAX_ADJ); 16633 } 16634 16635 app.adjTypeCode = ActivityManager.RunningAppProcessInfo.REASON_UNKNOWN; 16636 app.adjSource = null; 16637 app.adjTarget = null; 16638 app.empty = false; 16639 app.cached = false; 16640 16641 final int activitiesSize = app.activities.size(); 16642 16643 if (app.maxAdj <= ProcessList.FOREGROUND_APP_ADJ) { 16644 // The max adjustment doesn't allow this app to be anything 16645 // below foreground, so it is not worth doing work for it. 16646 app.adjType = "fixed"; 16647 app.adjSeq = mAdjSeq; 16648 app.curRawAdj = app.maxAdj; 16649 app.foregroundActivities = false; 16650 app.curSchedGroup = Process.THREAD_GROUP_DEFAULT; 16651 app.curProcState = ActivityManager.PROCESS_STATE_PERSISTENT; 16652 // System processes can do UI, and when they do we want to have 16653 // them trim their memory after the user leaves the UI. To 16654 // facilitate this, here we need to determine whether or not it 16655 // is currently showing UI. 16656 app.systemNoUi = true; 16657 if (app == TOP_APP) { 16658 app.systemNoUi = false; 16659 } else if (activitiesSize > 0) { 16660 for (int j = 0; j < activitiesSize; j++) { 16661 final ActivityRecord r = app.activities.get(j); 16662 if (r.visible) { 16663 app.systemNoUi = false; 16664 } 16665 } 16666 } 16667 if (!app.systemNoUi) { 16668 app.curProcState = ActivityManager.PROCESS_STATE_PERSISTENT_UI; 16669 } 16670 return (app.curAdj=app.maxAdj); 16671 } 16672 16673 app.systemNoUi = false; 16674 16675 // Determine the importance of the process, starting with most 16676 // important to least, and assign an appropriate OOM adjustment. 16677 int adj; 16678 int schedGroup; 16679 int procState; 16680 boolean foregroundActivities = false; 16681 BroadcastQueue queue; 16682 if (app == TOP_APP) { 16683 // The last app on the list is the foreground app. 16684 adj = ProcessList.FOREGROUND_APP_ADJ; 16685 schedGroup = Process.THREAD_GROUP_DEFAULT; 16686 app.adjType = "top-activity"; 16687 foregroundActivities = true; 16688 procState = ActivityManager.PROCESS_STATE_TOP; 16689 } else if (app.instrumentationClass != null) { 16690 // Don't want to kill running instrumentation. 16691 adj = ProcessList.FOREGROUND_APP_ADJ; 16692 schedGroup = Process.THREAD_GROUP_DEFAULT; 16693 app.adjType = "instrumentation"; 16694 procState = ActivityManager.PROCESS_STATE_IMPORTANT_FOREGROUND; 16695 } else if ((queue = isReceivingBroadcast(app)) != null) { 16696 // An app that is currently receiving a broadcast also 16697 // counts as being in the foreground for OOM killer purposes. 16698 // It's placed in a sched group based on the nature of the 16699 // broadcast as reflected by which queue it's active in. 16700 adj = ProcessList.FOREGROUND_APP_ADJ; 16701 schedGroup = (queue == mFgBroadcastQueue) 16702 ? Process.THREAD_GROUP_DEFAULT : Process.THREAD_GROUP_BG_NONINTERACTIVE; 16703 app.adjType = "broadcast"; 16704 procState = ActivityManager.PROCESS_STATE_RECEIVER; 16705 } else if (app.executingServices.size() > 0) { 16706 // An app that is currently executing a service callback also 16707 // counts as being in the foreground. 16708 adj = ProcessList.FOREGROUND_APP_ADJ; 16709 schedGroup = app.execServicesFg ? 16710 Process.THREAD_GROUP_DEFAULT : Process.THREAD_GROUP_BG_NONINTERACTIVE; 16711 app.adjType = "exec-service"; 16712 procState = ActivityManager.PROCESS_STATE_SERVICE; 16713 //Slog.i(TAG, "EXEC " + (app.execServicesFg ? "FG" : "BG") + ": " + app); 16714 } else { 16715 // As far as we know the process is empty. We may change our mind later. 16716 schedGroup = Process.THREAD_GROUP_BG_NONINTERACTIVE; 16717 // At this point we don't actually know the adjustment. Use the cached adj 16718 // value that the caller wants us to. 16719 adj = cachedAdj; 16720 procState = ActivityManager.PROCESS_STATE_CACHED_EMPTY; 16721 app.cached = true; 16722 app.empty = true; 16723 app.adjType = "cch-empty"; 16724 } 16725 16726 // Examine all activities if not already foreground. 16727 if (!foregroundActivities && activitiesSize > 0) { 16728 for (int j = 0; j < activitiesSize; j++) { 16729 final ActivityRecord r = app.activities.get(j); 16730 if (r.app != app) { 16731 Slog.w(TAG, "Wtf, activity " + r + " in proc activity list not using proc " 16732 + app + "?!?"); 16733 continue; 16734 } 16735 if (r.visible) { 16736 // App has a visible activity; only upgrade adjustment. 16737 if (adj > ProcessList.VISIBLE_APP_ADJ) { 16738 adj = ProcessList.VISIBLE_APP_ADJ; 16739 app.adjType = "visible"; 16740 } 16741 if (procState > ActivityManager.PROCESS_STATE_TOP) { 16742 procState = ActivityManager.PROCESS_STATE_TOP; 16743 } 16744 schedGroup = Process.THREAD_GROUP_DEFAULT; 16745 app.cached = false; 16746 app.empty = false; 16747 foregroundActivities = true; 16748 break; 16749 } else if (r.state == ActivityState.PAUSING || r.state == ActivityState.PAUSED) { 16750 if (adj > ProcessList.PERCEPTIBLE_APP_ADJ) { 16751 adj = ProcessList.PERCEPTIBLE_APP_ADJ; 16752 app.adjType = "pausing"; 16753 } 16754 if (procState > ActivityManager.PROCESS_STATE_TOP) { 16755 procState = ActivityManager.PROCESS_STATE_TOP; 16756 } 16757 schedGroup = Process.THREAD_GROUP_DEFAULT; 16758 app.cached = false; 16759 app.empty = false; 16760 foregroundActivities = true; 16761 } else if (r.state == ActivityState.STOPPING) { 16762 if (adj > ProcessList.PERCEPTIBLE_APP_ADJ) { 16763 adj = ProcessList.PERCEPTIBLE_APP_ADJ; 16764 app.adjType = "stopping"; 16765 } 16766 // For the process state, we will at this point consider the 16767 // process to be cached. It will be cached either as an activity 16768 // or empty depending on whether the activity is finishing. We do 16769 // this so that we can treat the process as cached for purposes of 16770 // memory trimming (determing current memory level, trim command to 16771 // send to process) since there can be an arbitrary number of stopping 16772 // processes and they should soon all go into the cached state. 16773 if (!r.finishing) { 16774 if (procState > ActivityManager.PROCESS_STATE_LAST_ACTIVITY) { 16775 procState = ActivityManager.PROCESS_STATE_LAST_ACTIVITY; 16776 } 16777 } 16778 app.cached = false; 16779 app.empty = false; 16780 foregroundActivities = true; 16781 } else { 16782 if (procState > ActivityManager.PROCESS_STATE_CACHED_ACTIVITY) { 16783 procState = ActivityManager.PROCESS_STATE_CACHED_ACTIVITY; 16784 app.adjType = "cch-act"; 16785 } 16786 } 16787 } 16788 } 16789 16790 if (adj > ProcessList.PERCEPTIBLE_APP_ADJ) { 16791 if (app.foregroundServices) { 16792 // The user is aware of this app, so make it visible. 16793 adj = ProcessList.PERCEPTIBLE_APP_ADJ; 16794 procState = ActivityManager.PROCESS_STATE_IMPORTANT_FOREGROUND; 16795 app.cached = false; 16796 app.adjType = "fg-service"; 16797 schedGroup = Process.THREAD_GROUP_DEFAULT; 16798 } else if (app.forcingToForeground != null) { 16799 // The user is aware of this app, so make it visible. 16800 adj = ProcessList.PERCEPTIBLE_APP_ADJ; 16801 procState = ActivityManager.PROCESS_STATE_IMPORTANT_FOREGROUND; 16802 app.cached = false; 16803 app.adjType = "force-fg"; 16804 app.adjSource = app.forcingToForeground; 16805 schedGroup = Process.THREAD_GROUP_DEFAULT; 16806 } 16807 } 16808 16809 if (app == mHeavyWeightProcess) { 16810 if (adj > ProcessList.HEAVY_WEIGHT_APP_ADJ) { 16811 // We don't want to kill the current heavy-weight process. 16812 adj = ProcessList.HEAVY_WEIGHT_APP_ADJ; 16813 schedGroup = Process.THREAD_GROUP_BG_NONINTERACTIVE; 16814 app.cached = false; 16815 app.adjType = "heavy"; 16816 } 16817 if (procState > ActivityManager.PROCESS_STATE_HEAVY_WEIGHT) { 16818 procState = ActivityManager.PROCESS_STATE_HEAVY_WEIGHT; 16819 } 16820 } 16821 16822 if (app == mHomeProcess) { 16823 if (adj > ProcessList.HOME_APP_ADJ) { 16824 // This process is hosting what we currently consider to be the 16825 // home app, so we don't want to let it go into the background. 16826 adj = ProcessList.HOME_APP_ADJ; 16827 schedGroup = Process.THREAD_GROUP_BG_NONINTERACTIVE; 16828 app.cached = false; 16829 app.adjType = "home"; 16830 } 16831 if (procState > ActivityManager.PROCESS_STATE_HOME) { 16832 procState = ActivityManager.PROCESS_STATE_HOME; 16833 } 16834 } 16835 16836 if (app == mPreviousProcess && app.activities.size() > 0) { 16837 if (adj > ProcessList.PREVIOUS_APP_ADJ) { 16838 // This was the previous process that showed UI to the user. 16839 // We want to try to keep it around more aggressively, to give 16840 // a good experience around switching between two apps. 16841 adj = ProcessList.PREVIOUS_APP_ADJ; 16842 schedGroup = Process.THREAD_GROUP_BG_NONINTERACTIVE; 16843 app.cached = false; 16844 app.adjType = "previous"; 16845 } 16846 if (procState > ActivityManager.PROCESS_STATE_LAST_ACTIVITY) { 16847 procState = ActivityManager.PROCESS_STATE_LAST_ACTIVITY; 16848 } 16849 } 16850 16851 if (false) Slog.i(TAG, "OOM " + app + ": initial adj=" + adj 16852 + " reason=" + app.adjType); 16853 16854 // By default, we use the computed adjustment. It may be changed if 16855 // there are applications dependent on our services or providers, but 16856 // this gives us a baseline and makes sure we don't get into an 16857 // infinite recursion. 16858 app.adjSeq = mAdjSeq; 16859 app.curRawAdj = adj; 16860 app.hasStartedServices = false; 16861 16862 if (mBackupTarget != null && app == mBackupTarget.app) { 16863 // If possible we want to avoid killing apps while they're being backed up 16864 if (adj > ProcessList.BACKUP_APP_ADJ) { 16865 if (DEBUG_BACKUP) Slog.v(TAG, "oom BACKUP_APP_ADJ for " + app); 16866 adj = ProcessList.BACKUP_APP_ADJ; 16867 if (procState > ActivityManager.PROCESS_STATE_IMPORTANT_BACKGROUND) { 16868 procState = ActivityManager.PROCESS_STATE_IMPORTANT_BACKGROUND; 16869 } 16870 app.adjType = "backup"; 16871 app.cached = false; 16872 } 16873 if (procState > ActivityManager.PROCESS_STATE_BACKUP) { 16874 procState = ActivityManager.PROCESS_STATE_BACKUP; 16875 } 16876 } 16877 16878 boolean mayBeTop = false; 16879 16880 for (int is = app.services.size()-1; 16881 is >= 0 && (adj > ProcessList.FOREGROUND_APP_ADJ 16882 || schedGroup == Process.THREAD_GROUP_BG_NONINTERACTIVE 16883 || procState > ActivityManager.PROCESS_STATE_TOP); 16884 is--) { 16885 ServiceRecord s = app.services.valueAt(is); 16886 if (s.startRequested) { 16887 app.hasStartedServices = true; 16888 if (procState > ActivityManager.PROCESS_STATE_SERVICE) { 16889 procState = ActivityManager.PROCESS_STATE_SERVICE; 16890 } 16891 if (app.hasShownUi && app != mHomeProcess) { 16892 // If this process has shown some UI, let it immediately 16893 // go to the LRU list because it may be pretty heavy with 16894 // UI stuff. We'll tag it with a label just to help 16895 // debug and understand what is going on. 16896 if (adj > ProcessList.SERVICE_ADJ) { 16897 app.adjType = "cch-started-ui-services"; 16898 } 16899 } else { 16900 if (now < (s.lastActivity + ActiveServices.MAX_SERVICE_INACTIVITY)) { 16901 // This service has seen some activity within 16902 // recent memory, so we will keep its process ahead 16903 // of the background processes. 16904 if (adj > ProcessList.SERVICE_ADJ) { 16905 adj = ProcessList.SERVICE_ADJ; 16906 app.adjType = "started-services"; 16907 app.cached = false; 16908 } 16909 } 16910 // If we have let the service slide into the background 16911 // state, still have some text describing what it is doing 16912 // even though the service no longer has an impact. 16913 if (adj > ProcessList.SERVICE_ADJ) { 16914 app.adjType = "cch-started-services"; 16915 } 16916 } 16917 } 16918 for (int conni = s.connections.size()-1; 16919 conni >= 0 && (adj > ProcessList.FOREGROUND_APP_ADJ 16920 || schedGroup == Process.THREAD_GROUP_BG_NONINTERACTIVE 16921 || procState > ActivityManager.PROCESS_STATE_TOP); 16922 conni--) { 16923 ArrayList<ConnectionRecord> clist = s.connections.valueAt(conni); 16924 for (int i = 0; 16925 i < clist.size() && (adj > ProcessList.FOREGROUND_APP_ADJ 16926 || schedGroup == Process.THREAD_GROUP_BG_NONINTERACTIVE 16927 || procState > ActivityManager.PROCESS_STATE_TOP); 16928 i++) { 16929 // XXX should compute this based on the max of 16930 // all connected clients. 16931 ConnectionRecord cr = clist.get(i); 16932 if (cr.binding.client == app) { 16933 // Binding to ourself is not interesting. 16934 continue; 16935 } 16936 if ((cr.flags&Context.BIND_WAIVE_PRIORITY) == 0) { 16937 ProcessRecord client = cr.binding.client; 16938 int clientAdj = computeOomAdjLocked(client, cachedAdj, 16939 TOP_APP, doingAll, now); 16940 int clientProcState = client.curProcState; 16941 if (clientProcState >= ActivityManager.PROCESS_STATE_CACHED_ACTIVITY) { 16942 // If the other app is cached for any reason, for purposes here 16943 // we are going to consider it empty. The specific cached state 16944 // doesn't propagate except under certain conditions. 16945 clientProcState = ActivityManager.PROCESS_STATE_CACHED_EMPTY; 16946 } 16947 String adjType = null; 16948 if ((cr.flags&Context.BIND_ALLOW_OOM_MANAGEMENT) != 0) { 16949 // Not doing bind OOM management, so treat 16950 // this guy more like a started service. 16951 if (app.hasShownUi && app != mHomeProcess) { 16952 // If this process has shown some UI, let it immediately 16953 // go to the LRU list because it may be pretty heavy with 16954 // UI stuff. We'll tag it with a label just to help 16955 // debug and understand what is going on. 16956 if (adj > clientAdj) { 16957 adjType = "cch-bound-ui-services"; 16958 } 16959 app.cached = false; 16960 clientAdj = adj; 16961 clientProcState = procState; 16962 } else { 16963 if (now >= (s.lastActivity 16964 + ActiveServices.MAX_SERVICE_INACTIVITY)) { 16965 // This service has not seen activity within 16966 // recent memory, so allow it to drop to the 16967 // LRU list if there is no other reason to keep 16968 // it around. We'll also tag it with a label just 16969 // to help debug and undertand what is going on. 16970 if (adj > clientAdj) { 16971 adjType = "cch-bound-services"; 16972 } 16973 clientAdj = adj; 16974 } 16975 } 16976 } 16977 if (adj > clientAdj) { 16978 // If this process has recently shown UI, and 16979 // the process that is binding to it is less 16980 // important than being visible, then we don't 16981 // care about the binding as much as we care 16982 // about letting this process get into the LRU 16983 // list to be killed and restarted if needed for 16984 // memory. 16985 if (app.hasShownUi && app != mHomeProcess 16986 && clientAdj > ProcessList.PERCEPTIBLE_APP_ADJ) { 16987 adjType = "cch-bound-ui-services"; 16988 } else { 16989 if ((cr.flags&(Context.BIND_ABOVE_CLIENT 16990 |Context.BIND_IMPORTANT)) != 0) { 16991 adj = clientAdj >= ProcessList.PERSISTENT_SERVICE_ADJ 16992 ? clientAdj : ProcessList.PERSISTENT_SERVICE_ADJ; 16993 } else if ((cr.flags&Context.BIND_NOT_VISIBLE) != 0 16994 && clientAdj < ProcessList.PERCEPTIBLE_APP_ADJ 16995 && adj > ProcessList.PERCEPTIBLE_APP_ADJ) { 16996 adj = ProcessList.PERCEPTIBLE_APP_ADJ; 16997 } else if (clientAdj > ProcessList.VISIBLE_APP_ADJ) { 16998 adj = clientAdj; 16999 } else { 17000 if (adj > ProcessList.VISIBLE_APP_ADJ) { 17001 adj = ProcessList.VISIBLE_APP_ADJ; 17002 } 17003 } 17004 if (!client.cached) { 17005 app.cached = false; 17006 } 17007 adjType = "service"; 17008 } 17009 } 17010 if ((cr.flags&Context.BIND_NOT_FOREGROUND) == 0) { 17011 if (client.curSchedGroup == Process.THREAD_GROUP_DEFAULT) { 17012 schedGroup = Process.THREAD_GROUP_DEFAULT; 17013 } 17014 if (clientProcState <= ActivityManager.PROCESS_STATE_TOP) { 17015 if (clientProcState == ActivityManager.PROCESS_STATE_TOP) { 17016 // Special handling of clients who are in the top state. 17017 // We *may* want to consider this process to be in the 17018 // top state as well, but only if there is not another 17019 // reason for it to be running. Being on the top is a 17020 // special state, meaning you are specifically running 17021 // for the current top app. If the process is already 17022 // running in the background for some other reason, it 17023 // is more important to continue considering it to be 17024 // in the background state. 17025 mayBeTop = true; 17026 clientProcState = ActivityManager.PROCESS_STATE_CACHED_EMPTY; 17027 } else { 17028 // Special handling for above-top states (persistent 17029 // processes). These should not bring the current process 17030 // into the top state, since they are not on top. Instead 17031 // give them the best state after that. 17032 clientProcState = 17033 ActivityManager.PROCESS_STATE_IMPORTANT_FOREGROUND; 17034 } 17035 } 17036 } else { 17037 if (clientProcState < 17038 ActivityManager.PROCESS_STATE_IMPORTANT_BACKGROUND) { 17039 clientProcState = 17040 ActivityManager.PROCESS_STATE_IMPORTANT_BACKGROUND; 17041 } 17042 } 17043 if (procState > clientProcState) { 17044 procState = clientProcState; 17045 } 17046 if (procState < ActivityManager.PROCESS_STATE_IMPORTANT_BACKGROUND 17047 && (cr.flags&Context.BIND_SHOWING_UI) != 0) { 17048 app.pendingUiClean = true; 17049 } 17050 if (adjType != null) { 17051 app.adjType = adjType; 17052 app.adjTypeCode = ActivityManager.RunningAppProcessInfo 17053 .REASON_SERVICE_IN_USE; 17054 app.adjSource = cr.binding.client; 17055 app.adjSourceProcState = clientProcState; 17056 app.adjTarget = s.name; 17057 } 17058 } 17059 if ((cr.flags&Context.BIND_TREAT_LIKE_ACTIVITY) != 0) { 17060 app.treatLikeActivity = true; 17061 } 17062 final ActivityRecord a = cr.activity; 17063 if ((cr.flags&Context.BIND_ADJUST_WITH_ACTIVITY) != 0) { 17064 if (a != null && adj > ProcessList.FOREGROUND_APP_ADJ && 17065 (a.visible || a.state == ActivityState.RESUMED 17066 || a.state == ActivityState.PAUSING)) { 17067 adj = ProcessList.FOREGROUND_APP_ADJ; 17068 if ((cr.flags&Context.BIND_NOT_FOREGROUND) == 0) { 17069 schedGroup = Process.THREAD_GROUP_DEFAULT; 17070 } 17071 app.cached = false; 17072 app.adjType = "service"; 17073 app.adjTypeCode = ActivityManager.RunningAppProcessInfo 17074 .REASON_SERVICE_IN_USE; 17075 app.adjSource = a; 17076 app.adjSourceProcState = procState; 17077 app.adjTarget = s.name; 17078 } 17079 } 17080 } 17081 } 17082 } 17083 17084 for (int provi = app.pubProviders.size()-1; 17085 provi >= 0 && (adj > ProcessList.FOREGROUND_APP_ADJ 17086 || schedGroup == Process.THREAD_GROUP_BG_NONINTERACTIVE 17087 || procState > ActivityManager.PROCESS_STATE_TOP); 17088 provi--) { 17089 ContentProviderRecord cpr = app.pubProviders.valueAt(provi); 17090 for (int i = cpr.connections.size()-1; 17091 i >= 0 && (adj > ProcessList.FOREGROUND_APP_ADJ 17092 || schedGroup == Process.THREAD_GROUP_BG_NONINTERACTIVE 17093 || procState > ActivityManager.PROCESS_STATE_TOP); 17094 i--) { 17095 ContentProviderConnection conn = cpr.connections.get(i); 17096 ProcessRecord client = conn.client; 17097 if (client == app) { 17098 // Being our own client is not interesting. 17099 continue; 17100 } 17101 int clientAdj = computeOomAdjLocked(client, cachedAdj, TOP_APP, doingAll, now); 17102 int clientProcState = client.curProcState; 17103 if (clientProcState >= ActivityManager.PROCESS_STATE_CACHED_ACTIVITY) { 17104 // If the other app is cached for any reason, for purposes here 17105 // we are going to consider it empty. 17106 clientProcState = ActivityManager.PROCESS_STATE_CACHED_EMPTY; 17107 } 17108 if (adj > clientAdj) { 17109 if (app.hasShownUi && app != mHomeProcess 17110 && clientAdj > ProcessList.PERCEPTIBLE_APP_ADJ) { 17111 app.adjType = "cch-ui-provider"; 17112 } else { 17113 adj = clientAdj > ProcessList.FOREGROUND_APP_ADJ 17114 ? clientAdj : ProcessList.FOREGROUND_APP_ADJ; 17115 app.adjType = "provider"; 17116 } 17117 app.cached &= client.cached; 17118 app.adjTypeCode = ActivityManager.RunningAppProcessInfo 17119 .REASON_PROVIDER_IN_USE; 17120 app.adjSource = client; 17121 app.adjSourceProcState = clientProcState; 17122 app.adjTarget = cpr.name; 17123 } 17124 if (clientProcState <= ActivityManager.PROCESS_STATE_TOP) { 17125 if (clientProcState == ActivityManager.PROCESS_STATE_TOP) { 17126 // Special handling of clients who are in the top state. 17127 // We *may* want to consider this process to be in the 17128 // top state as well, but only if there is not another 17129 // reason for it to be running. Being on the top is a 17130 // special state, meaning you are specifically running 17131 // for the current top app. If the process is already 17132 // running in the background for some other reason, it 17133 // is more important to continue considering it to be 17134 // in the background state. 17135 mayBeTop = true; 17136 clientProcState = ActivityManager.PROCESS_STATE_CACHED_EMPTY; 17137 } else { 17138 // Special handling for above-top states (persistent 17139 // processes). These should not bring the current process 17140 // into the top state, since they are not on top. Instead 17141 // give them the best state after that. 17142 clientProcState = 17143 ActivityManager.PROCESS_STATE_IMPORTANT_FOREGROUND; 17144 } 17145 } 17146 if (procState > clientProcState) { 17147 procState = clientProcState; 17148 } 17149 if (client.curSchedGroup == Process.THREAD_GROUP_DEFAULT) { 17150 schedGroup = Process.THREAD_GROUP_DEFAULT; 17151 } 17152 } 17153 // If the provider has external (non-framework) process 17154 // dependencies, ensure that its adjustment is at least 17155 // FOREGROUND_APP_ADJ. 17156 if (cpr.hasExternalProcessHandles()) { 17157 if (adj > ProcessList.FOREGROUND_APP_ADJ) { 17158 adj = ProcessList.FOREGROUND_APP_ADJ; 17159 schedGroup = Process.THREAD_GROUP_DEFAULT; 17160 app.cached = false; 17161 app.adjType = "provider"; 17162 app.adjTarget = cpr.name; 17163 } 17164 if (procState > ActivityManager.PROCESS_STATE_IMPORTANT_FOREGROUND) { 17165 procState = ActivityManager.PROCESS_STATE_IMPORTANT_FOREGROUND; 17166 } 17167 } 17168 } 17169 17170 if (mayBeTop && procState > ActivityManager.PROCESS_STATE_TOP) { 17171 // A client of one of our services or providers is in the top state. We 17172 // *may* want to be in the top state, but not if we are already running in 17173 // the background for some other reason. For the decision here, we are going 17174 // to pick out a few specific states that we want to remain in when a client 17175 // is top (states that tend to be longer-term) and otherwise allow it to go 17176 // to the top state. 17177 switch (procState) { 17178 case ActivityManager.PROCESS_STATE_IMPORTANT_FOREGROUND: 17179 case ActivityManager.PROCESS_STATE_IMPORTANT_BACKGROUND: 17180 case ActivityManager.PROCESS_STATE_SERVICE: 17181 // These all are longer-term states, so pull them up to the top 17182 // of the background states, but not all the way to the top state. 17183 procState = ActivityManager.PROCESS_STATE_IMPORTANT_FOREGROUND; 17184 break; 17185 default: 17186 // Otherwise, top is a better choice, so take it. 17187 procState = ActivityManager.PROCESS_STATE_TOP; 17188 break; 17189 } 17190 } 17191 17192 if (procState >= ActivityManager.PROCESS_STATE_CACHED_EMPTY) { 17193 if (app.hasClientActivities) { 17194 // This is a cached process, but with client activities. Mark it so. 17195 procState = ActivityManager.PROCESS_STATE_CACHED_ACTIVITY_CLIENT; 17196 app.adjType = "cch-client-act"; 17197 } else if (app.treatLikeActivity) { 17198 // This is a cached process, but somebody wants us to treat it like it has 17199 // an activity, okay! 17200 procState = ActivityManager.PROCESS_STATE_CACHED_ACTIVITY; 17201 app.adjType = "cch-as-act"; 17202 } 17203 } 17204 17205 if (adj == ProcessList.SERVICE_ADJ) { 17206 if (doingAll) { 17207 app.serviceb = mNewNumAServiceProcs > (mNumServiceProcs/3); 17208 mNewNumServiceProcs++; 17209 //Slog.i(TAG, "ADJ " + app + " serviceb=" + app.serviceb); 17210 if (!app.serviceb) { 17211 // This service isn't far enough down on the LRU list to 17212 // normally be a B service, but if we are low on RAM and it 17213 // is large we want to force it down since we would prefer to 17214 // keep launcher over it. 17215 if (mLastMemoryLevel > ProcessStats.ADJ_MEM_FACTOR_NORMAL 17216 && app.lastPss >= mProcessList.getCachedRestoreThresholdKb()) { 17217 app.serviceHighRam = true; 17218 app.serviceb = true; 17219 //Slog.i(TAG, "ADJ " + app + " high ram!"); 17220 } else { 17221 mNewNumAServiceProcs++; 17222 //Slog.i(TAG, "ADJ " + app + " not high ram!"); 17223 } 17224 } else { 17225 app.serviceHighRam = false; 17226 } 17227 } 17228 if (app.serviceb) { 17229 adj = ProcessList.SERVICE_B_ADJ; 17230 } 17231 } 17232 17233 app.curRawAdj = adj; 17234 17235 //Slog.i(TAG, "OOM ADJ " + app + ": pid=" + app.pid + 17236 // " adj=" + adj + " curAdj=" + app.curAdj + " maxAdj=" + app.maxAdj); 17237 if (adj > app.maxAdj) { 17238 adj = app.maxAdj; 17239 if (app.maxAdj <= ProcessList.PERCEPTIBLE_APP_ADJ) { 17240 schedGroup = Process.THREAD_GROUP_DEFAULT; 17241 } 17242 } 17243 17244 // Do final modification to adj. Everything we do between here and applying 17245 // the final setAdj must be done in this function, because we will also use 17246 // it when computing the final cached adj later. Note that we don't need to 17247 // worry about this for max adj above, since max adj will always be used to 17248 // keep it out of the cached vaues. 17249 app.curAdj = app.modifyRawOomAdj(adj); 17250 app.curSchedGroup = schedGroup; 17251 app.curProcState = procState; 17252 app.foregroundActivities = foregroundActivities; 17253 17254 return app.curRawAdj; 17255 } 17256 17257 /** 17258 * Schedule PSS collection of a process. 17259 */ 17260 void requestPssLocked(ProcessRecord proc, int procState) { 17261 if (mPendingPssProcesses.contains(proc)) { 17262 return; 17263 } 17264 if (mPendingPssProcesses.size() == 0) { 17265 mBgHandler.sendEmptyMessage(COLLECT_PSS_BG_MSG); 17266 } 17267 if (DEBUG_PSS) Slog.d(TAG, "Requesting PSS of: " + proc); 17268 proc.pssProcState = procState; 17269 mPendingPssProcesses.add(proc); 17270 } 17271 17272 /** 17273 * Schedule PSS collection of all processes. 17274 */ 17275 void requestPssAllProcsLocked(long now, boolean always, boolean memLowered) { 17276 if (!always) { 17277 if (now < (mLastFullPssTime + 17278 (memLowered ? FULL_PSS_LOWERED_INTERVAL : FULL_PSS_MIN_INTERVAL))) { 17279 return; 17280 } 17281 } 17282 if (DEBUG_PSS) Slog.d(TAG, "Requesting PSS of all procs! memLowered=" + memLowered); 17283 mLastFullPssTime = now; 17284 mFullPssPending = true; 17285 mPendingPssProcesses.ensureCapacity(mLruProcesses.size()); 17286 mPendingPssProcesses.clear(); 17287 for (int i=mLruProcesses.size()-1; i>=0; i--) { 17288 ProcessRecord app = mLruProcesses.get(i); 17289 if (memLowered || now > (app.lastStateTime+ProcessList.PSS_ALL_INTERVAL)) { 17290 app.pssProcState = app.setProcState; 17291 app.nextPssTime = ProcessList.computeNextPssTime(app.curProcState, true, 17292 isSleeping(), now); 17293 mPendingPssProcesses.add(app); 17294 } 17295 } 17296 mBgHandler.sendEmptyMessage(COLLECT_PSS_BG_MSG); 17297 } 17298 17299 /** 17300 * Ask a given process to GC right now. 17301 */ 17302 final void performAppGcLocked(ProcessRecord app) { 17303 try { 17304 app.lastRequestedGc = SystemClock.uptimeMillis(); 17305 if (app.thread != null) { 17306 if (app.reportLowMemory) { 17307 app.reportLowMemory = false; 17308 app.thread.scheduleLowMemory(); 17309 } else { 17310 app.thread.processInBackground(); 17311 } 17312 } 17313 } catch (Exception e) { 17314 // whatever. 17315 } 17316 } 17317 17318 /** 17319 * Returns true if things are idle enough to perform GCs. 17320 */ 17321 private final boolean canGcNowLocked() { 17322 boolean processingBroadcasts = false; 17323 for (BroadcastQueue q : mBroadcastQueues) { 17324 if (q.mParallelBroadcasts.size() != 0 || q.mOrderedBroadcasts.size() != 0) { 17325 processingBroadcasts = true; 17326 } 17327 } 17328 return !processingBroadcasts 17329 && (isSleeping() || mStackSupervisor.allResumedActivitiesIdle()); 17330 } 17331 17332 /** 17333 * Perform GCs on all processes that are waiting for it, but only 17334 * if things are idle. 17335 */ 17336 final void performAppGcsLocked() { 17337 final int N = mProcessesToGc.size(); 17338 if (N <= 0) { 17339 return; 17340 } 17341 if (canGcNowLocked()) { 17342 while (mProcessesToGc.size() > 0) { 17343 ProcessRecord proc = mProcessesToGc.remove(0); 17344 if (proc.curRawAdj > ProcessList.PERCEPTIBLE_APP_ADJ || proc.reportLowMemory) { 17345 if ((proc.lastRequestedGc+GC_MIN_INTERVAL) 17346 <= SystemClock.uptimeMillis()) { 17347 // To avoid spamming the system, we will GC processes one 17348 // at a time, waiting a few seconds between each. 17349 performAppGcLocked(proc); 17350 scheduleAppGcsLocked(); 17351 return; 17352 } else { 17353 // It hasn't been long enough since we last GCed this 17354 // process... put it in the list to wait for its time. 17355 addProcessToGcListLocked(proc); 17356 break; 17357 } 17358 } 17359 } 17360 17361 scheduleAppGcsLocked(); 17362 } 17363 } 17364 17365 /** 17366 * If all looks good, perform GCs on all processes waiting for them. 17367 */ 17368 final void performAppGcsIfAppropriateLocked() { 17369 if (canGcNowLocked()) { 17370 performAppGcsLocked(); 17371 return; 17372 } 17373 // Still not idle, wait some more. 17374 scheduleAppGcsLocked(); 17375 } 17376 17377 /** 17378 * Schedule the execution of all pending app GCs. 17379 */ 17380 final void scheduleAppGcsLocked() { 17381 mHandler.removeMessages(GC_BACKGROUND_PROCESSES_MSG); 17382 17383 if (mProcessesToGc.size() > 0) { 17384 // Schedule a GC for the time to the next process. 17385 ProcessRecord proc = mProcessesToGc.get(0); 17386 Message msg = mHandler.obtainMessage(GC_BACKGROUND_PROCESSES_MSG); 17387 17388 long when = proc.lastRequestedGc + GC_MIN_INTERVAL; 17389 long now = SystemClock.uptimeMillis(); 17390 if (when < (now+GC_TIMEOUT)) { 17391 when = now + GC_TIMEOUT; 17392 } 17393 mHandler.sendMessageAtTime(msg, when); 17394 } 17395 } 17396 17397 /** 17398 * Add a process to the array of processes waiting to be GCed. Keeps the 17399 * list in sorted order by the last GC time. The process can't already be 17400 * on the list. 17401 */ 17402 final void addProcessToGcListLocked(ProcessRecord proc) { 17403 boolean added = false; 17404 for (int i=mProcessesToGc.size()-1; i>=0; i--) { 17405 if (mProcessesToGc.get(i).lastRequestedGc < 17406 proc.lastRequestedGc) { 17407 added = true; 17408 mProcessesToGc.add(i+1, proc); 17409 break; 17410 } 17411 } 17412 if (!added) { 17413 mProcessesToGc.add(0, proc); 17414 } 17415 } 17416 17417 /** 17418 * Set up to ask a process to GC itself. This will either do it 17419 * immediately, or put it on the list of processes to gc the next 17420 * time things are idle. 17421 */ 17422 final void scheduleAppGcLocked(ProcessRecord app) { 17423 long now = SystemClock.uptimeMillis(); 17424 if ((app.lastRequestedGc+GC_MIN_INTERVAL) > now) { 17425 return; 17426 } 17427 if (!mProcessesToGc.contains(app)) { 17428 addProcessToGcListLocked(app); 17429 scheduleAppGcsLocked(); 17430 } 17431 } 17432 17433 final void checkExcessivePowerUsageLocked(boolean doKills) { 17434 updateCpuStatsNow(); 17435 17436 BatteryStatsImpl stats = mBatteryStatsService.getActiveStatistics(); 17437 boolean doWakeKills = doKills; 17438 boolean doCpuKills = doKills; 17439 if (mLastPowerCheckRealtime == 0) { 17440 doWakeKills = false; 17441 } 17442 if (mLastPowerCheckUptime == 0) { 17443 doCpuKills = false; 17444 } 17445 if (stats.isScreenOn()) { 17446 doWakeKills = false; 17447 } 17448 final long curRealtime = SystemClock.elapsedRealtime(); 17449 final long realtimeSince = curRealtime - mLastPowerCheckRealtime; 17450 final long curUptime = SystemClock.uptimeMillis(); 17451 final long uptimeSince = curUptime - mLastPowerCheckUptime; 17452 mLastPowerCheckRealtime = curRealtime; 17453 mLastPowerCheckUptime = curUptime; 17454 if (realtimeSince < WAKE_LOCK_MIN_CHECK_DURATION) { 17455 doWakeKills = false; 17456 } 17457 if (uptimeSince < CPU_MIN_CHECK_DURATION) { 17458 doCpuKills = false; 17459 } 17460 int i = mLruProcesses.size(); 17461 while (i > 0) { 17462 i--; 17463 ProcessRecord app = mLruProcesses.get(i); 17464 if (app.setProcState >= ActivityManager.PROCESS_STATE_HOME) { 17465 long wtime; 17466 synchronized (stats) { 17467 wtime = stats.getProcessWakeTime(app.info.uid, 17468 app.pid, curRealtime); 17469 } 17470 long wtimeUsed = wtime - app.lastWakeTime; 17471 long cputimeUsed = app.curCpuTime - app.lastCpuTime; 17472 if (DEBUG_POWER) { 17473 StringBuilder sb = new StringBuilder(128); 17474 sb.append("Wake for "); 17475 app.toShortString(sb); 17476 sb.append(": over "); 17477 TimeUtils.formatDuration(realtimeSince, sb); 17478 sb.append(" used "); 17479 TimeUtils.formatDuration(wtimeUsed, sb); 17480 sb.append(" ("); 17481 sb.append((wtimeUsed*100)/realtimeSince); 17482 sb.append("%)"); 17483 Slog.i(TAG, sb.toString()); 17484 sb.setLength(0); 17485 sb.append("CPU for "); 17486 app.toShortString(sb); 17487 sb.append(": over "); 17488 TimeUtils.formatDuration(uptimeSince, sb); 17489 sb.append(" used "); 17490 TimeUtils.formatDuration(cputimeUsed, sb); 17491 sb.append(" ("); 17492 sb.append((cputimeUsed*100)/uptimeSince); 17493 sb.append("%)"); 17494 Slog.i(TAG, sb.toString()); 17495 } 17496 // If a process has held a wake lock for more 17497 // than 50% of the time during this period, 17498 // that sounds bad. Kill! 17499 if (doWakeKills && realtimeSince > 0 17500 && ((wtimeUsed*100)/realtimeSince) >= 50) { 17501 synchronized (stats) { 17502 stats.reportExcessiveWakeLocked(app.info.uid, app.processName, 17503 realtimeSince, wtimeUsed); 17504 } 17505 app.kill("excessive wake held " + wtimeUsed + " during " + realtimeSince, true); 17506 app.baseProcessTracker.reportExcessiveWake(app.pkgList); 17507 } else if (doCpuKills && uptimeSince > 0 17508 && ((cputimeUsed*100)/uptimeSince) >= 25) { 17509 synchronized (stats) { 17510 stats.reportExcessiveCpuLocked(app.info.uid, app.processName, 17511 uptimeSince, cputimeUsed); 17512 } 17513 app.kill("excessive cpu " + cputimeUsed + " during " + uptimeSince, true); 17514 app.baseProcessTracker.reportExcessiveCpu(app.pkgList); 17515 } else { 17516 app.lastWakeTime = wtime; 17517 app.lastCpuTime = app.curCpuTime; 17518 } 17519 } 17520 } 17521 } 17522 17523 private final boolean applyOomAdjLocked(ProcessRecord app, 17524 ProcessRecord TOP_APP, boolean doingAll, long now) { 17525 boolean success = true; 17526 17527 if (app.curRawAdj != app.setRawAdj) { 17528 app.setRawAdj = app.curRawAdj; 17529 } 17530 17531 int changes = 0; 17532 17533 if (app.curAdj != app.setAdj) { 17534 ProcessList.setOomAdj(app.pid, app.info.uid, app.curAdj); 17535 if (DEBUG_SWITCH || DEBUG_OOM_ADJ) Slog.v( 17536 TAG, "Set " + app.pid + " " + app.processName + 17537 " adj " + app.curAdj + ": " + app.adjType); 17538 app.setAdj = app.curAdj; 17539 } 17540 17541 if (app.setSchedGroup != app.curSchedGroup) { 17542 app.setSchedGroup = app.curSchedGroup; 17543 if (DEBUG_SWITCH || DEBUG_OOM_ADJ) Slog.v(TAG, 17544 "Setting process group of " + app.processName 17545 + " to " + app.curSchedGroup); 17546 if (app.waitingToKill != null && 17547 app.setSchedGroup == Process.THREAD_GROUP_BG_NONINTERACTIVE) { 17548 app.kill(app.waitingToKill, true); 17549 success = false; 17550 } else { 17551 if (true) { 17552 long oldId = Binder.clearCallingIdentity(); 17553 try { 17554 Process.setProcessGroup(app.pid, app.curSchedGroup); 17555 } catch (Exception e) { 17556 Slog.w(TAG, "Failed setting process group of " + app.pid 17557 + " to " + app.curSchedGroup); 17558 e.printStackTrace(); 17559 } finally { 17560 Binder.restoreCallingIdentity(oldId); 17561 } 17562 } else { 17563 if (app.thread != null) { 17564 try { 17565 app.thread.setSchedulingGroup(app.curSchedGroup); 17566 } catch (RemoteException e) { 17567 } 17568 } 17569 } 17570 Process.setSwappiness(app.pid, 17571 app.curSchedGroup <= Process.THREAD_GROUP_BG_NONINTERACTIVE); 17572 } 17573 } 17574 if (app.repForegroundActivities != app.foregroundActivities) { 17575 app.repForegroundActivities = app.foregroundActivities; 17576 changes |= ProcessChangeItem.CHANGE_ACTIVITIES; 17577 } 17578 if (app.repProcState != app.curProcState) { 17579 app.repProcState = app.curProcState; 17580 changes |= ProcessChangeItem.CHANGE_PROCESS_STATE; 17581 if (app.thread != null) { 17582 try { 17583 if (false) { 17584 //RuntimeException h = new RuntimeException("here"); 17585 Slog.i(TAG, "Sending new process state " + app.repProcState 17586 + " to " + app /*, h*/); 17587 } 17588 app.thread.setProcessState(app.repProcState); 17589 } catch (RemoteException e) { 17590 } 17591 } 17592 } 17593 if (app.setProcState < 0 || ProcessList.procStatesDifferForMem(app.curProcState, 17594 app.setProcState)) { 17595 app.lastStateTime = now; 17596 app.nextPssTime = ProcessList.computeNextPssTime(app.curProcState, true, 17597 isSleeping(), now); 17598 if (DEBUG_PSS) Slog.d(TAG, "Process state change from " 17599 + ProcessList.makeProcStateString(app.setProcState) + " to " 17600 + ProcessList.makeProcStateString(app.curProcState) + " next pss in " 17601 + (app.nextPssTime-now) + ": " + app); 17602 } else { 17603 if (now > app.nextPssTime || (now > (app.lastPssTime+ProcessList.PSS_MAX_INTERVAL) 17604 && now > (app.lastStateTime+ProcessList.PSS_MIN_TIME_FROM_STATE_CHANGE))) { 17605 requestPssLocked(app, app.setProcState); 17606 app.nextPssTime = ProcessList.computeNextPssTime(app.curProcState, false, 17607 isSleeping(), now); 17608 } else if (false && DEBUG_PSS) { 17609 Slog.d(TAG, "Not requesting PSS of " + app + ": next=" + (app.nextPssTime-now)); 17610 } 17611 } 17612 if (app.setProcState != app.curProcState) { 17613 if (DEBUG_SWITCH || DEBUG_OOM_ADJ) Slog.v(TAG, 17614 "Proc state change of " + app.processName 17615 + " to " + app.curProcState); 17616 boolean setImportant = app.setProcState < ActivityManager.PROCESS_STATE_SERVICE; 17617 boolean curImportant = app.curProcState < ActivityManager.PROCESS_STATE_SERVICE; 17618 if (setImportant && !curImportant) { 17619 // This app is no longer something we consider important enough to allow to 17620 // use arbitrary amounts of battery power. Note 17621 // its current wake lock time to later know to kill it if 17622 // it is not behaving well. 17623 BatteryStatsImpl stats = mBatteryStatsService.getActiveStatistics(); 17624 synchronized (stats) { 17625 app.lastWakeTime = stats.getProcessWakeTime(app.info.uid, 17626 app.pid, SystemClock.elapsedRealtime()); 17627 } 17628 app.lastCpuTime = app.curCpuTime; 17629 17630 } 17631 app.setProcState = app.curProcState; 17632 if (app.setProcState >= ActivityManager.PROCESS_STATE_HOME) { 17633 app.notCachedSinceIdle = false; 17634 } 17635 if (!doingAll) { 17636 setProcessTrackerStateLocked(app, mProcessStats.getMemFactorLocked(), now); 17637 } else { 17638 app.procStateChanged = true; 17639 } 17640 } 17641 17642 if (changes != 0) { 17643 if (DEBUG_PROCESS_OBSERVERS) Slog.i(TAG, "Changes in " + app + ": " + changes); 17644 int i = mPendingProcessChanges.size()-1; 17645 ProcessChangeItem item = null; 17646 while (i >= 0) { 17647 item = mPendingProcessChanges.get(i); 17648 if (item.pid == app.pid) { 17649 if (DEBUG_PROCESS_OBSERVERS) Slog.i(TAG, "Re-using existing item: " + item); 17650 break; 17651 } 17652 i--; 17653 } 17654 if (i < 0) { 17655 // No existing item in pending changes; need a new one. 17656 final int NA = mAvailProcessChanges.size(); 17657 if (NA > 0) { 17658 item = mAvailProcessChanges.remove(NA-1); 17659 if (DEBUG_PROCESS_OBSERVERS) Slog.i(TAG, "Retreiving available item: " + item); 17660 } else { 17661 item = new ProcessChangeItem(); 17662 if (DEBUG_PROCESS_OBSERVERS) Slog.i(TAG, "Allocating new item: " + item); 17663 } 17664 item.changes = 0; 17665 item.pid = app.pid; 17666 item.uid = app.info.uid; 17667 if (mPendingProcessChanges.size() == 0) { 17668 if (DEBUG_PROCESS_OBSERVERS) Slog.i(TAG, 17669 "*** Enqueueing dispatch processes changed!"); 17670 mHandler.obtainMessage(DISPATCH_PROCESSES_CHANGED).sendToTarget(); 17671 } 17672 mPendingProcessChanges.add(item); 17673 } 17674 item.changes |= changes; 17675 item.processState = app.repProcState; 17676 item.foregroundActivities = app.repForegroundActivities; 17677 if (DEBUG_PROCESS_OBSERVERS) Slog.i(TAG, "Item " 17678 + Integer.toHexString(System.identityHashCode(item)) 17679 + " " + app.toShortString() + ": changes=" + item.changes 17680 + " procState=" + item.processState 17681 + " foreground=" + item.foregroundActivities 17682 + " type=" + app.adjType + " source=" + app.adjSource 17683 + " target=" + app.adjTarget); 17684 } 17685 17686 return success; 17687 } 17688 17689 private final void setProcessTrackerStateLocked(ProcessRecord proc, int memFactor, long now) { 17690 if (proc.thread != null) { 17691 if (proc.baseProcessTracker != null) { 17692 proc.baseProcessTracker.setState(proc.repProcState, memFactor, now, proc.pkgList); 17693 } 17694 if (proc.repProcState >= 0) { 17695 mBatteryStatsService.noteProcessState(proc.processName, proc.info.uid, 17696 proc.repProcState); 17697 } 17698 } 17699 } 17700 17701 private final boolean updateOomAdjLocked(ProcessRecord app, int cachedAdj, 17702 ProcessRecord TOP_APP, boolean doingAll, long now) { 17703 if (app.thread == null) { 17704 return false; 17705 } 17706 17707 computeOomAdjLocked(app, cachedAdj, TOP_APP, doingAll, now); 17708 17709 return applyOomAdjLocked(app, TOP_APP, doingAll, now); 17710 } 17711 17712 final void updateProcessForegroundLocked(ProcessRecord proc, boolean isForeground, 17713 boolean oomAdj) { 17714 if (isForeground != proc.foregroundServices) { 17715 proc.foregroundServices = isForeground; 17716 ArrayList<ProcessRecord> curProcs = mForegroundPackages.get(proc.info.packageName, 17717 proc.info.uid); 17718 if (isForeground) { 17719 if (curProcs == null) { 17720 curProcs = new ArrayList<ProcessRecord>(); 17721 mForegroundPackages.put(proc.info.packageName, proc.info.uid, curProcs); 17722 } 17723 if (!curProcs.contains(proc)) { 17724 curProcs.add(proc); 17725 mBatteryStatsService.noteEvent(BatteryStats.HistoryItem.EVENT_FOREGROUND_START, 17726 proc.info.packageName, proc.info.uid); 17727 } 17728 } else { 17729 if (curProcs != null) { 17730 if (curProcs.remove(proc)) { 17731 mBatteryStatsService.noteEvent( 17732 BatteryStats.HistoryItem.EVENT_FOREGROUND_FINISH, 17733 proc.info.packageName, proc.info.uid); 17734 if (curProcs.size() <= 0) { 17735 mForegroundPackages.remove(proc.info.packageName, proc.info.uid); 17736 } 17737 } 17738 } 17739 } 17740 if (oomAdj) { 17741 updateOomAdjLocked(); 17742 } 17743 } 17744 } 17745 17746 private final ActivityRecord resumedAppLocked() { 17747 ActivityRecord act = mStackSupervisor.resumedAppLocked(); 17748 String pkg; 17749 int uid; 17750 if (act != null) { 17751 pkg = act.packageName; 17752 uid = act.info.applicationInfo.uid; 17753 } else { 17754 pkg = null; 17755 uid = -1; 17756 } 17757 // Has the UID or resumed package name changed? 17758 if (uid != mCurResumedUid || (pkg != mCurResumedPackage 17759 && (pkg == null || !pkg.equals(mCurResumedPackage)))) { 17760 if (mCurResumedPackage != null) { 17761 mBatteryStatsService.noteEvent(BatteryStats.HistoryItem.EVENT_TOP_FINISH, 17762 mCurResumedPackage, mCurResumedUid); 17763 } 17764 mCurResumedPackage = pkg; 17765 mCurResumedUid = uid; 17766 if (mCurResumedPackage != null) { 17767 mBatteryStatsService.noteEvent(BatteryStats.HistoryItem.EVENT_TOP_START, 17768 mCurResumedPackage, mCurResumedUid); 17769 } 17770 } 17771 return act; 17772 } 17773 17774 final boolean updateOomAdjLocked(ProcessRecord app) { 17775 final ActivityRecord TOP_ACT = resumedAppLocked(); 17776 final ProcessRecord TOP_APP = TOP_ACT != null ? TOP_ACT.app : null; 17777 final boolean wasCached = app.cached; 17778 17779 mAdjSeq++; 17780 17781 // This is the desired cached adjusment we want to tell it to use. 17782 // If our app is currently cached, we know it, and that is it. Otherwise, 17783 // we don't know it yet, and it needs to now be cached we will then 17784 // need to do a complete oom adj. 17785 final int cachedAdj = app.curRawAdj >= ProcessList.CACHED_APP_MIN_ADJ 17786 ? app.curRawAdj : ProcessList.UNKNOWN_ADJ; 17787 boolean success = updateOomAdjLocked(app, cachedAdj, TOP_APP, false, 17788 SystemClock.uptimeMillis()); 17789 if (wasCached != app.cached || app.curRawAdj == ProcessList.UNKNOWN_ADJ) { 17790 // Changed to/from cached state, so apps after it in the LRU 17791 // list may also be changed. 17792 updateOomAdjLocked(); 17793 } 17794 return success; 17795 } 17796 17797 final void updateOomAdjLocked() { 17798 final ActivityRecord TOP_ACT = resumedAppLocked(); 17799 final ProcessRecord TOP_APP = TOP_ACT != null ? TOP_ACT.app : null; 17800 final long now = SystemClock.uptimeMillis(); 17801 final long oldTime = now - ProcessList.MAX_EMPTY_TIME; 17802 final int N = mLruProcesses.size(); 17803 17804 if (false) { 17805 RuntimeException e = new RuntimeException(); 17806 e.fillInStackTrace(); 17807 Slog.i(TAG, "updateOomAdj: top=" + TOP_ACT, e); 17808 } 17809 17810 mAdjSeq++; 17811 mNewNumServiceProcs = 0; 17812 mNewNumAServiceProcs = 0; 17813 17814 final int emptyProcessLimit; 17815 final int cachedProcessLimit; 17816 if (mProcessLimit <= 0) { 17817 emptyProcessLimit = cachedProcessLimit = 0; 17818 } else if (mProcessLimit == 1) { 17819 emptyProcessLimit = 1; 17820 cachedProcessLimit = 0; 17821 } else { 17822 emptyProcessLimit = ProcessList.computeEmptyProcessLimit(mProcessLimit); 17823 cachedProcessLimit = mProcessLimit - emptyProcessLimit; 17824 } 17825 17826 // Let's determine how many processes we have running vs. 17827 // how many slots we have for background processes; we may want 17828 // to put multiple processes in a slot of there are enough of 17829 // them. 17830 int numSlots = (ProcessList.CACHED_APP_MAX_ADJ 17831 - ProcessList.CACHED_APP_MIN_ADJ + 1) / 2; 17832 int numEmptyProcs = N - mNumNonCachedProcs - mNumCachedHiddenProcs; 17833 if (numEmptyProcs > cachedProcessLimit) { 17834 // If there are more empty processes than our limit on cached 17835 // processes, then use the cached process limit for the factor. 17836 // This ensures that the really old empty processes get pushed 17837 // down to the bottom, so if we are running low on memory we will 17838 // have a better chance at keeping around more cached processes 17839 // instead of a gazillion empty processes. 17840 numEmptyProcs = cachedProcessLimit; 17841 } 17842 int emptyFactor = numEmptyProcs/numSlots; 17843 if (emptyFactor < 1) emptyFactor = 1; 17844 int cachedFactor = (mNumCachedHiddenProcs > 0 ? mNumCachedHiddenProcs : 1)/numSlots; 17845 if (cachedFactor < 1) cachedFactor = 1; 17846 int stepCached = 0; 17847 int stepEmpty = 0; 17848 int numCached = 0; 17849 int numEmpty = 0; 17850 int numTrimming = 0; 17851 17852 mNumNonCachedProcs = 0; 17853 mNumCachedHiddenProcs = 0; 17854 17855 // First update the OOM adjustment for each of the 17856 // application processes based on their current state. 17857 int curCachedAdj = ProcessList.CACHED_APP_MIN_ADJ; 17858 int nextCachedAdj = curCachedAdj+1; 17859 int curEmptyAdj = ProcessList.CACHED_APP_MIN_ADJ; 17860 int nextEmptyAdj = curEmptyAdj+2; 17861 for (int i=N-1; i>=0; i--) { 17862 ProcessRecord app = mLruProcesses.get(i); 17863 if (!app.killedByAm && app.thread != null) { 17864 app.procStateChanged = false; 17865 computeOomAdjLocked(app, ProcessList.UNKNOWN_ADJ, TOP_APP, true, now); 17866 17867 // If we haven't yet assigned the final cached adj 17868 // to the process, do that now. 17869 if (app.curAdj >= ProcessList.UNKNOWN_ADJ) { 17870 switch (app.curProcState) { 17871 case ActivityManager.PROCESS_STATE_CACHED_ACTIVITY: 17872 case ActivityManager.PROCESS_STATE_CACHED_ACTIVITY_CLIENT: 17873 // This process is a cached process holding activities... 17874 // assign it the next cached value for that type, and then 17875 // step that cached level. 17876 app.curRawAdj = curCachedAdj; 17877 app.curAdj = app.modifyRawOomAdj(curCachedAdj); 17878 if (DEBUG_LRU && false) Slog.d(TAG, "Assigning activity LRU #" + i 17879 + " adj: " + app.curAdj + " (curCachedAdj=" + curCachedAdj 17880 + ")"); 17881 if (curCachedAdj != nextCachedAdj) { 17882 stepCached++; 17883 if (stepCached >= cachedFactor) { 17884 stepCached = 0; 17885 curCachedAdj = nextCachedAdj; 17886 nextCachedAdj += 2; 17887 if (nextCachedAdj > ProcessList.CACHED_APP_MAX_ADJ) { 17888 nextCachedAdj = ProcessList.CACHED_APP_MAX_ADJ; 17889 } 17890 } 17891 } 17892 break; 17893 default: 17894 // For everything else, assign next empty cached process 17895 // level and bump that up. Note that this means that 17896 // long-running services that have dropped down to the 17897 // cached level will be treated as empty (since their process 17898 // state is still as a service), which is what we want. 17899 app.curRawAdj = curEmptyAdj; 17900 app.curAdj = app.modifyRawOomAdj(curEmptyAdj); 17901 if (DEBUG_LRU && false) Slog.d(TAG, "Assigning empty LRU #" + i 17902 + " adj: " + app.curAdj + " (curEmptyAdj=" + curEmptyAdj 17903 + ")"); 17904 if (curEmptyAdj != nextEmptyAdj) { 17905 stepEmpty++; 17906 if (stepEmpty >= emptyFactor) { 17907 stepEmpty = 0; 17908 curEmptyAdj = nextEmptyAdj; 17909 nextEmptyAdj += 2; 17910 if (nextEmptyAdj > ProcessList.CACHED_APP_MAX_ADJ) { 17911 nextEmptyAdj = ProcessList.CACHED_APP_MAX_ADJ; 17912 } 17913 } 17914 } 17915 break; 17916 } 17917 } 17918 17919 applyOomAdjLocked(app, TOP_APP, true, now); 17920 17921 // Count the number of process types. 17922 switch (app.curProcState) { 17923 case ActivityManager.PROCESS_STATE_CACHED_ACTIVITY: 17924 case ActivityManager.PROCESS_STATE_CACHED_ACTIVITY_CLIENT: 17925 mNumCachedHiddenProcs++; 17926 numCached++; 17927 if (numCached > cachedProcessLimit) { 17928 app.kill("cached #" + numCached, true); 17929 } 17930 break; 17931 case ActivityManager.PROCESS_STATE_CACHED_EMPTY: 17932 if (numEmpty > ProcessList.TRIM_EMPTY_APPS 17933 && app.lastActivityTime < oldTime) { 17934 app.kill("empty for " 17935 + ((oldTime + ProcessList.MAX_EMPTY_TIME - app.lastActivityTime) 17936 / 1000) + "s", true); 17937 } else { 17938 numEmpty++; 17939 if (numEmpty > emptyProcessLimit) { 17940 app.kill("empty #" + numEmpty, true); 17941 } 17942 } 17943 break; 17944 default: 17945 mNumNonCachedProcs++; 17946 break; 17947 } 17948 17949 if (app.isolated && app.services.size() <= 0) { 17950 // If this is an isolated process, and there are no 17951 // services running in it, then the process is no longer 17952 // needed. We agressively kill these because we can by 17953 // definition not re-use the same process again, and it is 17954 // good to avoid having whatever code was running in them 17955 // left sitting around after no longer needed. 17956 app.kill("isolated not needed", true); 17957 } 17958 17959 if (app.curProcState >= ActivityManager.PROCESS_STATE_HOME 17960 && !app.killedByAm) { 17961 numTrimming++; 17962 } 17963 } 17964 } 17965 17966 mNumServiceProcs = mNewNumServiceProcs; 17967 17968 // Now determine the memory trimming level of background processes. 17969 // Unfortunately we need to start at the back of the list to do this 17970 // properly. We only do this if the number of background apps we 17971 // are managing to keep around is less than half the maximum we desire; 17972 // if we are keeping a good number around, we'll let them use whatever 17973 // memory they want. 17974 final int numCachedAndEmpty = numCached + numEmpty; 17975 int memFactor; 17976 if (numCached <= ProcessList.TRIM_CACHED_APPS 17977 && numEmpty <= ProcessList.TRIM_EMPTY_APPS) { 17978 if (numCachedAndEmpty <= ProcessList.TRIM_CRITICAL_THRESHOLD) { 17979 memFactor = ProcessStats.ADJ_MEM_FACTOR_CRITICAL; 17980 } else if (numCachedAndEmpty <= ProcessList.TRIM_LOW_THRESHOLD) { 17981 memFactor = ProcessStats.ADJ_MEM_FACTOR_LOW; 17982 } else { 17983 memFactor = ProcessStats.ADJ_MEM_FACTOR_MODERATE; 17984 } 17985 } else { 17986 memFactor = ProcessStats.ADJ_MEM_FACTOR_NORMAL; 17987 } 17988 // We always allow the memory level to go up (better). We only allow it to go 17989 // down if we are in a state where that is allowed, *and* the total number of processes 17990 // has gone down since last time. 17991 if (DEBUG_OOM_ADJ) Slog.d(TAG, "oom: memFactor=" + memFactor + " last=" + mLastMemoryLevel 17992 + " allowLow=" + mAllowLowerMemLevel + " numProcs=" + mLruProcesses.size() 17993 + " last=" + mLastNumProcesses); 17994 if (memFactor > mLastMemoryLevel) { 17995 if (!mAllowLowerMemLevel || mLruProcesses.size() >= mLastNumProcesses) { 17996 memFactor = mLastMemoryLevel; 17997 if (DEBUG_OOM_ADJ) Slog.d(TAG, "Keeping last mem factor!"); 17998 } 17999 } 18000 mLastMemoryLevel = memFactor; 18001 mLastNumProcesses = mLruProcesses.size(); 18002 boolean allChanged = mProcessStats.setMemFactorLocked(memFactor, !isSleeping(), now); 18003 final int trackerMemFactor = mProcessStats.getMemFactorLocked(); 18004 if (memFactor != ProcessStats.ADJ_MEM_FACTOR_NORMAL) { 18005 if (mLowRamStartTime == 0) { 18006 mLowRamStartTime = now; 18007 } 18008 int step = 0; 18009 int fgTrimLevel; 18010 switch (memFactor) { 18011 case ProcessStats.ADJ_MEM_FACTOR_CRITICAL: 18012 fgTrimLevel = ComponentCallbacks2.TRIM_MEMORY_RUNNING_CRITICAL; 18013 break; 18014 case ProcessStats.ADJ_MEM_FACTOR_LOW: 18015 fgTrimLevel = ComponentCallbacks2.TRIM_MEMORY_RUNNING_LOW; 18016 break; 18017 default: 18018 fgTrimLevel = ComponentCallbacks2.TRIM_MEMORY_RUNNING_MODERATE; 18019 break; 18020 } 18021 int factor = numTrimming/3; 18022 int minFactor = 2; 18023 if (mHomeProcess != null) minFactor++; 18024 if (mPreviousProcess != null) minFactor++; 18025 if (factor < minFactor) factor = minFactor; 18026 int curLevel = ComponentCallbacks2.TRIM_MEMORY_COMPLETE; 18027 for (int i=N-1; i>=0; i--) { 18028 ProcessRecord app = mLruProcesses.get(i); 18029 if (allChanged || app.procStateChanged) { 18030 setProcessTrackerStateLocked(app, trackerMemFactor, now); 18031 app.procStateChanged = false; 18032 } 18033 if (app.curProcState >= ActivityManager.PROCESS_STATE_HOME 18034 && !app.killedByAm) { 18035 if (app.trimMemoryLevel < curLevel && app.thread != null) { 18036 try { 18037 if (DEBUG_SWITCH || DEBUG_OOM_ADJ) Slog.v(TAG, 18038 "Trimming memory of " + app.processName 18039 + " to " + curLevel); 18040 app.thread.scheduleTrimMemory(curLevel); 18041 } catch (RemoteException e) { 18042 } 18043 if (false) { 18044 // For now we won't do this; our memory trimming seems 18045 // to be good enough at this point that destroying 18046 // activities causes more harm than good. 18047 if (curLevel >= ComponentCallbacks2.TRIM_MEMORY_COMPLETE 18048 && app != mHomeProcess && app != mPreviousProcess) { 18049 // Need to do this on its own message because the stack may not 18050 // be in a consistent state at this point. 18051 // For these apps we will also finish their activities 18052 // to help them free memory. 18053 mStackSupervisor.scheduleDestroyAllActivities(app, "trim"); 18054 } 18055 } 18056 } 18057 app.trimMemoryLevel = curLevel; 18058 step++; 18059 if (step >= factor) { 18060 step = 0; 18061 switch (curLevel) { 18062 case ComponentCallbacks2.TRIM_MEMORY_COMPLETE: 18063 curLevel = ComponentCallbacks2.TRIM_MEMORY_MODERATE; 18064 break; 18065 case ComponentCallbacks2.TRIM_MEMORY_MODERATE: 18066 curLevel = ComponentCallbacks2.TRIM_MEMORY_BACKGROUND; 18067 break; 18068 } 18069 } 18070 } else if (app.curProcState == ActivityManager.PROCESS_STATE_HEAVY_WEIGHT) { 18071 if (app.trimMemoryLevel < ComponentCallbacks2.TRIM_MEMORY_BACKGROUND 18072 && app.thread != null) { 18073 try { 18074 if (DEBUG_SWITCH || DEBUG_OOM_ADJ) Slog.v(TAG, 18075 "Trimming memory of heavy-weight " + app.processName 18076 + " to " + ComponentCallbacks2.TRIM_MEMORY_BACKGROUND); 18077 app.thread.scheduleTrimMemory( 18078 ComponentCallbacks2.TRIM_MEMORY_BACKGROUND); 18079 } catch (RemoteException e) { 18080 } 18081 } 18082 app.trimMemoryLevel = ComponentCallbacks2.TRIM_MEMORY_BACKGROUND; 18083 } else { 18084 if ((app.curProcState >= ActivityManager.PROCESS_STATE_IMPORTANT_BACKGROUND 18085 || app.systemNoUi) && app.pendingUiClean) { 18086 // If this application is now in the background and it 18087 // had done UI, then give it the special trim level to 18088 // have it free UI resources. 18089 final int level = ComponentCallbacks2.TRIM_MEMORY_UI_HIDDEN; 18090 if (app.trimMemoryLevel < level && app.thread != null) { 18091 try { 18092 if (DEBUG_SWITCH || DEBUG_OOM_ADJ) Slog.v(TAG, 18093 "Trimming memory of bg-ui " + app.processName 18094 + " to " + level); 18095 app.thread.scheduleTrimMemory(level); 18096 } catch (RemoteException e) { 18097 } 18098 } 18099 app.pendingUiClean = false; 18100 } 18101 if (app.trimMemoryLevel < fgTrimLevel && app.thread != null) { 18102 try { 18103 if (DEBUG_SWITCH || DEBUG_OOM_ADJ) Slog.v(TAG, 18104 "Trimming memory of fg " + app.processName 18105 + " to " + fgTrimLevel); 18106 app.thread.scheduleTrimMemory(fgTrimLevel); 18107 } catch (RemoteException e) { 18108 } 18109 } 18110 app.trimMemoryLevel = fgTrimLevel; 18111 } 18112 } 18113 } else { 18114 if (mLowRamStartTime != 0) { 18115 mLowRamTimeSinceLastIdle += now - mLowRamStartTime; 18116 mLowRamStartTime = 0; 18117 } 18118 for (int i=N-1; i>=0; i--) { 18119 ProcessRecord app = mLruProcesses.get(i); 18120 if (allChanged || app.procStateChanged) { 18121 setProcessTrackerStateLocked(app, trackerMemFactor, now); 18122 app.procStateChanged = false; 18123 } 18124 if ((app.curProcState >= ActivityManager.PROCESS_STATE_IMPORTANT_BACKGROUND 18125 || app.systemNoUi) && app.pendingUiClean) { 18126 if (app.trimMemoryLevel < ComponentCallbacks2.TRIM_MEMORY_UI_HIDDEN 18127 && app.thread != null) { 18128 try { 18129 if (DEBUG_SWITCH || DEBUG_OOM_ADJ) Slog.v(TAG, 18130 "Trimming memory of ui hidden " + app.processName 18131 + " to " + ComponentCallbacks2.TRIM_MEMORY_UI_HIDDEN); 18132 app.thread.scheduleTrimMemory( 18133 ComponentCallbacks2.TRIM_MEMORY_UI_HIDDEN); 18134 } catch (RemoteException e) { 18135 } 18136 } 18137 app.pendingUiClean = false; 18138 } 18139 app.trimMemoryLevel = 0; 18140 } 18141 } 18142 18143 if (mAlwaysFinishActivities) { 18144 // Need to do this on its own message because the stack may not 18145 // be in a consistent state at this point. 18146 mStackSupervisor.scheduleDestroyAllActivities(null, "always-finish"); 18147 } 18148 18149 if (allChanged) { 18150 requestPssAllProcsLocked(now, false, mProcessStats.isMemFactorLowered()); 18151 } 18152 18153 if (mProcessStats.shouldWriteNowLocked(now)) { 18154 mHandler.post(new Runnable() { 18155 @Override public void run() { 18156 synchronized (ActivityManagerService.this) { 18157 mProcessStats.writeStateAsyncLocked(); 18158 } 18159 } 18160 }); 18161 } 18162 18163 if (DEBUG_OOM_ADJ) { 18164 if (false) { 18165 RuntimeException here = new RuntimeException("here"); 18166 here.fillInStackTrace(); 18167 Slog.d(TAG, "Did OOM ADJ in " + (SystemClock.uptimeMillis()-now) + "ms", here); 18168 } else { 18169 Slog.d(TAG, "Did OOM ADJ in " + (SystemClock.uptimeMillis()-now) + "ms"); 18170 } 18171 } 18172 } 18173 18174 final void trimApplications() { 18175 synchronized (this) { 18176 int i; 18177 18178 // First remove any unused application processes whose package 18179 // has been removed. 18180 for (i=mRemovedProcesses.size()-1; i>=0; i--) { 18181 final ProcessRecord app = mRemovedProcesses.get(i); 18182 if (app.activities.size() == 0 18183 && app.curReceiver == null && app.services.size() == 0) { 18184 Slog.i( 18185 TAG, "Exiting empty application process " 18186 + app.processName + " (" 18187 + (app.thread != null ? app.thread.asBinder() : null) 18188 + ")\n"); 18189 if (app.pid > 0 && app.pid != MY_PID) { 18190 app.kill("empty", false); 18191 } else { 18192 try { 18193 app.thread.scheduleExit(); 18194 } catch (Exception e) { 18195 // Ignore exceptions. 18196 } 18197 } 18198 cleanUpApplicationRecordLocked(app, false, true, -1); 18199 mRemovedProcesses.remove(i); 18200 18201 if (app.persistent) { 18202 addAppLocked(app.info, false, null /* ABI override */); 18203 } 18204 } 18205 } 18206 18207 // Now update the oom adj for all processes. 18208 updateOomAdjLocked(); 18209 } 18210 } 18211 18212 /** This method sends the specified signal to each of the persistent apps */ 18213 public void signalPersistentProcesses(int sig) throws RemoteException { 18214 if (sig != Process.SIGNAL_USR1) { 18215 throw new SecurityException("Only SIGNAL_USR1 is allowed"); 18216 } 18217 18218 synchronized (this) { 18219 if (checkCallingPermission(android.Manifest.permission.SIGNAL_PERSISTENT_PROCESSES) 18220 != PackageManager.PERMISSION_GRANTED) { 18221 throw new SecurityException("Requires permission " 18222 + android.Manifest.permission.SIGNAL_PERSISTENT_PROCESSES); 18223 } 18224 18225 for (int i = mLruProcesses.size() - 1 ; i >= 0 ; i--) { 18226 ProcessRecord r = mLruProcesses.get(i); 18227 if (r.thread != null && r.persistent) { 18228 Process.sendSignal(r.pid, sig); 18229 } 18230 } 18231 } 18232 } 18233 18234 private void stopProfilerLocked(ProcessRecord proc, int profileType) { 18235 if (proc == null || proc == mProfileProc) { 18236 proc = mProfileProc; 18237 profileType = mProfileType; 18238 clearProfilerLocked(); 18239 } 18240 if (proc == null) { 18241 return; 18242 } 18243 try { 18244 proc.thread.profilerControl(false, null, profileType); 18245 } catch (RemoteException e) { 18246 throw new IllegalStateException("Process disappeared"); 18247 } 18248 } 18249 18250 private void clearProfilerLocked() { 18251 if (mProfileFd != null) { 18252 try { 18253 mProfileFd.close(); 18254 } catch (IOException e) { 18255 } 18256 } 18257 mProfileApp = null; 18258 mProfileProc = null; 18259 mProfileFile = null; 18260 mProfileType = 0; 18261 mAutoStopProfiler = false; 18262 mSamplingInterval = 0; 18263 } 18264 18265 public boolean profileControl(String process, int userId, boolean start, 18266 ProfilerInfo profilerInfo, int profileType) throws RemoteException { 18267 18268 try { 18269 synchronized (this) { 18270 // note: hijacking SET_ACTIVITY_WATCHER, but should be changed to 18271 // its own permission. 18272 if (checkCallingPermission(android.Manifest.permission.SET_ACTIVITY_WATCHER) 18273 != PackageManager.PERMISSION_GRANTED) { 18274 throw new SecurityException("Requires permission " 18275 + android.Manifest.permission.SET_ACTIVITY_WATCHER); 18276 } 18277 18278 if (start && (profilerInfo == null || profilerInfo.profileFd == null)) { 18279 throw new IllegalArgumentException("null profile info or fd"); 18280 } 18281 18282 ProcessRecord proc = null; 18283 if (process != null) { 18284 proc = findProcessLocked(process, userId, "profileControl"); 18285 } 18286 18287 if (start && (proc == null || proc.thread == null)) { 18288 throw new IllegalArgumentException("Unknown process: " + process); 18289 } 18290 18291 if (start) { 18292 stopProfilerLocked(null, 0); 18293 setProfileApp(proc.info, proc.processName, profilerInfo); 18294 mProfileProc = proc; 18295 mProfileType = profileType; 18296 ParcelFileDescriptor fd = profilerInfo.profileFd; 18297 try { 18298 fd = fd.dup(); 18299 } catch (IOException e) { 18300 fd = null; 18301 } 18302 profilerInfo.profileFd = fd; 18303 proc.thread.profilerControl(start, profilerInfo, profileType); 18304 fd = null; 18305 mProfileFd = null; 18306 } else { 18307 stopProfilerLocked(proc, profileType); 18308 if (profilerInfo != null && profilerInfo.profileFd != null) { 18309 try { 18310 profilerInfo.profileFd.close(); 18311 } catch (IOException e) { 18312 } 18313 } 18314 } 18315 18316 return true; 18317 } 18318 } catch (RemoteException e) { 18319 throw new IllegalStateException("Process disappeared"); 18320 } finally { 18321 if (profilerInfo != null && profilerInfo.profileFd != null) { 18322 try { 18323 profilerInfo.profileFd.close(); 18324 } catch (IOException e) { 18325 } 18326 } 18327 } 18328 } 18329 18330 private ProcessRecord findProcessLocked(String process, int userId, String callName) { 18331 userId = handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(), 18332 userId, true, ALLOW_FULL_ONLY, callName, null); 18333 ProcessRecord proc = null; 18334 try { 18335 int pid = Integer.parseInt(process); 18336 synchronized (mPidsSelfLocked) { 18337 proc = mPidsSelfLocked.get(pid); 18338 } 18339 } catch (NumberFormatException e) { 18340 } 18341 18342 if (proc == null) { 18343 ArrayMap<String, SparseArray<ProcessRecord>> all 18344 = mProcessNames.getMap(); 18345 SparseArray<ProcessRecord> procs = all.get(process); 18346 if (procs != null && procs.size() > 0) { 18347 proc = procs.valueAt(0); 18348 if (userId != UserHandle.USER_ALL && proc.userId != userId) { 18349 for (int i=1; i<procs.size(); i++) { 18350 ProcessRecord thisProc = procs.valueAt(i); 18351 if (thisProc.userId == userId) { 18352 proc = thisProc; 18353 break; 18354 } 18355 } 18356 } 18357 } 18358 } 18359 18360 return proc; 18361 } 18362 18363 public boolean dumpHeap(String process, int userId, boolean managed, 18364 String path, ParcelFileDescriptor fd) throws RemoteException { 18365 18366 try { 18367 synchronized (this) { 18368 // note: hijacking SET_ACTIVITY_WATCHER, but should be changed to 18369 // its own permission (same as profileControl). 18370 if (checkCallingPermission(android.Manifest.permission.SET_ACTIVITY_WATCHER) 18371 != PackageManager.PERMISSION_GRANTED) { 18372 throw new SecurityException("Requires permission " 18373 + android.Manifest.permission.SET_ACTIVITY_WATCHER); 18374 } 18375 18376 if (fd == null) { 18377 throw new IllegalArgumentException("null fd"); 18378 } 18379 18380 ProcessRecord proc = findProcessLocked(process, userId, "dumpHeap"); 18381 if (proc == null || proc.thread == null) { 18382 throw new IllegalArgumentException("Unknown process: " + process); 18383 } 18384 18385 boolean isDebuggable = "1".equals(SystemProperties.get(SYSTEM_DEBUGGABLE, "0")); 18386 if (!isDebuggable) { 18387 if ((proc.info.flags&ApplicationInfo.FLAG_DEBUGGABLE) == 0) { 18388 throw new SecurityException("Process not debuggable: " + proc); 18389 } 18390 } 18391 18392 proc.thread.dumpHeap(managed, path, fd); 18393 fd = null; 18394 return true; 18395 } 18396 } catch (RemoteException e) { 18397 throw new IllegalStateException("Process disappeared"); 18398 } finally { 18399 if (fd != null) { 18400 try { 18401 fd.close(); 18402 } catch (IOException e) { 18403 } 18404 } 18405 } 18406 } 18407 18408 /** In this method we try to acquire our lock to make sure that we have not deadlocked */ 18409 public void monitor() { 18410 synchronized (this) { } 18411 } 18412 18413 void onCoreSettingsChange(Bundle settings) { 18414 for (int i = mLruProcesses.size() - 1; i >= 0; i--) { 18415 ProcessRecord processRecord = mLruProcesses.get(i); 18416 try { 18417 if (processRecord.thread != null) { 18418 processRecord.thread.setCoreSettings(settings); 18419 } 18420 } catch (RemoteException re) { 18421 /* ignore */ 18422 } 18423 } 18424 } 18425 18426 // Multi-user methods 18427 18428 /** 18429 * Start user, if its not already running, but don't bring it to foreground. 18430 */ 18431 @Override 18432 public boolean startUserInBackground(final int userId) { 18433 return startUser(userId, /* foreground */ false); 18434 } 18435 18436 /** 18437 * Start user, if its not already running, and bring it to foreground. 18438 */ 18439 boolean startUserInForeground(final int userId, Dialog dlg) { 18440 boolean result = startUser(userId, /* foreground */ true); 18441 dlg.dismiss(); 18442 return result; 18443 } 18444 18445 /** 18446 * Refreshes the list of users related to the current user when either a 18447 * user switch happens or when a new related user is started in the 18448 * background. 18449 */ 18450 private void updateCurrentProfileIdsLocked() { 18451 final List<UserInfo> profiles = getUserManagerLocked().getProfiles( 18452 mCurrentUserId, false /* enabledOnly */); 18453 int[] currentProfileIds = new int[profiles.size()]; // profiles will not be null 18454 for (int i = 0; i < currentProfileIds.length; i++) { 18455 currentProfileIds[i] = profiles.get(i).id; 18456 } 18457 mCurrentProfileIds = currentProfileIds; 18458 18459 synchronized (mUserProfileGroupIdsSelfLocked) { 18460 mUserProfileGroupIdsSelfLocked.clear(); 18461 final List<UserInfo> users = getUserManagerLocked().getUsers(false); 18462 for (int i = 0; i < users.size(); i++) { 18463 UserInfo user = users.get(i); 18464 if (user.profileGroupId != UserInfo.NO_PROFILE_GROUP_ID) { 18465 mUserProfileGroupIdsSelfLocked.put(user.id, user.profileGroupId); 18466 } 18467 } 18468 } 18469 } 18470 18471 private Set getProfileIdsLocked(int userId) { 18472 Set userIds = new HashSet<Integer>(); 18473 final List<UserInfo> profiles = getUserManagerLocked().getProfiles( 18474 userId, false /* enabledOnly */); 18475 for (UserInfo user : profiles) { 18476 userIds.add(Integer.valueOf(user.id)); 18477 } 18478 return userIds; 18479 } 18480 18481 @Override 18482 public boolean switchUser(final int userId) { 18483 enforceShellRestriction(UserManager.DISALLOW_DEBUGGING_FEATURES, userId); 18484 String userName; 18485 synchronized (this) { 18486 UserInfo userInfo = getUserManagerLocked().getUserInfo(userId); 18487 if (userInfo == null) { 18488 Slog.w(TAG, "No user info for user #" + userId); 18489 return false; 18490 } 18491 if (userInfo.isManagedProfile()) { 18492 Slog.w(TAG, "Cannot switch to User #" + userId + ": not a full user"); 18493 return false; 18494 } 18495 userName = userInfo.name; 18496 mTargetUserId = userId; 18497 } 18498 mHandler.removeMessages(START_USER_SWITCH_MSG); 18499 mHandler.sendMessage(mHandler.obtainMessage(START_USER_SWITCH_MSG, userId, 0, userName)); 18500 return true; 18501 } 18502 18503 private void showUserSwitchDialog(int userId, String userName) { 18504 // The dialog will show and then initiate the user switch by calling startUserInForeground 18505 Dialog d = new UserSwitchingDialog(this, mContext, userId, userName, 18506 true /* above system */); 18507 d.show(); 18508 } 18509 18510 private boolean startUser(final int userId, final boolean foreground) { 18511 if (checkCallingPermission(INTERACT_ACROSS_USERS_FULL) 18512 != PackageManager.PERMISSION_GRANTED) { 18513 String msg = "Permission Denial: switchUser() from pid=" 18514 + Binder.getCallingPid() 18515 + ", uid=" + Binder.getCallingUid() 18516 + " requires " + INTERACT_ACROSS_USERS_FULL; 18517 Slog.w(TAG, msg); 18518 throw new SecurityException(msg); 18519 } 18520 18521 if (DEBUG_MU) Slog.i(TAG_MU, "starting userid:" + userId + " fore:" + foreground); 18522 18523 final long ident = Binder.clearCallingIdentity(); 18524 try { 18525 synchronized (this) { 18526 final int oldUserId = mCurrentUserId; 18527 if (oldUserId == userId) { 18528 return true; 18529 } 18530 18531 mStackSupervisor.setLockTaskModeLocked(null, false); 18532 18533 final UserInfo userInfo = getUserManagerLocked().getUserInfo(userId); 18534 if (userInfo == null) { 18535 Slog.w(TAG, "No user info for user #" + userId); 18536 return false; 18537 } 18538 if (foreground && userInfo.isManagedProfile()) { 18539 Slog.w(TAG, "Cannot switch to User #" + userId + ": not a full user"); 18540 return false; 18541 } 18542 18543 if (foreground) { 18544 mWindowManager.startFreezingScreen(R.anim.screen_user_exit, 18545 R.anim.screen_user_enter); 18546 } 18547 18548 boolean needStart = false; 18549 18550 // If the user we are switching to is not currently started, then 18551 // we need to start it now. 18552 if (mStartedUsers.get(userId) == null) { 18553 mStartedUsers.put(userId, new UserStartedState(new UserHandle(userId), false)); 18554 updateStartedUserArrayLocked(); 18555 needStart = true; 18556 } 18557 18558 final Integer userIdInt = Integer.valueOf(userId); 18559 mUserLru.remove(userIdInt); 18560 mUserLru.add(userIdInt); 18561 18562 if (foreground) { 18563 mCurrentUserId = userId; 18564 mTargetUserId = UserHandle.USER_NULL; // reset, mCurrentUserId has caught up 18565 updateCurrentProfileIdsLocked(); 18566 mWindowManager.setCurrentUser(userId, mCurrentProfileIds); 18567 // Once the internal notion of the active user has switched, we lock the device 18568 // with the option to show the user switcher on the keyguard. 18569 mWindowManager.lockNow(null); 18570 } else { 18571 final Integer currentUserIdInt = Integer.valueOf(mCurrentUserId); 18572 updateCurrentProfileIdsLocked(); 18573 mWindowManager.setCurrentProfileIds(mCurrentProfileIds); 18574 mUserLru.remove(currentUserIdInt); 18575 mUserLru.add(currentUserIdInt); 18576 } 18577 18578 final UserStartedState uss = mStartedUsers.get(userId); 18579 18580 // Make sure user is in the started state. If it is currently 18581 // stopping, we need to knock that off. 18582 if (uss.mState == UserStartedState.STATE_STOPPING) { 18583 // If we are stopping, we haven't sent ACTION_SHUTDOWN, 18584 // so we can just fairly silently bring the user back from 18585 // the almost-dead. 18586 uss.mState = UserStartedState.STATE_RUNNING; 18587 updateStartedUserArrayLocked(); 18588 needStart = true; 18589 } else if (uss.mState == UserStartedState.STATE_SHUTDOWN) { 18590 // This means ACTION_SHUTDOWN has been sent, so we will 18591 // need to treat this as a new boot of the user. 18592 uss.mState = UserStartedState.STATE_BOOTING; 18593 updateStartedUserArrayLocked(); 18594 needStart = true; 18595 } 18596 18597 if (uss.mState == UserStartedState.STATE_BOOTING) { 18598 // Booting up a new user, need to tell system services about it. 18599 // Note that this is on the same handler as scheduling of broadcasts, 18600 // which is important because it needs to go first. 18601 mHandler.sendMessage(mHandler.obtainMessage(SYSTEM_USER_START_MSG, userId, 0)); 18602 } 18603 18604 if (foreground) { 18605 mHandler.sendMessage(mHandler.obtainMessage(SYSTEM_USER_CURRENT_MSG, userId, 18606 oldUserId)); 18607 mHandler.removeMessages(REPORT_USER_SWITCH_MSG); 18608 mHandler.removeMessages(USER_SWITCH_TIMEOUT_MSG); 18609 mHandler.sendMessage(mHandler.obtainMessage(REPORT_USER_SWITCH_MSG, 18610 oldUserId, userId, uss)); 18611 mHandler.sendMessageDelayed(mHandler.obtainMessage(USER_SWITCH_TIMEOUT_MSG, 18612 oldUserId, userId, uss), USER_SWITCH_TIMEOUT); 18613 } 18614 18615 if (needStart) { 18616 // Send USER_STARTED broadcast 18617 Intent intent = new Intent(Intent.ACTION_USER_STARTED); 18618 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY 18619 | Intent.FLAG_RECEIVER_FOREGROUND); 18620 intent.putExtra(Intent.EXTRA_USER_HANDLE, userId); 18621 broadcastIntentLocked(null, null, intent, 18622 null, null, 0, null, null, null, AppOpsManager.OP_NONE, 18623 false, false, MY_PID, Process.SYSTEM_UID, userId); 18624 } 18625 18626 if ((userInfo.flags&UserInfo.FLAG_INITIALIZED) == 0) { 18627 if (userId != UserHandle.USER_OWNER) { 18628 Intent intent = new Intent(Intent.ACTION_USER_INITIALIZE); 18629 intent.addFlags(Intent.FLAG_RECEIVER_FOREGROUND); 18630 broadcastIntentLocked(null, null, intent, null, 18631 new IIntentReceiver.Stub() { 18632 public void performReceive(Intent intent, int resultCode, 18633 String data, Bundle extras, boolean ordered, 18634 boolean sticky, int sendingUser) { 18635 onUserInitialized(uss, foreground, oldUserId, userId); 18636 } 18637 }, 0, null, null, null, AppOpsManager.OP_NONE, 18638 true, false, MY_PID, Process.SYSTEM_UID, 18639 userId); 18640 uss.initializing = true; 18641 } else { 18642 getUserManagerLocked().makeInitialized(userInfo.id); 18643 } 18644 } 18645 18646 if (foreground) { 18647 if (!uss.initializing) { 18648 moveUserToForeground(uss, oldUserId, userId); 18649 } 18650 } else { 18651 mStackSupervisor.startBackgroundUserLocked(userId, uss); 18652 } 18653 18654 if (needStart) { 18655 Intent intent = new Intent(Intent.ACTION_USER_STARTING); 18656 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY); 18657 intent.putExtra(Intent.EXTRA_USER_HANDLE, userId); 18658 broadcastIntentLocked(null, null, intent, 18659 null, new IIntentReceiver.Stub() { 18660 @Override 18661 public void performReceive(Intent intent, int resultCode, String data, 18662 Bundle extras, boolean ordered, boolean sticky, int sendingUser) 18663 throws RemoteException { 18664 } 18665 }, 0, null, null, 18666 INTERACT_ACROSS_USERS, AppOpsManager.OP_NONE, 18667 true, false, MY_PID, Process.SYSTEM_UID, UserHandle.USER_ALL); 18668 } 18669 } 18670 } finally { 18671 Binder.restoreCallingIdentity(ident); 18672 } 18673 18674 return true; 18675 } 18676 18677 void sendUserSwitchBroadcastsLocked(int oldUserId, int newUserId) { 18678 long ident = Binder.clearCallingIdentity(); 18679 try { 18680 Intent intent; 18681 if (oldUserId >= 0) { 18682 // Send USER_BACKGROUND broadcast to all profiles of the outgoing user 18683 List<UserInfo> profiles = mUserManager.getProfiles(oldUserId, false); 18684 int count = profiles.size(); 18685 for (int i = 0; i < count; i++) { 18686 int profileUserId = profiles.get(i).id; 18687 intent = new Intent(Intent.ACTION_USER_BACKGROUND); 18688 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY 18689 | Intent.FLAG_RECEIVER_FOREGROUND); 18690 intent.putExtra(Intent.EXTRA_USER_HANDLE, profileUserId); 18691 broadcastIntentLocked(null, null, intent, 18692 null, null, 0, null, null, null, AppOpsManager.OP_NONE, 18693 false, false, MY_PID, Process.SYSTEM_UID, profileUserId); 18694 } 18695 } 18696 if (newUserId >= 0) { 18697 // Send USER_FOREGROUND broadcast to all profiles of the incoming user 18698 List<UserInfo> profiles = mUserManager.getProfiles(newUserId, false); 18699 int count = profiles.size(); 18700 for (int i = 0; i < count; i++) { 18701 int profileUserId = profiles.get(i).id; 18702 intent = new Intent(Intent.ACTION_USER_FOREGROUND); 18703 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY 18704 | Intent.FLAG_RECEIVER_FOREGROUND); 18705 intent.putExtra(Intent.EXTRA_USER_HANDLE, profileUserId); 18706 broadcastIntentLocked(null, null, intent, 18707 null, null, 0, null, null, null, AppOpsManager.OP_NONE, 18708 false, false, MY_PID, Process.SYSTEM_UID, profileUserId); 18709 } 18710 intent = new Intent(Intent.ACTION_USER_SWITCHED); 18711 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY 18712 | Intent.FLAG_RECEIVER_FOREGROUND); 18713 intent.putExtra(Intent.EXTRA_USER_HANDLE, newUserId); 18714 broadcastIntentLocked(null, null, intent, 18715 null, null, 0, null, null, 18716 android.Manifest.permission.MANAGE_USERS, AppOpsManager.OP_NONE, 18717 false, false, MY_PID, Process.SYSTEM_UID, UserHandle.USER_ALL); 18718 } 18719 } finally { 18720 Binder.restoreCallingIdentity(ident); 18721 } 18722 } 18723 18724 void dispatchUserSwitch(final UserStartedState uss, final int oldUserId, 18725 final int newUserId) { 18726 final int N = mUserSwitchObservers.beginBroadcast(); 18727 if (N > 0) { 18728 final IRemoteCallback callback = new IRemoteCallback.Stub() { 18729 int mCount = 0; 18730 @Override 18731 public void sendResult(Bundle data) throws RemoteException { 18732 synchronized (ActivityManagerService.this) { 18733 if (mCurUserSwitchCallback == this) { 18734 mCount++; 18735 if (mCount == N) { 18736 sendContinueUserSwitchLocked(uss, oldUserId, newUserId); 18737 } 18738 } 18739 } 18740 } 18741 }; 18742 synchronized (this) { 18743 uss.switching = true; 18744 mCurUserSwitchCallback = callback; 18745 } 18746 for (int i=0; i<N; i++) { 18747 try { 18748 mUserSwitchObservers.getBroadcastItem(i).onUserSwitching( 18749 newUserId, callback); 18750 } catch (RemoteException e) { 18751 } 18752 } 18753 } else { 18754 synchronized (this) { 18755 sendContinueUserSwitchLocked(uss, oldUserId, newUserId); 18756 } 18757 } 18758 mUserSwitchObservers.finishBroadcast(); 18759 } 18760 18761 void timeoutUserSwitch(UserStartedState uss, int oldUserId, int newUserId) { 18762 synchronized (this) { 18763 Slog.w(TAG, "User switch timeout: from " + oldUserId + " to " + newUserId); 18764 sendContinueUserSwitchLocked(uss, oldUserId, newUserId); 18765 } 18766 } 18767 18768 void sendContinueUserSwitchLocked(UserStartedState uss, int oldUserId, int newUserId) { 18769 mCurUserSwitchCallback = null; 18770 mHandler.removeMessages(USER_SWITCH_TIMEOUT_MSG); 18771 mHandler.sendMessage(mHandler.obtainMessage(CONTINUE_USER_SWITCH_MSG, 18772 oldUserId, newUserId, uss)); 18773 } 18774 18775 void onUserInitialized(UserStartedState uss, boolean foreground, int oldUserId, int newUserId) { 18776 synchronized (this) { 18777 if (foreground) { 18778 moveUserToForeground(uss, oldUserId, newUserId); 18779 } 18780 } 18781 18782 completeSwitchAndInitalize(uss, newUserId, true, false); 18783 } 18784 18785 void moveUserToForeground(UserStartedState uss, int oldUserId, int newUserId) { 18786 boolean homeInFront = mStackSupervisor.switchUserLocked(newUserId, uss); 18787 if (homeInFront) { 18788 startHomeActivityLocked(newUserId); 18789 } else { 18790 mStackSupervisor.resumeTopActivitiesLocked(); 18791 } 18792 EventLogTags.writeAmSwitchUser(newUserId); 18793 getUserManagerLocked().userForeground(newUserId); 18794 sendUserSwitchBroadcastsLocked(oldUserId, newUserId); 18795 } 18796 18797 void continueUserSwitch(UserStartedState uss, int oldUserId, int newUserId) { 18798 completeSwitchAndInitalize(uss, newUserId, false, true); 18799 } 18800 18801 void completeSwitchAndInitalize(UserStartedState uss, int newUserId, 18802 boolean clearInitializing, boolean clearSwitching) { 18803 boolean unfrozen = false; 18804 synchronized (this) { 18805 if (clearInitializing) { 18806 uss.initializing = false; 18807 getUserManagerLocked().makeInitialized(uss.mHandle.getIdentifier()); 18808 } 18809 if (clearSwitching) { 18810 uss.switching = false; 18811 } 18812 if (!uss.switching && !uss.initializing) { 18813 mWindowManager.stopFreezingScreen(); 18814 unfrozen = true; 18815 } 18816 } 18817 if (unfrozen) { 18818 final int N = mUserSwitchObservers.beginBroadcast(); 18819 for (int i=0; i<N; i++) { 18820 try { 18821 mUserSwitchObservers.getBroadcastItem(i).onUserSwitchComplete(newUserId); 18822 } catch (RemoteException e) { 18823 } 18824 } 18825 mUserSwitchObservers.finishBroadcast(); 18826 } 18827 } 18828 18829 void scheduleStartProfilesLocked() { 18830 if (!mHandler.hasMessages(START_PROFILES_MSG)) { 18831 mHandler.sendMessageDelayed(mHandler.obtainMessage(START_PROFILES_MSG), 18832 DateUtils.SECOND_IN_MILLIS); 18833 } 18834 } 18835 18836 void startProfilesLocked() { 18837 if (DEBUG_MU) Slog.i(TAG_MU, "startProfilesLocked"); 18838 List<UserInfo> profiles = getUserManagerLocked().getProfiles( 18839 mCurrentUserId, false /* enabledOnly */); 18840 List<UserInfo> toStart = new ArrayList<UserInfo>(profiles.size()); 18841 for (UserInfo user : profiles) { 18842 if ((user.flags & UserInfo.FLAG_INITIALIZED) == UserInfo.FLAG_INITIALIZED 18843 && user.id != mCurrentUserId) { 18844 toStart.add(user); 18845 } 18846 } 18847 final int n = toStart.size(); 18848 int i = 0; 18849 for (; i < n && i < (MAX_RUNNING_USERS - 1); ++i) { 18850 startUserInBackground(toStart.get(i).id); 18851 } 18852 if (i < n) { 18853 Slog.w(TAG_MU, "More profiles than MAX_RUNNING_USERS"); 18854 } 18855 } 18856 18857 void finishUserBoot(UserStartedState uss) { 18858 synchronized (this) { 18859 if (uss.mState == UserStartedState.STATE_BOOTING 18860 && mStartedUsers.get(uss.mHandle.getIdentifier()) == uss) { 18861 uss.mState = UserStartedState.STATE_RUNNING; 18862 final int userId = uss.mHandle.getIdentifier(); 18863 Intent intent = new Intent(Intent.ACTION_BOOT_COMPLETED, null); 18864 intent.putExtra(Intent.EXTRA_USER_HANDLE, userId); 18865 intent.addFlags(Intent.FLAG_RECEIVER_NO_ABORT); 18866 broadcastIntentLocked(null, null, intent, 18867 null, null, 0, null, null, 18868 android.Manifest.permission.RECEIVE_BOOT_COMPLETED, AppOpsManager.OP_NONE, 18869 true, false, MY_PID, Process.SYSTEM_UID, userId); 18870 } 18871 } 18872 } 18873 18874 void finishUserSwitch(UserStartedState uss) { 18875 synchronized (this) { 18876 finishUserBoot(uss); 18877 18878 startProfilesLocked(); 18879 18880 int num = mUserLru.size(); 18881 int i = 0; 18882 while (num > MAX_RUNNING_USERS && i < mUserLru.size()) { 18883 Integer oldUserId = mUserLru.get(i); 18884 UserStartedState oldUss = mStartedUsers.get(oldUserId); 18885 if (oldUss == null) { 18886 // Shouldn't happen, but be sane if it does. 18887 mUserLru.remove(i); 18888 num--; 18889 continue; 18890 } 18891 if (oldUss.mState == UserStartedState.STATE_STOPPING 18892 || oldUss.mState == UserStartedState.STATE_SHUTDOWN) { 18893 // This user is already stopping, doesn't count. 18894 num--; 18895 i++; 18896 continue; 18897 } 18898 if (oldUserId == UserHandle.USER_OWNER || oldUserId == mCurrentUserId) { 18899 // Owner and current can't be stopped, but count as running. 18900 i++; 18901 continue; 18902 } 18903 // This is a user to be stopped. 18904 stopUserLocked(oldUserId, null); 18905 num--; 18906 i++; 18907 } 18908 } 18909 } 18910 18911 @Override 18912 public int stopUser(final int userId, final IStopUserCallback callback) { 18913 if (checkCallingPermission(INTERACT_ACROSS_USERS_FULL) 18914 != PackageManager.PERMISSION_GRANTED) { 18915 String msg = "Permission Denial: switchUser() from pid=" 18916 + Binder.getCallingPid() 18917 + ", uid=" + Binder.getCallingUid() 18918 + " requires " + INTERACT_ACROSS_USERS_FULL; 18919 Slog.w(TAG, msg); 18920 throw new SecurityException(msg); 18921 } 18922 if (userId <= 0) { 18923 throw new IllegalArgumentException("Can't stop primary user " + userId); 18924 } 18925 enforceShellRestriction(UserManager.DISALLOW_DEBUGGING_FEATURES, userId); 18926 synchronized (this) { 18927 return stopUserLocked(userId, callback); 18928 } 18929 } 18930 18931 private int stopUserLocked(final int userId, final IStopUserCallback callback) { 18932 if (DEBUG_MU) Slog.i(TAG_MU, "stopUserLocked userId=" + userId); 18933 if (mCurrentUserId == userId && mTargetUserId == UserHandle.USER_NULL) { 18934 return ActivityManager.USER_OP_IS_CURRENT; 18935 } 18936 18937 final UserStartedState uss = mStartedUsers.get(userId); 18938 if (uss == null) { 18939 // User is not started, nothing to do... but we do need to 18940 // callback if requested. 18941 if (callback != null) { 18942 mHandler.post(new Runnable() { 18943 @Override 18944 public void run() { 18945 try { 18946 callback.userStopped(userId); 18947 } catch (RemoteException e) { 18948 } 18949 } 18950 }); 18951 } 18952 return ActivityManager.USER_OP_SUCCESS; 18953 } 18954 18955 if (callback != null) { 18956 uss.mStopCallbacks.add(callback); 18957 } 18958 18959 if (uss.mState != UserStartedState.STATE_STOPPING 18960 && uss.mState != UserStartedState.STATE_SHUTDOWN) { 18961 uss.mState = UserStartedState.STATE_STOPPING; 18962 updateStartedUserArrayLocked(); 18963 18964 long ident = Binder.clearCallingIdentity(); 18965 try { 18966 // We are going to broadcast ACTION_USER_STOPPING and then 18967 // once that is done send a final ACTION_SHUTDOWN and then 18968 // stop the user. 18969 final Intent stoppingIntent = new Intent(Intent.ACTION_USER_STOPPING); 18970 stoppingIntent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY); 18971 stoppingIntent.putExtra(Intent.EXTRA_USER_HANDLE, userId); 18972 stoppingIntent.putExtra(Intent.EXTRA_SHUTDOWN_USERSPACE_ONLY, true); 18973 final Intent shutdownIntent = new Intent(Intent.ACTION_SHUTDOWN); 18974 // This is the result receiver for the final shutdown broadcast. 18975 final IIntentReceiver shutdownReceiver = new IIntentReceiver.Stub() { 18976 @Override 18977 public void performReceive(Intent intent, int resultCode, String data, 18978 Bundle extras, boolean ordered, boolean sticky, int sendingUser) { 18979 finishUserStop(uss); 18980 } 18981 }; 18982 // This is the result receiver for the initial stopping broadcast. 18983 final IIntentReceiver stoppingReceiver = new IIntentReceiver.Stub() { 18984 @Override 18985 public void performReceive(Intent intent, int resultCode, String data, 18986 Bundle extras, boolean ordered, boolean sticky, int sendingUser) { 18987 // On to the next. 18988 synchronized (ActivityManagerService.this) { 18989 if (uss.mState != UserStartedState.STATE_STOPPING) { 18990 // Whoops, we are being started back up. Abort, abort! 18991 return; 18992 } 18993 uss.mState = UserStartedState.STATE_SHUTDOWN; 18994 } 18995 mBatteryStatsService.noteEvent( 18996 BatteryStats.HistoryItem.EVENT_USER_RUNNING_FINISH, 18997 Integer.toString(userId), userId); 18998 mSystemServiceManager.stopUser(userId); 18999 broadcastIntentLocked(null, null, shutdownIntent, 19000 null, shutdownReceiver, 0, null, null, null, AppOpsManager.OP_NONE, 19001 true, false, MY_PID, Process.SYSTEM_UID, userId); 19002 } 19003 }; 19004 // Kick things off. 19005 broadcastIntentLocked(null, null, stoppingIntent, 19006 null, stoppingReceiver, 0, null, null, 19007 INTERACT_ACROSS_USERS, AppOpsManager.OP_NONE, 19008 true, false, MY_PID, Process.SYSTEM_UID, UserHandle.USER_ALL); 19009 } finally { 19010 Binder.restoreCallingIdentity(ident); 19011 } 19012 } 19013 19014 return ActivityManager.USER_OP_SUCCESS; 19015 } 19016 19017 void finishUserStop(UserStartedState uss) { 19018 final int userId = uss.mHandle.getIdentifier(); 19019 boolean stopped; 19020 ArrayList<IStopUserCallback> callbacks; 19021 synchronized (this) { 19022 callbacks = new ArrayList<IStopUserCallback>(uss.mStopCallbacks); 19023 if (mStartedUsers.get(userId) != uss) { 19024 stopped = false; 19025 } else if (uss.mState != UserStartedState.STATE_SHUTDOWN) { 19026 stopped = false; 19027 } else { 19028 stopped = true; 19029 // User can no longer run. 19030 mStartedUsers.remove(userId); 19031 mUserLru.remove(Integer.valueOf(userId)); 19032 updateStartedUserArrayLocked(); 19033 19034 // Clean up all state and processes associated with the user. 19035 // Kill all the processes for the user. 19036 forceStopUserLocked(userId, "finish user"); 19037 } 19038 19039 // Explicitly remove the old information in mRecentTasks. 19040 removeRecentTasksForUserLocked(userId); 19041 } 19042 19043 for (int i=0; i<callbacks.size(); i++) { 19044 try { 19045 if (stopped) callbacks.get(i).userStopped(userId); 19046 else callbacks.get(i).userStopAborted(userId); 19047 } catch (RemoteException e) { 19048 } 19049 } 19050 19051 if (stopped) { 19052 mSystemServiceManager.cleanupUser(userId); 19053 synchronized (this) { 19054 mStackSupervisor.removeUserLocked(userId); 19055 } 19056 } 19057 } 19058 19059 @Override 19060 public UserInfo getCurrentUser() { 19061 if ((checkCallingPermission(INTERACT_ACROSS_USERS) 19062 != PackageManager.PERMISSION_GRANTED) && ( 19063 checkCallingPermission(INTERACT_ACROSS_USERS_FULL) 19064 != PackageManager.PERMISSION_GRANTED)) { 19065 String msg = "Permission Denial: getCurrentUser() from pid=" 19066 + Binder.getCallingPid() 19067 + ", uid=" + Binder.getCallingUid() 19068 + " requires " + INTERACT_ACROSS_USERS; 19069 Slog.w(TAG, msg); 19070 throw new SecurityException(msg); 19071 } 19072 synchronized (this) { 19073 int userId = mTargetUserId != UserHandle.USER_NULL ? mTargetUserId : mCurrentUserId; 19074 return getUserManagerLocked().getUserInfo(userId); 19075 } 19076 } 19077 19078 int getCurrentUserIdLocked() { 19079 return mTargetUserId != UserHandle.USER_NULL ? mTargetUserId : mCurrentUserId; 19080 } 19081 19082 @Override 19083 public boolean isUserRunning(int userId, boolean orStopped) { 19084 if (checkCallingPermission(INTERACT_ACROSS_USERS) 19085 != PackageManager.PERMISSION_GRANTED) { 19086 String msg = "Permission Denial: isUserRunning() from pid=" 19087 + Binder.getCallingPid() 19088 + ", uid=" + Binder.getCallingUid() 19089 + " requires " + INTERACT_ACROSS_USERS; 19090 Slog.w(TAG, msg); 19091 throw new SecurityException(msg); 19092 } 19093 synchronized (this) { 19094 return isUserRunningLocked(userId, orStopped); 19095 } 19096 } 19097 19098 boolean isUserRunningLocked(int userId, boolean orStopped) { 19099 UserStartedState state = mStartedUsers.get(userId); 19100 if (state == null) { 19101 return false; 19102 } 19103 if (orStopped) { 19104 return true; 19105 } 19106 return state.mState != UserStartedState.STATE_STOPPING 19107 && state.mState != UserStartedState.STATE_SHUTDOWN; 19108 } 19109 19110 @Override 19111 public int[] getRunningUserIds() { 19112 if (checkCallingPermission(INTERACT_ACROSS_USERS) 19113 != PackageManager.PERMISSION_GRANTED) { 19114 String msg = "Permission Denial: isUserRunning() from pid=" 19115 + Binder.getCallingPid() 19116 + ", uid=" + Binder.getCallingUid() 19117 + " requires " + INTERACT_ACROSS_USERS; 19118 Slog.w(TAG, msg); 19119 throw new SecurityException(msg); 19120 } 19121 synchronized (this) { 19122 return mStartedUserArray; 19123 } 19124 } 19125 19126 private void updateStartedUserArrayLocked() { 19127 int num = 0; 19128 for (int i=0; i<mStartedUsers.size(); i++) { 19129 UserStartedState uss = mStartedUsers.valueAt(i); 19130 // This list does not include stopping users. 19131 if (uss.mState != UserStartedState.STATE_STOPPING 19132 && uss.mState != UserStartedState.STATE_SHUTDOWN) { 19133 num++; 19134 } 19135 } 19136 mStartedUserArray = new int[num]; 19137 num = 0; 19138 for (int i=0; i<mStartedUsers.size(); i++) { 19139 UserStartedState uss = mStartedUsers.valueAt(i); 19140 if (uss.mState != UserStartedState.STATE_STOPPING 19141 && uss.mState != UserStartedState.STATE_SHUTDOWN) { 19142 mStartedUserArray[num] = mStartedUsers.keyAt(i); 19143 num++; 19144 } 19145 } 19146 } 19147 19148 @Override 19149 public void registerUserSwitchObserver(IUserSwitchObserver observer) { 19150 if (checkCallingPermission(INTERACT_ACROSS_USERS_FULL) 19151 != PackageManager.PERMISSION_GRANTED) { 19152 String msg = "Permission Denial: registerUserSwitchObserver() from pid=" 19153 + Binder.getCallingPid() 19154 + ", uid=" + Binder.getCallingUid() 19155 + " requires " + INTERACT_ACROSS_USERS_FULL; 19156 Slog.w(TAG, msg); 19157 throw new SecurityException(msg); 19158 } 19159 19160 mUserSwitchObservers.register(observer); 19161 } 19162 19163 @Override 19164 public void unregisterUserSwitchObserver(IUserSwitchObserver observer) { 19165 mUserSwitchObservers.unregister(observer); 19166 } 19167 19168 private boolean userExists(int userId) { 19169 if (userId == 0) { 19170 return true; 19171 } 19172 UserManagerService ums = getUserManagerLocked(); 19173 return ums != null ? (ums.getUserInfo(userId) != null) : false; 19174 } 19175 19176 int[] getUsersLocked() { 19177 UserManagerService ums = getUserManagerLocked(); 19178 return ums != null ? ums.getUserIds() : new int[] { 0 }; 19179 } 19180 19181 UserManagerService getUserManagerLocked() { 19182 if (mUserManager == null) { 19183 IBinder b = ServiceManager.getService(Context.USER_SERVICE); 19184 mUserManager = (UserManagerService)IUserManager.Stub.asInterface(b); 19185 } 19186 return mUserManager; 19187 } 19188 19189 private int applyUserId(int uid, int userId) { 19190 return UserHandle.getUid(userId, uid); 19191 } 19192 19193 ApplicationInfo getAppInfoForUser(ApplicationInfo info, int userId) { 19194 if (info == null) return null; 19195 ApplicationInfo newInfo = new ApplicationInfo(info); 19196 newInfo.uid = applyUserId(info.uid, userId); 19197 newInfo.dataDir = USER_DATA_DIR + userId + "/" 19198 + info.packageName; 19199 return newInfo; 19200 } 19201 19202 ActivityInfo getActivityInfoForUser(ActivityInfo aInfo, int userId) { 19203 if (aInfo == null 19204 || (userId < 1 && aInfo.applicationInfo.uid < UserHandle.PER_USER_RANGE)) { 19205 return aInfo; 19206 } 19207 19208 ActivityInfo info = new ActivityInfo(aInfo); 19209 info.applicationInfo = getAppInfoForUser(info.applicationInfo, userId); 19210 return info; 19211 } 19212 19213 private final class LocalService extends ActivityManagerInternal { 19214 @Override 19215 public void goingToSleep() { 19216 ActivityManagerService.this.goingToSleep(); 19217 } 19218 19219 @Override 19220 public void wakingUp() { 19221 ActivityManagerService.this.wakingUp(); 19222 } 19223 19224 @Override 19225 public int startIsolatedProcess(String entryPoint, String[] entryPointArgs, 19226 String processName, String abiOverride, int uid, Runnable crashHandler) { 19227 return ActivityManagerService.this.startIsolatedProcess(entryPoint, entryPointArgs, 19228 processName, abiOverride, uid, crashHandler); 19229 } 19230 } 19231 19232 /** 19233 * An implementation of IAppTask, that allows an app to manage its own tasks via 19234 * {@link android.app.ActivityManager.AppTask}. We keep track of the callingUid to ensure that 19235 * only the process that calls getAppTasks() can call the AppTask methods. 19236 */ 19237 class AppTaskImpl extends IAppTask.Stub { 19238 private int mTaskId; 19239 private int mCallingUid; 19240 19241 public AppTaskImpl(int taskId, int callingUid) { 19242 mTaskId = taskId; 19243 mCallingUid = callingUid; 19244 } 19245 19246 private void checkCaller() { 19247 if (mCallingUid != Binder.getCallingUid()) { 19248 throw new SecurityException("Caller " + mCallingUid 19249 + " does not match caller of getAppTasks(): " + Binder.getCallingUid()); 19250 } 19251 } 19252 19253 @Override 19254 public void finishAndRemoveTask() { 19255 checkCaller(); 19256 19257 synchronized (ActivityManagerService.this) { 19258 long origId = Binder.clearCallingIdentity(); 19259 try { 19260 if (!removeTaskByIdLocked(mTaskId, false)) { 19261 throw new IllegalArgumentException("Unable to find task ID " + mTaskId); 19262 } 19263 } finally { 19264 Binder.restoreCallingIdentity(origId); 19265 } 19266 } 19267 } 19268 19269 @Override 19270 public ActivityManager.RecentTaskInfo getTaskInfo() { 19271 checkCaller(); 19272 19273 synchronized (ActivityManagerService.this) { 19274 long origId = Binder.clearCallingIdentity(); 19275 try { 19276 TaskRecord tr = recentTaskForIdLocked(mTaskId); 19277 if (tr == null) { 19278 throw new IllegalArgumentException("Unable to find task ID " + mTaskId); 19279 } 19280 return createRecentTaskInfoFromTaskRecord(tr); 19281 } finally { 19282 Binder.restoreCallingIdentity(origId); 19283 } 19284 } 19285 } 19286 19287 @Override 19288 public void moveToFront() { 19289 checkCaller(); 19290 19291 final TaskRecord tr; 19292 synchronized (ActivityManagerService.this) { 19293 tr = recentTaskForIdLocked(mTaskId); 19294 if (tr == null) { 19295 throw new IllegalArgumentException("Unable to find task ID " + mTaskId); 19296 } 19297 if (tr.getRootActivity() != null) { 19298 moveTaskToFrontLocked(tr.taskId, 0, null); 19299 return; 19300 } 19301 } 19302 19303 startActivityFromRecentsInner(tr.taskId, null); 19304 } 19305 19306 @Override 19307 public int startActivity(IBinder whoThread, String callingPackage, 19308 Intent intent, String resolvedType, Bundle options) { 19309 checkCaller(); 19310 19311 int callingUser = UserHandle.getCallingUserId(); 19312 TaskRecord tr; 19313 IApplicationThread appThread; 19314 synchronized (ActivityManagerService.this) { 19315 tr = recentTaskForIdLocked(mTaskId); 19316 if (tr == null) { 19317 throw new IllegalArgumentException("Unable to find task ID " + mTaskId); 19318 } 19319 appThread = ApplicationThreadNative.asInterface(whoThread); 19320 if (appThread == null) { 19321 throw new IllegalArgumentException("Bad app thread " + appThread); 19322 } 19323 } 19324 return mStackSupervisor.startActivityMayWait(appThread, -1, callingPackage, intent, 19325 resolvedType, null, null, null, null, 0, 0, null, null, 19326 null, options, callingUser, null, tr); 19327 } 19328 19329 @Override 19330 public void setExcludeFromRecents(boolean exclude) { 19331 checkCaller(); 19332 19333 synchronized (ActivityManagerService.this) { 19334 long origId = Binder.clearCallingIdentity(); 19335 try { 19336 TaskRecord tr = recentTaskForIdLocked(mTaskId); 19337 if (tr == null) { 19338 throw new IllegalArgumentException("Unable to find task ID " + mTaskId); 19339 } 19340 Intent intent = tr.getBaseIntent(); 19341 if (exclude) { 19342 intent.addFlags(Intent.FLAG_ACTIVITY_EXCLUDE_FROM_RECENTS); 19343 } else { 19344 intent.setFlags(intent.getFlags() 19345 & ~Intent.FLAG_ACTIVITY_EXCLUDE_FROM_RECENTS); 19346 } 19347 } finally { 19348 Binder.restoreCallingIdentity(origId); 19349 } 19350 } 19351 } 19352 } 19353} 19354